data64.isa revision 14128:6ed23d07d0d1
12SN/A// -*- mode:c++ -*- 21762SN/A 32SN/A// Copyright (c) 2011-2013, 2016-2019 ARM Limited 42SN/A// All rights reserved 52SN/A// 62SN/A// The license below extends only to copyright in the software and shall 72SN/A// not be construed as granting a license to any other intellectual 82SN/A// property including but not limited to intellectual property relating 92SN/A// to a hardware implementation of the functionality of the software 102SN/A// licensed hereunder. You may use the software subject to the license 112SN/A// terms below provided that you ensure that this notice is replicated 122SN/A// unmodified and in its entirety in all distributions of the software, 132SN/A// modified or unmodified, in source code or in binary form. 142SN/A// 152SN/A// Redistribution and use in source and binary forms, with or without 162SN/A// modification, are permitted provided that the following conditions are 172SN/A// met: redistributions of source code must retain the above copyright 182SN/A// notice, this list of conditions and the following disclaimer; 192SN/A// redistributions in binary form must reproduce the above copyright 202SN/A// notice, this list of conditions and the following disclaimer in the 212SN/A// documentation and/or other materials provided with the distribution; 222SN/A// neither the name of the copyright holders nor the names of its 232SN/A// contributors may be used to endorse or promote products derived from 242SN/A// this software without specific prior written permission. 252SN/A// 262SN/A// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 272665Ssaidi@eecs.umich.edu// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 282665Ssaidi@eecs.umich.edu// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 292SN/A// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 302SN/A// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 312439SN/A// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 322984Sgblack@eecs.umich.edu// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 33146SN/A// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 34146SN/A// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 35146SN/A// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 36146SN/A// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 37146SN/A// 38146SN/A// Authors: Gabe Black 391717SN/A 40146SN/Alet {{ 411717SN/A 42146SN/A header_output = "" 431977SN/A decoder_output = "" 442623SN/A exec_output = "" 452683Sktlim@umich.edu 461717SN/A def createCcCode64(carry, overflow): 47146SN/A code = "" 482683Sktlim@umich.edu code += ''' 493348Sbinkertn@umich.edu uint16_t _iz, _in; 502036SN/A _in = bits(resTemp, intWidth - 1); 51146SN/A _iz = ((resTemp & mask(intWidth)) == 0); 5256SN/A CondCodesNZ = (_in << 1) | _iz; 5356SN/A DPRINTF(Arm, "(in, iz) = (%d, %d)\\n", _in, _iz); 5456SN/A ''' 55695SN/A if overflow and overflow != "none": 562901Ssaidi@eecs.umich.edu code += ''' 572SN/A uint16_t _iv; 581858SN/A _iv = %s & 1; 593565Sgblack@eecs.umich.edu CondCodesV = _iv; 603565Sgblack@eecs.umich.edu DPRINTF(Arm, "(iv) = (%%d)\\n", _iv); 612171SN/A ''' % overflow 622170SN/A if carry and carry != "none": 633562Sgblack@eecs.umich.edu code += ''' 64146SN/A uint16_t _ic; 652462SN/A _ic = %s & 1; 66146SN/A CondCodesC = _ic; 672SN/A DPRINTF(Arm, "(ic) = (%%d)\\n", _ic); 685529Snate@binkert.org ''' % carry 695529Snate@binkert.org return code 702SN/A 712449SN/A oldC = 'CondCodesC' 721355SN/A oldV = 'CondCodesV' 735529Snate@binkert.org # Dicts of ways to set the carry flag. 744495Sacolyte@umich.edu carryCode64 = { 75224SN/A "none": "none", 761858SN/A "add": 'findCarry(intWidth, resTemp, Op164, secOp)', 772683Sktlim@umich.edu "sub": 'findCarry(intWidth, resTemp, Op164, ~secOp)', 782420SN/A "logic": '0' 795529Snate@binkert.org } 804997Sgblack@eecs.umich.edu # Dict of ways to set the overflow flag. 812420SN/A overflowCode64 = { 822SN/A "none": "none", 834400Srdreslin@umich.edu "add": 'findOverflow(intWidth, resTemp, Op164, secOp)', 842672Sktlim@umich.edu "sub": 'findOverflow(intWidth, resTemp, Op164, ~secOp)', 852683Sktlim@umich.edu "logic": '0' 862SN/A } 872SN/A 88334SN/A immOp2 = "uint64_t secOp M5_VAR_USED = imm;" 89140SN/A sRegOp2 = "uint64_t secOp M5_VAR_USED = " + \ 90334SN/A "shiftReg64(Op264, shiftAmt, shiftType, intWidth);" 912SN/A eRegOp2 = "uint64_t secOp M5_VAR_USED = " + \ 922SN/A "extendReg64(Op264, extendType, shiftAmt, intWidth);" 932SN/A 942680Sktlim@umich.edu def buildDataWork(mnem, code, flagType, suffix, buildCc, buildNonCc, 954377Sgblack@eecs.umich.edu base, templateBase): 965169Ssaidi@eecs.umich.edu code = ''' 974377Sgblack@eecs.umich.edu uint64_t resTemp M5_VAR_USED = 0; 984377Sgblack@eecs.umich.edu ''' + code 992SN/A ccCode = createCcCode64(carryCode64[flagType], overflowCode64[flagType]) 1002SN/A Name = mnem.capitalize() + suffix 1012623SN/A iop = InstObjParams(mnem, Name, base, code) 1022SN/A iopCc = InstObjParams(mnem + "s", Name + "Cc", base, code + ccCode) 1032SN/A 1042SN/A def subst(iop): 105180SN/A global header_output, decoder_output, exec_output 1062623SN/A header_output += eval(templateBase + "Declare").subst(iop) 107393SN/A decoder_output += eval(templateBase + "Constructor").subst(iop) 108393SN/A exec_output += BasicExecute.subst(iop) 109393SN/A 110393SN/A if buildNonCc: 111384SN/A subst(iop) 112384SN/A if buildCc: 113393SN/A subst(iopCc) 1142623SN/A 115393SN/A def buildXImmDataInst(mnem, code, flagType = "logic", \ 116393SN/A buildCc = True, buildNonCc = True, \ 117393SN/A suffix = "XImm"): 118393SN/A buildDataWork(mnem, immOp2 + code, flagType, suffix, 119384SN/A buildCc, buildNonCc, "DataXImmOp", "DataXImm") 120189SN/A 121189SN/A def buildXSRegDataInst(mnem, code, flagType = "logic", \ 1222623SN/A buildCc = True, buildNonCc = True, \ 1232SN/A suffix = "XSReg"): 124729SN/A buildDataWork(mnem, sRegOp2 + code, flagType, suffix, 125334SN/A buildCc, buildNonCc, "DataXSRegOp", "DataXSReg") 1262SN/A 1272SN/A def buildXERegDataInst(mnem, code, flagType = "logic", \ 1282SN/A buildCc = True, buildNonCc = True, \ 1292SN/A suffix = "XEReg"): 1302SN/A buildDataWork(mnem, eRegOp2 + code, flagType, suffix, 1312SN/A buildCc, buildNonCc, "DataXERegOp", "DataXEReg") 1322SN/A 1332SN/A def buildDataInst(mnem, code, flagType = "logic", 1342SN/A buildCc = True, buildNonCc = True): 1352SN/A buildXImmDataInst(mnem, code, flagType, buildCc, buildNonCc) 1362SN/A buildXSRegDataInst(mnem, code, flagType, buildCc, buildNonCc) 1372SN/A buildXERegDataInst(mnem, code, flagType, buildCc, buildNonCc) 1381001SN/A 1391001SN/A buildXImmDataInst("adr", "Dest64 = RawPC + imm", buildCc = False); 1401001SN/A buildXImmDataInst("adrp", "Dest64 = (RawPC & ~mask(12)) + imm", 1411001SN/A buildCc = False); 1421001SN/A buildDataInst("and", "Dest64 = resTemp = Op164 & secOp;") 1432SN/A buildDataInst("eor", "Dest64 = Op164 ^ secOp;", buildCc = False) 1442SN/A buildXSRegDataInst("eon", "Dest64 = Op164 ^ ~secOp;", buildCc = False) 1452SN/A buildDataInst("sub", "Dest64 = resTemp = Op164 - secOp;", "sub") 1462SN/A buildDataInst("add", "Dest64 = resTemp = Op164 + secOp;", "add") 1472SN/A buildXSRegDataInst("adc", 1482SN/A "Dest64 = resTemp = Op164 + secOp + %s;" % oldC, "add") 1492SN/A buildXSRegDataInst("sbc", 1502SN/A "Dest64 = resTemp = Op164 - secOp - !%s;" % oldC, "sub") 1512SN/A buildDataInst("orr", "Dest64 = Op164 | secOp;", buildCc = False) 1522SN/A buildXSRegDataInst("orn", "Dest64 = Op164 | ~secOp;", buildCc = False) 1532SN/A buildXSRegDataInst("bic", "Dest64 = resTemp = Op164 & ~secOp;") 1542SN/A 1552SN/A def buildDataXImmInst(mnem, code, optArgs = []): 1562SN/A global header_output, decoder_output, exec_output 1572SN/A classNamePrefix = mnem[0].upper() + mnem[1:] 1582SN/A templateBase = "DataXImm" 1592SN/A iop = InstObjParams(mnem, classNamePrefix + "64", 1602390SN/A templateBase + "Op", code, optArgs) 1612390SN/A header_output += eval(templateBase + "Declare").subst(iop) 1622390SN/A decoder_output += eval(templateBase + "Constructor").subst(iop) 1632390SN/A exec_output += BasicExecute.subst(iop) 1642390SN/A 1652390SN/A def buildDataXRegInst(mnem, regOps, code, optArgs = [], 1662390SN/A overrideOpClass=None): 1672390SN/A global header_output, decoder_output, exec_output 1682390SN/A templateBase = "DataX%dReg" % regOps 1692390SN/A classNamePrefix = mnem[0].upper() + mnem[1:] 1702390SN/A if overrideOpClass: 1712390SN/A iop = InstObjParams(mnem, classNamePrefix + "64", 172385SN/A templateBase + "Op", 1732SN/A { 'code': code, 'op_class': overrideOpClass}, 1742SN/A optArgs) 1752SN/A else: 1762623SN/A iop = InstObjParams(mnem, classNamePrefix + "64", 177334SN/A templateBase + "Op", code, optArgs) 1782361SN/A header_output += eval(templateBase + "Declare").subst(iop) 1795496Ssaidi@eecs.umich.edu decoder_output += eval(templateBase + "Constructor").subst(iop) 180334SN/A exec_output += BasicExecute.subst(iop) 181334SN/A 182334SN/A buildDataXRegInst("madd", 3, "Dest64 = Op164 + Op264 * Op364", 1832623SN/A overrideOpClass="IntMultOp") 1842SN/A buildDataXRegInst("msub", 3, "Dest64 = Op164 - Op264 * Op364", 1855496Ssaidi@eecs.umich.edu overrideOpClass="IntMultOp") 186921SN/A buildDataXRegInst("smaddl", 3, 1872915Sktlim@umich.edu "XDest = XOp1 + sext<32>(WOp2) * sext<32>(WOp3)", 1882915Sktlim@umich.edu overrideOpClass="IntMultOp") 1892683Sktlim@umich.edu buildDataXRegInst("smsubl", 3, 1902SN/A "XDest = XOp1 - sext<32>(WOp2) * sext<32>(WOp3)", 1912SN/A overrideOpClass="IntMultOp") 1922SN/A buildDataXRegInst("smulh", 2, ''' 1932623SN/A uint64_t op1H = (int32_t)(XOp1 >> 32); 1942SN/A uint64_t op1L = (uint32_t)XOp1; 1955496Ssaidi@eecs.umich.edu uint64_t op2H = (int32_t)(XOp2 >> 32); 196921SN/A uint64_t op2L = (uint32_t)XOp2; 1972915Sktlim@umich.edu uint64_t mid1 = ((op1L * op2L) >> 32) + op1H * op2L; 1982915Sktlim@umich.edu uint64_t mid2 = op1L * op2H; 1992SN/A uint64_t result = ((uint64_t)(uint32_t)mid1 + (uint32_t)mid2) >> 32; 2002SN/A result += shiftReg64(mid1, 32, ASR, intWidth); 2012SN/A result += shiftReg64(mid2, 32, ASR, intWidth); 2022SN/A XDest = result + op1H * op2H; 2032SN/A ''', overrideOpClass="IntMultOp") 2042SN/A buildDataXRegInst("umaddl", 3, "XDest = XOp1 + WOp2 * WOp3", 2052SN/A overrideOpClass="IntMultOp") 206595SN/A buildDataXRegInst("umsubl", 3, "XDest = XOp1 - WOp2 * WOp3", 2072623SN/A overrideOpClass="IntMultOp") 208595SN/A buildDataXRegInst("umulh", 2, ''' 2092390SN/A uint64_t op1H = (uint32_t)(XOp1 >> 32); 2101080SN/A uint64_t op1L = (uint32_t)XOp1; 2111080SN/A uint64_t op2H = (uint32_t)(XOp2 >> 32); 2121080SN/A uint64_t op2L = (uint32_t)XOp2; 2131080SN/A uint64_t mid1 = ((op1L * op2L) >> 32) + op1H * op2L; 2141080SN/A uint64_t mid2 = op1L * op2H; 2151080SN/A uint64_t result = ((uint64_t)(uint32_t)mid1 + (uint32_t)mid2) >> 32; 2161080SN/A result += mid1 >> 32; 2171121SN/A result += mid2 >> 32; 2182107SN/A XDest = result + op1H * op2H; 2191089SN/A ''', overrideOpClass="IntMultOp") 2201089SN/A 2211080SN/A buildDataXRegInst("asrv", 2, 2221080SN/A "Dest64 = shiftReg64(Op164, Op264, ASR, intWidth)") 2231080SN/A buildDataXRegInst("lslv", 2, 2241080SN/A "Dest64 = shiftReg64(Op164, Op264, LSL, intWidth)") 225595SN/A buildDataXRegInst("lsrv", 2, 2262623SN/A "Dest64 = shiftReg64(Op164, Op264, LSR, intWidth)") 2272683Sktlim@umich.edu buildDataXRegInst("rorv", 2, 228595SN/A "Dest64 = shiftReg64(Op164, Op264, ROR, intWidth)") 2292090SN/A 2302683Sktlim@umich.edu crcCode = ''' 2312683Sktlim@umich.edu constexpr uint8_t size_bytes = %(sz)d; 232595SN/A constexpr uint32_t poly = %(polynom)s; 2332205SN/A 2342205SN/A // Initial value is often a previously evaluated 2352683Sktlim@umich.edu // crc value hence is always 32bit in CRC32 2362683Sktlim@umich.edu uint32_t initial_crc = Op164 & 0xFFFFFFFF; 237595SN/A 238595SN/A uint64_t data = htole(Op264); 2392390SN/A auto data_buffer = reinterpret_cast<uint8_t*>(&data); 2402423SN/A 2412390SN/A Dest = crc32<poly>( 242595SN/A data_buffer, /* Message register */ 243595SN/A initial_crc, /* Initial value of the CRC */ 244595SN/A size_bytes /* Size of the original Message */ 2452623SN/A ); 246595SN/A ''' 2472390SN/A buildDataXRegInst("crc32b", 2, 2481080SN/A crcCode % {"sz": 1, "polynom": "0x04C11DB7"}) 249595SN/A buildDataXRegInst("crc32h", 2, 2501080SN/A crcCode % {"sz": 2, "polynom": "0x04C11DB7"}) 2511080SN/A buildDataXRegInst("crc32w", 2, 252595SN/A crcCode % {"sz": 4, "polynom": "0x04C11DB7"}) 2532683Sktlim@umich.edu buildDataXRegInst("crc32x", 2, 2541080SN/A crcCode % {"sz": 8, "polynom": "0x04C11DB7"}) 2551080SN/A 2561080SN/A buildDataXRegInst("crc32cb", 2, 2571121SN/A crcCode % {"sz": 1, "polynom": "0x1EDC6F41"}) 2582107SN/A buildDataXRegInst("crc32ch", 2, 2591089SN/A crcCode % {"sz": 2, "polynom": "0x1EDC6F41"}) 2601080SN/A buildDataXRegInst("crc32cw", 2, 2611089SN/A crcCode % {"sz": 4, "polynom": "0x1EDC6F41"}) 2621080SN/A buildDataXRegInst("crc32cx", 2, 2631080SN/A crcCode % {"sz": 8, "polynom": "0x1EDC6F41"}) 2641080SN/A 265595SN/A buildDataXRegInst("sdiv", 2, ''' 2662683Sktlim@umich.edu int64_t op1 = Op164; 2671080SN/A int64_t op2 = Op264; 2682090SN/A if (intWidth == 32) { 2691080SN/A op1 = sext<32>(op1); 270595SN/A op2 = sext<32>(op2); 2712683Sktlim@umich.edu } 2722683Sktlim@umich.edu Dest64 = op2 == -1 ? -op1 : op2 ? op1 / op2 : 0; 273595SN/A ''', overrideOpClass="IntDivOp") 2742683Sktlim@umich.edu buildDataXRegInst("udiv", 2, "Dest64 = Op264 ? Op164 / Op264 : 0", 2751098SN/A overrideOpClass="IntDivOp") 2761098SN/A 2771098SN/A buildDataXRegInst("cls", 1, ''' 2782683Sktlim@umich.edu uint64_t op1 = Op164; 2791098SN/A if (bits(op1, intWidth - 1)) 2801098SN/A op1 ^= mask(intWidth); 2811098SN/A Dest64 = (op1 == 0) ? intWidth - 1 : (intWidth - 2 - findMsbSet(op1)); 2822012SN/A ''') 2831098SN/A buildDataXRegInst("clz", 1, ''' 2841098SN/A Dest64 = (Op164 == 0) ? intWidth : (intWidth - 1 - findMsbSet(Op164)); 285595SN/A ''') 2862205SN/A buildDataXRegInst("rbit", 1, ''' 2872205SN/A Dest64 = reverseBits(Op164, intWidth/8); 2882205SN/A ''') 289595SN/A buildDataXRegInst("rev", 1, ''' 2902390SN/A if (intWidth == 32) 2912420SN/A Dest64 = betole<uint32_t>(Op164); 2922423SN/A else 2932390SN/A Dest64 = betole<uint64_t>(Op164); 294595SN/A ''') 295595SN/A buildDataXRegInst("rev16", 1, ''' 2961858SN/A int count = intWidth / 16; 2972SN/A uint64_t result = 0; 2982623SN/A for (unsigned i = 0; i < count; i++) { 2992SN/A uint16_t hw = Op164 >> (i * 16); 3002680Sktlim@umich.edu result |= (uint64_t)betole<uint16_t>(hw) << (i * 16); 3012SN/A } 3022SN/A Dest64 = result; 3032SN/A ''') 3041858SN/A buildDataXRegInst("rev32", 1, ''' 3052SN/A int count = intWidth / 32; 3065807Snate@binkert.org uint64_t result = 0; 3072SN/A for (unsigned i = 0; i < count; i++) { 3085807Snate@binkert.org uint32_t hw = Op164 >> (i * 32); 3095807Snate@binkert.org result |= (uint64_t)betole<uint32_t>(hw) << (i * 32); 3102SN/A } 3115807Snate@binkert.org Dest64 = result; 3125807Snate@binkert.org ''') 3132SN/A 3142SN/A msrMrs64EnabledCheckCode = ''' 3152SN/A // Check for read/write access right 3162SN/A if (!can%sAArch64SysReg(flat_idx, Scr64, cpsr, xc->tcBase())) { 3172623SN/A if (flat_idx == MISCREG_DAIF || 3182SN/A flat_idx == MISCREG_DC_ZVA_Xt || 3191858SN/A flat_idx == MISCREG_DC_CVAC_Xt || 3205704Snate@binkert.org flat_idx == MISCREG_DC_CIVAC_Xt 3215647Sgblack@eecs.umich.edu ) 3222SN/A return std::make_shared<UndefinedInstruction>( 3233520Sgblack@eecs.umich.edu machInst, 0, EC_TRAPPED_MSR_MRS_64, 3245647Sgblack@eecs.umich.edu mnemonic); 3253520Sgblack@eecs.umich.edu return std::make_shared<UndefinedInstruction>(machInst, false, 3262SN/A mnemonic); 3272SN/A } 3282SN/A 3292623SN/A fault = this->trap(xc->tcBase(), flat_idx, el, imm); 3302SN/A if (fault != NoFault) return fault; 3312623SN/A ''' 3322623SN/A 3332662Sstever@eecs.umich.edu mrsCode = ''' 3342623SN/A MiscRegIndex flat_idx = (MiscRegIndex) xc->tcBase()-> 3354514Ssaidi@eecs.umich.edu flattenRegId(RegId(MiscRegClass, op1)).index(); 3364495Sacolyte@umich.edu CPSR cpsr = Cpsr; 3372623SN/A ExceptionLevel el = (ExceptionLevel) (uint8_t) cpsr.el; 3383093Sksewell@umich.edu %s 3394495Sacolyte@umich.edu XDest = MiscOp1_ud; 3403093Sksewell@umich.edu ''' % (msrMrs64EnabledCheckCode % ('Read'),) 3413093Sksewell@umich.edu 3424564Sgblack@eecs.umich.edu mrsIop = InstObjParams("mrs", "Mrs64", "RegMiscRegImmOp64", 3432741Sksewell@umich.edu mrsCode, 3442741Sksewell@umich.edu ["IsSerializeBefore"]) 3452623SN/A header_output += RegMiscRegOp64Declare.subst(mrsIop) 3464564Sgblack@eecs.umich.edu decoder_output += RegMiscRegOp64Constructor.subst(mrsIop) 3474564Sgblack@eecs.umich.edu exec_output += BasicExecute.subst(mrsIop) 3482623SN/A 3492683Sktlim@umich.edu buildDataXRegInst("mrsNZCV", 1, ''' 3502623SN/A CPSR cpsr = 0; 3512623SN/A cpsr.nz = CondCodesNZ; 3522623SN/A cpsr.c = CondCodesC; 3532623SN/A cpsr.v = CondCodesV; 3542623SN/A XDest = cpsr; 3552623SN/A ''') 3562623SN/A 3572623SN/A msrCode = ''' 3582SN/A MiscRegIndex flat_idx = (MiscRegIndex) xc->tcBase()-> 3592683Sktlim@umich.edu flattenRegId(RegId(MiscRegClass, dest)).index(); 3602427SN/A CPSR cpsr = Cpsr; 3612683Sktlim@umich.edu ExceptionLevel el = (ExceptionLevel) (uint8_t) cpsr.el; 3622427SN/A %s 3632SN/A MiscDest_ud = XOp1; 3642623SN/A ''' % (msrMrs64EnabledCheckCode % ('Write'),) 3652623SN/A 3662SN/A msrIop = InstObjParams("msr", "Msr64", "MiscRegRegImmOp64", 3672623SN/A msrCode, 3682623SN/A ["IsSerializeAfter", "IsNonSpeculative"]) 3694377Sgblack@eecs.umich.edu header_output += MiscRegRegOp64Declare.subst(msrIop) 3705665Sgblack@eecs.umich.edu decoder_output += MiscRegRegOp64Constructor.subst(msrIop) 3714377Sgblack@eecs.umich.edu exec_output += BasicExecute.subst(msrIop) 3725665Sgblack@eecs.umich.edu 3735665Sgblack@eecs.umich.edu 3745665Sgblack@eecs.umich.edu buildDataXRegInst("msrNZCV", 1, ''' 3755665Sgblack@eecs.umich.edu CPSR cpsr = XOp1; 3765665Sgblack@eecs.umich.edu CondCodesNZ = cpsr.nz; 3774181Sgblack@eecs.umich.edu CondCodesC = cpsr.c; 3784181Sgblack@eecs.umich.edu CondCodesV = cpsr.v; 3794181Sgblack@eecs.umich.edu ''') 3804182Sgblack@eecs.umich.edu 3814182Sgblack@eecs.umich.edu msr_check_code = ''' 3824182Sgblack@eecs.umich.edu MiscRegIndex flat_idx = (MiscRegIndex) xc->tcBase()-> 3834593Sgblack@eecs.umich.edu flattenRegId(RegId(MiscRegClass, dest)).index(); 3844593Sgblack@eecs.umich.edu CPSR cpsr = Cpsr; 3854593Sgblack@eecs.umich.edu ExceptionLevel el = (ExceptionLevel) (uint8_t) cpsr.el; 3864593Sgblack@eecs.umich.edu %s 3874593Sgblack@eecs.umich.edu ''' % (msrMrs64EnabledCheckCode % ('Write'),) 3884377Sgblack@eecs.umich.edu 3894377Sgblack@eecs.umich.edu 3904377Sgblack@eecs.umich.edu msrdczva_ea_code = msr_check_code 3914377Sgblack@eecs.umich.edu msrdczva_ea_code += ''' 3924377Sgblack@eecs.umich.edu Request::Flags memAccessFlags = Request::CACHE_BLOCK_ZERO | 3934377Sgblack@eecs.umich.edu ArmISA::TLB::MustBeOne; 3944377Sgblack@eecs.umich.edu EA = XBase; 3954377Sgblack@eecs.umich.edu assert(!(Dczid & 0x10)); 3964572Sacolyte@umich.edu uint64_t op_size = power(2, Dczid + 2); 3974572Sacolyte@umich.edu EA &= ~(op_size - 1); 3984377Sgblack@eecs.umich.edu 3994377Sgblack@eecs.umich.edu ''' 4004377Sgblack@eecs.umich.edu 4014377Sgblack@eecs.umich.edu msrDCZVAIop = InstObjParams("dc zva", "Dczva", "SysDC64", 4024181Sgblack@eecs.umich.edu { "ea_code" : msrdczva_ea_code, 4034181Sgblack@eecs.umich.edu "memacc_code" : ';', 4044181Sgblack@eecs.umich.edu "use_uops" : 0, 4054539Sgblack@eecs.umich.edu "op_wb" : ";", 4063276Sgblack@eecs.umich.edu "fa_code" : ";"}, 4075665Sgblack@eecs.umich.edu ['IsStore', 'IsMemRef']); 4083280Sgblack@eecs.umich.edu header_output += DCStore64Declare.subst(msrDCZVAIop); 4093280Sgblack@eecs.umich.edu decoder_output += DCStore64Constructor.subst(msrDCZVAIop); 4103276Sgblack@eecs.umich.edu exec_output += DCStore64Execute.subst(msrDCZVAIop); 4113276Sgblack@eecs.umich.edu exec_output += DCStore64InitiateAcc.subst(msrDCZVAIop); 4123276Sgblack@eecs.umich.edu exec_output += Store64CompleteAcc.subst(msrDCZVAIop); 4135665Sgblack@eecs.umich.edu 4143276Sgblack@eecs.umich.edu 4153276Sgblack@eecs.umich.edu msrdccvau_ea_code = msr_check_code 4164181Sgblack@eecs.umich.edu msrdccvau_ea_code += ''' 4174181Sgblack@eecs.umich.edu Request::Flags memAccessFlags = Request::CLEAN | Request::DST_POU | 4184181Sgblack@eecs.umich.edu ArmISA::TLB::MustBeOne; 4194522Ssaidi@eecs.umich.edu EA = XBase; 4205784Sgblack@eecs.umich.edu System *sys = xc->tcBase()->getSystemPtr(); 4215784Sgblack@eecs.umich.edu Addr op_size = sys->cacheLineSize(); 4225784Sgblack@eecs.umich.edu EA &= ~(op_size - 1); 4232470SN/A ''' 4244181Sgblack@eecs.umich.edu 4254181Sgblack@eecs.umich.edu msrDCCVAUIop = InstObjParams("dc cvau", "Dccvau", "SysDC64", 4264522Ssaidi@eecs.umich.edu { "ea_code" : msrdccvau_ea_code, 4272623SN/A "memacc_code" : ';', 4282623SN/A "use_uops" : 0, 4294181Sgblack@eecs.umich.edu "op_wb" : ";", "fa_code" : ";"}, 4302623SN/A ['IsStore', 'IsMemRef']); 4314181Sgblack@eecs.umich.edu header_output += DCStore64Declare.subst(msrDCCVAUIop); 4322623SN/A decoder_output += DCStore64Constructor.subst(msrDCCVAUIop); 4332623SN/A exec_output += DCStore64Execute.subst(msrDCCVAUIop); 4342623SN/A exec_output += DCStore64InitiateAcc.subst(msrDCCVAUIop); 4352623SN/A exec_output += Store64CompleteAcc.subst(msrDCCVAUIop); 4362623SN/A 4372623SN/A 4385086Sgblack@eecs.umich.edu msrdccvac_ea_code = msr_check_code 4393577Sgblack@eecs.umich.edu msrdccvac_ea_code += ''' 4402683Sktlim@umich.edu Request::Flags memAccessFlags = Request::CLEAN | Request::DST_POC | 4415086Sgblack@eecs.umich.edu ArmISA::TLB::MustBeOne; 4422623SN/A EA = XBase; 4432683Sktlim@umich.edu System *sys = xc->tcBase()->getSystemPtr(); 4442623SN/A Addr op_size = sys->cacheLineSize(); 4452420SN/A EA &= ~(op_size - 1); 4462SN/A ''' 4472623SN/A 4482623SN/A msrDCCVACIop = InstObjParams("dc cvac", "Dccvac", "SysDC64", 4492SN/A { "ea_code" : msrdccvac_ea_code, 4502SN/A "memacc_code" : ';', 4512623SN/A "use_uops" : 0, 4522623SN/A "op_wb" : ";", "fa_code" : ";"}, 4532623SN/A ['IsStore', 'IsMemRef']); 4542623SN/A header_output += DCStore64Declare.subst(msrDCCVACIop); 4552SN/A decoder_output += DCStore64Constructor.subst(msrDCCVACIop); 4562683Sktlim@umich.edu exec_output += DCStore64Execute.subst(msrDCCVACIop); 4572644Sstever@eecs.umich.edu exec_output += DCStore64InitiateAcc.subst(msrDCCVACIop); 4582644Sstever@eecs.umich.edu exec_output += Store64CompleteAcc.subst(msrDCCVACIop); 4594046Sbinkertn@umich.edu 4604046Sbinkertn@umich.edu 4614046Sbinkertn@umich.edu msrdccivac_ea_code = msr_check_code 4622644Sstever@eecs.umich.edu msrdccivac_ea_code += ''' 4632623SN/A Request::Flags memAccessFlags = Request::CLEAN | 4642SN/A Request::INVALIDATE | Request::DST_POC | ArmISA::TLB::MustBeOne; 4652SN/A EA = XBase; 4662623SN/A System *sys = xc->tcBase()->getSystemPtr(); 4672623SN/A Addr op_size = sys->cacheLineSize(); 4682623SN/A EA &= ~(op_size - 1); 4694377Sgblack@eecs.umich.edu ''' 4704377Sgblack@eecs.umich.edu 4712090SN/A msrDCCIVACIop = InstObjParams("dc civac", "Dccivac", "SysDC64", 4723905Ssaidi@eecs.umich.edu { "ea_code" : msrdccivac_ea_code, 4735120Sgblack@eecs.umich.edu "memacc_code" : ';', 4745665Sgblack@eecs.umich.edu "use_uops" : 0, 4755665Sgblack@eecs.umich.edu "op_wb" : ";", "fa_code" : ";"}, 4765281Sgblack@eecs.umich.edu ['IsStore', 'IsMemRef']); 4774377Sgblack@eecs.umich.edu header_output += DCStore64Declare.subst(msrDCCIVACIop); 4783276Sgblack@eecs.umich.edu decoder_output += DCStore64Constructor.subst(msrDCCIVACIop); 4794539Sgblack@eecs.umich.edu exec_output += DCStore64Execute.subst(msrDCCIVACIop); 4805665Sgblack@eecs.umich.edu exec_output += DCStore64InitiateAcc.subst(msrDCCIVACIop); 4815665Sgblack@eecs.umich.edu exec_output += Store64CompleteAcc.subst(msrDCCIVACIop); 4825665Sgblack@eecs.umich.edu 4833276Sgblack@eecs.umich.edu 4843276Sgblack@eecs.umich.edu msrdcivac_ea_code = msr_check_code 4853280Sgblack@eecs.umich.edu msrdcivac_ea_code += ''' 4865665Sgblack@eecs.umich.edu Request::Flags memAccessFlags = Request::INVALIDATE | 4875665Sgblack@eecs.umich.edu Request::DST_POC | ArmISA::TLB::MustBeOne; 4883276Sgblack@eecs.umich.edu EA = XBase; 4893276Sgblack@eecs.umich.edu HCR hcr = Hcr64; 4905665Sgblack@eecs.umich.edu SCR scr = Scr64; 4913276Sgblack@eecs.umich.edu if (el == EL1 && ArmSystem::haveVirtualization(xc->tcBase()) && 4923280Sgblack@eecs.umich.edu hcr.vm && (scr.ns || !ArmSystem::haveSecurity(xc->tcBase()))) { 4933276Sgblack@eecs.umich.edu memAccessFlags = memAccessFlags | Request::CLEAN; 4943276Sgblack@eecs.umich.edu } 4953280Sgblack@eecs.umich.edu System *sys = xc->tcBase()->getSystemPtr(); 4963276Sgblack@eecs.umich.edu Addr op_size = sys->cacheLineSize(); 4973276Sgblack@eecs.umich.edu EA &= ~(op_size - 1); 4983276Sgblack@eecs.umich.edu ''' 4993276Sgblack@eecs.umich.edu 5003276Sgblack@eecs.umich.edu msrDCIVACIop = InstObjParams("dc ivac", "Dcivac", "SysDC64", 5013276Sgblack@eecs.umich.edu { "ea_code" : msrdcivac_ea_code, 5023276Sgblack@eecs.umich.edu "memacc_code" : ';', 5032SN/A "use_uops" : 0, 5042SN/A "op_wb" : ";", "fa_code" : ";"}, 5052SN/A ['IsStore', 'IsMemRef']); 5065250Sksewell@umich.edu header_output += DCStore64Declare.subst(msrDCIVACIop); 5075222Sksewell@umich.edu decoder_output += DCStore64Constructor.subst(msrDCIVACIop); 5085222Sksewell@umich.edu exec_output += DCStore64Execute.subst(msrDCIVACIop); 5095222Sksewell@umich.edu exec_output += DCStore64InitiateAcc.subst(msrDCIVACIop); 5105222Sksewell@umich.edu exec_output += Store64CompleteAcc.subst(msrDCIVACIop); 5115222Sksewell@umich.edu 5125222Sksewell@umich.edu def buildMsrImmInst(mnem, inst_name, code): 5135222Sksewell@umich.edu global header_output, decoder_output, exec_output 5145222Sksewell@umich.edu msrImmPermission = ''' 5155222Sksewell@umich.edu auto misc_index = (MiscRegIndex) xc->tcBase()->flattenRegId( 5165222Sksewell@umich.edu RegId(MiscRegClass, dest)).index(); 5175222Sksewell@umich.edu 5185222Sksewell@umich.edu if (!miscRegInfo[misc_index][MISCREG_IMPLEMENTED]) { 5195222Sksewell@umich.edu return std::make_shared<UndefinedInstruction>( 5205222Sksewell@umich.edu machInst, false, 5215222Sksewell@umich.edu mnemonic); 5225222Sksewell@umich.edu } 5235222Sksewell@umich.edu 5245222Sksewell@umich.edu if (!canWriteAArch64SysReg(misc_index, 5255222Sksewell@umich.edu Scr64, Cpsr, xc->tcBase())) { 5265222Sksewell@umich.edu 5275222Sksewell@umich.edu return std::make_shared<UndefinedInstruction>( 5285222Sksewell@umich.edu machInst, 0, EC_TRAPPED_MSR_MRS_64, 5295222Sksewell@umich.edu mnemonic); 5305222Sksewell@umich.edu } 5315222Sksewell@umich.edu 5325222Sksewell@umich.edu ''' 5335222Sksewell@umich.edu msrIop = InstObjParams("msr", inst_name, "MiscRegImmOp64", 5345222Sksewell@umich.edu msrImmPermission + code, 5355222Sksewell@umich.edu ["IsSerializeAfter", "IsNonSpeculative"]) 5365222Sksewell@umich.edu header_output += MiscRegOp64Declare.subst(msrIop) 5375222Sksewell@umich.edu decoder_output += MiscRegOp64Constructor.subst(msrIop) 5385222Sksewell@umich.edu exec_output += BasicExecute.subst(msrIop) 5395250Sksewell@umich.edu 540 buildMsrImmInst("msr", "MsrImm64", ''' 541 // Mask and shift immediate (depending on PSTATE field) 542 // before assignment 543 MiscDest_ud = miscRegImm(); 544 ''') 545 546 buildMsrImmInst("msr", "MsrImmDAIFSet64", ''' 547 CPSR cpsr = Cpsr; 548 cpsr.daif = cpsr.daif | imm; 549 Cpsr = cpsr; 550 ''') 551 552 buildMsrImmInst("msr", "MsrImmDAIFClr64", ''' 553 CPSR cpsr = Cpsr; 554 cpsr.daif = cpsr.daif & ~imm; 555 Cpsr = cpsr; 556 ''') 557 558 def buildDataXCompInst(mnem, instType, suffix, code): 559 global header_output, decoder_output, exec_output 560 templateBase = "DataXCond%s" % instType 561 iop = InstObjParams(mnem, mnem.capitalize() + suffix + "64", 562 templateBase + "Op", code) 563 header_output += eval(templateBase + "Declare").subst(iop) 564 decoder_output += eval(templateBase + "Constructor").subst(iop) 565 exec_output += BasicExecute.subst(iop) 566 567 def buildDataXCondImmInst(mnem, code): 568 buildDataXCompInst(mnem, "CompImm", "Imm", code) 569 def buildDataXCondRegInst(mnem, code): 570 buildDataXCompInst(mnem, "CompReg", "Reg", code) 571 def buildDataXCondSelInst(mnem, code): 572 buildDataXCompInst(mnem, "Sel", "", code) 573 574 def condCompCode(flagType, op, imm): 575 ccCode = createCcCode64(carryCode64[flagType], overflowCode64[flagType]) 576 opDecl = "uint64_t secOp M5_VAR_USED = imm;" 577 if not imm: 578 opDecl = "uint64_t secOp M5_VAR_USED = Op264;" 579 return opDecl + ''' 580 if (testPredicate(CondCodesNZ, CondCodesC, CondCodesV, condCode)) { 581 uint64_t resTemp = Op164 ''' + op + ''' secOp; 582 ''' + ccCode + ''' 583 } else { 584 CondCodesNZ = (defCc >> 2) & 0x3; 585 CondCodesC = (defCc >> 1) & 0x1; 586 CondCodesV = defCc & 0x1; 587 } 588 ''' 589 590 buildDataXCondImmInst("ccmn", condCompCode("add", "+", True)) 591 buildDataXCondImmInst("ccmp", condCompCode("sub", "-", True)) 592 buildDataXCondRegInst("ccmn", condCompCode("add", "+", False)) 593 buildDataXCondRegInst("ccmp", condCompCode("sub", "-", False)) 594 595 condSelCode = ''' 596 if (testPredicate(CondCodesNZ, CondCodesC, CondCodesV, condCode)) { 597 Dest64 = Op164; 598 } else { 599 Dest64 = %(altVal)s; 600 } 601 ''' 602 buildDataXCondSelInst("csel", condSelCode % {"altVal" : "Op264"}) 603 buildDataXCondSelInst("csinc", condSelCode % {"altVal" : "Op264 + 1"}) 604 buildDataXCondSelInst("csinv", condSelCode % {"altVal" : "~Op264"}) 605 buildDataXCondSelInst("csneg", condSelCode % {"altVal" : "-Op264"}) 606}}; 607