aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/infiniband/hw/ipath/ipath_iba6120.c
diff options
context:
space:
mode:
authorBryan O'Sullivan <bos@pathscale.com>2007-03-15 17:45:07 -0400
committerRoland Dreier <rolandd@cisco.com>2007-04-18 23:20:58 -0400
commit9783ab405844202b452ac673677e6c8f8c9a6a99 (patch)
tree32aac9ac3ff1089a7ecb05c4ef0b825a95227694 /drivers/infiniband/hw/ipath/ipath_iba6120.c
parent820054b7ca7a54ba94d89db4b3c53a24d2d66633 (diff)
IB/ipath: Improve handling and reporting of parity errors
Mostly cleanup. Signed-off-by: Dave Olson <dave.olson@qlogic.com> Signed-off-by: Bryan O'Sullivan <bryan.osullivan@qlogic.com> Signed-off-by: Roland Dreier <rolandd@cisco.com>
Diffstat (limited to 'drivers/infiniband/hw/ipath/ipath_iba6120.c')
-rw-r--r--drivers/infiniband/hw/ipath/ipath_iba6120.c58
1 files changed, 39 insertions, 19 deletions
diff --git a/drivers/infiniband/hw/ipath/ipath_iba6120.c b/drivers/infiniband/hw/ipath/ipath_iba6120.c
index 5c50383880f2..aa2b51944331 100644
--- a/drivers/infiniband/hw/ipath/ipath_iba6120.c
+++ b/drivers/infiniband/hw/ipath/ipath_iba6120.c
@@ -321,6 +321,12 @@ static const struct ipath_hwerror_msgs ipath_6120_hwerror_msgs[] = {
321 INFINIPATH_HWE_MSG(SERDESPLLFAILED, "SerDes PLL"), 321 INFINIPATH_HWE_MSG(SERDESPLLFAILED, "SerDes PLL"),
322}; 322};
323 323
324#define TXE_PIO_PARITY ((INFINIPATH_HWE_TXEMEMPARITYERR_PIOBUF | \
325 INFINIPATH_HWE_TXEMEMPARITYERR_PIOPBC) \
326 << INFINIPATH_HWE_TXEMEMPARITYERR_SHIFT)
327
328static int ipath_pe_txe_recover(struct ipath_devdata *);
329
324/** 330/**
325 * ipath_pe_handle_hwerrors - display hardware errors. 331 * ipath_pe_handle_hwerrors - display hardware errors.
326 * @dd: the infinipath device 332 * @dd: the infinipath device
@@ -394,25 +400,8 @@ static void ipath_pe_handle_hwerrors(struct ipath_devdata *dd, char *msg,
394 * occur if a processor speculative read is done to the PIO 400 * occur if a processor speculative read is done to the PIO
395 * buffer while we are sending a packet, for example. 401 * buffer while we are sending a packet, for example.
396 */ 402 */
397 if (hwerrs & ((INFINIPATH_HWE_TXEMEMPARITYERR_PIOBUF | 403 if ((hwerrs & TXE_PIO_PARITY) && ipath_pe_txe_recover(dd))
398 INFINIPATH_HWE_TXEMEMPARITYERR_PIOPBC) 404 hwerrs &= ~TXE_PIO_PARITY;
399 << INFINIPATH_HWE_TXEMEMPARITYERR_SHIFT)) {
400 ipath_stats.sps_txeparity++;
401 ipath_dbg("Recovering from TXE parity error (%llu), "
402 "hwerrstatus=%llx\n",
403 (unsigned long long) ipath_stats.sps_txeparity,
404 (unsigned long long) hwerrs);
405 ipath_disarm_senderrbufs(dd);
406 hwerrs &= ~((INFINIPATH_HWE_TXEMEMPARITYERR_PIOBUF |
407 INFINIPATH_HWE_TXEMEMPARITYERR_PIOPBC)
408 << INFINIPATH_HWE_TXEMEMPARITYERR_SHIFT);
409 if (!hwerrs) { /* else leave in freeze mode */
410 ipath_write_kreg(dd,
411 dd->ipath_kregs->kr_control,
412 dd->ipath_control);
413 return;
414 }
415 }
416 if (hwerrs) { 405 if (hwerrs) {
417 /* 406 /*
418 * if any set that we aren't ignoring only make the 407 * if any set that we aren't ignoring only make the
@@ -581,6 +570,8 @@ static void ipath_pe_init_hwerrors(struct ipath_devdata *dd)
581 570
582 if (!(extsval & INFINIPATH_EXTS_MEMBIST_ENDTEST)) 571 if (!(extsval & INFINIPATH_EXTS_MEMBIST_ENDTEST))
583 ipath_dev_err(dd, "MemBIST did not complete!\n"); 572 ipath_dev_err(dd, "MemBIST did not complete!\n");
573 if (extsval & INFINIPATH_EXTS_MEMBIST_FOUND)
574 ipath_dbg("MemBIST corrected\n");
584 575
585 val = ~0ULL; /* barring bugs, all hwerrors become interrupts, */ 576 val = ~0ULL; /* barring bugs, all hwerrors become interrupts, */
586 577
@@ -1330,6 +1321,35 @@ static void ipath_pe_free_irq(struct ipath_devdata *dd)
1330 dd->ipath_irq = 0; 1321 dd->ipath_irq = 0;
1331} 1322}
1332 1323
1324/*
1325 * On platforms using this chip, and not having ordered WC stores, we
1326 * can get TXE parity errors due to speculative reads to the PIO buffers,
1327 * and this, due to a chip bug can result in (many) false parity error
1328 * reports. So it's a debug print on those, and an info print on systems
1329 * where the speculative reads don't occur.
1330 * Because we can get lots of false errors, we have no upper limit
1331 * on recovery attempts on those platforms.
1332 */
1333static int ipath_pe_txe_recover(struct ipath_devdata *dd)
1334{
1335 if (ipath_unordered_wc())
1336 ipath_dbg("Recovering from TXE PIO parity error\n");
1337 else {
1338 int cnt = ++ipath_stats.sps_txeparity;
1339 if (cnt >= IPATH_MAX_PARITY_ATTEMPTS) {
1340 if (cnt == IPATH_MAX_PARITY_ATTEMPTS)
1341 ipath_dev_err(dd,
1342 "Too many attempts to recover from "
1343 "TXE parity, giving up\n");
1344 return 0;
1345 }
1346 dev_info(&dd->pcidev->dev,
1347 "Recovering from TXE PIO parity error\n");
1348 }
1349 ipath_disarm_senderrbufs(dd, 1);
1350 return 1;
1351}
1352
1333/** 1353/**
1334 * ipath_init_iba6120_funcs - set up the chip-specific function pointers 1354 * ipath_init_iba6120_funcs - set up the chip-specific function pointers
1335 * @dd: the infinipath device 1355 * @dd: the infinipath device