1 /* $OpenBSD: qle.c,v 1.31 2014/07/13 23:10:23 deraadt Exp $ */ 2 3 /* 4 * Copyright (c) 2013, 2014 Jonathan Matthew <jmatthew@openbsd.org> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19 #include "bio.h" 20 21 #include <sys/param.h> 22 #include <sys/systm.h> 23 #include <sys/kernel.h> 24 #include <sys/malloc.h> 25 #include <sys/device.h> 26 #include <sys/sensors.h> 27 #include <sys/rwlock.h> 28 #include <sys/task.h> 29 30 #include <machine/atomic.h> 31 #include <machine/bus.h> 32 33 #include <dev/pci/pcireg.h> 34 #include <dev/pci/pcivar.h> 35 #include <dev/pci/pcidevs.h> 36 37 #ifdef __sparc64__ 38 #include <dev/ofw/openfirm.h> 39 #endif 40 41 #include <scsi/scsi_all.h> 42 #include <scsi/scsiconf.h> 43 44 #include <dev/pci/qlereg.h> 45 46 #ifdef QLE_DEBUG 47 #define DPRINTF(m, f...) do { if ((qledebug & (m)) == (m)) printf(f); } \ 48 while (0) 49 #define QLE_D_MBOX 0x01 50 #define QLE_D_INTR 0x02 51 #define QLE_D_PORT 0x04 52 #define QLE_D_IO 0x08 53 #define QLE_D_IOCB 0x10 54 int qledebug = QLE_D_PORT; 55 #else 56 #define DPRINTF(m, f...) 57 #endif 58 59 #ifndef QLE_NOFIRMWARE 60 #include <dev/microcode/isp/asm_2400.h> 61 #include <dev/microcode/isp/asm_2500.h> 62 #endif 63 64 #define QLE_PCI_MEM_BAR 0x14 65 #define QLE_PCI_IO_BAR 0x10 66 67 68 #define QLE_DEFAULT_PORT_NAME 0x400000007F000003ULL /* from isp(4) */ 69 70 #define QLE_WAIT_FOR_LOOP 10 71 72 /* rounded up range of assignable handles */ 73 #define QLE_MAX_TARGETS 2048 74 75 /* maximum number of segments allowed for in a single io */ 76 #define QLE_MAX_SEGS 16 77 78 enum qle_isp_gen { 79 QLE_GEN_ISP24XX = 1, 80 QLE_GEN_ISP25XX 81 }; 82 83 enum qle_isp_type { 84 QLE_ISP2422 = 1, 85 QLE_ISP2432, 86 QLE_ISP2512, 87 QLE_ISP2522, 88 QLE_ISP2532 89 }; 90 91 /* port database things */ 92 #define QLE_SCRATCH_SIZE 0x1000 93 94 enum qle_port_disp { 95 QLE_PORT_DISP_NEW, 96 QLE_PORT_DISP_GONE, 97 QLE_PORT_DISP_SAME, 98 QLE_PORT_DISP_CHANGED, 99 QLE_PORT_DISP_MOVED, 100 QLE_PORT_DISP_DUP 101 }; 102 103 #define QLE_LOCATION_LOOP (1 << 24) 104 #define QLE_LOCATION_FABRIC (2 << 24) 105 #define QLE_LOCATION_LOOP_ID(l) (l | QLE_LOCATION_LOOP) 106 #define QLE_LOCATION_PORT_ID(p) (p | QLE_LOCATION_FABRIC) 107 108 struct qle_fc_port { 109 TAILQ_ENTRY(qle_fc_port) ports; 110 TAILQ_ENTRY(qle_fc_port) update; 111 112 u_int64_t node_name; 113 u_int64_t port_name; 114 u_int32_t location; /* port id or loop id */ 115 116 int flags; 117 #define QLE_PORT_FLAG_IS_TARGET 1 118 #define QLE_PORT_FLAG_NEEDS_LOGIN 2 119 120 u_int32_t portid; 121 u_int16_t loopid; 122 }; 123 124 125 /* request/response queue stuff */ 126 #define QLE_QUEUE_ENTRY_SIZE 64 127 128 struct qle_ccb { 129 struct qle_softc *ccb_sc; 130 int ccb_id; 131 struct scsi_xfer *ccb_xs; 132 133 bus_dmamap_t ccb_dmamap; 134 135 struct qle_iocb_seg *ccb_segs; 136 u_int64_t ccb_seg_offset; 137 138 SIMPLEQ_ENTRY(qle_ccb) ccb_link; 139 }; 140 141 SIMPLEQ_HEAD(qle_ccb_list, qle_ccb); 142 143 struct qle_dmamem { 144 bus_dmamap_t qdm_map; 145 bus_dma_segment_t qdm_seg; 146 size_t qdm_size; 147 caddr_t qdm_kva; 148 }; 149 #define QLE_DMA_MAP(_qdm) ((_qdm)->qdm_map) 150 #define QLE_DMA_LEN(_qdm) ((_qdm)->qdm_size) 151 #define QLE_DMA_DVA(_qdm) ((u_int64_t)(_qdm)->qdm_map->dm_segs[0].ds_addr) 152 #define QLE_DMA_KVA(_qdm) ((void *)(_qdm)->qdm_kva) 153 154 struct qle_softc { 155 struct device sc_dev; 156 157 pci_chipset_tag_t sc_pc; 158 pcitag_t sc_tag; 159 160 void *sc_ih; 161 bus_space_tag_t sc_iot; 162 bus_space_handle_t sc_ioh; 163 bus_size_t sc_ios; 164 bus_dma_tag_t sc_dmat; 165 166 struct scsi_link sc_link; 167 168 struct scsibus_softc *sc_scsibus; 169 170 enum qle_isp_type sc_isp_type; 171 enum qle_isp_gen sc_isp_gen; 172 int sc_port; 173 174 bus_space_handle_t sc_mbox_ioh; 175 u_int16_t sc_mbox[QLE_MBOX_COUNT]; 176 int sc_mbox_pending; 177 struct mutex sc_mbox_mtx; 178 179 int sc_loop_up; 180 int sc_topology; 181 int sc_loop_id; 182 int sc_port_id; 183 int sc_loop_max_id; 184 u_int64_t sc_sns_port_name; 185 186 struct mutex sc_port_mtx; 187 TAILQ_HEAD(, qle_fc_port) sc_ports; 188 TAILQ_HEAD(, qle_fc_port) sc_ports_new; 189 TAILQ_HEAD(, qle_fc_port) sc_ports_gone; 190 TAILQ_HEAD(, qle_fc_port) sc_ports_found; 191 struct qle_fc_port *sc_targets[QLE_MAX_TARGETS]; 192 193 struct taskq *sc_update_taskq; 194 struct task sc_update_task; 195 int sc_update; 196 int sc_update_tasks; 197 #define QLE_UPDATE_TASK_CLEAR_ALL 0x00000001 198 #define QLE_UPDATE_TASK_SOFTRESET 0x00000002 199 #define QLE_UPDATE_TASK_UPDATE_TOPO 0x00000004 200 #define QLE_UPDATE_TASK_GET_PORT_LIST 0x00000008 201 #define QLE_UPDATE_TASK_PORT_LIST 0x00000010 202 #define QLE_UPDATE_TASK_SCAN_FABRIC 0x00000020 203 #define QLE_UPDATE_TASK_SCANNING_FABRIC 0x00000040 204 #define QLE_UPDATE_TASK_FABRIC_LOGIN 0x00000080 205 #define QLE_UPDATE_TASK_FABRIC_RELOGIN 0x00000100 206 #define QLE_UPDATE_TASK_DETACH_TARGET 0x00000200 207 #define QLE_UPDATE_TASK_ATTACH_TARGET 0x00000400 208 209 int sc_maxcmds; 210 struct qle_dmamem *sc_requests; 211 struct qle_dmamem *sc_responses; 212 struct qle_dmamem *sc_segments; 213 struct qle_dmamem *sc_pri_requests; 214 struct qle_dmamem *sc_scratch; 215 struct qle_dmamem *sc_fcp_cmnds; 216 struct qle_ccb *sc_ccbs; 217 struct qle_ccb_list sc_ccb_free; 218 struct mutex sc_ccb_mtx; 219 struct mutex sc_queue_mtx; 220 struct scsi_iopool sc_iopool; 221 u_int32_t sc_next_req_id; 222 u_int32_t sc_last_resp_id; 223 int sc_marker_required; 224 int sc_fabric_pending; 225 u_int8_t sc_fabric_response[QLE_QUEUE_ENTRY_SIZE]; 226 227 struct qle_nvram sc_nvram; 228 int sc_nvram_valid; 229 }; 230 #define DEVNAME(_sc) ((_sc)->sc_dev.dv_xname) 231 232 int qle_intr(void *); 233 234 int qle_match(struct device *, void *, void *); 235 void qle_attach(struct device *, struct device *, void *); 236 int qle_detach(struct device *, int); 237 238 struct cfattach qle_ca = { 239 sizeof(struct qle_softc), 240 qle_match, 241 qle_attach, 242 qle_detach 243 }; 244 245 struct cfdriver qle_cd = { 246 NULL, 247 "qle", 248 DV_DULL 249 }; 250 251 void qle_scsi_cmd(struct scsi_xfer *); 252 int qle_scsi_probe(struct scsi_link *); 253 254 255 struct scsi_adapter qle_switch = { 256 qle_scsi_cmd, 257 scsi_minphys, 258 qle_scsi_probe, 259 NULL, /* scsi_free */ 260 NULL /* ioctl */ 261 }; 262 263 u_int32_t qle_read(struct qle_softc *, int); 264 void qle_write(struct qle_softc *, int, u_int32_t); 265 void qle_host_cmd(struct qle_softc *sc, u_int32_t); 266 267 int qle_mbox(struct qle_softc *, int); 268 int qle_ct_pass_through(struct qle_softc *sc, 269 u_int32_t port_handle, struct qle_dmamem *mem, 270 size_t req_size, size_t resp_size); 271 void qle_mbox_putaddr(u_int16_t *, struct qle_dmamem *); 272 u_int16_t qle_read_mbox(struct qle_softc *, int); 273 void qle_write_mbox(struct qle_softc *, int, u_int16_t); 274 275 void qle_handle_intr(struct qle_softc *, u_int16_t, u_int16_t); 276 void qle_set_ints(struct qle_softc *, int); 277 int qle_read_isr(struct qle_softc *, u_int16_t *, u_int16_t *); 278 void qle_clear_isr(struct qle_softc *, u_int16_t); 279 280 void qle_put_marker(struct qle_softc *, void *); 281 void qle_put_cmd(struct qle_softc *, void *, struct scsi_xfer *, 282 struct qle_ccb *, u_int32_t); 283 struct qle_ccb *qle_handle_resp(struct qle_softc *, u_int32_t); 284 void qle_sge(struct qle_iocb_seg *, u_int64_t, u_int32_t); 285 286 struct qle_fc_port *qle_next_fabric_port(struct qle_softc *, u_int32_t *, 287 u_int32_t *); 288 int qle_get_port_db(struct qle_softc *, u_int16_t, 289 struct qle_dmamem *); 290 int qle_get_port_name_list(struct qle_softc *sc, u_int32_t); 291 int qle_add_loop_port(struct qle_softc *, struct qle_fc_port *); 292 int qle_add_fabric_port(struct qle_softc *, struct qle_fc_port *); 293 int qle_add_logged_in_port(struct qle_softc *, u_int16_t, 294 u_int32_t); 295 int qle_classify_port(struct qle_softc *, u_int32_t, u_int64_t, 296 u_int64_t, struct qle_fc_port **); 297 int qle_get_loop_id(struct qle_softc *sc, int); 298 void qle_clear_port_lists(struct qle_softc *); 299 int qle_softreset(struct qle_softc *); 300 void qle_update_topology(struct qle_softc *); 301 int qle_update_fabric(struct qle_softc *); 302 int qle_fabric_plogx(struct qle_softc *, struct qle_fc_port *, int, 303 u_int32_t *); 304 int qle_fabric_plogi(struct qle_softc *, struct qle_fc_port *); 305 void qle_fabric_plogo(struct qle_softc *, struct qle_fc_port *); 306 307 void qle_update_start(struct qle_softc *, int); 308 void qle_update_done(struct qle_softc *, int); 309 void qle_do_update(void *, void *); 310 int qle_async(struct qle_softc *, u_int16_t); 311 312 int qle_load_fwchunk(struct qle_softc *, 313 struct qle_dmamem *, const u_int32_t *); 314 u_int32_t qle_read_ram_word(struct qle_softc *, u_int32_t); 315 int qle_verify_firmware(struct qle_softc *, u_int32_t); 316 int qle_load_firmware_chunks(struct qle_softc *, const u_int32_t *); 317 int qle_read_nvram(struct qle_softc *); 318 319 struct qle_dmamem *qle_dmamem_alloc(struct qle_softc *, size_t); 320 void qle_dmamem_free(struct qle_softc *, struct qle_dmamem *); 321 322 int qle_alloc_ccbs(struct qle_softc *); 323 void qle_free_ccbs(struct qle_softc *); 324 void *qle_get_ccb(void *); 325 void qle_put_ccb(void *, void *); 326 327 void qle_dump_stuff(struct qle_softc *, void *, int); 328 void qle_dump_iocb(struct qle_softc *, void *); 329 void qle_dump_iocb_segs(struct qle_softc *, void *, int); 330 331 static const struct pci_matchid qle_devices[] = { 332 { PCI_VENDOR_QLOGIC, PCI_PRODUCT_QLOGIC_ISP2422 }, 333 { PCI_VENDOR_QLOGIC, PCI_PRODUCT_QLOGIC_ISP2432 }, 334 { PCI_VENDOR_QLOGIC, PCI_PRODUCT_QLOGIC_ISP2512 }, 335 { PCI_VENDOR_QLOGIC, PCI_PRODUCT_QLOGIC_ISP2522 }, 336 { PCI_VENDOR_QLOGIC, PCI_PRODUCT_QLOGIC_ISP2532 }, 337 }; 338 339 int 340 qle_match(struct device *parent, void *match, void *aux) 341 { 342 return (pci_matchbyid(aux, qle_devices, nitems(qle_devices))); 343 } 344 345 void 346 qle_attach(struct device *parent, struct device *self, void *aux) 347 { 348 struct qle_softc *sc = (void *)self; 349 struct pci_attach_args *pa = aux; 350 pci_intr_handle_t ih; 351 const char *intrstr; 352 u_int32_t pcictl; 353 struct scsibus_attach_args saa; 354 struct qle_init_cb *icb; 355 bus_size_t mbox_base; 356 u_int32_t firmware_addr; 357 #ifndef QLE_NOFIRMWARE 358 const u_int32_t *firmware = NULL; 359 #endif 360 361 pcireg_t bars[] = { QLE_PCI_MEM_BAR, QLE_PCI_IO_BAR }; 362 pcireg_t memtype; 363 int r, i, rv; 364 365 sc->sc_pc = pa->pa_pc; 366 sc->sc_tag = pa->pa_tag; 367 sc->sc_ih = NULL; 368 sc->sc_dmat = pa->pa_dmat; 369 sc->sc_ios = 0; 370 371 for (r = 0; r < nitems(bars); r++) { 372 memtype = pci_mapreg_type(sc->sc_pc, sc->sc_tag, bars[r]); 373 if (pci_mapreg_map(pa, bars[r], memtype, 0, 374 &sc->sc_iot, &sc->sc_ioh, NULL, &sc->sc_ios, 0) == 0) 375 break; 376 377 sc->sc_ios = 0; 378 } 379 if (sc->sc_ios == 0) { 380 printf(": unable to map registers\n"); 381 return; 382 } 383 384 if (pci_intr_map_msi(pa, &ih) != 0 && pci_intr_map(pa, &ih) != 0) { 385 printf(": unable to map interrupt\n"); 386 goto unmap; 387 } 388 intrstr = pci_intr_string(sc->sc_pc, ih); 389 sc->sc_ih = pci_intr_establish(sc->sc_pc, ih, IPL_BIO, 390 qle_intr, sc, DEVNAME(sc)); 391 if (sc->sc_ih == NULL) { 392 printf(": unable to establish interrupt"); 393 if (intrstr != NULL) 394 printf(" at %s", intrstr); 395 printf("\n"); 396 goto deintr; 397 } 398 399 printf(": %s\n", intrstr); 400 401 pcictl = pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_COMMAND_STATUS_REG); 402 pcictl |= PCI_COMMAND_INVALIDATE_ENABLE | 403 PCI_COMMAND_PARITY_ENABLE | PCI_COMMAND_SERR_ENABLE; 404 pci_conf_write(pa->pa_pc, pa->pa_tag, PCI_COMMAND_STATUS_REG, pcictl); 405 406 pcictl = pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_BHLC_REG); 407 pcictl &= ~(PCI_LATTIMER_MASK << PCI_LATTIMER_SHIFT); 408 pcictl &= ~(PCI_CACHELINE_MASK << PCI_CACHELINE_SHIFT); 409 pcictl |= (0x80 << PCI_LATTIMER_SHIFT); 410 pcictl |= (0x10 << PCI_CACHELINE_SHIFT); 411 pci_conf_write(pa->pa_pc, pa->pa_tag, PCI_BHLC_REG, pcictl); 412 413 pcictl = pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_ROM_REG); 414 pcictl &= ~1; 415 pci_conf_write(pa->pa_pc, pa->pa_tag, PCI_ROM_REG, pcictl); 416 417 switch (PCI_PRODUCT(pa->pa_id)) { 418 case PCI_PRODUCT_QLOGIC_ISP2422: 419 sc->sc_isp_type = QLE_ISP2422; 420 sc->sc_isp_gen = QLE_GEN_ISP24XX; 421 break; 422 case PCI_PRODUCT_QLOGIC_ISP2432: 423 sc->sc_isp_type = QLE_ISP2432; 424 sc->sc_isp_gen = QLE_GEN_ISP24XX; 425 break; 426 case PCI_PRODUCT_QLOGIC_ISP2512: 427 sc->sc_isp_type = QLE_ISP2512; 428 sc->sc_isp_gen = QLE_GEN_ISP25XX; 429 break; 430 case PCI_PRODUCT_QLOGIC_ISP2522: 431 sc->sc_isp_type = QLE_ISP2522; 432 sc->sc_isp_gen = QLE_GEN_ISP25XX; 433 break; 434 case PCI_PRODUCT_QLOGIC_ISP2532: 435 sc->sc_isp_type = QLE_ISP2532; 436 sc->sc_isp_gen = QLE_GEN_ISP25XX; 437 break; 438 439 default: 440 printf("unknown pci id %x", pa->pa_id); 441 goto deintr; 442 } 443 444 /* these are the same for 24xx and 25xx but may vary later */ 445 mbox_base = QLE_MBOX_BASE_24XX; 446 firmware_addr = QLE_2400_CODE_ORG; 447 448 if (bus_space_subregion(sc->sc_iot, sc->sc_ioh, mbox_base, 449 sizeof(sc->sc_mbox), &sc->sc_mbox_ioh) != 0) { 450 printf("%s: unable to map mbox registers\n", DEVNAME(sc)); 451 goto deintr; 452 } 453 454 sc->sc_port = pa->pa_function; 455 456 TAILQ_INIT(&sc->sc_ports); 457 TAILQ_INIT(&sc->sc_ports_new); 458 TAILQ_INIT(&sc->sc_ports_gone); 459 TAILQ_INIT(&sc->sc_ports_found); 460 461 /* after reset, mbox regs 1 and 2 contain the string "ISP " */ 462 if (qle_read_mbox(sc, 1) != 0x4953 || 463 qle_read_mbox(sc, 2) != 0x5020) { 464 /* try releasing the risc processor */ 465 printf("%s: bad startup mboxes: %x %x\n", DEVNAME(sc), 466 qle_read_mbox(sc, 1), qle_read_mbox(sc, 2)); 467 qle_host_cmd(sc, QLE_HOST_CMD_RELEASE); 468 } 469 470 qle_host_cmd(sc, QLE_HOST_CMD_PAUSE); 471 if (qle_softreset(sc) != 0) { 472 printf("softreset failed\n"); 473 goto deintr; 474 } 475 476 if (qle_read_nvram(sc) == 0) 477 sc->sc_nvram_valid = 1; 478 479 #ifdef QLE_NOFIRMWARE 480 if (qle_verify_firmware(sc, firmware_addr)) { 481 printf("%s: no firmware loaded\n", DEVNAME(sc)); 482 goto deintr; 483 } 484 #else 485 switch (sc->sc_isp_gen) { 486 case QLE_GEN_ISP24XX: 487 firmware = isp_2400_risc_code; 488 break; 489 case QLE_GEN_ISP25XX: 490 firmware = isp_2500_risc_code; 491 break; 492 default: 493 printf("%s: no firmware to load?\n", DEVNAME(sc)); 494 goto deintr; 495 } 496 if (qle_load_firmware_chunks(sc, firmware)) { 497 printf("%s: firmware load failed\n", DEVNAME(sc)); 498 goto deintr; 499 } 500 #endif 501 502 /* execute firmware */ 503 sc->sc_mbox[0] = QLE_MBOX_EXEC_FIRMWARE; 504 sc->sc_mbox[1] = firmware_addr >> 16; 505 sc->sc_mbox[2] = firmware_addr & 0xffff; 506 #ifdef QLE_NOFIRMWARE 507 sc->sc_mbox[3] = 1; 508 #else 509 sc->sc_mbox[3] = 0; 510 #endif 511 sc->sc_mbox[4] = 0; 512 if (qle_mbox(sc, 0x001f)) { 513 printf("ISP couldn't exec firmware: %x\n", sc->sc_mbox[0]); 514 goto deintr; 515 } 516 517 delay(250000); /* from isp(4) */ 518 519 sc->sc_mbox[0] = QLE_MBOX_ABOUT_FIRMWARE; 520 if (qle_mbox(sc, 0x0001)) { 521 printf("ISP not talking after firmware exec: %x\n", 522 sc->sc_mbox[0]); 523 goto deintr; 524 } 525 printf("%s: firmware rev %d.%d.%d, attrs 0x%x\n", DEVNAME(sc), 526 sc->sc_mbox[1], sc->sc_mbox[2], sc->sc_mbox[3], sc->sc_mbox[6]); 527 528 sc->sc_maxcmds = 4096; 529 530 /* reserve queue slots for markers and fabric ops */ 531 sc->sc_maxcmds -= 2; 532 533 if (qle_alloc_ccbs(sc)) { 534 /* error already printed */ 535 goto deintr; 536 } 537 sc->sc_scratch = qle_dmamem_alloc(sc, QLE_SCRATCH_SIZE); 538 if (sc->sc_scratch == NULL) { 539 printf("%s: unable to allocate scratch\n", DEVNAME(sc)); 540 goto free_ccbs; 541 } 542 543 /* build init buffer thing */ 544 icb = (struct qle_init_cb *)QLE_DMA_KVA(sc->sc_scratch); 545 memset(icb, 0, sizeof(*icb)); 546 icb->icb_version = QLE_ICB_VERSION; 547 if (sc->sc_nvram_valid) { 548 icb->icb_max_frame_len = sc->sc_nvram.frame_payload_size; 549 icb->icb_exec_throttle = sc->sc_nvram.execution_throttle; 550 icb->icb_hardaddr = sc->sc_nvram.hard_address; 551 icb->icb_portname = sc->sc_nvram.port_name; 552 icb->icb_nodename = sc->sc_nvram.node_name; 553 icb->icb_login_retry = sc->sc_nvram.login_retry; 554 icb->icb_login_timeout = sc->sc_nvram.login_timeout; 555 icb->icb_fwoptions1 = sc->sc_nvram.fwoptions1; 556 icb->icb_fwoptions2 = sc->sc_nvram.fwoptions2; 557 icb->icb_fwoptions3 = sc->sc_nvram.fwoptions3; 558 } else { 559 /* defaults copied from isp(4) */ 560 htolem16(&icb->icb_max_frame_len, 1024); 561 htolem16(&icb->icb_exec_throttle, 16); 562 icb->icb_portname = htobe64(QLE_DEFAULT_PORT_NAME); 563 icb->icb_nodename = 0; 564 icb->icb_login_retry = 3; 565 566 htolem32(&icb->icb_fwoptions1, QLE_ICB_FW1_FAIRNESS | 567 QLE_ICB_FW1_HARD_ADDR | QLE_ICB_FW1_FULL_DUPLEX); 568 htolem32(&icb->icb_fwoptions2, QLE_ICB_FW2_LOOP_PTP); 569 htolem32(&icb->icb_fwoptions3, QLE_ICB_FW3_FCP_RSP_24_0 | 570 QLE_ICB_FW3_AUTONEG); 571 } 572 573 icb->icb_exchange_count = 0; 574 575 icb->icb_req_out = 0; 576 icb->icb_resp_in = 0; 577 icb->icb_pri_req_out = 0; 578 htolem16(&icb->icb_req_queue_len, sc->sc_maxcmds); 579 htolem16(&icb->icb_resp_queue_len, sc->sc_maxcmds); 580 htolem16(&icb->icb_pri_req_queue_len, 8); /* apparently the minimum */ 581 htolem32(&icb->icb_req_queue_addr_lo, 582 QLE_DMA_DVA(sc->sc_requests)); 583 htolem32(&icb->icb_req_queue_addr_hi, 584 QLE_DMA_DVA(sc->sc_requests) >> 32); 585 htolem32(&icb->icb_resp_queue_addr_lo, 586 QLE_DMA_DVA(sc->sc_responses)); 587 htolem32(&icb->icb_resp_queue_addr_hi, 588 QLE_DMA_DVA(sc->sc_responses) >> 32); 589 htolem32(&icb->icb_pri_req_queue_addr_lo, 590 QLE_DMA_DVA(sc->sc_pri_requests)); 591 htolem32(&icb->icb_pri_req_queue_addr_hi, 592 QLE_DMA_DVA(sc->sc_pri_requests) >> 32); 593 594 htolem16(&icb->icb_link_down_nos, 200); 595 icb->icb_int_delay = 0; 596 icb->icb_login_timeout = 0; 597 598 sc->sc_mbox[0] = QLE_MBOX_INIT_FIRMWARE; 599 sc->sc_mbox[4] = 0; 600 sc->sc_mbox[5] = 0; 601 qle_mbox_putaddr(sc->sc_mbox, sc->sc_scratch); 602 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 603 sizeof(*icb), BUS_DMASYNC_PREWRITE); 604 rv = qle_mbox(sc, 0x00fd); 605 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 606 sizeof(*icb), BUS_DMASYNC_POSTWRITE); 607 608 if (rv != 0) { 609 printf("%s: ISP firmware init failed: %x\n", DEVNAME(sc), 610 sc->sc_mbox[0]); 611 goto free_scratch; 612 } 613 614 /* enable some more notifications */ 615 sc->sc_mbox[0] = QLE_MBOX_SET_FIRMWARE_OPTIONS; 616 sc->sc_mbox[1] = QLE_FW_OPTION1_ASYNC_LIP_F8 | 617 QLE_FW_OPTION1_ASYNC_LIP_RESET | 618 QLE_FW_OPTION1_ASYNC_LIP_ERROR | 619 QLE_FW_OPTION1_ASYNC_LOGIN_RJT; 620 sc->sc_mbox[2] = 0; 621 sc->sc_mbox[3] = 0; 622 if (qle_mbox(sc, 0x000f)) { 623 printf("%s: setting firmware options failed: %x\n", 624 DEVNAME(sc), sc->sc_mbox[0]); 625 goto free_scratch; 626 } 627 628 sc->sc_update_taskq = taskq_create(DEVNAME(sc), 1, IPL_BIO); 629 task_set(&sc->sc_update_task, qle_do_update, sc, NULL); 630 631 /* wait a bit for link to come up so we can scan and attach devices */ 632 for (i = 0; i < QLE_WAIT_FOR_LOOP * 10000; i++) { 633 u_int16_t isr, info; 634 635 delay(100); 636 637 if (qle_read_isr(sc, &isr, &info) == 0) 638 continue; 639 640 qle_handle_intr(sc, isr, info); 641 642 if (sc->sc_loop_up) 643 break; 644 } 645 646 if (sc->sc_loop_up) { 647 qle_do_update(sc, NULL); 648 } else { 649 DPRINTF(QLE_D_PORT, "%s: loop still down, giving up\n", 650 DEVNAME(sc)); 651 } 652 653 /* we should be good to go now, attach scsibus */ 654 sc->sc_link.adapter = &qle_switch; 655 sc->sc_link.adapter_softc = sc; 656 sc->sc_link.adapter_target = QLE_MAX_TARGETS; 657 sc->sc_link.adapter_buswidth = QLE_MAX_TARGETS; 658 sc->sc_link.openings = sc->sc_maxcmds; 659 sc->sc_link.pool = &sc->sc_iopool; 660 if (sc->sc_nvram_valid) { 661 sc->sc_link.port_wwn = betoh64(sc->sc_nvram.port_name); 662 sc->sc_link.node_wwn = betoh64(sc->sc_nvram.node_name); 663 } else { 664 sc->sc_link.port_wwn = QLE_DEFAULT_PORT_NAME; 665 sc->sc_link.node_wwn = 0; 666 } 667 if (sc->sc_link.node_wwn == 0) { 668 /* 669 * mask out the port number from the port name to get 670 * the node name. 671 */ 672 sc->sc_link.node_wwn = sc->sc_link.port_wwn; 673 sc->sc_link.node_wwn &= ~(0xfULL << 56); 674 } 675 676 memset(&saa, 0, sizeof(saa)); 677 saa.saa_sc_link = &sc->sc_link; 678 679 /* config_found() returns the scsibus attached to us */ 680 sc->sc_scsibus = (struct scsibus_softc *)config_found(&sc->sc_dev, 681 &saa, scsiprint); 682 683 return; 684 685 free_scratch: 686 qle_dmamem_free(sc, sc->sc_scratch); 687 free_ccbs: 688 qle_free_ccbs(sc); 689 deintr: 690 pci_intr_disestablish(sc->sc_pc, sc->sc_ih); 691 sc->sc_ih = NULL; 692 unmap: 693 bus_space_unmap(sc->sc_iot, sc->sc_ioh, sc->sc_ios); 694 sc->sc_ios = 0; 695 } 696 697 int 698 qle_detach(struct device *self, int flags) 699 { 700 struct qle_softc *sc = (struct qle_softc *)self; 701 702 if (sc->sc_ih == NULL) { 703 /* we didnt attach properly, so nothing to detach */ 704 return (0); 705 } 706 707 pci_intr_disestablish(sc->sc_pc, sc->sc_ih); 708 sc->sc_ih = NULL; 709 710 bus_space_unmap(sc->sc_iot, sc->sc_ioh, sc->sc_ios); 711 sc->sc_ios = 0; 712 713 return (0); 714 } 715 716 int 717 qle_classify_port(struct qle_softc *sc, u_int32_t location, 718 u_int64_t port_name, u_int64_t node_name, struct qle_fc_port **prev) 719 { 720 struct qle_fc_port *port, *locmatch, *wwnmatch; 721 locmatch = NULL; 722 wwnmatch = NULL; 723 724 /* make sure we don't try to add a port or location twice */ 725 TAILQ_FOREACH(port, &sc->sc_ports_new, update) { 726 if ((port->port_name == port_name && 727 port->node_name == node_name) || 728 port->location == location) { 729 *prev = port; 730 return (QLE_PORT_DISP_DUP); 731 } 732 } 733 734 /* if we're attaching, everything is new */ 735 if (sc->sc_scsibus == NULL) { 736 *prev = NULL; 737 return (QLE_PORT_DISP_NEW); 738 } 739 740 TAILQ_FOREACH(port, &sc->sc_ports, ports) { 741 if (port->location == location) 742 locmatch = port; 743 744 if (port->port_name == port_name && 745 port->node_name == node_name) 746 wwnmatch = port; 747 } 748 749 if (locmatch == NULL && wwnmatch == NULL) { 750 *prev = NULL; 751 return (QLE_PORT_DISP_NEW); 752 } else if (locmatch == wwnmatch) { 753 *prev = locmatch; 754 return (QLE_PORT_DISP_SAME); 755 } else if (wwnmatch != NULL) { 756 *prev = wwnmatch; 757 return (QLE_PORT_DISP_MOVED); 758 } else { 759 *prev = locmatch; 760 return (QLE_PORT_DISP_CHANGED); 761 } 762 } 763 764 int 765 qle_get_loop_id(struct qle_softc *sc, int start) 766 { 767 int i, last; 768 769 i = QLE_MIN_HANDLE; 770 last = QLE_MAX_HANDLE; 771 if (i < start) 772 i = start; 773 774 for (; i <= last; i++) { 775 if (sc->sc_targets[i] == NULL) 776 return (i); 777 } 778 779 return (-1); 780 } 781 782 int 783 qle_get_port_db(struct qle_softc *sc, u_int16_t loopid, struct qle_dmamem *mem) 784 { 785 sc->sc_mbox[0] = QLE_MBOX_GET_PORT_DB; 786 sc->sc_mbox[1] = loopid; 787 qle_mbox_putaddr(sc->sc_mbox, mem); 788 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, 789 sizeof(struct qle_get_port_db), BUS_DMASYNC_PREREAD); 790 if (qle_mbox(sc, 0x00cf)) { 791 DPRINTF(QLE_D_PORT, "%s: get port db for %d failed: %x\n", 792 DEVNAME(sc), loopid, sc->sc_mbox[0]); 793 return (1); 794 } 795 796 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, 797 sizeof(struct qle_get_port_db), BUS_DMASYNC_POSTREAD); 798 return (0); 799 } 800 801 int 802 qle_get_port_name_list(struct qle_softc *sc, u_int32_t match) 803 { 804 struct qle_port_name_list *l; 805 struct qle_fc_port *port; 806 int i; 807 808 sc->sc_mbox[0] = QLE_MBOX_GET_PORT_NAME_LIST; 809 sc->sc_mbox[1] = 0; 810 sc->sc_mbox[8] = QLE_DMA_LEN(sc->sc_scratch); 811 sc->sc_mbox[9] = 0; 812 qle_mbox_putaddr(sc->sc_mbox, sc->sc_scratch); 813 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 814 QLE_DMA_LEN(sc->sc_scratch), BUS_DMASYNC_PREREAD); 815 if (qle_mbox(sc, 0x03cf)) { 816 DPRINTF(QLE_D_PORT, "%s: get port name list failed: %x\n", 817 DEVNAME(sc), sc->sc_mbox[0]); 818 return (1); 819 } 820 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 821 sc->sc_mbox[1], BUS_DMASYNC_POSTREAD); 822 823 i = 0; 824 l = QLE_DMA_KVA(sc->sc_scratch); 825 mtx_enter(&sc->sc_port_mtx); 826 while (i * sizeof(*l) < sc->sc_mbox[1]) { 827 u_int16_t loopid; 828 u_int32_t loc; 829 830 loopid = lemtoh16(&l[i].loopid) & 0xfff; 831 /* skip special ports */ 832 switch (loopid) { 833 case QLE_F_PORT_HANDLE: 834 case QLE_SNS_HANDLE: 835 case QLE_FABRIC_CTRL_HANDLE: 836 case QLE_IP_BCAST_HANDLE: 837 loc = 0; 838 break; 839 default: 840 if (loopid <= sc->sc_loop_max_id) { 841 loc = QLE_LOCATION_LOOP_ID(loopid); 842 } else { 843 /* 844 * we don't have the port id here, so just 845 * indicate it's a fabric port. 846 */ 847 loc = QLE_LOCATION_FABRIC; 848 } 849 break; 850 } 851 852 if (match & loc) { 853 port = malloc(sizeof(*port), M_DEVBUF, M_ZERO | 854 M_NOWAIT); 855 if (port == NULL) { 856 printf("%s: failed to allocate port struct\n", 857 DEVNAME(sc)); 858 break; 859 } 860 port->location = loc; 861 port->loopid = loopid; 862 port->port_name = letoh64(l[i].port_name); 863 DPRINTF(QLE_D_PORT, "%s: loop id %d, port name %llx\n", 864 DEVNAME(sc), port->loopid, port->port_name); 865 TAILQ_INSERT_TAIL(&sc->sc_ports_found, port, update); 866 } 867 i++; 868 } 869 mtx_leave(&sc->sc_port_mtx); 870 871 return (0); 872 } 873 874 int 875 qle_add_loop_port(struct qle_softc *sc, struct qle_fc_port *port) 876 { 877 struct qle_get_port_db *pdb; 878 struct qle_fc_port *pport; 879 int disp; 880 881 if (qle_get_port_db(sc, port->loopid, sc->sc_scratch) != 0) { 882 return (1); 883 } 884 pdb = QLE_DMA_KVA(sc->sc_scratch); 885 886 if (lemtoh16(&pdb->prli_svc_word3) & QLE_SVC3_TARGET_ROLE) 887 port->flags |= QLE_PORT_FLAG_IS_TARGET; 888 889 port->port_name = betoh64(pdb->port_name); 890 port->node_name = betoh64(pdb->node_name); 891 port->portid = (pdb->port_id[0] << 16) | (pdb->port_id[1] << 8) | 892 pdb->port_id[2]; 893 894 mtx_enter(&sc->sc_port_mtx); 895 disp = qle_classify_port(sc, port->location, port->port_name, 896 port->node_name, &pport); 897 switch (disp) { 898 case QLE_PORT_DISP_CHANGED: 899 case QLE_PORT_DISP_MOVED: 900 case QLE_PORT_DISP_NEW: 901 TAILQ_INSERT_TAIL(&sc->sc_ports_new, port, update); 902 sc->sc_targets[port->loopid] = port; 903 break; 904 case QLE_PORT_DISP_DUP: 905 free(port, M_DEVBUF, 0); 906 break; 907 case QLE_PORT_DISP_SAME: 908 TAILQ_REMOVE(&sc->sc_ports_gone, pport, update); 909 free(port, M_DEVBUF, 0); 910 break; 911 } 912 mtx_leave(&sc->sc_port_mtx); 913 914 switch (disp) { 915 case QLE_PORT_DISP_CHANGED: 916 case QLE_PORT_DISP_MOVED: 917 case QLE_PORT_DISP_NEW: 918 DPRINTF(QLE_D_PORT, "%s: %s %d; name %llx\n", 919 DEVNAME(sc), ISSET(port->flags, QLE_PORT_FLAG_IS_TARGET) ? 920 "target" : "non-target", port->loopid, 921 betoh64(pdb->port_name)); 922 break; 923 default: 924 break; 925 } 926 return (0); 927 } 928 929 int 930 qle_add_fabric_port(struct qle_softc *sc, struct qle_fc_port *port) 931 { 932 struct qle_get_port_db *pdb; 933 934 if (qle_get_port_db(sc, port->loopid, sc->sc_scratch) != 0) { 935 free(port, M_DEVBUF, 0); 936 return (1); 937 } 938 pdb = QLE_DMA_KVA(sc->sc_scratch); 939 940 if (lemtoh16(&pdb->prli_svc_word3) & QLE_SVC3_TARGET_ROLE) 941 port->flags |= QLE_PORT_FLAG_IS_TARGET; 942 943 /* 944 * if we only know about this port because qle_get_port_name_list 945 * returned it, we don't have its port id or node name, so fill 946 * those in and update its location. 947 */ 948 if (port->location == QLE_LOCATION_FABRIC) { 949 port->node_name = betoh64(pdb->node_name); 950 port->port_name = betoh64(pdb->port_name); 951 port->portid = (pdb->port_id[0] << 16) | 952 (pdb->port_id[1] << 8) | pdb->port_id[2]; 953 port->location = QLE_LOCATION_PORT_ID(port->portid); 954 } 955 956 mtx_enter(&sc->sc_port_mtx); 957 TAILQ_INSERT_TAIL(&sc->sc_ports_new, port, update); 958 sc->sc_targets[port->loopid] = port; 959 mtx_leave(&sc->sc_port_mtx); 960 961 DPRINTF(QLE_D_PORT, "%s: %s %d; name %llx\n", 962 DEVNAME(sc), ISSET(port->flags, QLE_PORT_FLAG_IS_TARGET) ? 963 "target" : "non-target", port->loopid, port->port_name); 964 return (0); 965 } 966 967 int 968 qle_add_logged_in_port(struct qle_softc *sc, u_int16_t loopid, 969 u_int32_t portid) 970 { 971 struct qle_fc_port *port; 972 struct qle_get_port_db *pdb; 973 u_int64_t node_name, port_name; 974 int flags, ret; 975 976 ret = qle_get_port_db(sc, loopid, sc->sc_scratch); 977 mtx_enter(&sc->sc_port_mtx); 978 if (ret != 0) { 979 /* put in a fake port to prevent use of this loop id */ 980 printf("%s: loop id %d used, but can't see what's using it\n", 981 DEVNAME(sc), loopid); 982 node_name = 0; 983 port_name = 0; 984 flags = 0; 985 } else { 986 pdb = QLE_DMA_KVA(sc->sc_scratch); 987 node_name = betoh64(pdb->node_name); 988 port_name = betoh64(pdb->port_name); 989 flags = 0; 990 if (lemtoh16(&pdb->prli_svc_word3) & QLE_SVC3_TARGET_ROLE) 991 flags |= QLE_PORT_FLAG_IS_TARGET; 992 993 /* see if we've already found this port */ 994 TAILQ_FOREACH(port, &sc->sc_ports_found, update) { 995 if ((port->node_name == node_name) && 996 (port->port_name == port_name) && 997 (port->portid == portid)) { 998 mtx_leave(&sc->sc_port_mtx); 999 DPRINTF(QLE_D_PORT, "%s: already found port " 1000 "%06x\n", DEVNAME(sc), portid); 1001 return (0); 1002 } 1003 } 1004 } 1005 1006 port = malloc(sizeof(*port), M_DEVBUF, M_ZERO | M_NOWAIT); 1007 if (port == NULL) { 1008 mtx_leave(&sc->sc_port_mtx); 1009 printf("%s: failed to allocate a port structure\n", 1010 DEVNAME(sc)); 1011 return (1); 1012 } 1013 port->location = QLE_LOCATION_PORT_ID(portid); 1014 port->port_name = port_name; 1015 port->node_name = node_name; 1016 port->loopid = loopid; 1017 port->portid = portid; 1018 port->flags = flags; 1019 1020 TAILQ_INSERT_TAIL(&sc->sc_ports, port, ports); 1021 sc->sc_targets[port->loopid] = port; 1022 mtx_leave(&sc->sc_port_mtx); 1023 1024 DPRINTF(QLE_D_PORT, "%s: added logged in port %06x at %d\n", 1025 DEVNAME(sc), portid, loopid); 1026 return (0); 1027 } 1028 1029 struct qle_ccb * 1030 qle_handle_resp(struct qle_softc *sc, u_int32_t id) 1031 { 1032 struct qle_ccb *ccb; 1033 struct qle_iocb_status *status; 1034 struct qle_iocb_req6 *req; 1035 struct scsi_xfer *xs; 1036 u_int32_t handle; 1037 u_int16_t completion; 1038 u_int8_t *entry; 1039 u_int8_t *data; 1040 1041 ccb = NULL; 1042 entry = QLE_DMA_KVA(sc->sc_responses) + (id * QLE_QUEUE_ENTRY_SIZE); 1043 1044 bus_dmamap_sync(sc->sc_dmat, 1045 QLE_DMA_MAP(sc->sc_responses), id * QLE_QUEUE_ENTRY_SIZE, 1046 QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_POSTREAD); 1047 1048 qle_dump_iocb(sc, entry); 1049 switch(entry[0]) { 1050 case QLE_IOCB_STATUS: 1051 status = (struct qle_iocb_status *)entry; 1052 handle = status->handle; 1053 if (handle > sc->sc_maxcmds) { 1054 panic("bad completed command handle: %d (> %d)", 1055 handle, sc->sc_maxcmds); 1056 } 1057 1058 ccb = &sc->sc_ccbs[handle]; 1059 xs = ccb->ccb_xs; 1060 if (xs == NULL) { 1061 DPRINTF(QLE_D_IO, "%s: got status for inactive ccb %d\n", 1062 DEVNAME(sc), handle); 1063 ccb = NULL; 1064 break; 1065 } 1066 if (xs->io != ccb) { 1067 panic("completed command handle doesn't match xs " 1068 "(handle %d, ccb %p, xs->io %p)", handle, ccb, 1069 xs->io); 1070 } 1071 qle_dump_iocb(sc, status); 1072 1073 if (xs->datalen > 0) { 1074 if (ccb->ccb_dmamap->dm_nsegs > 1075 QLE_IOCB_SEGS_PER_CMD) { 1076 bus_dmamap_sync(sc->sc_dmat, 1077 QLE_DMA_MAP(sc->sc_segments), 1078 ccb->ccb_seg_offset, 1079 sizeof(*ccb->ccb_segs) * 1080 ccb->ccb_dmamap->dm_nsegs, 1081 BUS_DMASYNC_POSTWRITE); 1082 } 1083 1084 bus_dmamap_sync(sc->sc_dmat, ccb->ccb_dmamap, 0, 1085 ccb->ccb_dmamap->dm_mapsize, 1086 (xs->flags & SCSI_DATA_IN) ? BUS_DMASYNC_POSTREAD : 1087 BUS_DMASYNC_POSTWRITE); 1088 bus_dmamap_unload(sc->sc_dmat, ccb->ccb_dmamap); 1089 } 1090 1091 xs->status = lemtoh16(&status->scsi_status) & 0x0f; 1092 completion = lemtoh16(&status->completion); 1093 switch (completion) { 1094 case QLE_IOCB_STATUS_DATA_OVERRUN: 1095 case QLE_IOCB_STATUS_DATA_UNDERRUN: 1096 case QLE_IOCB_STATUS_COMPLETE: 1097 if (completion == QLE_IOCB_STATUS_COMPLETE) { 1098 xs->resid = 0; 1099 } else { 1100 xs->resid = lemtoh32(&status->resid); 1101 } 1102 1103 if (lemtoh16(&status->scsi_status) & 1104 QLE_SCSI_STATUS_SENSE_VALID) { 1105 u_int32_t *pp; 1106 int sr; 1107 data = status->data + 1108 lemtoh32(&status->fcp_rsp_len); 1109 memcpy(&xs->sense, data, 1110 lemtoh32(&status->fcp_sense_len)); 1111 xs->error = XS_SENSE; 1112 pp = (u_int32_t *)&xs->sense; 1113 for (sr = 0; sr < sizeof(xs->sense)/4; sr++) { 1114 pp[sr] = swap32(pp[sr]); 1115 } 1116 } else { 1117 xs->error = XS_NOERROR; 1118 } 1119 break; 1120 1121 case QLE_IOCB_STATUS_DMA_ERROR: 1122 DPRINTF(QLE_D_IO, "%s: dma error\n", DEVNAME(sc)); 1123 /* set resid apparently? */ 1124 break; 1125 1126 case QLE_IOCB_STATUS_RESET: 1127 DPRINTF(QLE_D_IO, "%s: reset destroyed command\n", 1128 DEVNAME(sc)); 1129 sc->sc_marker_required = 1; 1130 xs->error = XS_RESET; 1131 break; 1132 1133 case QLE_IOCB_STATUS_ABORTED: 1134 DPRINTF(QLE_D_IO, "%s: aborted\n", DEVNAME(sc)); 1135 sc->sc_marker_required = 1; 1136 xs->error = XS_DRIVER_STUFFUP; 1137 break; 1138 1139 case QLE_IOCB_STATUS_TIMEOUT: 1140 DPRINTF(QLE_D_IO, "%s: command timed out\n", 1141 DEVNAME(sc)); 1142 xs->error = XS_TIMEOUT; 1143 break; 1144 1145 case QLE_IOCB_STATUS_QUEUE_FULL: 1146 DPRINTF(QLE_D_IO, "%s: queue full\n", DEVNAME(sc)); 1147 xs->error = XS_BUSY; 1148 break; 1149 1150 case QLE_IOCB_STATUS_PORT_UNAVAIL: 1151 case QLE_IOCB_STATUS_PORT_LOGGED_OUT: 1152 case QLE_IOCB_STATUS_PORT_CHANGED: 1153 DPRINTF(QLE_D_IO, "%s: dev gone\n", DEVNAME(sc)); 1154 xs->error = XS_SELTIMEOUT; 1155 /* mark port as needing relogin? */ 1156 break; 1157 1158 default: 1159 DPRINTF(QLE_D_IO, "%s: unexpected completion status " 1160 "%x\n", DEVNAME(sc), status->completion); 1161 xs->error = XS_DRIVER_STUFFUP; 1162 break; 1163 } 1164 break; 1165 1166 case QLE_IOCB_STATUS_CONT: 1167 DPRINTF(QLE_D_IO, "%s: ignoring status continuation iocb\n", 1168 DEVNAME(sc)); 1169 break; 1170 1171 case QLE_IOCB_PLOGX: 1172 case QLE_IOCB_CT_PASSTHROUGH: 1173 if (sc->sc_fabric_pending) { 1174 qle_dump_iocb(sc, entry); 1175 memcpy(sc->sc_fabric_response, entry, 1176 QLE_QUEUE_ENTRY_SIZE); 1177 sc->sc_fabric_pending = 2; 1178 wakeup(sc->sc_scratch); 1179 } else { 1180 DPRINTF(QLE_D_IO, "%s: unexpected fabric response %x\n", 1181 DEVNAME(sc), entry[0]); 1182 } 1183 break; 1184 1185 case QLE_IOCB_MARKER: 1186 break; 1187 1188 case QLE_IOCB_CMD_TYPE_6: 1189 case QLE_IOCB_CMD_TYPE_7: 1190 DPRINTF(QLE_D_IO, "%s: request bounced back\n", DEVNAME(sc)); 1191 req = (struct qle_iocb_req6 *)entry; 1192 handle = req->req_handle; 1193 if (handle > sc->sc_maxcmds) { 1194 panic("bad bounced command handle: %d (> %d)", 1195 handle, sc->sc_maxcmds); 1196 } 1197 1198 ccb = &sc->sc_ccbs[handle]; 1199 xs = ccb->ccb_xs; 1200 xs->error = XS_DRIVER_STUFFUP; 1201 break; 1202 default: 1203 DPRINTF(QLE_D_IO, "%s: unexpected response entry type %x\n", 1204 DEVNAME(sc), entry[0]); 1205 break; 1206 } 1207 1208 return (ccb); 1209 } 1210 1211 void 1212 qle_handle_intr(struct qle_softc *sc, u_int16_t isr, u_int16_t info) 1213 { 1214 int i; 1215 u_int32_t rspin; 1216 struct qle_ccb *ccb; 1217 1218 switch (isr) { 1219 case QLE_INT_TYPE_ASYNC: 1220 qle_async(sc, info); 1221 break; 1222 1223 case QLE_INT_TYPE_IO: 1224 rspin = qle_read(sc, QLE_RESP_IN); 1225 if (rspin == sc->sc_last_resp_id) 1226 break; 1227 1228 do { 1229 ccb = qle_handle_resp(sc, sc->sc_last_resp_id); 1230 if (ccb) 1231 scsi_done(ccb->ccb_xs); 1232 1233 sc->sc_last_resp_id++; 1234 sc->sc_last_resp_id %= sc->sc_maxcmds; 1235 } while (sc->sc_last_resp_id != rspin); 1236 1237 qle_write(sc, QLE_RESP_OUT, sc->sc_last_resp_id); 1238 break; 1239 1240 case QLE_INT_TYPE_MBOX: 1241 mtx_enter(&sc->sc_mbox_mtx); 1242 if (sc->sc_mbox_pending) { 1243 for (i = 0; i < nitems(sc->sc_mbox); i++) { 1244 sc->sc_mbox[i] = qle_read_mbox(sc, i); 1245 } 1246 sc->sc_mbox_pending = 2; 1247 wakeup(sc->sc_mbox); 1248 mtx_leave(&sc->sc_mbox_mtx); 1249 } else { 1250 mtx_leave(&sc->sc_mbox_mtx); 1251 DPRINTF(QLE_D_INTR, "%s: unexpected mbox interrupt: " 1252 "%x\n", DEVNAME(sc), info); 1253 } 1254 break; 1255 1256 default: 1257 break; 1258 } 1259 1260 qle_clear_isr(sc, isr); 1261 } 1262 1263 int 1264 qle_intr(void *xsc) 1265 { 1266 struct qle_softc *sc = xsc; 1267 u_int16_t isr; 1268 u_int16_t info; 1269 1270 if (qle_read_isr(sc, &isr, &info) == 0) 1271 return (0); 1272 1273 qle_handle_intr(sc, isr, info); 1274 return (1); 1275 } 1276 1277 int 1278 qle_scsi_probe(struct scsi_link *link) 1279 { 1280 struct qle_softc *sc = link->adapter_softc; 1281 int rv = 0; 1282 1283 mtx_enter(&sc->sc_port_mtx); 1284 if (sc->sc_targets[link->target] == NULL) 1285 rv = ENXIO; 1286 else if (!ISSET(sc->sc_targets[link->target]->flags, 1287 QLE_PORT_FLAG_IS_TARGET)) 1288 rv = ENXIO; 1289 mtx_leave(&sc->sc_port_mtx); 1290 1291 return (rv); 1292 } 1293 1294 void 1295 qle_scsi_cmd(struct scsi_xfer *xs) 1296 { 1297 struct scsi_link *link = xs->sc_link; 1298 struct qle_softc *sc = link->adapter_softc; 1299 struct qle_ccb *ccb; 1300 void *iocb; 1301 struct qle_ccb_list list; 1302 u_int16_t req; 1303 u_int32_t portid; 1304 int offset, error, done; 1305 bus_dmamap_t dmap; 1306 1307 if (xs->cmdlen > 16) { 1308 DPRINTF(QLE_D_IO, "%s: cmd too big (%d)\n", DEVNAME(sc), 1309 xs->cmdlen); 1310 memset(&xs->sense, 0, sizeof(xs->sense)); 1311 xs->sense.error_code = SSD_ERRCODE_VALID | SSD_ERRCODE_CURRENT; 1312 xs->sense.flags = SKEY_ILLEGAL_REQUEST; 1313 xs->sense.add_sense_code = 0x20; 1314 xs->error = XS_SENSE; 1315 scsi_done(xs); 1316 return; 1317 } 1318 1319 portid = 0xffffffff; 1320 mtx_enter(&sc->sc_port_mtx); 1321 if (sc->sc_targets[xs->sc_link->target] != NULL) { 1322 portid = sc->sc_targets[xs->sc_link->target]->portid; 1323 } 1324 mtx_leave(&sc->sc_port_mtx); 1325 if (portid == 0xffffffff) { 1326 xs->error = XS_DRIVER_STUFFUP; 1327 scsi_done(xs); 1328 return; 1329 } 1330 1331 ccb = xs->io; 1332 dmap = ccb->ccb_dmamap; 1333 if (xs->datalen > 0) { 1334 error = bus_dmamap_load(sc->sc_dmat, dmap, xs->data, 1335 xs->datalen, NULL, (xs->flags & SCSI_NOSLEEP) ? 1336 BUS_DMA_NOWAIT : BUS_DMA_WAITOK); 1337 if (error) { 1338 xs->error = XS_DRIVER_STUFFUP; 1339 scsi_done(xs); 1340 return; 1341 } 1342 1343 bus_dmamap_sync(sc->sc_dmat, dmap, 0, 1344 dmap->dm_mapsize, 1345 (xs->flags & SCSI_DATA_IN) ? BUS_DMASYNC_PREREAD : 1346 BUS_DMASYNC_PREWRITE); 1347 } 1348 1349 mtx_enter(&sc->sc_queue_mtx); 1350 1351 /* put in a sync marker if required */ 1352 if (sc->sc_marker_required) { 1353 req = sc->sc_next_req_id++; 1354 if (sc->sc_next_req_id == sc->sc_maxcmds) 1355 sc->sc_next_req_id = 0; 1356 1357 DPRINTF(QLE_D_IO, "%s: writing marker at request %d\n", 1358 DEVNAME(sc), req); 1359 offset = (req * QLE_QUEUE_ENTRY_SIZE); 1360 iocb = QLE_DMA_KVA(sc->sc_requests) + offset; 1361 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_requests), 1362 offset, QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_POSTWRITE); 1363 qle_put_marker(sc, iocb); 1364 qle_write(sc, QLE_REQ_IN, sc->sc_next_req_id); 1365 sc->sc_marker_required = 0; 1366 } 1367 1368 req = sc->sc_next_req_id++; 1369 if (sc->sc_next_req_id == sc->sc_maxcmds) 1370 sc->sc_next_req_id = 0; 1371 1372 offset = (req * QLE_QUEUE_ENTRY_SIZE); 1373 iocb = QLE_DMA_KVA(sc->sc_requests) + offset; 1374 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_requests), offset, 1375 QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_POSTWRITE); 1376 1377 ccb->ccb_xs = xs; 1378 1379 qle_put_cmd(sc, iocb, xs, ccb, portid); 1380 1381 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_requests), offset, 1382 QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_PREREAD); 1383 qle_write(sc, QLE_REQ_IN, sc->sc_next_req_id); 1384 1385 if (!ISSET(xs->flags, SCSI_POLL)) { 1386 mtx_leave(&sc->sc_queue_mtx); 1387 return; 1388 } 1389 1390 done = 0; 1391 SIMPLEQ_INIT(&list); 1392 do { 1393 u_int16_t isr, info; 1394 u_int32_t rspin; 1395 delay(100); 1396 1397 if (qle_read_isr(sc, &isr, &info) == 0) { 1398 continue; 1399 } 1400 1401 if (isr != QLE_INT_TYPE_IO) { 1402 qle_handle_intr(sc, isr, info); 1403 continue; 1404 } 1405 1406 rspin = qle_read(sc, QLE_RESP_IN); 1407 while (rspin != sc->sc_last_resp_id) { 1408 ccb = qle_handle_resp(sc, sc->sc_last_resp_id); 1409 1410 sc->sc_last_resp_id++; 1411 if (sc->sc_last_resp_id == sc->sc_maxcmds) 1412 sc->sc_last_resp_id = 0; 1413 1414 if (ccb != NULL) 1415 SIMPLEQ_INSERT_TAIL(&list, ccb, ccb_link); 1416 if (ccb == xs->io) 1417 done = 1; 1418 } 1419 qle_write(sc, QLE_RESP_OUT, sc->sc_last_resp_id); 1420 qle_clear_isr(sc, isr); 1421 } while (done == 0); 1422 1423 mtx_leave(&sc->sc_queue_mtx); 1424 1425 while ((ccb = SIMPLEQ_FIRST(&list)) != NULL) { 1426 SIMPLEQ_REMOVE_HEAD(&list, ccb_link); 1427 scsi_done(ccb->ccb_xs); 1428 } 1429 } 1430 1431 u_int32_t 1432 qle_read(struct qle_softc *sc, int offset) 1433 { 1434 u_int32_t v; 1435 v = bus_space_read_4(sc->sc_iot, sc->sc_ioh, offset); 1436 bus_space_barrier(sc->sc_iot, sc->sc_ioh, offset, 4, 1437 BUS_SPACE_BARRIER_READ | BUS_SPACE_BARRIER_WRITE); 1438 return (v); 1439 } 1440 1441 void 1442 qle_write(struct qle_softc *sc, int offset, u_int32_t value) 1443 { 1444 bus_space_write_4(sc->sc_iot, sc->sc_ioh, offset, value); 1445 bus_space_barrier(sc->sc_iot, sc->sc_ioh, offset, 4, 1446 BUS_SPACE_BARRIER_READ | BUS_SPACE_BARRIER_WRITE); 1447 } 1448 1449 u_int16_t 1450 qle_read_mbox(struct qle_softc *sc, int mbox) 1451 { 1452 u_int16_t v; 1453 bus_size_t offset = mbox * 2; 1454 v = bus_space_read_2(sc->sc_iot, sc->sc_mbox_ioh, offset); 1455 bus_space_barrier(sc->sc_iot, sc->sc_mbox_ioh, offset, 2, 1456 BUS_SPACE_BARRIER_READ | BUS_SPACE_BARRIER_WRITE); 1457 return (v); 1458 } 1459 1460 void 1461 qle_write_mbox(struct qle_softc *sc, int mbox, u_int16_t value) 1462 { 1463 bus_size_t offset = (mbox * 2); 1464 bus_space_write_2(sc->sc_iot, sc->sc_mbox_ioh, offset, value); 1465 bus_space_barrier(sc->sc_iot, sc->sc_mbox_ioh, offset, 2, 1466 BUS_SPACE_BARRIER_READ | BUS_SPACE_BARRIER_WRITE); 1467 } 1468 1469 void 1470 qle_host_cmd(struct qle_softc *sc, u_int32_t cmd) 1471 { 1472 qle_write(sc, QLE_HOST_CMD_CTRL, cmd << QLE_HOST_CMD_SHIFT); 1473 } 1474 1475 #define MBOX_COMMAND_TIMEOUT 400000 1476 1477 int 1478 qle_mbox(struct qle_softc *sc, int maskin) 1479 { 1480 int i; 1481 int result = 0; 1482 int rv; 1483 1484 for (i = 0; i < nitems(sc->sc_mbox); i++) { 1485 if (maskin & (1 << i)) { 1486 qle_write_mbox(sc, i, sc->sc_mbox[i]); 1487 } 1488 } 1489 qle_host_cmd(sc, QLE_HOST_CMD_SET_HOST_INT); 1490 1491 if (sc->sc_scsibus != NULL) { 1492 mtx_enter(&sc->sc_mbox_mtx); 1493 sc->sc_mbox_pending = 1; 1494 while (sc->sc_mbox_pending == 1) { 1495 msleep(sc->sc_mbox, &sc->sc_mbox_mtx, PRIBIO, 1496 "qlembox", 0); 1497 } 1498 result = sc->sc_mbox[0]; 1499 sc->sc_mbox_pending = 0; 1500 mtx_leave(&sc->sc_mbox_mtx); 1501 return (result == QLE_MBOX_COMPLETE ? 0 : result); 1502 } 1503 1504 for (i = 0; i < MBOX_COMMAND_TIMEOUT && result == 0; i++) { 1505 u_int16_t isr, info; 1506 1507 delay(100); 1508 1509 if (qle_read_isr(sc, &isr, &info) == 0) 1510 continue; 1511 1512 switch (isr) { 1513 case QLE_INT_TYPE_MBOX: 1514 result = info; 1515 break; 1516 1517 default: 1518 qle_handle_intr(sc, isr, info); 1519 break; 1520 } 1521 } 1522 1523 if (result == 0) { 1524 /* timed out; do something? */ 1525 DPRINTF(QLE_D_MBOX, "%s: mbox timed out\n", DEVNAME(sc)); 1526 rv = 1; 1527 } else { 1528 for (i = 0; i < nitems(sc->sc_mbox); i++) { 1529 sc->sc_mbox[i] = qle_read_mbox(sc, i); 1530 } 1531 rv = (result == QLE_MBOX_COMPLETE ? 0 : result); 1532 } 1533 1534 qle_clear_isr(sc, QLE_INT_TYPE_MBOX); 1535 return (rv); 1536 } 1537 1538 void 1539 qle_mbox_putaddr(u_int16_t *mbox, struct qle_dmamem *mem) 1540 { 1541 mbox[2] = (QLE_DMA_DVA(mem) >> 16) & 0xffff; 1542 mbox[3] = (QLE_DMA_DVA(mem) >> 0) & 0xffff; 1543 mbox[6] = (QLE_DMA_DVA(mem) >> 48) & 0xffff; 1544 mbox[7] = (QLE_DMA_DVA(mem) >> 32) & 0xffff; 1545 } 1546 1547 void 1548 qle_set_ints(struct qle_softc *sc, int enabled) 1549 { 1550 u_int32_t v = enabled ? QLE_INT_CTRL_ENABLE : 0; 1551 qle_write(sc, QLE_INT_CTRL, v); 1552 } 1553 1554 int 1555 qle_read_isr(struct qle_softc *sc, u_int16_t *isr, u_int16_t *info) 1556 { 1557 u_int32_t v; 1558 1559 switch (sc->sc_isp_gen) { 1560 case QLE_GEN_ISP24XX: 1561 case QLE_GEN_ISP25XX: 1562 if ((qle_read(sc, QLE_INT_STATUS) & QLE_RISC_INT_REQ) == 0) 1563 return (0); 1564 1565 v = qle_read(sc, QLE_RISC_STATUS); 1566 1567 switch (v & QLE_INT_STATUS_MASK) { 1568 case QLE_24XX_INT_ROM_MBOX: 1569 case QLE_24XX_INT_ROM_MBOX_FAIL: 1570 case QLE_24XX_INT_MBOX: 1571 case QLE_24XX_INT_MBOX_FAIL: 1572 *isr = QLE_INT_TYPE_MBOX; 1573 break; 1574 1575 case QLE_24XX_INT_ASYNC: 1576 *isr = QLE_INT_TYPE_ASYNC; 1577 break; 1578 1579 case QLE_24XX_INT_RSPQ: 1580 *isr = QLE_INT_TYPE_IO; 1581 break; 1582 1583 default: 1584 *isr = QLE_INT_TYPE_OTHER; 1585 break; 1586 } 1587 1588 *info = (v >> QLE_INT_INFO_SHIFT); 1589 return (1); 1590 1591 default: 1592 return (0); 1593 } 1594 } 1595 1596 void 1597 qle_clear_isr(struct qle_softc *sc, u_int16_t isr) 1598 { 1599 qle_host_cmd(sc, QLE_HOST_CMD_CLR_RISC_INT); 1600 } 1601 1602 void 1603 qle_update_done(struct qle_softc *sc, int task) 1604 { 1605 atomic_clearbits_int(&sc->sc_update_tasks, task); 1606 } 1607 1608 void 1609 qle_update_start(struct qle_softc *sc, int task) 1610 { 1611 atomic_setbits_int(&sc->sc_update_tasks, task); 1612 task_add(sc->sc_update_taskq, &sc->sc_update_task); 1613 } 1614 1615 void 1616 qle_clear_port_lists(struct qle_softc *sc) 1617 { 1618 struct qle_fc_port *p; 1619 while (!TAILQ_EMPTY(&sc->sc_ports_found)) { 1620 p = TAILQ_FIRST(&sc->sc_ports_found); 1621 TAILQ_REMOVE(&sc->sc_ports_found, p, update); 1622 free(p, M_DEVBUF, 0); 1623 } 1624 1625 while (!TAILQ_EMPTY(&sc->sc_ports_new)) { 1626 p = TAILQ_FIRST(&sc->sc_ports_new); 1627 TAILQ_REMOVE(&sc->sc_ports_new, p, update); 1628 free(p, M_DEVBUF, 0); 1629 } 1630 1631 while (!TAILQ_EMPTY(&sc->sc_ports_gone)) { 1632 p = TAILQ_FIRST(&sc->sc_ports_gone); 1633 TAILQ_REMOVE(&sc->sc_ports_gone, p, update); 1634 } 1635 } 1636 1637 int 1638 qle_softreset(struct qle_softc *sc) 1639 { 1640 int i; 1641 qle_set_ints(sc, 0); 1642 1643 /* set led control bits, stop dma */ 1644 qle_write(sc, QLE_GPIO_DATA, 0); 1645 qle_write(sc, QLE_CTRL_STATUS, QLE_CTRL_DMA_SHUTDOWN); 1646 while (qle_read(sc, QLE_CTRL_STATUS) & QLE_CTRL_DMA_ACTIVE) { 1647 DPRINTF(QLE_D_IO, "%s: dma still active\n", DEVNAME(sc)); 1648 delay(100); 1649 } 1650 1651 /* reset */ 1652 qle_write(sc, QLE_CTRL_STATUS, QLE_CTRL_RESET | QLE_CTRL_DMA_SHUTDOWN); 1653 delay(100); 1654 /* clear data and control dma engines? */ 1655 1656 /* wait for soft reset to clear */ 1657 for (i = 0; i < 1000; i++) { 1658 if (qle_read_mbox(sc, 0) == 0x0000) 1659 break; 1660 1661 delay(100); 1662 } 1663 1664 if (i == 1000) { 1665 printf("%s: reset mbox didn't clear\n", DEVNAME(sc)); 1666 qle_set_ints(sc, 0); 1667 return (ENXIO); 1668 } 1669 1670 for (i = 0; i < 500000; i++) { 1671 if ((qle_read(sc, QLE_CTRL_STATUS) & QLE_CTRL_RESET) == 0) 1672 break; 1673 delay(5); 1674 } 1675 if (i == 500000) { 1676 printf("%s: reset status didn't clear\n", DEVNAME(sc)); 1677 return (ENXIO); 1678 } 1679 1680 /* reset risc processor */ 1681 qle_host_cmd(sc, QLE_HOST_CMD_RESET); 1682 qle_host_cmd(sc, QLE_HOST_CMD_RELEASE); 1683 qle_host_cmd(sc, QLE_HOST_CMD_CLEAR_RESET); 1684 1685 /* wait for reset to clear */ 1686 for (i = 0; i < 1000; i++) { 1687 if (qle_read_mbox(sc, 0) == 0x0000) 1688 break; 1689 delay(100); 1690 } 1691 if (i == 1000) { 1692 printf("%s: risc not ready after reset\n", DEVNAME(sc)); 1693 return (ENXIO); 1694 } 1695 1696 /* reset queue pointers */ 1697 qle_write(sc, QLE_REQ_IN, 0); 1698 qle_write(sc, QLE_REQ_OUT, 0); 1699 qle_write(sc, QLE_RESP_IN, 0); 1700 qle_write(sc, QLE_RESP_OUT, 0); 1701 1702 qle_set_ints(sc, 1); 1703 1704 /* do a basic mailbox operation to check we're alive */ 1705 sc->sc_mbox[0] = QLE_MBOX_NOP; 1706 if (qle_mbox(sc, 0x0001)) { 1707 printf("ISP not responding after reset\n"); 1708 return (ENXIO); 1709 } 1710 1711 return (0); 1712 } 1713 1714 void 1715 qle_update_topology(struct qle_softc *sc) 1716 { 1717 sc->sc_mbox[0] = QLE_MBOX_GET_ID; 1718 if (qle_mbox(sc, 0x0001)) { 1719 DPRINTF(QLE_D_PORT, "%s: unable to get loop id\n", DEVNAME(sc)); 1720 sc->sc_topology = QLE_TOPO_N_PORT_NO_TARGET; 1721 } else { 1722 sc->sc_topology = sc->sc_mbox[6]; 1723 sc->sc_loop_id = sc->sc_mbox[1]; 1724 1725 switch (sc->sc_topology) { 1726 case QLE_TOPO_NL_PORT: 1727 case QLE_TOPO_N_PORT: 1728 DPRINTF(QLE_D_PORT, "%s: loop id %d\n", DEVNAME(sc), 1729 sc->sc_loop_id); 1730 break; 1731 1732 case QLE_TOPO_FL_PORT: 1733 case QLE_TOPO_F_PORT: 1734 sc->sc_port_id = sc->sc_mbox[2] | 1735 (sc->sc_mbox[3] << 16); 1736 DPRINTF(QLE_D_PORT, "%s: fabric port id %06x\n", 1737 DEVNAME(sc), sc->sc_port_id); 1738 break; 1739 1740 case QLE_TOPO_N_PORT_NO_TARGET: 1741 default: 1742 DPRINTF(QLE_D_PORT, "%s: not useful\n", DEVNAME(sc)); 1743 break; 1744 } 1745 1746 switch (sc->sc_topology) { 1747 case QLE_TOPO_NL_PORT: 1748 case QLE_TOPO_FL_PORT: 1749 sc->sc_loop_max_id = 126; 1750 break; 1751 1752 case QLE_TOPO_N_PORT: 1753 sc->sc_loop_max_id = 2; 1754 break; 1755 1756 default: 1757 sc->sc_loop_max_id = 0; 1758 break; 1759 } 1760 } 1761 } 1762 1763 int 1764 qle_update_fabric(struct qle_softc *sc) 1765 { 1766 /*struct qle_sns_rft_id *rft;*/ 1767 1768 switch (sc->sc_topology) { 1769 case QLE_TOPO_F_PORT: 1770 case QLE_TOPO_FL_PORT: 1771 break; 1772 1773 default: 1774 return (0); 1775 } 1776 1777 /* get the name server's port db entry */ 1778 sc->sc_mbox[0] = QLE_MBOX_GET_PORT_DB; 1779 sc->sc_mbox[1] = QLE_F_PORT_HANDLE; 1780 qle_mbox_putaddr(sc->sc_mbox, sc->sc_scratch); 1781 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 1782 sizeof(struct qle_get_port_db), BUS_DMASYNC_PREREAD); 1783 if (qle_mbox(sc, 0x00cf)) { 1784 DPRINTF(QLE_D_PORT, "%s: get port db for SNS failed: %x\n", 1785 DEVNAME(sc), sc->sc_mbox[0]); 1786 sc->sc_sns_port_name = 0; 1787 } else { 1788 struct qle_get_port_db *pdb; 1789 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_scratch), 0, 1790 sizeof(struct qle_get_port_db), BUS_DMASYNC_POSTREAD); 1791 pdb = QLE_DMA_KVA(sc->sc_scratch); 1792 DPRINTF(QLE_D_PORT, "%s: SNS port name %llx\n", DEVNAME(sc), 1793 betoh64(pdb->port_name)); 1794 sc->sc_sns_port_name = betoh64(pdb->port_name); 1795 } 1796 1797 /* 1798 * register fc4 types with the fabric 1799 * some switches do this automatically, but apparently 1800 * some don't. 1801 */ 1802 /* 1803 rft = QLE_DMA_KVA(sc->sc_scratch); 1804 memset(rft, 0, sizeof(*rft) + sizeof(struct qle_sns_req_hdr)); 1805 htolem16(&rft->subcmd, QLE_SNS_RFT_ID); 1806 htolem16(&rft->max_word, sizeof(struct qle_sns_req_hdr) / 4); 1807 htolem32(&rft->port_id, sc->sc_port_id); 1808 rft->fc4_types[0] = (1 << QLE_FC4_SCSI); 1809 if (qle_sns_req(sc, sc->sc_scratch, sizeof(*rft))) { 1810 printf("%s: RFT_ID failed\n", DEVNAME(sc)); 1811 / * we might be able to continue after this fails * / 1812 } 1813 */ 1814 1815 return (1); 1816 } 1817 1818 int 1819 qle_ct_pass_through(struct qle_softc *sc, u_int32_t port_handle, 1820 struct qle_dmamem *mem, size_t req_size, size_t resp_size) 1821 { 1822 struct qle_iocb_ct_passthrough *iocb; 1823 u_int16_t req; 1824 u_int64_t offset; 1825 int rv; 1826 1827 mtx_enter(&sc->sc_queue_mtx); 1828 1829 req = sc->sc_next_req_id++; 1830 if (sc->sc_next_req_id == sc->sc_maxcmds) 1831 sc->sc_next_req_id = 0; 1832 1833 offset = (req * QLE_QUEUE_ENTRY_SIZE); 1834 iocb = QLE_DMA_KVA(sc->sc_requests) + offset; 1835 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_requests), offset, 1836 QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_POSTWRITE); 1837 1838 memset(iocb, 0, QLE_QUEUE_ENTRY_SIZE); 1839 iocb->entry_type = QLE_IOCB_CT_PASSTHROUGH; 1840 iocb->entry_count = 1; 1841 1842 iocb->req_handle = 9; 1843 htolem16(&iocb->req_nport_handle, port_handle); 1844 htolem16(&iocb->req_dsd_count, 1); 1845 htolem16(&iocb->req_resp_dsd_count, 1); 1846 htolem32(&iocb->req_cmd_byte_count, req_size); 1847 htolem32(&iocb->req_resp_byte_count, resp_size); 1848 qle_sge(&iocb->req_cmd_seg, QLE_DMA_DVA(mem), req_size); 1849 qle_sge(&iocb->req_resp_seg, QLE_DMA_DVA(mem) + req_size, resp_size); 1850 1851 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, QLE_DMA_LEN(mem), 1852 BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE); 1853 qle_write(sc, QLE_REQ_IN, sc->sc_next_req_id); 1854 sc->sc_fabric_pending = 1; 1855 mtx_leave(&sc->sc_queue_mtx); 1856 1857 /* maybe put a proper timeout on this */ 1858 rv = 0; 1859 while (sc->sc_fabric_pending == 1) { 1860 if (sc->sc_scsibus == NULL) { 1861 u_int16_t isr, info; 1862 1863 delay(100); 1864 if (qle_read_isr(sc, &isr, &info) != 0) 1865 qle_handle_intr(sc, isr, info); 1866 } else { 1867 tsleep(sc->sc_scratch, PRIBIO, "qle_fabric", 100); 1868 } 1869 } 1870 if (rv == 0) 1871 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, 1872 QLE_DMA_LEN(mem), BUS_DMASYNC_POSTREAD | 1873 BUS_DMASYNC_POSTWRITE); 1874 1875 sc->sc_fabric_pending = 0; 1876 1877 return (rv); 1878 } 1879 1880 struct qle_fc_port * 1881 qle_next_fabric_port(struct qle_softc *sc, u_int32_t *firstport, 1882 u_int32_t *lastport) 1883 { 1884 struct qle_ct_ga_nxt_req *ga; 1885 struct qle_ct_ga_nxt_resp *gar; 1886 struct qle_fc_port *fport; 1887 int result; 1888 1889 /* get the next port from the fabric nameserver */ 1890 ga = QLE_DMA_KVA(sc->sc_scratch); 1891 memset(ga, 0, sizeof(*ga) + sizeof(*gar)); 1892 ga->header.ct_revision = 0x01; 1893 ga->header.ct_gs_type = 0xfc; 1894 ga->header.ct_gs_subtype = 0x02; 1895 ga->subcmd = htobe16(QLE_SNS_GA_NXT); 1896 ga->max_word = htobe16((sizeof(*gar) - 16) / 4); 1897 ga->port_id = htobe32(*lastport); 1898 result = qle_ct_pass_through(sc, QLE_SNS_HANDLE, sc->sc_scratch, 1899 sizeof(*ga), sizeof(*gar)); 1900 if (result) { 1901 DPRINTF(QLE_D_PORT, "%s: GA_NXT %06x failed: %x\n", DEVNAME(sc), 1902 *lastport, result); 1903 *lastport = 0xffffffff; 1904 return (NULL); 1905 } 1906 1907 gar = (struct qle_ct_ga_nxt_resp *)(ga + 1); 1908 /* if the response is all zeroes, try again */ 1909 if (gar->port_type_id == 0 && gar->port_name == 0 && 1910 gar->node_name == 0) { 1911 DPRINTF(QLE_D_PORT, "%s: GA_NXT returned junk\n", DEVNAME(sc)); 1912 return (NULL); 1913 } 1914 1915 /* are we back at the start? */ 1916 *lastport = betoh32(gar->port_type_id) & 0xffffff; 1917 if (*lastport == *firstport) { 1918 *lastport = 0xffffffff; 1919 return (NULL); 1920 } 1921 if (*firstport == 0xffffffff) 1922 *firstport = *lastport; 1923 1924 DPRINTF(QLE_D_PORT, "%s: GA_NXT: port id: %06x, wwpn %llx, wwnn %llx\n", 1925 DEVNAME(sc), *lastport, betoh64(gar->port_name), 1926 betoh64(gar->node_name)); 1927 1928 /* don't try to log in to ourselves */ 1929 if (*lastport == sc->sc_port_id) { 1930 return (NULL); 1931 } 1932 1933 fport = malloc(sizeof(*fport), M_DEVBUF, M_ZERO | M_NOWAIT); 1934 if (fport == NULL) { 1935 printf("%s: failed to allocate a port struct\n", 1936 DEVNAME(sc)); 1937 *lastport = 0xffffffff; 1938 return (NULL); 1939 } 1940 fport->port_name = betoh64(gar->port_name); 1941 fport->node_name = betoh64(gar->node_name); 1942 fport->location = QLE_LOCATION_PORT_ID(*lastport); 1943 fport->portid = *lastport; 1944 return (fport); 1945 } 1946 1947 int 1948 qle_fabric_plogx(struct qle_softc *sc, struct qle_fc_port *port, int flags, 1949 u_int32_t *info) 1950 { 1951 struct qle_iocb_plogx *iocb; 1952 u_int16_t req; 1953 u_int64_t offset; 1954 int rv; 1955 1956 mtx_enter(&sc->sc_queue_mtx); 1957 1958 req = sc->sc_next_req_id++; 1959 if (sc->sc_next_req_id == sc->sc_maxcmds) 1960 sc->sc_next_req_id = 0; 1961 1962 offset = (req * QLE_QUEUE_ENTRY_SIZE); 1963 iocb = QLE_DMA_KVA(sc->sc_requests) + offset; 1964 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(sc->sc_requests), offset, 1965 QLE_QUEUE_ENTRY_SIZE, BUS_DMASYNC_POSTWRITE); 1966 1967 memset(iocb, 0, QLE_QUEUE_ENTRY_SIZE); 1968 iocb->entry_type = QLE_IOCB_PLOGX; 1969 iocb->entry_count = 1; 1970 1971 iocb->req_handle = 7; 1972 htolem16(&iocb->req_nport_handle, port->loopid); 1973 htolem16(&iocb->req_port_id_lo, port->portid); 1974 iocb->req_port_id_hi = port->portid >> 16; 1975 htolem16(&iocb->req_flags, flags); 1976 1977 DPRINTF(QLE_D_PORT, "%s: plogx loop id %d port %06x, flags %x\n", 1978 DEVNAME(sc), port->loopid, port->portid, flags); 1979 qle_dump_iocb(sc, iocb); 1980 1981 qle_write(sc, QLE_REQ_IN, sc->sc_next_req_id); 1982 sc->sc_fabric_pending = 1; 1983 mtx_leave(&sc->sc_queue_mtx); 1984 1985 /* maybe put a proper timeout on this */ 1986 rv = 0; 1987 while (sc->sc_fabric_pending == 1) { 1988 if (sc->sc_scsibus == NULL) { 1989 u_int16_t isr, info; 1990 1991 delay(100); 1992 if (qle_read_isr(sc, &isr, &info) != 0) 1993 qle_handle_intr(sc, isr, info); 1994 } else { 1995 tsleep(sc->sc_scratch, PRIBIO, "qle_fabric", 100); 1996 } 1997 } 1998 sc->sc_fabric_pending = 0; 1999 2000 iocb = (struct qle_iocb_plogx *)&sc->sc_fabric_response; 2001 rv = lemtoh16(&iocb->req_status); 2002 if (rv == QLE_PLOGX_ERROR) { 2003 rv = lemtoh32(&iocb->req_ioparms[0]); 2004 *info = lemtoh32(&iocb->req_ioparms[1]); 2005 } 2006 2007 return (rv); 2008 } 2009 2010 int 2011 qle_fabric_plogi(struct qle_softc *sc, struct qle_fc_port *port) 2012 { 2013 u_int32_t info; 2014 int err, loopid; 2015 2016 loopid = 0; 2017 retry: 2018 if (port->loopid == 0) { 2019 2020 mtx_enter(&sc->sc_port_mtx); 2021 loopid = qle_get_loop_id(sc, loopid); 2022 mtx_leave(&sc->sc_port_mtx); 2023 if (loopid == -1) { 2024 printf("%s: ran out of loop ids\n", DEVNAME(sc)); 2025 return (1); 2026 } 2027 2028 port->loopid = loopid; 2029 } 2030 2031 err = qle_fabric_plogx(sc, port, QLE_PLOGX_LOGIN, &info); 2032 switch (err) { 2033 case 0: 2034 DPRINTF(QLE_D_PORT, "%s: logged in to %06x as %d\n", 2035 DEVNAME(sc), port->portid, port->loopid); 2036 port->flags &= ~QLE_PORT_FLAG_NEEDS_LOGIN; 2037 return (0); 2038 2039 case QLE_PLOGX_ERROR_PORT_ID_USED: 2040 DPRINTF(QLE_D_PORT, "%s: already logged in to %06x as %d\n", 2041 DEVNAME(sc), port->portid, info); 2042 port->loopid = info; 2043 port->flags &= ~QLE_PORT_FLAG_NEEDS_LOGIN; 2044 return (0); 2045 2046 case QLE_PLOGX_ERROR_HANDLE_USED: 2047 if (qle_add_logged_in_port(sc, loopid, info)) { 2048 return (1); 2049 } 2050 port->loopid = 0; 2051 loopid++; 2052 goto retry; 2053 2054 default: 2055 DPRINTF(QLE_D_PORT, "%s: error %x logging in to port %06x\n", 2056 DEVNAME(sc), err, port->portid); 2057 port->loopid = 0; 2058 return (1); 2059 } 2060 } 2061 2062 void 2063 qle_fabric_plogo(struct qle_softc *sc, struct qle_fc_port *port) 2064 { 2065 int err; 2066 u_int32_t info; 2067 2068 /* 2069 * we only log out if we can't see the port any more, so we always 2070 * want to do an explicit logout and free the n-port handle. 2071 */ 2072 err = qle_fabric_plogx(sc, port, QLE_PLOGX_LOGOUT | 2073 QLE_PLOGX_LOGOUT_EXPLICIT | QLE_PLOGX_LOGOUT_FREE_HANDLE, &info); 2074 if (err == 0) { 2075 DPRINTF(QLE_D_PORT, "%s: logged out of port %06x\n", 2076 DEVNAME(sc), port->portid); 2077 } else { 2078 DPRINTF(QLE_D_PORT, "%s: failed to log out of port %06x: " 2079 "%x %x\n", DEVNAME(sc), port->portid, err, info); 2080 } 2081 } 2082 2083 void 2084 qle_do_update(void *xsc, void *x) 2085 { 2086 struct qle_softc *sc = xsc; 2087 int firstport, lastport; 2088 struct qle_fc_port *port, *fport; 2089 2090 DPRINTF(QLE_D_PORT, "%s: updating\n", DEVNAME(sc)); 2091 while (sc->sc_update_tasks != 0) { 2092 if (sc->sc_update_tasks & QLE_UPDATE_TASK_CLEAR_ALL) { 2093 TAILQ_HEAD(, qle_fc_port) detach; 2094 DPRINTF(QLE_D_PORT, "%s: detaching everything\n", 2095 DEVNAME(sc)); 2096 2097 mtx_enter(&sc->sc_port_mtx); 2098 qle_clear_port_lists(sc); 2099 TAILQ_INIT(&detach); 2100 while (!TAILQ_EMPTY(&sc->sc_ports)) { 2101 port = TAILQ_FIRST(&sc->sc_ports); 2102 TAILQ_REMOVE(&sc->sc_ports, port, ports); 2103 TAILQ_INSERT_TAIL(&detach, port, ports); 2104 } 2105 mtx_leave(&sc->sc_port_mtx); 2106 2107 while (!TAILQ_EMPTY(&detach)) { 2108 port = TAILQ_FIRST(&detach); 2109 TAILQ_REMOVE(&detach, port, ports); 2110 if (port->flags & QLE_PORT_FLAG_IS_TARGET) { 2111 scsi_detach_target(sc->sc_scsibus, 2112 port->loopid, -1); 2113 sc->sc_targets[port->loopid] = NULL; 2114 } 2115 if (port->location & QLE_LOCATION_FABRIC) 2116 qle_fabric_plogo(sc, port); 2117 2118 free(port, M_DEVBUF, 0); 2119 } 2120 2121 qle_update_done(sc, QLE_UPDATE_TASK_CLEAR_ALL); 2122 continue; 2123 } 2124 2125 if (sc->sc_update_tasks & QLE_UPDATE_TASK_SOFTRESET) { 2126 DPRINTF(QLE_D_IO, "%s: attempting softreset\n", 2127 DEVNAME(sc)); 2128 if (qle_softreset(sc) != 0) { 2129 DPRINTF(QLE_D_IO, "%s: couldn't softreset\n", 2130 DEVNAME(sc)); 2131 } 2132 qle_update_done(sc, QLE_UPDATE_TASK_SOFTRESET); 2133 continue; 2134 } 2135 2136 if (sc->sc_update_tasks & QLE_UPDATE_TASK_UPDATE_TOPO) { 2137 DPRINTF(QLE_D_PORT, "%s: updating topology\n", 2138 DEVNAME(sc)); 2139 qle_update_topology(sc); 2140 qle_update_done(sc, QLE_UPDATE_TASK_UPDATE_TOPO); 2141 continue; 2142 } 2143 2144 if (sc->sc_update_tasks & QLE_UPDATE_TASK_GET_PORT_LIST) { 2145 DPRINTF(QLE_D_PORT, "%s: getting port name list\n", 2146 DEVNAME(sc)); 2147 mtx_enter(&sc->sc_port_mtx); 2148 qle_clear_port_lists(sc); 2149 mtx_leave(&sc->sc_port_mtx); 2150 2151 qle_get_port_name_list(sc, QLE_LOCATION_LOOP | 2152 QLE_LOCATION_FABRIC); 2153 mtx_enter(&sc->sc_port_mtx); 2154 TAILQ_FOREACH(port, &sc->sc_ports, ports) { 2155 TAILQ_INSERT_TAIL(&sc->sc_ports_gone, port, 2156 update); 2157 if (port->location & QLE_LOCATION_FABRIC) { 2158 port->flags |= 2159 QLE_PORT_FLAG_NEEDS_LOGIN; 2160 } 2161 } 2162 2163 /* take care of ports that haven't changed first */ 2164 TAILQ_FOREACH(fport, &sc->sc_ports_found, update) { 2165 port = sc->sc_targets[fport->loopid]; 2166 if (port == NULL || fport->port_name != 2167 port->port_name) { 2168 /* new or changed port, handled later */ 2169 continue; 2170 } 2171 2172 /* 2173 * the port hasn't been logged out, which 2174 * means we don't need to log in again, and, 2175 * for loop ports, that the port still exists 2176 */ 2177 port->flags &= ~QLE_PORT_FLAG_NEEDS_LOGIN; 2178 if (port->location & QLE_LOCATION_LOOP) 2179 TAILQ_REMOVE(&sc->sc_ports_gone, 2180 port, update); 2181 2182 fport->location = 0; 2183 } 2184 mtx_leave(&sc->sc_port_mtx); 2185 qle_update_start(sc, QLE_UPDATE_TASK_PORT_LIST); 2186 qle_update_done(sc, QLE_UPDATE_TASK_GET_PORT_LIST); 2187 continue; 2188 } 2189 2190 if (sc->sc_update_tasks & QLE_UPDATE_TASK_PORT_LIST) { 2191 mtx_enter(&sc->sc_port_mtx); 2192 fport = TAILQ_FIRST(&sc->sc_ports_found); 2193 if (fport != NULL) { 2194 TAILQ_REMOVE(&sc->sc_ports_found, fport, 2195 update); 2196 } 2197 mtx_leave(&sc->sc_port_mtx); 2198 2199 if (fport == NULL) { 2200 DPRINTF(QLE_D_PORT, "%s: done with ports\n", 2201 DEVNAME(sc)); 2202 qle_update_done(sc, 2203 QLE_UPDATE_TASK_PORT_LIST); 2204 qle_update_start(sc, 2205 QLE_UPDATE_TASK_SCAN_FABRIC); 2206 } else if (fport->location & QLE_LOCATION_LOOP) { 2207 DPRINTF(QLE_D_PORT, "%s: loop port %04x\n", 2208 DEVNAME(sc), fport->loopid); 2209 if (qle_add_loop_port(sc, fport) != 0) 2210 free(fport, M_DEVBUF, 0); 2211 } else if (fport->location & QLE_LOCATION_FABRIC) { 2212 qle_add_fabric_port(sc, fport); 2213 } else { 2214 /* already processed */ 2215 free(fport, M_DEVBUF, 0); 2216 } 2217 continue; 2218 } 2219 2220 if (sc->sc_update_tasks & QLE_UPDATE_TASK_SCAN_FABRIC) { 2221 DPRINTF(QLE_D_PORT, "%s: starting fabric scan\n", 2222 DEVNAME(sc)); 2223 lastport = sc->sc_port_id; 2224 firstport = 0xffffffff; 2225 if (qle_update_fabric(sc)) 2226 qle_update_start(sc, 2227 QLE_UPDATE_TASK_SCANNING_FABRIC); 2228 2229 qle_update_done(sc, QLE_UPDATE_TASK_SCAN_FABRIC); 2230 continue; 2231 } 2232 2233 if (sc->sc_update_tasks & QLE_UPDATE_TASK_SCANNING_FABRIC) { 2234 fport = qle_next_fabric_port(sc, &firstport, &lastport); 2235 if (fport != NULL) { 2236 int disp; 2237 2238 mtx_enter(&sc->sc_port_mtx); 2239 disp = qle_classify_port(sc, fport->location, 2240 fport->port_name, fport->node_name, &port); 2241 switch (disp) { 2242 case QLE_PORT_DISP_CHANGED: 2243 case QLE_PORT_DISP_MOVED: 2244 /* we'll log out the old port later */ 2245 case QLE_PORT_DISP_NEW: 2246 DPRINTF(QLE_D_PORT, "%s: new port " 2247 "%06x\n", DEVNAME(sc), 2248 fport->portid); 2249 TAILQ_INSERT_TAIL(&sc->sc_ports_found, 2250 fport, update); 2251 break; 2252 case QLE_PORT_DISP_DUP: 2253 free(fport, M_DEVBUF, 0); 2254 break; 2255 case QLE_PORT_DISP_SAME: 2256 DPRINTF(QLE_D_PORT, "%s: existing port " 2257 " %06x\n", DEVNAME(sc), 2258 fport->portid); 2259 TAILQ_REMOVE(&sc->sc_ports_gone, port, 2260 update); 2261 free(fport, M_DEVBUF, 0); 2262 break; 2263 } 2264 mtx_leave(&sc->sc_port_mtx); 2265 } 2266 if (lastport == 0xffffffff) { 2267 DPRINTF(QLE_D_PORT, "%s: finished\n", 2268 DEVNAME(sc)); 2269 qle_update_done(sc, 2270 QLE_UPDATE_TASK_SCANNING_FABRIC); 2271 qle_update_start(sc, 2272 QLE_UPDATE_TASK_FABRIC_LOGIN); 2273 } 2274 continue; 2275 } 2276 2277 if (sc->sc_update_tasks & QLE_UPDATE_TASK_FABRIC_LOGIN) { 2278 mtx_enter(&sc->sc_port_mtx); 2279 port = TAILQ_FIRST(&sc->sc_ports_found); 2280 if (port != NULL) { 2281 TAILQ_REMOVE(&sc->sc_ports_found, port, update); 2282 } 2283 mtx_leave(&sc->sc_port_mtx); 2284 2285 if (port != NULL) { 2286 DPRINTF(QLE_D_PORT, "%s: found port %06x\n", 2287 DEVNAME(sc), port->portid); 2288 if (qle_fabric_plogi(sc, port) == 0) { 2289 qle_add_fabric_port(sc, port); 2290 } else { 2291 DPRINTF(QLE_D_PORT, "%s: plogi %06x " 2292 "failed\n", DEVNAME(sc), 2293 port->portid); 2294 free(port, M_DEVBUF, 0); 2295 } 2296 } else { 2297 DPRINTF(QLE_D_PORT, "%s: done with logins\n", 2298 DEVNAME(sc)); 2299 qle_update_done(sc, 2300 QLE_UPDATE_TASK_FABRIC_LOGIN); 2301 qle_update_start(sc, 2302 QLE_UPDATE_TASK_ATTACH_TARGET | 2303 QLE_UPDATE_TASK_DETACH_TARGET); 2304 } 2305 continue; 2306 } 2307 2308 if (sc->sc_update_tasks & QLE_UPDATE_TASK_FABRIC_RELOGIN) { 2309 TAILQ_FOREACH(port, &sc->sc_ports, ports) { 2310 if (port->flags & QLE_PORT_FLAG_NEEDS_LOGIN) { 2311 qle_fabric_plogi(sc, port); 2312 break; 2313 } 2314 } 2315 2316 if (port == TAILQ_END(&sc->sc_ports)) 2317 qle_update_done(sc, 2318 QLE_UPDATE_TASK_FABRIC_RELOGIN); 2319 continue; 2320 } 2321 2322 if (sc->sc_update_tasks & QLE_UPDATE_TASK_DETACH_TARGET) { 2323 mtx_enter(&sc->sc_port_mtx); 2324 port = TAILQ_FIRST(&sc->sc_ports_gone); 2325 if (port != NULL) { 2326 sc->sc_targets[port->loopid] = NULL; 2327 TAILQ_REMOVE(&sc->sc_ports_gone, port, update); 2328 TAILQ_REMOVE(&sc->sc_ports, port, ports); 2329 } 2330 mtx_leave(&sc->sc_port_mtx); 2331 2332 if (port != NULL) { 2333 DPRINTF(QLE_D_PORT, "%s: detaching port %06x\n", 2334 DEVNAME(sc), port->portid); 2335 if (sc->sc_scsibus != NULL) 2336 scsi_detach_target(sc->sc_scsibus, 2337 port->loopid, -1); 2338 2339 if (port->location & QLE_LOCATION_FABRIC) 2340 qle_fabric_plogo(sc, port); 2341 2342 free(port, M_DEVBUF, 0); 2343 } else { 2344 DPRINTF(QLE_D_PORT, "%s: nothing to detach\n", 2345 DEVNAME(sc)); 2346 qle_update_done(sc, 2347 QLE_UPDATE_TASK_DETACH_TARGET); 2348 } 2349 continue; 2350 } 2351 2352 if (sc->sc_update_tasks & QLE_UPDATE_TASK_ATTACH_TARGET) { 2353 mtx_enter(&sc->sc_port_mtx); 2354 port = TAILQ_FIRST(&sc->sc_ports_new); 2355 if (port != NULL) { 2356 TAILQ_REMOVE(&sc->sc_ports_new, port, update); 2357 TAILQ_INSERT_TAIL(&sc->sc_ports, port, ports); 2358 } 2359 mtx_leave(&sc->sc_port_mtx); 2360 2361 if (port != NULL) { 2362 if (sc->sc_scsibus != NULL) 2363 scsi_probe_target(sc->sc_scsibus, 2364 port->loopid); 2365 } else { 2366 qle_update_done(sc, 2367 QLE_UPDATE_TASK_ATTACH_TARGET); 2368 } 2369 continue; 2370 } 2371 2372 } 2373 2374 DPRINTF(QLE_D_PORT, "%s: done updating\n", DEVNAME(sc)); 2375 } 2376 2377 int 2378 qle_async(struct qle_softc *sc, u_int16_t info) 2379 { 2380 switch (info) { 2381 case QLE_ASYNC_SYSTEM_ERROR: 2382 qle_update_start(sc, QLE_UPDATE_TASK_SOFTRESET); 2383 break; 2384 2385 case QLE_ASYNC_REQ_XFER_ERROR: 2386 qle_update_start(sc, QLE_UPDATE_TASK_SOFTRESET); 2387 break; 2388 2389 case QLE_ASYNC_RSP_XFER_ERROR: 2390 qle_update_start(sc, QLE_UPDATE_TASK_SOFTRESET); 2391 break; 2392 2393 case QLE_ASYNC_LIP_OCCURRED: 2394 DPRINTF(QLE_D_INTR, "%s: lip occurred\n", DEVNAME(sc)); 2395 break; 2396 2397 case QLE_ASYNC_LOOP_UP: 2398 DPRINTF(QLE_D_PORT, "%s: loop up\n", DEVNAME(sc)); 2399 sc->sc_loop_up = 1; 2400 sc->sc_marker_required = 1; 2401 qle_update_start(sc, QLE_UPDATE_TASK_UPDATE_TOPO | 2402 QLE_UPDATE_TASK_GET_PORT_LIST); 2403 break; 2404 2405 case QLE_ASYNC_LOOP_DOWN: 2406 DPRINTF(QLE_D_PORT, "%s: loop down\n", DEVNAME(sc)); 2407 sc->sc_loop_up = 0; 2408 qle_update_start(sc, QLE_UPDATE_TASK_CLEAR_ALL); 2409 break; 2410 2411 case QLE_ASYNC_LIP_RESET: 2412 DPRINTF(QLE_D_PORT, "%s: lip reset\n", DEVNAME(sc)); 2413 sc->sc_marker_required = 1; 2414 qle_update_start(sc, QLE_UPDATE_TASK_FABRIC_RELOGIN); 2415 break; 2416 2417 case QLE_ASYNC_PORT_DB_CHANGE: 2418 DPRINTF(QLE_D_PORT, "%s: port db changed %x\n", DEVNAME(sc), 2419 qle_read_mbox(sc, 1)); 2420 qle_update_start(sc, QLE_UPDATE_TASK_GET_PORT_LIST); 2421 break; 2422 2423 case QLE_ASYNC_CHANGE_NOTIFY: 2424 DPRINTF(QLE_D_PORT, "%s: name server change (%02x:%02x)\n", 2425 DEVNAME(sc), qle_read_mbox(sc, 1), qle_read_mbox(sc, 2)); 2426 qle_update_start(sc, QLE_UPDATE_TASK_GET_PORT_LIST); 2427 break; 2428 2429 case QLE_ASYNC_LIP_F8: 2430 DPRINTF(QLE_D_INTR, "%s: lip f8\n", DEVNAME(sc)); 2431 break; 2432 2433 case QLE_ASYNC_LOOP_INIT_ERROR: 2434 DPRINTF(QLE_D_PORT, "%s: loop initialization error: %x\n", 2435 DEVNAME(sc), qle_read_mbox(sc, 1)); 2436 break; 2437 2438 case QLE_ASYNC_POINT_TO_POINT: 2439 DPRINTF(QLE_D_PORT, "%s: connected in point-to-point mode\n", 2440 DEVNAME(sc)); 2441 break; 2442 2443 case QLE_ASYNC_ZIO_RESP_UPDATE: 2444 /* shouldn't happen, we don't do zio */ 2445 break; 2446 2447 default: 2448 DPRINTF(QLE_D_INTR, "%s: unknown async %x\n", DEVNAME(sc), info); 2449 break; 2450 } 2451 return (1); 2452 } 2453 2454 void 2455 qle_dump_stuff(struct qle_softc *sc, void *buf, int n) 2456 { 2457 #ifdef QLE_DEBUG 2458 u_int8_t *d = buf; 2459 int l; 2460 2461 if ((qledebug & QLE_D_IOCB) == 0) 2462 return; 2463 2464 printf("%s: stuff\n", DEVNAME(sc)); 2465 for (l = 0; l < n; l++) { 2466 printf(" %2.2x", d[l]); 2467 if (l % 16 == 15) 2468 printf("\n"); 2469 } 2470 if (n % 16 != 0) 2471 printf("\n"); 2472 #endif 2473 } 2474 2475 void 2476 qle_dump_iocb(struct qle_softc *sc, void *buf) 2477 { 2478 #ifdef QLE_DEBUG 2479 u_int8_t *iocb = buf; 2480 int l; 2481 int b; 2482 2483 if ((qledebug & QLE_D_IOCB) == 0) 2484 return; 2485 2486 printf("%s: iocb:\n", DEVNAME(sc)); 2487 for (l = 0; l < 4; l++) { 2488 for (b = 0; b < 16; b++) { 2489 printf(" %2.2x", iocb[(l*16)+b]); 2490 } 2491 printf("\n"); 2492 } 2493 #endif 2494 } 2495 2496 void 2497 qle_dump_iocb_segs(struct qle_softc *sc, void *segs, int n) 2498 { 2499 #ifdef QLE_DEBUG 2500 u_int8_t *buf = segs; 2501 int s, b; 2502 2503 if ((qledebug & QLE_D_IOCB) == 0) 2504 return; 2505 2506 printf("%s: iocb segs:\n", DEVNAME(sc)); 2507 for (s = 0; s < n; s++) { 2508 for (b = 0; b < sizeof(struct qle_iocb_seg); b++) { 2509 printf(" %2.2x", buf[(s*(sizeof(struct qle_iocb_seg))) 2510 + b]); 2511 } 2512 printf("\n"); 2513 } 2514 #endif 2515 } 2516 2517 void 2518 qle_put_marker(struct qle_softc *sc, void *buf) 2519 { 2520 struct qle_iocb_marker *marker = buf; 2521 2522 marker->entry_type = QLE_IOCB_MARKER; 2523 marker->entry_count = 1; 2524 marker->seqno = 0; 2525 marker->flags = 0; 2526 2527 /* could be more specific here; isp(4) isn't */ 2528 marker->target = 0; 2529 marker->modifier = QLE_IOCB_MARKER_SYNC_ALL; 2530 } 2531 2532 void 2533 qle_sge(struct qle_iocb_seg *seg, u_int64_t addr, u_int32_t len) 2534 { 2535 htolem32(&seg->seg_addr_lo, addr); 2536 htolem32(&seg->seg_addr_hi, addr >> 32); 2537 htolem32(&seg->seg_len, len); 2538 } 2539 2540 void 2541 qle_put_cmd(struct qle_softc *sc, void *buf, struct scsi_xfer *xs, 2542 struct qle_ccb *ccb, u_int32_t target_port) 2543 { 2544 bus_dmamap_t dmap = ccb->ccb_dmamap; 2545 struct qle_iocb_req6 *req = buf; 2546 struct qle_fcp_cmnd *cmnd; 2547 u_int64_t fcp_cmnd_offset; 2548 u_int32_t fcp_dl; 2549 int seg; 2550 int target = xs->sc_link->target; 2551 int lun = xs->sc_link->lun; 2552 u_int16_t flags; 2553 2554 memset(req, 0, sizeof(*req)); 2555 req->entry_type = QLE_IOCB_CMD_TYPE_6; 2556 req->entry_count = 1; 2557 2558 req->req_handle = ccb->ccb_id; 2559 htolem16(&req->req_nport_handle, target); 2560 2561 /* 2562 * timeout is in seconds. make sure it's at least 1 if a timeout 2563 * was specified in xs 2564 */ 2565 if (xs->timeout != 0) 2566 htolem16(&req->req_timeout, MAX(1, xs->timeout/1000)); 2567 2568 if (xs->datalen > 0) { 2569 flags = (xs->flags & SCSI_DATA_IN) ? 2570 QLE_IOCB_CTRL_FLAG_READ : QLE_IOCB_CTRL_FLAG_WRITE; 2571 if (dmap->dm_nsegs == 1) { 2572 qle_sge(&req->req_data_seg, dmap->dm_segs[0].ds_addr, 2573 dmap->dm_segs[0].ds_len); 2574 } else { 2575 flags |= QLE_IOCB_CTRL_FLAG_EXT_SEG; 2576 qle_sge(&req->req_data_seg, 2577 QLE_DMA_DVA(sc->sc_segments) + 2578 ccb->ccb_seg_offset, 2579 (ccb->ccb_dmamap->dm_nsegs + 1) * 2580 sizeof(struct qle_iocb_seg)); 2581 2582 for (seg = 0; seg < dmap->dm_nsegs; seg++) { 2583 qle_sge(&ccb->ccb_segs[seg], 2584 dmap->dm_segs[seg].ds_addr, 2585 dmap->dm_segs[seg].ds_len); 2586 } 2587 qle_sge(&ccb->ccb_segs[seg], 0, 0); 2588 2589 bus_dmamap_sync(sc->sc_dmat, 2590 QLE_DMA_MAP(sc->sc_segments), ccb->ccb_seg_offset, 2591 sizeof(*ccb->ccb_segs) * ccb->ccb_dmamap->dm_nsegs, 2592 BUS_DMASYNC_PREWRITE); 2593 } 2594 2595 htolem16(&req->req_data_seg_count, dmap->dm_nsegs); 2596 htolem32(&req->req_data_len, xs->datalen); 2597 htolem16(&req->req_ctrl_flags, flags); 2598 } 2599 2600 htobem16(&req->req_fcp_lun[0], lun); 2601 htobem16(&req->req_fcp_lun[1], lun >> 16); 2602 htolem32(&req->req_target_id, target_port & 0xffffff); 2603 2604 fcp_cmnd_offset = ccb->ccb_id * sizeof(*cmnd); 2605 /* set up FCP_CMND */ 2606 cmnd = (struct qle_fcp_cmnd *)QLE_DMA_KVA(sc->sc_fcp_cmnds) + 2607 ccb->ccb_id; 2608 2609 memset(cmnd, 0, sizeof(*cmnd)); 2610 htobem16(&cmnd->fcp_lun[0], lun); 2611 htobem16(&cmnd->fcp_lun[1], lun >> 16); 2612 /* cmnd->fcp_task_attr = TSK_SIMPLE; */ 2613 /* cmnd->fcp_task_mgmt = 0; */ 2614 memcpy(cmnd->fcp_cdb, xs->cmd, xs->cmdlen); 2615 2616 /* FCP_DL goes after the cdb */ 2617 fcp_dl = htobe32(xs->datalen); 2618 if (xs->cmdlen > 16) { 2619 htolem16(&req->req_fcp_cmnd_len, 12 + xs->cmdlen + 4); 2620 cmnd->fcp_add_cdb_len = xs->cmdlen - 16; 2621 memcpy(cmnd->fcp_cdb + xs->cmdlen, &fcp_dl, sizeof(fcp_dl)); 2622 } else { 2623 htolem16(&req->req_fcp_cmnd_len, 12 + 16 + 4); 2624 cmnd->fcp_add_cdb_len = 0; 2625 memcpy(cmnd->fcp_cdb + 16, &fcp_dl, sizeof(fcp_dl)); 2626 } 2627 if (xs->datalen > 0) 2628 cmnd->fcp_add_cdb_len |= (xs->flags & SCSI_DATA_IN) ? 2 : 1; 2629 2630 bus_dmamap_sync(sc->sc_dmat, 2631 QLE_DMA_MAP(sc->sc_fcp_cmnds), fcp_cmnd_offset, 2632 sizeof(*cmnd), BUS_DMASYNC_PREWRITE); 2633 2634 /* link req to cmnd */ 2635 fcp_cmnd_offset += QLE_DMA_DVA(sc->sc_fcp_cmnds); 2636 htolem32(&req->req_fcp_cmnd_addr_lo, fcp_cmnd_offset); 2637 htolem32(&req->req_fcp_cmnd_addr_hi, fcp_cmnd_offset >> 32); 2638 } 2639 2640 int 2641 qle_load_fwchunk(struct qle_softc *sc, struct qle_dmamem *mem, 2642 const u_int32_t *src) 2643 { 2644 u_int32_t dest, done, total; 2645 int i; 2646 2647 dest = src[2]; 2648 done = 0; 2649 total = src[3]; 2650 2651 while (done < total) { 2652 u_int32_t *copy; 2653 u_int32_t words; 2654 2655 /* limit transfer size otherwise it just doesn't work */ 2656 words = MIN(total - done, 1 << 10); 2657 copy = QLE_DMA_KVA(mem); 2658 for (i = 0; i < words; i++) { 2659 htolem32(©[i], src[done++]); 2660 } 2661 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, words * 4, 2662 BUS_DMASYNC_PREWRITE); 2663 2664 sc->sc_mbox[0] = QLE_MBOX_LOAD_RISC_RAM; 2665 sc->sc_mbox[1] = dest; 2666 sc->sc_mbox[4] = words >> 16; 2667 sc->sc_mbox[5] = words & 0xffff; 2668 sc->sc_mbox[8] = dest >> 16; 2669 qle_mbox_putaddr(sc->sc_mbox, mem); 2670 if (qle_mbox(sc, 0x01ff)) { 2671 printf("firmware load failed\n"); 2672 return (1); 2673 } 2674 bus_dmamap_sync(sc->sc_dmat, QLE_DMA_MAP(mem), 0, words * 4, 2675 BUS_DMASYNC_POSTWRITE); 2676 2677 dest += words; 2678 } 2679 2680 return (qle_verify_firmware(sc, src[2])); 2681 } 2682 2683 int 2684 qle_load_firmware_chunks(struct qle_softc *sc, const u_int32_t *fw) 2685 { 2686 struct qle_dmamem *mem; 2687 int res = 0; 2688 2689 mem = qle_dmamem_alloc(sc, 65536); 2690 for (;;) { 2691 if (qle_load_fwchunk(sc, mem, fw)) { 2692 res = 1; 2693 break; 2694 } 2695 if (fw[1] == 0) 2696 break; 2697 fw += fw[3]; 2698 } 2699 2700 qle_dmamem_free(sc, mem); 2701 return (res); 2702 } 2703 2704 u_int32_t 2705 qle_read_ram_word(struct qle_softc *sc, u_int32_t addr) 2706 { 2707 sc->sc_mbox[0] = QLE_MBOX_READ_RISC_RAM; 2708 sc->sc_mbox[1] = addr & 0xffff; 2709 sc->sc_mbox[8] = addr >> 16; 2710 if (qle_mbox(sc, 0x0103)) { 2711 return (0); 2712 } 2713 return ((sc->sc_mbox[3] << 16) | sc->sc_mbox[2]); 2714 } 2715 2716 int 2717 qle_verify_firmware(struct qle_softc *sc, u_int32_t addr) 2718 { 2719 /* 2720 * QLE_MBOX_VERIFY_CSUM requires at least the firmware header 2721 * to be correct, otherwise it wanders all over ISP memory and 2722 * gets lost. Check that chunk address (addr+2) is right and 2723 * size (addr+3) is plausible first. 2724 */ 2725 if ((qle_read_ram_word(sc, addr+2) != addr) || 2726 (qle_read_ram_word(sc, addr+3) > 0xffff)) { 2727 return (1); 2728 } 2729 2730 sc->sc_mbox[0] = QLE_MBOX_VERIFY_CSUM; 2731 sc->sc_mbox[1] = addr >> 16; 2732 sc->sc_mbox[2] = addr; 2733 if (qle_mbox(sc, 0x0007)) { 2734 return (1); 2735 } 2736 return (0); 2737 } 2738 2739 int 2740 qle_read_nvram(struct qle_softc *sc) 2741 { 2742 u_int32_t data[sizeof(sc->sc_nvram) / 4]; 2743 u_int32_t csum, tmp, v; 2744 int i, base, l; 2745 2746 switch (sc->sc_isp_gen) { 2747 case QLE_GEN_ISP24XX: 2748 base = 0x7ffe0080; 2749 break; 2750 case QLE_GEN_ISP25XX: 2751 base = 0x7ff48080; 2752 break; 2753 } 2754 base += sc->sc_port * 0x100; 2755 2756 csum = 0; 2757 for (i = 0; i < nitems(data); i++) { 2758 data[i] = 0xffffffff; 2759 qle_write(sc, QLE_FLASH_NVRAM_ADDR, base + i); 2760 for (l = 0; l < 5000; l++) { 2761 delay(10); 2762 tmp = qle_read(sc, QLE_FLASH_NVRAM_ADDR); 2763 if (tmp & (1U << 31)) { 2764 v = qle_read(sc, QLE_FLASH_NVRAM_DATA); 2765 csum += v; 2766 data[i] = letoh32(v); 2767 break; 2768 } 2769 } 2770 } 2771 2772 bcopy(data, &sc->sc_nvram, sizeof(sc->sc_nvram)); 2773 /* id field should be 'ISP' */ 2774 if (sc->sc_nvram.id[0] != 'I' || sc->sc_nvram.id[1] != 'S' || 2775 sc->sc_nvram.id[2] != 'P' || csum != 0) { 2776 printf("%s: nvram corrupt\n", DEVNAME(sc)); 2777 return (1); 2778 } 2779 return (0); 2780 } 2781 2782 struct qle_dmamem * 2783 qle_dmamem_alloc(struct qle_softc *sc, size_t size) 2784 { 2785 struct qle_dmamem *m; 2786 int nsegs; 2787 2788 m = malloc(sizeof(*m), M_DEVBUF, M_NOWAIT | M_ZERO); 2789 if (m == NULL) 2790 return (NULL); 2791 2792 m->qdm_size = size; 2793 2794 if (bus_dmamap_create(sc->sc_dmat, size, 1, size, 0, 2795 BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, &m->qdm_map) != 0) 2796 goto qdmfree; 2797 2798 if (bus_dmamem_alloc(sc->sc_dmat, size, PAGE_SIZE, 0, &m->qdm_seg, 1, 2799 &nsegs, BUS_DMA_NOWAIT | BUS_DMA_ZERO) != 0) 2800 goto destroy; 2801 2802 if (bus_dmamem_map(sc->sc_dmat, &m->qdm_seg, nsegs, size, &m->qdm_kva, 2803 BUS_DMA_NOWAIT) != 0) 2804 goto free; 2805 2806 if (bus_dmamap_load(sc->sc_dmat, m->qdm_map, m->qdm_kva, size, NULL, 2807 BUS_DMA_NOWAIT) != 0) 2808 goto unmap; 2809 2810 return (m); 2811 2812 unmap: 2813 bus_dmamem_unmap(sc->sc_dmat, m->qdm_kva, m->qdm_size); 2814 free: 2815 bus_dmamem_free(sc->sc_dmat, &m->qdm_seg, 1); 2816 destroy: 2817 bus_dmamap_destroy(sc->sc_dmat, m->qdm_map); 2818 qdmfree: 2819 free(m, M_DEVBUF, 0); 2820 2821 return (NULL); 2822 } 2823 2824 void 2825 qle_dmamem_free(struct qle_softc *sc, struct qle_dmamem *m) 2826 { 2827 bus_dmamap_unload(sc->sc_dmat, m->qdm_map); 2828 bus_dmamem_unmap(sc->sc_dmat, m->qdm_kva, m->qdm_size); 2829 bus_dmamem_free(sc->sc_dmat, &m->qdm_seg, 1); 2830 bus_dmamap_destroy(sc->sc_dmat, m->qdm_map); 2831 free(m, M_DEVBUF, 0); 2832 } 2833 2834 int 2835 qle_alloc_ccbs(struct qle_softc *sc) 2836 { 2837 struct qle_ccb *ccb; 2838 u_int8_t *cmd; 2839 int i; 2840 2841 SIMPLEQ_INIT(&sc->sc_ccb_free); 2842 mtx_init(&sc->sc_ccb_mtx, IPL_BIO); 2843 mtx_init(&sc->sc_queue_mtx, IPL_BIO); 2844 mtx_init(&sc->sc_port_mtx, IPL_BIO); 2845 mtx_init(&sc->sc_mbox_mtx, IPL_BIO); 2846 2847 sc->sc_ccbs = mallocarray(sc->sc_maxcmds, sizeof(struct qle_ccb), 2848 M_DEVBUF, M_WAITOK | M_CANFAIL | M_ZERO); 2849 if (sc->sc_ccbs == NULL) { 2850 printf("%s: unable to allocate ccbs\n", DEVNAME(sc)); 2851 return (1); 2852 } 2853 2854 sc->sc_requests = qle_dmamem_alloc(sc, sc->sc_maxcmds * 2855 QLE_QUEUE_ENTRY_SIZE); 2856 if (sc->sc_requests == NULL) { 2857 printf("%s: unable to allocate ccb dmamem\n", DEVNAME(sc)); 2858 goto free_ccbs; 2859 } 2860 sc->sc_responses = qle_dmamem_alloc(sc, sc->sc_maxcmds * 2861 QLE_QUEUE_ENTRY_SIZE); 2862 if (sc->sc_responses == NULL) { 2863 printf("%s: unable to allocate rcb dmamem\n", DEVNAME(sc)); 2864 goto free_req; 2865 } 2866 sc->sc_pri_requests = qle_dmamem_alloc(sc, 8 * QLE_QUEUE_ENTRY_SIZE); 2867 if (sc->sc_pri_requests == NULL) { 2868 printf("%s: unable to allocate pri ccb dmamem\n", DEVNAME(sc)); 2869 goto free_pri; 2870 } 2871 sc->sc_segments = qle_dmamem_alloc(sc, sc->sc_maxcmds * QLE_MAX_SEGS * 2872 sizeof(struct qle_iocb_seg)); 2873 if (sc->sc_segments == NULL) { 2874 printf("%s: unable to allocate iocb segments\n", DEVNAME(sc)); 2875 goto free_res; 2876 } 2877 2878 sc->sc_fcp_cmnds = qle_dmamem_alloc(sc, sc->sc_maxcmds * 2879 sizeof(struct qle_fcp_cmnd)); 2880 if (sc->sc_fcp_cmnds == NULL) { 2881 printf("%s: unable to allocate FCP_CMNDs\n", DEVNAME(sc)); 2882 goto free_seg; 2883 } 2884 2885 cmd = QLE_DMA_KVA(sc->sc_requests); 2886 memset(cmd, 0, QLE_QUEUE_ENTRY_SIZE * sc->sc_maxcmds); 2887 for (i = 0; i < sc->sc_maxcmds; i++) { 2888 ccb = &sc->sc_ccbs[i]; 2889 2890 if (bus_dmamap_create(sc->sc_dmat, MAXPHYS, 2891 QLE_MAX_SEGS, MAXPHYS, 0, 2892 BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW, 2893 &ccb->ccb_dmamap) != 0) { 2894 printf("%s: unable to create dma map\n", DEVNAME(sc)); 2895 goto free_maps; 2896 } 2897 2898 ccb->ccb_sc = sc; 2899 ccb->ccb_id = i; 2900 2901 ccb->ccb_seg_offset = i * QLE_MAX_SEGS * 2902 sizeof(struct qle_iocb_seg); 2903 ccb->ccb_segs = QLE_DMA_KVA(sc->sc_segments) + 2904 ccb->ccb_seg_offset; 2905 2906 qle_put_ccb(sc, ccb); 2907 } 2908 2909 scsi_iopool_init(&sc->sc_iopool, sc, qle_get_ccb, qle_put_ccb); 2910 return (0); 2911 2912 free_maps: 2913 while ((ccb = qle_get_ccb(sc)) != NULL) 2914 bus_dmamap_destroy(sc->sc_dmat, ccb->ccb_dmamap); 2915 2916 qle_dmamem_free(sc, sc->sc_fcp_cmnds); 2917 free_seg: 2918 qle_dmamem_free(sc, sc->sc_segments); 2919 free_pri: 2920 qle_dmamem_free(sc, sc->sc_pri_requests); 2921 free_res: 2922 qle_dmamem_free(sc, sc->sc_responses); 2923 free_req: 2924 qle_dmamem_free(sc, sc->sc_requests); 2925 free_ccbs: 2926 free(sc->sc_ccbs, M_DEVBUF, 0); 2927 2928 return (1); 2929 } 2930 2931 void 2932 qle_free_ccbs(struct qle_softc *sc) 2933 { 2934 struct qle_ccb *ccb; 2935 2936 scsi_iopool_destroy(&sc->sc_iopool); 2937 while ((ccb = qle_get_ccb(sc)) != NULL) 2938 bus_dmamap_destroy(sc->sc_dmat, ccb->ccb_dmamap); 2939 qle_dmamem_free(sc, sc->sc_segments); 2940 qle_dmamem_free(sc, sc->sc_responses); 2941 qle_dmamem_free(sc, sc->sc_requests); 2942 free(sc->sc_ccbs, M_DEVBUF, 0); 2943 } 2944 2945 void * 2946 qle_get_ccb(void *xsc) 2947 { 2948 struct qle_softc *sc = xsc; 2949 struct qle_ccb *ccb; 2950 2951 mtx_enter(&sc->sc_ccb_mtx); 2952 ccb = SIMPLEQ_FIRST(&sc->sc_ccb_free); 2953 if (ccb != NULL) { 2954 SIMPLEQ_REMOVE_HEAD(&sc->sc_ccb_free, ccb_link); 2955 } 2956 mtx_leave(&sc->sc_ccb_mtx); 2957 return (ccb); 2958 } 2959 2960 void 2961 qle_put_ccb(void *xsc, void *io) 2962 { 2963 struct qle_softc *sc = xsc; 2964 struct qle_ccb *ccb = io; 2965 2966 ccb->ccb_xs = NULL; 2967 mtx_enter(&sc->sc_ccb_mtx); 2968 SIMPLEQ_INSERT_HEAD(&sc->sc_ccb_free, ccb, ccb_link); 2969 mtx_leave(&sc->sc_ccb_mtx); 2970 } 2971