ARM: Implement CPACR register and return Undefined Instruction when FP access is disabled.

This commit is contained in:
Gabe Black 2010-08-25 19:10:42 -05:00
parent 6368edb281
commit 54a919f225
11 changed files with 172 additions and 106 deletions

View file

@ -159,8 +159,12 @@ Reset::invoke(ThreadContext *tc)
void
UndefinedInstruction::invoke(ThreadContext *tc)
{
// If the mnemonic isn't defined this has to be an unknown instruction.
assert(unknown || mnemonic != NULL);
if (unknown) {
if (disabled) {
panic("Attempted to execute disabled instruction "
"'%s' (inst 0x%08x)", mnemonic, machInst);
} else if (unknown) {
panic("Attempted to execute unknown instruction (inst 0x%08x)",
machInst);
} else {

View file

@ -153,12 +153,15 @@ class UndefinedInstruction : public ArmFaultVals<UndefinedInstruction>
ExtMachInst machInst;
bool unknown;
const char *mnemonic;
bool disabled;
public:
UndefinedInstruction(ExtMachInst _machInst,
bool _unknown,
const char *_mnemonic = NULL) :
machInst(_machInst), unknown(_unknown), mnemonic(_mnemonic)
const char *_mnemonic = NULL,
bool _disabled = false) :
machInst(_machInst), unknown(_unknown),
mnemonic(_mnemonic), disabled(_disabled)
{
}

View file

@ -42,6 +42,7 @@
#ifndef __ARCH_ARM_INSTS_STATICINST_HH__
#define __ARCH_ARM_INSTS_STATICINST_HH__
#include "arch/arm/faults.hh"
#include "base/trace.hh"
#include "cpu/static_inst.hh"
@ -319,6 +320,16 @@ class ArmStaticInst : public StaticInst
setNextPC(xc, val);
}
}
inline Fault
disabledFault() const
{
#if FULL_SYSTEM
return new UndefinedInstruction();
#else
return new UndefinedInstruction(machInst, false, mnemonic, true);
#endif
}
};
}

View file

@ -66,17 +66,6 @@ ISA::clear()
miscRegs[MISCREG_SCTLR] = sctlr;
miscRegs[MISCREG_SCTLR_RST] = sctlr_rst;
/*
* Technically this should be 0, but we don't support those
* settings.
*/
CPACR cpacr = 0;
// Enable CP 10, 11
cpacr.cp10 = 0x3;
cpacr.cp11 = 0x3;
miscRegs[MISCREG_CPACR] = cpacr;
/* Start with an event in the mailbox */
miscRegs[MISCREG_SEV_MAILBOX] = 1;
@ -278,9 +267,9 @@ ISA::setMiscReg(int misc_reg, const MiscReg &val, ThreadContext *tc)
CPACR valCpacr = val;
newCpacr.cp10 = valCpacr.cp10;
newCpacr.cp11 = valCpacr.cp11;
if (newCpacr.cp10 != 0x3 || newCpacr.cp11 != 3) {
panic("Disabling coprocessors isn't implemented.\n");
}
//XXX d32dis isn't implemented. The manual says whether or not
//it works is implementation defined.
newCpacr.asedis = valCpacr.asedis;
newVal = newCpacr;
}
break;

View file

