VirtualBox

Changeset 83619 in vbox


Ignore:
Timestamp:
Apr 8, 2020 11:41:57 AM (5 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
137040
Message:

AMD IOMMU: bugref:9654 Bits.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Bus/DevIommuAmd.cpp

    r83615 r83619  
    3333/** @name PCI configuration register offsets.
    3434 @{ */
    35 #define IOMMU_PCI_OFF_CAP_HDR                       0x00
    36 #define IOMMU_PCI_OFF_BASE_ADDR_REG_LO              0x04
    37 #define IOMMU_PCI_OFF_BASE_ADDR_REG_HI              0x08
    38 #define IOMMU_PCI_OFF_RANGE_REG                     0x0c
    39 #define IOMMU_PCI_OFF_MISCINFO_REG_0                0x10
    40 #define IOMMU_PCI_OFF_MISCINFO_REG_1                0x14
     35#define IOMMU_PCI_OFF_CAP_HDR                       0x40
     36#define IOMMU_PCI_OFF_BASE_ADDR_REG_LO              0x44
     37#define IOMMU_PCI_OFF_BASE_ADDR_REG_HI              0x48
     38#define IOMMU_PCI_OFF_RANGE_REG                     0x4c
     39#define IOMMU_PCI_OFF_MISCINFO_REG_0                0x50
     40#define IOMMU_PCI_OFF_MISCINFO_REG_1                0x54
     41#define IOMMU_PCI_OFF_MSI_CAP_HDR                   0x64
     42#define IOMMU_PCI_OFF_MSI_ADDR_LO                   0x68
     43#define IOMMU_PCI_OFF_MSI_ADDR_HI                   0x6c
     44#define IOMMU_PCI_OFF_MSI_DATA                      0x70
     45#define IOMMU_PCI_OFF_MSI_MAP_CAP_HDR               0x74
    4146/** @} */
    4247
     
    21462151
    21472152/**
     2153 * Resets read-write portions of the IOMMU state.
     2154 *
     2155 * State data not initialized here is expected to be initialized in the construct
     2156 * callback and remain read-only through the lifetime of the VM.
     2157 *
     2158 * @param   pDevIns   The device instance.
     2159 */
     2160static void iommuAmdR3Init(PPDMDEVINS pDevIns)
     2161{
     2162    PIOMMU pThis = PDMDEVINS_2_DATA(pDevIns, PIOMMU);
     2163    Assert(pThis);
     2164
     2165    PPDMPCIDEV pPciDev = pDevIns->apPciDevs[0];
     2166    PDMPCIDEV_ASSERT_VALID(pDevIns, pPciDev);
     2167
     2168    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_BASE_ADDR_REG_LO, 0);
     2169    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_BASE_ADDR_REG_HI, 0);
     2170    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_RANGE_REG,        0);
     2171}
     2172
     2173
     2174/**
    21482175 * @callback_method_impl{FNPCICONFIGREAD}
    21492176 */
     
    27472774static DECLCALLBACK(void) iommuAmdR3Reset(PPDMDEVINS pDevIns)
    27482775{
    2749     NOREF(pDevIns);
     2776    iommuAmdR3Init(pDevIns);
    27502777}
    27512778
     
    27982825    PDMPCIDEV_ASSERT_VALID(pDevIns, pPciDev);
    27992826
    2800     uint8_t const offCapHdr       = 0x40;
    2801     uint8_t const offBaseAddrLo   = offCapHdr + 0x4;
    2802     uint8_t const offBaseAddrHi   = offCapHdr + 0x8;
    2803     uint8_t const offRange        = offCapHdr + 0xc;
    2804     uint8_t const offMiscInfo0    = offCapHdr + 0x10;
    2805     uint8_t const offMiscInfo1    = offCapHdr + 0x14;
    2806     uint8_t const offMsiCapHdr    = offCapHdr + 0x24;
    2807     uint8_t const offMsiAddrLo    = offCapHdr + 0x28;
    2808     uint8_t const offMsiAddrHi    = offCapHdr + 0x2c;
    2809     uint8_t const offMsiData      = offCapHdr + 0x30;
    2810     uint8_t const offMsiMapCapHdr = offCapHdr + 0x34;
    2811 
    28122827    /* Header. */
    2813     PDMPciDevSetVendorId(pPciDev,           IOMMU_PCI_VENDOR_ID);   /* RO - AMD */
    2814     PDMPciDevSetDeviceId(pPciDev,           IOMMU_PCI_DEVICE_ID);   /* RO - VirtualBox IOMMU device */
    2815     PDMPciDevSetCommand(pPciDev,            0);                     /* RW - Command */
    2816     PDMPciDevSetStatus(pPciDev,             0x5);                   /* RW - Status - CapList supported */
    2817     PDMPciDevSetRevisionId(pPciDev,         IOMMU_PCI_REVISION_ID); /* RO - VirtualBox specific device implementation revision */
    2818     PDMPciDevSetClassBase(pPciDev,          0x08);                  /* RO - System Base Peripheral */
    2819     PDMPciDevSetClassSub(pPciDev,           0x06);                  /* RO - IOMMU */
    2820     PDMPciDevSetClassProg(pPciDev,          0x00);                  /* RO - IOMMU Programming interface */
    2821     PDMPciDevSetHeaderType(pPciDev,         0x00);                  /* RO - Single function, type 0. */
    2822     PDMPciDevSetSubSystemId(pPciDev,        IOMMU_PCI_DEVICE_ID);   /* RO - AMD */
    2823     PDMPciDevSetSubSystemVendorId(pPciDev,  IOMMU_PCI_VENDOR_ID);   /* RO - VirtualBox IOMMU device */
    2824     PDMPciDevSetCapabilityList(pPciDev,     offCapHdr);             /* RO - Offset into capability registers. */
    2825     PDMPciDevSetInterruptPin(pPciDev,       0x01);                  /* RO - INTA#. */
    2826     PDMPciDevSetInterruptLine(pPciDev,      0x00);                  /* RW - For software compatibility; no effect on hardware. */
     2828    PDMPciDevSetVendorId(pPciDev,           IOMMU_PCI_VENDOR_ID);     /* AMD */
     2829    PDMPciDevSetDeviceId(pPciDev,           IOMMU_PCI_DEVICE_ID);     /* VirtualBox IOMMU device */
     2830    PDMPciDevSetCommand(pPciDev,            0);                       /* Command */
     2831    PDMPciDevSetStatus(pPciDev,             0x5);                     /* Status - CapList supported */
     2832    PDMPciDevSetRevisionId(pPciDev,         IOMMU_PCI_REVISION_ID);   /* VirtualBox specific device implementation revision */
     2833    PDMPciDevSetClassBase(pPciDev,          0x08);                    /* System Base Peripheral */
     2834    PDMPciDevSetClassSub(pPciDev,           0x06);                    /* IOMMU */
     2835    PDMPciDevSetClassProg(pPciDev,          0x00);                    /* IOMMU Programming interface */
     2836    PDMPciDevSetHeaderType(pPciDev,         0x00);                    /* Single function, type 0. */
     2837    PDMPciDevSetSubSystemId(pPciDev,        IOMMU_PCI_DEVICE_ID);     /* AMD */
     2838    PDMPciDevSetSubSystemVendorId(pPciDev,  IOMMU_PCI_VENDOR_ID);     /* VirtualBox IOMMU device */
     2839    PDMPciDevSetCapabilityList(pPciDev,     IOMMU_PCI_OFF_CAP_HDR);   /* Offset into capability registers. */
     2840    PDMPciDevSetInterruptPin(pPciDev,       0x01);                    /* INTA#. */
     2841    PDMPciDevSetInterruptLine(pPciDev,      0x00);                    /* For software compatibility; no effect on hardware. */
    28272842
    28282843    /* Capability Header. */
    2829     PDMPciDevSetDWord(pPciDev, offCapHdr,
    2830                         RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_ID,     0xf)             /* RO - Secure Device capability block */
    2831                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_PTR,    offMsiCapHdr)    /* RO - Offset to next capability block */
    2832                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_TYPE,   0x3)             /* RO - IOMMU capability block */
    2833                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_REV,    0x1)             /* RO - IOMMU interface revision */
    2834                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_IOTLB_SUP,  0x0)             /* RO - Remote IOTLB support */
    2835                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_HT_TUNNEL,  0x0)             /* RO - HyperTransport Tunnel support */
    2836                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_NP_CACHE,   0x0)             /* RO - Cache Not-present page table entries */
    2837                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_EFR_SUP,    0x1)             /* RO - Extended Feature Register support */
    2838                       | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_EXT,    0x1));           /* RO - Misc. Information Register support */
    2839 
     2844    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_CAP_HDR,
     2845                        RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_ID,    0xf)    /* RO - Secure Device capability block */
     2846                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_PTR,   IOMMU_PCI_OFF_MSI_CAP_HDR)  /* RO - Offset to next capability block */
     2847                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_TYPE,  0x3)    /* RO - IOMMU capability block */
     2848                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_REV,   0x1)    /* RO - IOMMU interface revision */
     2849                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_IOTLB_SUP, 0x0)    /* RO - Remote IOTLB support */
     2850                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_HT_TUNNEL, 0x0)    /* RO - HyperTransport Tunnel support */
     2851                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_NP_CACHE,  0x0)    /* RO - Cache NP page table entries */
     2852                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_EFR_SUP,   0x1)    /* RO - Extended Feature Register support */
     2853                      | RT_BF_MAKE(IOMMU_BF_CAPHDR_CAP_EXT,   0x1));  /* RO - Misc. Information Register support */
    28402854    /* Base Address Low Register. */
    2841     PDMPciDevSetDWord(pPciDev, offBaseAddrLo, 0x0);   /* RW - Base address (Lo) and enable bit. */
    2842 
     2855    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_BASE_ADDR_REG_LO, 0x0);  /* RW - Base address (Lo) and enable bit. */
    28432856    /* Base Address High Register. */
    2844     PDMPciDevSetDWord(pPciDev, offBaseAddrHi, 0x0);   /* RW - Base address (Hi) */
    2845 
     2857    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_BASE_ADDR_REG_HI, 0x0);  /* RW - Base address (Hi) */
    28462858    /* IOMMU Range Register. */
    2847     PDMPciDevSetDWord(pPciDev, offRange, 0x0);        /* RO - Range register. */
    2848 
     2859    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_RANGE_REG, 0x0);         /* RW - Range register. */
    28492860    /* Misc. Information Register 0. */
    2850     PDMPciDevSetDWord(pPciDev, offMiscInfo0,
     2861    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MISCINFO_REG_0,
    28512862                        RT_BF_MAKE(IOMMU_BF_MISCINFO_0_MSI_NUM,     0x0)    /* RO - MSI number */
    28522863                      | RT_BF_MAKE(IOMMU_BF_MISCINFO_0_GVA_SIZE,    0x2)    /* RO - Guest Virt. Addr size (2=48 bits) */
     
    28552866                      | RT_BF_MAKE(IOMMU_BF_MISCINFO_0_HT_ATS_RESV, 0x0)    /* RW - HT ATS reserved */
    28562867                      | RT_BF_MAKE(IOMMU_BF_MISCINFO_0_MSI_NUM_PPR, 0x0));  /* RW - PPR interrupt number */
    2857 
    28582868    /* Misc. Information Register 1. */
    2859     PDMPciDevSetDWord(pPciDev, offMiscInfo1, 0);
    2860 
     2869    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MISCINFO_REG_0, 0);
    28612870    /* MSI Capability Header register. */
    28622871#if 0
    2863     PDMPciDevSetDWord(pPciDev, offMsiCapHdr,
     2872    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MSI_CAP_HDR,
    28642873                        RT_BF_MAKE(IOMMU_BF_MSI_CAPHDR_CAP_ID,       0x5)             /* RO - Capability ID. */
    2865                       | RT_BF_MAKE(IOMMU_BF_MSI_CAPHDR_CAP_PTR,      offMsiMapCapHdr) /* RO - Offset to mapping capability block */
     2874                      | RT_BF_MAKE(IOMMU_BF_MSI_CAPHDR_CAP_PTR,      offMsiMapCapHdr) /* RO - Offset to next capability block */
    28662875                      | RT_BF_MAKE(IOMMU_BF_MSI_CAPHDR_EN,           0x0)             /* RW - MSI capability enable */
    28672876                      | RT_BF_MAKE(IOMMU_BF_MSI_CAPHDR_MULTMESS_CAP, 0x0)             /* RO - MSI multi-message capability */
     
    28722881    RT_ZERO(MsiReg);
    28732882    MsiReg.cMsiVectors    = 1;
    2874     MsiReg.iMsiCapOffset  = offMsiCapHdr;
    2875     MsiReg.iMsiNextOffset = offMsiMapCapHdr;
     2883    MsiReg.iMsiCapOffset  = IOMMU_PCI_OFF_MSI_CAP_HDR;
     2884    MsiReg.iMsiNextOffset = IOMMU_PCI_OFF_MSI_MAP_CAP_HDR;
    28762885    rc = PDMDevHlpPCIRegisterMsi(pDevIns, &MsiReg);
    28772886    AssertRCReturn(rc, rc);
    28782887#endif
    2879 
     2888#if 0
    28802889    /* MSI Address Lo. */
    2881     PDMPciDevSetDWord(pPciDev, offMsiAddrLo, 0);                            /* RW - MSI message address (Lo). */
    2882 
     2890    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MSI_ADDR_LO, 0);         /* RW - MSI message address (Lo). */
    28832891    /* MSI Address Hi. */
    2884     PDMPciDevSetDWord(pPciDev, offMsiAddrHi, 0);                            /* RW - MSI message address (Hi). */
    2885 
     2892    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MSI_ADDR_HI, 0);         /* RW - MSI message address (Hi). */
    28862893    /* MSI Data. */
    2887     PDMPciDevSetDWord(pPciDev, offMsiData, 0);                              /* RW - MSI data. */
    2888 
     2894    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MSI_DATA, 0);            /* RW - MSI data. */
     2895#else
     2896    /* These are initialized in iommuAmdInit. */
     2897#endif
    28892898    /** @todo IOMMU: I don't know if we can support this, disable later if required. */
    28902899    /* MSI Mapping Capability Header register. */
    2891     PDMPciDevSetDWord(pPciDev, offMsiMapCapHdr,
     2900    PDMPciDevSetDWord(pPciDev, IOMMU_PCI_OFF_MSI_MAP_CAP_HDR,
    28922901                        RT_BF_MAKE(IOMMU_BF_MSI_MAP_CAPHDR_CAP_ID,   0x8)       /* RO - Capability ID */
    28932902                      | RT_BF_MAKE(IOMMU_BF_MSI_MAP_CAPHDR_CAP_PTR,  0x0)       /* RO - Offset to next capability (NULL) */
     
    28952904                      | RT_BF_MAKE(IOMMU_BF_MSI_MAP_CAPHDR_FIXED,    0x1)       /* RO - MSI mapping range is fixed */
    28962905                      | RT_BF_MAKE(IOMMU_BF_MSI_MAP_CAPHDR_CAP_TYPE, 0x15));    /* RO - MSI mapping capability */
     2906
     2907    /*
     2908     * Initialize parts of the IOMMU state as it would during reset.
     2909     */
     2910    iommuAmdR3Init(pDevIns);
    28972911
    28982912    /*
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette