Skip to content

Commit 1a8a6af

Browse files
qzhuo2aegl
authored andcommitted
EDAC/{skx_common,i10nm}: Structure the per-channel RRL registers
As the number of RRL (retry_rd_err_log) registers per memory channel increases, the positions of the RRL control bits and the widths of the RRL registers vary across different CPU generations. Adding RRL support for a new CPU requires handling these differences throughout the RRL-related code. Structure the offsets, widths, control bit positions, set numbers, modes, etc., of the per-channel RRL registers and make them configurable to facilitate easier RRL support for new CPUs. No functional changes are intended. Signed-off-by: Qiuxu Zhuo <qiuxu.zhuo@intel.com> Signed-off-by: Tony Luck <tony.luck@intel.com> Tested-by: Feng Xu <feng.f.xu@intel.com> Link: https://lore.kernel.org/r/20250417150724.1170168-5-qiuxu.zhuo@intel.com
1 parent 4878e1e commit 1a8a6af

File tree

2 files changed

+69
-44
lines changed

2 files changed

+69
-44
lines changed

drivers/edac/i10nm_base.c

Lines changed: 56 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -86,15 +86,38 @@ static int retry_rd_err_log;
8686
static int decoding_via_mca;
8787
static bool mem_cfg_2lm;
8888

89-
static u32 offsets_scrub_icx[] = {0x22c60, 0x22c54, 0x22c5c, 0x22c58, 0x22c28, 0x20ed8};
90-
static u32 offsets_scrub_spr[] = {0x22c60, 0x22c54, 0x22f08, 0x22c58, 0x22c28, 0x20ed8};
91-
static u32 offsets_scrub_spr_hbm0[] = {0x2860, 0x2854, 0x2b08, 0x2858, 0x2828, 0x0ed8};
92-
static u32 offsets_scrub_spr_hbm1[] = {0x2c60, 0x2c54, 0x2f08, 0x2c58, 0x2c28, 0x0fa8};
93-
static u32 offsets_demand_icx[] = {0x22e54, 0x22e60, 0x22e64, 0x22e58, 0x22e5c, 0x20ee0};
94-
static u32 offsets_demand_spr[] = {0x22e54, 0x22e60, 0x22f10, 0x22e58, 0x22e5c, 0x20ee0};
95-
static u32 offsets_demand2_spr[] = {0x22c70, 0x22d80, 0x22f18, 0x22d58, 0x22c64, 0x20f10};
96-
static u32 offsets_demand_spr_hbm0[] = {0x2a54, 0x2a60, 0x2b10, 0x2a58, 0x2a5c, 0x0ee0};
97-
static u32 offsets_demand_spr_hbm1[] = {0x2e54, 0x2e60, 0x2f10, 0x2e58, 0x2e5c, 0x0fb0};
89+
static struct reg_rrl icx_reg_rrl_ddr = {
90+
.set_num = 2,
91+
.offsets = {
92+
{0x22c60, 0x22c54, 0x22c5c, 0x22c58, 0x22c28, 0x20ed8},
93+
{0x22e54, 0x22e60, 0x22e64, 0x22e58, 0x22e5c, 0x20ee0},
94+
},
95+
};
96+
97+
static struct reg_rrl spr_reg_rrl_ddr = {
98+
.set_num = 3,
99+
.offsets = {
100+
{0x22c60, 0x22c54, 0x22f08, 0x22c58, 0x22c28, 0x20ed8},
101+
{0x22e54, 0x22e60, 0x22f10, 0x22e58, 0x22e5c, 0x20ee0},
102+
{0x22c70, 0x22d80, 0x22f18, 0x22d58, 0x22c64, 0x20f10},
103+
},
104+
};
105+
106+
static struct reg_rrl spr_reg_rrl_hbm_pch0 = {
107+
.set_num = 2,
108+
.offsets = {
109+
{0x2860, 0x2854, 0x2b08, 0x2858, 0x2828, 0x0ed8},
110+
{0x2a54, 0x2a60, 0x2b10, 0x2a58, 0x2a5c, 0x0ee0},
111+
},
112+
};
113+
114+
static struct reg_rrl spr_reg_rrl_hbm_pch1 = {
115+
.set_num = 2,
116+
.offsets = {
117+
{0x2c60, 0x2c54, 0x2f08, 0x2c58, 0x2c28, 0x0fa8},
118+
{0x2e54, 0x2e60, 0x2f10, 0x2e58, 0x2e5c, 0x0fb0},
119+
},
120+
};
98121

