mirror of
https://github.com/projectacrn/acrn-hypervisor.git
synced 2025-06-28 16:27:01 +00:00
HV: add hypercall interface of get vcpu state data
We can use this interface for VHM to pass per-cpu power state data to guest per its request. For now the vcpu power state is per-vm, this could be changed if per-cpu power state support is required in the future. Signed-off-by: Victor Sun <victor.sun@intel.com> Acked-by: Kevin Tian <kevin.tian@intel.com>
This commit is contained in:
parent
0e2b9fc7fa
commit
1d0d4d3185
@ -142,6 +142,10 @@ int vmcall_handler(struct vcpu *vcpu)
|
|||||||
ret = hcall_initialize_trusty(vcpu, param1);
|
ret = hcall_initialize_trusty(vcpu, param1);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case HC_PM_GET_CPU_STATE:
|
||||||
|
ret = hcall_get_cpu_pm_state(vm, param1, param2);
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
pr_err("op %d: Invalid hypercall\n", hypcall_id);
|
pr_err("op %d: Invalid hypercall\n", hypcall_id);
|
||||||
ret = -1;
|
ret = -1;
|
||||||
|
@ -37,6 +37,7 @@
|
|||||||
#include <acrn_hv_defs.h>
|
#include <acrn_hv_defs.h>
|
||||||
#include <hv_debug.h>
|
#include <hv_debug.h>
|
||||||
#include <version.h>
|
#include <version.h>
|
||||||
|
#include <cpu_state_tbl.h>
|
||||||
|
|
||||||
#define ACRN_DBG_HYCALL 6
|
#define ACRN_DBG_HYCALL 6
|
||||||
|
|
||||||
@ -664,6 +665,63 @@ int64_t hcall_setup_sbuf(struct vm *vm, uint64_t param)
|
|||||||
return sbuf_share_setup(ssp.pcpu_id, ssp.sbuf_id, hva);
|
return sbuf_share_setup(ssp.pcpu_id, ssp.sbuf_id, hva);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int64_t hcall_get_cpu_pm_state(struct vm *vm, uint64_t cmd, uint64_t param)
|
||||||
|
{
|
||||||
|
int target_vm_id, target_vcpu_id;
|
||||||
|
struct vm *target_vm;
|
||||||
|
struct vcpu *target_vcpu;
|
||||||
|
|
||||||
|
target_vm_id = (cmd & PMCMD_VMID_MASK) >> PMCMD_VMID_SHIFT;
|
||||||
|
target_vm = get_vm_from_vmid(target_vm_id);
|
||||||
|
|
||||||
|
if (!target_vm) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (cmd & PMCMD_TYPE_MASK) {
|
||||||
|
case PMCMD_GET_PX_CNT: {
|
||||||
|
|
||||||
|
if (!target_vm->pm.px_cnt) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (copy_to_vm(vm, &(target_vm->pm.px_cnt), param)) {
|
||||||
|
pr_err("%s: Unable copy param to vm\n", __func__);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
case PMCMD_GET_PX_DATA: {
|
||||||
|
int pn;
|
||||||
|
struct cpu_px_data *px_data;
|
||||||
|
|
||||||
|
/* For now we put px data as per-vm,
|
||||||
|
* If it is stored as per-cpu in the future,
|
||||||
|
* we need to check PMCMD_VCPUID_MASK in cmd.
|
||||||
|
*/
|
||||||
|
if (!target_vm->pm.px_cnt) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
pn = (cmd & PMCMD_STATE_NUM_MASK) >> PMCMD_STATE_NUM_SHIFT;
|
||||||
|
if (pn >= target_vm->pm.px_cnt) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
px_data = target_vm->pm.px_data + pn;
|
||||||
|
if (copy_to_vm(vm, px_data, param)) {
|
||||||
|
pr_err("%s: Unable copy param to vm\n", __func__);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void fire_vhm_interrupt(void)
|
static void fire_vhm_interrupt(void)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
|
@ -333,6 +333,17 @@ int64_t hcall_setup_sbuf(struct vm *vm, uint64_t param);
|
|||||||
*
|
*
|
||||||
* @return 0 on success, non-zero on error.
|
* @return 0 on success, non-zero on error.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
int64_t hcall_get_cpu_pm_state(struct vm *vm, uint64_t cmd, uint64_t param);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Get VCPU Power state.
|
||||||
|
*
|
||||||
|
* @param VCPU power state data
|
||||||
|
*
|
||||||
|
* @return 0 on success, non-zero on error.
|
||||||
|
*/
|
||||||
|
|
||||||
int64_t hcall_world_switch(struct vcpu *vcpu);
|
int64_t hcall_world_switch(struct vcpu *vcpu);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -301,6 +301,26 @@ struct cpu_px_data {
|
|||||||
uint64_t status; /* success indicator */
|
uint64_t status; /* success indicator */
|
||||||
} __attribute__((aligned(8)));
|
} __attribute__((aligned(8)));
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Info PM command from DM/VHM.
|
||||||
|
*
|
||||||
|
* The command would specify request type(i.e. get px count or data) for
|
||||||
|
* specific VM and specific VCPU with specific state number.like P(n).
|
||||||
|
*/
|
||||||
|
#define PMCMD_VMID_MASK 0xff000000
|
||||||
|
#define PMCMD_VCPUID_MASK 0x00ff0000
|
||||||
|
#define PMCMD_STATE_NUM_MASK 0x0000ff00
|
||||||
|
#define PMCMD_TYPE_MASK 0x000000ff
|
||||||
|
|
||||||
|
#define PMCMD_VMID_SHIFT 24
|
||||||
|
#define PMCMD_VCPUID_SHIFT 16
|
||||||
|
#define PMCMD_STATE_NUM_SHIFT 8
|
||||||
|
|
||||||
|
enum pm_cmd_type {
|
||||||
|
PMCMD_GET_PX_CNT,
|
||||||
|
PMCMD_GET_PX_DATA,
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @}
|
* @}
|
||||||
*/
|
*/
|
||||||
|
@ -99,6 +99,10 @@
|
|||||||
#define HC_WORLD_SWITCH _HC_ID(HC_ID, HC_ID_TRUSTY_BASE + 0x01)
|
#define HC_WORLD_SWITCH _HC_ID(HC_ID, HC_ID_TRUSTY_BASE + 0x01)
|
||||||
#define HC_GET_SEC_INFO _HC_ID(HC_ID, HC_ID_TRUSTY_BASE + 0x02)
|
#define HC_GET_SEC_INFO _HC_ID(HC_ID, HC_ID_TRUSTY_BASE + 0x02)
|
||||||
|
|
||||||
|
/* Power management */
|
||||||
|
#define HC_ID_PM_BASE 0x80UL
|
||||||
|
#define HC_PM_GET_CPU_STATE _HC_ID(HC_ID, HC_ID_PM_BASE + 0x00)
|
||||||
|
|
||||||
#define ACRN_DOM0_VMID (0UL)
|
#define ACRN_DOM0_VMID (0UL)
|
||||||
#define ACRN_INVALID_VMID (-1)
|
#define ACRN_INVALID_VMID (-1)
|
||||||
#define ACRN_INVALID_HPA (-1UL)
|
#define ACRN_INVALID_HPA (-1UL)
|
||||||
|
Loading…
Reference in New Issue
Block a user