* Convert a bunch of drivers to static attribute groups (Takashi Iwai)
* misc cleanups -----BEGIN PGP SIGNATURE----- Version: GnuPG v1 iQIcBAABAgAGBQJVK3RNAAoJEBLB8Bhh3lVKsTEP/3iQpdwyNzMO7z8uTuC6fJCL CZdWT5VyUg+JVWP9GuXBUUfyUngWP0d+krIcIFQBiRZIpd+Ib9m6bUqm/vXkbfI+ nPj9WHe8peOOgeo/fErDu/JOcZT87ceP92IrjKsn8VWBLp6S7X03ulW/MlCVvlmk eqf5dg5d142AkYm6QkDuDgxQwR643IjvEZgWjcuxvPXkAx/6YV26GBSh6SgxJ+wZ BANTuW4tBiKk3ruc9Z+O8li7ImjwWDbgFVZ3VmSvClXKpvNgxmk5PBMJJICwBXgG sPQRpxv+I64mZon/T3EE2VEuMyBZ0E9t2ZC3O9G74AqnNAVDX2r/mnOvil4Lm28+ bPvpbH1WLvxUULA/rgCS5ftsYA6EVGuej/Fwo4g4k/z5EjN+TEE8S3nfskHwxfl0 r7cHk9YYQbGD1V2IlVR0l5iqcnUOTFrDVPUBmbi9jJPz1qIA7pdlPS9o4xlBrLvy +hV2Jpv0VO494lxroRwo4ujgomwOQU4ymsYO9vPu8dD/nCjrs91BPsLVNxA9qnxl lPQ4ARjyFcTqlgvWSQnwVj/RKnoe4iT30exay+PQb2Jro91Mdrq5OTmH8h60X2Iz BfLxbODOJXEuu4NHZPTnhvwStlu8OVBkF330hONS9EIHIww0qieZtdesxBMgUoG0 RHaqTnAF8MIjZAF0FICw =h2wl -----END PGP SIGNATURE----- Merge tag 'edac_for_4.1' of git://git.kernel.org/pub/scm/linux/kernel/git/bp/bp Pull EDAC updates from Borislav Petkov: - convert a bunch of drivers to static attribute groups (Takashi Iwai) - misc cleanups * tag 'edac_for_4.1' of git://git.kernel.org/pub/scm/linux/kernel/git/bp/bp: EDAC: Constify of_device_id array EDAC, i82443bxgx: Don't export static symbol EDAC, amd64_edac: Get rid of per-node driver instances EDAC: Properly unwind on failure path in edac_init() EDAC: highbank: Use static attribute groups for sysfs entries EDAC: octeon: Use static attribute groups for sysfs entries EDAC: mpc85xx: Use static attribute groups for sysfs entries EDAC: i7core: Use static attribute groups for sysfs entries EDAC: i7core: Return proper error codes for kzalloc() errors EDAC: amd64: Use static attribute groups EDAC: Allow to pass driver-specific attribute groups EDAC: Use static attribute groups for managing sysfs entries EDAC: Delete unnecessary checks before pci_dev_put()
This commit is contained in:
commit
1a370f4cd9
|
@ -20,8 +20,7 @@ static struct msr __percpu *msrs;
|
|||
*/
|
||||
static atomic_t drv_instances = ATOMIC_INIT(0);
|
||||
|
||||
/* Per-node driver instances */
|
||||
static struct mem_ctl_info **mcis;
|
||||
/* Per-node stuff */
|
||||
static struct ecc_settings **ecc_stngs;
|
||||
|
||||
/*
|
||||
|
@ -903,9 +902,17 @@ static int k8_early_channel_count(struct amd64_pvt *pvt)
|
|||
/* On F10h and later ErrAddr is MC4_ADDR[47:1] */
|
||||
static u64 get_error_address(struct amd64_pvt *pvt, struct mce *m)
|
||||
{
|
||||
u64 addr;
|
||||
u16 mce_nid = amd_get_nb_id(m->extcpu);
|
||||
struct mem_ctl_info *mci;
|
||||
u8 start_bit = 1;
|
||||
u8 end_bit = 47;
|
||||
u64 addr;
|
||||
|
||||
mci = edac_mc_find(mce_nid);
|
||||
if (!mci)
|
||||
return 0;
|
||||
|
||||
pvt = mci->pvt_info;
|
||||
|
||||
if (pvt->fam == 0xf) {
|
||||
start_bit = 3;
|
||||
|
@ -918,17 +925,13 @@ static u64 get_error_address(struct amd64_pvt *pvt, struct mce *m)
|
|||
* Erratum 637 workaround
|
||||
*/
|
||||
if (pvt->fam == 0x15) {
|
||||
struct amd64_pvt *pvt;
|
||||
u64 cc6_base, tmp_addr;
|
||||
u32 tmp;
|
||||
u16 mce_nid;
|
||||
u8 intlv_en;
|
||||
|
||||
if ((addr & GENMASK_ULL(47, 24)) >> 24 != 0x00fdf7)
|
||||
return addr;
|
||||
|
||||
mce_nid = amd_get_nb_id(m->extcpu);
|
||||
pvt = mcis[mce_nid]->pvt_info;
|
||||
|
||||
amd64_read_pci_cfg(pvt->F1, DRAM_LOCAL_NODE_LIM, &tmp);
|
||||
intlv_en = tmp >> 21 & 0x7;
|
||||
|
@ -1511,7 +1514,7 @@ static int f1x_lookup_addr_in_dct(u64 in_addr, u8 nid, u8 dct)
|
|||
int cs_found = -EINVAL;
|
||||
int csrow;
|
||||
|
||||
mci = mcis[nid];
|
||||
mci = edac_mc_find(nid);
|
||||
if (!mci)
|
||||
return cs_found;
|
||||
|
||||
|
@ -2663,34 +2666,6 @@ static bool ecc_enabled(struct pci_dev *F3, u16 nid)
|
|||
return true;
|
||||
}
|
||||
|
||||
static int set_mc_sysfs_attrs(struct mem_ctl_info *mci)
|
||||
{
|
||||
struct amd64_pvt *pvt = mci->pvt_info;
|
||||
int rc;
|
||||
|
||||
rc = amd64_create_sysfs_dbg_files(mci);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
if (pvt->fam >= 0x10) {
|
||||
rc = amd64_create_sysfs_inject_files(mci);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void del_mc_sysfs_attrs(struct mem_ctl_info *mci)
|
||||
{
|
||||
struct amd64_pvt *pvt = mci->pvt_info;
|
||||
|
||||
amd64_remove_sysfs_dbg_files(mci);
|
||||
|
||||
if (pvt->fam >= 0x10)
|
||||
amd64_remove_sysfs_inject_files(mci);
|
||||
}
|
||||
|
||||
static void setup_mci_misc_attrs(struct mem_ctl_info *mci,
|
||||
struct amd64_family_type *fam)
|
||||
{
|
||||
|
@ -2778,6 +2753,16 @@ static struct amd64_family_type *per_family_init(struct amd64_pvt *pvt)
|
|||
return fam_type;
|
||||
}
|
||||
|
||||
static const struct attribute_group *amd64_edac_attr_groups[] = {
|
||||
#ifdef CONFIG_EDAC_DEBUG
|
||||
&amd64_edac_dbg_group,
|
||||
#endif
|
||||
#ifdef CONFIG_EDAC_AMD64_ERROR_INJECTION
|
||||
&amd64_edac_inj_group,
|
||||
#endif
|
||||
NULL
|
||||
};
|
||||
|
||||
static int init_one_instance(struct pci_dev *F2)
|
||||
{
|
||||
struct amd64_pvt *pvt = NULL;
|
||||
|
@ -2844,14 +2829,10 @@ static int init_one_instance(struct pci_dev *F2)
|
|||
mci->edac_cap = EDAC_FLAG_NONE;
|
||||
|
||||
ret = -ENODEV;
|
||||
if (edac_mc_add_mc(mci)) {
|
||||
if (edac_mc_add_mc_with_groups(mci, amd64_edac_attr_groups)) {
|
||||
edac_dbg(1, "failed edac_mc_add_mc()\n");
|
||||
goto err_add_mc;
|
||||
}
|
||||
if (set_mc_sysfs_attrs(mci)) {
|
||||
edac_dbg(1, "failed edac_mc_add_mc()\n");
|
||||
goto err_add_sysfs;
|
||||
}
|
||||
|
||||
/* register stuff with EDAC MCE */
|
||||
if (report_gart_errors)
|
||||
|
@ -2859,14 +2840,10 @@ static int init_one_instance(struct pci_dev *F2)
|
|||
|
||||
amd_register_ecc_decoder(decode_bus_error);
|
||||
|
||||
mcis[nid] = mci;
|
||||
|
||||
atomic_inc(&drv_instances);
|
||||
|
||||
return 0;
|
||||
|
||||
err_add_sysfs:
|
||||
edac_mc_del_mc(mci->pdev);
|
||||
err_add_mc:
|
||||
edac_mc_free(mci);
|
||||
|
||||
|
@ -2940,7 +2917,6 @@ static void remove_one_instance(struct pci_dev *pdev)
|
|||
mci = find_mci_by_dev(&pdev->dev);
|
||||
WARN_ON(!mci);
|
||||
|
||||
del_mc_sysfs_attrs(mci);
|
||||
/* Remove from EDAC CORE tracking list */
|
||||
mci = edac_mc_del_mc(&pdev->dev);
|
||||
if (!mci)
|
||||
|
@ -2961,7 +2937,6 @@ static void remove_one_instance(struct pci_dev *pdev)
|
|||
|
||||
/* Free the EDAC CORE resources */
|
||||
mci->pvt_info = NULL;
|
||||
mcis[nid] = NULL;
|
||||
|
||||
kfree(pvt);
|
||||
edac_mc_free(mci);
|
||||
|
@ -2999,7 +2974,7 @@ static void setup_pci_device(void)
|
|||
if (pci_ctl)
|
||||
return;
|
||||
|
||||
mci = mcis[0];
|
||||
mci = edac_mc_find(0);
|
||||
if (!mci)
|
||||
return;
|
||||
|
||||
|
@ -3023,9 +2998,8 @@ static int __init amd64_edac_init(void)
|
|||
goto err_ret;
|
||||
|
||||
err = -ENOMEM;
|
||||
mcis = kzalloc(amd_nb_num() * sizeof(mcis[0]), GFP_KERNEL);
|
||||
ecc_stngs = kzalloc(amd_nb_num() * sizeof(ecc_stngs[0]), GFP_KERNEL);
|
||||
if (!(mcis && ecc_stngs))
|
||||
if (!ecc_stngs)
|
||||
goto err_free;
|
||||
|
||||
msrs = msrs_alloc();
|
||||
|
@ -3056,9 +3030,6 @@ err_pci:
|
|||
msrs = NULL;
|
||||
|
||||
err_free:
|
||||
kfree(mcis);
|
||||
mcis = NULL;
|
||||
|
||||
kfree(ecc_stngs);
|
||||
ecc_stngs = NULL;
|
||||
|
||||
|
@ -3076,9 +3047,6 @@ static void __exit amd64_edac_exit(void)
|
|||
kfree(ecc_stngs);
|
||||
ecc_stngs = NULL;
|
||||
|
||||
kfree(mcis);
|
||||
mcis = NULL;
|
||||
|
||||
msrs_free(msrs);
|
||||
msrs = NULL;
|
||||
}
|
||||
|
|
|
@ -453,31 +453,11 @@ struct ecc_settings {
|
|||
};
|
||||
|
||||
#ifdef CONFIG_EDAC_DEBUG
|
||||
int amd64_create_sysfs_dbg_files(struct mem_ctl_info *mci);
|
||||
void amd64_remove_sysfs_dbg_files(struct mem_ctl_info *mci);
|
||||
|
||||
#else
|
||||
static inline int amd64_create_sysfs_dbg_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
static void inline amd64_remove_sysfs_dbg_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
}
|
||||
extern const struct attribute_group amd64_edac_dbg_group;
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_EDAC_AMD64_ERROR_INJECTION
|
||||
int amd64_create_sysfs_inject_files(struct mem_ctl_info *mci);
|
||||
void amd64_remove_sysfs_inject_files(struct mem_ctl_info *mci);
|
||||
|
||||
#else
|
||||
static inline int amd64_create_sysfs_inject_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
static inline void amd64_remove_sysfs_inject_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
}
|
||||
extern const struct attribute_group amd64_edac_inj_group;
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
|
|
@ -40,34 +40,15 @@ static DEVICE_ATTR(topmem, S_IRUGO, amd64_top_mem_show, NULL);
|
|||
static DEVICE_ATTR(topmem2, S_IRUGO, amd64_top_mem2_show, NULL);
|
||||
static DEVICE_ATTR(dram_hole, S_IRUGO, amd64_hole_show, NULL);
|
||||
|
||||
int amd64_create_sysfs_dbg_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
int rc;
|
||||
static struct attribute *amd64_edac_dbg_attrs[] = {
|
||||
&dev_attr_dhar.attr,
|
||||
&dev_attr_dbam.attr,
|
||||
&dev_attr_topmem.attr,
|
||||
&dev_attr_topmem2.attr,
|
||||
&dev_attr_dram_hole.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
rc = device_create_file(&mci->dev, &dev_attr_dhar);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_dbam);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_topmem);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_topmem2);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_dram_hole);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void amd64_remove_sysfs_dbg_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
device_remove_file(&mci->dev, &dev_attr_dhar);
|
||||
device_remove_file(&mci->dev, &dev_attr_dbam);
|
||||
device_remove_file(&mci->dev, &dev_attr_topmem);
|
||||
device_remove_file(&mci->dev, &dev_attr_topmem2);
|
||||
device_remove_file(&mci->dev, &dev_attr_dram_hole);
|
||||
}
|
||||
const struct attribute_group amd64_edac_dbg_group = {
|
||||
.attrs = amd64_edac_dbg_attrs,
|
||||
};
|
||||
|
|
|
@ -207,35 +207,28 @@ static DEVICE_ATTR(inject_write, S_IWUSR,
|
|||
static DEVICE_ATTR(inject_read, S_IWUSR,
|
||||
NULL, amd64_inject_read_store);
|
||||
|
||||
static struct attribute *amd64_edac_inj_attrs[] = {
|
||||
&dev_attr_inject_section.attr,
|
||||
&dev_attr_inject_word.attr,
|
||||
&dev_attr_inject_ecc_vector.attr,
|
||||
&dev_attr_inject_write.attr,
|
||||
&dev_attr_inject_read.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
int amd64_create_sysfs_inject_files(struct mem_ctl_info *mci)
|
||||
static umode_t amd64_edac_inj_is_visible(struct kobject *kobj,
|
||||
struct attribute *attr, int idx)
|
||||
{
|
||||
int rc;
|
||||
struct device *dev = kobj_to_dev(kobj);
|
||||
struct mem_ctl_info *mci = container_of(dev, struct mem_ctl_info, dev);
|
||||
struct amd64_pvt *pvt = mci->pvt_info;
|
||||
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_section);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_word);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_ecc_vector);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_write);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_read);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
return 0;
|
||||
if (pvt->fam < 0x10)
|
||||
return 0;
|
||||
return attr->mode;
|
||||
}
|
||||
|
||||
void amd64_remove_sysfs_inject_files(struct mem_ctl_info *mci)
|
||||
{
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_section);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_word);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_ecc_vector);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_write);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_read);
|
||||
}
|
||||
const struct attribute_group amd64_edac_inj_group = {
|
||||
.attrs = amd64_edac_inj_attrs,
|
||||
.is_visible = amd64_edac_inj_is_visible,
|
||||
};
|
||||
|
|
|
@ -446,7 +446,9 @@ struct mem_ctl_info *edac_mc_alloc(unsigned mc_num,
|
|||
unsigned n_layers,
|
||||
struct edac_mc_layer *layers,
|
||||
unsigned sz_pvt);
|
||||
extern int edac_mc_add_mc(struct mem_ctl_info *mci);
|
||||
extern int edac_mc_add_mc_with_groups(struct mem_ctl_info *mci,
|
||||
const struct attribute_group **groups);
|
||||
#define edac_mc_add_mc(mci) edac_mc_add_mc_with_groups(mci, NULL)
|
||||
extern void edac_mc_free(struct mem_ctl_info *mci);
|
||||
extern struct mem_ctl_info *edac_mc_find(int idx);
|
||||
extern struct mem_ctl_info *find_mci_by_dev(struct device *dev);
|
||||
|
|
|
@ -710,9 +710,10 @@ struct mem_ctl_info *edac_mc_find(int idx)
|
|||
EXPORT_SYMBOL(edac_mc_find);
|
||||
|
||||
/**
|
||||
* edac_mc_add_mc: Insert the 'mci' structure into the mci global list and
|
||||
* create sysfs entries associated with mci structure
|
||||
* edac_mc_add_mc_with_groups: Insert the 'mci' structure into the mci
|
||||
* global list and create sysfs entries associated with mci structure
|
||||
* @mci: pointer to the mci structure to be added to the list
|
||||
* @groups: optional attribute groups for the driver-specific sysfs entries
|
||||
*
|
||||
* Return:
|
||||
* 0 Success
|
||||
|
@ -720,7 +721,8 @@ EXPORT_SYMBOL(edac_mc_find);
|
|||
*/
|
||||
|
||||
/* FIXME - should a warning be printed if no error detection? correction? */
|
||||
int edac_mc_add_mc(struct mem_ctl_info *mci)
|
||||
int edac_mc_add_mc_with_groups(struct mem_ctl_info *mci,
|
||||
const struct attribute_group **groups)
|
||||
{
|
||||
int ret = -EINVAL;
|
||||
edac_dbg(0, "\n");
|
||||
|
@ -771,7 +773,7 @@ int edac_mc_add_mc(struct mem_ctl_info *mci)
|
|||
|
||||
mci->bus = &mc_bus[mci->mc_idx];
|
||||
|
||||
if (edac_create_sysfs_mci_device(mci)) {
|
||||
if (edac_create_sysfs_mci_device(mci, groups)) {
|
||||
edac_mc_printk(mci, KERN_WARNING,
|
||||
"failed to create sysfs device\n");
|
||||
goto fail1;
|
||||
|
@ -805,7 +807,7 @@ fail0:
|
|||
mutex_unlock(&mem_ctls_mutex);
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(edac_mc_add_mc);
|
||||
EXPORT_SYMBOL_GPL(edac_mc_add_mc_with_groups);
|
||||
|
||||
/**
|
||||
* edac_mc_del_mc: Remove sysfs entries for specified mci structure and
|
||||
|
|
|
@ -323,13 +323,14 @@ DEVICE_CHANNEL(ch5_dimm_label, S_IRUGO | S_IWUSR,
|
|||
channel_dimm_label_show, channel_dimm_label_store, 5);
|
||||
|
||||
/* Total possible dynamic DIMM Label attribute file table */
|
||||
static struct device_attribute *dynamic_csrow_dimm_attr[] = {
|
||||
&dev_attr_legacy_ch0_dimm_label.attr,
|
||||
&dev_attr_legacy_ch1_dimm_label.attr,
|
||||
&dev_attr_legacy_ch2_dimm_label.attr,
|
||||
&dev_attr_legacy_ch3_dimm_label.attr,
|
||||
&dev_attr_legacy_ch4_dimm_label.attr,
|
||||
&dev_attr_legacy_ch5_dimm_label.attr
|
||||
static struct attribute *dynamic_csrow_dimm_attr[] = {
|
||||
&dev_attr_legacy_ch0_dimm_label.attr.attr,
|
||||
&dev_attr_legacy_ch1_dimm_label.attr.attr,
|
||||
&dev_attr_legacy_ch2_dimm_label.attr.attr,
|
||||
&dev_attr_legacy_ch3_dimm_label.attr.attr,
|
||||
&dev_attr_legacy_ch4_dimm_label.attr.attr,
|
||||
&dev_attr_legacy_ch5_dimm_label.attr.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
/* possible dynamic channel ce_count attribute files */
|
||||
|
@ -347,13 +348,45 @@ DEVICE_CHANNEL(ch5_ce_count, S_IRUGO,
|
|||
channel_ce_count_show, NULL, 5);
|
||||
|
||||
/* Total possible dynamic ce_count attribute file table */
|
||||
static struct device_attribute *dynamic_csrow_ce_count_attr[] = {
|
||||
&dev_attr_legacy_ch0_ce_count.attr,
|
||||
&dev_attr_legacy_ch1_ce_count.attr,
|
||||
&dev_attr_legacy_ch2_ce_count.attr,
|
||||
&dev_attr_legacy_ch3_ce_count.attr,
|
||||
&dev_attr_legacy_ch4_ce_count.attr,
|
||||
&dev_attr_legacy_ch5_ce_count.attr
|
||||
static struct attribute *dynamic_csrow_ce_count_attr[] = {
|
||||
&dev_attr_legacy_ch0_ce_count.attr.attr,
|
||||
&dev_attr_legacy_ch1_ce_count.attr.attr,
|
||||
&dev_attr_legacy_ch2_ce_count.attr.attr,
|
||||
&dev_attr_legacy_ch3_ce_count.attr.attr,
|
||||
&dev_attr_legacy_ch4_ce_count.attr.attr,
|
||||
&dev_attr_legacy_ch5_ce_count.attr.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static umode_t csrow_dev_is_visible(struct kobject *kobj,
|
||||
struct attribute *attr, int idx)
|
||||
{
|
||||
struct device *dev = kobj_to_dev(kobj);
|
||||
struct csrow_info *csrow = container_of(dev, struct csrow_info, dev);
|
||||
|
||||
if (idx >= csrow->nr_channels)
|
||||
return 0;
|
||||
/* Only expose populated DIMMs */
|
||||
if (!csrow->channels[idx]->dimm->nr_pages)
|
||||
return 0;
|
||||
return attr->mode;
|
||||
}
|
||||
|
||||
|
||||
static const struct attribute_group csrow_dev_dimm_group = {
|
||||
.attrs = dynamic_csrow_dimm_attr,
|
||||
.is_visible = csrow_dev_is_visible,
|
||||
};
|
||||
|
||||
static const struct attribute_group csrow_dev_ce_count_group = {
|
||||
.attrs = dynamic_csrow_ce_count_attr,
|
||||
.is_visible = csrow_dev_is_visible,
|
||||
};
|
||||
|
||||
static const struct attribute_group *csrow_dev_groups[] = {
|
||||
&csrow_dev_dimm_group,
|
||||
&csrow_dev_ce_count_group,
|
||||
NULL
|
||||
};
|
||||
|
||||
static inline int nr_pages_per_csrow(struct csrow_info *csrow)
|
||||
|
@ -370,13 +403,12 @@ static inline int nr_pages_per_csrow(struct csrow_info *csrow)
|
|||
static int edac_create_csrow_object(struct mem_ctl_info *mci,
|
||||
struct csrow_info *csrow, int index)
|
||||
{
|
||||
int err, chan;
|
||||
|
||||
if (csrow->nr_channels > EDAC_NR_CHANNELS)
|
||||
return -ENODEV;
|
||||
|
||||
csrow->dev.type = &csrow_attr_type;
|
||||
csrow->dev.bus = mci->bus;
|
||||
csrow->dev.groups = csrow_dev_groups;
|
||||
device_initialize(&csrow->dev);
|
||||
csrow->dev.parent = &mci->dev;
|
||||
csrow->mci = mci;
|
||||
|
@ -386,45 +418,13 @@ static int edac_create_csrow_object(struct mem_ctl_info *mci,
|
|||
edac_dbg(0, "creating (virtual) csrow node %s\n",
|
||||
dev_name(&csrow->dev));
|
||||
|
||||
err = device_add(&csrow->dev);
|
||||
if (err < 0)
|
||||
return err;
|
||||
|
||||
for (chan = 0; chan < csrow->nr_channels; chan++) {
|
||||
/* Only expose populated DIMMs */
|
||||
if (!csrow->channels[chan]->dimm->nr_pages)
|
||||
continue;
|
||||
err = device_create_file(&csrow->dev,
|
||||
dynamic_csrow_dimm_attr[chan]);
|
||||
if (err < 0)
|
||||
goto error;
|
||||
err = device_create_file(&csrow->dev,
|
||||
dynamic_csrow_ce_count_attr[chan]);
|
||||
if (err < 0) {
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_dimm_attr[chan]);
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
for (--chan; chan >= 0; chan--) {
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_dimm_attr[chan]);
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_ce_count_attr[chan]);
|
||||
}
|
||||
put_device(&csrow->dev);
|
||||
|
||||
return err;
|
||||
return device_add(&csrow->dev);
|
||||
}
|
||||
|
||||
/* Create a CSROW object under specifed edac_mc_device */
|
||||
static int edac_create_csrow_objects(struct mem_ctl_info *mci)
|
||||
{
|
||||
int err, i, chan;
|
||||
int err, i;
|
||||
struct csrow_info *csrow;
|
||||
|
||||
for (i = 0; i < mci->nr_csrows; i++) {
|
||||
|
@ -446,14 +446,6 @@ error:
|
|||
csrow = mci->csrows[i];
|
||||
if (!nr_pages_per_csrow(csrow))
|
||||
continue;
|
||||
for (chan = csrow->nr_channels - 1; chan >= 0; chan--) {
|
||||
if (!csrow->channels[chan]->dimm->nr_pages)
|
||||
continue;
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_dimm_attr[chan]);
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_ce_count_attr[chan]);
|
||||
}
|
||||
put_device(&mci->csrows[i]->dev);
|
||||
}
|
||||
|
||||
|
@ -462,23 +454,13 @@ error:
|
|||
|
||||
static void edac_delete_csrow_objects(struct mem_ctl_info *mci)
|
||||
{
|
||||
int i, chan;
|
||||
int i;
|
||||
struct csrow_info *csrow;
|
||||
|
||||
for (i = mci->nr_csrows - 1; i >= 0; i--) {
|
||||
csrow = mci->csrows[i];
|
||||
if (!nr_pages_per_csrow(csrow))
|
||||
continue;
|
||||
for (chan = csrow->nr_channels - 1; chan >= 0; chan--) {
|
||||
if (!csrow->channels[chan]->dimm->nr_pages)
|
||||
continue;
|
||||
edac_dbg(1, "Removing csrow %d channel %d sysfs nodes\n",
|
||||
i, chan);
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_dimm_attr[chan]);
|
||||
device_remove_file(&csrow->dev,
|
||||
dynamic_csrow_ce_count_attr[chan]);
|
||||
}
|
||||
device_unregister(&mci->csrows[i]->dev);
|
||||
}
|
||||
}
|
||||
|
@ -863,7 +845,8 @@ static DEVICE_ATTR(ce_count, S_IRUGO, mci_ce_count_show, NULL);
|
|||
static DEVICE_ATTR(max_location, S_IRUGO, mci_max_location_show, NULL);
|
||||
|
||||
/* memory scrubber attribute file */
|
||||
static DEVICE_ATTR(sdram_scrub_rate, 0, NULL, NULL);
|
||||
DEVICE_ATTR(sdram_scrub_rate, 0, mci_sdram_scrub_rate_show,
|
||||
mci_sdram_scrub_rate_store); /* umode set later in is_visible */
|
||||
|
||||
static struct attribute *mci_attrs[] = {
|
||||
&dev_attr_reset_counters.attr,
|
||||
|
@ -875,11 +858,29 @@ static struct attribute *mci_attrs[] = {
|
|||
&dev_attr_ue_count.attr,
|
||||
&dev_attr_ce_count.attr,
|
||||
&dev_attr_max_location.attr,
|
||||
&dev_attr_sdram_scrub_rate.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static umode_t mci_attr_is_visible(struct kobject *kobj,
|
||||
struct attribute *attr, int idx)
|
||||
{
|
||||
struct device *dev = kobj_to_dev(kobj);
|
||||
struct mem_ctl_info *mci = to_mci(dev);
|
||||
umode_t mode = 0;
|
||||
|
||||
if (attr != &dev_attr_sdram_scrub_rate.attr)
|
||||
return attr->mode;
|
||||
if (mci->get_sdram_scrub_rate)
|
||||
mode |= S_IRUGO;
|
||||
if (mci->set_sdram_scrub_rate)
|
||||
mode |= S_IWUSR;
|
||||
return mode;
|
||||
}
|
||||
|
||||
static struct attribute_group mci_attr_grp = {
|
||||
.attrs = mci_attrs,
|
||||
.is_visible = mci_attr_is_visible,
|
||||
};
|
||||
|
||||
static const struct attribute_group *mci_attr_groups[] = {
|
||||
|
@ -913,7 +914,7 @@ int __init edac_debugfs_init(void)
|
|||
return 0;
|
||||
}
|
||||
|
||||
void __exit edac_debugfs_exit(void)
|
||||
void edac_debugfs_exit(void)
|
||||
{
|
||||
debugfs_remove(edac_debugfs);
|
||||
}
|
||||
|
@ -973,7 +974,8 @@ nomem:
|
|||
* 0 Success
|
||||
* !0 Failure
|
||||
*/
|
||||
int edac_create_sysfs_mci_device(struct mem_ctl_info *mci)
|
||||
int edac_create_sysfs_mci_device(struct mem_ctl_info *mci,
|
||||
const struct attribute_group **groups)
|
||||
{
|
||||
int i, err;
|
||||
|
||||
|
@ -997,6 +999,7 @@ int edac_create_sysfs_mci_device(struct mem_ctl_info *mci)
|
|||
|
||||
mci->dev.parent = mci_pdev;
|
||||
mci->dev.bus = mci->bus;
|
||||
mci->dev.groups = groups;
|
||||
dev_set_name(&mci->dev, "mc%d", mci->mc_idx);
|
||||
dev_set_drvdata(&mci->dev, mci);
|
||||
pm_runtime_forbid(&mci->dev);
|
||||
|
@ -1008,23 +1011,6 @@ int edac_create_sysfs_mci_device(struct mem_ctl_info *mci)
|
|||
goto fail_unregister_bus;
|
||||
}
|
||||
|
||||
if (mci->set_sdram_scrub_rate || mci->get_sdram_scrub_rate) {
|
||||
if (mci->get_sdram_scrub_rate) {
|
||||
dev_attr_sdram_scrub_rate.attr.mode |= S_IRUGO;
|
||||
dev_attr_sdram_scrub_rate.show = &mci_sdram_scrub_rate_show;
|
||||
}
|
||||
|
||||
if (mci->set_sdram_scrub_rate) {
|
||||
dev_attr_sdram_scrub_rate.attr.mode |= S_IWUSR;
|
||||
dev_attr_sdram_scrub_rate.store = &mci_sdram_scrub_rate_store;
|
||||
}
|
||||
|
||||
err = device_create_file(&mci->dev, &dev_attr_sdram_scrub_rate);
|
||||
if (err) {
|
||||
edac_dbg(1, "failure: create sdram_scrub_rate\n");
|
||||
goto fail_unregister_dev;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* Create the dimm/rank devices
|
||||
*/
|
||||
|
@ -1071,7 +1057,6 @@ fail_unregister_dimm:
|
|||
|
||||
device_unregister(&dimm->dev);
|
||||
}
|
||||
fail_unregister_dev:
|
||||
device_unregister(&mci->dev);
|
||||
fail_unregister_bus:
|
||||
bus_unregister(mci->bus);
|
||||
|
@ -1170,7 +1155,7 @@ int __init edac_mc_sysfs_init(void)
|
|||
return err;
|
||||
}
|
||||
|
||||
void __exit edac_mc_sysfs_exit(void)
|
||||
void edac_mc_sysfs_exit(void)
|
||||
{
|
||||
device_unregister(mci_pdev);
|
||||
edac_put_sysfs_subsys();
|
||||
|
|
|
@ -112,20 +112,23 @@ static int __init edac_init(void)
|
|||
|
||||
err = edac_mc_sysfs_init();
|
||||
if (err)
|
||||
goto error;
|
||||
goto err_sysfs;
|
||||
|
||||
edac_debugfs_init();
|
||||
|
||||
/* Setup/Initialize the workq for this core */
|
||||
err = edac_workqueue_setup();
|
||||
if (err) {
|
||||
edac_printk(KERN_ERR, EDAC_MC, "init WorkQueue failure\n");
|
||||
goto error;
|
||||
edac_printk(KERN_ERR, EDAC_MC, "Failure initializing workqueue\n");
|
||||
goto err_wq;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
err_wq:
|
||||
edac_debugfs_exit();
|
||||
edac_mc_sysfs_exit();
|
||||
|
||||
err_sysfs:
|
||||
return err;
|
||||
}
|
||||
|
||||
|
|
|
@ -22,7 +22,8 @@
|
|||
/* on edac_mc_sysfs.c */
|
||||
int edac_mc_sysfs_init(void);
|
||||
void edac_mc_sysfs_exit(void);
|
||||
extern int edac_create_sysfs_mci_device(struct mem_ctl_info *mci);
|
||||
extern int edac_create_sysfs_mci_device(struct mem_ctl_info *mci,
|
||||
const struct attribute_group **groups);
|
||||
extern void edac_remove_sysfs_mci_device(struct mem_ctl_info *mci);
|
||||
void edac_unregister_sysfs(struct mem_ctl_info *mci);
|
||||
extern int edac_get_log_ue(void);
|
||||
|
|
|
@ -124,6 +124,13 @@ static ssize_t highbank_mc_inject_ctrl(struct device *dev,
|
|||
|
||||
static DEVICE_ATTR(inject_ctrl, S_IWUSR, NULL, highbank_mc_inject_ctrl);
|
||||
|
||||
static struct attribute *highbank_dev_attrs[] = {
|
||||
&dev_attr_inject_ctrl.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
ATTRIBUTE_GROUPS(highbank_dev);
|
||||
|
||||
struct hb_mc_settings {
|
||||
int err_offset;
|
||||
int int_offset;
|
||||
|
@ -139,7 +146,7 @@ static struct hb_mc_settings mw_settings = {
|
|||
.int_offset = MW_DDR_ECC_INT_BASE,
|
||||
};
|
||||
|
||||
static struct of_device_id hb_ddr_ctrl_of_match[] = {
|
||||
static const struct of_device_id hb_ddr_ctrl_of_match[] = {
|
||||
{ .compatible = "calxeda,hb-ddr-ctrl", .data = &hb_settings },
|
||||
{ .compatible = "calxeda,ecx-2000-ddr-ctrl", .data = &mw_settings },
|
||||
{},
|
||||
|
@ -231,7 +238,7 @@ static int highbank_mc_probe(struct platform_device *pdev)
|
|||
dimm->mtype = MEM_DDR3;
|
||||
dimm->edac_mode = EDAC_SECDED;
|
||||
|
||||
res = edac_mc_add_mc(mci);
|
||||
res = edac_mc_add_mc_with_groups(mci, highbank_dev_groups);
|
||||
if (res < 0)
|
||||
goto err;
|
||||
|
||||
|
@ -243,8 +250,6 @@ static int highbank_mc_probe(struct platform_device *pdev)
|
|||
goto err2;
|
||||
}
|
||||
|
||||
device_create_file(&mci->dev, &dev_attr_inject_ctrl);
|
||||
|
||||
devres_close_group(&pdev->dev, NULL);
|
||||
return 0;
|
||||
err2:
|
||||
|
@ -259,7 +264,6 @@ static int highbank_mc_remove(struct platform_device *pdev)
|
|||
{
|
||||
struct mem_ctl_info *mci = platform_get_drvdata(pdev);
|
||||
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_ctrl);
|
||||
edac_mc_del_mc(&pdev->dev);
|
||||
edac_mc_free(mci);
|
||||
return 0;
|
||||
|
|
|
@ -1157,27 +1157,24 @@ static DEVICE_ATTR(inject_eccmask, S_IRUGO | S_IWUSR,
|
|||
static DEVICE_ATTR(inject_enable, S_IRUGO | S_IWUSR,
|
||||
i7core_inject_enable_show, i7core_inject_enable_store);
|
||||
|
||||
static struct attribute *i7core_dev_attrs[] = {
|
||||
&dev_attr_inject_section.attr,
|
||||
&dev_attr_inject_type.attr,
|
||||
&dev_attr_inject_eccmask.attr,
|
||||
&dev_attr_inject_enable.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
ATTRIBUTE_GROUPS(i7core_dev);
|
||||
|
||||
static int i7core_create_sysfs_devices(struct mem_ctl_info *mci)
|
||||
{
|
||||
struct i7core_pvt *pvt = mci->pvt_info;
|
||||
int rc;
|
||||
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_section);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_type);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_eccmask);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_enable);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
pvt->addrmatch_dev = kzalloc(sizeof(*pvt->addrmatch_dev), GFP_KERNEL);
|
||||
if (!pvt->addrmatch_dev)
|
||||
return rc;
|
||||
return -ENOMEM;
|
||||
|
||||
pvt->addrmatch_dev->type = &addrmatch_type;
|
||||
pvt->addrmatch_dev->bus = mci->dev.bus;
|
||||
|
@ -1198,7 +1195,7 @@ static int i7core_create_sysfs_devices(struct mem_ctl_info *mci)
|
|||
if (!pvt->chancounts_dev) {
|
||||
put_device(pvt->addrmatch_dev);
|
||||
device_del(pvt->addrmatch_dev);
|
||||
return rc;
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
pvt->chancounts_dev->type = &all_channel_counts_type;
|
||||
|
@ -1223,11 +1220,6 @@ static void i7core_delete_sysfs_devices(struct mem_ctl_info *mci)
|
|||
|
||||
edac_dbg(1, "\n");
|
||||
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_section);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_type);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_eccmask);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_enable);
|
||||
|
||||
if (!pvt->is_registered) {
|
||||
put_device(pvt->chancounts_dev);
|
||||
device_del(pvt->chancounts_dev);
|
||||
|
@ -2259,7 +2251,7 @@ static int i7core_register_mci(struct i7core_dev *i7core_dev)
|
|||
enable_sdram_scrub_setting(mci);
|
||||
|
||||
/* add this new MC control structure to EDAC's list of MCs */
|
||||
if (unlikely(edac_mc_add_mc(mci))) {
|
||||
if (unlikely(edac_mc_add_mc_with_groups(mci, i7core_dev_groups))) {
|
||||
edac_dbg(0, "MC: failed edac_mc_add_mc()\n");
|
||||
/* FIXME: perhaps some code should go here that disables error
|
||||
* reporting if we just enabled it
|
||||
|
|
|
@ -350,8 +350,6 @@ fail:
|
|||
return -ENODEV;
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(i82443bxgx_edacmc_probe1);
|
||||
|
||||
/* returns count (>= 0), or negative on error */
|
||||
static int i82443bxgx_edacmc_init_one(struct pci_dev *pdev,
|
||||
const struct pci_device_id *ent)
|
||||
|
@ -384,8 +382,6 @@ static void i82443bxgx_edacmc_remove_one(struct pci_dev *pdev)
|
|||
edac_mc_free(mci);
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(i82443bxgx_edacmc_remove_one);
|
||||
|
||||
static const struct pci_device_id i82443bxgx_pci_tbl[] = {
|
||||
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82443BX_0)},
|
||||
{PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82443BX_2)},
|
||||
|
@ -445,9 +441,7 @@ fail1:
|
|||
pci_unregister_driver(&i82443bxgx_edacmc_driver);
|
||||
|
||||
fail0:
|
||||
if (mci_pdev != NULL)
|
||||
pci_dev_put(mci_pdev);
|
||||
|
||||
pci_dev_put(mci_pdev);
|
||||
return pci_rc;
|
||||
}
|
||||
|
||||
|
|
|
@ -343,20 +343,15 @@ fail1:
|
|||
pci_unregister_driver(&i82860_driver);
|
||||
|
||||
fail0:
|
||||
if (mci_pdev != NULL)
|
||||
pci_dev_put(mci_pdev);
|
||||
|
||||
pci_dev_put(mci_pdev);
|
||||
return pci_rc;
|
||||
}
|
||||
|
||||
static void __exit i82860_exit(void)
|
||||
{
|
||||
edac_dbg(3, "\n");
|
||||
|
||||
pci_unregister_driver(&i82860_driver);
|
||||
|
||||
if (mci_pdev != NULL)
|
||||
pci_dev_put(mci_pdev);
|
||||
pci_dev_put(mci_pdev);
|
||||
}
|
||||
|
||||
module_init(i82860_init);
|
||||
|
|
|
@ -576,9 +576,7 @@ fail1:
|
|||
pci_unregister_driver(&i82875p_driver);
|
||||
|
||||
fail0:
|
||||
if (mci_pdev != NULL)
|
||||
pci_dev_put(mci_pdev);
|
||||
|
||||
pci_dev_put(mci_pdev);
|
||||
return pci_rc;
|
||||
}
|
||||
|
||||
|
|
|
@ -685,9 +685,7 @@ fail1:
|
|||
pci_unregister_driver(&i82975x_driver);
|
||||
|
||||
fail0:
|
||||
if (mci_pdev != NULL)
|
||||
pci_dev_put(mci_pdev);
|
||||
|
||||
pci_dev_put(mci_pdev);
|
||||
return pci_rc;
|
||||
}
|
||||
|
||||
|
|
|
@ -134,29 +134,14 @@ DEVICE_ATTR(inject_data_lo, S_IRUGO | S_IWUSR,
|
|||
DEVICE_ATTR(inject_ctrl, S_IRUGO | S_IWUSR,
|
||||
mpc85xx_mc_inject_ctrl_show, mpc85xx_mc_inject_ctrl_store);
|
||||
|
||||
static int mpc85xx_create_sysfs_attributes(struct mem_ctl_info *mci)
|
||||
{
|
||||
int rc;
|
||||
static struct attribute *mpc85xx_dev_attrs[] = {
|
||||
&dev_attr_inject_data_hi.attr,
|
||||
&dev_attr_inject_data_lo.attr,
|
||||
&dev_attr_inject_ctrl.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_data_hi);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_data_lo);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject_ctrl);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void mpc85xx_remove_sysfs_attributes(struct mem_ctl_info *mci)
|
||||
{
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_data_hi);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_data_lo);
|
||||
device_remove_file(&mci->dev, &dev_attr_inject_ctrl);
|
||||
}
|
||||
ATTRIBUTE_GROUPS(mpc85xx_dev);
|
||||
|
||||
/**************************** PCI Err device ***************************/
|
||||
#ifdef CONFIG_PCI
|
||||
|
@ -685,7 +670,7 @@ static int mpc85xx_l2_err_remove(struct platform_device *op)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static struct of_device_id mpc85xx_l2_err_of_match[] = {
|
||||
static const struct of_device_id mpc85xx_l2_err_of_match[] = {
|
||||
/* deprecate the fsl,85.. forms in the future, 2.6.30? */
|
||||
{ .compatible = "fsl,8540-l2-cache-controller", },
|
||||
{ .compatible = "fsl,8541-l2-cache-controller", },
|
||||
|
@ -1106,13 +1091,7 @@ static int mpc85xx_mc_err_probe(struct platform_device *op)
|
|||
/* clear all error bits */
|
||||
out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT, ~0);
|
||||
|
||||
if (edac_mc_add_mc(mci)) {
|
||||
edac_dbg(3, "failed edac_mc_add_mc()\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (mpc85xx_create_sysfs_attributes(mci)) {
|
||||
edac_mc_del_mc(mci->pdev);
|
||||
if (edac_mc_add_mc_with_groups(mci, mpc85xx_dev_groups)) {
|
||||
edac_dbg(3, "failed edac_mc_add_mc()\n");
|
||||
goto err;
|
||||
}
|
||||
|
@ -1176,13 +1155,12 @@ static int mpc85xx_mc_err_remove(struct platform_device *op)
|
|||
orig_ddr_err_disable);
|
||||
out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_SBE, orig_ddr_err_sbe);
|
||||
|
||||
mpc85xx_remove_sysfs_attributes(mci);
|
||||
edac_mc_del_mc(&op->dev);
|
||||
edac_mc_free(mci);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct of_device_id mpc85xx_mc_err_of_match[] = {
|
||||
static const struct of_device_id mpc85xx_mc_err_of_match[] = {
|
||||
/* deprecate the fsl,85.. forms in the future, 2.6.30? */
|
||||
{ .compatible = "fsl,8540-memory-controller", },
|
||||
{ .compatible = "fsl,8541-memory-controller", },
|
||||
|
|
|
@ -209,35 +209,18 @@ static DEVICE_ATTR(row, S_IRUGO | S_IWUSR,
|
|||
static DEVICE_ATTR(col, S_IRUGO | S_IWUSR,
|
||||
octeon_mc_inject_col_show, octeon_mc_inject_col_store);
|
||||
|
||||
static struct attribute *octeon_dev_attrs[] = {
|
||||
&dev_attr_inject.attr,
|
||||
&dev_attr_error_type.attr,
|
||||
&dev_attr_dimm.attr,
|
||||
&dev_attr_rank.attr,
|
||||
&dev_attr_bank.attr,
|
||||
&dev_attr_row.attr,
|
||||
&dev_attr_col.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static int octeon_set_mc_sysfs_attributes(struct mem_ctl_info *mci)
|
||||
{
|
||||
int rc;
|
||||
|
||||
rc = device_create_file(&mci->dev, &dev_attr_inject);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_error_type);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_dimm);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_rank);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_bank);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_row);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
rc = device_create_file(&mci->dev, &dev_attr_col);
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
return 0;
|
||||
}
|
||||
ATTRIBUTE_GROUPS(octeon_dev);
|
||||
|
||||
static int octeon_lmc_edac_probe(struct platform_device *pdev)
|
||||
{
|
||||
|
@ -271,18 +254,12 @@ static int octeon_lmc_edac_probe(struct platform_device *pdev)
|
|||
mci->ctl_name = "octeon-lmc-err";
|
||||
mci->edac_check = octeon_lmc_edac_poll;
|
||||
|
||||
if (edac_mc_add_mc(mci)) {
|
||||
if (edac_mc_add_mc_with_groups(mci, octeon_dev_groups)) {
|
||||
dev_err(&pdev->dev, "edac_mc_add_mc() failed\n");
|
||||
edac_mc_free(mci);
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
if (octeon_set_mc_sysfs_attributes(mci)) {
|
||||
dev_err(&pdev->dev, "octeon_set_mc_sysfs_attributes() failed\n");
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
|
||||
cfg0.u64 = cvmx_read_csr(CVMX_LMCX_MEM_CFG0(mc));
|
||||
cfg0.s.intr_ded_ena = 0; /* We poll */
|
||||
cfg0.s.intr_sec_ena = 0;
|
||||
|
@ -309,18 +286,12 @@ static int octeon_lmc_edac_probe(struct platform_device *pdev)
|
|||
mci->ctl_name = "co_lmc_err";
|
||||
mci->edac_check = octeon_lmc_edac_poll_o2;
|
||||
|
||||
if (edac_mc_add_mc(mci)) {
|
||||
if (edac_mc_add_mc_with_groups(mci, octeon_dev_groups)) {
|
||||
dev_err(&pdev->dev, "edac_mc_add_mc() failed\n");
|
||||
edac_mc_free(mci);
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
if (octeon_set_mc_sysfs_attributes(mci)) {
|
||||
dev_err(&pdev->dev, "octeon_set_mc_sysfs_attributes() failed\n");
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
|
||||
en.u64 = cvmx_read_csr(CVMX_LMCX_MEM_CFG0(mc));
|
||||
en.s.intr_ded_ena = 0; /* We poll */
|
||||
en.s.intr_sec_ena = 0;
|
||||
|
|
|
@ -193,7 +193,7 @@ static int ppc4xx_edac_remove(struct platform_device *device);
|
|||
* Device tree node type and compatible tuples this driver can match
|
||||
* on.
|
||||
*/
|
||||
static struct of_device_id ppc4xx_edac_match[] = {
|
||||
static const struct of_device_id ppc4xx_edac_match[] = {
|
||||
{
|
||||
.compatible = "ibm,sdram-4xx-ddr2"
|
||||
},
|
||||
|
|
|
@ -512,7 +512,7 @@ static int synps_edac_mc_remove(struct platform_device *pdev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static struct of_device_id synps_edac_match[] = {
|
||||
static const struct of_device_id synps_edac_match[] = {
|
||||
{ .compatible = "xlnx,zynq-ddrc-a05", },
|
||||
{ /* end of table */ }
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue