From cf48b9c38f186d7b0877ca69029e282ac900fae5 Mon Sep 17 00:00:00 2001 From: dongshen Date: Mon, 13 May 2019 18:26:13 -0700 Subject: [PATCH] HV: use is_prelaunched_vm/is_hostbridge to check if the code is only for pre-launched VMs Currently host bridge emulation and bar emulation are only for pre-launched vms, use is_prelaunched_vm to check if it is for pre-launched vms when calling init/deinit/cfgread/cfgwrite, also use is_hostbridge() to check if the access if for host bridge, so that these functions can be unified for sos and pre-launched vm in subsequent commits. Move is_hostbridge function to vpci_priv.h so that it can be used by multiple files. vhostbridge_cfgread/vhostbridge_cfgwrite: return -ENODEV if the pci cfg access is not targeted for vhostbridge so that cfgread/cfgwrite functions can be unified for sos and pre-launched vm in subsequent commits Fix @pre for functions Tracked-On: #3056 Signed-off-by: dongshen Reviewed-by: Eddie Dong --- hypervisor/dm/vpci/pci_pt.c | 4 +- hypervisor/dm/vpci/vhostbridge.c | 118 ++++++++++++++++++++----------- hypervisor/dm/vpci/vpci.c | 8 --- hypervisor/dm/vpci/vpci_priv.h | 8 +++ 4 files changed, 85 insertions(+), 53 deletions(-) diff --git a/hypervisor/dm/vpci/pci_pt.c b/hypervisor/dm/vpci/pci_pt.c index 6b2c3c048..179d43b1e 100644 --- a/hypervisor/dm/vpci/pci_pt.c +++ b/hypervisor/dm/vpci/pci_pt.c @@ -50,7 +50,7 @@ int32_t vdev_pt_cfgread(const struct pci_vdev *vdev, uint32_t offset, int32_t ret = -ENODEV; /* PCI BARs is emulated */ - if (pci_bar_access(offset)) { + if (is_prelaunched_vm(vdev->vpci->vm) && pci_bar_access(offset)) { *val = pci_vdev_read_cfg(vdev, offset, bytes); ret = 0; } @@ -254,7 +254,7 @@ int32_t vdev_pt_cfgwrite(struct pci_vdev *vdev, uint32_t offset, int32_t ret = -ENODEV; /* PCI BARs are emulated */ - if (pci_bar_access(offset)) { + if (is_prelaunched_vm(vdev->vpci->vm) && pci_bar_access(offset)) { vdev_pt_cfgwrite_bar(vdev, offset, bytes, val); ret = 0; } diff --git a/hypervisor/dm/vpci/vhostbridge.c b/hypervisor/dm/vpci/vhostbridge.c index d56728b68..9e284fe54 100644 --- a/hypervisor/dm/vpci/vhostbridge.c +++ b/hypervisor/dm/vpci/vhostbridge.c @@ -36,71 +36,103 @@ #include #include +#include #include "vpci_priv.h" + +/** + * @pre vdev != NULL + * @pre vdev->vpci != NULL + * @pre vdev->vpci->vm != NULL + */ void vhostbridge_init(struct pci_vdev *vdev) { - /* PCI config space */ - pci_vdev_write_cfg_u16(vdev, PCIR_VENDOR, (uint16_t)0x8086U); - pci_vdev_write_cfg_u16(vdev, PCIR_DEVICE, (uint16_t)0x5af0U); + if (is_hostbridge(vdev) && is_prelaunched_vm(vdev->vpci->vm)) { + /* PCI config space */ + pci_vdev_write_cfg_u16(vdev, PCIR_VENDOR, (uint16_t)0x8086U); + pci_vdev_write_cfg_u16(vdev, PCIR_DEVICE, (uint16_t)0x5af0U); - pci_vdev_write_cfg_u8(vdev, PCIR_REVID, (uint8_t)0xbU); + pci_vdev_write_cfg_u8(vdev, PCIR_REVID, (uint8_t)0xbU); - pci_vdev_write_cfg_u8(vdev, PCIR_HDRTYPE, (uint8_t)PCIM_HDRTYPE_NORMAL - | PCIM_MFDEV); - pci_vdev_write_cfg_u8(vdev, PCIR_CLASS, (uint8_t)PCIC_BRIDGE); - pci_vdev_write_cfg_u8(vdev, PCIR_SUBCLASS, (uint8_t)PCIS_BRIDGE_HOST); + pci_vdev_write_cfg_u8(vdev, PCIR_HDRTYPE, (uint8_t)PCIM_HDRTYPE_NORMAL + | PCIM_MFDEV); + pci_vdev_write_cfg_u8(vdev, PCIR_CLASS, (uint8_t)PCIC_BRIDGE); + pci_vdev_write_cfg_u8(vdev, PCIR_SUBCLASS, (uint8_t)PCIS_BRIDGE_HOST); - pci_vdev_write_cfg_u8(vdev, 0x34U, (uint8_t)0xe0U); - pci_vdev_write_cfg_u8(vdev, 0x3cU, (uint8_t)0xe0U); - pci_vdev_write_cfg_u8(vdev, 0x48U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0x4aU, (uint8_t)0xd1U); - pci_vdev_write_cfg_u8(vdev, 0x4bU, (uint8_t)0xfeU); - pci_vdev_write_cfg_u8(vdev, 0x50U, (uint8_t)0xc1U); - pci_vdev_write_cfg_u8(vdev, 0x51U, (uint8_t)0x2U); - pci_vdev_write_cfg_u8(vdev, 0x54U, (uint8_t)0x33U); - pci_vdev_write_cfg_u8(vdev, 0x58U, (uint8_t)0x7U); - pci_vdev_write_cfg_u8(vdev, 0x5aU, (uint8_t)0xf0U); - pci_vdev_write_cfg_u8(vdev, 0x5bU, (uint8_t)0x7fU); - pci_vdev_write_cfg_u8(vdev, 0x60U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0x63U, (uint8_t)0xe0U); - pci_vdev_write_cfg_u8(vdev, 0xabU, (uint8_t)0x80U); - pci_vdev_write_cfg_u8(vdev, 0xacU, (uint8_t)0x2U); - pci_vdev_write_cfg_u8(vdev, 0xb0U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0xb3U, (uint8_t)0x7cU); - pci_vdev_write_cfg_u8(vdev, 0xb4U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0xb6U, (uint8_t)0x80U); - pci_vdev_write_cfg_u8(vdev, 0xb7U, (uint8_t)0x7bU); - pci_vdev_write_cfg_u8(vdev, 0xb8U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0xbbU, (uint8_t)0x7bU); - pci_vdev_write_cfg_u8(vdev, 0xbcU, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0xbfU, (uint8_t)0x80U); - pci_vdev_write_cfg_u8(vdev, 0xe0U, (uint8_t)0x9U); - pci_vdev_write_cfg_u8(vdev, 0xe2U, (uint8_t)0xcU); - pci_vdev_write_cfg_u8(vdev, 0xe3U, (uint8_t)0x1U); - pci_vdev_write_cfg_u8(vdev, 0xf5U, (uint8_t)0xfU); - pci_vdev_write_cfg_u8(vdev, 0xf6U, (uint8_t)0x1cU); - pci_vdev_write_cfg_u8(vdev, 0xf7U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0x34U, (uint8_t)0xe0U); + pci_vdev_write_cfg_u8(vdev, 0x3cU, (uint8_t)0xe0U); + pci_vdev_write_cfg_u8(vdev, 0x48U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0x4aU, (uint8_t)0xd1U); + pci_vdev_write_cfg_u8(vdev, 0x4bU, (uint8_t)0xfeU); + pci_vdev_write_cfg_u8(vdev, 0x50U, (uint8_t)0xc1U); + pci_vdev_write_cfg_u8(vdev, 0x51U, (uint8_t)0x2U); + pci_vdev_write_cfg_u8(vdev, 0x54U, (uint8_t)0x33U); + pci_vdev_write_cfg_u8(vdev, 0x58U, (uint8_t)0x7U); + pci_vdev_write_cfg_u8(vdev, 0x5aU, (uint8_t)0xf0U); + pci_vdev_write_cfg_u8(vdev, 0x5bU, (uint8_t)0x7fU); + pci_vdev_write_cfg_u8(vdev, 0x60U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0x63U, (uint8_t)0xe0U); + pci_vdev_write_cfg_u8(vdev, 0xabU, (uint8_t)0x80U); + pci_vdev_write_cfg_u8(vdev, 0xacU, (uint8_t)0x2U); + pci_vdev_write_cfg_u8(vdev, 0xb0U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0xb3U, (uint8_t)0x7cU); + pci_vdev_write_cfg_u8(vdev, 0xb4U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0xb6U, (uint8_t)0x80U); + pci_vdev_write_cfg_u8(vdev, 0xb7U, (uint8_t)0x7bU); + pci_vdev_write_cfg_u8(vdev, 0xb8U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0xbbU, (uint8_t)0x7bU); + pci_vdev_write_cfg_u8(vdev, 0xbcU, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0xbfU, (uint8_t)0x80U); + pci_vdev_write_cfg_u8(vdev, 0xe0U, (uint8_t)0x9U); + pci_vdev_write_cfg_u8(vdev, 0xe2U, (uint8_t)0xcU); + pci_vdev_write_cfg_u8(vdev, 0xe3U, (uint8_t)0x1U); + pci_vdev_write_cfg_u8(vdev, 0xf5U, (uint8_t)0xfU); + pci_vdev_write_cfg_u8(vdev, 0xf6U, (uint8_t)0x1cU); + pci_vdev_write_cfg_u8(vdev, 0xf7U, (uint8_t)0x1U); + } } void vhostbridge_deinit(__unused const struct pci_vdev *vdev) { } + +/** + * @pre vdev != NULL + * @pre vdev->vpci != NULL + * @pre vdev->vpci->vm != NULL + */ int32_t vhostbridge_cfgread(const struct pci_vdev *vdev, uint32_t offset, uint32_t bytes, uint32_t *val) { - *val = pci_vdev_read_cfg(vdev, offset, bytes); + int32_t ret = -ENODEV; - return 0; + if (is_hostbridge(vdev) && is_prelaunched_vm(vdev->vpci->vm)) { + *val = pci_vdev_read_cfg(vdev, offset, bytes); + ret = 0; + } + + return ret; } + +/** + * @pre vdev != NULL + * @pre vdev->vpci != NULL + * @pre vdev->vpci->vm != NULL + */ int32_t vhostbridge_cfgwrite(struct pci_vdev *vdev, uint32_t offset, uint32_t bytes, uint32_t val) { - if (!pci_bar_access(offset)) { - pci_vdev_write_cfg(vdev, offset, bytes, val); + int32_t ret = -ENODEV; + + if (is_hostbridge(vdev) && is_prelaunched_vm(vdev->vpci->vm)) { + if (!pci_bar_access(offset)) { + pci_vdev_write_cfg(vdev, offset, bytes, val); + } + + ret = 0; } - return 0; + return ret; } diff --git a/hypervisor/dm/vpci/vpci.c b/hypervisor/dm/vpci/vpci.c index ff87dfe39..285dcb2f4 100644 --- a/hypervisor/dm/vpci/vpci.c +++ b/hypervisor/dm/vpci/vpci.c @@ -260,14 +260,6 @@ void vpci_cleanup(const struct acrn_vm *vm) } } -/** - * @pre vdev != NULL - */ -static inline bool is_hostbridge(const struct pci_vdev *vdev) -{ - return (vdev->vbdf.value == 0U); -} - /** * @pre vdev != NULL * @pre vdev->vpci != NULL diff --git a/hypervisor/dm/vpci/vpci_priv.h b/hypervisor/dm/vpci/vpci_priv.h index 5638202c9..2f7a54756 100644 --- a/hypervisor/dm/vpci/vpci_priv.h +++ b/hypervisor/dm/vpci/vpci_priv.h @@ -75,6 +75,14 @@ static inline bool has_msix_cap(const struct pci_vdev *vdev) return (vdev->msix.capoff != 0U); } +/** + * @pre vdev != NULL + */ +static inline bool is_hostbridge(const struct pci_vdev *vdev) +{ + return (vdev->vbdf.value == 0U); +} + void vhostbridge_init(struct pci_vdev *vdev); int32_t vhostbridge_cfgread(const struct pci_vdev *vdev, uint32_t offset, uint32_t bytes, uint32_t *val); int32_t vhostbridge_cfgwrite(struct pci_vdev *vdev, uint32_t offset, uint32_t bytes, uint32_t val);