99122
static void __enable_retry_rd_err_log(struct skx_imc *imc, int chan, bool enable, u32 *rrl_ctl,
100123
u32 *offsets_scrub, u32 *offsets_demand,
@@ -185,9 +208,11 @@ static void enable_retry_rd_err_log(bool enable)
185208
chan = d->imc[i].chan;
186209
for (j = 0; j < chan_num; j++)
187210
__enable_retry_rd_err_log(imc, j, enable, chan[j].rrl_ctl[0],
188-
res_cfg->offsets_scrub,
189-
res_cfg->offsets_demand,
190-
res_cfg->offsets_demand2);
211+
res_cfg->reg_rrl_ddr->offsets[0],
212+
res_cfg->reg_rrl_ddr->offsets[1],
213+
res_cfg->reg_rrl_ddr->set_num > 2 ?
214+
res_cfg->reg_rrl_ddr->offsets[2] : NULL);
215+
191216
}
192217

193218
imc_num += res_cfg->hbm_imc_num;
@@ -201,12 +226,12 @@ static void enable_retry_rd_err_log(bool enable)
201226
chan = d->imc[i].chan;
202227
for (j = 0; j < chan_num; j++) {
203228
__enable_retry_rd_err_log(imc, j, enable, chan[j].rrl_ctl[0],
204-
res_cfg->offsets_scrub_hbm0,
205-
res_cfg->offsets_demand_hbm0,
229+
res_cfg->reg_rrl_hbm[0]->offsets[0],
230+
res_cfg->reg_rrl_hbm[0]->offsets[1],
206231
NULL);
207232
__enable_retry_rd_err_log(imc, j, enable, chan[j].rrl_ctl[1],
208-
res_cfg->offsets_scrub_hbm1,
209-
res_cfg->offsets_demand_hbm1,
233+
res_cfg->reg_rrl_hbm[1]->offsets[0],
234+
res_cfg->reg_rrl_hbm[1]->offsets[1],
210235
NULL);
211236
}
212237
}
@@ -233,17 +258,18 @@ static void show_retry_rd_err_log(struct decoded_addr *res, char *msg,
233258
pch = res->cs & 1;
234259

235260
if (pch)
236-
offsets = scrub_err ? res_cfg->offsets_scrub_hbm1 :
237-
res_cfg->offsets_demand_hbm1;
261+
offsets = scrub_err ? res_cfg->reg_rrl_hbm[1]->offsets[0] :
262+
res_cfg->reg_rrl_hbm[1]->offsets[1];
238263
else
239-
offsets = scrub_err ? res_cfg->offsets_scrub_hbm0 :
240-
res_cfg->offsets_demand_hbm0;
264+
offsets = scrub_err ? res_cfg->reg_rrl_hbm[0]->offsets[0] :
265+
res_cfg->reg_rrl_hbm[0]->offsets[1];
241266
} else {
242267
if (scrub_err) {
243-
offsets = res_cfg->offsets_scrub;
268+
offsets = res_cfg->reg_rrl_ddr->offsets[0];
244269
} else {
245-
offsets = res_cfg->offsets_demand;
246-
xffsets = res_cfg->offsets_demand2;
270+
offsets = res_cfg->reg_rrl_ddr->offsets[1];
271+
if (res_cfg->reg_rrl_ddr->set_num > 2)
272+
xffsets = res_cfg->reg_rrl_ddr->offsets[2];
247273
}
248274
}
249275

@@ -883,8 +909,7 @@ static struct res_config i10nm_cfg0 = {
883909
.ddr_mdev_bdf = {0, 12, 0},
884910
.hbm_mdev_bdf = {0, 12, 1},
885911
.sad_all_offset = 0x108,
886-
.offsets_scrub = offsets_scrub_icx,
887-
.offsets_demand = offsets_demand_icx,
912+
.reg_rrl_ddr = &icx_reg_rrl_ddr,
888913
};
889914

