[SCSI] bfa: Fabric Assigned Address implementation fix
authorKrishna Gudipati <kgudipat@brocade.com>
Sat, 22 Sep 2012 00:26:18 +0000 (17:26 -0700)
committerJames Bottomley <JBottomley@Parallels.com>
Sun, 7 Oct 2012 10:18:29 +0000 (11:18 +0100)
- Made changes such that once the PWWN is acquired from the fabric through FAA,
  and if the FAPWWN configuration is modified on the switch side, driver should
  show relevant information to the user.
- Added logic to cache the reason code when the given port is disabled implicitl
  due to FAA error condition.
- If the port is disabled, while sending SCN to upper layer, update the
  reason code appropriately. With this, BFA FC port state machine will enter
  into faa_err_config state. This state will be shown to the user.

Signed-off-by: Krishna Gudipati <kgudipat@brocade.com>
Signed-off-by: James Bottomley <JBottomley@Parallels.com>
drivers/scsi/bfa/bfa_defs_svc.h
drivers/scsi/bfa/bfa_svc.c

index 4533b28a6799930852bb4766a1cb8e41e9cf855f..76ea10d37ad700c32c913421d7770d34e3302754 100644 (file)
@@ -721,7 +721,7 @@ enum bfa_port_states {
        BFA_PORT_ST_FWMISMATCH          = 12,
        BFA_PORT_ST_PREBOOT_DISABLED    = 13,
        BFA_PORT_ST_TOGGLING_QWAIT      = 14,
-       BFA_PORT_ST_ACQ_ADDR            = 15,
+       BFA_PORT_ST_FAA_MISCONFIG       = 15,
        BFA_PORT_ST_DPORT               = 16,
        BFA_PORT_ST_MAX_STATE,
 };