@ -192,14 +192,16 @@ let {{
exec_output = ""
vmsrIop = InstObjParams("vmsr", "Vmsr", "FpRegRegOp",
{ "code": "MiscDest = Op1;",
{ "code": vmsrrsEnabledCheckCode + \
"MiscDest = Op1;",
"predicate_test": predicateTest }, [])
header_output += FpRegRegOpDeclare.subst(vmsrIop);
decoder_output += FpRegRegOpConstructor.subst(vmsrIop);
exec_output += PredOpExecute.subst(vmsrIop);
vmrsIop = InstObjParams("vmrs", "Vmrs", "FpRegRegOp",
{ "code": "Dest = MiscOp1;",
{ "code": vmsrrsEnabledCheckCode + \
"Dest = MiscOp1;",
"predicate_test": predicateTest }, [])
header_output += FpRegRegOpDeclare.subst(vmrsIop);
decoder_output += FpRegRegOpConstructor.subst(vmrsIop);
@ -213,7 +215,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmrsApsrIop);
exec_output += PredOpExecute.subst(vmrsApsrIop);
vmovImmSCode = '''
vmovImmSCode = vfpEnabledCheckCode + '''
FpDest.uw = bits(imm, 31, 0);
'''
vmovImmSIop = InstObjParams("vmov", "VmovImmS", "FpRegImmOp",
@ -223,7 +225,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vmovImmSIop);
exec_output += PredOpExecute.subst(vmovImmSIop);
vmovImmDCode = '''
vmovImmDCode = vfpEnabledCheckCode + '''
FpDestP0.uw = bits(imm, 31, 0);
FpDestP1.uw = bits(imm, 63, 32);
'''
@ -234,7 +236,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vmovImmDIop);
exec_output += PredOpExecute.subst(vmovImmDIop);
vmovImmQCode = '''
vmovImmQCode = vfpEnabledCheckCode + '''
FpDestP0.uw = bits(imm, 31, 0);
FpDestP1.uw = bits(imm, 63, 32);
FpDestP2.uw = bits(imm, 31, 0);
@ -247,7 +249,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vmovImmQIop);
exec_output += PredOpExecute.subst(vmovImmQIop);
vmovRegSCode = '''
vmovRegSCode = vfpEnabledCheckCode + '''
FpDest.uw = FpOp1.uw;
'''
vmovRegSIop = InstObjParams("vmov", "VmovRegS", "FpRegRegOp",
@ -257,7 +259,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vmovRegSIop);
exec_output += PredOpExecute.subst(vmovRegSIop);
vmovRegDCode = '''
vmovRegDCode = vfpEnabledCheckCode + '''
FpDestP0.uw = FpOp1P0.uw;
FpDestP1.uw = FpOp1P1.uw;
'''
@ -268,7 +270,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vmovRegDIop);
exec_output += PredOpExecute.subst(vmovRegDIop);
vmovRegQCode = '''
vmovRegQCode = vfpEnabledCheckCode + '''
FpDestP0.uw = FpOp1P0.uw;
FpDestP1.uw = FpOp1P1.uw;
FpDestP2.uw = FpOp1P2.uw;
@ -281,7 +283,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vmovRegQIop);
exec_output += PredOpExecute.subst(vmovRegQIop);
vmovCoreRegBCode = '''
vmovCoreRegBCode = vfpEnabledCheckCode + '''
FpDest.uw = insertBits(FpDest.uw, imm * 8 + 7, imm * 8, Op1.ub);
'''
vmovCoreRegBIop = InstObjParams("vmov", "VmovCoreRegB", "FpRegRegImmOp",
@ -291,7 +293,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovCoreRegBIop);
exec_output += PredOpExecute.subst(vmovCoreRegBIop);
vmovCoreRegHCode = '''
vmovCoreRegHCode = vfpEnabledCheckCode + '''
FpDest.uw = insertBits(FpDest.uw, imm * 16 + 15, imm * 16, Op1.uh);
'''
vmovCoreRegHIop = InstObjParams("vmov", "VmovCoreRegH", "FpRegRegImmOp",
@ -301,7 +303,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovCoreRegHIop);
exec_output += PredOpExecute.subst(vmovCoreRegHIop);
vmovCoreRegWCode = '''
vmovCoreRegWCode = vfpEnabledCheckCode + '''
FpDest.uw = Op1.uw;
'''
vmovCoreRegWIop = InstObjParams("vmov", "VmovCoreRegW", "FpRegRegOp",
@ -311,7 +313,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vmovCoreRegWIop);
exec_output += PredOpExecute.subst(vmovCoreRegWIop);
vmovRegCoreUBCode = '''
vmovRegCoreUBCode = vfpEnabledCheckCode + '''
assert(imm < 4);
Dest = bits(FpOp1.uw, imm * 8 + 7, imm * 8);
'''
@ -322,7 +324,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovRegCoreUBIop);
exec_output += PredOpExecute.subst(vmovRegCoreUBIop);
vmovRegCoreUHCode = '''
vmovRegCoreUHCode = vfpEnabledCheckCode + '''
assert(imm < 2);
Dest = bits(FpOp1.uw, imm * 16 + 15, imm * 16);
'''
@ -333,7 +335,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovRegCoreUHIop);
exec_output += PredOpExecute.subst(vmovRegCoreUHIop);
vmovRegCoreSBCode = '''
vmovRegCoreSBCode = vfpEnabledCheckCode + '''
assert(imm < 4);
Dest = sext<8>(bits(FpOp1.uw, imm * 8 + 7, imm * 8));
'''
@ -344,7 +346,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovRegCoreSBIop);
exec_output += PredOpExecute.subst(vmovRegCoreSBIop);
vmovRegCoreSHCode = '''
vmovRegCoreSHCode = vfpEnabledCheckCode + '''
assert(imm < 2);
Dest = sext<16>(bits(FpOp1.uw, imm * 16 + 15, imm * 16));
'''
@ -355,7 +357,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmovRegCoreSHIop);
exec_output += PredOpExecute.subst(vmovRegCoreSHIop);
vmovRegCoreWCode = '''
vmovRegCoreWCode = vfpEnabledCheckCode + '''
Dest = FpOp1.uw;
'''
vmovRegCoreWIop = InstObjParams("vmov", "VmovRegCoreW", "FpRegRegOp",
@ -365,7 +367,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vmovRegCoreWIop);
exec_output += PredOpExecute.subst(vmovRegCoreWIop);
vmov2Reg2CoreCode = '''
vmov2Reg2CoreCode = vfpEnabledCheckCode + '''
FpDestP0.uw = Op1.uw;
FpDestP1.uw = Op2.uw;
'''
@ -376,7 +378,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vmov2Reg2CoreIop);
exec_output += PredOpExecute.subst(vmov2Reg2CoreIop);
vmov2Core2RegCode = '''
vmov2Core2RegCode = vfpEnabledCheckCode + '''
Dest.uw = FpOp2P0.uw;
Op1.uw = FpOp2P1.uw;
'''
@ -394,7 +396,7 @@ let {{
decoder_output = ""
exec_output = ""
singleCode = '''
singleCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
FpDest = %(op)s;
Fpscr = fpscr;
@ -402,7 +404,7 @@ let {{
singleBinOp = "binaryOp(fpscr, FpOp1, FpOp2," + \
"%(func)s, fpscr.fz, fpscr.dn, fpscr.rMode)"
singleUnaryOp = "unaryOp(fpscr, FpOp1, %(func)s, fpscr.fz, fpscr.rMode)"
doubleCode = '''
doubleCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double dest = %(op)s;
Fpscr = fpscr;
@ -500,7 +502,7 @@ let {{
decoder_output = ""
exec_output = ""
vmlaSCode = '''
vmlaSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
float mid = binaryOp(fpscr, FpOp1, FpOp2,
fpMulS, fpscr.fz, fpscr.dn, fpscr.rMode);
@ -515,7 +517,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vmlaSIop);
exec_output += PredOpExecute.subst(vmlaSIop);
vmlaDCode = '''
vmlaDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double mid = binaryOp(fpscr, dbl(FpOp1P0.uw, FpOp1P1.uw),
dbl(FpOp2P0.uw, FpOp2P1.uw),
@ -534,7 +536,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vmlaDIop);
exec_output += PredOpExecute.subst(vmlaDIop);
vmlsSCode = '''
vmlsSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
float mid = binaryOp(fpscr, FpOp1, FpOp2,
fpMulS, fpscr.fz, fpscr.dn, fpscr.rMode);
@ -549,7 +551,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vmlsSIop);
exec_output += PredOpExecute.subst(vmlsSIop);
vmlsDCode = '''
vmlsDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double mid = binaryOp(fpscr, dbl(FpOp1P0.uw, FpOp1P1.uw),
dbl(FpOp2P0.uw, FpOp2P1.uw),
@ -568,7 +570,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vmlsDIop);
exec_output += PredOpExecute.subst(vmlsDIop);
vnmlaSCode = '''
vnmlaSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
float mid = binaryOp(fpscr, FpOp1, FpOp2,
fpMulS, fpscr.fz, fpscr.dn, fpscr.rMode);
@ -583,7 +585,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vnmlaSIop);
exec_output += PredOpExecute.subst(vnmlaSIop);
vnmlaDCode = '''
vnmlaDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double mid = binaryOp(fpscr, dbl(FpOp1P0.uw, FpOp1P1.uw),
dbl(FpOp2P0.uw, FpOp2P1.uw),
@ -602,7 +604,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vnmlaDIop);
exec_output += PredOpExecute.subst(vnmlaDIop);
vnmlsSCode = '''
vnmlsSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
float mid = binaryOp(fpscr, FpOp1, FpOp2,
fpMulS, fpscr.fz, fpscr.dn, fpscr.rMode);
@ -617,7 +619,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vnmlsSIop);
exec_output += PredOpExecute.subst(vnmlsSIop);
vnmlsDCode = '''
vnmlsDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double mid = binaryOp(fpscr, dbl(FpOp1P0.uw, FpOp1P1.uw),
dbl(FpOp2P0.uw, FpOp2P1.uw),
@ -636,7 +638,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vnmlsDIop);
exec_output += PredOpExecute.subst(vnmlsDIop);
vnmulSCode = '''
vnmulSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
FpDest = -binaryOp(fpscr, FpOp1, FpOp2, fpMulS,
fpscr.fz, fpscr.dn, fpscr.rMode);
@ -649,7 +651,7 @@ let {{
decoder_output += FpRegRegRegOpConstructor.subst(vnmulSIop);
exec_output += PredOpExecute.subst(vnmulSIop);
vnmulDCode = '''
vnmulDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double dest = -binaryOp(fpscr, dbl(FpOp1P0.uw, FpOp1P1.uw),
dbl(FpOp2P0.uw, FpOp2P1.uw),
@ -673,7 +675,7 @@ let {{
decoder_output = ""
exec_output = ""
vcvtUIntFpSCode = '''
vcvtUIntFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.uw) : "m" (FpOp1.uw));
@ -689,7 +691,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtUIntFpSIop);
exec_output += PredOpExecute.subst(vcvtUIntFpSIop);
vcvtUIntFpDCode = '''
vcvtUIntFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1P0.uw) : "m" (FpOp1P0.uw));
@ -707,7 +709,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtUIntFpDIop);
exec_output += PredOpExecute.subst(vcvtUIntFpDIop);
vcvtSIntFpSCode = '''
vcvtSIntFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.sw) : "m" (FpOp1.sw));
@ -723,7 +725,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtSIntFpSIop);
exec_output += PredOpExecute.subst(vcvtSIntFpSIop);
vcvtSIntFpDCode = '''
vcvtSIntFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1P0.sw) : "m" (FpOp1P0.sw));
@ -741,7 +743,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtSIntFpDIop);
exec_output += PredOpExecute.subst(vcvtSIntFpDIop);
vcvtFpUIntSRCode = '''
vcvtFpUIntSRCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
vfpFlushToZero(fpscr, FpOp1);
@ -758,7 +760,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpUIntSRIop);
exec_output += PredOpExecute.subst(vcvtFpUIntSRIop);
vcvtFpUIntDRCode = '''
vcvtFpUIntDRCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -777,7 +779,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpUIntDRIop);
exec_output += PredOpExecute.subst(vcvtFpUIntDRIop);
vcvtFpSIntSRCode = '''
vcvtFpSIntSRCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
vfpFlushToZero(fpscr, FpOp1);
@ -794,7 +796,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSIntSRIop);
exec_output += PredOpExecute.subst(vcvtFpSIntSRIop);
vcvtFpSIntDRCode = '''
vcvtFpSIntDRCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -813,7 +815,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSIntDRIop);
exec_output += PredOpExecute.subst(vcvtFpSIntDRIop);
vcvtFpUIntSCode = '''
vcvtFpUIntSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -831,7 +833,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpUIntSIop);
exec_output += PredOpExecute.subst(vcvtFpUIntSIop);
vcvtFpUIntDCode = '''
vcvtFpUIntDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -851,7 +853,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpUIntDIop);
exec_output += PredOpExecute.subst(vcvtFpUIntDIop);
vcvtFpSIntSCode = '''
vcvtFpSIntSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -869,7 +871,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSIntSIop);
exec_output += PredOpExecute.subst(vcvtFpSIntSIop);
vcvtFpSIntDCode = '''
vcvtFpSIntDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -889,7 +891,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSIntDIop);
exec_output += PredOpExecute.subst(vcvtFpSIntDIop);
vcvtFpSFpDCode = '''
vcvtFpSFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -908,7 +910,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSFpDIop);
exec_output += PredOpExecute.subst(vcvtFpSFpDIop);
vcvtFpDFpSCode = '''
vcvtFpDFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -926,7 +928,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpDFpSIop);
exec_output += PredOpExecute.subst(vcvtFpDFpSIop);
vcvtFpHTFpSCode = '''
vcvtFpHTFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -944,7 +946,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpHTFpSIop);
exec_output += PredOpExecute.subst(vcvtFpHTFpSIop);
vcvtFpHBFpSCode = '''
vcvtFpHBFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1) : "m" (FpOp1));
@ -961,7 +963,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpHBFpSIop);
exec_output += PredOpExecute.subst(vcvtFpHBFpSIop);
vcvtFpSFpHTCode = '''
vcvtFpSFpHTCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -981,7 +983,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSFpHTIop);
exec_output += PredOpExecute.subst(vcvtFpSFpHTIop);
vcvtFpSFpHBCode = '''
vcvtFpSFpHBCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1001,7 +1003,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcvtFpSFpHBIop);
exec_output += PredOpExecute.subst(vcvtFpSFpHBIop);
vcmpSCode = '''
vcmpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpDest, FpOp1);
if (FpDest == FpOp1) {
@ -1029,7 +1031,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcmpSIop);
exec_output += PredOpExecute.subst(vcmpSIop);
vcmpDCode = '''
vcmpDCode = vfpEnabledCheckCode + '''
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
double cDest = dbl(FpDestP0.uw, FpDestP1.uw);
FPSCR fpscr = Fpscr;
@ -1059,7 +1061,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcmpDIop);
exec_output += PredOpExecute.subst(vcmpDIop);
vcmpZeroSCode = '''
vcmpZeroSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpDest);
// This only handles imm == 0 for now.
@ -1087,7 +1089,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vcmpZeroSIop);
exec_output += PredOpExecute.subst(vcmpZeroSIop);
vcmpZeroDCode = '''
vcmpZeroDCode = vfpEnabledCheckCode + '''
// This only handles imm == 0 for now.
assert(imm == 0);
double cDest = dbl(FpDestP0.uw, FpDestP1.uw);
@ -1116,7 +1118,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vcmpZeroDIop);
exec_output += PredOpExecute.subst(vcmpZeroDIop);
vcmpeSCode = '''
vcmpeSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpDest, FpOp1);
if (FpDest == FpOp1) {
@ -1138,7 +1140,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcmpeSIop);
exec_output += PredOpExecute.subst(vcmpeSIop);
vcmpeDCode = '''
vcmpeDCode = vfpEnabledCheckCode + '''
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
double cDest = dbl(FpDestP0.uw, FpDestP1.uw);
FPSCR fpscr = Fpscr;
@ -1162,7 +1164,7 @@ let {{
decoder_output += FpRegRegOpConstructor.subst(vcmpeDIop);
exec_output += PredOpExecute.subst(vcmpeDIop);
vcmpeZeroSCode = '''
vcmpeZeroSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpDest);
if (FpDest == imm) {
@ -1184,7 +1186,7 @@ let {{
decoder_output += FpRegImmOpConstructor.subst(vcmpeZeroSIop);
exec_output += PredOpExecute.subst(vcmpeZeroSIop);
vcmpeZeroDCode = '''
vcmpeZeroDCode = vfpEnabledCheckCode + '''
double cDest = dbl(FpDestP0.uw, FpDestP1.uw);
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, cDest);
@ -1214,7 +1216,7 @@ let {{
decoder_output = ""
exec_output = ""
vcvtFpSFixedSCode = '''
vcvtFpSFixedSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1231,7 +1233,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpSFixedSIop);
exec_output += PredOpExecute.subst(vcvtFpSFixedSIop);
vcvtFpSFixedDCode = '''
vcvtFpSFixedDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -1251,7 +1253,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpSFixedDIop);
exec_output += PredOpExecute.subst(vcvtFpSFixedDIop);
vcvtFpUFixedSCode = '''
vcvtFpUFixedSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1268,7 +1270,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpUFixedSIop);
exec_output += PredOpExecute.subst(vcvtFpUFixedSIop);
vcvtFpUFixedDCode = '''
vcvtFpUFixedDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -1288,7 +1290,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpUFixedDIop);
exec_output += PredOpExecute.subst(vcvtFpUFixedDIop);
vcvtSFixedFpSCode = '''
vcvtSFixedFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.sw) : "m" (FpOp1.sw));
@ -1304,7 +1306,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtSFixedFpSIop);
exec_output += PredOpExecute.subst(vcvtSFixedFpSIop);
vcvtSFixedFpDCode = '''
vcvtSFixedFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
uint64_t mid = ((uint64_t)FpOp1P0.uw | ((uint64_t)FpOp1P1.uw << 32));
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1323,7 +1325,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtSFixedFpDIop);
exec_output += PredOpExecute.subst(vcvtSFixedFpDIop);
vcvtUFixedFpSCode = '''
vcvtUFixedFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.uw) : "m" (FpOp1.uw));
@ -1339,7 +1341,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtUFixedFpSIop);
exec_output += PredOpExecute.subst(vcvtUFixedFpSIop);
vcvtUFixedFpDCode = '''
vcvtUFixedFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
uint64_t mid = ((uint64_t)FpOp1P0.uw | ((uint64_t)FpOp1P1.uw << 32));
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1358,7 +1360,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtUFixedFpDIop);
exec_output += PredOpExecute.subst(vcvtUFixedFpDIop);
vcvtFpSHFixedSCode = '''
vcvtFpSHFixedSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1376,7 +1378,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpSHFixedSIop);
exec_output += PredOpExecute.subst(vcvtFpSHFixedSIop);
vcvtFpSHFixedDCode = '''
vcvtFpSHFixedDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -1397,7 +1399,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpSHFixedDIop);
exec_output += PredOpExecute.subst(vcvtFpSHFixedDIop);
vcvtFpUHFixedSCode = '''
vcvtFpUHFixedSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
vfpFlushToZero(fpscr, FpOp1);
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1415,7 +1417,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpUHFixedSIop);
exec_output += PredOpExecute.subst(vcvtFpUHFixedSIop);
vcvtFpUHFixedDCode = '''
vcvtFpUHFixedDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
double cOp1 = dbl(FpOp1P0.uw, FpOp1P1.uw);
vfpFlushToZero(fpscr, cOp1);
@ -1436,7 +1438,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtFpUHFixedDIop);
exec_output += PredOpExecute.subst(vcvtFpUHFixedDIop);
vcvtSHFixedFpSCode = '''
vcvtSHFixedFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.sh) : "m" (FpOp1.sh));
@ -1453,7 +1455,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtSHFixedFpSIop);
exec_output += PredOpExecute.subst(vcvtSHFixedFpSIop);
vcvtSHFixedFpDCode = '''
vcvtSHFixedFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
uint64_t mid = ((uint64_t)FpOp1P0.uw | ((uint64_t)FpOp1P1.uw << 32));
VfpSavedState state = prepFpState(fpscr.rMode);
@ -1473,7 +1475,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtSHFixedFpDIop);
exec_output += PredOpExecute.subst(vcvtSHFixedFpDIop);
vcvtUHFixedFpSCode = '''
vcvtUHFixedFpSCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
VfpSavedState state = prepFpState(fpscr.rMode);
__asm__ __volatile__("" : "=m" (FpOp1.uh) : "m" (FpOp1.uh));
@ -1490,7 +1492,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vcvtUHFixedFpSIop);
exec_output += PredOpExecute.subst(vcvtUHFixedFpSIop);
vcvtUHFixedFpDCode = '''
vcvtUHFixedFpDCode = vfpEnabledCheckCode + '''
FPSCR fpscr = Fpscr;
uint64_t mid = ((uint64_t)FpOp1P0.uw | ((uint64_t)FpOp1P1.uw << 32));
VfpSavedState state = prepFpState(fpscr.rMode);

View file

@ -619,6 +619,13 @@ output exec {{
}
}};
let {{
simdEnabledCheckCode = '''
if (!neonEnabled(Cpacr, Cpsr, Fpexc))
return disabledFault();
'''
}};
let {{
header_output = ""
@ -634,7 +641,7 @@ let {{
def threeEqualRegInst(name, Name, types, rCount, op,
readDest=False, pairwise=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, srcReg2, destReg;
'''
for reg in range(rCount):
@ -694,7 +701,7 @@ let {{
def threeEqualRegInstFp(name, Name, types, rCount, op,
readDest=False, pairwise=False, toInt=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
typedef FloatReg FloatVect[rCount];
FloatVect srcRegs1, srcRegs2;
'''
@ -789,7 +796,7 @@ let {{
if bigDest:
destCnt = 4
destPrefix = 'Big'
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
%sRegVect srcReg1;
%sRegVect srcReg2;
%sRegVect destReg;
@ -852,7 +859,7 @@ let {{
def twoEqualRegInst(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, srcReg2, destReg;
'''
for reg in range(rCount):
@ -897,7 +904,7 @@ let {{
def twoRegLongInst(name, Name, types, op, readDest=False):
global header_output, exec_output
rCount = 2
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, srcReg2;
BigRegVect destReg;
'''
@ -943,7 +950,7 @@ let {{
def twoEqualRegInstFp(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
typedef FloatReg FloatVect[rCount];
FloatVect srcRegs1, srcRegs2, destRegs;
'''
@ -989,7 +996,7 @@ let {{
def twoRegShiftInst(name, Name, types, rCount, op,
readDest=False, toInt=False, fromInt=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcRegs1, destRegs;
'''
for reg in range(rCount):
@ -1044,7 +1051,7 @@ let {{
def twoRegNarrowShiftInst(name, Name, types, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
BigRegVect srcReg1;
RegVect destReg;
'''
@ -1087,7 +1094,7 @@ let {{
def twoRegLongShiftInst(name, Name, types, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1;
BigRegVect destReg;
'''
@ -1130,7 +1137,7 @@ let {{
def twoRegMiscInst(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, destReg;
'''
for reg in range(rCount):
@ -1172,7 +1179,7 @@ let {{
def twoRegMiscScInst(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, destReg;
'''
for reg in range(rCount):
@ -1213,7 +1220,7 @@ let {{
def twoRegMiscScramble(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1, destReg;
'''
for reg in range(rCount):
@ -1248,7 +1255,7 @@ let {{
def twoRegMiscInstFp(name, Name, types, rCount, op,
readDest=False, toInt=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
typedef FloatReg FloatVect[rCount];
FloatVect srcRegs1;
'''
@ -1312,7 +1319,7 @@ let {{
def twoRegCondenseInst(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcRegs;
BigRegVect destReg;
'''
@ -1355,7 +1362,7 @@ let {{
def twoRegNarrowMiscInst(name, Name, types, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
BigRegVect srcReg1;
RegVect destReg;
'''
@ -1398,7 +1405,7 @@ let {{
def oneRegImmInst(name, Name, types, rCount, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect destReg;
'''
if readDest:
@ -1435,7 +1442,7 @@ let {{
def twoRegLongMiscInst(name, Name, types, op, readDest=False):
global header_output, exec_output
eWalkCode = '''
eWalkCode = simdEnabledCheckCode + '''
RegVect srcReg1;
BigRegVect destReg;
'''

View file

@ -205,6 +205,7 @@ def operands {{
'Fpsr': ('ControlReg', 'uw', 'MISCREG_FPSR', None, 2),
'Fpsid': ('ControlReg', 'uw', 'MISCREG_FPSID', None, 2),
'Fpscr': ('ControlReg', 'uw', 'MISCREG_FPSCR', None, 2),
'Cpacr': ('ControlReg', 'uw', 'MISCREG_CPACR', (None, None, 'IsControl'), 2),
'Fpexc': ('ControlReg', 'uw', 'MISCREG_FPEXC', None, 2),
'Sctlr': ('ControlReg', 'uw', 'MISCREG_SCTLR', None, 2),
'SevMailbox': ('ControlReg', 'uw', 'MISCREG_SEV_MAILBOX', None, 2),

View file

@ -37,6 +37,18 @@
//
// Authors: Gabe Black
let {{
vfpEnabledCheckCode = '''
if (!vfpEnabled(Cpacr, Cpsr, Fpexc))
return disabledFault();
'''
vmsrrsEnabledCheckCode = '''
if (!vfpEnabled(Cpacr, Cpsr))
return disabledFault();
'''
}};
def template FpRegRegOpDeclare {{
class %(class_name)s : public %(base_class)s
{

View file

@ -354,6 +354,12 @@ namespace ArmISA
Bitfield<31> n;
EndBitUnion(FPSCR)
BitUnion32(FPEXC)
Bitfield<31> ex;
Bitfield<30> en;
Bitfield<29, 0> subArchDefined;
EndBitUnion(FPEXC)
BitUnion32(MVFR0)
Bitfield<3, 0> advSimdRegisters;
Bitfield<7, 4> singlePrecision;

View file

@ -78,6 +78,18 @@ ArmLiveProcess::startup()
{
LiveProcess::startup();
argsInit(MachineBytes, VMPageSize);
for (int i = 0; i < contextIds.size(); i++) {
ThreadContext * tc = system->getThreadContext(contextIds[i]);
CPACR cpacr = tc->readMiscReg(MISCREG_CPACR);
// Enable the floating point coprocessors.
cpacr.cp10 = 0x3;
cpacr.cp11 = 0x3;
tc->setMiscReg(MISCREG_CPACR, cpacr);
// Generically enable floating point support.
FPEXC fpexc = tc->readMiscReg(MISCREG_FPEXC);
fpexc.en = 1;
tc->setMiscReg(MISCREG_FPEXC, fpexc);
}
}
void

View file

@ -146,6 +146,25 @@ namespace ArmISA {
return !inUserMode(tc);
}
static inline bool
vfpEnabled(CPACR cpacr, CPSR cpsr)
{
return cpacr.cp10 == 0x3 ||
(cpacr.cp10 == 0x2 && inPrivilegedMode(cpsr));
}
static inline bool
vfpEnabled(CPACR cpacr, CPSR cpsr, FPEXC fpexc)
{
return fpexc.en && vfpEnabled(cpacr, cpsr);
}
static inline bool
neonEnabled(CPACR cpacr, CPSR cpsr, FPEXC fpexc)
{
return !cpacr.asedis && vfpEnabled(cpacr, cpsr, fpexc);
}
uint64_t getArgument(ThreadContext *tc, int number, bool fp);
Fault setCp15Register(uint32_t &Rd, int CRn, int opc1, int CRm, int opc2);