1*b2441318SGreg Kroah-Hartman // SPDX-License-Identifier: GPL-2.0
21da177e4SLinus Torvalds /*
31da177e4SLinus Torvalds * linux/arch/alpha/kernel/err_marvel.c
41da177e4SLinus Torvalds *
51da177e4SLinus Torvalds * Copyright (C) 2001 Jeff Wiedemeier (Compaq Computer Corporation)
61da177e4SLinus Torvalds *
71da177e4SLinus Torvalds */
81da177e4SLinus Torvalds
91da177e4SLinus Torvalds #include <linux/init.h>
101da177e4SLinus Torvalds #include <linux/pci.h>
111da177e4SLinus Torvalds #include <linux/sched.h>
121da177e4SLinus Torvalds
131da177e4SLinus Torvalds #include <asm/io.h>
141da177e4SLinus Torvalds #include <asm/console.h>
151da177e4SLinus Torvalds #include <asm/core_marvel.h>
161da177e4SLinus Torvalds #include <asm/hwrpb.h>
171da177e4SLinus Torvalds #include <asm/smp.h>
181da177e4SLinus Torvalds #include <asm/err_common.h>
191da177e4SLinus Torvalds #include <asm/err_ev7.h>
201da177e4SLinus Torvalds
211da177e4SLinus Torvalds #include "err_impl.h"
221da177e4SLinus Torvalds #include "proto.h"
231da177e4SLinus Torvalds
241da177e4SLinus Torvalds static void
marvel_print_680_frame(struct ev7_lf_subpackets * lf_subpackets)251da177e4SLinus Torvalds marvel_print_680_frame(struct ev7_lf_subpackets *lf_subpackets)
261da177e4SLinus Torvalds {
271da177e4SLinus Torvalds #ifdef CONFIG_VERBOSE_MCHECK
281da177e4SLinus Torvalds struct ev7_pal_environmental_subpacket *env;
291da177e4SLinus Torvalds struct { int type; char *name; } ev_packets[] = {
301da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__AMBIENT_TEMPERATURE,
311da177e4SLinus Torvalds "Ambient Temperature" },
321da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__AIRMOVER_FAN,
331da177e4SLinus Torvalds "AirMover / Fan" },
341da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__VOLTAGE,
351da177e4SLinus Torvalds "Voltage" },
361da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__INTRUSION,
371da177e4SLinus Torvalds "Intrusion" },
381da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__POWER_SUPPLY,
391da177e4SLinus Torvalds "Power Supply" },
401da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__LAN,
411da177e4SLinus Torvalds "LAN" },
421da177e4SLinus Torvalds { EL_TYPE__PAL__ENV__HOT_PLUG,
431da177e4SLinus Torvalds "Hot Plug" },
441da177e4SLinus Torvalds { 0, NULL }
451da177e4SLinus Torvalds };
461da177e4SLinus Torvalds int i;
471da177e4SLinus Torvalds
481da177e4SLinus Torvalds for (i = 0; ev_packets[i].type != 0; i++) {
491da177e4SLinus Torvalds env = lf_subpackets->env[ev7_lf_env_index(ev_packets[i].type)];
501da177e4SLinus Torvalds if (!env)
511da177e4SLinus Torvalds continue;
521da177e4SLinus Torvalds
531da177e4SLinus Torvalds printk("%s**%s event (cabinet %d, drawer %d)\n",
541da177e4SLinus Torvalds err_print_prefix,
551da177e4SLinus Torvalds ev_packets[i].name,
561da177e4SLinus Torvalds env->cabinet,
571da177e4SLinus Torvalds env->drawer);
581da177e4SLinus Torvalds printk("%s Module Type: 0x%x - Unit ID 0x%x - "
591da177e4SLinus Torvalds "Condition 0x%x\n",
601da177e4SLinus Torvalds err_print_prefix,
611da177e4SLinus Torvalds env->module_type,
621da177e4SLinus Torvalds env->unit_id,
631da177e4SLinus Torvalds env->condition);
641da177e4SLinus Torvalds }
651da177e4SLinus Torvalds #endif /* CONFIG_VERBOSE_MCHECK */
661da177e4SLinus Torvalds }
671da177e4SLinus Torvalds
681da177e4SLinus Torvalds static int
marvel_process_680_frame(struct ev7_lf_subpackets * lf_subpackets,int print)691da177e4SLinus Torvalds marvel_process_680_frame(struct ev7_lf_subpackets *lf_subpackets, int print)
701da177e4SLinus Torvalds {
711da177e4SLinus Torvalds int status = MCHK_DISPOSITION_UNKNOWN_ERROR;
721da177e4SLinus Torvalds int i;
731da177e4SLinus Torvalds
741da177e4SLinus Torvalds for (i = ev7_lf_env_index(EL_TYPE__PAL__ENV__AMBIENT_TEMPERATURE);
751da177e4SLinus Torvalds i <= ev7_lf_env_index(EL_TYPE__PAL__ENV__HOT_PLUG);
761da177e4SLinus Torvalds i++) {
771da177e4SLinus Torvalds if (lf_subpackets->env[i])
781da177e4SLinus Torvalds status = MCHK_DISPOSITION_REPORT;
791da177e4SLinus Torvalds }
801da177e4SLinus Torvalds
811da177e4SLinus Torvalds if (print)
821da177e4SLinus Torvalds marvel_print_680_frame(lf_subpackets);
831da177e4SLinus Torvalds
841da177e4SLinus Torvalds return status;
851da177e4SLinus Torvalds }
861da177e4SLinus Torvalds
871da177e4SLinus Torvalds #ifdef CONFIG_VERBOSE_MCHECK
881da177e4SLinus Torvalds
891da177e4SLinus Torvalds static void
marvel_print_err_cyc(u64 err_cyc)901da177e4SLinus Torvalds marvel_print_err_cyc(u64 err_cyc)
911da177e4SLinus Torvalds {
921da177e4SLinus Torvalds static char *packet_desc[] = {
931da177e4SLinus Torvalds "No Error",
941da177e4SLinus Torvalds "UNKNOWN",
951da177e4SLinus Torvalds "1 cycle (1 or 2 flit packet)",
961da177e4SLinus Torvalds "2 cycles (3 flit packet)",
971da177e4SLinus Torvalds "9 cycles (18 flit packet)",
981da177e4SLinus Torvalds "10 cycles (19 flit packet)",
991da177e4SLinus Torvalds "UNKNOWN",
1001da177e4SLinus Torvalds "UNKNOWN",
1011da177e4SLinus Torvalds "UNKNOWN"
1021da177e4SLinus Torvalds };
1031da177e4SLinus Torvalds
1041da177e4SLinus Torvalds #define IO7__ERR_CYC__ODD_FLT (1UL << 0)
1051da177e4SLinus Torvalds #define IO7__ERR_CYC__EVN_FLT (1UL << 1)
1061da177e4SLinus Torvalds #define IO7__ERR_CYC__PACKET__S (6)
1071da177e4SLinus Torvalds #define IO7__ERR_CYC__PACKET__M (0x7)
1081da177e4SLinus Torvalds #define IO7__ERR_CYC__LOC (1UL << 5)
1091da177e4SLinus Torvalds #define IO7__ERR_CYC__CYCLE__S (2)
1101da177e4SLinus Torvalds #define IO7__ERR_CYC__CYCLE__M (0x7)
1111da177e4SLinus Torvalds
1121da177e4SLinus Torvalds printk("%s Packet In Error: %s\n"
1133e073367SMichael Cree "%s Error in %s, cycle %lld%s%s\n",
1141da177e4SLinus Torvalds err_print_prefix,
1151da177e4SLinus Torvalds packet_desc[EXTRACT(err_cyc, IO7__ERR_CYC__PACKET)],
1161da177e4SLinus Torvalds err_print_prefix,
1171da177e4SLinus Torvalds (err_cyc & IO7__ERR_CYC__LOC) ? "DATA" : "HEADER",
1181da177e4SLinus Torvalds EXTRACT(err_cyc, IO7__ERR_CYC__CYCLE),
1191da177e4SLinus Torvalds (err_cyc & IO7__ERR_CYC__ODD_FLT) ? " [ODD Flit]": "",
1201da177e4SLinus Torvalds (err_cyc & IO7__ERR_CYC__EVN_FLT) ? " [Even Flit]": "");
1211da177e4SLinus Torvalds }
1221da177e4SLinus Torvalds
1231da177e4SLinus Torvalds static void
marvel_print_po7_crrct_sym(u64 crrct_sym)1241da177e4SLinus Torvalds marvel_print_po7_crrct_sym(u64 crrct_sym)
1251da177e4SLinus Torvalds {
1261da177e4SLinus Torvalds #define IO7__PO7_CRRCT_SYM__SYN__S (0)
1271da177e4SLinus Torvalds #define IO7__PO7_CRRCT_SYM__SYN__M (0x7f)
1281da177e4SLinus Torvalds #define IO7__PO7_CRRCT_SYM__ERR_CYC__S (7) /* ERR_CYC + ODD_FLT + EVN_FLT */
1291da177e4SLinus Torvalds #define IO7__PO7_CRRCT_SYM__ERR_CYC__M (0x1ff)
1301da177e4SLinus Torvalds
1311da177e4SLinus Torvalds
1321da177e4SLinus Torvalds printk("%s Correctable Error Symptoms:\n"
1335f0e3da6SRandy Dunlap "%s Syndrome: 0x%llx\n",
1341da177e4SLinus Torvalds err_print_prefix,
1351da177e4SLinus Torvalds err_print_prefix, EXTRACT(crrct_sym, IO7__PO7_CRRCT_SYM__SYN));
1361da177e4SLinus Torvalds marvel_print_err_cyc(EXTRACT(crrct_sym, IO7__PO7_CRRCT_SYM__ERR_CYC));
1371da177e4SLinus Torvalds }
1381da177e4SLinus Torvalds
1391da177e4SLinus Torvalds static void
marvel_print_po7_uncrr_sym(u64 uncrr_sym,u64 valid_mask)1401da177e4SLinus Torvalds marvel_print_po7_uncrr_sym(u64 uncrr_sym, u64 valid_mask)
1411da177e4SLinus Torvalds {
1421da177e4SLinus Torvalds static char *clk_names[] = { "_h[0]", "_h[1]", "_n[0]", "_n[1]" };
1431da177e4SLinus Torvalds static char *clk_decode[] = {
1441da177e4SLinus Torvalds "No Error",
1451da177e4SLinus Torvalds "One extra rising edge",
1461da177e4SLinus Torvalds "Two extra rising edges",
1471da177e4SLinus Torvalds "Lost one clock"
1481da177e4SLinus Torvalds };
1491da177e4SLinus Torvalds static char *port_names[] = { "Port 0", "Port 1",
1501da177e4SLinus Torvalds "Port 2", "Port 3",
1511da177e4SLinus Torvalds "Unknown Port", "Unknown Port",
1521da177e4SLinus Torvalds "Unknown Port", "Port 7" };
1531da177e4SLinus Torvalds int scratch, i;
1541da177e4SLinus Torvalds
1551da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__SYN__S (0)
1561da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__SYN__M (0x7f)
1571da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__ERR_CYC__S (7) /* ERR_CYC + ODD_FLT... */
1581da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__ERR_CYC__M (0x1ff) /* ... + EVN_FLT */
1591da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CLK__S (16)
1601da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CLK__M (0xff)
1611da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CDT_OVF_TO__REQ (1UL << 24)
1621da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CDT_OVF_TO__RIO (1UL << 25)
1631da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CDT_OVF_TO__WIO (1UL << 26)
1641da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CDT_OVF_TO__BLK (1UL << 27)
1651da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__CDT_OVF_TO__NBK (1UL << 28)
1661da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__OVF__READIO (1UL << 29)
1671da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__OVF__WRITEIO (1UL << 30)
1681da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__OVF__FWD (1UL << 31)
1691da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__VICTIM_SP__S (32)
1701da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__VICTIM_SP__M (0xff)
1711da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__DETECT_SP__S (40)
1721da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__DETECT_SP__M (0xff)
1731da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__STRV_VTR__S (48)
1741da177e4SLinus Torvalds #define IO7__PO7_UNCRR_SYM__STRV_VTR__M (0x3ff)
1751da177e4SLinus Torvalds
1761da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__INTX__S (0)
1771da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__INTX__M (0x3)
1781da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__SLOT__S (2)
1791da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__SLOT__M (0x7)
1801da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__BUS__S (5)
1811da177e4SLinus Torvalds #define IO7__STRV_VTR__LSI__BUS__M (0x3)
1821da177e4SLinus Torvalds #define IO7__STRV_VTR__MSI__INTNUM__S (0)
1831da177e4SLinus Torvalds #define IO7__STRV_VTR__MSI__INTNUM__M (0x1ff)
1841da177e4SLinus Torvalds #define IO7__STRV_VTR__IS_MSI (1UL << 9)
1851da177e4SLinus Torvalds
1861da177e4SLinus Torvalds printk("%s Uncorrectable Error Symptoms:\n", err_print_prefix);
1871da177e4SLinus Torvalds uncrr_sym &= valid_mask;
1881da177e4SLinus Torvalds
1891da177e4SLinus Torvalds if (EXTRACT(valid_mask, IO7__PO7_UNCRR_SYM__SYN))
1905f0e3da6SRandy Dunlap printk("%s Syndrome: 0x%llx\n",
1911da177e4SLinus Torvalds err_print_prefix,
1921da177e4SLinus Torvalds EXTRACT(uncrr_sym, IO7__PO7_UNCRR_SYM__SYN));
1931da177e4SLinus Torvalds
1941da177e4SLinus Torvalds if (EXTRACT(valid_mask, IO7__PO7_UNCRR_SYM__ERR_CYC))
1951da177e4SLinus Torvalds marvel_print_err_cyc(EXTRACT(uncrr_sym,
1961da177e4SLinus Torvalds IO7__PO7_UNCRR_SYM__ERR_CYC));
1971da177e4SLinus Torvalds
1981da177e4SLinus Torvalds scratch = EXTRACT(uncrr_sym, IO7__PO7_UNCRR_SYM__CLK);
1991da177e4SLinus Torvalds for (i = 0; i < 4; i++, scratch >>= 2) {
2001da177e4SLinus Torvalds if (scratch & 0x3)
2011da177e4SLinus Torvalds printk("%s Clock %s: %s\n",
2021da177e4SLinus Torvalds err_print_prefix,
2031da177e4SLinus Torvalds clk_names[i], clk_decode[scratch & 0x3]);
2041da177e4SLinus Torvalds }
2051da177e4SLinus Torvalds
2061da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__CDT_OVF_TO__REQ)
2071da177e4SLinus Torvalds printk("%s REQ Credit Timeout or Overflow\n",
2081da177e4SLinus Torvalds err_print_prefix);
2091da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__CDT_OVF_TO__RIO)
2101da177e4SLinus Torvalds printk("%s RIO Credit Timeout or Overflow\n",
2111da177e4SLinus Torvalds err_print_prefix);
2121da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__CDT_OVF_TO__WIO)
2131da177e4SLinus Torvalds printk("%s WIO Credit Timeout or Overflow\n",
2141da177e4SLinus Torvalds err_print_prefix);
2151da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__CDT_OVF_TO__BLK)
2161da177e4SLinus Torvalds printk("%s BLK Credit Timeout or Overflow\n",
2171da177e4SLinus Torvalds err_print_prefix);
2181da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__CDT_OVF_TO__NBK)
2191da177e4SLinus Torvalds printk("%s NBK Credit Timeout or Overflow\n",
2201da177e4SLinus Torvalds err_print_prefix);
2211da177e4SLinus Torvalds
2221da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__OVF__READIO)
2231da177e4SLinus Torvalds printk("%s Read I/O Buffer Overflow\n",
2241da177e4SLinus Torvalds err_print_prefix);
2251da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__OVF__WRITEIO)
2261da177e4SLinus Torvalds printk("%s Write I/O Buffer Overflow\n",
2271da177e4SLinus Torvalds err_print_prefix);
2281da177e4SLinus Torvalds if (uncrr_sym & IO7__PO7_UNCRR_SYM__OVF__FWD)
2291da177e4SLinus Torvalds printk("%s FWD Buffer Overflow\n",
2301da177e4SLinus Torvalds err_print_prefix);
2311da177e4SLinus Torvalds
2321da177e4SLinus Torvalds if ((scratch = EXTRACT(uncrr_sym, IO7__PO7_UNCRR_SYM__VICTIM_SP))) {
2331da177e4SLinus Torvalds int lost = scratch & (1UL << 4);
2341da177e4SLinus Torvalds scratch &= ~lost;
2351da177e4SLinus Torvalds for (i = 0; i < 8; i++, scratch >>= 1) {
2361da177e4SLinus Torvalds if (!(scratch & 1))
2371da177e4SLinus Torvalds continue;
2381da177e4SLinus Torvalds printk("%s Error Response sent to %s",
2391da177e4SLinus Torvalds err_print_prefix, port_names[i]);
2401da177e4SLinus Torvalds }
2411da177e4SLinus Torvalds if (lost)
2421da177e4SLinus Torvalds printk("%s Lost Error sent somewhere else\n",
2431da177e4SLinus Torvalds err_print_prefix);
2441da177e4SLinus Torvalds }
2451da177e4SLinus Torvalds
2461da177e4SLinus Torvalds if ((scratch = EXTRACT(uncrr_sym, IO7__PO7_UNCRR_SYM__DETECT_SP))) {
2471da177e4SLinus Torvalds for (i = 0; i < 8; i++, scratch >>= 1) {
2481da177e4SLinus Torvalds if (!(scratch & 1))
2491da177e4SLinus Torvalds continue;
2501da177e4SLinus Torvalds printk("%s Error Reported by %s",
2511da177e4SLinus Torvalds err_print_prefix, port_names[i]);
2521da177e4SLinus Torvalds }
2531da177e4SLinus Torvalds }
2541da177e4SLinus Torvalds
2551da177e4SLinus Torvalds if (EXTRACT(valid_mask, IO7__PO7_UNCRR_SYM__STRV_VTR)) {
2561da177e4SLinus Torvalds char starvation_message[80];
2571da177e4SLinus Torvalds
2581da177e4SLinus Torvalds scratch = EXTRACT(uncrr_sym, IO7__PO7_UNCRR_SYM__STRV_VTR);
2591da177e4SLinus Torvalds if (scratch & IO7__STRV_VTR__IS_MSI)
2601da177e4SLinus Torvalds sprintf(starvation_message,
2611da177e4SLinus Torvalds "MSI Interrupt 0x%x",
2621da177e4SLinus Torvalds EXTRACT(scratch, IO7__STRV_VTR__MSI__INTNUM));
2631da177e4SLinus Torvalds else
2641da177e4SLinus Torvalds sprintf(starvation_message,
2651da177e4SLinus Torvalds "LSI INT%c for Bus:Slot (%d:%d)\n",
2661da177e4SLinus Torvalds 'A' + EXTRACT(scratch,
2671da177e4SLinus Torvalds IO7__STRV_VTR__LSI__INTX),
2681da177e4SLinus Torvalds EXTRACT(scratch, IO7__STRV_VTR__LSI__BUS),
2691da177e4SLinus Torvalds EXTRACT(scratch, IO7__STRV_VTR__LSI__SLOT));
2701da177e4SLinus Torvalds
2711da177e4SLinus Torvalds printk("%s Starvation Int Trigger By: %s\n",
2721da177e4SLinus Torvalds err_print_prefix, starvation_message);
2731da177e4SLinus Torvalds }
2741da177e4SLinus Torvalds }
2751da177e4SLinus Torvalds
2761da177e4SLinus Torvalds static void
marvel_print_po7_ugbge_sym(u64 ugbge_sym)2771da177e4SLinus Torvalds marvel_print_po7_ugbge_sym(u64 ugbge_sym)
2781da177e4SLinus Torvalds {
2791da177e4SLinus Torvalds char opcode_str[10];
2801da177e4SLinus Torvalds
2811da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_PKT_OFF__S (6)
2821da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_PKT_OFF__M (0xfffffffful)
2831da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_OPCODE__S (40)
2841da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_OPCODE__M (0xff)
2851da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_SRC_PORT__S (48)
2861da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_SRC_PORT__M (0xf)
2871da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_DEST_PID__S (52)
2881da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__UPH_DEST_PID__M (0x7ff)
2891da177e4SLinus Torvalds #define IO7__PO7_UGBGE_SYM__VALID (1UL << 63)
2901da177e4SLinus Torvalds
2911da177e4SLinus Torvalds if (!(ugbge_sym & IO7__PO7_UGBGE_SYM__VALID))
2921da177e4SLinus Torvalds return;
2931da177e4SLinus Torvalds
2941da177e4SLinus Torvalds switch(EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_OPCODE)) {
2951da177e4SLinus Torvalds case 0x51:
2961da177e4SLinus Torvalds sprintf(opcode_str, "Wr32");
2971da177e4SLinus Torvalds break;
2981da177e4SLinus Torvalds case 0x50:
2991da177e4SLinus Torvalds sprintf(opcode_str, "WrQW");
3001da177e4SLinus Torvalds break;
3011da177e4SLinus Torvalds case 0x54:
3021da177e4SLinus Torvalds sprintf(opcode_str, "WrIPR");
3031da177e4SLinus Torvalds break;
3041da177e4SLinus Torvalds case 0xD8:
3051da177e4SLinus Torvalds sprintf(opcode_str, "Victim");
3061da177e4SLinus Torvalds break;
3071da177e4SLinus Torvalds case 0xC5:
3081da177e4SLinus Torvalds sprintf(opcode_str, "BlkIO");
3091da177e4SLinus Torvalds break;
3101da177e4SLinus Torvalds default:
3115f0e3da6SRandy Dunlap sprintf(opcode_str, "0x%llx\n",
3121da177e4SLinus Torvalds EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_OPCODE));
3131da177e4SLinus Torvalds break;
3141da177e4SLinus Torvalds }
3151da177e4SLinus Torvalds
3161da177e4SLinus Torvalds printk("%s Up Hose Garbage Symptom:\n"
3173e073367SMichael Cree "%s Source Port: %lld - Dest PID: %lld - OpCode: %s\n",
3181da177e4SLinus Torvalds err_print_prefix,
3191da177e4SLinus Torvalds err_print_prefix,
3201da177e4SLinus Torvalds EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_SRC_PORT),
3211da177e4SLinus Torvalds EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_DEST_PID),
3221da177e4SLinus Torvalds opcode_str);
3231da177e4SLinus Torvalds
3241da177e4SLinus Torvalds if (0xC5 != EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_OPCODE))
3255f0e3da6SRandy Dunlap printk("%s Packet Offset 0x%08llx\n",
3261da177e4SLinus Torvalds err_print_prefix,
3271da177e4SLinus Torvalds EXTRACT(ugbge_sym, IO7__PO7_UGBGE_SYM__UPH_PKT_OFF));
3281da177e4SLinus Torvalds }
3291da177e4SLinus Torvalds
3301da177e4SLinus Torvalds static void
marvel_print_po7_err_sum(struct ev7_pal_io_subpacket * io)3311da177e4SLinus Torvalds marvel_print_po7_err_sum(struct ev7_pal_io_subpacket *io)
3321da177e4SLinus Torvalds {
3331da177e4SLinus Torvalds u64 uncrr_sym_valid = 0;
3341da177e4SLinus Torvalds
3351da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_SBE (1UL << 32)
3361da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_SBE2 (1UL << 33)
3371da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_PIO_WBYTE (1UL << 34)
3381da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_CSR_NXM (1UL << 35)
3391da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_RPID_ACV (1UL << 36)
3401da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_RSP_NXM (1UL << 37)
3411da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_ERR_RESP (1UL << 38)
3421da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_CLK_DERR (1UL << 39)
3431da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_DAT_DBE (1UL << 40)
3441da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CR_DAT_GRBG (1UL << 41)
3451da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__MAF_TO (1UL << 42)
3461da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__UGBGE (1UL << 43)
3471da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__UN_MAF_LOST (1UL << 44)
3481da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__UN_PKT_OVF (1UL << 45)
3491da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__UN_CDT_OVF (1UL << 46)
3501da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__UN_DEALLOC (1UL << 47)
3511da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_CDT_TO (1UL << 51)
3521da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_CLK_HDR (1UL << 52)
3531da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_DBE_HDR (1UL << 53)
3541da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_GBG_HDR (1UL << 54)
3551da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_BAD_CMD (1UL << 55)
3561da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__HLT_INT (1UL << 56)
3571da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__HP_INT (1UL << 57)
3581da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__CRD_INT (1UL << 58)
3591da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__STV_INT (1UL << 59)
3601da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__HRD_INT (1UL << 60)
3611da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__BH_SUM (1UL << 61)
3621da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__ERR_LST (1UL << 62)
3631da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__ERR_VALID (1UL << 63)
3641da177e4SLinus Torvalds
3651da177e4SLinus Torvalds #define IO7__PO7_ERRSUM__ERR_MASK (IO7__PO7_ERRSUM__ERR_VALID | \
3661da177e4SLinus Torvalds IO7__PO7_ERRSUM__CR_SBE)
3671da177e4SLinus Torvalds
3681da177e4SLinus Torvalds /*
3691da177e4SLinus Torvalds * Single bit errors aren't covered by ERR_VALID.
3701da177e4SLinus Torvalds */
3711da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_SBE) {
3721da177e4SLinus Torvalds printk("%s %sSingle Bit Error(s) detected/corrected\n",
3731da177e4SLinus Torvalds err_print_prefix,
3741da177e4SLinus Torvalds (io->po7_error_sum & IO7__PO7_ERRSUM__CR_SBE2)
3751da177e4SLinus Torvalds ? "Multiple " : "");
3761da177e4SLinus Torvalds marvel_print_po7_crrct_sym(io->po7_crrct_sym);
3771da177e4SLinus Torvalds }
3781da177e4SLinus Torvalds
3791da177e4SLinus Torvalds /*
3801da177e4SLinus Torvalds * Neither are the interrupt status bits
3811da177e4SLinus Torvalds */
3821da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__HLT_INT)
3831da177e4SLinus Torvalds printk("%s Halt Interrupt posted", err_print_prefix);
3841da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__HP_INT) {
3851da177e4SLinus Torvalds printk("%s Hot Plug Event Interrupt posted",
3861da177e4SLinus Torvalds err_print_prefix);
3871da177e4SLinus Torvalds uncrr_sym_valid |= GEN_MASK(IO7__PO7_UNCRR_SYM__DETECT_SP);
3881da177e4SLinus Torvalds }
3891da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CRD_INT)
3901da177e4SLinus Torvalds printk("%s Correctable Error Interrupt posted",
3911da177e4SLinus Torvalds err_print_prefix);
3921da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__STV_INT) {
3931da177e4SLinus Torvalds printk("%s Starvation Interrupt posted", err_print_prefix);
3941da177e4SLinus Torvalds uncrr_sym_valid |= GEN_MASK(IO7__PO7_UNCRR_SYM__STRV_VTR);
3951da177e4SLinus Torvalds }
3961da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__HRD_INT) {
3971da177e4SLinus Torvalds printk("%s Hard Error Interrupt posted", err_print_prefix);
3981da177e4SLinus Torvalds uncrr_sym_valid |= GEN_MASK(IO7__PO7_UNCRR_SYM__DETECT_SP);
3991da177e4SLinus Torvalds }
4001da177e4SLinus Torvalds
4011da177e4SLinus Torvalds /*
4021da177e4SLinus Torvalds * Everything else is valid only with ERR_VALID, so skip to the end
4031da177e4SLinus Torvalds * (uncrr_sym check) unless ERR_VALID is set.
4041da177e4SLinus Torvalds */
4051da177e4SLinus Torvalds if (!(io->po7_error_sum & IO7__PO7_ERRSUM__ERR_VALID))
4061da177e4SLinus Torvalds goto check_uncrr_sym;
4071da177e4SLinus Torvalds
4081da177e4SLinus Torvalds /*
4091da177e4SLinus Torvalds * Since ERR_VALID is set, VICTIM_SP in uncrr_sym is valid.
4101da177e4SLinus Torvalds * For bits [29:0] to also be valid, the following bits must
4111da177e4SLinus Torvalds * not be set:
4121da177e4SLinus Torvalds * CR_PIO_WBYTE CR_CSR_NXM CR_RSP_NXM
4131da177e4SLinus Torvalds * CR_ERR_RESP MAF_TO
4141da177e4SLinus Torvalds */
4151da177e4SLinus Torvalds uncrr_sym_valid |= GEN_MASK(IO7__PO7_UNCRR_SYM__VICTIM_SP);
4161da177e4SLinus Torvalds if (!(io->po7_error_sum & (IO7__PO7_ERRSUM__CR_PIO_WBYTE |
4171da177e4SLinus Torvalds IO7__PO7_ERRSUM__CR_CSR_NXM |
4181da177e4SLinus Torvalds IO7__PO7_ERRSUM__CR_RSP_NXM |
4191da177e4SLinus Torvalds IO7__PO7_ERRSUM__CR_ERR_RESP |
4201da177e4SLinus Torvalds IO7__PO7_ERRSUM__MAF_TO)))
4211da177e4SLinus Torvalds uncrr_sym_valid |= 0x3ffffffful;
4221da177e4SLinus Torvalds
4231da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_PIO_WBYTE)
4241da177e4SLinus Torvalds printk("%s Write byte into IO7 CSR\n", err_print_prefix);
4251da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_CSR_NXM)
4261da177e4SLinus Torvalds printk("%s PIO to non-existent CSR\n", err_print_prefix);
4271da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_RPID_ACV)
4281da177e4SLinus Torvalds printk("%s Bus Requester PID (Access Violation)\n",
4291da177e4SLinus Torvalds err_print_prefix);
4301da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_RSP_NXM)
4311da177e4SLinus Torvalds printk("%s Received NXM response from EV7\n",
4321da177e4SLinus Torvalds err_print_prefix);
4331da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_ERR_RESP)
4341da177e4SLinus Torvalds printk("%s Received ERROR RESPONSE\n", err_print_prefix);
4351da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_CLK_DERR)
4361da177e4SLinus Torvalds printk("%s Clock error on data flit\n", err_print_prefix);
4371da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_DAT_DBE)
4381da177e4SLinus Torvalds printk("%s Double Bit Error Data Error Detected\n",
4391da177e4SLinus Torvalds err_print_prefix);
4401da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__CR_DAT_GRBG)
4411da177e4SLinus Torvalds printk("%s Garbage Encoding Detected on the data\n",
4421da177e4SLinus Torvalds err_print_prefix);
4431da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__UGBGE) {
4441da177e4SLinus Torvalds printk("%s Garbage Encoding sent up hose\n",
4451da177e4SLinus Torvalds err_print_prefix);
4461da177e4SLinus Torvalds marvel_print_po7_ugbge_sym(io->po7_ugbge_sym);
4471da177e4SLinus Torvalds }
4481da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__UN_MAF_LOST)
4491da177e4SLinus Torvalds printk("%s Orphan response (unexpected response)\n",
4501da177e4SLinus Torvalds err_print_prefix);
4511da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__UN_PKT_OVF)
4521da177e4SLinus Torvalds printk("%s Down hose packet overflow\n", err_print_prefix);
4531da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__UN_CDT_OVF)
4541da177e4SLinus Torvalds printk("%s Down hose credit overflow\n", err_print_prefix);
4551da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__UN_DEALLOC)
4561da177e4SLinus Torvalds printk("%s Unexpected or bad dealloc field\n",
4571da177e4SLinus Torvalds err_print_prefix);
4581da177e4SLinus Torvalds
4591da177e4SLinus Torvalds /*
4601da177e4SLinus Torvalds * The black hole events.
4611da177e4SLinus Torvalds */
4621da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__MAF_TO)
4631da177e4SLinus Torvalds printk("%s BLACK HOLE: Timeout for all responses\n",
4641da177e4SLinus Torvalds err_print_prefix);
4651da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__BH_CDT_TO)
4661da177e4SLinus Torvalds printk("%s BLACK HOLE: Credit Timeout\n", err_print_prefix);
4671da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__BH_CLK_HDR)
4681da177e4SLinus Torvalds printk("%s BLACK HOLE: Clock check on header\n",
4691da177e4SLinus Torvalds err_print_prefix);
4701da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__BH_DBE_HDR)
4711da177e4SLinus Torvalds printk("%s BLACK HOLE: Uncorrectable Error on header\n",
4721da177e4SLinus Torvalds err_print_prefix);
4731da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__BH_GBG_HDR)
4741da177e4SLinus Torvalds printk("%s BLACK HOLE: Garbage on header\n",
4751da177e4SLinus Torvalds err_print_prefix);
4761da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__BH_BAD_CMD)
4771da177e4SLinus Torvalds printk("%s BLACK HOLE: Bad EV7 command\n",
4781da177e4SLinus Torvalds err_print_prefix);
4791da177e4SLinus Torvalds
4801da177e4SLinus Torvalds if (io->po7_error_sum & IO7__PO7_ERRSUM__ERR_LST)
4811da177e4SLinus Torvalds printk("%s Lost Error\n", err_print_prefix);
4821da177e4SLinus Torvalds
4831da177e4SLinus Torvalds printk("%s Failing Packet:\n"
4845f0e3da6SRandy Dunlap "%s Cycle 1: %016llx\n"
4855f0e3da6SRandy Dunlap "%s Cycle 2: %016llx\n",
4861da177e4SLinus Torvalds err_print_prefix,
4871da177e4SLinus Torvalds err_print_prefix, io->po7_err_pkt0,
4881da177e4SLinus Torvalds err_print_prefix, io->po7_err_pkt1);
4891da177e4SLinus Torvalds /*
4901da177e4SLinus Torvalds * If there are any valid bits in UNCRR sym for this err,
4911da177e4SLinus Torvalds * print UNCRR_SYM as well.
4921da177e4SLinus Torvalds */
4931da177e4SLinus Torvalds check_uncrr_sym:
4941da177e4SLinus Torvalds if (uncrr_sym_valid)
4951da177e4SLinus Torvalds marvel_print_po7_uncrr_sym(io->po7_uncrr_sym, uncrr_sym_valid);
4961da177e4SLinus Torvalds }
4971da177e4SLinus Torvalds
4981da177e4SLinus Torvalds static void
marvel_print_pox_tlb_err(u64 tlb_err)4991da177e4SLinus Torvalds marvel_print_pox_tlb_err(u64 tlb_err)
5001da177e4SLinus Torvalds {
5011da177e4SLinus Torvalds static char *tlb_errors[] = {
5021da177e4SLinus Torvalds "No Error",
5031da177e4SLinus Torvalds "North Port Signaled Error fetching TLB entry",
5041da177e4SLinus Torvalds "PTE invalid or UCC or GBG error on this entry",
5051da177e4SLinus Torvalds "Address did not hit any DMA window"
5061da177e4SLinus Torvalds };
5071da177e4SLinus Torvalds
5081da177e4SLinus Torvalds #define IO7__POX_TLBERR__ERR_VALID (1UL << 63)
5091da177e4SLinus Torvalds #define IO7__POX_TLBERR__ERRCODE__S (0)
5101da177e4SLinus Torvalds #define IO7__POX_TLBERR__ERRCODE__M (0x3)
5111da177e4SLinus Torvalds #define IO7__POX_TLBERR__ERR_TLB_PTR__S (3)
5121da177e4SLinus Torvalds #define IO7__POX_TLBERR__ERR_TLB_PTR__M (0x7)
5131da177e4SLinus Torvalds #define IO7__POX_TLBERR__FADDR__S (6)
5141da177e4SLinus Torvalds #define IO7__POX_TLBERR__FADDR__M (0x3fffffffffful)
5151da177e4SLinus Torvalds
5161da177e4SLinus Torvalds if (!(tlb_err & IO7__POX_TLBERR__ERR_VALID))
5171da177e4SLinus Torvalds return;
5181da177e4SLinus Torvalds
5195f0e3da6SRandy Dunlap printk("%s TLB Error on index 0x%llx:\n"
5201da177e4SLinus Torvalds "%s - %s\n"
5215f0e3da6SRandy Dunlap "%s - Addr: 0x%016llx\n",
5221da177e4SLinus Torvalds err_print_prefix,
5231da177e4SLinus Torvalds EXTRACT(tlb_err, IO7__POX_TLBERR__ERR_TLB_PTR),
5241da177e4SLinus Torvalds err_print_prefix,
5251da177e4SLinus Torvalds tlb_errors[EXTRACT(tlb_err, IO7__POX_TLBERR__ERRCODE)],
5261da177e4SLinus Torvalds err_print_prefix,
5271da177e4SLinus Torvalds EXTRACT(tlb_err, IO7__POX_TLBERR__FADDR) << 6);
5281da177e4SLinus Torvalds }
5291da177e4SLinus Torvalds
5301da177e4SLinus Torvalds static void
marvel_print_pox_spl_cmplt(u64 spl_cmplt)5311da177e4SLinus Torvalds marvel_print_pox_spl_cmplt(u64 spl_cmplt)
5321da177e4SLinus Torvalds {
5331da177e4SLinus Torvalds char message[80];
5341da177e4SLinus Torvalds
5351da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MESSAGE__S (0)
5361da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MESSAGE__M (0x0fffffffful)
5371da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_BUS__S (40)
5381da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_BUS__M (0xfful)
5391da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_DEV__S (35)
5401da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_DEV__M (0x1ful)
5411da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_FUNC__S (32)
5421da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__SOURCE_FUNC__M (0x07ul)
5431da177e4SLinus Torvalds
5441da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_CLASS__S (28)
5451da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_CLASS__M (0xf)
5461da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_INDEX__S (20)
5471da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_INDEX__M (0xff)
5481da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_CLASSINDEX__S (20)
5491da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__MSG_CLASSINDEX__M (0xfff)
5501da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__REM_LOWER_ADDR__S (12)
5511da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__REM_LOWER_ADDR__M (0x7f)
5521da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__REM_BYTE_COUNT__S (0)
5531da177e4SLinus Torvalds #define IO7__POX_SPLCMPLT__REM_BYTE_COUNT__M (0xfff)
5541da177e4SLinus Torvalds
5551da177e4SLinus Torvalds printk("%s Split Completion Error:\n"
5563e073367SMichael Cree "%s Source (Bus:Dev:Func): %lld:%lld:%lld\n",
5571da177e4SLinus Torvalds err_print_prefix,
5581da177e4SLinus Torvalds err_print_prefix,
5591da177e4SLinus Torvalds EXTRACT(spl_cmplt, IO7__POX_SPLCMPLT__SOURCE_BUS),
5601da177e4SLinus Torvalds EXTRACT(spl_cmplt, IO7__POX_SPLCMPLT__SOURCE_DEV),
5611da177e4SLinus Torvalds EXTRACT(spl_cmplt, IO7__POX_SPLCMPLT__SOURCE_FUNC));
5621da177e4SLinus Torvalds
5631da177e4SLinus Torvalds switch(EXTRACT(spl_cmplt, IO7__POX_SPLCMPLT__MSG_CLASSINDEX)) {
5641da177e4SLinus Torvalds case 0x000:
5651da177e4SLinus Torvalds sprintf(message, "Normal completion");
5661da177e4SLinus Torvalds break;
5671da177e4SLinus Torvalds case 0x100:
5681da177e4SLinus Torvalds sprintf(message, "Bridge - Master Abort");
5691da177e4SLinus Torvalds break;
5701da177e4SLinus Torvalds case 0x101:
5711da177e4SLinus Torvalds sprintf(message, "Bridge - Target Abort");
5721da177e4SLinus Torvalds break;
5731da177e4SLinus Torvalds case 0x102:
5741da177e4SLinus Torvalds sprintf(message, "Bridge - Uncorrectable Write Data Error");
5751da177e4SLinus Torvalds break;
5761da177e4SLinus Torvalds case 0x200:
5771da177e4SLinus Torvalds sprintf(message, "Byte Count Out of Range");
5781da177e4SLinus Torvalds break;
5791da177e4SLinus Torvalds case 0x201:
5801da177e4SLinus Torvalds sprintf(message, "Uncorrectable Split Write Data Error");
5811da177e4SLinus Torvalds break;
5821da177e4SLinus Torvalds default:
5835f0e3da6SRandy Dunlap sprintf(message, "%08llx\n",
5841da177e4SLinus Torvalds EXTRACT(spl_cmplt, IO7__POX_SPLCMPLT__MESSAGE));
5851da177e4SLinus Torvalds break;
5861da177e4SLinus Torvalds }
5871da177e4SLinus Torvalds printk("%s Message: %s\n", err_print_prefix, message);
5881da177e4SLinus Torvalds }
5891da177e4SLinus Torvalds
5901da177e4SLinus Torvalds static void
marvel_print_pox_trans_sum(u64 trans_sum)5911da177e4SLinus Torvalds marvel_print_pox_trans_sum(u64 trans_sum)
5921da177e4SLinus Torvalds {
59331019075SJoe Perches static const char * const pcix_cmd[] = {
59431019075SJoe Perches "Interrupt Acknowledge",
5951da177e4SLinus Torvalds "Special Cycle",
5961da177e4SLinus Torvalds "I/O Read",
5971da177e4SLinus Torvalds "I/O Write",
5981da177e4SLinus Torvalds "Reserved",
5991da177e4SLinus Torvalds "Reserved / Device ID Message",
6001da177e4SLinus Torvalds "Memory Read",
6011da177e4SLinus Torvalds "Memory Write",
6021da177e4SLinus Torvalds "Reserved / Alias to Memory Read Block",
6031da177e4SLinus Torvalds "Reserved / Alias to Memory Write Block",
6041da177e4SLinus Torvalds "Configuration Read",
6051da177e4SLinus Torvalds "Configuration Write",
6061da177e4SLinus Torvalds "Memory Read Multiple / Split Completion",
6071da177e4SLinus Torvalds "Dual Address Cycle",
6081da177e4SLinus Torvalds "Memory Read Line / Memory Read Block",
6091da177e4SLinus Torvalds "Memory Write and Invalidate / Memory Write Block"
6101da177e4SLinus Torvalds };
6111da177e4SLinus Torvalds
6121da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCI_ADDR__S (0)
6131da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCI_ADDR__M (0x3fffffffffffful)
6141da177e4SLinus Torvalds #define IO7__POX_TRANSUM__DAC (1UL << 50)
6151da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCIX_MASTER_SLOT__S (52)
6161da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCIX_MASTER_SLOT__M (0xf)
6171da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCIX_CMD__S (56)
6181da177e4SLinus Torvalds #define IO7__POX_TRANSUM__PCIX_CMD__M (0xf)
6191da177e4SLinus Torvalds #define IO7__POX_TRANSUM__ERR_VALID (1UL << 63)
6201da177e4SLinus Torvalds
6211da177e4SLinus Torvalds if (!(trans_sum & IO7__POX_TRANSUM__ERR_VALID))
6221da177e4SLinus Torvalds return;
6231da177e4SLinus Torvalds
6241da177e4SLinus Torvalds printk("%s Transaction Summary:\n"
6255f0e3da6SRandy Dunlap "%s Command: 0x%llx - %s\n"
6265f0e3da6SRandy Dunlap "%s Address: 0x%016llx%s\n"
6275f0e3da6SRandy Dunlap "%s PCI-X Master Slot: 0x%llx\n",
6281da177e4SLinus Torvalds err_print_prefix,
6291da177e4SLinus Torvalds err_print_prefix,
6301da177e4SLinus Torvalds EXTRACT(trans_sum, IO7__POX_TRANSUM__PCIX_CMD),
6311da177e4SLinus Torvalds pcix_cmd[EXTRACT(trans_sum, IO7__POX_TRANSUM__PCIX_CMD)],
6321da177e4SLinus Torvalds err_print_prefix,
6331da177e4SLinus Torvalds EXTRACT(trans_sum, IO7__POX_TRANSUM__PCI_ADDR),
6341da177e4SLinus Torvalds (trans_sum & IO7__POX_TRANSUM__DAC) ? " (DAC)" : "",
6351da177e4SLinus Torvalds err_print_prefix,
6361da177e4SLinus Torvalds EXTRACT(trans_sum, IO7__POX_TRANSUM__PCIX_MASTER_SLOT));
6371da177e4SLinus Torvalds }
6381da177e4SLinus Torvalds
6391da177e4SLinus Torvalds static void
marvel_print_pox_err(u64 err_sum,struct ev7_pal_io_one_port * port)6401da177e4SLinus Torvalds marvel_print_pox_err(u64 err_sum, struct ev7_pal_io_one_port *port)
6411da177e4SLinus Torvalds {
6421da177e4SLinus Torvalds #define IO7__POX_ERRSUM__AGP_REQQ_OVFL (1UL << 4)
6431da177e4SLinus Torvalds #define IO7__POX_ERRSUM__AGP_SYNC_ERR (1UL << 5)
6441da177e4SLinus Torvalds #define IO7__POX_ERRSUM__MRETRY_TO (1UL << 6)
6451da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PCIX_UX_SPL (1UL << 7)
6461da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PCIX_SPLIT_TO (1UL << 8)
6471da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PCIX_DISCARD_SPL (1UL << 9)
6481da177e4SLinus Torvalds #define IO7__POX_ERRSUM__DMA_RD_TO (1UL << 10)
6491da177e4SLinus Torvalds #define IO7__POX_ERRSUM__CSR_NXM_RD (1UL << 11)
6501da177e4SLinus Torvalds #define IO7__POX_ERRSUM__CSR_NXM_WR (1UL << 12)
6511da177e4SLinus Torvalds #define IO7__POX_ERRSUM__DMA_TO (1UL << 13)
6521da177e4SLinus Torvalds #define IO7__POX_ERRSUM__ALL_MABORTS (1UL << 14)
6531da177e4SLinus Torvalds #define IO7__POX_ERRSUM__MABORT (1UL << 15)
6541da177e4SLinus Torvalds #define IO7__POX_ERRSUM__MABORT_MASK (IO7__POX_ERRSUM__ALL_MABORTS|\
6551da177e4SLinus Torvalds IO7__POX_ERRSUM__MABORT)
6561da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PT_TABORT (1UL << 16)
6571da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PM_TABORT (1UL << 17)
6581da177e4SLinus Torvalds #define IO7__POX_ERRSUM__TABORT_MASK (IO7__POX_ERRSUM__PT_TABORT | \
6591da177e4SLinus Torvalds IO7__POX_ERRSUM__PM_TABORT)
6601da177e4SLinus Torvalds #define IO7__POX_ERRSUM__SERR (1UL << 18)
6611da177e4SLinus Torvalds #define IO7__POX_ERRSUM__ADDRERR_STB (1UL << 19)
6621da177e4SLinus Torvalds #define IO7__POX_ERRSUM__DETECTED_SERR (1UL << 20)
6631da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PERR (1UL << 21)
6641da177e4SLinus Torvalds #define IO7__POX_ERRSUM__DATAERR_STB_NIOW (1UL << 22)
6651da177e4SLinus Torvalds #define IO7__POX_ERRSUM__DETECTED_PERR (1UL << 23)
6661da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PM_PERR (1UL << 24)
6671da177e4SLinus Torvalds #define IO7__POX_ERRSUM__PT_SCERROR (1UL << 26)
6681da177e4SLinus Torvalds #define IO7__POX_ERRSUM__HUNG_BUS (1UL << 28)
6691da177e4SLinus Torvalds #define IO7__POX_ERRSUM__UPE_ERROR__S (51)
6701da177e4SLinus Torvalds #define IO7__POX_ERRSUM__UPE_ERROR__M (0xffUL)
6711da177e4SLinus Torvalds #define IO7__POX_ERRSUM__UPE_ERROR GEN_MASK(IO7__POX_ERRSUM__UPE_ERROR)
6721da177e4SLinus Torvalds #define IO7__POX_ERRSUM__TLB_ERR (1UL << 59)
6731da177e4SLinus Torvalds #define IO7__POX_ERRSUM__ERR_VALID (1UL << 63)
6741da177e4SLinus Torvalds
6751da177e4SLinus Torvalds #define IO7__POX_ERRSUM__TRANS_SUM__MASK (IO7__POX_ERRSUM__MRETRY_TO | \
6761da177e4SLinus Torvalds IO7__POX_ERRSUM__PCIX_UX_SPL | \
6771da177e4SLinus Torvalds IO7__POX_ERRSUM__PCIX_SPLIT_TO | \
6781da177e4SLinus Torvalds IO7__POX_ERRSUM__DMA_TO | \
6791da177e4SLinus Torvalds IO7__POX_ERRSUM__MABORT_MASK | \
6801da177e4SLinus Torvalds IO7__POX_ERRSUM__TABORT_MASK | \
6811da177e4SLinus Torvalds IO7__POX_ERRSUM__SERR | \
6821da177e4SLinus Torvalds IO7__POX_ERRSUM__ADDRERR_STB | \
6831da177e4SLinus Torvalds IO7__POX_ERRSUM__PERR | \
6841da177e4SLinus Torvalds IO7__POX_ERRSUM__DATAERR_STB_NIOW |\
6851da177e4SLinus Torvalds IO7__POX_ERRSUM__DETECTED_PERR | \
6861da177e4SLinus Torvalds IO7__POX_ERRSUM__PM_PERR | \
6871da177e4SLinus Torvalds IO7__POX_ERRSUM__PT_SCERROR | \
6881da177e4SLinus Torvalds IO7__POX_ERRSUM__UPE_ERROR)
6891da177e4SLinus Torvalds
6901da177e4SLinus Torvalds if (!(err_sum & IO7__POX_ERRSUM__ERR_VALID))
6911da177e4SLinus Torvalds return;
6921da177e4SLinus Torvalds
6931da177e4SLinus Torvalds /*
6941da177e4SLinus Torvalds * First the transaction summary errors
6951da177e4SLinus Torvalds */
6961da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__MRETRY_TO)
6971da177e4SLinus Torvalds printk("%s IO7 Master Retry Timeout expired\n",
6981da177e4SLinus Torvalds err_print_prefix);
6991da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PCIX_UX_SPL)
7001da177e4SLinus Torvalds printk("%s Unexpected Split Completion\n",
7011da177e4SLinus Torvalds err_print_prefix);
7021da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PCIX_SPLIT_TO)
7031da177e4SLinus Torvalds printk("%s IO7 Split Completion Timeout expired\n",
7041da177e4SLinus Torvalds err_print_prefix);
7051da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__DMA_TO)
7061da177e4SLinus Torvalds printk("%s Hung bus during DMA transaction\n",
7071da177e4SLinus Torvalds err_print_prefix);
7081da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__MABORT_MASK)
7091da177e4SLinus Torvalds printk("%s Master Abort\n", err_print_prefix);
7101da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PT_TABORT)
7111da177e4SLinus Torvalds printk("%s IO7 Asserted Target Abort\n", err_print_prefix);
7121da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PM_TABORT)
7131da177e4SLinus Torvalds printk("%s IO7 Received Target Abort\n", err_print_prefix);
7141da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__ADDRERR_STB) {
7151da177e4SLinus Torvalds printk("%s Address or PCI-X Attribute Parity Error\n",
7161da177e4SLinus Torvalds err_print_prefix);
7171da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__SERR)
7181da177e4SLinus Torvalds printk("%s IO7 Asserted SERR\n", err_print_prefix);
7191da177e4SLinus Torvalds }
7201da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PERR) {
7211da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__DATAERR_STB_NIOW)
7221da177e4SLinus Torvalds printk("%s IO7 Detected Data Parity Error\n",
7231da177e4SLinus Torvalds err_print_prefix);
7241da177e4SLinus Torvalds else
7251da177e4SLinus Torvalds printk("%s Split Completion Response with "
7261da177e4SLinus Torvalds "Parity Error\n", err_print_prefix);
7271da177e4SLinus Torvalds }
7281da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__DETECTED_PERR)
7291da177e4SLinus Torvalds printk("%s PERR detected\n", err_print_prefix);
7301da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PM_PERR)
7311da177e4SLinus Torvalds printk("%s PERR while IO7 is master\n", err_print_prefix);
7321da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PT_SCERROR) {
7331da177e4SLinus Torvalds printk("%s IO7 Received Split Completion Error message\n",
7341da177e4SLinus Torvalds err_print_prefix);
7351da177e4SLinus Torvalds marvel_print_pox_spl_cmplt(port->pox_spl_cmplt);
7361da177e4SLinus Torvalds }
7371da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__UPE_ERROR) {
7381da177e4SLinus Torvalds unsigned int upe_error = EXTRACT(err_sum,
7391da177e4SLinus Torvalds IO7__POX_ERRSUM__UPE_ERROR);
7401da177e4SLinus Torvalds int i;
7411da177e4SLinus Torvalds static char *upe_errors[] = {
7421da177e4SLinus Torvalds "Parity Error on MSI write data",
7431da177e4SLinus Torvalds "MSI read (MSI window is write only",
7441da177e4SLinus Torvalds "TLB - Invalid WR transaction",
7451da177e4SLinus Torvalds "TLB - Invalid RD transaction",
7461da177e4SLinus Torvalds "DMA - WR error (see north port)",
7471da177e4SLinus Torvalds "DMA - RD error (see north port)",
7481da177e4SLinus Torvalds "PPR - WR error (see north port)",
7491da177e4SLinus Torvalds "PPR - RD error (see north port)"
7501da177e4SLinus Torvalds };
7511da177e4SLinus Torvalds
7521da177e4SLinus Torvalds printk("%s UPE Error:\n", err_print_prefix);
7531da177e4SLinus Torvalds for (i = 0; i < 8; i++) {
7541da177e4SLinus Torvalds if (upe_error & (1 << i))
7551da177e4SLinus Torvalds printk("%s %s\n", err_print_prefix,
7561da177e4SLinus Torvalds upe_errors[i]);
7571da177e4SLinus Torvalds }
7581da177e4SLinus Torvalds }
7591da177e4SLinus Torvalds
7601da177e4SLinus Torvalds /*
7611da177e4SLinus Torvalds * POx_TRANS_SUM, if appropriate.
7621da177e4SLinus Torvalds */
7631da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__TRANS_SUM__MASK)
7641da177e4SLinus Torvalds marvel_print_pox_trans_sum(port->pox_trans_sum);
7651da177e4SLinus Torvalds
7661da177e4SLinus Torvalds /*
7671da177e4SLinus Torvalds * Then TLB_ERR.
7681da177e4SLinus Torvalds */
7691da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__TLB_ERR) {
7701da177e4SLinus Torvalds printk("%s TLB ERROR\n", err_print_prefix);
7711da177e4SLinus Torvalds marvel_print_pox_tlb_err(port->pox_tlb_err);
7721da177e4SLinus Torvalds }
7731da177e4SLinus Torvalds
7741da177e4SLinus Torvalds /*
7751da177e4SLinus Torvalds * And the single bit status errors.
7761da177e4SLinus Torvalds */
7771da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__AGP_REQQ_OVFL)
7781da177e4SLinus Torvalds printk("%s AGP Request Queue Overflow\n", err_print_prefix);
7791da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__AGP_SYNC_ERR)
7801da177e4SLinus Torvalds printk("%s AGP Sync Error\n", err_print_prefix);
7811da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__PCIX_DISCARD_SPL)
7821da177e4SLinus Torvalds printk("%s Discarded split completion\n", err_print_prefix);
7831da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__DMA_RD_TO)
7841da177e4SLinus Torvalds printk("%s DMA Read Timeout\n", err_print_prefix);
7851da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__CSR_NXM_RD)
7861da177e4SLinus Torvalds printk("%s CSR NXM READ\n", err_print_prefix);
7871da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__CSR_NXM_WR)
7881da177e4SLinus Torvalds printk("%s CSR NXM WRITE\n", err_print_prefix);
7891da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__DETECTED_SERR)
7901da177e4SLinus Torvalds printk("%s SERR detected\n", err_print_prefix);
7911da177e4SLinus Torvalds if (err_sum & IO7__POX_ERRSUM__HUNG_BUS)
7921da177e4SLinus Torvalds printk("%s HUNG BUS detected\n", err_print_prefix);
7931da177e4SLinus Torvalds }
7941da177e4SLinus Torvalds
7951da177e4SLinus Torvalds #endif /* CONFIG_VERBOSE_MCHECK */
7961da177e4SLinus Torvalds
7971da177e4SLinus Torvalds static struct ev7_pal_io_subpacket *
marvel_find_io7_with_error(struct ev7_lf_subpackets * lf_subpackets)7981da177e4SLinus Torvalds marvel_find_io7_with_error(struct ev7_lf_subpackets *lf_subpackets)
7991da177e4SLinus Torvalds {
8001da177e4SLinus Torvalds struct ev7_pal_io_subpacket *io = lf_subpackets->io;
8011da177e4SLinus Torvalds struct io7 *io7;
8021da177e4SLinus Torvalds int i;
8031da177e4SLinus Torvalds
8041da177e4SLinus Torvalds /*
8051da177e4SLinus Torvalds * Caller must provide the packet to fill
8061da177e4SLinus Torvalds */
8071da177e4SLinus Torvalds if (!io)
8081da177e4SLinus Torvalds return NULL;
8091da177e4SLinus Torvalds
8101da177e4SLinus Torvalds /*
8111da177e4SLinus Torvalds * Fill the subpacket with the console's standard fill pattern
8121da177e4SLinus Torvalds */
8131da177e4SLinus Torvalds memset(io, 0x55, sizeof(*io));
8141da177e4SLinus Torvalds
8151da177e4SLinus Torvalds for (io7 = NULL; NULL != (io7 = marvel_next_io7(io7)); ) {
8161da177e4SLinus Torvalds unsigned long err_sum = 0;
8171da177e4SLinus Torvalds
8181da177e4SLinus Torvalds err_sum |= io7->csrs->PO7_ERROR_SUM.csr;
8191da177e4SLinus Torvalds for (i = 0; i < IO7_NUM_PORTS; i++) {
8201da177e4SLinus Torvalds if (!io7->ports[i].enabled)
8211da177e4SLinus Torvalds continue;
8221da177e4SLinus Torvalds err_sum |= io7->ports[i].csrs->POx_ERR_SUM.csr;
8231da177e4SLinus Torvalds }
8241da177e4SLinus Torvalds
8251da177e4SLinus Torvalds /*
8261da177e4SLinus Torvalds * Is there at least one error?
8271da177e4SLinus Torvalds */
8281da177e4SLinus Torvalds if (err_sum & (1UL << 63))
8291da177e4SLinus Torvalds break;
8301da177e4SLinus Torvalds }
8311da177e4SLinus Torvalds
8321da177e4SLinus Torvalds /*
8331da177e4SLinus Torvalds * Did we find an IO7 with an error?
8341da177e4SLinus Torvalds */
8351da177e4SLinus Torvalds if (!io7)
8361da177e4SLinus Torvalds return NULL;
8371da177e4SLinus Torvalds
8381da177e4SLinus Torvalds /*
8391da177e4SLinus Torvalds * We have an IO7 with an error.
8401da177e4SLinus Torvalds *
8411da177e4SLinus Torvalds * Fill in the IO subpacket.
8421da177e4SLinus Torvalds */
8431da177e4SLinus Torvalds io->io_asic_rev = io7->csrs->IO_ASIC_REV.csr;
8441da177e4SLinus Torvalds io->io_sys_rev = io7->csrs->IO_SYS_REV.csr;
8451da177e4SLinus Torvalds io->io7_uph = io7->csrs->IO7_UPH.csr;
8461da177e4SLinus Torvalds io->hpi_ctl = io7->csrs->HPI_CTL.csr;
8471da177e4SLinus Torvalds io->crd_ctl = io7->csrs->CRD_CTL.csr;
8481da177e4SLinus Torvalds io->hei_ctl = io7->csrs->HEI_CTL.csr;
8491da177e4SLinus Torvalds io->po7_error_sum = io7->csrs->PO7_ERROR_SUM.csr;
8501da177e4SLinus Torvalds io->po7_uncrr_sym = io7->csrs->PO7_UNCRR_SYM.csr;
8511da177e4SLinus Torvalds io->po7_crrct_sym = io7->csrs->PO7_CRRCT_SYM.csr;
8521da177e4SLinus Torvalds io->po7_ugbge_sym = io7->csrs->PO7_UGBGE_SYM.csr;
8531da177e4SLinus Torvalds io->po7_err_pkt0 = io7->csrs->PO7_ERR_PKT[0].csr;
8541da177e4SLinus Torvalds io->po7_err_pkt1 = io7->csrs->PO7_ERR_PKT[1].csr;
8551da177e4SLinus Torvalds
8561da177e4SLinus Torvalds for (i = 0; i < IO7_NUM_PORTS; i++) {
8571da177e4SLinus Torvalds io7_ioport_csrs *csrs = io7->ports[i].csrs;
8581da177e4SLinus Torvalds
8591da177e4SLinus Torvalds if (!io7->ports[i].enabled)
8601da177e4SLinus Torvalds continue;
8611da177e4SLinus Torvalds
8621da177e4SLinus Torvalds io->ports[i].pox_err_sum = csrs->POx_ERR_SUM.csr;
8631da177e4SLinus Torvalds io->ports[i].pox_tlb_err = csrs->POx_TLB_ERR.csr;
8641da177e4SLinus Torvalds io->ports[i].pox_spl_cmplt = csrs->POx_SPL_COMPLT.csr;
8651da177e4SLinus Torvalds io->ports[i].pox_trans_sum = csrs->POx_TRANS_SUM.csr;
8661da177e4SLinus Torvalds io->ports[i].pox_first_err = csrs->POx_FIRST_ERR.csr;
8671da177e4SLinus Torvalds io->ports[i].pox_mult_err = csrs->POx_MULT_ERR.csr;
8681da177e4SLinus Torvalds io->ports[i].pox_dm_source = csrs->POx_DM_SOURCE.csr;
8691da177e4SLinus Torvalds io->ports[i].pox_dm_dest = csrs->POx_DM_DEST.csr;
8701da177e4SLinus Torvalds io->ports[i].pox_dm_size = csrs->POx_DM_SIZE.csr;
8711da177e4SLinus Torvalds io->ports[i].pox_dm_ctrl = csrs->POx_DM_CTRL.csr;
8721da177e4SLinus Torvalds
8731da177e4SLinus Torvalds /*
8741da177e4SLinus Torvalds * Ack this port's errors, if any. POx_ERR_SUM must be last.
8751da177e4SLinus Torvalds *
8761da177e4SLinus Torvalds * Most of the error registers get cleared and unlocked when
8771da177e4SLinus Torvalds * the associated bits in POx_ERR_SUM are cleared (by writing
8781da177e4SLinus Torvalds * 1). POx_TLB_ERR is an exception and must be explicitly
8791da177e4SLinus Torvalds * cleared.
8801da177e4SLinus Torvalds */
8811da177e4SLinus Torvalds csrs->POx_TLB_ERR.csr = io->ports[i].pox_tlb_err;
8821da177e4SLinus Torvalds csrs->POx_ERR_SUM.csr = io->ports[i].pox_err_sum;
8831da177e4SLinus Torvalds mb();
8841da177e4SLinus Torvalds csrs->POx_ERR_SUM.csr;
8851da177e4SLinus Torvalds }
8861da177e4SLinus Torvalds
8871da177e4SLinus Torvalds /*
8881da177e4SLinus Torvalds * Ack any port 7 error(s).
8891da177e4SLinus Torvalds */
8901da177e4SLinus Torvalds io7->csrs->PO7_ERROR_SUM.csr = io->po7_error_sum;
8911da177e4SLinus Torvalds mb();
8921da177e4SLinus Torvalds io7->csrs->PO7_ERROR_SUM.csr;
8931da177e4SLinus Torvalds
8941da177e4SLinus Torvalds /*
8951da177e4SLinus Torvalds * Correct the io7_pid.
8961da177e4SLinus Torvalds */
8971da177e4SLinus Torvalds lf_subpackets->io_pid = io7->pe;
8981da177e4SLinus Torvalds
8991da177e4SLinus Torvalds return io;
9001da177e4SLinus Torvalds }
9011da177e4SLinus Torvalds
9021da177e4SLinus Torvalds static int
marvel_process_io_error(struct ev7_lf_subpackets * lf_subpackets,int print)9031da177e4SLinus Torvalds marvel_process_io_error(struct ev7_lf_subpackets *lf_subpackets, int print)
9041da177e4SLinus Torvalds {
9051da177e4SLinus Torvalds int status = MCHK_DISPOSITION_UNKNOWN_ERROR;
9061da177e4SLinus Torvalds
9071da177e4SLinus Torvalds #ifdef CONFIG_VERBOSE_MCHECK
9081da177e4SLinus Torvalds struct ev7_pal_io_subpacket *io = lf_subpackets->io;
9091da177e4SLinus Torvalds int i;
9101da177e4SLinus Torvalds #endif /* CONFIG_VERBOSE_MCHECK */
9111da177e4SLinus Torvalds
9121da177e4SLinus Torvalds #define MARVEL_IO_ERR_VALID(x) ((x) & (1UL << 63))
9131da177e4SLinus Torvalds
9141da177e4SLinus Torvalds if (!lf_subpackets->logout || !lf_subpackets->io)
9151da177e4SLinus Torvalds return status;
9161da177e4SLinus Torvalds
9171da177e4SLinus Torvalds /*
9181da177e4SLinus Torvalds * The PALcode only builds an IO subpacket if there is a
9191da177e4SLinus Torvalds * locally connected IO7. In the cases of
9201da177e4SLinus Torvalds * 1) a uniprocessor kernel
9211da177e4SLinus Torvalds * 2) an mp kernel before the local secondary has called in
9221da177e4SLinus Torvalds * error interrupts are all directed to the primary processor.
9231da177e4SLinus Torvalds * In that case, we may not have an IO subpacket at all and, event
9241da177e4SLinus Torvalds * if we do, it may not be the right now.
9251da177e4SLinus Torvalds *
9261da177e4SLinus Torvalds * If the RBOX indicates an I/O error interrupt, make sure we have
9271da177e4SLinus Torvalds * the correct IO7 information. If we don't have an IO subpacket
9281da177e4SLinus Torvalds * or it's the wrong one, try to find the right one.
9291da177e4SLinus Torvalds *
9301da177e4SLinus Torvalds * RBOX I/O error interrupts are indicated by RBOX_INT<29> and
9311da177e4SLinus Torvalds * RBOX_INT<10>.
9321da177e4SLinus Torvalds */
9331da177e4SLinus Torvalds if ((lf_subpackets->io->po7_error_sum & (1UL << 32)) ||
9341da177e4SLinus Torvalds ((lf_subpackets->io->po7_error_sum |
9351da177e4SLinus Torvalds lf_subpackets->io->ports[0].pox_err_sum |
9361da177e4SLinus Torvalds lf_subpackets->io->ports[1].pox_err_sum |
9371da177e4SLinus Torvalds lf_subpackets->io->ports[2].pox_err_sum |
9381da177e4SLinus Torvalds lf_subpackets->io->ports[3].pox_err_sum) & (1UL << 63))) {
9391da177e4SLinus Torvalds /*
9401da177e4SLinus Torvalds * Either we have no IO subpacket or no error is
9411da177e4SLinus Torvalds * indicated in the one we do have. Try find the
9421da177e4SLinus Torvalds * one with the error.
9431da177e4SLinus Torvalds */
9441da177e4SLinus Torvalds if (!marvel_find_io7_with_error(lf_subpackets))
9451da177e4SLinus Torvalds return status;
9461da177e4SLinus Torvalds }
9471da177e4SLinus Torvalds
9481da177e4SLinus Torvalds /*
9491da177e4SLinus Torvalds * We have an IO7 indicating an error - we're going to report it
9501da177e4SLinus Torvalds */
9511da177e4SLinus Torvalds status = MCHK_DISPOSITION_REPORT;
9521da177e4SLinus Torvalds
9531da177e4SLinus Torvalds #ifdef CONFIG_VERBOSE_MCHECK
9541da177e4SLinus Torvalds
9551da177e4SLinus Torvalds if (!print)
9561da177e4SLinus Torvalds return status;
9571da177e4SLinus Torvalds
9581da177e4SLinus Torvalds printk("%s*Error occurred on IO7 at PID %u\n",
9591da177e4SLinus Torvalds err_print_prefix, lf_subpackets->io_pid);
9601da177e4SLinus Torvalds
9611da177e4SLinus Torvalds /*
9621da177e4SLinus Torvalds * Check port 7 first
9631da177e4SLinus Torvalds */
9641da177e4SLinus Torvalds if (lf_subpackets->io->po7_error_sum & IO7__PO7_ERRSUM__ERR_MASK) {
9651da177e4SLinus Torvalds marvel_print_po7_err_sum(io);
9661da177e4SLinus Torvalds
9671da177e4SLinus Torvalds #if 0
9681da177e4SLinus Torvalds printk("%s PORT 7 ERROR:\n"
9695f0e3da6SRandy Dunlap "%s PO7_ERROR_SUM: %016llx\n"
9705f0e3da6SRandy Dunlap "%s PO7_UNCRR_SYM: %016llx\n"
9715f0e3da6SRandy Dunlap "%s PO7_CRRCT_SYM: %016llx\n"
9725f0e3da6SRandy Dunlap "%s PO7_UGBGE_SYM: %016llx\n"
9735f0e3da6SRandy Dunlap "%s PO7_ERR_PKT0: %016llx\n"
9745f0e3da6SRandy Dunlap "%s PO7_ERR_PKT1: %016llx\n",
9751da177e4SLinus Torvalds err_print_prefix,
9761da177e4SLinus Torvalds err_print_prefix, io->po7_error_sum,
9771da177e4SLinus Torvalds err_print_prefix, io->po7_uncrr_sym,
9781da177e4SLinus Torvalds err_print_prefix, io->po7_crrct_sym,
9791da177e4SLinus Torvalds err_print_prefix, io->po7_ugbge_sym,
9801da177e4SLinus Torvalds err_print_prefix, io->po7_err_pkt0,
9811da177e4SLinus Torvalds err_print_prefix, io->po7_err_pkt1);
9821da177e4SLinus Torvalds #endif
9831da177e4SLinus Torvalds }
9841da177e4SLinus Torvalds
9851da177e4SLinus Torvalds /*
9861da177e4SLinus Torvalds * Then loop through the ports
9871da177e4SLinus Torvalds */
9881da177e4SLinus Torvalds for (i = 0; i < IO7_NUM_PORTS; i++) {
9891da177e4SLinus Torvalds if (!MARVEL_IO_ERR_VALID(io->ports[i].pox_err_sum))
9901da177e4SLinus Torvalds continue;
9911da177e4SLinus Torvalds
9925f0e3da6SRandy Dunlap printk("%s PID %u PORT %d POx_ERR_SUM: %016llx\n",
9931da177e4SLinus Torvalds err_print_prefix,
9941da177e4SLinus Torvalds lf_subpackets->io_pid, i, io->ports[i].pox_err_sum);
9951da177e4SLinus Torvalds marvel_print_pox_err(io->ports[i].pox_err_sum, &io->ports[i]);
9961da177e4SLinus Torvalds
9975f0e3da6SRandy Dunlap printk("%s [ POx_FIRST_ERR: %016llx ]\n",
9981da177e4SLinus Torvalds err_print_prefix, io->ports[i].pox_first_err);
9991da177e4SLinus Torvalds marvel_print_pox_err(io->ports[i].pox_first_err,
10001da177e4SLinus Torvalds &io->ports[i]);
10011da177e4SLinus Torvalds
10021da177e4SLinus Torvalds }
10031da177e4SLinus Torvalds
10041da177e4SLinus Torvalds
10051da177e4SLinus Torvalds #endif /* CONFIG_VERBOSE_MCHECK */
10061da177e4SLinus Torvalds
10071da177e4SLinus Torvalds return status;
10081da177e4SLinus Torvalds }
10091da177e4SLinus Torvalds
10101da177e4SLinus Torvalds static int
marvel_process_logout_frame(struct ev7_lf_subpackets * lf_subpackets,int print)10111da177e4SLinus Torvalds marvel_process_logout_frame(struct ev7_lf_subpackets *lf_subpackets, int print)
10121da177e4SLinus Torvalds {
10131da177e4SLinus Torvalds int status = MCHK_DISPOSITION_UNKNOWN_ERROR;
10141da177e4SLinus Torvalds
10151da177e4SLinus Torvalds /*
10161da177e4SLinus Torvalds * I/O error?
10171da177e4SLinus Torvalds */
10181da177e4SLinus Torvalds #define EV7__RBOX_INT__IO_ERROR__MASK 0x20000400ul
10191da177e4SLinus Torvalds if (lf_subpackets->logout &&
10201da177e4SLinus Torvalds (lf_subpackets->logout->rbox_int & 0x20000400ul))
10211da177e4SLinus Torvalds status = marvel_process_io_error(lf_subpackets, print);
10221da177e4SLinus Torvalds
10231da177e4SLinus Torvalds /*
10241da177e4SLinus Torvalds * Probing behind PCI-X bridges can cause machine checks on
10251da177e4SLinus Torvalds * Marvel when the probe is handled by the bridge as a split
10261da177e4SLinus Torvalds * completion transaction. The symptom is an ERROR_RESPONSE
10271da177e4SLinus Torvalds * to a CONFIG address. Since these errors will happen in
10281da177e4SLinus Torvalds * normal operation, dismiss them.
10291da177e4SLinus Torvalds *
10301da177e4SLinus Torvalds * Dismiss if:
103125985edcSLucas De Marchi * C_STAT = 0x14 (Error Response)
10321da177e4SLinus Torvalds * C_STS<3> = 0 (C_ADDR valid)
10331da177e4SLinus Torvalds * C_ADDR<42> = 1 (I/O)
10341da177e4SLinus Torvalds * C_ADDR<31:22> = 111110xxb (PCI Config space)
10351da177e4SLinus Torvalds */
10361da177e4SLinus Torvalds if (lf_subpackets->ev7 &&
10371da177e4SLinus Torvalds (lf_subpackets->ev7->c_stat == 0x14) &&
10381da177e4SLinus Torvalds !(lf_subpackets->ev7->c_sts & 0x8) &&
10391da177e4SLinus Torvalds ((lf_subpackets->ev7->c_addr & 0x400ff000000ul)
10401da177e4SLinus Torvalds == 0x400fe000000ul))
10411da177e4SLinus Torvalds status = MCHK_DISPOSITION_DISMISS;
10421da177e4SLinus Torvalds
10431da177e4SLinus Torvalds return status;
10441da177e4SLinus Torvalds }
10451da177e4SLinus Torvalds
10461da177e4SLinus Torvalds void
marvel_machine_check(unsigned long vector,unsigned long la_ptr)10471ffb1c0cSIvan Kokshaysky marvel_machine_check(unsigned long vector, unsigned long la_ptr)
10481da177e4SLinus Torvalds {
10491da177e4SLinus Torvalds struct el_subpacket *el_ptr = (struct el_subpacket *)la_ptr;
10501da177e4SLinus Torvalds int (*process_frame)(struct ev7_lf_subpackets *, int) = NULL;
10511da177e4SLinus Torvalds struct ev7_lf_subpackets subpacket_collection = { NULL, };
10521da177e4SLinus Torvalds struct ev7_pal_io_subpacket scratch_io_packet = { 0, };
10531da177e4SLinus Torvalds struct ev7_lf_subpackets *lf_subpackets = NULL;
10541da177e4SLinus Torvalds int disposition = MCHK_DISPOSITION_UNKNOWN_ERROR;
10551da177e4SLinus Torvalds char *saved_err_prefix = err_print_prefix;
10561da177e4SLinus Torvalds char *error_type = NULL;
10571da177e4SLinus Torvalds
10581da177e4SLinus Torvalds /*
10591da177e4SLinus Torvalds * Sync the processor
10601da177e4SLinus Torvalds */
10611da177e4SLinus Torvalds mb();
10621da177e4SLinus Torvalds draina();
10631da177e4SLinus Torvalds
10641da177e4SLinus Torvalds switch(vector) {
10651da177e4SLinus Torvalds case SCB_Q_SYSEVENT:
10661da177e4SLinus Torvalds process_frame = marvel_process_680_frame;
10671da177e4SLinus Torvalds error_type = "System Event";
10681da177e4SLinus Torvalds break;
10691da177e4SLinus Torvalds
10701da177e4SLinus Torvalds case SCB_Q_SYSMCHK:
10711da177e4SLinus Torvalds process_frame = marvel_process_logout_frame;
10721da177e4SLinus Torvalds error_type = "System Uncorrectable Error";
10731da177e4SLinus Torvalds break;
10741da177e4SLinus Torvalds
10751da177e4SLinus Torvalds case SCB_Q_SYSERR:
10761da177e4SLinus Torvalds process_frame = marvel_process_logout_frame;
10771da177e4SLinus Torvalds error_type = "System Correctable Error";
10781da177e4SLinus Torvalds break;
10791da177e4SLinus Torvalds
10801da177e4SLinus Torvalds default:
10811da177e4SLinus Torvalds /* Don't know it - pass it up. */
10824fa1970aSAl Viro ev7_machine_check(vector, la_ptr);
10831da177e4SLinus Torvalds return;
10841da177e4SLinus Torvalds }
10851da177e4SLinus Torvalds
10861da177e4SLinus Torvalds /*
1087c3a2ddeeSSimon Arlott * A system event or error has occurred, handle it here.
10881da177e4SLinus Torvalds *
10891da177e4SLinus Torvalds * Any errors in the logout frame have already been cleared by the
10901da177e4SLinus Torvalds * PALcode, so just parse it.
10911da177e4SLinus Torvalds */
10921da177e4SLinus Torvalds err_print_prefix = KERN_CRIT;
10931da177e4SLinus Torvalds
10941da177e4SLinus Torvalds /*
10951da177e4SLinus Torvalds * Parse the logout frame without printing first. If the only error(s)
10961da177e4SLinus Torvalds * found are classified as "dismissable", then just dismiss them and
10971da177e4SLinus Torvalds * don't print any message
10981da177e4SLinus Torvalds */
10991da177e4SLinus Torvalds lf_subpackets =
11001da177e4SLinus Torvalds ev7_collect_logout_frame_subpackets(el_ptr,
11011da177e4SLinus Torvalds &subpacket_collection);
11021da177e4SLinus Torvalds if (process_frame && lf_subpackets && lf_subpackets->logout) {
11031da177e4SLinus Torvalds /*
11041da177e4SLinus Torvalds * We might not have the correct (or any) I/O subpacket.
11051da177e4SLinus Torvalds * [ See marvel_process_io_error() for explanation. ]
11061da177e4SLinus Torvalds * If we don't have one, point the io subpacket in
11071da177e4SLinus Torvalds * lf_subpackets at scratch_io_packet so that
11081da177e4SLinus Torvalds * marvel_find_io7_with_error() will have someplace to
11091da177e4SLinus Torvalds * store the info.
11101da177e4SLinus Torvalds */
11111da177e4SLinus Torvalds if (!lf_subpackets->io)
11121da177e4SLinus Torvalds lf_subpackets->io = &scratch_io_packet;
11131da177e4SLinus Torvalds
11141da177e4SLinus Torvalds /*
11151da177e4SLinus Torvalds * Default io_pid to the processor reporting the error
11161da177e4SLinus Torvalds * [this will get changed in marvel_find_io7_with_error()
11171da177e4SLinus Torvalds * if a different one is needed]
11181da177e4SLinus Torvalds */
11191da177e4SLinus Torvalds lf_subpackets->io_pid = lf_subpackets->logout->whami;
11201da177e4SLinus Torvalds
11211da177e4SLinus Torvalds /*
11221da177e4SLinus Torvalds * Evaluate the frames.
11231da177e4SLinus Torvalds */
11241da177e4SLinus Torvalds disposition = process_frame(lf_subpackets, 0);
11251da177e4SLinus Torvalds }
11261da177e4SLinus Torvalds switch(disposition) {
11271da177e4SLinus Torvalds case MCHK_DISPOSITION_DISMISS:
11281da177e4SLinus Torvalds /* Nothing to do. */
11291da177e4SLinus Torvalds break;
11301da177e4SLinus Torvalds
11311da177e4SLinus Torvalds case MCHK_DISPOSITION_REPORT:
11321da177e4SLinus Torvalds /* Recognized error, report it. */
11331da177e4SLinus Torvalds printk("%s*%s (Vector 0x%x) reported on CPU %d\n",
11341da177e4SLinus Torvalds err_print_prefix, error_type,
11351da177e4SLinus Torvalds (unsigned int)vector, (int)smp_processor_id());
11361da177e4SLinus Torvalds el_print_timestamp(&lf_subpackets->logout->timestamp);
11371da177e4SLinus Torvalds process_frame(lf_subpackets, 1);
11381da177e4SLinus Torvalds break;
11391da177e4SLinus Torvalds
11401da177e4SLinus Torvalds default:
11411da177e4SLinus Torvalds /* Unknown - dump the annotated subpackets. */
11421da177e4SLinus Torvalds printk("%s*%s (Vector 0x%x) reported on CPU %d\n",
11431da177e4SLinus Torvalds err_print_prefix, error_type,
11441da177e4SLinus Torvalds (unsigned int)vector, (int)smp_processor_id());
11451da177e4SLinus Torvalds el_process_subpacket(el_ptr);
11461da177e4SLinus Torvalds break;
11471da177e4SLinus Torvalds
11481da177e4SLinus Torvalds }
11491da177e4SLinus Torvalds
11501da177e4SLinus Torvalds err_print_prefix = saved_err_prefix;
11511da177e4SLinus Torvalds
11521da177e4SLinus Torvalds /* Release the logout frame. */
11531da177e4SLinus Torvalds wrmces(0x7);
11541da177e4SLinus Torvalds mb();
11551da177e4SLinus Torvalds }
11561da177e4SLinus Torvalds
11579548b209SIvan Kokshaysky void __init
marvel_register_error_handlers(void)11581da177e4SLinus Torvalds marvel_register_error_handlers(void)
11591da177e4SLinus Torvalds {
11601da177e4SLinus Torvalds ev7_register_error_handlers();
11611da177e4SLinus Torvalds }
1162