1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #include <sys/types.h> 28 #include <sys/cmn_err.h> 29 #include <sys/errno.h> 30 #include <sys/log.h> 31 #include <sys/systm.h> 32 #include <sys/modctl.h> 33 #include <sys/errorq.h> 34 #include <sys/controlregs.h> 35 #include <sys/fm/util.h> 36 #include <sys/fm/protocol.h> 37 #include <sys/sysevent.h> 38 #include <sys/pghw.h> 39 #include <sys/cyclic.h> 40 #include <sys/pci_cfgspace.h> 41 #include <sys/mc_intel.h> 42 #include <sys/smbios.h> 43 #include <sys/pci.h> 44 #include <sys/pcie.h> 45 #include "nb5000.h" 46 #include "nb_log.h" 47 #include "dimm_phys.h" 48 #include "rank.h" 49 50 int nb_hw_memory_scrub_enable = 1; 51 static int nb_sw_scrub_disabled = 0; 52 53 int nb_5000_memory_controller = 0; 54 int nb_number_memory_controllers = NB_5000_MAX_MEM_CONTROLLERS; 55 int nb_dimms_per_channel = 0; 56 57 nb_dimm_t **nb_dimms; 58 int nb_ndimm; 59 uint32_t nb_chipset; 60 enum nb_memory_mode nb_mode; 61 bank_select_t nb_banks[NB_MAX_MEM_BRANCH_SELECT]; 62 rank_select_t nb_ranks[NB_5000_MAX_MEM_CONTROLLERS][NB_MAX_MEM_RANK_SELECT]; 63 uint32_t top_of_low_memory; 64 uint8_t spare_rank[NB_5000_MAX_MEM_CONTROLLERS]; 65 66 extern int nb_no_smbios; 67 68 errorq_t *nb_queue; 69 kmutex_t nb_mutex; 70 71 static int nb_dimm_slots; 72 73 static uint8_t nb_err0_int; 74 static uint8_t nb_err1_int; 75 static uint8_t nb_err2_int; 76 static uint8_t nb_mcerr_int; 77 static uint32_t nb_emask_int; 78 79 static uint32_t nb_err0_fbd; 80 static uint32_t nb_err1_fbd; 81 static uint32_t nb_err2_fbd; 82 static uint32_t nb_mcerr_fbd; 83 static uint32_t nb_emask_fbd; 84 85 static uint16_t nb_err0_fsb; 86 static uint16_t nb_err1_fsb; 87 static uint16_t nb_err2_fsb; 88 static uint16_t nb_mcerr_fsb; 89 static uint16_t nb_emask_fsb; 90 91 static uint16_t nb_err0_thr; 92 static uint16_t nb_err1_thr; 93 static uint16_t nb_err2_thr; 94 static uint16_t nb_mcerr_thr; 95 static uint16_t nb_emask_thr; 96 97 static uint32_t emask_uncor_pex[NB_PCI_DEV]; 98 static uint32_t emask_cor_pex[NB_PCI_DEV]; 99 static uint32_t emask_rp_pex[NB_PCI_DEV]; 100 static uint32_t docmd_pex[NB_PCI_DEV]; 101 static uint32_t uncerrsev[NB_PCI_DEV]; 102 103 static uint8_t l_mcerr_int; 104 static uint32_t l_mcerr_fbd; 105 static uint16_t l_mcerr_fsb; 106 static uint16_t l_mcerr_thr; 107 108 uint_t nb5000_emask_fbd = EMASK_5000_FBD_RES; 109 uint_t nb5400_emask_fbd = 0; 110 int nb5000_reset_emask_fbd = 1; 111 uint_t nb5000_mask_poll_fbd = EMASK_FBD_NF; 112 uint_t nb5000_mask_bios_fbd = EMASK_FBD_FATAL; 113 uint_t nb5400_mask_poll_fbd = EMASK_5400_FBD_NF; 114 uint_t nb5400_mask_bios_fbd = EMASK_5400_FBD_FATAL; 115 116 uint_t nb5000_emask_fsb = 0; 117 int nb5000_reset_emask_fsb = 1; 118 uint_t nb5000_mask_poll_fsb = EMASK_FSB_NF; 119 uint_t nb5000_mask_bios_fsb = EMASK_FSB_FATAL; 120 121 uint_t nb5400_emask_int = 0; 122 123 uint_t nb7300_emask_int = EMASK_INT_7300; 124 uint_t nb7300_emask_int_step0 = EMASK_INT_7300_STEP_0; 125 uint_t nb5000_emask_int = EMASK_INT_5000; 126 int nb5000_reset_emask_int = 1; 127 uint_t nb5000_mask_poll_int = EMASK_INT_NF; 128 uint_t nb5000_mask_bios_int = EMASK_INT_FATAL; 129 130 uint_t nb_mask_poll_thr = EMASK_THR_NF; 131 uint_t nb_mask_bios_thr = EMASK_THR_FATAL; 132 133 int nb5000_reset_uncor_pex = 0; 134 uint_t nb5000_mask_uncor_pex = 0; 135 int nb5000_reset_cor_pex = 0; 136 uint_t nb5000_mask_cor_pex = 0xffffffff; 137 int nb_set_docmd = 1; 138 uint32_t nb5000_rp_pex = 0x1; 139 uint32_t nb5000_docmd_pex_mask = DOCMD_PEX_MASK; 140 uint32_t nb5400_docmd_pex_mask = DOCMD_5400_PEX_MASK; 141 uint32_t nb5000_docmd_pex = DOCMD_PEX; 142 uint32_t nb5400_docmd_pex = DOCMD_5400_PEX; 143 144 int nb_mask_mc_set; 145 146 typedef struct find_dimm_label { 147 void (*label_function)(int, char *, int); 148 } find_dimm_label_t; 149 150 static void x8450_dimm_label(int, char *, int); 151 152 static struct platform_label { 153 const char *sys_vendor; /* SMB_TYPE_SYSTEM vendor prefix */ 154 const char *sys_product; /* SMB_TYPE_SYSTEM product prefix */ 155 find_dimm_label_t dimm_label; 156 int dimms_per_channel; 157 } platform_label[] = { 158 { "SUN MICROSYSTEMS", "SUN BLADE X8450 SERVER MODULE", 159 x8450_dimm_label, 8 }, 160 { NULL, NULL, NULL, 0 } 161 }; 162 163 static unsigned short 164 read_spd(int bus) 165 { 166 unsigned short rt = 0; 167 int branch = bus >> 1; 168 int channel = bus & 1; 169 170 rt = SPD_RD(branch, channel); 171 172 return (rt); 173 } 174 175 static void 176 write_spdcmd(int bus, uint32_t val) 177 { 178 int branch = bus >> 1; 179 int channel = bus & 1; 180 SPDCMD_WR(branch, channel, val); 181 } 182 183 static int 184 read_spd_eeprom(int bus, int slave, int addr) 185 { 186 int retry = 4; 187 int wait; 188 int spd; 189 uint32_t cmd; 190 191 for (;;) { 192 wait = 1000; 193 for (;;) { 194 spd = read_spd(bus); 195 if ((spd & SPD_BUSY) == 0) 196 break; 197 if (--wait == 0) 198 return (-1); 199 drv_usecwait(10); 200 } 201 cmd = SPD_EEPROM_WRITE | SPD_ADDR(slave, addr); 202 write_spdcmd(bus, cmd); 203 wait = 1000; 204 for (;;) { 205 spd = read_spd(bus); 206 if ((spd & SPD_BUSY) == 0) 207 break; 208 if (--wait == 0) { 209 spd = SPD_BUS_ERROR; 210 break; 211 } 212 drv_usecwait(10); 213 } 214 while ((spd & SPD_BUS_ERROR) == 0 && 215 (spd & (SPD_READ_DATA_VALID|SPD_BUSY)) != 216 SPD_READ_DATA_VALID) { 217 spd = read_spd(bus); 218 if (--wait == 0) 219 return (-1); 220 } 221 if ((spd & SPD_BUS_ERROR) == 0) 222 break; 223 if (--retry == 0) 224 return (-1); 225 } 226 return (spd & 0xff); 227 } 228 229 static void 230 nb_fini() 231 { 232 int i, j; 233 int nchannels = nb_number_memory_controllers * 2; 234 nb_dimm_t **dimmpp; 235 nb_dimm_t *dimmp; 236 237 dimmpp = nb_dimms; 238 for (i = 0; i < nchannels; i++) { 239 for (j = 0; j < nb_dimms_per_channel; j++) { 240 dimmp = *dimmpp; 241 if (dimmp) { 242 kmem_free(dimmp, sizeof (nb_dimm_t)); 243 *dimmpp = NULL; 244 } 245 dimmp++; 246 } 247 } 248 kmem_free(nb_dimms, sizeof (nb_dimm_t *) * nb_dimm_slots); 249 nb_dimms = NULL; 250 dimm_fini(); 251 } 252 253 void 254 nb_scrubber_enable() 255 { 256 uint32_t mc; 257 258 if (!nb_hw_memory_scrub_enable) 259 return; 260 261 mc = MC_RD(); 262 if ((mc & MC_MIRROR) != 0) /* mirror mode */ 263 mc |= MC_PATROL_SCRUB; 264 else 265 mc |= MC_PATROL_SCRUB|MC_DEMAND_SCRUB; 266 MC_WR(mc); 267 268 if (nb_sw_scrub_disabled++) 269 cmi_mc_sw_memscrub_disable(); 270 } 271 272 static nb_dimm_t * 273 nb_dimm_init(int channel, int dimm, uint16_t mtr) 274 { 275 nb_dimm_t *dp; 276 int i, t; 277 int spd_sz; 278 279 if (MTR_PRESENT(mtr) == 0) 280 return (NULL); 281 t = read_spd_eeprom(channel, dimm, 2) & 0xf; 282 283 if (t != 9) 284 return (NULL); 285 286 dp = kmem_zalloc(sizeof (nb_dimm_t), KM_SLEEP); 287 288 t = read_spd_eeprom(channel, dimm, 0) & 0xf; 289 if (t == 1) 290 spd_sz = 128; 291 else if (t == 2) 292 spd_sz = 176; 293 else 294 spd_sz = 256; 295 dp->manufacture_id = read_spd_eeprom(channel, dimm, 117) | 296 (read_spd_eeprom(channel, dimm, 118) << 8); 297 dp->manufacture_location = read_spd_eeprom(channel, dimm, 119); 298 dp->serial_number = 299 (read_spd_eeprom(channel, dimm, 122) << 24) | 300 (read_spd_eeprom(channel, dimm, 123) << 16) | 301 (read_spd_eeprom(channel, dimm, 124) << 8) | 302 read_spd_eeprom(channel, dimm, 125); 303 t = read_spd_eeprom(channel, dimm, 121); 304 dp->manufacture_week = (t >> 4) * 10 + (t & 0xf); 305 dp->manufacture_year = read_spd_eeprom(channel, dimm, 120); 306 if (spd_sz > 128) { 307 for (i = 0; i < sizeof (dp->part_number); i++) { 308 dp->part_number[i] = 309 read_spd_eeprom(channel, dimm, 128 + i); 310 } 311 for (i = 0; i < sizeof (dp->revision); i++) { 312 dp->revision[i] = 313 read_spd_eeprom(channel, dimm, 146 + i); 314 } 315 } 316 dp->mtr_present = MTR_PRESENT(mtr); 317 dp->nranks = MTR_NUMRANK(mtr); 318 dp->nbanks = MTR_NUMBANK(mtr); 319 dp->ncolumn = MTR_NUMCOL(mtr); 320 dp->nrow = MTR_NUMROW(mtr); 321 dp->width = MTR_WIDTH(mtr); 322 dp->dimm_size = MTR_DIMMSIZE(mtr); 323 324 return (dp); 325 } 326 327 static uint64_t 328 mc_range(int controller, uint64_t base) 329 { 330 int i; 331 uint64_t limit = 0; 332 333 for (i = 0; i < NB_MEM_BRANCH_SELECT; i++) { 334 if (nb_banks[i].way[controller] && base >= nb_banks[i].base && 335 base < nb_banks[i].limit) { 336 limit = nb_banks[i].limit; 337 if (base <= top_of_low_memory && 338 limit > top_of_low_memory) { 339 limit -= TLOW_MAX - top_of_low_memory; 340 } 341 if (nb_banks[i].way[0] && nb_banks[i].way[1] && 342 nb_mode != NB_MEMORY_MIRROR) { 343 limit = limit / 2; 344 } 345 } 346 } 347 return (limit); 348 } 349 350 void 351 nb_mc_init() 352 { 353 uint16_t tolm; 354 uint16_t mir; 355 uint32_t hole_base; 356 uint32_t hole_size; 357 uint32_t dmir; 358 uint64_t base; 359 uint64_t limit; 360 uint8_t way0, way1, rank0, rank1, rank2, rank3, branch_interleave; 361 int i, j, k; 362 uint8_t interleave; 363 364 base = 0; 365 tolm = TOLM_RD(); 366 top_of_low_memory = ((uint32_t)(tolm >> 12) & 0xf) << 28; 367 for (i = 0; i < NB_MEM_BRANCH_SELECT; i++) { 368 mir = MIR_RD(i); 369 limit = (uint64_t)(mir >> 4) << 28; 370 way0 = mir & 1; 371 way1 = (mir >> 1) & 1; 372 if (way0 == 0 && way1 == 0) { 373 way0 = 1; 374 way1 = 1; 375 } 376 if (limit > top_of_low_memory) 377 limit += TLOW_MAX - top_of_low_memory; 378 nb_banks[i].base = base; 379 nb_banks[i].limit = limit; 380 nb_banks[i].way[0] = way0; 381 nb_banks[i].way[1] = way1; 382 base = limit; 383 } 384 for (i = 0; i < nb_number_memory_controllers; i++) { 385 base = 0; 386 387 for (j = 0; j < NB_MEM_RANK_SELECT; j++) { 388 dmir = DMIR_RD(i, j); 389 limit = ((uint64_t)(dmir >> 16) & 0xff) << 28; 390 if (limit == 0) { 391 limit = mc_range(i, base); 392 } 393 branch_interleave = 0; 394 hole_base = 0; 395 hole_size = 0; 396 DMIR_RANKS(dmir, rank0, rank1, rank2, rank3); 397 if (rank0 == rank1) 398 interleave = 1; 399 else if (rank0 == rank2) 400 interleave = 2; 401 else 402 interleave = 4; 403 if (nb_mode != NB_MEMORY_MIRROR && 404 nb_mode != NB_MEMORY_SINGLE_CHANNEL) { 405 for (k = 0; k < NB_MEM_BRANCH_SELECT; k++) { 406 if (base >= nb_banks[k].base && 407 base < nb_banks[k].limit) { 408 if (nb_banks[i].way[0] && 409 nb_banks[i].way[1]) { 410 interleave *= 2; 411 limit *= 2; 412 branch_interleave = 1; 413 } 414 break; 415 } 416 } 417 } 418 if (base < top_of_low_memory && 419 limit > top_of_low_memory) { 420 hole_base = top_of_low_memory; 421 hole_size = TLOW_MAX - top_of_low_memory; 422 limit += hole_size; 423 } else if (base > top_of_low_memory) { 424 limit += TLOW_MAX - top_of_low_memory; 425 } 426 nb_ranks[i][j].base = base; 427 nb_ranks[i][j].limit = limit; 428 nb_ranks[i][j].rank[0] = rank0; 429 nb_ranks[i][j].rank[1] = rank1; 430 nb_ranks[i][j].rank[2] = rank2; 431 nb_ranks[i][j].rank[3] = rank3; 432 nb_ranks[i][j].interleave = interleave; 433 nb_ranks[i][j].branch_interleave = branch_interleave; 434 nb_ranks[i][j].hole_base = hole_base; 435 nb_ranks[i][j].hole_size = hole_size; 436 if (limit > base) { 437 dimm_add_rank(i, rank0, branch_interleave, 0, 438 base, hole_base, hole_size, interleave, 439 limit); 440 if (rank0 != rank1) { 441 dimm_add_rank(i, rank1, 442 branch_interleave, 1, base, 443 hole_base, hole_size, interleave, 444 limit); 445 if (rank0 != rank2) { 446 dimm_add_rank(i, rank2, 447 branch_interleave, 2, base, 448 hole_base, hole_size, 449 interleave, limit); 450 dimm_add_rank(i, rank3, 451 branch_interleave, 3, base, 452 hole_base, hole_size, 453 interleave, limit); 454 } 455 } 456 } 457 base = limit; 458 } 459 } 460 } 461 462 void 463 nb_used_spare_rank(int branch, int bad_rank) 464 { 465 int i; 466 int j; 467 468 for (i = 0; i < NB_MEM_RANK_SELECT; i++) { 469 for (j = 0; j < NB_RANKS_IN_SELECT; j++) { 470 if (nb_ranks[branch][i].rank[j] == bad_rank) { 471 nb_ranks[branch][i].rank[j] = 472 spare_rank[branch]; 473 i = NB_MEM_RANK_SELECT; 474 break; 475 } 476 } 477 } 478 } 479 480 find_dimm_label_t * 481 find_dimms_per_channel() 482 { 483 struct platform_label *pl; 484 smbios_info_t si; 485 smbios_system_t sy; 486 id_t id; 487 int i, j; 488 uint16_t mtr; 489 find_dimm_label_t *rt = NULL; 490 491 if (ksmbios != NULL && nb_no_smbios == 0) { 492 if ((id = smbios_info_system(ksmbios, &sy)) != SMB_ERR && 493 smbios_info_common(ksmbios, id, &si) != SMB_ERR) { 494 for (pl = platform_label; pl->sys_vendor; pl++) { 495 if (strncmp(pl->sys_vendor, 496 si.smbi_manufacturer, 497 strlen(pl->sys_vendor)) == 0 && 498 strncmp(pl->sys_product, si.smbi_product, 499 strlen(pl->sys_product)) == 0) { 500 nb_dimms_per_channel = 501 pl->dimms_per_channel; 502 rt = &pl->dimm_label; 503 break; 504 } 505 } 506 } 507 } 508 if (nb_dimms_per_channel == 0) { 509 /* 510 * Scan all memory channels if we find a channel which has more 511 * dimms then we have seen before set nb_dimms_per_channel to 512 * the number of dimms on the channel 513 */ 514 for (i = 0; i < nb_number_memory_controllers; i++) { 515 for (j = nb_dimms_per_channel; 516 j < NB_MAX_DIMMS_PER_CHANNEL; j++) { 517 mtr = MTR_RD(i, j); 518 if (MTR_PRESENT(mtr)) 519 nb_dimms_per_channel = j + 1; 520 } 521 } 522 } 523 return (rt); 524 } 525 526 static int 527 dimm_label(smbios_hdl_t *shp, const smbios_struct_t *sp, void *arg) 528 { 529 nb_dimm_t ***dimmpp = arg; 530 nb_dimm_t *dimmp; 531 smbios_memdevice_t md; 532 533 if (sp->smbstr_type == SMB_TYPE_MEMDEVICE) { 534 if (*dimmpp >= &nb_dimms[nb_dimm_slots]) 535 return (-1); 536 dimmp = **dimmpp; 537 if (smbios_info_memdevice(shp, sp->smbstr_id, &md) == 0 && 538 md.smbmd_dloc != NULL) { 539 if (md.smbmd_size) { 540 /* 541 * if there is no physical dimm for this smbios 542 * record it is because this system has less 543 * physical slots than the controller supports 544 * so skip empty slots to find the slot this 545 * smbios record belongs too 546 */ 547 while (dimmp == NULL) { 548 if (*dimmpp >= &nb_dimms[nb_dimm_slots]) 549 return (-1); 550 dimmp = *(++(*dimmpp)); 551 } 552 (void) snprintf(dimmp->label, 553 sizeof (dimmp->label), "%s", md.smbmd_dloc); 554 (*dimmpp)++; 555 } 556 } 557 } 558 return (0); 559 } 560 561 void 562 nb_smbios() 563 { 564 nb_dimm_t **dimmpp; 565 566 if (ksmbios != NULL && nb_no_smbios == 0) { 567 dimmpp = nb_dimms; 568 (void) smbios_iter(ksmbios, dimm_label, &dimmpp); 569 } 570 } 571 572 static void 573 x8450_dimm_label(int dimm, char *label, int label_sz) 574 { 575 int channel = dimm >> 3; 576 577 dimm = dimm & 0x7; 578 (void) snprintf(label, label_sz, "D%d", (dimm * 4) + channel); 579 } 580 581 static void 582 nb_dimms_init(find_dimm_label_t *label_function) 583 { 584 int i, j, k, l; 585 uint16_t mtr; 586 uint32_t mc, mca; 587 uint32_t spcpc; 588 uint8_t spcps; 589 nb_dimm_t **dimmpp; 590 591 mca = MCA_RD(); 592 mc = MC_RD(); 593 if (mca & MCA_SCHDIMM) /* single-channel mode */ 594 nb_mode = NB_MEMORY_SINGLE_CHANNEL; 595 else if ((mc & MC_MIRROR) != 0) /* mirror mode */ 596 nb_mode = NB_MEMORY_MIRROR; 597 else 598 nb_mode = NB_MEMORY_NORMAL; 599 nb_dimm_slots = nb_number_memory_controllers * 2 * nb_dimms_per_channel; 600 nb_dimms = (nb_dimm_t **)kmem_zalloc(sizeof (nb_dimm_t *) * 601 nb_dimm_slots, KM_SLEEP); 602 dimmpp = nb_dimms; 603 for (i = 0; i < nb_number_memory_controllers; i++) { 604 if (nb_mode == NB_MEMORY_NORMAL) { 605 spcpc = SPCPC_RD(i); 606 spcps = SPCPS_RD(i); 607 if ((spcpc & SPCPC_SPARE_ENABLE) != 0 && 608 (spcps & SPCPS_SPARE_DEPLOYED) != 0) 609 nb_mode = NB_MEMORY_SPARE_RANK; 610 spare_rank[i] = SPCPC_SPRANK(spcpc); 611 } 612 for (j = 0; j < nb_dimms_per_channel; j++) { 613 mtr = MTR_RD(i, j); 614 k = i * 2; 615 dimmpp[j] = nb_dimm_init(k, j, mtr); 616 if (dimmpp[j]) { 617 nb_ndimm ++; 618 dimm_add_geometry(i, j, dimmpp[j]->nbanks, 619 dimmpp[j]->width, dimmpp[j]->ncolumn, 620 dimmpp[j]->nrow); 621 if (label_function) { 622 label_function->label_function( 623 (k * nb_dimms_per_channel) + j, 624 dimmpp[j]->label, 625 sizeof (dimmpp[j]->label)); 626 } 627 } 628 dimmpp[j + nb_dimms_per_channel] = 629 nb_dimm_init(k + 1, j, mtr); 630 l = j + nb_dimms_per_channel; 631 if (dimmpp[l]) { 632 if (label_function) { 633 label_function->label_function( 634 (k * nb_dimms_per_channel) + l, 635 dimmpp[l]->label, 636 sizeof (dimmpp[l]->label)); 637 } 638 nb_ndimm ++; 639 } 640 } 641 dimmpp += nb_dimms_per_channel * 2; 642 } 643 if (label_function == NULL) 644 nb_smbios(); 645 } 646 647 648 /* Setup the ESI port registers to enable SERR for southbridge */ 649 static void 650 nb_pex_init() 651 { 652 int i = 0; /* ESI port */ 653 uint32_t mask; 654 uint16_t regw; 655 656 emask_uncor_pex[i] = EMASK_UNCOR_PEX_RD(i); 657 emask_cor_pex[i] = EMASK_COR_PEX_RD(i); 658 emask_rp_pex[i] = EMASK_RP_PEX_RD(i); 659 docmd_pex[i] = PEX_ERR_DOCMD_RD(i); 660 uncerrsev[i] = UNCERRSEV_RD(i); 661 662 if (nb5000_reset_uncor_pex) 663 EMASK_UNCOR_PEX_WR(i, nb5000_mask_uncor_pex); 664 if (nb5000_reset_cor_pex) 665 EMASK_COR_PEX_WR(i, nb5000_mask_cor_pex); 666 if (nb_set_docmd) { 667 if (nb_chipset == INTEL_NB_5400) { 668 /* disable masking of ERR pins used by DOCMD */ 669 PEX_ERR_PIN_MASK_WR(i, 0x10); 670 671 mask = (docmd_pex[i] & nb5400_docmd_pex_mask) | 672 (nb5400_docmd_pex & ~nb5400_docmd_pex_mask); 673 } else { 674 mask = (docmd_pex[i] & nb5000_docmd_pex_mask) | 675 (nb5000_docmd_pex & ~nb5000_docmd_pex_mask); 676 } 677 PEX_ERR_DOCMD_WR(i, mask); 678 } 679 680 /* RP error message (CE/NFE/FE) detect mask */ 681 EMASK_RP_PEX_WR(i, nb5000_rp_pex); 682 683 /* Command Register - Enable SERR */ 684 regw = nb_pci_getw(0, i, 0, PCI_CONF_COMM, 0); 685 nb_pci_putw(0, i, 0, PCI_CONF_COMM, 686 regw | PCI_COMM_SERR_ENABLE); 687 688 /* Root Control Register - SERR on NFE/FE */ 689 PEXROOTCTL_WR(i, PCIE_ROOTCTL_SYS_ERR_ON_NFE_EN | 690 PCIE_ROOTCTL_SYS_ERR_ON_FE_EN); 691 692 /* AER UE Mask - Mask UR */ 693 UNCERRMSK_WR(i, PCIE_AER_UCE_UR); 694 } 695 696 static void 697 nb_pex_fini() 698 { 699 int i = 0; /* ESI port */ 700 701 EMASK_UNCOR_PEX_WR(i, emask_uncor_pex[i]); 702 EMASK_COR_PEX_WR(i, emask_cor_pex[i]); 703 EMASK_RP_PEX_WR(i, emask_rp_pex[i]); 704 PEX_ERR_DOCMD_WR(i, docmd_pex[i]); 705 706 if (nb5000_reset_uncor_pex) 707 EMASK_UNCOR_PEX_WR(i, nb5000_mask_uncor_pex); 708 if (nb5000_reset_cor_pex) 709 EMASK_COR_PEX_WR(i, nb5000_mask_cor_pex); 710 } 711 712 void 713 nb_int_init() 714 { 715 uint8_t err0_int; 716 uint8_t err1_int; 717 uint8_t err2_int; 718 uint8_t mcerr_int; 719 uint32_t emask_int; 720 uint16_t stepping; 721 722 err0_int = ERR0_INT_RD(); 723 err1_int = ERR1_INT_RD(); 724 err2_int = ERR2_INT_RD(); 725 mcerr_int = MCERR_INT_RD(); 726 emask_int = EMASK_INT_RD(); 727 728 nb_err0_int = err0_int; 729 nb_err1_int = err1_int; 730 nb_err2_int = err2_int; 731 nb_mcerr_int = mcerr_int; 732 nb_emask_int = emask_int; 733 734 ERR0_INT_WR(0xff); 735 ERR1_INT_WR(0xff); 736 ERR2_INT_WR(0xff); 737 MCERR_INT_WR(0xff); 738 EMASK_INT_WR(0xff); 739 740 mcerr_int &= ~nb5000_mask_bios_int; 741 mcerr_int |= nb5000_mask_bios_int & (~err0_int | ~err1_int | ~err2_int); 742 mcerr_int |= nb5000_mask_poll_int; 743 err0_int |= nb5000_mask_poll_int; 744 err1_int |= nb5000_mask_poll_int; 745 err2_int |= nb5000_mask_poll_int; 746 747 l_mcerr_int = mcerr_int; 748 ERR0_INT_WR(err0_int); 749 ERR1_INT_WR(err1_int); 750 ERR2_INT_WR(err2_int); 751 MCERR_INT_WR(mcerr_int); 752 if (nb5000_reset_emask_int) { 753 if (nb_chipset == INTEL_NB_7300) { 754 stepping = NB5000_STEPPING(); 755 if (stepping == 0) 756 EMASK_5000_INT_WR(nb7300_emask_int_step0); 757 else 758 EMASK_5000_INT_WR(nb7300_emask_int); 759 } else if (nb_chipset == INTEL_NB_5400) { 760 EMASK_5400_INT_WR(nb5400_emask_int | 761 (emask_int & EMASK_INT_RES)); 762 } else { 763 EMASK_5000_INT_WR(nb5000_emask_int); 764 } 765 } else { 766 EMASK_INT_WR(nb_emask_int); 767 } 768 } 769 770 void 771 nb_int_fini() 772 { 773 ERR0_INT_WR(0xff); 774 ERR1_INT_WR(0xff); 775 ERR2_INT_WR(0xff); 776 MCERR_INT_WR(0xff); 777 EMASK_INT_WR(0xff); 778 779 ERR0_INT_WR(nb_err0_int); 780 ERR1_INT_WR(nb_err1_int); 781 ERR2_INT_WR(nb_err2_int); 782 MCERR_INT_WR(nb_mcerr_int); 783 EMASK_INT_WR(nb_emask_int); 784 } 785 786 void 787 nb_int_mask_mc(uint32_t mc_mask_int) 788 { 789 uint32_t emask_int; 790 791 emask_int = MCERR_INT_RD(); 792 if ((emask_int & mc_mask_int) != mc_mask_int) { 793 MCERR_INT_WR(emask_int|mc_mask_int); 794 nb_mask_mc_set = 1; 795 } 796 } 797 798 void 799 nb_fbd_init() 800 { 801 uint32_t err0_fbd; 802 uint32_t err1_fbd; 803 uint32_t err2_fbd; 804 uint32_t mcerr_fbd; 805 uint32_t emask_fbd; 806 uint32_t emask_bios_fbd; 807 uint32_t emask_poll_fbd; 808 809 err0_fbd = ERR0_FBD_RD(); 810 err1_fbd = ERR1_FBD_RD(); 811 err2_fbd = ERR2_FBD_RD(); 812 mcerr_fbd = MCERR_FBD_RD(); 813 emask_fbd = EMASK_FBD_RD(); 814 815 nb_err0_fbd = err0_fbd; 816 nb_err1_fbd = err1_fbd; 817 nb_err2_fbd = err2_fbd; 818 nb_mcerr_fbd = mcerr_fbd; 819 nb_emask_fbd = emask_fbd; 820 821 ERR0_FBD_WR(0xffffffff); 822 ERR1_FBD_WR(0xffffffff); 823 ERR2_FBD_WR(0xffffffff); 824 MCERR_FBD_WR(0xffffffff); 825 EMASK_FBD_WR(0xffffffff); 826 827 if (nb_chipset == INTEL_NB_7300 && nb_mode == NB_MEMORY_MIRROR) { 828 /* MCH 7300 errata 34 */ 829 emask_bios_fbd = nb5000_mask_bios_fbd & ~EMASK_FBD_M23; 830 emask_poll_fbd = nb5000_mask_poll_fbd; 831 mcerr_fbd |= EMASK_FBD_M23; 832 } else if (nb_chipset == INTEL_NB_5400) { 833 emask_bios_fbd = nb5400_mask_bios_fbd; 834 emask_poll_fbd = nb5400_mask_poll_fbd; 835 } else { 836 emask_bios_fbd = nb5000_mask_bios_fbd; 837 emask_poll_fbd = nb5000_mask_poll_fbd; 838 } 839 mcerr_fbd &= ~emask_bios_fbd; 840 mcerr_fbd |= emask_bios_fbd & (~err0_fbd | ~err1_fbd | ~err2_fbd); 841 mcerr_fbd |= emask_poll_fbd; 842 err0_fbd |= emask_poll_fbd; 843 err1_fbd |= emask_poll_fbd; 844 err2_fbd |= emask_poll_fbd; 845 846 l_mcerr_fbd = mcerr_fbd; 847 ERR0_FBD_WR(err0_fbd); 848 ERR1_FBD_WR(err1_fbd); 849 ERR2_FBD_WR(err2_fbd); 850 MCERR_FBD_WR(mcerr_fbd); 851 if (nb5000_reset_emask_fbd) { 852 if (nb_chipset == INTEL_NB_5400) 853 EMASK_FBD_WR(nb5400_emask_fbd); 854 else 855 EMASK_FBD_WR(nb5000_emask_fbd); 856 } else { 857 EMASK_FBD_WR(nb_emask_fbd); 858 } 859 } 860 861 void 862 nb_fbd_mask_mc(uint32_t mc_mask_fbd) 863 { 864 uint32_t emask_fbd; 865 866 emask_fbd = MCERR_FBD_RD(); 867 if ((emask_fbd & mc_mask_fbd) != mc_mask_fbd) { 868 MCERR_FBD_WR(emask_fbd|mc_mask_fbd); 869 nb_mask_mc_set = 1; 870 } 871 } 872 873 void 874 nb_fbd_fini() 875 { 876 ERR0_FBD_WR(0xffffffff); 877 ERR1_FBD_WR(0xffffffff); 878 ERR2_FBD_WR(0xffffffff); 879 MCERR_FBD_WR(0xffffffff); 880 EMASK_FBD_WR(0xffffffff); 881 882 ERR0_FBD_WR(nb_err0_fbd); 883 ERR1_FBD_WR(nb_err1_fbd); 884 ERR2_FBD_WR(nb_err2_fbd); 885 MCERR_FBD_WR(nb_mcerr_fbd); 886 EMASK_FBD_WR(nb_emask_fbd); 887 } 888 889 static void 890 nb_fsb_init() 891 { 892 uint16_t err0_fsb; 893 uint16_t err1_fsb; 894 uint16_t err2_fsb; 895 uint16_t mcerr_fsb; 896 uint16_t emask_fsb; 897 898 err0_fsb = ERR0_FSB_RD(0); 899 err1_fsb = ERR1_FSB_RD(0); 900 err2_fsb = ERR2_FSB_RD(0); 901 mcerr_fsb = MCERR_FSB_RD(0); 902 emask_fsb = EMASK_FSB_RD(0); 903 904 ERR0_FSB_WR(0, 0xffff); 905 ERR1_FSB_WR(0, 0xffff); 906 ERR2_FSB_WR(0, 0xffff); 907 MCERR_FSB_WR(0, 0xffff); 908 EMASK_FSB_WR(0, 0xffff); 909 910 ERR0_FSB_WR(1, 0xffff); 911 ERR1_FSB_WR(1, 0xffff); 912 ERR2_FSB_WR(1, 0xffff); 913 MCERR_FSB_WR(1, 0xffff); 914 EMASK_FSB_WR(1, 0xffff); 915 916 nb_err0_fsb = err0_fsb; 917 nb_err1_fsb = err1_fsb; 918 nb_err2_fsb = err2_fsb; 919 nb_mcerr_fsb = mcerr_fsb; 920 nb_emask_fsb = emask_fsb; 921 922 mcerr_fsb &= ~nb5000_mask_bios_fsb; 923 mcerr_fsb |= nb5000_mask_bios_fsb & (~err2_fsb | ~err1_fsb | ~err0_fsb); 924 mcerr_fsb |= nb5000_mask_poll_fsb; 925 err0_fsb |= nb5000_mask_poll_fsb; 926 err1_fsb |= nb5000_mask_poll_fsb; 927 err2_fsb |= nb5000_mask_poll_fsb; 928 929 l_mcerr_fsb = mcerr_fsb; 930 ERR0_FSB_WR(0, err0_fsb); 931 ERR1_FSB_WR(0, err1_fsb); 932 ERR2_FSB_WR(0, err2_fsb); 933 MCERR_FSB_WR(0, mcerr_fsb); 934 if (nb5000_reset_emask_fsb) { 935 EMASK_FSB_WR(0, nb5000_emask_fsb); 936 } else { 937 EMASK_FSB_WR(0, nb_emask_fsb); 938 } 939 940 ERR0_FSB_WR(1, err0_fsb); 941 ERR1_FSB_WR(1, err1_fsb); 942 ERR2_FSB_WR(1, err2_fsb); 943 MCERR_FSB_WR(1, mcerr_fsb); 944 if (nb5000_reset_emask_fsb) { 945 EMASK_FSB_WR(1, nb5000_emask_fsb); 946 } else { 947 EMASK_FSB_WR(1, nb_emask_fsb); 948 } 949 950 if (nb_chipset == INTEL_NB_7300) { 951 ERR0_FSB_WR(2, 0xffff); 952 ERR1_FSB_WR(2, 0xffff); 953 ERR2_FSB_WR(2, 0xffff); 954 MCERR_FSB_WR(2, 0xffff); 955 EMASK_FSB_WR(2, 0xffff); 956 957 ERR0_FSB_WR(3, 0xffff); 958 ERR1_FSB_WR(3, 0xffff); 959 ERR2_FSB_WR(3, 0xffff); 960 MCERR_FSB_WR(3, 0xffff); 961 EMASK_FSB_WR(3, 0xffff); 962 963 ERR0_FSB_WR(2, err0_fsb); 964 ERR1_FSB_WR(2, err1_fsb); 965 ERR2_FSB_WR(2, err2_fsb); 966 MCERR_FSB_WR(2, mcerr_fsb); 967 if (nb5000_reset_emask_fsb) { 968 EMASK_FSB_WR(2, nb5000_emask_fsb); 969 } else { 970 EMASK_FSB_WR(2, nb_emask_fsb); 971 } 972 973 ERR0_FSB_WR(3, err0_fsb); 974 ERR1_FSB_WR(3, err1_fsb); 975 ERR2_FSB_WR(3, err2_fsb); 976 MCERR_FSB_WR(3, mcerr_fsb); 977 if (nb5000_reset_emask_fsb) { 978 EMASK_FSB_WR(3, nb5000_emask_fsb); 979 } else { 980 EMASK_FSB_WR(3, nb_emask_fsb); 981 } 982 } 983 } 984 985 static void 986 nb_fsb_fini() { 987 ERR0_FSB_WR(0, 0xffff); 988 ERR1_FSB_WR(0, 0xffff); 989 ERR2_FSB_WR(0, 0xffff); 990 MCERR_FSB_WR(0, 0xffff); 991 EMASK_FSB_WR(0, 0xffff); 992 993 ERR0_FSB_WR(0, nb_err0_fsb); 994 ERR1_FSB_WR(0, nb_err1_fsb); 995 ERR2_FSB_WR(0, nb_err2_fsb); 996 MCERR_FSB_WR(0, nb_mcerr_fsb); 997 EMASK_FSB_WR(0, nb_emask_fsb); 998 999 ERR0_FSB_WR(1, 0xffff); 1000 ERR1_FSB_WR(1, 0xffff); 1001 ERR2_FSB_WR(1, 0xffff); 1002 MCERR_FSB_WR(1, 0xffff); 1003 EMASK_FSB_WR(1, 0xffff); 1004 1005 ERR0_FSB_WR(1, nb_err0_fsb); 1006 ERR1_FSB_WR(1, nb_err1_fsb); 1007 ERR2_FSB_WR(1, nb_err2_fsb); 1008 MCERR_FSB_WR(1, nb_mcerr_fsb); 1009 EMASK_FSB_WR(1, nb_emask_fsb); 1010 1011 if (nb_chipset == INTEL_NB_7300) { 1012 ERR0_FSB_WR(2, 0xffff); 1013 ERR1_FSB_WR(2, 0xffff); 1014 ERR2_FSB_WR(2, 0xffff); 1015 MCERR_FSB_WR(2, 0xffff); 1016 EMASK_FSB_WR(2, 0xffff); 1017 1018 ERR0_FSB_WR(2, nb_err0_fsb); 1019 ERR1_FSB_WR(2, nb_err1_fsb); 1020 ERR2_FSB_WR(2, nb_err2_fsb); 1021 MCERR_FSB_WR(2, nb_mcerr_fsb); 1022 EMASK_FSB_WR(2, nb_emask_fsb); 1023 1024 ERR0_FSB_WR(3, 0xffff); 1025 ERR1_FSB_WR(3, 0xffff); 1026 ERR2_FSB_WR(3, 0xffff); 1027 MCERR_FSB_WR(3, 0xffff); 1028 EMASK_FSB_WR(3, 0xffff); 1029 1030 ERR0_FSB_WR(3, nb_err0_fsb); 1031 ERR1_FSB_WR(3, nb_err1_fsb); 1032 ERR2_FSB_WR(3, nb_err2_fsb); 1033 MCERR_FSB_WR(3, nb_mcerr_fsb); 1034 EMASK_FSB_WR(3, nb_emask_fsb); 1035 } 1036 } 1037 1038 void 1039 nb_fsb_mask_mc(int fsb, uint16_t mc_mask_fsb) 1040 { 1041 uint16_t emask_fsb; 1042 1043 emask_fsb = MCERR_FSB_RD(fsb); 1044 if ((emask_fsb & mc_mask_fsb) != mc_mask_fsb) { 1045 MCERR_FSB_WR(fsb, emask_fsb|mc_mask_fsb|EMASK_FBD_RES); 1046 nb_mask_mc_set = 1; 1047 } 1048 } 1049 1050 static void 1051 nb_thr_init() 1052 { 1053 uint16_t err0_thr; 1054 uint16_t err1_thr; 1055 uint16_t err2_thr; 1056 uint16_t mcerr_thr; 1057 uint16_t emask_thr; 1058 1059 if (nb_chipset == INTEL_NB_5400) { 1060 err0_thr = ERR0_THR_RD(0); 1061 err1_thr = ERR1_THR_RD(0); 1062 err2_thr = ERR2_THR_RD(0); 1063 mcerr_thr = MCERR_THR_RD(0); 1064 emask_thr = EMASK_THR_RD(0); 1065 1066 ERR0_THR_WR(0xffff); 1067 ERR1_THR_WR(0xffff); 1068 ERR2_THR_WR(0xffff); 1069 MCERR_THR_WR(0xffff); 1070 EMASK_THR_WR(0xffff); 1071 1072 nb_err0_thr = err0_thr; 1073 nb_err1_thr = err1_thr; 1074 nb_err2_thr = err2_thr; 1075 nb_mcerr_thr = mcerr_thr; 1076 nb_emask_thr = emask_thr; 1077 1078 mcerr_thr &= ~nb_mask_bios_thr; 1079 mcerr_thr |= nb_mask_bios_thr & 1080 (~err2_thr | ~err1_thr | ~err0_thr); 1081 mcerr_thr |= nb_mask_poll_thr; 1082 err0_thr |= nb_mask_poll_thr; 1083 err1_thr |= nb_mask_poll_thr; 1084 err2_thr |= nb_mask_poll_thr; 1085 1086 l_mcerr_thr = mcerr_thr; 1087 ERR0_THR_WR(err0_thr); 1088 ERR1_THR_WR(err1_thr); 1089 ERR2_THR_WR(err2_thr); 1090 MCERR_THR_WR(mcerr_thr); 1091 EMASK_THR_WR(nb_emask_thr); 1092 } 1093 } 1094 1095 static void 1096 nb_thr_fini() 1097 { 1098 if (nb_chipset == INTEL_NB_5400) { 1099 ERR0_THR_WR(0xffff); 1100 ERR1_THR_WR(0xffff); 1101 ERR2_THR_WR(0xffff); 1102 MCERR_THR_WR(0xffff); 1103 EMASK_THR_WR(0xffff); 1104 1105 ERR0_THR_WR(nb_err0_thr); 1106 ERR1_THR_WR(nb_err1_thr); 1107 ERR2_THR_WR(nb_err2_thr); 1108 MCERR_THR_WR(nb_mcerr_thr); 1109 EMASK_THR_WR(nb_emask_thr); 1110 } 1111 } 1112 1113 void 1114 nb_thr_mask_mc(uint16_t mc_mask_thr) 1115 { 1116 uint16_t emask_thr; 1117 1118 emask_thr = MCERR_THR_RD(0); 1119 if ((emask_thr & mc_mask_thr) != mc_mask_thr) { 1120 MCERR_THR_WR(emask_thr|mc_mask_thr); 1121 nb_mask_mc_set = 1; 1122 } 1123 } 1124 1125 void 1126 nb_mask_mc_reset() 1127 { 1128 MCERR_FBD_WR(l_mcerr_fbd); 1129 MCERR_INT_WR(l_mcerr_int); 1130 MCERR_FSB_WR(0, l_mcerr_fsb); 1131 MCERR_FSB_WR(1, l_mcerr_fsb); 1132 if (nb_chipset == INTEL_NB_7300) { 1133 MCERR_FSB_WR(2, l_mcerr_fsb); 1134 MCERR_FSB_WR(3, l_mcerr_fsb); 1135 } 1136 if (nb_chipset == INTEL_NB_5400) { 1137 MCERR_THR_WR(l_mcerr_thr); 1138 } 1139 } 1140 1141 int 1142 nb_dev_init() 1143 { 1144 find_dimm_label_t *label_function_p; 1145 1146 label_function_p = find_dimms_per_channel(); 1147 mutex_init(&nb_mutex, NULL, MUTEX_DRIVER, NULL); 1148 nb_queue = errorq_create("nb_queue", nb_drain, NULL, NB_MAX_ERRORS, 1149 sizeof (nb_logout_t), 1, ERRORQ_VITAL); 1150 if (nb_queue == NULL) { 1151 mutex_destroy(&nb_mutex); 1152 return (EAGAIN); 1153 } 1154 nb_int_init(); 1155 nb_thr_init(); 1156 dimm_init(); 1157 nb_dimms_init(label_function_p); 1158 nb_mc_init(); 1159 nb_pex_init(); 1160 nb_fbd_init(); 1161 nb_fsb_init(); 1162 nb_scrubber_enable(); 1163 return (0); 1164 } 1165 1166 int 1167 nb_init() 1168 { 1169 /* return ENOTSUP if there is no PCI config space support. */ 1170 if (pci_getl_func == NULL) 1171 return (ENOTSUP); 1172 1173 /* get vendor and device */ 1174 nb_chipset = (*pci_getl_func)(0, 0, 0, PCI_CONF_VENID); 1175 switch (nb_chipset) { 1176 default: 1177 if (nb_5000_memory_controller == 0) 1178 return (ENOTSUP); 1179 break; 1180 case INTEL_NB_7300: 1181 case INTEL_NB_5000P: 1182 case INTEL_NB_5000X: 1183 break; 1184 case INTEL_NB_5000V: 1185 case INTEL_NB_5000Z: 1186 nb_number_memory_controllers = 1; 1187 break; 1188 case INTEL_NB_5400: 1189 case INTEL_NB_5400A: 1190 case INTEL_NB_5400B: 1191 nb_chipset = INTEL_NB_5400; 1192 break; 1193 } 1194 return (0); 1195 } 1196 1197 void 1198 nb_dev_reinit() 1199 { 1200 int i, j; 1201 int nchannels = nb_number_memory_controllers * 2; 1202 nb_dimm_t **dimmpp; 1203 nb_dimm_t *dimmp; 1204 nb_dimm_t **old_nb_dimms; 1205 int old_nb_dimms_per_channel; 1206 find_dimm_label_t *label_function_p; 1207 int dimm_slot = nb_dimm_slots; 1208 1209 old_nb_dimms = nb_dimms; 1210 old_nb_dimms_per_channel = nb_dimms_per_channel; 1211 1212 dimm_fini(); 1213 nb_dimms_per_channel = 0; 1214 label_function_p = find_dimms_per_channel(); 1215 dimm_init(); 1216 nb_dimms_init(label_function_p); 1217 nb_mc_init(); 1218 nb_pex_init(); 1219 nb_int_init(); 1220 nb_thr_init(); 1221 nb_fbd_init(); 1222 nb_fsb_init(); 1223 nb_scrubber_enable(); 1224 1225 dimmpp = old_nb_dimms; 1226 for (i = 0; i < nchannels; i++) { 1227 for (j = 0; j < old_nb_dimms_per_channel; j++) { 1228 dimmp = *dimmpp; 1229 if (dimmp) { 1230 kmem_free(dimmp, sizeof (nb_dimm_t)); 1231 *dimmpp = NULL; 1232 } 1233 dimmp++; 1234 } 1235 } 1236 kmem_free(old_nb_dimms, sizeof (nb_dimm_t *) * dimm_slot); 1237 } 1238 1239 void 1240 nb_dev_unload() 1241 { 1242 errorq_destroy(nb_queue); 1243 nb_queue = NULL; 1244 mutex_destroy(&nb_mutex); 1245 nb_int_fini(); 1246 nb_thr_fini(); 1247 nb_fbd_fini(); 1248 nb_fsb_fini(); 1249 nb_pex_fini(); 1250 nb_fini(); 1251 } 1252 1253 void 1254 nb_unload() 1255 { 1256 } 1257