diff options
Diffstat (limited to 'drivers/edac/e752x_edac.c')
-rw-r--r-- | drivers/edac/e752x_edac.c | 346 |
1 files changed, 191 insertions, 155 deletions
diff --git a/drivers/edac/e752x_edac.c b/drivers/edac/e752x_edac.c index fce31936e6d7..c82bc0ed7f14 100644 --- a/drivers/edac/e752x_edac.c +++ b/drivers/edac/e752x_edac.c | |||
@@ -17,7 +17,6 @@ | |||
17 | * | 17 | * |
18 | */ | 18 | */ |
19 | 19 | ||
20 | #include <linux/config.h> | ||
21 | #include <linux/module.h> | 20 | #include <linux/module.h> |
22 | #include <linux/init.h> | 21 | #include <linux/init.h> |
23 | #include <linux/pci.h> | 22 | #include <linux/pci.h> |
@@ -25,6 +24,9 @@ | |||
25 | #include <linux/slab.h> | 24 | #include <linux/slab.h> |
26 | #include "edac_mc.h" | 25 | #include "edac_mc.h" |
27 | 26 | ||
27 | #define E752X_REVISION " Ver: 2.0.1 " __DATE__ | ||
28 | #define EDAC_MOD_STR "e752x_edac" | ||
29 | |||
28 | static int force_function_unhide; | 30 | static int force_function_unhide; |
29 | 31 | ||
30 | #define e752x_printk(level, fmt, arg...) \ | 32 | #define e752x_printk(level, fmt, arg...) \ |
@@ -763,22 +765,174 @@ static void e752x_check(struct mem_ctl_info *mci) | |||
763 | e752x_process_error_info(mci, &info, 1); | 765 | e752x_process_error_info(mci, &info, 1); |
764 | } | 766 | } |
765 | 767 | ||
766 | static int e752x_probe1(struct pci_dev *pdev, int dev_idx) | 768 | /* Return 1 if dual channel mode is active. Else return 0. */ |
769 | static inline int dual_channel_active(u16 ddrcsr) | ||
770 | { | ||
771 | return (((ddrcsr >> 12) & 3) == 3); | ||
772 | } | ||
773 | |||
774 | static void e752x_init_csrows(struct mem_ctl_info *mci, struct pci_dev *pdev, | ||
775 | u16 ddrcsr) | ||
776 | { | ||
777 | struct csrow_info *csrow; | ||
778 | unsigned long last_cumul_size; | ||
779 | int index, mem_dev, drc_chan; | ||
780 | int drc_drbg; /* DRB granularity 0=64mb, 1=128mb */ | ||
781 | int drc_ddim; /* DRAM Data Integrity Mode 0=none, 2=edac */ | ||
782 | u8 value; | ||
783 | u32 dra, drc, cumul_size; | ||
784 | |||
785 | pci_read_config_dword(pdev, E752X_DRA, &dra); | ||
786 | pci_read_config_dword(pdev, E752X_DRC, &drc); | ||
787 | drc_chan = dual_channel_active(ddrcsr); | ||
788 | drc_drbg = drc_chan + 1; /* 128 in dual mode, 64 in single */ | ||
789 | drc_ddim = (drc >> 20) & 0x3; | ||
790 | |||
791 | /* The dram row boundary (DRB) reg values are boundary address for | ||
792 | * each DRAM row with a granularity of 64 or 128MB (single/dual | ||
793 | * channel operation). DRB regs are cumulative; therefore DRB7 will | ||
794 | * contain the total memory contained in all eight rows. | ||
795 | */ | ||
796 | for (last_cumul_size = index = 0; index < mci->nr_csrows; index++) { | ||
797 | /* mem_dev 0=x8, 1=x4 */ | ||
798 | mem_dev = (dra >> (index * 4 + 2)) & 0x3; | ||
799 | csrow = &mci->csrows[index]; | ||
800 | |||
801 | mem_dev = (mem_dev == 2); | ||
802 | pci_read_config_byte(pdev, E752X_DRB + index, &value); | ||
803 | /* convert a 128 or 64 MiB DRB to a page size. */ | ||
804 | cumul_size = value << (25 + drc_drbg - PAGE_SHIFT); | ||
805 | debugf3("%s(): (%d) cumul_size 0x%x\n", __func__, index, | ||
806 | cumul_size); | ||
807 | if (cumul_size == last_cumul_size) | ||
808 | continue; /* not populated */ | ||
809 | |||
810 | csrow->first_page = last_cumul_size; | ||
811 | csrow->last_page = cumul_size - 1; | ||
812 | csrow->nr_pages = cumul_size - last_cumul_size; | ||
813 | last_cumul_size = cumul_size; | ||
814 | csrow->grain = 1 << 12; /* 4KiB - resolution of CELOG */ | ||
815 | csrow->mtype = MEM_RDDR; /* only one type supported */ | ||
816 | csrow->dtype = mem_dev ? DEV_X4 : DEV_X8; | ||
817 | |||
818 | /* | ||
819 | * if single channel or x8 devices then SECDED | ||
820 | * if dual channel and x4 then S4ECD4ED | ||
821 | */ | ||
822 | if (drc_ddim) { | ||
823 | if (drc_chan && mem_dev) { | ||
824 | csrow->edac_mode = EDAC_S4ECD4ED; | ||
825 | mci->edac_cap |= EDAC_FLAG_S4ECD4ED; | ||
826 | } else { | ||
827 | csrow->edac_mode = EDAC_SECDED; | ||
828 | mci->edac_cap |= EDAC_FLAG_SECDED; | ||
829 | } | ||
830 | } else | ||
831 | csrow->edac_mode = EDAC_NONE; | ||
832 | } | ||
833 | } | ||
834 | |||
835 | static void e752x_init_mem_map_table(struct pci_dev *pdev, | ||
836 | struct e752x_pvt *pvt) | ||
767 | { | 837 | { |
768 | int rc = -ENODEV; | ||
769 | int index; | 838 | int index; |
839 | u8 value, last, row, stat8; | ||
840 | |||
841 | last = 0; | ||
842 | row = 0; | ||
843 | |||
844 | for (index = 0; index < 8; index += 2) { | ||
845 | pci_read_config_byte(pdev, E752X_DRB + index, &value); | ||
846 | /* test if there is a dimm in this slot */ | ||
847 | if (value == last) { | ||
848 | /* no dimm in the slot, so flag it as empty */ | ||
849 | pvt->map[index] = 0xff; | ||
850 | pvt->map[index + 1] = 0xff; | ||
851 | } else { /* there is a dimm in the slot */ | ||
852 | pvt->map[index] = row; | ||
853 | row++; | ||
854 | last = value; | ||
855 | /* test the next value to see if the dimm is double | ||
856 | * sided | ||
857 | */ | ||
858 | pci_read_config_byte(pdev, E752X_DRB + index + 1, | ||
859 | &value); | ||
860 | pvt->map[index + 1] = (value == last) ? | ||
861 | 0xff : /* the dimm is single sided, | ||
862 | so flag as empty */ | ||
863 | row; /* this is a double sided dimm | ||
864 | to save the next row # */ | ||
865 | row++; | ||
866 | last = value; | ||
867 | } | ||
868 | } | ||
869 | |||
870 | /* set the map type. 1 = normal, 0 = reversed */ | ||
871 | pci_read_config_byte(pdev, E752X_DRM, &stat8); | ||
872 | pvt->map_type = ((stat8 & 0x0f) > ((stat8 >> 4) & 0x0f)); | ||
873 | } | ||
874 | |||
875 | /* Return 0 on success or 1 on failure. */ | ||
876 | static int e752x_get_devs(struct pci_dev *pdev, int dev_idx, | ||
877 | struct e752x_pvt *pvt) | ||
878 | { | ||
879 | struct pci_dev *dev; | ||
880 | |||
881 | pvt->bridge_ck = pci_get_device(PCI_VENDOR_ID_INTEL, | ||
882 | pvt->dev_info->err_dev, | ||
883 | pvt->bridge_ck); | ||
884 | |||
885 | if (pvt->bridge_ck == NULL) | ||
886 | pvt->bridge_ck = pci_scan_single_device(pdev->bus, | ||
887 | PCI_DEVFN(0, 1)); | ||
888 | |||
889 | if (pvt->bridge_ck == NULL) { | ||
890 | e752x_printk(KERN_ERR, "error reporting device not found:" | ||
891 | "vendor %x device 0x%x (broken BIOS?)\n", | ||
892 | PCI_VENDOR_ID_INTEL, e752x_devs[dev_idx].err_dev); | ||
893 | return 1; | ||
894 | } | ||
895 | |||
896 | dev = pci_get_device(PCI_VENDOR_ID_INTEL, e752x_devs[dev_idx].ctl_dev, | ||
897 | NULL); | ||
898 | |||
899 | if (dev == NULL) | ||
900 | goto fail; | ||
901 | |||
902 | pvt->dev_d0f0 = dev; | ||
903 | pvt->dev_d0f1 = pci_dev_get(pvt->bridge_ck); | ||
904 | |||
905 | return 0; | ||
906 | |||
907 | fail: | ||
908 | pci_dev_put(pvt->bridge_ck); | ||
909 | return 1; | ||
910 | } | ||
911 | |||
912 | static void e752x_init_error_reporting_regs(struct e752x_pvt *pvt) | ||
913 | { | ||
914 | struct pci_dev *dev; | ||
915 | |||
916 | dev = pvt->dev_d0f1; | ||
917 | /* Turn off error disable & SMI in case the BIOS turned it on */ | ||
918 | pci_write_config_byte(dev, E752X_HI_ERRMASK, 0x00); | ||
919 | pci_write_config_byte(dev, E752X_HI_SMICMD, 0x00); | ||
920 | pci_write_config_word(dev, E752X_SYSBUS_ERRMASK, 0x00); | ||
921 | pci_write_config_word(dev, E752X_SYSBUS_SMICMD, 0x00); | ||
922 | pci_write_config_byte(dev, E752X_BUF_ERRMASK, 0x00); | ||
923 | pci_write_config_byte(dev, E752X_BUF_SMICMD, 0x00); | ||
924 | pci_write_config_byte(dev, E752X_DRAM_ERRMASK, 0x00); | ||
925 | pci_write_config_byte(dev, E752X_DRAM_SMICMD, 0x00); | ||
926 | } | ||
927 | |||
928 | static int e752x_probe1(struct pci_dev *pdev, int dev_idx) | ||
929 | { | ||
770 | u16 pci_data; | 930 | u16 pci_data; |
771 | u8 stat8; | 931 | u8 stat8; |
772 | struct mem_ctl_info *mci = NULL; | 932 | struct mem_ctl_info *mci; |
773 | struct e752x_pvt *pvt = NULL; | 933 | struct e752x_pvt *pvt; |
774 | u16 ddrcsr; | 934 | u16 ddrcsr; |
775 | u32 drc; | ||
776 | int drc_chan; /* Number of channels 0=1chan,1=2chan */ | 935 | int drc_chan; /* Number of channels 0=1chan,1=2chan */ |
777 | int drc_drbg; /* DRB granularity 0=64mb, 1=128mb */ | ||
778 | int drc_ddim; /* DRAM Data Integrity Mode 0=none,2=edac */ | ||
779 | u32 dra; | ||
780 | unsigned long last_cumul_size; | ||
781 | struct pci_dev *dev = NULL; | ||
782 | struct e752x_error_info discard; | 936 | struct e752x_error_info discard; |
783 | 937 | ||
784 | debugf0("%s(): mci\n", __func__); | 938 | debugf0("%s(): mci\n", __func__); |
@@ -792,25 +946,20 @@ static int e752x_probe1(struct pci_dev *pdev, int dev_idx) | |||
792 | if (!force_function_unhide && !(stat8 & (1 << 5))) { | 946 | if (!force_function_unhide && !(stat8 & (1 << 5))) { |
793 | printk(KERN_INFO "Contact your BIOS vendor to see if the " | 947 | printk(KERN_INFO "Contact your BIOS vendor to see if the " |
794 | "E752x error registers can be safely un-hidden\n"); | 948 | "E752x error registers can be safely un-hidden\n"); |
795 | goto fail; | 949 | return -ENOMEM; |
796 | } | 950 | } |
797 | stat8 |= (1 << 5); | 951 | stat8 |= (1 << 5); |
798 | pci_write_config_byte(pdev, E752X_DEVPRES1, stat8); | 952 | pci_write_config_byte(pdev, E752X_DEVPRES1, stat8); |
799 | 953 | ||
800 | /* need to find out the number of channels */ | ||
801 | pci_read_config_dword(pdev, E752X_DRC, &drc); | ||
802 | pci_read_config_word(pdev, E752X_DDRCSR, &ddrcsr); | 954 | pci_read_config_word(pdev, E752X_DDRCSR, &ddrcsr); |
803 | /* FIXME: should check >>12 or 0xf, true for all? */ | 955 | /* FIXME: should check >>12 or 0xf, true for all? */ |
804 | /* Dual channel = 1, Single channel = 0 */ | 956 | /* Dual channel = 1, Single channel = 0 */ |
805 | drc_chan = (((ddrcsr >> 12) & 3) == 3); | 957 | drc_chan = dual_channel_active(ddrcsr); |
806 | drc_drbg = drc_chan + 1; /* 128 in dual mode, 64 in single */ | ||
807 | drc_ddim = (drc >> 20) & 0x3; | ||
808 | 958 | ||
809 | mci = edac_mc_alloc(sizeof(*pvt), E752X_NR_CSROWS, drc_chan + 1); | 959 | mci = edac_mc_alloc(sizeof(*pvt), E752X_NR_CSROWS, drc_chan + 1); |
810 | 960 | ||
811 | if (mci == NULL) { | 961 | if (mci == NULL) { |
812 | rc = -ENOMEM; | 962 | return -ENOMEM; |
813 | goto fail; | ||
814 | } | 963 | } |
815 | 964 | ||
816 | debugf3("%s(): init mci\n", __func__); | 965 | debugf3("%s(): init mci\n", __func__); |
@@ -819,159 +968,54 @@ static int e752x_probe1(struct pci_dev *pdev, int dev_idx) | |||
819 | EDAC_FLAG_S4ECD4ED; | 968 | EDAC_FLAG_S4ECD4ED; |
820 | /* FIXME - what if different memory types are in different csrows? */ | 969 | /* FIXME - what if different memory types are in different csrows? */ |
821 | mci->mod_name = EDAC_MOD_STR; | 970 | mci->mod_name = EDAC_MOD_STR; |
822 | mci->mod_ver = "$Revision: 1.5.2.11 $"; | 971 | mci->mod_ver = E752X_REVISION; |
823 | mci->pdev = pdev; | 972 | mci->dev = &pdev->dev; |
824 | 973 | ||
825 | debugf3("%s(): init pvt\n", __func__); | 974 | debugf3("%s(): init pvt\n", __func__); |
826 | pvt = (struct e752x_pvt *) mci->pvt_info; | 975 | pvt = (struct e752x_pvt *) mci->pvt_info; |
827 | pvt->dev_info = &e752x_devs[dev_idx]; | 976 | pvt->dev_info = &e752x_devs[dev_idx]; |
828 | pvt->bridge_ck = pci_get_device(PCI_VENDOR_ID_INTEL, | 977 | pvt->mc_symmetric = ((ddrcsr & 0x10) != 0); |
829 | pvt->dev_info->err_dev, | ||
830 | pvt->bridge_ck); | ||
831 | |||
832 | if (pvt->bridge_ck == NULL) | ||
833 | pvt->bridge_ck = pci_scan_single_device(pdev->bus, | ||
834 | PCI_DEVFN(0, 1)); | ||
835 | 978 | ||
836 | if (pvt->bridge_ck == NULL) { | 979 | if (e752x_get_devs(pdev, dev_idx, pvt)) { |
837 | e752x_printk(KERN_ERR, "error reporting device not found:" | 980 | edac_mc_free(mci); |
838 | "vendor %x device 0x%x (broken BIOS?)\n", | 981 | return -ENODEV; |
839 | PCI_VENDOR_ID_INTEL, e752x_devs[dev_idx].err_dev); | ||
840 | goto fail; | ||
841 | } | 982 | } |
842 | 983 | ||
843 | pvt->mc_symmetric = ((ddrcsr & 0x10) != 0); | ||
844 | debugf3("%s(): more mci init\n", __func__); | 984 | debugf3("%s(): more mci init\n", __func__); |
845 | mci->ctl_name = pvt->dev_info->ctl_name; | 985 | mci->ctl_name = pvt->dev_info->ctl_name; |
846 | mci->edac_check = e752x_check; | 986 | mci->edac_check = e752x_check; |
847 | mci->ctl_page_to_phys = ctl_page_to_phys; | 987 | mci->ctl_page_to_phys = ctl_page_to_phys; |
848 | 988 | ||
849 | /* find out the device types */ | 989 | e752x_init_csrows(mci, pdev, ddrcsr); |
850 | pci_read_config_dword(pdev, E752X_DRA, &dra); | 990 | e752x_init_mem_map_table(pdev, pvt); |
851 | |||
852 | /* | ||
853 | * The dram row boundary (DRB) reg values are boundary address for | ||
854 | * each DRAM row with a granularity of 64 or 128MB (single/dual | ||
855 | * channel operation). DRB regs are cumulative; therefore DRB7 will | ||
856 | * contain the total memory contained in all eight rows. | ||
857 | */ | ||
858 | for (last_cumul_size = index = 0; index < mci->nr_csrows; index++) { | ||
859 | u8 value; | ||
860 | u32 cumul_size; | ||
861 | |||
862 | /* mem_dev 0=x8, 1=x4 */ | ||
863 | int mem_dev = (dra >> (index * 4 + 2)) & 0x3; | ||
864 | struct csrow_info *csrow = &mci->csrows[index]; | ||
865 | |||
866 | mem_dev = (mem_dev == 2); | ||
867 | pci_read_config_byte(mci->pdev, E752X_DRB + index, &value); | ||
868 | /* convert a 128 or 64 MiB DRB to a page size. */ | ||
869 | cumul_size = value << (25 + drc_drbg - PAGE_SHIFT); | ||
870 | debugf3("%s(): (%d) cumul_size 0x%x\n", __func__, index, | ||
871 | cumul_size); | ||
872 | |||
873 | if (cumul_size == last_cumul_size) | ||
874 | continue; /* not populated */ | ||
875 | |||
876 | csrow->first_page = last_cumul_size; | ||
877 | csrow->last_page = cumul_size - 1; | ||
878 | csrow->nr_pages = cumul_size - last_cumul_size; | ||
879 | last_cumul_size = cumul_size; | ||
880 | csrow->grain = 1 << 12; /* 4KiB - resolution of CELOG */ | ||
881 | csrow->mtype = MEM_RDDR; /* only one type supported */ | ||
882 | csrow->dtype = mem_dev ? DEV_X4 : DEV_X8; | ||
883 | |||
884 | /* | ||
885 | * if single channel or x8 devices then SECDED | ||
886 | * if dual channel and x4 then S4ECD4ED | ||
887 | */ | ||
888 | if (drc_ddim) { | ||
889 | if (drc_chan && mem_dev) { | ||
890 | csrow->edac_mode = EDAC_S4ECD4ED; | ||
891 | mci->edac_cap |= EDAC_FLAG_S4ECD4ED; | ||
892 | } else { | ||
893 | csrow->edac_mode = EDAC_SECDED; | ||
894 | mci->edac_cap |= EDAC_FLAG_SECDED; | ||
895 | } | ||
896 | } else | ||
897 | csrow->edac_mode = EDAC_NONE; | ||
898 | } | ||
899 | |||
900 | /* Fill in the memory map table */ | ||
901 | { | ||
902 | u8 value; | ||
903 | u8 last = 0; | ||
904 | u8 row = 0; | ||
905 | |||
906 | for (index = 0; index < 8; index += 2) { | ||
907 | pci_read_config_byte(mci->pdev, E752X_DRB + index, | ||
908 | &value); | ||
909 | |||
910 | /* test if there is a dimm in this slot */ | ||
911 | if (value == last) { | ||
912 | /* no dimm in the slot, so flag it as empty */ | ||
913 | pvt->map[index] = 0xff; | ||
914 | pvt->map[index + 1] = 0xff; | ||
915 | } else { /* there is a dimm in the slot */ | ||
916 | pvt->map[index] = row; | ||
917 | row++; | ||
918 | last = value; | ||
919 | /* test the next value to see if the dimm is | ||
920 | double sided */ | ||
921 | pci_read_config_byte(mci->pdev, | ||
922 | E752X_DRB + index + 1, | ||
923 | &value); | ||
924 | pvt->map[index + 1] = (value == last) ? | ||
925 | 0xff : /* the dimm is single sided, | ||
926 | * so flag as empty | ||
927 | */ | ||
928 | row; /* this is a double sided dimm | ||
929 | * to save the next row # | ||
930 | */ | ||
931 | row++; | ||
932 | last = value; | ||
933 | } | ||
934 | } | ||
935 | } | ||
936 | 991 | ||
937 | /* set the map type. 1 = normal, 0 = reversed */ | 992 | /* set the map type. 1 = normal, 0 = reversed */ |
938 | pci_read_config_byte(mci->pdev, E752X_DRM, &stat8); | 993 | pci_read_config_byte(pdev, E752X_DRM, &stat8); |
939 | pvt->map_type = ((stat8 & 0x0f) > ((stat8 >> 4) & 0x0f)); | 994 | pvt->map_type = ((stat8 & 0x0f) > ((stat8 >> 4) & 0x0f)); |
940 | 995 | ||
941 | mci->edac_cap |= EDAC_FLAG_NONE; | 996 | mci->edac_cap |= EDAC_FLAG_NONE; |
942 | debugf3("%s(): tolm, remapbase, remaplimit\n", __func__); | 997 | debugf3("%s(): tolm, remapbase, remaplimit\n", __func__); |
943 | 998 | ||
944 | /* load the top of low memory, remap base, and remap limit vars */ | 999 | /* load the top of low memory, remap base, and remap limit vars */ |
945 | pci_read_config_word(mci->pdev, E752X_TOLM, &pci_data); | 1000 | pci_read_config_word(pdev, E752X_TOLM, &pci_data); |
946 | pvt->tolm = ((u32) pci_data) << 4; | 1001 | pvt->tolm = ((u32) pci_data) << 4; |
947 | pci_read_config_word(mci->pdev, E752X_REMAPBASE, &pci_data); | 1002 | pci_read_config_word(pdev, E752X_REMAPBASE, &pci_data); |
948 | pvt->remapbase = ((u32) pci_data) << 14; | 1003 | pvt->remapbase = ((u32) pci_data) << 14; |
949 | pci_read_config_word(mci->pdev, E752X_REMAPLIMIT, &pci_data); | 1004 | pci_read_config_word(pdev, E752X_REMAPLIMIT, &pci_data); |
950 | pvt->remaplimit = ((u32) pci_data) << 14; | 1005 | pvt->remaplimit = ((u32) pci_data) << 14; |
951 | e752x_printk(KERN_INFO, | 1006 | e752x_printk(KERN_INFO, |
952 | "tolm = %x, remapbase = %x, remaplimit = %x\n", pvt->tolm, | 1007 | "tolm = %x, remapbase = %x, remaplimit = %x\n", pvt->tolm, |
953 | pvt->remapbase, pvt->remaplimit); | 1008 | pvt->remapbase, pvt->remaplimit); |
954 | 1009 | ||
955 | if (edac_mc_add_mc(mci)) { | 1010 | /* Here we assume that we will never see multiple instances of this |
1011 | * type of memory controller. The ID is therefore hardcoded to 0. | ||
1012 | */ | ||
1013 | if (edac_mc_add_mc(mci,0)) { | ||
956 | debugf3("%s(): failed edac_mc_add_mc()\n", __func__); | 1014 | debugf3("%s(): failed edac_mc_add_mc()\n", __func__); |
957 | goto fail; | 1015 | goto fail; |
958 | } | 1016 | } |
959 | 1017 | ||
960 | dev = pci_get_device(PCI_VENDOR_ID_INTEL, e752x_devs[dev_idx].ctl_dev, | 1018 | e752x_init_error_reporting_regs(pvt); |
961 | NULL); | ||
962 | pvt->dev_d0f0 = dev; | ||
963 | /* find the error reporting device and clear errors */ | ||
964 | dev = pvt->dev_d0f1 = pci_dev_get(pvt->bridge_ck); | ||
965 | /* Turn off error disable & SMI in case the BIOS turned it on */ | ||
966 | pci_write_config_byte(dev, E752X_HI_ERRMASK, 0x00); | ||
967 | pci_write_config_byte(dev, E752X_HI_SMICMD, 0x00); | ||
968 | pci_write_config_word(dev, E752X_SYSBUS_ERRMASK, 0x00); | ||
969 | pci_write_config_word(dev, E752X_SYSBUS_SMICMD, 0x00); | ||
970 | pci_write_config_byte(dev, E752X_BUF_ERRMASK, 0x00); | ||
971 | pci_write_config_byte(dev, E752X_BUF_SMICMD, 0x00); | ||
972 | pci_write_config_byte(dev, E752X_DRAM_ERRMASK, 0x00); | ||
973 | pci_write_config_byte(dev, E752X_DRAM_SMICMD, 0x00); | ||
974 | |||
975 | e752x_get_error_info(mci, &discard); /* clear other MCH errors */ | 1019 | e752x_get_error_info(mci, &discard); /* clear other MCH errors */ |
976 | 1020 | ||
977 | /* get this far and it's successful */ | 1021 | /* get this far and it's successful */ |
@@ -979,20 +1023,12 @@ static int e752x_probe1(struct pci_dev *pdev, int dev_idx) | |||
979 | return 0; | 1023 | return 0; |
980 | 1024 | ||
981 | fail: | 1025 | fail: |
982 | if (mci) { | 1026 | pci_dev_put(pvt->dev_d0f0); |
983 | if (pvt->dev_d0f0) | 1027 | pci_dev_put(pvt->dev_d0f1); |
984 | pci_dev_put(pvt->dev_d0f0); | 1028 | pci_dev_put(pvt->bridge_ck); |
985 | 1029 | edac_mc_free(mci); | |
986 | if (pvt->dev_d0f1) | ||
987 | pci_dev_put(pvt->dev_d0f1); | ||
988 | |||
989 | if (pvt->bridge_ck) | ||
990 | pci_dev_put(pvt->bridge_ck); | ||
991 | |||
992 | edac_mc_free(mci); | ||
993 | } | ||
994 | 1030 | ||
995 | return rc; | 1031 | return -ENODEV; |
996 | } | 1032 | } |
997 | 1033 | ||
998 | /* returns count (>= 0), or negative on error */ | 1034 | /* returns count (>= 0), or negative on error */ |
@@ -1015,7 +1051,7 @@ static void __devexit e752x_remove_one(struct pci_dev *pdev) | |||
1015 | 1051 | ||
1016 | debugf0("%s()\n", __func__); | 1052 | debugf0("%s()\n", __func__); |
1017 | 1053 | ||
1018 | if ((mci = edac_mc_del_mc(pdev)) == NULL) | 1054 | if ((mci = edac_mc_del_mc(&pdev->dev)) == NULL) |
1019 | return; | 1055 | return; |
1020 | 1056 | ||
1021 | pvt = (struct e752x_pvt *) mci->pvt_info; | 1057 | pvt = (struct e752x_pvt *) mci->pvt_info; |