Loading drivers/edac/amd64_edac.h +9 −8 Original line number Diff line number Diff line Loading @@ -267,18 +267,19 @@ #define online_spare_bad_dramcs(pvt, c) (((pvt)->online_spare >> (4 + 4 * (c))) & 0x7) #define F10_NB_ARRAY_ADDR 0xB8 #define F10_NB_ARRAY_DRAM_ECC BIT(31) #define F10_NB_ARRAY_DRAM BIT(31) /* Bits [2:1] are used to select 16-byte section within a 64-byte cacheline */ #define SET_NB_ARRAY_ADDRESS(section) (((section) & 0x3) << 1) #define SET_NB_ARRAY_ADDR(section) (((section) & 0x3) << 1) #define F10_NB_ARRAY_DATA 0xBC #define SET_NB_DRAM_INJECTION_WRITE(word, bits) \ (BIT(((word) & 0xF) + 20) | \ BIT(17) | bits) #define SET_NB_DRAM_INJECTION_READ(word, bits) \ (BIT(((word) & 0xF) + 20) | \ BIT(16) | bits) #define SET_NB_DRAM_INJECTION_WRITE(inj) \ (BIT(((inj.word) & 0xF) + 20) | \ BIT(17) | inj.bit_map) #define SET_NB_DRAM_INJECTION_READ(inj) \ (BIT(((inj.word) & 0xF) + 20) | \ BIT(16) | inj.bit_map) #define NBCAP 0xE8 #define NBCAP_CHIPKILL BIT(4) Loading drivers/edac/amd64_edac_inj.c +51 −61 Original line number Diff line number Diff line Loading @@ -22,10 +22,11 @@ static ssize_t amd64_inject_section_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value > 3) { amd64_warn("%s: invalid section 0x%lx\n", __func__, value); Loading @@ -35,8 +36,6 @@ static ssize_t amd64_inject_section_store(struct device *dev, pvt->injection.section = (u32) value; return count; } return ret; } static ssize_t amd64_inject_word_show(struct device *dev, struct device_attribute *mattr, Loading @@ -60,10 +59,11 @@ static ssize_t amd64_inject_word_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value > 8) { amd64_warn("%s: invalid word 0x%lx\n", __func__, value); Loading @@ -73,8 +73,6 @@ static ssize_t amd64_inject_word_store(struct device *dev, pvt->injection.word = (u32) value; return count; } return ret; } static ssize_t amd64_inject_ecc_vector_show(struct device *dev, struct device_attribute *mattr, Loading @@ -97,22 +95,20 @@ static ssize_t amd64_inject_ecc_vector_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 16, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value & 0xFFFF0000) { amd64_warn("%s: invalid EccVector: 0x%lx\n", __func__, value); amd64_warn("%s: invalid EccVector: 0x%lx\n", __func__, value); return -EINVAL; } pvt->injection.bit_map = (u32) value; return count; } return ret; } /* * Do a DRAM ECC read. Assemble staged values in the pvt area, format into Loading @@ -126,29 +122,26 @@ static ssize_t amd64_inject_read_store(struct device *dev, struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; u32 section, word_bits; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; /* Form value to choose 16-byte section of cacheline */ section = F10_NB_ARRAY_DRAM_ECC | SET_NB_ARRAY_ADDRESS(pvt->injection.section); section = F10_NB_ARRAY_DRAM | SET_NB_ARRAY_ADDR(pvt->injection.section); amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_ADDR, section); word_bits = SET_NB_DRAM_INJECTION_READ(pvt->injection.word, pvt->injection.bit_map); word_bits = SET_NB_DRAM_INJECTION_READ(pvt->injection); /* Issue 'word' and 'bit' along with the READ request */ amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_DATA, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); return count; } return ret; } /* * Do a DRAM ECC write. Assemble staged values in the pvt area and format into Loading @@ -162,29 +155,26 @@ static ssize_t amd64_inject_write_store(struct device *dev, struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; u32 section, word_bits; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; /* Form value to choose 16-byte section of cacheline */ section = F10_NB_ARRAY_DRAM_ECC | SET_NB_ARRAY_ADDRESS(pvt->injection.section); section = F10_NB_ARRAY_DRAM | SET_NB_ARRAY_ADDR(pvt->injection.section); amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_ADDR, section); word_bits = SET_NB_DRAM_INJECTION_WRITE(pvt->injection.word, pvt->injection.bit_map); word_bits = SET_NB_DRAM_INJECTION_WRITE(pvt->injection); /* Issue 'word' and 'bit' along with the READ request */ amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_DATA, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); return count; } return ret; } /* * update NUM_INJ_ATTRS in case you add new members Loading Loading
drivers/edac/amd64_edac.h +9 −8 Original line number Diff line number Diff line Loading @@ -267,18 +267,19 @@ #define online_spare_bad_dramcs(pvt, c) (((pvt)->online_spare >> (4 + 4 * (c))) & 0x7) #define F10_NB_ARRAY_ADDR 0xB8 #define F10_NB_ARRAY_DRAM_ECC BIT(31) #define F10_NB_ARRAY_DRAM BIT(31) /* Bits [2:1] are used to select 16-byte section within a 64-byte cacheline */ #define SET_NB_ARRAY_ADDRESS(section) (((section) & 0x3) << 1) #define SET_NB_ARRAY_ADDR(section) (((section) & 0x3) << 1) #define F10_NB_ARRAY_DATA 0xBC #define SET_NB_DRAM_INJECTION_WRITE(word, bits) \ (BIT(((word) & 0xF) + 20) | \ BIT(17) | bits) #define SET_NB_DRAM_INJECTION_READ(word, bits) \ (BIT(((word) & 0xF) + 20) | \ BIT(16) | bits) #define SET_NB_DRAM_INJECTION_WRITE(inj) \ (BIT(((inj.word) & 0xF) + 20) | \ BIT(17) | inj.bit_map) #define SET_NB_DRAM_INJECTION_READ(inj) \ (BIT(((inj.word) & 0xF) + 20) | \ BIT(16) | inj.bit_map) #define NBCAP 0xE8 #define NBCAP_CHIPKILL BIT(4) Loading
drivers/edac/amd64_edac_inj.c +51 −61 Original line number Diff line number Diff line Loading @@ -22,10 +22,11 @@ static ssize_t amd64_inject_section_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value > 3) { amd64_warn("%s: invalid section 0x%lx\n", __func__, value); Loading @@ -35,8 +36,6 @@ static ssize_t amd64_inject_section_store(struct device *dev, pvt->injection.section = (u32) value; return count; } return ret; } static ssize_t amd64_inject_word_show(struct device *dev, struct device_attribute *mattr, Loading @@ -60,10 +59,11 @@ static ssize_t amd64_inject_word_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value > 8) { amd64_warn("%s: invalid word 0x%lx\n", __func__, value); Loading @@ -73,8 +73,6 @@ static ssize_t amd64_inject_word_store(struct device *dev, pvt->injection.word = (u32) value; return count; } return ret; } static ssize_t amd64_inject_ecc_vector_show(struct device *dev, struct device_attribute *mattr, Loading @@ -97,22 +95,20 @@ static ssize_t amd64_inject_ecc_vector_store(struct device *dev, struct mem_ctl_info *mci = to_mci(dev); struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; int ret = 0; int ret; ret = strict_strtoul(data, 16, &value); if (ret != -EINVAL) { if (ret < 0) return ret; if (value & 0xFFFF0000) { amd64_warn("%s: invalid EccVector: 0x%lx\n", __func__, value); amd64_warn("%s: invalid EccVector: 0x%lx\n", __func__, value); return -EINVAL; } pvt->injection.bit_map = (u32) value; return count; } return ret; } /* * Do a DRAM ECC read. Assemble staged values in the pvt area, format into Loading @@ -126,29 +122,26 @@ static ssize_t amd64_inject_read_store(struct device *dev, struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; u32 section, word_bits; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; /* Form value to choose 16-byte section of cacheline */ section = F10_NB_ARRAY_DRAM_ECC | SET_NB_ARRAY_ADDRESS(pvt->injection.section); section = F10_NB_ARRAY_DRAM | SET_NB_ARRAY_ADDR(pvt->injection.section); amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_ADDR, section); word_bits = SET_NB_DRAM_INJECTION_READ(pvt->injection.word, pvt->injection.bit_map); word_bits = SET_NB_DRAM_INJECTION_READ(pvt->injection); /* Issue 'word' and 'bit' along with the READ request */ amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_DATA, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); return count; } return ret; } /* * Do a DRAM ECC write. Assemble staged values in the pvt area and format into Loading @@ -162,29 +155,26 @@ static ssize_t amd64_inject_write_store(struct device *dev, struct amd64_pvt *pvt = mci->pvt_info; unsigned long value; u32 section, word_bits; int ret = 0; int ret; ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { if (ret < 0) return ret; /* Form value to choose 16-byte section of cacheline */ section = F10_NB_ARRAY_DRAM_ECC | SET_NB_ARRAY_ADDRESS(pvt->injection.section); section = F10_NB_ARRAY_DRAM | SET_NB_ARRAY_ADDR(pvt->injection.section); amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_ADDR, section); word_bits = SET_NB_DRAM_INJECTION_WRITE(pvt->injection.word, pvt->injection.bit_map); word_bits = SET_NB_DRAM_INJECTION_WRITE(pvt->injection); /* Issue 'word' and 'bit' along with the READ request */ amd64_write_pci_cfg(pvt->F3, F10_NB_ARRAY_DATA, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); edac_dbg(0, "section=0x%x word_bits=0x%x\n", section, word_bits); return count; } return ret; } /* * update NUM_INJ_ATTRS in case you add new members Loading