diff options
| author | Christopher Baumbauer - Sun Microsystems - San Diego United States <Christopher.Baumbauer@Sun.COM> | 2010-03-24 14:33:13 -0700 |
|---|---|---|
| committer | Christopher Baumbauer - Sun Microsystems - San Diego United States <Christopher.Baumbauer@Sun.COM> | 2010-03-24 14:33:13 -0700 |
| commit | f60f9424b15116bdcad4382e47e7d324ff25e022 (patch) | |
| tree | 88d8dcb3d1c732dbebc920fafb1ca83b9180fecb /usr/src/uts/sun4u | |
| parent | 36802407db97b1bcd32a63b16112e95ffcc5bb98 (diff) | |
| download | illumos-joyent-f60f9424b15116bdcad4382e47e7d324ff25e022.tar.gz | |
6536893 customer still sees ddspe's under FMA - even after replacing US3is
Diffstat (limited to 'usr/src/uts/sun4u')
| -rw-r--r-- | usr/src/uts/sun4u/cpu/us3_common.c | 64 |
1 files changed, 61 insertions, 3 deletions
diff --git a/usr/src/uts/sun4u/cpu/us3_common.c b/usr/src/uts/sun4u/cpu/us3_common.c index 7b95703ac1..7fc8fcc986 100644 --- a/usr/src/uts/sun4u/cpu/us3_common.c +++ b/usr/src/uts/sun4u/cpu/us3_common.c @@ -19,7 +19,7 @@ * CDDL HEADER END */ /* - * Copyright 2009 Sun Microsystems, Inc. All rights reserved. + * Copyright 2010 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -314,6 +314,12 @@ NA, MTC0, MTC1, M2, MTC2, M2, M2, MT0, MTC3, M2, M2, MT1, M2, MT2, M2, M2 #endif /* !(JALAPENO || SERRANO) */ /* + * Virtual Address bit flag in the data cache. This is actually bit 2 in the + * dcache data tag. + */ +#define VA13 INT64_C(0x0000000000000002) + +/* * Types returned from cpu_error_to_resource_type() */ #define ERRTYPE_UNKNOWN 0 @@ -2082,6 +2088,12 @@ cpu_parity_error(struct regs *rp, uint_t flags, caddr_t tpc) uchar_t iparity = ((flags & CH_ERR_IPE) != 0); uchar_t panic = ((flags & CH_ERR_PANIC) != 0); char *error_class; + int index, way, word; + ch_dc_data_t tmp_dcp; + int dc_set_size = dcache_size / CH_DCACHE_NWAY; + uint64_t parity_bits, pbits; + /* The parity bit array corresponds to the result of summing two bits */ + static int parity_bits_popc[] = { 0, 1, 1, 0 }; /* * Log the error. @@ -2116,9 +2128,55 @@ cpu_parity_error(struct regs *rp, uint_t flags, caddr_t tpc) aflt->flt_payload = FM_EREPORT_PAYLOAD_ICACHE_PE; } else { cpu_dcache_parity_info(&ch_flt); - if (ch_flt.parity_data.dpe.cpl_off != -1) + if (ch_flt.parity_data.dpe.cpl_off != -1) { + /* + * If not at TL 0 and running on a Jalapeno processor, + * then process as a true ddspe. A true + * ddspe error can only occur if the way == 0 + */ + way = ch_flt.parity_data.dpe.cpl_way; + if ((tl == 0) && (way != 0) && + IS_JALAPENO(cpunodes[CPU->cpu_id].implementation)) { + for (index = 0; index < dc_set_size; + index += dcache_linesize) { + get_dcache_dtag(index + way * + dc_set_size, + (uint64_t *)&tmp_dcp); + /* + * Check data array for even parity. + * The 8 parity bits are grouped into + * 4 pairs each of which covers a 64-bit + * word. The endianness is reversed + * -- the low-order parity bits cover + * the high-order data words. + */ + parity_bits = tmp_dcp.dc_utag >> 8; + for (word = 0; word < 4; word++) { + pbits = (parity_bits >> + (6 - word * 2)) & 3; + if (((popc64( + tmp_dcp.dc_data[word]) + + parity_bits_popc[pbits]) & + 1) && (tmp_dcp.dc_tag & + VA13)) { + /* cleanup */ + correct_dcache_parity( + dcache_size, + dcache_linesize); + if (cache_boot_state & + DCU_DC) { + flush_dcache(); + } + + set_dcu(get_dcu() | + cache_boot_state); + return; + } + } + } + } /* (tl == 0) && (way != 0) && IS JALAPENO */ error_class = FM_EREPORT_CPU_USIII_DDSPE; - else if (ch_flt.parity_data.dpe.cpl_way != -1) + } else if (ch_flt.parity_data.dpe.cpl_way != -1) error_class = FM_EREPORT_CPU_USIII_DTSPE; else error_class = FM_EREPORT_CPU_USIII_DPE; |
