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 /* 23 * Copyright (c) 1994, 2010, Oracle and/or its affiliates. All rights reserved. 24 */ 25 26 #include <sys/note.h> 27 28 /* 29 * Generic SCSI Host Bus Adapter interface implementation 30 */ 31 #include <sys/scsi/scsi.h> 32 #include <sys/scsi/generic/sas.h> 33 #include <sys/file.h> 34 #include <sys/disp.h> /* for minclsyspri */ 35 #include <sys/ddi_impldefs.h> 36 #include <sys/ndi_impldefs.h> 37 #include <sys/sunndi.h> 38 #include <sys/ddi.h> 39 #include <sys/sunmdi.h> 40 #include <sys/mdi_impldefs.h> 41 #include <sys/callb.h> 42 #include <sys/epm.h> 43 #include <sys/damap.h> 44 #include <sys/time.h> 45 #include <sys/sunldi.h> 46 #include <sys/fm/protocol.h> 47 48 extern struct scsi_pkt *scsi_init_cache_pkt(struct scsi_address *, 49 struct scsi_pkt *, struct buf *, int, int, int, int, 50 int (*)(caddr_t), caddr_t); 51 extern void scsi_free_cache_pkt(struct scsi_address *, struct scsi_pkt *); 52 extern void scsi_cache_dmafree(struct scsi_address *, struct scsi_pkt *); 53 extern void scsi_sync_cache_pkt(struct scsi_address *, struct scsi_pkt *); 54 extern int modrootloaded; 55 56 /* 57 * Round up all allocations so that we can guarantee 58 * long-long alignment. This is the same alignment 59 * provided by kmem_alloc(). 60 */ 61 #define ROUNDUP(x) (((x) + 0x07) & ~0x07) 62 63 /* Magic number to track correct allocations in wrappers */ 64 #define PKT_WRAPPER_MAGIC 0xa110ced /* alloced correctly */ 65 66 kmutex_t scsi_flag_nointr_mutex; 67 kcondvar_t scsi_flag_nointr_cv; 68 kmutex_t scsi_log_mutex; 69 70 /* asynchronous probe barrier deletion data structures */ 71 static kmutex_t scsi_hba_barrier_mutex; 72 static kcondvar_t scsi_hba_barrier_cv; 73 static struct scsi_hba_barrier { 74 struct scsi_hba_barrier *barrier_next; 75 clock_t barrier_endtime; 76 dev_info_t *barrier_probe; 77 } *scsi_hba_barrier_list; 78 static int scsi_hba_devi_is_barrier(dev_info_t *probe); 79 static void scsi_hba_barrier_tran_tgt_free(dev_info_t *probe); 80 static void scsi_hba_barrier_add(dev_info_t *probe, int seconds); 81 static int scsi_hba_remove_node(dev_info_t *child); 82 static void scsi_hba_barrier_daemon(void *arg); 83 84 /* LUN-change ASC/ASCQ processing data structures (stage1 and stage2) */ 85 static kmutex_t scsi_lunchg1_mutex; 86 static kcondvar_t scsi_lunchg1_cv; 87 static struct scsi_pkt *scsi_lunchg1_list; 88 static void scsi_lunchg1_daemon(void *arg); 89 static kmutex_t scsi_lunchg2_mutex; 90 static kcondvar_t scsi_lunchg2_cv; 91 static struct scsi_lunchg2 { 92 struct scsi_lunchg2 *lunchg2_next; 93 char *lunchg2_path; 94 } *scsi_lunchg2_list; 95 static void scsi_lunchg2_daemon(void *arg); 96 97 static int scsi_findchild(dev_info_t *self, char *name, char *addr, 98 int init, dev_info_t **dchildp, mdi_pathinfo_t **pchildp, int *ppi); 99 100 /* return value defines for scsi_findchild */ 101 #define CHILD_TYPE_NONE 0 102 #define CHILD_TYPE_DEVINFO 1 103 #define CHILD_TYPE_PATHINFO 2 104 105 /* 106 * Enumeration code path currently being followed. SE_BUSCONFIG results in 107 * DEVI_SID_NODEID, and SE_HP (hotplug) results in DEVI_SID_HP_NODEID. 108 * 109 * Since hotplug enumeration is based on information obtained from hardware 110 * (tgtmap/report_lun) the type/severity of enumeration error messages is 111 * sometimes based SE_HP (indirectly via ndi_dev_is_hotplug_node()). By 112 * convention, these messages are all produced by scsi_enumeration_failed(). 113 */ 114 typedef enum { SE_BUSCONFIG = 0, SE_HP = 1 } scsi_enum_t; 115 116 /* compatible properties of driver to use during probe/enumeration operations */ 117 static char *compatible_probe = "scsa,probe"; 118 static char *compatible_nodev = "scsa,nodev"; 119 static char *scsi_probe_ascii[] = SCSIPROBE_ASCII; 120 121 /* number of LUNs we attempt to get on the first SCMD_REPORT_LUNS command */ 122 int scsi_lunrpt_default_max = 256; 123 int scsi_lunrpt_timeout = 3; /* seconds */ 124 125 /* 126 * Only enumerate one lun if reportluns fails on a SCSI_VERSION_3 device 127 * (tunable based on calling context). 128 */ 129 int scsi_lunrpt_failed_do1lun = (1 << SE_HP); 130 131 /* 'scsi-binding-set' value for legacy enumerated 'spi' transports */ 132 char *scsi_binding_set_spi = "spi"; 133 134 /* enable NDI_DEVI_DEBUG for bus_[un]config operations */ 135 int scsi_hba_bus_config_debug = 0; 136 137 /* DEBUG: enable NDI_DEVI_REMOVE for bus_unconfig of dynamic node */ 138 int scsi_hba_bus_unconfig_remove = 0; 139 140 /* number of probe serilization messages */ 141 int scsi_hba_wait_msg = 5; 142 143 /* 144 * Establish the timeout used to cache (in the probe node) the fact that the 145 * device does not exist. This replaces the target specific probe cache. 146 */ 147 int scsi_hba_barrier_timeout = (60); /* seconds */ 148 149 #ifdef DEBUG 150 int scsi_hba_bus_config_failure_msg = 0; 151 int scsi_hba_bus_config_failure_dbg = 0; 152 int scsi_hba_bus_config_success_msg = 0; 153 int scsi_hba_bus_config_success_dbg = 0; 154 #endif /* DEBUG */ 155 156 /* 157 * Structure for scsi_hba_iportmap_* implementation/wrap. 158 */ 159 typedef struct impl_scsi_iportmap { 160 dev_info_t *iportmap_hba_dip; 161 damap_t *iportmap_dam; 162 int iportmap_create_window; 163 uint64_t iportmap_create_time; /* clock64_t */ 164 int iportmap_create_csync_usec; 165 int iportmap_settle_usec; 166 int iportmap_sync_cnt; 167 } impl_scsi_iportmap_t; 168 169 /* 170 * Structure for scsi_hba_tgtmap_* implementation/wrap. 171 * 172 * Every call to scsi_hba_tgtmap_set_begin will increment tgtmap_reports, 173 * and a call to scsi_hba_tgtmap_set_end will reset tgtmap_reports to zero. 174 * If, in scsi_hba_tgtmap_set_begin, we detect a tgtmap_reports value of 175 * scsi_hba_tgtmap_reports_max we produce a message to indicate that 176 * the caller is never completing an observation (i.e. we are not making 177 * any forward progress). If this message occurs, it indicates that the 178 * solaris hotplug ramifications at the target and lun level are no longer 179 * tracking. 180 * 181 * NOTE: LUNMAPSIZE OK for now, but should be dynamic in reportlun code. 182 */ 183 typedef struct impl_scsi_tgtmap { 184 scsi_hba_tran_t *tgtmap_tran; 185 int tgtmap_reports; /* _begin, no _end */ 186 int tgtmap_noisy; 187 scsi_tgt_activate_cb_t tgtmap_activate_cb; 188 scsi_tgt_deactivate_cb_t tgtmap_deactivate_cb; 189 void *tgtmap_mappriv; 190 damap_t *tgtmap_dam[SCSI_TGT_NTYPES]; 191 int tgtmap_create_window; 192 uint64_t tgtmap_create_time; /* clock64_t */ 193 int tgtmap_create_csync_usec; 194 int tgtmap_settle_usec; 195 int tgtmap_sync_cnt; 196 } impl_scsi_tgtmap_t; 197 #define LUNMAPSIZE 256 /* 256 LUNs/target */ 198 199 /* Produce warning if number of begins without an end exceed this value */ 200 int scsi_hba_tgtmap_reports_max = 256; 201 202 static int scsi_tgtmap_sync(scsi_hba_tgtmap_t *, int); 203 204 /* Default settle_usec damap_sync factor */ 205 int scsi_hba_map_settle_f = 10; 206 207 208 /* Prototype for static dev_ops devo_*() functions */ 209 static int scsi_hba_info( 210 dev_info_t *self, 211 ddi_info_cmd_t infocmd, 212 void *arg, 213 void **result); 214 215 /* Prototypes for static bus_ops bus_*() functions */ 216 static int scsi_hba_bus_ctl( 217 dev_info_t *self, 218 dev_info_t *child, 219 ddi_ctl_enum_t op, 220 void *arg, 221 void *result); 222 223 static int scsi_hba_map_fault( 224 dev_info_t *self, 225 dev_info_t *child, 226 struct hat *hat, 227 struct seg *seg, 228 caddr_t addr, 229 struct devpage *dp, 230 pfn_t pfn, 231 uint_t prot, 232 uint_t lock); 233 234 static int scsi_hba_get_eventcookie( 235 dev_info_t *self, 236 dev_info_t *child, 237 char *name, 238 ddi_eventcookie_t *eventp); 239 240 static int scsi_hba_add_eventcall( 241 dev_info_t *self, 242 dev_info_t *child, 243 ddi_eventcookie_t event, 244 void (*callback)( 245 dev_info_t *dip, 246 ddi_eventcookie_t event, 247 void *arg, 248 void *bus_impldata), 249 void *arg, 250 ddi_callback_id_t *cb_id); 251 252 static int scsi_hba_remove_eventcall( 253 dev_info_t *self, 254 ddi_callback_id_t id); 255 256 static int scsi_hba_post_event( 257 dev_info_t *self, 258 dev_info_t *child, 259 ddi_eventcookie_t event, 260 void *bus_impldata); 261 262 static int scsi_hba_bus_config( 263 dev_info_t *self, 264 uint_t flags, 265 ddi_bus_config_op_t op, 266 void *arg, 267 dev_info_t **childp); 268 269 static int scsi_hba_bus_unconfig( 270 dev_info_t *self, 271 uint_t flags, 272 ddi_bus_config_op_t op, 273 void *arg); 274 275 static int scsi_hba_fm_init_child( 276 dev_info_t *self, 277 dev_info_t *child, 278 int cap, 279 ddi_iblock_cookie_t *ibc); 280 281 static int scsi_hba_bus_power( 282 dev_info_t *self, 283 void *impl_arg, 284 pm_bus_power_op_t op, 285 void *arg, 286 void *result); 287 288 /* bus_ops vector for SCSI HBA's. */ 289 static struct bus_ops scsi_hba_busops = { 290 BUSO_REV, 291 nullbusmap, /* bus_map */ 292 NULL, /* bus_get_intrspec */ 293 NULL, /* bus_add_intrspec */ 294 NULL, /* bus_remove_intrspec */ 295 scsi_hba_map_fault, /* bus_map_fault */ 296 ddi_dma_map, /* bus_dma_map */ 297 ddi_dma_allochdl, /* bus_dma_allochdl */ 298 ddi_dma_freehdl, /* bus_dma_freehdl */ 299 ddi_dma_bindhdl, /* bus_dma_bindhdl */ 300 ddi_dma_unbindhdl, /* bus_unbindhdl */ 301 ddi_dma_flush, /* bus_dma_flush */ 302 ddi_dma_win, /* bus_dma_win */ 303 ddi_dma_mctl, /* bus_dma_ctl */ 304 scsi_hba_bus_ctl, /* bus_ctl */ 305 ddi_bus_prop_op, /* bus_prop_op */ 306 scsi_hba_get_eventcookie, /* bus_get_eventcookie */ 307 scsi_hba_add_eventcall, /* bus_add_eventcall */ 308 scsi_hba_remove_eventcall, /* bus_remove_eventcall */ 309 scsi_hba_post_event, /* bus_post_event */ 310 NULL, /* bus_intr_ctl */ 311 scsi_hba_bus_config, /* bus_config */ 312 scsi_hba_bus_unconfig, /* bus_unconfig */ 313 scsi_hba_fm_init_child, /* bus_fm_init */ 314 NULL, /* bus_fm_fini */ 315 NULL, /* bus_fm_access_enter */ 316 NULL, /* bus_fm_access_exit */ 317 scsi_hba_bus_power /* bus_power */ 318 }; 319 320 /* cb_ops for hotplug :devctl and :scsi support */ 321 static struct cb_ops scsi_hba_cbops = { 322 scsi_hba_open, 323 scsi_hba_close, 324 nodev, /* strategy */ 325 nodev, /* print */ 326 nodev, /* dump */ 327 nodev, /* read */ 328 nodev, /* write */ 329 scsi_hba_ioctl, /* ioctl */ 330 nodev, /* devmap */ 331 nodev, /* mmap */ 332 nodev, /* segmap */ 333 nochpoll, /* poll */ 334 ddi_prop_op, /* prop_op */ 335 NULL, /* stream */ 336 D_NEW|D_MP|D_HOTPLUG, /* cb_flag */ 337 CB_REV, /* rev */ 338 nodev, /* int (*cb_aread)() */ 339 nodev /* int (*cb_awrite)() */ 340 }; 341 342 /* Prototypes for static scsi_hba.c/SCSA private lunmap interfaces */ 343 static int scsi_lunmap_create( 344 dev_info_t *self, 345 impl_scsi_tgtmap_t *tgtmap, 346 char *tgt_addr); 347 static void scsi_lunmap_destroy( 348 dev_info_t *self, 349 impl_scsi_tgtmap_t *tgtmap, 350 char *tgt_addr); 351 static void scsi_lunmap_set_begin( 352 dev_info_t *self, 353 damap_t *lundam); 354 static int scsi_lunmap_set_add( 355 dev_info_t *self, 356 damap_t *lundam, 357 char *taddr, 358 scsi_lun64_t lun_num, 359 int lun_sfunc); 360 static void scsi_lunmap_set_end( 361 dev_info_t *self, 362 damap_t *lundam); 363 364 /* Prototypes for static misc. scsi_hba.c private bus_config interfaces */ 365 static int scsi_hba_bus_config_iports(dev_info_t *self, uint_t flags, 366 ddi_bus_config_op_t op, void *arg, dev_info_t **childp); 367 static int scsi_hba_bus_config_spi(dev_info_t *self, uint_t flags, 368 ddi_bus_config_op_t op, void *arg, dev_info_t **childp); 369 static dev_info_t *scsi_hba_bus_config_port(dev_info_t *self, 370 char *nameaddr, scsi_enum_t se); 371 372 #ifdef sparc 373 static int scsi_hba_bus_config_prom_node(dev_info_t *self, uint_t flags, 374 void *arg, dev_info_t **childp); 375 #endif /* sparc */ 376 377 378 /* 379 * SCSI_HBA_LOG is used for all messages. A logging level is specified when 380 * generating a message. Some levels correspond directly to cmn_err levels, 381 * some are associated with increasing levels diagnostic/debug output (LOG1-4), 382 * and others are associated with specific levels of interface (LOGMAP). 383 * For _LOG() messages, a __func__ prefix will identify the function origin 384 * of the message. For _LOG_NF messages, there is no function prefix or 385 * self/child context. Filtering of messages is provided based on logging 386 * level, but messages with cmn_err logging level and messages generated 387 * generated with _LOG_NF() are never filtered. 388 * 389 * For debugging, more complete information can be displayed with each message 390 * (full device path and pointer values) by adjusting scsi_hba_log_info. 391 */ 392 /* logging levels */ 393 #define SCSI_HBA_LOGCONT CE_CONT 394 #define SCSI_HBA_LOGNOTE CE_NOTE 395 #define SCSI_HBA_LOGWARN CE_WARN 396 #define SCSI_HBA_LOGPANIC CE_PANIC 397 #define SCSI_HBA_LOGIGNORE CE_IGNORE 398 #define SCSI_HBA_LOG_CE_MASK 0x0000000F /* no filter for these levels */ 399 #define SCSI_HBA_LOG1 0x00000010 /* DIAG1 level enable */ 400 #define SCSI_HBA_LOG2 0x00000020 /* DIAG2 level enable */ 401 #define SCSI_HBA_LOG3 0x00000040 /* DIAG3 level enable */ 402 #define SCSI_HBA_LOG4 0x00000080 /* DIAG4 level enable */ 403 #define SCSI_HBA_LOGMAPPHY 0x00000100 /* MAPPHY level enable */ 404 #define SCSI_HBA_LOGMAPIPT 0x00000200 /* MAPIPT level enable */ 405 #define SCSI_HBA_LOGMAPTGT 0x00000400 /* MAPTGT level enable */ 406 #define SCSI_HBA_LOGMAPLUN 0x00000800 /* MAPLUN level enable */ 407 #define SCSI_HBA_LOGMAPCFG 0x00001000 /* MAPCFG level enable */ 408 #define SCSI_HBA_LOGMAPUNCFG 0x00002000 /* MAPUNCFG level enable */ 409 #define SCSI_HBA_LOGTRACE 0x00010000 /* TRACE enable */ 410 #if (CE_CONT | CE_NOTE | CE_WARN | CE_PANIC | CE_IGNORE) > SCSI_HBA_LOG_CE_MASK 411 Error, problem with CE_ definitions 412 #endif 413 414 /* 415 * Tunable log message augmentation and filters: filters do not apply to 416 * SCSI_HBA_LOG_CE_MASK level messages or LOG_NF() messages. 417 * 418 * An example set of /etc/system tunings to simplify debug a SCSA pHCI HBA 419 * driver called "pmcs", including "scsi_vhci" operation, by capturing 420 * log information in the system log might be: 421 * 422 * echo "set scsi:scsi_hba_log_filter_level=0x3ff0" >> /etc/system 423 * echo "set scsi:scsi_hba_log_filter_phci=\"pmcs\"" >> /etc/system 424 * echo "set scsi:scsi_hba_log_filter_vhci=\"scsi_vhci\"" >> /etc/system 425 * 426 * To capture information on just HBA-SCSAv3 *map operation, use 427 * echo "set scsi:scsi_hba_log_filter_level=0x3f10" >> /etc/system 428 * 429 * For debugging an HBA driver, you may also want to set: 430 * 431 * echo "set scsi:scsi_hba_log_align=1" >> /etc/system 432 * echo "set scsi:scsi_hba_log_mt_disable=0x6" >> /etc/system 433 * echo "set mtc_off=1" >> /etc/system 434 * echo "set mdi_mtc_off=1" >> /etc/system 435 * echo "set scsi:scsi_hba_log_fcif=0" >> /etc/system 436 */ 437 int scsi_hba_log_filter_level = 438 SCSI_HBA_LOG1 | 439 0; 440 char *scsi_hba_log_filter_phci = "\0\0\0\0\0\0\0\0\0\0\0\0"; 441 char *scsi_hba_log_filter_vhci = "\0\0\0\0\0\0\0\0\0\0\0\0"; 442 int scsi_hba_log_align = 0; /* NOTE: will not cause truncation */ 443 int scsi_hba_log_fcif = '!'; /* "^!?" first char in format */ 444 /* NOTE: iff level > SCSI_HBA_LOG1 */ 445 /* '\0'0x00 -> console and system log */ 446 /* '^' 0x5e -> console_only */ 447 /* '!' 0x21 -> system log only */ 448 /* '?' 0x2F -> See cmn_err(9F) */ 449 int scsi_hba_log_info = /* augmentation: extra info output */ 450 (0 << 0) | /* 0x0001: process information */ 451 (0 << 1) | /* 0x0002: full /devices path */ 452 (0 << 2); /* 0x0004: devinfo pointer */ 453 454 int scsi_hba_log_mt_disable = 455 /* SCSI_ENUMERATION_MT_LUN_DISABLE | (ie 0x02) */ 456 /* SCSI_ENUMERATION_MT_TARGET_DISABLE | (ie 0x04) */ 457 0; 458 459 /* static data for HBA logging subsystem */ 460 static kmutex_t scsi_hba_log_mutex; 461 static char scsi_hba_log_i[512]; 462 static char scsi_hba_log_buf[512]; 463 static char scsi_hba_fmt[512]; 464 465 /* Macros to use in scsi_hba.c source code below */ 466 #define SCSI_HBA_LOG(x) scsi_hba_log x 467 #define _LOG(level) SCSI_HBA_LOG##level, __func__ 468 #define _MAP(map) SCSI_HBA_LOGMAP##map, __func__ 469 #define _LOG_NF(level) SCSI_HBA_LOG##level, NULL, NULL, NULL 470 #define _LOG_TRACE _LOG(TRACE) 471 #define _LOGLUN _MAP(LUN) 472 #define _LOGTGT _MAP(TGT) 473 #define _LOGIPT _MAP(IPT) 474 #define _LOGPHY _MAP(PHY) 475 #define _LOGCFG _MAP(CFG) 476 #define _LOGUNCFG _MAP(UNCFG) 477 478 /*PRINTFLIKE5*/ 479 static void 480 scsi_hba_log(int level, const char *func, dev_info_t *self, dev_info_t *child, 481 const char *fmt, ...) 482 { 483 va_list ap; 484 int clevel; 485 int align; 486 char *info; 487 char *f; 488 char *ua; 489 490 /* derive self from child's parent */ 491 if ((self == NULL) && child) 492 self = ddi_get_parent(child); 493 494 /* no filtering of SCSI_HBA_LOG_CE_MASK or LOG_NF messages */ 495 if (((level & SCSI_HBA_LOG_CE_MASK) != level) && (func != NULL)) { 496 /* scsi_hba_log_filter_level: filter on level as bitmask */ 497 if ((level & scsi_hba_log_filter_level) == 0) 498 return; 499 500 /* scsi_hba_log_filter_phci/vhci: on name of driver */ 501 if (*scsi_hba_log_filter_phci && 502 ((self == NULL) || 503 (ddi_driver_name(self) == NULL) || 504 strcmp(ddi_driver_name(self), scsi_hba_log_filter_phci))) { 505 /* does not match pHCI, check vHCI */ 506 if (*scsi_hba_log_filter_vhci && 507 ((self == NULL) || 508 (ddi_driver_name(self) == NULL) || 509 strcmp(ddi_driver_name(self), 510 scsi_hba_log_filter_vhci))) { 511 /* does not match vHCI */ 512 return; 513 } 514 } 515 516 517 /* passed filters, determine align */ 518 align = scsi_hba_log_align; 519 520 /* shorten func for filtered output */ 521 if (strncmp(func, "scsi_hba_", 9) == 0) 522 func += 9; 523 if (strncmp(func, "scsi_", 5) == 0) 524 func += 5; 525 } else { 526 /* don't align output that is never filtered */ 527 align = 0; 528 } 529 530 /* determine the cmn_err form from the level */ 531 clevel = ((level & SCSI_HBA_LOG_CE_MASK) == level) ? level : CE_CONT; 532 533 /* protect common buffers used to format output */ 534 mutex_enter(&scsi_hba_log_mutex); 535 536 /* skip special first characters, we add them back below */ 537 f = (char *)fmt; 538 if (*f && strchr("^!?", *f)) 539 f++; 540 va_start(ap, fmt); 541 (void) vsprintf(scsi_hba_log_buf, f, ap); 542 va_end(ap); 543 544 /* augment message with 'information' */ 545 info = scsi_hba_log_i; 546 *info = '\0'; 547 if ((scsi_hba_log_info & 0x0001) && curproc && PTOU(curproc)->u_comm) { 548 (void) sprintf(info, "%s[%d]%p ", 549 PTOU(curproc)->u_comm, curproc->p_pid, (void *)curthread); 550 info += strlen(info); 551 } 552 if (self) { 553 if ((scsi_hba_log_info & 0x0004) && (child || self)) { 554 (void) sprintf(info, "%p ", 555 (void *)(child ? child : self)); 556 info += strlen(info); 557 } 558 if (scsi_hba_log_info & 0x0002) { 559 (void) ddi_pathname(child ? child : self, info); 560 (void) strcat(info, " "); 561 info += strlen(info); 562 } 563 564 /* always provide 'default' information about self &child */ 565 (void) sprintf(info, "%s%d ", ddi_driver_name(self), 566 ddi_get_instance(self)); 567 info += strlen(info); 568 if (child) { 569 ua = ddi_get_name_addr(child); 570 (void) sprintf(info, "%s@%s ", 571 ddi_node_name(child), (ua && *ua) ? ua : ""); 572 info += strlen(info); 573 } 574 } 575 576 /* turn off alignment if truncation would occur */ 577 if (align && ((strlen(func) > 18) || (strlen(scsi_hba_log_i) > 36))) 578 align = 0; 579 580 /* adjust for aligned output */ 581 if (align) { 582 if (func == NULL) 583 func = ""; 584 /* remove trailing blank with align output */ 585 if ((info != scsi_hba_log_i) && (*(info -1) == '\b')) 586 *(info - 1) = '\0'; 587 } 588 589 /* special "first character in format" must be in format itself */ 590 f = scsi_hba_fmt; 591 if (fmt[0] && strchr("^!?", fmt[0])) 592 *f++ = fmt[0]; 593 else if (scsi_hba_log_fcif && (level > SCSI_HBA_LOG1)) 594 *f++ = (char)scsi_hba_log_fcif; /* add global fcif */ 595 if (align) 596 (void) sprintf(f, "%s", "%-18.18s: %36.36s: %s%s"); 597 else 598 (void) sprintf(f, "%s", func ? "%s: %s%s%s" : "%s%s%s"); 599 600 if (func) 601 cmn_err(clevel, scsi_hba_fmt, func, scsi_hba_log_i, 602 scsi_hba_log_buf, clevel == CE_CONT ? "\n" : ""); 603 else 604 cmn_err(clevel, scsi_hba_fmt, scsi_hba_log_i, 605 scsi_hba_log_buf, clevel == CE_CONT ? "\n" : ""); 606 mutex_exit(&scsi_hba_log_mutex); 607 } 608 609 int scsi_enumeration_failed_panic = 0; 610 int scsi_enumeration_failed_hotplug = 1; 611 612 static void 613 scsi_enumeration_failed(dev_info_t *child, scsi_enum_t se, 614 char *arg, char *when) 615 { 616 /* If 'se' is -1 the 'se' value comes from child. */ 617 if (se == -1) { 618 ASSERT(child); 619 se = ndi_dev_is_hotplug_node(child) ? SE_HP : SE_BUSCONFIG; 620 } 621 622 if (scsi_enumeration_failed_panic) { 623 /* set scsi_enumeration_failed_panic to debug */ 624 SCSI_HBA_LOG((_LOG(PANIC), NULL, child, 625 "%s%senumeration failed during %s", 626 arg ? arg : "", arg ? " " : "", when)); 627 } else if (scsi_enumeration_failed_hotplug && (se == SE_HP)) { 628 /* set scsi_enumeration_failed_hotplug for console messages */ 629 SCSI_HBA_LOG((_LOG(WARN), NULL, child, 630 "%s%senumeration failed during %s", 631 arg ? arg : "", arg ? " " : "", when)); 632 } else { 633 /* default */ 634 SCSI_HBA_LOG((_LOG(2), NULL, child, 635 "%s%senumeration failed during %s", 636 arg ? arg : "", arg ? " " : "", when)); 637 } 638 } 639 640 /* 641 * scsi_hba version of [nm]di_devi_enter/[nm]di_devi_exit that detects if HBA 642 * is a PHCI, and chooses mdi/ndi locking implementation. 643 */ 644 static void 645 scsi_hba_devi_enter(dev_info_t *self, int *circp) 646 { 647 if (MDI_PHCI(self)) 648 mdi_devi_enter(self, circp); 649 else 650 ndi_devi_enter(self, circp); 651 } 652 653 static int 654 scsi_hba_devi_tryenter(dev_info_t *self, int *circp) 655 { 656 if (MDI_PHCI(self)) 657 return (mdi_devi_tryenter(self, circp)); 658 else 659 return (ndi_devi_tryenter(self, circp)); 660 } 661 662 static void 663 scsi_hba_devi_exit(dev_info_t *self, int circ) 664 { 665 if (MDI_PHCI(self)) 666 mdi_devi_exit(self, circ); 667 else 668 ndi_devi_exit(self, circ); 669 } 670 671 static void 672 scsi_hba_devi_enter_phci(dev_info_t *self, int *circp) 673 { 674 if (MDI_PHCI(self)) 675 mdi_devi_enter_phci(self, circp); 676 } 677 678 static void 679 scsi_hba_devi_exit_phci(dev_info_t *self, int circ) 680 { 681 if (MDI_PHCI(self)) 682 mdi_devi_exit_phci(self, circ); 683 } 684 685 static int 686 scsi_hba_dev_is_sid(dev_info_t *child) 687 { 688 /* 689 * Use ndi_dev_is_persistent_node instead of ddi_dev_is_sid to avoid 690 * any possible locking issues in mixed nexus devctl code (like usb). 691 */ 692 return (ndi_dev_is_persistent_node(child)); 693 } 694 695 /* 696 * Called from _init() when loading "scsi" module 697 */ 698 void 699 scsi_initialize_hba_interface() 700 { 701 SCSI_HBA_LOG((_LOG_TRACE, NULL, NULL, __func__)); 702 703 /* We need "scsiprobe" and "scsinodev" as an alias or a driver. */ 704 if (ddi_name_to_major(compatible_probe) == DDI_MAJOR_T_NONE) { 705 SCSI_HBA_LOG((_LOG_NF(WARN), "failed to resolve '%s' " 706 "driver alias, defaulting to 'nulldriver'", 707 compatible_probe)); 708 709 /* If no "nulldriver" driver nothing will work... */ 710 compatible_probe = "nulldriver"; 711 if (ddi_name_to_major(compatible_probe) == DDI_MAJOR_T_NONE) 712 SCSI_HBA_LOG((_LOG_NF(WARN), "no probe '%s' driver, " 713 "system misconfigured", compatible_probe)); 714 } 715 if (ddi_name_to_major(compatible_nodev) == DDI_MAJOR_T_NONE) { 716 SCSI_HBA_LOG((_LOG_NF(WARN), "failed to resolve '%s' " 717 "driver alias, defaulting to 'nulldriver'", 718 compatible_nodev)); 719 720 /* If no "nulldriver" driver nothing will work... */ 721 compatible_nodev = "nulldriver"; 722 if (ddi_name_to_major(compatible_nodev) == DDI_MAJOR_T_NONE) 723 SCSI_HBA_LOG((_LOG_NF(WARN), "no nodev '%s' driver, " 724 "system misconfigured", compatible_nodev)); 725 } 726 727 /* 728 * Verify our special node name "probe" will not be used in other ways. 729 * Don't expect things to work if they are. 730 */ 731 if (ddi_major_to_name(ddi_name_to_major("probe"))) 732 SCSI_HBA_LOG((_LOG_NF(WARN), 733 "driver already using special node name 'probe'")); 734 735 mutex_init(&scsi_log_mutex, NULL, MUTEX_DRIVER, NULL); 736 mutex_init(&scsi_flag_nointr_mutex, NULL, MUTEX_DRIVER, NULL); 737 cv_init(&scsi_flag_nointr_cv, NULL, CV_DRIVER, NULL); 738 mutex_init(&scsi_hba_log_mutex, NULL, MUTEX_DRIVER, NULL); 739 740 /* initialize the asynchronous barrier deletion daemon */ 741 mutex_init(&scsi_hba_barrier_mutex, NULL, MUTEX_DRIVER, NULL); 742 cv_init(&scsi_hba_barrier_cv, NULL, CV_DRIVER, NULL); 743 (void) thread_create(NULL, 0, 744 (void (*)())scsi_hba_barrier_daemon, NULL, 745 0, &p0, TS_RUN, minclsyspri); 746 747 /* initialize lun change ASC/ASCQ processing daemon (stage1 & stage2) */ 748 mutex_init(&scsi_lunchg1_mutex, NULL, MUTEX_DRIVER, NULL); 749 cv_init(&scsi_lunchg1_cv, NULL, CV_DRIVER, NULL); 750 (void) thread_create(NULL, 0, 751 (void (*)())scsi_lunchg1_daemon, NULL, 752 0, &p0, TS_RUN, minclsyspri); 753 mutex_init(&scsi_lunchg2_mutex, NULL, MUTEX_DRIVER, NULL); 754 cv_init(&scsi_lunchg2_cv, NULL, CV_DRIVER, NULL); 755 (void) thread_create(NULL, 0, 756 (void (*)())scsi_lunchg2_daemon, NULL, 757 0, &p0, TS_RUN, minclsyspri); 758 } 759 760 int 761 scsi_hba_pkt_constructor(void *buf, void *arg, int kmflag) 762 { 763 struct scsi_pkt_cache_wrapper *pktw; 764 struct scsi_pkt *pkt; 765 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 766 int pkt_len; 767 char *ptr; 768 769 /* 770 * allocate a chunk of memory for the following: 771 * scsi_pkt 772 * pcw_* fields 773 * pkt_ha_private 774 * pkt_cdbp, if needed 775 * (pkt_private always null) 776 * pkt_scbp, if needed 777 */ 778 pkt_len = tran->tran_hba_len + sizeof (struct scsi_pkt_cache_wrapper); 779 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CDB) 780 pkt_len += DEFAULT_CDBLEN; 781 if (tran->tran_hba_flags & SCSI_HBA_TRAN_SCB) 782 pkt_len += DEFAULT_SCBLEN; 783 bzero(buf, pkt_len); 784 785 ptr = buf; 786 pktw = buf; 787 ptr += sizeof (struct scsi_pkt_cache_wrapper); 788 pkt = &(pktw->pcw_pkt); 789 pkt->pkt_ha_private = (opaque_t)ptr; 790 791 pktw->pcw_magic = PKT_WRAPPER_MAGIC; /* alloced correctly */ 792 /* 793 * keep track of the granularity at the time this handle was 794 * allocated 795 */ 796 pktw->pcw_granular = tran->tran_dma_attr.dma_attr_granular; 797 798 if (ddi_dma_alloc_handle(tran->tran_hba_dip, &tran->tran_dma_attr, 799 kmflag == KM_SLEEP ? SLEEP_FUNC: NULL_FUNC, NULL, 800 &pkt->pkt_handle) != DDI_SUCCESS) { 801 802 return (-1); 803 } 804 ptr += tran->tran_hba_len; 805 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CDB) { 806 pkt->pkt_cdbp = (opaque_t)ptr; 807 ptr += DEFAULT_CDBLEN; 808 } 809 pkt->pkt_private = NULL; 810 if (tran->tran_hba_flags & SCSI_HBA_TRAN_SCB) 811 pkt->pkt_scbp = (opaque_t)ptr; 812 if (tran->tran_pkt_constructor) 813 return ((*tran->tran_pkt_constructor)(pkt, arg, kmflag)); 814 else 815 return (0); 816 } 817 818 #define P_TO_TRAN(pkt) ((pkt)->pkt_address.a_hba_tran) 819 820 void 821 scsi_hba_pkt_destructor(void *buf, void *arg) 822 { 823 struct scsi_pkt_cache_wrapper *pktw = buf; 824 struct scsi_pkt *pkt = &(pktw->pcw_pkt); 825 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 826 827 ASSERT(pktw->pcw_magic == PKT_WRAPPER_MAGIC); 828 ASSERT((pktw->pcw_flags & PCW_BOUND) == 0); 829 if (tran->tran_pkt_destructor) 830 (*tran->tran_pkt_destructor)(pkt, arg); 831 832 /* make sure nobody messed with our pointers */ 833 ASSERT(pkt->pkt_ha_private == (opaque_t)((char *)pkt + 834 sizeof (struct scsi_pkt_cache_wrapper))); 835 ASSERT(((tran->tran_hba_flags & SCSI_HBA_TRAN_SCB) == 0) || 836 (pkt->pkt_scbp == (opaque_t)((char *)pkt + 837 tran->tran_hba_len + 838 (((tran->tran_hba_flags & SCSI_HBA_TRAN_CDB) == 0) ? 839 0 : DEFAULT_CDBLEN) + 840 DEFAULT_PRIVLEN + sizeof (struct scsi_pkt_cache_wrapper)))); 841 ASSERT(((tran->tran_hba_flags & SCSI_HBA_TRAN_CDB) == 0) || 842 (pkt->pkt_cdbp == (opaque_t)((char *)pkt + 843 tran->tran_hba_len + 844 sizeof (struct scsi_pkt_cache_wrapper)))); 845 ASSERT(pkt->pkt_handle); 846 ddi_dma_free_handle(&pkt->pkt_handle); 847 pkt->pkt_handle = NULL; 848 pkt->pkt_numcookies = 0; 849 pktw->pcw_total_xfer = 0; 850 pktw->pcw_totalwin = 0; 851 pktw->pcw_curwin = 0; 852 } 853 854 /* 855 * Called by an HBA from _init() to plumb in common SCSA bus_ops and 856 * cb_ops for the HBA's :devctl and :scsi minor nodes. 857 */ 858 int 859 scsi_hba_init(struct modlinkage *modlp) 860 { 861 struct dev_ops *hba_dev_ops; 862 863 SCSI_HBA_LOG((_LOG_TRACE, NULL, NULL, __func__)); 864 865 /* 866 * Get a pointer to the dev_ops structure of the HBA and plumb our 867 * bus_ops vector into the HBA's dev_ops structure. 868 */ 869 hba_dev_ops = ((struct modldrv *)(modlp->ml_linkage[0]))->drv_dev_ops; 870 ASSERT(hba_dev_ops->devo_bus_ops == NULL); 871 hba_dev_ops->devo_bus_ops = &scsi_hba_busops; 872 873 /* 874 * Plumb our cb_ops vector into the HBA's dev_ops structure to 875 * provide getinfo and hotplugging ioctl support if the HBA driver 876 * does not already provide this support. 877 */ 878 if (hba_dev_ops->devo_cb_ops == NULL) { 879 hba_dev_ops->devo_cb_ops = &scsi_hba_cbops; 880 } 881 if (hba_dev_ops->devo_cb_ops->cb_open == scsi_hba_open) { 882 ASSERT(hba_dev_ops->devo_cb_ops->cb_close == scsi_hba_close); 883 hba_dev_ops->devo_getinfo = scsi_hba_info; 884 } 885 return (0); 886 } 887 888 /* 889 * Called by an HBA attach(9E) to allocate a scsi_hba_tran(9S) structure. An 890 * HBA driver will then initialize the structure and then call 891 * scsi_hba_attach_setup(9F). 892 */ 893 /*ARGSUSED*/ 894 scsi_hba_tran_t * 895 scsi_hba_tran_alloc( 896 dev_info_t *self, 897 int flags) 898 { 899 scsi_hba_tran_t *tran; 900 901 SCSI_HBA_LOG((_LOG_TRACE, self, NULL, __func__)); 902 903 /* allocate SCSA flavors for self */ 904 ndi_flavorv_alloc(self, SCSA_NFLAVORS); 905 906 tran = kmem_zalloc(sizeof (scsi_hba_tran_t), 907 (flags & SCSI_HBA_CANSLEEP) ? KM_SLEEP : KM_NOSLEEP); 908 909 if (tran) { 910 tran->tran_interconnect_type = INTERCONNECT_PARALLEL; 911 912 /* 913 * HBA driver called scsi_hba_tran_alloc(), so tran structure 914 * is proper size and unused/newer fields are zero. 915 * 916 * NOTE: We use SCSA_HBA_SCSA_TA as an obtuse form of 917 * versioning to detect old HBA drivers that do not use 918 * scsi_hba_tran_alloc, and would present garbage data 919 * (instead of valid/zero data) for newer tran fields. 920 */ 921 tran->tran_hba_flags |= SCSI_HBA_SCSA_TA; 922 } 923 924 return (tran); 925 } 926 927 /* 928 * Called by an HBA to free a scsi_hba_tran structure 929 */ 930 void 931 scsi_hba_tran_free( 932 scsi_hba_tran_t *tran) 933 { 934 SCSI_HBA_LOG((_LOG_TRACE, tran->tran_hba_dip, NULL, __func__)); 935 936 kmem_free(tran, sizeof (scsi_hba_tran_t)); 937 } 938 939 int 940 scsi_tran_ext_alloc( 941 scsi_hba_tran_t *tran, 942 size_t length, 943 int flags) 944 { 945 void *tran_ext; 946 int ret = DDI_FAILURE; 947 948 tran_ext = kmem_zalloc(length, 949 (flags & SCSI_HBA_CANSLEEP) ? KM_SLEEP : KM_NOSLEEP); 950 if (tran_ext != NULL) { 951 tran->tran_extension = tran_ext; 952 ret = DDI_SUCCESS; 953 } 954 return (ret); 955 } 956 957 void 958 scsi_tran_ext_free( 959 scsi_hba_tran_t *tran, 960 size_t length) 961 { 962 if (tran->tran_extension != NULL) { 963 kmem_free(tran->tran_extension, length); 964 tran->tran_extension = NULL; 965 } 966 } 967 968 /* 969 * Obsolete: Called by an HBA to attach an instance of the driver 970 * Implement this older interface in terms of the new. 971 */ 972 /*ARGSUSED*/ 973 int 974 scsi_hba_attach( 975 dev_info_t *self, 976 ddi_dma_lim_t *hba_lim, 977 scsi_hba_tran_t *tran, 978 int flags, 979 void *hba_options) 980 { 981 ddi_dma_attr_t hba_dma_attr; 982 983 bzero(&hba_dma_attr, sizeof (ddi_dma_attr_t)); 984 hba_dma_attr.dma_attr_burstsizes = hba_lim->dlim_burstsizes; 985 hba_dma_attr.dma_attr_minxfer = hba_lim->dlim_minxfer; 986 987 return (scsi_hba_attach_setup(self, &hba_dma_attr, tran, flags)); 988 } 989 990 /* 991 * Common nexus teardown code: used by both scsi_hba_detach() on SCSA HBA node 992 * and iport_postdetach_tran_scsi_device() on a SCSA HBA iport node (and for 993 * failure cleanup). Undo scsa_nexus_setup in reverse order. 994 * 995 * NOTE: Since we are in the Solaris IO framework, we can depend on 996 * undocumented cleanup operations performed by other parts of the framework: 997 * like detach_node() calling ddi_prop_remove_all() and 998 * ddi_remove_minor_node(,NULL). 999 */ 1000 static void 1001 scsa_nexus_teardown(dev_info_t *self, scsi_hba_tran_t *tran) 1002 { 1003 /* Teardown FMA. */ 1004 if (tran->tran_hba_flags & SCSI_HBA_SCSA_FM) { 1005 ddi_fm_fini(self); 1006 tran->tran_hba_flags &= ~SCSI_HBA_SCSA_FM; 1007 } 1008 } 1009 1010 /* 1011 * Common nexus setup code: used by both scsi_hba_attach_setup() on SCSA HBA 1012 * node and iport_preattach_tran_scsi_device() on a SCSA HBA iport node. 1013 * 1014 * This code makes no assumptions about tran use by scsi_device children. 1015 */ 1016 static int 1017 scsa_nexus_setup(dev_info_t *self, scsi_hba_tran_t *tran) 1018 { 1019 int capable; 1020 int scsa_minor; 1021 1022 /* 1023 * NOTE: SCSA maintains an 'fm-capable' domain, in tran_fm_capable, 1024 * that is not dependent (limited by) the capabilities of its parents. 1025 * For example a devinfo node in a branch that is not 1026 * DDI_FM_EREPORT_CAPABLE may report as capable, via tran_fm_capable, 1027 * to its scsi_device children. 1028 * 1029 * Get 'fm-capable' property from driver.conf, if present. If not 1030 * present, default to the scsi_fm_capable global (which has 1031 * DDI_FM_EREPORT_CAPABLE set by default). 1032 */ 1033 if (tran->tran_fm_capable == DDI_FM_NOT_CAPABLE) 1034 tran->tran_fm_capable = ddi_prop_get_int(DDI_DEV_T_ANY, self, 1035 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1036 "fm-capable", scsi_fm_capable); 1037 1038 /* 1039 * If an HBA is *not* doing its own fma support by calling 1040 * ddi_fm_init() prior to scsi_hba_attach_setup(), we provide a minimal 1041 * common SCSA implementation so that scsi_device children can generate 1042 * ereports via scsi_fm_ereport_post(). We use ddi_fm_capable() to 1043 * detect an HBA calling ddi_fm_init() prior to scsi_hba_attach_setup(). 1044 */ 1045 if (tran->tran_fm_capable && 1046 (ddi_fm_capable(self) == DDI_FM_NOT_CAPABLE)) { 1047 /* 1048 * We are capable of something, pass our capabilities up the 1049 * tree, but use a local variable so our parent can't limit 1050 * our capabilities (we don't want our parent to clear 1051 * DDI_FM_EREPORT_CAPABLE). 1052 * 1053 * NOTE: iblock cookies are not important because scsi HBAs 1054 * always interrupt below LOCK_LEVEL. 1055 */ 1056 capable = tran->tran_fm_capable; 1057 ddi_fm_init(self, &capable, NULL); 1058 1059 /* 1060 * Set SCSI_HBA_SCSA_FM bit to mark us as using the common 1061 * minimal SCSA fm implementation - we called ddi_fm_init(), 1062 * so we are responsible for calling ddi_fm_fini() in 1063 * scsi_hba_detach(). 1064 * 1065 * NOTE: if ddi_fm_init fails to establish handle, SKIP cleanup. 1066 */ 1067 if (DEVI(self)->devi_fmhdl) 1068 tran->tran_hba_flags |= SCSI_HBA_SCSA_FM; 1069 } 1070 1071 /* If SCSA responsible for for minor nodes, create :devctl minor. */ 1072 scsa_minor = (ddi_get_driver(self)->devo_cb_ops->cb_open == 1073 scsi_hba_open) ? 1 : 0; 1074 if (scsa_minor && ((ddi_create_minor_node(self, "devctl", S_IFCHR, 1075 INST2DEVCTL(ddi_get_instance(self)), DDI_NT_SCSI_NEXUS, 0) != 1076 DDI_SUCCESS))) { 1077 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 1078 "can't create :devctl minor node")); 1079 goto fail; 1080 } 1081 1082 return (DDI_SUCCESS); 1083 1084 fail: scsa_nexus_teardown(self, tran); 1085 return (DDI_FAILURE); 1086 } 1087 1088 /* 1089 * Common tran teardown code: used by iport_postdetach_tran_scsi_device() on a 1090 * SCSA HBA iport node and (possibly) by scsi_hba_detach() on SCSA HBA node 1091 * (and for failure cleanup). Undo scsa_tran_setup in reverse order. 1092 * 1093 * NOTE: Since we are in the Solaris IO framework, we can depend on 1094 * undocumented cleanup operations performed by other parts of the framework: 1095 * like detach_node() calling ddi_prop_remove_all() and 1096 * ddi_remove_minor_node(,NULL). 1097 */ 1098 static void 1099 scsa_tran_teardown(dev_info_t *self, scsi_hba_tran_t *tran) 1100 { 1101 tran->tran_iport_dip = NULL; 1102 1103 /* Teardown pHCI registration */ 1104 if (tran->tran_hba_flags & SCSI_HBA_SCSA_PHCI) { 1105 (void) mdi_phci_unregister(self, 0); 1106 tran->tran_hba_flags &= ~SCSI_HBA_SCSA_PHCI; 1107 } 1108 } 1109 1110 /* 1111 * Common tran setup code: used by iport_preattach_tran_scsi_device() on a 1112 * SCSA HBA iport node and (possibly) by scsi_hba_attach_setup() on SCSA HBA 1113 * node. 1114 */ 1115 static int 1116 scsa_tran_setup(dev_info_t *self, scsi_hba_tran_t *tran) 1117 { 1118 int scsa_minor; 1119 int id; 1120 char *scsi_binding_set; 1121 static const char *interconnect[] = INTERCONNECT_TYPE_ASCII; 1122 1123 SCSI_HBA_LOG((_LOG_TRACE, self, NULL, __func__)); 1124 1125 /* If SCSA responsible for for minor nodes, create ":scsi" */ 1126 scsa_minor = (ddi_get_driver(self)->devo_cb_ops->cb_open == 1127 scsi_hba_open) ? 1 : 0; 1128 if (scsa_minor && (ddi_create_minor_node(self, "scsi", S_IFCHR, 1129 INST2SCSI(ddi_get_instance(self)), 1130 DDI_NT_SCSI_ATTACHMENT_POINT, 0) != DDI_SUCCESS)) { 1131 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 1132 "can't create :scsi minor node")); 1133 goto fail; 1134 } 1135 1136 /* 1137 * If the property does not already exist on self then see if we can 1138 * pull it from further up the tree and define it on self. If the 1139 * property does not exist above (including options.conf) then use the 1140 * default value specified (global variable). We pull things down from 1141 * above for faster "DDI_PROP_NOTPROM | DDI_PROP_DONTPASS" runtime 1142 * access. 1143 * 1144 * Future: Should we avoid creating properties when value == global? 1145 */ 1146 #define CONFIG_INT_PROP(s, p, dv) { \ 1147 if ((ddi_prop_exists(DDI_DEV_T_ANY, s, \ 1148 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, p) == 0) && \ 1149 (ndi_prop_update_int(DDI_DEV_T_NONE, s, p, \ 1150 ddi_prop_get_int(DDI_DEV_T_ANY, ddi_get_parent(s), \ 1151 DDI_PROP_NOTPROM, p, dv)) != DDI_PROP_SUCCESS)) \ 1152 SCSI_HBA_LOG((_LOG(WARN), NULL, s, \ 1153 "can't create property '%s'", p)); \ 1154 } 1155 1156 /* Decorate with scsi configuration properties */ 1157 CONFIG_INT_PROP(self, "scsi-enumeration", scsi_enumeration); 1158 CONFIG_INT_PROP(self, "scsi-options", scsi_options); 1159 CONFIG_INT_PROP(self, "scsi-reset-delay", scsi_reset_delay); 1160 CONFIG_INT_PROP(self, "scsi-watchdog-tick", scsi_watchdog_tick); 1161 CONFIG_INT_PROP(self, "scsi-selection-timeout", scsi_selection_timeout); 1162 CONFIG_INT_PROP(self, "scsi-tag-age-limit", scsi_tag_age_limit); 1163 1164 /* 1165 * Pull down the scsi-initiator-id from further up the tree, or as 1166 * defined by OBP. Place on node for faster access. NOTE: there is 1167 * some confusion about what the name of the property should be. 1168 */ 1169 id = ddi_prop_get_int(DDI_DEV_T_ANY, self, 0, "initiator-id", -1); 1170 if (id == -1) 1171 id = ddi_prop_get_int(DDI_DEV_T_ANY, self, 0, 1172 "scsi-initiator-id", -1); 1173 if (id != -1) 1174 CONFIG_INT_PROP(self, "scsi-initiator-id", id); 1175 1176 /* 1177 * If we are responsible for tran allocation, establish 1178 * 'initiator-interconnect-type'. 1179 */ 1180 if ((tran->tran_hba_flags & SCSI_HBA_SCSA_TA) && 1181 (tran->tran_interconnect_type > 0) && 1182 (tran->tran_interconnect_type < INTERCONNECT_MAX)) { 1183 if (ndi_prop_update_string(DDI_DEV_T_NONE, self, 1184 "initiator-interconnect-type", 1185 (char *)interconnect[tran->tran_interconnect_type]) 1186 != DDI_PROP_SUCCESS) { 1187 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 1188 "failed to establish " 1189 "'initiator-interconnect-type'")); 1190 goto fail; 1191 } 1192 } 1193 1194 /* 1195 * The 'scsi-binding-set' property can be defined in driver.conf 1196 * files of legacy drivers on an as-needed basis. If 'scsi-binding-set' 1197 * is not driver.conf defined, and the HBA is not implementing its own 1198 * private bus_config, we define scsi-binding-set to the default 1199 * 'spi' legacy value. 1200 * 1201 * NOTE: This default 'spi' value will be deleted if an HBA driver 1202 * ends up using the scsi_hba_tgtmap_create() enumeration services. 1203 * 1204 * NOTE: If we were ever to decide to derive 'scsi-binding-set' from 1205 * the IEEE-1275 'device_type' property then this is where that code 1206 * should go - there is not enough consistency in 'device_type' to do 1207 * this correctly at this point in time. 1208 */ 1209 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, self, 1210 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-binding-set", 1211 &scsi_binding_set) == DDI_PROP_SUCCESS) { 1212 SCSI_HBA_LOG((_LOG(2), NULL, self, 1213 "external 'scsi-binding-set' \"%s\"", scsi_binding_set)); 1214 ddi_prop_free(scsi_binding_set); 1215 } else if (scsi_binding_set_spi && 1216 ((tran->tran_bus_config == NULL) || 1217 (tran->tran_bus_config == scsi_hba_bus_config_spi))) { 1218 if (ndi_prop_update_string(DDI_DEV_T_NONE, self, 1219 "scsi-binding-set", scsi_binding_set_spi) != 1220 DDI_PROP_SUCCESS) { 1221 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 1222 "failed to establish 'scsi_binding_set' default")); 1223 goto fail; 1224 } 1225 SCSI_HBA_LOG((_LOG(2), NULL, self, 1226 "default 'scsi-binding-set' \"%s\"", scsi_binding_set_spi)); 1227 } else 1228 SCSI_HBA_LOG((_LOG(2), NULL, self, 1229 "no 'scsi-binding-set'")); 1230 1231 /* 1232 * If SCSI_HBA_TRAN_PHCI is set, take care of pHCI registration of the 1233 * initiator. 1234 */ 1235 if ((tran->tran_hba_flags & SCSI_HBA_TRAN_PHCI) && 1236 (mdi_phci_register(MDI_HCI_CLASS_SCSI, self, 0) == MDI_SUCCESS)) 1237 tran->tran_hba_flags |= SCSI_HBA_SCSA_PHCI; 1238 1239 /* NOTE: tran_hba_dip is for DMA operation at the HBA node level */ 1240 tran->tran_iport_dip = self; /* for iport association */ 1241 return (DDI_SUCCESS); 1242 1243 fail: scsa_tran_teardown(self, tran); 1244 return (DDI_FAILURE); 1245 } 1246 1247 /* 1248 * Called by a SCSA HBA driver to attach an instance of the driver to 1249 * SCSA HBA node enumerated by PCI. 1250 */ 1251 int 1252 scsi_hba_attach_setup( 1253 dev_info_t *self, 1254 ddi_dma_attr_t *hba_dma_attr, 1255 scsi_hba_tran_t *tran, 1256 int flags) 1257 { 1258 int len; 1259 char cache_name[96]; 1260 1261 SCSI_HBA_LOG((_LOG_TRACE, self, NULL, __func__)); 1262 1263 /* 1264 * Verify that we are a driver so other code does not need to 1265 * check for NULL ddi_get_driver() result. 1266 */ 1267 if (ddi_get_driver(self) == NULL) 1268 return (DDI_FAILURE); 1269 1270 /* 1271 * Verify that we are called on a SCSA HBA node (function enumerated 1272 * by PCI), not on an iport node. 1273 */ 1274 ASSERT(scsi_hba_iport_unit_address(self) == NULL); 1275 if (scsi_hba_iport_unit_address(self)) 1276 return (DDI_FAILURE); /* self can't be an iport */ 1277 1278 /* Caller must provide the tran. */ 1279 ASSERT(tran); 1280 if (tran == NULL) 1281 return (DDI_FAILURE); 1282 1283 /* 1284 * Verify correct scsi_hba_tran_t form: 1285 * 1286 * o Both or none of tran_get_name/tran_get_addr. 1287 * NOTE: Older SCSA HBA drivers for SCSI transports with addressing 1288 * that did not fit the SPI "struct scsi_address" model were required 1289 * to implement tran_get_name and tran_get_addr. This is no longer 1290 * true - modern transport drivers should now use common SCSA 1291 * enumeration services. The SCSA enumeration code will represent 1292 * the unit-address using well-known address properties 1293 * (SCSI_ADDR_PROP_TARGET_PORT, SCSI_ADDR_PROP_LUN64) during 1294 * devinfo/pathinfo node creation. The HBA driver can obtain values 1295 * using scsi_device_prop_lookup_*() from its tran_tgt_init(9E). 1296 * 1297 */ 1298 if ((tran->tran_get_name == NULL) ^ (tran->tran_get_bus_addr == NULL)) { 1299 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 1300 "should support both or neither: " 1301 "tran_get_name, tran_get_bus_addr")); 1302 return (DDI_FAILURE); 1303 } 1304 1305 /* 1306 * Establish the devinfo context of this tran structure, preserving 1307 * knowledge of how the tran was allocated. 1308 */ 1309 tran->tran_hba_dip = self; /* for DMA */ 1310 tran->tran_hba_flags = (flags & ~SCSI_HBA_SCSA_TA) | 1311 (tran->tran_hba_flags & SCSI_HBA_SCSA_TA); 1312 1313 /* Establish flavor of transport (and ddi_get_driver_private()) */ 1314 ndi_flavorv_set(self, SCSA_FLAVOR_SCSI_DEVICE, tran); 1315 1316 /* 1317 * Note: We only need dma_attr_minxfer and dma_attr_burstsizes 1318 * from the DMA attributes. scsi_hba_attach(9f) only guarantees 1319 * that these two fields are initialized properly. If this 1320 * changes, be sure to revisit the implementation of 1321 * scsi_hba_attach(9F). 1322 */ 1323 (void) memcpy(&tran->tran_dma_attr, hba_dma_attr, 1324 sizeof (ddi_dma_attr_t)); 1325 1326 /* Create tran_setup_pkt(9E) kmem_cache. */ 1327 if (tran->tran_setup_pkt) { 1328 ASSERT(tran->tran_init_pkt == NULL); 1329 ASSERT(tran->tran_destroy_pkt == NULL); 1330 if (tran->tran_init_pkt || tran->tran_destroy_pkt) 1331 goto fail; 1332 1333 tran->tran_init_pkt = scsi_init_cache_pkt; 1334 tran->tran_destroy_pkt = scsi_free_cache_pkt; 1335 tran->tran_sync_pkt = scsi_sync_cache_pkt; 1336 tran->tran_dmafree = scsi_cache_dmafree; 1337 1338 len = sizeof (struct scsi_pkt_cache_wrapper); 1339 len += ROUNDUP(tran->tran_hba_len); 1340 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CDB) 1341 len += ROUNDUP(DEFAULT_CDBLEN); 1342 if (tran->tran_hba_flags & SCSI_HBA_TRAN_SCB) 1343 len += ROUNDUP(DEFAULT_SCBLEN); 1344 1345 (void) snprintf(cache_name, sizeof (cache_name), 1346 "pkt_cache_%s_%d", ddi_driver_name(self), 1347 ddi_get_instance(self)); 1348 1349 tran->tran_pkt_cache_ptr = kmem_cache_create( 1350 cache_name, len, 8, scsi_hba_pkt_constructor, 1351 scsi_hba_pkt_destructor, NULL, tran, NULL, 0); 1352 } 1353 1354 /* Perform node setup independent of initiator role */ 1355 if (scsa_nexus_setup(self, tran) != DDI_SUCCESS) 1356 goto fail; 1357 1358 /* 1359 * The SCSI_HBA_HBA flag is passed to scsi_hba_attach_setup when the 1360 * HBA driver knows that *all* children of the SCSA HBA node will be 1361 * 'iports'. If the SCSA HBA node can have iport children and also 1362 * function as an initiator for xxx_device children then it should 1363 * not specify SCSI_HBA_HBA in its scsi_hba_attach_setup call. An 1364 * HBA driver that does not manage iports should not set SCSA_HBA_HBA. 1365 */ 1366 if (tran->tran_hba_flags & SCSI_HBA_HBA) { 1367 /* 1368 * Set the 'ddi-config-driver-node' property on the nexus 1369 * node that notify attach_driver_nodes() to configure all 1370 * immediate children so that nodes which bind to the 1371 * same driver as parent are able to be added into per-driver 1372 * list. 1373 */ 1374 if (ndi_prop_create_boolean(DDI_DEV_T_NONE, 1375 self, "ddi-config-driver-node") != DDI_PROP_SUCCESS) 1376 goto fail; 1377 } else { 1378 if (scsa_tran_setup(self, tran) != DDI_SUCCESS) 1379 goto fail; 1380 } 1381 1382 return (DDI_SUCCESS); 1383 1384 fail: (void) scsi_hba_detach(self); 1385 return (DDI_FAILURE); 1386 } 1387 1388 /* 1389 * Called by an HBA to detach an instance of the driver. This may be called 1390 * for SCSA HBA nodes and for SCSA iport nodes. 1391 */ 1392 int 1393 scsi_hba_detach(dev_info_t *self) 1394 { 1395 scsi_hba_tran_t *tran; 1396 1397 ASSERT(scsi_hba_iport_unit_address(self) == NULL); 1398 if (scsi_hba_iport_unit_address(self)) 1399 return (DDI_FAILURE); /* self can't be an iport */ 1400 1401 /* Check all error return conditions upfront */ 1402 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 1403 ASSERT(tran); 1404 if (tran == NULL) 1405 return (DDI_FAILURE); 1406 1407 ASSERT(tran->tran_open_flag == 0); 1408 if (tran->tran_open_flag) 1409 return (DDI_FAILURE); 1410 1411 if (!(tran->tran_hba_flags & SCSI_HBA_HBA)) 1412 scsa_tran_teardown(self, tran); 1413 scsa_nexus_teardown(self, tran); 1414 1415 /* Teardown tran_setup_pkt(9E) kmem_cache. */ 1416 if (tran->tran_pkt_cache_ptr) { 1417 kmem_cache_destroy(tran->tran_pkt_cache_ptr); 1418 tran->tran_pkt_cache_ptr = NULL; 1419 } 1420 1421 (void) memset(&tran->tran_dma_attr, 0, sizeof (ddi_dma_attr_t)); 1422 1423 /* Teardown flavor of transport (and ddi_get_driver_private()) */ 1424 ndi_flavorv_set(self, SCSA_FLAVOR_SCSI_DEVICE, NULL); 1425 1426 tran->tran_hba_dip = NULL; 1427 1428 return (DDI_SUCCESS); 1429 } 1430 1431 1432 /* 1433 * Called by an HBA from _fini() 1434 */ 1435 void 1436 scsi_hba_fini(struct modlinkage *modlp) 1437 { 1438 struct dev_ops *hba_dev_ops; 1439 1440 SCSI_HBA_LOG((_LOG_TRACE, NULL, NULL, __func__)); 1441 1442 /* Get the devops structure of this module and clear bus_ops vector. */ 1443 hba_dev_ops = ((struct modldrv *)(modlp->ml_linkage[0]))->drv_dev_ops; 1444 1445 if (hba_dev_ops->devo_cb_ops == &scsi_hba_cbops) 1446 hba_dev_ops->devo_cb_ops = NULL; 1447 1448 if (hba_dev_ops->devo_getinfo == scsi_hba_info) 1449 hba_dev_ops->devo_getinfo = NULL; 1450 1451 hba_dev_ops->devo_bus_ops = (struct bus_ops *)NULL; 1452 } 1453 1454 /* 1455 * SAS specific functions 1456 */ 1457 smp_hba_tran_t * 1458 smp_hba_tran_alloc(dev_info_t *self) 1459 { 1460 /* allocate SCSA flavors for self */ 1461 ndi_flavorv_alloc(self, SCSA_NFLAVORS); 1462 return (kmem_zalloc(sizeof (smp_hba_tran_t), KM_SLEEP)); 1463 } 1464 1465 void 1466 smp_hba_tran_free(smp_hba_tran_t *tran) 1467 { 1468 kmem_free(tran, sizeof (smp_hba_tran_t)); 1469 } 1470 1471 int 1472 smp_hba_attach_setup( 1473 dev_info_t *self, 1474 smp_hba_tran_t *tran) 1475 { 1476 ASSERT(scsi_hba_iport_unit_address(self) == NULL); 1477 if (scsi_hba_iport_unit_address(self)) 1478 return (DDI_FAILURE); /* self can't be an iport */ 1479 1480 /* 1481 * The owner of the this devinfo_t was responsible 1482 * for informing the framework already about 1483 * additional flavors. 1484 */ 1485 ndi_flavorv_set(self, SCSA_FLAVOR_SMP, tran); 1486 return (DDI_SUCCESS); 1487 } 1488 1489 int 1490 smp_hba_detach(dev_info_t *self) 1491 { 1492 ASSERT(scsi_hba_iport_unit_address(self) == NULL); 1493 if (scsi_hba_iport_unit_address(self)) 1494 return (DDI_FAILURE); /* self can't be an iport */ 1495 1496 ndi_flavorv_set(self, SCSA_FLAVOR_SMP, NULL); 1497 return (DDI_SUCCESS); 1498 } 1499 1500 /* 1501 * SMP child flavored functions 1502 */ 1503 static int 1504 smp_busctl_ua(dev_info_t *child, char *addr, int maxlen) 1505 { 1506 char *tport; 1507 char *wwn; 1508 1509 /* limit ndi_devi_findchild_by_callback to expected flavor */ 1510 if (ndi_flavor_get(child) != SCSA_FLAVOR_SMP) 1511 return (DDI_FAILURE); 1512 1513 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 1514 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1515 SCSI_ADDR_PROP_TARGET_PORT, &tport) == DDI_SUCCESS) { 1516 (void) snprintf(addr, maxlen, "%s", tport); 1517 ddi_prop_free(tport); 1518 return (DDI_SUCCESS); 1519 } 1520 1521 /* 1522 * NOTE: the following code should be deleted when mpt is changed to 1523 * use SCSI_ADDR_PROP_TARGET_PORT instead of SMP_WWN. 1524 */ 1525 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 1526 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1527 SMP_WWN, &wwn) == DDI_SUCCESS) { 1528 (void) snprintf(addr, maxlen, "w%s", wwn); 1529 ddi_prop_free(wwn); 1530 return (DDI_SUCCESS); 1531 } 1532 return (DDI_FAILURE); 1533 } 1534 1535 static int 1536 smp_busctl_reportdev(dev_info_t *child) 1537 { 1538 dev_info_t *self = ddi_get_parent(child); 1539 char *tport; 1540 char *wwn; 1541 1542 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 1543 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1544 SCSI_ADDR_PROP_TARGET_PORT, &tport) == DDI_SUCCESS) { 1545 SCSI_HBA_LOG((_LOG_NF(CONT), "?%s%d at %s%d: target-port %s", 1546 ddi_driver_name(child), ddi_get_instance(child), 1547 ddi_driver_name(self), ddi_get_instance(self), tport)); 1548 ddi_prop_free(tport); 1549 return (DDI_SUCCESS); 1550 } 1551 1552 /* 1553 * NOTE: the following code should be deleted when mpt is changed to 1554 * use SCSI_ADDR_PROP_TARGET_PORT instead of SMP_WWN. 1555 */ 1556 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 1557 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1558 SMP_WWN, &wwn) == DDI_SUCCESS) { 1559 SCSI_HBA_LOG((_LOG_NF(CONT), "?%s%d at %s%d: wwn %s", 1560 ddi_driver_name(child), ddi_get_instance(child), 1561 ddi_driver_name(self), ddi_get_instance(self), wwn)); 1562 ddi_prop_free(wwn); 1563 return (DDI_SUCCESS); 1564 } 1565 return (DDI_FAILURE); 1566 } 1567 1568 static int 1569 smp_busctl_initchild(dev_info_t *child) 1570 { 1571 dev_info_t *self = ddi_get_parent(child); 1572 smp_hba_tran_t *tran; 1573 dev_info_t *dup; 1574 char addr[SCSI_MAXNAMELEN]; 1575 struct smp_device *smp_sd; 1576 uint64_t wwn; 1577 1578 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SMP); 1579 ASSERT(tran); 1580 if (tran == NULL) 1581 return (DDI_FAILURE); 1582 1583 if (smp_busctl_ua(child, addr, sizeof (addr)) != DDI_SUCCESS) 1584 return (DDI_NOT_WELL_FORMED); 1585 if (scsi_wwnstr_to_wwn(addr, &wwn)) 1586 return (DDI_NOT_WELL_FORMED); 1587 1588 /* Prevent duplicate nodes. */ 1589 dup = ndi_devi_findchild_by_callback(self, ddi_node_name(child), addr, 1590 smp_busctl_ua); 1591 if (dup) { 1592 ASSERT(ndi_flavor_get(dup) == SCSA_FLAVOR_SMP); 1593 if (ndi_flavor_get(dup) != SCSA_FLAVOR_SMP) { 1594 SCSI_HBA_LOG((_LOG(1), NULL, child, 1595 "init failed: %s@%s: not SMP flavored", 1596 ddi_node_name(child), addr)); 1597 return (DDI_FAILURE); 1598 } 1599 if (dup != child) { 1600 SCSI_HBA_LOG((_LOG(4), NULL, child, 1601 "init failed: %s@%s: detected duplicate %p", 1602 ddi_node_name(child), addr, (void *)dup)); 1603 return (DDI_FAILURE); 1604 } 1605 } 1606 1607 1608 /* set the node @addr string */ 1609 ddi_set_name_addr(child, addr); 1610 1611 /* Allocate and initialize smp_device. */ 1612 smp_sd = kmem_zalloc(sizeof (struct smp_device), KM_SLEEP); 1613 smp_sd->smp_sd_dev = child; 1614 smp_sd->smp_sd_address.smp_a_hba_tran = tran; 1615 bcopy(&wwn, smp_sd->smp_sd_address.smp_a_wwn, SAS_WWN_BYTE_SIZE); 1616 1617 ddi_set_driver_private(child, smp_sd); 1618 1619 if (tran->smp_tran_init && ((*tran->smp_tran_init)(self, child, 1620 tran, smp_sd) != DDI_SUCCESS)) { 1621 kmem_free(smp_sd, sizeof (struct smp_device)); 1622 scsi_enumeration_failed(child, -1, NULL, "smp_tran_init"); 1623 ddi_set_driver_private(child, NULL); 1624 ddi_set_name_addr(child, NULL); 1625 return (DDI_FAILURE); 1626 } 1627 1628 return (DDI_SUCCESS); 1629 } 1630 1631 /*ARGSUSED*/ 1632 static int 1633 smp_busctl_uninitchild(dev_info_t *child) 1634 { 1635 dev_info_t *self = ddi_get_parent(child); 1636 struct smp_device *smp_sd = ddi_get_driver_private(child); 1637 smp_hba_tran_t *tran; 1638 1639 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SMP); 1640 ASSERT(smp_sd && tran); 1641 if ((smp_sd == NULL) || (tran == NULL)) 1642 return (DDI_FAILURE); 1643 1644 if (tran->smp_tran_free) 1645 (*tran->smp_tran_free) (self, child, tran, smp_sd); 1646 1647 kmem_free(smp_sd, sizeof (*smp_sd)); 1648 ddi_set_driver_private(child, NULL); 1649 ddi_set_name_addr(child, NULL); 1650 return (DDI_SUCCESS); 1651 } 1652 1653 /* Find an "smp" child at the specified address. */ 1654 static dev_info_t * 1655 smp_findchild(dev_info_t *self, char *addr) 1656 { 1657 dev_info_t *child; 1658 1659 /* Search "smp" devinfo child at specified address. */ 1660 ASSERT(self && DEVI_BUSY_OWNED(self) && addr); 1661 for (child = ddi_get_child(self); child; 1662 child = ddi_get_next_sibling(child)) { 1663 /* skip non-"smp" nodes */ 1664 if (ndi_flavor_get(child) != SCSA_FLAVOR_SMP) 1665 continue; 1666 1667 /* Attempt initchild to establish unit-address */ 1668 if (i_ddi_node_state(child) < DS_INITIALIZED) 1669 (void) ddi_initchild(self, child); 1670 1671 /* Verify state and non-NULL unit-address. */ 1672 if ((i_ddi_node_state(child) < DS_INITIALIZED) || 1673 (ddi_get_name_addr(child) == NULL)) 1674 continue; 1675 1676 /* Return "smp" child if unit-address matches. */ 1677 if (strcmp(ddi_get_name_addr(child), addr) == 0) 1678 return (child); 1679 } 1680 return (NULL); 1681 } 1682 1683 /* 1684 * Search for "smp" child of self at the specified address. If found, online 1685 * and return with a hold. Unlike general SCSI configuration, we can assume 1686 * the the device is actually there when we are called (i.e., device is 1687 * created by hotplug, not by bus_config). 1688 */ 1689 int 1690 smp_hba_bus_config(dev_info_t *self, char *addr, dev_info_t **childp) 1691 { 1692 dev_info_t *child; 1693 int circ; 1694 1695 ASSERT(self && addr && childp); 1696 *childp = NULL; 1697 1698 /* Search for "smp" child. */ 1699 scsi_hba_devi_enter(self, &circ); 1700 if ((child = smp_findchild(self, addr)) == NULL) { 1701 scsi_hba_devi_exit(self, circ); 1702 return (NDI_FAILURE); 1703 } 1704 1705 /* Attempt online. */ 1706 if (ndi_devi_online(child, 0) != NDI_SUCCESS) { 1707 scsi_hba_devi_exit(self, circ); 1708 return (NDI_FAILURE); 1709 } 1710 1711 /* On success, return with active hold. */ 1712 ndi_hold_devi(child); 1713 scsi_hba_devi_exit(self, circ); 1714 *childp = child; 1715 return (NDI_SUCCESS); 1716 } 1717 1718 1719 1720 /* Create "smp" child devinfo node at specified unit-address. */ 1721 int 1722 smp_hba_bus_config_taddr(dev_info_t *self, char *addr) 1723 { 1724 dev_info_t *child; 1725 int circ; 1726 1727 /* 1728 * NOTE: If we ever uses a generic node name (.vs. a driver name) 1729 * or define a 'compatible' property, this code will need to use 1730 * a 'probe' node (ala scsi_device support) to obtain identity 1731 * information from the device. 1732 */ 1733 1734 /* Search for "smp" child. */ 1735 scsi_hba_devi_enter(self, &circ); 1736 child = smp_findchild(self, addr); 1737 if (child) { 1738 /* Child exists, note if this was a new reinsert. */ 1739 if (ndi_devi_device_insert(child)) 1740 SCSI_HBA_LOG((_LOGCFG, self, NULL, 1741 "devinfo smp@%s device_reinsert", addr)); 1742 1743 scsi_hba_devi_exit(self, circ); 1744 return (NDI_SUCCESS); 1745 } 1746 1747 /* Allocate "smp" child devinfo node and establish flavor of child. */ 1748 ndi_devi_alloc_sleep(self, "smp", DEVI_SID_HP_NODEID, &child); 1749 ASSERT(child); 1750 ndi_flavor_set(child, SCSA_FLAVOR_SMP); 1751 1752 /* Add unit-address property to child. */ 1753 if (ndi_prop_update_string(DDI_DEV_T_NONE, child, 1754 SCSI_ADDR_PROP_TARGET_PORT, addr) != DDI_PROP_SUCCESS) { 1755 (void) ndi_devi_free(child); 1756 scsi_hba_devi_exit(self, circ); 1757 return (NDI_FAILURE); 1758 } 1759 1760 /* Attempt to online the new "smp" node. */ 1761 (void) ndi_devi_online(child, 0); 1762 1763 scsi_hba_devi_exit(self, circ); 1764 return (NDI_SUCCESS); 1765 } 1766 1767 /* 1768 * Wrapper to scsi_ua_get which takes a devinfo argument instead of a 1769 * scsi_device structure. 1770 */ 1771 static int 1772 scsi_busctl_ua(dev_info_t *child, char *addr, int maxlen) 1773 { 1774 struct scsi_device *sd; 1775 1776 /* limit ndi_devi_findchild_by_callback to expected flavor */ 1777 if (ndi_flavor_get(child) != SCSA_FLAVOR_SCSI_DEVICE) 1778 return (DDI_FAILURE); 1779 1780 /* nodes are named by tran_get_name or default "tgt,lun" */ 1781 sd = ddi_get_driver_private(child); 1782 if (sd && (scsi_ua_get(sd, addr, maxlen) == 1)) 1783 return (DDI_SUCCESS); 1784 1785 return (DDI_FAILURE); 1786 } 1787 1788 static int 1789 scsi_busctl_reportdev(dev_info_t *child) 1790 { 1791 dev_info_t *self = ddi_get_parent(child); 1792 struct scsi_device *sd = ddi_get_driver_private(child); 1793 scsi_hba_tran_t *tran; 1794 char ua[SCSI_MAXNAMELEN]; 1795 char ra[SCSI_MAXNAMELEN]; 1796 1797 SCSI_HBA_LOG((_LOG_TRACE, NULL, child, __func__)); 1798 1799 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 1800 ASSERT(tran && sd); 1801 if ((tran == NULL) || (sd == NULL)) 1802 return (DDI_FAILURE); 1803 1804 /* get the unit_address and bus_addr information */ 1805 if ((scsi_ua_get(sd, ua, sizeof (ua)) == 0) || 1806 (scsi_ua_get_reportdev(sd, ra, sizeof (ra)) == 0)) { 1807 SCSI_HBA_LOG((_LOG(WARN), NULL, child, "REPORTDEV failure")); 1808 return (DDI_FAILURE); 1809 } 1810 1811 if (tran->tran_get_name == NULL) 1812 SCSI_HBA_LOG((_LOG_NF(CONT), "?%s%d at %s%d: %s", 1813 ddi_driver_name(child), ddi_get_instance(child), 1814 ddi_driver_name(self), ddi_get_instance(self), ra)); 1815 else if (*ra) 1816 SCSI_HBA_LOG((_LOG_NF(CONT), 1817 "?%s%d at %s%d: unit-address %s: %s", 1818 ddi_driver_name(child), ddi_get_instance(child), 1819 ddi_driver_name(self), ddi_get_instance(self), ua, ra)); 1820 else 1821 SCSI_HBA_LOG((_LOG_NF(CONT), 1822 "?%s%d at %s%d: unit-address %s", 1823 ddi_driver_name(child), ddi_get_instance(child), 1824 ddi_driver_name(self), ddi_get_instance(self), ua)); 1825 1826 return (DDI_SUCCESS); 1827 } 1828 1829 1830 /* 1831 * scsi_busctl_initchild is called to initialize the SCSA transport for 1832 * communication with a particular child scsi target device. Successful 1833 * initialization requires properties on the node which describe the address 1834 * of the target device. If the address of the target device can't be 1835 * determined from properties then DDI_NOT_WELL_FORMED is returned. Nodes that 1836 * are DDI_NOT_WELL_FORMED are considered an implementation artifact and 1837 * are hidden from devinfo snapshots by calling ndi_devi_set_hidden(). 1838 * The child may be one of the following types of devinfo nodes: 1839 * 1840 * OBP node: 1841 * OBP does not enumerate target devices attached a SCSI bus. These 1842 * template/stub/wild-card nodes are a legacy artifact for support of old 1843 * driver loading methods. Since they have no properties, 1844 * DDI_NOT_WELL_FORMED will be returned. 1845 * 1846 * SID node: 1847 * The node may be either a: 1848 * o probe/barrier SID node 1849 * o a dynamic SID target node 1850 * 1851 * driver.conf node: The situation for this nexus is different than most. 1852 * Typically a driver.conf node definition is used to either define a 1853 * new child devinfo node or to further decorate (via merge) a SID 1854 * child with properties. In our case we use the nodes for *both* 1855 * purposes. 1856 * 1857 * In both the SID node and driver.conf node cases we must form the nodes 1858 * "@addr" from the well-known scsi(9P) device unit-address properties on 1859 * the node. 1860 * 1861 * For HBA drivers that implement the deprecated tran_get_name interface, 1862 * "@addr" construction involves having that driver interpret properties via 1863 * scsi_busctl_ua -> scsi_ua_get -> tran_get_name: there is no 1864 * requirement for the property names to be well-known. 1865 * 1866 * NOTE: We don't currently support "merge". When this support is added a 1867 * specific property, like "unit-address", should *always* identify a 1868 * driver.conf node that needs to be merged into a specific SID node. When 1869 * enumeration is enabled, a .conf node without the "unit-address" property 1870 * should be ignored. The best way to establish the "unit-address" property 1871 * would be to have the system assign parent= and unit-address= from an 1872 * instance=# driver.conf entry (by using the instance tree). 1873 */ 1874 static int 1875 scsi_busctl_initchild(dev_info_t *child) 1876 { 1877 dev_info_t *self = ddi_get_parent(child); 1878 dev_info_t *dup; 1879 scsi_hba_tran_t *tran; 1880 struct scsi_device *sd; 1881 scsi_hba_tran_t *tran_clone; 1882 char *class; 1883 int tgt; 1884 int lun; 1885 int sfunc; 1886 int err = DDI_FAILURE; 1887 char addr[SCSI_MAXNAMELEN]; 1888 1889 ASSERT(DEVI_BUSY_OWNED(self)); 1890 SCSI_HBA_LOG((_LOG(4), NULL, child, "init begin")); 1891 1892 /* 1893 * For a driver like fp with multiple upper-layer-protocols 1894 * it is possible for scsi_hba_init in _init to plumb SCSA 1895 * and have the load of fcp (which does scsi_hba_attach_setup) 1896 * to fail. In this case we may get here with a NULL hba. 1897 */ 1898 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 1899 if (tran == NULL) 1900 return (DDI_NOT_WELL_FORMED); 1901 1902 /* 1903 * OBP may create template/stub/wild-card nodes for legacy driver 1904 * loading methods. These nodes have no properties, so we lack the 1905 * addressing properties to initchild them. Hide the node and return 1906 * DDI_NOT_WELL_FORMED. 1907 * 1908 * Future: define/use a ndi_devi_has_properties(dip) type interface. 1909 * 1910 * NOTE: It would be nice if we could delete these ill formed nodes by 1911 * implementing a DDI_NOT_WELL_FORMED_DELETE return code. This can't 1912 * be done until leadville debug code removes its dependencies 1913 * on the devinfo still being present after a failed ndi_devi_online. 1914 */ 1915 if ((DEVI(child)->devi_hw_prop_ptr == NULL) && 1916 (DEVI(child)->devi_drv_prop_ptr == NULL) && 1917 (DEVI(child)->devi_sys_prop_ptr == NULL)) { 1918 SCSI_HBA_LOG((_LOG(4), NULL, child, 1919 "init failed: no properties")); 1920 ndi_devi_set_hidden(child); 1921 return (DDI_NOT_WELL_FORMED); 1922 } 1923 1924 /* get legacy SPI addressing properties */ 1925 if ((tgt = ddi_prop_get_int(DDI_DEV_T_ANY, child, 1926 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 1927 SCSI_ADDR_PROP_TARGET, -1)) == -1) { 1928 tgt = 0; 1929 /* 1930 * A driver.conf node for merging always has a target= property, 1931 * even if it is just a dummy that does not contain the real 1932 * target address. However drivers that register devids may 1933 * create stub driver.conf nodes without a target= property so 1934 * that pathological devid resolution works. Hide the stub 1935 * node and return DDI_NOT_WELL_FORMED. 1936 */ 1937 if (!scsi_hba_dev_is_sid(child)) { 1938 SCSI_HBA_LOG((_LOG(4), NULL, child, 1939 "init failed: stub .conf node")); 1940 ndi_devi_set_hidden(child); 1941 return (DDI_NOT_WELL_FORMED); 1942 } 1943 } 1944 lun = ddi_prop_get_int(DDI_DEV_T_ANY, child, 1945 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, SCSI_ADDR_PROP_LUN, 0); 1946 sfunc = ddi_prop_get_int(DDI_DEV_T_ANY, child, 1947 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, SCSI_ADDR_PROP_SFUNC, -1); 1948 1949 /* 1950 * The scsi_address structure may not specify all the addressing 1951 * information. For an old HBA that doesn't support tran_get_name 1952 * (most pre-SCSI-3 HBAs) the scsi_address structure is still used, 1953 * so the target property must exist and the LUN must be < 256. 1954 */ 1955 if ((tran->tran_get_name == NULL) && 1956 ((tgt >= USHRT_MAX) || (lun >= 256))) { 1957 SCSI_HBA_LOG((_LOG(1), NULL, child, 1958 "init failed: illegal/missing properties")); 1959 ndi_devi_set_hidden(child); 1960 return (DDI_NOT_WELL_FORMED); 1961 } 1962 1963 /* 1964 * We need to initialize a fair amount of our environment to invoke 1965 * tran_get_name (via scsi_busctl_ua and scsi_ua_get) to 1966 * produce the "@addr" name from addressing properties. Allocate and 1967 * initialize scsi device structure. 1968 */ 1969 sd = kmem_zalloc(sizeof (struct scsi_device), KM_SLEEP); 1970 mutex_init(&sd->sd_mutex, NULL, MUTEX_DRIVER, NULL); 1971 sd->sd_dev = child; 1972 sd->sd_pathinfo = NULL; 1973 sd->sd_uninit_prevent = 0; 1974 ddi_set_driver_private(child, sd); 1975 1976 if (tran->tran_hba_flags & SCSI_HBA_ADDR_COMPLEX) { 1977 /* 1978 * For a SCSI_HBA_ADDR_COMPLEX transport we store a pointer to 1979 * scsi_device in the scsi_address structure. This allows an 1980 * HBA driver to find its per-scsi_device private data 1981 * (accessible to the HBA given just the scsi_address by using 1982 * scsi_address_device(9F)/scsi_device_hba_private_get(9F)). 1983 */ 1984 sd->sd_address.a.a_sd = sd; 1985 tran_clone = NULL; 1986 } else { 1987 /* 1988 * Initialize the scsi_address so that a SCSI-2 target driver 1989 * talking to a SCSI-2 device on a SCSI-3 bus (spi) continues 1990 * to work. We skew the secondary function value so that we 1991 * can tell from the address structure if we are processing 1992 * a secondary function request. 1993 */ 1994 sd->sd_address.a_target = (ushort_t)tgt; 1995 sd->sd_address.a_lun = (uchar_t)lun; 1996 if (sfunc == -1) 1997 sd->sd_address.a_sublun = (uchar_t)0; 1998 else 1999 sd->sd_address.a_sublun = (uchar_t)sfunc + 1; 2000 2001 /* 2002 * NOTE: Don't limit LUNs to scsi_options value because a 2003 * scsi_device discovered via SPI dynamic enumeration might 2004 * still support SCMD_REPORT_LUNS. 2005 */ 2006 2007 /* 2008 * Deprecated: Use SCSI_HBA_ADDR_COMPLEX: 2009 * Clone transport structure if requested. Cloning allows 2010 * an HBA to maintain target-specific information if 2011 * necessary, such as target addressing information that 2012 * does not adhere to the scsi_address structure format. 2013 */ 2014 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CLONE) { 2015 tran_clone = kmem_alloc( 2016 sizeof (scsi_hba_tran_t), KM_SLEEP); 2017 bcopy((caddr_t)tran, 2018 (caddr_t)tran_clone, sizeof (scsi_hba_tran_t)); 2019 tran = tran_clone; 2020 tran->tran_sd = sd; 2021 } else { 2022 tran_clone = NULL; 2023 ASSERT(tran->tran_sd == NULL); 2024 } 2025 } 2026 2027 /* establish scsi_address pointer to the HBA's tran structure */ 2028 sd->sd_address.a_hba_tran = tran; 2029 2030 /* 2031 * This is a grotty hack that allows direct-access (non-scsa) drivers 2032 * (like chs, ata, and mlx which all make cmdk children) to put its 2033 * own vector in the 'a_hba_tran' field. When all the drivers that do 2034 * this are fixed, please remove this hack. 2035 * 2036 * NOTE: This hack is also shows up in the DEVP_TO_TRAN implementation 2037 * in scsi_confsubr.c. 2038 */ 2039 sd->sd_tran_safe = tran; 2040 2041 /* 2042 * If the class property is not already established, set it to "scsi". 2043 * This is done so that parent= driver.conf nodes have class. 2044 */ 2045 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 2046 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "class", 2047 &class) == DDI_PROP_SUCCESS) { 2048 ddi_prop_free(class); 2049 } else if (ndi_prop_update_string(DDI_DEV_T_NONE, child, 2050 "class", "scsi") != DDI_PROP_SUCCESS) { 2051 SCSI_HBA_LOG((_LOG(2), NULL, child, "init failed: class")); 2052 ndi_devi_set_hidden(child); 2053 err = DDI_NOT_WELL_FORMED; 2054 goto failure; 2055 } 2056 2057 /* Establish the @addr name of the child. */ 2058 *addr = '\0'; 2059 if (scsi_busctl_ua(child, addr, sizeof (addr)) != DDI_SUCCESS) { 2060 /* 2061 * Some driver.conf files add bogus target properties (relative 2062 * to their nexus representation of target) to their stub 2063 * nodes, causing the check above to not filter them. 2064 */ 2065 SCSI_HBA_LOG((_LOG(3), NULL, child, 2066 "init failed: scsi_busctl_ua call")); 2067 ndi_devi_set_hidden(child); 2068 err = DDI_NOT_WELL_FORMED; 2069 goto failure; 2070 } 2071 if (*addr == '\0') { 2072 SCSI_HBA_LOG((_LOG(2), NULL, child, "init failed: ua")); 2073 ndi_devi_set_hidden(child); 2074 err = DDI_NOT_WELL_FORMED; 2075 goto failure; 2076 } 2077 2078 /* Prevent duplicate nodes. */ 2079 dup = ndi_devi_findchild_by_callback(self, ddi_node_name(child), addr, 2080 scsi_busctl_ua); 2081 if (dup) { 2082 ASSERT(ndi_flavor_get(dup) == SCSA_FLAVOR_SCSI_DEVICE); 2083 if (ndi_flavor_get(dup) != SCSA_FLAVOR_SCSI_DEVICE) { 2084 SCSI_HBA_LOG((_LOG(1), NULL, child, 2085 "init failed: %s@%s: not SCSI_DEVICE flavored", 2086 ddi_node_name(child), addr)); 2087 goto failure; 2088 } 2089 if (dup != child) { 2090 SCSI_HBA_LOG((_LOG(4), NULL, child, 2091 "init failed: %s@%s: detected duplicate %p", 2092 ddi_node_name(child), addr, (void *)dup)); 2093 goto failure; 2094 } 2095 } 2096 2097 /* set the node @addr string */ 2098 ddi_set_name_addr(child, addr); 2099 2100 /* call HBA's target init entry point if it exists */ 2101 if (tran->tran_tgt_init != NULL) { 2102 SCSI_HBA_LOG((_LOG(4), NULL, child, "init tran_tgt_init")); 2103 sd->sd_tran_tgt_free_done = 0; 2104 if ((*tran->tran_tgt_init) 2105 (self, child, tran, sd) != DDI_SUCCESS) { 2106 scsi_enumeration_failed(child, -1, NULL, 2107 "tran_tgt_init"); 2108 goto failure; 2109 } 2110 } 2111 2112 SCSI_HBA_LOG((_LOG(3), NULL, child, "init successful")); 2113 return (DDI_SUCCESS); 2114 2115 failure: 2116 if (tran_clone) 2117 kmem_free(tran_clone, sizeof (scsi_hba_tran_t)); 2118 mutex_destroy(&sd->sd_mutex); 2119 kmem_free(sd, sizeof (*sd)); 2120 ddi_set_driver_private(child, NULL); 2121 ddi_set_name_addr(child, NULL); 2122 2123 return (err); /* remove the node */ 2124 } 2125 2126 static int 2127 scsi_busctl_uninitchild(dev_info_t *child) 2128 { 2129 dev_info_t *self = ddi_get_parent(child); 2130 struct scsi_device *sd = ddi_get_driver_private(child); 2131 scsi_hba_tran_t *tran; 2132 scsi_hba_tran_t *tran_clone; 2133 2134 ASSERT(DEVI_BUSY_OWNED(self)); 2135 2136 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 2137 ASSERT(tran && sd); 2138 if ((tran == NULL) || (sd == NULL)) 2139 return (DDI_FAILURE); 2140 2141 /* 2142 * We use sd_uninit_prevent to avoid uninitializing barrier/probe 2143 * nodes that are still in use. Since barrier/probe nodes are not 2144 * attached we can't prevent their state demotion via ndi_hold_devi. 2145 */ 2146 if (sd->sd_uninit_prevent) { 2147 SCSI_HBA_LOG((_LOG(2), NULL, child, "uninit prevented")); 2148 return (DDI_FAILURE); 2149 } 2150 2151 /* 2152 * Don't uninitialize a client node if it still has paths. 2153 */ 2154 if (MDI_CLIENT(child) && mdi_client_get_path_count(child)) { 2155 SCSI_HBA_LOG((_LOG(2), NULL, child, 2156 "uninit prevented, client has paths")); 2157 return (DDI_FAILURE); 2158 } 2159 2160 SCSI_HBA_LOG((_LOG(3), NULL, child, "uninit begin")); 2161 2162 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CLONE) { 2163 tran_clone = sd->sd_address.a_hba_tran; 2164 2165 /* ... grotty hack, involving sd_tran_safe, continued. */ 2166 if (tran_clone != sd->sd_tran_safe) { 2167 tran_clone = sd->sd_tran_safe; 2168 #ifdef DEBUG 2169 /* 2170 * Complain so things get fixed and hack can, at 2171 * some point in time, be removed. 2172 */ 2173 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 2174 "'%s' is corrupting a_hba_tran", sd->sd_dev ? 2175 ddi_driver_name(sd->sd_dev) : "unknown_driver")); 2176 #endif /* DEBUG */ 2177 } 2178 2179 ASSERT(tran_clone->tran_hba_flags & SCSI_HBA_TRAN_CLONE); 2180 ASSERT(tran_clone->tran_sd == sd); 2181 tran = tran_clone; 2182 } else { 2183 tran_clone = NULL; 2184 ASSERT(tran->tran_sd == NULL); 2185 } 2186 2187 /* 2188 * To simplify host adapter drivers we guarantee that multiple 2189 * tran_tgt_init(9E) calls of the same unit address are never 2190 * active at the same time. This requires that we always call 2191 * tran_tgt_free on probe/barrier nodes directly prior to 2192 * uninitchild. 2193 * 2194 * NOTE: To correctly support SCSI_HBA_TRAN_CLONE, we must use 2195 * the (possibly cloned) hba_tran pointer from the scsi_device 2196 * instead of hba_tran. 2197 */ 2198 if (tran->tran_tgt_free) { 2199 if (!sd->sd_tran_tgt_free_done) { 2200 SCSI_HBA_LOG((_LOG(4), NULL, child, 2201 "uninit tran_tgt_free")); 2202 (*tran->tran_tgt_free) (self, child, tran, sd); 2203 sd->sd_tran_tgt_free_done = 1; 2204 } else { 2205 SCSI_HBA_LOG((_LOG(4), NULL, child, 2206 "uninit tran_tgt_free already done")); 2207 } 2208 } 2209 2210 /* 2211 * If a inquiry data is still allocated (by scsi_probe()) we 2212 * free the allocation here. This keeps scsi_inq valid for the 2213 * same duration as the corresponding inquiry properties. It 2214 * also allows a tran_tgt_init() implementation that establishes 2215 * sd_inq to deal with deallocation in its tran_tgt_free 2216 * (setting sd_inq back to NULL) without upsetting the 2217 * framework. Moving the inquiry free here also allows setting 2218 * of sd_uninit_prevent to preserve the data for lun0 based 2219 * scsi_get_device_type_scsi_options() calls. 2220 */ 2221 if (sd->sd_inq) { 2222 kmem_free(sd->sd_inq, SUN_INQSIZE); 2223 sd->sd_inq = (struct scsi_inquiry *)NULL; 2224 } 2225 2226 mutex_destroy(&sd->sd_mutex); 2227 if (tran_clone) 2228 kmem_free(tran_clone, sizeof (scsi_hba_tran_t)); 2229 kmem_free(sd, sizeof (*sd)); 2230 2231 ddi_set_driver_private(child, NULL); 2232 SCSI_HBA_LOG((_LOG(3), NULL, child, "uninit complete")); 2233 ddi_set_name_addr(child, NULL); 2234 return (DDI_SUCCESS); 2235 } 2236 2237 static int 2238 iport_busctl_ua(dev_info_t *child, char *addr, int maxlen) 2239 { 2240 char *iport_ua; 2241 2242 /* limit ndi_devi_findchild_by_callback to expected flavor */ 2243 if (ndi_flavor_get(child) != SCSA_FLAVOR_IPORT) 2244 return (DDI_FAILURE); 2245 2246 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 2247 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 2248 SCSI_ADDR_PROP_IPORTUA, &iport_ua) != DDI_SUCCESS) { 2249 return (DDI_FAILURE); 2250 } 2251 2252 (void) snprintf(addr, maxlen, "%s", iport_ua); 2253 ddi_prop_free(iport_ua); 2254 return (DDI_SUCCESS); 2255 } 2256 2257 static int 2258 iport_busctl_reportdev(dev_info_t *child) 2259 { 2260 dev_info_t *self = ddi_get_parent(child); 2261 char *iport_ua; 2262 char *initiator_port = NULL; 2263 2264 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 2265 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 2266 SCSI_ADDR_PROP_IPORTUA, &iport_ua) != DDI_SUCCESS) 2267 return (DDI_FAILURE); 2268 2269 (void) ddi_prop_lookup_string(DDI_DEV_T_ANY, child, 2270 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 2271 SCSI_ADDR_PROP_INITIATOR_PORT, &initiator_port); 2272 2273 if (initiator_port) { 2274 SCSI_HBA_LOG((_LOG_NF(CONT), 2275 "?%s%d at %s%d: %s %s %s %s", 2276 ddi_driver_name(child), ddi_get_instance(child), 2277 ddi_driver_name(self), ddi_get_instance(self), 2278 SCSI_ADDR_PROP_INITIATOR_PORT, initiator_port, 2279 SCSI_ADDR_PROP_IPORTUA, iport_ua)); 2280 ddi_prop_free(initiator_port); 2281 } else { 2282 SCSI_HBA_LOG((_LOG_NF(CONT), "?%s%d at %s%d: %s %s", 2283 ddi_driver_name(child), ddi_get_instance(child), 2284 ddi_driver_name(self), ddi_get_instance(self), 2285 SCSI_ADDR_PROP_IPORTUA, iport_ua)); 2286 } 2287 ddi_prop_free(iport_ua); 2288 return (DDI_SUCCESS); 2289 } 2290 2291 /* initchild SCSA iport 'child' node */ 2292 static int 2293 iport_busctl_initchild(dev_info_t *child) 2294 { 2295 dev_info_t *self = ddi_get_parent(child); 2296 dev_info_t *dup = NULL; 2297 char addr[SCSI_MAXNAMELEN]; 2298 2299 if (iport_busctl_ua(child, addr, sizeof (addr)) != DDI_SUCCESS) 2300 return (DDI_NOT_WELL_FORMED); 2301 2302 /* Prevent duplicate nodes. */ 2303 dup = ndi_devi_findchild_by_callback(self, ddi_node_name(child), addr, 2304 iport_busctl_ua); 2305 if (dup) { 2306 ASSERT(ndi_flavor_get(dup) == SCSA_FLAVOR_IPORT); 2307 if (ndi_flavor_get(dup) != SCSA_FLAVOR_IPORT) { 2308 SCSI_HBA_LOG((_LOG(1), NULL, child, 2309 "init failed: %s@%s: not IPORT flavored", 2310 ddi_node_name(child), addr)); 2311 return (DDI_FAILURE); 2312 } 2313 if (dup != child) { 2314 SCSI_HBA_LOG((_LOG(4), NULL, child, 2315 "init failed: %s@%s: detected duplicate %p", 2316 ddi_node_name(child), addr, (void *)dup)); 2317 return (DDI_FAILURE); 2318 } 2319 } 2320 2321 /* set the node @addr string */ 2322 ddi_set_name_addr(child, addr); 2323 2324 return (DDI_SUCCESS); 2325 } 2326 2327 /* uninitchild SCSA iport 'child' node */ 2328 static int 2329 iport_busctl_uninitchild(dev_info_t *child) 2330 { 2331 ddi_set_name_addr(child, NULL); 2332 return (DDI_SUCCESS); 2333 } 2334 2335 /* Uninitialize scsi_device flavor of transport on SCSA iport 'child' node. */ 2336 static void 2337 iport_postdetach_tran_scsi_device(dev_info_t *child) 2338 { 2339 scsi_hba_tran_t *tran; 2340 2341 tran = ndi_flavorv_get(child, SCSA_FLAVOR_SCSI_DEVICE); 2342 if (tran == NULL) 2343 return; 2344 2345 scsa_tran_teardown(child, tran); 2346 scsa_nexus_teardown(child, tran); 2347 2348 ndi_flavorv_set(child, SCSA_FLAVOR_SCSI_DEVICE, NULL); 2349 scsi_hba_tran_free(tran); 2350 } 2351 2352 /* Initialize scsi_device flavor of transport on SCSA iport 'child' node. */ 2353 static void 2354 iport_preattach_tran_scsi_device(dev_info_t *child) 2355 { 2356 dev_info_t *hba = ddi_get_parent(child); 2357 scsi_hba_tran_t *htran; 2358 scsi_hba_tran_t *tran; 2359 2360 /* parent HBA node scsi_device tran is required */ 2361 htran = ndi_flavorv_get(hba, SCSA_FLAVOR_SCSI_DEVICE); 2362 ASSERT(htran); 2363 2364 /* Allocate iport child's scsi_device transport vector */ 2365 tran = scsi_hba_tran_alloc(child, SCSI_HBA_CANSLEEP); 2366 ASSERT(tran); 2367 2368 /* Structure-copy scsi_device transport of HBA to iport. */ 2369 *tran = *htran; 2370 2371 /* 2372 * Reset scsi_device transport fields not shared with the 2373 * parent, and not established below. 2374 */ 2375 tran->tran_open_flag = 0; 2376 tran->tran_hba_private = NULL; 2377 2378 /* Establish the devinfo context of this tran structure. */ 2379 tran->tran_iport_dip = child; 2380 2381 /* Clear SCSI_HBA_SCSA flags (except TA) */ 2382 tran->tran_hba_flags &= 2383 ~(SCSI_HBA_SCSA_FM | SCSI_HBA_SCSA_PHCI); /* clear parent state */ 2384 tran->tran_hba_flags |= SCSI_HBA_SCSA_TA; /* always TA */ 2385 tran->tran_hba_flags &= ~SCSI_HBA_HBA; /* never HBA */ 2386 2387 /* Establish flavor of transport (and ddi_get_driver_private()) */ 2388 ndi_flavorv_set(child, SCSA_FLAVOR_SCSI_DEVICE, tran); 2389 2390 /* Setup iport node */ 2391 if ((scsa_nexus_setup(child, tran) != DDI_SUCCESS) || 2392 (scsa_tran_setup(child, tran) != DDI_SUCCESS)) 2393 iport_postdetach_tran_scsi_device(child); 2394 } 2395 2396 /* Uninitialize smp_device flavor of transport on SCSA iport 'child' node. */ 2397 static void 2398 iport_postdetach_tran_smp_device(dev_info_t *child) 2399 { 2400 smp_hba_tran_t *tran; 2401 2402 tran = ndi_flavorv_get(child, SCSA_FLAVOR_SMP); 2403 if (tran == NULL) 2404 return; 2405 2406 ndi_flavorv_set(child, SCSA_FLAVOR_SMP, NULL); 2407 smp_hba_tran_free(tran); 2408 } 2409 2410 /* Initialize smp_device flavor of transport on SCSA iport 'child' node. */ 2411 static void 2412 iport_preattach_tran_smp_device(dev_info_t *child) 2413 { 2414 dev_info_t *hba = ddi_get_parent(child); 2415 smp_hba_tran_t *htran; 2416 smp_hba_tran_t *tran; 2417 2418 /* parent HBA node smp_device tran is optional */ 2419 htran = ndi_flavorv_get(hba, SCSA_FLAVOR_SMP); 2420 if (htran == NULL) { 2421 ndi_flavorv_set(child, SCSA_FLAVOR_SMP, NULL); 2422 return; 2423 } 2424 2425 /* Allocate iport child's smp_device transport vector */ 2426 tran = smp_hba_tran_alloc(child); 2427 2428 /* Structure-copy smp_device transport of HBA to iport. */ 2429 *tran = *htran; 2430 2431 /* Establish flavor of transport */ 2432 ndi_flavorv_set(child, SCSA_FLAVOR_SMP, tran); 2433 } 2434 2435 /* 2436 * Generic bus_ctl operations for SCSI HBA's, 2437 * hiding the busctl interface from the HBA. 2438 */ 2439 /*ARGSUSED*/ 2440 static int 2441 scsi_hba_bus_ctl( 2442 dev_info_t *self, 2443 dev_info_t *child, 2444 ddi_ctl_enum_t op, 2445 void *arg, 2446 void *result) 2447 { 2448 int child_flavor = 0; 2449 int val; 2450 ddi_dma_attr_t *attr; 2451 scsi_hba_tran_t *tran; 2452 struct attachspec *as; 2453 struct detachspec *ds; 2454 2455 /* For some ops, child is 'arg'. */ 2456 if ((op == DDI_CTLOPS_INITCHILD) || (op == DDI_CTLOPS_UNINITCHILD)) 2457 child = (dev_info_t *)arg; 2458 2459 /* Determine the flavor of the child: scsi, smp, iport */ 2460 child_flavor = ndi_flavor_get(child); 2461 2462 switch (op) { 2463 case DDI_CTLOPS_INITCHILD: 2464 switch (child_flavor) { 2465 case SCSA_FLAVOR_SCSI_DEVICE: 2466 return (scsi_busctl_initchild(child)); 2467 case SCSA_FLAVOR_SMP: 2468 return (smp_busctl_initchild(child)); 2469 case SCSA_FLAVOR_IPORT: 2470 return (iport_busctl_initchild(child)); 2471 default: 2472 return (DDI_FAILURE); 2473 } 2474 /* NOTREACHED */ 2475 2476 case DDI_CTLOPS_UNINITCHILD: 2477 switch (child_flavor) { 2478 case SCSA_FLAVOR_SCSI_DEVICE: 2479 return (scsi_busctl_uninitchild(child)); 2480 case SCSA_FLAVOR_SMP: 2481 return (smp_busctl_uninitchild(child)); 2482 case SCSA_FLAVOR_IPORT: 2483 return (iport_busctl_uninitchild(child)); 2484 default: 2485 return (DDI_FAILURE); 2486 } 2487 /* NOTREACHED */ 2488 2489 case DDI_CTLOPS_REPORTDEV: 2490 switch (child_flavor) { 2491 case SCSA_FLAVOR_SCSI_DEVICE: 2492 return (scsi_busctl_reportdev(child)); 2493 case SCSA_FLAVOR_SMP: 2494 return (smp_busctl_reportdev(child)); 2495 case SCSA_FLAVOR_IPORT: 2496 return (iport_busctl_reportdev(child)); 2497 default: 2498 return (DDI_FAILURE); 2499 } 2500 /* NOTREACHED */ 2501 2502 case DDI_CTLOPS_ATTACH: 2503 as = (struct attachspec *)arg; 2504 2505 if (child_flavor != SCSA_FLAVOR_IPORT) 2506 return (DDI_SUCCESS); 2507 2508 /* iport processing */ 2509 if (as->when == DDI_PRE) { 2510 /* setup pre attach(9E) */ 2511 iport_preattach_tran_scsi_device(child); 2512 iport_preattach_tran_smp_device(child); 2513 } else if ((as->when == DDI_POST) && 2514 (as->result != DDI_SUCCESS)) { 2515 /* cleanup if attach(9E) failed */ 2516 iport_postdetach_tran_scsi_device(child); 2517 iport_postdetach_tran_smp_device(child); 2518 } 2519 return (DDI_SUCCESS); 2520 2521 case DDI_CTLOPS_DETACH: 2522 ds = (struct detachspec *)arg; 2523 2524 if (child_flavor != SCSA_FLAVOR_IPORT) 2525 return (DDI_SUCCESS); 2526 2527 /* iport processing */ 2528 if ((ds->when == DDI_POST) && 2529 (ds->result == DDI_SUCCESS)) { 2530 /* cleanup if detach(9E) was successful */ 2531 iport_postdetach_tran_scsi_device(child); 2532 iport_postdetach_tran_smp_device(child); 2533 } 2534 return (DDI_SUCCESS); 2535 2536 case DDI_CTLOPS_IOMIN: 2537 tran = ddi_get_driver_private(self); 2538 ASSERT(tran); 2539 if (tran == NULL) 2540 return (DDI_FAILURE); 2541 2542 /* 2543 * The 'arg' value of nonzero indicates 'streaming' 2544 * mode. If in streaming mode, pick the largest 2545 * of our burstsizes available and say that that 2546 * is our minimum value (modulo what minxfer is). 2547 */ 2548 attr = &tran->tran_dma_attr; 2549 val = *((int *)result); 2550 val = maxbit(val, attr->dma_attr_minxfer); 2551 *((int *)result) = maxbit(val, ((intptr_t)arg ? 2552 (1<<ddi_ffs(attr->dma_attr_burstsizes)-1) : 2553 (1<<(ddi_fls(attr->dma_attr_burstsizes)-1)))); 2554 2555 return (ddi_ctlops(self, child, op, arg, result)); 2556 2557 case DDI_CTLOPS_SIDDEV: 2558 return (ndi_dev_is_persistent_node(child) ? 2559 DDI_SUCCESS : DDI_FAILURE); 2560 2561 case DDI_CTLOPS_POWER: 2562 return (DDI_SUCCESS); 2563 2564 /* 2565 * These ops correspond to functions that "shouldn't" be called 2566 * by a SCSI target driver. So we whine when we're called. 2567 */ 2568 case DDI_CTLOPS_DMAPMAPC: 2569 case DDI_CTLOPS_REPORTINT: 2570 case DDI_CTLOPS_REGSIZE: 2571 case DDI_CTLOPS_NREGS: 2572 case DDI_CTLOPS_SLAVEONLY: 2573 case DDI_CTLOPS_AFFINITY: 2574 case DDI_CTLOPS_POKE: 2575 case DDI_CTLOPS_PEEK: 2576 SCSI_HBA_LOG((_LOG(WARN), self, NULL, "invalid op (%d)", op)); 2577 return (DDI_FAILURE); 2578 2579 /* Everything else we pass up */ 2580 case DDI_CTLOPS_PTOB: 2581 case DDI_CTLOPS_BTOP: 2582 case DDI_CTLOPS_BTOPR: 2583 case DDI_CTLOPS_DVMAPAGESIZE: 2584 default: 2585 return (ddi_ctlops(self, child, op, arg, result)); 2586 } 2587 /* NOTREACHED */ 2588 } 2589 2590 /* 2591 * Private wrapper for scsi_pkt's allocated via scsi_hba_pkt_alloc() 2592 */ 2593 struct scsi_pkt_wrapper { 2594 struct scsi_pkt scsi_pkt; 2595 int pkt_wrapper_magic; 2596 int pkt_wrapper_len; 2597 }; 2598 2599 #if !defined(lint) 2600 _NOTE(SCHEME_PROTECTS_DATA("unique per thread", scsi_pkt_wrapper)) 2601 _NOTE(SCHEME_PROTECTS_DATA("Unshared Data", dev_ops)) 2602 #endif 2603 2604 /* 2605 * Called by an HBA to allocate a scsi_pkt 2606 */ 2607 /*ARGSUSED*/ 2608 struct scsi_pkt * 2609 scsi_hba_pkt_alloc( 2610 dev_info_t *self, 2611 struct scsi_address *ap, 2612 int cmdlen, 2613 int statuslen, 2614 int tgtlen, 2615 int hbalen, 2616 int (*callback)(caddr_t arg), 2617 caddr_t arg) 2618 { 2619 struct scsi_pkt *pkt; 2620 struct scsi_pkt_wrapper *hba_pkt; 2621 caddr_t p; 2622 int acmdlen, astatuslen, atgtlen, ahbalen; 2623 int pktlen; 2624 2625 /* Sanity check */ 2626 if (callback != SLEEP_FUNC && callback != NULL_FUNC) 2627 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 2628 "callback must be SLEEP_FUNC or NULL_FUNC")); 2629 2630 /* 2631 * Round up so everything gets allocated on long-word boundaries 2632 */ 2633 acmdlen = ROUNDUP(cmdlen); 2634 astatuslen = ROUNDUP(statuslen); 2635 atgtlen = ROUNDUP(tgtlen); 2636 ahbalen = ROUNDUP(hbalen); 2637 pktlen = sizeof (struct scsi_pkt_wrapper) + 2638 acmdlen + astatuslen + atgtlen + ahbalen; 2639 2640 hba_pkt = kmem_zalloc(pktlen, 2641 (callback == SLEEP_FUNC) ? KM_SLEEP : KM_NOSLEEP); 2642 if (hba_pkt == NULL) { 2643 ASSERT(callback == NULL_FUNC); 2644 return (NULL); 2645 } 2646 2647 /* 2648 * Set up our private info on this pkt 2649 */ 2650 hba_pkt->pkt_wrapper_len = pktlen; 2651 hba_pkt->pkt_wrapper_magic = PKT_WRAPPER_MAGIC; /* alloced correctly */ 2652 pkt = &hba_pkt->scsi_pkt; 2653 2654 /* 2655 * Set up pointers to private data areas, cdb, and status. 2656 */ 2657 p = (caddr_t)(hba_pkt + 1); 2658 if (hbalen > 0) { 2659 pkt->pkt_ha_private = (opaque_t)p; 2660 p += ahbalen; 2661 } 2662 if (tgtlen > 0) { 2663 pkt->pkt_private = (opaque_t)p; 2664 p += atgtlen; 2665 } 2666 if (statuslen > 0) { 2667 pkt->pkt_scbp = (uchar_t *)p; 2668 p += astatuslen; 2669 } 2670 if (cmdlen > 0) { 2671 pkt->pkt_cdbp = (uchar_t *)p; 2672 } 2673 2674 /* 2675 * Initialize the pkt's scsi_address 2676 */ 2677 pkt->pkt_address = *ap; 2678 2679 /* 2680 * NB: It may not be safe for drivers, esp target drivers, to depend 2681 * on the following fields being set until all the scsi_pkt 2682 * allocation violations discussed in scsi_pkt.h are all resolved. 2683 */ 2684 pkt->pkt_cdblen = cmdlen; 2685 pkt->pkt_tgtlen = tgtlen; 2686 pkt->pkt_scblen = statuslen; 2687 2688 return (pkt); 2689 } 2690 2691 /* 2692 * Called by an HBA to free a scsi_pkt 2693 */ 2694 /*ARGSUSED*/ 2695 void 2696 scsi_hba_pkt_free( 2697 struct scsi_address *ap, 2698 struct scsi_pkt *pkt) 2699 { 2700 kmem_free(pkt, ((struct scsi_pkt_wrapper *)pkt)->pkt_wrapper_len); 2701 } 2702 2703 /* 2704 * Return 1 if the scsi_pkt used a proper allocator. 2705 * 2706 * The DDI does not allow a driver to allocate it's own scsi_pkt(9S), a 2707 * driver should not have *any* compiled in dependencies on "sizeof (struct 2708 * scsi_pkt)". While this has been the case for many years, a number of 2709 * drivers have still not been fixed. This function can be used to detect 2710 * improperly allocated scsi_pkt structures, and produce messages identifying 2711 * drivers that need to be fixed. 2712 * 2713 * While drivers in violation are being fixed, this function can also 2714 * be used by the framework to detect packets that violated allocation 2715 * rules. 2716 * 2717 * NB: It is possible, but very unlikely, for this code to return a false 2718 * positive (finding correct magic, but for wrong reasons). Careful 2719 * consideration is needed for callers using this interface to condition 2720 * access to newer scsi_pkt fields (those after pkt_reason). 2721 * 2722 * NB: As an aid to minimizing the amount of work involved in 'fixing' legacy 2723 * drivers that violate scsi_*(9S) allocation rules, private 2724 * scsi_pkt_size()/scsi_size_clean() functions are available (see their 2725 * implementation for details). 2726 * 2727 * *** Non-legacy use of scsi_pkt_size() is discouraged. *** 2728 * 2729 * NB: When supporting broken HBA drivers is not longer a concern, this 2730 * code should be removed. 2731 */ 2732 int 2733 scsi_pkt_allocated_correctly(struct scsi_pkt *pkt) 2734 { 2735 struct scsi_pkt_wrapper *hba_pkt = (struct scsi_pkt_wrapper *)pkt; 2736 int magic; 2737 major_t major; 2738 #ifdef DEBUG 2739 int *pspwm, *pspcwm; 2740 2741 /* 2742 * We are getting scsi packets from two 'correct' wrapper schemes, 2743 * make sure we are looking at the same place in both to detect 2744 * proper allocation. 2745 */ 2746 pspwm = &((struct scsi_pkt_wrapper *)0)->pkt_wrapper_magic; 2747 pspcwm = &((struct scsi_pkt_cache_wrapper *)0)->pcw_magic; 2748 ASSERT(pspwm == pspcwm); 2749 #endif /* DEBUG */ 2750 2751 2752 /* 2753 * Check to see if driver is scsi_size_clean(), assume it 2754 * is using the scsi_pkt_size() interface everywhere it needs to 2755 * if the driver indicates it is scsi_size_clean(). 2756 */ 2757 major = ddi_driver_major(P_TO_TRAN(pkt)->tran_hba_dip); 2758 if (devnamesp[major].dn_flags & DN_SCSI_SIZE_CLEAN) 2759 return (1); /* ok */ 2760 2761 /* 2762 * Special case crossing a page boundary. If the scsi_pkt was not 2763 * allocated correctly, then across a page boundary we have a 2764 * fault hazard. 2765 */ 2766 if ((((uintptr_t)(&hba_pkt->scsi_pkt)) & MMU_PAGEMASK) == 2767 (((uintptr_t)(&hba_pkt->pkt_wrapper_magic)) & MMU_PAGEMASK)) { 2768 /* fastpath, no cross-page hazard */ 2769 magic = hba_pkt->pkt_wrapper_magic; 2770 } else { 2771 /* add protection for cross-page hazard */ 2772 if (ddi_peek32((dev_info_t *)NULL, 2773 &hba_pkt->pkt_wrapper_magic, &magic) == DDI_FAILURE) { 2774 return (0); /* violation */ 2775 } 2776 } 2777 2778 /* properly allocated packet always has correct magic */ 2779 return ((magic == PKT_WRAPPER_MAGIC) ? 1 : 0); 2780 } 2781 2782 /* 2783 * Private interfaces to simplify conversion of legacy drivers so they don't 2784 * depend on scsi_*(9S) size. Instead of using these private interface, HBA 2785 * drivers should use DDI sanctioned allocation methods: 2786 * 2787 * scsi_pkt Use scsi_hba_pkt_alloc(9F), or implement 2788 * tran_setup_pkt(9E). 2789 * 2790 * scsi_device You are doing something strange/special, a scsi_device 2791 * structure should only be allocated by scsi_hba.c 2792 * initchild code or scsi_vhci.c code. 2793 * 2794 * scsi_hba_tran Use scsi_hba_tran_alloc(9F). 2795 */ 2796 size_t 2797 scsi_pkt_size() 2798 { 2799 return (sizeof (struct scsi_pkt)); 2800 } 2801 2802 size_t 2803 scsi_hba_tran_size() 2804 { 2805 return (sizeof (scsi_hba_tran_t)); 2806 } 2807 2808 size_t 2809 scsi_device_size() 2810 { 2811 return (sizeof (struct scsi_device)); 2812 } 2813 2814 /* 2815 * Legacy compliance to scsi_pkt(9S) allocation rules through use of 2816 * scsi_pkt_size() is detected by the 'scsi-size-clean' driver.conf property 2817 * or an HBA driver calling to scsi_size_clean() from attach(9E). A driver 2818 * developer should only indicate that a legacy driver is clean after using 2819 * SCSI_SIZE_CLEAN_VERIFY to ensure compliance (see scsi_pkt.h). 2820 */ 2821 void 2822 scsi_size_clean(dev_info_t *self) 2823 { 2824 major_t major; 2825 struct devnames *dnp; 2826 2827 ASSERT(self); 2828 major = ddi_driver_major(self); 2829 ASSERT(major < devcnt); 2830 if (major >= devcnt) { 2831 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 2832 "scsi_pkt_size: bogus major: %d", major)); 2833 return; 2834 } 2835 2836 /* Set DN_SCSI_SIZE_CLEAN flag in dn_flags. */ 2837 dnp = &devnamesp[major]; 2838 if ((dnp->dn_flags & DN_SCSI_SIZE_CLEAN) == 0) { 2839 LOCK_DEV_OPS(&dnp->dn_lock); 2840 dnp->dn_flags |= DN_SCSI_SIZE_CLEAN; 2841 UNLOCK_DEV_OPS(&dnp->dn_lock); 2842 } 2843 } 2844 2845 2846 /* 2847 * Called by an HBA to map strings to capability indices 2848 */ 2849 int 2850 scsi_hba_lookup_capstr( 2851 char *capstr) 2852 { 2853 /* 2854 * Capability strings: only add entries to mask the legacy 2855 * '_' vs. '-' misery. All new capabilities should use '-', 2856 * and be captured be added to SCSI_CAP_ASCII. 2857 */ 2858 static struct cap_strings { 2859 char *cap_string; 2860 int cap_index; 2861 } cap_strings[] = { 2862 { "dma_max", SCSI_CAP_DMA_MAX }, 2863 { "msg_out", SCSI_CAP_MSG_OUT }, 2864 { "wide_xfer", SCSI_CAP_WIDE_XFER }, 2865 { NULL, 0 } 2866 }; 2867 static char *cap_ascii[] = SCSI_CAP_ASCII; 2868 char **cap; 2869 int i; 2870 struct cap_strings *cp; 2871 2872 for (cap = cap_ascii, i = 0; *cap != NULL; cap++, i++) 2873 if (strcmp(*cap, capstr) == 0) 2874 return (i); 2875 2876 for (cp = cap_strings; cp->cap_string != NULL; cp++) 2877 if (strcmp(cp->cap_string, capstr) == 0) 2878 return (cp->cap_index); 2879 2880 return (-1); 2881 } 2882 2883 /* 2884 * Called by an HBA to determine if the system is in 'panic' state. 2885 */ 2886 int 2887 scsi_hba_in_panic() 2888 { 2889 return (panicstr != NULL); 2890 } 2891 2892 /* 2893 * If a SCSI target driver attempts to mmap memory, 2894 * the buck stops here. 2895 */ 2896 /*ARGSUSED*/ 2897 static int 2898 scsi_hba_map_fault( 2899 dev_info_t *self, 2900 dev_info_t *child, 2901 struct hat *hat, 2902 struct seg *seg, 2903 caddr_t addr, 2904 struct devpage *dp, 2905 pfn_t pfn, 2906 uint_t prot, 2907 uint_t lock) 2908 { 2909 return (DDI_FAILURE); 2910 } 2911 2912 static int 2913 scsi_hba_get_eventcookie( 2914 dev_info_t *self, 2915 dev_info_t *child, 2916 char *name, 2917 ddi_eventcookie_t *eventp) 2918 { 2919 scsi_hba_tran_t *tran; 2920 2921 tran = ddi_get_driver_private(self); 2922 if (tran->tran_get_eventcookie && 2923 ((*tran->tran_get_eventcookie)(self, 2924 child, name, eventp) == DDI_SUCCESS)) { 2925 return (DDI_SUCCESS); 2926 } 2927 2928 return (ndi_busop_get_eventcookie(self, child, name, eventp)); 2929 } 2930 2931 static int 2932 scsi_hba_add_eventcall( 2933 dev_info_t *self, 2934 dev_info_t *child, 2935 ddi_eventcookie_t event, 2936 void (*callback)( 2937 dev_info_t *self, 2938 ddi_eventcookie_t event, 2939 void *arg, 2940 void *bus_impldata), 2941 void *arg, 2942 ddi_callback_id_t *cb_id) 2943 { 2944 scsi_hba_tran_t *tran; 2945 2946 tran = ddi_get_driver_private(self); 2947 if (tran->tran_add_eventcall && 2948 ((*tran->tran_add_eventcall)(self, child, 2949 event, callback, arg, cb_id) == DDI_SUCCESS)) { 2950 return (DDI_SUCCESS); 2951 } 2952 2953 return (DDI_FAILURE); 2954 } 2955 2956 static int 2957 scsi_hba_remove_eventcall(dev_info_t *self, ddi_callback_id_t cb_id) 2958 { 2959 scsi_hba_tran_t *tran; 2960 ASSERT(cb_id); 2961 2962 tran = ddi_get_driver_private(self); 2963 if (tran->tran_remove_eventcall && 2964 ((*tran->tran_remove_eventcall)( 2965 self, cb_id) == DDI_SUCCESS)) { 2966 return (DDI_SUCCESS); 2967 } 2968 2969 return (DDI_FAILURE); 2970 } 2971 2972 static int 2973 scsi_hba_post_event( 2974 dev_info_t *self, 2975 dev_info_t *child, 2976 ddi_eventcookie_t event, 2977 void *bus_impldata) 2978 { 2979 scsi_hba_tran_t *tran; 2980 2981 tran = ddi_get_driver_private(self); 2982 if (tran->tran_post_event && 2983 ((*tran->tran_post_event)(self, 2984 child, event, bus_impldata) == DDI_SUCCESS)) { 2985 return (DDI_SUCCESS); 2986 } 2987 2988 return (DDI_FAILURE); 2989 } 2990 2991 /* 2992 * Default getinfo(9e) for scsi_hba 2993 */ 2994 /* ARGSUSED */ 2995 static int 2996 scsi_hba_info(dev_info_t *self, ddi_info_cmd_t infocmd, void *arg, 2997 void **result) 2998 { 2999 int error = DDI_SUCCESS; 3000 3001 switch (infocmd) { 3002 case DDI_INFO_DEVT2INSTANCE: 3003 *result = (void *)(intptr_t)(MINOR2INST(getminor((dev_t)arg))); 3004 break; 3005 default: 3006 error = DDI_FAILURE; 3007 } 3008 return (error); 3009 } 3010 3011 /* 3012 * Default open and close routine for scsi_hba 3013 */ 3014 /* ARGSUSED */ 3015 int 3016 scsi_hba_open(dev_t *devp, int flags, int otyp, cred_t *credp) 3017 { 3018 dev_info_t *self; 3019 scsi_hba_tran_t *tran; 3020 int rv = 0; 3021 3022 if (otyp != OTYP_CHR) 3023 return (EINVAL); 3024 3025 if ((self = e_ddi_hold_devi_by_dev(*devp, 0)) == NULL) 3026 return (ENXIO); 3027 3028 tran = ddi_get_driver_private(self); 3029 if (tran == NULL) { 3030 ddi_release_devi(self); 3031 return (ENXIO); 3032 } 3033 3034 /* 3035 * tran_open_flag bit field: 3036 * 0: closed 3037 * 1: shared open by minor at bit position 3038 * 1 at 31st bit: exclusive open 3039 */ 3040 mutex_enter(&(tran->tran_open_lock)); 3041 if (flags & FEXCL) { 3042 if (tran->tran_open_flag != 0) { 3043 rv = EBUSY; /* already open */ 3044 } else { 3045 tran->tran_open_flag = TRAN_OPEN_EXCL; 3046 } 3047 } else { 3048 if (tran->tran_open_flag == TRAN_OPEN_EXCL) { 3049 rv = EBUSY; /* already excl. open */ 3050 } else { 3051 int minor = getminor(*devp) & TRAN_MINOR_MASK; 3052 tran->tran_open_flag |= (1 << minor); 3053 /* 3054 * Ensure that the last framework reserved minor 3055 * is unused. Otherwise, the exclusive open 3056 * mechanism may break. 3057 */ 3058 ASSERT(minor != 31); 3059 } 3060 } 3061 mutex_exit(&(tran->tran_open_lock)); 3062 3063 ddi_release_devi(self); 3064 return (rv); 3065 } 3066 3067 /* ARGSUSED */ 3068 int 3069 scsi_hba_close(dev_t dev, int flag, int otyp, cred_t *credp) 3070 { 3071 dev_info_t *self; 3072 scsi_hba_tran_t *tran; 3073 3074 if (otyp != OTYP_CHR) 3075 return (EINVAL); 3076 3077 if ((self = e_ddi_hold_devi_by_dev(dev, 0)) == NULL) 3078 return (ENXIO); 3079 3080 tran = ddi_get_driver_private(self); 3081 if (tran == NULL) { 3082 ddi_release_devi(self); 3083 return (ENXIO); 3084 } 3085 3086 mutex_enter(&(tran->tran_open_lock)); 3087 if (tran->tran_open_flag == TRAN_OPEN_EXCL) { 3088 tran->tran_open_flag = 0; 3089 } else { 3090 int minor = getminor(dev) & TRAN_MINOR_MASK; 3091 tran->tran_open_flag &= ~(1 << minor); 3092 } 3093 mutex_exit(&(tran->tran_open_lock)); 3094 3095 ddi_release_devi(self); 3096 return (0); 3097 } 3098 3099 /* 3100 * standard ioctl commands for SCSI hotplugging 3101 */ 3102 /* ARGSUSED */ 3103 int 3104 scsi_hba_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *credp, 3105 int *rvalp) 3106 { 3107 dev_info_t *self; 3108 struct devctl_iocdata *dcp = NULL; 3109 dev_info_t *child = NULL; 3110 mdi_pathinfo_t *path = NULL; 3111 struct scsi_device *sd; 3112 scsi_hba_tran_t *tran; 3113 uint_t bus_state; 3114 int rv = 0; 3115 int circ; 3116 char *name; 3117 char *addr; 3118 3119 self = e_ddi_hold_devi_by_dev(dev, 0); 3120 if (self == NULL) { 3121 rv = ENXIO; 3122 goto out; 3123 } 3124 3125 tran = ddi_get_driver_private(self); 3126 if (tran == NULL) { 3127 rv = ENXIO; 3128 goto out; 3129 } 3130 3131 /* Ioctls for which the generic implementation suffices. */ 3132 switch (cmd) { 3133 case DEVCTL_BUS_GETSTATE: 3134 rv = ndi_devctl_ioctl(self, cmd, arg, mode, 0); 3135 goto out; 3136 } 3137 3138 /* read devctl ioctl data */ 3139 if (ndi_dc_allochdl((void *)arg, &dcp) != NDI_SUCCESS) { 3140 rv = EFAULT; 3141 goto out; 3142 } 3143 3144 /* Ioctls that require child identification */ 3145 switch (cmd) { 3146 case DEVCTL_DEVICE_GETSTATE: 3147 case DEVCTL_DEVICE_ONLINE: 3148 case DEVCTL_DEVICE_OFFLINE: 3149 case DEVCTL_DEVICE_REMOVE: 3150 case DEVCTL_DEVICE_RESET: 3151 name = ndi_dc_getname(dcp); 3152 addr = ndi_dc_getaddr(dcp); 3153 if ((name == NULL) || (addr == NULL)) { 3154 rv = EINVAL; 3155 goto out; 3156 } 3157 3158 /* 3159 * Find child with name@addr - might find a devinfo 3160 * child (child), a pathinfo child (path), or nothing. 3161 */ 3162 scsi_hba_devi_enter(self, &circ); 3163 3164 (void) scsi_findchild(self, name, addr, 1, &child, &path, NULL); 3165 if (path) { 3166 /* Found a pathinfo */ 3167 ASSERT(path && (child == NULL)); 3168 mdi_hold_path(path); 3169 scsi_hba_devi_exit_phci(self, circ); 3170 sd = NULL; 3171 } else if (child) { 3172 /* Found a devinfo */ 3173 ASSERT(child && (path == NULL)); 3174 3175 /* verify scsi_device of child */ 3176 if (ndi_flavor_get(child) == SCSA_FLAVOR_SCSI_DEVICE) 3177 sd = ddi_get_driver_private(child); 3178 else 3179 sd = NULL; 3180 } else { 3181 ASSERT((path == NULL) && (child == NULL)); 3182 scsi_hba_devi_exit(self, circ); 3183 rv = ENXIO; /* found nothing */ 3184 goto out; 3185 } 3186 break; 3187 3188 case DEVCTL_BUS_RESETALL: /* ioctl that operate on any child */ 3189 /* 3190 * Find a child's scsi_address so we can invoke tran_reset. 3191 * 3192 * Future: If no child exists, we could fake a child. This will 3193 * be a enhancement for the future - for now, we fall back to 3194 * BUS_RESET. 3195 */ 3196 scsi_hba_devi_enter(self, &circ); 3197 child = ddi_get_child(self); 3198 sd = NULL; 3199 while (child) { 3200 /* verify scsi_device of child */ 3201 if (ndi_flavor_get(child) == SCSA_FLAVOR_SCSI_DEVICE) 3202 sd = ddi_get_driver_private(child); 3203 if (sd != NULL) { 3204 /* 3205 * NOTE: node has a scsi_device structure, so 3206 * it must be initialized. 3207 */ 3208 ndi_hold_devi(child); 3209 break; 3210 } 3211 child = ddi_get_next_sibling(child); 3212 } 3213 scsi_hba_devi_exit(self, circ); 3214 break; 3215 } 3216 3217 switch (cmd) { 3218 case DEVCTL_DEVICE_GETSTATE: 3219 if (path) { 3220 if (mdi_dc_return_dev_state(path, dcp) != MDI_SUCCESS) 3221 rv = EFAULT; 3222 } else if (child) { 3223 if (ndi_dc_return_dev_state(child, dcp) != NDI_SUCCESS) 3224 rv = EFAULT; 3225 } else { 3226 rv = ENXIO; 3227 } 3228 break; 3229 3230 case DEVCTL_DEVICE_RESET: 3231 if (sd == NULL) { 3232 rv = ENOTTY; 3233 break; 3234 } 3235 if (tran->tran_reset == NULL) { 3236 rv = ENOTSUP; 3237 break; 3238 } 3239 3240 /* Start with the small stick */ 3241 if (scsi_reset(&sd->sd_address, RESET_LUN) == 1) 3242 break; /* LUN reset worked */ 3243 if (scsi_reset(&sd->sd_address, RESET_TARGET) != 1) 3244 rv = EIO; /* Target reset failed */ 3245 break; 3246 3247 case DEVCTL_BUS_QUIESCE: 3248 if ((ndi_get_bus_state(self, &bus_state) == NDI_SUCCESS) && 3249 (bus_state == BUS_QUIESCED)) 3250 rv = EALREADY; 3251 else if (tran->tran_quiesce == NULL) 3252 rv = ENOTSUP; /* man ioctl(7I) says ENOTTY */ 3253 else if (tran->tran_quiesce(self) != 0) 3254 rv = EIO; 3255 else if (ndi_set_bus_state(self, BUS_QUIESCED) != NDI_SUCCESS) 3256 rv = EIO; 3257 break; 3258 3259 case DEVCTL_BUS_UNQUIESCE: 3260 if ((ndi_get_bus_state(self, &bus_state) == NDI_SUCCESS) && 3261 (bus_state == BUS_ACTIVE)) 3262 rv = EALREADY; 3263 else if (tran->tran_unquiesce == NULL) 3264 rv = ENOTSUP; /* man ioctl(7I) says ENOTTY */ 3265 else if (tran->tran_unquiesce(self) != 0) 3266 rv = EIO; 3267 else if (ndi_set_bus_state(self, BUS_ACTIVE) != NDI_SUCCESS) 3268 rv = EIO; 3269 break; 3270 3271 case DEVCTL_BUS_RESET: 3272 if (tran->tran_bus_reset == NULL) 3273 rv = ENOTSUP; /* man ioctl(7I) says ENOTTY */ 3274 else if (tran->tran_bus_reset(self, RESET_BUS) != 1) 3275 rv = EIO; 3276 break; 3277 3278 case DEVCTL_BUS_RESETALL: 3279 if ((sd != NULL) && 3280 (scsi_reset(&sd->sd_address, RESET_ALL) == 1)) { 3281 break; /* reset all worked */ 3282 } 3283 if (tran->tran_bus_reset == NULL) { 3284 rv = ENOTSUP; /* man ioctl(7I) says ENOTTY */ 3285 break; 3286 } 3287 if (tran->tran_bus_reset(self, RESET_BUS) != 1) 3288 rv = EIO; /* bus reset failed */ 3289 break; 3290 3291 case DEVCTL_BUS_CONFIGURE: 3292 if (ndi_devi_config(self, NDI_DEVFS_CLEAN | NDI_DEVI_PERSIST | 3293 NDI_CONFIG_REPROBE) != NDI_SUCCESS) { 3294 rv = EIO; 3295 } 3296 break; 3297 3298 case DEVCTL_BUS_UNCONFIGURE: 3299 if (ndi_devi_unconfig(self, 3300 NDI_DEVFS_CLEAN | NDI_DEVI_REMOVE) != NDI_SUCCESS) { 3301 rv = EBUSY; 3302 } 3303 break; 3304 3305 case DEVCTL_DEVICE_ONLINE: 3306 ASSERT(child || path); 3307 if (path) { 3308 if (mdi_pi_online(path, NDI_USER_REQ) != MDI_SUCCESS) 3309 rv = EIO; 3310 } else { 3311 if (ndi_devi_online(child, 0) != NDI_SUCCESS) 3312 rv = EIO; 3313 } 3314 break; 3315 3316 case DEVCTL_DEVICE_OFFLINE: 3317 ASSERT(child || path); 3318 if (sd != NULL) 3319 (void) scsi_clear_task_set(&sd->sd_address); 3320 if (path) { 3321 if (mdi_pi_offline(path, NDI_USER_REQ) != MDI_SUCCESS) 3322 rv = EIO; 3323 } else { 3324 if (ndi_devi_offline(child, 3325 NDI_DEVFS_CLEAN) != NDI_SUCCESS) 3326 rv = EIO; 3327 } 3328 break; 3329 3330 case DEVCTL_DEVICE_REMOVE: 3331 ASSERT(child || path); 3332 if (sd != NULL) 3333 (void) scsi_clear_task_set(&sd->sd_address); 3334 if (path) { 3335 /* NOTE: don't pass NDI_DEVI_REMOVE to mdi_pi_offline */ 3336 if (mdi_pi_offline(path, NDI_USER_REQ) == MDI_SUCCESS) { 3337 scsi_hba_devi_enter_phci(self, &circ); 3338 mdi_rele_path(path); 3339 3340 /* ... here is the DEVICE_REMOVE part. */ 3341 (void) mdi_pi_free(path, 0); 3342 path = NULL; 3343 } else { 3344 rv = EIO; 3345 } 3346 } else { 3347 if (ndi_devi_offline(child, 3348 NDI_DEVFS_CLEAN | NDI_DEVI_REMOVE) != NDI_SUCCESS) 3349 rv = EIO; 3350 } 3351 break; 3352 3353 default: 3354 ASSERT(dcp != NULL); 3355 rv = ENOTTY; 3356 break; 3357 } 3358 3359 /* all done -- clean up and return */ 3360 out: 3361 /* release hold on what we found */ 3362 if (path) { 3363 scsi_hba_devi_enter_phci(self, &circ); 3364 mdi_rele_path(path); 3365 } 3366 if (path || child) 3367 scsi_hba_devi_exit(self, circ); 3368 3369 if (dcp) 3370 ndi_dc_freehdl(dcp); 3371 3372 if (self) 3373 ddi_release_devi(self); 3374 3375 *rvalp = rv; 3376 3377 return (rv); 3378 } 3379 3380 /*ARGSUSED*/ 3381 static int 3382 scsi_hba_fm_init_child(dev_info_t *self, dev_info_t *child, int cap, 3383 ddi_iblock_cookie_t *ibc) 3384 { 3385 scsi_hba_tran_t *tran = ddi_get_driver_private(self); 3386 3387 return (tran ? tran->tran_fm_capable : scsi_fm_capable); 3388 } 3389 3390 static int 3391 scsi_hba_bus_power(dev_info_t *self, void *impl_arg, pm_bus_power_op_t op, 3392 void *arg, void *result) 3393 { 3394 scsi_hba_tran_t *tran; 3395 3396 tran = ddi_get_driver_private(self); 3397 if (tran && tran->tran_bus_power) { 3398 return (tran->tran_bus_power(self, impl_arg, 3399 op, arg, result)); 3400 } 3401 3402 return (pm_busop_bus_power(self, impl_arg, op, arg, result)); 3403 } 3404 3405 /* 3406 * Return the lun64 value from a address string: "addr,lun[,sfunc]". Either 3407 * the lun is after the first ',' or the entire address string is the lun. 3408 * Return SCSI_LUN64_ILLEGAL if the format is incorrect. A lun64 is at most 3409 * 16 hex digits long. 3410 * 3411 * If the address string specified has incorrect syntax (busconfig one of 3412 * bogus /devices path) then scsi_addr_to_lun64 can return SCSI_LUN64_ILLEGAL. 3413 */ 3414 static scsi_lun64_t 3415 scsi_addr_to_lun64(char *addr) 3416 { 3417 scsi_lun64_t lun64; 3418 char *s; 3419 int i; 3420 3421 if (addr) { 3422 s = strchr(addr, ','); /* "addr,lun" */ 3423 if (s) 3424 s++; /* skip ',', at lun */ 3425 else 3426 s = addr; /* "lun" */ 3427 3428 for (lun64 = 0, i = 0; *s && (i < 16); s++, i++) { 3429 if (*s >= '0' && *s <= '9') 3430 lun64 = (lun64 << 4) + (*s - '0'); 3431 else if (*s >= 'A' && *s <= 'F') 3432 lun64 = (lun64 << 4) + 10 + (*s - 'A'); 3433 else if (*s >= 'a' && *s <= 'f') 3434 lun64 = (lun64 << 4) + 10 + (*s - 'a'); 3435 else 3436 break; 3437 } 3438 if (*s && (*s != ',')) /* [,sfunc] is OK */ 3439 lun64 = SCSI_LUN64_ILLEGAL; 3440 } else 3441 lun64 = SCSI_LUN64_ILLEGAL; 3442 3443 if (lun64 == SCSI_LUN64_ILLEGAL) 3444 SCSI_HBA_LOG((_LOG(2), NULL, NULL, 3445 "addr_to_lun64 %s lun %" PRIlun64, 3446 addr ? addr : "NULL", lun64)); 3447 return (lun64); 3448 } 3449 3450 /* 3451 * Return the sfunc value from a address string: "addr,lun[,sfunc]". Either the 3452 * sfunc is after the second ',' or the entire address string is the sfunc. 3453 * Return -1 if there is only one ',' in the address string or the string is 3454 * invalid. An sfunc is at most two hex digits long. 3455 */ 3456 static int 3457 scsi_addr_to_sfunc(char *addr) 3458 { 3459 int sfunc; 3460 char *s; 3461 int i; 3462 3463 if (addr) { 3464 s = strchr(addr, ','); /* "addr,lun" */ 3465 if (s) { 3466 s++; /* skip ',', at lun */ 3467 s = strchr(s, ','); /* "lun,sfunc" */ 3468 if (s == NULL) 3469 return (-1); /* no ",sfunc" */ 3470 s++; /* skip ',', at sfunc */ 3471 } else 3472 s = addr; /* "sfunc" */ 3473 3474 for (sfunc = 0, i = 0; *s && (i < 2); s++, i++) { 3475 if (*s >= '0' && *s <= '9') 3476 sfunc = (sfunc << 4) + (*s - '0'); 3477 else if (*s >= 'A' && *s <= 'F') 3478 sfunc = (sfunc << 4) + 10 + (*s - 'A'); 3479 else if (*s >= 'a' && *s <= 'f') 3480 sfunc = (sfunc << 4) + 10 + (*s - 'a'); 3481 else 3482 break; 3483 } 3484 if (*s) 3485 sfunc = -1; /* illegal */ 3486 } else 3487 sfunc = -1; 3488 return (sfunc); 3489 } 3490 3491 /* 3492 * Convert scsi ascii string data to NULL terminated (semi) legal IEEE 1275 3493 * "compatible" (name) property form. 3494 * 3495 * For ASCII INQUIRY data, a one-way conversion algorithm is needed to take 3496 * SCSI_ASCII (20h - 7Eh) to a 1275-like compatible form. The 1275 spec allows 3497 * letters, digits, one ",", and ". _ + -", all limited by a maximum 31 3498 * character length. Since ", ." are used as separators in the compatible 3499 * string itself, they are converted to "_". All SCSI_ASCII characters that 3500 * are illegal in 1275, as well as any illegal SCSI_ASCII characters 3501 * encountered, are converted to "_". To reduce length, trailing blanks are 3502 * trimmed from SCSI_ASCII fields prior to conversion. 3503 * 3504 * Example: SCSI_ASCII "ST32550W SUN2.1G" -> "ST32550W_SUN2_1G" 3505 * 3506 * NOTE: the 1275 string form is always less than or equal to the scsi form. 3507 */ 3508 static char * 3509 string_scsi_to_1275(char *s_1275, char *s_scsi, int len) 3510 { 3511 (void) strncpy(s_1275, s_scsi, len); 3512 s_1275[len--] = '\0'; 3513 3514 while (len >= 0) { 3515 if (s_1275[len] == ' ') 3516 s_1275[len--] = '\0'; /* trim trailing " " */ 3517 else 3518 break; 3519 } 3520 3521 while (len >= 0) { 3522 if (((s_1275[len] >= 'a') && (s_1275[len] <= 'z')) || 3523 ((s_1275[len] >= 'A') && (s_1275[len] <= 'Z')) || 3524 ((s_1275[len] >= '0') && (s_1275[len] <= '9')) || 3525 (s_1275[len] == '_') || 3526 (s_1275[len] == '+') || 3527 (s_1275[len] == '-')) 3528 len--; /* legal 1275 */ 3529 else 3530 s_1275[len--] = '_'; /* illegal SCSI_ASCII | 1275 */ 3531 } 3532 3533 return (s_1275); 3534 } 3535 3536 /* 3537 * Given the inquiry data, binding_set, and dtype_node for a scsi device, 3538 * return the nodename and compatible property for the device. The "compatible" 3539 * concept comes from IEEE-1275. The compatible information is returned is in 3540 * the correct form for direct use defining the "compatible" string array 3541 * property. Internally, "compatible" is also used to determine the nodename 3542 * to return. 3543 * 3544 * This function is provided as a separate entry point for use by drivers that 3545 * currently issue their own non-SCSA inquiry command and perform their own 3546 * node creation based their own private compiled in tables. Converting these 3547 * drivers to use this interface provides a quick easy way of obtaining 3548 * consistency as well as the flexibility associated with the 1275 techniques. 3549 * 3550 * The dtype_node is passed as a separate argument (instead of having the 3551 * implementation use inq_dtype). It indicates that information about 3552 * a secondary function embedded service should be produced. 3553 * 3554 * Callers must always use scsi_hba_nodename_compatible_free, even if 3555 * *nodenamep is null, to free the nodename and compatible information 3556 * when done. 3557 * 3558 * If a nodename can't be determined then **compatiblep will point to a 3559 * diagnostic string containing all the compatible forms. 3560 * 3561 * NOTE: some compatible strings may violate the 31 character restriction 3562 * imposed by IEEE-1275. This is not a problem because Solaris does not care 3563 * about this 31 character limit. 3564 * 3565 * Each compatible form belongs to a form-group. The form-groups currently 3566 * defined are generic ("scsiclass"), binding-set ("scsa.b"), and failover 3567 * ("scsa.f"). 3568 * 3569 * The following compatible forms, in high to low precedence 3570 * order, are defined for SCSI target device nodes. 3571 * 3572 * scsiclass,DDEEFFF.vVVVVVVVV.pPPPPPPPPPPPPPPPP.rRRRR (1 *1&2) 3573 * scsiclass,DDEE.vVVVVVVVV.pPPPPPPPPPPPPPPPP.rRRRR (2 *1) 3574 * scsiclass,DDFFF.vVVVVVVVV.pPPPPPPPPPPPPPPPP.rRRRR (3 *2) 3575 * scsiclass,DD.vVVVVVVVV.pPPPPPPPPPPPPPPPP.rRRRR (4) 3576 * scsiclass,DDEEFFF.vVVVVVVVV.pPPPPPPPPPPPPPPPP (5 *1&2) 3577 * scsiclass,DDEE.vVVVVVVVV.pPPPPPPPPPPPPPPPP (6 *1) 3578 * scsiclass,DDFFF.vVVVVVVVV.pPPPPPPPPPPPPPPPP (7 *2) 3579 * scsiclass,DD.vVVVVVVVV.pPPPPPPPPPPPPPPPP (8) 3580 * scsa,DD.bBBBBBBBB (8.5 *3) 3581 * scsiclass,DDEEFFF (9 *1&2) 3582 * scsiclass,DDEE (10 *1) 3583 * scsiclass,DDFFF (11 *2) 3584 * scsiclass,DD (12) 3585 * scsa.fFFF (12.5 *4) 3586 * scsiclass (13) 3587 * 3588 * *1 only produced on a secondary function node 3589 * *2 only produced when generic form-group flags exist. 3590 * *3 only produced when binding-set form-group legacy support is needed 3591 * *4 only produced when failover form-group flags exist. 3592 * 3593 * where: 3594 * 3595 * v is the letter 'v'. Denotest the 3596 * beginning of VVVVVVVV. 3597 * 3598 * VVVVVVVV Translated scsi_vendor. 3599 * 3600 * p is the letter 'p'. Denotes the 3601 * beginning of PPPPPPPPPPPPPPPP. 3602 * 3603 * PPPPPPPPPPPPPPPP Translated scsi_product. 3604 * 3605 * r is the letter 'r'. Denotes the 3606 * beginning of RRRR. 3607 * 3608 * RRRR Translated scsi_revision. 3609 * 3610 * DD is a two digit ASCII hexadecimal 3611 * number. The value of the two digits is 3612 * based one the SCSI "Peripheral device 3613 * type" command set associated with the 3614 * node. On a primary node this is the 3615 * scsi_dtype of the primary command set, 3616 * on a secondary node this is the 3617 * scsi_dtype associated with the secondary 3618 * function embedded command set. 3619 * 3620 * EE Same encoding used for DD. This form is 3621 * only generated on secondary function 3622 * nodes. The DD secondary function is embedded 3623 * in an EE device. 3624 * 3625 * FFF Concatenation, in alphabetical order, 3626 * of the flag characters within a form-group. 3627 * For a given form-group, the following 3628 * flags are defined. 3629 * 3630 * scsiclass: (generic form-group): 3631 * R Removable_Media: Used when 3632 * inq_rmb is set. 3633 * S SAF-TE device: Used when 3634 * inquiry information indicates 3635 * SAF-TE devices. 3636 * 3637 * scsa.f: (failover form-group): 3638 * E Explicit Target_Port_Group: Used 3639 * when inq_tpgse is set and 'G' is 3640 * alse present. 3641 * G GUID: Used when a GUID can be 3642 * generated for the device. 3643 * I Implicit Target_Port_Group: Used 3644 * when inq_tpgs is set and 'G' is 3645 * also present. 3646 * 3647 * Forms using FFF are only be generated 3648 * if there are applicable flag 3649 * characters. 3650 * 3651 * b is the letter 'b'. Denotes the 3652 * beginning of BBBBBBBB. 3653 * 3654 * BBBBBBBB Binding-set. Operating System Specific: 3655 * scsi-binding-set property of HBA. 3656 */ 3657 #define NCOMPAT (1 + (13 + 2) + 1) 3658 #define COMPAT_LONGEST (strlen( \ 3659 "scsiclass,DDEEFFF.vVVVVVVVV.pPPPPPPPPPPPPPPPP.rRRRR" + 1)) 3660 3661 /* 3662 * Private version with extra device 'identity' arguments to allow code 3663 * to determine GUID FFF support. 3664 */ 3665 static void 3666 scsi_hba_ident_nodename_compatible_get(struct scsi_inquiry *inq, 3667 uchar_t *inq80, size_t inq80len, uchar_t *inq83, size_t inq83len, 3668 char *binding_set, int dtype_node, char *compat0, 3669 char **nodenamep, char **drivernamep, 3670 char ***compatiblep, int *ncompatiblep) 3671 { 3672 char vid[sizeof (inq->inq_vid) + 1 ]; 3673 char pid[sizeof (inq->inq_pid) + 1]; 3674 char rev[sizeof (inq->inq_revision) + 1]; 3675 char gf[sizeof ("RS\0")]; 3676 char ff[sizeof ("EGI\0")]; 3677 int dtype_device; 3678 int ncompat; /* number of compatible */ 3679 char **compatp; /* compatible ptrs */ 3680 int i; 3681 char *nname; /* nodename */ 3682 char *dname; /* driver name */ 3683 char **csp; 3684 char *p; 3685 int tlen; 3686 int len; 3687 major_t major; 3688 ddi_devid_t devid; 3689 char *guid; 3690 uchar_t *iqd = (uchar_t *)inq; 3691 3692 /* 3693 * Nodename_aliases: This table was originally designed to be 3694 * implemented via a new nodename_aliases file - a peer to the 3695 * driver_aliases that selects a nodename based on compatible 3696 * forms in much the same say driver_aliases is used to select 3697 * driver bindings from compatible forms. Each compatible form 3698 * is an 'alias'. Until a more general need for a 3699 * nodename_aliases file exists, which may never occur, the 3700 * scsi mappings are described here via a compiled in table. 3701 * 3702 * This table contains nodename mappings for self-identifying 3703 * scsi devices enumerated by the Solaris kernel. For a given 3704 * device, the highest precedence "compatible" form with a 3705 * mapping is used to select the nodename for the device. This 3706 * will typically be a generic nodename, however in some legacy 3707 * compatibility cases a driver nodename mapping may be selected. 3708 * 3709 * Because of possible breakage associated with switching SCSI 3710 * target devices from driver nodenames to generic nodenames, 3711 * we are currently unable to support generic nodenames for all 3712 * SCSI devices (binding-sets). Although /devices paths are 3713 * defined as unstable, avoiding possible breakage is 3714 * important. Some of the newer SCSI transports (USB) already 3715 * use generic nodenames. All new SCSI transports and target 3716 * devices should use generic nodenames. At times this decision 3717 * may be architecture dependent (sparc .vs. intel) based on when 3718 * a transport was supported on a particular architecture. 3719 * 3720 * We provide a base set of generic nodename mappings based on 3721 * scsiclass dtype and higher-precedence driver nodename 3722 * mappings based on scsa "binding-set" to cover legacy 3723 * issues. The binding-set is typically associated with 3724 * "scsi-binding-set" property value of the HBA. The legacy 3725 * mappings are provided independent of whether the driver they 3726 * refer to is installed. This allows a correctly named node 3727 * be created at discovery time, and binding to occur when/if 3728 * an add_drv of the legacy driver occurs. 3729 * 3730 * We also have mappings for legacy SUN hardware that 3731 * misidentifies itself (enclosure services which identify 3732 * themselves as processors). All future hardware should use 3733 * the correct dtype. 3734 * 3735 * As SCSI HBAs are modified to use the SCSA interfaces for 3736 * self-identifying SCSI target devices (PSARC/2004/116) the 3737 * nodename_aliases table (PSARC/2004/420) should be augmented 3738 * with legacy mappings in order to maintain compatibility with 3739 * existing /devices paths, especially for devices that house 3740 * an OS. Failure to do this may cause upgrade problems. 3741 * Additions for new target devices or transports should not 3742 * add scsa binding-set compatible mappings. 3743 */ 3744 static struct nodename_aliases { 3745 char *na_nodename; /* nodename */ 3746 char *na_alias; /* compatible form match */ 3747 } na[] = { 3748 /* # mapping to generic nodenames based on scsi dtype */ 3749 {"disk", "scsiclass,00"}, 3750 {"tape", "scsiclass,01"}, 3751 {"printer", "scsiclass,02"}, 3752 {"processor", "scsiclass,03"}, 3753 {"worm", "scsiclass,04"}, 3754 {"cdrom", "scsiclass,05"}, 3755 {"scanner", "scsiclass,06"}, 3756 {"optical-disk", "scsiclass,07"}, 3757 {"medium-changer", "scsiclass,08"}, 3758 {"obsolete", "scsiclass,09"}, 3759 {"prepress-a", "scsiclass,0a"}, 3760 {"prepress-b", "scsiclass,0b"}, 3761 {"array-controller", "scsiclass,0c"}, 3762 {"enclosure", "scsiclass,0d"}, 3763 {"disk", "scsiclass,0e"}, 3764 {"card-reader", "scsiclass,0f"}, 3765 {"bridge", "scsiclass,10"}, 3766 {"object-store", "scsiclass,11"}, 3767 {"reserved", "scsiclass,12"}, 3768 {"reserved", "scsiclass,13"}, 3769 {"reserved", "scsiclass,14"}, 3770 {"reserved", "scsiclass,15"}, 3771 {"reserved", "scsiclass,16"}, 3772 {"reserved", "scsiclass,17"}, 3773 {"reserved", "scsiclass,18"}, 3774 {"reserved", "scsiclass,19"}, 3775 {"reserved", "scsiclass,1a"}, 3776 {"reserved", "scsiclass,1b"}, 3777 {"reserved", "scsiclass,1c"}, 3778 {"reserved", "scsiclass,1d"}, 3779 {"well-known-lun", "scsiclass,1e"}, 3780 {"unknown", "scsiclass,1f"}, 3781 3782 #ifdef sparc 3783 /* # legacy mapping to driver nodenames for fcp binding-set */ 3784 {"ssd", "scsa,00.bfcp"}, 3785 {"st", "scsa,01.bfcp"}, 3786 {"sgen", "scsa,08.bfcp"}, 3787 {"ses", "scsa,0d.bfcp"}, 3788 3789 /* # legacy mapping to driver nodenames for vhci binding-set */ 3790 {"ssd", "scsa,00.bvhci"}, 3791 {"st", "scsa,01.bvhci"}, 3792 {"sgen", "scsa,08.bvhci"}, 3793 {"ses", "scsa,0d.bvhci"}, 3794 #else /* sparc */ 3795 /* # for x86 fcp and vhci use generic nodenames */ 3796 #endif /* sparc */ 3797 3798 /* # legacy mapping to driver nodenames for spi binding-set */ 3799 {"sd", "scsa,00.bspi"}, 3800 {"sd", "scsa,05.bspi"}, 3801 {"sd", "scsa,07.bspi"}, 3802 {"st", "scsa,01.bspi"}, 3803 {"ses", "scsa,0d.bspi"}, 3804 3805 /* # SUN misidentified spi hardware */ 3806 {"ses", "scsiclass,03.vSUN.pD2"}, 3807 {"ses", "scsiclass,03.vSYMBIOS.pD1000"}, 3808 3809 /* # legacy mapping to driver nodenames for atapi binding-set */ 3810 {"sd", "scsa,00.batapi"}, 3811 {"sd", "scsa,05.batapi"}, 3812 {"sd", "scsa,07.batapi"}, 3813 {"st", "scsa,01.batapi"}, 3814 {"unknown", "scsa,0d.batapi"}, 3815 3816 /* # legacy mapping to generic nodenames for usb binding-set */ 3817 {"disk", "scsa,05.busb"}, 3818 {"disk", "scsa,07.busb"}, 3819 {"changer", "scsa,08.busb"}, 3820 {"comm", "scsa,09.busb"}, 3821 {"array_ctlr", "scsa,0c.busb"}, 3822 {"esi", "scsa,0d.busb"}, 3823 3824 /* 3825 * mapping nodenames for mpt based on scsi dtype 3826 * for being compatible with the original node names 3827 * under mpt controller 3828 */ 3829 {"sd", "scsa,00.bmpt"}, 3830 {"sd", "scsa,05.bmpt"}, 3831 {"sd", "scsa,07.bmpt"}, 3832 {"st", "scsa,01.bmpt"}, 3833 {"ses", "scsa,0d.bmpt"}, 3834 {"sgen", "scsa,08.bmpt"}, 3835 {NULL, NULL} 3836 }; 3837 struct nodename_aliases *nap; 3838 3839 /* NOTE: drivernamep can be NULL */ 3840 ASSERT(nodenamep && compatiblep && ncompatiblep && 3841 (binding_set == NULL || (strlen(binding_set) <= 8))); 3842 if ((nodenamep == NULL) || (compatiblep == NULL) || 3843 (ncompatiblep == NULL)) 3844 return; 3845 3846 /* 3847 * In order to reduce runtime we allocate one block of memory that 3848 * contains both the NULL terminated array of pointers to compatible 3849 * forms and the individual compatible strings. This block is 3850 * somewhat larger than needed, but is short lived - it only exists 3851 * until the caller can transfer the information into the "compatible" 3852 * string array property and call scsi_hba_nodename_compatible_free. 3853 */ 3854 tlen = NCOMPAT * COMPAT_LONGEST; 3855 compatp = kmem_alloc((NCOMPAT * sizeof (char *)) + tlen, KM_SLEEP); 3856 3857 /* convert inquiry data from SCSI ASCII to 1275 string */ 3858 (void) string_scsi_to_1275(vid, inq->inq_vid, 3859 sizeof (inq->inq_vid)); 3860 (void) string_scsi_to_1275(pid, inq->inq_pid, 3861 sizeof (inq->inq_pid)); 3862 (void) string_scsi_to_1275(rev, inq->inq_revision, 3863 sizeof (inq->inq_revision)); 3864 ASSERT((strlen(vid) <= sizeof (inq->inq_vid)) && 3865 (strlen(pid) <= sizeof (inq->inq_pid)) && 3866 (strlen(rev) <= sizeof (inq->inq_revision))); 3867 3868 /* 3869 * Form flags in ***ALPHABETICAL*** order within form-group: 3870 * 3871 * NOTE: When adding a new flag to an existing form-group, careful 3872 * consideration must be given to not breaking existing bindings 3873 * based on that form-group. 3874 */ 3875 3876 /* 3877 * generic form-group flags 3878 * R removable: 3879 * Set when inq_rmb is set and for well known scsi dtypes. For a 3880 * bus where the entire device is removable (like USB), we expect 3881 * the HBA to intercept the inquiry data and set inq_rmb. 3882 * Since OBP does not distinguish removable media in its generic 3883 * name selection we avoid setting the 'R' flag if the root is not 3884 * yet mounted. 3885 * S SAF-TE device 3886 * Set when the device type is SAT-TE. 3887 */ 3888 i = 0; 3889 dtype_device = inq->inq_dtype & DTYPE_MASK; 3890 if (modrootloaded && (inq->inq_rmb || 3891 (dtype_device == DTYPE_WORM) || 3892 (dtype_device == DTYPE_RODIRECT) || 3893 (dtype_device == DTYPE_OPTICAL))) 3894 gf[i++] = 'R'; /* removable */ 3895 gf[i] = '\0'; 3896 3897 if (modrootloaded && 3898 (dtype_device == DTYPE_PROCESSOR) && 3899 (strncmp((char *)&iqd[44], "SAF-TE", 4) == 0)) 3900 gf[i++] = 'S'; 3901 gf[i] = '\0'; 3902 3903 /* 3904 * failover form-group flags 3905 * E Explicit Target_Port_Group_Supported: 3906 * Set for a device that has a GUID if inq_tpgse also set. 3907 * G GUID: 3908 * Set when we have identity information, can determine a devid 3909 * from the identity information, and can generate a guid from 3910 * that devid. 3911 * I Implicit Target_Port_Group_Supported: 3912 * Set for a device that has a GUID if inq_tpgs also set. 3913 */ 3914 i = 0; 3915 if ((inq80 || inq83) && 3916 (ddi_devid_scsi_encode(DEVID_SCSI_ENCODE_VERSION_LATEST, NULL, 3917 (uchar_t *)inq, sizeof (*inq), inq80, inq80len, inq83, inq83len, 3918 &devid) == DDI_SUCCESS)) { 3919 guid = ddi_devid_to_guid(devid); 3920 ddi_devid_free(devid); 3921 } else 3922 guid = NULL; 3923 if (guid && (inq->inq_tpgs & TPGS_FAILOVER_EXPLICIT)) 3924 ff[i++] = 'E'; /* EXPLICIT TPGS */ 3925 if (guid) 3926 ff[i++] = 'G'; /* GUID */ 3927 if (guid && (inq->inq_tpgs & TPGS_FAILOVER_IMPLICIT)) 3928 ff[i++] = 'I'; /* IMPLICIT TPGS */ 3929 ff[i] = '\0'; 3930 if (guid) 3931 ddi_devid_free_guid(guid); 3932 3933 /* 3934 * Construct all applicable compatible forms. See comment at the 3935 * head of the function for a description of the compatible forms. 3936 */ 3937 csp = compatp; 3938 p = (char *)(compatp + NCOMPAT); 3939 3940 /* ( 0) driver (optional, not documented in scsi(4)) */ 3941 if (compat0) { 3942 *csp++ = p; 3943 (void) snprintf(p, tlen, "%s", compat0); 3944 len = strlen(p) + 1; 3945 p += len; 3946 tlen -= len; 3947 } 3948 3949 /* ( 1) scsiclass,DDEEFFF.vV.pP.rR */ 3950 if ((dtype_device != dtype_node) && *gf && *vid && *pid && *rev) { 3951 *csp++ = p; 3952 (void) snprintf(p, tlen, "scsiclass,%02x%02x%s.v%s.p%s.r%s", 3953 dtype_node, dtype_device, gf, vid, pid, rev); 3954 len = strlen(p) + 1; 3955 p += len; 3956 tlen -= len; 3957 } 3958 3959 /* ( 2) scsiclass,DDEE.vV.pP.rR */ 3960 if ((dtype_device != dtype_node) && *vid && *pid && *rev) { 3961 *csp++ = p; 3962 (void) snprintf(p, tlen, "scsiclass,%02x%02x.v%s.p%s.r%s", 3963 dtype_node, dtype_device, vid, pid, rev); 3964 len = strlen(p) + 1; 3965 p += len; 3966 tlen -= len; 3967 } 3968 3969 /* ( 3) scsiclass,DDFFF.vV.pP.rR */ 3970 if (*gf && *vid && *pid && *rev) { 3971 *csp++ = p; 3972 (void) snprintf(p, tlen, "scsiclass,%02x%s.v%s.p%s.r%s", 3973 dtype_node, gf, vid, pid, rev); 3974 len = strlen(p) + 1; 3975 p += len; 3976 tlen -= len; 3977 } 3978 3979 /* ( 4) scsiclass,DD.vV.pP.rR */ 3980 if (*vid && *pid && rev) { 3981 *csp++ = p; 3982 (void) snprintf(p, tlen, "scsiclass,%02x.v%s.p%s.r%s", 3983 dtype_node, vid, pid, rev); 3984 len = strlen(p) + 1; 3985 p += len; 3986 tlen -= len; 3987 } 3988 3989 /* ( 5) scsiclass,DDEEFFF.vV.pP */ 3990 if ((dtype_device != dtype_node) && *gf && *vid && *pid) { 3991 *csp++ = p; 3992 (void) snprintf(p, tlen, "scsiclass,%02x%02x%s.v%s.p%s", 3993 dtype_node, dtype_device, gf, vid, pid); 3994 len = strlen(p) + 1; 3995 p += len; 3996 tlen -= len; 3997 } 3998 3999 /* ( 6) scsiclass,DDEE.vV.pP */ 4000 if ((dtype_device != dtype_node) && *vid && *pid) { 4001 *csp++ = p; 4002 (void) snprintf(p, tlen, "scsiclass,%02x%02x.v%s.p%s", 4003 dtype_node, dtype_device, vid, pid); 4004 len = strlen(p) + 1; 4005 p += len; 4006 tlen -= len; 4007 } 4008 4009 /* ( 7) scsiclass,DDFFF.vV.pP */ 4010 if (*gf && *vid && *pid) { 4011 *csp++ = p; 4012 (void) snprintf(p, tlen, "scsiclass,%02x%s.v%s.p%s", 4013 dtype_node, gf, vid, pid); 4014 len = strlen(p) + 1; 4015 p += len; 4016 tlen -= len; 4017 } 4018 4019 /* ( 8) scsiclass,DD.vV.pP */ 4020 if (*vid && *pid) { 4021 *csp++ = p; 4022 (void) snprintf(p, tlen, "scsiclass,%02x.v%s.p%s", 4023 dtype_node, vid, pid); 4024 len = strlen(p) + 1; 4025 p += len; 4026 tlen -= len; 4027 } 4028 4029 /* (8.5) scsa,DD.bB (not documented in scsi(4)) */ 4030 if (binding_set) { 4031 *csp++ = p; 4032 (void) snprintf(p, tlen, "scsa,%02x.b%s", 4033 dtype_node, binding_set); 4034 len = strlen(p) + 1; 4035 p += len; 4036 tlen -= len; 4037 } 4038 4039 /* ( 9) scsiclass,DDEEFFF */ 4040 if ((dtype_device != dtype_node) && *gf) { 4041 *csp++ = p; 4042 (void) snprintf(p, tlen, "scsiclass,%02x%02x%s", 4043 dtype_node, dtype_device, gf); 4044 len = strlen(p) + 1; 4045 p += len; 4046 tlen -= len; 4047 } 4048 4049 /* (10) scsiclass,DDEE */ 4050 if (dtype_device != dtype_node) { 4051 *csp++ = p; 4052 (void) snprintf(p, tlen, "scsiclass,%02x%02x", 4053 dtype_node, dtype_device); 4054 len = strlen(p) + 1; 4055 p += len; 4056 tlen -= len; 4057 } 4058 4059 /* (11) scsiclass,DDFFF */ 4060 if (*gf) { 4061 *csp++ = p; 4062 (void) snprintf(p, tlen, "scsiclass,%02x%s", 4063 dtype_node, gf); 4064 len = strlen(p) + 1; 4065 p += len; 4066 tlen -= len; 4067 } 4068 4069 /* (12) scsiclass,DD */ 4070 *csp++ = p; 4071 (void) snprintf(p, tlen, "scsiclass,%02x", dtype_node); 4072 len = strlen(p) + 1; 4073 p += len; 4074 tlen -= len; 4075 4076 /* (12.5) scsa.fFFF */ 4077 if (*ff) { 4078 *csp++ = p; 4079 (void) snprintf(p, tlen, "scsa.f%s", ff); 4080 len = strlen(p) + 1; 4081 p += len; 4082 tlen -= len; 4083 } 4084 4085 /* (13) scsiclass */ 4086 *csp++ = p; 4087 (void) snprintf(p, tlen, "scsiclass"); 4088 len = strlen(p) + 1; 4089 p += len; 4090 tlen -= len; 4091 ASSERT(tlen >= 0); 4092 4093 *csp = NULL; /* NULL terminate array of pointers */ 4094 ncompat = csp - compatp; 4095 4096 /* 4097 * When determining a nodename, a nodename_aliases specified 4098 * mapping has precedence over using a driver_aliases specified 4099 * driver binding as a nodename. 4100 * 4101 * See if any of the compatible forms have a nodename_aliases 4102 * specified nodename. These mappings are described by 4103 * nodename_aliases entries like: 4104 * 4105 * disk "scsiclass,00" 4106 * enclosure "scsiclass,03.vSYMBIOS.pD1000" 4107 * ssd "scsa,00.bfcp" 4108 * 4109 * All nodename_aliases mappings should idealy be to generic 4110 * names, however a higher precedence legacy mapping to a 4111 * driver name may exist. The highest precedence mapping 4112 * provides the nodename, so legacy driver nodename mappings 4113 * (if they exist) take precedence over generic nodename 4114 * mappings. 4115 */ 4116 for (nname = NULL, csp = compatp; (nname == NULL) && *csp; csp++) { 4117 for (nap = na; nap->na_nodename; nap++) { 4118 if (strcmp(*csp, nap->na_alias) == 0) { 4119 nname = nap->na_nodename; 4120 break; 4121 } 4122 } 4123 } 4124 4125 /* 4126 * Determine the driver name based on compatible (which may 4127 * have the passed in compat0 as the first item). The driver_aliases 4128 * file has entries like 4129 * 4130 * sd "scsiclass,00" 4131 * 4132 * that map compatible forms to specific drivers. These entries are 4133 * established by add_drv/update_drv. We use the most specific 4134 * driver binding as the nodename. This matches the eventual 4135 * ddi_driver_compatible_major() binding that will be 4136 * established by bind_node() 4137 */ 4138 for (dname = NULL, csp = compatp; *csp; csp++) { 4139 major = ddi_name_to_major(*csp); 4140 if ((major == DDI_MAJOR_T_NONE) || 4141 (devnamesp[major].dn_flags & DN_DRIVER_REMOVED)) 4142 continue; 4143 if (dname = ddi_major_to_name(major)) 4144 break; 4145 } 4146 4147 /* 4148 * If no nodename_aliases mapping exists then use the 4149 * driver_aliases specified driver binding as a nodename. 4150 */ 4151 if (nname == NULL) 4152 nname = dname; 4153 4154 /* return results */ 4155 if (nname) { 4156 *nodenamep = kmem_alloc(strlen(nname) + 1, KM_SLEEP); 4157 (void) strcpy(*nodenamep, nname); 4158 } else { 4159 *nodenamep = NULL; 4160 4161 /* 4162 * If no nodename could be determined return a special 4163 * 'compatible' to be used for a diagnostic message. This 4164 * compatible contains all compatible forms concatenated 4165 * into a single string pointed to by the first element. 4166 */ 4167 for (csp = compatp; *(csp + 1); csp++) 4168 *((*csp) + strlen(*csp)) = ' '; 4169 *(compatp + 1) = NULL; 4170 ncompat = 1; 4171 4172 } 4173 if (drivernamep) { 4174 if (dname) { 4175 *drivernamep = kmem_alloc(strlen(dname) + 1, KM_SLEEP); 4176 (void) strcpy(*drivernamep, dname); 4177 } else 4178 *drivernamep = NULL; 4179 } 4180 *compatiblep = compatp; 4181 *ncompatiblep = ncompat; 4182 } 4183 4184 /* 4185 * Free allocations associated with scsi_hba_ident_nodename_compatible_get. 4186 */ 4187 static void 4188 scsi_hba_ident_nodename_compatible_free(char *nodename, char *drivername, 4189 char **compatible) 4190 { 4191 if (nodename) 4192 kmem_free(nodename, strlen(nodename) + 1); 4193 if (drivername) 4194 kmem_free(drivername, strlen(drivername) + 1); 4195 if (compatible) 4196 kmem_free(compatible, (NCOMPAT * sizeof (char *)) + 4197 (NCOMPAT * COMPAT_LONGEST)); 4198 } 4199 4200 void 4201 scsi_hba_nodename_compatible_get(struct scsi_inquiry *inq, 4202 char *binding_set, int dtype_node, char *compat0, 4203 char **nodenamep, char ***compatiblep, int *ncompatiblep) 4204 { 4205 scsi_hba_ident_nodename_compatible_get(inq, 4206 NULL, 0, NULL, 0, binding_set, dtype_node, compat0, nodenamep, 4207 NULL, compatiblep, ncompatiblep); 4208 } 4209 4210 void 4211 scsi_hba_nodename_compatible_free(char *nodename, char **compatible) 4212 { 4213 scsi_hba_ident_nodename_compatible_free(nodename, NULL, compatible); 4214 } 4215 4216 /* return the unit_address associated with a scsi_device */ 4217 char * 4218 scsi_device_unit_address(struct scsi_device *sd) 4219 { 4220 mdi_pathinfo_t *pip; 4221 4222 ASSERT(sd && sd->sd_dev); 4223 if ((sd == NULL) || (sd->sd_dev == NULL)) 4224 return (NULL); 4225 4226 pip = (mdi_pathinfo_t *)sd->sd_pathinfo; 4227 if (pip) 4228 return (mdi_pi_get_addr(pip)); 4229 else 4230 return (ddi_get_name_addr(sd->sd_dev)); 4231 } 4232 4233 /* scsi_device property interfaces */ 4234 #define _TYPE_DEFINED(flags) \ 4235 (((flags & SCSI_DEVICE_PROP_TYPE_MSK) == SCSI_DEVICE_PROP_PATH) || \ 4236 ((flags & SCSI_DEVICE_PROP_TYPE_MSK) == SCSI_DEVICE_PROP_DEVICE)) 4237 4238 #define _DEVICE_PIP(sd, flags) \ 4239 ((((flags & SCSI_DEVICE_PROP_TYPE_MSK) == SCSI_DEVICE_PROP_PATH) && \ 4240 sd->sd_pathinfo) ? (mdi_pathinfo_t *)sd->sd_pathinfo : NULL) 4241 4242 int 4243 scsi_device_prop_get_int(struct scsi_device *sd, uint_t flags, 4244 char *name, int defval) 4245 { 4246 mdi_pathinfo_t *pip; 4247 int v = defval; 4248 int data; 4249 int rv; 4250 4251 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4252 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4253 !_TYPE_DEFINED(flags)) 4254 return (v); 4255 4256 pip = _DEVICE_PIP(sd, flags); 4257 if (pip) { 4258 rv = mdi_prop_lookup_int(pip, name, &data); 4259 if (rv == DDI_PROP_SUCCESS) 4260 v = data; 4261 } else 4262 v = ddi_prop_get_int(DDI_DEV_T_ANY, sd->sd_dev, 4263 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, name, v); 4264 return (v); 4265 } 4266 4267 4268 int64_t 4269 scsi_device_prop_get_int64(struct scsi_device *sd, uint_t flags, 4270 char *name, int64_t defval) 4271 { 4272 mdi_pathinfo_t *pip; 4273 int64_t v = defval; 4274 int64_t data; 4275 int rv; 4276 4277 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4278 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4279 !_TYPE_DEFINED(flags)) 4280 return (v); 4281 4282 pip = _DEVICE_PIP(sd, flags); 4283 if (pip) { 4284 rv = mdi_prop_lookup_int64(pip, name, &data); 4285 if (rv == DDI_PROP_SUCCESS) 4286 v = data; 4287 } else 4288 v = ddi_prop_get_int64(DDI_DEV_T_ANY, sd->sd_dev, 4289 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, name, v); 4290 return (v); 4291 } 4292 4293 int 4294 scsi_device_prop_lookup_byte_array(struct scsi_device *sd, uint_t flags, 4295 char *name, uchar_t **data, uint_t *nelements) 4296 { 4297 mdi_pathinfo_t *pip; 4298 int rv; 4299 4300 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4301 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4302 !_TYPE_DEFINED(flags)) 4303 return (DDI_PROP_INVAL_ARG); 4304 4305 pip = _DEVICE_PIP(sd, flags); 4306 if (pip) 4307 rv = mdi_prop_lookup_byte_array(pip, name, data, nelements); 4308 else 4309 rv = ddi_prop_lookup_byte_array(DDI_DEV_T_ANY, sd->sd_dev, 4310 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4311 name, data, nelements); 4312 return (rv); 4313 } 4314 4315 int 4316 scsi_device_prop_lookup_int_array(struct scsi_device *sd, uint_t flags, 4317 char *name, int **data, uint_t *nelements) 4318 { 4319 mdi_pathinfo_t *pip; 4320 int rv; 4321 4322 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4323 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4324 !_TYPE_DEFINED(flags)) 4325 return (DDI_PROP_INVAL_ARG); 4326 4327 pip = _DEVICE_PIP(sd, flags); 4328 if (pip) 4329 rv = mdi_prop_lookup_int_array(pip, name, data, nelements); 4330 else 4331 rv = ddi_prop_lookup_int_array(DDI_DEV_T_ANY, sd->sd_dev, 4332 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4333 name, data, nelements); 4334 return (rv); 4335 } 4336 4337 4338 int 4339 scsi_device_prop_lookup_string(struct scsi_device *sd, uint_t flags, 4340 char *name, char **data) 4341 { 4342 mdi_pathinfo_t *pip; 4343 int rv; 4344 4345 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4346 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4347 !_TYPE_DEFINED(flags)) 4348 return (DDI_PROP_INVAL_ARG); 4349 4350 pip = _DEVICE_PIP(sd, flags); 4351 if (pip) 4352 rv = mdi_prop_lookup_string(pip, name, data); 4353 else 4354 rv = ddi_prop_lookup_string(DDI_DEV_T_ANY, sd->sd_dev, 4355 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4356 name, data); 4357 return (rv); 4358 } 4359 4360 int 4361 scsi_device_prop_lookup_string_array(struct scsi_device *sd, uint_t flags, 4362 char *name, char ***data, uint_t *nelements) 4363 { 4364 mdi_pathinfo_t *pip; 4365 int rv; 4366 4367 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4368 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4369 !_TYPE_DEFINED(flags)) 4370 return (DDI_PROP_INVAL_ARG); 4371 4372 pip = _DEVICE_PIP(sd, flags); 4373 if (pip) 4374 rv = mdi_prop_lookup_string_array(pip, name, data, nelements); 4375 else 4376 rv = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, sd->sd_dev, 4377 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4378 name, data, nelements); 4379 return (rv); 4380 } 4381 4382 int 4383 scsi_device_prop_update_byte_array(struct scsi_device *sd, uint_t flags, 4384 char *name, uchar_t *data, uint_t nelements) 4385 { 4386 mdi_pathinfo_t *pip; 4387 int rv; 4388 4389 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4390 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4391 !_TYPE_DEFINED(flags)) 4392 return (DDI_PROP_INVAL_ARG); 4393 4394 pip = _DEVICE_PIP(sd, flags); 4395 if (pip) 4396 rv = mdi_prop_update_byte_array(pip, name, data, nelements); 4397 else 4398 rv = ndi_prop_update_byte_array(DDI_DEV_T_NONE, sd->sd_dev, 4399 name, data, nelements); 4400 return (rv); 4401 } 4402 4403 int 4404 scsi_device_prop_update_int(struct scsi_device *sd, uint_t flags, 4405 char *name, int data) 4406 { 4407 mdi_pathinfo_t *pip; 4408 int rv; 4409 4410 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4411 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4412 !_TYPE_DEFINED(flags)) 4413 return (DDI_PROP_INVAL_ARG); 4414 4415 pip = _DEVICE_PIP(sd, flags); 4416 if (pip) 4417 rv = mdi_prop_update_int(pip, name, data); 4418 else 4419 rv = ndi_prop_update_int(DDI_DEV_T_NONE, sd->sd_dev, 4420 name, data); 4421 return (rv); 4422 } 4423 4424 int 4425 scsi_device_prop_update_int64(struct scsi_device *sd, uint_t flags, 4426 char *name, int64_t data) 4427 { 4428 mdi_pathinfo_t *pip; 4429 int rv; 4430 4431 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4432 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4433 !_TYPE_DEFINED(flags)) 4434 return (DDI_PROP_INVAL_ARG); 4435 4436 pip = _DEVICE_PIP(sd, flags); 4437 if (pip) 4438 rv = mdi_prop_update_int64(pip, name, data); 4439 else 4440 rv = ndi_prop_update_int64(DDI_DEV_T_NONE, sd->sd_dev, 4441 name, data); 4442 return (rv); 4443 } 4444 4445 int 4446 scsi_device_prop_update_int_array(struct scsi_device *sd, uint_t flags, 4447 char *name, int *data, uint_t nelements) 4448 { 4449 mdi_pathinfo_t *pip; 4450 int rv; 4451 4452 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4453 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4454 !_TYPE_DEFINED(flags)) 4455 return (DDI_PROP_INVAL_ARG); 4456 4457 pip = _DEVICE_PIP(sd, flags); 4458 if (pip) 4459 rv = mdi_prop_update_int_array(pip, name, data, nelements); 4460 else 4461 rv = ndi_prop_update_int_array(DDI_DEV_T_NONE, sd->sd_dev, 4462 name, data, nelements); 4463 return (rv); 4464 } 4465 4466 int 4467 scsi_device_prop_update_string(struct scsi_device *sd, uint_t flags, 4468 char *name, char *data) 4469 { 4470 mdi_pathinfo_t *pip; 4471 int rv; 4472 4473 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4474 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4475 !_TYPE_DEFINED(flags)) 4476 return (DDI_PROP_INVAL_ARG); 4477 4478 pip = _DEVICE_PIP(sd, flags); 4479 if (pip) 4480 rv = mdi_prop_update_string(pip, name, data); 4481 else 4482 rv = ndi_prop_update_string(DDI_DEV_T_NONE, sd->sd_dev, 4483 name, data); 4484 return (rv); 4485 } 4486 4487 int 4488 scsi_device_prop_update_string_array(struct scsi_device *sd, uint_t flags, 4489 char *name, char **data, uint_t nelements) 4490 { 4491 mdi_pathinfo_t *pip; 4492 int rv; 4493 4494 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4495 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4496 !_TYPE_DEFINED(flags)) 4497 return (DDI_PROP_INVAL_ARG); 4498 4499 pip = _DEVICE_PIP(sd, flags); 4500 if (pip) 4501 rv = mdi_prop_update_string_array(pip, name, data, nelements); 4502 else 4503 rv = ndi_prop_update_string_array(DDI_DEV_T_NONE, sd->sd_dev, 4504 name, data, nelements); 4505 return (rv); 4506 } 4507 4508 int 4509 scsi_device_prop_remove(struct scsi_device *sd, uint_t flags, char *name) 4510 { 4511 mdi_pathinfo_t *pip; 4512 int rv; 4513 4514 ASSERT(sd && name && sd->sd_dev && _TYPE_DEFINED(flags)); 4515 if ((sd == NULL) || (name == NULL) || (sd->sd_dev == NULL) || 4516 !_TYPE_DEFINED(flags)) 4517 return (DDI_PROP_INVAL_ARG); 4518 4519 pip = _DEVICE_PIP(sd, flags); 4520 if (pip) 4521 rv = mdi_prop_remove(pip, name); 4522 else 4523 rv = ndi_prop_remove(DDI_DEV_T_NONE, sd->sd_dev, name); 4524 return (rv); 4525 } 4526 4527 void 4528 scsi_device_prop_free(struct scsi_device *sd, uint_t flags, void *data) 4529 { 4530 mdi_pathinfo_t *pip; 4531 4532 ASSERT(sd && data && sd->sd_dev && _TYPE_DEFINED(flags)); 4533 if ((sd == NULL) || (data == NULL) || (sd->sd_dev == NULL) || 4534 !_TYPE_DEFINED(flags)) 4535 return; 4536 4537 pip = _DEVICE_PIP(sd, flags); 4538 if (pip) 4539 (void) mdi_prop_free(data); 4540 else 4541 ddi_prop_free(data); 4542 } 4543 4544 /* SMP device property interfaces */ 4545 int 4546 smp_device_prop_get_int(struct smp_device *smp_sd, char *name, int defval) 4547 { 4548 int v = defval; 4549 4550 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4551 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4552 return (v); 4553 4554 v = ddi_prop_get_int(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4555 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, name, v); 4556 return (v); 4557 } 4558 4559 4560 int64_t 4561 smp_device_prop_get_int64(struct smp_device *smp_sd, char *name, int64_t defval) 4562 { 4563 int64_t v = defval; 4564 4565 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4566 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4567 return (v); 4568 4569 v = ddi_prop_get_int64(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4570 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, name, v); 4571 return (v); 4572 } 4573 4574 int 4575 smp_device_prop_lookup_byte_array(struct smp_device *smp_sd, char *name, 4576 uchar_t **data, uint_t *nelements) 4577 { 4578 int rv; 4579 4580 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4581 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4582 return (DDI_PROP_INVAL_ARG); 4583 4584 rv = ddi_prop_lookup_byte_array(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4585 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4586 name, data, nelements); 4587 return (rv); 4588 } 4589 4590 int 4591 smp_device_prop_lookup_int_array(struct smp_device *smp_sd, char *name, 4592 int **data, uint_t *nelements) 4593 { 4594 int rv; 4595 4596 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4597 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4598 return (DDI_PROP_INVAL_ARG); 4599 4600 rv = ddi_prop_lookup_int_array(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4601 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4602 name, data, nelements); 4603 return (rv); 4604 } 4605 4606 4607 int 4608 smp_device_prop_lookup_string(struct smp_device *smp_sd, char *name, 4609 char **data) 4610 { 4611 int rv; 4612 4613 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4614 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4615 return (DDI_PROP_INVAL_ARG); 4616 4617 rv = ddi_prop_lookup_string(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4618 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4619 name, data); 4620 return (rv); 4621 } 4622 4623 int 4624 smp_device_prop_lookup_string_array(struct smp_device *smp_sd, char *name, 4625 char ***data, uint_t *nelements) 4626 { 4627 int rv; 4628 4629 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4630 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4631 return (DDI_PROP_INVAL_ARG); 4632 4633 rv = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, smp_sd->smp_sd_dev, 4634 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 4635 name, data, nelements); 4636 return (rv); 4637 } 4638 4639 int 4640 smp_device_prop_update_byte_array(struct smp_device *smp_sd, char *name, 4641 uchar_t *data, uint_t nelements) 4642 { 4643 int rv; 4644 4645 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4646 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4647 return (DDI_PROP_INVAL_ARG); 4648 4649 rv = ndi_prop_update_byte_array(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4650 name, data, nelements); 4651 return (rv); 4652 } 4653 4654 int 4655 smp_device_prop_update_int(struct smp_device *smp_sd, char *name, int data) 4656 { 4657 int rv; 4658 4659 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4660 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4661 return (DDI_PROP_INVAL_ARG); 4662 4663 rv = ndi_prop_update_int(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4664 name, data); 4665 return (rv); 4666 } 4667 4668 int 4669 smp_device_prop_update_int64(struct smp_device *smp_sd, char *name, 4670 int64_t data) 4671 { 4672 int rv; 4673 4674 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4675 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4676 return (DDI_PROP_INVAL_ARG); 4677 4678 rv = ndi_prop_update_int64(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4679 name, data); 4680 return (rv); 4681 } 4682 4683 int 4684 smp_device_prop_update_int_array(struct smp_device *smp_sd, char *name, 4685 int *data, uint_t nelements) 4686 { 4687 int rv; 4688 4689 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4690 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4691 return (DDI_PROP_INVAL_ARG); 4692 4693 rv = ndi_prop_update_int_array(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4694 name, data, nelements); 4695 return (rv); 4696 } 4697 4698 int 4699 smp_device_prop_update_string(struct smp_device *smp_sd, char *name, char *data) 4700 { 4701 int rv; 4702 4703 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4704 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4705 return (DDI_PROP_INVAL_ARG); 4706 4707 rv = ndi_prop_update_string(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4708 name, data); 4709 return (rv); 4710 } 4711 4712 int 4713 smp_device_prop_update_string_array(struct smp_device *smp_sd, char *name, 4714 char **data, uint_t nelements) 4715 { 4716 int rv; 4717 4718 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4719 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4720 return (DDI_PROP_INVAL_ARG); 4721 4722 rv = ndi_prop_update_string_array(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, 4723 name, data, nelements); 4724 return (rv); 4725 } 4726 4727 int 4728 smp_device_prop_remove(struct smp_device *smp_sd, char *name) 4729 { 4730 int rv; 4731 4732 ASSERT(smp_sd && name && smp_sd->smp_sd_dev); 4733 if ((smp_sd == NULL) || (name == NULL) || (smp_sd->smp_sd_dev == NULL)) 4734 return (DDI_PROP_INVAL_ARG); 4735 4736 rv = ndi_prop_remove(DDI_DEV_T_NONE, smp_sd->smp_sd_dev, name); 4737 return (rv); 4738 } 4739 4740 void 4741 smp_device_prop_free(struct smp_device *smp_sd, void *data) 4742 { 4743 ASSERT(smp_sd && data && smp_sd->smp_sd_dev); 4744 if ((smp_sd == NULL) || (data == NULL) || (smp_sd->smp_sd_dev == NULL)) 4745 return; 4746 4747 ddi_prop_free(data); 4748 } 4749 4750 /* 4751 * scsi_hba_ua_set: given "unit-address" string, set properties. 4752 * 4753 * Function to set the properties on a devinfo or pathinfo node from 4754 * the "unit-address" part of a "name@unit-address" /devices path 'name' 4755 * string. 4756 * 4757 * This function works in conjunction with scsi_ua_get()/scsi_hba_ua_get() 4758 * (and possibly with an HBA driver's tran_tgt_init() implementation). 4759 */ 4760 static int 4761 scsi_hba_ua_set(char *ua, dev_info_t *dchild, mdi_pathinfo_t *pchild) 4762 { 4763 char *p; 4764 int tgt; 4765 char *tgt_port_end; 4766 char *tgt_port; 4767 int tgt_port_len; 4768 int sfunc; 4769 scsi_lun64_t lun64; 4770 4771 /* Caller must choose to decorate devinfo *or* pathinfo */ 4772 ASSERT((dchild != NULL) ^ (pchild != NULL)); 4773 if (dchild && pchild) 4774 return (0); 4775 4776 /* 4777 * generic implementation based on "tgt,lun[,sfunc]" address form. 4778 * parse hex "tgt" part of "tgt,lun[,sfunc]" 4779 */ 4780 p = ua; 4781 tgt_port_end = NULL; 4782 for (tgt = 0; *p && *p != ','; p++) { 4783 if (*p >= '0' && *p <= '9') 4784 tgt = (tgt << 4) + (*p - '0'); 4785 else if (*p >= 'a' && *p <= 'f') 4786 tgt = (tgt << 4) + 10 + (*p - 'a'); 4787 else 4788 tgt = -1; /* non-numeric */ 4789 4790 /* 4791 * if non-numeric or our of range set tgt to -1 and 4792 * skip forward 4793 */ 4794 if (tgt < 0) { 4795 tgt = -1; 4796 for (; *p && *p != ','; p++) 4797 ; 4798 break; 4799 } 4800 } 4801 tgt_port_end = p; 4802 4803 /* parse hex ",lun" part of "tgt,lun[,sfunc]" */ 4804 if (*p) 4805 p++; 4806 for (lun64 = 0; *p && *p != ','; p++) { 4807 if (*p >= '0' && *p <= '9') 4808 lun64 = (lun64 << 4) + (*p - '0'); 4809 else if (*p >= 'a' && *p <= 'f') 4810 lun64 = (lun64 << 4) + 10 + (*p - 'a'); 4811 else 4812 return (0); 4813 } 4814 4815 /* parse hex ",sfunc" part of "tgt,lun[,sfunc]" */ 4816 if (*p) { 4817 p++; 4818 for (sfunc = 0; *p; p++) { 4819 if (*p >= '0' && *p <= '9') 4820 sfunc = (sfunc << 4) + (*p - '0'); 4821 else if (*p >= 'a' && *p <= 'f') 4822 sfunc = (sfunc << 4) + 10 + (*p - 'a'); 4823 else 4824 return (0); 4825 } 4826 } else 4827 sfunc = -1; 4828 4829 if (dchild) { 4830 /* 4831 * Decorate a devinfo node with unit address properties. 4832 * This adds the the addressing properties needed to 4833 * DDI_CTLOPS_UNINITCHILD the devinfo node (i.e. perform 4834 * the reverse operation - form unit address from properties). 4835 */ 4836 if ((tgt != -1) && (ndi_prop_update_int(DDI_DEV_T_NONE, dchild, 4837 SCSI_ADDR_PROP_TARGET, tgt) != DDI_PROP_SUCCESS)) 4838 return (0); 4839 4840 if (tgt_port_end) { 4841 tgt_port_len = tgt_port_end - ua + 1; 4842 tgt_port = kmem_alloc(tgt_port_len, KM_SLEEP); 4843 (void) strlcpy(tgt_port, ua, tgt_port_len); 4844 if (ndi_prop_update_string(DDI_DEV_T_NONE, dchild, 4845 SCSI_ADDR_PROP_TARGET_PORT, tgt_port) != 4846 DDI_PROP_SUCCESS) { 4847 kmem_free(tgt_port, tgt_port_len); 4848 return (0); 4849 } 4850 kmem_free(tgt_port, tgt_port_len); 4851 } 4852 4853 /* Set the appropriate lun properties. */ 4854 if (lun64 < SCSI_32LUNS_PER_TARGET) { 4855 if (ndi_prop_update_int(DDI_DEV_T_NONE, dchild, 4856 SCSI_ADDR_PROP_LUN, (int)lun64) != DDI_PROP_SUCCESS) 4857 return (0); 4858 } 4859 if (ndi_prop_update_int64(DDI_DEV_T_NONE, dchild, 4860 SCSI_ADDR_PROP_LUN64, lun64) != DDI_PROP_SUCCESS) 4861 return (0); 4862 4863 /* Set the sfunc property */ 4864 if ((sfunc != -1) && 4865 (ndi_prop_update_int(DDI_DEV_T_NONE, dchild, 4866 SCSI_ADDR_PROP_SFUNC, (int)sfunc) != DDI_PROP_SUCCESS)) 4867 return (0); 4868 } else if (pchild) { 4869 /* 4870 * Decorate a pathinfo node with unit address properties. 4871 */ 4872 if ((tgt != -1) && (mdi_prop_update_int(pchild, 4873 SCSI_ADDR_PROP_TARGET, tgt) != DDI_PROP_SUCCESS)) 4874 return (0); 4875 4876 if (tgt_port_end) { 4877 tgt_port_len = tgt_port_end - ua + 1; 4878 tgt_port = kmem_alloc(tgt_port_len, KM_SLEEP); 4879 (void) strlcpy(tgt_port, ua, tgt_port_len); 4880 if (mdi_prop_update_string(pchild, 4881 SCSI_ADDR_PROP_TARGET_PORT, tgt_port) != 4882 DDI_PROP_SUCCESS) { 4883 kmem_free(tgt_port, tgt_port_len); 4884 return (0); 4885 } 4886 kmem_free(tgt_port, tgt_port_len); 4887 } 4888 4889 /* Set the appropriate lun properties */ 4890 if (lun64 < SCSI_32LUNS_PER_TARGET) { 4891 if (mdi_prop_update_int(pchild, SCSI_ADDR_PROP_LUN, 4892 (int)lun64) != DDI_PROP_SUCCESS) 4893 return (0); 4894 } 4895 4896 if (mdi_prop_update_int64(pchild, SCSI_ADDR_PROP_LUN64, 4897 lun64) != DDI_PROP_SUCCESS) 4898 return (0); 4899 4900 /* Set the sfunc property */ 4901 if ((sfunc != -1) && 4902 (mdi_prop_update_int(pchild, 4903 SCSI_ADDR_PROP_SFUNC, (int)sfunc) != DDI_PROP_SUCCESS)) 4904 return (0); 4905 } 4906 return (1); 4907 } 4908 4909 /* 4910 * Private ndi_devi_find/mdi_pi_find implementation - find the child 4911 * dev_info/path_info of self whose phci name matches "name@caddr". 4912 * We have our own implementation because we need to search with both 4913 * forms of sibling lists (dev_info and path_info) and we need to be able 4914 * to search with a NULL name in order to find siblings already associated 4915 * with a given unit-address (same @addr). NOTE: NULL name search will never 4916 * return probe node. 4917 * 4918 * If pchildp is NULL and we find a pathinfo child, we return the client 4919 * devinfo node in *dchildp. 4920 * 4921 * The init flag argument should be clear when called from places where 4922 * recursion could occur (like scsi_busctl_initchild) and when the caller 4923 * has already performed a search for name@addr with init set (performance). 4924 * 4925 * Future: Integrate ndi_devi_findchild_by_callback into scsi_findchild. 4926 */ 4927 static int 4928 scsi_findchild(dev_info_t *self, char *name, char *addr, int init, 4929 dev_info_t **dchildp, mdi_pathinfo_t **pchildp, int *ppi) 4930 { 4931 dev_info_t *dchild; /* devinfo child */ 4932 mdi_pathinfo_t *pchild; /* pathinfo child */ 4933 int found = CHILD_TYPE_NONE; 4934 char *daddr; 4935 4936 ASSERT(self && DEVI_BUSY_OWNED(self)); 4937 ASSERT(addr && dchildp); 4938 if ((self == NULL) || (addr == NULL) || (dchildp == NULL)) 4939 return (CHILD_TYPE_NONE); 4940 4941 *dchildp = NULL; 4942 if (pchildp) 4943 *pchildp = NULL; 4944 if (ppi) 4945 *ppi = 0; 4946 4947 /* Walk devinfo child list to find a match */ 4948 for (dchild = ddi_get_child(self); dchild; 4949 dchild = ddi_get_next_sibling(dchild)) { 4950 if (i_ddi_node_state(dchild) < DS_INITIALIZED) 4951 continue; 4952 4953 daddr = ddi_get_name_addr(dchild); 4954 if (daddr && (strcmp(addr, daddr) == 0) && 4955 ((name == NULL) || 4956 (strcmp(name, DEVI(dchild)->devi_node_name) == 0))) { 4957 /* 4958 * If we are asked to find "anything" at a given 4959 * unit-address (name == NULL), we don't realy want 4960 * to find the 'probe' node. The existance of 4961 * a probe node on a 'name == NULL' search should 4962 * fail. This will trigger slow-path code where 4963 * we explicity look for, and synchronize against, 4964 * a node named "probe" at the unit-address. 4965 */ 4966 if ((name == NULL) && 4967 scsi_hba_devi_is_barrier(dchild)) { 4968 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 4969 "%s@%s 'probe' devinfo found, skip", 4970 name ? name : "", addr)); 4971 continue; 4972 } 4973 4974 /* We have found a match. */ 4975 found |= CHILD_TYPE_DEVINFO; 4976 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 4977 "%s@%s devinfo found", name ? name : "", addr)); 4978 *dchildp = dchild; /* devinfo found */ 4979 break; 4980 } 4981 } 4982 4983 /* 4984 * Walk pathinfo child list to find a match. 4985 * 4986 * NOTE: Unlike devinfo nodes, pathinfo nodes have a string searchable 4987 * unit-address from creation - so there is no need for an 'init' 4988 * search block of code for pathinfo nodes below. 4989 */ 4990 pchild = mdi_pi_find(self, NULL, addr); 4991 if (pchild) { 4992 /* 4993 * NOTE: If name specified and we match a pathinfo unit 4994 * address, we don't check the client node name. 4995 */ 4996 if (ppi) 4997 *ppi = mdi_pi_get_path_instance(pchild); 4998 found |= CHILD_TYPE_PATHINFO; 4999 5000 if (pchildp) { 5001 SCSI_HBA_LOG((_LOG(4), self, NULL, 5002 "%s pathinfo found", mdi_pi_spathname(pchild))); 5003 *pchildp = pchild; /* pathinfo found */ 5004 } else if (*dchildp == NULL) { 5005 /* 5006 * Did not find a devinfo node, found a pathinfo node, 5007 * but caller did not ask us to return a pathinfo node: 5008 * we return the 'client' devinfo node instead (but 5009 * with CHILD_TYPE_PATHINFO 'found' return value). 5010 */ 5011 dchild = mdi_pi_get_client(pchild); 5012 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5013 "%s pathinfo found, client switch", 5014 mdi_pi_spathname(pchild))); 5015 5016 /* 5017 * A pathinfo node always has a 'client' devinfo node, 5018 * but we need to ensure that the 'client' is 5019 * initialized and has a scsi_device structure too. 5020 */ 5021 ASSERT(dchild); 5022 if (i_ddi_node_state(dchild) < DS_INITIALIZED) { 5023 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5024 "%s found client, initchild", 5025 mdi_pi_spathname(pchild))); 5026 (void) ddi_initchild(ddi_get_parent(dchild), 5027 dchild); 5028 } 5029 if (i_ddi_node_state(dchild) >= DS_INITIALIZED) { 5030 /* client found and initialized */ 5031 *dchildp = dchild; 5032 } else { 5033 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5034 "%s found client, but failed initchild", 5035 mdi_pi_spathname(pchild))); 5036 } 5037 } 5038 } 5039 5040 /* Try devinfo again with initchild of uninitialized nodes */ 5041 if ((found == CHILD_TYPE_NONE) && init) { 5042 for (dchild = ddi_get_child(self); dchild; 5043 dchild = ddi_get_next_sibling(dchild)) { 5044 /* skip if checked above */ 5045 if (i_ddi_node_state(dchild) >= DS_INITIALIZED) 5046 continue; 5047 /* attempt initchild to establish unit-address */ 5048 (void) ddi_initchild(self, dchild); 5049 if (i_ddi_node_state(dchild) < DS_INITIALIZED) 5050 continue; 5051 daddr = ddi_get_name_addr(dchild); 5052 if (daddr && 5053 ((name == NULL) || (strcmp(name, 5054 DEVI(dchild)->devi_node_name) == 0)) && 5055 (strcmp(addr, daddr) == 0)) { 5056 found |= CHILD_TYPE_DEVINFO; 5057 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5058 "%s@%s devinfo found post initchild", 5059 name ? name : "", addr)); 5060 *dchildp = dchild; /* devinfo found */ 5061 break; /* node found */ 5062 } 5063 } 5064 } 5065 5066 /* 5067 * We should never find devinfo and pathinfo at the same 5068 * unit-address. 5069 */ 5070 ASSERT(found != (CHILD_TYPE_DEVINFO | CHILD_TYPE_PATHINFO)); 5071 if (found == (CHILD_TYPE_DEVINFO | CHILD_TYPE_PATHINFO)) { 5072 found = CHILD_TYPE_NONE; 5073 *dchildp = NULL; 5074 *pchildp = NULL; 5075 } 5076 return (found); 5077 } 5078 5079 /* 5080 * Given information about a child device (contained on probe node) construct 5081 * and return a pointer to the dynamic SID devinfo node associated with the 5082 * device. In the creation of this SID node a compatible property for the 5083 * device is formed and used to establish a nodename (via 5084 * /etc/nodename_aliases) and to bind a driver (via /etc/driver_aliases). 5085 * 5086 * If this routine is called then we got a response from a device and 5087 * obtained the inquiry data from the device. Some inquiry results indicate 5088 * that the specific LUN we addressed does not exist, and we don't want to 5089 * bind a standard target driver to the node we create. Even though the 5090 * specific LUN is not usable, the framework may still want to bind a 5091 * target driver to the device for internal communication with the device - 5092 * an example would be issuing a report_lun to enumerate other LUNs under a 5093 * DPQ_NEVER LUN0. Another example would be wanting to known that the 5094 * DPQ_NEVER LUN0 device exists in BUS_CONFIG_ONE for non-existent LUN 5095 * caching optimizations. To support this we let the caller specify a 5096 * compatible property (or driver). If LUN0 inquiry data indicates that the 5097 * LUN does not exist then we establish compat0 as the highest precedence(0) 5098 * compatible form. If used, this compat0 driver will never be called on to 5099 * issue external commands to the device. 5100 * 5101 * If no driver binds to the device using driver_alias we establish the driver 5102 * passed in as the node name. 5103 */ 5104 5105 extern int e_devid_cache_pathinfo(mdi_pathinfo_t *, ddi_devid_t); 5106 5107 static int 5108 scsi_device_createchild(dev_info_t *self, char *addr, scsi_enum_t se, 5109 struct scsi_device *sdprobe, dev_info_t **dchildp, mdi_pathinfo_t **pchildp) 5110 { 5111 scsi_lun64_t lun64; 5112 int dtype; 5113 int dpq; 5114 int dpq_vu; 5115 int dtype_node; 5116 int lunexists; 5117 char *compat0; 5118 char *nname; 5119 char **compat = NULL; 5120 int ncompat; 5121 dev_info_t *dchild = NULL; 5122 mdi_pathinfo_t *pchild = NULL; 5123 dev_info_t *probe = sdprobe->sd_dev; 5124 struct scsi_inquiry *inq = sdprobe->sd_inq; 5125 uchar_t *inq80 = NULL; 5126 uchar_t *inq83 = NULL; 5127 uint_t inq80len, inq83len; 5128 char *binding_set = NULL; 5129 char *dname = NULL; 5130 ddi_devid_t devid; 5131 int have_devid = 0; 5132 ddi_devid_t cdevid; 5133 int have_cdevid = 0; 5134 char *devid_str; 5135 char *guid = NULL; 5136 5137 ASSERT(self && addr && *addr && DEVI_BUSY_OWNED(self)); 5138 ASSERT(dchildp && pchildp); 5139 5140 /* 5141 * Determine the lun and whether the lun exists. We may need to create 5142 * a node for LUN0 (with compat0 driver binding) even if the lun does 5143 * not exist - so we can run report_lun to find additional LUNs. 5144 */ 5145 lun64 = scsi_addr_to_lun64(addr); 5146 dtype = inq->inq_dtype & DTYPE_MASK; /* device */ 5147 dpq = inq->inq_dtype & DPQ_MASK; 5148 dpq_vu = inq->inq_dtype & DPQ_VUNIQ ? 1 : 0; 5149 5150 dtype_node = scsi_addr_to_sfunc(addr); /* secondary function */ 5151 if (dtype_node == -1) 5152 dtype_node = dtype; /* node for device */ 5153 5154 lunexists = (dtype != dtype_node) || /* override */ 5155 ((dpq_vu == 0) && (dpq == DPQ_POSSIBLE)) || /* ANSII */ 5156 (dpq_vu && (lun64 == 0)); /* VU LUN0 */ 5157 if (dtype == DTYPE_UNKNOWN) 5158 lunexists = 0; 5159 5160 SCSI_HBA_LOG((_LOG(4), self, NULL, 5161 "@%s dtype %x %x dpq_vu %d dpq %x: %d", 5162 addr, dtype, dtype_node, dpq_vu, dpq, lunexists)); 5163 5164 /* A non-existent LUN0 uses compatible_nodev. */ 5165 if (lunexists) { 5166 compat0 = NULL; /* compat0 not needed */ 5167 } else if (lun64 == 0) { 5168 compat0 = compatible_nodev; 5169 SCSI_HBA_LOG((_LOG(2), self, NULL, 5170 "@%s lun 0 with compat0 %s", addr, compat0)); 5171 } else 5172 goto out; /* no node created */ 5173 5174 /* Obtain identity information from probe node. */ 5175 if (ddi_prop_lookup_byte_array(DDI_DEV_T_ANY, probe, 5176 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "inquiry-page-80", 5177 &inq80, &inq80len) != DDI_PROP_SUCCESS) 5178 inq80 = NULL; 5179 if (ddi_prop_lookup_byte_array(DDI_DEV_T_ANY, probe, 5180 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "inquiry-page-83", 5181 &inq83, &inq83len) != DDI_PROP_SUCCESS) 5182 inq83 = NULL; 5183 5184 /* Get "scsi-binding-set" property (if there is one). */ 5185 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, self, 5186 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 5187 "scsi-binding-set", &binding_set) == DDI_PROP_SUCCESS) 5188 SCSI_HBA_LOG((_LOG(2), NULL, probe, 5189 "binding_set '%s'", binding_set)); 5190 5191 /* determine the node name and compatible information */ 5192 scsi_hba_ident_nodename_compatible_get(inq, 5193 inq80, inq80len, inq83, inq83len, binding_set, dtype_node, 5194 compat0, &nname, &dname, &compat, &ncompat); 5195 5196 if (nname == NULL) { 5197 /* 5198 * We will not be able to create a node because we could not 5199 * determine a node name. Print out a NODRIVER level warning 5200 * message with the compatible forms for the device. Note that 5201 * there may be a driver.conf node that attaches to the device, 5202 * which is why we only produce this warning message for debug 5203 * kernels. 5204 */ 5205 SCSI_HBA_LOG((_LOG(1), NULL, self, 5206 "no node_name for device @%s:\n compatible: %s", 5207 addr, *compat)); 5208 goto out; 5209 } 5210 5211 /* 5212 * FUTURE: some day we may want an accurate "compatible" on the probe 5213 * node so that vhci_is_dev_supported() in scsi_vhci could, at 5214 * least in part, determine/configure based on "compatible". 5215 * 5216 * if (ndi_prop_update_string_array(DDI_DEV_T_NONE, probe, 5217 * "compatible", compat, ncompat) != DDI_PROP_SUCCESS) { 5218 * SCSI_HBA_LOG((_LOG(3), self, NULL, 5219 * "%s@%s failed probe compatible decoration", 5220 * nname, addr)); 5221 * goto out; 5222 * } 5223 */ 5224 5225 /* Encode devid from identity information. */ 5226 if (ddi_devid_scsi_encode(DEVID_SCSI_ENCODE_VERSION_LATEST, dname, 5227 (uchar_t *)inq, sizeof (*inq), inq80, inq80len, inq83, inq83len, 5228 &devid) == DDI_SUCCESS) { 5229 have_devid = 1; 5230 5231 /* Attempt to form guid from devid. */ 5232 guid = ddi_devid_to_guid(devid); 5233 5234 /* Produce string devid for debug. */ 5235 devid_str = ddi_devid_str_encode(devid, NULL); 5236 SCSI_HBA_LOG((_LOG(3), self, probe, "devid '%s' guid '%s'", 5237 devid_str ? devid_str : "NULL", guid ? guid : "NULL")); 5238 ddi_devid_str_free(devid_str); 5239 } 5240 5241 5242 /* 5243 * Determine if the device should be enumerated as under the vHCI 5244 * (client node) or under the pHCI. By convention scsi_vhci expects 5245 * the "cinfo" argument identity information to be represented as a 5246 * devinfo node with the needed information (i.e. the pHCI probe node). 5247 */ 5248 if ((guid == NULL) || 5249 (mdi_is_dev_supported(MDI_HCI_CLASS_SCSI, self, sdprobe) != 5250 MDI_SUCCESS)) { 5251 SCSI_HBA_LOG((_LOG(3), self, probe, "==> devinfo")); 5252 5253 /* 5254 * Enumerate under pHCI: 5255 * 5256 * Create dynamic SID dchild node. No attempt is made to 5257 * transfer information (except the addressing and identity 5258 * information) from the probe node to the dynamic node since 5259 * there may be HBA specific side effects that the framework 5260 * does not known how to transfer. 5261 */ 5262 ndi_devi_alloc_sleep(self, nname, 5263 (se == SE_HP) ? DEVI_SID_HP_NODEID : DEVI_SID_NODEID, 5264 &dchild); 5265 ASSERT(dchild); 5266 ndi_flavor_set(dchild, SCSA_FLAVOR_SCSI_DEVICE); 5267 5268 /* 5269 * Decorate new node with addressing properties (via 5270 * scsi_hba_ua_set()), compatible, identity information, and 5271 * class. 5272 */ 5273 if ((scsi_hba_ua_set(addr, dchild, NULL) == 0) || 5274 (ndi_prop_update_string_array(DDI_DEV_T_NONE, dchild, 5275 "compatible", compat, ncompat) != DDI_PROP_SUCCESS) || 5276 (inq80 && (ndi_prop_update_byte_array(DDI_DEV_T_NONE, 5277 dchild, "inquiry-page-80", inq80, inq80len) != 5278 DDI_PROP_SUCCESS)) || 5279 (inq83 && (ndi_prop_update_byte_array(DDI_DEV_T_NONE, 5280 dchild, "inquiry-page-83", inq83, inq83len) != 5281 DDI_PROP_SUCCESS)) || 5282 (ndi_prop_update_string(DDI_DEV_T_NONE, dchild, 5283 "class", "scsi") != DDI_PROP_SUCCESS)) { 5284 SCSI_HBA_LOG((_LOG(2), self, NULL, 5285 "devinfo @%s failed decoration", addr)); 5286 (void) scsi_hba_remove_node(dchild); 5287 dchild = NULL; 5288 goto out; 5289 } 5290 5291 /* Bind the driver */ 5292 if (ndi_devi_bind_driver(dchild, 0) != NDI_SUCCESS) { 5293 /* need to bind in order to register a devid */ 5294 SCSI_HBA_LOG((_LOGCFG, NULL, dchild, 5295 "devinfo @%s created, no driver-> " 5296 "no devid_register", addr)); 5297 goto out; 5298 } 5299 5300 /* Register devid */ 5301 if (have_devid) { 5302 if (ddi_devid_register(dchild, devid) == DDI_FAILURE) 5303 SCSI_HBA_LOG((_LOG(1), NULL, dchild, 5304 "devinfo @%s created, " 5305 "devid register failed", addr)); 5306 else 5307 SCSI_HBA_LOG((_LOG(2), NULL, dchild, 5308 "devinfo @%s created with devid", addr)); 5309 } else 5310 SCSI_HBA_LOG((_LOG(2), NULL, dchild, 5311 "devinfo @%s created, no devid", addr)); 5312 } else { 5313 /* 5314 * Enumerate under vHCI: 5315 * 5316 * Create a pathinfo pchild node. 5317 */ 5318 SCSI_HBA_LOG((_LOG(3), self, probe, "==>pathinfo")); 5319 5320 if (mdi_pi_alloc_compatible(self, nname, guid, addr, compat, 5321 ncompat, 0, &pchild) != MDI_SUCCESS) { 5322 SCSI_HBA_LOG((_LOG(2), self, probe, 5323 "pathinfo alloc failed")); 5324 goto out; 5325 } 5326 5327 ASSERT(pchild); 5328 dchild = mdi_pi_get_client(pchild); 5329 ASSERT(dchild); 5330 ndi_flavor_set(dchild, SCSA_FLAVOR_SCSI_DEVICE); 5331 5332 /* 5333 * Decorate new node with addressing properties via 5334 * scsi_hba_ua_set(). 5335 */ 5336 if (scsi_hba_ua_set(addr, NULL, pchild) == 0) { 5337 SCSI_HBA_LOG((_LOG(1), self, NULL, 5338 "pathinfo %s decoration failed", 5339 mdi_pi_spathname(pchild))); 5340 (void) mdi_pi_free(pchild, 0); 5341 pchild = NULL; 5342 goto out; 5343 } 5344 5345 /* Bind the driver */ 5346 if (ndi_devi_bind_driver(dchild, 0) != NDI_SUCCESS) { 5347 /* need to bind in order to register a devid */ 5348 SCSI_HBA_LOG((_LOGCFG, self, NULL, 5349 "pathinfo %s created, no client driver-> " 5350 "no devid_register", mdi_pi_spathname(pchild))); 5351 goto out; 5352 } 5353 5354 /* Watch out for inconsistancies in devids. */ 5355 if (ddi_devid_get(dchild, &cdevid) == DDI_SUCCESS) 5356 have_cdevid = 1; 5357 5358 if (have_devid && !have_cdevid) { 5359 /* Client does not yet have devid, register ours. */ 5360 if (ddi_devid_register(dchild, devid) == DDI_FAILURE) 5361 SCSI_HBA_LOG((_LOG(1), self, NULL, 5362 "pathinfo %s created, " 5363 "devid register failed", 5364 mdi_pi_spathname(pchild))); 5365 else 5366 SCSI_HBA_LOG((_LOG(2), self, NULL, 5367 "pathinfo %s created with devid", 5368 mdi_pi_spathname(pchild))); 5369 } else if (have_devid && have_cdevid) { 5370 /* 5371 * We have devid and client already has devid: 5372 * they must be the same. 5373 */ 5374 if (ddi_devid_compare(cdevid, devid) != 0) { 5375 SCSI_HBA_LOG((_LOG(WARN), NULL, dchild, 5376 "mismatched devid on path %s", 5377 mdi_pi_spathname(pchild))); 5378 } 5379 } else if (!have_devid && have_cdevid) { 5380 /* 5381 * Client already has a devid, but we don't: 5382 * we should not have missing devids. 5383 */ 5384 SCSI_HBA_LOG((_LOG(WARN), NULL, dchild, 5385 "missing devid on path %s", 5386 mdi_pi_spathname(pchild))); 5387 } else if (!have_cdevid && !have_devid) { 5388 /* devid not supported */ 5389 SCSI_HBA_LOG((_LOG(2), self, NULL, 5390 "pathinfo %s created, no devid", 5391 mdi_pi_spathname(pchild))); 5392 } 5393 5394 /* 5395 * The above has registered devid for the device under 5396 * the client node. Now register it under the full pHCI 5397 * path to the device. We'll get an entry equivalent to 5398 * booting with mpxio disabled. This is needed for 5399 * telemetry during enumeration. 5400 */ 5401 if (e_devid_cache_pathinfo(pchild, devid) == DDI_SUCCESS) { 5402 SCSI_HBA_LOG((_LOG(2), NULL, dchild, 5403 "pathinfo @%s created with devid", addr)); 5404 } else { 5405 SCSI_HBA_LOG((_LOG(1), NULL, dchild, 5406 "pathinfo @%s devid cache failed", addr)); 5407 } 5408 } 5409 5410 /* free the node name and compatible information */ 5411 out: if (have_devid) 5412 ddi_devid_free(devid); 5413 if (have_cdevid) 5414 ddi_devid_free(cdevid); 5415 if (guid) 5416 ddi_devid_free_guid(guid); 5417 if (compat) 5418 scsi_hba_ident_nodename_compatible_free(nname, dname, compat); 5419 if (inq80) 5420 ddi_prop_free(inq80); 5421 if (inq83) 5422 ddi_prop_free(inq83); 5423 if (binding_set) 5424 ddi_prop_free(binding_set); 5425 5426 /* return child_type results */ 5427 if (pchild) { 5428 *dchildp = NULL; 5429 *pchildp = pchild; 5430 return (CHILD_TYPE_PATHINFO); 5431 } else if (dchild) { 5432 *dchildp = dchild; 5433 *pchildp = NULL; 5434 return (CHILD_TYPE_DEVINFO); 5435 } 5436 5437 return (CHILD_TYPE_NONE); 5438 } 5439 5440 /* 5441 * Call scsi_device_createchild and then initchild the new node. 5442 */ 5443 static dev_info_t * 5444 scsi_device_configchild(dev_info_t *self, char *addr, scsi_enum_t se, 5445 struct scsi_device *sdprobe, int *circp, int *ppi) 5446 { 5447 int child_type; 5448 dev_info_t *dchild; 5449 mdi_pathinfo_t *pchild; 5450 dev_info_t *child; 5451 int rval; 5452 5453 ASSERT(self && addr && *addr && DEVI_BUSY_OWNED(self)); 5454 if (ppi) 5455 *ppi = 0; 5456 5457 child_type = scsi_device_createchild(self, addr, se, sdprobe, 5458 &dchild, &pchild); 5459 5460 /* 5461 * Prevent multiple initialized (tran_tgt_init) nodes associated with 5462 * the same @addr at the same time by calling tran_tgt_free() on the 5463 * probe node prior to promotion of the 'real' node. After the call 5464 * to scsi_hba_barrier_tran_tgt_free(), the HBA no longer has any 5465 * probe node context. 5466 */ 5467 scsi_hba_barrier_tran_tgt_free(sdprobe->sd_dev); 5468 5469 switch (child_type) { 5470 case CHILD_TYPE_NONE: 5471 child = NULL; 5472 break; 5473 5474 case CHILD_TYPE_PATHINFO: 5475 /* 5476 * Online pathinfo: Hold the path and exit the pHCI while 5477 * calling mdi_pi_online() to avoid deadlock with power 5478 * management of pHCI. 5479 */ 5480 ASSERT(MDI_PHCI(self)); 5481 mdi_hold_path(pchild); 5482 scsi_hba_devi_exit_phci(self, *circp); 5483 5484 rval = mdi_pi_online(pchild, 0); 5485 5486 scsi_hba_devi_enter_phci(self, circp); 5487 mdi_rele_path(pchild); 5488 5489 if (rval != MDI_SUCCESS) { 5490 /* pathinfo form of "failed during tran_tgt_init" */ 5491 scsi_enumeration_failed(NULL, se, 5492 mdi_pi_spathname(pchild), "path online"); 5493 (void) mdi_pi_free(pchild, 0); 5494 return (NULL); 5495 } 5496 5497 /* 5498 * Return the path_instance of the pathinfo node. 5499 * 5500 * NOTE: We assume that sd_inq is not path-specific. 5501 */ 5502 if (ppi) 5503 *ppi = mdi_pi_get_path_instance(pchild); 5504 5505 5506 /* 5507 * Fallthrough into CHILD_TYPE_DEVINFO code to promote 5508 * the 'client' devinfo node as a dchild. 5509 */ 5510 dchild = mdi_pi_get_client(pchild); 5511 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5512 "pathinfo online successful")); 5513 /* FALLTHROUGH */ 5514 5515 case CHILD_TYPE_DEVINFO: 5516 /* 5517 * For now, we ndi_devi_online() the child because some other 5518 * parts of the IO framework, like degenerate devid code, 5519 * depend on bus_config driving nodes to DS_ATTACHED. At some 5520 * point in the future, to keep things light-weight, we would 5521 * like to change the ndi_devi_online call below to be 5522 * 5523 * if (ddi_initchild(self, dchild) != DDI_SUCCESS) 5524 * 5525 * This would promote the node so that framework code could 5526 * find the child with an @addr search, but does not incur 5527 * attach(9E) overhead for BUS_CONFIG_ALL cases where the 5528 * framework is not interested in attach of the node. 5529 * 5530 * NOTE: If the addr specified has incorrect syntax (busconfig 5531 * one of bogus /devices path) then call below can fail. 5532 */ 5533 if (ndi_devi_online(dchild, 0) != NDI_SUCCESS) { 5534 SCSI_HBA_LOG((_LOG(2), NULL, dchild, 5535 "devinfo online failed")); 5536 5537 /* failed online does not remove the node */ 5538 (void) scsi_hba_remove_node(dchild); 5539 return (NULL); 5540 } 5541 SCSI_HBA_LOG((_LOG(4), NULL, dchild, 5542 "devinfo initchild successful")); 5543 child = dchild; 5544 break; 5545 } 5546 return (child); 5547 } 5548 5549 void 5550 scsi_hba_pkt_comp(struct scsi_pkt *pkt) 5551 { 5552 scsi_hba_tran_t *tran; 5553 uint8_t *sensep; 5554 5555 ASSERT(pkt); 5556 5557 /* 5558 * Catch second call on the same packet before doing anything else. 5559 */ 5560 if (pkt->pkt_flags & FLAG_PKT_COMP_CALLED) { 5561 cmn_err( 5562 #ifdef DEBUG 5563 CE_PANIC, 5564 #else 5565 CE_WARN, 5566 #endif 5567 "%s duplicate scsi_hba_pkt_comp(9F) on same scsi_pkt(9S)", 5568 mod_containing_pc(caller())); 5569 } 5570 5571 pkt->pkt_flags |= FLAG_PKT_COMP_CALLED; 5572 5573 if (pkt->pkt_comp == NULL) 5574 return; 5575 5576 /* 5577 * For HBA drivers that implement tran_setup_pkt(9E), if we are 5578 * completing a 'consistent' mode DMA operation then we must 5579 * perform dma_sync prior to calling pkt_comp to ensure that 5580 * the target driver sees the correct data in memory. 5581 */ 5582 ASSERT((pkt->pkt_flags & FLAG_NOINTR) == 0); 5583 if (((pkt->pkt_dma_flags & DDI_DMA_CONSISTENT) && 5584 (pkt->pkt_dma_flags & DDI_DMA_READ)) && 5585 ((P_TO_TRAN(pkt)->tran_setup_pkt) != NULL)) { 5586 scsi_sync_pkt(pkt); 5587 } 5588 5589 /* 5590 * If the HBA driver is using SCSAv3 scsi_hba_tgtmap_create enumeration 5591 * then we detect the special ASC/ASCQ completion codes that indicate 5592 * that the lun configuration of a target has changed. Since we need to 5593 * be determine scsi_device given scsi_address enbedded in 5594 * scsi_pkt (via scsi_address_device(9F)), we also require use of 5595 * SCSI_HBA_ADDR_COMPLEX. 5596 */ 5597 tran = pkt->pkt_address.a_hba_tran; 5598 ASSERT(tran); 5599 if ((tran->tran_tgtmap == NULL) || 5600 !(tran->tran_hba_flags & SCSI_HBA_ADDR_COMPLEX)) 5601 goto comp; /* not using tgtmap */ 5602 5603 /* 5604 * Check for lun-change notification and queue the scsi_pkt for 5605 * lunchg1 processing. The 'pkt_comp' call to the target driver 5606 * is part of lunchg1 processing. 5607 */ 5608 if ((pkt->pkt_reason == CMD_CMPLT) && 5609 (((*pkt->pkt_scbp) & STATUS_MASK) == STATUS_CHECK) && 5610 (pkt->pkt_state & STATE_ARQ_DONE)) { 5611 sensep = (uint8_t *)&(((struct scsi_arq_status *)(uintptr_t) 5612 (pkt->pkt_scbp))->sts_sensedata); 5613 if (((scsi_sense_key(sensep) == KEY_UNIT_ATTENTION) && 5614 (scsi_sense_asc(sensep) == 0x3f) && 5615 (scsi_sense_ascq(sensep) == 0x0e)) || 5616 5617 ((scsi_sense_key(sensep) == KEY_UNIT_ATTENTION) && 5618 (scsi_sense_asc(sensep) == 0x25) && 5619 (scsi_sense_ascq(sensep) == 0x00))) { 5620 /* 5621 * The host adaptor is done with the packet, we use 5622 * pkt_stmp stage-temporary to link the packet for 5623 * lunchg1 processing. 5624 * 5625 * NOTE: pkt_ha_private is not available since its use 5626 * extends to tran_teardown_pkt. 5627 */ 5628 mutex_enter(&scsi_lunchg1_mutex); 5629 pkt->pkt_stmp = scsi_lunchg1_list; 5630 scsi_lunchg1_list = pkt; 5631 if (pkt->pkt_stmp == NULL) 5632 (void) cv_signal(&scsi_lunchg1_cv); 5633 mutex_exit(&scsi_lunchg1_mutex); 5634 return; 5635 } 5636 } 5637 5638 comp: (*pkt->pkt_comp)(pkt); 5639 } 5640 5641 /* 5642 * return 1 if the specified node is a barrier/probe node 5643 */ 5644 static int 5645 scsi_hba_devi_is_barrier(dev_info_t *probe) 5646 { 5647 if (probe && (strcmp(ddi_node_name(probe), "probe") == 0)) 5648 return (1); 5649 return (0); 5650 } 5651 5652 /* 5653 * A host adapter driver is easier to write if we prevent multiple initialized 5654 * (tran_tgt_init) scsi_device structures to the same unit-address at the same 5655 * time. We prevent this from occurring all the time during the barrier/probe 5656 * node to real child hand-off by calling scsi_hba_barrier_tran_tgt_free 5657 * on the probe node prior to ddi_inichild of the 'real' node. As part of 5658 * this early tran_tgt_free implementation, we must also call this function 5659 * as we put a probe node on the scsi_hba_barrier_list. 5660 */ 5661 static void 5662 scsi_hba_barrier_tran_tgt_free(dev_info_t *probe) 5663 { 5664 struct scsi_device *sdprobe; 5665 dev_info_t *self; 5666 scsi_hba_tran_t *tran; 5667 5668 ASSERT(probe && scsi_hba_devi_is_barrier(probe)); 5669 5670 /* Return if we never called tran_tgt_init(9E). */ 5671 if (i_ddi_node_state(probe) < DS_INITIALIZED) 5672 return; 5673 5674 sdprobe = ddi_get_driver_private(probe); 5675 self = ddi_get_parent(probe); 5676 ASSERT(sdprobe && self); 5677 tran = ddi_get_driver_private(self); 5678 ASSERT(tran); 5679 5680 if (tran->tran_tgt_free) { 5681 /* 5682 * To correctly support TRAN_CLONE, we need to use the same 5683 * cloned scsi_hba_tran(9S) structure for both tran_tgt_init(9E) 5684 * and tran_tgt_free(9E). 5685 */ 5686 if (tran->tran_hba_flags & SCSI_HBA_TRAN_CLONE) 5687 tran = sdprobe->sd_address.a_hba_tran; 5688 5689 if (!sdprobe->sd_tran_tgt_free_done) { 5690 SCSI_HBA_LOG((_LOG(4), NULL, probe, 5691 "tran_tgt_free EARLY")); 5692 (*tran->tran_tgt_free) (self, probe, tran, sdprobe); 5693 sdprobe->sd_tran_tgt_free_done = 1; 5694 } else { 5695 SCSI_HBA_LOG((_LOG(4), NULL, probe, 5696 "tran_tgt_free EARLY already done")); 5697 } 5698 } 5699 } 5700 5701 /* 5702 * Add an entry to the list of barrier nodes to be asynchronously deleted by 5703 * the scsi_hba_barrier_daemon after the specified timeout. Nodes on 5704 * the barrier list are used to implement the bus_config probe cache 5705 * of non-existent devices. The nodes are at DS_INITIALIZED, so their 5706 * @addr is established for searching. Since devi_ref of a DS_INITIALIZED 5707 * node will *not* prevent demotion, demotion is prevented by setting 5708 * sd_uninit_prevent. Devinfo snapshots attempt to attach probe cache 5709 * nodes, and on failure attempt to demote the node (without the participation 5710 * of bus_unconfig) to DS_BOUND - this demotion is prevented via 5711 * sd_uninit_prevent causing any attempted DDI_CTLOPS_UNINITCHILD to fail. 5712 * Probe nodes are bound to nulldriver. The list is sorted by 5713 * expiration time. 5714 * 5715 * NOTE: If we drove a probe node to DS_ATTACHED, we could use ndi_hold_devi() 5716 * to prevent demotion (instead of sd_uninit_prevent). 5717 */ 5718 static void 5719 scsi_hba_barrier_add(dev_info_t *probe, int seconds) 5720 { 5721 struct scsi_hba_barrier *nb; 5722 struct scsi_hba_barrier *b; 5723 struct scsi_hba_barrier **bp; 5724 clock_t endtime; 5725 5726 ASSERT(scsi_hba_devi_is_barrier(probe)); 5727 5728 /* HBA is no longer responsible for nodes on the barrier list. */ 5729 scsi_hba_barrier_tran_tgt_free(probe); 5730 nb = kmem_alloc(sizeof (struct scsi_hba_barrier), KM_SLEEP); 5731 mutex_enter(&scsi_hba_barrier_mutex); 5732 endtime = ddi_get_lbolt() + drv_usectohz(seconds * MICROSEC); 5733 for (bp = &scsi_hba_barrier_list; (b = *bp) != NULL; 5734 bp = &b->barrier_next) 5735 if (b->barrier_endtime > endtime) 5736 break; 5737 nb->barrier_next = *bp; 5738 nb->barrier_endtime = endtime; 5739 nb->barrier_probe = probe; 5740 *bp = nb; 5741 if (bp == &scsi_hba_barrier_list) 5742 (void) cv_signal(&scsi_hba_barrier_cv); 5743 mutex_exit(&scsi_hba_barrier_mutex); 5744 } 5745 5746 /* 5747 * Attempt to remove devinfo node node, return 1 if removed. We 5748 * don't try to remove barrier nodes that have sd_uninit_prevent set 5749 * (even though they should fail device_uninitchild). 5750 */ 5751 static int 5752 scsi_hba_remove_node(dev_info_t *child) 5753 { 5754 dev_info_t *self = ddi_get_parent(child); 5755 struct scsi_device *sd; 5756 int circ; 5757 int remove = 1; 5758 int ret = 0; 5759 char na[SCSI_MAXNAMELEN]; 5760 5761 scsi_hba_devi_enter(self, &circ); 5762 5763 /* Honor sd_uninit_prevent on barrier nodes */ 5764 if (scsi_hba_devi_is_barrier(child)) { 5765 sd = ddi_get_driver_private(child); 5766 if (sd && sd->sd_uninit_prevent) 5767 remove = 0; 5768 } 5769 5770 if (remove) { 5771 (void) ddi_deviname(child, na); 5772 if (ddi_remove_child(child, 0) != DDI_SUCCESS) { 5773 SCSI_HBA_LOG((_LOG(2), NULL, child, 5774 "remove_node failed")); 5775 } else { 5776 child = NULL; /* child is gone */ 5777 SCSI_HBA_LOG((_LOG(4), self, NULL, 5778 "remove_node removed %s", *na ? &na[1] : na)); 5779 ret = 1; 5780 } 5781 } else { 5782 SCSI_HBA_LOG((_LOG(4), NULL, child, "remove_node prevented")); 5783 } 5784 scsi_hba_devi_exit(self, circ); 5785 return (ret); 5786 } 5787 5788 /* 5789 * The asynchronous barrier deletion daemon. Waits for a barrier timeout 5790 * to expire, then deletes the barrier (removes it as a child). 5791 */ 5792 /*ARGSUSED*/ 5793 static void 5794 scsi_hba_barrier_daemon(void *arg) 5795 { 5796 struct scsi_hba_barrier *b; 5797 dev_info_t *probe; 5798 callb_cpr_t cprinfo; 5799 int circ; 5800 dev_info_t *self; 5801 5802 CALLB_CPR_INIT(&cprinfo, &scsi_hba_barrier_mutex, 5803 callb_generic_cpr, "scsi_hba_barrier_daemon"); 5804 again: mutex_enter(&scsi_hba_barrier_mutex); 5805 for (;;) { 5806 b = scsi_hba_barrier_list; 5807 if (b == NULL) { 5808 /* all barriers expired, wait for barrier_add */ 5809 CALLB_CPR_SAFE_BEGIN(&cprinfo); 5810 (void) cv_wait(&scsi_hba_barrier_cv, 5811 &scsi_hba_barrier_mutex); 5812 CALLB_CPR_SAFE_END(&cprinfo, &scsi_hba_barrier_mutex); 5813 } else { 5814 if (ddi_get_lbolt() >= b->barrier_endtime) { 5815 /* 5816 * Drop and retry if ordering issue. Do this 5817 * before calling scsi_hba_remove_node() and 5818 * deadlocking. 5819 */ 5820 probe = b->barrier_probe; 5821 self = ddi_get_parent(probe); 5822 if (scsi_hba_devi_tryenter(self, &circ) == 0) { 5823 delay: mutex_exit(&scsi_hba_barrier_mutex); 5824 delay_random(5); 5825 goto again; 5826 } 5827 5828 /* process expired barrier */ 5829 if (!scsi_hba_remove_node(probe)) { 5830 /* remove failed, delay and retry */ 5831 SCSI_HBA_LOG((_LOG(4), NULL, probe, 5832 "delay expire")); 5833 scsi_hba_devi_exit(self, circ); 5834 goto delay; 5835 } 5836 scsi_hba_barrier_list = b->barrier_next; 5837 kmem_free(b, sizeof (struct scsi_hba_barrier)); 5838 scsi_hba_devi_exit(self, circ); 5839 } else { 5840 /* establish timeout for next barrier expire */ 5841 (void) cv_timedwait(&scsi_hba_barrier_cv, 5842 &scsi_hba_barrier_mutex, 5843 b->barrier_endtime); 5844 } 5845 } 5846 } 5847 } 5848 5849 /* 5850 * Remove all barriers associated with the specified HBA. This is called 5851 * from from the bus_unconfig implementation to remove probe nodes associated 5852 * with the specified HBA (self) so that probe nodes that have not expired 5853 * will not prevent DR of the HBA. 5854 */ 5855 static void 5856 scsi_hba_barrier_purge(dev_info_t *self) 5857 { 5858 struct scsi_hba_barrier **bp; 5859 struct scsi_hba_barrier *b; 5860 5861 mutex_enter(&scsi_hba_barrier_mutex); 5862 for (bp = &scsi_hba_barrier_list; (b = *bp) != NULL; ) { 5863 if (ddi_get_parent(b->barrier_probe) == self) { 5864 if (scsi_hba_remove_node(b->barrier_probe)) { 5865 *bp = b->barrier_next; 5866 kmem_free(b, sizeof (struct scsi_hba_barrier)); 5867 } else { 5868 SCSI_HBA_LOG((_LOG(4), NULL, b->barrier_probe, 5869 "skip purge")); 5870 } 5871 } else 5872 bp = &b->barrier_next; 5873 } 5874 5875 mutex_exit(&scsi_hba_barrier_mutex); 5876 } 5877 5878 /* 5879 * LUN-change processing daemons: processing occurs in two stages: 5880 * 5881 * Stage 1: Daemon waits for a lunchg1 queued scsi_pkt, dequeues the pkt, 5882 * forms the path, completes the scsi_pkt (pkt_comp), and 5883 * queues the path for stage 2 processing. The use of stage 1 5884 * avoids issues related to memory allocation in interrupt context 5885 * (scsi_hba_pkt_comp()). We delay the pkt_comp completion until 5886 * after lunchg1 processing forms the path for stage 2 - this is 5887 * done to prevent the target driver from detaching until the 5888 * path formation is complete (driver with outstanding commands 5889 * should not detach). 5890 * 5891 * Stage 2: Daemon waits for a lunchg2 queued request, dequeues the 5892 * request, and opens the path using ldi_open_by_name(). The 5893 * path opened uses a special "@taddr,*" unit address that will 5894 * trigger lun enumeration in scsi_hba_bus_configone(). We 5895 * trigger lun enumeration in stage 2 to avoid problems when 5896 * initial ASC/ASCQ trigger occurs during discovery. 5897 */ 5898 /*ARGSUSED*/ 5899 static void 5900 scsi_lunchg1_daemon(void *arg) 5901 { 5902 callb_cpr_t cprinfo; 5903 struct scsi_pkt *pkt; 5904 scsi_hba_tran_t *tran; 5905 dev_info_t *self; 5906 struct scsi_device *sd; 5907 char *ua, *p; 5908 char taddr[SCSI_MAXNAMELEN]; 5909 char path[MAXPATHLEN]; 5910 struct scsi_lunchg2 *lunchg2; 5911 5912 CALLB_CPR_INIT(&cprinfo, &scsi_lunchg1_mutex, 5913 callb_generic_cpr, "scsi_lunchg1_daemon"); 5914 mutex_enter(&scsi_lunchg1_mutex); 5915 for (;;) { 5916 pkt = scsi_lunchg1_list; 5917 if (pkt == NULL) { 5918 /* All lunchg1 processing requests serviced, wait. */ 5919 CALLB_CPR_SAFE_BEGIN(&cprinfo); 5920 (void) cv_wait(&scsi_lunchg1_cv, 5921 &scsi_lunchg1_mutex); 5922 CALLB_CPR_SAFE_END(&cprinfo, &scsi_lunchg1_mutex); 5923 continue; 5924 } 5925 5926 /* Unlink and perform lunchg1 processing on pkt. */ 5927 scsi_lunchg1_list = pkt->pkt_stmp; 5928 5929 /* Determine initiator port (self) from the pkt_address. */ 5930 tran = pkt->pkt_address.a_hba_tran; 5931 ASSERT(tran && tran->tran_tgtmap && tran->tran_iport_dip); 5932 self = tran->tran_iport_dip; 5933 5934 /* 5935 * Determine scsi_devie from pkt_address (depends on 5936 * SCSI_HBA_ADDR_COMPLEX). 5937 */ 5938 sd = scsi_address_device(&(pkt->pkt_address)); 5939 ASSERT(sd); 5940 if (sd == NULL) { 5941 (*pkt->pkt_comp)(pkt); 5942 continue; 5943 } 5944 5945 /* Determine unit-address from scsi_device. */ 5946 ua = scsi_device_unit_address(sd); 5947 5948 /* Extract taddr from the unit-address. */ 5949 for (p = taddr; (*ua != ',') && (*ua != '\0'); ) 5950 *p++ = *ua++; 5951 *p = '\0'; /* NULL terminate taddr */ 5952 5953 /* 5954 * Form path using special "@taddr,*" notation to trigger 5955 * lun enumeration. 5956 */ 5957 (void) ddi_pathname(self, path); 5958 (void) strcat(path, "/luns@"); 5959 (void) strcat(path, taddr); 5960 (void) strcat(path, ",*"); 5961 5962 /* 5963 * Now that we have the path, complete the pkt that 5964 * triggered lunchg1 processing. 5965 */ 5966 (*pkt->pkt_comp)(pkt); 5967 5968 /* Allocate element for stage2 processing queue. */ 5969 lunchg2 = kmem_alloc(sizeof (*lunchg2), KM_SLEEP); 5970 lunchg2->lunchg2_path = strdup(path); 5971 5972 /* Queue and dispatch to stage 2. */ 5973 SCSI_HBA_LOG((_LOG(2), self, NULL, 5974 "lunchg stage1: queue %s", lunchg2->lunchg2_path)); 5975 mutex_enter(&scsi_lunchg2_mutex); 5976 lunchg2->lunchg2_next = scsi_lunchg2_list; 5977 scsi_lunchg2_list = lunchg2; 5978 if (lunchg2->lunchg2_next == NULL) 5979 (void) cv_signal(&scsi_lunchg2_cv); 5980 mutex_exit(&scsi_lunchg2_mutex); 5981 } 5982 } 5983 5984 /*ARGSUSED*/ 5985 static void 5986 scsi_lunchg2_daemon(void *arg) 5987 { 5988 callb_cpr_t cprinfo; 5989 struct scsi_lunchg2 *lunchg2; 5990 ldi_ident_t li; 5991 ldi_handle_t lh; 5992 5993 CALLB_CPR_INIT(&cprinfo, &scsi_lunchg2_mutex, 5994 callb_generic_cpr, "scsi_lunchg2_daemon"); 5995 5996 li = ldi_ident_from_anon(); 5997 mutex_enter(&scsi_lunchg2_mutex); 5998 for (;;) { 5999 lunchg2 = scsi_lunchg2_list; 6000 if (lunchg2 == NULL) { 6001 /* All lunchg2 processing requests serviced, wait. */ 6002 CALLB_CPR_SAFE_BEGIN(&cprinfo); 6003 (void) cv_wait(&scsi_lunchg2_cv, 6004 &scsi_lunchg2_mutex); 6005 CALLB_CPR_SAFE_END(&cprinfo, &scsi_lunchg2_mutex); 6006 continue; 6007 } 6008 6009 /* Unlink and perform lunchg2 processing on pkt. */ 6010 scsi_lunchg2_list = lunchg2->lunchg2_next; 6011 6012 /* 6013 * Open and close the path to trigger lun enumeration. We 6014 * don't expect the open to succeed, but we do expect code in 6015 * scsi_hba_bus_configone() to trigger lun enumeration. 6016 */ 6017 SCSI_HBA_LOG((_LOG(2), NULL, NULL, 6018 "lunchg stage2: open %s", lunchg2->lunchg2_path)); 6019 if (ldi_open_by_name(lunchg2->lunchg2_path, 6020 FREAD, kcred, &lh, li) == 0) 6021 (void) ldi_close(lh, FREAD, kcred); 6022 6023 /* Free path and linked element. */ 6024 strfree(lunchg2->lunchg2_path); 6025 kmem_free(lunchg2, sizeof (*lunchg2)); 6026 } 6027 } 6028 6029 /* 6030 * Enumerate a child at the specified @addr. If a device exists @addr then 6031 * ensure that we have the appropriately named devinfo node for it. Name is 6032 * NULL in the bus_config_all case. This routine has no knowledge of the 6033 * format of an @addr string or associated addressing properties. 6034 * 6035 * The caller must guarantee that there is an open scsi_hba_devi_enter on the 6036 * parent. We return the scsi_device structure for the child device. This 6037 * scsi_device structure is valid until the caller scsi_hba_devi_exit the 6038 * parent. The caller can add do ndi_hold_devi of the child prior to the 6039 * scsi_hba_devi_exit to extend the validity of the child. 6040 * 6041 * In some cases the returned scsi_device structure may be used to drive 6042 * additional SCMD_REPORT_LUNS operations by bus_config_all callers. 6043 * 6044 * The first operation performed is to see if there is a dynamic SID nodes 6045 * already attached at the specified "name@addr". This is the fastpath 6046 * case for resolving a reference to a node that has already been created. 6047 * All other references are serialized for a given @addr prior to probing 6048 * to determine the type of device, if any, at the specified @addr. 6049 * If no device is present then NDI_FAILURE is returned. The fact that a 6050 * device does not exist may be determined via the barrier/probe cache, 6051 * minimizing the probes of non-existent devices. 6052 * 6053 * When there is a device present the dynamic SID node is created based on 6054 * the device found. If a driver.conf node exists for the same @addr it 6055 * will either merge into the dynamic SID node (if the SID node bound to 6056 * that driver), or exist independently. To prevent the actions of one driver 6057 * causing side effects in another, code prevents multiple SID nodes from 6058 * binding to the same "@addr" at the same time. There is autodetach code 6059 * to allow one device to be replaced with another at the same @addr for 6060 * slot addressed SCSI bus implementations (SPI). For compatibility with 6061 * legacy driver.conf behavior, the code does not prevent multiple driver.conf 6062 * nodes from attaching to the same @addr at the same time. 6063 * 6064 * This routine may have the side effect of creating nodes for devices other 6065 * than the one being sought. It is possible that there is a different type of 6066 * target device at that target/lun address than we were asking for. In that 6067 * It is the caller's responsibility to determine whether the device we found, 6068 * if any, at the specified address, is the one it really wanted. 6069 */ 6070 static struct scsi_device * 6071 scsi_device_config(dev_info_t *self, char *name, char *addr, scsi_enum_t se, 6072 int *circp, int *ppi) 6073 { 6074 dev_info_t *child = NULL; 6075 dev_info_t *probe = NULL; 6076 struct scsi_device *sdchild; 6077 struct scsi_device *sdprobe; 6078 dev_info_t *dsearch; 6079 mdi_pathinfo_t *psearch; 6080 major_t major; 6081 int sp; 6082 int pi = 0; 6083 int wait_msg = scsi_hba_wait_msg; 6084 int chg; 6085 6086 ASSERT(self && addr && DEVI_BUSY_OWNED(self)); 6087 6088 SCSI_HBA_LOG((_LOG(4), self, NULL, "%s@%s wanted", 6089 name ? name : "", addr)); 6090 6091 /* playing with "probe" node name is dangerous */ 6092 if (name && (strcmp(name, "probe") == 0)) 6093 return (NULL); 6094 6095 /* 6096 * NOTE: use 'goto done;' or 'goto fail;'. There should only be one 6097 * 'return' statement from here to the end of the function - the one 6098 * on the last line of the function. 6099 */ 6100 6101 /* 6102 * Fastpath: search to see if we are requesting a named SID node that 6103 * already exists (we already created) - probe node does not count. 6104 * scsi_findchild() does not hold the returned devinfo node, but 6105 * this is OK since the caller has a scsi_hba_devi_enter on the 6106 * attached parent HBA (self). The caller is responsible for attaching 6107 * and placing a hold on the child (directly via ndi_hold_devi or 6108 * indirectly via ndi_busop_bus_config) before doing an 6109 * scsi_hba_devi_exit on the parent. 6110 * 6111 * NOTE: This fastpath prevents detecting a driver binding change 6112 * (autodetach) if the same nodename is used for old and new binding. 6113 */ 6114 /* first call is with init set */ 6115 (void) scsi_findchild(self, name, addr, 1, &dsearch, NULL, &pi); 6116 if (dsearch && scsi_hba_dev_is_sid(dsearch) && 6117 !scsi_hba_devi_is_barrier(dsearch)) { 6118 SCSI_HBA_LOG((_LOG(4), NULL, dsearch, 6119 "%s@%s devinfo fastpath", name ? name : "", addr)); 6120 child = dsearch; 6121 goto done; 6122 } 6123 6124 /* 6125 * Create a barrier devinfo node used to "probe" the device with. We 6126 * need to drive this node to DS_INITIALIZED so that the 6127 * DDI_CTLOPS_INITCHILD has occurred, bringing the SCSA transport to 6128 * a state useable state for issuing our "probe" commands. We establish 6129 * this barrier node with a node name of "probe" and compatible 6130 * property of "scsiprobe". The compatible property must be associated 6131 * in /etc/driver_aliases with a scsi target driver available in the 6132 * root file system (sd). 6133 * 6134 * The "probe" that we perform on the barrier node, after it is 6135 * DS_INITIALIZED, is used to find the information needed to create a 6136 * dynamic devinfo (SID) node. This "probe" is separate from the 6137 * probe(9E) call associated with the transition of a node from 6138 * DS_INITIALIZED to DS_PROBED. The probe(9E) call that eventually 6139 * occurs against the created SID node should find ddi_dev_is_sid and 6140 * just return DDI_PROBE_DONTCARE. 6141 * 6142 * Trying to avoid the use of a barrier node is not a good idea 6143 * because we may have an HBA driver that uses generic bus_config 6144 * (this code) but implements its own DDI_CTLOPS_INITCHILD with side 6145 * effects that we can't duplicate (such as the ATA nexus driver). 6146 * 6147 * The probe/barrier node plays an integral part of the locking scheme. 6148 * The objective is to single thread probes of the same device (same 6149 * @addr) while allowing parallelism for probes of different devices 6150 * with the same parent. At this point we are serialized on our self. 6151 * For parallelism we will need to release our self. Prior to release 6152 * we construct a barrier for probes of the same device to serialize 6153 * against. The "probe@addr" node acts as this barrier. An entering 6154 * thread must wait until the probe node does not exist - it can then 6155 * create and link the probe node - dropping the HBA (self) lock after 6156 * the node is linked and visible (after ddi_initchild). A side effect 6157 * of this is that transports should not "go over the wire" (i.e. do 6158 * things that incur significant delays) until after tran_target_init. 6159 * This means that the first "over the wire" operation should occur 6160 * at tran_target_probe time - when things are running in parallel 6161 * again. 6162 * 6163 * If the probe node exists then another probe with the same @addr is 6164 * in progress, we must wait until there is no probe in progress 6165 * before proceeding, and when we proceed we must continue to hold the 6166 * HBA (self) until we have linked a new probe node as a barrier. 6167 * 6168 * When a device is found to *not* exist, its probe/barrier node may be 6169 * marked with DEVICE_REMOVED with node deletion scheduled for some 6170 * future time (seconds). This asynchronous deletion allows the 6171 * framework to detect repeated requests to the same non-existent 6172 * device and avoid overhead associated with contacting a non-existent 6173 * device again and again. 6174 */ 6175 for (;;) { 6176 /* 6177 * Search for probe node - they should only exist as devinfo 6178 * nodes. 6179 */ 6180 (void) scsi_findchild(self, "probe", addr, 6181 0, &probe, &psearch, NULL); 6182 if (probe == NULL) { 6183 if (psearch) 6184 SCSI_HBA_LOG((_LOG(2), self, 6185 mdi_pi_get_client(psearch), 6186 "???? @%s 'probe' search found " 6187 "pathinfo: %p", addr, (void *)psearch)); 6188 break; 6189 } 6190 6191 /* 6192 * The barrier node may cache the non-existence of a device 6193 * by leaving the barrier node in place (with 6194 * DEVI_DEVICE_REMOVED flag set ) for some amount of time after 6195 * the failure of a probe. This flag is used to fail 6196 * additional probes until the barrier probe node is deleted, 6197 * which will occur from a timeout some time after a failed 6198 * probe. The failed probe will use DEVI_SET_DEVICE_REMOVED 6199 * and schedule probe node deletion from a timeout. The callers 6200 * scsi_hba_devi_exit on the way out of the first failure will 6201 * do the cv_broadcast associated with the cv_wait below - this 6202 * handles threads that wait prior to DEVI_DEVICE_REMOVED being 6203 * set. 6204 */ 6205 if (DEVI_IS_DEVICE_REMOVED(probe)) { 6206 SCSI_HBA_LOG((_LOG(3), NULL, probe, 6207 "detected probe DEVICE_REMOVED")); 6208 probe = NULL; /* deletion already scheduled */ 6209 goto fail; 6210 } 6211 6212 /* 6213 * Drop the lock on the HBA (self) and wait until the probe in 6214 * progress has completed. A changes in the sibling list from 6215 * removing the probe node will cause cv_wait to return 6216 * (scsi_hba_devi_exit does the cv_broadcast). 6217 */ 6218 if (wait_msg) { 6219 wait_msg--; 6220 SCSI_HBA_LOG((_LOG(2), NULL, probe, 6221 "exists, probe already in progress: %s", wait_msg ? 6222 "waiting..." : "last msg, but still waiting...")); 6223 } 6224 6225 /* 6226 * NOTE: we could avoid rare case of one second delay by 6227 * implementing scsi_hba_devi_exit_and_wait based on 6228 * ndi/mdi_devi_exit_and_wait (and consider switching devcfg.c 6229 * code to use these ndi/mdi interfaces too). 6230 */ 6231 scsi_hba_devi_exit(self, *circp); 6232 mutex_enter(&DEVI(self)->devi_lock); 6233 (void) cv_timedwait(&DEVI(self)->devi_cv, 6234 &DEVI(self)->devi_lock, 6235 ddi_get_lbolt() + drv_usectohz(MICROSEC)); 6236 mutex_exit(&DEVI(self)->devi_lock); 6237 scsi_hba_devi_enter(self, circp); 6238 } 6239 ASSERT(probe == NULL); 6240 6241 /* 6242 * Search to see if we are requesting a SID node that already exists. 6243 * We hold the HBA (self) and there is not another probe in progress at 6244 * the same @addr. scsi_findchild() does not hold the returned 6245 * devinfo node but this is OK since we hold the HBA (self). 6246 */ 6247 if (name) { 6248 (void) scsi_findchild(self, name, addr, 1, &dsearch, NULL, &pi); 6249 if (dsearch && scsi_hba_dev_is_sid(dsearch)) { 6250 SCSI_HBA_LOG((_LOG(4), NULL, dsearch, 6251 "%s@%s probe devinfo fastpath", 6252 name ? name : "", addr)); 6253 child = dsearch; 6254 goto done; 6255 } 6256 } 6257 6258 /* 6259 * We are looking for a SID node that does not exist or a driver.conf 6260 * node. 6261 * 6262 * To avoid probe side effects, before we probe the device at the 6263 * specified address we need to check to see if there is already an 6264 * initialized child "@addr". 6265 * 6266 * o If we find an initialized SID child and name is NULL or matches 6267 * the name or the name of the attached driver then we return the 6268 * existing node. 6269 * 6270 * o If we find a non-matching SID node, we will attempt to autodetach 6271 * and remove the node in preference to our new node. 6272 * 6273 * o If SID node found does not match and can't be autodetached, we 6274 * fail: we only allow one SID node at an address. 6275 * 6276 * NOTE: This code depends on SID nodes showing up prior to 6277 * driver.conf nodes in the sibling list. 6278 */ 6279 for (;;) { 6280 /* first NULL name call is with init set */ 6281 (void) scsi_findchild(self, NULL, addr, 1, &dsearch, NULL, &pi); 6282 if (dsearch == NULL) 6283 break; 6284 ASSERT(!scsi_hba_devi_is_barrier(dsearch)); 6285 6286 /* 6287 * To detect changes in driver binding that should attempt 6288 * autodetach we determine the major number of the driver 6289 * that should currently be associated with the device based 6290 * on the compatible property. 6291 */ 6292 major = DDI_MAJOR_T_NONE; 6293 if (scsi_hba_dev_is_sid(dsearch)) 6294 major = ddi_compatible_driver_major(dsearch, NULL); 6295 if ((major == DDI_MAJOR_T_NONE) && (name == NULL)) 6296 major = ddi_driver_major(dsearch); 6297 6298 if ((scsi_hba_dev_is_sid(dsearch) || 6299 (i_ddi_node_state(dsearch) >= DS_INITIALIZED)) && 6300 ((name == NULL) || 6301 (strcmp(ddi_node_name(dsearch), name) == 0) || 6302 (strcmp(ddi_driver_name(dsearch), name) == 0)) && 6303 (major == ddi_driver_major(dsearch))) { 6304 SCSI_HBA_LOG((_LOG(3), NULL, dsearch, 6305 "already attached @addr")); 6306 child = dsearch; 6307 goto done; 6308 } 6309 6310 if (!scsi_hba_dev_is_sid(dsearch)) 6311 break; /* driver.conf node */ 6312 6313 /* 6314 * Implement autodetach of SID node for situations like a 6315 * previously "scsinodev" LUN0 coming into existence (or a 6316 * disk/tape on an SPI transport at same addr but never both 6317 * powered on at the same time). Try to autodetach the existing 6318 * SID node @addr. If that works, search again - otherwise fail. 6319 */ 6320 SCSI_HBA_LOG((_LOG(2), NULL, dsearch, 6321 "looking for %s@%s: SID @addr exists, autodetach", 6322 name ? name : "", addr)); 6323 if (!scsi_hba_remove_node(dsearch)) { 6324 SCSI_HBA_LOG((_LOG(2), NULL, dsearch, 6325 "autodetach @%s failed: fail %s@%s", 6326 addr, name ? name : "", addr)); 6327 goto fail; 6328 } 6329 SCSI_HBA_LOG((_LOG(2), self, NULL, "autodetach @%s OK", addr)); 6330 } 6331 6332 /* 6333 * We will be creating a new SID node, allocate probe node 6334 * used to find out information about the device located @addr. 6335 * The probe node also acts as a barrier against additional 6336 * configuration at the same address, and in the case of non-existent 6337 * devices it will (for some amount of time) avoid re-learning that 6338 * the device does not exist on every reference. Once the probe 6339 * node is DS_LINKED we can drop the HBA (self). 6340 * 6341 * The probe node is allocated as a hidden node so that it does not 6342 * show up in devinfo snapshots. 6343 */ 6344 ndi_devi_alloc_sleep(self, "probe", 6345 (se == SE_HP) ? DEVI_SID_HP_HIDDEN_NODEID : DEVI_SID_HIDDEN_NODEID, 6346 &probe); 6347 ASSERT(probe); 6348 ndi_flavor_set(probe, SCSA_FLAVOR_SCSI_DEVICE); 6349 6350 /* 6351 * Decorate the probe node with the property representation of @addr 6352 * unit-address string prior to initchild so that initchild can 6353 * construct the name of the node from properties and tran_tgt_init 6354 * implementation can determine what LUN is being referenced. 6355 * 6356 * If the addr specified has incorrect syntax (busconfig one of bogus 6357 * /devices path) then scsi_hba_ua_set can fail. If the address 6358 * is not understood by the SCSA HBA driver then this operation will 6359 * work, but tran_tgt_init may still fail (for example the HBA 6360 * driver may not support secondary functions). 6361 */ 6362 if (scsi_hba_ua_set(addr, probe, NULL) == 0) { 6363 SCSI_HBA_LOG((_LOG(2), NULL, probe, 6364 "@%s failed scsi_hba_ua_set", addr)); 6365 goto fail; 6366 } 6367 6368 /* 6369 * Set the class property to "scsi". This is sufficient to distinguish 6370 * the node for HBAs that have multiple classes of children (like uata 6371 * - which has "dada" class for ATA children and "scsi" class for 6372 * ATAPI children) and may not use our scsi_busctl_initchild() 6373 * implementation. We also add a "compatible" property of "scsiprobe" 6374 * to select the probe driver. 6375 */ 6376 if ((ndi_prop_update_string(DDI_DEV_T_NONE, probe, 6377 "class", "scsi") != DDI_PROP_SUCCESS) || 6378 (ndi_prop_update_string_array(DDI_DEV_T_NONE, probe, 6379 "compatible", &compatible_probe, 1) != DDI_PROP_SUCCESS)) { 6380 SCSI_HBA_LOG((_LOG(1), NULL, probe, 6381 "@%s failed node decoration", addr)); 6382 goto fail; 6383 } 6384 6385 /* 6386 * Promote probe node to DS_INITIALIZED so that transport can be used 6387 * for scsi_probe. After this the node is linked and visible as a 6388 * barrier for serialization of other @addr operations. 6389 * 6390 * NOTE: If we attached the probe node, we could get rid of 6391 * uninit_prevent. 6392 */ 6393 if (ddi_initchild(self, probe) != DDI_SUCCESS) { 6394 SCSI_HBA_LOG((_LOG(2), NULL, probe, 6395 "@%s failed initchild", addr)); 6396 6397 /* probe node will be removed in fail exit path */ 6398 goto fail; 6399 } 6400 6401 /* get the scsi_device structure of the probe node */ 6402 sdprobe = ddi_get_driver_private(probe); 6403 ASSERT(sdprobe); 6404 6405 /* 6406 * Do scsi_probe. The probe node is linked and visible as a barrier. 6407 * We prevent uninitialization of the probe node and drop our HBA (self) 6408 * while we run scsi_probe() of this "@addr". This allows the framework 6409 * to support multiple scsi_probes for different devices attached to 6410 * the same HBA (self) in parallel. We prevent node demotion of the 6411 * probe node from DS_INITIALIZED by setting sd_uninit_prevent. The 6412 * probe node can not be successfully demoted below DS_INITIALIZED 6413 * (scsi_busctl_uninitchild will fail) until we zero sd_uninit_prevent 6414 * as we are freeing the node via scsi_hba_remove_node(probe). 6415 */ 6416 sdprobe->sd_uninit_prevent++; 6417 scsi_hba_devi_exit(self, *circp); 6418 sp = scsi_probe(sdprobe, SLEEP_FUNC); 6419 6420 /* Introduce a small delay here to increase parallelism. */ 6421 delay_random(5); 6422 6423 if (sp == SCSIPROBE_EXISTS) { 6424 /* 6425 * For a device that exists, while still running in parallel, 6426 * also get identity information from device. This is done 6427 * separate from scsi_probe/tran_tgt_probe/scsi_hba_probe 6428 * since the probe code path may still be used for HBAs 6429 * that don't use common bus_config services (we don't want 6430 * to expose that code path to a behavior change). This 6431 * operation is called 'identity' to avoid confusion with 6432 * deprecated identify(9E). 6433 * 6434 * Future: We may eventually want to allow HBA customization via 6435 * scsi_identity/tran_tgt_identity/scsi_device_identity, but for 6436 * now we just scsi_device_identity. 6437 * 6438 * The identity operation will establish additional properties 6439 * on the probe node related to device identity: 6440 * 6441 * "inquiry-page-80" byte array of SCSI page 80 6442 * "inquiry-page-83" byte array of SCSI page 83 6443 * 6444 * These properties will be used to generate a devid 6445 * (ddi_devid_scsi_encode) and guid - and to register 6446 * (ddi_devid_register) a devid for the device. 6447 * 6448 * If identify fails (non-zero return), the we had allocation 6449 * problems or the device returned inconsistent results then 6450 * we pretend that device does not exist. 6451 */ 6452 if (scsi_device_identity(sdprobe, SLEEP_FUNC)) { 6453 scsi_enumeration_failed(probe, -1, NULL, "identify"); 6454 sp = SCSIPROBE_FAILURE; 6455 } 6456 6457 /* 6458 * Future: Is there anything more we can do here to help avoid 6459 * serialization on iport parent during scsi_device attach(9E)? 6460 */ 6461 } 6462 scsi_hba_devi_enter(self, circp); 6463 sdprobe->sd_uninit_prevent--; 6464 6465 if (sp != SCSIPROBE_EXISTS) { 6466 scsi_enumeration_failed(probe, -1, NULL, "probe"); 6467 6468 if ((se != SE_HP) && scsi_hba_barrier_timeout) { 6469 /* 6470 * Target does not exist. Mark the barrier probe node 6471 * as DEVICE_REMOVED and schedule an asynchronous 6472 * deletion of the node in scsi_hba_barrier_timeout 6473 * seconds. We keep our hold on the probe node 6474 * until we are ready perform the asynchronous node 6475 * deletion. 6476 */ 6477 SCSI_HBA_LOG((_LOG(3), NULL, probe, 6478 "set probe DEVICE_REMOVED")); 6479 mutex_enter(&DEVI(probe)->devi_lock); 6480 DEVI_SET_DEVICE_REMOVED(probe); 6481 mutex_exit(&DEVI(probe)->devi_lock); 6482 6483 scsi_hba_barrier_add(probe, scsi_hba_barrier_timeout); 6484 probe = NULL; 6485 } 6486 goto fail; 6487 } 6488 6489 /* Create the child node from the inquiry data in the probe node. */ 6490 if ((child = scsi_device_configchild(self, addr, se, sdprobe, 6491 circp, &pi)) == NULL) { 6492 /* 6493 * This may fail because there was no driver binding identified 6494 * via driver_alias. We may still have a conf node. 6495 */ 6496 if (name) { 6497 (void) scsi_findchild(self, name, addr, 6498 0, &child, NULL, &pi); 6499 if (child) 6500 SCSI_HBA_LOG((_LOG(2), NULL, child, 6501 "using driver.conf driver binding")); 6502 } 6503 if (child == NULL) { 6504 SCSI_HBA_LOG((_LOG(2), NULL, probe, 6505 "device not configured")); 6506 goto fail; 6507 } 6508 } 6509 6510 /* 6511 * Transfer the inquiry data from the probe node to the child 6512 * SID node to avoid an extra scsi_probe. Callers depend on 6513 * established inquiry data for the returned scsi_device. 6514 */ 6515 sdchild = ddi_get_driver_private(child); 6516 if (sdchild && (sdchild->sd_inq == NULL)) { 6517 sdchild->sd_inq = sdprobe->sd_inq; 6518 sdprobe->sd_inq = NULL; 6519 } 6520 6521 /* 6522 * If we are doing a bus_configone and the node we created has the 6523 * wrong node and driver name then switch the return result to a 6524 * driver.conf node with the correct name - if such a node exists. 6525 */ 6526 if (name && (strcmp(ddi_node_name(child), name) != 0) && 6527 (strcmp(ddi_driver_name(child), name) != 0)) { 6528 (void) scsi_findchild(self, name, addr, 6529 0, &dsearch, NULL, &pi); 6530 if (dsearch == NULL) { 6531 SCSI_HBA_LOG((_LOG(2), NULL, child, 6532 "wrong device configured %s@%s", name, addr)); 6533 /* 6534 * We can't remove when modrootloaded == 0 in case 6535 * boot-device a uses generic name and 6536 * scsi_hba_nodename_compatible_get() returned a 6537 * legacy binding-set driver oriented name. 6538 */ 6539 if (modrootloaded) { 6540 (void) scsi_hba_remove_node(child); 6541 child = NULL; 6542 goto fail; 6543 } 6544 } else { 6545 SCSI_HBA_LOG((_LOG(2), NULL, dsearch, 6546 "device configured, but switching to driver.conf")); 6547 child = dsearch; 6548 } 6549 } 6550 6551 /* get the scsi_device structure from the node */ 6552 SCSI_HBA_LOG((_LOG(3), NULL, child, "device configured")); 6553 6554 if (child) { 6555 done: ASSERT(child); 6556 sdchild = ddi_get_driver_private(child); 6557 ASSERT(sdchild); 6558 6559 /* 6560 * We may have ended up here after promotion of a previously 6561 * demoted node, where demotion deleted sd_inq data in 6562 * scsi_busctl_uninitchild. We redo the scsi_probe() to 6563 * reestablish sd_inq. We also want to redo the scsi_probe 6564 * for devices are currently device_isremove in order to 6565 * detect new device_insert. 6566 */ 6567 if ((sdchild->sd_inq == NULL) || 6568 ((pi == NULL) && ndi_devi_device_isremoved(child))) { 6569 6570 /* hotplug_node can only be revived via hotplug. */ 6571 if ((se == SE_HP) || !ndi_dev_is_hotplug_node(child)) { 6572 SCSI_HBA_LOG((_LOG(3), NULL, child, 6573 "scsi_probe() demoted devinfo")); 6574 6575 sp = scsi_probe(sdchild, SLEEP_FUNC); 6576 6577 if (sp == SCSIPROBE_EXISTS) { 6578 ASSERT(sdchild->sd_inq); 6579 6580 /* 6581 * Devinfo child exists and we are 6582 * talking to the device, report 6583 * reinsert and note if this was a 6584 * new reinsert. 6585 */ 6586 chg = ndi_devi_device_insert(child); 6587 SCSI_HBA_LOG((_LOGCFG, NULL, child, 6588 "devinfo %s@%s device_reinsert%s", 6589 name ? name : "", addr, 6590 chg ? "" : "ed already")); 6591 } else { 6592 scsi_enumeration_failed(child, se, 6593 NULL, "reprobe"); 6594 6595 chg = ndi_devi_device_remove(child); 6596 SCSI_HBA_LOG((_LOG(2), NULL, child, 6597 "%s device_remove%s", 6598 (sp > (sizeof (scsi_probe_ascii) / 6599 sizeof (scsi_probe_ascii[0]))) ? 6600 "UNKNOWN" : scsi_probe_ascii[sp], 6601 chg ? "" : "ed already")); 6602 6603 child = NULL; 6604 sdchild = NULL; 6605 } 6606 } else { 6607 SCSI_HBA_LOG((_LOG(2), NULL, child, 6608 "no reprobe")); 6609 6610 child = NULL; 6611 sdchild = NULL; 6612 } 6613 } 6614 } else { 6615 fail: ASSERT(child == NULL); 6616 sdchild = NULL; 6617 } 6618 if (probe) { 6619 /* 6620 * Clean up probe node, destroying node if uninit_prevent 6621 * it is going to zero. Destroying the probe node (deleting 6622 * from the sibling list) will wake up any people waiting on 6623 * the probe node barrier. 6624 */ 6625 SCSI_HBA_LOG((_LOG(4), NULL, probe, "remove probe")); 6626 if (!scsi_hba_remove_node(probe)) { 6627 /* 6628 * Probe node removal should not fail, but if it 6629 * does we hand that responsibility over to the 6630 * async barrier deletion thread - other references 6631 * to the same unit-address can hang until the 6632 * probe node delete completes. 6633 */ 6634 SCSI_HBA_LOG((_LOG(4), NULL, probe, 6635 "remove probe failed, go async")); 6636 scsi_hba_barrier_add(probe, 1); 6637 } 6638 probe = NULL; 6639 } 6640 6641 /* 6642 * If we successfully resolved via a pathinfo node, we need to find 6643 * the pathinfo node and ensure that it is online (if possible). This 6644 * is done for the case where the device was open when 6645 * scsi_device_unconfig occurred, so mdi_pi_free did not occur. If the 6646 * device has now been reinserted, we want the path back online. 6647 * NOTE: This needs to occur after destruction of the probe node to 6648 * avoid ASSERT related to two nodes at the same unit-address. 6649 */ 6650 if (sdchild && pi && (probe == NULL)) { 6651 ASSERT(MDI_PHCI(self)); 6652 6653 (void) scsi_findchild(self, NULL, addr, 6654 0, &dsearch, &psearch, NULL); 6655 ASSERT((psearch == NULL) || 6656 (mdi_pi_get_client(psearch) == child)); 6657 6658 if (psearch && mdi_pi_device_isremoved(psearch)) { 6659 /* 6660 * Verify that we can talk to the device, and if 6661 * so note if this is a new device_insert. 6662 * 6663 * NOTE: We depend on mdi_path_select(), when given 6664 * a specific path_instance, to select that path 6665 * even if the path is offline. 6666 * 6667 * NOTE: A Client node is not ndi_dev_is_hotplug_node(). 6668 */ 6669 if (se == SE_HP) { 6670 SCSI_HBA_LOG((_LOG(3), NULL, child, 6671 "%s scsi_probe() demoted pathinfo", 6672 mdi_pi_spathname(psearch))); 6673 6674 sp = scsi_hba_probe_pi(sdchild, SLEEP_FUNC, pi); 6675 6676 if (sp == SCSIPROBE_EXISTS) { 6677 /* 6678 * Pathinfo child exists and we are 6679 * talking to the device, report 6680 * reinsert and note if this 6681 * was a new reinsert. 6682 */ 6683 chg = mdi_pi_device_insert(psearch); 6684 SCSI_HBA_LOG((_LOGCFG, self, NULL, 6685 "pathinfo %s device_reinsert%s", 6686 mdi_pi_spathname(psearch), 6687 chg ? "" : "ed already")); 6688 6689 if (chg) 6690 (void) mdi_pi_online(psearch, 6691 0); 6692 6693 /* 6694 * Report client reinsert and note if 6695 * this was a new reinsert. 6696 */ 6697 chg = ndi_devi_device_insert(child); 6698 SCSI_HBA_LOG((_LOGCFG, NULL, child, 6699 "client devinfo %s@%s " 6700 "device_reinsert%s", 6701 name ? name : "", addr, 6702 chg ? "" : "ed already")); 6703 } else { 6704 scsi_enumeration_failed(child, se, 6705 mdi_pi_spathname(psearch), 6706 "reprobe"); 6707 child = NULL; 6708 sdchild = NULL; 6709 } 6710 6711 } else { 6712 SCSI_HBA_LOG((_LOG(2), NULL, child, 6713 "%s no reprobe", 6714 mdi_pi_spathname(psearch))); 6715 6716 child = NULL; 6717 sdchild = NULL; 6718 } 6719 } 6720 } 6721 6722 /* If asked for path_instance, return it. */ 6723 if (ppi) 6724 *ppi = pi; 6725 6726 return (sdchild); 6727 } 6728 6729 static void 6730 scsi_device_unconfig(dev_info_t *self, char *name, char *addr, int *circp) 6731 { 6732 dev_info_t *child = NULL; 6733 mdi_pathinfo_t *path = NULL; 6734 char *spathname; 6735 int rval; 6736 6737 ASSERT(self && addr && DEVI_BUSY_OWNED(self)); 6738 6739 /* 6740 * We have a catch-22. We may have a demoted node that we need to find 6741 * and offline/remove. To find the node if it isn't demoted, we 6742 * use scsi_findchild. If it's demoted, we then use 6743 * ndi_devi_findchild_by_callback. 6744 */ 6745 (void) scsi_findchild(self, name, addr, 0, &child, &path, NULL); 6746 6747 if ((child == NULL) && (path == NULL)) { 6748 child = ndi_devi_findchild_by_callback(self, name, addr, 6749 scsi_busctl_ua); 6750 if (child) { 6751 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6752 "devinfo %s@%s found by callback", 6753 name ? name : "", addr)); 6754 ASSERT(ndi_flavor_get(child) == 6755 SCSA_FLAVOR_SCSI_DEVICE); 6756 if (ndi_flavor_get(child) != SCSA_FLAVOR_SCSI_DEVICE) { 6757 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6758 "devinfo %s@%s not SCSI_DEVICE flavored", 6759 name ? name : "", addr)); 6760 child = NULL; 6761 } 6762 } 6763 } 6764 6765 if (child) { 6766 ASSERT(child && (path == NULL)); 6767 6768 /* Don't unconfig probe nodes. */ 6769 if (scsi_hba_devi_is_barrier(child)) { 6770 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6771 "devinfo %s@%s is_barrier, skip", 6772 name ? name : "", addr)); 6773 return; 6774 } 6775 6776 /* Attempt to offline/remove the devinfo node */ 6777 if (ndi_devi_offline(child, 6778 NDI_DEVFS_CLEAN | NDI_DEVI_REMOVE) == DDI_SUCCESS) { 6779 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6780 "devinfo %s@%s offlined and removed", 6781 name ? name : "", addr)); 6782 } else if (ndi_devi_device_remove(child)) { 6783 /* Offline/remove failed, note new device_remove */ 6784 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6785 "devinfo %s@%s offline failed, device_remove", 6786 name ? name : "", addr)); 6787 } 6788 } else if (path) { 6789 ASSERT(path && (child == NULL)); 6790 6791 /* 6792 * Attempt to offline/remove the pathinfo node. 6793 * 6794 * NOTE: mdi_pi_offline of last path will fail if the 6795 * device is open (i.e. the client can't be offlined). 6796 * 6797 * NOTE: For mdi there is no REMOVE flag for mdi_pi_offline(). 6798 * When mdi_pi_offline returns MDI_SUCCESS, we are responsible 6799 * for remove via mdi_pi_free(). 6800 */ 6801 mdi_hold_path(path); 6802 spathname = mdi_pi_spathname(path); /* valid after free */ 6803 scsi_hba_devi_exit_phci(self, *circp); 6804 rval = mdi_pi_offline(path, 0); 6805 scsi_hba_devi_enter_phci(self, circp); 6806 6807 /* Note new device_remove */ 6808 if (mdi_pi_device_remove(path)) 6809 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6810 "pathinfo %s note device_remove", spathname)); 6811 6812 mdi_rele_path(path); 6813 if (rval == MDI_SUCCESS) { 6814 (void) mdi_pi_free(path, 0); 6815 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6816 "pathinfo %s offlined, then freed", spathname)); 6817 } 6818 } else { 6819 ASSERT((path == NULL) && (child == NULL)); 6820 6821 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 6822 "%s@%s not found", name ? name : "", addr)); 6823 } 6824 } 6825 6826 /* 6827 * configure the device at the specified "@addr" address. 6828 */ 6829 static struct scsi_device * 6830 scsi_hba_bus_configone_addr(dev_info_t *self, char *addr, scsi_enum_t se) 6831 { 6832 int circ; 6833 struct scsi_device *sd; 6834 6835 scsi_hba_devi_enter(self, &circ); 6836 sd = scsi_device_config(self, NULL, addr, se, &circ, NULL); 6837 scsi_hba_devi_exit(self, circ); 6838 return (sd); 6839 } 6840 6841 /* 6842 * unconfigure the device at the specified "@addr" address. 6843 */ 6844 static void 6845 scsi_hba_bus_unconfigone_addr(dev_info_t *self, char *addr) 6846 { 6847 int circ; 6848 6849 scsi_hba_devi_enter(self, &circ); 6850 (void) scsi_device_unconfig(self, NULL, addr, &circ); 6851 scsi_hba_devi_exit(self, circ); 6852 } 6853 6854 /* 6855 * The bus_config_all operations are multi-threaded for performance. A 6856 * separate thread per target and per LUN is used. The config handle is used 6857 * to coordinate all the threads at a given level and the config thread data 6858 * contains the required information for a specific thread to identify what it 6859 * is processing and the handle under which this is being processed. 6860 */ 6861 6862 /* multi-threaded config handle */ 6863 struct scsi_hba_mte_h { 6864 dev_info_t *h_self; /* initiator port */ 6865 int h_thr_count; 6866 kmutex_t h_lock; 6867 kcondvar_t h_cv; 6868 }; 6869 6870 /* target of 'self' config thread data */ 6871 struct scsi_hba_mte_td { 6872 struct scsi_hba_mte_h *td_h; 6873 char *td_taddr; /* target port */ 6874 int td_mt; 6875 scsi_enum_t td_se; 6876 }; 6877 6878 /* Invoke callback on a vector of taddrs from multiple threads */ 6879 static void 6880 scsi_hba_thread_taddrs(dev_info_t *self, char **taddrs, int mt, 6881 scsi_enum_t se, void (*callback)(void *arg)) 6882 { 6883 struct scsi_hba_mte_h *h; /* HBA header */ 6884 struct scsi_hba_mte_td *td; /* target data */ 6885 char **taddr; 6886 6887 /* allocate and initialize the handle */ 6888 h = kmem_zalloc(sizeof (*h), KM_SLEEP); 6889 mutex_init(&h->h_lock, NULL, MUTEX_DEFAULT, NULL); 6890 cv_init(&h->h_cv, NULL, CV_DEFAULT, NULL); 6891 h->h_self = self; 6892 6893 /* loop over all the targets */ 6894 for (taddr = taddrs; *taddr; taddr++) { 6895 /* allocate a thread data structure for target */ 6896 td = kmem_alloc(sizeof (*td), KM_SLEEP); 6897 td->td_h = h; 6898 td->td_taddr = *taddr; 6899 td->td_mt = mt; 6900 td->td_se = se; 6901 6902 /* process the target */ 6903 mutex_enter(&h->h_lock); 6904 h->h_thr_count++; 6905 mutex_exit(&h->h_lock); 6906 6907 if (mt & SCSI_ENUMERATION_MT_TARGET_DISABLE) 6908 callback((void *)td); 6909 else 6910 (void) thread_create(NULL, 0, callback, (void *)td, 6911 0, &p0, TS_RUN, minclsyspri); 6912 } 6913 6914 /* wait for all the target threads to complete */ 6915 mutex_enter(&h->h_lock); 6916 while (h->h_thr_count > 0) 6917 cv_wait(&h->h_cv, &h->h_lock); 6918 mutex_exit(&h->h_lock); 6919 6920 /* free the handle */ 6921 cv_destroy(&h->h_cv); 6922 mutex_destroy(&h->h_lock); 6923 kmem_free(h, sizeof (*h)); 6924 } 6925 6926 6927 /* lun/secondary function of lun0 config thread data */ 6928 struct scsi_hba_mte_ld { 6929 struct scsi_hba_mte_h *ld_h; 6930 char *ld_taddr; /* target port */ 6931 scsi_lun64_t ld_lun64; /* lun */ 6932 int ld_sfunc; /* secondary function */ 6933 scsi_enum_t ld_se; 6934 }; 6935 6936 /* 6937 * Enumerate the LUNs and secondary functions of the specified target. The 6938 * target portion of the "@addr" is already represented as a string in the 6939 * thread data, we add a ",lun" representation to this and perform a 6940 * bus_configone byte of enumeration on that "@addr". 6941 */ 6942 static void 6943 scsi_hba_enum_lsf_of_tgt_thr(void *arg) 6944 { 6945 struct scsi_hba_mte_ld *ld = (struct scsi_hba_mte_ld *)arg; 6946 struct scsi_hba_mte_h *h = ld->ld_h; 6947 dev_info_t *self = h->h_self; 6948 char addr[SCSI_MAXNAMELEN]; 6949 6950 /* make string form of "@taddr,lun[,sfunc]" and see if it exists */ 6951 if (ld->ld_sfunc == -1) 6952 (void) snprintf(addr, sizeof (addr), 6953 "%s,%" PRIx64, ld->ld_taddr, ld->ld_lun64); 6954 else 6955 (void) snprintf(addr, sizeof (addr), 6956 "%s,%" PRIx64 ",%x", 6957 ld->ld_taddr, ld->ld_lun64, ld->ld_sfunc); 6958 6959 /* configure device at that unit-address address */ 6960 (void) scsi_hba_bus_configone_addr(self, addr, ld->ld_se); 6961 6962 /* signal completion of this LUN thread to the target */ 6963 mutex_enter(&h->h_lock); 6964 if (--h->h_thr_count == 0) 6965 cv_broadcast(&h->h_cv); 6966 mutex_exit(&h->h_lock); 6967 6968 /* free config thread data */ 6969 kmem_free(ld, sizeof (*ld)); 6970 } 6971 6972 /* Format of SCSI REPORT_LUNS report */ 6973 typedef struct scsi_lunrpt { 6974 uchar_t lunrpt_len_msb; /* # LUNs being reported */ 6975 uchar_t lunrpt_len_mmsb; 6976 uchar_t lunrpt_len_mlsb; 6977 uchar_t lunrpt_len_lsb; 6978 uchar_t lunrpt_reserved[4]; 6979 scsi_lun_t lunrpt_luns[1]; /* LUNs, variable size */ 6980 } scsi_lunrpt_t; 6981 6982 /* 6983 * scsi_device_reportluns() 6984 * 6985 * Callers of this routine should ensure that the 'sd0' scsi_device structure 6986 * and 'pi' path_instance specified are associated with a responding LUN0. 6987 * This should not be called for SCSI-1 devices. 6988 * 6989 * To get a LUN report, we must allocate a buffer. To know how big to make the 6990 * buffer, we must know the number of LUNs. To know the number of LUNs, we must 6991 * get a LUN report. We first issue a SCMD_REPORT_LUNS command using a 6992 * reasonably sized buffer that's big enough to report all LUNs for most 6993 * typical devices. If it turns out that we needed a bigger buffer, we attempt 6994 * to allocate a buffer of sufficient size, and reissue the command. If the 6995 * first command succeeds, but the second fails, we return whatever we were 6996 * able to get the first time. We return enough information for the caller to 6997 * tell whether he got all the LUNs or only a subset. 6998 * 6999 * If successful, we allocate an array of scsi_lun_t to hold the results. The 7000 * caller must kmem_free(*lunarrayp, *sizep) when finished with it. Upon 7001 * successful return return value is NDI_SUCCESS and: 7002 * 7003 * *lunarrayp points to the allocated array, 7004 * *nlunsp is the number of valid LUN entries in the array, 7005 * *tlunsp is the total number of LUNs in the target, 7006 * *sizep is the size of the lunarrayp array, which must be freed. 7007 * 7008 * If the *nlunsp is less than *tlunsp, then we were only able to retrieve a 7009 * subset of the total set of LUNs in the target. 7010 */ 7011 static int 7012 scsi_device_reportluns(struct scsi_device *sd0, char *taddr, int pi, 7013 scsi_lun_t **lunarrayp, uint32_t *nlunsp, uint32_t *tlunsp, size_t *sizep) 7014 { 7015 struct buf *lunrpt_bp; 7016 struct scsi_pkt *lunrpt_pkt; 7017 scsi_lunrpt_t *lunrpt; 7018 uint32_t bsize; 7019 uint32_t tluns, nluns; 7020 int default_maxluns = scsi_lunrpt_default_max; 7021 dev_info_t *child; 7022 7023 ASSERT(sd0 && lunarrayp && nlunsp && tlunsp && sizep); 7024 7025 /* 7026 * NOTE: child should only be used in SCSI_HBA_LOG context since with 7027 * vHCI enumeration it may be the vHCI 'client' devinfo child instead 7028 * of a child of the 'self' pHCI we are enumerating. 7029 */ 7030 child = sd0->sd_dev; 7031 7032 /* first try, look for up to scsi_lunrpt_default_max LUNs */ 7033 nluns = default_maxluns; 7034 7035 again: bsize = sizeof (struct scsi_lunrpt) + 7036 ((nluns - 1) * sizeof (struct scsi_lun)); 7037 7038 lunrpt_bp = scsi_alloc_consistent_buf(&sd0->sd_address, 7039 (struct buf *)NULL, bsize, B_READ, SLEEP_FUNC, NULL); 7040 if (lunrpt_bp == NULL) { 7041 SCSI_HBA_LOG((_LOG(1), NULL, child, "failed alloc")); 7042 return (NDI_NOMEM); 7043 } 7044 7045 lunrpt_pkt = scsi_init_pkt(&sd0->sd_address, 7046 (struct scsi_pkt *)NULL, lunrpt_bp, CDB_GROUP5, 7047 sizeof (struct scsi_arq_status), 0, PKT_CONSISTENT, 7048 SLEEP_FUNC, NULL); 7049 if (lunrpt_pkt == NULL) { 7050 SCSI_HBA_LOG((_LOG(1), NULL, child, "failed init")); 7051 scsi_free_consistent_buf(lunrpt_bp); 7052 return (NDI_NOMEM); 7053 } 7054 7055 (void) scsi_setup_cdb((union scsi_cdb *)lunrpt_pkt->pkt_cdbp, 7056 SCMD_REPORT_LUNS, 0, bsize, 0); 7057 7058 lunrpt_pkt->pkt_time = scsi_lunrpt_timeout; 7059 7060 /* 7061 * When sd0 is a vHCI scsi device, we need reportlun to be issued 7062 * against a specific LUN0 path_instance that we are enumerating. 7063 */ 7064 lunrpt_pkt->pkt_path_instance = pi; 7065 lunrpt_pkt->pkt_flags |= FLAG_PKT_PATH_INSTANCE; 7066 7067 /* 7068 * NOTE: scsi_poll may not allow HBA specific recovery from TRAN_BUSY. 7069 */ 7070 if (scsi_poll(lunrpt_pkt) < 0) { 7071 SCSI_HBA_LOG((_LOG(2), NULL, child, "reportlun not supported")); 7072 scsi_destroy_pkt(lunrpt_pkt); 7073 scsi_free_consistent_buf(lunrpt_bp); 7074 return (NDI_FAILURE); 7075 } 7076 7077 scsi_destroy_pkt(lunrpt_pkt); 7078 7079 lunrpt = (scsi_lunrpt_t *)lunrpt_bp->b_un.b_addr; 7080 7081 /* Compute the total number of LUNs in the target */ 7082 tluns = (((uint_t)lunrpt->lunrpt_len_msb << 24) | 7083 ((uint_t)lunrpt->lunrpt_len_mmsb << 16) | 7084 ((uint_t)lunrpt->lunrpt_len_mlsb << 8) | 7085 ((uint_t)lunrpt->lunrpt_len_lsb)) >> 3; 7086 7087 if (tluns == 0) { 7088 /* Illegal response -- this target is broken */ 7089 SCSI_HBA_LOG((_LOG(1), NULL, child, "illegal tluns of zero")); 7090 scsi_free_consistent_buf(lunrpt_bp); 7091 return (DDI_NOT_WELL_FORMED); 7092 } 7093 7094 if (tluns > nluns) { 7095 /* have more than we allocated space for */ 7096 if (nluns == default_maxluns) { 7097 /* first time around, reallocate larger */ 7098 scsi_free_consistent_buf(lunrpt_bp); 7099 nluns = tluns; 7100 goto again; 7101 } 7102 7103 /* uh oh, we got a different tluns the second time! */ 7104 SCSI_HBA_LOG((_LOG(1), NULL, child, 7105 "tluns changed from %d to %d", nluns, tluns)); 7106 } else 7107 nluns = tluns; 7108 7109 /* 7110 * Now we have: 7111 * lunrpt_bp is the buffer we're using; 7112 * tluns is the total number of LUNs the target says it has; 7113 * nluns is the number of LUNs we were able to get into the buffer. 7114 * 7115 * Copy the data out of scarce iopb memory into regular kmem. 7116 * The caller must kmem_free(*lunarrayp, *sizep) when finished with it. 7117 */ 7118 *lunarrayp = (scsi_lun_t *)kmem_alloc( 7119 nluns * sizeof (scsi_lun_t), KM_SLEEP); 7120 if (*lunarrayp == NULL) { 7121 SCSI_HBA_LOG((_LOG(1), NULL, child, "NULL lunarray")); 7122 scsi_free_consistent_buf(lunrpt_bp); 7123 return (NDI_NOMEM); 7124 } 7125 7126 *sizep = nluns * sizeof (scsi_lun_t); 7127 *nlunsp = nluns; 7128 *tlunsp = tluns; 7129 bcopy((void *)&lunrpt->lunrpt_luns, (void *)*lunarrayp, *sizep); 7130 scsi_free_consistent_buf(lunrpt_bp); 7131 SCSI_HBA_LOG((_LOG(3), NULL, child, 7132 "@%s,0 path %d: %d/%d luns", taddr, pi, nluns, tluns)); 7133 return (NDI_SUCCESS); 7134 } 7135 7136 /* 7137 * Enumerate all the LUNs and secondary functions of the specified 'taddr' 7138 * target port as accessed via 'self' pHCI. Note that sd0 may be associated 7139 * with a child of the vHCI instead of 'self' - in this case the 'pi' 7140 * path_instance is used to ensure that the SCMD_REPORT_LUNS command is issued 7141 * through the 'self' pHCI path. 7142 * 7143 * We multi-thread across all the LUNs and secondary functions and enumerate 7144 * them. Which LUNs exist is based on SCMD_REPORT_LUNS data. 7145 * 7146 * The scsi_device we are called with should be for LUN0 and has been probed. 7147 * 7148 * This function is structured so that an HBA that has a different target 7149 * addressing structure can still use this function to enumerate the its 7150 * LUNs if it uses "taddr,lun" for its LUN space. 7151 * 7152 * We make assumptions about other LUNs associated with the target: 7153 * 7154 * For SCSI-2 and SCSI-3 target we will issue the SCSI report_luns 7155 * command. If this fails or we have a SCSI-1 then the number of 7156 * LUNs is determined based on SCSI_OPTIONS_NLUNS. For a SCSI-1 7157 * target we never probe above LUN 8, even if SCSI_OPTIONS_NLUNS 7158 * indicates we should. 7159 * 7160 * HBA drivers wanting a different set of assumptions should implement their 7161 * own LUN enumeration code. 7162 */ 7163 static int 7164 scsi_hba_enum_lsf_of_t(struct scsi_device *sd0, 7165 dev_info_t *self, char *taddr, int pi, int mt, scsi_enum_t se) 7166 { 7167 dev_info_t *child; 7168 scsi_hba_tran_t *tran; 7169 impl_scsi_tgtmap_t *tgtmap; 7170 damap_id_t tgtid; 7171 damap_t *tgtdam; 7172 damap_t *lundam = NULL; 7173 struct scsi_hba_mte_h *h; 7174 struct scsi_hba_mte_ld *ld; 7175 int aver; 7176 scsi_lun_t *lunp = NULL; 7177 int lun; 7178 uint32_t nluns; 7179 uint32_t tluns; 7180 size_t size; 7181 scsi_lun64_t lun64; 7182 int maxluns; 7183 7184 /* 7185 * If LUN0 failed then we have no other LUNs. 7186 * 7187 * NOTE: We need sd_inq to be valid to check ansi version. Since 7188 * scsi_unprobe is now a noop (sd_inq freeded in 7189 * scsi_busctl_uninitchild) sd_inq remains valid even if a target 7190 * driver detach(9E) occurs, resulting in a scsi_unprobe call 7191 * (sd_uninit_prevent keeps sd_inq valid by failing any 7192 * device_uninitchild attempts). 7193 */ 7194 ASSERT(sd0 && sd0->sd_uninit_prevent && sd0->sd_dev && sd0->sd_inq); 7195 if ((sd0 == NULL) || (sd0->sd_dev == NULL) || (sd0->sd_inq == NULL)) { 7196 SCSI_HBA_LOG((_LOG(1), NULL, sd0 ? sd0->sd_dev : NULL, 7197 "not setup correctly:%s%s%s", 7198 (sd0 == NULL) ? " device" : "", 7199 (sd0 && (sd0->sd_dev == NULL)) ? " dip" : "", 7200 (sd0 && (sd0->sd_inq == NULL)) ? " inq" : "")); 7201 return (DDI_FAILURE); 7202 } 7203 7204 /* 7205 * NOTE: child should only be used in SCSI_HBA_LOG context since with 7206 * vHCI enumeration it may be the vHCI 'client' devinfo child instead 7207 * of a child of the 'self' pHCI we are enumerating. 7208 */ 7209 child = sd0->sd_dev; 7210 7211 /* Determine if we are reporting lun observations into lunmap. */ 7212 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 7213 tgtmap = (impl_scsi_tgtmap_t *)tran->tran_tgtmap; 7214 if (tgtmap) { 7215 tgtdam = tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]; 7216 tgtid = damap_lookup(tgtdam, taddr); 7217 if (tgtid != NODAM) { 7218 lundam = damap_id_priv_get(tgtdam, tgtid); 7219 damap_id_rele(tgtdam, tgtid); 7220 ASSERT(lundam); 7221 } 7222 } 7223 7224 if (lundam) { 7225 /* If using lunmap, start the observation */ 7226 scsi_lunmap_set_begin(self, lundam); 7227 } else { 7228 /* allocate and initialize the LUN handle */ 7229 h = kmem_zalloc(sizeof (*h), KM_SLEEP); 7230 mutex_init(&h->h_lock, NULL, MUTEX_DEFAULT, NULL); 7231 cv_init(&h->h_cv, NULL, CV_DEFAULT, NULL); 7232 h->h_self = self; 7233 } 7234 7235 /* See if SCMD_REPORT_LUNS works for SCSI-2 and beyond */ 7236 aver = sd0->sd_inq->inq_ansi; 7237 if ((aver >= SCSI_VERSION_2) && (scsi_device_reportluns(sd0, 7238 taddr, pi, &lunp, &nluns, &tluns, &size) == NDI_SUCCESS)) { 7239 7240 ASSERT(lunp && (size > 0) && (nluns > 0) && (tluns > 0)); 7241 7242 /* loop over the reported LUNs */ 7243 SCSI_HBA_LOG((_LOG(2), NULL, child, 7244 "@%s,0 path %d: enumerating %d reported lun%s", taddr, pi, 7245 nluns, nluns > 1 ? "s" : "")); 7246 7247 for (lun = 0; lun < nluns; lun++) { 7248 lun64 = scsi_lun_to_lun64(lunp[lun]); 7249 7250 if (lundam) { 7251 if (scsi_lunmap_set_add(self, lundam, 7252 taddr, lun64, -1) != DDI_SUCCESS) { 7253 SCSI_HBA_LOG((_LOG_NF(WARN), 7254 "@%s,%" PRIx64 " failed to create", 7255 taddr, lun64)); 7256 } 7257 } else { 7258 if (lun64 == 0) 7259 continue; 7260 7261 /* allocate a thread data structure for LUN */ 7262 ld = kmem_alloc(sizeof (*ld), KM_SLEEP); 7263 ld->ld_h = h; 7264 ld->ld_taddr = taddr; 7265 ld->ld_lun64 = lun64; 7266 ld->ld_sfunc = -1; 7267 ld->ld_se = se; 7268 7269 /* process the LUN */ 7270 mutex_enter(&h->h_lock); 7271 h->h_thr_count++; 7272 mutex_exit(&h->h_lock); 7273 7274 if (mt & SCSI_ENUMERATION_MT_LUN_DISABLE) 7275 scsi_hba_enum_lsf_of_tgt_thr( 7276 (void *)ld); 7277 else 7278 (void) thread_create(NULL, 0, 7279 scsi_hba_enum_lsf_of_tgt_thr, 7280 (void *)ld, 0, &p0, TS_RUN, 7281 minclsyspri); 7282 } 7283 } 7284 7285 /* free the LUN array allocated by scsi_device_reportluns */ 7286 kmem_free(lunp, size); 7287 } else { 7288 /* Determine the number of LUNs to enumerate. */ 7289 maxluns = scsi_get_scsi_maxluns(sd0); 7290 7291 /* Couldn't get SCMD_REPORT_LUNS data */ 7292 if (aver >= SCSI_VERSION_3) { 7293 scsi_enumeration_failed(child, se, taddr, "report_lun"); 7294 7295 /* 7296 * Based on calling context tunable, only enumerate one 7297 * lun (lun0) if scsi_device_reportluns() fails on a 7298 * SCSI_VERSION_3 or greater device. 7299 */ 7300 if (scsi_lunrpt_failed_do1lun & (1 << se)) 7301 maxluns = 1; 7302 } 7303 7304 /* loop over possible LUNs, skipping LUN0 */ 7305 if (maxluns > 1) 7306 SCSI_HBA_LOG((_LOG(2), NULL, child, 7307 "@%s,0 path %d: enumerating luns 1-%d", taddr, pi, 7308 maxluns - 1)); 7309 else 7310 SCSI_HBA_LOG((_LOG(2), NULL, child, 7311 "@%s,0 path %d: enumerating just lun0", taddr, pi)); 7312 7313 for (lun64 = 0; lun64 < maxluns; lun64++) { 7314 if (lundam) { 7315 if (scsi_lunmap_set_add(self, lundam, 7316 taddr, lun64, -1) != DDI_SUCCESS) { 7317 SCSI_HBA_LOG((_LOG_NF(WARN), 7318 "@%s,%" PRIx64 " failed to create", 7319 taddr, lun64)); 7320 } 7321 } else { 7322 if (lun64 == 0) 7323 continue; 7324 7325 /* allocate a thread data structure for LUN */ 7326 ld = kmem_alloc(sizeof (*ld), KM_SLEEP); 7327 ld->ld_h = h; 7328 ld->ld_taddr = taddr; 7329 ld->ld_lun64 = lun64; 7330 ld->ld_sfunc = -1; 7331 ld->ld_se = se; 7332 7333 /* process the LUN */ 7334 mutex_enter(&h->h_lock); 7335 h->h_thr_count++; 7336 mutex_exit(&h->h_lock); 7337 if (mt & SCSI_ENUMERATION_MT_LUN_DISABLE) 7338 scsi_hba_enum_lsf_of_tgt_thr( 7339 (void *)ld); 7340 else 7341 (void) thread_create(NULL, 0, 7342 scsi_hba_enum_lsf_of_tgt_thr, 7343 (void *)ld, 0, &p0, TS_RUN, 7344 minclsyspri); 7345 } 7346 } 7347 } 7348 7349 /* 7350 * If we have an embedded service as a secondary function on LUN0 and 7351 * the primary LUN0 function is different than the secondary function 7352 * then enumerate the secondary function. The sfunc value is the dtype 7353 * associated with the embedded service. 7354 * 7355 * inq_encserv: enclosure service and our dtype is not DTYPE_ESI 7356 * or DTYPE_UNKNOWN then create a separate DTYPE_ESI node for 7357 * enclosure service access. 7358 */ 7359 ASSERT(sd0->sd_inq); 7360 if (sd0->sd_inq->inq_encserv && 7361 ((sd0->sd_inq->inq_dtype & DTYPE_MASK) != DTYPE_UNKNOWN) && 7362 ((sd0->sd_inq->inq_dtype & DTYPE_MASK) != DTYPE_ESI) && 7363 ((sd0->sd_inq->inq_ansi >= SCSI_VERSION_3))) { 7364 if (lundam) { 7365 if (scsi_lunmap_set_add(self, lundam, 7366 taddr, 0, DTYPE_ESI) != DDI_SUCCESS) { 7367 SCSI_HBA_LOG((_LOG_NF(WARN), 7368 "@%s,0,%x failed to create", 7369 taddr, DTYPE_ESI)); 7370 } 7371 } else { 7372 /* allocate a thread data structure for sfunc */ 7373 ld = kmem_alloc(sizeof (*ld), KM_SLEEP); 7374 ld->ld_h = h; 7375 ld->ld_taddr = taddr; 7376 ld->ld_lun64 = 0; 7377 ld->ld_sfunc = DTYPE_ESI; 7378 ld->ld_se = se; 7379 7380 /* process the LUN */ 7381 mutex_enter(&h->h_lock); 7382 h->h_thr_count++; 7383 mutex_exit(&h->h_lock); 7384 if (mt & SCSI_ENUMERATION_MT_LUN_DISABLE) 7385 scsi_hba_enum_lsf_of_tgt_thr((void *)ld); 7386 else 7387 (void) thread_create(NULL, 0, 7388 scsi_hba_enum_lsf_of_tgt_thr, (void *)ld, 7389 0, &p0, TS_RUN, minclsyspri); 7390 } 7391 } 7392 7393 /* 7394 * Future: Add secondary function support for: 7395 * inq_mchngr (DTYPE_CHANGER) 7396 * inq_sccs (DTYPE_ARRAY_CTRL) 7397 */ 7398 7399 if (lundam) { 7400 /* If using lunmap, end the observation */ 7401 scsi_lunmap_set_end(self, lundam); 7402 } else { 7403 /* wait for all the LUN threads of this target to complete */ 7404 mutex_enter(&h->h_lock); 7405 while (h->h_thr_count > 0) 7406 cv_wait(&h->h_cv, &h->h_lock); 7407 mutex_exit(&h->h_lock); 7408 7409 /* free the target handle */ 7410 cv_destroy(&h->h_cv); 7411 mutex_destroy(&h->h_lock); 7412 kmem_free(h, sizeof (*h)); 7413 } 7414 7415 return (DDI_SUCCESS); 7416 } 7417 7418 /* 7419 * Enumerate LUN0 and all other LUNs and secondary functions associated with 7420 * the specified target address. 7421 * 7422 * Return NDI_SUCCESS if we might have created a new node. 7423 * Return NDI_FAILURE if we definitely did not create a new node. 7424 */ 7425 static int 7426 scsi_hba_bus_config_taddr(dev_info_t *self, char *taddr, int mt, scsi_enum_t se) 7427 { 7428 char addr[SCSI_MAXNAMELEN]; 7429 struct scsi_device *sd; 7430 int circ; 7431 int ret; 7432 int pi; 7433 7434 /* See if LUN0 of the specified target exists. */ 7435 (void) snprintf(addr, sizeof (addr), "%s,0", taddr); 7436 7437 scsi_hba_devi_enter(self, &circ); 7438 sd = scsi_device_config(self, NULL, addr, se, &circ, &pi); 7439 7440 if (sd) { 7441 /* 7442 * LUN0 exists, enumerate all the other LUNs. 7443 * 7444 * With vHCI enumeration, when 'self' is a pHCI the sd 7445 * scsi_device may be associated with the vHCI 'client'. 7446 * In this case 'pi' is the path_instance needed to 7447 * continue enumeration communication LUN0 via 'self' 7448 * pHCI and specific 'taddr' target address. 7449 * 7450 * We prevent the removal of LUN0 until we are done with 7451 * prevent/allow because we must exit the parent for 7452 * multi-threaded scsi_hba_enum_lsf_of_t(). 7453 * 7454 * NOTE: scsi_unprobe is a noop, sd->sd_inq is valid until 7455 * device_uninitchild - so sd_uninit_prevent keeps sd_inq valid 7456 * by failing any device_uninitchild attempts. 7457 */ 7458 ret = NDI_SUCCESS; 7459 sd->sd_uninit_prevent++; 7460 scsi_hba_devi_exit(self, circ); 7461 7462 (void) scsi_hba_enum_lsf_of_t(sd, self, taddr, pi, mt, se); 7463 7464 scsi_hba_devi_enter(self, &circ); 7465 sd->sd_uninit_prevent--; 7466 } else 7467 ret = NDI_FAILURE; 7468 scsi_hba_devi_exit(self, circ); 7469 return (ret); 7470 } 7471 7472 /* Config callout from scsi_hba_thread_taddrs */ 7473 static void 7474 scsi_hba_taddr_config_thr(void *arg) 7475 { 7476 struct scsi_hba_mte_td *td = (struct scsi_hba_mte_td *)arg; 7477 struct scsi_hba_mte_h *h = td->td_h; 7478 7479 (void) scsi_hba_bus_config_taddr(h->h_self, td->td_taddr, 7480 td->td_mt, td->td_se); 7481 7482 /* signal completion of this target thread to the HBA */ 7483 mutex_enter(&h->h_lock); 7484 if (--h->h_thr_count == 0) 7485 cv_broadcast(&h->h_cv); 7486 mutex_exit(&h->h_lock); 7487 7488 /* free config thread data */ 7489 kmem_free(td, sizeof (*td)); 7490 } 7491 7492 /* 7493 * Enumerate all the children of the specified SCSI parallel interface (spi). 7494 * An HBA associated with a non-parallel scsi bus should be using another bus 7495 * level enumeration implementation (possibly their own) and calling 7496 * scsi_hba_bus_config_taddr to do enumeration of devices associated with a 7497 * particular target address. 7498 * 7499 * On an spi bus the targets are sequentially enumerated based on the 7500 * width of the bus. We also take care to try to skip the HBAs own initiator 7501 * id. See scsi_hba_enum_lsf_of_t() for LUN and secondary function enumeration. 7502 * 7503 * Return NDI_SUCCESS if we might have created a new node. 7504 * Return NDI_FAILURE if we definitely did not create a new node. 7505 * 7506 * Note: At some point we may want to expose this interface in transport.h 7507 * if we find an hba that implements bus_config but still uses spi-like target 7508 * addresses. 7509 */ 7510 static int 7511 scsi_hba_bus_configall_spi(dev_info_t *self, int mt) 7512 { 7513 int options; 7514 int ntargets; 7515 int id; 7516 int tgt; 7517 char **taddrs; 7518 char **taddr; 7519 char *tbuf; 7520 7521 /* 7522 * Find the number of targets supported on the bus. Look at the per 7523 * bus scsi-options property on the HBA node and check its 7524 * SCSI_OPTIONS_WIDE setting. 7525 */ 7526 options = ddi_prop_get_int(DDI_DEV_T_ANY, self, 7527 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-options", -1); 7528 if ((options != -1) && ((options & SCSI_OPTIONS_WIDE) == 0)) 7529 ntargets = NTARGETS; /* 8 */ 7530 else 7531 ntargets = NTARGETS_WIDE; /* 16 */ 7532 7533 /* 7534 * Find the initiator-id for the HBA so we can skip that. We get the 7535 * cached value on the HBA node, established in scsi_hba_attach_setup. 7536 * If we were unable to determine the id then we rely on the HBA to 7537 * fail gracefully when asked to enumerate itself. 7538 */ 7539 id = ddi_prop_get_int(DDI_DEV_T_ANY, self, 7540 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-initiator-id", -1); 7541 if (id > ntargets) { 7542 SCSI_HBA_LOG((_LOG(1), self, NULL, 7543 "'scsi-initiator-id' bogus for %d target bus: %d", 7544 ntargets, id)); 7545 id = -1; 7546 } 7547 SCSI_HBA_LOG((_LOG(2), self, NULL, 7548 "enumerating targets 0-%d skip %d", ntargets, id)); 7549 7550 /* form vector of target addresses */ 7551 taddrs = kmem_zalloc(sizeof (char *) * (ntargets + 1), KM_SLEEP); 7552 for (tgt = 0, taddr = taddrs; tgt < ntargets; tgt++) { 7553 /* skip initiator */ 7554 if (tgt == id) 7555 continue; 7556 7557 /* convert to string and enumerate the target address */ 7558 tbuf = kmem_alloc(((tgt/16) + 1) + 1, KM_SLEEP); 7559 (void) sprintf(tbuf, "%x", tgt); 7560 ASSERT(strlen(tbuf) == ((tgt/16) + 1)); 7561 *taddr++ = tbuf; 7562 } 7563 7564 /* null terminate vector of target addresses */ 7565 *taddr = NULL; 7566 7567 /* configure vector of target addresses */ 7568 scsi_hba_thread_taddrs(self, taddrs, mt, SE_BUSCONFIG, 7569 scsi_hba_taddr_config_thr); 7570 7571 /* free vector of target addresses */ 7572 for (taddr = taddrs; *taddr; taddr++) 7573 kmem_free(*taddr, strlen(*taddr) + 1); 7574 kmem_free(taddrs, sizeof (char *) * (ntargets + 1)); 7575 return (NDI_SUCCESS); 7576 } 7577 7578 /* 7579 * Transport independent bus_configone BUS_CONFIG_ONE implementation. Takes 7580 * same arguments, minus op, as scsi_hba_bus_config(), tran_bus_config(), 7581 * and scsi_hba_bus_config_spi(). 7582 */ 7583 int 7584 scsi_hba_bus_configone(dev_info_t *self, uint_t flags, char *arg, 7585 dev_info_t **childp) 7586 { 7587 int ret; 7588 int circ; 7589 char *name, *addr; 7590 char *lcp; 7591 char sc1, sc2; 7592 char nameaddr[SCSI_MAXNAMELEN]; 7593 extern int i_ndi_make_spec_children(dev_info_t *, uint_t); 7594 struct scsi_device *sd0, *sd; 7595 scsi_lun64_t lun64; 7596 int mt; 7597 7598 /* parse_name modifies arg1, we must duplicate "name@addr" */ 7599 (void) strcpy(nameaddr, arg); 7600 i_ddi_parse_name(nameaddr, &name, &addr, NULL); 7601 7602 /* verify the form of the node - we need an @addr */ 7603 if ((name == NULL) || (addr == NULL) || 7604 (*name == '\0') || (*addr == '\0')) { 7605 /* 7606 * OBP may create ill formed template/stub/wild-card 7607 * nodes (no @addr) for legacy driver loading methods - 7608 * ignore them. 7609 */ 7610 SCSI_HBA_LOG((_LOG(2), self, NULL, "%s ill formed", arg)); 7611 return (NDI_FAILURE); 7612 } 7613 7614 /* 7615 * Check to see if this is a non-scsi flavor configuration operation. 7616 */ 7617 if (strcmp(name, "smp") == 0) { 7618 /* 7619 * Configure the child, and if we're successful return with 7620 * active hold. 7621 */ 7622 return (smp_hba_bus_config(self, addr, childp)); 7623 } 7624 7625 /* 7626 * The framework does not ensure the creation of driver.conf 7627 * nodes prior to calling a nexus bus_config. For legacy 7628 * support of driver.conf file nodes we want to create our 7629 * driver.conf file children now so that we can detect if we 7630 * are being asked to bus_configone one of these nodes. 7631 * 7632 * Needing driver.conf file nodes prior to bus config is unique 7633 * to scsi_enumeration mixed mode (legacy driver.conf and 7634 * dynamic SID node) support. There is no general need for the 7635 * framework to make driver.conf children prior to bus_config. 7636 * 7637 * We enter our HBA (self) prior to scsi_device_config, and 7638 * pass it our circ. The scsi_device_config may exit the 7639 * HBA around scsi_probe() operations to allow for parallelism. 7640 * This is done after the probe node "@addr" is available as a 7641 * barrier to prevent parallel probes of the same device. The 7642 * probe node is also configured in a way that it can't be 7643 * removed by the framework until we are done with it. 7644 * 7645 * NOTE: The framework is currently preventing many parallel 7646 * sibling operations (such as attaches), so the parallelism 7647 * we are providing is of marginal use until that is improved. 7648 * The most logical way to solve this would be to have separate 7649 * target and lun nodes. This would be a large change in the 7650 * format of /devices paths and is not being pursued at this 7651 * time. The need for parallelism will become more of an issue 7652 * with top-down attach for mpxio/vhci and for iSCSI support. 7653 * We may want to eventually want a dual mode implementation, 7654 * where the HBA determines if we should construct separate 7655 * target and lun devinfo nodes. 7656 */ 7657 scsi_hba_devi_enter(self, &circ); 7658 SCSI_HBA_LOG((_LOG(4), self, NULL, "%s@%s config_one", name, addr)); 7659 (void) i_ndi_make_spec_children(self, flags); 7660 7661 /* 7662 * For bus_configone, we make sure that we can find LUN0 7663 * first. This allows the delayed probe/barrier deletion for a 7664 * non-existent LUN0 (if enabled in scsi_device_config) to 7665 * cover all LUNs on the target. This is done to minimize the 7666 * number of independent target selection timeouts that occur 7667 * when a target with many LUNs is no longer accessible 7668 * (powered off). This removes the need for target driver 7669 * probe cache implementations. 7670 * 7671 * This optimization may not be desirable in a pure bridge 7672 * environment where targets on the other side of the bridge 7673 * show up as LUNs to the host. If we ever need to support 7674 * such a configuration then we should consider implementing a 7675 * SCSI_OPTIONS_ILUN0 bit. 7676 * 7677 * NOTE: we are *not* applying any target limitation filtering 7678 * to bus_configone, which means that we are relying on the 7679 * HBA tran_tgt_init entry point invoked by scsi_busctl_initchild 7680 * to fail. 7681 */ 7682 sd0 = (struct scsi_device *)-1; 7683 lcp = strchr(addr, ','); /* "addr,lun[,sfunc]" */ 7684 if (lcp) { 7685 /* 7686 * With "tgt,lun[,sfunc]" addressing, multiple addressing levels 7687 * have been compressed into single devinfo node unit-address. 7688 * This presents a mismatch - there is no bus_config to discover 7689 * LUNs below a specific target, the only choice is to 7690 * BUS_CONFIG_ALL the HBA. To support BUS_CONFIG_ALL_LUNS below 7691 * a specific target, a bus_configone with lun address of "*" 7692 * triggers lun discovery below a target. 7693 */ 7694 if (*(lcp + 1) == '*') { 7695 mt = ddi_prop_get_int(DDI_DEV_T_ANY, self, 7696 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 7697 "scsi-enumeration", scsi_enumeration); 7698 mt |= scsi_hba_log_mt_disable; 7699 7700 SCSI_HBA_LOG((_LOG(2), self, NULL, 7701 "%s@%s lun enumeration triggered", name, addr)); 7702 *lcp = '\0'; /* turn ',' into '\0' */ 7703 scsi_hba_devi_exit(self, circ); 7704 (void) scsi_hba_bus_config_taddr(self, addr, 7705 mt, SE_BUSCONFIG); 7706 return (NDI_FAILURE); 7707 } 7708 7709 /* convert hex lun number from ascii */ 7710 lun64 = scsi_addr_to_lun64(lcp + 1); 7711 7712 if ((lun64 != 0) && (lun64 != SCSI_LUN64_ILLEGAL)) { 7713 /* 7714 * configure ",0" lun first, saving off 7715 * original lun characters. 7716 */ 7717 sc1 = *(lcp + 1); 7718 sc2 = *(lcp + 2); 7719 *(lcp + 1) = '0'; 7720 *(lcp + 2) = '\0'; 7721 sd0 = scsi_device_config(self, 7722 NULL, addr, SE_BUSCONFIG, &circ, NULL); 7723 7724 /* restore original lun */ 7725 *(lcp + 1) = sc1; 7726 *(lcp + 2) = sc2; 7727 7728 /* 7729 * Apply maxlun filtering. 7730 * 7731 * Future: We still have the kludged 7732 * scsi_check_ss2_LUN_limit() filtering off 7733 * scsi_probe() to catch bogus driver.conf 7734 * entries. 7735 */ 7736 if (sd0 && (lun64 < SCSI_32LUNS_PER_TARGET) && 7737 (lun64 >= scsi_get_scsi_maxluns(sd0))) { 7738 sd0 = NULL; 7739 SCSI_HBA_LOG((_LOG(4), self, NULL, 7740 "%s@%s filtered", name, addr)); 7741 } else 7742 SCSI_HBA_LOG((_LOG(4), self, NULL, 7743 "%s@%s lun 0 %s", name, addr, 7744 sd0 ? "worked" : "failed")); 7745 } 7746 } 7747 7748 /* 7749 * configure the requested device if LUN0 exists or we were 7750 * unable to determine the lun format to determine if LUN0 7751 * exists. 7752 */ 7753 if (sd0) { 7754 sd = scsi_device_config(self, 7755 name, addr, SE_BUSCONFIG, &circ, NULL); 7756 } else { 7757 sd = NULL; 7758 SCSI_HBA_LOG((_LOG(2), self, NULL, 7759 "%s@%s no lun 0 or filtered lun", name, addr)); 7760 } 7761 7762 /* 7763 * We know what we found, to reduce overhead we finish BUS_CONFIG_ONE 7764 * processing without calling back to the frameworks 7765 * ndi_busop_bus_config (unless we goto framework below). 7766 * 7767 * If the reference is to a driver name and we created a generic name 7768 * (bound to that driver) we will still succeed. This is important 7769 * for correctly resolving old drivername references to device that now 7770 * uses a generic names across the transition to generic naming. This 7771 * is effectively an internal implementation of the NDI_DRIVERNAME flag. 7772 * 7773 * We also need to special case the resolve_pathname OBP boot-device 7774 * case (modrootloaded == 0) where reference is to a generic name but 7775 * we created a legacy driver name node by returning just returning 7776 * the node created. 7777 */ 7778 if (sd && sd->sd_dev && 7779 ((strcmp(ddi_node_name(sd->sd_dev), name) == 0) || 7780 (strcmp(ddi_driver_name(sd->sd_dev), name) == 0) || 7781 (modrootloaded == 0)) && 7782 (ndi_devi_online(sd->sd_dev, 7783 flags & NDI_NO_EVENT) == NDI_SUCCESS)) { 7784 7785 /* device attached, return devinfo node with hold */ 7786 ret = NDI_SUCCESS; 7787 *childp = sd->sd_dev; 7788 ndi_hold_devi(sd->sd_dev); 7789 } else { 7790 /* 7791 * In the process of failing we may have added nodes to the HBA 7792 * (self), clearing DEVI_MADE_CHILDREN. To reduce the overhead 7793 * associated with the frameworks reaction to this we clear the 7794 * flag here. 7795 */ 7796 mutex_enter(&DEVI(self)->devi_lock); 7797 DEVI(self)->devi_flags &= ~DEVI_MADE_CHILDREN; 7798 mutex_exit(&DEVI(self)->devi_lock); 7799 ret = NDI_FAILURE; 7800 7801 /* 7802 * The framework may still be able to succeed with 7803 * with its GENERIC_PROP code. 7804 */ 7805 scsi_hba_devi_exit(self, circ); 7806 if (flags & NDI_DRV_CONF_REPROBE) 7807 flags |= NDI_CONFIG_REPROBE; 7808 flags |= NDI_MDI_FALLBACK; /* devinfo&pathinfo children */ 7809 return (ndi_busop_bus_config(self, flags, BUS_CONFIG_ONE, 7810 (void *)arg, childp, 0)); 7811 } 7812 7813 scsi_hba_devi_exit(self, circ); 7814 return (ret); 7815 } 7816 7817 /* 7818 * Perform SCSI Parallel Interconnect bus_config 7819 */ 7820 static int 7821 scsi_hba_bus_config_spi(dev_info_t *self, uint_t flags, 7822 ddi_bus_config_op_t op, void *arg, dev_info_t **childp) 7823 { 7824 int ret; 7825 int mt; 7826 7827 /* 7828 * Enumerate scsi target devices: See if we are doing generic dynamic 7829 * enumeration: if driver.conf has not specified the 'scsi-enumeration' 7830 * knob then use the global scsi_enumeration knob. 7831 */ 7832 mt = ddi_prop_get_int(DDI_DEV_T_ANY, self, 7833 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 7834 "scsi-enumeration", scsi_enumeration); 7835 mt |= scsi_hba_log_mt_disable; 7836 7837 if ((mt & SCSI_ENUMERATION_ENABLE) == 0) { 7838 /* 7839 * Static driver.conf file enumeration: 7840 * 7841 * Force reprobe for BUS_CONFIG_ONE or when manually 7842 * reconfiguring via devfsadm(1m) to emulate deferred attach. 7843 * Reprobe only discovers driver.conf enumerated nodes, more 7844 * dynamic implementations probably require their own 7845 * bus_config. 7846 */ 7847 if ((op == BUS_CONFIG_ONE) || (flags & NDI_DRV_CONF_REPROBE)) 7848 flags |= NDI_CONFIG_REPROBE; 7849 flags |= NDI_MDI_FALLBACK; /* devinfo&pathinfo children */ 7850 return (ndi_busop_bus_config(self, flags, op, arg, childp, 0)); 7851 } 7852 7853 if (scsi_hba_bus_config_debug) 7854 flags |= NDI_DEVI_DEBUG; 7855 7856 /* 7857 * Generic spi dynamic bus config enumeration to discover and enumerate 7858 * the target device nodes we are looking for. 7859 */ 7860 switch (op) { 7861 case BUS_CONFIG_ONE: /* enumerate the named child */ 7862 ret = scsi_hba_bus_configone(self, flags, (char *)arg, childp); 7863 break; 7864 7865 case BUS_CONFIG_ALL: /* enumerate all children on the bus */ 7866 case BUS_CONFIG_DRIVER: /* enumerate all children that bind to driver */ 7867 SCSI_HBA_LOG((_LOG(3), self, NULL, 7868 "BUS_CONFIG_%s mt %x", 7869 (op == BUS_CONFIG_ALL) ? "ALL" : "DRIVER", mt)); 7870 7871 /* 7872 * Enumerate targets on SCSI parallel interconnect and let the 7873 * framework finish the operation (attach the nodes). 7874 */ 7875 if ((ret = scsi_hba_bus_configall_spi(self, mt)) == NDI_SUCCESS) 7876 ret = ndi_busop_bus_config(self, flags, op, 7877 arg, childp, 0); 7878 break; 7879 7880 default: 7881 ret = NDI_FAILURE; 7882 break; 7883 } 7884 return (ret); 7885 } 7886 7887 /* 7888 * Perform SCSI Parallel Interconnect bus_unconfig 7889 */ 7890 static int 7891 scsi_hba_bus_unconfig_spi(dev_info_t *self, uint_t flags, 7892 ddi_bus_config_op_t op, void *arg) 7893 { 7894 int mt; 7895 int circ; 7896 int ret; 7897 7898 /* 7899 * See if we are doing generic dynamic enumeration: if driver.conf has 7900 * not specified the 'scsi-enumeration' knob then use the global 7901 * scsi_enumeration knob. 7902 */ 7903 mt = ddi_prop_get_int(DDI_DEV_T_ANY, self, 7904 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, 7905 "scsi-enumeration", scsi_enumeration); 7906 mt |= scsi_hba_log_mt_disable; 7907 7908 if ((mt & SCSI_ENUMERATION_ENABLE) == 0) 7909 return (ndi_busop_bus_unconfig(self, flags, op, arg)); 7910 7911 if (scsi_hba_bus_config_debug) 7912 flags |= NDI_DEVI_DEBUG; 7913 7914 scsi_hba_devi_enter(self, &circ); 7915 switch (op) { 7916 case BUS_UNCONFIG_ONE: 7917 SCSI_HBA_LOG((_LOG(3), self, NULL, 7918 "unconfig one: %s", (char *)arg)); 7919 ret = NDI_SUCCESS; 7920 break; 7921 7922 case BUS_UNCONFIG_ALL: 7923 case BUS_UNCONFIG_DRIVER: 7924 ret = NDI_SUCCESS; 7925 break; 7926 7927 default: 7928 ret = NDI_FAILURE; 7929 break; 7930 } 7931 7932 /* Perform the generic default bus unconfig */ 7933 if (ret == NDI_SUCCESS) 7934 ret = ndi_busop_bus_unconfig(self, flags, op, arg); 7935 7936 scsi_hba_devi_exit(self, circ); 7937 7938 return (ret); 7939 } 7940 7941 static int 7942 scsi_hba_bus_config_tgtmap(dev_info_t *self, uint_t flags, 7943 ddi_bus_config_op_t op, void *arg, dev_info_t **childp) 7944 { 7945 scsi_hba_tran_t *tran; 7946 impl_scsi_tgtmap_t *tgtmap; 7947 uint64_t tsa = 0; /* clock64_t */ 7948 int maxdev; 7949 int sync_usec; 7950 int synced; 7951 int ret = NDI_FAILURE; 7952 7953 if ((op != BUS_CONFIG_ONE) && (op != BUS_CONFIG_ALL) && 7954 (op != BUS_CONFIG_DRIVER)) 7955 goto out; 7956 7957 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 7958 tgtmap = (impl_scsi_tgtmap_t *)tran->tran_tgtmap; 7959 ASSERT(tgtmap); 7960 7961 /* 7962 * MPXIO is never a sure thing (and we have mixed children), so 7963 * set NDI_NDI_FALLBACK so that ndi_busop_bus_config will 7964 * search for both devinfo and pathinfo children. 7965 * 7966 * Future: Remove NDI_MDI_FALLBACK since devcfg.c now looks for 7967 * devinfo/pathinfo children in parallel (instead of old way of 7968 * looking for one form of child and then doing "fallback" to 7969 * look for other form of child). 7970 */ 7971 flags |= NDI_MDI_FALLBACK; /* devinfo&pathinfo children */ 7972 7973 /* 7974 * If bus_config occurred within the map create-to-hotplug_sync window, 7975 * we need the framework to wait for children that are physicaly 7976 * present at map create time to show up (via tgtmap hotplug config). 7977 * 7978 * The duration of this window is specified by the HBA driver at 7979 * scsi_hba_tgtmap_create(9F) time (during attach(9E)). Its 7980 * 'csync_usec' value is selected based on how long it takes the HBA 7981 * driver to get from map creation to initial observation for something 7982 * already plugged in. Estimate high, a low estimate can result in 7983 * devices not showing up correctly on first reference. The call to 7984 * ndi_busop_bus_config needs a timeout value large enough so that 7985 * the map sync call further down is not a noop (i.e. done against 7986 * an empty map when something is infact plugged in). With 7987 * BUS_CONFIG_ONE, the call to ndi_busop_bus_config will return as 7988 * soon as the desired device is enumerated via hotplug - so we are 7989 * not committed to waiting the entire time. 7990 * 7991 * We are typically outside the window, so timeout is 0. 7992 */ 7993 sync_usec = tgtmap->tgtmap_create_csync_usec; 7994 if (tgtmap->tgtmap_create_window) { 7995 tsa = ddi_get_lbolt64() - tgtmap->tgtmap_create_time; 7996 if (tsa < drv_usectohz(sync_usec)) { 7997 tsa = drv_usectohz(sync_usec) - tsa; 7998 ret = ndi_busop_bus_config(self, 7999 flags, op, arg, childp, (clock_t)tsa); 8000 } else 8001 tsa = 0; /* passed window */ 8002 8003 /* First one out closes the window. */ 8004 tgtmap->tgtmap_create_window = 0; 8005 } else if (op == BUS_CONFIG_ONE) 8006 ret = ndi_busop_bus_config(self, flags, op, arg, childp, 0); 8007 8008 /* Return if doing a BUS_CONFIG_ONE and we found what we want. */ 8009 if ((op == BUS_CONFIG_ONE) && (ret == NDI_SUCCESS)) 8010 goto out; /* performance path */ 8011 8012 /* 8013 * We sync if we were in the window, on the first bus_config_one, and 8014 * every bus_config_all (or bus_config_driver). 8015 */ 8016 if (tsa || (tgtmap->tgtmap_sync_cnt == 0) || 8017 (op != BUS_CONFIG_ONE)) { 8018 /* 8019 * Sync current observations in the map and look again. We 8020 * place an upper bound on the amount of time we will wait for 8021 * sync to complete to avoid a bad device causing this 8022 * busconfig operation to hang. 8023 * 8024 * We are typically stable, so damap_sync returns immediately. 8025 * 8026 * Max time to wait for sync is settle_usec per possible device. 8027 */ 8028 tgtmap->tgtmap_sync_cnt++; 8029 maxdev = damap_size(tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]); 8030 maxdev = (maxdev > scsi_hba_map_settle_f) ? maxdev : 8031 scsi_hba_map_settle_f; 8032 sync_usec = maxdev * tgtmap->tgtmap_settle_usec; 8033 synced = scsi_tgtmap_sync((scsi_hba_tgtmap_t *)tgtmap, 8034 sync_usec); 8035 if (!synced) 8036 SCSI_HBA_LOG((_LOGCFG, self, NULL, 8037 "tgtmap_sync timeout")); 8038 } else 8039 synced = -1; 8040 8041 if (op == BUS_CONFIG_ONE) 8042 ret = scsi_hba_bus_configone(self, flags, arg, childp); 8043 else 8044 ret = ndi_busop_bus_config(self, flags, op, arg, childp, 0); 8045 8046 out: 8047 #ifdef DEBUG 8048 if (ret != NDI_SUCCESS) { 8049 if (scsi_hba_bus_config_failure_msg || 8050 scsi_hba_bus_config_failure_dbg) { 8051 scsi_hba_bus_config_failure_msg--; 8052 printf("%s%d: bus_config_tgtmap %p failure on %s: " 8053 "%d %d\n", 8054 ddi_driver_name(self), ddi_get_instance(self), 8055 (void *)tgtmap, 8056 (op == BUS_CONFIG_ONE) ? (char *)arg : "ALL", 8057 (int)tsa, synced); 8058 } 8059 if (scsi_hba_bus_config_failure_dbg) { 8060 scsi_hba_bus_config_failure_dbg--; 8061 debug_enter("config_tgtmap failure"); 8062 } 8063 } else if (scsi_hba_bus_config_success_msg || 8064 scsi_hba_bus_config_success_dbg) { 8065 scsi_hba_bus_config_success_msg--; 8066 printf("%s%d: bus_config_tgtmap %p success on %s: %d %d\n", 8067 ddi_driver_name(self), ddi_get_instance(self), 8068 (void *)tgtmap, 8069 (op == BUS_CONFIG_ONE) ? (char *)arg : "ALL", 8070 (int)tsa, synced); 8071 if (scsi_hba_bus_config_success_dbg) { 8072 scsi_hba_bus_config_success_dbg--; 8073 debug_enter("config_tgtmap success"); 8074 } 8075 } 8076 #endif /* DEBUG */ 8077 return (ret); 8078 } 8079 8080 static int 8081 scsi_hba_bus_unconfig_tgtmap(dev_info_t *self, uint_t flags, 8082 ddi_bus_config_op_t op, void *arg) 8083 { 8084 int ret = NDI_FAILURE; 8085 8086 switch (op) { 8087 case BUS_UNCONFIG_ONE: 8088 case BUS_UNCONFIG_DRIVER: 8089 case BUS_UNCONFIG_ALL: 8090 ret = NDI_SUCCESS; 8091 break; 8092 default: 8093 break; 8094 } 8095 8096 if (ret == NDI_SUCCESS) { 8097 flags &= ~NDI_DEVI_REMOVE; 8098 ret = ndi_busop_bus_unconfig(self, flags, op, arg); 8099 } 8100 return (ret); 8101 } 8102 8103 static int 8104 scsi_hba_bus_config_iportmap(dev_info_t *self, uint_t flags, 8105 ddi_bus_config_op_t op, void *arg, dev_info_t **childp) 8106 { 8107 scsi_hba_tran_t *tran; 8108 impl_scsi_iportmap_t *iportmap; 8109 dev_info_t *child; 8110 int circ; 8111 uint64_t tsa = 0; /* clock64_t */ 8112 int sync_usec; 8113 int synced; 8114 int ret = NDI_FAILURE; 8115 8116 if ((op != BUS_CONFIG_ONE) && (op != BUS_CONFIG_ALL) && 8117 (op != BUS_CONFIG_DRIVER)) 8118 goto out; 8119 8120 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 8121 iportmap = (impl_scsi_iportmap_t *)tran->tran_iportmap; 8122 ASSERT(iportmap); 8123 8124 /* 8125 * MPXIO is never a sure thing (and we have mixed children), so 8126 * set NDI_NDI_FALLBACK so that ndi_busop_bus_config will 8127 * search for both devinfo and pathinfo children. 8128 * 8129 * Future: Remove NDI_MDI_FALLBACK since devcfg.c now looks for 8130 * devinfo/pathinfo children in parallel (instead of old way of 8131 * looking for one form of child and then doing "fallback" to 8132 * look for other form of child). 8133 */ 8134 flags |= NDI_MDI_FALLBACK; /* devinfo&pathinfo children */ 8135 8136 /* 8137 * If bus_config occurred within the map create-to-hotplug_sync window, 8138 * we need the framework to wait for children that are physicaly 8139 * present at map create time to show up (via iportmap hotplug config). 8140 * 8141 * The duration of this window is specified by the HBA driver at 8142 * scsi_hba_iportmap_create(9F) time (during attach(9E)). Its 8143 * 'csync_usec' value is selected based on how long it takes the HBA 8144 * driver to get from map creation to initial observation for something 8145 * already plugged in. Estimate high, a low estimate can result in 8146 * devices not showing up correctly on first reference. The call to 8147 * ndi_busop_bus_config needs a timeout value large enough so that 8148 * the map sync call further down is not a noop (i.e. done against 8149 * an empty map when something is infact plugged in). With 8150 * BUS_CONFIG_ONE, the call to ndi_busop_bus_config will return as 8151 * soon as the desired device is enumerated via hotplug - so we are 8152 * not committed to waiting the entire time. 8153 * 8154 * We are typically outside the window, so timeout is 0. 8155 */ 8156 sync_usec = iportmap->iportmap_create_csync_usec; 8157 if (iportmap->iportmap_create_window) { 8158 tsa = ddi_get_lbolt64() - iportmap->iportmap_create_time; 8159 if (tsa < drv_usectohz(sync_usec)) { 8160 tsa = drv_usectohz(sync_usec) - tsa; 8161 ret = ndi_busop_bus_config(self, 8162 flags, op, arg, childp, (clock_t)tsa); 8163 } else 8164 tsa = 0; /* passed window */ 8165 8166 /* First one out closes the window. */ 8167 iportmap->iportmap_create_window = 0; 8168 } else if (op == BUS_CONFIG_ONE) 8169 ret = ndi_busop_bus_config(self, flags, op, arg, childp, 0); 8170 8171 /* Return if doing a BUS_CONFIG_ONE and we found what we want. */ 8172 if ((op == BUS_CONFIG_ONE) && (ret == NDI_SUCCESS)) 8173 goto out; /* performance path */ 8174 8175 /* 8176 * We sync if we were in the window, on the first bus_config_one, and 8177 * every bus_config_all (or bus_config_driver). 8178 */ 8179 if (tsa || (iportmap->iportmap_sync_cnt == 0) || 8180 (op != BUS_CONFIG_ONE)) { 8181 /* 8182 * Sync current observations in the map and look again. We 8183 * place an upper bound on the amount of time we will wait for 8184 * sync to complete to avoid a bad device causing this 8185 * busconfig operation to hang. 8186 * 8187 * We are typically stable, so damap_sync returns immediately. 8188 * 8189 * Max time to wait for sync is settle_usec times settle factor. 8190 */ 8191 iportmap->iportmap_sync_cnt++; 8192 synced = damap_sync(iportmap->iportmap_dam, sync_usec); 8193 if (!synced) 8194 SCSI_HBA_LOG((_LOGCFG, self, NULL, 8195 "iportmap_sync timeout")); 8196 } else 8197 synced = -1; 8198 8199 if (op == BUS_CONFIG_ONE) { 8200 /* create the iport node child */ 8201 scsi_hba_devi_enter(self, &circ); 8202 if ((child = scsi_hba_bus_config_port(self, (char *)arg, 8203 SE_BUSCONFIG)) != NULL) { 8204 if (childp) { 8205 ndi_hold_devi(child); 8206 *childp = child; 8207 } 8208 ret = NDI_SUCCESS; 8209 } 8210 scsi_hba_devi_exit(self, circ); 8211 } else 8212 ret = ndi_busop_bus_config(self, flags, op, arg, childp, 0); 8213 8214 out: 8215 #ifdef DEBUG 8216 if (ret != NDI_SUCCESS) { 8217 if (scsi_hba_bus_config_failure_msg || 8218 scsi_hba_bus_config_failure_dbg) { 8219 scsi_hba_bus_config_failure_msg--; 8220 printf("%s%d: bus_config_iportmap %p failure on %s: " 8221 "%d %d\n", 8222 ddi_driver_name(self), ddi_get_instance(self), 8223 (void *)iportmap, 8224 (op == BUS_CONFIG_ONE) ? (char *)arg : "ALL", 8225 (int)tsa, synced); 8226 } 8227 if (scsi_hba_bus_config_failure_dbg) { 8228 scsi_hba_bus_config_failure_dbg--; 8229 debug_enter("config_iportmap failure"); 8230 } 8231 } else if (scsi_hba_bus_config_success_msg || 8232 scsi_hba_bus_config_success_dbg) { 8233 scsi_hba_bus_config_success_msg--; 8234 printf("%s%d: bus_config_iportmap %p success on %s: %d %d\n", 8235 ddi_driver_name(self), ddi_get_instance(self), 8236 (void *)iportmap, 8237 (op == BUS_CONFIG_ONE) ? (char *)arg : "ALL", 8238 (int)tsa, synced); 8239 if (scsi_hba_bus_config_success_dbg) { 8240 scsi_hba_bus_config_success_dbg--; 8241 debug_enter("config_iportmap success"); 8242 } 8243 } 8244 #endif /* DEBUG */ 8245 return (ret); 8246 } 8247 8248 static int 8249 scsi_hba_bus_unconfig_iportmap(dev_info_t *self, uint_t flags, 8250 ddi_bus_config_op_t op, void *arg) 8251 { 8252 flags &= ~NDI_DEVI_REMOVE; 8253 return (ndi_busop_bus_unconfig(self, flags, op, arg)); 8254 } 8255 8256 /* 8257 * SCSI HBA bus config enumeration entry point. Called via the bus_ops 8258 * bus_config entry point for all SCSA HBA drivers. 8259 * 8260 * o If an HBA implements its own bus_config via tran_bus_config then we 8261 * invoke it. An HBA that implements its own tran_bus_config entry point 8262 * may still call back into common SCSA code bus_config code for: 8263 * 8264 * o SPI bus_config (scsi_hba_bus_spi) 8265 * o LUN and secondary function enumeration (scsi_hba_enum_lsf_of_t()). 8266 * o configuration of a specific device (scsi_device_config). 8267 * o determining 1275 SCSI nodename and compatible property 8268 * (scsi_hba_nodename_compatible_get/_free). 8269 * 8270 * o Otherwise we implement a SCSI parallel interface (spi) bus config. 8271 * 8272 * Return NDI_SUCCESS if we might have created a new node. 8273 * Return NDI_FAILURE if we definitely did not create a new node. 8274 */ 8275 static int 8276 scsi_hba_bus_config(dev_info_t *self, uint_t flags, 8277 ddi_bus_config_op_t op, void *arg, dev_info_t **childp) 8278 { 8279 scsi_hba_tran_t *tran; 8280 int ret; 8281 8282 /* make sure that we will not disappear */ 8283 ASSERT(DEVI(self)->devi_ref); 8284 8285 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 8286 if (tran == NULL) { 8287 /* NULL tran driver.conf config (used by cmdk). */ 8288 if ((op == BUS_CONFIG_ONE) || (flags & NDI_DRV_CONF_REPROBE)) 8289 flags |= NDI_CONFIG_REPROBE; 8290 return (ndi_busop_bus_config(self, flags, op, arg, childp, 0)); 8291 } 8292 8293 /* Check if self is HBA-only node. */ 8294 if (tran->tran_hba_flags & SCSI_HBA_HBA) { 8295 /* The bus_config request is to configure iports below HBA. */ 8296 8297 #ifdef sparc 8298 /* 8299 * Sparc's 'boot-device' OBP property value lacks an /iport@X/ 8300 * component. Prior to the mount of root, we drive a disk@ 8301 * BUS_CONFIG_ONE operatino down a level to resolve an 8302 * OBP 'boot-device' path. 8303 * 8304 * Future: Add (modrootloaded == 0) below, and insure that 8305 * all attempts bus_conf of 'bo_name' (in OBP form) occur 8306 * prior to 'modrootloaded = 1;' assignment in vfs_mountroot. 8307 */ 8308 if ((op == BUS_CONFIG_ONE) && 8309 (strncmp((char *)arg, "disk@", strlen("disk@")) == 0)) { 8310 return (scsi_hba_bus_config_prom_node(self, 8311 flags, arg, childp)); 8312 } 8313 #endif /* sparc */ 8314 8315 if (tran->tran_iportmap) { 8316 /* config based on scsi_hba_iportmap API */ 8317 ret = scsi_hba_bus_config_iportmap(self, 8318 flags, op, arg, childp); 8319 } else { 8320 /* config based on 'iport_register' API */ 8321 ret = scsi_hba_bus_config_iports(self, 8322 flags, op, arg, childp); 8323 } 8324 return (ret); 8325 } 8326 8327 /* Check to see how the iport/HBA does target/lun bus config. */ 8328 if (tran->tran_bus_config) { 8329 /* HBA config based on Sun-private/legacy tran_bus_config */ 8330 ret = tran->tran_bus_config(self, flags, op, arg, childp); 8331 } else if (tran->tran_tgtmap) { 8332 /* SCSAv3 config based on scsi_hba_tgtmap_*() API */ 8333 ret = scsi_hba_bus_config_tgtmap(self, flags, op, arg, childp); 8334 } else { 8335 /* SCSA config based on SCSI Parallel Interconnect */ 8336 ret = scsi_hba_bus_config_spi(self, flags, op, arg, childp); 8337 } 8338 return (ret); 8339 } 8340 8341 /* 8342 * Called via the bus_ops bus_unconfig entry point for SCSI HBA drivers. 8343 */ 8344 static int 8345 scsi_hba_bus_unconfig(dev_info_t *self, uint_t flags, 8346 ddi_bus_config_op_t op, void *arg) 8347 { 8348 int circ; 8349 scsi_hba_tran_t *tran; 8350 int ret; 8351 8352 tran = ddi_get_driver_private(self); 8353 if (tran == NULL) { 8354 /* NULL tran driver.conf unconfig (used by cmdk). */ 8355 return (ndi_busop_bus_unconfig(self, flags, op, arg)); 8356 } 8357 8358 /* 8359 * Purge barrier/probe node children. We do this prior to 8360 * tran_bus_unconfig in case the unconfig implementation calls back 8361 * into the common code at a different enumeration level, such a 8362 * scsi_device_config, which still creates barrier/probe nodes. 8363 */ 8364 scsi_hba_devi_enter(self, &circ); 8365 scsi_hba_barrier_purge(self); 8366 scsi_hba_devi_exit(self, circ); 8367 8368 /* DEBUG: for testing, allow bus_unconfig do drive removal. */ 8369 if (scsi_hba_bus_unconfig_remove) 8370 flags |= NDI_DEVI_REMOVE; 8371 8372 /* Check if self is HBA-only node. */ 8373 if (tran->tran_hba_flags & SCSI_HBA_HBA) { 8374 /* The bus_config request is to unconfigure iports below HBA. */ 8375 if (tran->tran_iportmap) { 8376 /* SCSAv3 unconfig based on scsi_hba_iportmap API */ 8377 ret = scsi_hba_bus_unconfig_iportmap(self, 8378 flags, op, arg); 8379 } else if (tran->tran_bus_unconfig) { 8380 /* HBA unconfig based on Sun-private/legacy API */ 8381 ret = tran->tran_bus_unconfig(self, flags, op, arg); 8382 } else { 8383 /* Standard framework unconfig. */ 8384 ret = ndi_busop_bus_unconfig(self, flags, op, arg); 8385 } 8386 return (ret); 8387 } 8388 8389 /* Check to see how the iport/HBA does target/lun bus unconfig. */ 8390 if (tran->tran_bus_unconfig) { 8391 /* HBA unconfig based on Sun-private/legacy tran_bus_unconfig */ 8392 ret = tran->tran_bus_unconfig(self, flags, op, arg); 8393 } else if (tran->tran_tgtmap) { 8394 /* SCSAv3 unconfig based on scsi_hba_tgtmap_*() API */ 8395 ret = scsi_hba_bus_unconfig_tgtmap(self, flags, op, arg); 8396 } else { 8397 /* SCSA unconfig based on SCSI Parallel Interconnect */ 8398 ret = scsi_hba_bus_unconfig_spi(self, flags, op, arg); 8399 } 8400 return (ret); 8401 } 8402 8403 static int 8404 scsi_tgtmap_scsi_config(void *arg, damap_t *mapp, damap_id_t tgtid) 8405 { 8406 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 8407 dev_info_t *self = tran->tran_iport_dip; 8408 impl_scsi_tgtmap_t *tgtmap; 8409 char *tgtaddr; 8410 int cfg_status, mt; 8411 8412 tgtmap = (impl_scsi_tgtmap_t *)tran->tran_tgtmap; 8413 tgtaddr = damap_id2addr(mapp, tgtid); 8414 8415 if (scsi_lunmap_create(self, tgtmap, tgtaddr) != DDI_SUCCESS) { 8416 SCSI_HBA_LOG((_LOG_NF(WARN), 8417 "failed to create lunmap for %s", tgtaddr)); 8418 } 8419 8420 mt = ddi_prop_get_int(DDI_DEV_T_ANY, self, 8421 DDI_PROP_NOTPROM | DDI_PROP_DONTPASS, "scsi-enumeration", 8422 scsi_enumeration); 8423 mt |= scsi_hba_log_mt_disable; 8424 8425 cfg_status = scsi_hba_bus_config_taddr(self, tgtaddr, mt, SE_HP); 8426 if (cfg_status != NDI_SUCCESS) { 8427 SCSI_HBA_LOG((_LOGCFG, self, NULL, "%s @%s config status %d", 8428 damap_name(mapp), tgtaddr, cfg_status)); 8429 scsi_lunmap_destroy(self, tgtmap, tgtaddr); 8430 return (DAM_FAILURE); 8431 } 8432 8433 return (DAM_SUCCESS); 8434 } 8435 8436 8437 static int 8438 scsi_tgtmap_scsi_unconfig(void *arg, damap_t *mapp, damap_id_t tgtid) 8439 { 8440 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 8441 dev_info_t *self = tran->tran_iport_dip; 8442 impl_scsi_tgtmap_t *tgtmap; 8443 char *tgt_addr; 8444 8445 tgtmap = (impl_scsi_tgtmap_t *)tran->tran_tgtmap; 8446 tgt_addr = damap_id2addr(mapp, tgtid); 8447 8448 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, "%s @%s", damap_name(mapp), 8449 tgt_addr)); 8450 scsi_lunmap_destroy(self, tgtmap, tgt_addr); 8451 return (DAM_SUCCESS); 8452 } 8453 8454 static int 8455 scsi_tgtmap_smp_config(void *arg, damap_t *mapp, damap_id_t tgtid) 8456 { 8457 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 8458 dev_info_t *self = tran->tran_iport_dip; 8459 char *addr; 8460 8461 addr = damap_id2addr(mapp, tgtid); 8462 SCSI_HBA_LOG((_LOGCFG, self, NULL, "%s @%s", damap_name(mapp), addr)); 8463 8464 return ((smp_hba_bus_config_taddr(self, addr) == NDI_SUCCESS) ? 8465 DAM_SUCCESS : DAM_FAILURE); 8466 } 8467 8468 static int 8469 scsi_tgtmap_smp_unconfig(void *arg, damap_t *mapp, damap_id_t tgtid) 8470 { 8471 scsi_hba_tran_t *tran = (scsi_hba_tran_t *)arg; 8472 dev_info_t *self = tran->tran_iport_dip; 8473 char *addr; 8474 dev_info_t *child; 8475 char nameaddr[SCSI_MAXNAMELEN]; 8476 int circ; 8477 8478 addr = damap_id2addr(mapp, tgtid); 8479 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, "%s @%s", damap_name(mapp), addr)); 8480 8481 (void) snprintf(nameaddr, sizeof (nameaddr), "smp@%s", addr); 8482 scsi_hba_devi_enter(self, &circ); 8483 if ((child = ndi_devi_findchild(self, nameaddr)) == NULL) { 8484 scsi_hba_devi_exit(self, circ); 8485 return (DAM_SUCCESS); 8486 } 8487 8488 if (ndi_devi_offline(child, 8489 NDI_DEVFS_CLEAN | NDI_DEVI_REMOVE) == DDI_SUCCESS) { 8490 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 8491 "devinfo smp@%s offlined and removed", addr)); 8492 } else if (ndi_devi_device_remove(child)) { 8493 /* Offline/remove failed, note new device_remove */ 8494 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 8495 "devinfo smp@%s offline failed, device_remove", 8496 addr)); 8497 } 8498 scsi_hba_devi_exit(self, circ); 8499 return (DAM_SUCCESS); 8500 } 8501 8502 /* ARGSUSED1 */ 8503 static void 8504 scsi_tgtmap_smp_activate(void *map_priv, char *tgt_addr, int addrid, 8505 void **tgt_privp) 8506 { 8507 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)map_priv; 8508 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8509 8510 if (tgtmap->tgtmap_activate_cb) { 8511 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s @%s activated", 8512 damap_name(tgtmap->tgtmap_dam[SCSI_TGT_SMP_DEVICE]), 8513 tgt_addr)); 8514 8515 (*tgtmap->tgtmap_activate_cb)(tgtmap->tgtmap_mappriv, 8516 tgt_addr, SCSI_TGT_SMP_DEVICE, tgt_privp); 8517 } 8518 } 8519 8520 /* ARGSUSED1 */ 8521 static void 8522 scsi_tgtmap_smp_deactivate(void *map_priv, char *tgt_addr, int addrid, 8523 void *tgt_privp, damap_deact_rsn_t damap_rsn) 8524 { 8525 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)map_priv; 8526 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8527 boolean_t tgtmap_rereport; 8528 scsi_tgtmap_deact_rsn_t tgtmap_rsn; 8529 8530 if (tgtmap->tgtmap_deactivate_cb) { 8531 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s @%s deactivated %d", 8532 damap_name(tgtmap->tgtmap_dam[SCSI_TGT_SMP_DEVICE]), 8533 tgt_addr, damap_rsn)); 8534 8535 if (damap_rsn == DAMAP_DEACT_RSN_GONE) 8536 tgtmap_rsn = SCSI_TGT_DEACT_RSN_GONE; 8537 else if (damap_rsn == DAMAP_DEACT_RSN_CFG_FAIL) 8538 tgtmap_rsn = SCSI_TGT_DEACT_RSN_CFG_FAIL; 8539 else if (damap_rsn == DAMAP_DEACT_RSN_UNSTBL) 8540 tgtmap_rsn = SCSI_TGT_DEACT_RSN_UNSTBL; 8541 else { 8542 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 8543 "%s @%s deactivated with unknown rsn", 8544 damap_name(tgtmap->tgtmap_dam[SCSI_TGT_SMP_DEVICE]), 8545 tgt_addr)); 8546 return; 8547 } 8548 8549 tgtmap_rereport = (*tgtmap->tgtmap_deactivate_cb) 8550 (tgtmap->tgtmap_mappriv, tgt_addr, 8551 SCSI_TGT_SMP_DEVICE, tgt_privp, tgtmap_rsn); 8552 8553 if ((tgtmap_rsn == SCSI_TGT_DEACT_RSN_CFG_FAIL) && 8554 (tgtmap_rereport == B_FALSE)) { 8555 SCSI_HBA_LOG((_LOG(WARN), NULL, self, 8556 "%s enumeration failed, no more retries until " 8557 "config change occurs", tgt_addr)); 8558 } 8559 } 8560 } 8561 8562 /* ARGSUSED1 */ 8563 static void 8564 scsi_tgtmap_scsi_activate(void *map_priv, char *tgt_addr, int addrid, 8565 void **tgt_privp) 8566 { 8567 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)map_priv; 8568 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8569 8570 if (tgtmap->tgtmap_activate_cb) { 8571 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s @%s activated", 8572 damap_name(tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]), 8573 tgt_addr)); 8574 8575 (*tgtmap->tgtmap_activate_cb)(tgtmap->tgtmap_mappriv, 8576 tgt_addr, SCSI_TGT_SCSI_DEVICE, tgt_privp); 8577 } 8578 } 8579 8580 /* ARGSUSED1 */ 8581 static void 8582 scsi_tgtmap_scsi_deactivate(void *map_priv, char *tgt_addr, int addrid, 8583 void *tgt_privp, damap_deact_rsn_t damap_rsn) 8584 { 8585 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)map_priv; 8586 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8587 boolean_t tgtmap_rereport; 8588 scsi_tgtmap_deact_rsn_t tgtmap_rsn; 8589 8590 if (tgtmap->tgtmap_deactivate_cb) { 8591 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s @%s deactivated %d", 8592 damap_name(tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]), 8593 tgt_addr, damap_rsn)); 8594 8595 if (damap_rsn == DAMAP_DEACT_RSN_GONE) 8596 tgtmap_rsn = SCSI_TGT_DEACT_RSN_GONE; 8597 else if (damap_rsn == DAMAP_DEACT_RSN_CFG_FAIL) 8598 tgtmap_rsn = SCSI_TGT_DEACT_RSN_CFG_FAIL; 8599 else if (damap_rsn == DAMAP_DEACT_RSN_UNSTBL) 8600 tgtmap_rsn = SCSI_TGT_DEACT_RSN_UNSTBL; 8601 else { 8602 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 8603 "%s @%s deactivated with unknown rsn", damap_name( 8604 tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]), 8605 tgt_addr)); 8606 return; 8607 } 8608 8609 tgtmap_rereport = (*tgtmap->tgtmap_deactivate_cb) 8610 (tgtmap->tgtmap_mappriv, tgt_addr, 8611 SCSI_TGT_SCSI_DEVICE, tgt_privp, tgtmap_rsn); 8612 8613 if ((tgtmap_rsn == SCSI_TGT_DEACT_RSN_CFG_FAIL) && 8614 (tgtmap_rereport == B_FALSE)) { 8615 SCSI_HBA_LOG((_LOG(WARN), NULL, self, 8616 "%s enumeration failed, no more retries until " 8617 "config change occurs", tgt_addr)); 8618 } 8619 } 8620 } 8621 8622 8623 int 8624 scsi_hba_tgtmap_create(dev_info_t *self, scsi_tgtmap_mode_t mode, 8625 int csync_usec, int settle_usec, void *tgtmap_priv, 8626 scsi_tgt_activate_cb_t activate_cb, scsi_tgt_deactivate_cb_t deactivate_cb, 8627 scsi_hba_tgtmap_t **handle) 8628 { 8629 scsi_hba_tran_t *tran; 8630 damap_t *mapp; 8631 char context[64]; 8632 impl_scsi_tgtmap_t *tgtmap; 8633 damap_rptmode_t rpt_style; 8634 char *scsi_binding_set; 8635 int optflags; 8636 8637 if (self == NULL || csync_usec == 0 || 8638 settle_usec == 0 || handle == NULL) 8639 return (DDI_FAILURE); 8640 8641 *handle = NULL; 8642 8643 if (scsi_hba_iport_unit_address(self) == NULL) 8644 return (DDI_FAILURE); 8645 8646 switch (mode) { 8647 case SCSI_TM_FULLSET: 8648 rpt_style = DAMAP_REPORT_FULLSET; 8649 break; 8650 case SCSI_TM_PERADDR: 8651 rpt_style = DAMAP_REPORT_PERADDR; 8652 break; 8653 default: 8654 return (DDI_FAILURE); 8655 } 8656 8657 tran = (scsi_hba_tran_t *)ddi_get_driver_private(self); 8658 ASSERT(tran); 8659 if (tran == NULL) 8660 return (DDI_FAILURE); 8661 8662 tgtmap = kmem_zalloc(sizeof (*tgtmap), KM_SLEEP); 8663 tgtmap->tgtmap_tran = tran; 8664 tgtmap->tgtmap_activate_cb = activate_cb; 8665 tgtmap->tgtmap_deactivate_cb = deactivate_cb; 8666 tgtmap->tgtmap_mappriv = tgtmap_priv; 8667 8668 tgtmap->tgtmap_create_window = 1; /* start with window */ 8669 tgtmap->tgtmap_create_time = ddi_get_lbolt64(); 8670 tgtmap->tgtmap_create_csync_usec = csync_usec; 8671 tgtmap->tgtmap_settle_usec = settle_usec; 8672 tgtmap->tgtmap_sync_cnt = 0; 8673 8674 optflags = (ddi_prop_get_int(DDI_DEV_T_ANY, self, 8675 DDI_PROP_NOTPROM | DDI_PROP_DONTPASS, "scsi-enumeration", 8676 scsi_enumeration) & SCSI_ENUMERATION_MT_TARGET_DISABLE) ? 8677 DAMAP_SERIALCONFIG : DAMAP_MTCONFIG; 8678 8679 (void) snprintf(context, sizeof (context), "%s%d.tgtmap.scsi", 8680 ddi_driver_name(self), ddi_get_instance(self)); 8681 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s", context)); 8682 if (damap_create(context, rpt_style, optflags, settle_usec, 8683 tgtmap, scsi_tgtmap_scsi_activate, scsi_tgtmap_scsi_deactivate, 8684 tran, scsi_tgtmap_scsi_config, scsi_tgtmap_scsi_unconfig, 8685 &mapp) != DAM_SUCCESS) { 8686 kmem_free(tgtmap, sizeof (*tgtmap)); 8687 return (DDI_FAILURE); 8688 } 8689 tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE] = mapp; 8690 8691 (void) snprintf(context, sizeof (context), "%s%d.tgtmap.smp", 8692 ddi_driver_name(self), ddi_get_instance(self)); 8693 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s", context)); 8694 if (damap_create(context, rpt_style, optflags, 8695 settle_usec, tgtmap, scsi_tgtmap_smp_activate, 8696 scsi_tgtmap_smp_deactivate, 8697 tran, scsi_tgtmap_smp_config, scsi_tgtmap_smp_unconfig, 8698 &mapp) != DAM_SUCCESS) { 8699 damap_destroy(tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]); 8700 kmem_free(tgtmap, sizeof (*tgtmap)); 8701 return (DDI_FAILURE); 8702 } 8703 tgtmap->tgtmap_dam[SCSI_TGT_SMP_DEVICE] = mapp; 8704 8705 tran->tran_tgtmap = (scsi_hba_tgtmap_t *)tgtmap; 8706 *handle = (scsi_hba_tgtmap_t *)tgtmap; 8707 8708 /* 8709 * We have now set tran_tgtmap, marking the tran as using tgtmap 8710 * enumeration services. To prevent the generation of legacy spi 8711 * 'binding-set' compatible forms, remove the 'scsi-binding-set' 8712 * property. 8713 */ 8714 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, self, 8715 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-binding-set", 8716 &scsi_binding_set) == DDI_PROP_SUCCESS) { 8717 if (strcmp(scsi_binding_set, scsi_binding_set_spi) == 0) 8718 (void) ndi_prop_remove(DDI_DEV_T_NONE, self, 8719 "scsi-binding-set"); 8720 ddi_prop_free(scsi_binding_set); 8721 } 8722 return (DDI_SUCCESS); 8723 } 8724 8725 void 8726 scsi_hba_tgtmap_destroy(scsi_hba_tgtmap_t *handle) 8727 { 8728 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8729 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8730 int i; 8731 8732 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8733 if (tgtmap->tgtmap_dam[i]) { 8734 SCSI_HBA_LOG((_LOGTGT, self, NULL, 8735 "%s", damap_name(tgtmap->tgtmap_dam[i]))); 8736 damap_destroy(tgtmap->tgtmap_dam[i]); 8737 } 8738 } 8739 kmem_free(tgtmap, sizeof (*tgtmap)); 8740 } 8741 8742 /* return 1 if all maps ended up syned */ 8743 static int 8744 scsi_tgtmap_sync(scsi_hba_tgtmap_t *handle, int sync_usec) 8745 { 8746 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8747 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8748 int all_synced = 1; 8749 int synced; 8750 int i; 8751 8752 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8753 if (tgtmap->tgtmap_dam[i]) { 8754 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s sync begin", 8755 damap_name(tgtmap->tgtmap_dam[i]))); 8756 synced = damap_sync(tgtmap->tgtmap_dam[i], sync_usec); 8757 all_synced &= synced; 8758 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s sync end %d", 8759 damap_name(tgtmap->tgtmap_dam[i]), synced)); 8760 8761 } 8762 } 8763 return (all_synced); 8764 } 8765 8766 /* return 1 if all maps ended up empty */ 8767 static int 8768 scsi_tgtmap_is_empty(scsi_hba_tgtmap_t *handle) 8769 { 8770 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8771 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8772 int all_empty = 1; 8773 int empty; 8774 int i; 8775 8776 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8777 if (tgtmap->tgtmap_dam[i]) { 8778 empty = damap_is_empty(tgtmap->tgtmap_dam[i]); 8779 all_empty &= empty; 8780 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s is_empty %d", 8781 damap_name(tgtmap->tgtmap_dam[i]), empty)); 8782 } 8783 } 8784 8785 return (all_empty); 8786 } 8787 8788 static int 8789 scsi_tgtmap_beginf(scsi_hba_tgtmap_t *handle, boolean_t do_begin) 8790 { 8791 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8792 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8793 char *context; 8794 int rv = DAM_SUCCESS; 8795 int i; 8796 8797 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8798 if (tgtmap->tgtmap_dam[i] == NULL) { 8799 continue; 8800 } 8801 8802 context = damap_name(tgtmap->tgtmap_dam[i]); 8803 if (do_begin == B_TRUE) { 8804 if (i == SCSI_TGT_SCSI_DEVICE) { 8805 /* 8806 * In scsi_device context, so we have the 8807 * 'context' string, diagnose the case where 8808 * the tgtmap caller is failing to make 8809 * forward progress, i.e. the caller is never 8810 * completing an observation by calling 8811 * scsi_hbg_tgtmap_set_end. If this occurs, 8812 * the solaris target/lun state may be out 8813 * of sync with hardware. 8814 */ 8815 if (tgtmap->tgtmap_reports++ >= 8816 scsi_hba_tgtmap_reports_max) { 8817 tgtmap->tgtmap_noisy++; 8818 if (tgtmap->tgtmap_noisy == 1) { 8819 SCSI_HBA_LOG((_LOG(WARN), 8820 self, NULL, 8821 "%s: failing tgtmap begin", 8822 context)); 8823 } 8824 } 8825 } 8826 8827 rv = damap_addrset_begin(tgtmap->tgtmap_dam[i]); 8828 } else { 8829 rv = damap_addrset_flush(tgtmap->tgtmap_dam[i]); 8830 } 8831 8832 if (rv != DAM_SUCCESS) { 8833 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s FAIL", context)); 8834 } else { 8835 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s", context)); 8836 } 8837 } 8838 8839 return ((rv == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 8840 } 8841 8842 8843 int 8844 scsi_hba_tgtmap_set_begin(scsi_hba_tgtmap_t *handle) 8845 { 8846 return (scsi_tgtmap_beginf(handle, B_TRUE)); 8847 } 8848 8849 int 8850 scsi_hba_tgtmap_set_flush(scsi_hba_tgtmap_t *handle) 8851 { 8852 return (scsi_tgtmap_beginf(handle, B_FALSE)); 8853 } 8854 8855 int 8856 scsi_hba_tgtmap_set_add(scsi_hba_tgtmap_t *handle, 8857 scsi_tgtmap_tgt_type_t tgt_type, char *tgt_addr, void *tgt_priv) 8858 { 8859 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8860 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8861 8862 if (tgt_type >= SCSI_TGT_NTYPES || !tgtmap->tgtmap_dam[tgt_type]) 8863 return (DDI_FAILURE); 8864 8865 SCSI_HBA_LOG((_LOGTGT, self, NULL, 8866 "%s @%s", damap_name(tgtmap->tgtmap_dam[tgt_type]), tgt_addr)); 8867 8868 return ((damap_addrset_add(tgtmap->tgtmap_dam[tgt_type], tgt_addr, 8869 NULL, NULL, tgt_priv) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 8870 } 8871 8872 /*ARGSUSED*/ 8873 int 8874 scsi_hba_tgtmap_set_end(scsi_hba_tgtmap_t *handle, uint_t flags) 8875 { 8876 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8877 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8878 char *context; 8879 int rv = DDI_SUCCESS; 8880 int i; 8881 8882 tgtmap->tgtmap_reports = tgtmap->tgtmap_noisy = 0; 8883 8884 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8885 if (tgtmap->tgtmap_dam[i] == NULL) 8886 continue; 8887 context = damap_name(tgtmap->tgtmap_dam[i]); 8888 if (damap_addrset_end( 8889 tgtmap->tgtmap_dam[i], 0) != DAM_SUCCESS) { 8890 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s FAIL", context)); 8891 rv = DDI_FAILURE; 8892 continue; 8893 } 8894 8895 SCSI_HBA_LOG((_LOGTGT, self, NULL, "%s", context)); 8896 } 8897 return (rv); 8898 } 8899 8900 int 8901 scsi_hba_tgtmap_tgt_add(scsi_hba_tgtmap_t *handle, 8902 scsi_tgtmap_tgt_type_t tgt_type, char *tgt_addr, void *tgt_priv) 8903 8904 { 8905 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8906 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8907 8908 if (tgt_type >= SCSI_TGT_NTYPES || !tgtmap->tgtmap_dam[tgt_type]) 8909 return (DDI_FAILURE); 8910 8911 SCSI_HBA_LOG((_LOGTGT, self, NULL, 8912 "%s @%s", damap_name(tgtmap->tgtmap_dam[tgt_type]), tgt_addr)); 8913 8914 return ((damap_addr_add(tgtmap->tgtmap_dam[tgt_type], tgt_addr, NULL, 8915 NULL, tgt_priv) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 8916 } 8917 8918 int 8919 scsi_hba_tgtmap_tgt_remove(scsi_hba_tgtmap_t *handle, 8920 scsi_tgtmap_tgt_type_t tgt_type, char *tgt_addr) 8921 { 8922 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8923 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8924 8925 if (tgt_type >= SCSI_TGT_NTYPES || !tgtmap->tgtmap_dam[tgt_type]) 8926 return (DDI_FAILURE); 8927 8928 SCSI_HBA_LOG((_LOGTGT, self, NULL, 8929 "%s @%s", damap_name(tgtmap->tgtmap_dam[tgt_type]), tgt_addr)); 8930 8931 return ((damap_addr_del(tgtmap->tgtmap_dam[tgt_type], 8932 tgt_addr) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 8933 } 8934 8935 int 8936 scsi_hba_tgtmap_lookup(scsi_hba_tgtmap_t *handle, 8937 char *tgt_addr, scsi_tgtmap_tgt_type_t *r_type) 8938 { 8939 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)handle; 8940 dev_info_t *self = tgtmap->tgtmap_tran->tran_iport_dip; 8941 damap_id_t tgtid; 8942 int i; 8943 8944 for (i = 0; i < SCSI_TGT_NTYPES; i++) { 8945 tgtid = damap_lookup(tgtmap->tgtmap_dam[i], tgt_addr); 8946 if (tgtid != NODAM) { 8947 *r_type = i; 8948 SCSI_HBA_LOG((_LOG(3), self, NULL, 8949 "%s @%s found: type %d", 8950 damap_name(tgtmap->tgtmap_dam[i]), tgt_addr, i)); 8951 damap_id_rele(tgtmap->tgtmap_dam[i], tgtid); 8952 return (DDI_SUCCESS); 8953 } 8954 } 8955 8956 SCSI_HBA_LOG((_LOG(3), self, NULL, 8957 "%s%d.tgtmap @%s not found", 8958 ddi_driver_name(self), ddi_get_instance(self), tgt_addr)); 8959 return (DDI_FAILURE); 8960 } 8961 8962 /* 8963 * Return the unit-address of an 'iport' node, or NULL for non-iport node. 8964 */ 8965 char * 8966 scsi_hba_iport_unit_address(dev_info_t *self) 8967 { 8968 /* 8969 * NOTE: Since 'self' could be a SCSA iport node or a SCSA HBA node, 8970 * we can't use SCSA flavors: the flavor of a SCSA HBA node is not 8971 * established/owned by SCSA, it is established by the nexus that 8972 * created the SCSA HBA node (PCI) as a child. 8973 * 8974 * NOTE: If we want to support a node_name other than "iport" for 8975 * an iport node then we can add support for a "scsa-iport-node-name" 8976 * property on the SCSA HBA node. A SCSA HBA driver would set this 8977 * property on the SCSA HBA node prior to using the iport API. 8978 */ 8979 if (strcmp(ddi_node_name(self), "iport") == 0) 8980 return (ddi_get_name_addr(self)); 8981 else 8982 return (NULL); 8983 } 8984 8985 /* 8986 * Define a SCSI initiator port (bus/channel) for an HBA card that needs to 8987 * support multiple SCSI ports, but only has a single HBA devinfo node. This 8988 * function should be called from the HBA's attach(9E) implementation (when 8989 * processing the HBA devinfo node attach) after the number of SCSI ports on 8990 * the card is known or when the HBA driver DR handler detects a new port. 8991 * The function returns 0 on failure and 1 on success. 8992 * 8993 * The implementation will add the port value into the "scsi-iports" property 8994 * value maintained on the HBA node as. These properties are used by the generic 8995 * scsi bus_config implementation to dynamicaly enumerate the specified iport 8996 * children. The enumeration code will, on demand, create the appropriate 8997 * iport children with a SCSI_ADDR_PROP_IPORTUA unit address. This node will 8998 * bind to the same driver as the HBA node itself. This means that an HBA 8999 * driver that uses iports should expect probe(9E), attach(9E), and detach(9E) 9000 * calls on the iport children of the HBA. If configuration for all ports was 9001 * already done during HBA node attach, the driver should just return 9002 * DDI_SUCCESS when confronted with an iport node. 9003 * 9004 * A maximum of 32 iport ports are supported per HBA devinfo node. 9005 * 9006 * A NULL "port" can be used to indicate that the framework should enumerate 9007 * target children on the HBA node itself, in addition to enumerating target 9008 * children on any iport nodes declared. There are two reasons that an HBA may 9009 * wish to have target children enumerated on both the HBA node and iport 9010 * node(s): 9011 * 9012 * o If, in the past, HBA hardware had only a single physical port but now 9013 * supports multiple physical ports, the updated driver that supports 9014 * multiple physical ports may want to avoid /devices path upgrade issues 9015 * by enumerating the first physical port under the HBA instead of as a 9016 * iport. 9017 * 9018 * o Some hardware RAID HBA controllers (mlx, chs, etc) support multiple 9019 * SCSI physical ports configured so that various physical devices on 9020 * the physical ports are amalgamated into virtual devices on a virtual 9021 * port. Amalgamated physical devices no longer appear to the host OS 9022 * on the physical ports, but other non-amalgamated devices may still be 9023 * visible on the physical ports. These drivers use a model where the 9024 * physical ports are iport nodes and the HBA node is the virtual port to 9025 * the configured virtual devices. 9026 */ 9027 int 9028 scsi_hba_iport_register(dev_info_t *self, char *port) 9029 { 9030 unsigned int ports = 0; 9031 int rval, i; 9032 char **iports, **newiports; 9033 9034 ASSERT(self); 9035 if (self == NULL) 9036 return (DDI_FAILURE); 9037 9038 rval = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, self, 9039 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-iports", &iports, 9040 &ports); 9041 9042 if (ports >= SCSI_HBA_MAX_IPORTS) { 9043 ddi_prop_free(iports); 9044 return (DDI_FAILURE); 9045 } 9046 9047 if (rval == DDI_PROP_SUCCESS) { 9048 for (i = 0; i < ports; i++) { 9049 if (strcmp(port, iports[i]) == 0) { 9050 /* iport already registered */ 9051 ddi_prop_free(iports); 9052 return (DDI_SUCCESS); 9053 } 9054 } 9055 } 9056 9057 newiports = kmem_alloc((sizeof (char *) * (ports + 1)), KM_SLEEP); 9058 9059 for (i = 0; i < ports; i++) { 9060 newiports[i] = strdup(iports[i]); 9061 } 9062 newiports[ports] = strdup(port); 9063 ports++; 9064 9065 if (ddi_prop_update_string_array(DDI_DEV_T_NONE, self, 9066 "scsi-iports", newiports, ports) != DDI_PROP_SUCCESS) { 9067 SCSI_HBA_LOG((_LOG(WARN), self, NULL, 9068 "failed to establish %s %s", 9069 SCSI_ADDR_PROP_IPORTUA, port)); 9070 rval = DDI_FAILURE; 9071 } else { 9072 rval = DDI_SUCCESS; 9073 } 9074 9075 /* If there is iport exist, free property */ 9076 if (ports > 1) 9077 ddi_prop_free(iports); 9078 for (i = 0; i < ports; i++) { 9079 strfree(newiports[i]); 9080 } 9081 kmem_free(newiports, (sizeof (char *)) * ports); 9082 9083 return (rval); 9084 } 9085 9086 /* 9087 * Check if the HBA has any scsi_hba_iport_register()ed children. 9088 */ 9089 int 9090 scsi_hba_iport_exist(dev_info_t *self) 9091 { 9092 unsigned int ports = 0; 9093 char **iports; 9094 int rval; 9095 9096 rval = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, self, 9097 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-iports", &iports, 9098 &ports); 9099 9100 if (rval != DDI_PROP_SUCCESS) 9101 return (0); 9102 9103 /* If there is now at least 1 iport, then iports is valid */ 9104 if (ports > 0) { 9105 rval = 1; 9106 } else 9107 rval = 0; 9108 ddi_prop_free(iports); 9109 9110 return (rval); 9111 } 9112 9113 dev_info_t * 9114 scsi_hba_iport_find(dev_info_t *self, char *portnm) 9115 { 9116 char *addr = NULL; 9117 char **iports; 9118 unsigned int num_iports = 0; 9119 int rval = DDI_FAILURE; 9120 int i = 0; 9121 dev_info_t *child = NULL; 9122 9123 /* check to see if this is an HBA that defined scsi iports */ 9124 rval = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, self, 9125 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-iports", &iports, 9126 &num_iports); 9127 9128 if (rval != DDI_SUCCESS) { 9129 return (NULL); 9130 } 9131 ASSERT(num_iports > 0); 9132 9133 /* check to see if this port was registered */ 9134 for (i = 0; i < num_iports; i++) { 9135 if (strcmp(iports[i], portnm) == 0) 9136 break; 9137 } 9138 9139 if (i == num_iports) { 9140 child = NULL; 9141 goto out; 9142 } 9143 9144 addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP); 9145 (void) snprintf(addr, SCSI_MAXNAMELEN, "iport@%s", portnm); 9146 rval = ndi_devi_config_one(self, addr, &child, NDI_NO_EVENT); 9147 kmem_free(addr, SCSI_MAXNAMELEN); 9148 9149 if (rval != DDI_SUCCESS) { 9150 child = NULL; 9151 } 9152 out: 9153 ddi_prop_free(iports); 9154 return (child); 9155 } 9156 9157 /* 9158 * Search/create the specified iport node 9159 */ 9160 static dev_info_t * 9161 scsi_hba_bus_config_port(dev_info_t *self, char *nameaddr, scsi_enum_t se) 9162 { 9163 dev_info_t *child; /* iport child of HBA node */ 9164 scsi_hba_tran_t *tran; 9165 char *addr; 9166 char *compat; 9167 9168 /* 9169 * See if the iport node already exists. 9170 */ 9171 addr = nameaddr + strlen("iport@"); 9172 if (child = ndi_devi_findchild(self, nameaddr)) { 9173 if (ndi_devi_device_isremoved(child)) { 9174 if ((se == SE_HP) || !ndi_dev_is_hotplug_node(child)) { 9175 if (ndi_devi_device_insert(child)) 9176 SCSI_HBA_LOG((_LOGCFG, self, NULL, 9177 "devinfo iport@%s device_reinsert", 9178 addr)); 9179 } else 9180 return (NULL); 9181 } 9182 return (child); 9183 } 9184 9185 9186 /* 9187 * If config based on scsi_hba_iportmap API, only allow create 9188 * from hotplug. 9189 */ 9190 tran = ndi_flavorv_get(self, SCSA_FLAVOR_SCSI_DEVICE); 9191 ASSERT(tran); 9192 if (tran->tran_iportmap && (se != SE_HP)) 9193 return (NULL); 9194 9195 /* allocate and initialize a new "iport" node */ 9196 ndi_devi_alloc_sleep(self, "iport", 9197 (se == SE_HP) ? DEVI_SID_HP_NODEID : DEVI_SID_NODEID, 9198 &child); 9199 ASSERT(child); 9200 /* 9201 * Set the flavor of the child to be IPORT flavored 9202 */ 9203 ndi_flavor_set(child, SCSA_FLAVOR_IPORT); 9204 9205 /* 9206 * Add the SCSI_ADDR_PROP_IPORTUA addressing property for this child. 9207 * This property is used to identify a iport node, and to represent the 9208 * nodes @addr form via node properties. 9209 * 9210 * Add "compatible" property to the "scsi-iport" node to cause it bind 9211 * to the same driver as the HBA driver. Use the "driver" name 9212 * instead of the "binding name" to distinguish from hw node. 9213 * 9214 * Give the HBA a chance, via tran_set_name_prop, to set additional 9215 * iport node properties or to change the "compatible" binding 9216 * prior to init_child. 9217 * 9218 * NOTE: the order of these operations is important so that 9219 * scsi_hba_iport works when called. 9220 */ 9221 compat = (char *)ddi_driver_name(self); 9222 if ((ndi_prop_update_string(DDI_DEV_T_NONE, child, 9223 SCSI_ADDR_PROP_IPORTUA, addr) != DDI_PROP_SUCCESS) || 9224 (ndi_prop_update_string_array(DDI_DEV_T_NONE, child, 9225 "compatible", &compat, 1) != DDI_PROP_SUCCESS) || 9226 ddi_pathname_obp_set(child, NULL) != DDI_SUCCESS) { 9227 SCSI_HBA_LOG((_LOG_NF(WARN), "%s failed dynamic decoration", 9228 nameaddr)); 9229 (void) ddi_remove_child(child, 0); 9230 child = NULL; 9231 } else { 9232 /* 9233 * Online/attach in order to get events so devfsadm will 9234 * create public names. 9235 */ 9236 ndi_hold_devi(child); 9237 if (ndi_devi_online(child, 0) != NDI_SUCCESS) { 9238 ndi_rele_devi(child); 9239 ndi_prop_remove_all(child); 9240 (void) ndi_devi_free(child); 9241 child = NULL; 9242 } else 9243 ndi_rele_devi(child); 9244 } 9245 9246 return (child); 9247 } 9248 9249 #ifdef sparc 9250 /* 9251 * Future: When iportmap boot support is added, consider rewriting this to 9252 * perform a scsi_hba_bus_config(BUS_CONFIG_ALL) on self (HBA) followed by 9253 * a scsi_hba_bus_config(BUS_CONFIG_ONE) on each child of self (each iport). 9254 */ 9255 /* ARGSUSED */ 9256 static int 9257 scsi_hba_bus_config_prom_node(dev_info_t *self, uint_t flags, 9258 void *arg, dev_info_t **childp) 9259 { 9260 char **iports; 9261 int circ, i; 9262 int ret = NDI_FAILURE; 9263 unsigned int num_iports = 0; 9264 dev_info_t *pdip = NULL; 9265 char *addr = NULL; 9266 9267 /* check to see if this is an HBA that defined scsi iports */ 9268 ret = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, self, 9269 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-iports", &iports, 9270 &num_iports); 9271 9272 if (ret != DDI_SUCCESS) { 9273 return (ret); 9274 } 9275 9276 ASSERT(num_iports > 0); 9277 9278 addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP); 9279 9280 ret = NDI_FAILURE; 9281 9282 scsi_hba_devi_enter(self, &circ); 9283 9284 /* create iport nodes for each scsi port/bus */ 9285 for (i = 0; i < num_iports; i++) { 9286 bzero(addr, SCSI_MAXNAMELEN); 9287 /* Prepend the iport name */ 9288 (void) snprintf(addr, SCSI_MAXNAMELEN, "iport@%s", 9289 iports[i]); 9290 if (pdip = scsi_hba_bus_config_port(self, addr, SE_BUSCONFIG)) { 9291 if (ndi_busop_bus_config(self, NDI_NO_EVENT, 9292 BUS_CONFIG_ONE, addr, &pdip, 0) != 9293 NDI_SUCCESS) { 9294 continue; 9295 } 9296 /* 9297 * Try to configure child under iport see wehter 9298 * request node is the child of the iport node 9299 */ 9300 if (ndi_devi_config_one(pdip, arg, childp, 9301 NDI_NO_EVENT) == NDI_SUCCESS) { 9302 ret = NDI_SUCCESS; 9303 break; 9304 } 9305 } 9306 } 9307 9308 scsi_hba_devi_exit(self, circ); 9309 9310 kmem_free(addr, SCSI_MAXNAMELEN); 9311 9312 ddi_prop_free(iports); 9313 9314 return (ret); 9315 } 9316 #endif 9317 9318 /* 9319 * Perform iport port/bus bus_config. 9320 */ 9321 static int 9322 scsi_hba_bus_config_iports(dev_info_t *self, uint_t flags, 9323 ddi_bus_config_op_t op, void *arg, dev_info_t **childp) 9324 { 9325 char *nameaddr, *addr; 9326 char **iports; 9327 int circ, i; 9328 int ret = NDI_FAILURE; 9329 unsigned int num_iports = 0; 9330 9331 /* check to see if this is an HBA that defined scsi iports */ 9332 ret = ddi_prop_lookup_string_array(DDI_DEV_T_ANY, self, 9333 DDI_PROP_DONTPASS | DDI_PROP_NOTPROM, "scsi-iports", &iports, 9334 &num_iports); 9335 9336 if (ret != DDI_SUCCESS) { 9337 return (ret); 9338 } 9339 9340 ASSERT(num_iports > 0); 9341 9342 scsi_hba_devi_enter(self, &circ); 9343 9344 switch (op) { 9345 case BUS_CONFIG_ONE: 9346 /* return if this operation is not against an iport node */ 9347 nameaddr = (char *)arg; 9348 if ((nameaddr == NULL) || 9349 (strncmp(nameaddr, "iport@", strlen("iport@")) != 0)) { 9350 ret = NDI_FAILURE; 9351 scsi_hba_devi_exit(self, circ); 9352 ddi_prop_free(iports); 9353 return (ret); 9354 } 9355 9356 /* parse the port number from "iport@%s" */ 9357 addr = nameaddr + strlen("iport@"); 9358 9359 /* check to see if this port was registered */ 9360 for (i = 0; i < num_iports; i++) { 9361 if (strcmp((iports[i]), addr) == 0) 9362 break; 9363 } 9364 9365 if (i == num_iports) { 9366 ret = NDI_FAILURE; 9367 break; 9368 } 9369 9370 /* create the iport node child */ 9371 if (scsi_hba_bus_config_port(self, nameaddr, SE_BUSCONFIG)) { 9372 ret = NDI_SUCCESS; 9373 } 9374 break; 9375 9376 case BUS_CONFIG_ALL: 9377 case BUS_CONFIG_DRIVER: 9378 addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP); 9379 /* create iport nodes for each scsi port/bus */ 9380 for (i = 0; i < num_iports; i++) { 9381 bzero(addr, SCSI_MAXNAMELEN); 9382 /* Prepend the iport name */ 9383 (void) snprintf(addr, SCSI_MAXNAMELEN, "iport@%s", 9384 iports[i]); 9385 (void) scsi_hba_bus_config_port(self, addr, 9386 SE_BUSCONFIG); 9387 } 9388 9389 kmem_free(addr, SCSI_MAXNAMELEN); 9390 ret = NDI_SUCCESS; 9391 break; 9392 } 9393 if (ret == NDI_SUCCESS) { 9394 #ifdef sparc 9395 /* 9396 * Mask NDI_PROMNAME since PROM doesn't have iport 9397 * node at all. 9398 */ 9399 flags &= (~NDI_PROMNAME); 9400 #endif 9401 flags |= NDI_MDI_FALLBACK; /* devinfo&pathinfo children */ 9402 ret = ndi_busop_bus_config(self, flags, op, 9403 arg, childp, 0); 9404 } 9405 scsi_hba_devi_exit(self, circ); 9406 9407 ddi_prop_free(iports); 9408 9409 return (ret); 9410 } 9411 9412 static int 9413 scsi_iportmap_config(void *arg, damap_t *mapp, damap_id_t tgtid) 9414 { 9415 dev_info_t *self = (dev_info_t *)arg; 9416 int circ; 9417 char nameaddr[SCSI_MAXNAMELEN]; 9418 char *iport_addr; 9419 dev_info_t *childp; 9420 9421 scsi_hba_devi_enter(self, &circ); 9422 9423 iport_addr = damap_id2addr(mapp, tgtid); 9424 SCSI_HBA_LOG((_LOGIPT, self, NULL, 9425 "%s @%s", damap_name(mapp), iport_addr)); 9426 9427 (void) snprintf(nameaddr, sizeof (nameaddr), "iport@%s", iport_addr); 9428 childp = scsi_hba_bus_config_port(self, nameaddr, SE_HP); 9429 scsi_hba_devi_exit(self, circ); 9430 return (childp != NULL ? DAM_SUCCESS : DAM_FAILURE); 9431 } 9432 9433 static int 9434 scsi_iportmap_unconfig(void *arg, damap_t *mapp, damap_id_t tgtid) 9435 { 9436 dev_info_t *self = arg; 9437 dev_info_t *childp; /* iport child of HBA node */ 9438 int circ, empty; 9439 char *addr; 9440 char nameaddr[SCSI_MAXNAMELEN]; 9441 scsi_hba_tran_t *tran; 9442 9443 addr = damap_id2addr(mapp, tgtid); 9444 SCSI_HBA_LOG((_LOGIPT, self, NULL, "%s @%s", damap_name(mapp), addr)); 9445 9446 (void) snprintf(nameaddr, sizeof (nameaddr), "iport@%s", addr); 9447 scsi_hba_devi_enter(self, &circ); 9448 if ((childp = ndi_devi_findchild(self, nameaddr)) == NULL) { 9449 scsi_hba_devi_exit(self, circ); 9450 return (DAM_FAILURE); 9451 } 9452 9453 tran = ddi_get_driver_private(childp); 9454 ASSERT(tran); 9455 9456 ndi_hold_devi(childp); 9457 scsi_hba_devi_exit(self, circ); 9458 9459 /* 9460 * A begin/end (clear) against the iport's 9461 * tgtmap will trigger unconfigure of all 9462 * targets on the iport. 9463 * 9464 * Future: This bit of code only works if the 9465 * target map reporting style is are full 9466 * reports and not per-address. Maybe we 9467 * should plan on handling this by 9468 * auto-unconfiguration when destroying the 9469 * target map(s). 9470 */ 9471 (void) scsi_hba_tgtmap_set_begin(tran->tran_tgtmap); 9472 (void) scsi_hba_tgtmap_set_end(tran->tran_tgtmap, 0); 9473 9474 /* wait for unconfigure */ 9475 (void) scsi_tgtmap_sync(tran->tran_tgtmap, 0); 9476 empty = scsi_tgtmap_is_empty(tran->tran_tgtmap); 9477 9478 scsi_hba_devi_enter(self, &circ); 9479 ndi_rele_devi(childp); 9480 9481 /* If begin/end/sync ends in empty map, offline/remove. */ 9482 if (empty) { 9483 if (ndi_devi_offline(childp, 9484 NDI_DEVFS_CLEAN | NDI_DEVI_REMOVE) == DDI_SUCCESS) { 9485 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 9486 "devinfo iport@%s offlined and removed", 9487 addr)); 9488 } else if (ndi_devi_device_remove(childp)) { 9489 /* Offline/rem failed, note new device_remove */ 9490 SCSI_HBA_LOG((_LOGUNCFG, self, NULL, 9491 "devinfo iport@%s offline failed, " 9492 "device_remove", addr)); 9493 } 9494 } 9495 scsi_hba_devi_exit(self, circ); 9496 return (empty ? DAM_SUCCESS : DAM_FAILURE); 9497 } 9498 9499 9500 int 9501 scsi_hba_iportmap_create(dev_info_t *self, int csync_usec, int settle_usec, 9502 scsi_hba_iportmap_t **handle) 9503 { 9504 scsi_hba_tran_t *tran; 9505 damap_t *mapp; 9506 char context[64]; 9507 impl_scsi_iportmap_t *iportmap; 9508 9509 if (self == NULL || csync_usec == 0 || 9510 settle_usec == 0 || handle == NULL) 9511 return (DDI_FAILURE); 9512 9513 *handle = NULL; 9514 9515 if (scsi_hba_iport_unit_address(self) != NULL) 9516 return (DDI_FAILURE); 9517 9518 tran = (scsi_hba_tran_t *)ddi_get_driver_private(self); 9519 ASSERT(tran); 9520 if (tran == NULL) 9521 return (DDI_FAILURE); 9522 9523 (void) snprintf(context, sizeof (context), "%s%d.iportmap", 9524 ddi_driver_name(self), ddi_get_instance(self)); 9525 9526 if (damap_create(context, DAMAP_REPORT_PERADDR, DAMAP_SERIALCONFIG, 9527 settle_usec, NULL, NULL, NULL, self, 9528 scsi_iportmap_config, scsi_iportmap_unconfig, &mapp) != 9529 DAM_SUCCESS) { 9530 return (DDI_FAILURE); 9531 } 9532 iportmap = kmem_zalloc(sizeof (*iportmap), KM_SLEEP); 9533 iportmap->iportmap_hba_dip = self; 9534 iportmap->iportmap_dam = mapp; 9535 9536 iportmap->iportmap_create_window = 1; /* start with window */ 9537 iportmap->iportmap_create_time = ddi_get_lbolt64(); 9538 iportmap->iportmap_create_csync_usec = csync_usec; 9539 iportmap->iportmap_settle_usec = settle_usec; 9540 iportmap->iportmap_sync_cnt = 0; 9541 9542 tran->tran_iportmap = (scsi_hba_iportmap_t *)iportmap; 9543 *handle = (scsi_hba_iportmap_t *)iportmap; 9544 9545 SCSI_HBA_LOG((_LOGIPT, self, NULL, "%s", damap_name(mapp))); 9546 return (DDI_SUCCESS); 9547 } 9548 9549 void 9550 scsi_hba_iportmap_destroy(scsi_hba_iportmap_t *handle) 9551 { 9552 impl_scsi_iportmap_t *iportmap = (impl_scsi_iportmap_t *)handle; 9553 dev_info_t *self = iportmap->iportmap_hba_dip; 9554 9555 SCSI_HBA_LOG((_LOGIPT, self, NULL, 9556 "%s", damap_name(iportmap->iportmap_dam))); 9557 9558 damap_destroy(iportmap->iportmap_dam); 9559 kmem_free(iportmap, sizeof (*iportmap)); 9560 } 9561 9562 int 9563 scsi_hba_iportmap_iport_add(scsi_hba_iportmap_t *handle, 9564 char *iport_addr, void *iport_priv) 9565 { 9566 impl_scsi_iportmap_t *iportmap = (impl_scsi_iportmap_t *)handle; 9567 dev_info_t *self = iportmap->iportmap_hba_dip; 9568 9569 SCSI_HBA_LOG((_LOGIPT, self, NULL, 9570 "%s @%s", damap_name(iportmap->iportmap_dam), iport_addr)); 9571 9572 return ((damap_addr_add(iportmap->iportmap_dam, iport_addr, NULL, 9573 NULL, iport_priv) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 9574 } 9575 9576 int 9577 scsi_hba_iportmap_iport_remove(scsi_hba_iportmap_t *handle, 9578 char *iport_addr) 9579 { 9580 impl_scsi_iportmap_t *iportmap = (impl_scsi_iportmap_t *)handle; 9581 dev_info_t *self = iportmap->iportmap_hba_dip; 9582 9583 SCSI_HBA_LOG((_LOGIPT, self, NULL, 9584 "%s @%s", damap_name(iportmap->iportmap_dam), iport_addr)); 9585 9586 return ((damap_addr_del(iportmap->iportmap_dam, 9587 iport_addr) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 9588 } 9589 9590 int 9591 scsi_hba_iportmap_lookup(scsi_hba_iportmap_t *handle, 9592 char *iport_addr) 9593 { 9594 impl_scsi_iportmap_t *iportmap = (impl_scsi_iportmap_t *)handle; 9595 dev_info_t *self = iportmap->iportmap_hba_dip; 9596 damap_id_t iportid; 9597 9598 iportid = damap_lookup(iportmap->iportmap_dam, iport_addr); 9599 if (iportid != NODAM) { 9600 SCSI_HBA_LOG((_LOG(3), self, NULL, 9601 "%s @%s found", 9602 damap_name(iportmap->iportmap_dam), iport_addr)); 9603 damap_id_rele(iportmap->iportmap_dam, iportid); 9604 return (DDI_SUCCESS); 9605 } 9606 9607 SCSI_HBA_LOG((_LOG(3), self, NULL, 9608 "%s @%s not found", 9609 damap_name(iportmap->iportmap_dam), iport_addr)); 9610 return (DDI_FAILURE); 9611 } 9612 9613 9614 static int 9615 scsi_lunmap_config(void *arg, damap_t *lundam, damap_id_t lunid) 9616 { 9617 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)arg; 9618 scsi_hba_tran_t *tran = tgtmap->tgtmap_tran; 9619 dev_info_t *self = tran->tran_iport_dip; 9620 char *addr; 9621 9622 addr = damap_id2addr(lundam, lunid); 9623 SCSI_HBA_LOG((_LOGLUN, self, NULL, 9624 "%s @%s", damap_name(lundam), addr)); 9625 if (scsi_hba_bus_configone_addr(self, addr, SE_HP) != NULL) 9626 return (DAM_SUCCESS); 9627 else 9628 return (DAM_FAILURE); 9629 } 9630 9631 static int 9632 scsi_lunmap_unconfig(void *arg, damap_t *lundam, damap_id_t lunid) 9633 { 9634 impl_scsi_tgtmap_t *tgtmap = (impl_scsi_tgtmap_t *)arg; 9635 scsi_hba_tran_t *tran = tgtmap->tgtmap_tran; 9636 dev_info_t *self = tran->tran_iport_dip; 9637 char *addr; 9638 9639 addr = damap_id2addr(lundam, lunid); 9640 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s @%s", damap_name(lundam), 9641 addr)); 9642 9643 scsi_hba_bus_unconfigone_addr(self, addr); 9644 return (DAM_SUCCESS); 9645 } 9646 9647 static int 9648 scsi_lunmap_create(dev_info_t *self, impl_scsi_tgtmap_t *tgtmap, char *taddr) 9649 { 9650 char context[64]; 9651 damap_t *tgtdam; 9652 damap_id_t tgtid; 9653 damap_t *lundam; 9654 int optflags; 9655 9656 (void) snprintf(context, sizeof (context), "%s%d.%s.lunmap", 9657 ddi_driver_name(self), ddi_get_instance(self), taddr); 9658 9659 tgtdam = tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]; 9660 tgtid = damap_lookup(tgtdam, taddr); 9661 if (tgtid == NODAM) { 9662 SCSI_HBA_LOG((_LOG(1), self, NULL, 9663 "target %s not found", context)); 9664 return (DDI_FAILURE); 9665 } 9666 9667 lundam = damap_id_priv_get(tgtdam, tgtid); 9668 if (lundam) { 9669 SCSI_HBA_LOG((_LOG(1), self, NULL, 9670 "lunmap %s already created", context)); 9671 damap_id_rele(tgtdam, tgtid); 9672 return (DDI_FAILURE); 9673 } 9674 9675 optflags = (ddi_prop_get_int(DDI_DEV_T_ANY, self, 9676 DDI_PROP_NOTPROM | DDI_PROP_DONTPASS, "scsi-enumeration", 9677 scsi_enumeration) & SCSI_ENUMERATION_MT_LUN_DISABLE) ? 9678 DAMAP_SERIALCONFIG : DAMAP_MTCONFIG; 9679 9680 /* NOTE: expected ref at tgtid/taddr: 2: caller + lookup. */ 9681 ASSERT(damap_id_ref(tgtdam, tgtid) == 2); 9682 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s creat, id %d ref %d", 9683 context, tgtid, damap_id_ref(tgtdam, tgtid))); 9684 9685 /* create lundam */ 9686 if (damap_create(context, DAMAP_REPORT_FULLSET, optflags, 1, 9687 NULL, NULL, NULL, tgtmap, scsi_lunmap_config, scsi_lunmap_unconfig, 9688 &lundam) != DAM_SUCCESS) { 9689 SCSI_HBA_LOG((_LOG(1), self, NULL, 9690 "%s create failed, id %d ref %d", 9691 context, tgtid, damap_id_ref(tgtdam, tgtid))); 9692 damap_id_rele(tgtdam, tgtid); 9693 return (DDI_FAILURE); 9694 } 9695 9696 /* 9697 * Return with damap_id_hold at tgtid/taddr from damap_lookup to 9698 * account for damap_id_prv_set below. 9699 */ 9700 damap_id_priv_set(tgtdam, tgtid, lundam); 9701 return (DDI_SUCCESS); 9702 } 9703 9704 static void 9705 scsi_lunmap_destroy(dev_info_t *self, impl_scsi_tgtmap_t *tgtmap, char *taddr) 9706 { 9707 char context[64]; 9708 damap_t *tgtdam; 9709 damap_id_t tgtid; 9710 damap_t *lundam; 9711 9712 (void) snprintf(context, sizeof (context), "%s%d.%s.lunmap", 9713 ddi_driver_name(self), ddi_get_instance(self), taddr); 9714 9715 tgtdam = tgtmap->tgtmap_dam[SCSI_TGT_SCSI_DEVICE]; 9716 tgtid = damap_lookup(tgtdam, taddr); 9717 if (tgtid == NODAM) { 9718 SCSI_HBA_LOG((_LOG(1), self, NULL, 9719 "target %s not found", context)); 9720 return; 9721 } 9722 9723 lundam = (damap_t *)damap_id_priv_get(tgtdam, tgtid); 9724 if (lundam == NULL) { 9725 damap_id_rele(tgtdam, tgtid); /* from damap_lookup */ 9726 SCSI_HBA_LOG((_LOG(1), self, NULL, 9727 "lunmap %s already destroyed", context)); 9728 return; 9729 } 9730 9731 /* NOTE: expected ref at tgtid/taddr: 3: priv_set + caller + lookup. */ 9732 ASSERT(damap_id_ref(tgtdam, tgtid) == 3); 9733 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s, id %d ref %d", 9734 damap_name(lundam), tgtid, damap_id_ref(tgtdam, tgtid))); 9735 9736 /* 9737 * A begin/end (clear) against a target's lunmap will trigger 9738 * unconfigure of all LUNs on the target. 9739 */ 9740 scsi_lunmap_set_begin(self, lundam); 9741 scsi_lunmap_set_end(self, lundam); 9742 9743 SCSI_HBA_LOG((_LOGLUN, self, NULL, 9744 "%s sync begin", damap_name(lundam))); 9745 9746 (void) damap_sync(lundam, 0); /* wait for unconfigure */ 9747 9748 SCSI_HBA_LOG((_LOGLUN, self, NULL, 9749 "%s sync end", damap_name(lundam))); 9750 9751 damap_id_priv_set(tgtdam, tgtid, NULL); 9752 9753 /* release hold established by damap_lookup above */ 9754 damap_id_rele(tgtdam, tgtid); 9755 9756 /* release hold established since scsi_lunmap_create() */ 9757 damap_id_rele(tgtdam, tgtid); 9758 9759 damap_destroy(lundam); 9760 } 9761 9762 static void 9763 scsi_lunmap_set_begin(dev_info_t *self, damap_t *lundam) 9764 { 9765 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s", damap_name(lundam))); 9766 9767 (void) damap_addrset_begin(lundam); 9768 } 9769 9770 static int 9771 scsi_lunmap_set_add(dev_info_t *self, damap_t *lundam, 9772 char *taddr, scsi_lun64_t lun64, int sfunc) 9773 { 9774 char ua[SCSI_MAXNAMELEN]; 9775 9776 /* make unit address string form of "@taddr,lun[,sfunc]" */ 9777 if (sfunc == -1) 9778 (void) snprintf(ua, sizeof (ua), "%s,%" PRIx64, taddr, lun64); 9779 else 9780 (void) snprintf(ua, sizeof (ua), "%s,%" PRIx64 ",%x", 9781 taddr, lun64, sfunc); 9782 9783 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s @%s", damap_name(lundam), ua)); 9784 9785 return ((damap_addrset_add(lundam, ua, NULL, NULL, 9786 NULL) == DAM_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE); 9787 } 9788 9789 static void 9790 scsi_lunmap_set_end(dev_info_t *self, damap_t *lundam) 9791 { 9792 SCSI_HBA_LOG((_LOGLUN, self, NULL, "%s", damap_name(lundam))); 9793 9794 (void) damap_addrset_end(lundam, 0); 9795 } 9796 9797 int 9798 scsi_lunmap_lookup(dev_info_t *self, damap_t *lundam, char *addr) 9799 { 9800 damap_id_t lunid; 9801 9802 if ((lunid = damap_lookup(lundam, addr)) != NODAM) { 9803 SCSI_HBA_LOG((_LOG(3), self, NULL, 9804 "%s @%s found", damap_name(lundam), addr)); 9805 damap_id_rele(lundam, lunid); 9806 return (DDI_SUCCESS); 9807 } 9808 9809 SCSI_HBA_LOG((_LOG(3), self, NULL, 9810 "%s @%s not found", damap_name(lundam), addr)); 9811 return (DDI_FAILURE); 9812 } 9813 9814 /* 9815 * phymap implementation 9816 * 9817 * We manage the timed aggregation of phys into a phy map * by creating a 9818 * SAS port construct (based upon 'name' of "local,remote" SAS addresses) 9819 * upon the first link up. As time goes on additional phys may join that port. 9820 * After an appropriate amount of settle time, we trigger the activation 9821 * callback which will then take the resultant bit mask of phys (phymask) in 9822 * the SAS port and use that to call back to the callback function 9823 * provided by the additional caller. 9824 * 9825 * We cross check to make sure that phys only exist in one SAS port at a 9826 * time by having soft state for each phy point back to the created 9827 * SAS port. 9828 * 9829 * NOTE: Make SAS_PHY_UA_LEN max(SAS_PHY_PHYMASK_LEN, SAS_PHY_NAME_LEN) 9830 * so we have enough space if sas_phymap_bitset2phymaskua phymask address 9831 * is already in use, and we end up using port name as unit address. 9832 */ 9833 #define SAS_PHY_NAME_FMT "%" PRIx64 ",%" PRIx64 9834 #define SAS_PHY_NAME_LEN (16 + 1 + 16 + 1) 9835 #define SAS_PHY_NPHY (SAS2_PHYNUM_MAX + 1) 9836 #define SAS_PHY_PHYMASK_LEN ((roundup(SAS_PHY_NPHY, 4)) / 4) 9837 #if (SAS_PHY_PHYMASK_LEN > SAS_PHY_NAME_LEN) 9838 #define SAS_PHY_UA_LEN SAS_PHY_PHYMASK_LEN 9839 #else 9840 #define SAS_PHY_UA_LEN SAS_PHY_NAME_LEN 9841 #endif 9842 typedef struct impl_sas_physet { /* needed for name2phys destroy */ 9843 struct impl_sas_physet *physet_next; 9844 char *physet_name; 9845 bitset_t *physet_phys; 9846 } impl_sas_physet_t; 9847 typedef struct impl_sas_phymap { 9848 dev_info_t *phymap_self; 9849 9850 kmutex_t phymap_lock; 9851 damap_t *phymap_dam; 9852 void *phymap_phy2name; 9853 ddi_soft_state_bystr *phymap_name2phys; /* bitset */ 9854 ddi_soft_state_bystr *phymap_name2ua; 9855 ddi_soft_state_bystr *phymap_ua2name; 9856 9857 /* Noisy phy information - ensure forward progress for noisy phys */ 9858 int phymap_phy_max; /* max phy# */ 9859 int phymap_reports; /* per period */ 9860 int phymap_reports_max; /* scales */ 9861 int phymap_phys_noisy; /* detected */ 9862 9863 /* These are for callbacks to the consumer. */ 9864 sas_phymap_activate_cb_t phymap_acp; 9865 sas_phymap_deactivate_cb_t phymap_dcp; 9866 void *phymap_private; 9867 9868 struct impl_sas_physet *phymap_physets; 9869 } impl_sas_phymap_t; 9870 9871 /* Detect noisy phy: max changes per stabilization period per phy. */ 9872 static int sas_phymap_phy_max_factor = 16; 9873 9874 /* 9875 * Convert bitset into a unit-address string. The maximum string length would 9876 * be the maximum number of phys, rounded up by 4 and divided by 4. 9877 */ 9878 static void 9879 sas_phymap_bitset2phymaskua(bitset_t *phys, char *buf) 9880 { 9881 char *ptr; 9882 int grp; 9883 int cur; 9884 uint_t bit; 9885 9886 bit = roundup(SAS_PHY_NPHY, 4); 9887 grp = 4; 9888 ptr = buf; 9889 cur = 0; 9890 do { 9891 bit -= 1; 9892 grp -= 1; 9893 if (bitset_in_set(phys, bit)) { 9894 cur |= (1 << grp); 9895 } 9896 if (grp == 0) { 9897 grp = 4; 9898 if (cur || ptr != buf) { 9899 *ptr++ = "0123456789abcdef"[cur]; 9900 *ptr = 0; 9901 } 9902 cur = 0; 9903 } 9904 } while (bit != 0); 9905 if (ptr == buf) { 9906 *ptr++ = '0'; 9907 *ptr = 0; 9908 } 9909 } 9910 9911 static int 9912 sas_phymap_config(void *arg, damap_t *phydam, damap_id_t phyid) 9913 { 9914 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)arg; 9915 char *context = damap_name(phymap->phymap_dam); 9916 char *damn; 9917 char *name; 9918 bitset_t *phys; 9919 char *ua; 9920 void *ua_priv; 9921 9922 ASSERT(context); 9923 9924 mutex_enter(&phymap->phymap_lock); 9925 phymap->phymap_reports = phymap->phymap_phys_noisy = 0; 9926 9927 /* Get the name ("local,remote" address string) from damap. */ 9928 damn = damap_id2addr(phydam, phyid); 9929 9930 /* Get the bitset of phys currently forming the port. */ 9931 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, damn); 9932 if (phys == NULL) { 9933 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: %s: no phys", 9934 context, damn)); 9935 mutex_exit(&phymap->phymap_lock); 9936 return (DAM_FAILURE); 9937 } 9938 9939 /* allocate, get, and initialize name index of name2ua map */ 9940 if (ddi_soft_state_bystr_zalloc(phymap->phymap_name2ua, damn) != 9941 DDI_SUCCESS) { 9942 SCSI_HBA_LOG((_LOG_NF(WARN), 9943 "%s: %s: failed name2ua alloc", context, damn)); 9944 mutex_exit(&phymap->phymap_lock); 9945 return (DAM_FAILURE); 9946 } 9947 if (!(ua = ddi_soft_state_bystr_get(phymap->phymap_name2ua, damn))) { 9948 SCSI_HBA_LOG((_LOG_NF(WARN), 9949 "%s: %s: no name2ua", context, damn)); 9950 mutex_exit(&phymap->phymap_lock); 9951 return (DAM_FAILURE); 9952 } 9953 sas_phymap_bitset2phymaskua(phys, ua); /* set ua */ 9954 9955 /* see if phymask ua index already allocated in ua2name map */ 9956 if (name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua)) { 9957 /* 9958 * The 'phymask' sas_phymap_bitset2phymaskua ua is 9959 * already in use. This means that original phys have 9960 * formed into a new port, and that the original port 9961 * still exists (it has migrated to some completely 9962 * different set of phys). In this corner-case we use 9963 * "local,remote" name as a 'temporary' unit address. 9964 * Reset ua in name2ua map. 9965 */ 9966 (void) strlcpy(ua, damn, SAS_PHY_NAME_LEN); 9967 name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua); 9968 if (name) { 9969 /* The "local,remote" ua should be new... */ 9970 SCSI_HBA_LOG((_LOG_NF(WARN), 9971 "%s: %s ua already configured", 9972 context, ua)); 9973 mutex_exit(&phymap->phymap_lock); 9974 return (DAM_SUCCESS); 9975 } 9976 } 9977 9978 /* allocate, get, and init ua index of ua2name map */ 9979 if (ddi_soft_state_bystr_zalloc(phymap->phymap_ua2name, ua) != 9980 DDI_SUCCESS) { 9981 ddi_soft_state_bystr_free(phymap->phymap_name2ua, damn); 9982 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: %s: failed ua2name alloc", 9983 context, damn)); 9984 mutex_exit(&phymap->phymap_lock); 9985 return (DAM_FAILURE); 9986 } 9987 name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua); 9988 if (name == NULL) { 9989 ddi_soft_state_bystr_free(phymap->phymap_name2ua, damn); 9990 SCSI_HBA_LOG((_LOG_NF(WARN), 9991 "%s: %s: no ua2name", context, ua)); 9992 mutex_exit(&phymap->phymap_lock); 9993 return (DAM_FAILURE); 9994 } 9995 9996 /* set name in ua2name map */ 9997 (void) strlcpy(name, damn, SAS_PHY_NAME_LEN); 9998 9999 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10000 "%s: %s: ua %s: activate", context, damn, ua)); 10001 10002 if (phymap->phymap_acp) { 10003 /* 10004 * drop our lock and invoke the activation callback 10005 */ 10006 mutex_exit(&phymap->phymap_lock); 10007 ua_priv = NULL; 10008 (phymap->phymap_acp)(phymap->phymap_private, ua, &ua_priv); 10009 mutex_enter(&phymap->phymap_lock); 10010 damap_id_priv_set(phydam, phyid, ua_priv); 10011 } 10012 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10013 "%s: %s: ua %s: activate complete", context, damn, ua)); 10014 mutex_exit(&phymap->phymap_lock); 10015 return (DAM_SUCCESS); 10016 } 10017 10018 /*ARGSUSED*/ 10019 static int 10020 sas_phymap_unconfig(void *arg, damap_t *phydam, damap_id_t phyid) 10021 { 10022 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)arg; 10023 char *context = damap_name(phymap->phymap_dam); 10024 char *damn; 10025 char *ua; 10026 void *ua_priv; 10027 10028 ASSERT(context); 10029 10030 mutex_enter(&phymap->phymap_lock); 10031 phymap->phymap_reports = phymap->phymap_phys_noisy = 0; 10032 10033 /* Get the name ("local,remote" address string) from damap. */ 10034 damn = damap_id2addr(phydam, phyid); 10035 10036 if (!(ua = ddi_soft_state_bystr_get(phymap->phymap_name2ua, damn))) { 10037 SCSI_HBA_LOG((_LOG_NF(WARN), 10038 "%s: %s: no name2ua", context, damn)); 10039 mutex_exit(&phymap->phymap_lock); 10040 return (DAM_FAILURE); 10041 } 10042 10043 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10044 "%s: %s: ua %s: deactivate", context, damn, ua)); 10045 if (phymap->phymap_dcp) { 10046 ua_priv = damap_id_priv_get(phydam, phyid); 10047 mutex_exit(&phymap->phymap_lock); 10048 (phymap->phymap_dcp)(phymap->phymap_private, ua, ua_priv); 10049 mutex_enter(&phymap->phymap_lock); 10050 } 10051 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10052 "%s: %s: ua %s: deactivate complete", context, damn, ua)); 10053 10054 /* delete ua<->name mappings */ 10055 ddi_soft_state_bystr_free(phymap->phymap_ua2name, ua); 10056 ddi_soft_state_bystr_free(phymap->phymap_name2ua, damn); 10057 mutex_exit(&phymap->phymap_lock); 10058 return (DAM_SUCCESS); 10059 } 10060 10061 int 10062 sas_phymap_create(dev_info_t *self, int settle_usec, 10063 sas_phymap_mode_t mode, void *mode_argument, void *phymap_priv, 10064 sas_phymap_activate_cb_t activate_cb, 10065 sas_phymap_deactivate_cb_t deactivate_cb, 10066 sas_phymap_t **handlep) 10067 { 10068 _NOTE(ARGUNUSED(mode_argument)); 10069 char context[64]; 10070 impl_sas_phymap_t *phymap; 10071 10072 if (self == NULL || settle_usec == 0 || handlep == NULL) 10073 return (DDI_FAILURE); 10074 10075 if (mode != PHYMAP_MODE_SIMPLE) 10076 return (DDI_FAILURE); 10077 10078 phymap = kmem_zalloc(sizeof (*phymap), KM_SLEEP); 10079 phymap->phymap_self = self; 10080 phymap->phymap_reports_max = 1 * sas_phymap_phy_max_factor; 10081 phymap->phymap_acp = activate_cb; 10082 phymap->phymap_dcp = deactivate_cb; 10083 phymap->phymap_private = phymap_priv; 10084 mutex_init(&phymap->phymap_lock, NULL, MUTEX_DRIVER, NULL); 10085 10086 (void) snprintf(context, sizeof (context), "%s%d.phymap", 10087 ddi_driver_name(self), ddi_get_instance(self)); 10088 SCSI_HBA_LOG((_LOGPHY, self, NULL, "%s", context)); 10089 10090 if (ddi_soft_state_init(&phymap->phymap_phy2name, 10091 SAS_PHY_NAME_LEN, SAS_PHY_NPHY) != 0) 10092 goto fail; 10093 if (ddi_soft_state_bystr_init(&phymap->phymap_name2phys, 10094 sizeof (bitset_t), SAS_PHY_NPHY) != 0) 10095 goto fail; 10096 10097 if (ddi_soft_state_bystr_init(&phymap->phymap_name2ua, 10098 SAS_PHY_UA_LEN, SAS_PHY_NPHY) != 0) 10099 goto fail; 10100 if (ddi_soft_state_bystr_init(&phymap->phymap_ua2name, 10101 SAS_PHY_NAME_LEN, SAS_PHY_NPHY) != 0) 10102 goto fail; 10103 10104 if (damap_create(context, DAMAP_REPORT_PERADDR, DAMAP_SERIALCONFIG, 10105 settle_usec, NULL, NULL, NULL, 10106 phymap, sas_phymap_config, sas_phymap_unconfig, 10107 &phymap->phymap_dam) != DAM_SUCCESS) 10108 goto fail; 10109 10110 10111 *handlep = (sas_phymap_t *)phymap; 10112 return (DDI_SUCCESS); 10113 10114 fail: sas_phymap_destroy((sas_phymap_t *)phymap); 10115 *handlep = NULL; 10116 return (DDI_FAILURE); 10117 } 10118 10119 void 10120 sas_phymap_destroy(sas_phymap_t *handle) 10121 { 10122 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10123 char *context; 10124 struct impl_sas_physet *physet, *nphyset; 10125 bitset_t *phys; 10126 char *name; 10127 10128 context = phymap->phymap_dam ? 10129 damap_name(phymap->phymap_dam) : "unknown"; 10130 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, "%s", context)); 10131 10132 if (phymap->phymap_dam) 10133 damap_destroy(phymap->phymap_dam); 10134 10135 /* free the bitsets of allocated physets */ 10136 for (physet = phymap->phymap_physets; physet; physet = nphyset) { 10137 nphyset = physet->physet_next; 10138 phys = physet->physet_phys; 10139 name = physet->physet_name; 10140 10141 if (phys) 10142 bitset_fini(phys); 10143 if (name) { 10144 ddi_soft_state_bystr_free( 10145 phymap->phymap_name2phys, name); 10146 strfree(name); 10147 } 10148 kmem_free(physet, sizeof (*physet)); 10149 } 10150 10151 /* free the maps */ 10152 if (phymap->phymap_ua2name) 10153 ddi_soft_state_bystr_fini(&phymap->phymap_ua2name); 10154 if (phymap->phymap_name2ua) 10155 ddi_soft_state_bystr_fini(&phymap->phymap_name2ua); 10156 10157 if (phymap->phymap_name2phys) 10158 ddi_soft_state_bystr_fini(&phymap->phymap_name2phys); 10159 if (phymap->phymap_phy2name) 10160 ddi_soft_state_fini(&phymap->phymap_phy2name); 10161 10162 mutex_destroy(&phymap->phymap_lock); 10163 kmem_free(phymap, sizeof (*phymap)); 10164 } 10165 10166 10167 int 10168 sas_phymap_phy_add(sas_phymap_t *handle, 10169 int phy, uint64_t local, uint64_t remote) 10170 { 10171 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10172 char *context = damap_name(phymap->phymap_dam); 10173 char port[SAS_PHY_NAME_LEN]; 10174 char *name; 10175 int phy2name_allocated = 0; 10176 bitset_t *phys; 10177 struct impl_sas_physet *physet; 10178 int rv; 10179 10180 /* Create the SAS port name from the local and remote addresses. */ 10181 (void) snprintf(port, SAS_PHY_NAME_LEN, SAS_PHY_NAME_FMT, 10182 local, remote); 10183 10184 mutex_enter(&phymap->phymap_lock); 10185 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, "%s: %s: add phy %d", 10186 context, port, phy)); 10187 10188 /* Check for conflict in phy2name map */ 10189 name = ddi_get_soft_state(phymap->phymap_phy2name, phy); 10190 if (name) { 10191 if (strcmp(name, port) != 0) 10192 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: %s: add phy %d: " 10193 "already in %s", context, port, phy, name)); 10194 else 10195 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: %s: add phy %d: " 10196 "duplicate add", context, port, phy)); 10197 mutex_exit(&phymap->phymap_lock); 10198 return (DDI_FAILURE); 10199 } 10200 10201 /* allocate, get, and initialize phy index of phy2name map */ 10202 if (ddi_soft_state_zalloc( 10203 phymap->phymap_phy2name, phy) != DDI_SUCCESS) { 10204 SCSI_HBA_LOG((_LOG_NF(WARN), 10205 "%s: %s: failed phy2name alloc", context, port)); 10206 goto fail; 10207 } 10208 name = ddi_get_soft_state(phymap->phymap_phy2name, phy); 10209 if (name == NULL) { 10210 SCSI_HBA_LOG((_LOG_NF(WARN), 10211 "%s: %s: no phy2name", context, port)); 10212 goto fail; 10213 } 10214 phy2name_allocated = 1; 10215 (void) strlcpy(name, port, SAS_PHY_NAME_LEN); /* set name */ 10216 10217 /* Find/alloc, initialize name index of name2phys map */ 10218 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, name); 10219 if (phys == NULL) { 10220 if (ddi_soft_state_bystr_zalloc(phymap->phymap_name2phys, 10221 name) != DDI_SUCCESS) { 10222 SCSI_HBA_LOG((_LOG_NF(WARN), 10223 "%s: %s: failed name2phys alloc", context, name)); 10224 goto fail; 10225 } 10226 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, name); 10227 if (phys == NULL) { 10228 SCSI_HBA_LOG((_LOG_NF(WARN), 10229 "%s: %s: no name2phys", context, name)); 10230 goto fail; 10231 } 10232 10233 /* Initialize bitset of phys. */ 10234 bitset_init(phys); 10235 bitset_resize(phys, SAS_PHY_NPHY); 10236 10237 /* Keep a list of information for destroy. */ 10238 physet = kmem_zalloc(sizeof (*physet), KM_SLEEP); 10239 physet->physet_name = strdup(name); 10240 physet->physet_phys = phys; 10241 physet->physet_next = phymap->phymap_physets; 10242 phymap->phymap_physets = physet; 10243 } 10244 ASSERT(phys); 10245 10246 /* Reflect 'add' in phys bitset. */ 10247 if (bitset_atomic_test_and_add(phys, phy) < 0) { 10248 /* It is an error if the phy was already recorded. */ 10249 SCSI_HBA_LOG((_LOG_NF(WARN), 10250 "%s: %s: phy bit %d already in port", context, name, phy)); 10251 goto fail; 10252 } 10253 10254 /* 10255 * Check to see if we have a new phy_max for this map, and if so 10256 * scale phymap_reports_max to the new number of phys. 10257 */ 10258 if (phy > phymap->phymap_phy_max) { 10259 phymap->phymap_phy_max = phy + 1; 10260 phymap->phymap_reports_max = phymap->phymap_phy_max * 10261 sas_phymap_phy_max_factor; 10262 } 10263 10264 /* 10265 * If we have not reached phymap_reports_max, start/restart the 10266 * activate timer. Otherwise, if phymap->phymap_reports add/rem reports 10267 * ever exceeds phymap_reports_max due to noisy phys, then report the 10268 * noise and force stabilization by stopping reports into the damap. 10269 * 10270 * The first config/unconfig callout out of the damap will reset 10271 * phymap->phymap_reports. 10272 */ 10273 rv = DDI_SUCCESS; 10274 if (phymap->phymap_reports++ < phymap->phymap_reports_max) { 10275 if (damap_addr_add(phymap->phymap_dam, name, 10276 NULL, NULL, NULL) == DAM_SUCCESS) { 10277 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10278 "%s: %s: damap_addr_add", context, name)); 10279 } else { 10280 SCSI_HBA_LOG((_LOG_NF(WARN), 10281 "%s: %s: damap_addr_add failed", context, name)); 10282 rv = DDI_FAILURE; 10283 } 10284 } else { 10285 phymap->phymap_phys_noisy++; 10286 if (phymap->phymap_phys_noisy == 1) 10287 SCSI_HBA_LOG((_LOG_NF(WARN), 10288 "%s: %s: noisy phys", context, name)); 10289 } 10290 mutex_exit(&phymap->phymap_lock); 10291 return (rv); 10292 10293 fail: if (phy2name_allocated) 10294 ddi_soft_state_free(phymap->phymap_phy2name, phy); 10295 mutex_exit(&phymap->phymap_lock); 10296 return (DDI_FAILURE); 10297 } 10298 10299 int 10300 sas_phymap_phy_rem(sas_phymap_t *handle, int phy) 10301 { 10302 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10303 char *context = damap_name(phymap->phymap_dam); 10304 char *name; 10305 bitset_t *phys; 10306 int rv = DDI_FAILURE; 10307 10308 ASSERT(context); 10309 10310 mutex_enter(&phymap->phymap_lock); 10311 phymap->phymap_reports++; 10312 10313 /* Find and free phy index of phy2name map */ 10314 name = ddi_get_soft_state(phymap->phymap_phy2name, phy); 10315 if (name == NULL) { 10316 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: rem phy %d: never added", 10317 context, phy)); 10318 goto fail; 10319 } 10320 /* NOTE: always free phy index of phy2name map before return... */ 10321 10322 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, "%s: %s: rem phy %d", 10323 context, name, phy)); 10324 10325 /* Get bitset of phys currently associated with named port. */ 10326 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, name); 10327 if (phys == NULL) { 10328 SCSI_HBA_LOG((_LOG_NF(WARN), "%s: %s: name2phys failed", 10329 context, name)); 10330 goto fail; 10331 } 10332 10333 /* Reflect 'rem' in phys bitset. */ 10334 if (bitset_atomic_test_and_del(phys, phy) < 0) { 10335 /* It is an error if the phy wasn't one of the port's phys. */ 10336 SCSI_HBA_LOG((_LOG_NF(WARN), 10337 "%s: %s: phy bit %d not in port", context, name, phy)); 10338 goto fail; 10339 } 10340 10341 /* If this was the last phy in the port, start the deactivate timer. */ 10342 if (bitset_is_null(phys) && 10343 (phymap->phymap_reports++ < phymap->phymap_reports_max)) { 10344 if (damap_addr_del(phymap->phymap_dam, name) == DAM_SUCCESS) { 10345 SCSI_HBA_LOG((_LOGPHY, phymap->phymap_self, NULL, 10346 "%s: %s: damap_addr_del", context, name)); 10347 } else { 10348 SCSI_HBA_LOG((_LOG_NF(WARN), 10349 "%s: %s: damap_addr_del failure", context, name)); 10350 goto fail; 10351 } 10352 } 10353 rv = DDI_SUCCESS; 10354 10355 /* free phy index of phy2name map */ 10356 fail: if (name) 10357 ddi_soft_state_free(phymap->phymap_phy2name, phy); /* free */ 10358 mutex_exit(&phymap->phymap_lock); 10359 return (rv); 10360 } 10361 10362 char * 10363 sas_phymap_lookup_ua(sas_phymap_t *handle, uint64_t local, uint64_t remote) 10364 { 10365 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10366 char *context = damap_name(phymap->phymap_dam); 10367 char name[SAS_PHY_NAME_LEN]; 10368 char *ua; 10369 10370 ASSERT(context); 10371 10372 (void) snprintf(name, SAS_PHY_NAME_LEN, SAS_PHY_NAME_FMT, 10373 local, remote); 10374 10375 mutex_enter(&phymap->phymap_lock); 10376 ua = ddi_soft_state_bystr_get(phymap->phymap_name2ua, name); 10377 SCSI_HBA_LOG((_LOG(3), phymap->phymap_self, NULL, 10378 "%s: %s: ua %s", context, name, ua ? ua : "NULL")); 10379 mutex_exit(&phymap->phymap_lock); 10380 return (ua); 10381 } 10382 10383 void * 10384 sas_phymap_lookup_uapriv(sas_phymap_t *handle, char *ua) 10385 { 10386 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10387 char *context = damap_name(phymap->phymap_dam); 10388 char *name; 10389 damap_id_t phyid; 10390 void *ua_priv = NULL; 10391 10392 ASSERT(context); 10393 10394 mutex_enter(&phymap->phymap_lock); 10395 name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua); 10396 if (name) { 10397 phyid = damap_lookup(phymap->phymap_dam, name); 10398 if (phyid != NODAM) { 10399 ua_priv = damap_id_priv_get(phymap->phymap_dam, phyid); 10400 damap_id_rele(phymap->phymap_dam, phyid); 10401 } 10402 } 10403 10404 SCSI_HBA_LOG((_LOG(3), phymap->phymap_self, NULL, 10405 "%s: %s: ua %s ua_priv %p", context, name, 10406 ua ? ua : "NULL", ua_priv)); 10407 mutex_exit(&phymap->phymap_lock); 10408 return (ua_priv); 10409 } 10410 10411 int 10412 sas_phymap_uahasphys(sas_phymap_t *handle, char *ua) 10413 { 10414 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10415 char *name; 10416 bitset_t *phys; 10417 int n = 0; 10418 10419 mutex_enter(&phymap->phymap_lock); 10420 name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua); 10421 if (name) { 10422 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, name); 10423 if (phys) 10424 n = bitset_is_null(phys) ? 0 : 1; 10425 } 10426 mutex_exit(&phymap->phymap_lock); 10427 return (n); 10428 } 10429 10430 sas_phymap_phys_t * 10431 sas_phymap_ua2phys(sas_phymap_t *handle, char *ua) 10432 { 10433 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10434 char *name; 10435 bitset_t *phys; 10436 bitset_t *cphys = NULL; 10437 10438 mutex_enter(&phymap->phymap_lock); 10439 name = ddi_soft_state_bystr_get(phymap->phymap_ua2name, ua); 10440 if (name == NULL) 10441 goto fail; 10442 10443 phys = ddi_soft_state_bystr_get(phymap->phymap_name2phys, name); 10444 if (phys == NULL) 10445 goto fail; 10446 10447 /* dup the phys and return */ 10448 cphys = kmem_alloc(sizeof (*cphys), KM_SLEEP); 10449 bitset_init(cphys); 10450 bitset_resize(cphys, SAS_PHY_NPHY); 10451 bitset_copy(phys, cphys); 10452 10453 fail: mutex_exit(&phymap->phymap_lock); 10454 return ((sas_phymap_phys_t *)cphys); 10455 } 10456 10457 int 10458 sas_phymap_phys_next(sas_phymap_phys_t *phys) 10459 { 10460 bitset_t *cphys = (bitset_t *)phys; 10461 int phy; 10462 10463 phy = bitset_find(cphys); 10464 if (phy != -1) 10465 bitset_del(cphys, phy); 10466 return (phy); 10467 } 10468 10469 void 10470 sas_phymap_phys_free(sas_phymap_phys_t *phys) 10471 { 10472 bitset_t *cphys = (bitset_t *)phys; 10473 10474 if (cphys) { 10475 bitset_fini(cphys); 10476 kmem_free(cphys, sizeof (*cphys)); 10477 } 10478 } 10479 10480 char * 10481 sas_phymap_phy2ua(sas_phymap_t *handle, int phy) 10482 { 10483 impl_sas_phymap_t *phymap = (impl_sas_phymap_t *)handle; 10484 char *name; 10485 char *ua; 10486 char *rua = NULL; 10487 10488 mutex_enter(&phymap->phymap_lock); 10489 name = ddi_get_soft_state(phymap->phymap_phy2name, phy); 10490 if (name == NULL) 10491 goto fail; 10492 ua = ddi_soft_state_bystr_get(phymap->phymap_name2ua, name); 10493 if (ua == NULL) 10494 goto fail; 10495 10496 /* dup the ua and return */ 10497 rua = strdup(ua); 10498 10499 fail: mutex_exit(&phymap->phymap_lock); 10500 return (rua); 10501 } 10502 10503 void 10504 sas_phymap_ua_free(char *ua) 10505 { 10506 if (ua) 10507 strfree(ua); 10508 } 10509