890915
static struct res_config i10nm_cfg1 = {
@@ -902,8 +927,7 @@ static struct res_config i10nm_cfg1 = {
902927
.ddr_mdev_bdf = {0, 12, 0},
903928
.hbm_mdev_bdf = {0, 12, 1},
904929
.sad_all_offset = 0x108,
905-
.offsets_scrub = offsets_scrub_icx,
906-
.offsets_demand = offsets_demand_icx,
930+
.reg_rrl_ddr = &icx_reg_rrl_ddr,
907931
};
908932

909933
static struct res_config spr_cfg = {
@@ -926,13 +950,9 @@ static struct res_config spr_cfg = {
926950
.ddr_mdev_bdf = {0, 12, 0},
927951
.hbm_mdev_bdf = {0, 12, 1},
928952
.sad_all_offset = 0x300,
929-
.offsets_scrub = offsets_scrub_spr,
930-
.offsets_scrub_hbm0 = offsets_scrub_spr_hbm0,
931-
.offsets_scrub_hbm1 = offsets_scrub_spr_hbm1,
932-
.offsets_demand = offsets_demand_spr,
933-
.offsets_demand2 = offsets_demand2_spr,
934-
.offsets_demand_hbm0 = offsets_demand_spr_hbm0,
935-
.offsets_demand_hbm1 = offsets_demand_spr_hbm1,
953+
.reg_rrl_ddr = &spr_reg_rrl_ddr,
954+
.reg_rrl_hbm[0] = &spr_reg_rrl_hbm_pch0,
955+
.reg_rrl_hbm[1] = &spr_reg_rrl_hbm_pch1,
936956
};
937957

938958
static struct res_config gnr_cfg = {
@@ -1121,7 +1141,7 @@ static int __init i10nm_init(void)
11211141
mce_register_decode_chain(&i10nm_mce_dec);
11221142
skx_setup_debug("i10nm_test");
11231143

1124-
if (retry_rd_err_log && res_cfg->offsets_scrub && res_cfg->offsets_demand) {
1144+
if (retry_rd_err_log && res_cfg->reg_rrl_ddr) {
11251145
skx_set_decode(i10nm_mc_decode, show_retry_rd_err_log);
11261146
if (retry_rd_err_log == 2)
11271147
enable_retry_rd_err_log(true);
@@ -1141,7 +1161,7 @@ static void __exit i10nm_exit(void)
11411161
{
11421162
edac_dbg(2, "\n");
11431163

1144-
if (retry_rd_err_log && res_cfg->offsets_scrub && res_cfg->offsets_demand) {
1164+
if (retry_rd_err_log && res_cfg->reg_rrl_ddr) {
11451165
skx_set_decode(NULL, NULL);
11461166
if (retry_rd_err_log == 2)
11471167
enable_retry_rd_err_log(false);

drivers/edac/skx_common.h

Lines changed: 13 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,15 @@
8181

8282
/* Max RRL register sets per {,sub-,pseudo-}channel. */
8383
#define NUM_RRL_SET 3
84+
/* Max RRL registers per set. */
85+
#define NUM_RRL_REG 6
86+
87+
/* RRL registers per {,sub-,pseudo-}channel. */
88+
struct reg_rrl {
89+
/* RRL register parts. */
90+
int set_num;
91+
u32 offsets[NUM_RRL_SET][NUM_RRL_REG];
92+
};
8493

8594
/*
8695
* Each cpu socket contains some pci devices that provide global
@@ -237,14 +246,10 @@ struct res_config {
237246
/* HBM mdev device BDF */
238247
struct pci_bdf hbm_mdev_bdf;
239248
int sad_all_offset;
240-
/* Offsets of retry_rd_err_log registers */
241-
u32 *offsets_scrub;
242-
u32 *offsets_scrub_hbm0;
243-
u32 *offsets_scrub_hbm1;
244-
u32 *offsets_demand;
245-
u32 *offsets_demand2;
246-
u32 *offsets_demand_hbm0;
247-
u32 *offsets_demand_hbm1;
249+
/* RRL register sets per DDR channel */
250+
struct reg_rrl *reg_rrl_ddr;
251+
/* RRL register sets per HBM channel */
252+
struct reg_rrl *reg_rrl_hbm[2];
248253
};
249254

250255
typedef int (*get_dimm_config_f)(struct mem_ctl_info *mci,

0 commit comments

Comments
 (0)