aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/edac
diff options
context:
space:
mode:
authorBorislav Petkov <borislav.petkov@amd.com>2011-11-24 15:29:57 -0500
committerBorislav Petkov <bp@alien8.de>2012-03-19 07:06:25 -0400
commit68782673e6dd69054a9b75b0983a5e45e16f6625 (patch)
treeb25cf845be2205fa20d81edc456d03d03f440993 /drivers/edac
parentb64a99c1752d2b6525a5011a8e473f8f8a4bdd79 (diff)
MCE, AMD: Rework NB MCE signatures
Correct their formulation, replace per-family functions with a single, unified lookup table. Signed-off-by: Borislav Petkov <borislav.petkov@amd.com> Reviewed-by: Andreas Herrmann <andreas.herrmann3@amd.com>
Diffstat (limited to 'drivers/edac')
-rw-r--r--drivers/edac/mce_amd.c176
-rw-r--r--drivers/edac/mce_amd.h1
2 files changed, 48 insertions, 129 deletions
diff --git a/drivers/edac/mce_amd.c b/drivers/edac/mce_amd.c
index bf6dd9978aa7..f6ebe5e9a57f 100644
--- a/drivers/edac/mce_amd.c
+++ b/drivers/edac/mce_amd.c
@@ -64,17 +64,6 @@ EXPORT_SYMBOL_GPL(to_msgs);
64const char *ii_msgs[] = { "MEM", "RESV", "IO", "GEN" }; 64const char *ii_msgs[] = { "MEM", "RESV", "IO", "GEN" };
65EXPORT_SYMBOL_GPL(ii_msgs); 65EXPORT_SYMBOL_GPL(ii_msgs);
66 66
67static const char *f10h_nb_mce_desc[] = {
68 "HT link data error",
69 "Protocol error (link, L3, probe filter, etc.)",
70 "Parity error in NB-internal arrays",
71 "Link Retry due to IO link transmission error",
72 "L3 ECC data cache error",
73 "ECC error in L3 cache tag",
74 "L3 LRU parity bits error",
75 "ECC Error in the Probe Filter directory"
76};
77
78static const char * const f15h_ic_mce_desc[] = { 67static const char * const f15h_ic_mce_desc[] = {
79 "UC during a demand linefill from L2", 68 "UC during a demand linefill from L2",
80 "Parity error during data load from IC", 69 "Parity error during data load from IC",
@@ -112,6 +101,28 @@ static const char * const f15h_cu_mce_desc[] = {
112 "PRB address parity error" 101 "PRB address parity error"
113}; 102};
114 103
104static const char *nb_mce_desc[] = {
105 "DRAM ECC error detected on the NB",
106 "CRC error detected on HT link",
107 "Link-defined sync error packets detected on HT link",
108 "HT Master abort",
109 "HT Target abort",
110 "Invalid GART PTE entry during GART table walk",
111 "Unsupported atomic RMW received from an IO link",
112 "Watchdog timeout due to lack of progress",
113 "DRAM ECC error detected on the NB",
114 "SVM DMA Exclusion Vector error",
115 "HT data error detected on link",
116 "Protocol error (link, L3, probe filter)",
117 "NB internal arrays parity error",
118 "DRAM addr/ctl signals parity error",
119 "IO link transmission error",
120 "L3 data cache ECC error", /* xec = 0x1c */
121 "L3 cache tag error",
122 "L3 LRU parity bits error",
123 "ECC Error in the Probe Filter directory"
124};
125
115static const char * const fr_ex_mce_desc[] = { 126static const char * const fr_ex_mce_desc[] = {
116 "CPU Watchdog timer expire", 127 "CPU Watchdog timer expire",
117 "Wakeup array dest tag", 128 "Wakeup array dest tag",
@@ -499,58 +510,31 @@ wrong_ls_mce:
499 pr_emerg(HW_ERR "Corrupted LS MCE info?\n"); 510 pr_emerg(HW_ERR "Corrupted LS MCE info?\n");
500} 511}
501 512
502static bool k8_nb_mce(u16 ec, u8 xec) 513void amd_decode_nb_mce(struct mce *m)
503{ 514{
504 bool ret = true; 515 struct cpuinfo_x86 *c = &boot_cpu_data;
505 516 int node_id = amd_get_nb_id(m->extcpu);
506 switch (xec) { 517 u16 ec = EC(m->status);
507 case 0x1: 518 u8 xec = XEC(m->status, 0x1f);
508 pr_cont("CRC error detected on HT link.\n"); 519 u8 offset = 0;
509 break;
510
511 case 0x5:
512 pr_cont("Invalid GART PTE entry during GART table walk.\n");
513 break;
514
515 case 0x6:
516 pr_cont("Unsupported atomic RMW received from an IO link.\n");
517 break;
518
519 case 0x0:
520 case 0x8:
521 if (boot_cpu_data.x86 == 0x11)
522 return false;
523
524 pr_cont("DRAM ECC error detected on the NB.\n");
525 break;
526
527 case 0xd:
528 pr_cont("Parity error on the DRAM addr/ctl signals.\n");
529 break;
530
531 default:
532 ret = false;
533 break;
534 }
535 520
536 return ret; 521 pr_emerg(HW_ERR "Northbridge Error (node %d): ", node_id);
537}
538 522
539static bool f10h_nb_mce(u16 ec, u8 xec) 523 switch (xec) {
540{ 524 case 0x0 ... 0xe:
541 bool ret = true;
542 u8 offset = 0;
543 525
544 if (k8_nb_mce(ec, xec)) 526 /* special handling for DRAM ECCs */
545 return true; 527 if (xec == 0x0 || xec == 0x8) {
528 /* no ECCs on F11h */
529 if (c->x86 == 0x11)
530 goto wrong_nb_mce;
546 531
547 switch(xec) { 532 pr_cont("%s.\n", nb_mce_desc[xec]);
548 case 0xa ... 0xc:
549 offset = 10;
550 break;
551 533
552 case 0xe: 534 if (nb_bus_decoder)
553 offset = 11; 535 nb_bus_decoder(node_id, m);
536 return;
537 }
554 break; 538 break;
555 539
556 case 0xf: 540 case 0xf:
@@ -559,83 +543,25 @@ static bool f10h_nb_mce(u16 ec, u8 xec)
559 else if (BUS_ERROR(ec)) 543 else if (BUS_ERROR(ec))
560 pr_cont("DMA Exclusion Vector Table Walk error.\n"); 544 pr_cont("DMA Exclusion Vector Table Walk error.\n");
561 else 545 else
562 ret = false; 546 goto wrong_nb_mce;
563 547 return;
564 goto out;
565 break;
566 548
567 case 0x19: 549 case 0x19:
568 if (boot_cpu_data.x86 == 0x15) 550 if (boot_cpu_data.x86 == 0x15)
569 pr_cont("Compute Unit Data Error.\n"); 551 pr_cont("Compute Unit Data Error.\n");
570 else 552 else
571 ret = false; 553 goto wrong_nb_mce;
572 554 return;
573 goto out;
574 break;
575 555
576 case 0x1c ... 0x1f: 556 case 0x1c ... 0x1f:
577 offset = 24; 557 offset = 13;
578 break; 558 break;
579 559
580 default: 560 default:
581 ret = false;
582
583 goto out;
584 break;
585 }
586
587 pr_cont("%s.\n", f10h_nb_mce_desc[xec - offset]);
588
589out:
590 return ret;
591}
592
593static bool nb_noop_mce(u16 ec, u8 xec)
594{
595 return false;
596}
597
598void amd_decode_nb_mce(struct mce *m)
599{
600 struct cpuinfo_x86 *c = &boot_cpu_data;
601 int node_id = amd_get_nb_id(m->extcpu);
602 u16 ec = EC(m->status);
603 u8 xec = XEC(m->status, 0x1f);
604
605 pr_emerg(HW_ERR "Northbridge Error (node %d): ", node_id);
606
607 switch (xec) {
608 case 0x2:
609 pr_cont("Sync error (sync packets on HT link detected).\n");
610 return;
611
612 case 0x3:
613 pr_cont("HT Master abort.\n");
614 return;
615
616 case 0x4:
617 pr_cont("HT Target abort.\n");
618 return;
619
620 case 0x7:
621 pr_cont("NB Watchdog timeout.\n");
622 return;
623
624 case 0x9:
625 pr_cont("SVM DMA Exclusion Vector error.\n");
626 return;
627
628 default:
629 break;
630 }
631
632 if (!fam_ops->nb_mce(ec, xec))
633 goto wrong_nb_mce; 561 goto wrong_nb_mce;
562 }
634 563
635 if (c->x86 == 0xf || c->x86 == 0x10 || c->x86 == 0x15) 564 pr_cont("%s.\n", nb_mce_desc[xec - offset]);
636 if ((xec == 0x8 || xec == 0x0) && nb_bus_decoder)
637 nb_bus_decoder(node_id, m);
638
639 return; 565 return;
640 566
641wrong_nb_mce: 567wrong_nb_mce:
@@ -844,39 +770,33 @@ static int __init mce_amd_init(void)
844 case 0xf: 770 case 0xf:
845 fam_ops->dc_mce = k8_dc_mce; 771 fam_ops->dc_mce = k8_dc_mce;
846 fam_ops->ic_mce = k8_ic_mce; 772 fam_ops->ic_mce = k8_ic_mce;
847 fam_ops->nb_mce = k8_nb_mce;
848 break; 773 break;
849 774
850 case 0x10: 775 case 0x10:
851 fam_ops->dc_mce = f10h_dc_mce; 776 fam_ops->dc_mce = f10h_dc_mce;
852 fam_ops->ic_mce = k8_ic_mce; 777 fam_ops->ic_mce = k8_ic_mce;
853 fam_ops->nb_mce = f10h_nb_mce;
854 break; 778 break;
855 779
856 case 0x11: 780 case 0x11:
857 fam_ops->dc_mce = k8_dc_mce; 781 fam_ops->dc_mce = k8_dc_mce;
858 fam_ops->ic_mce = k8_ic_mce; 782 fam_ops->ic_mce = k8_ic_mce;
859 fam_ops->nb_mce = f10h_nb_mce;
860 break; 783 break;
861 784
862 case 0x12: 785 case 0x12:
863 fam_ops->dc_mce = f12h_dc_mce; 786 fam_ops->dc_mce = f12h_dc_mce;
864 fam_ops->ic_mce = k8_ic_mce; 787 fam_ops->ic_mce = k8_ic_mce;
865 fam_ops->nb_mce = nb_noop_mce;
866 break; 788 break;
867 789
868 case 0x14: 790 case 0x14:
869 nb_err_cpumask = 0x3; 791 nb_err_cpumask = 0x3;
870 fam_ops->dc_mce = f14h_dc_mce; 792 fam_ops->dc_mce = f14h_dc_mce;
871 fam_ops->ic_mce = f14h_ic_mce; 793 fam_ops->ic_mce = f14h_ic_mce;
872 fam_ops->nb_mce = nb_noop_mce;
873 break; 794 break;
874 795
875 case 0x15: 796 case 0x15:
876 xec_mask = 0x1f; 797 xec_mask = 0x1f;
877 fam_ops->dc_mce = f15h_dc_mce; 798 fam_ops->dc_mce = f15h_dc_mce;
878 fam_ops->ic_mce = f15h_ic_mce; 799 fam_ops->ic_mce = f15h_ic_mce;
879 fam_ops->nb_mce = f10h_nb_mce;
880 break; 800 break;
881 801
882 default: 802 default:
diff --git a/drivers/edac/mce_amd.h b/drivers/edac/mce_amd.h
index 0106747e240c..6fcf599e691f 100644
--- a/drivers/edac/mce_amd.h
+++ b/drivers/edac/mce_amd.h
@@ -82,7 +82,6 @@ extern const char *ii_msgs[];
82struct amd_decoder_ops { 82struct amd_decoder_ops {
83 bool (*dc_mce)(u16, u8); 83 bool (*dc_mce)(u16, u8);
84 bool (*ic_mce)(u16, u8); 84 bool (*ic_mce)(u16, u8);
85 bool (*nb_mce)(u16, u8);
86}; 85};
87 86
88void amd_report_gart_errors(bool); 87void amd_report_gart_errors(bool);