1 /* 2 * pcie_aer.c 3 * 4 * Copyright (c) 2010 Isaku Yamahata <yamahata at valinux co jp> 5 * VA Linux Systems Japan K.K. 6 * 7 * This program is free software; you can redistribute it and/or modify 8 * it under the terms of the GNU General Public License as published by 9 * the Free Software Foundation; either version 2 of the License, or 10 * (at your option) any later version. 11 * 12 * This program is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 * GNU General Public License for more details. 16 * 17 * You should have received a copy of the GNU General Public License along 18 * with this program; if not, see <http://www.gnu.org/licenses/>. 19 */ 20 21 #include "qemu/osdep.h" 22 #include "migration/vmstate.h" 23 #include "hw/pci/pci_bridge.h" 24 #include "hw/pci/pcie.h" 25 #include "hw/pci/msix.h" 26 #include "hw/pci/msi.h" 27 #include "hw/pci/pci_bus.h" 28 #include "hw/pci/pcie_regs.h" 29 #include "pci-internal.h" 30 31 //#define DEBUG_PCIE 32 #ifdef DEBUG_PCIE 33 # define PCIE_DPRINTF(fmt, ...) \ 34 fprintf(stderr, "%s:%d " fmt, __func__, __LINE__, ## __VA_ARGS__) 35 #else 36 # define PCIE_DPRINTF(fmt, ...) do {} while (0) 37 #endif 38 #define PCIE_DEV_PRINTF(dev, fmt, ...) \ 39 PCIE_DPRINTF("%s:%x "fmt, (dev)->name, (dev)->devfn, ## __VA_ARGS__) 40 41 #define PCI_ERR_SRC_COR_OFFS 0 42 #define PCI_ERR_SRC_UNCOR_OFFS 2 43 44 /* From 6.2.7 Error Listing and Rules. Table 6-2, 6-3 and 6-4 */ 45 static uint32_t pcie_aer_uncor_default_severity(uint32_t status) 46 { 47 switch (status) { 48 case PCI_ERR_UNC_INTN: 49 case PCI_ERR_UNC_DLP: 50 case PCI_ERR_UNC_SDN: 51 case PCI_ERR_UNC_RX_OVER: 52 case PCI_ERR_UNC_FCP: 53 case PCI_ERR_UNC_MALF_TLP: 54 return PCI_ERR_ROOT_CMD_FATAL_EN; 55 case PCI_ERR_UNC_POISON_TLP: 56 case PCI_ERR_UNC_ECRC: 57 case PCI_ERR_UNC_UNSUP: 58 case PCI_ERR_UNC_COMP_TIME: 59 case PCI_ERR_UNC_COMP_ABORT: 60 case PCI_ERR_UNC_UNX_COMP: 61 case PCI_ERR_UNC_ACSV: 62 case PCI_ERR_UNC_MCBTLP: 63 case PCI_ERR_UNC_ATOP_EBLOCKED: 64 case PCI_ERR_UNC_TLP_PRF_BLOCKED: 65 return PCI_ERR_ROOT_CMD_NONFATAL_EN; 66 default: 67 abort(); 68 break; 69 } 70 return PCI_ERR_ROOT_CMD_FATAL_EN; 71 } 72 73 static int aer_log_add_err(PCIEAERLog *aer_log, const PCIEAERErr *err) 74 { 75 if (aer_log->log_num == aer_log->log_max) { 76 return -1; 77 } 78 memcpy(&aer_log->log[aer_log->log_num], err, sizeof *err); 79 aer_log->log_num++; 80 return 0; 81 } 82 83 static void aer_log_del_err(PCIEAERLog *aer_log, PCIEAERErr *err) 84 { 85 assert(aer_log->log_num); 86 *err = aer_log->log[0]; 87 aer_log->log_num--; 88 memmove(&aer_log->log[0], &aer_log->log[1], 89 aer_log->log_num * sizeof *err); 90 } 91 92 static void aer_log_clear_all_err(PCIEAERLog *aer_log) 93 { 94 aer_log->log_num = 0; 95 } 96 97 int pcie_aer_init(PCIDevice *dev, uint8_t cap_ver, uint16_t offset, 98 uint16_t size, Error **errp) 99 { 100 pcie_add_capability(dev, PCI_EXT_CAP_ID_ERR, cap_ver, 101 offset, size); 102 dev->exp.aer_cap = offset; 103 104 /* clip down the value to avoid unreasonable memory usage */ 105 if (dev->exp.aer_log.log_max > PCIE_AER_LOG_MAX_LIMIT) { 106 error_setg(errp, "Invalid aer_log_max %d. The max number of aer log " 107 "is %d", dev->exp.aer_log.log_max, PCIE_AER_LOG_MAX_LIMIT); 108 return -EINVAL; 109 } 110 dev->exp.aer_log.log = g_malloc0(sizeof dev->exp.aer_log.log[0] * 111 dev->exp.aer_log.log_max); 112 113 pci_set_long(dev->w1cmask + offset + PCI_ERR_UNCOR_STATUS, 114 PCI_ERR_UNC_SUPPORTED); 115 116 pci_set_long(dev->config + offset + PCI_ERR_UNCOR_SEVER, 117 PCI_ERR_UNC_SEVERITY_DEFAULT); 118 pci_set_long(dev->wmask + offset + PCI_ERR_UNCOR_SEVER, 119 PCI_ERR_UNC_SUPPORTED); 120 121 pci_long_test_and_set_mask(dev->w1cmask + offset + PCI_ERR_COR_STATUS, 122 PCI_ERR_COR_SUPPORTED); 123 124 pci_set_long(dev->config + offset + PCI_ERR_COR_MASK, 125 PCI_ERR_COR_MASK_DEFAULT); 126 pci_set_long(dev->wmask + offset + PCI_ERR_COR_MASK, 127 PCI_ERR_COR_SUPPORTED); 128 129 /* capabilities and control. multiple header logging is supported */ 130 if (dev->exp.aer_log.log_max > 0) { 131 pci_set_long(dev->config + offset + PCI_ERR_CAP, 132 PCI_ERR_CAP_ECRC_GENC | PCI_ERR_CAP_ECRC_CHKC | 133 PCI_ERR_CAP_MHRC); 134 pci_set_long(dev->wmask + offset + PCI_ERR_CAP, 135 PCI_ERR_CAP_ECRC_GENE | PCI_ERR_CAP_ECRC_CHKE | 136 PCI_ERR_CAP_MHRE); 137 } else { 138 pci_set_long(dev->config + offset + PCI_ERR_CAP, 139 PCI_ERR_CAP_ECRC_GENC | PCI_ERR_CAP_ECRC_CHKC); 140 pci_set_long(dev->wmask + offset + PCI_ERR_CAP, 141 PCI_ERR_CAP_ECRC_GENE | PCI_ERR_CAP_ECRC_CHKE); 142 } 143 144 switch (pcie_cap_get_type(dev)) { 145 case PCI_EXP_TYPE_ROOT_PORT: 146 /* this case will be set by pcie_aer_root_init() */ 147 /* fallthrough */ 148 case PCI_EXP_TYPE_DOWNSTREAM: 149 case PCI_EXP_TYPE_UPSTREAM: 150 pci_word_test_and_set_mask(dev->wmask + PCI_BRIDGE_CONTROL, 151 PCI_BRIDGE_CTL_SERR); 152 pci_long_test_and_set_mask(dev->w1cmask + PCI_STATUS, 153 PCI_SEC_STATUS_RCV_SYSTEM_ERROR); 154 break; 155 default: 156 /* nothing */ 157 break; 158 } 159 return 0; 160 } 161 162 void pcie_aer_exit(PCIDevice *dev) 163 { 164 g_free(dev->exp.aer_log.log); 165 } 166 167 static void pcie_aer_update_uncor_status(PCIDevice *dev) 168 { 169 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 170 PCIEAERLog *aer_log = &dev->exp.aer_log; 171 172 uint16_t i; 173 for (i = 0; i < aer_log->log_num; i++) { 174 pci_long_test_and_set_mask(aer_cap + PCI_ERR_UNCOR_STATUS, 175 dev->exp.aer_log.log[i].status); 176 } 177 } 178 179 /* 180 * return value: 181 * true: error message needs to be sent up 182 * false: error message is masked 183 * 184 * 6.2.6 Error Message Control 185 * Figure 6-3 186 * all pci express devices part 187 */ 188 static bool 189 pcie_aer_msg_alldev(PCIDevice *dev, const PCIEAERMsg *msg) 190 { 191 if (!(pcie_aer_msg_is_uncor(msg) && 192 (pci_get_word(dev->config + PCI_COMMAND) & PCI_COMMAND_SERR))) { 193 return false; 194 } 195 196 /* Signaled System Error 197 * 198 * 7.5.1.1 Command register 199 * Bit 8 SERR# Enable 200 * 201 * When Set, this bit enables reporting of Non-fatal and Fatal 202 * errors detected by the Function to the Root Complex. Note that 203 * errors are reported if enabled either through this bit or through 204 * the PCI Express specific bits in the Device Control register (see 205 * Section 7.8.4). 206 */ 207 pci_word_test_and_set_mask(dev->config + PCI_STATUS, 208 PCI_STATUS_SIG_SYSTEM_ERROR); 209 210 if (!(msg->severity & 211 pci_get_word(dev->config + dev->exp.exp_cap + PCI_EXP_DEVCTL))) { 212 return false; 213 } 214 215 /* send up error message */ 216 return true; 217 } 218 219 /* 220 * return value: 221 * true: error message is sent up 222 * false: error message is masked 223 * 224 * 6.2.6 Error Message Control 225 * Figure 6-3 226 * virtual pci bridge part 227 */ 228 static bool pcie_aer_msg_vbridge(PCIDevice *dev, const PCIEAERMsg *msg) 229 { 230 uint16_t bridge_control = pci_get_word(dev->config + PCI_BRIDGE_CONTROL); 231 232 if (pcie_aer_msg_is_uncor(msg)) { 233 /* Received System Error */ 234 pci_word_test_and_set_mask(dev->config + PCI_SEC_STATUS, 235 PCI_SEC_STATUS_RCV_SYSTEM_ERROR); 236 } 237 238 if (!(bridge_control & PCI_BRIDGE_CTL_SERR)) { 239 return false; 240 } 241 return true; 242 } 243 244 void pcie_aer_root_set_vector(PCIDevice *dev, unsigned int vector) 245 { 246 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 247 assert(vector < PCI_ERR_ROOT_IRQ_MAX); 248 pci_long_test_and_clear_mask(aer_cap + PCI_ERR_ROOT_STATUS, 249 PCI_ERR_ROOT_IRQ); 250 pci_long_test_and_set_mask(aer_cap + PCI_ERR_ROOT_STATUS, 251 vector << PCI_ERR_ROOT_IRQ_SHIFT); 252 } 253 254 static unsigned int pcie_aer_root_get_vector(PCIDevice *dev) 255 { 256 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 257 uint32_t root_status = pci_get_long(aer_cap + PCI_ERR_ROOT_STATUS); 258 return (root_status & PCI_ERR_ROOT_IRQ) >> PCI_ERR_ROOT_IRQ_SHIFT; 259 } 260 261 /* Given a status register, get corresponding bits in the command register */ 262 static uint32_t pcie_aer_status_to_cmd(uint32_t status) 263 { 264 uint32_t cmd = 0; 265 if (status & PCI_ERR_ROOT_COR_RCV) { 266 cmd |= PCI_ERR_ROOT_CMD_COR_EN; 267 } 268 if (status & PCI_ERR_ROOT_NONFATAL_RCV) { 269 cmd |= PCI_ERR_ROOT_CMD_NONFATAL_EN; 270 } 271 if (status & PCI_ERR_ROOT_FATAL_RCV) { 272 cmd |= PCI_ERR_ROOT_CMD_FATAL_EN; 273 } 274 return cmd; 275 } 276 277 static void pcie_aer_root_notify(PCIDevice *dev) 278 { 279 if (msix_enabled(dev)) { 280 msix_notify(dev, pcie_aer_root_get_vector(dev)); 281 } else if (msi_enabled(dev)) { 282 msi_notify(dev, pcie_aer_root_get_vector(dev)); 283 } else if (pci_intx(dev) != -1) { 284 pci_irq_assert(dev); 285 } 286 } 287 288 /* 289 * 6.2.6 Error Message Control 290 * Figure 6-3 291 * root port part 292 */ 293 static void pcie_aer_msg_root_port(PCIDevice *dev, const PCIEAERMsg *msg) 294 { 295 uint16_t cmd; 296 uint8_t *aer_cap; 297 uint32_t root_cmd; 298 uint32_t root_status, prev_status; 299 300 cmd = pci_get_word(dev->config + PCI_COMMAND); 301 aer_cap = dev->config + dev->exp.aer_cap; 302 root_cmd = pci_get_long(aer_cap + PCI_ERR_ROOT_COMMAND); 303 prev_status = root_status = pci_get_long(aer_cap + PCI_ERR_ROOT_STATUS); 304 305 if (cmd & PCI_COMMAND_SERR) { 306 /* System Error. 307 * 308 * The way to report System Error is platform specific and 309 * it isn't implemented in qemu right now. 310 * So just discard the error for now. 311 * OS which cares of aer would receive errors via 312 * native aer mechanims, so this wouldn't matter. 313 */ 314 } 315 316 /* Error Message Received: Root Error Status register */ 317 switch (msg->severity) { 318 case PCI_ERR_ROOT_CMD_COR_EN: 319 if (root_status & PCI_ERR_ROOT_COR_RCV) { 320 root_status |= PCI_ERR_ROOT_MULTI_COR_RCV; 321 } else { 322 pci_set_word(aer_cap + PCI_ERR_ROOT_ERR_SRC + PCI_ERR_SRC_COR_OFFS, 323 msg->source_id); 324 } 325 root_status |= PCI_ERR_ROOT_COR_RCV; 326 break; 327 case PCI_ERR_ROOT_CMD_NONFATAL_EN: 328 root_status |= PCI_ERR_ROOT_NONFATAL_RCV; 329 break; 330 case PCI_ERR_ROOT_CMD_FATAL_EN: 331 if (!(root_status & PCI_ERR_ROOT_UNCOR_RCV)) { 332 root_status |= PCI_ERR_ROOT_FIRST_FATAL; 333 } 334 root_status |= PCI_ERR_ROOT_FATAL_RCV; 335 break; 336 default: 337 abort(); 338 break; 339 } 340 if (pcie_aer_msg_is_uncor(msg)) { 341 if (root_status & PCI_ERR_ROOT_UNCOR_RCV) { 342 root_status |= PCI_ERR_ROOT_MULTI_UNCOR_RCV; 343 } else { 344 pci_set_word(aer_cap + PCI_ERR_ROOT_ERR_SRC + 345 PCI_ERR_SRC_UNCOR_OFFS, msg->source_id); 346 } 347 root_status |= PCI_ERR_ROOT_UNCOR_RCV; 348 } 349 pci_set_long(aer_cap + PCI_ERR_ROOT_STATUS, root_status); 350 351 /* 6.2.4.1.2 Interrupt Generation */ 352 /* All the above did was set some bits in the status register. 353 * Specifically these that match message severity. 354 * The below code relies on this fact. */ 355 if (!(root_cmd & msg->severity) || 356 (pcie_aer_status_to_cmd(prev_status) & root_cmd)) { 357 /* Condition is not being set or was already true so nothing to do. */ 358 return; 359 } 360 361 pcie_aer_root_notify(dev); 362 } 363 364 /* 365 * 6.2.6 Error Message Control Figure 6-3 366 * 367 * Walk up the bus tree from the device, propagate the error message. 368 */ 369 static void pcie_aer_msg(PCIDevice *dev, const PCIEAERMsg *msg) 370 { 371 uint8_t type; 372 373 while (dev) { 374 if (!pci_is_express(dev)) { 375 /* just ignore it */ 376 /* TODO: Shouldn't we set PCI_STATUS_SIG_SYSTEM_ERROR? 377 * Consider e.g. a PCI bridge above a PCI Express device. */ 378 return; 379 } 380 381 type = pcie_cap_get_type(dev); 382 if ((type == PCI_EXP_TYPE_ROOT_PORT || 383 type == PCI_EXP_TYPE_UPSTREAM || 384 type == PCI_EXP_TYPE_DOWNSTREAM) && 385 !pcie_aer_msg_vbridge(dev, msg)) { 386 return; 387 } 388 if (!pcie_aer_msg_alldev(dev, msg)) { 389 return; 390 } 391 if (type == PCI_EXP_TYPE_ROOT_PORT) { 392 pcie_aer_msg_root_port(dev, msg); 393 /* Root port can notify system itself, 394 or send the error message to root complex event collector. */ 395 /* 396 * if root port is associated with an event collector, 397 * return the root complex event collector here. 398 * For now root complex event collector isn't supported. 399 */ 400 return; 401 } 402 dev = pci_bridge_get_device(pci_get_bus(dev)); 403 } 404 } 405 406 static void pcie_aer_update_log(PCIDevice *dev, const PCIEAERErr *err) 407 { 408 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 409 uint8_t first_bit = ctz32(err->status); 410 uint32_t errcap = pci_get_long(aer_cap + PCI_ERR_CAP); 411 int i; 412 413 assert(err->status); 414 assert(!(err->status & (err->status - 1))); 415 416 errcap &= ~(PCI_ERR_CAP_FEP_MASK | PCI_ERR_CAP_TLP); 417 errcap |= PCI_ERR_CAP_FEP(first_bit); 418 419 if (err->flags & PCIE_AER_ERR_HEADER_VALID) { 420 for (i = 0; i < ARRAY_SIZE(err->header); ++i) { 421 /* 7.10.8 Header Log Register */ 422 uint8_t *header_log = 423 aer_cap + PCI_ERR_HEADER_LOG + i * sizeof err->header[0]; 424 stl_be_p(header_log, err->header[i]); 425 } 426 } else { 427 assert(!(err->flags & PCIE_AER_ERR_TLP_PREFIX_PRESENT)); 428 memset(aer_cap + PCI_ERR_HEADER_LOG, 0, PCI_ERR_HEADER_LOG_SIZE); 429 } 430 431 if ((err->flags & PCIE_AER_ERR_TLP_PREFIX_PRESENT) && 432 (pci_get_long(dev->config + dev->exp.exp_cap + PCI_EXP_DEVCAP2) & 433 PCI_EXP_DEVCAP2_EETLPP)) { 434 for (i = 0; i < ARRAY_SIZE(err->prefix); ++i) { 435 /* 7.10.12 tlp prefix log register */ 436 uint8_t *prefix_log = 437 aer_cap + PCI_ERR_TLP_PREFIX_LOG + i * sizeof err->prefix[0]; 438 stl_be_p(prefix_log, err->prefix[i]); 439 } 440 errcap |= PCI_ERR_CAP_TLP; 441 } else { 442 memset(aer_cap + PCI_ERR_TLP_PREFIX_LOG, 0, 443 PCI_ERR_TLP_PREFIX_LOG_SIZE); 444 } 445 pci_set_long(aer_cap + PCI_ERR_CAP, errcap); 446 } 447 448 static void pcie_aer_clear_log(PCIDevice *dev) 449 { 450 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 451 452 pci_long_test_and_clear_mask(aer_cap + PCI_ERR_CAP, 453 PCI_ERR_CAP_FEP_MASK | PCI_ERR_CAP_TLP); 454 455 memset(aer_cap + PCI_ERR_HEADER_LOG, 0, PCI_ERR_HEADER_LOG_SIZE); 456 memset(aer_cap + PCI_ERR_TLP_PREFIX_LOG, 0, PCI_ERR_TLP_PREFIX_LOG_SIZE); 457 } 458 459 static void pcie_aer_clear_error(PCIDevice *dev) 460 { 461 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 462 uint32_t errcap = pci_get_long(aer_cap + PCI_ERR_CAP); 463 PCIEAERLog *aer_log = &dev->exp.aer_log; 464 PCIEAERErr err; 465 466 if (!(errcap & PCI_ERR_CAP_MHRE) || !aer_log->log_num) { 467 pcie_aer_clear_log(dev); 468 return; 469 } 470 471 /* 472 * If more errors are queued, set corresponding bits in uncorrectable 473 * error status. 474 * We emulate uncorrectable error status register as W1CS. 475 * So set bit in uncorrectable error status here again for multiple 476 * error recording support. 477 * 478 * 6.2.4.2 Multiple Error Handling(Advanced Error Reporting Capability) 479 */ 480 pcie_aer_update_uncor_status(dev); 481 482 aer_log_del_err(aer_log, &err); 483 pcie_aer_update_log(dev, &err); 484 } 485 486 static int pcie_aer_record_error(PCIDevice *dev, 487 const PCIEAERErr *err) 488 { 489 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 490 uint32_t errcap = pci_get_long(aer_cap + PCI_ERR_CAP); 491 int fep = PCI_ERR_CAP_FEP(errcap); 492 493 assert(err->status); 494 assert(!(err->status & (err->status - 1))); 495 496 if (errcap & PCI_ERR_CAP_MHRE && 497 (pci_get_long(aer_cap + PCI_ERR_UNCOR_STATUS) & (1U << fep))) { 498 /* Not first error. queue error */ 499 if (aer_log_add_err(&dev->exp.aer_log, err) < 0) { 500 /* overflow */ 501 return -1; 502 } 503 return 0; 504 } 505 506 pcie_aer_update_log(dev, err); 507 return 0; 508 } 509 510 typedef struct PCIEAERInject { 511 PCIDevice *dev; 512 uint8_t *aer_cap; 513 const PCIEAERErr *err; 514 uint16_t devctl; 515 uint16_t devsta; 516 uint32_t error_status; 517 bool unsupported_request; 518 bool log_overflow; 519 PCIEAERMsg msg; 520 } PCIEAERInject; 521 522 static bool pcie_aer_inject_cor_error(PCIEAERInject *inj, 523 uint32_t uncor_status, 524 bool is_advisory_nonfatal) 525 { 526 PCIDevice *dev = inj->dev; 527 528 inj->devsta |= PCI_EXP_DEVSTA_CED; 529 if (inj->unsupported_request) { 530 inj->devsta |= PCI_EXP_DEVSTA_URD; 531 } 532 pci_set_word(dev->config + dev->exp.exp_cap + PCI_EXP_DEVSTA, inj->devsta); 533 534 if (inj->aer_cap) { 535 uint32_t mask; 536 pci_long_test_and_set_mask(inj->aer_cap + PCI_ERR_COR_STATUS, 537 inj->error_status); 538 mask = pci_get_long(inj->aer_cap + PCI_ERR_COR_MASK); 539 if (mask & inj->error_status) { 540 return false; 541 } 542 if (is_advisory_nonfatal) { 543 uint32_t uncor_mask = 544 pci_get_long(inj->aer_cap + PCI_ERR_UNCOR_MASK); 545 if (!(uncor_mask & uncor_status)) { 546 inj->log_overflow = !!pcie_aer_record_error(dev, inj->err); 547 } 548 pci_long_test_and_set_mask(inj->aer_cap + PCI_ERR_UNCOR_STATUS, 549 uncor_status); 550 } 551 } 552 553 if (inj->unsupported_request && !(inj->devctl & PCI_EXP_DEVCTL_URRE)) { 554 return false; 555 } 556 if (!(inj->devctl & PCI_EXP_DEVCTL_CERE)) { 557 return false; 558 } 559 560 inj->msg.severity = PCI_ERR_ROOT_CMD_COR_EN; 561 return true; 562 } 563 564 static bool pcie_aer_inject_uncor_error(PCIEAERInject *inj, bool is_fatal) 565 { 566 PCIDevice *dev = inj->dev; 567 uint16_t cmd; 568 569 if (is_fatal) { 570 inj->devsta |= PCI_EXP_DEVSTA_FED; 571 } else { 572 inj->devsta |= PCI_EXP_DEVSTA_NFED; 573 } 574 if (inj->unsupported_request) { 575 inj->devsta |= PCI_EXP_DEVSTA_URD; 576 } 577 pci_set_long(dev->config + dev->exp.exp_cap + PCI_EXP_DEVSTA, inj->devsta); 578 579 if (inj->aer_cap) { 580 uint32_t mask = pci_get_long(inj->aer_cap + PCI_ERR_UNCOR_MASK); 581 if (mask & inj->error_status) { 582 pci_long_test_and_set_mask(inj->aer_cap + PCI_ERR_UNCOR_STATUS, 583 inj->error_status); 584 return false; 585 } 586 587 inj->log_overflow = !!pcie_aer_record_error(dev, inj->err); 588 pci_long_test_and_set_mask(inj->aer_cap + PCI_ERR_UNCOR_STATUS, 589 inj->error_status); 590 } 591 592 cmd = pci_get_word(dev->config + PCI_COMMAND); 593 if (inj->unsupported_request && 594 !(inj->devctl & PCI_EXP_DEVCTL_URRE) && !(cmd & PCI_COMMAND_SERR)) { 595 return false; 596 } 597 if (is_fatal) { 598 if (!((cmd & PCI_COMMAND_SERR) || 599 (inj->devctl & PCI_EXP_DEVCTL_FERE))) { 600 return false; 601 } 602 inj->msg.severity = PCI_ERR_ROOT_CMD_FATAL_EN; 603 } else { 604 if (!((cmd & PCI_COMMAND_SERR) || 605 (inj->devctl & PCI_EXP_DEVCTL_NFERE))) { 606 return false; 607 } 608 inj->msg.severity = PCI_ERR_ROOT_CMD_NONFATAL_EN; 609 } 610 return true; 611 } 612 613 /* 614 * non-Function specific error must be recorded in all functions. 615 * It is the responsibility of the caller of this function. 616 * It is also caller's responsibility to determine which function should 617 * report the error. 618 * 619 * 6.2.4 Error Logging 620 * 6.2.5 Sequence of Device Error Signaling and Logging Operations 621 * Figure 6-2: Flowchart Showing Sequence of Device Error Signaling and Logging 622 * Operations 623 */ 624 int pcie_aer_inject_error(PCIDevice *dev, const PCIEAERErr *err) 625 { 626 uint8_t *aer_cap = NULL; 627 uint16_t devctl = 0; 628 uint16_t devsta = 0; 629 uint32_t error_status = err->status; 630 PCIEAERInject inj; 631 632 if (!pci_is_express(dev)) { 633 return -ENOSYS; 634 } 635 636 if (err->flags & PCIE_AER_ERR_IS_CORRECTABLE) { 637 error_status &= PCI_ERR_COR_SUPPORTED; 638 } else { 639 error_status &= PCI_ERR_UNC_SUPPORTED; 640 } 641 642 /* invalid status bit. one and only one bit must be set */ 643 if (!error_status || (error_status & (error_status - 1))) { 644 return -EINVAL; 645 } 646 647 if (dev->exp.aer_cap) { 648 uint8_t *exp_cap = dev->config + dev->exp.exp_cap; 649 aer_cap = dev->config + dev->exp.aer_cap; 650 devctl = pci_get_long(exp_cap + PCI_EXP_DEVCTL); 651 devsta = pci_get_long(exp_cap + PCI_EXP_DEVSTA); 652 } 653 654 inj.dev = dev; 655 inj.aer_cap = aer_cap; 656 inj.err = err; 657 inj.devctl = devctl; 658 inj.devsta = devsta; 659 inj.error_status = error_status; 660 inj.unsupported_request = !(err->flags & PCIE_AER_ERR_IS_CORRECTABLE) && 661 err->status == PCI_ERR_UNC_UNSUP; 662 inj.log_overflow = false; 663 664 if (err->flags & PCIE_AER_ERR_IS_CORRECTABLE) { 665 if (!pcie_aer_inject_cor_error(&inj, 0, false)) { 666 return 0; 667 } 668 } else { 669 bool is_fatal = 670 pcie_aer_uncor_default_severity(error_status) == 671 PCI_ERR_ROOT_CMD_FATAL_EN; 672 if (aer_cap) { 673 is_fatal = 674 error_status & pci_get_long(aer_cap + PCI_ERR_UNCOR_SEVER); 675 } 676 if (!is_fatal && (err->flags & PCIE_AER_ERR_MAYBE_ADVISORY)) { 677 inj.error_status = PCI_ERR_COR_ADV_NONFATAL; 678 if (!pcie_aer_inject_cor_error(&inj, error_status, true)) { 679 return 0; 680 } 681 } else { 682 if (!pcie_aer_inject_uncor_error(&inj, is_fatal)) { 683 return 0; 684 } 685 } 686 } 687 688 /* send up error message */ 689 inj.msg.source_id = err->source_id; 690 pcie_aer_msg(dev, &inj.msg); 691 692 if (inj.log_overflow) { 693 PCIEAERErr header_log_overflow = { 694 .status = PCI_ERR_COR_HL_OVERFLOW, 695 .flags = PCIE_AER_ERR_IS_CORRECTABLE, 696 }; 697 int ret = pcie_aer_inject_error(dev, &header_log_overflow); 698 assert(!ret); 699 } 700 return 0; 701 } 702 703 void pcie_aer_write_config(PCIDevice *dev, 704 uint32_t addr, uint32_t val, int len) 705 { 706 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 707 uint32_t errcap = pci_get_long(aer_cap + PCI_ERR_CAP); 708 uint32_t first_error = 1U << PCI_ERR_CAP_FEP(errcap); 709 uint32_t uncorsta = pci_get_long(aer_cap + PCI_ERR_UNCOR_STATUS); 710 711 /* uncorrectable error */ 712 if (!(uncorsta & first_error)) { 713 /* the bit that corresponds to the first error is cleared */ 714 pcie_aer_clear_error(dev); 715 } else if (errcap & PCI_ERR_CAP_MHRE) { 716 /* When PCI_ERR_CAP_MHRE is enabled and the first error isn't cleared 717 * nothing should happen. So we have to revert the modification to 718 * the register. 719 */ 720 pcie_aer_update_uncor_status(dev); 721 } else { 722 /* capability & control 723 * PCI_ERR_CAP_MHRE might be cleared, so clear of header log. 724 */ 725 aer_log_clear_all_err(&dev->exp.aer_log); 726 } 727 } 728 729 void pcie_aer_root_init(PCIDevice *dev) 730 { 731 uint16_t pos = dev->exp.aer_cap; 732 733 pci_set_long(dev->wmask + pos + PCI_ERR_ROOT_COMMAND, 734 PCI_ERR_ROOT_CMD_EN_MASK); 735 pci_set_long(dev->w1cmask + pos + PCI_ERR_ROOT_STATUS, 736 PCI_ERR_ROOT_STATUS_REPORT_MASK); 737 /* PCI_ERR_ROOT_IRQ is RO but devices change it using a 738 * device-specific method. 739 */ 740 pci_set_long(dev->cmask + pos + PCI_ERR_ROOT_STATUS, 741 ~PCI_ERR_ROOT_IRQ); 742 } 743 744 void pcie_aer_root_reset(PCIDevice *dev) 745 { 746 uint8_t* aer_cap = dev->config + dev->exp.aer_cap; 747 748 pci_set_long(aer_cap + PCI_ERR_ROOT_COMMAND, 0); 749 750 /* 751 * Advanced Error Interrupt Message Number in Root Error Status Register 752 * must be updated by chip dependent code because it's chip dependent 753 * which number is used. 754 */ 755 } 756 757 void pcie_aer_root_write_config(PCIDevice *dev, 758 uint32_t addr, uint32_t val, int len, 759 uint32_t root_cmd_prev) 760 { 761 uint8_t *aer_cap = dev->config + dev->exp.aer_cap; 762 uint32_t root_status = pci_get_long(aer_cap + PCI_ERR_ROOT_STATUS); 763 uint32_t enabled_cmd = pcie_aer_status_to_cmd(root_status); 764 uint32_t root_cmd = pci_get_long(aer_cap + PCI_ERR_ROOT_COMMAND); 765 /* 6.2.4.1.2 Interrupt Generation */ 766 if (!msix_enabled(dev) && !msi_enabled(dev)) { 767 if (pci_intx(dev) != -1) { 768 pci_set_irq(dev, !!(root_cmd & enabled_cmd)); 769 } 770 return; 771 } 772 773 if ((root_cmd_prev & enabled_cmd) || !(root_cmd & enabled_cmd)) { 774 /* Send MSI on transition from false to true. */ 775 return; 776 } 777 778 pcie_aer_root_notify(dev); 779 } 780 781 static const VMStateDescription vmstate_pcie_aer_err = { 782 .name = "PCIE_AER_ERROR", 783 .version_id = 1, 784 .minimum_version_id = 1, 785 .fields = (VMStateField[]) { 786 VMSTATE_UINT32(status, PCIEAERErr), 787 VMSTATE_UINT16(source_id, PCIEAERErr), 788 VMSTATE_UINT16(flags, PCIEAERErr), 789 VMSTATE_UINT32_ARRAY(header, PCIEAERErr, 4), 790 VMSTATE_UINT32_ARRAY(prefix, PCIEAERErr, 4), 791 VMSTATE_END_OF_LIST() 792 } 793 }; 794 795 static bool pcie_aer_state_log_num_valid(void *opaque, int version_id) 796 { 797 PCIEAERLog *s = opaque; 798 799 return s->log_num <= s->log_max; 800 } 801 802 const VMStateDescription vmstate_pcie_aer_log = { 803 .name = "PCIE_AER_ERROR_LOG", 804 .version_id = 1, 805 .minimum_version_id = 1, 806 .fields = (VMStateField[]) { 807 VMSTATE_UINT16(log_num, PCIEAERLog), 808 VMSTATE_UINT16_EQUAL(log_max, PCIEAERLog, NULL), 809 VMSTATE_VALIDATE("log_num <= log_max", pcie_aer_state_log_num_valid), 810 VMSTATE_STRUCT_VARRAY_POINTER_UINT16(log, PCIEAERLog, log_num, 811 vmstate_pcie_aer_err, PCIEAERErr), 812 VMSTATE_END_OF_LIST() 813 } 814 }; 815 816 typedef struct PCIEAERErrorName { 817 const char *name; 818 uint32_t val; 819 bool correctable; 820 } PCIEAERErrorName; 821 822 /* 823 * AER error name -> value conversion table 824 * This naming scheme is same to linux aer-injection tool. 825 */ 826 static const struct PCIEAERErrorName pcie_aer_error_list[] = { 827 { 828 .name = "DLP", 829 .val = PCI_ERR_UNC_DLP, 830 .correctable = false, 831 }, { 832 .name = "SDN", 833 .val = PCI_ERR_UNC_SDN, 834 .correctable = false, 835 }, { 836 .name = "POISON_TLP", 837 .val = PCI_ERR_UNC_POISON_TLP, 838 .correctable = false, 839 }, { 840 .name = "FCP", 841 .val = PCI_ERR_UNC_FCP, 842 .correctable = false, 843 }, { 844 .name = "COMP_TIME", 845 .val = PCI_ERR_UNC_COMP_TIME, 846 .correctable = false, 847 }, { 848 .name = "COMP_ABORT", 849 .val = PCI_ERR_UNC_COMP_ABORT, 850 .correctable = false, 851 }, { 852 .name = "UNX_COMP", 853 .val = PCI_ERR_UNC_UNX_COMP, 854 .correctable = false, 855 }, { 856 .name = "RX_OVER", 857 .val = PCI_ERR_UNC_RX_OVER, 858 .correctable = false, 859 }, { 860 .name = "MALF_TLP", 861 .val = PCI_ERR_UNC_MALF_TLP, 862 .correctable = false, 863 }, { 864 .name = "ECRC", 865 .val = PCI_ERR_UNC_ECRC, 866 .correctable = false, 867 }, { 868 .name = "UNSUP", 869 .val = PCI_ERR_UNC_UNSUP, 870 .correctable = false, 871 }, { 872 .name = "ACSV", 873 .val = PCI_ERR_UNC_ACSV, 874 .correctable = false, 875 }, { 876 .name = "INTN", 877 .val = PCI_ERR_UNC_INTN, 878 .correctable = false, 879 }, { 880 .name = "MCBTLP", 881 .val = PCI_ERR_UNC_MCBTLP, 882 .correctable = false, 883 }, { 884 .name = "ATOP_EBLOCKED", 885 .val = PCI_ERR_UNC_ATOP_EBLOCKED, 886 .correctable = false, 887 }, { 888 .name = "TLP_PRF_BLOCKED", 889 .val = PCI_ERR_UNC_TLP_PRF_BLOCKED, 890 .correctable = false, 891 }, { 892 .name = "RCVR", 893 .val = PCI_ERR_COR_RCVR, 894 .correctable = true, 895 }, { 896 .name = "BAD_TLP", 897 .val = PCI_ERR_COR_BAD_TLP, 898 .correctable = true, 899 }, { 900 .name = "BAD_DLLP", 901 .val = PCI_ERR_COR_BAD_DLLP, 902 .correctable = true, 903 }, { 904 .name = "REP_ROLL", 905 .val = PCI_ERR_COR_REP_ROLL, 906 .correctable = true, 907 }, { 908 .name = "REP_TIMER", 909 .val = PCI_ERR_COR_REP_TIMER, 910 .correctable = true, 911 }, { 912 .name = "ADV_NONFATAL", 913 .val = PCI_ERR_COR_ADV_NONFATAL, 914 .correctable = true, 915 }, { 916 .name = "INTERNAL", 917 .val = PCI_ERR_COR_INTERNAL, 918 .correctable = true, 919 }, { 920 .name = "HL_OVERFLOW", 921 .val = PCI_ERR_COR_HL_OVERFLOW, 922 .correctable = true, 923 }, 924 }; 925 926 int pcie_aer_parse_error_string(const char *error_name, 927 uint32_t *status, bool *correctable) 928 { 929 int i; 930 931 for (i = 0; i < ARRAY_SIZE(pcie_aer_error_list); i++) { 932 const PCIEAERErrorName *e = &pcie_aer_error_list[i]; 933 if (strcmp(error_name, e->name)) { 934 continue; 935 } 936 937 *status = e->val; 938 *correctable = e->correctable; 939 return 0; 940 } 941 return -EINVAL; 942 } 943