diff options
| -rw-r--r-- | arch/x86/kernel/cpu/mce/core.c | 22 | ||||
| -rw-r--r-- | arch/x86/kernel/cpu/mce/inject.c | 14 |
2 files changed, 14 insertions, 22 deletions
diff --git a/arch/x86/kernel/cpu/mce/core.c b/arch/x86/kernel/cpu/mce/core.c index e558ca77cfe8..c3498732ba28 100644 --- a/arch/x86/kernel/cpu/mce/core.c +++ b/arch/x86/kernel/cpu/mce/core.c | |||
| @@ -1481,13 +1481,12 @@ EXPORT_SYMBOL_GPL(mce_notify_irq); | |||
| 1481 | static int __mcheck_cpu_mce_banks_init(void) | 1481 | static int __mcheck_cpu_mce_banks_init(void) |
| 1482 | { | 1482 | { |
| 1483 | int i; | 1483 | int i; |
| 1484 | u8 num_banks = mca_cfg.banks; | ||
| 1485 | 1484 | ||
| 1486 | mce_banks = kcalloc(num_banks, sizeof(struct mce_bank), GFP_KERNEL); | 1485 | mce_banks = kcalloc(MAX_NR_BANKS, sizeof(struct mce_bank), GFP_KERNEL); |
| 1487 | if (!mce_banks) | 1486 | if (!mce_banks) |
| 1488 | return -ENOMEM; | 1487 | return -ENOMEM; |
| 1489 | 1488 | ||
| 1490 | for (i = 0; i < num_banks; i++) { | 1489 | for (i = 0; i < MAX_NR_BANKS; i++) { |
| 1491 | struct mce_bank *b = &mce_banks[i]; | 1490 | struct mce_bank *b = &mce_banks[i]; |
| 1492 | 1491 | ||
| 1493 | b->ctl = -1ULL; | 1492 | b->ctl = -1ULL; |
| @@ -1501,28 +1500,19 @@ static int __mcheck_cpu_mce_banks_init(void) | |||
| 1501 | */ | 1500 | */ |
| 1502 | static int __mcheck_cpu_cap_init(void) | 1501 | static int __mcheck_cpu_cap_init(void) |
| 1503 | { | 1502 | { |
| 1504 | unsigned b; | ||
| 1505 | u64 cap; | 1503 | u64 cap; |
| 1504 | u8 b; | ||
| 1506 | 1505 | ||
| 1507 | rdmsrl(MSR_IA32_MCG_CAP, cap); | 1506 | rdmsrl(MSR_IA32_MCG_CAP, cap); |
| 1508 | 1507 | ||
| 1509 | b = cap & MCG_BANKCNT_MASK; | 1508 | b = cap & MCG_BANKCNT_MASK; |
| 1510 | if (!mca_cfg.banks) | 1509 | if (WARN_ON_ONCE(b > MAX_NR_BANKS)) |
| 1511 | pr_info("CPU supports %d MCE banks\n", b); | ||
| 1512 | |||
| 1513 | if (b > MAX_NR_BANKS) { | ||
| 1514 | pr_warn("Using only %u machine check banks out of %u\n", | ||
| 1515 | MAX_NR_BANKS, b); | ||
| 1516 | b = MAX_NR_BANKS; | 1510 | b = MAX_NR_BANKS; |
| 1517 | } | ||
| 1518 | 1511 | ||
| 1519 | /* Don't support asymmetric configurations today */ | 1512 | mca_cfg.banks = max(mca_cfg.banks, b); |
| 1520 | WARN_ON(mca_cfg.banks != 0 && b != mca_cfg.banks); | ||
| 1521 | mca_cfg.banks = b; | ||
| 1522 | 1513 | ||
| 1523 | if (!mce_banks) { | 1514 | if (!mce_banks) { |
| 1524 | int err = __mcheck_cpu_mce_banks_init(); | 1515 | int err = __mcheck_cpu_mce_banks_init(); |
| 1525 | |||
| 1526 | if (err) | 1516 | if (err) |
| 1527 | return err; | 1517 | return err; |
| 1528 | } | 1518 | } |
| @@ -2481,6 +2471,8 @@ EXPORT_SYMBOL_GPL(mcsafe_key); | |||
| 2481 | 2471 | ||
| 2482 | static int __init mcheck_late_init(void) | 2472 | static int __init mcheck_late_init(void) |
| 2483 | { | 2473 | { |
| 2474 | pr_info("Using %d MCE banks\n", mca_cfg.banks); | ||
| 2475 | |||
| 2484 | if (mca_cfg.recovery) | 2476 | if (mca_cfg.recovery) |
| 2485 | static_branch_inc(&mcsafe_key); | 2477 | static_branch_inc(&mcsafe_key); |
| 2486 | 2478 | ||
diff --git a/arch/x86/kernel/cpu/mce/inject.c b/arch/x86/kernel/cpu/mce/inject.c index 8492ef7d9015..3f82afd0f46f 100644 --- a/arch/x86/kernel/cpu/mce/inject.c +++ b/arch/x86/kernel/cpu/mce/inject.c | |||
| @@ -46,8 +46,6 @@ | |||
| 46 | static struct mce i_mce; | 46 | static struct mce i_mce; |
| 47 | static struct dentry *dfs_inj; | 47 | static struct dentry *dfs_inj; |
| 48 | 48 | ||
| 49 | static u8 n_banks; | ||
| 50 | |||
| 51 | #define MAX_FLAG_OPT_SIZE 4 | 49 | #define MAX_FLAG_OPT_SIZE 4 |
| 52 | #define NBCFG 0x44 | 50 | #define NBCFG 0x44 |
| 53 | 51 | ||
| @@ -570,9 +568,15 @@ err: | |||
| 570 | static int inj_bank_set(void *data, u64 val) | 568 | static int inj_bank_set(void *data, u64 val) |
| 571 | { | 569 | { |
| 572 | struct mce *m = (struct mce *)data; | 570 | struct mce *m = (struct mce *)data; |
| 571 | u8 n_banks; | ||
| 572 | u64 cap; | ||
| 573 | |||
| 574 | /* Get bank count on target CPU so we can handle non-uniform values. */ | ||
| 575 | rdmsrl_on_cpu(m->extcpu, MSR_IA32_MCG_CAP, &cap); | ||
| 576 | n_banks = cap & MCG_BANKCNT_MASK; | ||
| 573 | 577 | ||
| 574 | if (val >= n_banks) { | 578 | if (val >= n_banks) { |
| 575 | pr_err("Non-existent MCE bank: %llu\n", val); | 579 | pr_err("MCA bank %llu non-existent on CPU%d\n", val, m->extcpu); |
| 576 | return -EINVAL; | 580 | return -EINVAL; |
| 577 | } | 581 | } |
| 578 | 582 | ||
| @@ -665,10 +669,6 @@ static struct dfs_node { | |||
| 665 | static int __init debugfs_init(void) | 669 | static int __init debugfs_init(void) |
| 666 | { | 670 | { |
| 667 | unsigned int i; | 671 | unsigned int i; |
| 668 | u64 cap; | ||
| 669 | |||
| 670 | rdmsrl(MSR_IA32_MCG_CAP, cap); | ||
| 671 | n_banks = cap & MCG_BANKCNT_MASK; | ||
| 672 | 672 | ||
| 673 | dfs_inj = debugfs_create_dir("mce-inject", NULL); | 673 | dfs_inj = debugfs_create_dir("mce-inject", NULL); |
| 674 | if (!dfs_inj) | 674 | if (!dfs_inj) |
