summaryrefslogtreecommitdiffstats
path: root/sys/dev/isp/isp_pci.c
diff options
context:
space:
mode:
authormav <mav@FreeBSD.org>2015-12-15 04:51:50 +0000
committermav <mav@FreeBSD.org>2015-12-15 04:51:50 +0000
commit2278607d5fdffd38d675b8d8bf0447e8a3eb23ea (patch)
tree40ac35f70fdd2ef5cf0bd28f0712364e50880657 /sys/dev/isp/isp_pci.c
parent434ff9cdd9a3c39137cf08e0388bd059936a7902 (diff)
downloadFreeBSD-src-2278607d5fdffd38d675b8d8bf0447e8a3eb23ea.zip
FreeBSD-src-2278607d5fdffd38d675b8d8bf0447e8a3eb23ea.tar.gz
Add MSI-X support for 26XX cards.
Unlike previous, this generation does not support regular MSIs any more.
Diffstat (limited to 'sys/dev/isp/isp_pci.c')
-rw-r--r--sys/dev/isp/isp_pci.c41
1 files changed, 30 insertions, 11 deletions
diff --git a/sys/dev/isp/isp_pci.c b/sys/dev/isp/isp_pci.c
index 9bc9653..d30f6cb 100644
--- a/sys/dev/isp/isp_pci.c
+++ b/sys/dev/isp/isp_pci.c
@@ -373,11 +373,14 @@ struct isp_pcisoftc {
ispsoftc_t pci_isp;
device_t pci_dev;
struct resource * regs;
+ struct resource * regs1;
struct resource * regs2;
void * irq;
int iqd;
int rtp;
int rgd;
+ int rtp1;
+ int rgd1;
int rtp2;
int rgd2;
void * ih;
@@ -829,6 +832,10 @@ isp_pci_attach(device_t dev)
pcs->rgd = PCIR_BAR(0);
pcs->regs = bus_alloc_resource_any(dev, pcs->rtp, &pcs->rgd,
RF_ACTIVE);
+ pcs->rtp1 = SYS_RES_MEMORY;
+ pcs->rgd1 = PCIR_BAR(2);
+ pcs->regs1 = bus_alloc_resource_any(dev, pcs->rtp1, &pcs->rgd1,
+ RF_ACTIVE);
pcs->rtp2 = SYS_RES_MEMORY;
pcs->rgd2 = PCIR_BAR(4);
pcs->regs2 = bus_alloc_resource_any(dev, pcs->rtp2, &pcs->rgd2,
@@ -936,20 +943,28 @@ isp_pci_attach(device_t dev)
data &= ~1;
pci_write_config(dev, PCIR_ROMADDR, data, 4);
- /*
- * Do MSI
- *
- * NB: MSI-X needs to be disabled for the 2432 (PCI-Express)
- */
- if (IS_24XX(isp) || IS_2322(isp)) {
- pcs->msicount = pci_msi_count(dev);
- if (pcs->msicount > 1) {
- pcs->msicount = 1;
+ if (IS_26XX(isp)) {
+ /* 26XX chips support only MSI-X, so start from them. */
+ pcs->msicount = imin(pci_msix_count(dev), 1);
+ if (pcs->msicount > 0 &&
+ (i = pci_alloc_msix(dev, &pcs->msicount)) == 0) {
+ pcs->iqd = 1;
+ } else {
+ pcs->msicount = 0;
}
- if (pci_alloc_msi(dev, &pcs->msicount) == 0) {
+ }
+ if (pcs->msicount == 0 && (IS_24XX(isp) || IS_2322(isp))) {
+ /*
+ * Older chips support both MSI and MSI-X, but I have
+ * feeling that older firmware may not support MSI-X,
+ * but we have no way to check the firmware flag here.
+ */
+ pcs->msicount = imin(pci_msi_count(dev), 1);
+ if (pcs->msicount > 0 &&
+ pci_alloc_msi(dev, &pcs->msicount) == 0) {
pcs->iqd = 1;
} else {
- pcs->iqd = 0;
+ pcs->msicount = 0;
}
}
pcs->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &pcs->iqd, RF_ACTIVE | RF_SHAREABLE);
@@ -1006,6 +1021,8 @@ bad:
}
if (pcs->regs)
(void) bus_release_resource(dev, pcs->rtp, pcs->rgd, pcs->regs);
+ if (pcs->regs1)
+ (void) bus_release_resource(dev, pcs->rtp1, pcs->rgd1, pcs->regs1);
if (pcs->regs2)
(void) bus_release_resource(dev, pcs->rtp2, pcs->rgd2, pcs->regs2);
if (pcs->pci_isp.isp_param) {
@@ -1046,6 +1063,8 @@ isp_pci_detach(device_t dev)
pci_release_msi(dev);
}
(void) bus_release_resource(dev, pcs->rtp, pcs->rgd, pcs->regs);
+ if (pcs->regs1)
+ (void) bus_release_resource(dev, pcs->rtp1, pcs->rgd1, pcs->regs1);
if (pcs->regs2)
(void) bus_release_resource(dev, pcs->rtp2, pcs->rgd2, pcs->regs2);
/*
OpenPOWER on IntegriCloud