Print this page
NEX-5717 import QLogic 16G FC drivers
Reviewed by: Steve Peng <steve.peng@nexenta.com>
Reviewed by: Josef 'Jeff' Sipek <josef.sipek@nexenta.com>
Reviewed by: Yuri Pankov <yuri.pankov@nexenta.com>

*** 17,41 **** * information: Portions Copyright [yyyy] [name of copyright owner] * * CDDL HEADER END */ ! /* Copyright 2010 QLogic Corporation */ /* ! * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved. */ ! #pragma ident "Copyright 2010 QLogic Corporation; ql_init.c" /* * ISP2xxx Solaris Fibre Channel Adapter (FCA) driver source file. * * *********************************************************************** * * ** * * NOTICE ** ! * * COPYRIGHT (C) 1996-2010 QLOGIC CORPORATION ** * * ALL RIGHTS RESERVED ** * * ** * *********************************************************************** * */ --- 17,41 ---- * information: Portions Copyright [yyyy] [name of copyright owner] * * CDDL HEADER END */ ! /* Copyright 2015 QLogic Corporation */ /* ! * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved. */ ! #pragma ident "Copyright 2015 QLogic Corporation; ql_init.c" /* * ISP2xxx Solaris Fibre Channel Adapter (FCA) driver source file. * * *********************************************************************** * * ** * * NOTICE ** ! * * COPYRIGHT (C) 1996-2015 QLOGIC CORPORATION ** * * ALL RIGHTS RESERVED ** * * ** * *********************************************************************** * */
*** 57,78 **** /* * Local prototypes */ static uint16_t ql_nvram_request(ql_adapter_state_t *, uint32_t); static int ql_nvram_24xx_config(ql_adapter_state_t *); ! static void ql_23_properties(ql_adapter_state_t *, nvram_t *); ! static void ql_24xx_properties(ql_adapter_state_t *, nvram_24xx_t *); static int ql_check_isp_firmware(ql_adapter_state_t *); - static int ql_chip_diag(ql_adapter_state_t *); static int ql_load_flash_fw(ql_adapter_state_t *); static int ql_configure_loop(ql_adapter_state_t *); static int ql_configure_hba(ql_adapter_state_t *); static int ql_configure_fabric(ql_adapter_state_t *); static int ql_configure_device_d_id(ql_adapter_state_t *); static void ql_set_max_read_req(ql_adapter_state_t *); static void ql_configure_n_port_info(ql_adapter_state_t *); ! static void ql_clear_mcp(ql_adapter_state_t *); static void ql_mps_reset(ql_adapter_state_t *); /* * ql_initialize_adapter * Initialize board. --- 57,78 ---- /* * Local prototypes */ static uint16_t ql_nvram_request(ql_adapter_state_t *, uint32_t); static int ql_nvram_24xx_config(ql_adapter_state_t *); ! static void ql_23_properties(ql_adapter_state_t *, ql_init_cb_t *); ! static void ql_24xx_properties(ql_adapter_state_t *, ql_init_24xx_cb_t *); static int ql_check_isp_firmware(ql_adapter_state_t *); static int ql_load_flash_fw(ql_adapter_state_t *); static int ql_configure_loop(ql_adapter_state_t *); static int ql_configure_hba(ql_adapter_state_t *); static int ql_configure_fabric(ql_adapter_state_t *); static int ql_configure_device_d_id(ql_adapter_state_t *); + static void ql_update_dev(ql_adapter_state_t *, uint32_t); static void ql_set_max_read_req(ql_adapter_state_t *); static void ql_configure_n_port_info(ql_adapter_state_t *); ! static void ql_reset_24xx_chip(ql_adapter_state_t *); static void ql_mps_reset(ql_adapter_state_t *); /* * ql_initialize_adapter * Initialize board.
*** 93,103 **** class_svc_param_t *class3_param; caddr_t msg; la_els_logi_t *els = &ha->loginparams; int retries = 5; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); do { /* Clear adapter flags. */ TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= TASK_DAEMON_STOP_FLG | --- 93,103 ---- class_svc_param_t *class3_param; caddr_t msg; la_els_logi_t *els = &ha->loginparams; int retries = 5; ! QL_PRINT_10(ha, "started cfg=0x%llx\n", ha->cfg_flags); do { /* Clear adapter flags. */ TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= TASK_DAEMON_STOP_FLG |
*** 134,187 **** /* Get NVRAM configuration if needed. */ if (ha->init_ctrl_blk.cb.version == 0) { (void) ql_nvram_config(ha); } - /* Set login parameters. */ - if (CFG_IST(ha, CFG_CTRL_24258081)) { - els->common_service.rx_bufsize = CHAR_TO_SHORT( - ha->init_ctrl_blk.cb24.max_frame_length[0], - ha->init_ctrl_blk.cb24.max_frame_length[1]); - bcopy((void *)&ha->init_ctrl_blk.cb24.port_name[0], - (void *)&els->nport_ww_name.raw_wwn[0], 8); - bcopy((void *)&ha->init_ctrl_blk.cb24.node_name[0], - (void *)&els->node_ww_name.raw_wwn[0], 8); - } else { - els->common_service.rx_bufsize = CHAR_TO_SHORT( - ha->init_ctrl_blk.cb.max_frame_length[0], - ha->init_ctrl_blk.cb.max_frame_length[1]); - bcopy((void *)&ha->init_ctrl_blk.cb.port_name[0], - (void *)&els->nport_ww_name.raw_wwn[0], 8); - bcopy((void *)&ha->init_ctrl_blk.cb.node_name[0], - (void *)&els->node_ww_name.raw_wwn[0], 8); - } - bcopy(QL_VERSION, ha->adapter_stats->revlvl.qlddv, - strlen(QL_VERSION)); - /* Determine which RISC code to use. */ if ((rval = ql_check_isp_firmware(ha)) != QL_SUCCESS) { ! if ((rval = ql_chip_diag(ha)) == QL_SUCCESS) { rval = ql_load_isp_firmware(ha); } } if (rval == QL_SUCCESS && (rval = ql_set_cache_line(ha)) == QL_SUCCESS && (rval = ql_init_rings(ha)) == QL_SUCCESS) { (void) ql_fw_ready(ha, ha->fwwait); ! if (!(ha->task_daemon_flags & QL_SUSPENDED) && ha->loop_down_timer == LOOP_DOWN_TIMER_OFF) { if (ha->topology & QL_LOOP_CONNECTION) { ha->state = ha->state | FC_STATE_LOOP; msg = "Loop ONLINE"; ha->task_daemon_flags |= STATE_ONLINE; } else if (ha->topology & QL_P2P_CONNECTION) { ha->state = ha->state | FC_STATE_ONLINE; msg = "Link ONLINE"; ha->task_daemon_flags |= STATE_ONLINE; } else { msg = "Unknown Link state"; } } } else { --- 134,179 ---- /* Get NVRAM configuration if needed. */ if (ha->init_ctrl_blk.cb.version == 0) { (void) ql_nvram_config(ha); } /* Determine which RISC code to use. */ if ((rval = ql_check_isp_firmware(ha)) != QL_SUCCESS) { ! if (ha->dev_state != NX_DEV_READY) { ! EL(ha, "dev_state not ready, isp_abort_needed_2" ! "\n"); ! TASK_DAEMON_LOCK(ha); ! ha->task_daemon_flags |= ISP_ABORT_NEEDED; ! TASK_DAEMON_UNLOCK(ha); ! break; ! } ! if ((rval = ql_mbx_wrap_test(ha, NULL)) == QL_SUCCESS) { rval = ql_load_isp_firmware(ha); } } if (rval == QL_SUCCESS && (rval = ql_set_cache_line(ha)) == QL_SUCCESS && (rval = ql_init_rings(ha)) == QL_SUCCESS) { + ql_enable_intr(ha); (void) ql_fw_ready(ha, ha->fwwait); ! if (!DRIVER_SUSPENDED(ha) && ha->loop_down_timer == LOOP_DOWN_TIMER_OFF) { if (ha->topology & QL_LOOP_CONNECTION) { ha->state = ha->state | FC_STATE_LOOP; msg = "Loop ONLINE"; + TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= STATE_ONLINE; + TASK_DAEMON_UNLOCK(ha); } else if (ha->topology & QL_P2P_CONNECTION) { ha->state = ha->state | FC_STATE_ONLINE; msg = "Link ONLINE"; + TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= STATE_ONLINE; + TASK_DAEMON_UNLOCK(ha); } else { msg = "Unknown Link state"; } } } else {
*** 196,241 **** } while (retries-- != 0 && ha->task_daemon_flags & ISP_ABORT_NEEDED); cmn_err(CE_NOTE, "!Qlogic %s(%d): %s", QL_NAME, ha->instance, msg); ! /* Enable ISP interrupts and login parameters. */ ! if (CFG_IST(ha, CFG_CTRL_8021)) { ! ql_8021_enable_intrs(ha); ! } else if (CFG_IST(ha, CFG_CTRL_242581)) { ! WRT32_IO_REG(ha, ictrl, ISP_EN_RISC); ! } else { ! WRT16_IO_REG(ha, ictrl, ISP_EN_INT + ISP_EN_RISC); } ADAPTER_STATE_LOCK(ha); ! ha->flags |= (INTERRUPTS_ENABLED | ONLINE); ADAPTER_STATE_UNLOCK(ha); ! ha->task_daemon_flags &= ~(FC_STATE_CHANGE | RESET_MARKER_NEEDED | COMMAND_WAIT_NEEDED); /* * Setup login parameters. */ els->common_service.fcph_version = 0x2006; els->common_service.btob_credit = 3; ! els->common_service.cmn_features = 0x8800; els->common_service.conc_sequences = 0xff; els->common_service.relative_offset = 3; els->common_service.e_d_tov = 0x07d0; class3_param = (class_svc_param_t *)&els->class_3; class3_param->class_valid_svc_opt = 0x8800; class3_param->rcv_data_size = els->common_service.rx_bufsize; class3_param->conc_sequences = 0xff; if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 188,243 ---- } while (retries-- != 0 && ha->task_daemon_flags & ISP_ABORT_NEEDED); cmn_err(CE_NOTE, "!Qlogic %s(%d): %s", QL_NAME, ha->instance, msg); ! /* Enable ISP interrupts if not already enabled. */ ! if (!(ha->flags & INTERRUPTS_ENABLED)) { ! ql_enable_intr(ha); } ADAPTER_STATE_LOCK(ha); ! ha->flags |= ONLINE; ADAPTER_STATE_UNLOCK(ha); ! /* ! * Set flash write-protection. ! */ ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2) && ! ha->dev_state == NX_DEV_READY) { ! ql_24xx_protect_flash(ha); ! } ! ! TASK_DAEMON_LOCK(ha); ! ha->task_daemon_flags &= ~(FC_STATE_CHANGE | MARKER_NEEDED | COMMAND_WAIT_NEEDED); + TASK_DAEMON_UNLOCK(ha); /* * Setup login parameters. */ + bcopy(QL_VERSION, ha->adapter_stats->revlvl.qlddv, strlen(QL_VERSION)); + els->common_service.fcph_version = 0x2006; els->common_service.btob_credit = 3; ! els->common_service.cmn_features = ! ha->topology & QL_N_PORT ? 0x8000 : 0x8800; els->common_service.conc_sequences = 0xff; els->common_service.relative_offset = 3; els->common_service.e_d_tov = 0x07d0; class3_param = (class_svc_param_t *)&els->class_3; class3_param->class_valid_svc_opt = 0x8800; class3_param->rcv_data_size = els->common_service.rx_bufsize; class3_param->conc_sequences = 0xff; + class3_param->open_sequences_per_exch = 1; if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 255,265 **** ql_pci_sbus_config(ql_adapter_state_t *ha) { uint32_t timer; uint16_t cmd, w16; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); if (CFG_IST(ha, CFG_SBUS_CARD)) { w16 = (uint16_t)ddi_get16(ha->sbus_fpga_dev_handle, (uint16_t *)(ha->sbus_fpga_iobase + FPGA_REVISION)); EL(ha, "FPGA rev is %d.%d", (w16 & 0xf0) >> 4, --- 257,267 ---- ql_pci_sbus_config(ql_adapter_state_t *ha) { uint32_t timer; uint16_t cmd, w16; ! QL_PRINT_10(ha, "started\n"); if (CFG_IST(ha, CFG_SBUS_CARD)) { w16 = (uint16_t)ddi_get16(ha->sbus_fpga_dev_handle, (uint16_t *)(ha->sbus_fpga_iobase + FPGA_REVISION)); EL(ha, "FPGA rev is %d.%d", (w16 & 0xf0) >> 4,
*** 271,282 **** * want to make sure that all bits of interest to us * are properly set in command register. */ cmd = (uint16_t)ql_pci_config_get16(ha, PCI_CONF_COMM); cmd = (uint16_t)(cmd | PCI_COMM_IO | PCI_COMM_MAE | ! PCI_COMM_ME | PCI_COMM_MEMWR_INVAL | ! PCI_COMM_PARITY_DETECT | PCI_COMM_SERR_ENABLE); /* * If this is a 2300 card and not 2312, reset the * MEMWR_INVAL due to a bug in the 2300. Unfortunately, the * 2310 also reports itself as a 2300 so we need to get the --- 273,287 ---- * want to make sure that all bits of interest to us * are properly set in command register. */ cmd = (uint16_t)ql_pci_config_get16(ha, PCI_CONF_COMM); cmd = (uint16_t)(cmd | PCI_COMM_IO | PCI_COMM_MAE | ! PCI_COMM_ME | PCI_COMM_PARITY_DETECT | ! PCI_COMM_SERR_ENABLE); ! if (ql_get_cap_ofst(ha, PCI_CAP_ID_PCIX)) { ! cmd = (uint16_t)(cmd | PCI_COMM_MEMWR_INVAL); ! } /* * If this is a 2300 card and not 2312, reset the * MEMWR_INVAL due to a bug in the 2300. Unfortunately, the * 2310 also reports itself as a 2300 so we need to get the
*** 326,336 **** != 0) { ql_pci_config_put8(ha, 0x66, 0xc2); } } ! if (!(CFG_IST(ha, CFG_CTRL_8021)) && ha->pci_max_read_req != 0) { ql_set_max_read_req(ha); } ql_pci_config_put16(ha, PCI_CONF_COMM, cmd); --- 331,341 ---- != 0) { ql_pci_config_put8(ha, 0x66, 0xc2); } } ! if (!(CFG_IST(ha, CFG_CTRL_82XX)) && ha->pci_max_read_req != 0) { ql_set_max_read_req(ha); } ql_pci_config_put16(ha, PCI_CONF_COMM, cmd);
*** 340,355 **** /* Set latency register. */ ql_pci_config_put8(ha, PCI_CONF_LATENCY_TIMER, 0x40); /* Reset expansion ROM address decode enable. */ w16 = (uint16_t)ql_pci_config_get16(ha, PCI_CONF_ROM); w16 = (uint16_t)(w16 & ~BIT_0); ql_pci_config_put16(ha, PCI_CONF_ROM, w16); } ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); return (QL_SUCCESS); } /* --- 345,362 ---- /* Set latency register. */ ql_pci_config_put8(ha, PCI_CONF_LATENCY_TIMER, 0x40); /* Reset expansion ROM address decode enable. */ + if (!CFG_IST(ha, CFG_CTRL_278083)) { w16 = (uint16_t)ql_pci_config_get16(ha, PCI_CONF_ROM); w16 = (uint16_t)(w16 & ~BIT_0); ql_pci_config_put16(ha, PCI_CONF_ROM, w16); } + } ! QL_PRINT_10(ha, "done\n"); return (QL_SUCCESS); } /*
*** 368,430 **** */ static void ql_set_max_read_req(ql_adapter_state_t *ha) { uint16_t read_req, w16; uint16_t tmp = ha->pci_max_read_req; ! if ((ha->device_id == 0x2422) || ! ((ha->device_id & 0xff00) == 0x2300)) { /* check for vaild override value */ if (tmp == 512 || tmp == 1024 || tmp == 2048 || tmp == 4096) { /* shift away the don't cares */ tmp = (uint16_t)(tmp >> 10); /* convert bit pos to request value */ for (read_req = 0; tmp != 0; read_req++) { tmp = (uint16_t)(tmp >> 1); } ! w16 = (uint16_t)ql_pci_config_get16(ha, 0x4e); w16 = (uint16_t)(w16 & ~(BIT_3 & BIT_2)); w16 = (uint16_t)(w16 | (read_req << 2)); ! ql_pci_config_put16(ha, 0x4e, w16); } else { EL(ha, "invalid parameter value for " "'pci-max-read-request': %d; using system " "default\n", tmp); } ! } else if ((ha->device_id == 0x2432) || ((ha->device_id & 0xff00) == ! 0x2500) || (ha->device_id == 0x8432)) { ! /* check for vaild override value */ if (tmp == 128 || tmp == 256 || tmp == 512 || tmp == 1024 || tmp == 2048 || tmp == 4096) { /* shift away the don't cares */ tmp = (uint16_t)(tmp >> 8); /* convert bit pos to request value */ for (read_req = 0; tmp != 0; read_req++) { tmp = (uint16_t)(tmp >> 1); } ! w16 = (uint16_t)ql_pci_config_get16(ha, 0x54); w16 = (uint16_t)(w16 & ~(BIT_14 | BIT_13 | BIT_12)); w16 = (uint16_t)(w16 | (read_req << 12)); ! ql_pci_config_put16(ha, 0x54, w16); } else { EL(ha, "invalid parameter value for " "'pci-max-read-request': %d; using system " "default\n", tmp); } } } /* * NVRAM configuration. * * Input: * ha: adapter state pointer. ! * ha->hba_buf = request and response rings * * Output: * ha->init_ctrl_blk = initialization control block * host adapters parameters in host adapter block * --- 375,442 ---- */ static void ql_set_max_read_req(ql_adapter_state_t *ha) { + int ofst; uint16_t read_req, w16; uint16_t tmp = ha->pci_max_read_req; ! QL_PRINT_3(ha, "started\n"); ! ! if ((ofst = ql_get_cap_ofst(ha, PCI_CAP_ID_PCIX))) { ! ofst += PCI_PCIX_COMMAND; ! QL_PRINT_10(ha, "PCI-X Command Reg = %xh\n", ofst); /* check for vaild override value */ if (tmp == 512 || tmp == 1024 || tmp == 2048 || tmp == 4096) { /* shift away the don't cares */ tmp = (uint16_t)(tmp >> 10); /* convert bit pos to request value */ for (read_req = 0; tmp != 0; read_req++) { tmp = (uint16_t)(tmp >> 1); } ! w16 = (uint16_t)ql_pci_config_get16(ha, ofst); w16 = (uint16_t)(w16 & ~(BIT_3 & BIT_2)); w16 = (uint16_t)(w16 | (read_req << 2)); ! ql_pci_config_put16(ha, ofst, w16); } else { EL(ha, "invalid parameter value for " "'pci-max-read-request': %d; using system " "default\n", tmp); } ! } else if ((ofst = ql_get_cap_ofst(ha, PCI_CAP_ID_PCI_E))) { ! ofst += PCI_PCIE_DEVICE_CONTROL; ! QL_PRINT_10(ha, "PCI-E Device Control Reg = %xh\n", ofst); if (tmp == 128 || tmp == 256 || tmp == 512 || tmp == 1024 || tmp == 2048 || tmp == 4096) { /* shift away the don't cares */ tmp = (uint16_t)(tmp >> 8); /* convert bit pos to request value */ for (read_req = 0; tmp != 0; read_req++) { tmp = (uint16_t)(tmp >> 1); } ! w16 = (uint16_t)ql_pci_config_get16(ha, ofst); w16 = (uint16_t)(w16 & ~(BIT_14 | BIT_13 | BIT_12)); w16 = (uint16_t)(w16 | (read_req << 12)); ! ql_pci_config_put16(ha, ofst, w16); } else { EL(ha, "invalid parameter value for " "'pci-max-read-request': %d; using system " "default\n", tmp); } } + QL_PRINT_3(ha, "done\n"); } /* * NVRAM configuration. * * Input: * ha: adapter state pointer. ! * ha->req_q[0]: request ring * * Output: * ha->init_ctrl_blk = initialization control block * host adapters parameters in host adapter block *
*** 439,467 **** { uint32_t cnt; caddr_t dptr1, dptr2; ql_init_cb_t *icb = &ha->init_ctrl_blk.cb; ql_ip_init_cb_t *ip_icb = &ha->ip_init_ctrl_blk.cb; ! nvram_t *nv = (nvram_t *)ha->request_ring_bp; ! uint16_t *wptr = (uint16_t *)ha->request_ring_bp; uint8_t chksum = 0; int rval; int idpromlen; char idprombuf[32]; uint32_t start_addr; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); ! if (CFG_IST(ha, CFG_CTRL_24258081)) { return (ql_nvram_24xx_config(ha)); } start_addr = 0; if ((rval = ql_lock_nvram(ha, &start_addr, LNF_NVRAM_DATA)) == QL_SUCCESS) { /* Verify valid NVRAM checksum. */ ! for (cnt = 0; cnt < sizeof (nvram_t)/2; cnt++) { *wptr = (uint16_t)ql_get_nvram_word(ha, (uint32_t)(cnt + start_addr)); chksum = (uint8_t)(chksum + (uint8_t)*wptr); chksum = (uint8_t)(chksum + (uint8_t)(*wptr >> 8)); wptr++; --- 451,480 ---- { uint32_t cnt; caddr_t dptr1, dptr2; ql_init_cb_t *icb = &ha->init_ctrl_blk.cb; ql_ip_init_cb_t *ip_icb = &ha->ip_init_ctrl_blk.cb; ! nvram_t *nv = (nvram_t *)ha->req_q[0]->req_ring.bp; ! uint16_t *wptr = (uint16_t *)ha->req_q[0]->req_ring.bp; uint8_t chksum = 0; int rval; int idpromlen; char idprombuf[32]; uint32_t start_addr; + la_els_logi_t *els = &ha->loginparams; ! QL_PRINT_10(ha, "started\n"); ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2)) { return (ql_nvram_24xx_config(ha)); } start_addr = 0; if ((rval = ql_lock_nvram(ha, &start_addr, LNF_NVRAM_DATA)) == QL_SUCCESS) { /* Verify valid NVRAM checksum. */ ! for (cnt = 0; cnt < sizeof (nvram_t) / 2; cnt++) { *wptr = (uint16_t)ql_get_nvram_word(ha, (uint32_t)(cnt + start_addr)); chksum = (uint8_t)(chksum + (uint8_t)*wptr); chksum = (uint8_t)(chksum + (uint8_t)(*wptr >> 8)); wptr++;
*** 479,489 **** "nvram_version=%x\n", rval, chksum, nv->id[0], nv->id[1], nv->id[2], nv->id[3], ha->xioctl->fdesc.flash_size, ha->subven_id, nv->nvram_version); /* Don't print nvram message if it's an on-board 2200 */ ! if (!((CFG_IST(ha, CFG_CTRL_2200)) && (ha->xioctl->fdesc.flash_size == 0))) { cmn_err(CE_WARN, "%s(%d): NVRAM configuration failed," " using driver defaults.", QL_NAME, ha->instance); } --- 492,502 ---- "nvram_version=%x\n", rval, chksum, nv->id[0], nv->id[1], nv->id[2], nv->id[3], ha->xioctl->fdesc.flash_size, ha->subven_id, nv->nvram_version); /* Don't print nvram message if it's an on-board 2200 */ ! if (!((CFG_IST(ha, CFG_CTRL_22XX)) && (ha->xioctl->fdesc.flash_size == 0))) { cmn_err(CE_WARN, "%s(%d): NVRAM configuration failed," " using driver defaults.", QL_NAME, ha->instance); }
*** 500,510 **** nv->max_frame_length[1] = 4; /* * Allow 2048 byte frames for 2300 */ ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) { nv->max_frame_length[1] = 8; } nv->max_iocb_allocation[1] = 1; nv->execution_throttle[0] = 16; nv->login_retry_count = 8; --- 513,523 ---- nv->max_frame_length[1] = 4; /* * Allow 2048 byte frames for 2300 */ ! if (CFG_IST(ha, CFG_CTRL_2363)) { nv->max_frame_length[1] = 8; } nv->max_iocb_allocation[1] = 1; nv->execution_throttle[0] = 16; nv->login_retry_count = 8;
*** 514,525 **** /*LINTED [Solaris DDI_DEV_T_ANY Lint warning]*/ if (ddi_getlongprop_buf(DDI_DEV_T_ANY, ha->dip, DDI_PROP_CANSLEEP, "idprom", (caddr_t)idprombuf, &idpromlen) != DDI_PROP_SUCCESS) { ! QL_PRINT_3(CE_CONT, "(%d): Unable to read idprom " ! "property\n", ha->instance); cmn_err(CE_WARN, "%s(%d) : Unable to read idprom " "property", QL_NAME, ha->instance); nv->port_name[2] = 33; nv->port_name[3] = 224; --- 527,538 ---- /*LINTED [Solaris DDI_DEV_T_ANY Lint warning]*/ if (ddi_getlongprop_buf(DDI_DEV_T_ANY, ha->dip, DDI_PROP_CANSLEEP, "idprom", (caddr_t)idprombuf, &idpromlen) != DDI_PROP_SUCCESS) { ! QL_PRINT_10(ha, "Unable to read idprom " ! "property\n"); cmn_err(CE_WARN, "%s(%d) : Unable to read idprom " "property", QL_NAME, ha->instance); nv->port_name[2] = 33; nv->port_name[3] = 224;
*** 537,547 **** nv->port_name[0] = (uint8_t) (NAA_ID_IEEE_EXTENDED << 4 | ha->instance); } /* Don't print nvram message if it's an on-board 2200 */ ! if (!(CFG_IST(ha, CFG_CTRL_2200)) && (ha->xioctl->fdesc.flash_size == 0)) { cmn_err(CE_WARN, "%s(%d): Unreliable HBA NVRAM, using" " default HBA parameters and temporary WWPN:" " %02x%02x%02x%02x%02x%02x%02x%02x", QL_NAME, ha->instance, nv->port_name[0], nv->port_name[1], --- 550,560 ---- nv->port_name[0] = (uint8_t) (NAA_ID_IEEE_EXTENDED << 4 | ha->instance); } /* Don't print nvram message if it's an on-board 2200 */ ! if (!(CFG_IST(ha, CFG_CTRL_22XX)) && (ha->xioctl->fdesc.flash_size == 0)) { cmn_err(CE_WARN, "%s(%d): Unreliable HBA NVRAM, using" " default HBA parameters and temporary WWPN:" " %02x%02x%02x%02x%02x%02x%02x%02x", QL_NAME, ha->instance, nv->port_name[0], nv->port_name[1],
*** 551,561 **** } nv->login_timeout = 4; /* Set default connection options for the 23xx to 2 */ ! if (!(CFG_IST(ha, CFG_CTRL_2200))) { nv->add_fw_opt[0] = (uint8_t)(nv->add_fw_opt[0] | BIT_5); } /* --- 564,574 ---- } nv->login_timeout = 4; /* Set default connection options for the 23xx to 2 */ ! if (!(CFG_IST(ha, CFG_CTRL_22XX))) { nv->add_fw_opt[0] = (uint8_t)(nv->add_fw_opt[0] | BIT_5); } /*
*** 568,606 **** nv->maximum_luns_per_target[0] = 8; rval = QL_FUNCTION_FAILED; } - /* Check for adapter node name (big endian). */ - for (cnt = 0; cnt < 8; cnt++) { - if (nv->node_name[cnt] != 0) { - break; - } - } - - /* Copy port name if no node name (big endian). */ - if (cnt == 8) { - bcopy((void *)&nv->port_name[0], (void *)&nv->node_name[0], 8); - nv->node_name[0] = (uint8_t)(nv->node_name[0] & ~BIT_0); - nv->port_name[0] = (uint8_t)(nv->node_name[0] | BIT_0); - } - /* Reset initialization control blocks. */ bzero((void *)icb, sizeof (ql_init_cb_t)); - /* Get driver properties. */ - ql_23_properties(ha, nv); - - cmn_err(CE_CONT, "!Qlogic %s(%d) WWPN=%02x%02x%02x%02x" - "%02x%02x%02x%02x : WWNN=%02x%02x%02x%02x%02x%02x%02x%02x\n", - QL_NAME, ha->instance, nv->port_name[0], nv->port_name[1], - nv->port_name[2], nv->port_name[3], nv->port_name[4], - nv->port_name[5], nv->port_name[6], nv->port_name[7], - nv->node_name[0], nv->node_name[1], nv->node_name[2], - nv->node_name[3], nv->node_name[4], nv->node_name[5], - nv->node_name[6], nv->node_name[7]); - /* * Copy over NVRAM RISC parameter block * to initialization control block. */ dptr1 = (caddr_t)icb; --- 581,594 ---- nv->maximum_luns_per_target[0] = 8; rval = QL_FUNCTION_FAILED; } /* Reset initialization control blocks. */ bzero((void *)icb, sizeof (ql_init_cb_t)); + bzero((void *)ip_icb, sizeof (ql_ip_init_cb_t)); /* * Copy over NVRAM RISC parameter block * to initialization control block. */ dptr1 = (caddr_t)icb;
*** 613,627 **** /* Copy 2nd half. */ dptr1 = (caddr_t)&icb->add_fw_opt[0]; cnt = (uint32_t)((uintptr_t)&icb->reserved_3[0] - (uintptr_t)&icb->add_fw_opt[0]); - while (cnt-- != 0) { *dptr1++ = *dptr2++; } /* * Setup driver firmware options. */ icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] | BIT_6 | BIT_1); --- 601,667 ---- /* Copy 2nd half. */ dptr1 = (caddr_t)&icb->add_fw_opt[0]; cnt = (uint32_t)((uintptr_t)&icb->reserved_3[0] - (uintptr_t)&icb->add_fw_opt[0]); while (cnt-- != 0) { *dptr1++ = *dptr2++; } + ha->execution_throttle = CHAR_TO_SHORT(nv->execution_throttle[0], + nv->execution_throttle[1]); + ha->loop_reset_delay = nv->reset_delay; + ha->port_down_retry_count = nv->port_down_retry_count; + ha->maximum_luns_per_target = CHAR_TO_SHORT( + nv->maximum_luns_per_target[0], nv->maximum_luns_per_target[1]); + if (ha->maximum_luns_per_target == 0) { + ha->maximum_luns_per_target++; + } + ha->adapter_features = CHAR_TO_SHORT(nv->adapter_features[0], + nv->adapter_features[1]); + + /* Check for adapter node name (big endian). */ + for (cnt = 0; cnt < 8; cnt++) { + if (icb->node_name[cnt] != 0) { + break; + } + } + + /* Copy port name if no node name (big endian). */ + if (cnt == 8) { + for (cnt = 0; cnt < 8; cnt++) { + icb->node_name[cnt] = icb->port_name[cnt]; + } + icb->node_name[0] = (uint8_t)(icb->node_name[0] & ~BIT_0); + icb->port_name[0] = (uint8_t)(icb->node_name[0] | BIT_0); + } + + ADAPTER_STATE_LOCK(ha); + ha->cfg_flags &= ~(CFG_ENABLE_FULL_LIP_LOGIN | CFG_ENABLE_TARGET_RESET | + CFG_ENABLE_LIP_RESET | CFG_LOAD_FLASH_FW | CFG_FAST_TIMEOUT | + CFG_DISABLE_RISC_CODE_LOAD | CFG_ENABLE_FWEXTTRACE | + CFG_ENABLE_FWFCETRACE | CFG_SET_CACHE_LINE_SIZE_1 | CFG_LR_SUPPORT); + if (nv->host_p[0] & BIT_4) { + ha->cfg_flags |= CFG_DISABLE_RISC_CODE_LOAD; + } + if (nv->host_p[0] & BIT_5) { + ha->cfg_flags |= CFG_SET_CACHE_LINE_SIZE_1; + } + if (nv->host_p[1] & BIT_2) { + ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN; + } + if (nv->host_p[1] & BIT_3) { + ha->cfg_flags |= CFG_ENABLE_TARGET_RESET; + } + nv->adapter_features[0] & BIT_3 ? + (ha->flags |= MULTI_CHIP_ADAPTER) : + (ha->flags &= ~MULTI_CHIP_ADAPTER); + ADAPTER_STATE_UNLOCK(ha); + + /* Get driver properties. */ + ql_23_properties(ha, icb); + /* * Setup driver firmware options. */ icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] | BIT_6 | BIT_1);
*** 629,639 **** /* * There is no use enabling fast post for SBUS or 2300 * Always enable 64bit addressing, except SBUS cards. */ ha->cfg_flags |= CFG_ENABLE_64BIT_ADDRESSING; ! if (CFG_IST(ha, (CFG_SBUS_CARD | CFG_CTRL_2300 | CFG_CTRL_6322))) { icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] & ~BIT_3); if (CFG_IST(ha, CFG_SBUS_CARD)) { icb->special_options[0] = (uint8_t) (icb->special_options[0] | BIT_5); --- 669,679 ---- /* * There is no use enabling fast post for SBUS or 2300 * Always enable 64bit addressing, except SBUS cards. */ ha->cfg_flags |= CFG_ENABLE_64BIT_ADDRESSING; ! if (CFG_IST(ha, CFG_SBUS_CARD | CFG_CTRL_2363)) { icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] & ~BIT_3); if (CFG_IST(ha, CFG_SBUS_CARD)) { icb->special_options[0] = (uint8_t) (icb->special_options[0] | BIT_5);
*** 651,745 **** BIT_7 | BIT_6 | BIT_5 | BIT_2 | BIT_0); icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] & ~(BIT_5 | BIT_4)); icb->firmware_options[1] = (uint8_t) (icb->firmware_options[1] & ~BIT_4); ! icb->add_fw_opt[1] = (uint8_t)(icb->add_fw_opt[1] & ~(BIT_5 | BIT_4)); icb->special_options[0] = (uint8_t)(icb->special_options[0] | BIT_1); ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) { if ((icb->special_options[1] & 0x20) == 0) { EL(ha, "50 ohm is not set\n"); } } - icb->execution_throttle[0] = 0xff; - icb->execution_throttle[1] = 0xff; - if (CFG_IST(ha, CFG_ENABLE_FCP_2_SUPPORT)) { - icb->firmware_options[1] = (uint8_t) - (icb->firmware_options[1] | BIT_7 | BIT_6); - icb->add_fw_opt[1] = (uint8_t) - (icb->add_fw_opt[1] | BIT_5 | BIT_4); - } - /* * Set host adapter parameters */ ! ADAPTER_STATE_LOCK(ha); ! ha->nvram_version = nv->nvram_version; ! ha->adapter_features = CHAR_TO_SHORT(nv->adapter_features[0], ! nv->adapter_features[1]); - nv->host_p[0] & BIT_4 ? (ha->cfg_flags |= CFG_DISABLE_RISC_CODE_LOAD) : - (ha->cfg_flags &= ~CFG_DISABLE_RISC_CODE_LOAD); - nv->host_p[0] & BIT_5 ? (ha->cfg_flags |= CFG_SET_CACHE_LINE_SIZE_1) : - (ha->cfg_flags &= ~CFG_SET_CACHE_LINE_SIZE_1); - - nv->host_p[1] & BIT_1 ? (ha->cfg_flags |= CFG_ENABLE_LIP_RESET) : - (ha->cfg_flags &= ~CFG_ENABLE_LIP_RESET); - nv->host_p[1] & BIT_2 ? (ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN) : - (ha->cfg_flags &= ~CFG_ENABLE_FULL_LIP_LOGIN); - nv->host_p[1] & BIT_3 ? (ha->cfg_flags |= CFG_ENABLE_TARGET_RESET) : - (ha->cfg_flags &= ~CFG_ENABLE_TARGET_RESET); - - nv->adapter_features[0] & BIT_3 ? - (ha->cfg_flags |= CFG_MULTI_CHIP_ADAPTER) : - (ha->cfg_flags &= ~CFG_MULTI_CHIP_ADAPTER); - - ADAPTER_STATE_UNLOCK(ha); - - ha->execution_throttle = CHAR_TO_SHORT(nv->execution_throttle[0], - nv->execution_throttle[1]); - ha->loop_reset_delay = nv->reset_delay; - ha->port_down_retry_count = nv->port_down_retry_count; ha->r_a_tov = (uint16_t)(icb->login_timeout < R_A_TOV_DEFAULT ? R_A_TOV_DEFAULT : icb->login_timeout); - ha->maximum_luns_per_target = CHAR_TO_SHORT( - nv->maximum_luns_per_target[0], nv->maximum_luns_per_target[1]); - if (ha->maximum_luns_per_target == 0) { - ha->maximum_luns_per_target++; - } /* * Setup ring parameters in initialization control block */ ! cnt = REQUEST_ENTRY_CNT; icb->request_q_length[0] = LSB(cnt); icb->request_q_length[1] = MSB(cnt); ! cnt = RESPONSE_ENTRY_CNT; icb->response_q_length[0] = LSB(cnt); icb->response_q_length[1] = MSB(cnt); ! icb->request_q_address[0] = LSB(LSW(LSD(ha->request_dvma))); ! icb->request_q_address[1] = MSB(LSW(LSD(ha->request_dvma))); ! icb->request_q_address[2] = LSB(MSW(LSD(ha->request_dvma))); ! icb->request_q_address[3] = MSB(MSW(LSD(ha->request_dvma))); ! icb->request_q_address[4] = LSB(LSW(MSD(ha->request_dvma))); ! icb->request_q_address[5] = MSB(LSW(MSD(ha->request_dvma))); ! icb->request_q_address[6] = LSB(MSW(MSD(ha->request_dvma))); ! icb->request_q_address[7] = MSB(MSW(MSD(ha->request_dvma))); ! icb->response_q_address[0] = LSB(LSW(LSD(ha->response_dvma))); ! icb->response_q_address[1] = MSB(LSW(LSD(ha->response_dvma))); ! icb->response_q_address[2] = LSB(MSW(LSD(ha->response_dvma))); ! icb->response_q_address[3] = MSB(MSW(LSD(ha->response_dvma))); ! icb->response_q_address[4] = LSB(LSW(MSD(ha->response_dvma))); ! icb->response_q_address[5] = MSB(LSW(MSD(ha->response_dvma))); ! icb->response_q_address[6] = LSB(MSW(MSD(ha->response_dvma))); ! icb->response_q_address[7] = MSB(MSW(MSD(ha->response_dvma))); /* * Setup IP initialization control block */ ip_icb->version = IP_ICB_VERSION; --- 691,777 ---- BIT_7 | BIT_6 | BIT_5 | BIT_2 | BIT_0); icb->firmware_options[0] = (uint8_t) (icb->firmware_options[0] & ~(BIT_5 | BIT_4)); icb->firmware_options[1] = (uint8_t) (icb->firmware_options[1] & ~BIT_4); ! if (CFG_IST(ha, CFG_ENABLE_FCP_2_SUPPORT)) { ! icb->firmware_options[1] = (uint8_t) ! (icb->firmware_options[1] | BIT_7 | BIT_6); ! icb->add_fw_opt[1] = (uint8_t) ! (icb->add_fw_opt[1] | BIT_5 | BIT_4); ! } icb->add_fw_opt[1] = (uint8_t)(icb->add_fw_opt[1] & ~(BIT_5 | BIT_4)); icb->special_options[0] = (uint8_t)(icb->special_options[0] | BIT_1); ! if (CFG_IST(ha, CFG_CTRL_2363)) { if ((icb->special_options[1] & 0x20) == 0) { EL(ha, "50 ohm is not set\n"); } } /* * Set host adapter parameters */ ! /* Get adapter id string for Sun branded 23xx only */ ! if (CFG_IST(ha, CFG_CTRL_23XX) && nv->adapInfo[0] != 0) { ! (void) snprintf((int8_t *)ha->adapInfo, 16, "%s", ! nv->adapInfo); ! } ha->r_a_tov = (uint16_t)(icb->login_timeout < R_A_TOV_DEFAULT ? R_A_TOV_DEFAULT : icb->login_timeout); + els->common_service.rx_bufsize = CHAR_TO_SHORT( + icb->max_frame_length[0], icb->max_frame_length[1]); + bcopy((void *)icb->port_name, (void *)els->nport_ww_name.raw_wwn, 8); + bcopy((void *)icb->node_name, (void *)els->node_ww_name.raw_wwn, 8); + + cmn_err(CE_CONT, "!Qlogic %s(%d) WWPN=%02x%02x%02x%02x" + "%02x%02x%02x%02x : WWNN=%02x%02x%02x%02x%02x%02x%02x%02x\n", + QL_NAME, ha->instance, + els->nport_ww_name.raw_wwn[0], els->nport_ww_name.raw_wwn[1], + els->nport_ww_name.raw_wwn[2], els->nport_ww_name.raw_wwn[3], + els->nport_ww_name.raw_wwn[4], els->nport_ww_name.raw_wwn[5], + els->nport_ww_name.raw_wwn[6], els->nport_ww_name.raw_wwn[7], + els->node_ww_name.raw_wwn[0], els->node_ww_name.raw_wwn[1], + els->node_ww_name.raw_wwn[2], els->node_ww_name.raw_wwn[3], + els->node_ww_name.raw_wwn[4], els->node_ww_name.raw_wwn[5], + els->node_ww_name.raw_wwn[6], els->node_ww_name.raw_wwn[7]); /* * Setup ring parameters in initialization control block */ ! cnt = ha->req_q[0]->req_entry_cnt; icb->request_q_length[0] = LSB(cnt); icb->request_q_length[1] = MSB(cnt); ! cnt = ha->rsp_queues[0]->rsp_entry_cnt; icb->response_q_length[0] = LSB(cnt); icb->response_q_length[1] = MSB(cnt); ! start_addr = ha->req_q[0]->req_ring.cookie.dmac_address; ! icb->request_q_address[0] = LSB(LSW(start_addr)); ! icb->request_q_address[1] = MSB(LSW(start_addr)); ! icb->request_q_address[2] = LSB(MSW(start_addr)); ! icb->request_q_address[3] = MSB(MSW(start_addr)); ! start_addr = ha->req_q[0]->req_ring.cookie.dmac_notused; ! icb->request_q_address[4] = LSB(LSW(start_addr)); ! icb->request_q_address[5] = MSB(LSW(start_addr)); ! icb->request_q_address[6] = LSB(MSW(start_addr)); ! icb->request_q_address[7] = MSB(MSW(start_addr)); + start_addr = ha->rsp_queues[0]->rsp_ring.cookie.dmac_address; + icb->response_q_address[0] = LSB(LSW(start_addr)); + icb->response_q_address[1] = MSB(LSW(start_addr)); + icb->response_q_address[2] = LSB(MSW(start_addr)); + icb->response_q_address[3] = MSB(MSW(start_addr)); + + start_addr = ha->rsp_queues[0]->rsp_ring.cookie.dmac_notused; + icb->response_q_address[4] = LSB(LSW(start_addr)); + icb->response_q_address[5] = MSB(LSW(start_addr)); + icb->response_q_address[6] = LSB(MSW(start_addr)); + icb->response_q_address[7] = MSB(MSW(start_addr)); + /* * Setup IP initialization control block */ ip_icb->version = IP_ICB_VERSION;
*** 753,776 **** cnt = RCVBUF_CONTAINER_CNT; ip_icb->queue_size[0] = LSB(cnt); ip_icb->queue_size[1] = MSB(cnt); ! ip_icb->queue_address[0] = LSB(LSW(LSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[1] = MSB(LSW(LSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[2] = LSB(MSW(LSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[3] = MSB(MSW(LSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[4] = LSB(LSW(MSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[5] = MSB(LSW(MSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[6] = LSB(MSW(MSD(ha->rcvbuf_dvma))); ! ip_icb->queue_address[7] = MSB(MSW(MSD(ha->rcvbuf_dvma))); if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 785,811 ---- cnt = RCVBUF_CONTAINER_CNT; ip_icb->queue_size[0] = LSB(cnt); ip_icb->queue_size[1] = MSB(cnt); ! start_addr = ha->rcv_ring.cookie.dmac_address; ! ip_icb->queue_address[0] = LSB(LSW(start_addr)); ! ip_icb->queue_address[1] = MSB(LSW(start_addr)); ! ip_icb->queue_address[2] = LSB(MSW(start_addr)); ! ip_icb->queue_address[3] = MSB(MSW(start_addr)); + start_addr = ha->rcv_ring.cookie.dmac_notused; + ip_icb->queue_address[4] = LSB(LSW(start_addr)); + ip_icb->queue_address[5] = MSB(LSW(start_addr)); + ip_icb->queue_address[6] = LSB(MSW(start_addr)); + ip_icb->queue_address[7] = MSB(MSW(start_addr)); + if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 792,809 **** ql_get_nvram_word(ql_adapter_state_t *ha, uint32_t address) { uint32_t nv_cmd; uint16_t rval; ! QL_PRINT_4(CE_CONT, "(%d): started\n", ha->instance); nv_cmd = address << 16; nv_cmd = nv_cmd | NV_READ_OP; rval = (uint16_t)ql_nvram_request(ha, nv_cmd); ! QL_PRINT_4(CE_CONT, "(%d): NVRAM data = %xh\n", ha->instance, rval); return (rval); } /* --- 827,844 ---- ql_get_nvram_word(ql_adapter_state_t *ha, uint32_t address) { uint32_t nv_cmd; uint16_t rval; ! QL_PRINT_4(ha, "started\n"); nv_cmd = address << 16; nv_cmd = nv_cmd | NV_READ_OP; rval = (uint16_t)ql_nvram_request(ha, nv_cmd); ! QL_PRINT_4(ha, "NVRAM data = %xh\n", rval); return (rval); } /*
*** 843,853 **** } /* Read data from NVRAM. */ for (cnt = 0; cnt < 16; cnt++) { ! WRT16_IO_REG(ha, nvram, NV_SELECT+NV_CLOCK); ql_nv_delay(); data <<= 1; reg_data = RD16_IO_REG(ha, nvram); if (reg_data & NV_DATA_IN) { data = (uint16_t)(data | BIT_0); --- 878,888 ---- } /* Read data from NVRAM. */ for (cnt = 0; cnt < 16; cnt++) { ! WRT16_IO_REG(ha, nvram, NV_SELECT + NV_CLOCK); ql_nv_delay(); data <<= 1; reg_data = RD16_IO_REG(ha, nvram); if (reg_data & NV_DATA_IN) { data = (uint16_t)(data | BIT_0);
*** 885,895 **** * ql_nvram_24xx_config * ISP2400 nvram. * * Input: * ha: adapter state pointer. ! * ha->hba_buf = request and response rings * * Output: * ha->init_ctrl_blk = initialization control block * host adapters parameters in host adapter block * --- 920,930 ---- * ql_nvram_24xx_config * ISP2400 nvram. * * Input: * ha: adapter state pointer. ! * ha->req_q[0]: request ring * * Output: * ha->init_ctrl_blk = initialization control block * host adapters parameters in host adapter block *
*** 900,910 **** * Kernel context. */ int ql_nvram_24xx_config(ql_adapter_state_t *ha) { ! uint32_t index, addr, chksum, saved_chksum; uint32_t *longptr; nvram_24xx_t nvram; int idpromlen; char idprombuf[32]; caddr_t src, dst; --- 935,946 ---- * Kernel context. */ int ql_nvram_24xx_config(ql_adapter_state_t *ha) { ! uint32_t index, addr; ! uint32_t chksum = 0, saved_chksum = 0; uint32_t *longptr; nvram_24xx_t nvram; int idpromlen; char idprombuf[32]; caddr_t src, dst;
*** 912,923 **** int rval; nvram_24xx_t *nv = (nvram_24xx_t *)&nvram; ql_init_24xx_cb_t *icb = (ql_init_24xx_cb_t *)&ha->init_ctrl_blk.cb24; ql_ip_init_24xx_cb_t *ip_icb = &ha->ip_init_ctrl_blk.cb24; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); if ((rval = ql_lock_nvram(ha, &addr, LNF_NVRAM_DATA)) == QL_SUCCESS) { /* Get NVRAM data and calculate checksum. */ longptr = (uint32_t *)nv; --- 948,960 ---- int rval; nvram_24xx_t *nv = (nvram_24xx_t *)&nvram; ql_init_24xx_cb_t *icb = (ql_init_24xx_cb_t *)&ha->init_ctrl_blk.cb24; ql_ip_init_24xx_cb_t *ip_icb = &ha->ip_init_ctrl_blk.cb24; + la_els_logi_t *els = &ha->loginparams; ! QL_PRINT_10(ha, "started\n"); if ((rval = ql_lock_nvram(ha, &addr, LNF_NVRAM_DATA)) == QL_SUCCESS) { /* Get NVRAM data and calculate checksum. */ longptr = (uint32_t *)nv;
*** 942,952 **** nv->id[1] != 'S' || nv->id[2] != 'P' || nv->id[3] != ' ' || (nv->nvram_version[0] | nv->nvram_version[1]) == 0) { cmn_err(CE_WARN, "%s(%d): NVRAM configuration failed, using " "driver defaults.", QL_NAME, ha->instance); - EL(ha, "failed, rval=%xh, checksum=%xh, id=%c%c%c%c, " "nvram_version=%x\n", rval, chksum, nv->id[0], nv->id[1], nv->id[2], nv->id[3], CHAR_TO_SHORT(nv->nvram_version[0], nv->nvram_version[1])); --- 979,988 ----
*** 1019,1029 **** nv->reset_delay = 5; nv->max_luns_per_target[0] = 128; nv->port_down_retry_count[0] = 30; nv->link_down_timeout[0] = 30; ! if (CFG_IST(ha, CFG_CTRL_8081)) { nv->firmware_options_3[2] = BIT_4; nv->feature_mask_l[0] = 9; nv->ext_blk.version[0] = 1; nv->ext_blk.fcf_vlan_match = 1; nv->ext_blk.fcf_vlan_id[0] = LSB(1002); --- 1055,1065 ---- nv->reset_delay = 5; nv->max_luns_per_target[0] = 128; nv->port_down_retry_count[0] = 30; nv->link_down_timeout[0] = 30; ! if (CFG_IST(ha, CFG_FCOE_SUPPORT)) { nv->firmware_options_3[2] = BIT_4; nv->feature_mask_l[0] = 9; nv->ext_blk.version[0] = 1; nv->ext_blk.fcf_vlan_match = 1; nv->ext_blk.fcf_vlan_id[0] = LSB(1002);
*** 1036,1074 **** } rval = QL_FUNCTION_FAILED; } - /* Check for adapter node name (big endian). */ - for (index = 0; index < 8; index++) { - if (nv->node_name[index] != 0) { - break; - } - } - - /* Copy port name if no node name (big endian). */ - if (index == 8) { - bcopy((void *)&nv->port_name[0], (void *)&nv->node_name[0], 8); - nv->node_name[0] = (uint8_t)(nv->node_name[0] & ~BIT_0); - nv->port_name[0] = (uint8_t)(nv->node_name[0] | BIT_0); - } - /* Reset initialization control blocks. */ bzero((void *)icb, sizeof (ql_init_24xx_cb_t)); - /* Get driver properties. */ - ql_24xx_properties(ha, nv); - - cmn_err(CE_CONT, "!Qlogic %s(%d) WWPN=%02x%02x%02x%02x" - "%02x%02x%02x%02x : WWNN=%02x%02x%02x%02x%02x%02x%02x%02x\n", - QL_NAME, ha->instance, nv->port_name[0], nv->port_name[1], - nv->port_name[2], nv->port_name[3], nv->port_name[4], - nv->port_name[5], nv->port_name[6], nv->port_name[7], - nv->node_name[0], nv->node_name[1], nv->node_name[2], - nv->node_name[3], nv->node_name[4], nv->node_name[5], - nv->node_name[6], nv->node_name[7]); - /* * Copy over NVRAM Firmware Initialization Control Block. */ dst = (caddr_t)icb; src = (caddr_t)&nv->version; --- 1072,1084 ----
*** 1080,1101 **** icb->login_retry_count[0] = nv->login_retry_count[0]; icb->login_retry_count[1] = nv->login_retry_count[1]; icb->link_down_on_nos[0] = nv->link_down_on_nos[0]; icb->link_down_on_nos[1] = nv->link_down_on_nos[1]; dst = (caddr_t)&icb->interrupt_delay_timer; src = (caddr_t)&nv->interrupt_delay_timer; index = (uint32_t)((uintptr_t)&icb->qos - (uintptr_t)&icb->interrupt_delay_timer); while (index--) { *dst++ = *src++; } ! /* ! * Setup driver firmware options. ! */ ! if (CFG_IST(ha, CFG_CTRL_8081)) { dst = (caddr_t)icb->enode_mac_addr; src = (caddr_t)nv->fw.isp8001.e_node_mac_addr; index = sizeof (nv->fw.isp8001.e_node_mac_addr); while (index--) { *dst++ = *src++; --- 1090,1118 ---- icb->login_retry_count[0] = nv->login_retry_count[0]; icb->login_retry_count[1] = nv->login_retry_count[1]; icb->link_down_on_nos[0] = nv->link_down_on_nos[0]; icb->link_down_on_nos[1] = nv->link_down_on_nos[1]; + /* Copy 2nd half. */ dst = (caddr_t)&icb->interrupt_delay_timer; src = (caddr_t)&nv->interrupt_delay_timer; index = (uint32_t)((uintptr_t)&icb->qos - (uintptr_t)&icb->interrupt_delay_timer); while (index--) { *dst++ = *src++; } ! ha->execution_throttle = 16; ! ha->loop_reset_delay = nv->reset_delay; ! ha->port_down_retry_count = CHAR_TO_SHORT(nv->port_down_retry_count[0], ! nv->port_down_retry_count[1]); ! ha->maximum_luns_per_target = CHAR_TO_SHORT( ! nv->max_luns_per_target[0], nv->max_luns_per_target[1]); ! if (ha->maximum_luns_per_target == 0) { ! ha->maximum_luns_per_target++; ! } ! if (CFG_IST(ha, CFG_FCOE_SUPPORT)) { dst = (caddr_t)icb->enode_mac_addr; src = (caddr_t)nv->fw.isp8001.e_node_mac_addr; index = sizeof (nv->fw.isp8001.e_node_mac_addr); while (index--) { *dst++ = *src++;
*** 1108,1118 **** } EL(ha, "e_node_mac_addr=%02x-%02x-%02x-%02x-%02x-%02x\n", icb->enode_mac_addr[0], icb->enode_mac_addr[1], icb->enode_mac_addr[2], icb->enode_mac_addr[3], icb->enode_mac_addr[4], icb->enode_mac_addr[5]); ! } else { icb->firmware_options_1[0] = (uint8_t) (icb->firmware_options_1[0] | BIT_1); icb->firmware_options_1[1] = (uint8_t) (icb->firmware_options_1[1] | BIT_5 | BIT_2); icb->firmware_options_3[0] = (uint8_t) --- 1125,1173 ---- } EL(ha, "e_node_mac_addr=%02x-%02x-%02x-%02x-%02x-%02x\n", icb->enode_mac_addr[0], icb->enode_mac_addr[1], icb->enode_mac_addr[2], icb->enode_mac_addr[3], icb->enode_mac_addr[4], icb->enode_mac_addr[5]); ! } ! ! /* Check for adapter node name (big endian). */ ! for (index = 0; index < 8; index++) { ! if (icb->node_name[index] != 0) { ! break; ! } ! } ! ! /* Copy port name if no node name (big endian). */ ! if (index == 8) { ! for (index = 0; index < 8; index++) { ! icb->node_name[index] = icb->port_name[index]; ! } ! icb->node_name[0] = (uint8_t)(icb->node_name[0] & ~BIT_0); ! icb->port_name[0] = (uint8_t)(icb->node_name[0] | BIT_0); ! } ! ! ADAPTER_STATE_LOCK(ha); ! ha->cfg_flags &= ~(CFG_ENABLE_FULL_LIP_LOGIN | CFG_ENABLE_TARGET_RESET | ! CFG_ENABLE_LIP_RESET | CFG_LOAD_FLASH_FW | CFG_FAST_TIMEOUT | ! CFG_DISABLE_RISC_CODE_LOAD | CFG_ENABLE_FWEXTTRACE | ! CFG_ENABLE_FWFCETRACE | CFG_SET_CACHE_LINE_SIZE_1 | CFG_LR_SUPPORT); ! if (nv->host_p[1] & BIT_2) { ! ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN; ! } ! if (nv->host_p[1] & BIT_3) { ! ha->cfg_flags |= CFG_ENABLE_TARGET_RESET; ! } ! ha->flags &= ~MULTI_CHIP_ADAPTER; ! ADAPTER_STATE_UNLOCK(ha); ! ! /* Get driver properties. */ ! ql_24xx_properties(ha, icb); ! ! /* ! * Setup driver firmware options. ! */ ! if (!CFG_IST(ha, CFG_FCOE_SUPPORT)) { icb->firmware_options_1[0] = (uint8_t) (icb->firmware_options_1[0] | BIT_1); icb->firmware_options_1[1] = (uint8_t) (icb->firmware_options_1[1] | BIT_5 | BIT_2); icb->firmware_options_3[0] = (uint8_t)
*** 1129,1184 **** (icb->firmware_options_2[1] | BIT_4); } else { icb->firmware_options_2[1] = (uint8_t) (icb->firmware_options_2[1] & ~BIT_4); } - icb->firmware_options_3[0] = (uint8_t)(icb->firmware_options_3[0] & ~BIT_7); - /* enable special N port 2 N port login behaviour */ - if (CFG_IST(ha, CFG_CTRL_2425)) { - icb->firmware_options_3[1] = - (uint8_t)(icb->firmware_options_3[1] | BIT_0); - } - - icb->execution_throttle[0] = 0xff; - icb->execution_throttle[1] = 0xff; - /* * Set host adapter parameters */ ADAPTER_STATE_LOCK(ha); - ha->nvram_version = CHAR_TO_SHORT(nv->nvram_version[0], - nv->nvram_version[1]); - nv->host_p[1] & BIT_2 ? (ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN) : - (ha->cfg_flags &= ~CFG_ENABLE_FULL_LIP_LOGIN); - nv->host_p[1] & BIT_3 ? (ha->cfg_flags |= CFG_ENABLE_TARGET_RESET) : - (ha->cfg_flags &= ~CFG_ENABLE_TARGET_RESET); - ha->cfg_flags &= ~(CFG_DISABLE_RISC_CODE_LOAD | CFG_LR_SUPPORT | - CFG_SET_CACHE_LINE_SIZE_1 | CFG_MULTI_CHIP_ADAPTER); ha->cfg_flags |= CFG_ENABLE_64BIT_ADDRESSING; if (CFG_IST(ha, CFG_CTRL_81XX) && nv->enhanced_features[0] & BIT_0) { ha->cfg_flags |= CFG_LR_SUPPORT; } ADAPTER_STATE_UNLOCK(ha); ! ha->execution_throttle = CHAR_TO_SHORT(nv->execution_throttle[0], ! nv->execution_throttle[1]); ! ha->loop_reset_delay = nv->reset_delay; ! ha->port_down_retry_count = CHAR_TO_SHORT(nv->port_down_retry_count[0], ! nv->port_down_retry_count[1]); ! w1 = CHAR_TO_SHORT(icb->login_timeout[0], icb->login_timeout[1]); ! ha->r_a_tov = (uint16_t)(w1 < R_A_TOV_DEFAULT ? R_A_TOV_DEFAULT : w1); ! ha->maximum_luns_per_target = CHAR_TO_SHORT( ! nv->max_luns_per_target[0], nv->max_luns_per_target[1]); ! if (ha->maximum_luns_per_target == 0) { ! ha->maximum_luns_per_target++; } /* ISP2422 Serial Link Control */ ! if (CFG_IST(ha, CFG_CTRL_2422)) { ha->serdes_param[0] = CHAR_TO_SHORT(nv->fw.isp2400.swing_opt[0], nv->fw.isp2400.swing_opt[1]); ha->serdes_param[1] = CHAR_TO_SHORT(nv->fw.isp2400.swing_1g[0], nv->fw.isp2400.swing_1g[1]); ha->serdes_param[2] = CHAR_TO_SHORT(nv->fw.isp2400.swing_2g[0], --- 1184,1220 ---- (icb->firmware_options_2[1] | BIT_4); } else { icb->firmware_options_2[1] = (uint8_t) (icb->firmware_options_2[1] & ~BIT_4); } icb->firmware_options_3[0] = (uint8_t)(icb->firmware_options_3[0] & ~BIT_7); /* * Set host adapter parameters */ + w1 = CHAR_TO_SHORT(icb->login_timeout[0], icb->login_timeout[1]); + ha->r_a_tov = (uint16_t)(w1 < R_A_TOV_DEFAULT ? R_A_TOV_DEFAULT : w1); + ADAPTER_STATE_LOCK(ha); ha->cfg_flags |= CFG_ENABLE_64BIT_ADDRESSING; if (CFG_IST(ha, CFG_CTRL_81XX) && nv->enhanced_features[0] & BIT_0) { ha->cfg_flags |= CFG_LR_SUPPORT; } ADAPTER_STATE_UNLOCK(ha); ! /* Queue shadowing */ ! if (ha->flags & QUEUE_SHADOW_PTRS) { ! icb->firmware_options_2[3] = (uint8_t) ! (icb->firmware_options_2[3] | BIT_6 | BIT_5); ! } else { ! icb->firmware_options_2[3] = (uint8_t) ! (icb->firmware_options_2[3] | ~(BIT_6 | BIT_5)); } /* ISP2422 Serial Link Control */ ! if (CFG_IST(ha, CFG_CTRL_24XX)) { ha->serdes_param[0] = CHAR_TO_SHORT(nv->fw.isp2400.swing_opt[0], nv->fw.isp2400.swing_opt[1]); ha->serdes_param[1] = CHAR_TO_SHORT(nv->fw.isp2400.swing_1g[0], nv->fw.isp2400.swing_1g[1]); ha->serdes_param[2] = CHAR_TO_SHORT(nv->fw.isp2400.swing_2g[0],
*** 1185,1222 **** nv->fw.isp2400.swing_2g[1]); ha->serdes_param[3] = CHAR_TO_SHORT(nv->fw.isp2400.swing_4g[0], nv->fw.isp2400.swing_4g[1]); } /* * Setup ring parameters in initialization control block */ ! w1 = REQUEST_ENTRY_CNT; icb->request_q_length[0] = LSB(w1); icb->request_q_length[1] = MSB(w1); ! w1 = RESPONSE_ENTRY_CNT; icb->response_q_length[0] = LSB(w1); icb->response_q_length[1] = MSB(w1); ! icb->request_q_address[0] = LSB(LSW(LSD(ha->request_dvma))); ! icb->request_q_address[1] = MSB(LSW(LSD(ha->request_dvma))); ! icb->request_q_address[2] = LSB(MSW(LSD(ha->request_dvma))); ! icb->request_q_address[3] = MSB(MSW(LSD(ha->request_dvma))); ! icb->request_q_address[4] = LSB(LSW(MSD(ha->request_dvma))); ! icb->request_q_address[5] = MSB(LSW(MSD(ha->request_dvma))); ! icb->request_q_address[6] = LSB(MSW(MSD(ha->request_dvma))); ! icb->request_q_address[7] = MSB(MSW(MSD(ha->request_dvma))); ! icb->response_q_address[0] = LSB(LSW(LSD(ha->response_dvma))); ! icb->response_q_address[1] = MSB(LSW(LSD(ha->response_dvma))); ! icb->response_q_address[2] = LSB(MSW(LSD(ha->response_dvma))); ! icb->response_q_address[3] = MSB(MSW(LSD(ha->response_dvma))); ! icb->response_q_address[4] = LSB(LSW(MSD(ha->response_dvma))); ! icb->response_q_address[5] = MSB(LSW(MSD(ha->response_dvma))); ! icb->response_q_address[6] = LSB(MSW(MSD(ha->response_dvma))); ! icb->response_q_address[7] = MSB(MSW(MSD(ha->response_dvma))); /* * Setup IP initialization control block */ ip_icb->version = IP_ICB_24XX_VERSION; --- 1221,1280 ---- nv->fw.isp2400.swing_2g[1]); ha->serdes_param[3] = CHAR_TO_SHORT(nv->fw.isp2400.swing_4g[0], nv->fw.isp2400.swing_4g[1]); } + els->common_service.rx_bufsize = CHAR_TO_SHORT( + icb->max_frame_length[0], icb->max_frame_length[1]); + bcopy((void *)icb->port_name, (void *)els->nport_ww_name.raw_wwn, 8); + bcopy((void *)icb->node_name, (void *)els->node_ww_name.raw_wwn, 8); + + cmn_err(CE_CONT, "!Qlogic %s(%d) WWPN=%02x%02x%02x%02x" + "%02x%02x%02x%02x : WWNN=%02x%02x%02x%02x%02x%02x%02x%02x\n", + QL_NAME, ha->instance, + els->nport_ww_name.raw_wwn[0], els->nport_ww_name.raw_wwn[1], + els->nport_ww_name.raw_wwn[2], els->nport_ww_name.raw_wwn[3], + els->nport_ww_name.raw_wwn[4], els->nport_ww_name.raw_wwn[5], + els->nport_ww_name.raw_wwn[6], els->nport_ww_name.raw_wwn[7], + els->node_ww_name.raw_wwn[0], els->node_ww_name.raw_wwn[1], + els->node_ww_name.raw_wwn[2], els->node_ww_name.raw_wwn[3], + els->node_ww_name.raw_wwn[4], els->node_ww_name.raw_wwn[5], + els->node_ww_name.raw_wwn[6], els->node_ww_name.raw_wwn[7]); /* * Setup ring parameters in initialization control block */ ! w1 = ha->req_q[0]->req_entry_cnt; icb->request_q_length[0] = LSB(w1); icb->request_q_length[1] = MSB(w1); ! w1 = ha->rsp_queues[0]->rsp_entry_cnt; icb->response_q_length[0] = LSB(w1); icb->response_q_length[1] = MSB(w1); ! addr = ha->req_q[0]->req_ring.cookie.dmac_address; ! icb->request_q_address[0] = LSB(LSW(addr)); ! icb->request_q_address[1] = MSB(LSW(addr)); ! icb->request_q_address[2] = LSB(MSW(addr)); ! icb->request_q_address[3] = MSB(MSW(addr)); ! addr = ha->req_q[0]->req_ring.cookie.dmac_notused; ! icb->request_q_address[4] = LSB(LSW(addr)); ! icb->request_q_address[5] = MSB(LSW(addr)); ! icb->request_q_address[6] = LSB(MSW(addr)); ! icb->request_q_address[7] = MSB(MSW(addr)); + addr = ha->rsp_queues[0]->rsp_ring.cookie.dmac_address; + icb->response_q_address[0] = LSB(LSW(addr)); + icb->response_q_address[1] = MSB(LSW(addr)); + icb->response_q_address[2] = LSB(MSW(addr)); + icb->response_q_address[3] = MSB(MSW(addr)); + + addr = ha->rsp_queues[0]->rsp_ring.cookie.dmac_notused; + icb->response_q_address[4] = LSB(LSW(addr)); + icb->response_q_address[5] = MSB(LSW(addr)); + icb->response_q_address[6] = LSB(MSW(addr)); + icb->response_q_address[7] = MSB(MSW(addr)); + /* * Setup IP initialization control block */ ip_icb->version = IP_ICB_24XX_VERSION;
*** 1225,1235 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 1283,1293 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 1252,1261 **** --- 1310,1321 ---- int ql_lock_nvram(ql_adapter_state_t *ha, uint32_t *addr, uint32_t flags) { int i; + QL_PRINT_3(ha, "started\n"); + if ((flags & LNF_NVRAM_DATA) && (flags & LNF_VPD_DATA)) { EL(ha, "invalid options for function"); return (QL_FUNCTION_FAILED); }
*** 1283,1293 **** if ((RD16_IO_REG(ha, host_to_host_sema) & 1) == 0) { cmn_err(CE_WARN, "%s(%d): unable to get NVRAM lock", QL_NAME, ha->instance); return (QL_FUNCTION_FAILED); } ! } else if (CFG_IST(ha, CFG_CTRL_2422)) { if (flags & LNF_VPD_DATA) { *addr = NVRAM_DATA_ADDR | ha->flash_vpd_addr; } else if (flags & LNF_NVRAM_DATA) { *addr = NVRAM_DATA_ADDR | ha->flash_nvram_addr; } else { --- 1343,1353 ---- if ((RD16_IO_REG(ha, host_to_host_sema) & 1) == 0) { cmn_err(CE_WARN, "%s(%d): unable to get NVRAM lock", QL_NAME, ha->instance); return (QL_FUNCTION_FAILED); } ! } else if (CFG_IST(ha, CFG_CTRL_24XX)) { if (flags & LNF_VPD_DATA) { *addr = NVRAM_DATA_ADDR | ha->flash_vpd_addr; } else if (flags & LNF_NVRAM_DATA) { *addr = NVRAM_DATA_ADDR | ha->flash_nvram_addr; } else {
*** 1294,1304 **** EL(ha, "invalid 2422 option for HBA"); return (QL_FUNCTION_FAILED); } GLOBAL_HW_LOCK(); ! } else if (CFG_IST(ha, CFG_CTRL_258081)) { if (flags & LNF_VPD_DATA) { *addr = ha->flash_data_addr | ha->flash_vpd_addr; } else if (flags & LNF_NVRAM_DATA) { *addr = ha->flash_data_addr | ha->flash_nvram_addr; } else { --- 1354,1364 ---- EL(ha, "invalid 2422 option for HBA"); return (QL_FUNCTION_FAILED); } GLOBAL_HW_LOCK(); ! } else if (CFG_IST(ha, CFG_CTRL_252780818283)) { if (flags & LNF_VPD_DATA) { *addr = ha->flash_data_addr | ha->flash_vpd_addr; } else if (flags & LNF_NVRAM_DATA) { *addr = ha->flash_data_addr | ha->flash_nvram_addr; } else {
*** 1314,1323 **** --- 1374,1385 ---- } *addr = 0; GLOBAL_HW_LOCK(); } + QL_PRINT_3(ha, "done\n"); + return (QL_SUCCESS); } /* * ql_release_nvram
*** 1330,1345 **** --- 1392,1411 ---- * Kernel context. */ void ql_release_nvram(ql_adapter_state_t *ha) { + QL_PRINT_3(ha, "started\n"); + if (ha->device_id == 0x2312 || ha->device_id == 0x2322) { /* Release resource lock */ WRT16_IO_REG(ha, host_to_host_sema, 0); } else { GLOBAL_HW_UNLOCK(); } + + QL_PRINT_3(ha, "done\n"); } /* * ql_23_properties * Copies driver properties to NVRAM or adapter structure.
*** 1348,1553 **** * completely from administrators. Knowledgeable folks can * override the default values using driver.conf * * Input: * ha: adapter state pointer. ! * nv: NVRAM structure pointer. * * Context: * Kernel context. */ static void ! ql_23_properties(ql_adapter_state_t *ha, nvram_t *nv) { uint32_t data, cnt; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Get frame payload size. */ if ((data = ql_get_prop(ha, "max-frame-length")) == 0xffffffff) { data = 2048; } if (data == 512 || data == 1024 || data == 2048) { ! nv->max_frame_length[0] = LSB(data); ! nv->max_frame_length[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'max-frame-length': " "%d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! nv->max_frame_length[0], nv->max_frame_length[1])); } /* Get max IOCB allocation. */ ! nv->max_iocb_allocation[0] = 0; ! nv->max_iocb_allocation[1] = 1; /* Get execution throttle. */ if ((data = ql_get_prop(ha, "execution-throttle")) == 0xffffffff) { data = 32; } if (data != 0 && data < 65536) { ! nv->execution_throttle[0] = LSB(data); ! nv->execution_throttle[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'execution-throttle': " "%d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! nv->execution_throttle[0], nv->execution_throttle[1])); } /* Get Login timeout. */ if ((data = ql_get_prop(ha, "login-timeout")) == 0xffffffff) { data = 3; } if (data < 256) { ! nv->login_timeout = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'login-timeout': " ! "%d; using nvram value of %d\n", data, nv->login_timeout); } /* Get retry count. */ if ((data = ql_get_prop(ha, "login-retry-count")) == 0xffffffff) { data = 4; } if (data < 256) { ! nv->login_retry_count = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'login-retry-count': " "%d; using nvram value of %d\n", data, ! nv->login_retry_count); } /* Get adapter hard loop ID enable. */ data = ql_get_prop(ha, "enable-adapter-hard-loop-ID"); if (data == 0) { ! nv->firmware_options[0] = ! (uint8_t)(nv->firmware_options[0] & ~BIT_0); } else if (data == 1) { ! nv->firmware_options[0] = ! (uint8_t)(nv->firmware_options[0] | BIT_0); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for " "'enable-adapter-hard-loop-ID': %d; using nvram value " ! "of %d\n", data, nv->firmware_options[0] & BIT_0 ? 1 : 0); } /* Get adapter hard loop ID. */ data = ql_get_prop(ha, "adapter-hard-loop-ID"); if (data < 126) { ! nv->hard_address[0] = (uint8_t)data; } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for 'adapter-hard-loop-ID': " "%d; using nvram value of %d\n", ! data, nv->hard_address[0]); } /* Get LIP reset. */ if ((data = ql_get_prop(ha, "enable-LIP-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] & ~BIT_1); } else if (data == 1) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] | BIT_1); } else { EL(ha, "invalid parameter value for " "'enable-LIP-reset-on-bus-reset': %d; using nvram value " ! "of %d\n", data, nv->host_p[1] & BIT_1 ? 1 : 0); } /* Get LIP full login. */ if ((data = ql_get_prop(ha, "enable-LIP-full-login-on-bus-reset")) == 0xffffffff) { data = 1; } if (data == 0) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] & ~BIT_2); } else if (data == 1) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] | BIT_2); } else { EL(ha, "invalid parameter value for " "'enable-LIP-full-login-on-bus-reset': %d; using nvram " ! "value of %d\n", data, nv->host_p[1] & BIT_2 ? 1 : 0); } /* Get target reset. */ if ((data = ql_get_prop(ha, "enable-target-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] & ~BIT_3); } else if (data == 1) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] | BIT_3); } else { EL(ha, "invalid parameter value for " "'enable-target-reset-on-bus-reset': %d; using nvram " ! "value of %d", data, nv->host_p[1] & BIT_3 ? 1 : 0); } /* Get reset delay. */ if ((data = ql_get_prop(ha, "reset-delay")) == 0xffffffff) { data = 5; } if (data != 0 && data < 256) { ! nv->reset_delay = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'reset-delay': %d; " ! "using nvram value of %d", data, nv->reset_delay); } /* Get port down retry count. */ if ((data = ql_get_prop(ha, "port-down-retry-count")) == 0xffffffff) { data = 8; } if (data < 256) { ! nv->port_down_retry_count = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'port-down-retry-count':" " %d; using nvram value of %d\n", data, ! nv->port_down_retry_count); } /* Get connection mode setting. */ if ((data = ql_get_prop(ha, "connection-options")) == 0xffffffff) { data = 2; } ! cnt = CFG_IST(ha, CFG_CTRL_2200) ? 3 : 2; if (data <= cnt) { ! nv->add_fw_opt[0] = (uint8_t)(nv->add_fw_opt[0] & ~(BIT_6 | BIT_5 | BIT_4)); ! nv->add_fw_opt[0] = (uint8_t)(nv->add_fw_opt[0] | (uint8_t)(data << 4)); } else { EL(ha, "invalid parameter value for 'connection-options': " "%d; using nvram value of %d\n", data, ! (nv->add_fw_opt[0] >> 4) & 0x3); } /* Get data rate setting. */ ! if ((CFG_IST(ha, CFG_CTRL_2200)) == 0) { if ((data = ql_get_prop(ha, "fc-data-rate")) == 0xffffffff) { data = 2; } if (data < 3) { ! nv->special_options[1] = (uint8_t) ! (nv->special_options[1] & 0x3f); ! nv->special_options[1] = (uint8_t) ! (nv->special_options[1] | (uint8_t)(data << 6)); } else { EL(ha, "invalid parameter value for 'fc-data-rate': " "%d; using nvram value of %d\n", data, ! (nv->special_options[1] >> 6) & 0x3); } } - /* Get adapter id string for Sun branded 23xx only */ - if ((CFG_IST(ha, CFG_CTRL_2300)) && nv->adapInfo[0] != 0) { - (void) snprintf((int8_t *)ha->adapInfo, 16, "%s", - nv->adapInfo); - } - /* Get IP FW container count. */ ha->ip_init_ctrl_blk.cb.cc[0] = LSB(ql_ip_buffer_count); ha->ip_init_ctrl_blk.cb.cc[1] = MSB(ql_ip_buffer_count); /* Get IP low water mark. */ --- 1414,1616 ---- * completely from administrators. Knowledgeable folks can * override the default values using driver.conf * * Input: * ha: adapter state pointer. ! * icb: Init control block structure pointer. * * Context: * Kernel context. */ static void ! ql_23_properties(ql_adapter_state_t *ha, ql_init_cb_t *icb) { uint32_t data, cnt; ! QL_PRINT_3(ha, "started\n"); /* Get frame payload size. */ if ((data = ql_get_prop(ha, "max-frame-length")) == 0xffffffff) { data = 2048; } if (data == 512 || data == 1024 || data == 2048) { ! icb->max_frame_length[0] = LSB(data); ! icb->max_frame_length[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'max-frame-length': " "%d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! icb->max_frame_length[0], icb->max_frame_length[1])); } /* Get max IOCB allocation. */ ! icb->max_iocb_allocation[0] = 0; ! icb->max_iocb_allocation[1] = 1; /* Get execution throttle. */ if ((data = ql_get_prop(ha, "execution-throttle")) == 0xffffffff) { data = 32; } if (data != 0 && data < 65536) { ! icb->execution_throttle[0] = LSB(data); ! icb->execution_throttle[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'execution-throttle': " "%d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! icb->execution_throttle[0], icb->execution_throttle[1])); } /* Get Login timeout. */ if ((data = ql_get_prop(ha, "login-timeout")) == 0xffffffff) { data = 3; } if (data < 256) { ! icb->login_timeout = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'login-timeout': " ! "%d; using nvram value of %d\n", data, icb->login_timeout); } /* Get retry count. */ if ((data = ql_get_prop(ha, "login-retry-count")) == 0xffffffff) { data = 4; } if (data < 256) { ! icb->login_retry_count = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'login-retry-count': " "%d; using nvram value of %d\n", data, ! icb->login_retry_count); } /* Get adapter hard loop ID enable. */ data = ql_get_prop(ha, "enable-adapter-hard-loop-ID"); if (data == 0) { ! icb->firmware_options[0] = ! (uint8_t)(icb->firmware_options[0] & ~BIT_0); } else if (data == 1) { ! icb->firmware_options[0] = ! (uint8_t)(icb->firmware_options[0] | BIT_0); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for " "'enable-adapter-hard-loop-ID': %d; using nvram value " ! "of %d\n", data, icb->firmware_options[0] & BIT_0 ? 1 : 0); } /* Get adapter hard loop ID. */ data = ql_get_prop(ha, "adapter-hard-loop-ID"); if (data < 126) { ! icb->hard_address[0] = (uint8_t)data; } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for 'adapter-hard-loop-ID': " "%d; using nvram value of %d\n", ! data, icb->hard_address[0]); } /* Get LIP reset. */ if ((data = ql_get_prop(ha, "enable-LIP-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! ha->cfg_flags &= ~CFG_ENABLE_LIP_RESET; } else if (data == 1) { ! ha->cfg_flags |= CFG_ENABLE_LIP_RESET; } else { EL(ha, "invalid parameter value for " "'enable-LIP-reset-on-bus-reset': %d; using nvram value " ! "of %d\n", data, ! CFG_IST(ha, CFG_ENABLE_LIP_RESET) ? 1 : 0); } /* Get LIP full login. */ if ((data = ql_get_prop(ha, "enable-LIP-full-login-on-bus-reset")) == 0xffffffff) { data = 1; } if (data == 0) { ! ha->cfg_flags &= ~CFG_ENABLE_FULL_LIP_LOGIN; } else if (data == 1) { ! ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN; } else { EL(ha, "invalid parameter value for " "'enable-LIP-full-login-on-bus-reset': %d; using nvram " ! "value of %d\n", data, ! CFG_IST(ha, CFG_ENABLE_FULL_LIP_LOGIN) ? 1 : 0); } /* Get target reset. */ if ((data = ql_get_prop(ha, "enable-target-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! ha->cfg_flags &= ~CFG_ENABLE_TARGET_RESET; } else if (data == 1) { ! ha->cfg_flags |= CFG_ENABLE_TARGET_RESET; } else { EL(ha, "invalid parameter value for " "'enable-target-reset-on-bus-reset': %d; using nvram " ! "value of %d", data, ! CFG_IST(ha, CFG_ENABLE_TARGET_RESET) ? 1 : 0); } /* Get reset delay. */ if ((data = ql_get_prop(ha, "reset-delay")) == 0xffffffff) { data = 5; } if (data != 0 && data < 256) { ! ha->loop_reset_delay = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'reset-delay': %d; " ! "using nvram value of %d", data, ha->loop_reset_delay); } /* Get port down retry count. */ if ((data = ql_get_prop(ha, "port-down-retry-count")) == 0xffffffff) { data = 8; } if (data < 256) { ! ha->port_down_retry_count = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'port-down-retry-count':" " %d; using nvram value of %d\n", data, ! ha->port_down_retry_count); } /* Get connection mode setting. */ if ((data = ql_get_prop(ha, "connection-options")) == 0xffffffff) { data = 2; } ! cnt = CFG_IST(ha, CFG_CTRL_22XX) ? 3 : 2; if (data <= cnt) { ! icb->add_fw_opt[0] = (uint8_t)(icb->add_fw_opt[0] & ~(BIT_6 | BIT_5 | BIT_4)); ! icb->add_fw_opt[0] = (uint8_t)(icb->add_fw_opt[0] | (uint8_t)(data << 4)); } else { EL(ha, "invalid parameter value for 'connection-options': " "%d; using nvram value of %d\n", data, ! (icb->add_fw_opt[0] >> 4) & 0x3); } /* Get data rate setting. */ ! if ((CFG_IST(ha, CFG_CTRL_22XX)) == 0) { if ((data = ql_get_prop(ha, "fc-data-rate")) == 0xffffffff) { data = 2; } if (data < 3) { ! icb->special_options[1] = (uint8_t) ! (icb->special_options[1] & 0x3f); ! icb->special_options[1] = (uint8_t) ! (icb->special_options[1] | (uint8_t)(data << 6)); } else { EL(ha, "invalid parameter value for 'fc-data-rate': " "%d; using nvram value of %d\n", data, ! (icb->special_options[1] >> 6) & 0x3); } } /* Get IP FW container count. */ ha->ip_init_ctrl_blk.cb.cc[0] = LSB(ql_ip_buffer_count); ha->ip_init_ctrl_blk.cb.cc[1] = MSB(ql_ip_buffer_count); /* Get IP low water mark. */
*** 1562,1572 **** ql_common_properties(ha); ADAPTER_STATE_UNLOCK(ha); ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } /* * ql_common_properties * Driver properties adapter structure. --- 1625,1635 ---- ql_common_properties(ha); ADAPTER_STATE_UNLOCK(ha); ! QL_PRINT_3(ha, "done\n"); } /* * ql_common_properties * Driver properties adapter structure.
*** 1584,1621 **** void ql_common_properties(ql_adapter_state_t *ha) { uint32_t data; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); - /* Get extended logging trace buffer size. */ - if ((data = ql_get_prop(ha, "set-ext-log-buffer-size")) != - 0xffffffff && data != 0) { - char *new_trace; - uint32_t new_size; - - if (ha->el_trace_desc->trace_buffer != NULL) { - new_size = 1024 * data; - new_trace = (char *)kmem_zalloc(new_size, KM_SLEEP); - - if (new_trace == NULL) { - cmn_err(CE_WARN, "%s(%d): can't get new" - " trace buffer", - QL_NAME, ha->instance); - } else { - /* free the previous */ - kmem_free(ha->el_trace_desc->trace_buffer, - ha->el_trace_desc->trace_buffer_size); - /* Use the new one */ - ha->el_trace_desc->trace_buffer = new_trace; - ha->el_trace_desc->trace_buffer_size = new_size; - } - } - - } - /* Get extended logging enable. */ if ((data = ql_get_prop(ha, "extended-logging")) == 0xffffffff || data == 0) { ha->cfg_flags &= ~CFG_ENABLE_EXTENDED_LOGGING; } else if (data == 1) { --- 1647,1658 ---- void ql_common_properties(ql_adapter_state_t *ha) { uint32_t data; ! QL_PRINT_10(ha, "started\n"); /* Get extended logging enable. */ if ((data = ql_get_prop(ha, "extended-logging")) == 0xffffffff || data == 0) { ha->cfg_flags &= ~CFG_ENABLE_EXTENDED_LOGGING; } else if (data == 1) {
*** 1624,1646 **** EL(ha, "invalid parameter value for 'extended-logging': %d;" " using default value of 0\n", data); ha->cfg_flags &= ~CFG_ENABLE_EXTENDED_LOGGING; } - /* Get extended logging trace disable. */ - if ((data = ql_get_prop(ha, "disable-extended-logging-trace")) == - 0xffffffff || data == 0) { - ha->cfg_flags &= ~CFG_DISABLE_EXTENDED_LOGGING_TRACE; - } else if (data == 1) { - ha->cfg_flags |= CFG_DISABLE_EXTENDED_LOGGING_TRACE; - } else { - EL(ha, "invalid parameter value for " - "'disable-extended-logging-trace': %d;" - " using default value of 0\n", data); - ha->cfg_flags &= ~CFG_DISABLE_EXTENDED_LOGGING_TRACE; - } - /* Get FCP 2 Error Recovery. */ if ((data = ql_get_prop(ha, "enable-FCP-2-error-recovery")) == 0xffffffff || data == 1) { ha->cfg_flags |= CFG_ENABLE_FCP_2_SUPPORT; } else if (data == 0) { --- 1661,1670 ----
*** 1745,1759 **** if ((data = ql_get_prop(ha, "pci-max-read-request")) != 0xffffffff && data != 0) { ha->pci_max_read_req = (uint16_t)(data); } /* * Set default fw wait, adjusted for slow FCF's. * Revisit when FCF's as fast as FC switches. */ ! ha->fwwait = (uint8_t)(CFG_IST(ha, CFG_CTRL_8081) ? 45 : 10); /* Get the attach fw_ready override value. */ if ((data = ql_get_prop(ha, "init-loop-sync-wait")) != 0xffffffff) { if (data > 0 && data <= 240) { ha->fwwait = (uint8_t)data; } else { --- 1769,1793 ---- if ((data = ql_get_prop(ha, "pci-max-read-request")) != 0xffffffff && data != 0) { ha->pci_max_read_req = (uint16_t)(data); } + /* Get the plogi retry params overrides. */ + if ((data = ql_get_prop(ha, "plogi_params_retry_count")) != + 0xffffffff && data != 0) { + ha->plogi_params->retry_cnt = (uint32_t)(data); + } + if ((data = ql_get_prop(ha, "plogi_params_retry_delay")) != + 0xffffffff && data != 0) { + ha->plogi_params->retry_dly_usec = (uint32_t)(data); + } + /* * Set default fw wait, adjusted for slow FCF's. * Revisit when FCF's as fast as FC switches. */ ! ha->fwwait = (uint8_t)(CFG_IST(ha, CFG_FCOE_SUPPORT) ? 45 : 10); /* Get the attach fw_ready override value. */ if ((data = ql_get_prop(ha, "init-loop-sync-wait")) != 0xffffffff) { if (data > 0 && data <= 240) { ha->fwwait = (uint8_t)data; } else {
*** 1761,1771 **** "'init-loop-sync-wait': %d; using default " "value of %d\n", data, ha->fwwait); } } ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } /* * ql_24xx_properties * Copies driver properties to NVRAM or adapter structure. --- 1795,1842 ---- "'init-loop-sync-wait': %d; using default " "value of %d\n", data, ha->fwwait); } } ! /* Get fm-capable property */ ! ha->fm_capabilities = DDI_FM_NOT_CAPABLE; ! if ((data = ql_get_prop(ha, "fm-capable")) != 0xffffffff) { ! if (data == 0) { ! ha->fm_capabilities = DDI_FM_NOT_CAPABLE; ! } else if (data > 0xf) { ! ha->fm_capabilities = 0xf; ! ! } else { ! ha->fm_capabilities = (int)(data); ! } ! } else { ! ha->fm_capabilities = (int)(DDI_FM_EREPORT_CAPABLE ! | DDI_FM_ERRCB_CAPABLE); ! } ! ! if ((data = ql_get_prop(ha, "msix-vectors")) == 0xffffffff) { ! ha->mq_msix_vectors = 0; ! } else if (data < 256) { ! ha->mq_msix_vectors = (uint8_t)data; ! } else { ! EL(ha, "invalid parameter value for 'msix-vectors': " ! "%d; using value of %d\n", data, 0); ! ha->mq_msix_vectors = 0; ! } ! ! /* Get number of completion threads. */ ! if ((data = ql_get_prop(ha, "completion-threads")) == 0xffffffff) { ! ha->completion_thds = 4; ! } else if (data < 256 && data >= 1) { ! ha->completion_thds = (uint8_t)data; ! } else { ! EL(ha, "invalid parameter value for 'completion-threads':" ! " %d; using default value of %d", data, 4); ! ha->completion_thds = 4; ! } ! ! QL_PRINT_3(ha, "done\n"); } /* * ql_24xx_properties * Copies driver properties to NVRAM or adapter structure.
*** 1774,1871 **** * completely from administrators. Knowledgeable folks can * override the default values using /etc/system. * * Input: * ha: adapter state pointer. ! * nv: NVRAM structure pointer. * * Context: * Kernel context. */ static void ! ql_24xx_properties(ql_adapter_state_t *ha, nvram_24xx_t *nv) { uint32_t data; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Get frame size */ if ((data = ql_get_prop(ha, "max-frame-length")) == 0xffffffff) { data = 2048; } if (data == 512 || data == 1024 || data == 2048 || data == 2112) { ! nv->max_frame_length[0] = LSB(data); ! nv->max_frame_length[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'max-frame-length': %d;" " using nvram default of %d\n", data, CHAR_TO_SHORT( ! nv->max_frame_length[0], nv->max_frame_length[1])); } /* Get execution throttle. */ if ((data = ql_get_prop(ha, "execution-throttle")) == 0xffffffff) { data = 32; } if (data != 0 && data < 65536) { ! nv->execution_throttle[0] = LSB(data); ! nv->execution_throttle[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'execution-throttle':" " %d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! nv->execution_throttle[0], nv->execution_throttle[1])); } /* Get Login timeout. */ if ((data = ql_get_prop(ha, "login-timeout")) == 0xffffffff) { data = 3; } if (data < 65536) { ! nv->login_timeout[0] = LSB(data); ! nv->login_timeout[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'login-timeout': %d; " "using nvram value of %d\n", data, CHAR_TO_SHORT( ! nv->login_timeout[0], nv->login_timeout[1])); } /* Get retry count. */ if ((data = ql_get_prop(ha, "login-retry-count")) == 0xffffffff) { data = 4; } if (data < 65536) { ! nv->login_retry_count[0] = LSB(data); ! nv->login_retry_count[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'login-retry-count': " "%d; using nvram value of %d\n", data, CHAR_TO_SHORT( ! nv->login_retry_count[0], nv->login_retry_count[1])); } /* Get adapter hard loop ID enable. */ data = ql_get_prop(ha, "enable-adapter-hard-loop-ID"); if (data == 0) { ! nv->firmware_options_1[0] = ! (uint8_t)(nv->firmware_options_1[0] & ~BIT_0); } else if (data == 1) { ! nv->firmware_options_1[0] = ! (uint8_t)(nv->firmware_options_1[0] | BIT_0); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for " "'enable-adapter-hard-loop-ID': %d; using nvram value " "of %d\n", data, ! nv->firmware_options_1[0] & BIT_0 ? 1 : 0); } /* Get adapter hard loop ID. */ data = ql_get_prop(ha, "adapter-hard-loop-ID"); if (data < 126) { ! nv->hard_address[0] = LSB(data); ! nv->hard_address[1] = MSB(data); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for 'adapter-hard-loop-ID':" " %d; using nvram value of %d\n", data, CHAR_TO_SHORT( ! nv->hard_address[0], nv->hard_address[1])); } /* Get LIP reset. */ if ((data = ql_get_prop(ha, "enable-LIP-reset-on-bus-reset")) == 0xffffffff) { --- 1845,1942 ---- * completely from administrators. Knowledgeable folks can * override the default values using /etc/system. * * Input: * ha: adapter state pointer. ! * icb: Init control block structure pointer. * * Context: * Kernel context. */ static void ! ql_24xx_properties(ql_adapter_state_t *ha, ql_init_24xx_cb_t *icb) { uint32_t data; ! QL_PRINT_10(ha, "started\n"); /* Get frame size */ if ((data = ql_get_prop(ha, "max-frame-length")) == 0xffffffff) { data = 2048; } if (data == 512 || data == 1024 || data == 2048 || data == 2112) { ! icb->max_frame_length[0] = LSB(data); ! icb->max_frame_length[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'max-frame-length': %d;" " using nvram default of %d\n", data, CHAR_TO_SHORT( ! icb->max_frame_length[0], icb->max_frame_length[1])); } /* Get execution throttle. */ if ((data = ql_get_prop(ha, "execution-throttle")) == 0xffffffff) { data = 32; } if (data != 0 && data < 65536) { ! icb->execution_throttle[0] = LSB(data); ! icb->execution_throttle[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'execution-throttle':" " %d; using nvram default of %d\n", data, CHAR_TO_SHORT( ! icb->execution_throttle[0], icb->execution_throttle[1])); } /* Get Login timeout. */ if ((data = ql_get_prop(ha, "login-timeout")) == 0xffffffff) { data = 3; } if (data < 65536) { ! icb->login_timeout[0] = LSB(data); ! icb->login_timeout[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'login-timeout': %d; " "using nvram value of %d\n", data, CHAR_TO_SHORT( ! icb->login_timeout[0], icb->login_timeout[1])); } /* Get retry count. */ if ((data = ql_get_prop(ha, "login-retry-count")) == 0xffffffff) { data = 4; } if (data < 65536) { ! icb->login_retry_count[0] = LSB(data); ! icb->login_retry_count[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'login-retry-count': " "%d; using nvram value of %d\n", data, CHAR_TO_SHORT( ! icb->login_retry_count[0], icb->login_retry_count[1])); } /* Get adapter hard loop ID enable. */ data = ql_get_prop(ha, "enable-adapter-hard-loop-ID"); if (data == 0) { ! icb->firmware_options_1[0] = ! (uint8_t)(icb->firmware_options_1[0] & ~BIT_0); } else if (data == 1) { ! icb->firmware_options_1[0] = ! (uint8_t)(icb->firmware_options_1[0] | BIT_0); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for " "'enable-adapter-hard-loop-ID': %d; using nvram value " "of %d\n", data, ! icb->firmware_options_1[0] & BIT_0 ? 1 : 0); } /* Get adapter hard loop ID. */ data = ql_get_prop(ha, "adapter-hard-loop-ID"); if (data < 126) { ! icb->hard_address[0] = LSB(data); ! icb->hard_address[1] = MSB(data); } else if (data != 0xffffffff) { EL(ha, "invalid parameter value for 'adapter-hard-loop-ID':" " %d; using nvram value of %d\n", data, CHAR_TO_SHORT( ! icb->hard_address[0], icb->hard_address[1])); } /* Get LIP reset. */ if ((data = ql_get_prop(ha, "enable-LIP-reset-on-bus-reset")) == 0xffffffff) {
*** 1885,1975 **** if ((data = ql_get_prop(ha, "enable-LIP-full-login-on-bus-reset")) == 0xffffffff) { data = 1; } if (data == 0) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] & ~BIT_2); } else if (data == 1) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] | BIT_2); } else { EL(ha, "invalid parameter value for " "'enable-LIP-full-login-on-bus-reset': %d; using nvram " ! "value of %d\n", data, nv->host_p[1] & BIT_2 ? 1 : 0); } /* Get target reset. */ if ((data = ql_get_prop(ha, "enable-target-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] & ~BIT_3); } else if (data == 1) { ! nv->host_p[1] = (uint8_t)(nv->host_p[1] | BIT_3); } else { EL(ha, "invalid parameter value for " "'enable-target-reset-on-bus-reset': %d; using nvram " ! "value of %d", data, nv->host_p[1] & BIT_3 ? 1 : 0); } /* Get reset delay. */ if ((data = ql_get_prop(ha, "reset-delay")) == 0xffffffff) { data = 5; } if (data != 0 && data < 256) { ! nv->reset_delay = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'reset-delay': %d; " ! "using nvram value of %d", data, nv->reset_delay); } /* Get port down retry count. */ if ((data = ql_get_prop(ha, "port-down-retry-count")) == 0xffffffff) { data = 8; } if (data < 256) { ! nv->port_down_retry_count[0] = LSB(data); ! nv->port_down_retry_count[1] = MSB(data); } else { EL(ha, "invalid parameter value for 'port-down-retry-count':" ! " %d; using nvram value of %d\n", data, CHAR_TO_SHORT( ! nv->port_down_retry_count[0], ! nv->port_down_retry_count[1])); } ! if (!(CFG_IST(ha, CFG_CTRL_8081))) { /* Get connection mode setting. */ ! if ((data = ql_get_prop(ha, "connection-options")) == 0xffffffff) { ! data = 2; } ! if (data <= 2) { ! nv->firmware_options_2[0] = (uint8_t) ! (nv->firmware_options_2[0] & ~(BIT_6 | BIT_5 | BIT_4)); ! nv->firmware_options_2[0] = (uint8_t) ! (nv->firmware_options_2[0] | (uint8_t)(data << 4)); } else { EL(ha, "invalid parameter value for 'connection-" ! "options': %d; using nvram value of %d\n", data, ! (nv->firmware_options_2[0] >> 4) & 0x3); } /* Get data rate setting. */ if ((data = ql_get_prop(ha, "fc-data-rate")) == 0xffffffff) { data = 2; } ! if ((CFG_IST(ha, CFG_CTRL_2422) && data < 4) || ! (CFG_IST(ha, CFG_CTRL_258081) && data < 5)) { ! nv->firmware_options_3[1] = (uint8_t) ! (nv->firmware_options_3[1] & 0x1f); ! nv->firmware_options_3[1] = (uint8_t) ! (nv->firmware_options_3[1] | (uint8_t)(data << 5)); } else { EL(ha, "invalid parameter value for 'fc-data-rate': " "%d; using nvram value of %d\n", data, ! (nv->firmware_options_3[1] >> 5) & 0x7); } } /* Get IP FW container count. */ ha->ip_init_ctrl_blk.cb24.cc[0] = LSB(ql_ip_buffer_count); --- 1956,2060 ---- if ((data = ql_get_prop(ha, "enable-LIP-full-login-on-bus-reset")) == 0xffffffff) { data = 1; } if (data == 0) { ! ha->cfg_flags &= ~CFG_ENABLE_FULL_LIP_LOGIN; } else if (data == 1) { ! ha->cfg_flags |= CFG_ENABLE_FULL_LIP_LOGIN; } else { EL(ha, "invalid parameter value for " "'enable-LIP-full-login-on-bus-reset': %d; using nvram " ! "value of %d\n", data, ! ha->cfg_flags & CFG_ENABLE_FULL_LIP_LOGIN ? 1 : 0); } /* Get target reset. */ if ((data = ql_get_prop(ha, "enable-target-reset-on-bus-reset")) == 0xffffffff) { data = 0; } if (data == 0) { ! ha->cfg_flags &= ~CFG_ENABLE_TARGET_RESET; } else if (data == 1) { ! ha->cfg_flags |= CFG_ENABLE_TARGET_RESET; } else { EL(ha, "invalid parameter value for " "'enable-target-reset-on-bus-reset': %d; using nvram " ! "value of %d", data, ! ha->cfg_flags & CFG_ENABLE_TARGET_RESET ? 1 : 0); } /* Get reset delay. */ if ((data = ql_get_prop(ha, "reset-delay")) == 0xffffffff) { data = 5; } if (data != 0 && data < 256) { ! ha->loop_reset_delay = (uint8_t)data; } else { EL(ha, "invalid parameter value for 'reset-delay': %d; " ! "using nvram value of %d", data, ha->loop_reset_delay); } /* Get port down retry count. */ if ((data = ql_get_prop(ha, "port-down-retry-count")) == 0xffffffff) { data = 8; } if (data < 256) { ! ha->port_down_retry_count = (uint16_t)data; } else { EL(ha, "invalid parameter value for 'port-down-retry-count':" ! " %d; using nvram value of %d\n", data, ! ha->port_down_retry_count); } ! if (!(CFG_IST(ha, CFG_FCOE_SUPPORT))) { ! uint32_t conn; ! /* Get connection mode setting. */ ! if ((conn = ql_get_prop(ha, "connection-options")) == 0xffffffff) { ! conn = 2; } ! if (conn <= 2) { ! icb->firmware_options_2[0] = (uint8_t) ! (icb->firmware_options_2[0] & ~(BIT_6 | BIT_5 | BIT_4)); ! icb->firmware_options_2[0] = (uint8_t) ! (icb->firmware_options_2[0] | (uint8_t)(conn << 4)); } else { EL(ha, "invalid parameter value for 'connection-" ! "options': %d; using nvram value of %d\n", conn, ! (icb->firmware_options_2[0] >> 4) & 0x3); } + conn = icb->firmware_options_2[0] >> 4 & 0x3; + if (conn == 0 && ha->max_vports > 125) { + ha->max_vports = 125; + } /* Get data rate setting. */ if ((data = ql_get_prop(ha, "fc-data-rate")) == 0xffffffff) { data = 2; } ! if ((CFG_IST(ha, CFG_CTRL_24XX) && data < 4) || ! (CFG_IST(ha, CFG_CTRL_25XX) && data < 5) || ! (CFG_IST(ha, CFG_CTRL_2783) && data < 6)) { ! if (CFG_IST(ha, CFG_CTRL_2783) && data == 5 && ! conn == 0) { ! EL(ha, "invalid parameter value for 'fc-data-" ! "rate': %d; using nvram value of %d\n", ! data, 2); ! data = 2; ! } ! icb->firmware_options_3[1] = (uint8_t) ! (icb->firmware_options_3[1] & 0x1f); ! icb->firmware_options_3[1] = (uint8_t) ! (icb->firmware_options_3[1] | (uint8_t)(data << 5)); } else { EL(ha, "invalid parameter value for 'fc-data-rate': " "%d; using nvram value of %d\n", data, ! (icb->firmware_options_3[1] >> 5) & 0x7); } } /* Get IP FW container count. */ ha->ip_init_ctrl_blk.cb24.cc[0] = LSB(ql_ip_buffer_count);
*** 2014,2024 **** ql_common_properties(ha); ADAPTER_STATE_UNLOCK(ha); ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } /* * ql_get_prop * Get property value from configuration file. --- 2099,2109 ---- ql_common_properties(ha); ADAPTER_STATE_UNLOCK(ha); ! QL_PRINT_3(ha, "done\n"); } /* * ql_get_prop * Get property value from configuration file.
*** 2040,2050 **** uint32_t data = 0xffffffff; /* * Look for a adapter instance NPIV (virtual port) specific parameter */ ! if (CFG_IST(ha, CFG_CTRL_24258081)) { (void) sprintf(buf, "hba%d-vp%d-%s", ha->instance, ha->vp_index, string); /*LINTED [Solaris DDI_DEV_T_ANY Lint warning]*/ data = (uint32_t)ddi_prop_get_int(DDI_DEV_T_ANY, ha->dip, 0, buf, (int)0xffffffff); --- 2125,2135 ---- uint32_t data = 0xffffffff; /* * Look for a adapter instance NPIV (virtual port) specific parameter */ ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2)) { (void) sprintf(buf, "hba%d-vp%d-%s", ha->instance, ha->vp_index, string); /*LINTED [Solaris DDI_DEV_T_ANY Lint warning]*/ data = (uint32_t)ddi_prop_get_int(DDI_DEV_T_ANY, ha->dip, 0, buf, (int)0xffffffff);
*** 2093,2123 **** uint32_t byte_count; uint32_t fw_size, *lptr; caddr_t bufp; uint16_t risc_address = (uint16_t)ha->risc_fw[0].addr; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Test for firmware running. */ ! if (CFG_IST(ha, CFG_CTRL_8021)) { ! if (ql_8021_idc_handler(ha) != NX_DEV_READY) { rval = QL_FUNCTION_FAILED; } else { ! rval = ql_start_firmware(ha); } } else if (CFG_IST(ha, CFG_DISABLE_RISC_CODE_LOAD)) { if (ha->risc_code != NULL) { kmem_free(ha->risc_code, ha->risc_code_size); ha->risc_code = NULL; ha->risc_code_size = 0; } /* Get RISC code length. */ ! rval = ql_rd_risc_ram(ha, risc_address + 3, ha->request_dvma, ! 1); if (rval == QL_SUCCESS) { ! lptr = (uint32_t *)ha->request_ring_bp; fw_size = *lptr << 1; if ((bufp = kmem_alloc(fw_size, KM_SLEEP)) != NULL) { ha->risc_code_size = fw_size; ha->risc_code = bufp; --- 2178,2219 ---- uint32_t byte_count; uint32_t fw_size, *lptr; caddr_t bufp; uint16_t risc_address = (uint16_t)ha->risc_fw[0].addr; ! QL_PRINT_10(ha, "started\n"); /* Test for firmware running. */ ! if (CFG_IST(ha, CFG_CTRL_82XX)) { ! if ((rval = ql_8021_fw_chk(ha)) == QL_SUCCESS) { ! rval = ql_start_firmware(ha); ! } ! } else if (CFG_IST(ha, CFG_CTRL_278083)) { ! ha->dev_state = NX_DEV_READY; ! if (ha->rom_status == MBS_ROM_FW_RUNNING) { ! EL(ha, "ISP ROM Status = MBS_ROM_FW_RUNNING\n"); ! rval = QL_SUCCESS; ! } else if (ha->rom_status == MBS_ROM_IDLE) { ! EL(ha, "ISP ROM Status = MBS_ROM_IDLE\n"); rval = QL_FUNCTION_FAILED; } else { ! EL(ha, "ISP ROM Status, mbx0=%xh\n", ha->rom_status); ! rval = QL_FUNCTION_FAILED; } } else if (CFG_IST(ha, CFG_DISABLE_RISC_CODE_LOAD)) { + ha->dev_state = NX_DEV_READY; if (ha->risc_code != NULL) { kmem_free(ha->risc_code, ha->risc_code_size); ha->risc_code = NULL; ha->risc_code_size = 0; } /* Get RISC code length. */ ! rval = ql_rd_risc_ram(ha, risc_address + 3, ! ha->req_q[0]->req_ring.cookie.dmac_laddress, 1); if (rval == QL_SUCCESS) { ! lptr = (uint32_t *)ha->req_q[0]->req_ring.bp; fw_size = *lptr << 1; if ((bufp = kmem_alloc(fw_size, KM_SLEEP)) != NULL) { ha->risc_code_size = fw_size; ha->risc_code = bufp;
*** 2134,2160 **** word_count = (uint16_t)(byte_count >> 1); rval = ql_rd_risc_ram(ha, risc_address, ! ha->request_dvma, word_count); if (rval != QL_SUCCESS) { kmem_free(ha->risc_code, ha->risc_code_size); ha->risc_code = NULL; ha->risc_code_size = 0; break; } (void) ddi_dma_sync( ! ha->hba_buf.dma_handle, ! REQUEST_Q_BUFFER_OFFSET, ! byte_count, DDI_DMA_SYNC_FORKERNEL); ! ddi_rep_get16(ha->hba_buf.acc_handle, ! (uint16_t *)bufp, ! (uint16_t *)ha->request_ring_bp, word_count, DDI_DEV_AUTOINCR); risc_address += word_count; fw_size -= byte_count; bufp += byte_count; --- 2230,2257 ---- word_count = (uint16_t)(byte_count >> 1); rval = ql_rd_risc_ram(ha, risc_address, ! ha->req_q[0]->req_ring.cookie. ! dmac_laddress, word_count); if (rval != QL_SUCCESS) { kmem_free(ha->risc_code, ha->risc_code_size); ha->risc_code = NULL; ha->risc_code_size = 0; break; } (void) ddi_dma_sync( ! ha->req_q[0]->req_ring.dma_handle, ! 0, byte_count, DDI_DMA_SYNC_FORKERNEL); ! ddi_rep_get16( ! ha->req_q[0]->req_ring.acc_handle, ! (uint16_t *)bufp, (uint16_t *) ! ha->req_q[0]->req_ring.bp, word_count, DDI_DEV_AUTOINCR); risc_address += word_count; fw_size -= byte_count; bufp += byte_count;
*** 2161,2300 **** } while (fw_size != 0); } rval = QL_FUNCTION_FAILED; } } else { rval = QL_FUNCTION_FAILED; } if (rval != QL_SUCCESS) { EL(ha, "Load RISC code\n"); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* - * Chip diagnostics - * Test chip for proper operation. - * - * Input: - * ha = adapter state pointer. - * - * Returns: - * ql local function return status code. - * - * Context: - * Kernel context. - */ - static int - ql_chip_diag(ql_adapter_state_t *ha) - { - ql_mbx_data_t mr; - int rval; - int32_t retries = 4; - uint16_t id; - - QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); - - do { - /* Reset ISP chip. */ - TASK_DAEMON_LOCK(ha); - ha->task_daemon_flags &= ~ISP_ABORT_NEEDED; - TASK_DAEMON_UNLOCK(ha); - - /* For ISP2200A reduce firmware load size. */ - if (CFG_IST(ha, CFG_CTRL_2200) && - RD16_IO_REG(ha, mailbox_out[7]) == 4) { - ha->fw_transfer_size = 128; - } else { - ha->fw_transfer_size = REQUEST_QUEUE_SIZE; - } - - rval = QL_SUCCESS; - if (!(CFG_IST(ha, CFG_CTRL_8021))) { - ql_reset_chip(ha); - - /* Check product ID of chip */ - mr.mb[1] = RD16_IO_REG(ha, mailbox_out[1]); - mr.mb[2] = RD16_IO_REG(ha, mailbox_out[2]); - mr.mb[3] = RD16_IO_REG(ha, mailbox_out[3]); - - if (ha->device_id == 0x5432 || - ha->device_id == 0x8432) { - id = 0x2432; - } else if (ha->device_id == 0x5422 || - ha->device_id == 0x8422) { - id = 0x2422; - } else { - id = ha->device_id; - } - - if (mr.mb[1] == PROD_ID_1 && - (mr.mb[2] == PROD_ID_2 || mr.mb[2] == PROD_ID_2a) && - (mr.mb[3] == PROD_ID_3 || mr.mb[3] == id)) { - ha->adapter_stats->revlvl.isp2200 = - RD16_IO_REG(ha, mailbox_out[4]); - ha->adapter_stats->revlvl.risc = - RD16_IO_REG(ha, mailbox_out[5]); - ha->adapter_stats->revlvl.frmbfr = - RD16_IO_REG(ha, mailbox_out[6]); - ha->adapter_stats->revlvl.riscrom = - RD16_IO_REG(ha, mailbox_out[7]); - } else { - cmn_err(CE_WARN, "%s(%d) - prod id failed!, " - "mb1=%xh, mb2=%xh, mb3=%xh", QL_NAME, - ha->instance, mr.mb[1], mr.mb[2], mr.mb[3]); - rval = QL_FUNCTION_FAILED; - } - } else if (!(ha->task_daemon_flags & FIRMWARE_LOADED)) { - break; - } - - if (rval == QL_SUCCESS) { - /* Wrap Incoming Mailboxes Test. */ - mr.mb[1] = 0xAAAA; - mr.mb[2] = 0x5555; - mr.mb[3] = 0xAA55; - mr.mb[4] = 0x55AA; - mr.mb[5] = 0xA5A5; - mr.mb[6] = 0x5A5A; - mr.mb[7] = 0x2525; - rval = ql_mbx_wrap_test(ha, &mr); - if (rval == QL_SUCCESS) { - if (mr.mb[1] != 0xAAAA || - mr.mb[2] != 0x5555 || - mr.mb[3] != 0xAA55 || - mr.mb[4] != 0x55AA || - mr.mb[5] != 0xA5A5 || - mr.mb[6] != 0x5A5A || - mr.mb[7] != 0x2525) { - rval = QL_FUNCTION_FAILED; - (void) ql_flash_errlog(ha, - FLASH_ERRLOG_ISP_ERR, 0, - RD16_IO_REG(ha, hccr), - RD16_IO_REG(ha, istatus)); - } - } else { - cmn_err(CE_WARN, "%s(%d) - reg test failed=" - "%xh!", QL_NAME, ha->instance, rval); - } - } - } while ((retries-- != 0) && (rval != QL_SUCCESS)); - - if (rval != QL_SUCCESS) { - EL(ha, "failed, rval = %xh\n", rval); - } else { - /*EMPTY*/ - QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); - } - return (rval); - } - - /* * ql_load_isp_firmware * Load and start RISC firmware. * Uses request ring for DMA buffer. * * Input: --- 2258,2281 ---- } while (fw_size != 0); } rval = QL_FUNCTION_FAILED; } } else { + ha->dev_state = NX_DEV_READY; rval = QL_FUNCTION_FAILED; } if (rval != QL_SUCCESS) { EL(ha, "Load RISC code\n"); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /* * ql_load_isp_firmware * Load and start RISC firmware. * Uses request ring for DMA buffer. * * Input:
*** 2309,2375 **** int ql_load_isp_firmware(ql_adapter_state_t *vha) { caddr_t risc_code_address; uint32_t risc_address, risc_code_size; ! int rval; uint32_t word_count, cnt; size_t byte_count; ql_adapter_state_t *ha = vha->pha; ! if (CFG_IST(ha, CFG_CTRL_8021)) { ! rval = ql_8021_load_risc(ha); } else { if (CFG_IST(ha, CFG_CTRL_81XX)) { ql_mps_reset(ha); } if (CFG_IST(ha, CFG_LOAD_FLASH_FW)) { return (ql_load_flash_fw(ha)); } ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Load firmware segments */ for (cnt = 0; cnt < MAX_RISC_CODE_SEGMENTS && ha->risc_fw[cnt].code != NULL; cnt++) { risc_code_address = ha->risc_fw[cnt].code; risc_address = ha->risc_fw[cnt].addr; risc_code_size = ha->risc_fw[cnt].length; while (risc_code_size) { ! if (CFG_IST(ha, CFG_CTRL_242581)) { word_count = ha->fw_transfer_size >> 2; if (word_count > risc_code_size) { word_count = risc_code_size; } byte_count = word_count << 2; ! ddi_rep_put32(ha->hba_buf.acc_handle, (uint32_t *)risc_code_address, ! (uint32_t *)ha->request_ring_bp, word_count, DDI_DEV_AUTOINCR); } else { word_count = ha->fw_transfer_size >> 1; if (word_count > risc_code_size) { word_count = risc_code_size; } byte_count = word_count << 1; ! ddi_rep_put16(ha->hba_buf.acc_handle, (uint16_t *)risc_code_address, ! (uint16_t *)ha->request_ring_bp, word_count, DDI_DEV_AUTOINCR); } ! (void) ddi_dma_sync(ha->hba_buf.dma_handle, ! REQUEST_Q_BUFFER_OFFSET, byte_count, ! DDI_DMA_SYNC_FORDEV); rval = ql_wrt_risc_ram(ha, risc_address, ! ha->request_dvma, word_count); if (rval != QL_SUCCESS) { EL(ha, "failed, load=%xh\n", rval); cnt = MAX_RISC_CODE_SEGMENTS; break; } --- 2290,2370 ---- int ql_load_isp_firmware(ql_adapter_state_t *vha) { caddr_t risc_code_address; uint32_t risc_address, risc_code_size; ! int rval = QL_FUNCTION_FAILED; uint32_t word_count, cnt; size_t byte_count; ql_adapter_state_t *ha = vha->pha; ! QL_PRINT_10(ha, "started\n"); ! ! if (CFG_IST(ha, CFG_CTRL_82XX)) { ! rval = ql_8021_reset_fw(ha) == NX_DEV_READY ? ! QL_SUCCESS : QL_FUNCTION_FAILED; } else { if (CFG_IST(ha, CFG_CTRL_81XX)) { ql_mps_reset(ha); } if (CFG_IST(ha, CFG_LOAD_FLASH_FW)) { + QL_PRINT_10(ha, "CFG_LOAD_FLASH_FW exit\n"); return (ql_load_flash_fw(ha)); } ! if (CFG_IST(ha, CFG_CTRL_27XX)) { ! (void) ql_2700_get_module_dmp_template(ha); ! } /* Load firmware segments */ for (cnt = 0; cnt < MAX_RISC_CODE_SEGMENTS && ha->risc_fw[cnt].code != NULL; cnt++) { risc_code_address = ha->risc_fw[cnt].code; risc_address = ha->risc_fw[cnt].addr; + if ((risc_address = ha->risc_fw[cnt].addr) == 0) { + continue; + } risc_code_size = ha->risc_fw[cnt].length; while (risc_code_size) { ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2)) { word_count = ha->fw_transfer_size >> 2; if (word_count > risc_code_size) { word_count = risc_code_size; } byte_count = word_count << 2; ! ddi_rep_put32( ! ha->req_q[0]->req_ring.acc_handle, (uint32_t *)risc_code_address, ! (uint32_t *) ! ha->req_q[0]->req_ring.bp, word_count, DDI_DEV_AUTOINCR); } else { word_count = ha->fw_transfer_size >> 1; if (word_count > risc_code_size) { word_count = risc_code_size; } byte_count = word_count << 1; ! ddi_rep_put16( ! ha->req_q[0]->req_ring.acc_handle, (uint16_t *)risc_code_address, ! (uint16_t *) ! ha->req_q[0]->req_ring.bp, word_count, DDI_DEV_AUTOINCR); } ! (void) ddi_dma_sync( ! ha->req_q[0]->req_ring.dma_handle, ! 0, byte_count, DDI_DMA_SYNC_FORDEV); rval = ql_wrt_risc_ram(ha, risc_address, ! ha->req_q[0]->req_ring.cookie.dmac_laddress, ! word_count); if (rval != QL_SUCCESS) { EL(ha, "failed, load=%xh\n", rval); cnt = MAX_RISC_CODE_SEGMENTS; break; }
*** 2378,2387 **** --- 2373,2383 ---- risc_code_size -= word_count; risc_code_address += byte_count; } } } + bzero(ha->req_q[0]->req_ring.bp, ha->fw_transfer_size); /* Start firmware. */ if (rval == QL_SUCCESS) { rval = ql_start_firmware(ha); }
*** 2388,2398 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } --- 2384,2394 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); }
*** 2412,2467 **** int rval; uint8_t seg_cnt; uint32_t risc_address, xfer_size, count, *bp, faddr; uint32_t risc_code_size = 0; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); faddr = ha->flash_data_addr | ha->flash_fw_addr; for (seg_cnt = 0; seg_cnt < 2; seg_cnt++) { xfer_size = ha->fw_transfer_size >> 2; do { GLOBAL_HW_LOCK(); /* Read data from flash. */ ! bp = (uint32_t *)ha->request_ring_bp; for (count = 0; count < xfer_size; count++) { ! rval = ql_24xx_read_flash(ha, faddr++, bp); if (rval != QL_SUCCESS) { break; } ql_chg_endian((uint8_t *)bp++, 4); } GLOBAL_HW_UNLOCK(); if (rval != QL_SUCCESS) { ! EL(ha, "24xx_read_flash failed=%xh\n", rval); break; } if (risc_code_size == 0) { ! bp = (uint32_t *)ha->request_ring_bp; risc_address = bp[2]; risc_code_size = bp[3]; ! ha->risc_fw[seg_cnt].addr = risc_address; } if (risc_code_size < xfer_size) { faddr -= xfer_size - risc_code_size; xfer_size = risc_code_size; } ! (void) ddi_dma_sync(ha->hba_buf.dma_handle, ! REQUEST_Q_BUFFER_OFFSET, xfer_size << 2, ! DDI_DMA_SYNC_FORDEV); rval = ql_wrt_risc_ram(ha, risc_address, ! ha->request_dvma, xfer_size); if (rval != QL_SUCCESS) { ! EL(ha, "ql_wrt_risc_ram failed=%xh\n", rval); break; } risc_address += xfer_size; risc_code_size -= xfer_size; --- 2408,2478 ---- int rval; uint8_t seg_cnt; uint32_t risc_address, xfer_size, count, *bp, faddr; uint32_t risc_code_size = 0; ! QL_PRINT_10(ha, "started\n"); + if (CFG_IST(ha, CFG_CTRL_278083)) { + if ((rval = ql_load_flash_image(ha)) != QL_SUCCESS) { + EL(ha, "load_flash_image status=%xh\n", rval); + } else if (CFG_IST(ha, CFG_CTRL_27XX) && + (rval = ql_2700_get_flash_dmp_template(ha)) != + QL_SUCCESS) { + EL(ha, "get_flash_dmp_template status=%xh\n", rval); + } + } else { faddr = ha->flash_data_addr | ha->flash_fw_addr; for (seg_cnt = 0; seg_cnt < 2; seg_cnt++) { xfer_size = ha->fw_transfer_size >> 2; do { GLOBAL_HW_LOCK(); /* Read data from flash. */ ! bp = (uint32_t *)ha->req_q[0]->req_ring.bp; for (count = 0; count < xfer_size; count++) { ! rval = ql_24xx_read_flash(ha, faddr++, ! bp); if (rval != QL_SUCCESS) { break; } ql_chg_endian((uint8_t *)bp++, 4); } GLOBAL_HW_UNLOCK(); if (rval != QL_SUCCESS) { ! EL(ha, "24xx_read_flash failed=%xh\n", ! rval); break; } if (risc_code_size == 0) { ! bp = (uint32_t *) ! ha->req_q[0]->req_ring.bp; risc_address = bp[2]; risc_code_size = bp[3]; ! ha->risc_fw[seg_cnt].addr = ! risc_address; } if (risc_code_size < xfer_size) { faddr -= xfer_size - risc_code_size; xfer_size = risc_code_size; } ! (void) ddi_dma_sync( ! ha->req_q[0]->req_ring.dma_handle, ! 0, xfer_size << 2, DDI_DMA_SYNC_FORDEV); rval = ql_wrt_risc_ram(ha, risc_address, ! ha->req_q[0]->req_ring.cookie.dmac_laddress, ! xfer_size); if (rval != QL_SUCCESS) { ! EL(ha, "ql_wrt_risc_ram failed=%xh\n", ! rval); break; } risc_address += xfer_size; risc_code_size -= xfer_size;
*** 2469,2478 **** --- 2480,2490 ---- if (rval != QL_SUCCESS) { break; } } + } /* Start firmware. */ if (rval == QL_SUCCESS) { rval = ql_start_firmware(ha); }
*** 2479,2489 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 2491,2501 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 2502,2517 **** int ql_start_firmware(ql_adapter_state_t *vha) { int rval, rval2; uint32_t data; ! ql_mbx_data_t mr; ql_adapter_state_t *ha = vha->pha; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); ! if (CFG_IST(ha, CFG_CTRL_8021)) { /* Save firmware version. */ rval = ql_get_fw_version(ha, &mr, MAILBOX_TOV); ha->fw_major_version = mr.mb[1]; ha->fw_minor_version = mr.mb[2]; ha->fw_subminor_version = mr.mb[3]; --- 2514,2531 ---- int ql_start_firmware(ql_adapter_state_t *vha) { int rval, rval2; uint32_t data; ! ql_mbx_data_t mr = {0}; ql_adapter_state_t *ha = vha->pha; + ql_init_24xx_cb_t *icb = + (ql_init_24xx_cb_t *)&ha->init_ctrl_blk.cb24; ! QL_PRINT_10(ha, "started\n"); ! if (CFG_IST(ha, CFG_CTRL_82XX)) { /* Save firmware version. */ rval = ql_get_fw_version(ha, &mr, MAILBOX_TOV); ha->fw_major_version = mr.mb[1]; ha->fw_minor_version = mr.mb[2]; ha->fw_subminor_version = mr.mb[3];
*** 2524,2559 **** /* Save firmware version. */ (void) ql_get_fw_version(ha, &mr, MAILBOX_TOV); ha->fw_major_version = mr.mb[1]; ha->fw_minor_version = mr.mb[2]; ha->fw_subminor_version = mr.mb[3]; ! ha->fw_ext_memory_size = ((SHORT_TO_LONG(mr.mb[4], mr.mb[5]) - 0x100000) + 1) * 4; ha->fw_attributes = mr.mb[6]; - - if (CFG_IST(ha, CFG_CTRL_81XX)) { ha->phy_fw_major_version = LSB(mr.mb[8]); ha->phy_fw_minor_version = MSB(mr.mb[9]); ha->phy_fw_subminor_version = LSB(mr.mb[9]); ha->mpi_fw_major_version = LSB(mr.mb[10]); ha->mpi_fw_minor_version = MSB(mr.mb[11]); ha->mpi_fw_subminor_version = LSB(mr.mb[11]); ! ha->mpi_capability_list = SHORT_TO_LONG(mr.mb[13], ! mr.mb[12]); if ((rval2 = ql_flash_access(ha, FAC_GET_SECTOR_SIZE, 0, 0, &data)) == QL_SUCCESS) { ha->xioctl->fdesc.block_size = data << 2; ! QL_PRINT_10(CE_CONT, "(%d): fdesc.block_size=" ! "%xh\n", ha->instance, ha->xioctl->fdesc.block_size); } else { EL(ha, "flash_access status=%xh\n", rval2); } } /* Set Serdes Transmit Parameters. */ ! if (CFG_IST(ha, CFG_CTRL_2422) && ha->serdes_param[0] & BIT_0) { mr.mb[1] = ha->serdes_param[0]; mr.mb[2] = ha->serdes_param[1]; mr.mb[3] = ha->serdes_param[2]; mr.mb[4] = ha->serdes_param[3]; (void) ql_serdes_param(ha, &mr); --- 2538,2592 ---- /* Save firmware version. */ (void) ql_get_fw_version(ha, &mr, MAILBOX_TOV); ha->fw_major_version = mr.mb[1]; ha->fw_minor_version = mr.mb[2]; ha->fw_subminor_version = mr.mb[3]; ! ha->fw_ext_memory_end = SHORT_TO_LONG(mr.mb[4], mr.mb[5]); ! ha->fw_ext_memory_size = ((ha->fw_ext_memory_end - 0x100000) + 1) * 4; + if (CFG_IST(ha, CFG_CTRL_278083)) { + ha->fw_attributes = SHORT_TO_LONG(mr.mb[6], mr.mb[15]); + ha->phy_fw_major_version = LSB(mr.mb[13]); + ha->phy_fw_minor_version = MSB(mr.mb[14]); + ha->phy_fw_subminor_version = LSB(mr.mb[14]); + ha->fw_ext_attributes = SHORT_TO_LONG(mr.mb[16], + mr.mb[17]); + } else { ha->fw_attributes = mr.mb[6]; ha->phy_fw_major_version = LSB(mr.mb[8]); ha->phy_fw_minor_version = MSB(mr.mb[9]); ha->phy_fw_subminor_version = LSB(mr.mb[9]); + ha->mpi_capability_list = + SHORT_TO_LONG(mr.mb[13], mr.mb[12]); + } ha->mpi_fw_major_version = LSB(mr.mb[10]); ha->mpi_fw_minor_version = MSB(mr.mb[11]); ha->mpi_fw_subminor_version = LSB(mr.mb[11]); ! if (CFG_IST(ha, CFG_CTRL_27XX)) { ! ha->fw_shared_ram_start = ! SHORT_TO_LONG(mr.mb[18], mr.mb[19]); ! ha->fw_shared_ram_end = ! SHORT_TO_LONG(mr.mb[20], mr.mb[21]); ! ha->fw_ddr_ram_start = ! SHORT_TO_LONG(mr.mb[22], mr.mb[23]); ! ha->fw_ddr_ram_end = ! SHORT_TO_LONG(mr.mb[24], mr.mb[25]); ! } ! if (CFG_IST(ha, CFG_FLASH_ACC_SUPPORT)) { if ((rval2 = ql_flash_access(ha, FAC_GET_SECTOR_SIZE, 0, 0, &data)) == QL_SUCCESS) { ha->xioctl->fdesc.block_size = data << 2; ! QL_PRINT_10(ha, "fdesc.block_size=" ! "%xh\n", ha->xioctl->fdesc.block_size); } else { EL(ha, "flash_access status=%xh\n", rval2); } } /* Set Serdes Transmit Parameters. */ ! if (CFG_IST(ha, CFG_CTRL_24XX) && ha->serdes_param[0] & BIT_0) { mr.mb[1] = ha->serdes_param[0]; mr.mb[2] = ha->serdes_param[1]; mr.mb[3] = ha->serdes_param[2]; mr.mb[4] = ha->serdes_param[3]; (void) ql_serdes_param(ha, &mr);
*** 2565,2580 **** mr.mb[2] = (uint16_t) (mr.mb[2] | FO2_FCOE_512_MAX_MEM_WR_BURST); (void) ql_set_firmware_option(ha, &mr); } } if (rval != QL_SUCCESS) { ha->task_daemon_flags &= ~FIRMWARE_LOADED; EL(ha, "failed, rval = %xh\n", rval); } else { ha->task_daemon_flags |= FIRMWARE_LOADED; ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 2598,2656 ---- mr.mb[2] = (uint16_t) (mr.mb[2] | FO2_FCOE_512_MAX_MEM_WR_BURST); (void) ql_set_firmware_option(ha, &mr); } } + + if (ha->flags & MULTI_QUEUE) { + QL_PRINT_10(ha, "MULTI_QUEUE\n"); + icb->msi_x_vector[0] = LSB(ha->rsp_queues[0]->msi_x_vector); + icb->msi_x_vector[1] = MSB(ha->rsp_queues[0]->msi_x_vector); + if (ha->iflags & IFLG_INTR_MSIX && + CFG_IST(ha, CFG_NO_INTR_HSHAKE_SUP)) { + QL_PRINT_10(ha, "NO_INTR_HANDSHAKE\n"); + ADAPTER_STATE_LOCK(ha); + ha->flags |= NO_INTR_HANDSHAKE; + ADAPTER_STATE_UNLOCK(ha); + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] & ~(BIT_6 | BIT_5)); + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] | BIT_7); + } else { + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] & ~BIT_5); + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] | BIT_7 | BIT_6); + } + } else { + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] & ~(BIT_7 | BIT_5)); + icb->firmware_options_2[2] = (uint8_t) + (icb->firmware_options_2[2] | BIT_6); + } + icb->firmware_options_2[3] = (uint8_t) + (icb->firmware_options_2[3] & ~(BIT_1 | BIT_0)); + + /* Set fw execution throttle. */ + if (CFG_IST(ha, CFG_CTRL_22XX) || + ql_get_resource_cnts(ha, &mr) != QL_SUCCESS) { + icb->execution_throttle[0] = 0xff; + icb->execution_throttle[1] = 0xff; + } else { + icb->execution_throttle[0] = LSB(mr.mb[6]); + icb->execution_throttle[1] = MSB(mr.mb[6]); + } + EL(ha, "icb->execution_throttle %d\n", + CHAR_TO_SHORT(icb->execution_throttle[0], + icb->execution_throttle[1])); + if (rval != QL_SUCCESS) { ha->task_daemon_flags &= ~FIRMWARE_LOADED; EL(ha, "failed, rval = %xh\n", rval); } else { ha->task_daemon_flags |= FIRMWARE_LOADED; ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 2591,2609 **** * Kernel context. */ int ql_set_cache_line(ql_adapter_state_t *ha) { ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Set the cache line. */ if (CFG_IST(ha->pha, CFG_SET_CACHE_LINE_SIZE_1)) { /* Set cache line register. */ ql_pci_config_put8(ha->pha, PCI_CONF_CACHE_LINESZ, 1); } ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); return (QL_SUCCESS); } /* --- 2667,2685 ---- * Kernel context. */ int ql_set_cache_line(ql_adapter_state_t *ha) { ! QL_PRINT_3(ha, "started\n"); /* Set the cache line. */ if (CFG_IST(ha->pha, CFG_SET_CACHE_LINE_SIZE_1)) { /* Set cache line register. */ ql_pci_config_put8(ha->pha, PCI_CONF_CACHE_LINESZ, 1); } ! QL_PRINT_3(ha, "done\n"); return (QL_SUCCESS); } /*
*** 2613,2623 **** * Beginning of response ring has initialization control block * already built by nvram config routine. * * Input: * ha = adapter state pointer. ! * ha->hba_buf = request and response rings * ha->init_ctrl_blk = initialization control block * * Returns: * ql local function return status code. * --- 2689,2700 ---- * Beginning of response ring has initialization control block * already built by nvram config routine. * * Input: * ha = adapter state pointer. ! * ha->req_q = request rings ! * ha->rsp_queues = response rings * ha->init_ctrl_blk = initialization control block * * Returns: * ql local function return status code. *
*** 2630,2684 **** int rval, rval2; uint16_t index; ql_mbx_data_t mr; ql_adapter_state_t *ha = vha2->pha; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Clear outstanding commands array. */ ! for (index = 0; index < MAX_OUTSTANDING_COMMANDS; index++) { ha->outstanding_cmds[index] = NULL; } ha->osc_index = 1; ha->pending_cmds.first = NULL; ha->pending_cmds.last = NULL; /* Initialize firmware. */ ! ha->request_ring_ptr = ha->request_ring_bp; ! ha->req_ring_index = 0; ! ha->req_q_cnt = REQUEST_ENTRY_CNT - 1; ! ha->response_ring_ptr = ha->response_ring_bp; ! ha->rsp_ring_index = 0; if (ha->flags & VP_ENABLED) { ql_adapter_state_t *vha; - uint16_t cnt; - uint32_t max_vports; ql_init_24xx_cb_t *icb = &ha->init_ctrl_blk.cb24; - max_vports = (CFG_IST(ha, CFG_CTRL_2422) ? - MAX_24_VIRTUAL_PORTS : MAX_25_VIRTUAL_PORTS); bzero(icb->vp_count, ((uintptr_t)icb + sizeof (ql_init_24xx_cb_t)) - (uintptr_t)icb->vp_count); ! icb->vp_count[0] = (uint8_t)max_vports; /* Allow connection option 2. */ icb->global_vp_option[0] = BIT_1; ! for (cnt = 0, vha = ha->vp_next; cnt < max_vports && ! vha != NULL; vha = vha->vp_next, cnt++) { index = (uint8_t)(vha->vp_index - 1); bcopy(vha->loginparams.node_ww_name.raw_wwn, icb->vpc[index].node_name, 8); bcopy(vha->loginparams.nport_ww_name.raw_wwn, icb->vpc[index].port_name, 8); - icb->vpc[index].options = VPO_TARGET_MODE_DISABLED | - VPO_INITIATOR_MODE_ENABLED; if (vha->flags & VP_ENABLED) { icb->vpc[index].options = (uint8_t) (icb->vpc[index].options | VPO_ENABLED); } } --- 2707,2764 ---- int rval, rval2; uint16_t index; ql_mbx_data_t mr; ql_adapter_state_t *ha = vha2->pha; ! QL_PRINT_3(ha, "started\n"); /* Clear outstanding commands array. */ ! for (index = 0; index < ha->osc_max_cnt; index++) { ha->outstanding_cmds[index] = NULL; } ha->osc_index = 1; ha->pending_cmds.first = NULL; ha->pending_cmds.last = NULL; /* Initialize firmware. */ ! ha->req_q[0]->req_ring_ptr = ha->req_q[0]->req_ring.bp; ! ha->req_q[0]->req_ring_index = 0; ! ha->req_q[0]->req_q_cnt = REQUEST_ENTRY_CNT - 1; ! ha->rsp_queues[0]->rsp_ring_ptr = ha->rsp_queues[0]->rsp_ring.bp; ! ha->rsp_queues[0]->rsp_ring_index = 0; if (ha->flags & VP_ENABLED) { ql_adapter_state_t *vha; ql_init_24xx_cb_t *icb = &ha->init_ctrl_blk.cb24; bzero(icb->vp_count, ((uintptr_t)icb + sizeof (ql_init_24xx_cb_t)) - (uintptr_t)icb->vp_count); ! icb->vp_count[0] = ha->max_vports - 1; /* Allow connection option 2. */ icb->global_vp_option[0] = BIT_1; ! /* Setup default options for all ports. */ ! for (index = 0; index < ha->max_vports; index++) { ! icb->vpc[index].options = VPO_TARGET_MODE_DISABLED | ! VPO_INITIATOR_MODE_ENABLED; ! } ! /* Setup enabled ports. */ ! for (vha = ha->vp_next; vha != NULL; vha = vha->vp_next) { ! if (vha->vp_index == 0 || ! vha->vp_index >= ha->max_vports) { ! continue; ! } index = (uint8_t)(vha->vp_index - 1); bcopy(vha->loginparams.node_ww_name.raw_wwn, icb->vpc[index].node_name, 8); bcopy(vha->loginparams.nport_ww_name.raw_wwn, icb->vpc[index].port_name, 8); if (vha->flags & VP_ENABLED) { icb->vpc[index].options = (uint8_t) (icb->vpc[index].options | VPO_ENABLED); } }
*** 2692,2702 **** } else { break; } } ! if (rval == QL_SUCCESS && (CFG_IST(ha, CFG_CTRL_24258081)) == 0) { /* Tell firmware to enable MBA_PORT_BYPASS_CHANGED event */ rval = ql_get_firmware_option(ha, &mr); if (rval == QL_SUCCESS) { mr.mb[1] = (uint16_t)(mr.mb[1] | BIT_9); mr.mb[2] = 0; --- 2772,2782 ---- } else { break; } } ! if (rval == QL_SUCCESS && CFG_IST(ha, CFG_ISP_FW_TYPE_1)) { /* Tell firmware to enable MBA_PORT_BYPASS_CHANGED event */ rval = ql_get_firmware_option(ha, &mr); if (rval == QL_SUCCESS) { mr.mb[1] = (uint16_t)(mr.mb[1] | BIT_9); mr.mb[2] = 0;
*** 2710,2720 **** if ((rval2 = ql_get_dma_mem(ha, &ha->fwfcetracebuf, FWFCESIZE, LITTLE_ENDIAN_DMA, QL_DMA_RING_ALIGN)) != QL_SUCCESS) { EL(ha, "fcetrace buffer alloc failed: %xh\n", rval2); } else { if ((rval2 = ql_fw_etrace(ha, &ha->fwfcetracebuf, ! FTO_FCE_TRACE_ENABLE)) != QL_SUCCESS) { EL(ha, "fcetrace enable failed: %xh\n", rval2); ql_free_phys(ha, &ha->fwfcetracebuf); } } } --- 2790,2800 ---- if ((rval2 = ql_get_dma_mem(ha, &ha->fwfcetracebuf, FWFCESIZE, LITTLE_ENDIAN_DMA, QL_DMA_RING_ALIGN)) != QL_SUCCESS) { EL(ha, "fcetrace buffer alloc failed: %xh\n", rval2); } else { if ((rval2 = ql_fw_etrace(ha, &ha->fwfcetracebuf, ! FTO_FCE_TRACE_ENABLE, NULL)) != QL_SUCCESS) { EL(ha, "fcetrace enable failed: %xh\n", rval2); ql_free_phys(ha, &ha->fwfcetracebuf); } } }
*** 2724,2734 **** if ((rval2 = ql_get_dma_mem(ha, &ha->fwexttracebuf, FWEXTSIZE, LITTLE_ENDIAN_DMA, QL_DMA_RING_ALIGN)) != QL_SUCCESS) { EL(ha, "exttrace buffer alloc failed: %xh\n", rval2); } else { if ((rval2 = ql_fw_etrace(ha, &ha->fwexttracebuf, ! FTO_EXT_TRACE_ENABLE)) != QL_SUCCESS) { EL(ha, "exttrace enable failed: %xh\n", rval2); ql_free_phys(ha, &ha->fwexttracebuf); } } } --- 2804,2814 ---- if ((rval2 = ql_get_dma_mem(ha, &ha->fwexttracebuf, FWEXTSIZE, LITTLE_ENDIAN_DMA, QL_DMA_RING_ALIGN)) != QL_SUCCESS) { EL(ha, "exttrace buffer alloc failed: %xh\n", rval2); } else { if ((rval2 = ql_fw_etrace(ha, &ha->fwexttracebuf, ! FTO_EXT_TRACE_ENABLE, NULL)) != QL_SUCCESS) { EL(ha, "exttrace enable failed: %xh\n", rval2); ql_free_phys(ha, &ha->fwexttracebuf); } } }
*** 2800,2810 **** EL(ha, "failed, rval = %xh\n", rval); } else { TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= FIRMWARE_UP; TASK_DAEMON_UNLOCK(ha); ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 2880,2890 ---- EL(ha, "failed, rval = %xh\n", rval); } else { TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= FIRMWARE_UP; TASK_DAEMON_UNLOCK(ha); ! QL_PRINT_3(ha, "done\n"); } return (rval); } /*
*** 2824,2857 **** */ int ql_fw_ready(ql_adapter_state_t *ha, uint8_t secs) { ql_mbx_data_t mr; ! clock_t timer; clock_t dly = 250000; clock_t sec_delay = MICROSEC / dly; - clock_t wait = secs * sec_delay; int rval = QL_FUNCTION_FAILED; ! uint16_t state = 0xffff; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); ! timer = ha->r_a_tov < secs ? secs : ha->r_a_tov; ! timer = (timer + 2) * sec_delay; /* Wait for ISP to finish LIP */ ! while (timer != 0 && wait != 0 && ! !(ha->task_daemon_flags & ISP_ABORT_NEEDED)) { rval = ql_get_firmware_state(ha, &mr); if (rval == QL_SUCCESS) { ! if (ha->task_daemon_flags & (ISP_ABORT_NEEDED | ! LOOP_DOWN)) { ! wait--; ! } else if (mr.mb[1] != FSTATE_READY) { if (mr.mb[1] != FSTATE_WAIT_LOGIN) { ! wait--; } rval = QL_FUNCTION_FAILED; } else { /* Firmware is ready. Get 2 * R_A_TOV. */ rval = ql_get_timeout_parameters(ha, --- 2904,2953 ---- */ int ql_fw_ready(ql_adapter_state_t *ha, uint8_t secs) { ql_mbx_data_t mr; ! clock_t timer, login_wait, wait; clock_t dly = 250000; clock_t sec_delay = MICROSEC / dly; int rval = QL_FUNCTION_FAILED; ! uint16_t state[6] = {0}; ! QL_PRINT_3(ha, "started\n"); ! login_wait = ha->r_a_tov * 2 * sec_delay; ! timer = wait = secs * sec_delay; ! state[0] = 0xffff; /* Wait for ISP to finish LIP */ ! while (login_wait != 0 && wait != 0 && ! !(ha->task_daemon_flags & ISP_ABORT_NEEDED) && ! !(ha->flags & MPI_RESET_NEEDED)) { rval = ql_get_firmware_state(ha, &mr); if (rval == QL_SUCCESS) { ! if (mr.mb[1] != FSTATE_READY) { ! if (mr.mb[1] == FSTATE_LOSS_SYNC && ! mr.mb[4] == FSTATE_MPI_NIC_ERROR && ! CFG_IST(ha, CFG_FCOE_SUPPORT)) { ! EL(ha, "mpi_nic_error, " ! "isp_abort_needed\n"); ! ADAPTER_STATE_LOCK(ha); ! ha->flags |= MPI_RESET_NEEDED; ! ADAPTER_STATE_UNLOCK(ha); ! if (!(ha->task_daemon_flags & ! ABORT_ISP_ACTIVE)) { ! TASK_DAEMON_LOCK(ha); ! ha->task_daemon_flags |= ! ISP_ABORT_NEEDED; ! TASK_DAEMON_UNLOCK(ha); ! } ! } if (mr.mb[1] != FSTATE_WAIT_LOGIN) { ! timer = --wait; ! } else { ! timer = --login_wait; } rval = QL_FUNCTION_FAILED; } else { /* Firmware is ready. Get 2 * R_A_TOV. */ rval = ql_get_timeout_parameters(ha,
*** 2873,2892 **** } else { break; } } } else { ! wait--; } ! if (state != mr.mb[1]) { ! EL(ha, "mailbox_reg[1] = %xh\n", mr.mb[1]); ! state = mr.mb[1]; } /* Delay for a tick if waiting. */ ! if (timer-- != 0 && wait != 0) { if (timer % 4 == 0) { delay(drv_usectohz(dly)); } else { drv_usecwait(dly); } --- 2969,2997 ---- } else { break; } } } else { ! break; } ! if (state[0] != mr.mb[1] || state[1] != mr.mb[2] || ! state[2] != mr.mb[3] || state[3] != mr.mb[4] || ! state[4] != mr.mb[5] || state[5] != mr.mb[6]) { ! EL(ha, "mbx1=%xh, mbx2=%xh, mbx3=%xh, mbx4=%xh, " ! "mbx5=%xh, mbx6=%xh\n", mr.mb[1], mr.mb[2], ! mr.mb[3], mr.mb[4], mr.mb[5], mr.mb[6]); ! state[0] = mr.mb[1]; ! state[1] = mr.mb[2]; ! state[2] = mr.mb[3]; ! state[3] = mr.mb[4]; ! state[4] = mr.mb[5]; ! state[5] = mr.mb[6]; } /* Delay for a tick if waiting. */ ! if (timer != 0) { if (timer % 4 == 0) { delay(drv_usectohz(dly)); } else { drv_usecwait(dly); }
*** 2894,2907 **** rval = QL_FUNCTION_TIMEOUT; } } if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 2999,3019 ---- rval = QL_FUNCTION_TIMEOUT; } } if (rval != QL_SUCCESS) { + if ((ha->task_daemon_flags & ISP_ABORT_NEEDED || + ha->flags & MPI_RESET_NEEDED) && + ha->task_daemon_flags & LOOP_RESYNC_NEEDED) { + TASK_DAEMON_LOCK(ha); + ha->task_daemon_flags &= ~LOOP_RESYNC_NEEDED; + TASK_DAEMON_UNLOCK(ha); + } EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(ha, "done\n"); } return (rval); } /*
*** 2918,2936 **** * Kernel context. */ static int ql_configure_loop(ql_adapter_state_t *ha) { ! int rval; ql_adapter_state_t *vha; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); for (vha = ha; vha != NULL; vha = vha->vp_next) { TASK_DAEMON_LOCK(ha); if (!(vha->task_daemon_flags & LOOP_RESYNC_NEEDED) && ! vha->vp_index != 0 && !(vha->flags & VP_ENABLED)) { TASK_DAEMON_UNLOCK(ha); continue; } vha->task_daemon_flags &= ~LOOP_RESYNC_NEEDED; TASK_DAEMON_UNLOCK(ha); --- 3030,3050 ---- * Kernel context. */ static int ql_configure_loop(ql_adapter_state_t *ha) { ! int rval = QL_SUCCESS; ql_adapter_state_t *vha; ! QL_PRINT_10(ha, "started\n"); for (vha = ha; vha != NULL; vha = vha->vp_next) { TASK_DAEMON_LOCK(ha); if (!(vha->task_daemon_flags & LOOP_RESYNC_NEEDED) && ! vha->vp_index != 0 && ! (!(vha->flags & VP_ENABLED) || ! vha->flags & VP_ID_NOT_ACQUIRED)) { TASK_DAEMON_UNLOCK(ha); continue; } vha->task_daemon_flags &= ~LOOP_RESYNC_NEEDED; TASK_DAEMON_UNLOCK(ha);
*** 2948,2958 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 3062,3072 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 2965,2997 **** * Returns: * ql local function return status code. * * Context: * Kernel context. */ static void ql_configure_n_port_info(ql_adapter_state_t *ha) { ql_tgt_t tmp_tq; ql_tgt_t *tq; uint8_t *cb_port_name; ql_link_t *link; int index, rval; ! tq = &tmp_tq; /* Free existing target queues. */ for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { link = ha->dev[index].first; while (link != NULL) { tq = link->base_address; link = link->next; ! ql_remove_link(&ha->dev[index], &tq->device); ! ql_dev_free(ha, tq); } } /* * If the N_Port's WWPN is larger than our's then it has the * N_Port login initiative. It will have determined that and * logged in with the firmware. This results in a device * database entry. In this situation we will later send up a PLOGI --- 3079,3157 ---- * Returns: * ql local function return status code. * * Context: * Kernel context. + * ADAPTER_STATE_LOCK must be already obtained */ static void ql_configure_n_port_info(ql_adapter_state_t *ha) { ql_tgt_t tmp_tq; ql_tgt_t *tq; uint8_t *cb_port_name; ql_link_t *link; int index, rval; + uint16_t loop_id = 0; + uint32_t found = 0; + ql_dev_id_list_t *list; + uint32_t list_size; + ql_mbx_data_t mr; + port_id_t d_id = {0, 0, 0, 0}; ! QL_PRINT_10(ha, "started\n"); /* Free existing target queues. */ for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { link = ha->dev[index].first; while (link != NULL) { tq = link->base_address; link = link->next; ! ! /* workaround FW issue, do implicit logout */ ! /* Never logo to the reused loopid!! */ ! if ((tq->loop_id != 0x7ff) && ! (tq->loop_id != 0x7fe)) { ! if (found == 0) { ! rval = ql_get_port_database(ha, ! tq, PDF_NONE); ! if ((rval == QL_SUCCESS) && ! (tq->master_state == ! PD_STATE_PORT_LOGGED_IN)) { ! EL(ha, "nport id (%xh) " ! "loop_id=%xh " ! "reappeared\n", ! tq->d_id.b24, ! tq->loop_id); ! bcopy((void *)&tq->port_name[0], ! (void *)&ha->n_port-> ! port_name[0], ! 8); ! bcopy((void *)&tq->node_name[0], ! (void *)&ha->n_port-> ! node_name[0], ! 8); ! ha->n_port->d_id.b24 = ! tq->d_id.b24; ! found = 1; ! continue; } } + (void) ql_logout_fabric_port(ha, tq); + } + tq->loop_id = PORT_NO_LOOP_ID; + } + } + + if (found == 1) { + QL_PRINT_10(ha, "done found\n"); + return; + } + + tq = &tmp_tq; + /* * If the N_Port's WWPN is larger than our's then it has the * N_Port login initiative. It will have determined that and * logged in with the firmware. This results in a device * database entry. In this situation we will later send up a PLOGI
*** 3015,3034 **** tq->d_id.b.area = 0; tq->d_id.b.domain = 0; tq->loop_id = 0x7fe; rval = ql_get_port_database(ha, tq, PDF_NONE); - if (rval == QL_SUCCESS || rval == QL_NOT_LOGGED_IN) { - ql_dev_id_list_t *list; - uint32_t list_size; - ql_mbx_data_t mr; - port_id_t d_id = {0, 0, 0, 0}; - uint16_t loop_id = 0; ! cb_port_name = (uint8_t *)(CFG_IST(ha, CFG_CTRL_24258081) ? ! &ha->init_ctrl_blk.cb24.port_name[0] : ! &ha->init_ctrl_blk.cb.port_name[0]); if ((ql_wwn_cmp(ha, (la_wwn_t *)&tq->port_name[0], (la_wwn_t *)cb_port_name) == 1)) { EL(ha, "target port has N_Port login initiative\n"); } else { --- 3175,3192 ---- tq->d_id.b.area = 0; tq->d_id.b.domain = 0; tq->loop_id = 0x7fe; rval = ql_get_port_database(ha, tq, PDF_NONE); ! /* ! * Only collect the P2P remote port information in the case of ! * QL_SUCCESS. FW should have always logged in (flogi) to remote ! * port at this point. ! */ ! if (rval == QL_SUCCESS) { ! cb_port_name = &ha->loginparams.nport_ww_name.raw_wwn[0]; if ((ql_wwn_cmp(ha, (la_wwn_t *)&tq->port_name[0], (la_wwn_t *)cb_port_name) == 1)) { EL(ha, "target port has N_Port login initiative\n"); } else {
*** 3043,3065 **** (void *)&ha->n_port->node_name[0], 8); /* Resolve an n_port_handle */ ha->n_port->n_port_handle = 0x7fe; list_size = sizeof (ql_dev_id_list_t) * DEVICE_LIST_ENTRIES; list = (ql_dev_id_list_t *)kmem_zalloc(list_size, KM_SLEEP); ! if (list != NULL && ! ql_get_id_list(ha, (caddr_t)list, list_size, &mr) == QL_SUCCESS) { ! if (mr.mb[1]) { ! EL(ha, "id list entries = %d\n", mr.mb[1]); ! for (index = 0; index < mr.mb[1]; index++) { ql_dev_list(ha, list, index, &d_id, &loop_id); ha->n_port->n_port_handle = loop_id; ! } } else { for (index = 0; index <= LAST_LOCAL_LOOP_ID; index++) { /* resuse tq */ tq->loop_id = (uint16_t)index; --- 3201,3227 ---- (void *)&ha->n_port->node_name[0], 8); /* Resolve an n_port_handle */ ha->n_port->n_port_handle = 0x7fe; + } + list_size = sizeof (ql_dev_id_list_t) * DEVICE_LIST_ENTRIES; list = (ql_dev_id_list_t *)kmem_zalloc(list_size, KM_SLEEP); ! if (ql_get_id_list(ha, (caddr_t)list, list_size, &mr) == QL_SUCCESS) { ! /* For the p2p mr.mb[1] must be 1 */ ! if (mr.mb[1] == 1) { ! index = 0; ql_dev_list(ha, list, index, &d_id, &loop_id); ha->n_port->n_port_handle = loop_id; ! ! tq->loop_id = loop_id; ! tq->d_id.b24 = d_id.b24; ! ha->n_port->d_id.b24 = d_id.b24; } else { for (index = 0; index <= LAST_LOCAL_LOOP_ID; index++) { /* resuse tq */ tq->loop_id = (uint16_t)index;
*** 3069,3095 **** if (tq->master_state == PD_STATE_PLOGI_PENDING) { ha->n_port-> n_port_handle = tq->loop_id; break; } ! } else { ha->n_port->n_port_handle = tq->loop_id; break; } } } - } else { - cmn_err(CE_WARN, "!%s(%d) didn't get list for %xh", - QL_NAME, ha->instance, d_id.b24); } ! if (list != NULL) { kmem_free(list, list_size); } } } /* * ql_configure_hba --- 3231,3298 ---- if (tq->master_state == PD_STATE_PLOGI_PENDING) { ha->n_port-> n_port_handle = tq->loop_id; + ha->n_port->d_id.b24 = + tq->hard_addr.b24; break; } ! } else if (rval == QL_SUCCESS) { ha->n_port->n_port_handle = tq->loop_id; + ha->n_port->d_id.b24 = + tq->hard_addr.b24; + break; } } + if (index > LAST_LOCAL_LOOP_ID) { + EL(ha, "P2P:exceeded last id, " + "n_port_handle = %xh\n", + ha->n_port->n_port_handle); + + ha->n_port->n_port_handle = 0; + tq->loop_id = 0; } } ! } else { kmem_free(list, list_size); + EL(ha, "ql_get_dev_list unsuccessful\n"); + return; } + + /* with the tq->loop_id to get the port database */ + + rval = ql_get_port_database(ha, tq, PDF_NONE); + + if (rval == QL_NOT_LOGGED_IN) { + if (tq->master_state == PD_STATE_PLOGI_PENDING) { + bcopy((void *)&tq->port_name[0], + (void *)&ha->n_port->port_name[0], 8); + bcopy((void *)&tq->node_name[0], + (void *)&ha->n_port->node_name[0], 8); + bcopy((void *)&tq->hard_addr, + (void *)&ha->n_port->d_id, + sizeof (port_id_t)); + ha->n_port->d_id.b24 = d_id.b24; } + } else if (rval == QL_SUCCESS) { + bcopy((void *)&tq->port_name[0], + (void *)&ha->n_port->port_name[0], 8); + bcopy((void *)&tq->node_name[0], + (void *)&ha->n_port->node_name[0], 8); + bcopy((void *)&tq->hard_addr, + (void *)&ha->n_port->d_id, sizeof (port_id_t)); + ha->n_port->d_id.b24 = d_id.b24; + + } + + kmem_free(list, list_size); + + EL(ha, "d_id = %xh, nport_handle = %xh, tq->loop_id = %xh", + tq->d_id.b24, ha->n_port->n_port_handle, tq->loop_id); } /* * ql_configure_hba
*** 3110,3120 **** uint8_t *bp; int rval; uint32_t state; ql_mbx_data_t mr; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* Get host addresses. */ rval = ql_get_adapter_id(ha, &mr); if (rval == QL_SUCCESS) { ha->topology = (uint8_t)(ha->topology & --- 3313,3323 ---- uint8_t *bp; int rval; uint32_t state; ql_mbx_data_t mr; ! QL_PRINT_10(ha, "started\n"); /* Get host addresses. */ rval = ql_get_adapter_id(ha, &mr); if (rval == QL_SUCCESS) { ha->topology = (uint8_t)(ha->topology &
*** 3123,3185 **** /* Save Host d_id, alpa, loop ID. */ ha->loop_id = mr.mb[1]; ha->d_id.b.al_pa = LSB(mr.mb[2]); ha->d_id.b.area = MSB(mr.mb[2]); ha->d_id.b.domain = LSB(mr.mb[3]); ADAPTER_STATE_LOCK(ha); ha->flags &= ~FDISC_ENABLED; /* Get loop topology. */ switch (mr.mb[6]) { ! case CNX_LOOP_NO_FABRIC: ha->topology = (uint8_t)(ha->topology | QL_NL_PORT); break; ! case CNX_FLPORT_IN_LOOP: ha->topology = (uint8_t)(ha->topology | QL_FL_PORT); break; ! case CNX_NPORT_2_NPORT_P2P: ! case CNX_NPORT_2_NPORT_NO_TGT_RSP: ha->flags |= POINT_TO_POINT; ha->topology = (uint8_t)(ha->topology | QL_N_PORT); ! if (CFG_IST(ha, CFG_CTRL_2425)) { ql_configure_n_port_info(ha); } break; ! case CNX_FLPORT_P2P: ha->flags |= POINT_TO_POINT; ha->topology = (uint8_t)(ha->topology | QL_F_PORT); /* Get supported option. */ ! if (CFG_IST(ha, CFG_CTRL_24258081) && mr.mb[7] & GID_FP_NPIV_SUPPORT) { ha->flags |= FDISC_ENABLED; } /* Get VLAN ID, mac address */ ! if (CFG_IST(ha, CFG_CTRL_8081)) { ha->fabric_params = mr.mb[7]; ha->fcoe_vlan_id = (uint16_t)(mr.mb[9] & 0xfff); ha->fcoe_fcf_idx = mr.mb[10]; ! ha->fcoe_vnport_mac[0] = MSB(mr.mb[11]); ! ha->fcoe_vnport_mac[1] = LSB(mr.mb[11]); ! ha->fcoe_vnport_mac[2] = MSB(mr.mb[12]); ! ha->fcoe_vnport_mac[3] = LSB(mr.mb[12]); ! ha->fcoe_vnport_mac[4] = MSB(mr.mb[13]); ! ha->fcoe_vnport_mac[5] = LSB(mr.mb[13]); } break; default: ! QL_PRINT_2(CE_CONT, "(%d,%d): UNKNOWN topology=%xh, " ! "d_id=%xh\n", ha->instance, ha->vp_index, mr.mb[6], ! ha->d_id.b24); rval = QL_FUNCTION_FAILED; break; } - ADAPTER_STATE_UNLOCK(ha); ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322 | ! CFG_CTRL_24258081))) { mr.mb[1] = 0; mr.mb[2] = 0; rval = ql_data_rate(ha, &mr); if (rval != QL_SUCCESS) { EL(ha, "data_rate status=%xh\n", rval); --- 3326,3395 ---- /* Save Host d_id, alpa, loop ID. */ ha->loop_id = mr.mb[1]; ha->d_id.b.al_pa = LSB(mr.mb[2]); ha->d_id.b.area = MSB(mr.mb[2]); ha->d_id.b.domain = LSB(mr.mb[3]); + ha->bbcr_initial = LSB(mr.mb[15]); + ha->bbcr_runtime = MSB(mr.mb[15]); ADAPTER_STATE_LOCK(ha); ha->flags &= ~FDISC_ENABLED; + ADAPTER_STATE_UNLOCK(ha); /* Get loop topology. */ switch (mr.mb[6]) { ! case GID_TOP_NL_PORT: ha->topology = (uint8_t)(ha->topology | QL_NL_PORT); + ha->loop_id = mr.mb[1]; break; ! case GID_TOP_FL_PORT: ha->topology = (uint8_t)(ha->topology | QL_FL_PORT); + ha->loop_id = mr.mb[1]; break; ! case GID_TOP_N_PORT: ! case GID_TOP_N_PORT_NO_TGT: ha->flags |= POINT_TO_POINT; ha->topology = (uint8_t)(ha->topology | QL_N_PORT); ! ha->loop_id = 0xffff; ! if (CFG_IST(ha, CFG_N2N_SUPPORT)) { ql_configure_n_port_info(ha); } break; ! case GID_TOP_F_PORT: ha->flags |= POINT_TO_POINT; ha->topology = (uint8_t)(ha->topology | QL_F_PORT); + ha->loop_id = 0xffff; /* Get supported option. */ ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2) && mr.mb[7] & GID_FP_NPIV_SUPPORT) { + ADAPTER_STATE_LOCK(ha); ha->flags |= FDISC_ENABLED; + ADAPTER_STATE_UNLOCK(ha); } /* Get VLAN ID, mac address */ ! if (CFG_IST(ha, CFG_FCOE_SUPPORT)) { ! ha->flags |= FDISC_ENABLED; ha->fabric_params = mr.mb[7]; ha->fcoe_vlan_id = (uint16_t)(mr.mb[9] & 0xfff); ha->fcoe_fcf_idx = mr.mb[10]; ! ha->fcoe_vnport_mac[5] = MSB(mr.mb[11]); ! ha->fcoe_vnport_mac[4] = LSB(mr.mb[11]); ! ha->fcoe_vnport_mac[3] = MSB(mr.mb[12]); ! ha->fcoe_vnport_mac[2] = LSB(mr.mb[12]); ! ha->fcoe_vnport_mac[1] = MSB(mr.mb[13]); ! ha->fcoe_vnport_mac[0] = LSB(mr.mb[13]); } break; default: ! QL_PRINT_2(ha, "UNKNOWN topology=%xh, d_id=%xh\n", ! mr.mb[6], ha->d_id.b24); rval = QL_FUNCTION_FAILED; break; } ! if (CFG_IST(ha, CFG_CTRL_2363 | CFG_ISP_FW_TYPE_2)) { mr.mb[1] = 0; mr.mb[2] = 0; rval = ql_data_rate(ha, &mr); if (rval != QL_SUCCESS) { EL(ha, "data_rate status=%xh\n", rval);
*** 3194,3203 **** --- 3404,3417 ---- state = FC_STATE_4GBIT_SPEED; } else if (mr.mb[1] == IIDMA_RATE_8GB) { state = FC_STATE_8GBIT_SPEED; } else if (mr.mb[1] == IIDMA_RATE_10GB) { state = FC_STATE_10GBIT_SPEED; + } else if (mr.mb[1] == IIDMA_RATE_16GB) { + state = FC_STATE_16GBIT_SPEED; + } else if (mr.mb[1] == IIDMA_RATE_32GB) { + state = FC_STATE_32GBIT_SPEED; } else { state = 0; } } } else {
*** 3212,3222 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { bp = ha->loginparams.nport_ww_name.raw_wwn; ! EL(ha, "topology=%xh, d_id=%xh, " "wwpn=%02x%02x%02x%02x%02x%02x%02x%02xh\n", ha->topology, ha->d_id.b24, bp[0], bp[1], bp[2], bp[3], bp[4], bp[5], bp[6], bp[7]); } return (rval); --- 3426,3436 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { bp = ha->loginparams.nport_ww_name.raw_wwn; ! EL(ha, "topology=%xh, hba port id=%xh, " "wwpn=%02x%02x%02x%02x%02x%02x%02x%02xh\n", ha->topology, ha->d_id.b24, bp[0], bp[1], bp[2], bp[3], bp[4], bp[5], bp[6], bp[7]); } return (rval);
*** 3248,3258 **** uint32_t list_size; uint16_t index, loop_id; ql_mbx_data_t mr; uint8_t retries = MAX_DEVICE_LOST_RETRY; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); list_size = sizeof (ql_dev_id_list_t) * DEVICE_LIST_ENTRIES; list = kmem_zalloc(list_size, KM_SLEEP); if (list == NULL) { rval = QL_MEMORY_ALLOC_FAILED; --- 3462,3472 ---- uint32_t list_size; uint16_t index, loop_id; ql_mbx_data_t mr; uint8_t retries = MAX_DEVICE_LOST_RETRY; ! QL_PRINT_10(ha, "started\n"); list_size = sizeof (ql_dev_id_list_t) * DEVICE_LIST_ENTRIES; list = kmem_zalloc(list_size, KM_SLEEP); if (list == NULL) { rval = QL_MEMORY_ALLOC_FAILED;
*** 3269,3390 **** kmem_free(list, list_size); EL(ha, "failed, rval = %xh\n", rval); return (rval); } ! /* Acquire adapter state lock. */ ! ADAPTER_STATE_LOCK(ha); ! ! /* Mark all queues as unusable. */ for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { for (link = ha->dev[index].first; link != NULL; link = link->next) { tq = link->base_address; DEVICE_QUEUE_LOCK(tq); if (!(tq->flags & TQF_PLOGI_PROGRS) && !(ha->topology & QL_N_PORT)) { tq->loop_id = (uint16_t) ! (tq->loop_id | PORT_LOST_ID); } DEVICE_QUEUE_UNLOCK(tq); } } /* If device not in queues add new queue. */ for (index = 0; index < mr.mb[1]; index++) { ql_dev_list(ha, list, index, &d_id, &loop_id); if (VALID_DEVICE_ID(ha, loop_id)) { tq = ql_dev_init(ha, d_id, loop_id); if (tq != NULL) { tq->loop_id = loop_id; /* Test for fabric device. */ ! if (d_id.b.domain != ha->d_id.b.domain || d_id.b.area != ha->d_id.b.area) { tq->flags |= TQF_FABRIC_DEVICE; } - ADAPTER_STATE_UNLOCK(ha); if (ql_get_port_database(ha, tq, PDF_NONE) == QL_SUCCESS) { - ADAPTER_STATE_LOCK(ha); tq->loop_id = (uint16_t) (tq->loop_id & ~PORT_LOST_ID); - } else { - ADAPTER_STATE_LOCK(ha); } } } } /* 24xx does not report switch devices in ID list. */ ! if ((CFG_IST(ha, CFG_CTRL_24258081)) && ! ha->topology & (QL_F_PORT | QL_FL_PORT)) { ! d_id.b24 = 0xfffffe; tq = ql_dev_init(ha, d_id, FL_PORT_24XX_HDL); if (tq != NULL) { tq->flags |= TQF_FABRIC_DEVICE; - ADAPTER_STATE_UNLOCK(ha); (void) ql_get_port_database(ha, tq, PDF_NONE); - ADAPTER_STATE_LOCK(ha); } ! d_id.b24 = 0xfffffc; tq = ql_dev_init(ha, d_id, SNS_24XX_HDL); if (tq != NULL) { tq->flags |= TQF_FABRIC_DEVICE; - ADAPTER_STATE_UNLOCK(ha); if (ha->vp_index != 0) { (void) ql_login_fport(ha, tq, SNS_24XX_HDL, LFF_NONE, NULL); } (void) ql_get_port_database(ha, tq, PDF_NONE); - ADAPTER_STATE_LOCK(ha); } } - /* If F_port exists, allocate queue for FL_Port. */ - index = ql_alpa_to_index[0xfe]; - d_id.b24 = 0; - if (ha->dev[index].first != NULL) { - tq = ql_dev_init(ha, d_id, (uint16_t) - (CFG_IST(ha, CFG_CTRL_24258081) ? - FL_PORT_24XX_HDL : FL_PORT_LOOP_ID)); - if (tq != NULL) { - tq->flags |= TQF_FABRIC_DEVICE; - ADAPTER_STATE_UNLOCK(ha); - (void) ql_get_port_database(ha, tq, PDF_NONE); - ADAPTER_STATE_LOCK(ha); - } - } - /* Allocate queue for broadcast. */ ! d_id.b24 = 0xffffff; (void) ql_dev_init(ha, d_id, (uint16_t) ! (CFG_IST(ha, CFG_CTRL_24258081) ? BROADCAST_24XX_HDL : IP_BROADCAST_LOOP_ID)); ! /* Check for any devices lost. */ loop = FALSE; for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { ! for (link = ha->dev[index].first; link != NULL; ! link = link->next) { ! tq = link->base_address; ! if ((tq->loop_id & PORT_LOST_ID) && ! !(tq->flags & (TQF_INITIATOR_DEVICE | ! TQF_FABRIC_DEVICE))) { loop = TRUE; } - } - } - /* Release adapter state lock. */ - ADAPTER_STATE_UNLOCK(ha); - /* Give devices time to recover. */ if (loop == TRUE) { drv_usecwait(1000000); } } while (retries-- && loop == TRUE && --- 3483,3604 ---- kmem_free(list, list_size); EL(ha, "failed, rval = %xh\n", rval); return (rval); } ! /* ! * Mark queues as unusable selectively. ! * If the current topology is AL, only fabric tgt queues ! * are marked as unusable and eventually removed. ! * If the current topology is P2P, all fabric tgt queues ! * are processed in ql_configure_n_port_info(). ! * If the current topology is Fabric, all previous created ! * non-fabric device should be marked as lost and eventually ! * should be removed. ! */ for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { for (link = ha->dev[index].first; link != NULL; link = link->next) { tq = link->base_address; + + if (VALID_DEVICE_ID(ha, tq->loop_id)) { DEVICE_QUEUE_LOCK(tq); if (!(tq->flags & TQF_PLOGI_PROGRS) && !(ha->topology & QL_N_PORT)) { tq->loop_id = (uint16_t) ! (tq->loop_id | ! PORT_LOST_ID); } + if ((ha->topology & QL_NL_PORT) && + (tq->flags & TQF_FABRIC_DEVICE)) { + tq->loop_id = (uint16_t) + (tq->loop_id | + PORT_LOST_ID); + } DEVICE_QUEUE_UNLOCK(tq); } } + } /* If device not in queues add new queue. */ for (index = 0; index < mr.mb[1]; index++) { ql_dev_list(ha, list, index, &d_id, &loop_id); if (VALID_DEVICE_ID(ha, loop_id)) { + ADAPTER_STATE_LOCK(ha); tq = ql_dev_init(ha, d_id, loop_id); + ADAPTER_STATE_UNLOCK(ha); if (tq != NULL) { tq->loop_id = loop_id; /* Test for fabric device. */ ! if (ha->topology & QL_F_PORT || ! d_id.b.domain != ha->d_id.b.domain || d_id.b.area != ha->d_id.b.area) { tq->flags |= TQF_FABRIC_DEVICE; } if (ql_get_port_database(ha, tq, PDF_NONE) == QL_SUCCESS) { tq->loop_id = (uint16_t) (tq->loop_id & ~PORT_LOST_ID); } } } } /* 24xx does not report switch devices in ID list. */ ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2) && ! ha->topology & QL_FABRIC_CONNECTION) { ! d_id.b24 = FS_FABRIC_F_PORT; ! ADAPTER_STATE_LOCK(ha); tq = ql_dev_init(ha, d_id, FL_PORT_24XX_HDL); + ADAPTER_STATE_UNLOCK(ha); if (tq != NULL) { tq->flags |= TQF_FABRIC_DEVICE; (void) ql_get_port_database(ha, tq, PDF_NONE); } ! ! d_id.b24 = FS_NAME_SERVER; ! ADAPTER_STATE_LOCK(ha); tq = ql_dev_init(ha, d_id, SNS_24XX_HDL); + ADAPTER_STATE_UNLOCK(ha); if (tq != NULL) { tq->flags |= TQF_FABRIC_DEVICE; if (ha->vp_index != 0) { (void) ql_login_fport(ha, tq, SNS_24XX_HDL, LFF_NONE, NULL); } (void) ql_get_port_database(ha, tq, PDF_NONE); } } /* Allocate queue for broadcast. */ ! d_id.b24 = FS_BROADCAST; ! ADAPTER_STATE_LOCK(ha); (void) ql_dev_init(ha, d_id, (uint16_t) ! (CFG_IST(ha, CFG_ISP_FW_TYPE_2) ? BROADCAST_24XX_HDL : IP_BROADCAST_LOOP_ID)); + ADAPTER_STATE_UNLOCK(ha); ! /* ! * Topology change (fabric<->p2p),(fabric<->al) ! * (al<->p2p) have to be taken care of. ! */ loop = FALSE; for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { ! ql_update_dev(ha, index); ! } ! if ((ha->topology & QL_NL_PORT) && (mr.mb[1] != 0)) { ! loop = FALSE; ! } else if (mr.mb[1] == 0 && !(ha->topology & QL_F_PORT)) { loop = TRUE; } /* Give devices time to recover. */ if (loop == TRUE) { drv_usecwait(1000000); } } while (retries-- && loop == TRUE &&
*** 3394,3404 **** if (rval != QL_SUCCESS) { EL(ha, "failed=%xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } --- 3608,3618 ---- if (rval != QL_SUCCESS) { EL(ha, "failed=%xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); }
*** 3418,3428 **** */ void ql_dev_list(ql_adapter_state_t *ha, union ql_dev_id_list *list, uint32_t index, port_id_t *d_id, uint16_t *id) { ! if (CFG_IST(ha, CFG_CTRL_24258081)) { struct ql_24_dev_id *list24 = (struct ql_24_dev_id *)list; d_id->b.al_pa = list24[index].al_pa; d_id->b.area = list24[index].area; d_id->b.domain = list24[index].domain; --- 3632,3642 ---- */ void ql_dev_list(ql_adapter_state_t *ha, union ql_dev_id_list *list, uint32_t index, port_id_t *d_id, uint16_t *id) { ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2)) { struct ql_24_dev_id *list24 = (struct ql_24_dev_id *)list; d_id->b.al_pa = list24[index].al_pa; d_id->b.area = list24[index].area; d_id->b.domain = list24[index].domain;
*** 3466,3479 **** { port_id_t d_id; ql_tgt_t *tq; int rval = QL_FUNCTION_FAILED; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); ! ha->topology = (uint8_t)(ha->topology & ~QL_SNS_CONNECTION); ! /* Test switch fabric controller present. */ d_id.b24 = FS_FABRIC_F_PORT; tq = ql_d_id_to_queue(ha, d_id); if (tq != NULL) { /* Get port/node names of F_Port. */ --- 3680,3692 ---- { port_id_t d_id; ql_tgt_t *tq; int rval = QL_FUNCTION_FAILED; ! QL_PRINT_10(ha, "started\n"); ! if (ha->topology & QL_FABRIC_CONNECTION) { /* Test switch fabric controller present. */ d_id.b24 = FS_FABRIC_F_PORT; tq = ql_d_id_to_queue(ha, d_id); if (tq != NULL) { /* Get port/node names of F_Port. */
*** 3481,3501 **** d_id.b24 = FS_NAME_SERVER; tq = ql_d_id_to_queue(ha, d_id); if (tq != NULL) { (void) ql_get_port_database(ha, tq, PDF_NONE); - ha->topology = (uint8_t) - (ha->topology | QL_SNS_CONNECTION); rval = QL_SUCCESS; } } if (rval != QL_SUCCESS) { EL(ha, "failed=%xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* --- 3694,3713 ---- d_id.b24 = FS_NAME_SERVER; tq = ql_d_id_to_queue(ha, d_id); if (tq != NULL) { (void) ql_get_port_database(ha, tq, PDF_NONE); rval = QL_SUCCESS; } } + } if (rval != QL_SUCCESS) { EL(ha, "failed=%xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 3515,3559 **** { uint32_t cnt; uint16_t cmd; ql_adapter_state_t *ha = vha->pha; ! QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance); /* * accessing pci space while not powered can cause panic's * on some platforms (i.e. Sunblade 1000's) */ if (ha->power_level == PM_LEVEL_D3) { ! QL_PRINT_2(CE_CONT, "(%d): Low Power exit\n", ha->instance); return; } /* Reset all outbound mailbox registers */ for (cnt = 0; cnt < ha->reg_off->mbox_cnt; cnt++) { WRT16_IO_REG(ha, mailbox_in[cnt], (uint16_t)0); } ! if (CFG_IST(ha, CFG_CTRL_8021)) { ha->timeout_cnt = 0; ql_8021_reset_chip(ha); ! QL_PRINT_3(CE_CONT, "(%d): 8021 exit\n", ha->instance); return; } ! /* Disable ISP interrupts. */ ! WRT16_IO_REG(ha, ictrl, 0); ! ADAPTER_STATE_LOCK(ha); ! ha->flags &= ~INTERRUPTS_ENABLED; ! ADAPTER_STATE_UNLOCK(ha); ! ! if (CFG_IST(ha, CFG_CTRL_242581)) { ! RD32_IO_REG(ha, ictrl); ql_reset_24xx_chip(ha); ! QL_PRINT_3(CE_CONT, "(%d): 24xx exit\n", ha->instance); return; } /* * We are going to reset the chip in case of 2300. That might cause * a PBM ERR if a DMA transaction is in progress. One way of * avoiding it is to disable Bus Master operation before we start --- 3727,3768 ---- { uint32_t cnt; uint16_t cmd; ql_adapter_state_t *ha = vha->pha; ! QL_PRINT_10(ha, "started\n"); /* * accessing pci space while not powered can cause panic's * on some platforms (i.e. Sunblade 1000's) */ if (ha->power_level == PM_LEVEL_D3) { ! QL_PRINT_2(ha, "Low Power exit\n"); return; } + /* Disable ISP interrupts. */ + ql_disable_intr(ha); + /* Reset all outbound mailbox registers */ for (cnt = 0; cnt < ha->reg_off->mbox_cnt; cnt++) { WRT16_IO_REG(ha, mailbox_in[cnt], (uint16_t)0); } ! if (CFG_IST(ha, CFG_CTRL_82XX)) { ha->timeout_cnt = 0; ql_8021_reset_chip(ha); ! QL_PRINT_10(ha, "8021 exit\n"); return; } ! if (CFG_IST(ha, CFG_ISP_FW_TYPE_2)) { ql_reset_24xx_chip(ha); ! QL_PRINT_10(ha, "24xx exit\n"); return; } + QL_PRINT_10(ha, "CFG_ISP_FW_TYPE_1 reset\n"); /* * We are going to reset the chip in case of 2300. That might cause * a PBM ERR if a DMA transaction is in progress. One way of * avoiding it is to disable Bus Master operation before we start
*** 3586,3604 **** /* FPM Soft Reset. */ WRT16_IO_REG(ha, fpm_diag_config, 0x100); /* Toggle FPM reset for 2300 */ ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) { WRT16_IO_REG(ha, fpm_diag_config, 0); } /* Select frame buffer registers. */ WRT16_IO_REG(ha, ctrl_status, 0x10); /* Reset frame buffer FIFOs. */ ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) { WRT16_IO_REG(ha, fb_cmd, 0x00fc); /* read back fb_cmd until zero or 3 seconds max */ for (cnt = 0; cnt < 300000; cnt++) { if ((RD16_IO_REG(ha, fb_cmd) & 0xff) == 0) { break; --- 3795,3813 ---- /* FPM Soft Reset. */ WRT16_IO_REG(ha, fpm_diag_config, 0x100); /* Toggle FPM reset for 2300 */ ! if (CFG_IST(ha, CFG_CTRL_2363)) { WRT16_IO_REG(ha, fpm_diag_config, 0); } /* Select frame buffer registers. */ WRT16_IO_REG(ha, ctrl_status, 0x10); /* Reset frame buffer FIFOs. */ ! if (CFG_IST(ha, CFG_CTRL_2363)) { WRT16_IO_REG(ha, fb_cmd, 0x00fc); /* read back fb_cmd until zero or 3 seconds max */ for (cnt = 0; cnt < 300000; cnt++) { if ((RD16_IO_REG(ha, fb_cmd) & 0xff) == 0) { break;
*** 3624,3640 **** /* Insure mailbox registers are free. */ WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT); WRT16_IO_REG(ha, hccr, HC_CLR_HOST_INT); /* clear the mailbox command pointer. */ ! ql_clear_mcp(ha); ha->mailbox_flags = (uint8_t)(ha->mailbox_flags & ~(MBX_BUSY_FLG | MBX_WANT_FLG | MBX_ABORT | MBX_INTERRUPT)); /* Bus Master is disabled so chip reset is safe. */ ! if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) { WRT16_IO_REG(ha, ctrl_status, ISP_RESET); drv_usecwait(MILLISEC); /* Wait for reset to finish. */ for (cnt = 0; cnt < 30000; cnt++) { --- 3833,3853 ---- /* Insure mailbox registers are free. */ WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT); WRT16_IO_REG(ha, hccr, HC_CLR_HOST_INT); /* clear the mailbox command pointer. */ ! INTR_LOCK(ha); ! ha->mcp = NULL; ! INTR_UNLOCK(ha); + MBX_REGISTER_LOCK(ha); ha->mailbox_flags = (uint8_t)(ha->mailbox_flags & ~(MBX_BUSY_FLG | MBX_WANT_FLG | MBX_ABORT | MBX_INTERRUPT)); + MBX_REGISTER_UNLOCK(ha); /* Bus Master is disabled so chip reset is safe. */ ! if (CFG_IST(ha, CFG_CTRL_2363)) { WRT16_IO_REG(ha, ctrl_status, ISP_RESET); drv_usecwait(MILLISEC); /* Wait for reset to finish. */ for (cnt = 0; cnt < 30000; cnt++) {
*** 3645,3655 **** } } /* Wait for RISC to recover from reset. */ for (cnt = 0; cnt < 30000; cnt++) { ! if (RD16_IO_REG(ha, mailbox_out[0]) != MBS_BUSY) { break; } drv_usecwait(MILLISEC); } --- 3858,3868 ---- } } /* Wait for RISC to recover from reset. */ for (cnt = 0; cnt < 30000; cnt++) { ! if (RD16_IO_REG(ha, mailbox_out[0]) != MBS_ROM_BUSY) { break; } drv_usecwait(MILLISEC); }
*** 3659,3668 **** --- 3872,3886 ---- ql_pci_config_put16(ha, PCI_CONF_COMM, cmd); /* Disable RISC pause on FPM parity error. */ WRT16_IO_REG(ha, hccr, HC_DISABLE_PARITY_PAUSE); + if (CFG_IST(ha, CFG_CTRL_22XX) && + RD16_IO_REG(ha, mailbox_out[7]) == 4) { + ha->fw_transfer_size = 128; + } + /* Initialize probe registers */ if (CFG_IST(ha, CFG_SBUS_CARD)) { /* Pause RISC. */ WRT16_IO_REG(ha, hccr, HC_PAUSE_RISC); for (cnt = 0; cnt < 30000; cnt++) {
*** 3684,3694 **** /* Release RISC module. */ WRT16_IO_REG(ha, hccr, HC_RELEASE_RISC); } ! QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance); } /* * ql_reset_24xx_chip * Reset ISP24xx chip. --- 3902,3912 ---- /* Release RISC module. */ WRT16_IO_REG(ha, hccr, HC_RELEASE_RISC); } ! QL_PRINT_10(ha, "done\n"); } /* * ql_reset_24xx_chip * Reset ISP24xx chip.
*** 3698,3714 **** * All activity on chip must be already stopped. * * Context: * Interrupt or Kernel context, no mailbox commands allowed. */ ! void ql_reset_24xx_chip(ql_adapter_state_t *ha) { uint32_t timer, stat; /* Shutdown DMA. */ WRT32_IO_REG(ha, ctrl_status, DMA_SHUTDOWN | MWB_4096_BYTES); /* Wait for DMA to stop. */ for (timer = 0; timer < 30000; timer++) { if ((RD32_IO_REG(ha, ctrl_status) & DMA_ACTIVE) == 0) { break; --- 3916,3938 ---- * All activity on chip must be already stopped. * * Context: * Interrupt or Kernel context, no mailbox commands allowed. */ ! static void ql_reset_24xx_chip(ql_adapter_state_t *ha) { uint32_t timer, stat; + QL_PRINT_10(ha, "started\n"); + /* Shutdown DMA. */ + if (CFG_IST(ha, CFG_MWB_4096_SUPPORT)) { WRT32_IO_REG(ha, ctrl_status, DMA_SHUTDOWN | MWB_4096_BYTES); + } else { + WRT32_IO_REG(ha, ctrl_status, DMA_SHUTDOWN); + } /* Wait for DMA to stop. */ for (timer = 0; timer < 30000; timer++) { if ((RD32_IO_REG(ha, ctrl_status) & DMA_ACTIVE) == 0) { break;
*** 3717,3726 **** --- 3941,3958 ---- } /* Stop the firmware. */ WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT); WRT16_IO_REG(ha, mailbox_in[0], MBC_STOP_FIRMWARE); + WRT16_IO_REG(ha, mailbox_in[1], 0); + WRT16_IO_REG(ha, mailbox_in[2], 0); + WRT16_IO_REG(ha, mailbox_in[3], 0); + WRT16_IO_REG(ha, mailbox_in[4], 0); + WRT16_IO_REG(ha, mailbox_in[5], 0); + WRT16_IO_REG(ha, mailbox_in[6], 0); + WRT16_IO_REG(ha, mailbox_in[7], 0); + WRT16_IO_REG(ha, mailbox_in[8], 0); WRT32_IO_REG(ha, hccr, HC24_SET_HOST_INT); for (timer = 0; timer < 30000; timer++) { stat = RD32_IO_REG(ha, risc2host); if (stat & BIT_15) { if ((stat & 0xff) < 0x12) {
*** 3731,3749 **** } drv_usecwait(100); } /* Reset the chip. */ ! WRT32_IO_REG(ha, ctrl_status, ISP_RESET | DMA_SHUTDOWN | ! MWB_4096_BYTES); drv_usecwait(100); /* Wait for idle status from ROM firmware. */ ! for (timer = 0; timer < 30000; timer++) { ! if (RD16_IO_REG(ha, mailbox_out[0]) == 0) { break; } drv_usecwait(100); } /* Wait for reset to finish. */ for (timer = 0; timer < 30000; timer++) { --- 3963,3990 ---- } drv_usecwait(100); } /* Reset the chip. */ ! WRT32_IO_REG(ha, ctrl_status, ISP_RESET); drv_usecwait(100); + /* Wait for RISC to recover from reset. */ + for (timer = 30000; timer; timer--) { + ha->rom_status = RD16_IO_REG(ha, mailbox_out[0]); + if (CFG_IST(ha, CFG_CTRL_278083)) { + /* Wait for RISC to recover from reset. */ + if ((ha->rom_status & MBS_ROM_STATUS_MASK) != + MBS_ROM_BUSY) { + break; + } + } else { /* Wait for idle status from ROM firmware. */ ! if (ha->rom_status == MBS_ROM_IDLE) { break; } + } drv_usecwait(100); } /* Wait for reset to finish. */ for (timer = 0; timer < 30000; timer++) {
*** 3751,3766 **** break; } drv_usecwait(100); } /* clear the mailbox command pointer. */ ! ql_clear_mcp(ha); /* Insure mailbox registers are free. */ ha->mailbox_flags = (uint8_t)(ha->mailbox_flags & ~(MBX_BUSY_FLG | MBX_WANT_FLG | MBX_ABORT | MBX_INTERRUPT)); if (ha->flags & MPI_RESET_NEEDED) { WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT); WRT16_IO_REG(ha, mailbox_in[0], MBC_RESTART_MPI); WRT32_IO_REG(ha, hccr, HC24_SET_HOST_INT); --- 3992,4020 ---- break; } drv_usecwait(100); } + ha->adapter_stats->revlvl.isp2200 = RD16_IO_REG(ha, mailbox_out[4]); + ha->adapter_stats->revlvl.risc = RD16_IO_REG(ha, mailbox_out[5]); + ha->adapter_stats->revlvl.frmbfr = RD16_IO_REG(ha, mailbox_out[6]); + ha->adapter_stats->revlvl.riscrom = RD16_IO_REG(ha, mailbox_out[8]); + + /* Insure mailbox registers are free. */ + WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT); + WRT32_IO_REG(ha, hccr, HC24_CLR_HOST_INT); + /* clear the mailbox command pointer. */ ! INTR_LOCK(ha); ! ha->mcp = NULL; ! INTR_UNLOCK(ha); /* Insure mailbox registers are free. */ + MBX_REGISTER_LOCK(ha); ha->mailbox_flags = (uint8_t)(ha->mailbox_flags & ~(MBX_BUSY_FLG | MBX_WANT_FLG | MBX_ABORT | MBX_INTERRUPT)); + MBX_REGISTER_UNLOCK(ha); if (ha->flags & MPI_RESET_NEEDED) { WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT); WRT16_IO_REG(ha, mailbox_in[0], MBC_RESTART_MPI); WRT32_IO_REG(ha, hccr, HC24_SET_HOST_INT);
*** 3779,3830 **** ADAPTER_STATE_LOCK(ha); ha->flags &= ~MPI_RESET_NEEDED; ADAPTER_STATE_UNLOCK(ha); } ! /* ! * Set flash write-protection. ! */ ! if ((ha->flags & ONLINE) == 0) { ! ql_24xx_protect_flash(ha); ! } } /* - * ql_clear_mcp - * Carefully clear the mailbox command pointer in the ha struct. - * - * Input: - * ha = adapter block pointer. - * - * Context: - * Interrupt or Kernel context, no mailbox commands allowed. - */ - - static void - ql_clear_mcp(ql_adapter_state_t *ha) - { - uint32_t cnt; - - /* Don't null ha->mcp without the lock, but don't hang either. */ - if (MBX_REGISTER_LOCK_OWNER(ha) == curthread) { - ha->mcp = NULL; - } else { - for (cnt = 0; cnt < 300000; cnt++) { - if (TRY_MBX_REGISTER_LOCK(ha) != 0) { - ha->mcp = NULL; - MBX_REGISTER_UNLOCK(ha); - break; - } else { - drv_usecwait(10); - } - } - } - } - - - /* * ql_abort_isp * Resets ISP and aborts all outstanding commands. * * Input: * ha = adapter state pointer. --- 4033,4046 ---- ADAPTER_STATE_LOCK(ha); ha->flags &= ~MPI_RESET_NEEDED; ADAPTER_STATE_UNLOCK(ha); } ! QL_PRINT_10(ha, "done\n"); } /* * ql_abort_isp * Resets ISP and aborts all outstanding commands. * * Input: * ha = adapter state pointer.
*** 3838,3876 **** */ int ql_abort_isp(ql_adapter_state_t *vha) { ql_link_t *link, *link2; - ddi_devstate_t state; uint16_t index; ql_tgt_t *tq; ql_lun_t *lq; - ql_srb_t *sp; int rval = QL_SUCCESS; ql_adapter_state_t *ha = vha->pha; ! QL_PRINT_2(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= ~ISP_ABORT_NEEDED; if (ha->task_daemon_flags & ABORT_ISP_ACTIVE || (ha->flags & ONLINE) == 0 || ha->flags & ADAPTER_SUSPENDED) { TASK_DAEMON_UNLOCK(ha); return (rval); } ha->task_daemon_flags |= ABORT_ISP_ACTIVE; ! ha->task_daemon_flags &= ~(RESET_MARKER_NEEDED | FIRMWARE_UP | FIRMWARE_LOADED); for (vha = ha; vha != NULL; vha = vha->vp_next) { - vha->task_daemon_flags |= LOOP_DOWN; vha->task_daemon_flags &= ~(COMMAND_WAIT_NEEDED | LOOP_RESYNC_NEEDED); } TASK_DAEMON_UNLOCK(ha); if (ha->mailbox_flags & MBX_BUSY_FLG) { /* Acquire mailbox register lock. */ MBX_REGISTER_LOCK(ha); /* Wake up mailbox box routine. */ --- 4054,4099 ---- */ int ql_abort_isp(ql_adapter_state_t *vha) { ql_link_t *link, *link2; uint16_t index; ql_tgt_t *tq; ql_lun_t *lq; int rval = QL_SUCCESS; ql_adapter_state_t *ha = vha->pha; + boolean_t abort_loop_down = B_FALSE; ! QL_PRINT_2(ha, "started\n"); TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= ~ISP_ABORT_NEEDED; if (ha->task_daemon_flags & ABORT_ISP_ACTIVE || (ha->flags & ONLINE) == 0 || ha->flags & ADAPTER_SUSPENDED) { TASK_DAEMON_UNLOCK(ha); + QL_PRINT_2(ha, "already active or suspended tdf=0x%llx, " + "flgs=0x%llx\n", ha->task_daemon_flags, ha->flags); return (rval); } ha->task_daemon_flags |= ABORT_ISP_ACTIVE; ! ha->task_daemon_flags &= ~(MARKER_NEEDED | FIRMWARE_UP | FIRMWARE_LOADED); for (vha = ha; vha != NULL; vha = vha->vp_next) { vha->task_daemon_flags &= ~(COMMAND_WAIT_NEEDED | LOOP_RESYNC_NEEDED); + vha->task_daemon_flags |= LOOP_DOWN; + if (vha->loop_down_timer == LOOP_DOWN_TIMER_OFF) { + abort_loop_down = B_TRUE; + vha->loop_down_timer = LOOP_DOWN_TIMER_START; } + } TASK_DAEMON_UNLOCK(ha); + ql_port_state(ha, FC_STATE_OFFLINE, FC_STATE_CHANGE); + if (ha->mailbox_flags & MBX_BUSY_FLG) { /* Acquire mailbox register lock. */ MBX_REGISTER_LOCK(ha); /* Wake up mailbox box routine. */
*** 3881,3891 **** MBX_REGISTER_UNLOCK(ha); /* Wait for mailbox. */ for (index = 100; index && ha->mailbox_flags & MBX_ABORT; index--) { ! drv_usecwait(50000); } } /* Wait for commands to end gracefully if not in panic. */ if (ha->flags & PARITY_ERROR) { --- 4104,4114 ---- MBX_REGISTER_UNLOCK(ha); /* Wait for mailbox. */ for (index = 100; index && ha->mailbox_flags & MBX_ABORT; index--) { ! delay(1); } } /* Wait for commands to end gracefully if not in panic. */ if (ha->flags & PARITY_ERROR) {
*** 3894,3910 **** --- 4117,4147 ---- ADAPTER_STATE_UNLOCK(ha); } else if (ddi_in_panic() == 0) { ql_cmd_wait(ha); } + rval = QL_ABORTED; + if (ha->flags & FW_DUMP_NEEDED) { + rval = ql_binary_fw_dump(ha, TRUE); + } + /* Shutdown IP. */ if (ha->flags & IP_INITIALIZED) { (void) ql_shutdown_ip(ha); } + if (ha->task_daemon_flags & ISP_ABORT_NEEDED) { + TASK_DAEMON_LOCK(ha); + ha->task_daemon_flags &= ~ISP_ABORT_NEEDED; + TASK_DAEMON_UNLOCK(ha); + } + /* Reset the chip. */ + if (rval != QL_SUCCESS) { + rval = QL_SUCCESS; ql_reset_chip(ha); + } /* * Even though we have waited for outstanding commands to complete, * except for ones marked SRB_COMMAND_TIMEOUT, and reset the ISP, * there could still be an interrupt thread active. The interrupt
*** 3911,3980 **** * lock will prevent us from getting an sp from the outstanding * cmds array that the ISR may be using. */ /* Place all commands in outstanding cmd list on device queue. */ ! for (index = 1; index < MAX_OUTSTANDING_COMMANDS; index++) { ! REQUEST_RING_LOCK(ha); ! INTR_LOCK(ha); ! if ((link = ha->pending_cmds.first) != NULL) { ! sp = link->base_address; ! ql_remove_link(&ha->pending_cmds, &sp->cmd); - REQUEST_RING_UNLOCK(ha); - index = 0; - } else { - REQUEST_RING_UNLOCK(ha); - if ((sp = ha->outstanding_cmds[index]) == NULL) { - INTR_UNLOCK(ha); - continue; - } - } - /* - * It's not obvious but the index for commands pulled from - * pending will be zero and that entry in the outstanding array - * is not used so nulling it is "no harm, no foul". - */ - - ha->outstanding_cmds[index] = NULL; - sp->handle = 0; - sp->flags &= ~SRB_IN_TOKEN_ARRAY; - - INTR_UNLOCK(ha); - - /* If command timeout. */ - if (sp->flags & SRB_COMMAND_TIMEOUT) { - sp->pkt->pkt_reason = CS_TIMEOUT; - sp->flags &= ~SRB_RETRY; - sp->flags |= SRB_ISP_COMPLETED; - - /* Call done routine to handle completion. */ - ql_done(&sp->cmd); - continue; - } - - /* Acquire target queue lock. */ - lq = sp->lun_queue; - tq = lq->target_queue; - DEVICE_QUEUE_LOCK(tq); - - /* Reset watchdog time. */ - sp->wdg_q_time = sp->init_wdg_q_time; - - /* Place request back on top of device queue. */ - sp->flags &= ~(SRB_ISP_STARTED | SRB_ISP_COMPLETED | - SRB_RETRY); - - ql_add_link_t(&lq->cmd, &sp->cmd); - sp->flags |= SRB_IN_DEVICE_QUEUE; - - /* Release target queue lock. */ - DEVICE_QUEUE_UNLOCK(tq); - } - - /* * Clear per LUN active count, because there should not be * any IO outstanding at this time. */ for (vha = ha; vha != NULL; vha = vha->vp_next) { for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) { --- 4148,4160 ---- * lock will prevent us from getting an sp from the outstanding * cmds array that the ISR may be using. */ /* Place all commands in outstanding cmd list on device queue. */ ! ql_requeue_all_cmds(ha); /* * Clear per LUN active count, because there should not be * any IO outstanding at this time. */ for (vha = ha; vha != NULL; vha = vha->vp_next) { for (index = 0; index < DEVICE_HEAD_LIST_SIZE; index++) {
*** 3995,4073 **** } } } if ((rval = ql_check_isp_firmware(ha)) != QL_SUCCESS) { ! if ((rval = ql_chip_diag(ha)) == QL_SUCCESS) { rval = ql_load_isp_firmware(ha); } } if (rval == QL_SUCCESS && (rval = ql_set_cache_line(ha)) == QL_SUCCESS && (rval = ql_init_rings(ha)) == QL_SUCCESS && (rval = ql_fw_ready(ha, 10)) == QL_SUCCESS) { /* If reset abort needed that may have been set. */ TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= ~(ISP_ABORT_NEEDED | ABORT_ISP_ACTIVE); TASK_DAEMON_UNLOCK(ha); - /* Enable ISP interrupts. */ - if (CFG_IST(ha, CFG_CTRL_8021)) { - ql_8021_enable_intrs(ha); - } else if (CFG_IST(ha, CFG_CTRL_242581)) { - WRT32_IO_REG(ha, ictrl, ISP_EN_RISC); - } else { - WRT16_IO_REG(ha, ictrl, ISP_EN_INT + ISP_EN_RISC); - } - - ADAPTER_STATE_LOCK(ha); - ha->flags |= INTERRUPTS_ENABLED; - ADAPTER_STATE_UNLOCK(ha); - /* Set loop online, if it really is. */ ql_loop_online(ha); - - state = ddi_get_devstate(ha->dip); - if (state != DDI_DEVSTATE_UP) { - /*EMPTY*/ - ddi_dev_report_fault(ha->dip, DDI_SERVICE_RESTORED, - DDI_DEVICE_FAULT, "Device reset succeeded"); - } } else { /* Enable ISP interrupts. */ ! if (CFG_IST(ha, CFG_CTRL_8021)) { ! ql_8021_enable_intrs(ha); ! } else if (CFG_IST(ha, CFG_CTRL_242581)) { ! WRT32_IO_REG(ha, ictrl, ISP_EN_RISC); ! } else { ! WRT16_IO_REG(ha, ictrl, ISP_EN_INT + ISP_EN_RISC); } - ADAPTER_STATE_LOCK(ha); - ha->flags |= INTERRUPTS_ENABLED; - ADAPTER_STATE_UNLOCK(ha); - TASK_DAEMON_LOCK(ha); ! ha->task_daemon_flags &= ~(ISP_ABORT_NEEDED | ABORT_ISP_ACTIVE); ! ha->task_daemon_flags |= LOOP_DOWN; TASK_DAEMON_UNLOCK(ha); ql_port_state(ha, FC_STATE_OFFLINE, FC_STATE_CHANGE); } if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_2(CE_CONT, "(%d): done\n", ha->instance); } return (rval); } /* * ql_vport_control * Issue Virtual Port Control command. * * Input: * ha = virtual adapter state pointer. --- 4175,4345 ---- } } } if ((rval = ql_check_isp_firmware(ha)) != QL_SUCCESS) { ! if (ha->dev_state != NX_DEV_READY) { ! EL(ha, "dev_state not ready\n"); ! } else if ((rval = ql_mbx_wrap_test(ha, NULL)) == QL_SUCCESS) { rval = ql_load_isp_firmware(ha); } } if (rval == QL_SUCCESS && (rval = ql_set_cache_line(ha)) == QL_SUCCESS && (rval = ql_init_rings(ha)) == QL_SUCCESS && (rval = ql_fw_ready(ha, 10)) == QL_SUCCESS) { + /* Enable ISP interrupts. */ + if (!(ha->flags & INTERRUPTS_ENABLED)) { + ql_enable_intr(ha); + } + /* If reset abort needed that may have been set. */ TASK_DAEMON_LOCK(ha); ha->task_daemon_flags &= ~(ISP_ABORT_NEEDED | ABORT_ISP_ACTIVE); TASK_DAEMON_UNLOCK(ha); /* Set loop online, if it really is. */ ql_loop_online(ha); } else { /* Enable ISP interrupts. */ ! if (!(ha->flags & INTERRUPTS_ENABLED)) { ! ql_enable_intr(ha); } TASK_DAEMON_LOCK(ha); ! for (vha = ha; vha != NULL; vha = vha->vp_next) { ! vha->task_daemon_flags |= LOOP_DOWN; ! } ! ha->task_daemon_flags &= ~ISP_ABORT_NEEDED; TASK_DAEMON_UNLOCK(ha); ql_port_state(ha, FC_STATE_OFFLINE, FC_STATE_CHANGE); + + ql_abort_queues(ha); + + TASK_DAEMON_LOCK(ha); + ha->task_daemon_flags &= ~ABORT_ISP_ACTIVE; + TASK_DAEMON_UNLOCK(ha); } + for (vha = ha; vha != NULL; vha = vha->vp_next) { + if (!(vha->task_daemon_flags & LOOP_DOWN) && + abort_loop_down == B_TRUE) { + vha->loop_down_timer = LOOP_DOWN_TIMER_OFF; + } + } + if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_2(ha, "done\n"); } return (rval); } /* + * ql_requeue_all_cmds + * Requeue all commands. + * + * Input: + * ha = virtual adapter state pointer. + * + * Returns: + * ql local function return status code. + * + * Context: + * Kernel context. + */ + void + ql_requeue_all_cmds(ql_adapter_state_t *ha) + { + ql_link_t *link; + ql_tgt_t *tq; + ql_lun_t *lq; + ql_srb_t *sp; + uint16_t index; + + /* Place all commands in outstanding cmd list on device queue. */ + for (index = 1; index < ha->osc_max_cnt; index++) { + INTR_LOCK(ha); + REQUEST_RING_LOCK(ha); + if ((link = ha->pending_cmds.first) != NULL) { + sp = link->base_address; + ql_remove_link(&ha->pending_cmds, &sp->cmd); + + REQUEST_RING_UNLOCK(ha); + index = 0; + } else { + REQUEST_RING_UNLOCK(ha); + if ((sp = ha->outstanding_cmds[index]) == NULL || + sp == QL_ABORTED_SRB(ha)) { + INTR_UNLOCK(ha); + continue; + } + } + + /* + * It's not obvious but the index for commands pulled from + * pending will be zero and that entry in the outstanding array + * is not used so nulling it is "no harm, no foul". + */ + + ha->outstanding_cmds[index] = NULL; + sp->handle = 0; + sp->flags &= ~SRB_IN_TOKEN_ARRAY; + + INTR_UNLOCK(ha); + + /* If command timeout. */ + if (sp->flags & SRB_COMMAND_TIMEOUT) { + sp->pkt->pkt_reason = CS_TIMEOUT; + sp->flags &= ~SRB_RETRY; + sp->flags |= SRB_ISP_COMPLETED; + + /* Call done routine to handle completion. */ + ql_done(&sp->cmd, B_FALSE); + continue; + } + + /* Acquire target queue lock. */ + lq = sp->lun_queue; + tq = lq->target_queue; + + /* return any tape IO as exchange dropped due to chip reset */ + if (tq->flags & TQF_TAPE_DEVICE) { + sp->pkt->pkt_reason = CS_TRANSPORT; + sp->flags &= ~SRB_RETRY; + sp->flags |= SRB_ISP_COMPLETED; + + EL(ha, "rtn seq IO, sp=%ph", sp); + + /* Call done routine to handle completion. */ + ql_done(&sp->cmd, B_FALSE); + continue; + } + + DEVICE_QUEUE_LOCK(tq); + + /* Reset watchdog time. */ + sp->wdg_q_time = sp->init_wdg_q_time; + + /* Place request back on top of device queue. */ + sp->flags &= ~(SRB_ISP_STARTED | SRB_ISP_COMPLETED | + SRB_RETRY); + + ql_add_link_t(&lq->cmd, &sp->cmd); + sp->flags |= SRB_IN_DEVICE_QUEUE; + + /* Release target queue lock. */ + DEVICE_QUEUE_UNLOCK(tq); + } + } + + /* * ql_vport_control * Issue Virtual Port Control command. * * Input: * ha = virtual adapter state pointer.
*** 4085,4095 **** ql_mbx_iocb_t *pkt; uint8_t bit; int rval; uint32_t pkt_size; ! QL_PRINT_10(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); if (ha->vp_index != 0) { pkt_size = sizeof (ql_mbx_iocb_t); pkt = kmem_zalloc(pkt_size, KM_SLEEP); if (pkt == NULL) { --- 4357,4367 ---- ql_mbx_iocb_t *pkt; uint8_t bit; int rval; uint32_t pkt_size; ! QL_PRINT_10(ha, "started\n"); if (ha->vp_index != 0) { pkt_size = sizeof (ql_mbx_iocb_t); pkt = kmem_zalloc(pkt_size, KM_SLEEP); if (pkt == NULL) {
*** 4099,4108 **** --- 4371,4381 ---- pkt->vpc.entry_type = VP_CONTROL_TYPE; pkt->vpc.entry_count = 1; pkt->vpc.command = cmd; pkt->vpc.vp_count = 1; + pkt->vpc.fcf_index = ha->fcoe_fcf_idx; bit = (uint8_t)(ha->vp_index - 1); pkt->vpc.vp_index[bit / 8] = (uint8_t) (pkt->vpc.vp_index[bit / 8] | BIT_0 << bit % 8); rval = ql_issue_mbx_iocb(ha, (caddr_t)pkt, pkt_size);
*** 4117,4128 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(CE_CONT, "(%d,%d): done\n", ha->instance, ! ha->vp_index); } return (rval); } /* --- 4390,4400 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 4142,4153 **** { ql_mbx_iocb_t *pkt; int rval; uint32_t pkt_size; ! QL_PRINT_10(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); pkt_size = sizeof (ql_mbx_iocb_t); pkt = kmem_zalloc(pkt_size, KM_SLEEP); if (pkt == NULL) { EL(ha, "failed, kmem_zalloc\n"); return (QL_MEMORY_ALLOC_FAILED); --- 4414,4430 ---- { ql_mbx_iocb_t *pkt; int rval; uint32_t pkt_size; ! QL_PRINT_10(ha, "started\n"); + if (ha->pha->task_daemon_flags & LOOP_DOWN) { + QL_PRINT_10(ha, "loop_down\n"); + return (QL_FUNCTION_FAILED); + } + pkt_size = sizeof (ql_mbx_iocb_t); pkt = kmem_zalloc(pkt_size, KM_SLEEP); if (pkt == NULL) { EL(ha, "failed, kmem_zalloc\n"); return (QL_MEMORY_ALLOC_FAILED);
*** 4157,4166 **** --- 4434,4444 ---- pkt->vpm.entry_count = 1; pkt->vpm.command = cmd; pkt->vpm.vp_count = 1; pkt->vpm.first_vp_index = ha->vp_index; pkt->vpm.first_options = opt; + pkt->vpm.fcf_index = ha->fcoe_fcf_idx; bcopy(ha->loginparams.nport_ww_name.raw_wwn, pkt->vpm.first_port_name, 8); bcopy(ha->loginparams.node_ww_name.raw_wwn, pkt->vpm.first_node_name, 8);
*** 4175,4186 **** if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(CE_CONT, "(%d,%d): done\n", ha->instance, ! ha->vp_index); } return (rval); } /* --- 4453,4463 ---- if (rval != QL_SUCCESS) { EL(ha, "failed, rval = %xh\n", rval); } else { /*EMPTY*/ ! QL_PRINT_10(ha, "done\n"); } return (rval); } /*
*** 4196,4233 **** int ql_vport_enable(ql_adapter_state_t *ha) { int timer; ! QL_PRINT_10(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); ha->state = FC_PORT_SPEED_MASK(ha->state) | FC_STATE_OFFLINE; TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= LOOP_DOWN; ha->task_daemon_flags &= ~(FC_STATE_CHANGE | STATE_ONLINE); TASK_DAEMON_UNLOCK(ha); ADAPTER_STATE_LOCK(ha); ha->flags |= VP_ENABLED; ADAPTER_STATE_UNLOCK(ha); if (ql_vport_modify(ha, VPM_MODIFY_ENABLE, VPO_TARGET_MODE_DISABLED | VPO_INITIATOR_MODE_ENABLED | VPO_ENABLED) != QL_SUCCESS) { ! QL_PRINT_2(CE_CONT, "(%d): failed to enable virtual port=%d\n", ! ha->instance, ha->vp_index); return (QL_FUNCTION_FAILED); } if (!(ha->pha->task_daemon_flags & LOOP_DOWN)) { /* Wait for loop to come up. */ for (timer = 0; timer < 3000 && !(ha->task_daemon_flags & STATE_ONLINE); timer++) { delay(1); } } ! QL_PRINT_10(CE_CONT, "(%d,%d): done\n", ha->instance, ha->vp_index); return (QL_SUCCESS); } /* --- 4473,4514 ---- int ql_vport_enable(ql_adapter_state_t *ha) { int timer; ! QL_PRINT_10(ha, "started\n"); ha->state = FC_PORT_SPEED_MASK(ha->state) | FC_STATE_OFFLINE; TASK_DAEMON_LOCK(ha); ha->task_daemon_flags |= LOOP_DOWN; ha->task_daemon_flags &= ~(FC_STATE_CHANGE | STATE_ONLINE); TASK_DAEMON_UNLOCK(ha); ADAPTER_STATE_LOCK(ha); ha->flags |= VP_ENABLED; + ha->flags &= ~VP_ID_NOT_ACQUIRED; ADAPTER_STATE_UNLOCK(ha); + ha->fcoe_fcf_idx = 0; if (ql_vport_modify(ha, VPM_MODIFY_ENABLE, VPO_TARGET_MODE_DISABLED | VPO_INITIATOR_MODE_ENABLED | VPO_ENABLED) != QL_SUCCESS) { ! QL_PRINT_2(ha, "failed to enable virtual port\n"); return (QL_FUNCTION_FAILED); } if (!(ha->pha->task_daemon_flags & LOOP_DOWN)) { /* Wait for loop to come up. */ for (timer = 0; timer < 3000 && !(ha->task_daemon_flags & STATE_ONLINE); timer++) { + if (ha->flags & VP_ID_NOT_ACQUIRED) { + break; + } delay(1); } } ! QL_PRINT_10(ha, "done\n"); return (QL_SUCCESS); } /*
*** 4244,4254 **** ql_adapter_state_t * ql_vport_create(ql_adapter_state_t *ha, uint8_t index) { ql_adapter_state_t *vha; ! QL_PRINT_10(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); /* Inherit the parents data. */ vha = kmem_alloc(sizeof (ql_adapter_state_t), KM_SLEEP); ADAPTER_STATE_LOCK(ha); --- 4525,4535 ---- ql_adapter_state_t * ql_vport_create(ql_adapter_state_t *ha, uint8_t index) { ql_adapter_state_t *vha; ! QL_PRINT_10(ha, "started\n"); /* Inherit the parents data. */ vha = kmem_alloc(sizeof (ql_adapter_state_t), KM_SLEEP); ADAPTER_STATE_LOCK(ha);
*** 4270,4280 **** vha->dev = kmem_zalloc(sizeof (*vha->dev) * DEVICE_HEAD_LIST_SIZE, KM_SLEEP); vha->ub_array = kmem_zalloc(sizeof (*vha->ub_array) * QL_UB_LIMIT, KM_SLEEP); ! QL_PRINT_10(CE_CONT, "(%d,%d): done\n", ha->instance, ha->vp_index); return (vha); } /* --- 4551,4561 ---- vha->dev = kmem_zalloc(sizeof (*vha->dev) * DEVICE_HEAD_LIST_SIZE, KM_SLEEP); vha->ub_array = kmem_zalloc(sizeof (*vha->ub_array) * QL_UB_LIMIT, KM_SLEEP); ! QL_PRINT_10(ha, "done\n"); return (vha); } /*
*** 4290,4300 **** void ql_vport_destroy(ql_adapter_state_t *ha) { ql_adapter_state_t *vha; ! QL_PRINT_10(CE_CONT, "(%d,%d): started\n", ha->instance, ha->vp_index); /* Remove port from list. */ ADAPTER_STATE_LOCK(ha); for (vha = ha->pha; vha != NULL; vha = vha->vp_next) { if (vha->vp_next == ha) { --- 4571,4581 ---- void ql_vport_destroy(ql_adapter_state_t *ha) { ql_adapter_state_t *vha; ! QL_PRINT_10(ha, "started\n"); /* Remove port from list. */ ADAPTER_STATE_LOCK(ha); for (vha = ha->pha; vha != NULL; vha = vha->vp_next) { if (vha->vp_next == ha) {
*** 4310,4320 **** if (ha->dev != NULL) { kmem_free(ha->dev, sizeof (*vha->dev) * DEVICE_HEAD_LIST_SIZE); } kmem_free(ha, sizeof (ql_adapter_state_t)); ! QL_PRINT_10(CE_CONT, "(%d,%d): done\n", ha->instance, ha->vp_index); } /* * ql_mps_reset * Reset MPS for FCoE functions. --- 4591,4601 ---- if (ha->dev != NULL) { kmem_free(ha->dev, sizeof (*vha->dev) * DEVICE_HEAD_LIST_SIZE); } kmem_free(ha, sizeof (ql_adapter_state_t)); ! QL_PRINT_10(ha, "done\n"); } /* * ql_mps_reset * Reset MPS for FCoE functions.
*** 4341,4353 **** } } while (!(data & BIT_0)); if (ql_rd_risc_ram_word(ha, 0x7A15, &data) == QL_SUCCESS) { dctl = (uint16_t)ql_pci_config_get16(ha, 0x54); ! if ((data & 0xe0) != (dctl & 0xe0)) { data &= 0xff1f; data |= dctl & 0xe0; (void) ql_wrt_risc_ram_word(ha, 0x7A15, data); } } (void) ql_wrt_risc_ram_word(ha, 0x7c00, 0); } --- 4622,4717 ---- } } while (!(data & BIT_0)); if (ql_rd_risc_ram_word(ha, 0x7A15, &data) == QL_SUCCESS) { dctl = (uint16_t)ql_pci_config_get16(ha, 0x54); ! if ((data & 0xe0) < (dctl & 0xe0)) { data &= 0xff1f; data |= dctl & 0xe0; (void) ql_wrt_risc_ram_word(ha, 0x7A15, data); + } else if ((data & 0xe0) != (dctl & 0xe0)) { + data &= 0xff1f; + data |= dctl & 0xe0; + (void) ql_wrt_risc_ram_word(ha, 0x7A15, data); } } (void) ql_wrt_risc_ram_word(ha, 0x7c00, 0); + } + + /* + * ql_update_dev + * Updates device status on loop reconfigure. + * + * Input: + * ha: adapter state pointer. + * index: list index of device data. + * + * Context: + * Kernel context. + */ + static void + ql_update_dev(ql_adapter_state_t *ha, uint32_t index) + { + ql_link_t *link; + ql_tgt_t *tq; + int rval; + + QL_PRINT_3(ha, "started\n"); + + link = ha->dev[index].first; + while (link != NULL) { + tq = link->base_address; + link = link->next; + + if (tq->loop_id & PORT_LOST_ID && + !(tq->flags & (TQF_INITIATOR_DEVICE | TQF_FABRIC_DEVICE))) { + + tq->loop_id &= ~PORT_LOST_ID; + + if (VALID_DEVICE_ID(ha, tq->loop_id)) { + /* implicit logo due to fw issue */ + rval = ql_get_port_database(ha, tq, PDF_NONE); + + if (rval == QL_NOT_LOGGED_IN) { + if (tq->master_state == + PD_STATE_PORT_UNAVAILABLE) { + (void) ql_logout_fabric_port( + ha, tq); + tq->loop_id = PORT_NO_LOOP_ID; + } + } else if (rval == QL_SUCCESS) { + tq->loop_id = PORT_NO_LOOP_ID; + } + } + } else if (ha->topology & QL_NL_PORT && + tq->flags & TQF_FABRIC_DEVICE) { + + tq->loop_id &= ~PORT_LOST_ID; + + if (VALID_DEVICE_ID(ha, tq->loop_id)) { + /* implicit logo due to fw issue */ + rval = ql_get_port_database(ha, tq, PDF_NONE); + + if (rval == QL_NOT_LOGGED_IN) { + if (tq->master_state == + PD_STATE_PORT_UNAVAILABLE) { + (void) ql_logout_fabric_port( + ha, tq); + /* + * fabric to AL topo change + */ + tq->loop_id = PORT_NO_LOOP_ID; + } + } else if (rval == QL_SUCCESS) { + /* + * Normally this is 7fe, + * Don't issue logo, it causes + * logo in single tgt AL. + */ + tq->loop_id = PORT_NO_LOOP_ID; + } + } + } + } + + QL_PRINT_3(ha, "done\n"); }