1// -*- mode:c++ -*- 2 3// Copyright (c) 2010-2013, 2016 ARM Limited 4// All rights reserved 5// 6// The license below extends only to copyright in the software and shall 7// not be construed as granting a license to any other intellectual 8// property including but not limited to intellectual property relating 9// to a hardware implementation of the functionality of the software 10// licensed hereunder. You may use the software subject to the license 11// terms below provided that you ensure that this notice is replicated 12// unmodified and in its entirety in all distributions of the software, 13// modified or unmodified, in source code or in binary form. 14// 15// Redistribution and use in source and binary forms, with or without 16// modification, are permitted provided that the following conditions are 17// met: redistributions of source code must retain the above copyright 18// notice, this list of conditions and the following disclaimer; 19// redistributions in binary form must reproduce the above copyright 20// notice, this list of conditions and the following disclaimer in the 21// documentation and/or other materials provided with the distribution; 22// neither the name of the copyright holders nor the names of its 23// contributors may be used to endorse or promote products derived from 24// this software without specific prior written permission. 25// 26// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 27// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 28// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 29// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 30// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 31// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 32// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 33// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 34// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 35// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 36// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 37// 38// Authors: Gabe Black 39 40let {{ 41 vfpEnabledCheckCode = ''' 42 { 43 Fault fault = checkAdvSIMDOrFPEnabled32(xc->tcBase(), 44 Cpsr, Cpacr, Nsacr, Fpexc, 45 true, false); 46 if (fault != NoFault) 47 return fault; 48 } 49 ''' 50 51 vfp64EnabledCheckCode = ''' 52 { 53 Fault fault = checkFPAdvSIMDEnabled64(xc->tcBase(), Cpsr, Cpacr64); 54 if (fault != NoFault) 55 return fault; 56 } 57 ''' 58 59 vmsrEnabledCheckCode = ''' 60 { 61 Fault fault = NoFault; 62 if (dest == (int)MISCREG_FPSCR) { 63 fault = checkAdvSIMDOrFPEnabled32(xc->tcBase(), 64 Cpsr, Cpacr, Nsacr, Fpexc, 65 true, false); 66 } else if (!inPrivilegedMode(Cpsr)) { 67 fault = disabledFault(); 68 } else { 69 fault = checkAdvSIMDOrFPEnabled32(xc->tcBase(), 70 Cpsr, Cpacr, Nsacr, Fpexc, 71 false, false); 72 } 73 74 if (fault != NoFault) 75 return fault; 76 } 77 ''' 78 79 vmrsEnabledCheckCode = ''' 80 { 81 Fault fault = NoFault; 82 if (op1 == (int)MISCREG_FPSCR) { 83 fault = checkAdvSIMDOrFPEnabled32(xc->tcBase(), 84 Cpsr, Cpacr, Nsacr, Fpexc, 85 true, false); 86 } else if (!inPrivilegedMode(Cpsr)) { 87 fault = disabledFault(); 88 } else { 89 fault = checkAdvSIMDOrFPEnabled32(xc->tcBase(), 90 Cpsr, Cpacr, Nsacr, Fpexc, 91 false, false); 92 } 93 94 if (fault != NoFault) 95 return fault; 96 } 97 ''' 98}}; 99 100def template FpRegRegOpDeclare {{ 101class %(class_name)s : public %(base_class)s 102{ 103 public: 104 // Constructor 105 %(class_name)s(ExtMachInst machInst, 106 IntRegIndex _dest, IntRegIndex _op1, 107 VfpMicroMode mode = VfpNotAMicroop); 108 Fault execute(ExecContext *, Trace::InstRecord *) const override; 109}; 110}}; 111 112def template FpRegRegOpConstructor {{ 113 %(class_name)s::%(class_name)s(ExtMachInst machInst, 114 IntRegIndex _dest, IntRegIndex _op1, 115 VfpMicroMode mode) 116 : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s, 117 _dest, _op1, mode) 118 { 119 %(constructor)s; 120 if (!(condCode == COND_AL || condCode == COND_UC)) { 121 for (int x = 0; x < _numDestRegs; x++) { 122 _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; 123 } 124 } 125 } 126}}; 127 128def template FpRegImmOpDeclare {{ 129class %(class_name)s : public %(base_class)s 130{ 131 public: 132 // Constructor 133 %(class_name)s(ExtMachInst machInst, IntRegIndex _dest, 134 uint64_t _imm, VfpMicroMode mode = VfpNotAMicroop); 135 Fault execute(ExecContext *, Trace::InstRecord *) const override; 136}; 137}}; 138 139def template FpRegImmOpConstructor {{ 140 %(class_name)s::%(class_name)s(ExtMachInst machInst, 141 IntRegIndex _dest, uint64_t _imm, VfpMicroMode mode) 142 : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s, 143 _dest, _imm, mode) 144 { 145 %(constructor)s; 146 if (!(condCode == COND_AL || condCode == COND_UC)) { 147 for (int x = 0; x < _numDestRegs; x++) { 148 _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; 149 } 150 } 151 } 152}}; 153 154def template FpRegRegImmOpDeclare {{ 155class %(class_name)s : public %(base_class)s 156{ 157 public: 158 // Constructor 159 %(class_name)s(ExtMachInst machInst, 160 IntRegIndex _dest, IntRegIndex _op1, 161 uint64_t _imm, VfpMicroMode mode = VfpNotAMicroop); 162 Fault execute(ExecContext *, Trace::InstRecord *) const override; 163}; 164}}; 165 166def template FpRegRegImmOpConstructor {{ 167 %(class_name)s::%(class_name)s(ExtMachInst machInst, 168 IntRegIndex _dest, 169 IntRegIndex _op1, 170 uint64_t _imm, 171 VfpMicroMode mode) 172 : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s, 173 _dest, _op1, _imm, mode) 174 { 175 %(constructor)s; 176 if (!(condCode == COND_AL || condCode == COND_UC)) { 177 for (int x = 0; x < _numDestRegs; x++) { 178 _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; 179 } 180 } 181 } 182}}; 183 184def template FpRegRegRegOpDeclare {{ 185class %(class_name)s : public %(base_class)s 186{ 187 public: 188 // Constructor 189 %(class_name)s(ExtMachInst machInst, 190 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 191 VfpMicroMode mode = VfpNotAMicroop); 192 Fault execute(ExecContext *, Trace::InstRecord *) const override; 193}; 194}}; 195 196def template FpRegRegRegOpConstructor {{ 197 %(class_name)s::%(class_name)s(ExtMachInst machInst, 198 IntRegIndex _dest, 199 IntRegIndex _op1, 200 IntRegIndex _op2, 201 VfpMicroMode mode) 202 : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s, 203 _dest, _op1, _op2, mode) 204 { 205 %(constructor)s; 206 if (!(condCode == COND_AL || condCode == COND_UC)) { 207 for (int x = 0; x < _numDestRegs; x++) { 208 _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; 209 } 210 } 211 } 212}}; 213 214def template FpRegRegRegCondOpDeclare {{ 215class %(class_name)s : public %(base_class)s 216{ 217 public: 218 // Constructor 219 %(class_name)s(ExtMachInst machInst, 220 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 221 ConditionCode _cond, 222 VfpMicroMode mode = VfpNotAMicroop); 223 Fault execute(ExecContext *, Trace::InstRecord *) const override; 224}; 225}}; 226 227def template FpRegRegRegCondOpConstructor {{ 228 %(class_name)s::%(class_name)s(ExtMachInst machInst, 229 IntRegIndex _dest, 230 IntRegIndex _op1, 231 IntRegIndex _op2, 232 ConditionCode _cond, 233 VfpMicroMode mode) 234 : %(base_class)s("%(mnemonic)s", machInst, %(op_class)s, 235 _dest, _op1, _op2, _cond, mode) 236 { 237 %(constructor)s; 238 } 239}}; 240