ARM: Fix VFP enabled checks for mem instructions

This commit is contained in:
Ali Saidi 2010-08-25 19:10:42 -05:00
parent 63464d950e
commit 99fafb72b8
9 changed files with 60 additions and 25 deletions

View file

@ -139,6 +139,8 @@ ISA::clear()
(0 << 2) | // 3:2 (0 << 2) | // 3:2
0; // 1:0 0; // 1:0
miscRegs[MISCREG_CPACR] = 0;
miscRegs[MISCREG_FPSID] = 0x410430A0;
//XXX We need to initialize the rest of the state. //XXX We need to initialize the rest of the state.
} }

View file

@ -192,14 +192,14 @@ let {{
exec_output = "" exec_output = ""
vmsrIop = InstObjParams("vmsr", "Vmsr", "FpRegRegOp", vmsrIop = InstObjParams("vmsr", "Vmsr", "FpRegRegOp",
{ "code": vmsrrsEnabledCheckCode + \ { "code": vmsrEnabledCheckCode + \
"MiscDest = Op1;", "MiscDest = Op1;",
"predicate_test": predicateTest }, []) "predicate_test": predicateTest }, [])
header_output += FpRegRegOpDeclare.subst(vmsrIop); header_output += FpRegRegOpDeclare.subst(vmsrIop);
decoder_output += FpRegRegOpConstructor.subst(vmsrIop); decoder_output += FpRegRegOpConstructor.subst(vmsrIop);
exec_output += PredOpExecute.subst(vmsrIop); exec_output += PredOpExecute.subst(vmsrIop);
vmsrFpscrCode = vmsrrsEnabledCheckCode + ''' vmsrFpscrCode = vmsrEnabledCheckCode + '''
Fpscr = Op1 & ~FpCondCodesMask; Fpscr = Op1 & ~FpCondCodesMask;
FpCondCodes = Op1 & FpCondCodesMask; FpCondCodes = Op1 & FpCondCodesMask;
''' '''
@ -211,7 +211,7 @@ let {{
exec_output += PredOpExecute.subst(vmsrFpscrIop); exec_output += PredOpExecute.subst(vmsrFpscrIop);
vmrsIop = InstObjParams("vmrs", "Vmrs", "FpRegRegOp", vmrsIop = InstObjParams("vmrs", "Vmrs", "FpRegRegOp",
{ "code": vmsrrsEnabledCheckCode + \ { "code": vmrsEnabledCheckCode + \
"Dest = MiscOp1;", "Dest = MiscOp1;",
"predicate_test": predicateTest }, []) "predicate_test": predicateTest }, [])
header_output += FpRegRegOpDeclare.subst(vmrsIop); header_output += FpRegRegOpDeclare.subst(vmrsIop);
@ -219,14 +219,14 @@ let {{
exec_output += PredOpExecute.subst(vmrsIop); exec_output += PredOpExecute.subst(vmrsIop);
vmrsFpscrIop = InstObjParams("vmrs", "VmrsFpscr", "FpRegRegOp", vmrsFpscrIop = InstObjParams("vmrs", "VmrsFpscr", "FpRegRegOp",
{ "code": vmsrrsEnabledCheckCode + \ { "code": vmrsEnabledCheckCode + \
"Dest = Fpscr | FpCondCodes;", "Dest = Fpscr | FpCondCodes;",
"predicate_test": predicateTest }, []) "predicate_test": predicateTest }, [])
header_output += FpRegRegOpDeclare.subst(vmrsFpscrIop); header_output += FpRegRegOpDeclare.subst(vmrsFpscrIop);
decoder_output += FpRegRegOpConstructor.subst(vmrsFpscrIop); decoder_output += FpRegRegOpConstructor.subst(vmrsFpscrIop);
exec_output += PredOpExecute.subst(vmrsFpscrIop); exec_output += PredOpExecute.subst(vmrsFpscrIop);
vmrsApsrCode = vmsrrsEnabledCheckCode + ''' vmrsApsrCode = vmrsEnabledCheckCode + '''
Dest = (MiscOp1 & imm) | (Dest & ~imm); Dest = (MiscOp1 & imm) | (Dest & ~imm);
''' '''
vmrsApsrIop = InstObjParams("vmrs", "VmrsApsr", "FpRegRegImmOp", vmrsApsrIop = InstObjParams("vmrs", "VmrsApsr", "FpRegRegImmOp",
@ -236,7 +236,7 @@ let {{
decoder_output += FpRegRegImmOpConstructor.subst(vmrsApsrIop); decoder_output += FpRegRegImmOpConstructor.subst(vmrsApsrIop);
exec_output += PredOpExecute.subst(vmrsApsrIop); exec_output += PredOpExecute.subst(vmrsApsrIop);
vmrsApsrFpscrCode = vmsrrsEnabledCheckCode + ''' vmrsApsrFpscrCode = vmrsEnabledCheckCode + '''
assert((imm & ~FpCondCodesMask) == 0); assert((imm & ~FpCondCodesMask) == 0);
Dest = (FpCondCodes & imm) | (Dest & ~imm); Dest = (FpCondCodes & imm) | (Dest & ~imm);
''' '''

View file

@ -160,6 +160,10 @@ let {{
if not self.post: if not self.post:
eaCode += self.offset eaCode += self.offset
eaCode += ";" eaCode += ";"
if self.flavor == "fp":
eaCode += vfpEnabledCheckCode
self.codeBlobs["ea_code"] = eaCode self.codeBlobs["ea_code"] = eaCode
# Code that actually handles the access # Code that actually handles the access
@ -220,6 +224,10 @@ let {{
if not self.post: if not self.post:
eaCode += self.offset eaCode += self.offset
eaCode += ";" eaCode += ";"
if self.flavor == "fp":
eaCode += vfpEnabledCheckCode
self.codeBlobs["ea_code"] = eaCode self.codeBlobs["ea_code"] = eaCode
# Code that actually handles the access # Code that actually handles the access

View file

@ -59,7 +59,7 @@ let {{
microLdrFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrFpUop', microLdrFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrFpUop',
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microLdrFpUopCode, {'memacc_code': microLdrFpUopCode,
'ea_code': 'ea_code': vfpEnabledCheckCode +
'EA = Rb + (up ? imm : -imm);', 'EA = Rb + (up ? imm : -imm);',
'predicate_test': predicateTest}, 'predicate_test': predicateTest},
['IsMicroop']) ['IsMicroop'])
@ -68,7 +68,7 @@ let {{
microLdrDBFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrDBFpUop', microLdrDBFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrDBFpUop',
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microLdrFpUopCode, {'memacc_code': microLdrFpUopCode,
'ea_code': ''' 'ea_code': vfpEnabledCheckCode + '''
EA = Rb + (up ? imm : -imm) + EA = Rb + (up ? imm : -imm) +
(((CPSR)Cpsr).e ? 4 : 0); (((CPSR)Cpsr).e ? 4 : 0);
''', ''',
@ -79,7 +79,7 @@ let {{
microLdrDTFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrDTFpUop', microLdrDTFpUopIop = InstObjParams('ldrfp_uop', 'MicroLdrDTFpUop',
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microLdrFpUopCode, {'memacc_code': microLdrFpUopCode,
'ea_code': ''' 'ea_code': vfpEnabledCheckCode + '''
EA = Rb + (up ? imm : -imm) - EA = Rb + (up ? imm : -imm) -
(((CPSR)Cpsr).e ? 4 : 0); (((CPSR)Cpsr).e ? 4 : 0);
''', ''',
@ -117,7 +117,8 @@ let {{
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microStrFpUopCode, {'memacc_code': microStrFpUopCode,
'postacc_code': "", 'postacc_code': "",
'ea_code': 'EA = Rb + (up ? imm : -imm);', 'ea_code': vfpEnabledCheckCode +
'EA = Rb + (up ? imm : -imm);',
'predicate_test': predicateTest}, 'predicate_test': predicateTest},
['IsMicroop']) ['IsMicroop'])
@ -126,7 +127,7 @@ let {{
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microStrFpUopCode, {'memacc_code': microStrFpUopCode,
'postacc_code': "", 'postacc_code': "",
'ea_code': ''' 'ea_code': vfpEnabledCheckCode + '''
EA = Rb + (up ? imm : -imm) + EA = Rb + (up ? imm : -imm) +
(((CPSR)Cpsr).e ? 4 : 0); (((CPSR)Cpsr).e ? 4 : 0);
''', ''',
@ -138,7 +139,7 @@ let {{
'MicroMemOp', 'MicroMemOp',
{'memacc_code': microStrFpUopCode, {'memacc_code': microStrFpUopCode,
'postacc_code': "", 'postacc_code': "",
'ea_code': ''' 'ea_code': vfpEnabledCheckCode + '''
EA = Rb + (up ? imm : -imm) - EA = Rb + (up ? imm : -imm) -
(((CPSR)Cpsr).e ? 4 : 0); (((CPSR)Cpsr).e ? 4 : 0);
''', ''',
@ -222,7 +223,7 @@ let {{
{ 'mem_decl' : memDecl, { 'mem_decl' : memDecl,
'size' : size, 'size' : size,
'memacc_code' : loadMemAccCode, 'memacc_code' : loadMemAccCode,
'ea_code' : eaCode, 'ea_code' : simdEnabledCheckCode + eaCode,
'predicate_test' : predicateTest }, 'predicate_test' : predicateTest },
[ 'IsMicroop', 'IsMemRef', 'IsLoad' ]) [ 'IsMicroop', 'IsMemRef', 'IsLoad' ])
storeIop = InstObjParams('strneon%(size)d_uop' % subst, storeIop = InstObjParams('strneon%(size)d_uop' % subst,
@ -231,7 +232,7 @@ let {{
{ 'mem_decl' : memDecl, { 'mem_decl' : memDecl,
'size' : size, 'size' : size,
'memacc_code' : storeMemAccCode, 'memacc_code' : storeMemAccCode,
'ea_code' : eaCode, 'ea_code' : simdEnabledCheckCode + eaCode,
'predicate_test' : predicateTest }, 'predicate_test' : predicateTest },
[ 'IsMicroop', 'IsMemRef', 'IsStore' ]) [ 'IsMicroop', 'IsMemRef', 'IsStore' ])

View file

@ -619,13 +619,6 @@ output exec {{
} }
}}; }};
let {{
simdEnabledCheckCode = '''
if (!neonEnabled(Cpacr, Cpsr, Fpexc))
return disabledFault();
'''
}};
let {{ let {{
header_output = "" header_output = ""
@ -3235,7 +3228,7 @@ let {{
RegVect srcReg1, srcReg2, destReg; RegVect srcReg1, srcReg2, destReg;
''' '''
for reg in range(rCount): for reg in range(rCount):
eWalkCode += ''' eWalkCode += simdEnabledCheckCode + '''
srcReg1.regs[%(reg)d] = htog(FpOp1P%(reg)d.uw); srcReg1.regs[%(reg)d] = htog(FpOp1P%(reg)d.uw);
srcReg2.regs[%(reg)d] = htog(FpOp2P%(reg)d.uw); srcReg2.regs[%(reg)d] = htog(FpOp2P%(reg)d.uw);
''' % { "reg" : reg } ''' % { "reg" : reg }

View file

@ -171,6 +171,10 @@ let {{
if not self.post: if not self.post:
eaCode += self.offset eaCode += self.offset
eaCode += ";" eaCode += ";"
if self.flavor == "fp":
eaCode += vfpEnabledCheckCode
self.codeBlobs["ea_code"] = eaCode self.codeBlobs["ea_code"] = eaCode
# Code that actually handles the access # Code that actually handles the access
@ -241,6 +245,10 @@ let {{
if not self.post: if not self.post:
eaCode += self.offset eaCode += self.offset
eaCode += ";" eaCode += ";"
if self.flavor == "fp":
eaCode += vfpEnabledCheckCode
self.codeBlobs["ea_code"] = eaCode self.codeBlobs["ea_code"] = eaCode
# Code that actually handles the access # Code that actually handles the access

View file

@ -37,6 +37,14 @@
// //
// Authors: Gabe Black // Authors: Gabe Black
let {{
simdEnabledCheckCode = '''
if (!neonEnabled(Cpacr, Cpsr, Fpexc))
return disabledFault();
'''
}};
def template NeonRegRegRegOpDeclare {{ def template NeonRegRegRegOpDeclare {{
template <class _Element> template <class _Element>
class %(class_name)s : public %(base_class)s class %(class_name)s : public %(base_class)s

View file

@ -43,8 +43,23 @@ let {{
return disabledFault(); return disabledFault();
''' '''
vmsrrsEnabledCheckCode = ''' vmsrEnabledCheckCode = '''
if (!vfpEnabled(Cpacr, Cpsr)) if (!vfpEnabled(Cpacr, Cpsr))
if (dest != (int)MISCREG_FPEXC && dest != (int)MISCREG_FPSID)
return disabledFault();
if (!inPrivilegedMode(Cpsr))
if (dest != (int)MISCREG_FPSCR)
return disabledFault();
'''
vmrsEnabledCheckCode = '''
if (!vfpEnabled(Cpacr, Cpsr))
if (op1 != (int)MISCREG_FPEXC && op1 != (int)MISCREG_FPSID &&
op1 != (int)MISCREG_MVFR0 && op1 != (int)MISCREG_MVFR1)
return disabledFault();
if (!inPrivilegedMode(Cpsr))
if (op1 != (int)MISCREG_FPSCR)
return disabledFault(); return disabledFault();
''' '''
}}; }};

View file

@ -150,7 +150,7 @@ namespace ArmISA {
vfpEnabled(CPACR cpacr, CPSR cpsr) vfpEnabled(CPACR cpacr, CPSR cpsr)
{ {
return cpacr.cp10 == 0x3 || return cpacr.cp10 == 0x3 ||
(cpacr.cp10 == 0x2 && inPrivilegedMode(cpsr)); (cpacr.cp10 == 0x1 && inPrivilegedMode(cpsr));
} }
static inline bool static inline bool