fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * CDDL HEADER START
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * The contents of this file are subject to the terms of the
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Common Development and Distribution License (the "License").
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * You may not use this file except in compliance with the License.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * or http://www.opensolaris.org/os/licensing.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * See the License for the specific language governing permissions
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * and limitations under the License.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * When distributing Covered Code, include this CDDL HEADER in each
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * If applicable, add the following below this CDDL HEADER, with the
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * fields enclosed by brackets "[]" replaced with your own identifying
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * information: Portions Copyright [yyyy] [name of copyright owner]
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * CDDL HEADER END
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
c1fad183c9a0deeb49586645ec9baa8f3c1bc8beDaniel Beauregard/* Copyright 2010 QLogic Corporation */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
c1fad183c9a0deeb49586645ec9baa8f3c1bc8beDaniel Beauregard#pragma ident "Copyright 2010 QLogic Corporation; ql_isr.c"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ISP2xxx Solaris Fibre Channel Adapter (FCA) driver source file.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ***********************************************************************
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * * **
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * * NOTICE **
c1fad183c9a0deeb49586645ec9baa8f3c1bc8beDaniel Beauregard * * COPYRIGHT (C) 1996-2010 QLOGIC CORPORATION **
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * * ALL RIGHTS RESERVED **
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * * **
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ***********************************************************************
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_apps.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_api.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_debug.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_iocb.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_isr.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_init.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_mbx.h>
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard#include <ql_nx.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#include <ql_xioctl.h>
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Local Function Prototypes.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregardstatic void ql_handle_uncommon_risc_intr(ql_adapter_state_t *, uint32_t,
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_spurious_intr(ql_adapter_state_t *, int);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_mbx_completion(ql_adapter_state_t *, uint16_t, uint32_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, int);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_async_event(ql_adapter_state_t *, uint32_t, ql_head_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, uint32_t *, int);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_fast_fcp_post(ql_srb_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_response_pkt(ql_adapter_state_t *, ql_head_t *, uint32_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, int);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_error_entry(ql_adapter_state_t *, response_t *, ql_head_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int ql_status_entry(ql_adapter_state_t *, sts_entry_t *, ql_head_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int ql_24xx_status_entry(ql_adapter_state_t *, sts_24xx_entry_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int ql_status_error(ql_adapter_state_t *, ql_srb_t *, sts_entry_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_status_cont_entry(ql_adapter_state_t *, sts_cont_entry_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_ip_entry(ql_adapter_state_t *, ip_entry_t *, ql_head_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_ip_rcv_entry(ql_adapter_state_t *, ip_rcv_entry_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_ip_rcv_cont_entry(ql_adapter_state_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ip_rcv_cont_entry_t *, ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_ip_24xx_rcv_entry(ql_adapter_state_t *, ip_rcv_24xx_entry_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_ms_entry(ql_adapter_state_t *, ms_entry_t *, ql_head_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *, uint32_t *);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void ql_report_id_entry(ql_adapter_state_t *, report_id_1_t *,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *, uint32_t *, uint32_t *);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregardstatic void ql_els_passthru_entry(ql_adapter_state_t *,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard els_passthru_entry_rsp_t *, ql_head_t *, uint32_t *, uint32_t *);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardstatic ql_srb_t *ql_verify_preprocessed_cmd(ql_adapter_state_t *, uint32_t *,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t *, uint32_t *);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardstatic void ql_signal_abort(ql_adapter_state_t *ha, uint32_t *set_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard/*
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard * Spurious interrupt counter
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard */
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregarduint32_t ql_spurious_cnt = 4;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregarduint32_t ql_max_intr_loop = 16;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_isr
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Process all INTX intr types.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * arg1: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * DDI_INTR_CLAIMED or DDI_INTR_UNCLAIMED
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteuint_t
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_isr(caddr_t arg1)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (ql_isr_aif(arg1, 0));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_isr_default
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Process unknown/unvectored intr types
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * arg1: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * arg2: interrupt vector.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * DDI_INTR_CLAIMED or DDI_INTR_UNCLAIMED
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteuint_t
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_isr_default(caddr_t arg1, caddr_t arg2)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_adapter_state_t *ha = (void *)arg1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "isr_default called: idx=%x\n", arg2);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (ql_isr_aif(arg1, arg2));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_isr_aif
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Process mailbox and I/O command completions.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * arg: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * intvec: interrupt vector.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * DDI_INTR_CLAIMED or DDI_INTR_UNCLAIMED
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteuint_t
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_isr_aif(caddr_t arg, caddr_t intvec)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t mbx;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t stat;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_adapter_state_t *ha = (void *)arg;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t set_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t reset_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t isr_done_q = {NULL, NULL};
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint_t rval = DDI_INTR_UNCLAIMED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int spurious_intr = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte boolean_t intr = B_FALSE, daemon = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int intr_loop = 4;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard boolean_t clear_spurious = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PM_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->power_level != PM_LEVEL_D0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Looks like we are about to go down soon, exit early.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PM_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): power down exit\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (DDI_INTR_UNCLAIMED);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->busy++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PM_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire interrupt lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte INTR_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (CFG_IST(ha, CFG_CTRL_2200)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte while (RD16_IO_REG(ha, istatus) & RISC_INT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Reset idle timer. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->idle_timer = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval = DDI_INTR_CLAIMED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_loop) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr_loop--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Special Fast Post 2200. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->task_daemon_flags & FIRMWARE_LOADED &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags & ONLINE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mbx = RD16_IO_REG(ha, mailbox_out[23]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((mbx & 3) == MBX23_SCSI_COMPLETION) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release mailbox registers. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, semaphore, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_loop) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, hccr,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte HC_CLR_RISC_INT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Get handle. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx >>= 4;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = mbx & OSC_INDEX_MASK;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Validate handle. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp = stat < MAX_OUTSTANDING_COMMANDS ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->outstanding_cmds[stat] : NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp != NULL && (sp->handle & 0xfff)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte == mbx) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->outstanding_cmds[stat] =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->handle = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags &=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ~SRB_IN_TOKEN_ARRAY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completion status */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_fast_fcp_post(sp);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (mbx !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (QL_FCA_BRAND & 0xfff)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "unknown IOCB"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " handle=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "mismatch IOCB"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " handle pkt=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "sp=%xh\n", mbx,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->handle & 0xfff);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_binary_fw_dump(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FALSE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(ha->task_daemon_flags &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ISP_ABORT_NEEDED |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ABORT_ISP_ACTIVE))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ISP Invalid "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "handle, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "isp_abort_needed"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags |=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (stat == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Check for mailbox interrupt. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx = RD16_IO_REG(ha, semaphore);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (mbx & BIT_0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release mailbox registers. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, semaphore, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Get mailbox data. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mbx = RD16_IO_REG(ha, mailbox_out[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (mbx > 0x3fff && mbx < 0x8000) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_mbx_completion(ha, mbx,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (mbx > 0x7fff &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx < 0xc000) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, mbx,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &isr_done_q, &set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "UNKNOWN interrupt "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "type\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->isp_rsp_index = RD16_IO_REG(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte resp_in);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->isp_rsp_index !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->rsp_ring_index) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_response_pkt(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &isr_done_q, &set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (++spurious_intr ==
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MAX_SPURIOUS_INTR) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Process excessive
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * spurious intrrupts
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_spurious_intr(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "excessive spurious "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "interrupts, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr || intr_loop == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (set_flags != 0 || reset_flags != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->task_daemon_flags |= set_flags;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->task_daemon_flags &= ~reset_flags;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte daemon = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard uint32_t ql_max_intr_loop_cnt = 0;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_hw_intr(ha);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard intr_loop = 1;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard while (((stat = RD32_IO_REG(ha, risc2host)) & RH_RISC_INT) &&
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard (++ql_max_intr_loop_cnt < ql_max_intr_loop)) {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard clear_spurious = B_TRUE; /* assume ok */
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard /* Capture FW defined interrupt info */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx = MSW(stat);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Reset idle timer. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->idle_timer = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval = DDI_INTR_CLAIMED;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021) &&
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard (RD32_IO_REG(ha, nx_risc_int) == 0 ||
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard intr_loop == 0)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard break;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_loop) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr_loop--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (stat & 0x1ff) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case ROM_MBX_SUCCESS:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case ROM_MBX_ERR:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_mbx_completion(ha, mbx, &set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release mailbox registers. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if ((CFG_IST(ha, CFG_CTRL_24258081)) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, semaphore, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBX_SUCCESS:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBX_ERR:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Sun FW, Release mailbox registers. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if ((CFG_IST(ha, CFG_CTRL_24258081)) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, semaphore, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_mbx_completion(ha, mbx, &set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case ASYNC_EVENT:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Sun FW, Release mailbox registers. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if ((CFG_IST(ha, CFG_CTRL_24258081)) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, semaphore, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, (uint32_t)mbx, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case RESP_UPDATE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (mbx != ha->rsp_ring_index) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->isp_rsp_index = mbx;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_response_pkt(ha, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (++spurious_intr ==
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ql_spurious_cnt) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Process excessive spurious intr. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_spurious_intr(ha, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "excessive spurious "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "interrupts, isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags |= ISP_ABORT_NEEDED;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard clear_spurious = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard QL_PRINT_10(CE_CONT, "(%d): response "
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard "ring index same as before\n",
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard clear_spurious = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case SCSI_FAST_POST_16:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) | MBA_CMPLT_1_16BIT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case SCSI_FAST_POST_32:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) | MBA_CMPLT_1_32BIT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case CTIO_FAST_POST:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MBA_CTIO_COMPLETION;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_FAST_POST_XMT:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) | MBA_IP_COMPLETION;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_FAST_POST_RCV:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) | MBA_IP_RECEIVE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_FAST_POST_BRD:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) | MBA_IP_BROADCAST;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_FAST_POST_RCV_ALN:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte stat = (stat & 0xffff0000) |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MBA_IP_HDR_DATA_SPLIT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_async_event(ha, stat, &isr_done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &set_flags, &reset_flags, intr_loop);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case ATIO_UPDATE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "unsupported ATIO queue update"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " interrupt, status=%xh\n", stat);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case ATIO_RESP_UPDATE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "unsupported ATIO response queue "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "update interrupt, status=%xh\n", stat);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ql_handle_uncommon_risc_intr(ha, stat,
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard &set_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr || intr_loop == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_FALSE;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr,
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (set_flags != 0 || reset_flags != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->task_daemon_flags |= set_flags;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->task_daemon_flags &= ~reset_flags;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte daemon = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->flags & PARITY_ERROR) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "parity/pause exit\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mbx = RD16_IO_REG(ha, hccr); /* PCI posting */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard if (clear_spurious) {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard spurious_intr = 0;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Process claimed interrupts during polls. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (rval == DDI_INTR_UNCLAIMED && ha->intr_claimed == B_TRUE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->intr_claimed = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval = DDI_INTR_CLAIMED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release interrupt lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte INTR_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (daemon) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_awaken_task_daemon(ha, NULL, 0, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (isr_done_q.first != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_done(isr_done_q.first);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (rval == DDI_INTR_CLAIMED) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->TotalInterrupts++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*EMPTY*/
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): interrupt not claimed\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PM_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->busy--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PM_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (rval);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard/*
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * ql_handle_uncommon_risc_intr
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * Handle an uncommon RISC interrupt.
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard *
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * Input:
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * ha: adapter state pointer.
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * stat: interrupt status
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard *
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * Context:
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard * Interrupt or Kernel context, no mailbox commands allowed.
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard */
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregardstatic void
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregardql_handle_uncommon_risc_intr(ql_adapter_state_t *ha, uint32_t stat,
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard uint32_t *set_flags)
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard{
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard uint16_t hccr_reg;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard hccr_reg = RD16_IO_REG(ha, hccr);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard if (stat & RH_RISC_PAUSED ||
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard (hccr_reg & (BIT_15 | BIT_13 | BIT_11 | BIT_8))) {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ADAPTER_STATE_LOCK(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->flags |= PARITY_ERROR;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ADAPTER_STATE_UNLOCK(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard if (ha->parity_pause_errors == 0 ||
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_hccr_err != hccr_reg ||
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_stat_err != stat) {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard cmn_err(CE_WARN, "qlc(%d): isr, Internal Parity/"
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard "Pause Error - hccr=%xh, stat=%xh, count=%d",
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->instance, hccr_reg, stat,
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_pause_errors);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_hccr_err = hccr_reg;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_stat_err = stat;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard EL(ha, "parity/pause error, isp_abort_needed\n");
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard if (ql_binary_fw_dump(ha, FALSE) != QL_SUCCESS) {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ql_reset_chip(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard if (ha->parity_pause_errors == 0) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->log_parity_pause = B_TRUE;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard if (ha->parity_pause_errors < 0xffffffff) {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->parity_pause_errors++;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard *set_flags |= ISP_ABORT_NEEDED;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard /* Disable ISP interrupts. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard CFG_IST(ha, CFG_CTRL_8021) ? ql_8021_disable_intrs(ha) :
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, ictrl, 0);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ADAPTER_STATE_LOCK(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ha->flags &= ~INTERRUPTS_ENABLED;
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard ADAPTER_STATE_UNLOCK(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard } else {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard EL(ha, "UNKNOWN interrupt status=%xh, hccr=%xh\n",
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard stat, hccr_reg);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard}
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_spurious_intr
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Inform Solaris of spurious interrupts.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * intr_clr: early interrupt clear
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_spurious_intr(ql_adapter_state_t *ha, int intr_clr)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_devstate_t state;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Spurious interrupt\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Disable ISP interrupts. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, ictrl, 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags &= ~INTERRUPTS_ENABLED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_clr) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte state = ddi_get_devstate(ha->dip);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (state == DDI_DEVSTATE_UP) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*EMPTY*/
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_dev_report_fault(ha->dip, DDI_SERVICE_DEGRADED,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DEVICE_FAULT, "spurious interrupts");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_mbx_completion
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes mailbox completions.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * mb0: Mailbox 0 contents.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * intr_clr: early interrupt clear
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt context.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_mbx_completion(ql_adapter_state_t *ha, uint16_t mb0, uint32_t *set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *reset_flags, int intr_clr)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Load return mailbox registers. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MBX_REGISTER_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->mcp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->mcp->mb[0] = mb0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = ha->mcp->in_mb & ~MBX_0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 1; cnt < MAX_MBOX_COUNT && index != 0; cnt++) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index >>= 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (index & MBX_0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->mcp->mb[cnt] = RD16_IO_REG(ha,
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mailbox_out[cnt]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "mcp == NULL\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_clr) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt. */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->mailbox_flags = (uint8_t)(ha->mailbox_flags | MBX_INTERRUPT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->flags & INTERRUPTS_ENABLED) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte cv_broadcast(&ha->cv_mbx_intr);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MBX_REGISTER_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_async_event
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes asynchronous events.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * mbx: Mailbox 0 register.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: head pointer to done queue.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * intr_clr: early interrupt clear
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_async_event(ql_adapter_state_t *ha, uint32_t mbx, ql_head_t *done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *set_flags, uint32_t *reset_flags, int intr_clr)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t handle;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t mb[MAX_MBOX_COUNT];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte port_id_t s_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte boolean_t intr = B_TRUE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_adapter_state_t *vha;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup to process fast completion. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0] = LSW(mbx);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (mb[0]) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_SCSI_COMPLETION:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard handle = SHORT_TO_LONG(RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_CMPLT_1_16BIT:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte handle = MSW(mbx);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0] = MBA_SCSI_COMPLETION;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_CMPLT_1_32BIT:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard handle = SHORT_TO_LONG(MSW(mbx),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0] = MBA_SCSI_COMPLETION;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_CTIO_COMPLETION:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_COMPLETION:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte handle = CFG_IST(ha, CFG_CTRL_2200) ? SHORT_TO_LONG(
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2])) :
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard SHORT_TO_LONG(MSW(mbx), RD16_IO_REG(ha, mailbox_out[2]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0] = MBA_SCSI_COMPLETION;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Handle asynchronous event */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (mb[0]) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_SCSI_COMPLETION:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_5(CE_CONT, "(%d): Fast post completion\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_clr) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->flags & ONLINE) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Get handle. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = handle & OSC_INDEX_MASK;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Validate handle. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp = index < MAX_OUTSTANDING_COMMANDS ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->outstanding_cmds[index] : NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp != NULL && sp->handle == handle) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->outstanding_cmds[index] = NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->handle = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags &= ~SRB_IN_TOKEN_ARRAY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completion status */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(sp->flags & SRB_FCP_CMD_PKT)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Place block on done queue */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_fast_fcp_post(sp);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (handle != QL_FCA_BRAND) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh unknown IOCB handle=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0], handle);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh mismatch IOCB handle pkt=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "sp=%xh\n", mb[0], handle, sp->handle);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Fast post, mbx1=%xh, mbx2=%xh, mbx3=%xh,"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx6=%xh, mbx7=%xh\n", mb[0],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[6]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[7]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_binary_fw_dump(ha, FALSE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(ha->task_daemon_flags &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ISP_ABORT_NEEDED | ABORT_ISP_ACTIVE))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh ISP Invalid handle, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "isp_abort_needed\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_RESET: /* Reset */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Reset received\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= RESET_MARKER_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_SYSTEM_ERR: /* System Error */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[3] = RD16_IO_REG(ha, mailbox_out[3]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[7] = RD16_IO_REG(ha, mailbox_out[7]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh ISP System Error, isp_abort_needed\n mbx1=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx2=%xh, mbx3=%xh, mbx4=%xh, mbx5=%xh, mbx6=%xh,\n "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx7=%xh, mbx8=%xh, mbx9=%xh, mbx10=%xh, mbx11=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx12=%xh,\n", mb[0], mb[1], mb[2], mb[3],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[4]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[5]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[6]), mb[7],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[8]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[9]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[10]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[11]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[12]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh ISP System Error, isp_abort_needed\n mbx13=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx14=%xh, mbx15=%xh, mbx16=%xh, mbx17=%xh, mbx18=%xh,\n"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx19=%xh, mbx20=%xh, mbx21=%xh, mbx22=%xh, mbx23=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[13]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[14]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[15]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[16]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[17]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[18]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[19]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[20]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[21]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[22]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[23]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->reg_off->mbox_cnt > 24) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh ISP System Error, mbx24=%xh, mbx25=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx26=%xh,\n mbx27=%xh, mbx28=%xh, mbx29=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx30=%xh, mbx31=%xh\n", mb[0],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[24]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[25]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[26]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[27]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[28]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[29]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[30]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[31]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_binary_fw_dump(ha, FALSE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_flash_errlog(ha, FLASH_ERRLOG_AEN_8002, mb[1],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_81XX) && mb[7] & SE_MPI_RISC) {
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard ADAPTER_STATE_LOCK(ha);
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard ha->flags |= MPI_RESET_NEEDED;
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard ADAPTER_STATE_UNLOCK(ha);
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard }
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->ControllerErrorCount++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_REQ_TRANSFER_ERR: /* Request Transfer Error */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Request Transfer Error received, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "isp_abort_needed\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_flash_errlog(ha, FLASH_ERRLOG_AEN_8003,
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->ControllerErrorCount++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_RSP_TRANSFER_ERR: /* Response Xfer Err */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Response Transfer Error received,"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " isp_abort_needed\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ql_flash_errlog(ha, FLASH_ERRLOG_AEN_8004,
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->ControllerErrorCount++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_WAKEUP_THRES: /* Request Queue Wake-up */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Request Queue Wake-up received\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_MENLO_ALERT: /* Menlo Alert Notification */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[3] = RD16_IO_REG(ha, mailbox_out[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Menlo Alert Notification received, mbx1=%xh,"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " mbx2=%xh, mbx3=%xh\n", mb[0], mb[1], mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (mb[1]) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MLA_LOGIN_OPERATIONAL_FW:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags |= MENLO_LOGIN_OPERATIONAL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MLA_PANIC_RECOVERY:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MLA_LOGIN_DIAGNOSTIC_FW:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MLA_LOGIN_GOLDEN_FW:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MLA_REJECT_RESPONSE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LIP_F8: /* Received a LIP F8. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LIP_RESET: /* LIP reset occurred. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LIP_OCCURRED: /* Loop Initialization Procedure */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8081)) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh DCBX_STARTED received, mbx1=%xh, mbx2=%xh"
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard "\n", mb[0], RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]));
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard } else {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh LIP received\n", mb[0]);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags &= ~POINT_TO_POINT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(ha->task_daemon_flags & LOOP_DOWN)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_port_state(ha, FC_STATE_OFFLINE,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FC_STATE_CHANGE | COMMAND_WAIT_NEEDED | LOOP_DOWN);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->loop_down_timer == LOOP_DOWN_TIMER_OFF) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->loop_down_timer = LOOP_DOWN_TIMER_START;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->adapter_stats->lip_count++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update AEN queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->TotalLipResets++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->xioctl->flags & QL_AEN_TRACKING_ENABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_enqueue_aen(ha, mb[0], NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LOOP_UP:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322 |
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard CFG_CTRL_24258081))) {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->iidma_rate = RD16_IO_REG(ha, mailbox_out[1]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard if (ha->iidma_rate == IIDMA_RATE_1GB) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state) | FC_STATE_1GBIT_SPEED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 1;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard } else if (ha->iidma_rate == IIDMA_RATE_2GB) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state) | FC_STATE_2GBIT_SPEED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 2;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard } else if (ha->iidma_rate == IIDMA_RATE_4GB) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state) | FC_STATE_4GBIT_SPEED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 4;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard } else if (ha->iidma_rate == IIDMA_RATE_8GB) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state) | FC_STATE_8GBIT_SPEED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 8;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard } else if (ha->iidma_rate == IIDMA_RATE_10GB) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->state = FC_PORT_STATE_MASK(
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->state) | FC_STATE_10GBIT_SPEED;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard index = 10;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->iidma_rate = IIDMA_RATE_1GB;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->state = FC_PORT_STATE_MASK(ha->state) |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FC_STATE_FULL_SPEED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (vha = ha; vha != NULL; vha = vha->vp_next) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->state = FC_PORT_STATE_MASK(vha->state) |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FC_PORT_SPEED_MASK(ha->state);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%d GB %xh Loop Up received\n", index, mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update AEN queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->xioctl->flags & QL_AEN_TRACKING_ENABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_enqueue_aen(ha, mb[0], NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LOOP_DOWN:
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard EL(ha, "%xh Loop Down received, mbx1=%xh, mbx2=%xh, mbx3=%xh, "
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard "mbx4=%xh\n", mb[0], RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[4]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(ha->task_daemon_flags & LOOP_DOWN)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_port_state(ha, FC_STATE_OFFLINE,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FC_STATE_CHANGE | COMMAND_WAIT_NEEDED | LOOP_DOWN);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->loop_down_timer == LOOP_DOWN_TIMER_OFF) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->loop_down_timer = LOOP_DOWN_TIMER_START;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_258081)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->sfp_stat = RD16_IO_REG(ha, mailbox_out[2]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update AEN queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->xioctl->flags & QL_AEN_TRACKING_ENABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_enqueue_aen(ha, mb[0], NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_PORT_UPDATE:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[3] = (uint16_t)(ha->flags & VP_ENABLED ?
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]) : 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate port state structure. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (vha = ha; vha != NULL; vha = vha->vp_next) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (vha->vp_index == LSB(mb[3])) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (vha == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8081) && mb[1] == 0xffff &&
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] == 7 && (MSB(mb[3]) == 0xe || MSB(mb[3]) == 0x1a ||
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard MSB(mb[3]) == 0x1c || MSB(mb[3]) == 0x1d ||
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard MSB(mb[3]) == 0x1e)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard /*
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * received FLOGI reject
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * received FLOGO
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * FCF configuration changed
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * FIP Clear Virtual Link received
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * FKA timeout
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (!(ha->task_daemon_flags & LOOP_DOWN)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard *set_flags |= LOOP_DOWN;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_port_state(ha, FC_STATE_OFFLINE, FC_STATE_CHANGE |
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard COMMAND_WAIT_NEEDED | LOOP_DOWN);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (ha->loop_down_timer == LOOP_DOWN_TIMER_OFF) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->loop_down_timer = LOOP_DOWN_TIMER_START;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /*
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * In N port 2 N port topology the FW provides a port
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * database entry at loop_id 0x7fe which we use to
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * acquire the Ports WWPN.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if ((mb[1] != 0x7fe) &&
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ((FC_PORT_STATE_MASK(vha->state) != FC_STATE_OFFLINE ||
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard (CFG_IST(ha, CFG_CTRL_24258081) &&
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard (mb[1] != 0xffff || mb[2] != 6 || mb[3] != 0))))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Port Database Update, Login/Logout "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "received, mbx1=%xh, mbx2=%xh, mbx3=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0], mb[1], mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Port Database Update received, mbx1=%xh,"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte " mbx2=%xh, mbx3=%xh\n", mb[0], mb[1], mb[2],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags &= ~LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *reset_flags |= LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *reset_flags &= ~LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->loop_down_timer = LOOP_DOWN_TIMER_OFF;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->task_daemon_flags |= LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->task_daemon_flags &= ~LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard vha->flags &= ~ABORT_CMDS_LOOP_DOWN_TMO;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update AEN queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->xioctl->flags & QL_AEN_TRACKING_ENABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_enqueue_aen(ha, mb[0], NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_RSCN_UPDATE:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[3] = (uint16_t)(ha->flags & VP_ENABLED ?
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]) : 0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate port state structure. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (vha = ha; vha != NULL; vha = vha->vp_next) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (vha->vp_index == LSB(mb[3])) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (vha == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (LSB(mb[1]) == vha->d_id.b.domain &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte MSB(mb[2]) == vha->d_id.b.area &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte LSB(mb[2]) == vha->d_id.b.al_pa) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh RSCN match adapter, mbx1=%xh, mbx2=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx3=%xh\n", mb[0], mb[1], mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh RSCN received, mbx1=%xh, mbx2=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx3=%xh\n", mb[0], mb[1], mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (FC_PORT_STATE_MASK(vha->state) !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte FC_STATE_OFFLINE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_rcv_rscn_els(vha, &mb[0], done_q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->task_daemon_flags |= RSCN_UPDATE_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= RSCN_UPDATE_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update AEN queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->xioctl->flags & QL_AEN_TRACKING_ENABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_enqueue_aen(ha, mb[0], NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LIP_ERROR: /* Loop initialization errors. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh LIP error received, mbx1=%xh\n", mb[0],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_RECEIVE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_BROADCAST:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[3] = RD16_IO_REG(ha, mailbox_out[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh IP packet/broadcast received, mbx1=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx2=%xh, mbx3=%xh\n", mb[0], mb[1], mb[2], mb[3]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate device queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.al_pa = LSB(mb[2]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.area = MSB(mb[2]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.domain = LSB(mb[1]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq = ql_d_id_to_queue(ha, s_id)) == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Unknown IP device=%xh\n", s_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard cnt = (uint16_t)(CFG_IST(ha, CFG_CTRL_24258081) ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte CHAR_TO_SHORT(ha->ip_init_ctrl_blk.cb24.buf_size[0],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->ip_init_ctrl_blk.cb24.buf_size[1]) :
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte CHAR_TO_SHORT(ha->ip_init_ctrl_blk.cb.buf_size[0],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->ip_init_ctrl_blk.cb.buf_size[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_sequence_length = mb[3];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt = (uint8_t)(mb[3] / cnt);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (mb[3] % cnt) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte cnt = (uint16_t)(tq->ub_total_seg_cnt + 10);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (index = 10; index < ha->reg_off->mbox_cnt && index < cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index++) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[index] = RD16_IO_REG(ha, mailbox_out[index]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_id = ++ha->ub_seq_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_cnt = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_frame_ro = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_loop_id = (uint16_t)(mb[0] == MBA_IP_BROADCAST ?
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard (CFG_IST(ha, CFG_CTRL_24258081) ? BROADCAST_24XX_HDL :
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte IP_BROADCAST_LOOP_ID) : tq->loop_id);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->rcv_dev_q = tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 10; cnt < ha->reg_off->mbox_cnt &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_cnt < tq->ub_total_seg_cnt; cnt++) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ql_ub_frame_hdr(ha, tq, mb[cnt], done_q) !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_SUCCESS) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ql_ub_frame_hdr failed, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_LOW_WATER_MARK:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_RCV_BUFFER_EMPTY:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh IP low water mark / RCV buffer empty received\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= NEED_UNSOLICITED_BUFFERS;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_IP_HDR_DATA_SPLIT:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh IP HDR data split received\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard case MBA_ERROR_LOGGING_DISABLED:
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard EL(ha, "%xh error logging disabled received, "
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard "mbx1=%xh\n", mb[0], RD16_IO_REG(ha, mailbox_out[1]));
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard break;
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_POINT_TO_POINT:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* case MBA_DCBX_COMPLETED: */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8081)) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh DCBX completed received\n", mb[0]);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard } else {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh Point to Point Mode received\n", mb[0]);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags |= POINT_TO_POINT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard case MBA_FCF_CONFIG_ERROR:
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard EL(ha, "%xh FCF configuration Error received, mbx1=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[1]));
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard case MBA_DCBX_PARAM_CHANGED:
4f8b8adc54496e548e2d73094de038a131d9cd45Daniel Beauregard EL(ha, "%xh DCBX parameters changed received, mbx1=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_CHG_IN_CONNECTION:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (mb[1] == 2) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Change In Connection received, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx1=%xh\n", mb[0], mb[1]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->flags &= ~POINT_TO_POINT;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->topology & QL_N_PORT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->topology = (uint8_t)(ha->topology &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ~QL_N_PORT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->topology = (uint8_t)(ha->topology |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_NL_PORT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Change In Connection received, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "mbx1=%xh, isp_abort_needed\n", mb[0], mb[1]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_ZIO_UPDATE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh ZIO response received\n", mb[0]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->isp_rsp_index = RD16_IO_REG(ha, resp_in);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_response_pkt(ha, done_q, set_flags, reset_flags, intr_clr);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte intr = B_FALSE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_PORT_BYPASS_CHANGED:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Port Bypass Changed received, mbx1=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Event generated when there is a transition on
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * port bypass of crystal+.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Mailbox 1: Bit 0 - External.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Bit 2 - Internal.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * When the bit is 0, the port is bypassed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * For now we will generate a LIP for all cases.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= HANDLE_PORT_BYPASS_CHANGE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_RECEIVE_ERROR:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh Receive Error received, mbx1=%xh, mbx2=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_LS_RJT_SENT:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh LS_RJT Response Sent ELS=%xh\n", mb[0],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MBA_FW_RESTART_COMP:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh firmware restart complete received mb1=%xh\n",
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard mb[0], RD16_IO_REG(ha, mailbox_out[1]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard /*
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard * MBA_IDC_COMPLETE & MBA_IDC_NOTIFICATION: We won't get another
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard * IDC async event until we ACK the current one.
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard case MBA_IDC_COMPLETE:
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[0] = mb[0];
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[3] = RD16_IO_REG(ha, mailbox_out[3]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[4] = RD16_IO_REG(ha, mailbox_out[4]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[5] = RD16_IO_REG(ha, mailbox_out[5]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[6] = RD16_IO_REG(ha, mailbox_out[6]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[7] = RD16_IO_REG(ha, mailbox_out[7]);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh Inter-driver communication complete received, "
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard " mbx1=%xh, mbx2=%xh, mbx3=%xh, mbx4=%xh, mbx5=%xh,"
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard " mbx6=%xh, mbx7=%xh\n", mb[0], ha->idc_mb[1],
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[2], ha->idc_mb[3], ha->idc_mb[4], ha->idc_mb[5],
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[6], ha->idc_mb[7]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard *set_flags |= IDC_EVENT;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard case MBA_IDC_NOTIFICATION:
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->idc_mb[0] = mb[0];
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[1] = RD16_IO_REG(ha, mailbox_out[1]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[2] = RD16_IO_REG(ha, mailbox_out[2]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[3] = RD16_IO_REG(ha, mailbox_out[3]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[4] = RD16_IO_REG(ha, mailbox_out[4]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[5] = RD16_IO_REG(ha, mailbox_out[5]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[6] = RD16_IO_REG(ha, mailbox_out[6]);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ha->idc_mb[7] = RD16_IO_REG(ha, mailbox_out[7]);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh Inter-driver communication request notification "
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard "received, mbx1=%xh, mbx2=%xh, mbx3=%xh, mbx4=%xh, "
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard "mbx5=%xh, mbx6=%xh, mbx7=%xh\n", mb[0], ha->idc_mb[1],
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->idc_mb[2], ha->idc_mb[3], ha->idc_mb[4], ha->idc_mb[5],
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->idc_mb[6], ha->idc_mb[7]);
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard *set_flags |= IDC_EVENT;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard case MBA_IDC_TIME_EXTENDED:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "%xh Inter-driver communication time extended received,"
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard " mbx1=%xh, mbx2=%xh\n", mb[0],
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]));
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "%xh UNKNOWN event received, mbx1=%xh, mbx2=%xh, "
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard "mbx3=%xh\n", mb[0], RD16_IO_REG(ha, mailbox_out[1]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[2]),
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard RD16_IO_REG(ha, mailbox_out[3]));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr && intr_clr) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_fast_fcp_post
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Fast path for good SCSI I/O completion.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * sp: SRB pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_fast_fcp_post(ql_srb_t *sp)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_adapter_state_t *ha = sp->ha;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_lun_t *lq = sp->lun_queue;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq = lq->target_queue;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire device queue lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_LOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Decrement outstanding commands on device. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (tq->outcnt != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->outcnt--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->flags & SRB_FCP_CMD_PKT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->fcp->fcp_cntl.cntl_qtype == FCP_QTYPE_UNTAGGED) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Clear the flag for this LUN so that
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * untagged commands can be submitted
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * for it.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte lq->flags &= ~LQF_UNTAGGED_PENDING;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (lq->lun_outcnt != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte lq->lun_outcnt--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Reset port down retry count on good completion. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count = ha->port_down_retry_count;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->qfull_retry_count = ha->qfull_retry_count;
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard ha->pha->timeout_cnt = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Remove command from watchdog queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->flags & SRB_WATCHDOG_ENABLED) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_remove_link(&tq->wdg, &sp->wdg);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags &= ~SRB_WATCHDOG_ENABLED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (lq->cmd.first != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_next(ha, lq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release LU queue specific lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_UNLOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->pha->pending_cmds.first != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_start_iocb(ha, NULL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Sync buffers if required. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->flags & SRB_MS_PKT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ddi_dma_sync(sp->pkt->pkt_resp_dma, 0, 0,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DMA_SYNC_FORCPU);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Map ISP completion codes. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_expln = FC_EXPLN_NONE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_action = FC_ACTION_RETRYABLE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_state = FC_PKT_SUCCESS;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Now call the pkt completion callback */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->flags & SRB_POLL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags &= ~SRB_POLL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->pkt->pkt_comp) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte INTR_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (*sp->pkt->pkt_comp)(sp->pkt);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte INTR_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_response_pkt
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes response entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: head pointer to done queue.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * intr_clr: early interrupt clear
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_response_pkt(ql_adapter_state_t *ha, ql_head_t *done_q, uint32_t *set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *reset_flags, int intr_clr)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte response_t *pkt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t dma_sync_size_1 = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t dma_sync_size_2 = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int status = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Clear RISC interrupt */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (intr_clr) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_8021)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard ql_8021_clr_fw_intr(ha);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_242581)) {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT32_IO_REG(ha, hccr, HC24_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else {
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard WRT16_IO_REG(ha, hccr, HC_CLR_RISC_INT);
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->isp_rsp_index >= RESPONSE_ENTRY_CNT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "index error = %xh, isp_abort_needed",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->isp_rsp_index);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->flags & ONLINE) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): not onlne, done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Calculate size of response queue entries to sync. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->isp_rsp_index > ha->rsp_ring_index) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte dma_sync_size_1 = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ((uint32_t)(ha->isp_rsp_index - ha->rsp_ring_index) *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (ha->isp_rsp_index == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte dma_sync_size_1 = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ((uint32_t)(RESPONSE_ENTRY_CNT - ha->rsp_ring_index) *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Responses wrap around the Q */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte dma_sync_size_1 = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ((uint32_t)(RESPONSE_ENTRY_CNT - ha->rsp_ring_index) *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte dma_sync_size_2 = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ha->isp_rsp_index * RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Sync DMA buffer. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ddi_dma_sync(ha->hba_buf.dma_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (off_t)(ha->rsp_ring_index * RESPONSE_ENTRY_SIZE +
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_Q_BUFFER_OFFSET), dma_sync_size_1,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DMA_SYNC_FORKERNEL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (dma_sync_size_2) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (void) ddi_dma_sync(ha->hba_buf.dma_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_Q_BUFFER_OFFSET, dma_sync_size_2,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DMA_SYNC_FORKERNEL);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte while (ha->rsp_ring_index != ha->isp_rsp_index) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt = ha->response_ring_ptr;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_5(CE_CONT, "(%d): ha->rsp_rg_idx=%xh, mbx[5]=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance, ha->rsp_ring_index, ha->isp_rsp_index);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_DUMP_5((uint8_t *)ha->response_ring_ptr, 8,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Adjust ring index. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->rsp_ring_index++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->rsp_ring_index == RESPONSE_ENTRY_CNT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->rsp_ring_index = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->response_ring_ptr = ha->response_ring_bp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->response_ring_ptr++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Process packet. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->status_srb != NULL && pkt->entry_type !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte STATUS_CONT_TYPE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &ha->status_srb->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->status_srb = NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard pkt->entry_status = (uint8_t)(CFG_IST(ha, CFG_CTRL_24258081) ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->entry_status & 0x3c : pkt->entry_status & 0x7e);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (pkt->entry_status != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_error_entry(ha, pkt, done_q, set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (pkt->entry_type) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case STATUS_TYPE:
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard status |= CFG_IST(ha, CFG_CTRL_24258081) ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_24xx_status_entry(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts_24xx_entry_t *)pkt, done_q, set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags) :
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_status_entry(ha, (sts_entry_t *)pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte done_q, set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case STATUS_CONT_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_status_cont_entry(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts_cont_entry_t *)pkt, done_q, set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_A64_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_CMD_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ip_entry(ha, (ip_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_RECEIVE_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ip_rcv_entry(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ip_rcv_entry_t *)pkt, done_q, set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_RECEIVE_CONT_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ip_rcv_cont_entry(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ip_rcv_cont_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_24XX_RECEIVE_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ip_24xx_rcv_entry(ha,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (ip_rcv_24xx_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MS_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ms_entry(ha, (ms_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case REPORT_ID_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_report_id_entry(ha, (report_id_1_t *)pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte done_q, set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard case ELS_PASSTHRU_TYPE:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_els_passthru_entry(ha,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard (els_passthru_entry_rsp_t *)pkt,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard done_q, set_flags, reset_flags);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case IP_BUF_POOL_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case MARKER_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case VP_MODIFY_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case VP_CONTROL_TYPE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Unknown IOCB entry type=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->entry_type);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Inform RISC of processed responses. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte WRT16_IO_REG(ha, resp_out, ha->rsp_ring_index);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* RESET packet received delay for possible async event. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (status & BIT_0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte drv_usecwait(500000);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_error_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes error entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha = adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt = entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q = head pointer to done queue.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags = task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags = task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_error_entry(ql_adapter_state_t *ha, response_t *pkt, ql_head_t *done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (pkt->entry_type == INVALID_ENTRY_TYPE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Aborted command\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_2(CE_CONT, "(%d): started, packet:\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_DUMP_2((uint8_t *)pkt, 8, RESPONSE_ENTRY_SIZE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (pkt->entry_status & BIT_6) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Request Queue DMA error\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_5) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Invalid Entry Order\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_4) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Invalid Entry Count\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_3) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Invalid Entry Parameter\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_2) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Invalid Entry Type\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_1) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Busy\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "UNKNOWN flag = %xh error\n", pkt->entry_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &pkt->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, sp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&pkt->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Bad payload or header */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (pkt->entry_status & (BIT_5 + BIT_4 + BIT_3 + BIT_2)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Bad payload or header, set error status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_BAD_PAYLOAD;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (pkt->entry_status & BIT_1) /* FULL flag */ {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_QUEUE_FULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set error status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_UNKNOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Place command on done queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_status_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP2200-2300 status entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * BIT_0 = CS_RESET status received.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_status_entry(ql_adapter_state_t *ha, sts_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t comp_status;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int rval = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &pkt->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, sp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&pkt->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * We dont care about SCSI QFULLs.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (comp_status == CS_QUEUE_FULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "CS_QUEUE_FULL, d_id=%xh, lun=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->target_queue->d_id.b24,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * 2300 firmware marks completion status as data underrun
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * for scsi qfulls. Make it transport complete.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((CFG_IST(ha, (CFG_CTRL_2300 | CFG_CTRL_6322))) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (comp_status == CS_DATA_UNDERRUN) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (pkt->scsi_status_l != 0)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Workaround T3 issue where we do not get any data xferred
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * but get back a good status.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((pkt->state_flags_h & SF_XFERRED_DATA) == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status == CS_COMPLETE &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->scsi_status_l == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (pkt->scsi_status_h & FCP_RSP_MASK) == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->residual_length == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp->fcp_data_len != 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (pkt->state_flags_l & (SF_DATA_OUT | SF_DATA_IN)) ==
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte SF_DATA_OUT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_ABORTED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->flags & SRB_MS_PKT) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Ideally it should never be true. But there
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * is a bug in FW which upon receiving invalid
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * parameters in MS IOCB returns it as
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * status entry and not as ms entry type.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_ms_entry(ha, (ms_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): ql_ms_entry done\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Fast path to good SCSI I/O completion
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((comp_status == CS_COMPLETE) &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (!pkt->scsi_status_l) &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (!(pkt->scsi_status_h & FCP_RSP_MASK))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = comp_status;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_fast_fcp_post(sp);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): ql_fast_fcp_post done\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval = ql_status_error(ha, sp, pkt, done_q, set_flags,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte reset_flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (rval);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_24xx_status_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP24xx status entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * BIT_0 = CS_RESET status received.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_24xx_status_entry(ql_adapter_state_t *ha, sts_24xx_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_srb_t *sp = NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t comp_status;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int rval = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &pkt->handle);
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, sp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&pkt->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* We dont care about SCSI QFULLs. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (comp_status == CS_QUEUE_FULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "CS_QUEUE_FULL, d_id=%xh, lun=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->target_queue->d_id.b24,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * 2300 firmware marks completion status as data underrun
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * for scsi qfulls. Make it transport complete.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((comp_status == CS_DATA_UNDERRUN) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (pkt->scsi_status_l != 0)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Workaround T3 issue where we do not get any data xferred
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * but get back a good status.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (comp_status == CS_COMPLETE &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->scsi_status_l == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (pkt->scsi_status_h & FCP_RSP_MASK) == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->residual_length != 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp->fcp_data_len != 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp->fcp_cntl.cntl_write_data) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte comp_status = CS_ABORTED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Fast path to good SCSI I/O completion
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((comp_status == CS_COMPLETE) &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (!pkt->scsi_status_l) &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (!(pkt->scsi_status_h & FCP_RSP_MASK))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = comp_status;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_fast_fcp_post(sp);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): ql_fast_fcp_post done\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (0);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval = ql_status_error(ha, sp, (sts_entry_t *)pkt, done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard return (rval);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard/*
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * ql_verify_preprocessed_cmd
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Handles preprocessed cmds..
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Input:
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * ha: adapter state pointer.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * pkt_handle: handle pointer.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * set_flags: task daemon flags to set.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * reset_flags: task daemon flags to reset.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Returns:
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * srb pointer or NULL
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Context:
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Interrupt or Kernel context, no mailbox commands allowed.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard/* ARGSUSED */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardql_srb_t *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardql_verify_preprocessed_cmd(ql_adapter_state_t *ha, uint32_t *pkt_handle,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t *set_flags, uint32_t *reset_flags)
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard{
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_srb_t *sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t get_handle = 10;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard while (get_handle) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Get handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, pkt_handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
f33c1cdb6d38eb0715f03cf492f31c3d4d395c98Daniel Beauregard EL(ha, "sp=%xh, resp_id=%xh, get=%d, index=%xh\n", sp,
f33c1cdb6d38eb0715f03cf492f31c3d4d395c98Daniel Beauregard resp_identifier, get_handle, index);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard break;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard get_handle -= 1;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard drv_usecwait(10000);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (get_handle == 1) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Last chance, Sync whole DMA buffer. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (void) ddi_dma_sync(ha->hba_buf.dma_handle,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard RESPONSE_Q_BUFFER_OFFSET,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard RESPONSE_QUEUE_SIZE,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard DDI_DMA_SYNC_FORKERNEL);
f33c1cdb6d38eb0715f03cf492f31c3d4d395c98Daniel Beauregard EL(ha, "last chance DMA sync, index=%xh\n",
f33c1cdb6d38eb0715f03cf492f31c3d4d395c98Daniel Beauregard index);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard return (sp);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_status_error
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP status entry error.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * sp: SRB pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Returns:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * BIT_0 = CS_RESET status received.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic int
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_status_error(ql_adapter_state_t *ha, ql_srb_t *sp, sts_entry_t *pkt23,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t sense_sz = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcp_rsp_t *fcpr;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte struct fcp_rsp_info *rsp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte int rval = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte struct {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t *rsp_info;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t *req_sense_data;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t residual_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t fcp_residual_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t rsp_info_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t req_sense_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t comp_status;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t state_flags_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t state_flags_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t scsi_status_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t scsi_status_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } sts;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_24258081)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts_24xx_entry_t *pkt24 = (sts_24xx_entry_t *)pkt23;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt24->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_l = pkt24->scsi_status_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_h = pkt24->scsi_status_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup firmware residuals. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.residual_length = sts.comp_status == CS_DATA_UNDERRUN ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t *)&pkt24->residual_length) : 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup FCP residuals. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.fcp_residual_length = sts.scsi_status_h &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (FCP_RESID_UNDER | FCP_RESID_OVER) ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t *)&pkt24->fcp_rsp_residual_count) : 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sts.comp_status == CS_DATA_UNDERRUN) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.scsi_status_h & FCP_RESID_UNDER) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.residual_length != pkt24->fcp_rsp_residual_count)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "mismatch resid's: fw=%xh, pkt=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.residual_length,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt24->fcp_rsp_residual_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_h = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.scsi_status_h & ~FCP_RESID_UNDER);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup state flags. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = pkt24->state_flags_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_h = pkt24->state_flags_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->fcp->fcp_data_len &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status != CS_DATA_UNDERRUN ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.residual_length != sp->fcp->fcp_data_len)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_h = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_h | SF_GOT_BUS |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte SF_GOT_TARGET | SF_SENT_CMD |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte SF_XFERRED_DATA | SF_GOT_STATUS);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_h = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_h | SF_GOT_BUS |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte SF_GOT_TARGET | SF_SENT_CMD |
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte SF_GOT_STATUS);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->fcp->fcp_cntl.cntl_write_data) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_l | SF_DATA_OUT);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->fcp->fcp_cntl.cntl_read_data) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_l | SF_DATA_IN);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->fcp->fcp_cntl.cntl_qtype == FCP_QTYPE_HEAD_OF_Q) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_l | SF_HEAD_OF_Q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->fcp->fcp_cntl.cntl_qtype == FCP_QTYPE_ORDERED) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_l | SF_ORDERED_Q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->fcp->fcp_cntl.cntl_qtype == FCP_QTYPE_SIMPLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_l | SF_SIMPLE_Q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup FCP response info. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info = &pkt24->rsp_sense_data[0];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sts.scsi_status_h & FCP_RSP_LEN_VALID) != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length = ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t *)&pkt24->fcp_rsp_data_length);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.rsp_info_length >
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (struct fcp_rsp_info)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (struct fcp_rsp_info);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 0; cnt < sts.rsp_info_length; cnt += 4) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_chg_endian(sts.rsp_info + cnt, 4);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup sense data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt24->rsp_sense_data[sts.rsp_info_length];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_SNS_LEN_VALID) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_length =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t *)&pkt24->fcp_sense_length);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_h = (uint8_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.state_flags_h | SF_ARQ_DONE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (((uintptr_t)pkt24 + sizeof (sts_24xx_entry_t)) -
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uintptr_t)sts.req_sense_data);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 0; cnt < sense_sz; cnt += 4) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_chg_endian(sts.req_sense_data + cnt, 4);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_length = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status = (uint16_t)ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt23->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_l = pkt23->scsi_status_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_h = pkt23->scsi_status_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup firmware residuals. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.residual_length = sts.comp_status == CS_DATA_UNDERRUN ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t *)&pkt23->residual_length) : 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup FCP residuals. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.fcp_residual_length = sts.scsi_status_h &
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (FCP_RESID_UNDER | FCP_RESID_OVER) ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.residual_length : 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup state flags. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_l = pkt23->state_flags_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.state_flags_h = pkt23->state_flags_h;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup FCP response info. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info = &pkt23->rsp_info[0];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sts.scsi_status_h & FCP_RSP_LEN_VALID) != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length = ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint16_t *)&pkt23->rsp_info_length);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.rsp_info_length >
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (struct fcp_rsp_info)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (struct fcp_rsp_info);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info_length = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Setup sense data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data = &pkt23->req_sense_data[0];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_length = sts.scsi_status_h & FCP_SNS_LEN_VALID ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint16_t *)&pkt23->req_sense_length) : 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte bzero(sp->pkt->pkt_resp, sp->pkt->pkt_rsplen);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr = (fcp_rsp_t *)sp->pkt->pkt_resp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rsp = (struct fcp_rsp_info *)(sp->pkt->pkt_resp +
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (fcp_rsp_t));
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq = sp->lun_queue->target_queue;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.scsi_status = sts.scsi_status_l;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_RSP_LEN_VALID) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.rsp_len_set = 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_SNS_LEN_VALID) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.sense_len_set = 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_RESID_OVER) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.resid_over = 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_RESID_UNDER) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.resid_under = 1;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_u.fcp_status.reserved_1 = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set ISP completion status */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = sts.comp_status;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Update statistics. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sts.scsi_status_h & FCP_RSP_LEN_VALID) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sp->pkt->pkt_rsplen > sizeof (fcp_rsp_t))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = sp->pkt->pkt_rsplen - (uint32_t)sizeof (fcp_rsp_t);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sense_sz > sts.rsp_info_length) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = sts.rsp_info_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* copy response information data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sense_sz) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_rep_get8(ha->hba_buf.acc_handle, (uint8_t *)rsp,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.rsp_info, sense_sz, DDI_DEV_AUTOINCR);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_response_len = sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rsp = (struct fcp_rsp_info *)((caddr_t)rsp +
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_response_len);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte switch (*(sts.rsp_info + 3)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_NO_FAILURE:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_DL_LEN_MISMATCH:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->adapter_stats->d_stats[lobyte(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->loop_id)].dl_len_mismatches++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_CMND_INVALID:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_DATA_RO_MISMATCH:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->adapter_stats->d_stats[lobyte(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->loop_id)].data_ro_mismatches++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_TASK_MGMT_NOT_SUPPTD:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte case FCP_TASK_MGMT_FAILED:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->adapter_stats->d_stats[lobyte(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->loop_id)].task_mgmt_failures++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * EL(sp->ha, "scsi_h=%xh, pkt_rsplen=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * sts.scsi_status_h, sp->pkt->pkt_rsplen);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_response_len = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set reset status received. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.comp_status == CS_RESET && LOOP_READY(ha)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rval |= BIT_0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(tq->flags & TQF_TAPE_DEVICE) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (!(CFG_IST(ha, CFG_ENABLE_LINK_DOWN_REPORTING)) ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->loop_down_abort_time < LOOP_DOWN_TIMER_START) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->task_daemon_flags & LOOP_DOWN) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Loop Not Ready Retry, d_id=%xh, lun=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->d_id.b24, sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (!(tq->flags & TQF_TAPE_DEVICE) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count != 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status == CS_INCOMPLETE ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status == CS_PORT_UNAVAILABLE ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status == CS_PORT_LOGGED_OUT ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status == CS_PORT_CONFIG_CHG ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status == CS_PORT_BUSY)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Port Down Retry=%xh, d_id=%xh, lun=%xh, count=%d"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "\n", sts.comp_status, tq->d_id.b24, sp->lun_queue->lun_no,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq->flags & TQF_QUEUE_SUSPENDED) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire device queue lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_LOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->flags |= TQF_QUEUE_SUSPENDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Decrement port down count. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (CFG_IST(ha, CFG_ENABLE_LINK_DOWN_REPORTING)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_UNLOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->task_daemon_flags & ABORT_ISP_ACTIVE)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte == 0 &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status == CS_PORT_LOGGED_OUT ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.comp_status == CS_PORT_UNAVAILABLE)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->ha->adapter_stats->d_stats[lobyte(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->loop_id)].logouts_recvd++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_send_logo(sp->ha, tq, done_q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->port_retry_timer == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->port_retry_timer =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->port_down_retry_delay) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte PORT_RETRY_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (!(tq->flags & TQF_TAPE_DEVICE) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status == CS_RESET ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status == CS_QUEUE_FULL && tq->qfull_retry_count != 0) ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.comp_status == CS_ABORTED && !(sp->flags & SRB_ABORTING)))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.comp_status == CS_RESET) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Reset Retry, d_id=%xh, lun=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->d_id.b24, sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sts.comp_status == CS_QUEUE_FULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Queue Full Retry, d_id=%xh, lun=%xh, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "cnt=%d\n", tq->d_id.b24, sp->lun_queue->lun_no,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->qfull_retry_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq->flags & TQF_QUEUE_SUSPENDED) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->flags |= TQF_QUEUE_SUSPENDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->qfull_retry_count--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->port_retry_timer == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->port_retry_timer =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->qfull_retry_delay) ==
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte PORT_RETRY_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Abort Retry, d_id=%xh, lun=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->d_id.b24, sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_resid =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.fcp_residual_length > sp->fcp->fcp_data_len ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->fcp->fcp_data_len : sts.fcp_residual_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sts.comp_status == CS_DATA_UNDERRUN) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.scsi_status_h & FCP_RESID_UNDER) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_l == STATUS_CHECK) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "transport error - "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "underrun & invalid resid\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ssh=%xh, ssl=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_h, sts.scsi_status_l);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_FCP_RESPONSE_ERROR;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Ignore firmware underrun error. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.comp_status == CS_DATA_UNDERRUN &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.scsi_status_h & FCP_RESID_UNDER ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sts.scsi_status_l != STATUS_CHECK &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.scsi_status_l != STATUS_GOOD))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason != CS_COMPLETE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->DeviceErrorCount++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "Cmplt status err = %xh, d_id=%xh, lun=%xh"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "\n", sts.comp_status, tq->d_id.b24,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set target request sense data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_l == STATUS_CHECK) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sts.scsi_status_h & FCP_SNS_LEN_VALID) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason == CS_COMPLETE &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[2] != KEY_NO_SENSE &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[2] !=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte KEY_UNIT_ATTENTION) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->xioctl->DeviceErrorCount++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = sts.req_sense_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Insure data does not exceed buf. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_rsplen <=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint32_t)sizeof (fcp_rsp_t) +
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_response_len) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sp->pkt->pkt_rsplen -
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (fcp_rsp_t) -
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_response_len);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sense_sz <
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_ptr = (caddr_t)rsp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = (uint32_t)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (((uintptr_t)pkt23 +
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sizeof (sts_entry_t)) -
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uintptr_t)sts.req_sense_data);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->request_sense_length <
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fcpr->fcp_sense_len = sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Move sense data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_rep_get8(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint8_t *)sp->request_sense_ptr,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (size_t)sense_sz,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DEV_AUTOINCR);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_ptr += sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length -= sense_sz;
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (sp->request_sense_length != 0 &&
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard !(CFG_IST(ha, CFG_CTRL_8021))) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->status_srb = sp;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sense_sz != 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "check condition sense data, "
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "d_id=%xh, lun=%xh\n%2xh%3xh%3xh%3xh"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "%3xh%3xh%3xh%3xh%3xh%3xh%3xh%3xh%3xh"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "%3xh%3xh%3xh%3xh%3xh\n", tq->d_id.b24,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->lun_queue->lun_no,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[0],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[1],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[2],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[3],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[4],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[5],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[6],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[7],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[8],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[9],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[10],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[11],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[12],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[13],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[14],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[15],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[16],
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sts.req_sense_data[17]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(sp->ha, "check condition, d_id=%xh, lun=%xh"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte "\n", tq->d_id.b24, sp->lun_queue->lun_no);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Place command on done queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->status_srb == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return (rval);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_status_cont_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes status continuation entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_status_cont_entry(ql_adapter_state_t *ha, sts_cont_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t sense_sz, index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp = ha->status_srb;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp != NULL && sp->request_sense_length) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->request_sense_length > sizeof (pkt->req_sense_data)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = sizeof (pkt->req_sense_data);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sense_sz = sp->request_sense_length;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_24258081)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (index = 0; index < sense_sz; index += 4) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_chg_endian((uint8_t *)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->req_sense_data[0] + index, 4);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Move sense data. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ddi_rep_get8(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint8_t *)sp->request_sense_ptr,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (uint8_t *)&pkt->req_sense_data[0], (size_t)sense_sz,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DDI_DEV_AUTOINCR);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_ptr += sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->request_sense_length -= sense_sz;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Place command on done queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->request_sense_length == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->status_srb = NULL;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_ip_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP IP entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_ip_entry(ql_adapter_state_t *ha, ip_entry_t *pkt23, ql_head_t *done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &pkt23->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, sp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&pkt23->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq = sp->lun_queue->target_queue;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set ISP completion status */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_24258081)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ip_cmd_entry_t *pkt24 = (ip_cmd_entry_t *)pkt23;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt24->hdl_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt23->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->task_daemon_flags & LOOP_DOWN) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Loop Not Ready Retry, d_id=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->d_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (tq->port_down_retry_count &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sp->pkt->pkt_reason == CS_INCOMPLETE ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_UNAVAILABLE ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_LOGGED_OUT ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_CONFIG_CHG ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_BUSY)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Port Down Retry=%xh, d_id=%xh, count=%d\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason, tq->d_id.b24,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason == CS_PORT_LOGGED_OUT ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_UNAVAILABLE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->adapter_stats->d_stats[lobyte(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->loop_id)].logouts_recvd++;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_send_logo(ha, tq, done_q);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire device queue lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_LOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq->flags & TQF_QUEUE_SUSPENDED) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->flags |= TQF_QUEUE_SUSPENDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->port_retry_timer == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->port_retry_timer =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->port_down_retry_delay) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte PORT_RETRY_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release device queue specific lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_UNLOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->pkt->pkt_reason == CS_RESET) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Reset Retry, d_id=%xh\n", tq->d_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason != CS_COMPLETE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Cmplt status err=%xh, d_id=%xh\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason, tq->d_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_ip_rcv_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP IP buffers entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_ip_rcv_entry(ql_adapter_state_t *ha, ip_rcv_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte port_id_t s_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate device queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.al_pa = pkt->s_id[0];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.area = pkt->s_id[1];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.domain = pkt->s_id[2];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq = ql_d_id_to_queue(ha, s_id)) == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Unknown IP device ID=%xh\n", s_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_sequence_length = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->seq_length);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt = pkt->segment_count;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_id = ++ha->ub_seq_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_cnt = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_frame_ro = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_loop_id = pkt->loop_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->rcv_dev_q = tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 0; cnt < IP_RCVBUF_HANDLES && tq->ub_seq_cnt <
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt; cnt++) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->buffer_handle[cnt]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ql_ub_frame_hdr(ha, tq, index, done_q) != QL_SUCCESS) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ql_ub_frame_hdr failed, isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_ip_rcv_cont_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP IP buffers continuation entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_ip_rcv_cont_entry(ql_adapter_state_t *ha, ip_rcv_cont_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq = ha->rcv_dev_q) == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "No IP receive device\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 0; cnt < IP_RCVBUF_CONT_HANDLES &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_cnt < tq->ub_total_seg_cnt; cnt++) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->buffer_handle[cnt]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ql_ub_frame_hdr(ha, tq, index, done_q) != QL_SUCCESS) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ql_ub_frame_hdr failed, isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ip_rcv_24xx_entry_t
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received ISP24xx IP buffers entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_ip_24xx_rcv_entry(ql_adapter_state_t *ha, ip_rcv_24xx_entry_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte port_id_t s_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint16_t index;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint8_t cnt;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate device queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.al_pa = pkt->s_id[0];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.area = pkt->s_id[1];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte s_id.b.domain = pkt->s_id[2];
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq = ql_d_id_to_queue(ha, s_id)) == NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Unknown IP device ID=%xh\n", s_id.b24);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (tq->ub_total_seg_cnt == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_sequence_length = (uint16_t)ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt->seq_length);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt = pkt->segment_count;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_id = ++ha->ub_seq_id;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_seq_cnt = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_frame_ro = 0;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_loop_id = (uint16_t)ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt->n_port_hdl);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (cnt = 0; cnt < IP_24XX_RCVBUF_HANDLES && tq->ub_seq_cnt <
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->ub_total_seg_cnt; cnt++) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte index = (uint16_t)ddi_get16(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt->buffer_handle[cnt]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ql_ub_frame_hdr(ha, tq, index, done_q) != QL_SUCCESS) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "ql_ub_frame_hdr failed, isp_abort_needed\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_ms_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received Name/Management/CT Pass-Through entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * pkt23: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_ms_entry(ql_adapter_state_t *ha, ms_entry_t *pkt23, ql_head_t *done_q,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_srb_t *sp;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, cnt, resp_identifier;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_tgt_t *tq;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ct_passthru_entry_t *pkt24 = (ct_passthru_entry_t *)pkt23;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &pkt23->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, sp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard sp = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&pkt23->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (sp != NULL) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(sp->flags & SRB_MS_PKT)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Not SRB_MS_PKT flags=%xh, isp_abort_needed",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= ISP_ABORT_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte return;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq = sp->lun_queue->target_queue;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set ISP completion status */
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_24258081)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt24->status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = ddi_get16(
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->hba_buf.acc_handle, &pkt23->comp_status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason == CS_RESOUCE_UNAVAILABLE &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->retry_count) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Resouce Unavailable Retry = %d\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->retry_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->retry_count--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire device queue lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_LOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (!(tq->flags & TQF_QUEUE_SUSPENDED)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->flags |= TQF_QUEUE_SUSPENDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->port_retry_timer == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->port_retry_timer = 2;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release device queue specific lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_UNLOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (tq->port_down_retry_count &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte (sp->pkt->pkt_reason == CS_PORT_CONFIG_CHG ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_PORT_BUSY)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Port Down Retry\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Acquire device queue lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_LOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((tq->flags & TQF_QUEUE_SUSPENDED) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->flags |= TQF_QUEUE_SUSPENDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->port_down_retry_count--;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (ha->port_retry_timer == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((ha->port_retry_timer =
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ha->port_down_retry_delay) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |=
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte PORT_RETRY_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ADAPTER_STATE_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Release device queue specific lock. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte DEVICE_QUEUE_UNLOCK(tq);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->pkt->pkt_reason == CS_RESET) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "Reset Retry\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set retry status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_RETRY;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard } else if (CFG_IST(ha, CFG_CTRL_24258081) &&
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason == CS_DATA_UNDERRUN) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte cnt = ddi_get32(ha->hba_buf.acc_handle,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte &pkt24->resp_byte_count);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (cnt < sizeof (fc_ct_header_t)) {
16dd44c265271a75647fb0bb41109bb7c585a526Daniel Beauregard EL(ha, "Data underrun\n");
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_reason = CS_COMPLETE;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte } else if (sp->pkt->pkt_reason != CS_COMPLETE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "status err=%xh\n", sp->pkt->pkt_reason);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (sp->pkt->pkt_reason == CS_COMPLETE) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /*EMPTY*/
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard QL_PRINT_3(CE_CONT, "(%d): ct_cmdrsp=%x%02xh resp\n",
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->instance, sp->pkt->pkt_cmd[8],
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard sp->pkt->pkt_cmd[9]);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_DUMP_3(sp->pkt->pkt_resp, 8, sp->pkt->pkt_rsplen);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* For nameserver restore command, management change header. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if ((sp->flags & SRB_RETRY) == 0) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte tq->d_id.b24 == 0xfffffc ?
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_cthdr_endian(sp->pkt->pkt_cmd_acc,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_cmd, B_TRUE) :
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_cthdr_endian(sp->pkt->pkt_resp_acc,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->pkt->pkt_resp, B_TRUE);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Set completed status. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sp->flags |= SRB_ISP_COMPLETED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Place command on done queue. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_add_link_b(done_q, &sp->cmd);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ql_report_id_entry
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Processes received Name/Management/CT Pass-Through entry.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Input:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * ha: adapter state pointer.
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard * pkt: entry pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * done_q: done queue pointer.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * set_flags: task daemon flags to set.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * reset_flags: task daemon flags to reset.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Context:
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte * Interrupt or Kernel context, no mailbox commands allowed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte/* ARGSUSED */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortestatic void
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteql_report_id_entry(ql_adapter_state_t *ha, report_id_1_t *pkt,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte{
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ql_adapter_state_t *vha;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte EL(ha, "format=%d, vp=%d, status=%d\n",
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->format, pkt->vp_index, pkt->status);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (pkt->format == 1) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte /* Locate port state structure. */
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte for (vha = ha; vha != NULL; vha = vha->vp_next) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if (vha->vp_index == pkt->vp_index) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte break;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (vha != NULL && vha->vp_index != 0 &&
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard (pkt->status == CS_COMPLETE ||
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkt->status == CS_PORT_ID_CHANGE)) {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *set_flags |= LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte *reset_flags &= ~LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->loop_down_timer = LOOP_DOWN_TIMER_OFF;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_LOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->task_daemon_flags |= LOOP_RESYNC_NEEDED;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte vha->task_daemon_flags &= ~LOOP_DOWN;
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte TASK_DAEMON_UNLOCK(ha);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard/*
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * ql_els_entry
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * Processes received ELS Pass-Through entry.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard *
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * Input:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * ha: adapter state pointer.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * pkt23: entry pointer.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * done_q: done queue pointer.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * set_flags: task daemon flags to set.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * reset_flags: task daemon flags to reset.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard *
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * Context:
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard * Interrupt or Kernel context, no mailbox commands allowed.
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard/* ARGSUSED */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregardstatic void
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregardql_els_passthru_entry(ql_adapter_state_t *ha, els_passthru_entry_rsp_t *rsp,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_head_t *done_q, uint32_t *set_flags, uint32_t *reset_flags)
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard{
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_tgt_t *tq;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard port_id_t d_id, s_id;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_srb_t *srb;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard uint32_t index, resp_identifier;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard QL_PRINT_3(CE_CONT, "(%d): started\n", ha->instance);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Validate the response entry handle. */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier = ddi_get32(ha->hba_buf.acc_handle, &rsp->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index = resp_identifier & OSC_INDEX_MASK;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (index < MAX_OUTSTANDING_COMMANDS) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* the index seems reasonable */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard srb = ha->outstanding_cmds[index];
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (srb != NULL) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (srb->handle == resp_identifier) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard /* Neo, you're the one... */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ha->outstanding_cmds[index] = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard srb->handle = 0;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard srb->flags &= ~SRB_IN_TOKEN_ARRAY;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "IOCB handle mismatch pkt=%xh, sp=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard resp_identifier, srb->handle);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard srb = NULL;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard srb = ql_verify_preprocessed_cmd(ha,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (uint32_t *)&rsp->handle, set_flags, reset_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard } else {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard EL(ha, "osc index out of range, index=%xh, handle=%xh\n",
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard index, resp_identifier);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard ql_signal_abort(ha, set_flags);
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard if (srb != NULL) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (!(srb->flags & SRB_ELS_PKT)) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "Not SRB_ELS_PKT flags=%xh, isp_abort_needed",
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->flags);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard *set_flags |= ISP_ABORT_NEEDED;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard return;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard (void) ddi_dma_sync(srb->pkt->pkt_resp_dma, 0, 0,
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard DDI_DMA_SYNC_FORKERNEL);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* Set ISP completion status */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->pkt->pkt_reason = ddi_get16(
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->hba_buf.acc_handle, &rsp->comp_status);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (srb->pkt->pkt_reason != CS_COMPLETE) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard la_els_rjt_t rjt;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "status err=%xh\n", srb->pkt->pkt_reason);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (srb->pkt->pkt_reason == CS_LOGIN_LOGOUT_ERROR) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "e1=%xh e2=%xh\n",
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard rsp->error_subcode1, rsp->error_subcode2);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->pkt->pkt_state = FC_PKT_TRAN_ERROR;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* Build RJT in the response. */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard rjt.ls_code.ls_code = LA_ELS_RJT;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard rjt.reason = FC_REASON_NO_CONNECTION;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ddi_rep_put8(srb->pkt->pkt_resp_acc, (uint8_t *)&rjt,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard (uint8_t *)srb->pkt->pkt_resp,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard sizeof (rjt), DDI_DEV_AUTOINCR);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->pkt->pkt_state = FC_PKT_TRAN_ERROR;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->pkt->pkt_reason = FC_REASON_NO_CONNECTION;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (srb->pkt->pkt_reason == CS_COMPLETE) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard uint8_t opcode;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard uint16_t loop_id;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* Indicate ISP completion */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->flags |= SRB_ISP_COMPLETED;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard loop_id = ddi_get16(ha->hba_buf.acc_handle,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard &rsp->n_port_hdl);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (ha->topology & QL_N_PORT) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* create a target Q if there isn't one */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard tq = ql_loop_id_to_queue(ha, loop_id);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (tq == NULL) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard d_id.b.al_pa = rsp->d_id_7_0;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard d_id.b.area = rsp->d_id_15_8;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard d_id.b.domain = rsp->d_id_23_16;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* Acquire adapter state lock. */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ADAPTER_STATE_LOCK(ha);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard tq = ql_dev_init(ha, d_id, loop_id);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, " tq = %x\n", tq);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ADAPTER_STATE_UNLOCK(ha);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* on plogi success assume the chosen s_id */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard opcode = ddi_get8(ha->hba_buf.acc_handle,
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard &rsp->els_cmd_opcode);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "els_cmd_opcode=%x srb->pkt=%x\n",
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard opcode, srb->pkt);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (opcode == LA_ELS_PLOGI) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard s_id.b.al_pa = rsp->s_id_7_0;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard s_id.b.area = rsp->s_id_15_8;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard s_id.b.domain = rsp->s_id_23_16;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->d_id.b24 = s_id.b24;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "Set port's source ID %xh\n",
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ha->d_id.b24);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_isp_els_handle_rsp_endian(ha, srb);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (ha != srb->ha) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard EL(ha, "ha=%x srb->ha=%x\n", ha, srb->ha);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard if (tq != NULL) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard tq->logout_sent = 0;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard tq->flags &= ~TQF_NEED_AUTHENTICATION;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard
eb82ff87b34e625264561b2d267577cf9821dab0Daniel Beauregard if (CFG_IST(ha, CFG_CTRL_24258081)) {
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard tq->flags |= TQF_IIDMA_NEEDED;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard srb->pkt->pkt_state = FC_PKT_SUCCESS;
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard /* invoke the callback */
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard ql_awaken_task_daemon(ha, srb, 0, 0);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard }
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard QL_PRINT_3(CE_CONT, "(%d): done\n", ha->instance);
5dfd244acc8f144280c5bc8f69ed941185fc3cccDaniel Beauregard}
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard/*
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * ql_signal_abort
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Signal to the task daemon that a condition warranting an
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * isp reset has been detected.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Input:
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * ha: adapter state pointer.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * set_flags: task daemon flags to set.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Context:
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard * Interrupt or Kernel context, no mailbox commands allowed.
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard */
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardstatic void
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregardql_signal_abort(ql_adapter_state_t *ha, uint32_t *set_flags)
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard{
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard if (!CFG_IST(ha, CFG_CTRL_8021) &&
f885d00f4e3c96a769ce0228a732da31ad9d0b78Daniel Beauregard !(ha->task_daemon_flags & (ISP_ABORT_NEEDED | ABORT_ISP_ACTIVE))) {
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard *set_flags |= ISP_ABORT_NEEDED;
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard }
a2b3ff35eb5d7a6132b779a25b318545dae47cefDaniel Beauregard}