dm:passthrough opregion to uos gpu

uos IGD driver need opregion when enable GVT-d.

This patch pass-thru opregion to uos gpu.
Here is the steps:
(1) set opregion gpa(guest physical addrress) 0xDFFFD000;
(2) get opregion hpa(host physical addrress);
(3) build EPT mapping for opregion.

v1 -> v2:
        * initialize the EPT mapping for passthrough GPU opregion region
        in passthru_init instead of reading the ASLS config space

v2 -> v3:
        * add EPT unmap when deinit
        * change some micro name

Tracked-On: #4360

Signed-off-by: Junming Liu <junming.liu@intel.com>
Reviewed-by: Zhao Yakui <yakui.zhao@intel.com>
Reviewed-by: Liu XinYun <xinyun.liu@intel.com>
Reviewed-by: Shuo A Liu <shuo.a.liu@intel.com>
Reviewed-by: Wu Binbin <binbin.wu@intel.com>
Acked-by: Yu Wang <yu1.wang@intel.com>
This commit is contained in:
Junming Liu 2020-01-10 22:39:49 +00:00 committed by wenlingz
parent 4d882731ce
commit 1b3754aaee
2 changed files with 30 additions and 0 deletions

View File

@ -73,6 +73,14 @@
/* set gsm gpa=0xDB000000, which is reserved in e820 table */
#define GPU_GSM_GPA 0xDB000000
#define GPU_OPREGION_SIZE 0x3000
/* set opregion gpa=0xDFFFD000, which is reserved in e820 table.
* [0xDFFFD000, 0XE0000000] 12K opregion has reserved for GVT-g,
* because GVT-d is not compatible with GVT-g,
* so here can use [0xDFFFD000, 0XE0000000] region.
*/
#define GPU_OPREGION_GPA 0xDFFFD000
extern uint64_t audio_nhlt_len;
/* reference count for libpciaccess init/deinit */
@ -86,6 +94,7 @@ struct mmio_map {
};
uint32_t gsm_start_hpa = 0;
uint32_t opregion_start_hpa = 0;
struct passthru_dev {
struct pci_vdev *dev;
@ -873,6 +882,12 @@ passthru_init(struct vmctx *ctx, struct pci_vdev *dev, char *opts)
gsm_start_hpa &= PCIM_BDSM_GSM_MASK;
/* initialize the EPT mapping for passthrough GPU gsm region */
vm_map_ptdev_mmio(ctx, 0, 2, 0, GPU_GSM_GPA, GPU_GSM_SIZE, gsm_start_hpa);
/* get opregion hpa */
opregion_start_hpa = read_config(ptdev->phys_dev, PCIR_ASLS_CTL, 4);
opregion_start_hpa &= PCIM_ASLS_OPREGION_MASK;
/* initialize the EPT mapping for passthrough GPU opregion */
vm_map_ptdev_mmio(ctx, 0, 2, 0, GPU_OPREGION_GPA, GPU_OPREGION_SIZE, opregion_start_hpa);
}
/* If ptdev support MSI/MSIX, stop here to skip virtual INTx setup.
@ -962,6 +977,7 @@ passthru_deinit(struct vmctx *ctx, struct pci_vdev *dev, char *opts)
if (ptdev->phys_bdf == PCI_BDF_GPU) {
vm_unmap_ptdev_mmio(ctx, 0, 2, 0, GPU_GSM_GPA, GPU_GSM_SIZE, gsm_start_hpa);
vm_unmap_ptdev_mmio(ctx, 0, 2, 0, GPU_OPREGION_GPA, GPU_OPREGION_SIZE, opregion_start_hpa);
}
pciaccess_cleanup();
@ -1066,6 +1082,18 @@ passthru_cfgread(struct vmctx *ctx, int vcpu, struct pci_vdev *dev,
*rv |= GPU_GSM_GPA;
}
/* passthru_init has initialized the EPT mapping
* for GPU opregion.
* So uos GPU can passthrough physical opregion now.
* Here, only need return opregion gpa value for uos.
*/
if ((PCI_BDF(dev->bus, dev->slot, dev->func) == PCI_BDF_GPU)
&& (coff == PCIR_ASLS_CTL)) {
/* reserve opregion start addr offset to 4KB page */
*rv &= ~PCIM_ASLS_OPREGION_MASK;
*rv |= GPU_OPREGION_GPA;
}
return 0;
}

View File

@ -1068,4 +1068,6 @@
/* Graphics definitions */
#define PCIR_BDSM 0x5C /* BDSM graphics base data of stolen memory register */
#define PCIM_BDSM_GSM_MASK 0xFFF00000 /* bits 31:20 contains the base address of stolen memory */
#define PCIR_ASLS_CTL 0xFC /* Opregion start addr register */
#define PCIM_ASLS_OPREGION_MASK 0xFFFFF000 /* opregion need 4KB aligned */
#endif