arm: Add AArch64 hypervisor call instruction 'hvc'

This patch adds the AArch64 instruction hvc which raises an exception
from EL1 into EL2. The host OS uses this instruction to world switch
into the guest.

Change-Id: I930ee43f4f0abd4b35a68eb2a72e44e3ea6570be
This commit is contained in:
Dylan Johnson 2016-08-02 10:38:02 +01:00
parent c53a57f74f
commit 2950a95672
4 changed files with 30 additions and 4 deletions

View file

@ -840,6 +840,12 @@ HypervisorCall::HypervisorCall(ExtMachInst _machInst, uint32_t _imm) :
ArmFaultVals<HypervisorCall>(_machInst, _imm)
{}
ExceptionClass
HypervisorCall::ec(ThreadContext *tc) const
{
return from64 ? EC_HVC_64 : vals.ec;
}
ExceptionClass
HypervisorTrap::ec(ThreadContext *tc) const
{

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2010, 2012-2013 ARM Limited
* Copyright (c) 2010, 2012-2013, 2016 ARM Limited
* All rights reserved
*
* The license below extends only to copyright in the software and shall
@ -352,6 +352,8 @@ class HypervisorCall : public ArmFaultVals<HypervisorCall>
{
public:
HypervisorCall(ExtMachInst _machInst, uint32_t _imm);
ExceptionClass ec(ThreadContext *tc) const;
};
class HypervisorTrap : public ArmFaultVals<HypervisorTrap>

View file

@ -1,4 +1,4 @@
// Copyright (c) 2011-2015 ARM Limited
// Copyright (c) 2011-2016 ARM Limited
// All rights reserved
//
// The license below extends only to copyright in the software and shall
@ -250,7 +250,7 @@ namespace Aarch64
case 0x01:
return new Svc64(machInst);
case 0x02:
return new FailUnimplemented("hvc", machInst);
return new Hvc64(machInst);
case 0x03:
return new Smc64(machInst);
case 0x04:

View file

@ -1,6 +1,6 @@
// -*- mode:c++ -*-
// Copyright (c) 2011-2013 ARM Limited
// Copyright (c) 2011-2013, 2016 ARM Limited
// All rights reserved
//
// The license below extends only to copyright in the software and shall
@ -49,6 +49,24 @@ let {{
decoder_output = BasicConstructor64.subst(svcIop)
exec_output = BasicExecute.subst(svcIop)
hvcCode = '''
SCR scr = Scr64;
if (!ArmSystem::haveVirtualization(xc->tcBase()) ||
(ArmSystem::haveSecurity(xc->tcBase()) && !scr.hce)) {
fault = disabledFault();
} else {
fault = std::make_shared<HypervisorCall>(machInst, bits(machInst, 20, 5));
}
'''
hvcIop = InstObjParams("hvc", "Hvc64", "ArmStaticInst",
hvcCode, ["IsSyscall", "IsNonSpeculative",
"IsSerializeAfter"])
header_output += BasicDeclare.subst(hvcIop)
decoder_output += BasicConstructor64.subst(hvcIop)
exec_output += BasicExecute.subst(hvcIop)
# @todo: extend to take into account Virtualization.
smcCode = '''
SCR scr = Scr64;