mirror of
https://github.com/projectacrn/acrn-hypervisor.git
synced 2025-07-30 15:06:49 +00:00
hv: move function 'inject_msi_lapic_pt()' to vlapic.c
This function can be used by other modules instead of hypercall handling only, hence move it to vlapic.c Tracked-On: #5407 Signed-off-by: Yonghua Huang <yonghua.huang@intel.com> Reviewed-by: Li, Fei <fei1.li@intel.com> Reviewed-by: Wang, Yu1 <yu1.wang@intel.com> Acked-by: Eddie Dong <eddie.dong@intel.com>
This commit is contained in:
parent
f511a71c4e
commit
012927d0bd
@ -1930,6 +1930,56 @@ vlapic_intr_msi(struct acrn_vm *vm, uint64_t addr, uint64_t msg)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
*@pre Pointer vm shall point to SOS_VM
|
||||
*/
|
||||
void inject_msi_lapic_pt(struct acrn_vm *vm, const struct acrn_msi_entry *vmsi)
|
||||
{
|
||||
union apic_icr icr;
|
||||
struct acrn_vcpu *vcpu;
|
||||
union msi_addr_reg vmsi_addr;
|
||||
union msi_data_reg vmsi_data;
|
||||
uint64_t vdmask = 0UL;
|
||||
uint32_t vdest, dest = 0U;
|
||||
uint16_t vcpu_id;
|
||||
bool phys;
|
||||
|
||||
vmsi_addr.full = vmsi->msi_addr;
|
||||
vmsi_data.full = (uint32_t)vmsi->msi_data;
|
||||
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: msi_addr 0x%016lx, msi_data 0x%016lx",
|
||||
__func__, vmsi->msi_addr, vmsi->msi_data);
|
||||
|
||||
if (vmsi_addr.bits.addr_base == MSI_ADDR_BASE) {
|
||||
vdest = vmsi_addr.bits.dest_field;
|
||||
phys = (vmsi_addr.bits.dest_mode == MSI_ADDR_DESTMODE_PHYS);
|
||||
/*
|
||||
* calculate all reachable destination vcpu.
|
||||
* the delivery mode of vmsi will be forwarded to ICR delievry field
|
||||
* and handled by hardware.
|
||||
*/
|
||||
vlapic_calc_dest_lapic_pt(vm, &vdmask, false, vdest, phys);
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: vcpu destination mask 0x%016lx", __func__, vdmask);
|
||||
|
||||
vcpu_id = ffs64(vdmask);
|
||||
while (vcpu_id != INVALID_BIT_INDEX) {
|
||||
bitmap_clear_nolock(vcpu_id, &vdmask);
|
||||
vcpu = vcpu_from_vid(vm, vcpu_id);
|
||||
dest |= per_cpu(lapic_ldr, pcpuid_from_vcpu(vcpu));
|
||||
vcpu_id = ffs64(vdmask);
|
||||
}
|
||||
|
||||
icr.value = 0UL;
|
||||
icr.bits.dest_field = dest;
|
||||
icr.bits.vector = vmsi_data.bits.vector;
|
||||
icr.bits.delivery_mode = vmsi_data.bits.delivery_mode;
|
||||
icr.bits.destination_mode = MSI_ADDR_DESTMODE_LOGICAL;
|
||||
|
||||
msr_write(MSR_IA32_EXT_APIC_ICR, icr.value);
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: icr.value 0x%016lx", __func__, icr.value);
|
||||
}
|
||||
}
|
||||
|
||||
/* interrupt context */
|
||||
static void vlapic_timer_expired(void *data)
|
||||
{
|
||||
|
@ -417,56 +417,6 @@ int32_t hcall_set_irqline(struct acrn_vm *vm, struct acrn_vm *target_vm, __unuse
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
*@pre Pointer vm shall point to SOS_VM
|
||||
*/
|
||||
static void inject_msi_lapic_pt(struct acrn_vm *vm, const struct acrn_msi_entry *vmsi)
|
||||
{
|
||||
union apic_icr icr;
|
||||
struct acrn_vcpu *vcpu;
|
||||
union msi_addr_reg vmsi_addr;
|
||||
union msi_data_reg vmsi_data;
|
||||
uint64_t vdmask = 0UL;
|
||||
uint32_t vdest, dest = 0U;
|
||||
uint16_t vcpu_id;
|
||||
bool phys;
|
||||
|
||||
vmsi_addr.full = vmsi->msi_addr;
|
||||
vmsi_data.full = (uint32_t)vmsi->msi_data;
|
||||
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: msi_addr 0x%016lx, msi_data 0x%016lx",
|
||||
__func__, vmsi->msi_addr, vmsi->msi_data);
|
||||
|
||||
if (vmsi_addr.bits.addr_base == MSI_ADDR_BASE) {
|
||||
vdest = vmsi_addr.bits.dest_field;
|
||||
phys = (vmsi_addr.bits.dest_mode == MSI_ADDR_DESTMODE_PHYS);
|
||||
/*
|
||||
* calculate all reachable destination vcpu.
|
||||
* the delivery mode of vmsi will be forwarded to ICR delievry field
|
||||
* and handled by hardware.
|
||||
*/
|
||||
vlapic_calc_dest_lapic_pt(vm, &vdmask, false, vdest, phys);
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: vcpu destination mask 0x%016lx", __func__, vdmask);
|
||||
|
||||
vcpu_id = ffs64(vdmask);
|
||||
while (vcpu_id != INVALID_BIT_INDEX) {
|
||||
bitmap_clear_nolock(vcpu_id, &vdmask);
|
||||
vcpu = vcpu_from_vid(vm, vcpu_id);
|
||||
dest |= per_cpu(lapic_ldr, pcpuid_from_vcpu(vcpu));
|
||||
vcpu_id = ffs64(vdmask);
|
||||
}
|
||||
|
||||
icr.value = 0UL;
|
||||
icr.bits.dest_field = dest;
|
||||
icr.bits.vector = vmsi_data.bits.vector;
|
||||
icr.bits.delivery_mode = vmsi_data.bits.delivery_mode;
|
||||
icr.bits.destination_mode = MSI_ADDR_DESTMODE_LOGICAL;
|
||||
|
||||
msr_write(MSR_IA32_EXT_APIC_ICR, icr.value);
|
||||
dev_dbg(DBG_LEVEL_LAPICPT, "%s: icr.value 0x%016lx", __func__, icr.value);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief inject MSI interrupt
|
||||
*
|
||||
|
@ -160,6 +160,7 @@ int32_t vlapic_set_local_intr(struct acrn_vm *vm, uint16_t vcpu_id_arg, uint32_t
|
||||
* @pre vm != NULL
|
||||
*/
|
||||
int32_t vlapic_intr_msi(struct acrn_vm *vm, uint64_t addr, uint64_t msg);
|
||||
void inject_msi_lapic_pt(struct acrn_vm *vm, const struct acrn_msi_entry *vmsi);
|
||||
|
||||
void vlapic_receive_intr(struct acrn_vm *vm, bool level, uint32_t dest,
|
||||
bool phys, uint32_t delmode, uint32_t vec, bool rh);
|
||||
|
Loading…
Reference in New Issue
Block a user