Mercurial > illumos > illumos-gate
changeset 14067:a847fb624ac7
3815 AHCI: Support for Marvell 88SE9128 Reviewed by: Johann 'Myrkraverk' Oskarsson <johann@myrkraverk.com> Reviewed by: Richard Lowe <richlowe@richlowe.net> Reviewed by: Garrett D'Amore <garrett@damore.org>
author | Marcel Telka <Marcel.Telka@nexenta.com> |
---|---|
date | Mon, 24 Jun 2013 09:23:02 +0200 |
parents | dac943a98583 |
children | 2547a41b1162 |
files | usr/src/uts/common/io/sata/adapters/ahci/ahci.c usr/src/uts/common/io/sata/impl/sata.c usr/src/uts/common/sys/sata/impl/sata.h usr/src/uts/common/sys/sata/sata_defs.h usr/src/uts/common/sys/sata/sata_hba.h |
diffstat | 5 files changed, 58 insertions(+), 73 deletions(-) [+] |
line wrap: on
line diff
--- a/usr/src/uts/common/io/sata/adapters/ahci/ahci.c Fri Jun 21 16:28:00 2013 +0000 +++ b/usr/src/uts/common/io/sata/adapters/ahci/ahci.c Mon Jun 24 09:23:02 2013 +0200 @@ -5192,8 +5192,8 @@ { ahci_addr_t pmult_addr; uint32_t port_cmd_status; - uint32_t port_scontrol, port_sstatus, port_serror; - uint32_t port_intr_status, port_task_file; + uint32_t port_scontrol, port_sstatus; + uint32_t port_task_file; uint32_t port_state; uint8_t port = addrp->aa_port; @@ -5237,6 +5237,10 @@ port_cmd_status|AHCI_CMD_STATUS_FRE); /* + * The port enters P:StartComm state, and the HBA tells the link layer + * to start communication, which involves sending COMRESET to the + * device. And the HBA resets PxTFD.STS to 7Fh. + * * Give time for COMRESET to percolate, according to the AHCI * spec, software shall wait at least 1 millisecond before * clearing PxSCTL.DET @@ -5252,10 +5256,6 @@ port_scontrol); /* - * The port enters P:StartComm state, and HBA tells link layer to - * start communication, which involves sending COMRESET to device. - * And the HBA resets PxTFD.STS to 7Fh. - * * When a COMINIT is received from the device, then the port enters * P:ComInit state. And HBA sets PxTFD.STS to FFh or 80h. HBA sets * PxSSTS.DET to 1h to indicate a device is detected but communication @@ -5267,7 +5267,7 @@ * that the interface is in active state. */ loop_count = 0; - do { + for (;;) { port_sstatus = ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, (uint32_t *)AHCI_PORT_PxSSTS(ahci_ctlp, port)); @@ -5280,6 +5280,9 @@ SSTATUS_SET_DET(port_sstatus, SSTATUS_DET_NODEV); } + if (SSTATUS_GET_DET(port_sstatus) == SSTATUS_DET_DEVPRE_PHYCOM) + break; + if (loop_count++ > AHCI_POLLRATE_PORT_SSTATUS) { /* * We are effectively timing out after 0.1 sec. @@ -5289,15 +5292,14 @@ /* Wait for 10 millisec */ drv_usecwait(AHCI_10MS_USECS); - } while (SSTATUS_GET_DET(port_sstatus) != SSTATUS_DET_DEVPRE_PHYCOM); + } AHCIDBG(AHCIDBG_INIT|AHCIDBG_POLL_LOOP, ahci_ctlp, "ahci_port_reset: 1st loop count: %d, " "port_sstatus = 0x%x port %d", loop_count, port_sstatus, port); - if ((SSTATUS_GET_IPM(port_sstatus) != SSTATUS_IPM_ACTIVE) || - (SSTATUS_GET_DET(port_sstatus) != SSTATUS_DET_DEVPRE_PHYCOM)) { + if (SSTATUS_GET_DET(port_sstatus) != SSTATUS_DET_DEVPRE_PHYCOM) { /* * Either the port is not active or there * is no device present. @@ -5306,60 +5308,25 @@ return (AHCI_SUCCESS); } - /* Now we can make sure there is a device connected to the port */ - port_intr_status = ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, - (uint32_t *)AHCI_PORT_PxIS(ahci_ctlp, port)); - port_serror = ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, - (uint32_t *)AHCI_PORT_PxSERR(ahci_ctlp, port)); - - /* - * A COMINIT signal is supposed to be received - * PxSERR.DIAG.X or PxIS.PCS should be set - */ - if (!(port_intr_status & AHCI_INTR_STATUS_PCS) && - !(port_serror & SERROR_EXCHANGED_ERR)) { - cmn_err(CE_WARN, "!ahci%d: ahci_port_reset port %d " - "COMINIT signal from the device not received", - instance, port); - AHCIPORT_SET_STATE(ahci_portp, addrp, SATA_PSTATE_FAILED); - return (AHCI_FAILURE); - } - - /* - * According to the spec, when PxSCTL.DET is set to 0h, upon - * receiving a COMINIT from the attached device, PxTFD.STS.BSY - * shall be set to '1' by the HBA. - * - * However, we found JMicron JMB363 doesn't follow this, so - * remove this check, and just print a debug message. - */ -#if AHCI_DEBUG - port_task_file = ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, - (uint32_t *)AHCI_PORT_PxTFD(ahci_ctlp, port)); - if (!(port_task_file & AHCI_TFD_STS_BSY)) { - AHCIDBG(AHCIDBG_ERRS, ahci_ctlp, "ahci_port_reset: " - "port %d BSY bit is not set after COMINIT signal " - "is received", port); - } -#endif - - /* - * PxSERR.DIAG.X has to be cleared in order to update PxTFD with - * the D2H FIS received by HBA. - */ + /* Clear port serror register for the port */ ddi_put32(ahci_ctlp->ahcictl_ahci_acc_handle, (uint32_t *)AHCI_PORT_PxSERR(ahci_ctlp, port), - SERROR_EXCHANGED_ERR); + AHCI_SERROR_CLEAR_ALL); /* * Devices should return a FIS contains its signature to HBA after - * COMINIT signal. Check whether a D2H FIS is received by polling - * PxTFD.STS.ERR bit. + * COMINIT signal. Check whether a D2H Register FIS is received by + * polling PxTFD.STS. */ loop_count = 0; - do { - /* Wait for 10 millisec */ - drv_usecwait(AHCI_10MS_USECS); + for (;;) { + port_task_file = + ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, + (uint32_t *)AHCI_PORT_PxTFD(ahci_ctlp, port)); + + if ((port_task_file & (AHCI_TFD_STS_BSY | AHCI_TFD_STS_DRQ | + AHCI_TFD_STS_ERR)) == 0) + break; if (loop_count++ > AHCI_POLLRATE_PORT_TFD_ERROR) { /* @@ -5371,7 +5338,8 @@ instance, port); AHCIDBG(AHCIDBG_ERRS, ahci_ctlp, "ahci_port_reset: " - "port %d PxTFD.STS.ERR is not set, we need another " + "port %d: some or all of BSY, DRQ and ERR in " + "PxTFD.STS are not clear. We need another " "software reset.", port); /* Clear port serror register for the port */ @@ -5393,19 +5361,7 @@ /* Wait for 10 millisec */ drv_usecwait(AHCI_10MS_USECS); - - /* - * The Error bit '1' means COMRESET is finished successfully - * The device hardware has been initialized and the power-up - * diagnostics successfully completed. The device requests - * that the Transport layer transmit a Register - D2H FIS to - * the host. (SATA spec 11.5, v2.6) - */ - port_task_file = - ddi_get32(ahci_ctlp->ahcictl_ahci_acc_handle, - (uint32_t *)AHCI_PORT_PxTFD(ahci_ctlp, port)); - } while (((port_task_file & AHCI_TFD_ERR_MASK) - >> AHCI_TFD_ERR_SHIFT) != AHCI_TFD_ERR_SGS); + } AHCIDBG(AHCIDBG_INIT|AHCIDBG_POLL_LOOP, ahci_ctlp, "ahci_port_reset: 2nd loop count: %d, "
--- a/usr/src/uts/common/io/sata/impl/sata.c Fri Jun 21 16:28:00 2013 +0000 +++ b/usr/src/uts/common/io/sata/impl/sata.c Mon Jun 24 09:23:02 2013 +0200 @@ -23,7 +23,7 @@ * Copyright (c) 2006, 2010, Oracle and/or its affiliates. All rights reserved. */ /* - * Copyright 2011 Nexenta Systems, Inc. All rights reserved. + * Copyright 2013 Nexenta Systems, Inc. All rights reserved. */ /* @@ -12603,6 +12603,9 @@ case SATA_ATAPI_DIRACC_DEV: sdinfo->satadrv_type = SATA_DTYPE_ATAPIDISK; break; + case SATA_ATAPI_PROC_DEV: + sdinfo->satadrv_type = SATA_DTYPE_ATAPIPROC; + break; default: sdinfo->satadrv_type = SATA_DTYPE_UNKNOWN; } @@ -12706,6 +12709,10 @@ (void) sprintf(msg_buf, "SATA disk (ATAPI) device at"); break; + case SATA_DTYPE_ATAPIPROC: + (void) sprintf(msg_buf, "SATA processor (ATAPI) device at"); + break; + case SATA_DTYPE_UNKNOWN: (void) sprintf(msg_buf, "Unsupported SATA device type (cfg 0x%x) at ", @@ -15991,6 +15998,11 @@ } break; } + case SATA_DTYPE_ATAPIPROC: + ap_state->ap_rstate = AP_RSTATE_CONNECTED; + ap_state->ap_ostate = AP_OSTATE_UNCONFIGURED; + ap_state->ap_condition = AP_COND_OK; + break; default: ap_state->ap_rstate = AP_RSTATE_CONNECTED; ap_state->ap_ostate = AP_OSTATE_UNCONFIGURED; @@ -16093,6 +16105,10 @@ ap_type = "tape"; break; + case SATA_DTYPE_ATAPIPROC: + ap_type = "processor"; + break; + case SATA_DTYPE_PMULT: ap_type = "sata-pmult"; break;
--- a/usr/src/uts/common/sys/sata/impl/sata.h Fri Jun 21 16:28:00 2013 +0000 +++ b/usr/src/uts/common/sys/sata/impl/sata.h Mon Jun 24 09:23:02 2013 +0200 @@ -23,6 +23,9 @@ * Copyright 2010 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ +/* + * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + */ #ifndef _SATA_H #define _SATA_H @@ -157,6 +160,7 @@ * SATA_DTYPE_ATAPIDISK * SATA_DTYPE_PMULT * SATA_DTYPE_UNKNOWN + * SATA_DTYPE_ATAPIPROC */ uint32_t cport_dev_type; union { @@ -212,6 +216,7 @@ * SATA_DTYPE_ATAPICD * SATA_DTYPE_ATAPITAPE * SATA_DTYPE_ATAPIDISK + * SATA_DTYPE_ATAPIPROC */ uint32_t satadrv_type; @@ -304,6 +309,7 @@ * SATA_DTYPE_ATAPITAPE * SATA_DTYPE_ATAPIDISK * SATA_DTYPE_UNKNOWN + * SATA_DTYPE_ATAPIPROC */ uint32_t pmport_dev_type;
--- a/usr/src/uts/common/sys/sata/sata_defs.h Fri Jun 21 16:28:00 2013 +0000 +++ b/usr/src/uts/common/sys/sata/sata_defs.h Mon Jun 24 09:23:02 2013 +0200 @@ -21,6 +21,7 @@ /* * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright 2013 Nexenta Systems, Inc. All rights reserved. */ #ifndef _SATA_DEFS_H @@ -367,10 +368,11 @@ #define SATA_ATAPI_ID_DRQ_TYPE 0x0060 /* DRQ asserted in 3ms after pkt */ #define SATA_ATAPI_ID_DRQ_INTR 0x0020 /* Obsolete in ATA/ATAPI 7 */ -#define SATA_ATAPI_ID_DEV_TYPE 0x0f00 /* device type/command set mask */ +#define SATA_ATAPI_ID_DEV_TYPE 0x1f00 /* device type/command set mask */ #define SATA_ATAPI_ID_DEV_SHFT 8 #define SATA_ATAPI_DIRACC_DEV 0x0000 /* Direct Access device */ #define SATA_ATAPI_SQACC_DEV 0x0100 /* Sequential access dev (tape ?) */ +#define SATA_ATAPI_PROC_DEV 0x0300 /* Processor device */ #define SATA_ATAPI_CDROM_DEV 0x0500 /* CD_ROM device */ /*
--- a/usr/src/uts/common/sys/sata/sata_hba.h Fri Jun 21 16:28:00 2013 +0000 +++ b/usr/src/uts/common/sys/sata/sata_hba.h Mon Jun 24 09:23:02 2013 +0200 @@ -23,6 +23,9 @@ * Copyright 2009 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ +/* + * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + */ #ifndef _SATA_HBA_H #define _SATA_HBA_H @@ -224,6 +227,8 @@ (SATA_DTYPE_ATAPI|0x08) /* ATAPI disk */ #define SATA_DTYPE_PMULT 0x10 /* Port Multiplier */ #define SATA_DTYPE_UNKNOWN 0x20 /* Device attached, unkown */ +#define SATA_DTYPE_ATAPIPROC \ + (SATA_DTYPE_ATAPI|0x80) /* ATAPI processor */ /*