diff --git a/hypervisor/common/trusty_hypercall.c b/hypervisor/common/trusty_hypercall.c index 8df3f0bb0..396a98a7f 100644 --- a/hypervisor/common/trusty_hypercall.c +++ b/hypervisor/common/trusty_hypercall.c @@ -26,22 +26,10 @@ int32_t hcall_world_switch(struct acrn_vcpu *vcpu) { int32_t next_world_id = !(vcpu->arch.cur_context); - int32_t ret; + int32_t ret = -EPERM; - if (next_world_id >= NR_WORLD) { - dev_dbg(ACRN_DBG_TRUSTY_HYCALL, - "%s world_id %d exceed max number of Worlds\n", - __func__, next_world_id); - ret = -EINVAL; - } else if (vcpu->vm->sworld_control.flag.supported == 0UL) { - dev_dbg(ACRN_DBG_TRUSTY_HYCALL, - "Secure World is not supported!\n"); - ret = -EPERM; - } else if (vcpu->vm->sworld_control.flag.active == 0UL) { - dev_dbg(ACRN_DBG_TRUSTY_HYCALL, - "Trusty is not initialized!\n"); - ret = -EPERM; - } else { + if ((vcpu->vm->sworld_control.flag.supported != 0UL) && (next_world_id < NR_WORLD) + && (vcpu->vm->sworld_control.flag.active != 0UL)) { switch_world(vcpu, next_world_id); ret = 0; } @@ -64,30 +52,24 @@ int32_t hcall_world_switch(struct acrn_vcpu *vcpu) */ int32_t hcall_initialize_trusty(struct acrn_vcpu *vcpu, uint64_t param) { - int32_t ret = 0; + int32_t ret = -EFAULT; struct trusty_boot_param boot_param; - if (vcpu->vm->sworld_control.flag.supported == 0UL) { - pr_err("Secure World is not supported!\n"); - ret = -EPERM; - } else if (vcpu->vm->sworld_control.flag.active != 0UL) { - pr_err("Trusty already initialized!\n"); - ret = -EPERM; - } else if (vcpu->arch.cur_context != NORMAL_WORLD) { - pr_err("%s, must initialize Trusty from Normal World!\n", __func__); - ret = -EPERM; - } else { - (void)memset(&boot_param, 0U, sizeof(boot_param)); - if (copy_from_gpa(vcpu->vm, &boot_param, param, sizeof(boot_param)) != 0) { - pr_err("%s: Unable to copy trusty_boot_param\n", __func__); - ret = -EFAULT; - } else if (!initialize_trusty(vcpu, &boot_param)) { - ret = -ENODEV; - } else { - vcpu->vm->sworld_control.flag.active = 1UL; - } - } + if ((vcpu->vm->sworld_control.flag.supported != 0UL) + && (vcpu->vm->sworld_control.flag.active == 0UL) + && (vcpu->arch.cur_context == NORMAL_WORLD)) { + (void)memset(&boot_param, 0U, sizeof(boot_param)); + if (copy_from_gpa(vcpu->vm, &boot_param, param, sizeof(boot_param)) == 0) { + if (initialize_trusty(vcpu, &boot_param)) { + vcpu->vm->sworld_control.flag.active = 1UL; + ret = 0; + } + } + } else { + ret = -EPERM; + pr_err("%s, context mismatch when initialize trusty.\n", __func__); + } return ret; } @@ -101,28 +83,24 @@ int32_t hcall_initialize_trusty(struct acrn_vcpu *vcpu, uint64_t param) int32_t hcall_save_restore_sworld_ctx(struct acrn_vcpu *vcpu) { struct acrn_vm *vm = vcpu->vm; - int32_t ret = 0; + int32_t ret = -EINVAL; - if (vm->sworld_control.flag.supported == 0UL) { - dev_dbg(ACRN_DBG_TRUSTY_HYCALL, - "Secure World is not supported!\n"); - ret = -EPERM; - } else if (!is_vcpu_bsp(vcpu)) { - /* Currently, Secure World is only running on vCPU0 */ - dev_dbg(ACRN_DBG_TRUSTY_HYCALL, - "This hypercall is only allowed from vcpu0!"); - ret = -EPERM; - } else { + if (is_vcpu_bsp(vcpu) && (vm->sworld_control.flag.supported != 0UL)) { if (vm->sworld_control.flag.active != 0UL) { save_sworld_context(vcpu); vm->sworld_control.flag.ctx_saved = 1UL; + ret = 0; } else { if (vm->sworld_control.flag.ctx_saved != 0UL) { restore_sworld_context(vcpu); vm->sworld_control.flag.ctx_saved = 0UL; vm->sworld_control.flag.active = 1UL; + ret = 0; } } + } else { + ret = -EPERM; + pr_err("%s, states mismatch when save restore sworld context.\n", __func__); } return ret;