fp.isa revision 7326
16019Shines@cs.fsu.edu// -*- mode:c++ -*- 26019Shines@cs.fsu.edu 37178Sgblack@eecs.umich.edu// Copyright (c) 2010 ARM Limited 47178Sgblack@eecs.umich.edu// All rights reserved 57178Sgblack@eecs.umich.edu// 67178Sgblack@eecs.umich.edu// The license below extends only to copyright in the software and shall 77178Sgblack@eecs.umich.edu// not be construed as granting a license to any other intellectual 87178Sgblack@eecs.umich.edu// property including but not limited to intellectual property relating 97178Sgblack@eecs.umich.edu// to a hardware implementation of the functionality of the software 107178Sgblack@eecs.umich.edu// licensed hereunder. You may use the software subject to the license 117178Sgblack@eecs.umich.edu// terms below provided that you ensure that this notice is replicated 127178Sgblack@eecs.umich.edu// unmodified and in its entirety in all distributions of the software, 137178Sgblack@eecs.umich.edu// modified or unmodified, in source code or in binary form. 147178Sgblack@eecs.umich.edu// 156019Shines@cs.fsu.edu// Copyright (c) 2007-2008 The Florida State University 166019Shines@cs.fsu.edu// All rights reserved. 176019Shines@cs.fsu.edu// 186019Shines@cs.fsu.edu// Redistribution and use in source and binary forms, with or without 196019Shines@cs.fsu.edu// modification, are permitted provided that the following conditions are 206019Shines@cs.fsu.edu// met: redistributions of source code must retain the above copyright 216019Shines@cs.fsu.edu// notice, this list of conditions and the following disclaimer; 226019Shines@cs.fsu.edu// redistributions in binary form must reproduce the above copyright 236019Shines@cs.fsu.edu// notice, this list of conditions and the following disclaimer in the 246019Shines@cs.fsu.edu// documentation and/or other materials provided with the distribution; 256019Shines@cs.fsu.edu// neither the name of the copyright holders nor the names of its 266019Shines@cs.fsu.edu// contributors may be used to endorse or promote products derived from 276019Shines@cs.fsu.edu// this software without specific prior written permission. 286019Shines@cs.fsu.edu// 296019Shines@cs.fsu.edu// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 306019Shines@cs.fsu.edu// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 316019Shines@cs.fsu.edu// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 326019Shines@cs.fsu.edu// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 336019Shines@cs.fsu.edu// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 346019Shines@cs.fsu.edu// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 356019Shines@cs.fsu.edu// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 366019Shines@cs.fsu.edu// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 376019Shines@cs.fsu.edu// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 386019Shines@cs.fsu.edu// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 396019Shines@cs.fsu.edu// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 406019Shines@cs.fsu.edu// 416019Shines@cs.fsu.edu// Authors: Stephen Hines 426019Shines@cs.fsu.edu 436019Shines@cs.fsu.edu//////////////////////////////////////////////////////////////////// 446019Shines@cs.fsu.edu// 456019Shines@cs.fsu.edu// Floating Point operate instructions 466019Shines@cs.fsu.edu// 476019Shines@cs.fsu.edu 486019Shines@cs.fsu.edudef template FPAExecute {{ 496019Shines@cs.fsu.edu Fault %(class_name)s::execute(%(CPU_exec_context)s *xc, Trace::InstRecord *traceData) const 506019Shines@cs.fsu.edu { 516019Shines@cs.fsu.edu Fault fault = NoFault; 526019Shines@cs.fsu.edu 536019Shines@cs.fsu.edu %(fp_enable_check)s; 546019Shines@cs.fsu.edu 556019Shines@cs.fsu.edu %(op_decl)s; 566019Shines@cs.fsu.edu %(op_rd)s; 576019Shines@cs.fsu.edu 586243Sgblack@eecs.umich.edu if (%(predicate_test)s) { 596243Sgblack@eecs.umich.edu %(code)s; 606243Sgblack@eecs.umich.edu if (fault == NoFault) { 616243Sgblack@eecs.umich.edu %(op_wb)s; 626243Sgblack@eecs.umich.edu } 636019Shines@cs.fsu.edu } 646019Shines@cs.fsu.edu 656019Shines@cs.fsu.edu return fault; 666019Shines@cs.fsu.edu } 676019Shines@cs.fsu.edu}}; 686019Shines@cs.fsu.edu 696019Shines@cs.fsu.edudef template FloatDoubleDecode {{ 706019Shines@cs.fsu.edu { 716019Shines@cs.fsu.edu ArmStaticInst *i = NULL; 726019Shines@cs.fsu.edu switch (OPCODE_19 << 1 | OPCODE_7) 736019Shines@cs.fsu.edu { 746019Shines@cs.fsu.edu case 0: 756019Shines@cs.fsu.edu i = (ArmStaticInst *)new %(class_name)sS(machInst); 766019Shines@cs.fsu.edu break; 776019Shines@cs.fsu.edu case 1: 786019Shines@cs.fsu.edu i = (ArmStaticInst *)new %(class_name)sD(machInst); 796019Shines@cs.fsu.edu break; 806019Shines@cs.fsu.edu case 2: 816019Shines@cs.fsu.edu case 3: 826019Shines@cs.fsu.edu default: 836019Shines@cs.fsu.edu panic("Cannot decode float/double nature of the instruction"); 846019Shines@cs.fsu.edu } 856019Shines@cs.fsu.edu return i; 866019Shines@cs.fsu.edu } 876019Shines@cs.fsu.edu}}; 886019Shines@cs.fsu.edu 896019Shines@cs.fsu.edu// Primary format for float point operate instructions: 906019Shines@cs.fsu.edudef format FloatOp(code, *flags) {{ 916019Shines@cs.fsu.edu orig_code = code 926019Shines@cs.fsu.edu 936019Shines@cs.fsu.edu cblk = code 946252Sgblack@eecs.umich.edu iop = InstObjParams(name, Name, 'PredOp', 956243Sgblack@eecs.umich.edu {"code": cblk, 966243Sgblack@eecs.umich.edu "predicate_test": predicateTest}, 976243Sgblack@eecs.umich.edu flags) 986019Shines@cs.fsu.edu header_output = BasicDeclare.subst(iop) 996019Shines@cs.fsu.edu decoder_output = BasicConstructor.subst(iop) 1006019Shines@cs.fsu.edu exec_output = FPAExecute.subst(iop) 1016019Shines@cs.fsu.edu 1026019Shines@cs.fsu.edu sng_cblk = code 1036252Sgblack@eecs.umich.edu sng_iop = InstObjParams(name, Name+'S', 'PredOp', 1046243Sgblack@eecs.umich.edu {"code": sng_cblk, 1056243Sgblack@eecs.umich.edu "predicate_test": predicateTest}, 1066243Sgblack@eecs.umich.edu flags) 1076019Shines@cs.fsu.edu header_output += BasicDeclare.subst(sng_iop) 1086019Shines@cs.fsu.edu decoder_output += BasicConstructor.subst(sng_iop) 1096019Shines@cs.fsu.edu exec_output += FPAExecute.subst(sng_iop) 1106019Shines@cs.fsu.edu 1116019Shines@cs.fsu.edu dbl_code = re.sub(r'\.sf', '.df', orig_code) 1126019Shines@cs.fsu.edu 1136019Shines@cs.fsu.edu dbl_cblk = dbl_code 1146252Sgblack@eecs.umich.edu dbl_iop = InstObjParams(name, Name+'D', 'PredOp', 1156243Sgblack@eecs.umich.edu {"code": dbl_cblk, 1166243Sgblack@eecs.umich.edu "predicate_test": predicateTest}, 1176243Sgblack@eecs.umich.edu flags) 1186019Shines@cs.fsu.edu header_output += BasicDeclare.subst(dbl_iop) 1196019Shines@cs.fsu.edu decoder_output += BasicConstructor.subst(dbl_iop) 1206019Shines@cs.fsu.edu exec_output += FPAExecute.subst(dbl_iop) 1216019Shines@cs.fsu.edu 1226019Shines@cs.fsu.edu decode_block = FloatDoubleDecode.subst(iop) 1236019Shines@cs.fsu.edu}}; 1246019Shines@cs.fsu.edu 1256019Shines@cs.fsu.edulet {{ 1266019Shines@cs.fsu.edu calcFPCcCode = ''' 1276019Shines@cs.fsu.edu uint16_t _in, _iz, _ic, _iv; 1286019Shines@cs.fsu.edu 1296019Shines@cs.fsu.edu _in = %(fReg1)s < %(fReg2)s; 1306019Shines@cs.fsu.edu _iz = %(fReg1)s == %(fReg2)s; 1316019Shines@cs.fsu.edu _ic = %(fReg1)s >= %(fReg2)s; 1326019Shines@cs.fsu.edu _iv = (isnan(%(fReg1)s) || isnan(%(fReg2)s)) & 1; 1336019Shines@cs.fsu.edu 1346724Sgblack@eecs.umich.edu CondCodes = _in << 31 | _iz << 30 | _ic << 29 | _iv << 28 | 1356724Sgblack@eecs.umich.edu (CondCodes & 0x0FFFFFFF); 1366019Shines@cs.fsu.edu ''' 1376019Shines@cs.fsu.edu}}; 1386019Shines@cs.fsu.edu 1396019Shines@cs.fsu.edudef format FloatCmp(fReg1, fReg2, *flags) {{ 1406019Shines@cs.fsu.edu code = calcFPCcCode % vars() 1416252Sgblack@eecs.umich.edu iop = InstObjParams(name, Name, 'PredOp', 1426243Sgblack@eecs.umich.edu {"code": code, 1436243Sgblack@eecs.umich.edu "predicate_test": predicateTest}, 1446243Sgblack@eecs.umich.edu flags) 1456019Shines@cs.fsu.edu header_output = BasicDeclare.subst(iop) 1466019Shines@cs.fsu.edu decoder_output = BasicConstructor.subst(iop) 1476019Shines@cs.fsu.edu decode_block = BasicDecode.subst(iop) 1486019Shines@cs.fsu.edu exec_output = FPAExecute.subst(iop) 1496019Shines@cs.fsu.edu}}; 1506019Shines@cs.fsu.edu 1517178Sgblack@eecs.umich.edudef format ExtensionRegLoadStore() {{ 1527178Sgblack@eecs.umich.edu decode_block = ''' 1537178Sgblack@eecs.umich.edu { 1547178Sgblack@eecs.umich.edu const uint32_t opcode = bits(machInst, 24, 20); 1557178Sgblack@eecs.umich.edu const uint32_t offset = bits(machInst, 7, 0); 1567178Sgblack@eecs.umich.edu const bool single = bits(machInst, 22); 1577178Sgblack@eecs.umich.edu const IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 19, 16); 1587178Sgblack@eecs.umich.edu RegIndex vd; 1597178Sgblack@eecs.umich.edu if (single) { 1607178Sgblack@eecs.umich.edu vd = (RegIndex)(uint32_t)((bits(machInst, 15, 12) << 1) | 1617178Sgblack@eecs.umich.edu bits(machInst, 22)); 1627178Sgblack@eecs.umich.edu } else { 1637178Sgblack@eecs.umich.edu vd = (RegIndex)(uint32_t)((bits(machInst, 15, 12) << 1) | 1647178Sgblack@eecs.umich.edu (bits(machInst, 22) << 5)); 1657178Sgblack@eecs.umich.edu } 1667178Sgblack@eecs.umich.edu switch (bits(opcode, 4, 3)) { 1677178Sgblack@eecs.umich.edu case 0x0: 1687178Sgblack@eecs.umich.edu if (bits(opcode, 4, 1) == 0x2) { 1697178Sgblack@eecs.umich.edu return new WarnUnimplemented("core-to-extension-transfer", 1707178Sgblack@eecs.umich.edu machInst); 1717178Sgblack@eecs.umich.edu } 1727178Sgblack@eecs.umich.edu break; 1737178Sgblack@eecs.umich.edu case 0x1: 1747178Sgblack@eecs.umich.edu switch (bits(opcode, 1, 0)) { 1757178Sgblack@eecs.umich.edu case 0x0: 1767178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1777178Sgblack@eecs.umich.edu true, false, false, offset); 1787178Sgblack@eecs.umich.edu case 0x1: 1797178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1807178Sgblack@eecs.umich.edu true, false, true, offset); 1817178Sgblack@eecs.umich.edu case 0x2: 1827178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1837178Sgblack@eecs.umich.edu true, true, false, offset); 1847178Sgblack@eecs.umich.edu case 0x3: 1857178Sgblack@eecs.umich.edu // If rn == sp, then this is called vpop. 1867178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1877178Sgblack@eecs.umich.edu true, true, true, offset); 1887178Sgblack@eecs.umich.edu } 1897178Sgblack@eecs.umich.edu case 0x2: 1907178Sgblack@eecs.umich.edu if (bits(opcode, 1, 0) == 0x2) { 1917178Sgblack@eecs.umich.edu // If rn == sp, then this is called vpush. 1927178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1937178Sgblack@eecs.umich.edu false, true, false, offset); 1947178Sgblack@eecs.umich.edu } else if (bits(opcode, 1, 0) == 0x3) { 1957178Sgblack@eecs.umich.edu return new VLdmStm(machInst, rn, vd, single, 1967178Sgblack@eecs.umich.edu false, true, true, offset); 1977178Sgblack@eecs.umich.edu } 1987178Sgblack@eecs.umich.edu // Fall through on purpose 1997178Sgblack@eecs.umich.edu case 0x3: 2007178Sgblack@eecs.umich.edu if (bits(opcode, 1, 0) == 0x0) { 2017178Sgblack@eecs.umich.edu return new WarnUnimplemented("vstr", machInst); 2027178Sgblack@eecs.umich.edu } else if (bits(opcode, 1, 0) == 0x1) { 2037178Sgblack@eecs.umich.edu return new WarnUnimplemented("vldr", machInst); 2047178Sgblack@eecs.umich.edu } 2057178Sgblack@eecs.umich.edu } 2067178Sgblack@eecs.umich.edu return new Unknown(machInst); 2077178Sgblack@eecs.umich.edu } 2087178Sgblack@eecs.umich.edu ''' 2097178Sgblack@eecs.umich.edu}}; 2107321Sgblack@eecs.umich.edu 2117321Sgblack@eecs.umich.edudef format ShortFpTransfer() {{ 2127321Sgblack@eecs.umich.edu decode_block = ''' 2137321Sgblack@eecs.umich.edu { 2147321Sgblack@eecs.umich.edu const uint32_t l = bits(machInst, 20); 2157321Sgblack@eecs.umich.edu const uint32_t c = bits(machInst, 8); 2167321Sgblack@eecs.umich.edu const uint32_t a = bits(machInst, 23, 21); 2177321Sgblack@eecs.umich.edu const uint32_t b = bits(machInst, 6, 5); 2187321Sgblack@eecs.umich.edu if ((machInst.thumb == 1 && bits(machInst, 28) == 1) || 2197321Sgblack@eecs.umich.edu (machInst.thumb == 0 && machInst.condCode == 0xf)) { 2207321Sgblack@eecs.umich.edu return new Unknown(machInst); 2217321Sgblack@eecs.umich.edu } 2227321Sgblack@eecs.umich.edu if (l == 0 && c == 0) { 2237321Sgblack@eecs.umich.edu if (a == 0) { 2247321Sgblack@eecs.umich.edu // A8-648 2257321Sgblack@eecs.umich.edu return new WarnUnimplemented("vmov", machInst); 2267321Sgblack@eecs.umich.edu } else if (a == 0x7) { 2277323Sgblack@eecs.umich.edu const IntRegIndex rt = 2287323Sgblack@eecs.umich.edu (IntRegIndex)(uint32_t)bits(machInst, 15, 12); 2297323Sgblack@eecs.umich.edu uint32_t specReg = bits(machInst, 19, 16); 2307323Sgblack@eecs.umich.edu switch (specReg) { 2317323Sgblack@eecs.umich.edu case 0: 2327323Sgblack@eecs.umich.edu specReg = MISCREG_FPSID; 2337323Sgblack@eecs.umich.edu break; 2347323Sgblack@eecs.umich.edu case 1: 2357323Sgblack@eecs.umich.edu specReg = MISCREG_FPSCR; 2367323Sgblack@eecs.umich.edu break; 2377323Sgblack@eecs.umich.edu case 8: 2387323Sgblack@eecs.umich.edu specReg = MISCREG_FPEXC; 2397323Sgblack@eecs.umich.edu break; 2407323Sgblack@eecs.umich.edu default: 2417323Sgblack@eecs.umich.edu return new Unknown(machInst); 2427323Sgblack@eecs.umich.edu } 2437323Sgblack@eecs.umich.edu return new Vmsr(machInst, (IntRegIndex)specReg, rt); 2447321Sgblack@eecs.umich.edu } 2457321Sgblack@eecs.umich.edu } else if (l == 0 && c == 1) { 2467321Sgblack@eecs.umich.edu if (bits(a, 2) == 0) { 2477321Sgblack@eecs.umich.edu // A8-644 2487321Sgblack@eecs.umich.edu return new WarnUnimplemented("vmov", machInst); 2497321Sgblack@eecs.umich.edu } else if (bits(b, 1) == 0) { 2507321Sgblack@eecs.umich.edu // A8-594 2517321Sgblack@eecs.umich.edu return new WarnUnimplemented("vdup", machInst); 2527321Sgblack@eecs.umich.edu } 2537321Sgblack@eecs.umich.edu } else if (l == 1 && c == 0) { 2547321Sgblack@eecs.umich.edu if (a == 0) { 2557321Sgblack@eecs.umich.edu // A8-648 2567321Sgblack@eecs.umich.edu return new WarnUnimplemented("vmov", machInst); 2577321Sgblack@eecs.umich.edu } else if (a == 7) { 2587326Sgblack@eecs.umich.edu const IntRegIndex rt = 2597326Sgblack@eecs.umich.edu (IntRegIndex)(uint32_t)bits(machInst, 15, 12); 2607326Sgblack@eecs.umich.edu uint32_t specReg = bits(machInst, 19, 16); 2617326Sgblack@eecs.umich.edu switch (specReg) { 2627326Sgblack@eecs.umich.edu case 0: 2637326Sgblack@eecs.umich.edu specReg = MISCREG_FPSID; 2647326Sgblack@eecs.umich.edu break; 2657326Sgblack@eecs.umich.edu case 1: 2667326Sgblack@eecs.umich.edu specReg = MISCREG_FPSCR; 2677326Sgblack@eecs.umich.edu break; 2687326Sgblack@eecs.umich.edu case 6: 2697326Sgblack@eecs.umich.edu specReg = MISCREG_MVFR1; 2707326Sgblack@eecs.umich.edu break; 2717326Sgblack@eecs.umich.edu case 7: 2727326Sgblack@eecs.umich.edu specReg = MISCREG_MVFR0; 2737326Sgblack@eecs.umich.edu break; 2747326Sgblack@eecs.umich.edu case 8: 2757326Sgblack@eecs.umich.edu specReg = MISCREG_FPEXC; 2767326Sgblack@eecs.umich.edu break; 2777326Sgblack@eecs.umich.edu default: 2787326Sgblack@eecs.umich.edu return new Unknown(machInst); 2797326Sgblack@eecs.umich.edu } 2807326Sgblack@eecs.umich.edu return new Vmrs(machInst, rt, (IntRegIndex)specReg); 2817321Sgblack@eecs.umich.edu } 2827321Sgblack@eecs.umich.edu } else { 2837321Sgblack@eecs.umich.edu // A8-646 2847321Sgblack@eecs.umich.edu return new WarnUnimplemented("vmov", machInst); 2857321Sgblack@eecs.umich.edu } 2867321Sgblack@eecs.umich.edu return new Unknown(machInst); 2877321Sgblack@eecs.umich.edu } 2887321Sgblack@eecs.umich.edu ''' 2897321Sgblack@eecs.umich.edu}}; 290