1 /* Intel 7 core Memory Controller kernel module (Nehalem)
3 * This file may be distributed under the terms of the
4 * GNU General Public License version 2 only.
6 * Copyright (c) 2009 by:
7 * Mauro Carvalho Chehab <mchehab@redhat.com>
9 * Red Hat Inc. http://www.redhat.com
11 * Forked and adapted from the i5400_edac driver
13 * Based on the following public Intel datasheets:
14 * Intel Core i7 Processor Extreme Edition and Intel Core i7 Processor
15 * Datasheet, Volume 2:
16 * http://download.intel.com/design/processor/datashts/320835.pdf
17 * Intel Xeon Processor 5500 Series Datasheet Volume 2
18 * http://www.intel.com/Assets/PDF/datasheet/321322.pdf
20 * http://www.arrownac.com/manufacturers/intel/s/nehalem/5500-datasheet-v2.pdf
23 #include <linux/module.h>
24 #include <linux/init.h>
25 #include <linux/pci.h>
26 #include <linux/pci_ids.h>
27 #include <linux/slab.h>
28 #include <linux/edac.h>
29 #include <linux/mmzone.h>
30 #include <linux/edac_mce.h>
31 #include <linux/spinlock.h>
33 #include "edac_core.h"
36 * Alter this version for the module when modifications are made
38 #define I7CORE_REVISION " Ver: 1.0.0 " __DATE__
39 #define EDAC_MOD_STR "i7core_edac"
44 #define i7core_printk(level, fmt, arg...) \
45 edac_printk(level, "i7core", fmt, ##arg)
47 #define i7core_mc_printk(mci, level, fmt, arg...) \
48 edac_mc_chipset_printk(mci, level, "i7core", fmt, ##arg)
51 * i7core Memory Controller Registers
54 /* OFFSETS for Device 0 Function 0 */
56 #define MC_CFG_CONTROL 0x90
58 /* OFFSETS for Device 3 Function 0 */
60 #define MC_CONTROL 0x48
61 #define MC_STATUS 0x4c
62 #define MC_MAX_DOD 0x64
65 * OFFSETS for Device 3 Function 4, as inicated on Xeon 5500 datasheet:
66 * http://www.arrownac.com/manufacturers/intel/s/nehalem/5500-datasheet-v2.pdf
69 #define MC_TEST_ERR_RCV1 0x60
70 #define DIMM2_COR_ERR(r) ((r) & 0x7fff)
72 #define MC_TEST_ERR_RCV0 0x64
73 #define DIMM1_COR_ERR(r) (((r) >> 16) & 0x7fff)
74 #define DIMM0_COR_ERR(r) ((r) & 0x7fff)
76 /* OFFSETS for Devices 4,5 and 6 Function 0 */
78 #define MC_CHANNEL_DIMM_INIT_PARAMS 0x58
79 #define THREE_DIMMS_PRESENT (1 << 24)
80 #define SINGLE_QUAD_RANK_PRESENT (1 << 23)
81 #define QUAD_RANK_PRESENT (1 << 22)
82 #define REGISTERED_DIMM (1 << 15)
84 #define MC_CHANNEL_MAPPER 0x60
85 #define RDLCH(r, ch) ((((r) >> (3 + (ch * 6))) & 0x07) - 1)
86 #define WRLCH(r, ch) ((((r) >> (ch * 6)) & 0x07) - 1)
88 #define MC_CHANNEL_RANK_PRESENT 0x7c
89 #define RANK_PRESENT_MASK 0xffff
91 #define MC_CHANNEL_ADDR_MATCH 0xf0
92 #define MC_CHANNEL_ERROR_MASK 0xf8
93 #define MC_CHANNEL_ERROR_INJECT 0xfc
94 #define INJECT_ADDR_PARITY 0x10
95 #define INJECT_ECC 0x08
96 #define MASK_CACHELINE 0x06
97 #define MASK_FULL_CACHELINE 0x06
98 #define MASK_MSB32_CACHELINE 0x04
99 #define MASK_LSB32_CACHELINE 0x02
100 #define NO_MASK_CACHELINE 0x00
101 #define REPEAT_EN 0x01
103 /* OFFSETS for Devices 4,5 and 6 Function 1 */
105 #define MC_DOD_CH_DIMM0 0x48
106 #define MC_DOD_CH_DIMM1 0x4c
107 #define MC_DOD_CH_DIMM2 0x50
108 #define RANKOFFSET_MASK ((1 << 12) | (1 << 11) | (1 << 10))
109 #define RANKOFFSET(x) ((x & RANKOFFSET_MASK) >> 10)
110 #define DIMM_PRESENT_MASK (1 << 9)
111 #define DIMM_PRESENT(x) (((x) & DIMM_PRESENT_MASK) >> 9)
112 #define MC_DOD_NUMBANK_MASK ((1 << 8) | (1 << 7))
113 #define MC_DOD_NUMBANK(x) (((x) & MC_DOD_NUMBANK_MASK) >> 7)
114 #define MC_DOD_NUMRANK_MASK ((1 << 6) | (1 << 5))
115 #define MC_DOD_NUMRANK(x) (((x) & MC_DOD_NUMRANK_MASK) >> 5)
116 #define MC_DOD_NUMROW_MASK ((1 << 4) | (1 << 3) | (1 << 2))
117 #define MC_DOD_NUMROW(x) (((x) & MC_DOD_NUMROW_MASK) >> 2)
118 #define MC_DOD_NUMCOL_MASK 3
119 #define MC_DOD_NUMCOL(x) ((x) & MC_DOD_NUMCOL_MASK)
121 #define MC_RANK_PRESENT 0x7c
123 #define MC_SAG_CH_0 0x80
124 #define MC_SAG_CH_1 0x84
125 #define MC_SAG_CH_2 0x88
126 #define MC_SAG_CH_3 0x8c
127 #define MC_SAG_CH_4 0x90
128 #define MC_SAG_CH_5 0x94
129 #define MC_SAG_CH_6 0x98
130 #define MC_SAG_CH_7 0x9c
132 #define MC_RIR_LIMIT_CH_0 0x40
133 #define MC_RIR_LIMIT_CH_1 0x44
134 #define MC_RIR_LIMIT_CH_2 0x48
135 #define MC_RIR_LIMIT_CH_3 0x4C
136 #define MC_RIR_LIMIT_CH_4 0x50
137 #define MC_RIR_LIMIT_CH_5 0x54
138 #define MC_RIR_LIMIT_CH_6 0x58
139 #define MC_RIR_LIMIT_CH_7 0x5C
140 #define MC_RIR_LIMIT_MASK ((1 << 10) - 1)
142 #define MC_RIR_WAY_CH 0x80
143 #define MC_RIR_WAY_OFFSET_MASK (((1 << 14) - 1) & ~0x7)
144 #define MC_RIR_WAY_RANK_MASK 0x7
151 #define MAX_DIMMS 3 /* Max DIMMS per channel */
152 #define NUM_SOCKETS 2 /* Max number of MC sockets */
153 #define MAX_MCR_FUNC 4
154 #define MAX_CHAN_FUNC 3
164 struct i7core_inject {
172 /* Error address mask */
173 int channel, dimm, rank, bank, page, col;
176 struct i7core_channel {
181 struct pci_id_descr {
185 struct pci_dev *pdev[NUM_SOCKETS];
189 struct pci_dev *pci_noncore[NUM_SOCKETS];
190 struct pci_dev *pci_mcr[NUM_SOCKETS][MAX_MCR_FUNC + 1];
191 struct pci_dev *pci_ch[NUM_SOCKETS][NUM_CHANS][MAX_CHAN_FUNC + 1];
193 struct i7core_info info;
194 struct i7core_inject inject;
195 struct i7core_channel channel[NUM_SOCKETS][NUM_CHANS];
197 int sockets; /* Number of sockets */
198 int channels; /* Number of active channels */
200 int ce_count_available[NUM_SOCKETS];
201 /* ECC corrected errors counts per dimm */
202 unsigned long ce_count[NUM_SOCKETS][MAX_DIMMS];
203 int last_ce_count[NUM_SOCKETS][MAX_DIMMS];
206 struct edac_mce edac_mce;
207 struct mce mce_entry[MCE_LOG_LEN];
212 /* Device name and register DID (Device ID) */
213 struct i7core_dev_info {
214 const char *ctl_name; /* name for this device */
215 u16 fsb_mapping_errors; /* DID for the branchmap,control */
218 #define PCI_DESCR(device, function, device_id) \
220 .func = (function), \
221 .dev_id = (device_id)
223 struct pci_id_descr pci_devs[] = {
224 /* Memory controller */
225 { PCI_DESCR(3, 0, PCI_DEVICE_ID_INTEL_I7_MCR) },
226 { PCI_DESCR(3, 1, PCI_DEVICE_ID_INTEL_I7_MC_TAD) },
227 { PCI_DESCR(3, 2, PCI_DEVICE_ID_INTEL_I7_MC_RAS) }, /* if RDIMM */
228 { PCI_DESCR(3, 4, PCI_DEVICE_ID_INTEL_I7_MC_TEST) },
231 { PCI_DESCR(4, 0, PCI_DEVICE_ID_INTEL_I7_MC_CH0_CTRL) },
232 { PCI_DESCR(4, 1, PCI_DEVICE_ID_INTEL_I7_MC_CH0_ADDR) },
233 { PCI_DESCR(4, 2, PCI_DEVICE_ID_INTEL_I7_MC_CH0_RANK) },
234 { PCI_DESCR(4, 3, PCI_DEVICE_ID_INTEL_I7_MC_CH0_TC) },
237 { PCI_DESCR(5, 0, PCI_DEVICE_ID_INTEL_I7_MC_CH1_CTRL) },
238 { PCI_DESCR(5, 1, PCI_DEVICE_ID_INTEL_I7_MC_CH1_ADDR) },
239 { PCI_DESCR(5, 2, PCI_DEVICE_ID_INTEL_I7_MC_CH1_RANK) },
240 { PCI_DESCR(5, 3, PCI_DEVICE_ID_INTEL_I7_MC_CH1_TC) },
243 { PCI_DESCR(6, 0, PCI_DEVICE_ID_INTEL_I7_MC_CH2_CTRL) },
244 { PCI_DESCR(6, 1, PCI_DEVICE_ID_INTEL_I7_MC_CH2_ADDR) },
245 { PCI_DESCR(6, 2, PCI_DEVICE_ID_INTEL_I7_MC_CH2_RANK) },
246 { PCI_DESCR(6, 3, PCI_DEVICE_ID_INTEL_I7_MC_CH2_TC) },
248 /* Generic Non-core registers */
250 * This is the PCI device on i7core and on Xeon 35xx (8086:2c41)
251 * On Xeon 55xx, however, it has a different id (8086:2c40). So,
252 * the probing code needs to test for the other address in case of
253 * failure of this one
255 { PCI_DESCR(0, 0, PCI_DEVICE_ID_INTEL_I7_NOCORE) },
258 #define N_DEVS ARRAY_SIZE(pci_devs)
261 * pci_device_id table for which devices we are looking for
262 * This should match the first device at pci_devs table
264 static const struct pci_device_id i7core_pci_tbl[] __devinitdata = {
265 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_X58_HUB_MGMT)},
266 {0,} /* 0 terminated list. */
270 /* Table of devices attributes supported by this driver */
271 static const struct i7core_dev_info i7core_devs[] = {
273 .ctl_name = "i7 Core",
274 .fsb_mapping_errors = PCI_DEVICE_ID_INTEL_I7_MCR,
278 static struct edac_pci_ctl_info *i7core_pci;
280 /****************************************************************************
281 Anciliary status routines
282 ****************************************************************************/
284 /* MC_CONTROL bits */
285 #define CH_ACTIVE(pvt, ch) ((pvt)->info.mc_control & (1 << (8 + ch)))
286 #define ECCx8(pvt) ((pvt)->info.mc_control & (1 << 1))
289 #define ECC_ENABLED(pvt) ((pvt)->info.mc_status & (1 << 3))
290 #define CH_DISABLED(pvt, ch) ((pvt)->info.mc_status & (1 << ch))
292 /* MC_MAX_DOD read functions */
293 static inline int numdimms(u32 dimms)
295 return (dimms & 0x3) + 1;
298 static inline int numrank(u32 rank)
300 static int ranks[4] = { 1, 2, 4, -EINVAL };
302 return ranks[rank & 0x3];
305 static inline int numbank(u32 bank)
307 static int banks[4] = { 4, 8, 16, -EINVAL };
309 return banks[bank & 0x3];
312 static inline int numrow(u32 row)
314 static int rows[8] = {
315 1 << 12, 1 << 13, 1 << 14, 1 << 15,
316 1 << 16, -EINVAL, -EINVAL, -EINVAL,
319 return rows[row & 0x7];
322 static inline int numcol(u32 col)
324 static int cols[8] = {
325 1 << 10, 1 << 11, 1 << 12, -EINVAL,
327 return cols[col & 0x3];
330 /****************************************************************************
331 Memory check routines
332 ****************************************************************************/
333 static struct pci_dev *get_pdev_slot_func(u8 socket, unsigned slot,
338 for (i = 0; i < N_DEVS; i++) {
339 if (!pci_devs[i].pdev[socket])
342 if (PCI_SLOT(pci_devs[i].pdev[socket]->devfn) == slot &&
343 PCI_FUNC(pci_devs[i].pdev[socket]->devfn) == func) {
344 return pci_devs[i].pdev[socket];
352 * i7core_get_active_channels() - gets the number of channels and csrows
353 * @socket: Quick Path Interconnect socket
354 * @channels: Number of channels that will be returned
355 * @csrows: Number of csrows found
357 * Since EDAC core needs to know in advance the number of available channels
358 * and csrows, in order to allocate memory for csrows/channels, it is needed
359 * to run two similar steps. At the first step, implemented on this function,
360 * it checks the number of csrows/channels present at one socket.
361 * this is used in order to properly allocate the size of mci components.
363 * It should be noticed that none of the current available datasheets explain
364 * or even mention how csrows are seen by the memory controller. So, we need
365 * to add a fake description for csrows.
366 * So, this driver is attributing one DIMM memory for one csrow.
368 static int i7core_get_active_channels(u8 socket, unsigned *channels,
371 struct pci_dev *pdev = NULL;
378 pdev = get_pdev_slot_func(socket, 3, 0);
380 i7core_printk(KERN_ERR, "Couldn't find socket %d fn 3.0!!!\n",
385 /* Device 3 function 0 reads */
386 pci_read_config_dword(pdev, MC_STATUS, &status);
387 pci_read_config_dword(pdev, MC_CONTROL, &control);
389 for (i = 0; i < NUM_CHANS; i++) {
391 /* Check if the channel is active */
392 if (!(control & (1 << (8 + i))))
395 /* Check if the channel is disabled */
396 if (status & (1 << i))
399 pdev = get_pdev_slot_func(socket, i + 4, 1);
401 i7core_printk(KERN_ERR, "Couldn't find socket %d "
406 /* Devices 4-6 function 1 */
407 pci_read_config_dword(pdev,
408 MC_DOD_CH_DIMM0, &dimm_dod[0]);
409 pci_read_config_dword(pdev,
410 MC_DOD_CH_DIMM1, &dimm_dod[1]);
411 pci_read_config_dword(pdev,
412 MC_DOD_CH_DIMM2, &dimm_dod[2]);
416 for (j = 0; j < 3; j++) {
417 if (!DIMM_PRESENT(dimm_dod[j]))
423 debugf0("Number of active channels on socket %d: %d\n",
429 static int get_dimm_config(struct mem_ctl_info *mci, int *csrow, u8 socket)
431 struct i7core_pvt *pvt = mci->pvt_info;
432 struct csrow_info *csr;
433 struct pci_dev *pdev;
435 unsigned long last_page = 0;
439 /* Get data from the MC register, function 0 */
440 pdev = pvt->pci_mcr[socket][0];
444 /* Device 3 function 0 reads */
445 pci_read_config_dword(pdev, MC_CONTROL, &pvt->info.mc_control);
446 pci_read_config_dword(pdev, MC_STATUS, &pvt->info.mc_status);
447 pci_read_config_dword(pdev, MC_MAX_DOD, &pvt->info.max_dod);
448 pci_read_config_dword(pdev, MC_CHANNEL_MAPPER, &pvt->info.ch_map);
450 debugf0("QPI %d control=0x%08x status=0x%08x dod=0x%08x map=0x%08x\n",
451 socket, pvt->info.mc_control, pvt->info.mc_status,
452 pvt->info.max_dod, pvt->info.ch_map);
454 if (ECC_ENABLED(pvt)) {
455 debugf0("ECC enabled with x%d SDCC\n", ECCx8(pvt) ? 8 : 4);
457 mode = EDAC_S8ECD8ED;
459 mode = EDAC_S4ECD4ED;
461 debugf0("ECC disabled\n");
465 /* FIXME: need to handle the error codes */
466 debugf0("DOD Max limits: DIMMS: %d, %d-ranked, %d-banked "
468 numdimms(pvt->info.max_dod),
469 numrank(pvt->info.max_dod >> 2),
470 numbank(pvt->info.max_dod >> 4),
471 numrow(pvt->info.max_dod >> 6),
472 numcol(pvt->info.max_dod >> 9));
474 for (i = 0; i < NUM_CHANS; i++) {
475 u32 data, dimm_dod[3], value[8];
477 if (!CH_ACTIVE(pvt, i)) {
478 debugf0("Channel %i is not active\n", i);
481 if (CH_DISABLED(pvt, i)) {
482 debugf0("Channel %i is disabled\n", i);
486 /* Devices 4-6 function 0 */
487 pci_read_config_dword(pvt->pci_ch[socket][i][0],
488 MC_CHANNEL_DIMM_INIT_PARAMS, &data);
490 pvt->channel[socket][i].ranks = (data & QUAD_RANK_PRESENT) ?
493 if (data & REGISTERED_DIMM)
498 if (data & THREE_DIMMS_PRESENT)
499 pvt->channel[i].dimms = 3;
500 else if (data & SINGLE_QUAD_RANK_PRESENT)
501 pvt->channel[i].dimms = 1;
503 pvt->channel[i].dimms = 2;
506 /* Devices 4-6 function 1 */
507 pci_read_config_dword(pvt->pci_ch[socket][i][1],
508 MC_DOD_CH_DIMM0, &dimm_dod[0]);
509 pci_read_config_dword(pvt->pci_ch[socket][i][1],
510 MC_DOD_CH_DIMM1, &dimm_dod[1]);
511 pci_read_config_dword(pvt->pci_ch[socket][i][1],
512 MC_DOD_CH_DIMM2, &dimm_dod[2]);
514 debugf0("Ch%d phy rd%d, wr%d (0x%08x): "
515 "%d ranks, %cDIMMs\n",
517 RDLCH(pvt->info.ch_map, i), WRLCH(pvt->info.ch_map, i),
519 pvt->channel[socket][i].ranks,
520 (data & REGISTERED_DIMM) ? 'R' : 'U');
522 for (j = 0; j < 3; j++) {
523 u32 banks, ranks, rows, cols;
526 if (!DIMM_PRESENT(dimm_dod[j]))
529 banks = numbank(MC_DOD_NUMBANK(dimm_dod[j]));
530 ranks = numrank(MC_DOD_NUMRANK(dimm_dod[j]));
531 rows = numrow(MC_DOD_NUMROW(dimm_dod[j]));
532 cols = numcol(MC_DOD_NUMCOL(dimm_dod[j]));
534 /* DDR3 has 8 I/O banks */
535 size = (rows * cols * banks * ranks) >> (20 - 3);
537 pvt->channel[socket][i].dimms++;
539 debugf0("\tdimm %d %d Mb offset: %x, "
540 "bank: %d, rank: %d, row: %#x, col: %#x\n",
542 RANKOFFSET(dimm_dod[j]),
543 banks, ranks, rows, cols);
546 npages = size >> (PAGE_SHIFT - 20);
548 npages = size << (20 - PAGE_SHIFT);
551 csr = &mci->csrows[*csrow];
552 csr->first_page = last_page + 1;
554 csr->last_page = last_page;
555 csr->nr_pages = npages;
559 csr->csrow_idx = *csrow;
560 csr->nr_channels = 1;
562 csr->channels[0].chan_idx = i;
563 csr->channels[0].ce_count = 0;
573 csr->dtype = DEV_X16;
576 csr->dtype = DEV_UNKNOWN;
579 csr->edac_mode = mode;
585 pci_read_config_dword(pdev, MC_SAG_CH_0, &value[0]);
586 pci_read_config_dword(pdev, MC_SAG_CH_1, &value[1]);
587 pci_read_config_dword(pdev, MC_SAG_CH_2, &value[2]);
588 pci_read_config_dword(pdev, MC_SAG_CH_3, &value[3]);
589 pci_read_config_dword(pdev, MC_SAG_CH_4, &value[4]);
590 pci_read_config_dword(pdev, MC_SAG_CH_5, &value[5]);
591 pci_read_config_dword(pdev, MC_SAG_CH_6, &value[6]);
592 pci_read_config_dword(pdev, MC_SAG_CH_7, &value[7]);
593 debugf1("\t[%i] DIVBY3\tREMOVED\tOFFSET\n", i);
594 for (j = 0; j < 8; j++)
595 debugf1("\t\t%#x\t%#x\t%#x\n",
596 (value[j] >> 27) & 0x1,
597 (value[j] >> 24) & 0x7,
598 (value[j] && ((1 << 24) - 1)));
604 /****************************************************************************
605 Error insertion routines
606 ****************************************************************************/
608 /* The i7core has independent error injection features per channel.
609 However, to have a simpler code, we don't allow enabling error injection
610 on more than one channel.
611 Also, since a change at an inject parameter will be applied only at enable,
612 we're disabling error injection on all write calls to the sysfs nodes that
613 controls the error code injection.
615 static int disable_inject(struct mem_ctl_info *mci)
617 struct i7core_pvt *pvt = mci->pvt_info;
619 pvt->inject.enable = 0;
621 if (!pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0])
624 pci_write_config_dword(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
625 MC_CHANNEL_ERROR_INJECT, 0);
631 * i7core inject inject.socket
633 * accept and store error injection inject.socket value
635 static ssize_t i7core_inject_socket_store(struct mem_ctl_info *mci,
636 const char *data, size_t count)
638 struct i7core_pvt *pvt = mci->pvt_info;
642 rc = strict_strtoul(data, 10, &value);
643 if ((rc < 0) || (value >= pvt->sockets))
646 pvt->inject.socket = (u32) value;
650 static ssize_t i7core_inject_socket_show(struct mem_ctl_info *mci,
653 struct i7core_pvt *pvt = mci->pvt_info;
654 return sprintf(data, "%d\n", pvt->inject.socket);
658 * i7core inject inject.section
660 * accept and store error injection inject.section value
661 * bit 0 - refers to the lower 32-byte half cacheline
662 * bit 1 - refers to the upper 32-byte half cacheline
664 static ssize_t i7core_inject_section_store(struct mem_ctl_info *mci,
665 const char *data, size_t count)
667 struct i7core_pvt *pvt = mci->pvt_info;
671 if (pvt->inject.enable)
674 rc = strict_strtoul(data, 10, &value);
675 if ((rc < 0) || (value > 3))
678 pvt->inject.section = (u32) value;
682 static ssize_t i7core_inject_section_show(struct mem_ctl_info *mci,
685 struct i7core_pvt *pvt = mci->pvt_info;
686 return sprintf(data, "0x%08x\n", pvt->inject.section);
692 * accept and store error injection inject.section value
693 * bit 0 - repeat enable - Enable error repetition
694 * bit 1 - inject ECC error
695 * bit 2 - inject parity error
697 static ssize_t i7core_inject_type_store(struct mem_ctl_info *mci,
698 const char *data, size_t count)
700 struct i7core_pvt *pvt = mci->pvt_info;
704 if (pvt->inject.enable)
707 rc = strict_strtoul(data, 10, &value);
708 if ((rc < 0) || (value > 7))
711 pvt->inject.type = (u32) value;
715 static ssize_t i7core_inject_type_show(struct mem_ctl_info *mci,
718 struct i7core_pvt *pvt = mci->pvt_info;
719 return sprintf(data, "0x%08x\n", pvt->inject.type);
723 * i7core_inject_inject.eccmask_store
725 * The type of error (UE/CE) will depend on the inject.eccmask value:
726 * Any bits set to a 1 will flip the corresponding ECC bit
727 * Correctable errors can be injected by flipping 1 bit or the bits within
728 * a symbol pair (2 consecutive aligned 8-bit pairs - i.e. 7:0 and 15:8 or
729 * 23:16 and 31:24). Flipping bits in two symbol pairs will cause an
730 * uncorrectable error to be injected.
732 static ssize_t i7core_inject_eccmask_store(struct mem_ctl_info *mci,
733 const char *data, size_t count)
735 struct i7core_pvt *pvt = mci->pvt_info;
739 if (pvt->inject.enable)
742 rc = strict_strtoul(data, 10, &value);
746 pvt->inject.eccmask = (u32) value;
750 static ssize_t i7core_inject_eccmask_show(struct mem_ctl_info *mci,
753 struct i7core_pvt *pvt = mci->pvt_info;
754 return sprintf(data, "0x%08x\n", pvt->inject.eccmask);
760 * The type of error (UE/CE) will depend on the inject.eccmask value:
761 * Any bits set to a 1 will flip the corresponding ECC bit
762 * Correctable errors can be injected by flipping 1 bit or the bits within
763 * a symbol pair (2 consecutive aligned 8-bit pairs - i.e. 7:0 and 15:8 or
764 * 23:16 and 31:24). Flipping bits in two symbol pairs will cause an
765 * uncorrectable error to be injected.
767 static ssize_t i7core_inject_addrmatch_store(struct mem_ctl_info *mci,
768 const char *data, size_t count)
770 struct i7core_pvt *pvt = mci->pvt_info;
775 if (pvt->inject.enable)
779 cmd = strsep((char **) &data, ":");
782 val = strsep((char **) &data, " \n\t");
786 if (!strcasecmp(val, "any"))
789 rc = strict_strtol(val, 10, &value);
790 if ((rc < 0) || (value < 0))
794 if (!strcasecmp(cmd, "channel")) {
796 pvt->inject.channel = value;
799 } else if (!strcasecmp(cmd, "dimm")) {
801 pvt->inject.dimm = value;
804 } else if (!strcasecmp(cmd, "rank")) {
806 pvt->inject.rank = value;
809 } else if (!strcasecmp(cmd, "bank")) {
811 pvt->inject.bank = value;
814 } else if (!strcasecmp(cmd, "page")) {
816 pvt->inject.page = value;
819 } else if (!strcasecmp(cmd, "col") ||
820 !strcasecmp(cmd, "column")) {
822 pvt->inject.col = value;
831 static ssize_t i7core_inject_addrmatch_show(struct mem_ctl_info *mci,
834 struct i7core_pvt *pvt = mci->pvt_info;
835 char channel[4], dimm[4], bank[4], rank[4], page[7], col[7];
837 if (pvt->inject.channel < 0)
838 sprintf(channel, "any");
840 sprintf(channel, "%d", pvt->inject.channel);
841 if (pvt->inject.dimm < 0)
842 sprintf(dimm, "any");
844 sprintf(dimm, "%d", pvt->inject.dimm);
845 if (pvt->inject.bank < 0)
846 sprintf(bank, "any");
848 sprintf(bank, "%d", pvt->inject.bank);
849 if (pvt->inject.rank < 0)
850 sprintf(rank, "any");
852 sprintf(rank, "%d", pvt->inject.rank);
853 if (pvt->inject.page < 0)
854 sprintf(page, "any");
856 sprintf(page, "0x%04x", pvt->inject.page);
857 if (pvt->inject.col < 0)
860 sprintf(col, "0x%04x", pvt->inject.col);
862 return sprintf(data, "channel: %s\ndimm: %s\nbank: %s\n"
863 "rank: %s\npage: %s\ncolumn: %s\n",
864 channel, dimm, bank, rank, page, col);
867 static int write_and_test(struct pci_dev *dev, int where, u32 val)
872 debugf0("setting pci %02x:%02x.%x reg=%02x value=%08x\n",
873 dev->bus->number, PCI_SLOT(dev->devfn), PCI_FUNC(dev->devfn),
876 for (count = 0; count < 10; count++) {
879 pci_write_config_dword(dev, where, val);
880 pci_read_config_dword(dev, where, &read);
886 i7core_printk(KERN_ERR, "Error during set pci %02x:%02x.%x reg=%02x "
887 "write=%08x. Read=%08x\n",
888 dev->bus->number, PCI_SLOT(dev->devfn), PCI_FUNC(dev->devfn),
895 * This routine prepares the Memory Controller for error injection.
896 * The error will be injected when some process tries to write to the
897 * memory that matches the given criteria.
898 * The criteria can be set in terms of a mask where dimm, rank, bank, page
899 * and col can be specified.
900 * A -1 value for any of the mask items will make the MCU to ignore
901 * that matching criteria for error injection.
903 * It should be noticed that the error will only happen after a write operation
904 * on a memory that matches the condition. if REPEAT_EN is not enabled at
905 * inject mask, then it will produce just one error. Otherwise, it will repeat
906 * until the injectmask would be cleaned.
908 * FIXME: This routine assumes that MAXNUMDIMMS value of MC_MAX_DOD
909 * is reliable enough to check if the MC is using the
910 * three channels. However, this is not clear at the datasheet.
912 static ssize_t i7core_inject_enable_store(struct mem_ctl_info *mci,
913 const char *data, size_t count)
915 struct i7core_pvt *pvt = mci->pvt_info;
921 if (!pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0])
924 rc = strict_strtoul(data, 10, &enable);
929 pvt->inject.enable = 1;
935 /* Sets pvt->inject.dimm mask */
936 if (pvt->inject.dimm < 0)
939 if (pvt->channel[pvt->inject.socket][pvt->inject.channel].dimms > 2)
940 mask |= (pvt->inject.dimm & 0x3L) << 35;
942 mask |= (pvt->inject.dimm & 0x1L) << 36;
945 /* Sets pvt->inject.rank mask */
946 if (pvt->inject.rank < 0)
949 if (pvt->channel[pvt->inject.socket][pvt->inject.channel].dimms > 2)
950 mask |= (pvt->inject.rank & 0x1L) << 34;
952 mask |= (pvt->inject.rank & 0x3L) << 34;
955 /* Sets pvt->inject.bank mask */
956 if (pvt->inject.bank < 0)
959 mask |= (pvt->inject.bank & 0x15L) << 30;
961 /* Sets pvt->inject.page mask */
962 if (pvt->inject.page < 0)
965 mask |= (pvt->inject.page & 0xffffL) << 14;
967 /* Sets pvt->inject.column mask */
968 if (pvt->inject.col < 0)
971 mask |= (pvt->inject.col & 0x3fffL);
975 * bits 1-2: MASK_HALF_CACHELINE
977 * bit 4: INJECT_ADDR_PARITY
980 injectmask = (pvt->inject.type & 1) |
981 (pvt->inject.section & 0x3) << 1 |
982 (pvt->inject.type & 0x6) << (3 - 1);
984 /* Unlock writes to registers - this register is write only */
985 pci_write_config_dword(pvt->pci_noncore[pvt->inject.socket],
986 MC_CFG_CONTROL, 0x2);
988 write_and_test(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
989 MC_CHANNEL_ADDR_MATCH, mask);
990 write_and_test(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
991 MC_CHANNEL_ADDR_MATCH + 4, mask >> 32L);
993 write_and_test(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
994 MC_CHANNEL_ERROR_MASK, pvt->inject.eccmask);
996 write_and_test(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
997 MC_CHANNEL_ERROR_INJECT, injectmask);
1000 * This is something undocumented, based on my tests
1001 * Without writing 8 to this register, errors aren't injected. Not sure
1004 pci_write_config_dword(pvt->pci_noncore[pvt->inject.socket],
1007 debugf0("Error inject addr match 0x%016llx, ecc 0x%08x,"
1009 mask, pvt->inject.eccmask, injectmask);
1015 static ssize_t i7core_inject_enable_show(struct mem_ctl_info *mci,
1018 struct i7core_pvt *pvt = mci->pvt_info;
1021 pci_read_config_dword(pvt->pci_ch[pvt->inject.socket][pvt->inject.channel][0],
1022 MC_CHANNEL_ERROR_INJECT, &injectmask);
1024 debugf0("Inject error read: 0x%018x\n", injectmask);
1026 if (injectmask & 0x0c)
1027 pvt->inject.enable = 1;
1029 return sprintf(data, "%d\n", pvt->inject.enable);
1032 static ssize_t i7core_ce_regs_show(struct mem_ctl_info *mci, char *data)
1034 unsigned i, count, total = 0;
1035 struct i7core_pvt *pvt = mci->pvt_info;
1037 for (i = 0; i < pvt->sockets; i++) {
1038 if (!pvt->ce_count_available[i])
1039 count = sprintf(data, "socket 0 data unavailable\n");
1041 count = sprintf(data, "socket %d, dimm0: %lu\n"
1042 "dimm1: %lu\ndimm2: %lu\n",
1044 pvt->ce_count[i][0],
1045 pvt->ce_count[i][1],
1046 pvt->ce_count[i][2]);
1057 static struct mcidev_sysfs_attribute i7core_inj_attrs[] = {
1060 .name = "inject_socket",
1061 .mode = (S_IRUGO | S_IWUSR)
1063 .show = i7core_inject_socket_show,
1064 .store = i7core_inject_socket_store,
1067 .name = "inject_section",
1068 .mode = (S_IRUGO | S_IWUSR)
1070 .show = i7core_inject_section_show,
1071 .store = i7core_inject_section_store,
1074 .name = "inject_type",
1075 .mode = (S_IRUGO | S_IWUSR)
1077 .show = i7core_inject_type_show,
1078 .store = i7core_inject_type_store,
1081 .name = "inject_eccmask",
1082 .mode = (S_IRUGO | S_IWUSR)
1084 .show = i7core_inject_eccmask_show,
1085 .store = i7core_inject_eccmask_store,
1088 .name = "inject_addrmatch",
1089 .mode = (S_IRUGO | S_IWUSR)
1091 .show = i7core_inject_addrmatch_show,
1092 .store = i7core_inject_addrmatch_store,
1095 .name = "inject_enable",
1096 .mode = (S_IRUGO | S_IWUSR)
1098 .show = i7core_inject_enable_show,
1099 .store = i7core_inject_enable_store,
1102 .name = "corrected_error_counts",
1103 .mode = (S_IRUGO | S_IWUSR)
1105 .show = i7core_ce_regs_show,
1110 /****************************************************************************
1111 Device initialization routines: put/get, init/exit
1112 ****************************************************************************/
1115 * i7core_put_devices 'put' all the devices that we have
1116 * reserved via 'get'
1118 static void i7core_put_devices(void)
1122 for (i = 0; i < NUM_SOCKETS; i++)
1123 for (j = 0; j < N_DEVS; j++)
1124 pci_dev_put(pci_devs[j].pdev[i]);
1128 * i7core_get_devices Find and perform 'get' operation on the MCH's
1129 * device/functions we want to reference for this driver
1131 * Need to 'get' device 16 func 1 and func 2
1133 int i7core_get_onedevice(struct pci_dev **prev, int devno)
1135 struct pci_dev *pdev = NULL;
1139 pdev = pci_get_device(PCI_VENDOR_ID_INTEL,
1140 pci_devs[devno].dev_id, *prev);
1143 * On Xeon 55xx, the Intel Quckpath Arch Generic Non-core pci buses
1144 * aren't announced by acpi. So, we need to use a legacy scan probing
1147 if (unlikely(!pdev && !devno && !prev)) {
1148 pcibios_scan_specific_bus(254);
1149 pcibios_scan_specific_bus(255);
1151 pdev = pci_get_device(PCI_VENDOR_ID_INTEL,
1152 pci_devs[devno].dev_id, *prev);
1156 * On Xeon 55xx, the Intel Quckpath Arch Generic Non-core regs
1157 * is at addr 8086:2c40, instead of 8086:2c41. So, we need
1158 * to probe for the alternate address in case of failure
1160 if (pci_devs[devno].dev_id == PCI_DEVICE_ID_INTEL_I7_NOCORE && !pdev)
1161 pdev = pci_get_device(PCI_VENDOR_ID_INTEL,
1162 PCI_DEVICE_ID_INTEL_I7_NOCORE_ALT, *prev);
1171 * Dev 3 function 2 only exists on chips with RDIMMs
1172 * so, it is ok to not found it
1174 if ((pci_devs[devno].dev == 3) && (pci_devs[devno].func == 2)) {
1179 i7core_printk(KERN_ERR,
1180 "Device not found: dev %02x.%d PCI ID %04x:%04x\n",
1181 pci_devs[devno].dev, pci_devs[devno].func,
1182 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id);
1184 /* End of list, leave */
1187 bus = pdev->bus->number;
1194 if (socket >= NUM_SOCKETS) {
1195 i7core_printk(KERN_ERR,
1196 "Unexpected socket for "
1197 "dev %02x:%02x.%d PCI ID %04x:%04x\n",
1198 bus, pci_devs[devno].dev, pci_devs[devno].func,
1199 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id);
1204 if (pci_devs[devno].pdev[socket]) {
1205 i7core_printk(KERN_ERR,
1206 "Duplicated device for "
1207 "dev %02x:%02x.%d PCI ID %04x:%04x\n",
1208 bus, pci_devs[devno].dev, pci_devs[devno].func,
1209 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id);
1214 pci_devs[devno].pdev[socket] = pdev;
1217 if (unlikely(PCI_SLOT(pdev->devfn) != pci_devs[devno].dev ||
1218 PCI_FUNC(pdev->devfn) != pci_devs[devno].func)) {
1219 i7core_printk(KERN_ERR,
1220 "Device PCI ID %04x:%04x "
1221 "has dev %02x:%02x.%d instead of dev %02x:%02x.%d\n",
1222 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id,
1223 bus, PCI_SLOT(pdev->devfn), PCI_FUNC(pdev->devfn),
1224 bus, pci_devs[devno].dev, pci_devs[devno].func);
1228 /* Be sure that the device is enabled */
1229 if (unlikely(pci_enable_device(pdev) < 0)) {
1230 i7core_printk(KERN_ERR,
1232 "dev %02x:%02x.%d PCI ID %04x:%04x\n",
1233 bus, pci_devs[devno].dev, pci_devs[devno].func,
1234 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id);
1238 i7core_printk(KERN_INFO,
1239 "Registered socket %d "
1240 "dev %02x:%02x.%d PCI ID %04x:%04x\n",
1241 socket, bus, pci_devs[devno].dev, pci_devs[devno].func,
1242 PCI_VENDOR_ID_INTEL, pci_devs[devno].dev_id);
1249 static int i7core_get_devices(void)
1252 struct pci_dev *pdev = NULL;
1254 for (i = 0; i < N_DEVS; i++) {
1257 if (i7core_get_onedevice(&pdev, i) < 0) {
1258 i7core_put_devices();
1266 static int mci_bind_devs(struct mem_ctl_info *mci)
1268 struct i7core_pvt *pvt = mci->pvt_info;
1269 struct pci_dev *pdev;
1270 int i, j, func, slot;
1272 for (i = 0; i < pvt->sockets; i++) {
1273 for (j = 0; j < N_DEVS; j++) {
1274 pdev = pci_devs[j].pdev[i];
1278 func = PCI_FUNC(pdev->devfn);
1279 slot = PCI_SLOT(pdev->devfn);
1281 if (unlikely(func > MAX_MCR_FUNC))
1283 pvt->pci_mcr[i][func] = pdev;
1284 } else if (likely(slot >= 4 && slot < 4 + NUM_CHANS)) {
1285 if (unlikely(func > MAX_CHAN_FUNC))
1287 pvt->pci_ch[i][slot - 4][func] = pdev;
1288 } else if (!slot && !func)
1289 pvt->pci_noncore[i] = pdev;
1293 debugf0("Associated fn %d.%d, dev = %p, socket %d\n",
1294 PCI_SLOT(pdev->devfn), PCI_FUNC(pdev->devfn),
1302 i7core_printk(KERN_ERR, "Device %d, function %d "
1303 "is out of the expected range\n",
1308 /****************************************************************************
1309 Error check routines
1310 ****************************************************************************/
1312 /* This function is based on the device 3 function 4 registers as described on:
1313 * Intel Xeon Processor 5500 Series Datasheet Volume 2
1314 * http://www.intel.com/Assets/PDF/datasheet/321322.pdf
1315 * also available at:
1316 * http://www.arrownac.com/manufacturers/intel/s/nehalem/5500-datasheet-v2.pdf
1318 static void check_mc_test_err(struct mem_ctl_info *mci, u8 socket)
1320 struct i7core_pvt *pvt = mci->pvt_info;
1322 int new0, new1, new2;
1324 if (!pvt->pci_mcr[socket][4]) {
1325 debugf0("%s MCR registers not found\n", __func__);
1329 /* Corrected error reads */
1330 pci_read_config_dword(pvt->pci_mcr[socket][4], MC_TEST_ERR_RCV1, &rcv1);
1331 pci_read_config_dword(pvt->pci_mcr[socket][4], MC_TEST_ERR_RCV0, &rcv0);
1333 /* Store the new values */
1334 new2 = DIMM2_COR_ERR(rcv1);
1335 new1 = DIMM1_COR_ERR(rcv0);
1336 new0 = DIMM0_COR_ERR(rcv0);
1339 debugf2("%s CE rcv1=0x%08x rcv0=0x%08x, %d %d %d\n",
1340 (pvt->ce_count_available ? "UPDATE" : "READ"),
1341 rcv1, rcv0, new0, new1, new2);
1344 /* Updates CE counters if it is not the first time here */
1345 if (pvt->ce_count_available[socket]) {
1346 /* Updates CE counters */
1347 int add0, add1, add2;
1349 add2 = new2 - pvt->last_ce_count[socket][2];
1350 add1 = new1 - pvt->last_ce_count[socket][1];
1351 add0 = new0 - pvt->last_ce_count[socket][0];
1355 pvt->ce_count[socket][2] += add2;
1359 pvt->ce_count[socket][1] += add1;
1363 pvt->ce_count[socket][0] += add0;
1365 pvt->ce_count_available[socket] = 1;
1367 /* Store the new values */
1368 pvt->last_ce_count[socket][2] = new2;
1369 pvt->last_ce_count[socket][1] = new1;
1370 pvt->last_ce_count[socket][0] = new0;
1374 * According with tables E-11 and E-12 of chapter E.3.3 of Intel 64 and IA-32
1375 * Architectures Software Developer’s Manual Volume 3B.
1376 * Nehalem are defined as family 0x06, model 0x1a
1378 * The MCA registers used here are the following ones:
1379 * struct mce field MCA Register
1380 * m->status MSR_IA32_MC8_STATUS
1381 * m->addr MSR_IA32_MC8_ADDR
1382 * m->misc MSR_IA32_MC8_MISC
1383 * In the case of Nehalem, the error information is masked at .status and .misc
1386 static void i7core_mce_output_error(struct mem_ctl_info *mci,
1389 char *type, *optype, *err, *msg;
1390 unsigned long error = m->status & 0x1ff0000l;
1391 u32 optypenum = (m->status >> 4) & 0x07;
1392 u32 core_err_cnt = (m->status >> 38) && 0x7fff;
1393 u32 dimm = (m->misc >> 16) & 0x3;
1394 u32 channel = (m->misc >> 18) & 0x3;
1395 u32 syndrome = m->misc >> 32;
1396 u32 errnum = find_first_bit(&error, 32);
1398 if (m->mcgstatus & 1)
1403 switch (optypenum) {
1405 optype = "generic undef request";
1408 optype = "read error";
1411 optype = "write error";
1414 optype = "addr/cmd error";
1417 optype = "scrubbing error";
1420 optype = "reserved";
1426 err = "read ECC error";
1429 err = "RAS ECC error";
1432 err = "write parity error";
1435 err = "redundacy loss";
1441 err = "memory range error";
1444 err = "RTID out of range";
1447 err = "address parity error";
1450 err = "byte enable parity error";
1456 /* FIXME: should convert addr into bank and rank information */
1457 msg = kasprintf(GFP_ATOMIC,
1458 "%s (addr = 0x%08llx, socket=%d, Dimm=%d, Channel=%d, "
1459 "syndrome=0x%08x, count=%d, Err=%08llx:%08llx (%s: %s))\n",
1460 type, (long long) m->addr, m->cpu, dimm, channel,
1461 syndrome, core_err_cnt, (long long)m->status,
1462 (long long)m->misc, optype, err);
1466 /* Call the helper to output message */
1467 edac_mc_handle_fbd_ue(mci, 0 /* FIXME: should be rank here */,
1468 0, 0 /* FIXME: should be channel here */, msg);
1474 * i7core_check_error Retrieve and process errors reported by the
1475 * hardware. Called by the Core module.
1477 static void i7core_check_error(struct mem_ctl_info *mci)
1479 struct i7core_pvt *pvt = mci->pvt_info;
1482 struct mce *m = NULL;
1483 unsigned long flags;
1485 /* Copy all mce errors into a temporary buffer */
1486 spin_lock_irqsave(&pvt->mce_lock, flags);
1487 if (pvt->mce_count) {
1488 m = kmalloc(sizeof(*m) * pvt->mce_count, GFP_ATOMIC);
1490 count = pvt->mce_count;
1491 memcpy(m, &pvt->mce_entry, sizeof(*m) * count);
1495 spin_unlock_irqrestore(&pvt->mce_lock, flags);
1497 /* proccess mcelog errors */
1498 for (i = 0; i < count; i++)
1499 i7core_mce_output_error(mci, &m[i]);
1503 /* check memory count errors */
1504 for (i = 0; i < pvt->sockets; i++)
1505 check_mc_test_err(mci, i);
1509 * i7core_mce_check_error Replicates mcelog routine to get errors
1510 * This routine simply queues mcelog errors, and
1511 * return. The error itself should be handled later
1512 * by i7core_check_error.
1514 static int i7core_mce_check_error(void *priv, struct mce *mce)
1516 struct mem_ctl_info *mci = priv;
1517 struct i7core_pvt *pvt = mci->pvt_info;
1518 unsigned long flags;
1521 * Just let mcelog handle it if the error is
1522 * outside the memory controller
1524 if (((mce->status & 0xffff) >> 7) != 1)
1527 /* Bank 8 registers are the only ones that we know how to handle */
1531 spin_lock_irqsave(&pvt->mce_lock, flags);
1532 if (pvt->mce_count < MCE_LOG_LEN) {
1533 memcpy(&pvt->mce_entry[pvt->mce_count], mce, sizeof(*mce));
1536 spin_unlock_irqrestore(&pvt->mce_lock, flags);
1538 /* Handle fatal errors immediately */
1539 if (mce->mcgstatus & 1)
1540 i7core_check_error(mci);
1542 /* Advice mcelog that the error were handled */
1547 * i7core_probe Probe for ONE instance of device to see if it is
1550 * 0 for FOUND a device
1551 * < 0 for error code
1553 static int __devinit i7core_probe(struct pci_dev *pdev,
1554 const struct pci_device_id *id)
1556 struct mem_ctl_info *mci;
1557 struct i7core_pvt *pvt;
1558 int num_channels = 0;
1561 int dev_idx = id->driver_data;
1565 if (unlikely(dev_idx >= ARRAY_SIZE(i7core_devs)))
1568 /* get the pci devices we want to reserve for our use */
1569 rc = i7core_get_devices();
1570 if (unlikely(rc < 0))
1574 for (i = NUM_SOCKETS - 1; i > 0; i--)
1575 if (pci_devs[0].pdev[i]) {
1580 for (i = 0; i < sockets; i++) {
1584 /* Check the number of active and not disabled channels */
1585 rc = i7core_get_active_channels(i, &channels, &csrows);
1586 if (unlikely(rc < 0))
1589 num_channels += channels;
1590 num_csrows += csrows;
1593 /* allocate a new MC control structure */
1594 mci = edac_mc_alloc(sizeof(*pvt), num_csrows, num_channels, 0);
1595 if (unlikely(!mci)) {
1600 debugf0("MC: " __FILE__ ": %s(): mci = %p\n", __func__, mci);
1602 mci->dev = &pdev->dev; /* record ptr to the generic device */
1603 pvt = mci->pvt_info;
1604 memset(pvt, 0, sizeof(*pvt));
1605 pvt->sockets = sockets;
1609 * FIXME: how to handle RDDR3 at MCI level? It is possible to have
1610 * Mixed RDDR3/UDDR3 with Nehalem, provided that they are on different
1613 mci->mtype_cap = MEM_FLAG_DDR3;
1614 mci->edac_ctl_cap = EDAC_FLAG_NONE;
1615 mci->edac_cap = EDAC_FLAG_NONE;
1616 mci->mod_name = "i7core_edac.c";
1617 mci->mod_ver = I7CORE_REVISION;
1618 mci->ctl_name = i7core_devs[dev_idx].ctl_name;
1619 mci->dev_name = pci_name(pdev);
1620 mci->ctl_page_to_phys = NULL;
1621 mci->mc_driver_sysfs_attributes = i7core_inj_attrs;
1622 /* Set the function pointer to an actual operation function */
1623 mci->edac_check = i7core_check_error;
1625 /* Store pci devices at mci for faster access */
1626 rc = mci_bind_devs(mci);
1627 if (unlikely(rc < 0))
1630 /* Get dimm basic config */
1631 for (i = 0; i < sockets; i++)
1632 get_dimm_config(mci, &csrow, i);
1634 /* add this new MC control structure to EDAC's list of MCs */
1635 if (unlikely(edac_mc_add_mc(mci))) {
1636 debugf0("MC: " __FILE__
1637 ": %s(): failed edac_mc_add_mc()\n", __func__);
1638 /* FIXME: perhaps some code should go here that disables error
1639 * reporting if we just enabled it
1646 /* allocating generic PCI control info */
1647 i7core_pci = edac_pci_create_generic_ctl(&pdev->dev, EDAC_MOD_STR);
1648 if (unlikely(!i7core_pci)) {
1650 "%s(): Unable to create PCI control\n",
1653 "%s(): PCI error report via EDAC not setup\n",
1657 /* Default error mask is any memory */
1658 pvt->inject.channel = 0;
1659 pvt->inject.dimm = -1;
1660 pvt->inject.rank = -1;
1661 pvt->inject.bank = -1;
1662 pvt->inject.page = -1;
1663 pvt->inject.col = -1;
1665 /* Registers on edac_mce in order to receive memory errors */
1666 pvt->edac_mce.priv = mci;
1667 pvt->edac_mce.check_error = i7core_mce_check_error;
1668 spin_lock_init(&pvt->mce_lock);
1670 rc = edac_mce_register(&pvt->edac_mce);
1671 if (unlikely(rc < 0)) {
1672 debugf0("MC: " __FILE__
1673 ": %s(): failed edac_mce_register()\n", __func__);
1677 i7core_printk(KERN_INFO, "Driver loaded.\n");
1685 i7core_put_devices();
1690 * i7core_remove destructor for one instance of device
1693 static void __devexit i7core_remove(struct pci_dev *pdev)
1695 struct mem_ctl_info *mci;
1696 struct i7core_pvt *pvt;
1698 debugf0(__FILE__ ": %s()\n", __func__);
1701 edac_pci_release_generic_ctl(i7core_pci);
1704 mci = edac_mc_del_mc(&pdev->dev);
1708 /* Unregisters on edac_mce in order to receive memory errors */
1709 pvt = mci->pvt_info;
1710 edac_mce_unregister(&pvt->edac_mce);
1712 /* retrieve references to resources, and free those resources */
1713 i7core_put_devices();
1718 MODULE_DEVICE_TABLE(pci, i7core_pci_tbl);
1721 * i7core_driver pci_driver structure for this module
1724 static struct pci_driver i7core_driver = {
1725 .name = "i7core_edac",
1726 .probe = i7core_probe,
1727 .remove = __devexit_p(i7core_remove),
1728 .id_table = i7core_pci_tbl,
1732 * i7core_init Module entry function
1733 * Try to initialize this module for its devices
1735 static int __init i7core_init(void)
1739 debugf2("MC: " __FILE__ ": %s()\n", __func__);
1741 /* Ensure that the OPSTATE is set correctly for POLL or NMI */
1744 pci_rc = pci_register_driver(&i7core_driver);
1746 return (pci_rc < 0) ? pci_rc : 0;
1750 * i7core_exit() Module exit function
1751 * Unregister the driver
1753 static void __exit i7core_exit(void)
1755 debugf2("MC: " __FILE__ ": %s()\n", __func__);
1756 pci_unregister_driver(&i7core_driver);
1759 module_init(i7core_init);
1760 module_exit(i7core_exit);
1762 MODULE_LICENSE("GPL");
1763 MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@redhat.com>");
1764 MODULE_AUTHOR("Red Hat Inc. (http://www.redhat.com)");
1765 MODULE_DESCRIPTION("MC Driver for Intel i7 Core memory controllers - "
1768 module_param(edac_op_state, int, 0444);
1769 MODULE_PARM_DESC(edac_op_state, "EDAC Error Reporting state: 0=Poll,1=NMI");