diff options
author | Borislav Petkov <borislav.petkov@amd.com> | 2010-05-25 12:21:07 -0400 |
---|---|---|
committer | Borislav Petkov <borislav.petkov@amd.com> | 2010-08-03 10:14:06 -0400 |
commit | eba042a81edd6baaff44831b2d719b14a6d21e58 (patch) | |
tree | a1e768aadf18708114e2d6c4d4a54b3af49e42e9 /drivers/edac/edac_mc_sysfs.c | |
parent | bc57117856cf1e581135810b37d3b75f9d1749f5 (diff) |
edac, mc: Improve scrub rate handling
Fortify the interface to not accept negative values, remove
memctrl_int_store() as a result. Also, sanitize bandwidth setting by
making the argument a simple u32 instead of strange u32 pointer being
passed around for no obvious reason. Then, fix error handling and teach
it to return proper error values. Finally, make code more readable,
simplify debug messages.
Cc: Mauro Carvalho Chehab <mchehab@redhat.com>
Cc: Arthur Jones <ajones@riverbed.com>
Signed-off-by: Borislav Petkov <borislav.petkov@amd.com>
Acked-by: Doug Thompson <dougthompson@xmission.com>
Diffstat (limited to 'drivers/edac/edac_mc_sysfs.c')
-rw-r--r-- | drivers/edac/edac_mc_sysfs.c | 86 |
1 files changed, 37 insertions, 49 deletions
diff --git a/drivers/edac/edac_mc_sysfs.c b/drivers/edac/edac_mc_sysfs.c index c200c2fd43ea..8aad94d10c0c 100644 --- a/drivers/edac/edac_mc_sysfs.c +++ b/drivers/edac/edac_mc_sysfs.c | |||
@@ -124,19 +124,6 @@ static const char *edac_caps[] = { | |||
124 | [EDAC_S16ECD16ED] = "S16ECD16ED" | 124 | [EDAC_S16ECD16ED] = "S16ECD16ED" |
125 | }; | 125 | }; |
126 | 126 | ||
127 | |||
128 | |||
129 | static ssize_t memctrl_int_store(void *ptr, const char *buffer, size_t count) | ||
130 | { | ||
131 | int *value = (int *)ptr; | ||
132 | |||
133 | if (isdigit(*buffer)) | ||
134 | *value = simple_strtoul(buffer, NULL, 0); | ||
135 | |||
136 | return count; | ||
137 | } | ||
138 | |||
139 | |||
140 | /* EDAC sysfs CSROW data structures and methods | 127 | /* EDAC sysfs CSROW data structures and methods |
141 | */ | 128 | */ |
142 | 129 | ||
@@ -450,53 +437,54 @@ static ssize_t mci_reset_counters_store(struct mem_ctl_info *mci, | |||
450 | 437 | ||
451 | /* memory scrubbing */ | 438 | /* memory scrubbing */ |
452 | static ssize_t mci_sdram_scrub_rate_store(struct mem_ctl_info *mci, | 439 | static ssize_t mci_sdram_scrub_rate_store(struct mem_ctl_info *mci, |
453 | const char *data, size_t count) | 440 | const char *data, size_t count) |
454 | { | 441 | { |
455 | u32 bandwidth = -1; | 442 | unsigned long bandwidth = 0; |
443 | int err; | ||
456 | 444 | ||
457 | if (mci->set_sdram_scrub_rate) { | 445 | if (!mci->set_sdram_scrub_rate) { |
446 | edac_printk(KERN_WARNING, EDAC_MC, | ||
447 | "Memory scrub rate setting not implemented!\n"); | ||
448 | return -EINVAL; | ||
449 | } | ||
458 | 450 | ||
459 | memctrl_int_store(&bandwidth, data, count); | 451 | if (strict_strtoul(data, 10, &bandwidth) < 0) |
452 | return -EINVAL; | ||
460 | 453 | ||
461 | if (!(*mci->set_sdram_scrub_rate) (mci, &bandwidth)) { | 454 | err = mci->set_sdram_scrub_rate(mci, (u32)bandwidth); |
462 | edac_printk(KERN_DEBUG, EDAC_MC, | 455 | if (err) { |
463 | "Scrub rate set successfully, applied: %d\n", | 456 | edac_printk(KERN_DEBUG, EDAC_MC, |
464 | bandwidth); | 457 | "Failed setting scrub rate to %lu\n", bandwidth); |
465 | } else { | 458 | return -EINVAL; |
466 | /* FIXME: error codes maybe? */ | 459 | } |
467 | edac_printk(KERN_DEBUG, EDAC_MC, | 460 | else { |
468 | "Scrub rate set FAILED, could not apply: %d\n", | 461 | edac_printk(KERN_DEBUG, EDAC_MC, |
469 | bandwidth); | 462 | "Scrub rate set to: %lu\n", bandwidth); |
470 | } | 463 | return count; |
471 | } else { | ||
472 | /* FIXME: produce "not implemented" ERROR for user-side. */ | ||
473 | edac_printk(KERN_WARNING, EDAC_MC, | ||
474 | "Memory scrubbing 'set'control is not implemented!\n"); | ||
475 | } | 464 | } |
476 | return count; | ||
477 | } | 465 | } |
478 | 466 | ||
479 | static ssize_t mci_sdram_scrub_rate_show(struct mem_ctl_info *mci, char *data) | 467 | static ssize_t mci_sdram_scrub_rate_show(struct mem_ctl_info *mci, char *data) |
480 | { | 468 | { |
481 | u32 bandwidth = -1; | 469 | u32 bandwidth = 0; |
482 | 470 | int err; | |
483 | if (mci->get_sdram_scrub_rate) { | 471 | |
484 | if (!(*mci->get_sdram_scrub_rate) (mci, &bandwidth)) { | 472 | if (!mci->get_sdram_scrub_rate) { |
485 | edac_printk(KERN_DEBUG, EDAC_MC, | ||
486 | "Scrub rate successfully, fetched: %d\n", | ||
487 | bandwidth); | ||
488 | } else { | ||
489 | /* FIXME: error codes maybe? */ | ||
490 | edac_printk(KERN_DEBUG, EDAC_MC, | ||
491 | "Scrub rate fetch FAILED, got: %d\n", | ||
492 | bandwidth); | ||
493 | } | ||
494 | } else { | ||
495 | /* FIXME: produce "not implemented" ERROR for user-side. */ | ||
496 | edac_printk(KERN_WARNING, EDAC_MC, | 473 | edac_printk(KERN_WARNING, EDAC_MC, |
497 | "Memory scrubbing 'get' control is not implemented\n"); | 474 | "Memory scrub rate reading not implemented\n"); |
475 | return -EINVAL; | ||
476 | } | ||
477 | |||
478 | err = mci->get_sdram_scrub_rate(mci, &bandwidth); | ||
479 | if (err) { | ||
480 | edac_printk(KERN_DEBUG, EDAC_MC, "Error reading scrub rate\n"); | ||
481 | return err; | ||
482 | } | ||
483 | else { | ||
484 | edac_printk(KERN_DEBUG, EDAC_MC, | ||
485 | "Read scrub rate: %d\n", bandwidth); | ||
486 | return sprintf(data, "%d\n", bandwidth); | ||
498 | } | 487 | } |
499 | return sprintf(data, "%d\n", bandwidth); | ||
500 | } | 488 | } |
501 | 489 | ||
502 | /* default attribute files for the MCI object */ | 490 | /* default attribute files for the MCI object */ |