Changeset 65283 in vbox
- Timestamp:
- Jan 13, 2017 2:25:05 PM (8 years ago)
- svn:sync-xref-src-repo-rev:
- 112848
- Location:
- trunk/src/VBox/Devices/Bus
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Bus/DevPCI.cpp
r65101 r65283 1037 1037 1038 1038 /* commit the loaded device config. */ 1039 devpciR3CommonRestoreConfig(pDev, &DevTmp.abConfig[0] , false ); /** @todo fix bridge fun! */1039 devpciR3CommonRestoreConfig(pDev, &DevTmp.abConfig[0]); 1040 1040 1041 1041 pDev->Int.s.uIrqPinState = DevTmp.Int.s.uIrqPinState; -
trunk/src/VBox/Devices/Bus/DevPciIch9.cpp
r65101 r65283 9 9 * For the time being the DevPciMerge1.cpp.h file will remain separate, 10 10 * due to 5.1. We can merge it into this one later in the dev cycle. 11 * 12 * DO NOT use the PDMPciDev* or PCIDev* family of functions in this 13 * file except in the two callbacks for config space access (and the 14 * functions which are used exclusively by that code) and the two 15 * device constructors when setting up the config space for the 16 * bridges. Everything else need extremely careful review. Using 17 * them elsewhere (especially in the init code) causes weird failures 18 * with PCI passthrough, as it would only update the array of 19 * (emulated) config space, but not talk to the actual device (needs 20 * invoking the respective callback). 11 21 */ 12 22 13 23 /* 14 * Copyright (C) 2010-201 6Oracle Corporation24 * Copyright (C) 2010-2017 Oracle Corporation 15 25 * 16 26 * This file is part of VirtualBox Open Source Edition (OSE), as … … 229 239 if (pPciRoot->PciBus.cBridges) 230 240 { 231 #ifdef IN_RING3 /** @todo do lookup in R0/RC too! */241 #ifdef IN_RING3 /** @todo do lookup in R0/RC too! r=klaus don't think that it can work, since the config space access callback only works in R3 */ 232 242 PPDMPCIDEV pBridgeDevice = ich9pciFindBridge(&pPciRoot->PciBus, pAddr->iBus); 233 243 if (pBridgeDevice) … … 342 352 if (pPciRoot->PciBus.cBridges) 343 353 { 344 #ifdef IN_RING3 /** @todo do lookup in R0/RC too! */354 #ifdef IN_RING3 /** @todo do lookup in R0/RC too! r=klaus don't think that it can work, since the config space access callback only works in R3 */ 345 355 PPDMPCIDEV pBridgeDevice = ich9pciFindBridge(&pPciRoot->PciBus, pPciAddr->iBus); 346 356 if (pBridgeDevice) … … 544 554 } 545 555 546 PDEVPCIBUS pBus = &pPciRoot->PciBus; 547 const bool fIsAcpiDevice = PCIDevGetDeviceId(pPciDev) == 0x7113; 556 PDEVPCIBUS pBus = &pPciRoot->PciBus; 557 /* safe, only needs to go to the config space array */ 558 const bool fIsAcpiDevice = PDMPciDevGetDeviceId(pPciDev) == 0x7113; 548 559 549 560 LogFlowFunc(("PCI Dev %p : IRQ\n", pPciDev)); … … 562 573 * PCI device configuration space). 563 574 */ 564 ich9pciApicSetIrq(pBus, uDevFn, pPciDev, -1, iLevel, uTagSrc, PCIDevGetInterruptLine(pPciDev)); 575 /* safe, only needs to go to the config space array */ 576 ich9pciApicSetIrq(pBus, uDevFn, pPciDev, -1, iLevel, uTagSrc, PDMPciDevGetInterruptLine(pPciDev)); 565 577 else 566 578 ich9pciApicSetIrq(pBus, uDevFn, pPciDev, iIrq, iLevel, uTagSrc, -1); … … 699 711 AssertMsg(pBridge && pciDevIsPci2PciBridge(pBridge), 700 712 ("Device is not a PCI bridge but on the list of PCI bridges\n")); 713 /* safe, only needs to go to the config space array */ 701 714 uint32_t uSecondary = PDMPciDevGetByte(pBridge, VBOX_PCI_SECONDARY_BUS); 715 /* safe, only needs to go to the config space array */ 702 716 uint32_t uSubordinate = PDMPciDevGetByte(pBridge, VBOX_PCI_SUBORDINATE_BUS); 703 717 Log3(("ich9pciFindBridge on bus %p, bridge %d: %d in %d..%d\n", pBus, iBridge, uBus, uSecondary, uSubordinate)); … … 715 729 } 716 730 717 static uint8_tich9pciGetByte(PPDMPCIDEV pPciDev, int32_t iRegister)731 DECLINLINE(uint8_t) ich9pciGetByte(PPDMPCIDEV pPciDev, int32_t iRegister) 718 732 { 719 733 return (uint8_t)ich9pciGetCfg(pPciDev, iRegister, 1); 720 734 } 721 735 722 static uint16_tich9pciGetWord(PPDMPCIDEV pPciDev, int32_t iRegister)736 DECLINLINE(uint16_t) ich9pciGetWord(PPDMPCIDEV pPciDev, int32_t iRegister) 723 737 { 724 738 return (uint16_t)ich9pciGetCfg(pPciDev, iRegister, 2); 725 739 } 726 740 727 static uint32_tich9pciGetDWord(PPDMPCIDEV pPciDev, int32_t iRegister)741 DECLINLINE(uint32_t) ich9pciGetDWord(PPDMPCIDEV pPciDev, int32_t iRegister) 728 742 { 729 743 return (uint32_t)ich9pciGetCfg(pPciDev, iRegister, 4); … … 734 748 return iRegion == VBOX_PCI_ROM_SLOT 735 749 ? VBOX_PCI_ROM_ADDRESS : (VBOX_PCI_BASE_ADDRESS_0 + iRegion * 4); 750 } 751 752 static void ich9pciSetCfg(PPDMPCIDEV pPciDev, int32_t iRegister, uint32_t u32, int cb) 753 { 754 pPciDev->Int.s.pfnConfigWrite(pPciDev->Int.s.CTX_SUFF(pDevIns), pPciDev, iRegister, u32, cb); 755 } 756 757 DECLINLINE(void) ich9pciSetByte(PPDMPCIDEV pPciDev, int32_t iRegister, uint8_t u8) 758 { 759 ich9pciSetCfg(pPciDev, iRegister, u8, 1); 760 } 761 762 DECLINLINE(void) ich9pciSetWord(PPDMPCIDEV pPciDev, int32_t iRegister, uint16_t u16) 763 { 764 ich9pciSetCfg(pPciDev, iRegister, u16, 2); 765 } 766 767 DECLINLINE(void) ich9pciSetDWord(PPDMPCIDEV pPciDev, int32_t iRegister, uint32_t u32) 768 { 769 ich9pciSetCfg(pPciDev, iRegister, u32, 4); 736 770 } 737 771 … … 816 850 AssertCompile(PCI_ADDRESS_SPACE_MEM_PREFETCH == RT_BIT_32(3)); 817 851 uint32_t u32Value = (uint32_t)enmType & (PCI_ADDRESS_SPACE_IO | PCI_ADDRESS_SPACE_BAR64 | PCI_ADDRESS_SPACE_MEM_PREFETCH); 818 PCIDevSetDWord(pPciDev, ich9pciGetRegionReg(iRegion), u32Value); 852 /* safe, only needs to go to the config space array */ 853 PDMPciDevSetDWord(pPciDev, ich9pciGetRegionReg(iRegion), u32Value); 819 854 820 855 return VINF_SUCCESS; … … 929 964 930 965 /* If the current bus is not the target bus search for the bus which contains the device. */ 966 /* safe, only needs to go to the config space array */ 931 967 if (uBus != PDMPciDevGetByte(&pBus->PciDev, VBOX_PCI_SECONDARY_BUS)) 932 968 { … … 959 995 960 996 /* If the current bus is not the target bus search for the bus which contains the device. */ 997 /* safe, only needs to go to the config space array */ 961 998 if (uBus != PDMPciDevGetByte(&pBus->PciDev, VBOX_PCI_SECONDARY_BUS)) 962 999 { … … 997 1034 * @param pDev The PCI device. 998 1035 * @param pbSrcConfig The configuration register values to be loaded. 999 * @param fIsBridge Whether this is a bridge device or not. 1000 */ 1001 void devpciR3CommonRestoreConfig(PPDMPCIDEV pDev, uint8_t const *pbSrcConfig, bool fIsBridge) 1036 */ 1037 void devpciR3CommonRestoreConfig(PPDMPCIDEV pDev, uint8_t const *pbSrcConfig) 1002 1038 { 1003 1039 /* … … 1029 1065 { 0x14, 4, 1, 3, "BASE_ADDRESS_1" }, 1030 1066 { 0x18, 4, 1, 1, "BASE_ADDRESS_2" }, 1031 { 0x18, 1, 1, 2, "PRIMARY_BUS" }, // fWritable = ??1032 { 0x19, 1, 1, 2, "SECONDARY_BUS" }, // fWritable = ??1033 { 0x1a, 1, 1, 2, "SUBORDINATE_BUS" }, // fWritable = ??1034 { 0x1b, 1, 1, 2, "SEC_LATENCY_TIMER" }, // fWritable = ??1067 { 0x18, 1, 1, 2, "PRIMARY_BUS" }, 1068 { 0x19, 1, 1, 2, "SECONDARY_BUS" }, 1069 { 0x1a, 1, 1, 2, "SUBORDINATE_BUS" }, 1070 { 0x1b, 1, 1, 2, "SEC_LATENCY_TIMER" }, 1035 1071 { 0x1c, 4, 1, 1, "BASE_ADDRESS_3" }, 1036 { 0x1c, 1, 1, 2, "IO_BASE" }, // fWritable = ??1037 { 0x1d, 1, 1, 2, "IO_LIMIT" }, // fWritable = ??1038 { 0x1e, 2, 1, 2, "SEC_STATUS" }, // fWritable = ??1072 { 0x1c, 1, 1, 2, "IO_BASE" }, 1073 { 0x1d, 1, 1, 2, "IO_LIMIT" }, 1074 { 0x1e, 2, 1, 2, "SEC_STATUS" }, 1039 1075 { 0x20, 4, 1, 1, "BASE_ADDRESS_4" }, 1040 { 0x20, 2, 1, 2, "MEMORY_BASE" }, // fWritable = ??1041 { 0x22, 2, 1, 2, "MEMORY_LIMIT" }, // fWritable = ??1076 { 0x20, 2, 1, 2, "MEMORY_BASE" }, 1077 { 0x22, 2, 1, 2, "MEMORY_LIMIT" }, 1042 1078 { 0x24, 4, 1, 1, "BASE_ADDRESS_5" }, 1043 { 0x24, 2, 1, 2, "PREF_MEMORY_BASE" }, // fWritable = ??1044 { 0x26, 2, 1, 2, "PREF_MEMORY_LIMIT" }, // fWritable = ??1045 { 0x28, 4, 1, 1, "CARDBUS_CIS" }, // fWritable = ??1046 { 0x28, 4, 1, 2, "PREF_BASE_UPPER32" }, // fWritable = ??1047 { 0x2c, 2, 0, 1, "SUBSYSTEM_VENDOR_ID" }, // fWritable = !?1048 { 0x2c, 4, 1, 2, "PREF_LIMIT_UPPER32" }, // fWritable = ??1049 { 0x2e, 2, 0, 1, "SUBSYSTEM_ID" }, // fWritable = !?1050 { 0x30, 4, 1, 1, "ROM_ADDRESS" }, // fWritable = ?!1051 { 0x30, 2, 1, 2, "IO_BASE_UPPER16" }, // fWritable = ?!1052 { 0x32, 2, 1, 2, "IO_LIMIT_UPPER16" }, // fWritable = ?!1053 { 0x34, 4, 0, 3, "CAPABILITY_LIST" }, // fWritable = !? cb=!?1054 { 0x38, 4, 1, 1, "RESERVED_38" }, // ???1055 { 0x38, 4, 1, 2, "ROM_ADDRESS_BR" }, // fWritable = !? cb=!? fBridge=!?1056 { 0x3c, 1, 1, 3, "INTERRUPT_LINE" }, // fBridge=??1057 { 0x3d, 1, 0, 3, "INTERRUPT_PIN" }, // fBridge=??1079 { 0x24, 2, 1, 2, "PREF_MEMORY_BASE" }, 1080 { 0x26, 2, 1, 2, "PREF_MEMORY_LIMIT" }, 1081 { 0x28, 4, 0, 1, "CARDBUS_CIS" }, 1082 { 0x28, 4, 1, 2, "PREF_BASE_UPPER32" }, 1083 { 0x2c, 2, 0, 1, "SUBSYSTEM_VENDOR_ID" }, 1084 { 0x2c, 4, 1, 2, "PREF_LIMIT_UPPER32" }, 1085 { 0x2e, 2, 0, 1, "SUBSYSTEM_ID" }, 1086 { 0x30, 4, 1, 1, "ROM_ADDRESS" }, 1087 { 0x30, 2, 1, 2, "IO_BASE_UPPER16" }, 1088 { 0x32, 2, 1, 2, "IO_LIMIT_UPPER16" }, 1089 { 0x34, 4, 0, 3, "CAPABILITY_LIST" }, 1090 { 0x38, 4, 1, 1, "RESERVED_38" }, 1091 { 0x38, 4, 1, 2, "ROM_ADDRESS_BR" }, 1092 { 0x3c, 1, 1, 3, "INTERRUPT_LINE" }, 1093 { 0x3d, 1, 0, 3, "INTERRUPT_PIN" }, 1058 1094 { 0x3e, 1, 0, 1, "MIN_GNT" }, 1059 { 0x3e, 2, 1, 2, "BRIDGE_CONTROL" }, // fWritable = !?1095 { 0x3e, 2, 1, 2, "BRIDGE_CONTROL" }, 1060 1096 { 0x3f, 1, 0, 1, "MAX_LAT" }, 1061 1097 /* The COMMAND register must come last as it requires the *ADDRESS* … … 1095 1131 * Loop thru the fields covering the 64 bytes of standard registers. 1096 1132 */ 1097 uint8_t const fBridge = fIsBridge? 2 : 1;1133 uint8_t const fBridge = pciDevIsPci2PciBridge(pDev) ? 2 : 1; 1098 1134 Assert(!pciDevIsPassthrough(pDev)); 1099 1135 uint8_t *pbDstConfig = &pDev->abConfig[0]; … … 1138 1174 } 1139 1175 if (off == VBOX_PCI_COMMAND) 1140 PCIDevSetCommand(pDev, 0); /* For remapping, see ich9pciR3CommonLoadExec. */ 1176 /* safe, only needs to go to the config space array */ 1177 PDMPciDevSetCommand(pDev, 0); /* For remapping, see ich9pciR3CommonLoadExec. */ 1141 1178 pDev->Int.s.pfnConfigWrite(pDev->Int.s.CTX_SUFF(pDevIns), pDev, off, u32Src, cb); 1142 1179 } … … 1191 1228 if (pDev) 1192 1229 { 1193 uint16_t u16 = PCIDevGetCommand(pDev); 1230 /* safe, only needs to go to the config space array */ 1231 uint16_t u16 = PDMPciDevGetCommand(pDev); 1194 1232 pDev->Int.s.pfnConfigWrite(pDev->Int.s.CTX_SUFF(pDevIns), pDev, VBOX_PCI_COMMAND, 0, 2); 1195 PCIDevSetCommand(pDev, u16); 1196 Assert(PCIDevGetCommand(pDev) == u16); 1233 /* safe, only needs to go to the config space array */ 1234 PDMPciDevSetCommand(pDev, u16); 1235 /* safe, only needs to go to the config space array */ 1236 Assert(PDMPciDevGetCommand(pDev) == u16); 1197 1237 } 1198 1238 } … … 1223 1263 if (pDev) 1224 1264 { 1265 /* safe, only needs to go to the config space array */ 1225 1266 LogRel(("PCI: New device in slot %#x, %s (vendor=%#06x device=%#06x)\n", i, pDev->pszNameR3, 1226 P CIDevGetVendorId(pDev), PCIDevGetDeviceId(pDev)));1267 PDMPciDevGetVendorId(pDev), PDMPciDevGetDeviceId(pDev))); 1227 1268 if (SSMR3HandleGetAfter(pSSM) != SSMAFTER_DEBUG_IT) 1228 1269 { 1270 /* safe, only needs to go to the config space array */ 1229 1271 rc = SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("New device in slot %#x, %s (vendor=%#06x device=%#06x)"), 1230 i, pDev->pszNameR3, P CIDevGetVendorId(pDev), PCIDevGetDeviceId(pDev));1272 i, pDev->pszNameR3, PDMPciDevGetVendorId(pDev), PDMPciDevGetDeviceId(pDev)); 1231 1273 break; 1232 1274 } … … 1267 1309 if (!pDev) 1268 1310 { 1311 /* safe, only needs to go to the config space array */ 1269 1312 LogRel(("PCI: Device in slot %#x has been removed! vendor=%#06x device=%#06x\n", i, 1270 P CIDevGetVendorId(&DevTmp), PCIDevGetDeviceId(&DevTmp)));1313 PDMPciDevGetVendorId(&DevTmp), PDMPciDevGetDeviceId(&DevTmp))); 1271 1314 if (SSMR3HandleGetAfter(pSSM) != SSMAFTER_DEBUG_IT) 1272 1315 { 1316 /* safe, only needs to go to the config space array */ 1273 1317 rc = SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("Device in slot %#x has been removed! vendor=%#06x device=%#06x"), 1274 i, P CIDevGetVendorId(&DevTmp), PCIDevGetDeviceId(&DevTmp));1318 i, PDMPciDevGetVendorId(&DevTmp), PDMPciDevGetDeviceId(&DevTmp)); 1275 1319 break; 1276 1320 } … … 1279 1323 1280 1324 /* match the vendor id assuming that this will never be changed. */ 1281 if (PCIDevGetVendorId(&DevTmp) != PCIDevGetVendorId(pDev)) 1282 { 1325 /* safe, only needs to go to the config space array */ 1326 if (PDMPciDevGetVendorId(&DevTmp) != PDMPciDevGetVendorId(pDev)) 1327 { 1328 /* safe, only needs to go to the config space array */ 1283 1329 rc = SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("Device in slot %#x (%s) vendor id mismatch! saved=%.4Rhxs current=%.4Rhxs"), 1284 i, pDev->pszNameR3, P CIDevGetVendorId(&DevTmp), PCIDevGetVendorId(pDev));1330 i, pDev->pszNameR3, PDMPciDevGetVendorId(&DevTmp), PDMPciDevGetVendorId(pDev)); 1285 1331 break; 1286 1332 } … … 1288 1334 /* commit the loaded device config. */ 1289 1335 Assert(!pciDevIsPassthrough(pDev)); 1290 devpciR3CommonRestoreConfig(pDev, &DevTmp.abConfig[0] , false ); /** @todo fix bridge fun! */1336 devpciR3CommonRestoreConfig(pDev, &DevTmp.abConfig[0]); 1291 1337 1292 1338 pDev->Int.s.uIrqPinState = DevTmp.Int.s.uIrqPinState; … … 1355 1401 1356 1402 /* 1357 * Perform im eediate read of configuration space register.1403 * Perform immediate read of configuration space register. 1358 1404 * Cannot be rescheduled, as already in R3. 1359 1405 */ … … 1441 1487 1442 1488 /* 1443 * Set I/O limit register. If there is no device with I/O space behind the bridge 1444 * we set a lower value than in the base register. 1445 * The result with a real bridge is that no I/O transactions are passed to the secondary 1446 * interface. Again this doesn't really matter here but we want to be compliant to the spec. 1489 * Set I/O limit register. If there is no device with I/O space behind the 1490 * bridge we set a lower value than in the base register. 1447 1491 */ 1448 if ( (u32IoAddressBase != pPciRoot->uPciBiosIo) && ((pPciRoot->uPciBiosIo % 4096) != 0))1449 { 1450 /* The upper boundary must be one byte less thana 4KB boundary. */1492 if (u32IoAddressBase != pPciRoot->uPciBiosIo) 1493 { 1494 /* Need again alignment to a 4KB boundary. */ 1451 1495 pPciRoot->uPciBiosIo = RT_ALIGN_32(pPciRoot->uPciBiosIo, 4*1024); 1452 } 1453 1454 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_IO_LIMIT, ((pPciRoot->uPciBiosIo >> 8) & 0xf0) - 1, 1); 1496 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_IO_LIMIT, ((pPciRoot->uPciBiosIo >> 8) & 0xf0) - 1, 1); 1497 } 1498 else 1499 { 1500 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_IO_BASE, 0xf0, 1); 1501 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_IO_LIMIT, 0x00, 1); 1502 } 1455 1503 1456 1504 /* Same with the MMIO limit register but with 1MB boundary here. */ 1457 if ((u32MMIOAddressBase != pPciRoot->uPciBiosMmio) && ((pPciRoot->uPciBiosMmio % (1024 * 1024)) != 0)) 1458 { 1459 /* The upper boundary must be one byte less than a 1MB boundary. */ 1505 if (u32MMIOAddressBase != pPciRoot->uPciBiosMmio) 1506 { 1460 1507 pPciRoot->uPciBiosMmio = RT_ALIGN_32(pPciRoot->uPciBiosMmio, 1024*1024); 1461 } 1462 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_MEMORY_LIMIT, ((pPciRoot->uPciBiosMmio >> 16) & UINT32_C(0xfff0)) - 1, 2); 1508 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_MEMORY_LIMIT, ((pPciRoot->uPciBiosMmio >> 16) & UINT32_C(0xfff0)) - 1, 2); 1509 } 1510 else 1511 { 1512 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_MEMORY_BASE, 0xfff0, 2); 1513 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_MEMORY_LIMIT, 0x0000, 2); 1514 } 1463 1515 1464 1516 /* … … 1496 1548 bool f64Bit = (u8ResourceType & ((uint8_t)(PCI_ADDRESS_SPACE_BAR64 | PCI_ADDRESS_SPACE_IO))) 1497 1549 == PCI_ADDRESS_SPACE_BAR64; 1498 bool fIsPio = ((u8ResourceType & PCI_ COMMAND_IOACCESS) == PCI_COMMAND_IOACCESS);1550 bool fIsPio = ((u8ResourceType & PCI_ADDRESS_SPACE_IO) == PCI_ADDRESS_SPACE_IO); 1499 1551 uint64_t cbRegSize64 = 0; 1500 1552 … … 1510 1562 /* No 64-bit PIO regions possible. */ 1511 1563 #ifndef DEBUG_bird /* EFI triggers this for DevAHCI. */ 1512 AssertMsg((u8ResourceType & PCI_ COMMAND_IOACCESS) == 0, ("type=%#x rgn=%d\n", u8ResourceType, iRegion));1564 AssertMsg((u8ResourceType & PCI_ADDRESS_SPACE_IO) == 0, ("type=%#x rgn=%d\n", u8ResourceType, iRegion)); 1513 1565 #endif 1514 1566 } … … 1595 1647 uint8_t uCmd = ich9pciBiosInitReadConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_COMMAND, 2); 1596 1648 if (fActiveMemRegion) 1597 uCmd |= PCI_COMMAND_MEMACCESS; /* Enable MMIO access. */1649 uCmd |= VBOX_PCI_COMMAND_MEMORY; /* Enable MMIO access. */ 1598 1650 if (fActiveIORegion) 1599 uCmd |= PCI_COMMAND_IOACCESS; /* Enable I/O space access. */1651 uCmd |= VBOX_PCI_COMMAND_IO; /* Enable I/O space access. */ 1600 1652 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_COMMAND, uCmd, 2); 1601 1653 } … … 1638 1690 uint8_t uCmd = ich9pciBiosInitReadConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_COMMAND, 1); 1639 1691 ich9pciBiosInitWriteConfig(pPciRoot, uBus, uDevFn, VBOX_PCI_COMMAND, 1640 uCmd | PCI_COMMAND_IOACCESS,1692 uCmd | VBOX_PCI_COMMAND_IO, 1641 1693 1); 1642 1694 break; … … 1664 1716 break; 1665 1717 } 1718 /* safe, only needs to go to the config space array */ 1666 1719 if (uBus == PDMPciDevGetByte(pBridge, VBOX_PCI_SECONDARY_BUS)) 1667 1720 { … … 1735 1788 if (pBus->iBus != 0) 1736 1789 { 1737 PCIDevSetByte(pBridgeDev, VBOX_PCI_PRIMARY_BUS, uBusPrimary); 1738 PCIDevSetByte(pBridgeDev, VBOX_PCI_SECONDARY_BUS, pBus->iBus); 1790 ich9pciSetByte(pBridgeDev, VBOX_PCI_PRIMARY_BUS, uBusPrimary); 1791 ich9pciSetByte(pBridgeDev, VBOX_PCI_SECONDARY_BUS, pBus->iBus); 1792 /* Since the subordinate bus value can only be finalized once we 1793 * finished recursing through everything behind the bridge, the only 1794 * solution is temporarily configuring the subordinate to the maximum 1795 * possible value. This makes sure that the config space accesses work 1796 * (for our own sloppy emulation it apparently doesn't matter, but 1797 * this is vital for real PCI bridges/devices in passthrough mode). */ 1798 ich9pciSetByte(pBridgeDev, VBOX_PCI_SUBORDINATE_BUS, 0xff); 1739 1799 } 1740 1800 … … 1750 1810 } 1751 1811 1752 PCIDevSetByte(pBridgeDev, VBOX_PCI_SUBORDINATE_BUS, uMaxSubNum); 1812 if (pBus->iBus != 0) 1813 ich9pciSetByte(pBridgeDev, VBOX_PCI_SUBORDINATE_BUS, uMaxSubNum); 1753 1814 for (uint32_t i = pBus->iBus; i <= uMaxSubNum; i++) 1754 1815 *pbmUsed |= RT_BIT_32(i); 1755 1816 1817 /* Make sure that transactions are able to get through the bridge. Not 1818 * strictly speaking necessary this early (before any device is set up), 1819 * but on the other hand it can't hurt either. */ 1820 if (pBus->iBus != 0) 1821 ich9pciSetWord(pBridgeDev, VBOX_PCI_COMMAND, 1822 VBOX_PCI_COMMAND_IO 1823 | VBOX_PCI_COMMAND_MEMORY 1824 | VBOX_PCI_COMMAND_MASTER); 1825 1826 /* safe, only needs to go to the config space array */ 1756 1827 Log2(("ich9pciBiosInitBridgeTopology: for bus %p: primary=%d secondary=%d subordinate=%d\n", 1757 1828 pBus, … … 1825 1896 { 1826 1897 case 1: 1898 /* safe, only needs to go to the config space array */ 1827 1899 uValue = PDMPciDevGetByte(pPciDev, uAddress); 1828 1900 break; 1829 1901 case 2: 1902 /* safe, only needs to go to the config space array */ 1830 1903 uValue = PDMPciDevGetWord(pPciDev, uAddress); 1831 1904 break; 1832 1905 case 4: 1906 /* safe, only needs to go to the config space array */ 1833 1907 uValue = PDMPciDevGetDWord(pPciDev, uAddress); 1834 1908 break; … … 1934 2008 if (pRegion->type & PCI_ADDRESS_SPACE_IO) 1935 2009 { 1936 if (u16Cmd & PCI_COMMAND_IOACCESS)2010 if (u16Cmd & VBOX_PCI_COMMAND_IO) 1937 2011 { 1938 2012 uint32_t uIoBase = ich9pciGetDWord(pPciDev, offCfgReg); … … 1951 2025 * Note! We exclude the I/O-APIC/HPET/ROM area at the end of the first 4GB to 1952 2026 * prevent the (fake) PCI BIOS and others from making a mess. Pure paranoia. 2027 * Additionally addresses with the top 32 bits all set are excluded, to 2028 * catch silly OSes which probe 64-bit BARs without disabling the 2029 * corresponding transactions. 1953 2030 */ 1954 else if (u16Cmd & PCI_COMMAND_MEMACCESS)2031 else if (u16Cmd & VBOX_PCI_COMMAND_MEMORY) 1955 2032 { 1956 2033 uint64_t uMemBase = ich9pciGetDWord(pPciDev, offCfgReg); … … 1969 2046 && uMemBase > 0 1970 2047 && !( uMemBase <= UINT32_C(0xffffffff) 1971 && uLast >= UINT32_C(0xfec00000)) ) 2048 && uLast >= UINT32_C(0xfec00000)) 2049 && uMemBase <= UINT64_C(0xffffffff00000000) ) 1972 2050 uNew = uMemBase; 1973 2051 } … … 2036 2114 (1 << 4) - 1 /* 4 lowest bits for memory region, also ROM enable bit for ROM region */; 2037 2115 2116 /* safe, only needs to go to the config space array */ 2038 2117 uint8_t bOld = PDMPciDevGetByte(pPciDev, uAddr) & bMask; 2039 2118 bVal = (bOld & bMask) | (bVal & ~bMask); … … 2041 2120 Log3(("devpciR3WriteBarByte: %x changed to %x\n", bOld, bVal)); 2042 2121 2043 PCIDevSetByte(pPciDev, uAddr, bVal); 2122 /* safe, only needs to go to the config space array */ 2123 PDMPciDevSetByte(pPciDev, uAddr, bVal); 2044 2124 } 2045 2125 } … … 2168 2248 if (fWritable) 2169 2249 { 2170 PCIDevSetByte(pPciDev, uAddress, bVal); 2250 /* safe, only needs to go to the config space array */ 2251 PDMPciDevSetByte(pPciDev, uAddress, bVal); 2171 2252 fUpdateMappings = true; 2172 2253 } … … 2178 2259 /* don't change reserved bits (11-15) */ 2179 2260 bVal &= ~UINT8_C(0xf8); 2180 PCIDevSetByte(pPciDev, uAddress, bVal); 2261 /* safe, only needs to go to the config space array */ 2262 PDMPciDevSetByte(pPciDev, uAddress, bVal); 2181 2263 fUpdateMappings = true; 2182 2264 } … … 2224 2306 default: 2225 2307 if (fWritable) 2226 PCIDevSetByte(pPciDev, uAddress, bVal); 2308 /* safe, only needs to go to the config space array */ 2309 PDMPciDevSetByte(pPciDev, uAddress, bVal); 2227 2310 break; 2228 2311 } … … 2270 2353 static void devpciR3InfoPciBus(PDEVPCIBUS pBus, PCDBGFINFOHLP pHlp, unsigned iIndentLvl, bool fRegisters) 2271 2354 { 2272 /** @todo r=bird: Not sure if we should actually do PCI config space 2273 * callbacks from this code!! */ 2355 /* This has to use the callbacks for accuracy reasons. Otherwise it can get 2356 * confusing in the passthrough case or when the callbacks for some device 2357 * are doing something non-trivial (like implementing an indirect 2358 * passthrough approach), because then the abConfig array is an imprecise 2359 * cache needed for efficiency (so that certain reads can be done from 2360 * R0/GC), but far from authoritative or what the guest would see. */ 2274 2361 2275 2362 for (uint32_t iDev = 0; iDev < RT_ELEMENTS(pBus->apDevices); iDev++) … … 2391 2478 devpciR3InfoIndent(pHlp, iIndentLvl); 2392 2479 pHlp->pfnPrintf(pHlp, "bridge topology: primary=%d secondary=%d subordinate=%d\n", 2393 PDMPciDevGetByte(&pBusSub->PciDev, VBOX_PCI_PRIMARY_BUS),2394 PDMPciDevGetByte(&pBusSub->PciDev, VBOX_PCI_SECONDARY_BUS),2395 PDMPciDevGetByte(&pBusSub->PciDev, VBOX_PCI_SUBORDINATE_BUS));2480 ich9pciGetByte(&pBusSub->PciDev, VBOX_PCI_PRIMARY_BUS), 2481 ich9pciGetByte(&pBusSub->PciDev, VBOX_PCI_SECONDARY_BUS), 2482 ich9pciGetByte(&pBusSub->PciDev, VBOX_PCI_SUBORDINATE_BUS)); 2396 2483 devpciR3InfoIndent(pHlp, iIndentLvl); 2397 2484 pHlp->pfnPrintf(pHlp, "behind bridge: I/O %#06x..%#06x\n", 2398 ( PDMPciDevGetByte(&pBusSub->PciDev, VBOX_PCI_IO_BASE) & 0xf0) << 8,2399 ( PDMPciDevGetByte(&pBusSub->PciDev, VBOX_PCI_IO_LIMIT) & 0xf0) << 8 | 0xfff);2485 (ich9pciGetByte(&pBusSub->PciDev, VBOX_PCI_IO_BASE) & 0xf0) << 8, 2486 (ich9pciGetByte(&pBusSub->PciDev, VBOX_PCI_IO_LIMIT) & 0xf0) << 8 | 0xfff); 2400 2487 devpciR3InfoIndent(pHlp, iIndentLvl); 2401 2488 pHlp->pfnPrintf(pHlp, "behind bridge: memory %#010x..%#010x\n", 2402 PDMPciDevGetWord(&pBusSub->PciDev, VBOX_PCI_MEMORY_BASE) << 16, 2403 PDMPciDevGetWord(&pBusSub->PciDev, VBOX_PCI_MEMORY_LIMIT) << 16 | 0xffff); 2489 (ich9pciGetWord(&pBusSub->PciDev, VBOX_PCI_MEMORY_BASE) & 0xfff0) << 16, 2490 (ich9pciGetWord(&pBusSub->PciDev, VBOX_PCI_MEMORY_LIMIT) & 0xfff0) << 16 | 0xfffff); 2491 devpciR3InfoIndent(pHlp, iIndentLvl); 2492 pHlp->pfnPrintf(pHlp, "behind bridge: prefetch memory %#018x..%#018x\n", 2493 ( (uint64_t)ich9pciGetDWord(&pBusSub->PciDev, VBOX_PCI_PREF_BASE_UPPER32) << 32 2494 | ich9pciGetWord(&pBusSub->PciDev, VBOX_PCI_PREF_MEMORY_BASE) & 0xfff0) << 16, 2495 ( (uint64_t)ich9pciGetDWord(&pBusSub->PciDev, VBOX_PCI_PREF_LIMIT_UPPER32) << 32 2496 | ich9pciGetWord(&pBusSub->PciDev, VBOX_PCI_PREF_MEMORY_LIMIT) & 0xfff0) << 16 2497 | 0xfffff); 2404 2498 devpciR3InfoPciBus(pBusSub, pHlp, iIndentLvl + 1, fRegisters); 2405 2499 } … … 2554 2648 #if 0 2555 2649 /* Host bridge device */ 2556 P CIDevSetVendorId( &pBus->PciDev, 0x8086); /* Intel */2557 P CIDevSetDeviceId( &pBus->PciDev, 0x29e0); /* Desktop */2558 P CIDevSetRevisionId(&pBus->PciDev, 0x01); /* rev. 01 */2559 P CIDevSetClassBase( &pBus->PciDev, 0x06); /* bridge */2560 P CIDevSetClassSub( &pBus->PciDev, 0x00); /* Host/PCI bridge */2561 P CIDevSetClassProg( &pBus->PciDev, 0x00); /* Host/PCI bridge */2562 P CIDevSetHeaderType(&pBus->PciDev, 0x00); /* bridge */2563 P CIDevSetWord(&pBus->PciDev, VBOX_PCI_SEC_STATUS, 0x0280); /* secondary status */2650 PDMPciDevSetVendorId( &pBus->PciDev, 0x8086); /* Intel */ 2651 PDMPciDevSetDeviceId( &pBus->PciDev, 0x29e0); /* Desktop */ 2652 PDMPciDevSetRevisionId(&pBus->PciDev, 0x01); /* rev. 01 */ 2653 PDMPciDevSetClassBase( &pBus->PciDev, 0x06); /* bridge */ 2654 PDMPciDevSetClassSub( &pBus->PciDev, 0x00); /* Host/PCI bridge */ 2655 PDMPciDevSetClassProg( &pBus->PciDev, 0x00); /* Host/PCI bridge */ 2656 PDMPciDevSetHeaderType(&pBus->PciDev, 0x00); /* bridge */ 2657 PDMPciDevSetWord(&pBus->PciDev, VBOX_PCI_SEC_STATUS, 0x0280); /* secondary status */ 2564 2658 2565 2659 pBus->PciDev.pDevIns = pDevIns; … … 2657 2751 else 2658 2752 { 2659 PCIDevSetCommand(pDev, 2660 PCIDevGetCommand(pDev) 2661 & 2662 ~(VBOX_PCI_COMMAND_IO | VBOX_PCI_COMMAND_MEMORY | 2753 ich9pciSetWord(pDev, VBOX_PCI_COMMAND, 2754 ich9pciGetWord(pDev, VBOX_PCI_COMMAND) 2755 & ~(VBOX_PCI_COMMAND_IO | VBOX_PCI_COMMAND_MEMORY | 2663 2756 VBOX_PCI_COMMAND_MASTER | VBOX_PCI_COMMAND_SPECIAL | 2664 2757 VBOX_PCI_COMMAND_PARITY | VBOX_PCI_COMMAND_SERR | … … 2668 2761 if (!pciDevIsPci2PciBridge(pDev)) 2669 2762 { 2670 PCIDevSetByte(pDev, VBOX_PCI_CACHE_LINE_SIZE, 0x0);2671 PCIDevSetInterruptLine(pDev, 0x0);2763 ich9pciSetByte(pDev, VBOX_PCI_CACHE_LINE_SIZE, 0x0); 2764 ich9pciSetByte(pDev, VBOX_PCI_INTERRUPT_LINE, 0x0); 2672 2765 } 2673 2766 … … 2831 2924 * Fill in PCI configs and add them to the bus. 2832 2925 */ 2833 P CIDevSetVendorId( &pBus->PciDev, 0x8086); /* Intel */2834 P CIDevSetDeviceId( &pBus->PciDev, 0x2448); /* 82801 Mobile PCI bridge. */2835 P CIDevSetRevisionId(&pBus->PciDev, 0xf2);2836 P CIDevSetClassSub( &pBus->PciDev, 0x04); /* pci2pci */2837 P CIDevSetClassBase( &pBus->PciDev, 0x06); /* PCI_bridge */2838 P CIDevSetClassProg( &pBus->PciDev, 0x01); /* Supports subtractive decoding. */2839 P CIDevSetHeaderType(&pBus->PciDev, 0x01); /* Single function device which adheres to the PCI-to-PCI bridge spec. */2840 P CIDevSetCommand( &pBus->PciDev, 0x00);2841 P CIDevSetStatus( &pBus->PciDev, 0x20); /* 66MHz Capable. */2842 P CIDevSetInterruptLine(&pBus->PciDev, 0x00); /* This device does not assert interrupts. */2926 PDMPciDevSetVendorId( &pBus->PciDev, 0x8086); /* Intel */ 2927 PDMPciDevSetDeviceId( &pBus->PciDev, 0x2448); /* 82801 Mobile PCI bridge. */ 2928 PDMPciDevSetRevisionId(&pBus->PciDev, 0xf2); 2929 PDMPciDevSetClassSub( &pBus->PciDev, 0x04); /* pci2pci */ 2930 PDMPciDevSetClassBase( &pBus->PciDev, 0x06); /* PCI_bridge */ 2931 PDMPciDevSetClassProg( &pBus->PciDev, 0x01); /* Supports subtractive decoding. */ 2932 PDMPciDevSetHeaderType(&pBus->PciDev, 0x01); /* Single function device which adheres to the PCI-to-PCI bridge spec. */ 2933 PDMPciDevSetCommand( &pBus->PciDev, 0x00); 2934 PDMPciDevSetStatus( &pBus->PciDev, 0x20); /* 66MHz Capable. */ 2935 PDMPciDevSetInterruptLine(&pBus->PciDev, 0x00); /* This device does not assert interrupts. */ 2843 2936 2844 2937 /* … … 2846 2939 * devices attached to the bus is unaffected. 2847 2940 */ 2848 P CIDevSetInterruptPin (&pBus->PciDev, 0x00);2941 PDMPciDevSetInterruptPin (&pBus->PciDev, 0x00); 2849 2942 2850 2943 /* … … 2883 2976 2884 2977 /* Reset config space to default values. */ 2885 PCIDevSetByte(&pBus->PciDev, VBOX_PCI_PRIMARY_BUS, 0);2886 PCIDevSetByte(&pBus->PciDev, VBOX_PCI_SECONDARY_BUS, 0);2887 PCIDevSetByte(&pBus->PciDev, VBOX_PCI_SUBORDINATE_BUS, 0);2978 ich9pciSetByte(&pBus->PciDev, VBOX_PCI_PRIMARY_BUS, 0); 2979 ich9pciSetByte(&pBus->PciDev, VBOX_PCI_SECONDARY_BUS, 0); 2980 ich9pciSetByte(&pBus->PciDev, VBOX_PCI_SUBORDINATE_BUS, 0); 2888 2981 2889 2982 /* PCI-specific reset for each device. */ -
trunk/src/VBox/Devices/Bus/DevPciInternal.h
r64697 r65283 193 193 DECLCALLBACK(void) devpciR3CommonDefaultConfigWrite(PPDMDEVINS pDevIns, PPDMPCIDEV pPciDev, 194 194 uint32_t uAddress, uint32_t u32Value, unsigned cb); 195 void devpciR3CommonRestoreConfig(PPDMPCIDEV pDev, uint8_t const *pbSrcConfig , bool fIsBridge);195 void devpciR3CommonRestoreConfig(PPDMPCIDEV pDev, uint8_t const *pbSrcConfig); 196 196 197 197 #endif
Note:
See TracChangeset
for help on using the changeset viewer.