@@ -792,6 +792,7 @@ enum bfa_port_linkstate_rsn {
        BFA_PORT_LINKSTATE_RSN_LOCAL_FAULT      = 9,
        BFA_PORT_LINKSTATE_RSN_REMOTE_FAULT     = 10,
        BFA_PORT_LINKSTATE_RSN_TIMEOUT          = 11,
+       BFA_PORT_LINKSTATE_RSN_FAA_MISCONFIG    = 12,
 
 
 
index 549bd45a7dbedf9aaccff5067e9bd44f29660d42..309ab2ad3ce95bdeba02930338e5cf9048e0464e 100644 (file)
@@ -69,6 +69,7 @@ enum bfa_fcport_sm_event {
        BFA_FCPORT_SM_HWFAIL    = 9,    /*  IOC h/w failure             */
        BFA_FCPORT_SM_DPORTENABLE = 10, /*  enable dport      */
        BFA_FCPORT_SM_DPORTDISABLE = 11,/*  disable dport     */
+       BFA_FCPORT_SM_FAA_MISCONFIG = 12,       /* FAA misconfiguratin */
 };
 
 /*
@@ -201,6 +202,8 @@ static void     bfa_fcport_sm_iocfail(struct bfa_fcport_s *fcport,
                                        enum bfa_fcport_sm_event event);
 static void    bfa_fcport_sm_dport(struct bfa_fcport_s *fcport,
                                        enum bfa_fcport_sm_event event);
+static void    bfa_fcport_sm_faa_misconfig(struct bfa_fcport_s *fcport,
+                                       enum bfa_fcport_sm_event event);
 
 static void     bfa_fcport_ln_sm_dn(struct bfa_fcport_ln_s *ln,
                                        enum bfa_fcport_ln_sm_event event);
@@ -231,6 +234,7 @@ static struct bfa_sm_table_s hal_port_sm_table[] = {
        {BFA_SM(bfa_fcport_sm_iocdown), BFA_PORT_ST_IOCDOWN},
        {BFA_SM(bfa_fcport_sm_iocfail), BFA_PORT_ST_IOCDOWN},
        {BFA_SM(bfa_fcport_sm_dport), BFA_PORT_ST_DPORT},
+       {BFA_SM(bfa_fcport_sm_faa_misconfig), BFA_PORT_ST_FAA_MISCONFIG},
 };
 
 
@@ -2180,6 +2184,12 @@ bfa_fcport_sm_enabling_qwait(struct bfa_fcport_s *fcport,
                bfa_sm_set_state(fcport, bfa_fcport_sm_iocdown);
                break;
 
+       case BFA_FCPORT_SM_FAA_MISCONFIG:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISCONNECT);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_faa_misconfig);
+               break;
+
        default:
                bfa_sm_fault(fcport->bfa, event);
        }
@@ -2236,6 +2246,12 @@ bfa_fcport_sm_enabling(struct bfa_fcport_s *fcport,
                bfa_sm_set_state(fcport, bfa_fcport_sm_iocdown);
                break;
 
+       case BFA_FCPORT_SM_FAA_MISCONFIG:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISCONNECT);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_faa_misconfig);
+               break;
+
        default:
                bfa_sm_fault(fcport->bfa, event);
        }
@@ -2322,6 +2338,12 @@ bfa_fcport_sm_linkdown(struct bfa_fcport_s *fcport,
                bfa_sm_set_state(fcport, bfa_fcport_sm_iocdown);
                break;
 
+       case BFA_FCPORT_SM_FAA_MISCONFIG:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISCONNECT);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_faa_misconfig);
+               break;
+
        default:
                bfa_sm_fault(fcport->bfa, event);
        }
@@ -2415,6 +2437,12 @@ bfa_fcport_sm_linkup(struct bfa_fcport_s *fcport,
                }
                break;
 
+       case BFA_FCPORT_SM_FAA_MISCONFIG:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISCONNECT);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_faa_misconfig);
+               break;
+
        default:
                bfa_sm_fault(fcport->bfa, event);
        }
@@ -2460,6 +2488,12 @@ bfa_fcport_sm_disabling_qwait(struct bfa_fcport_s *fcport,
                bfa_reqq_wcancel(&fcport->reqq_wait);
                break;
 
+       case BFA_FCPORT_SM_FAA_MISCONFIG:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISCONNECT);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_faa_misconfig);
+               break;
+
        default:
                bfa_sm_fault(fcport->bfa, event);
        }
@@ -2727,6 +2761,49 @@ bfa_fcport_sm_dport(struct bfa_fcport_s *fcport, enum bfa_fcport_sm_event event)
        }
 }
 
+static void
+bfa_fcport_sm_faa_misconfig(struct bfa_fcport_s *fcport,
+                           enum bfa_fcport_sm_event event)
+{
+       bfa_trc(fcport->bfa, event);
+
+       switch (event) {
+       case BFA_FCPORT_SM_DPORTENABLE:
+       case BFA_FCPORT_SM_ENABLE:
+       case BFA_FCPORT_SM_START:
+               /*
+                * Ignore event for a port as there is FAA misconfig
+                */
+               break;
+
+       case BFA_FCPORT_SM_DISABLE:
+               if (bfa_fcport_send_disable(fcport))
+                       bfa_sm_set_state(fcport, bfa_fcport_sm_disabling);
+               else
+                       bfa_sm_set_state(fcport, bfa_fcport_sm_disabling_qwait);
+
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_scn(fcport, BFA_PORT_LINKDOWN, BFA_FALSE);
+               bfa_plog_str(fcport->bfa->plog, BFA_PL_MID_HAL,
+                            BFA_PL_EID_PORT_DISABLE, 0, "Port Disable");
+               bfa_fcport_aen_post(fcport, BFA_PORT_AEN_DISABLE);
+               break;
+
+       case BFA_FCPORT_SM_STOP:
+               bfa_sm_set_state(fcport, bfa_fcport_sm_stopped);
+               break;
+
+       case BFA_FCPORT_SM_HWFAIL:
+               bfa_fcport_reset_linkinfo(fcport);
+               bfa_fcport_scn(fcport, BFA_PORT_LINKDOWN, BFA_FALSE);
+               bfa_sm_set_state(fcport, bfa_fcport_sm_iocdown);
+               break;
+
+       default:
+               bfa_sm_fault(fcport->bfa, event);
+       }
+}
+
 /*
  * Link state is down
  */
@@ -3554,8 +3631,15 @@ bfa_fcport_isr(struct bfa_s *bfa, struct bfi_msg_s *msg)
        case BFI_FCPORT_I2H_EVENT:
                if (i2hmsg.event->link_state.linkstate == BFA_PORT_LINKUP)
                        bfa_sm_send_event(fcport, BFA_FCPORT_SM_LINKUP);
-               else
-                       bfa_sm_send_event(fcport, BFA_FCPORT_SM_LINKDOWN);
+               else {
+                       if (i2hmsg.event->link_state.linkstate_rsn ==
+                           BFA_PORT_LINKSTATE_RSN_FAA_MISCONFIG)
+                               bfa_sm_send_event(fcport,
+                                                 BFA_FCPORT_SM_FAA_MISCONFIG);
+                       else
+                               bfa_sm_send_event(fcport,
+                                                 BFA_FCPORT_SM_LINKDOWN);
+               }
                break;
 
        case BFI_FCPORT_I2H_TRUNK_SCN: