Author: mav
Date: Wed Sep  7 13:51:34 2016
New Revision: 305536
URL: https://svnweb.freebsd.org/changeset/base/305536

Log:
  Fix channel initialization in FBS mode.
  
  Due to reading initialized variable, FIS receive area was always allocated
  as 256 bytes, suitable for command-based switching, instead of 4096 bytes,
  required for FIS-based switching.  This caused memory corruption in case of
  port multipliers used on FBS-capable HBAs (Marvell).
  
  MFC after:    1 week

Modified:
  head/sys/dev/ahci/ahci.c

Modified: head/sys/dev/ahci/ahci.c
==============================================================================
--- head/sys/dev/ahci/ahci.c    Wed Sep  7 13:45:35 2016        (r305535)
+++ head/sys/dev/ahci/ahci.c    Wed Sep  7 13:51:34 2016        (r305536)
@@ -715,6 +715,21 @@ ahci_ch_attach(device_t dev)
        if (!(ch->r_mem = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
            &rid, RF_ACTIVE)))
                return (ENXIO);
+       ch->chcaps = ATA_INL(ch->r_mem, AHCI_P_CMD);
+       version = ATA_INL(ctlr->r_mem, AHCI_VS);
+       if (version < 0x00010200 && (ctlr->caps & AHCI_CAP_FBSS))
+               ch->chcaps |= AHCI_P_CMD_FBSCP;
+       if (ch->caps2 & AHCI_CAP2_SDS)
+               ch->chscaps = ATA_INL(ch->r_mem, AHCI_P_DEVSLP);
+       if (bootverbose) {
+               device_printf(dev, "Caps:%s%s%s%s%s%s\n",
+                   (ch->chcaps & AHCI_P_CMD_HPCP) ? " HPCP":"",
+                   (ch->chcaps & AHCI_P_CMD_MPSP) ? " MPSP":"",
+                   (ch->chcaps & AHCI_P_CMD_CPD) ? " CPD":"",
+                   (ch->chcaps & AHCI_P_CMD_ESP) ? " ESP":"",
+                   (ch->chcaps & AHCI_P_CMD_FBSCP) ? " FBSCP":"",
+                   (ch->chscaps & AHCI_P_DEVSLP_DSP) ? " DSP":"");
+       }
        ahci_dmainit(dev);
        ahci_slotsalloc(dev);
        mtx_lock(&ch->mtx);
@@ -733,21 +748,6 @@ ahci_ch_attach(device_t dev)
                error = ENXIO;
                goto err1;
        }
-       ch->chcaps = ATA_INL(ch->r_mem, AHCI_P_CMD);
-       version = ATA_INL(ctlr->r_mem, AHCI_VS);
-       if (version < 0x00010200 && (ctlr->caps & AHCI_CAP_FBSS))
-               ch->chcaps |= AHCI_P_CMD_FBSCP;
-       if (ch->caps2 & AHCI_CAP2_SDS)
-               ch->chscaps = ATA_INL(ch->r_mem, AHCI_P_DEVSLP);
-       if (bootverbose) {
-               device_printf(dev, "Caps:%s%s%s%s%s%s\n",
-                   (ch->chcaps & AHCI_P_CMD_HPCP) ? " HPCP":"",
-                   (ch->chcaps & AHCI_P_CMD_MPSP) ? " MPSP":"",
-                   (ch->chcaps & AHCI_P_CMD_CPD) ? " CPD":"",
-                   (ch->chcaps & AHCI_P_CMD_ESP) ? " ESP":"",
-                   (ch->chcaps & AHCI_P_CMD_FBSCP) ? " FBSCP":"",
-                   (ch->chscaps & AHCI_P_DEVSLP_DSP) ? " DSP":"");
-       }
        /* Create the device queue for our SIM. */
        devq = cam_simq_alloc(ch->numslots);
        if (devq == NULL) {
_______________________________________________
[email protected] mailing list
https://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "[email protected]"

Reply via email to