integerop.isa revision 3273:5aa5cc05fff9
1// Copyright (c) 2006 The Regents of The University of Michigan 2// All rights reserved. 3// 4// Redistribution and use in source and binary forms, with or without 5// modification, are permitted provided that the following conditions are 6// met: redistributions of source code must retain the above copyright 7// notice, this list of conditions and the following disclaimer; 8// redistributions in binary form must reproduce the above copyright 9// notice, this list of conditions and the following disclaimer in the 10// documentation and/or other materials provided with the distribution; 11// neither the name of the copyright holders nor the names of its 12// contributors may be used to endorse or promote products derived from 13// this software without specific prior written permission. 14// 15// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 16// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 17// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 18// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 19// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 20// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 21// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 25// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26// 27// Authors: Ali Saidi 28// Gabe Black 29// Steve Reinhardt 30 31//////////////////////////////////////////////////////////////////// 32// 33// Integer operate instructions 34// 35 36output header {{ 37 /** 38 * Base class for integer operations. 39 */ 40 class IntOp : public SparcStaticInst 41 { 42 protected: 43 // Constructor 44 IntOp(const char *mnem, ExtMachInst _machInst, 45 OpClass __opClass) : 46 SparcStaticInst(mnem, _machInst, __opClass) 47 { 48 } 49 50 std::string generateDisassembly(Addr pc, 51 const SymbolTable *symtab) const; 52 53 virtual bool printPseudoOps(std::ostream &os, Addr pc, 54 const SymbolTable *symtab) const; 55 }; 56 57 /** 58 * Base class for immediate integer operations. 59 */ 60 class IntOpImm : public IntOp 61 { 62 protected: 63 // Constructor 64 IntOpImm(const char *mnem, ExtMachInst _machInst, 65 OpClass __opClass) : 66 IntOp(mnem, _machInst, __opClass) 67 { 68 } 69 70 int64_t imm; 71 72 std::string generateDisassembly(Addr pc, 73 const SymbolTable *symtab) const; 74 75 virtual bool printPseudoOps(std::ostream &os, Addr pc, 76 const SymbolTable *symtab) const; 77 }; 78 79 /** 80 * Base class for 10 bit immediate integer operations. 81 */ 82 class IntOpImm10 : public IntOpImm 83 { 84 protected: 85 // Constructor 86 IntOpImm10(const char *mnem, ExtMachInst _machInst, 87 OpClass __opClass) : 88 IntOpImm(mnem, _machInst, __opClass) 89 { 90 imm = sext<10>(SIMM10); 91 } 92 }; 93 94 /** 95 * Base class for 11 bit immediate integer operations. 96 */ 97 class IntOpImm11 : public IntOpImm 98 { 99 protected: 100 // Constructor 101 IntOpImm11(const char *mnem, ExtMachInst _machInst, 102 OpClass __opClass) : 103 IntOpImm(mnem, _machInst, __opClass) 104 { 105 imm = sext<11>(SIMM11); 106 } 107 }; 108 109 /** 110 * Base class for 13 bit immediate integer operations. 111 */ 112 class IntOpImm13 : public IntOpImm 113 { 114 protected: 115 // Constructor 116 IntOpImm13(const char *mnem, ExtMachInst _machInst, 117 OpClass __opClass) : 118 IntOpImm(mnem, _machInst, __opClass) 119 { 120 imm = sext<13>(SIMM13); 121 } 122 }; 123 124 /** 125 * Base class for sethi. 126 */ 127 class SetHi : public IntOpImm 128 { 129 protected: 130 // Constructor 131 SetHi(const char *mnem, ExtMachInst _machInst, 132 OpClass __opClass) : 133 IntOpImm(mnem, _machInst, __opClass) 134 { 135 imm = (IMM22 & 0x3FFFFF) << 10; 136 } 137 138 std::string generateDisassembly(Addr pc, 139 const SymbolTable *symtab) const; 140 }; 141}}; 142 143def template SetHiDecode {{ 144 { 145 if(RD == 0 && IMM22 == 0) 146 return (SparcStaticInst *)(new Nop("nop", machInst, No_OpClass)); 147 else 148 return (SparcStaticInst *)(new %(class_name)s(machInst)); 149 } 150}}; 151 152output decoder {{ 153 154 bool IntOp::printPseudoOps(std::ostream &os, Addr pc, 155 const SymbolTable *symbab) const 156 { 157 if(!strcmp(mnemonic, "or") && _srcRegIdx[0] == 0) 158 { 159 printMnemonic(os, "mov"); 160 printSrcReg(os, 1); 161 ccprintf(os, ", "); 162 printDestReg(os, 0); 163 return true; 164 } 165 return false; 166 } 167 168 bool IntOpImm::printPseudoOps(std::ostream &os, Addr pc, 169 const SymbolTable *symbab) const 170 { 171 if(!strcmp(mnemonic, "or")) 172 { 173 if(_numSrcRegs > 0 && _srcRegIdx[0] == 0) 174 { 175 if(imm == 0) 176 printMnemonic(os, "clr"); 177 else 178 { 179 printMnemonic(os, "mov"); 180 ccprintf(os, " 0x%x, ", imm); 181 } 182 printDestReg(os, 0); 183 return true; 184 } 185 else if(imm == 0) 186 { 187 printMnemonic(os, "mov"); 188 printSrcReg(os, 0); 189 ccprintf(os, ", "); 190 printDestReg(os, 0); 191 return true; 192 } 193 } 194 return false; 195 } 196 197 std::string IntOp::generateDisassembly(Addr pc, 198 const SymbolTable *symtab) const 199 { 200 std::stringstream response; 201 202 if(printPseudoOps(response, pc, symtab)) 203 return response.str(); 204 printMnemonic(response, mnemonic); 205 printRegArray(response, _srcRegIdx, _numSrcRegs); 206 if(_numDestRegs && _numSrcRegs) 207 response << ", "; 208 printDestReg(response, 0); 209 return response.str(); 210 } 211 212 std::string IntOpImm::generateDisassembly(Addr pc, 213 const SymbolTable *symtab) const 214 { 215 std::stringstream response; 216 217 if(printPseudoOps(response, pc, symtab)) 218 return response.str(); 219 printMnemonic(response, mnemonic); 220 printRegArray(response, _srcRegIdx, _numSrcRegs); 221 if(_numSrcRegs > 0) 222 response << ", "; 223 ccprintf(response, "0x%x", imm); 224 if(_numDestRegs > 0) 225 response << ", "; 226 printDestReg(response, 0); 227 return response.str(); 228 } 229 230 std::string SetHi::generateDisassembly(Addr pc, 231 const SymbolTable *symtab) const 232 { 233 std::stringstream response; 234 235 printMnemonic(response, mnemonic); 236 ccprintf(response, "%%hi(0x%x), ", imm); 237 printDestReg(response, 0); 238 return response.str(); 239 } 240}}; 241 242def template IntOpExecute {{ 243 Fault %(class_name)s::execute(%(CPU_exec_context)s *xc, 244 Trace::InstRecord *traceData) const 245 { 246 Fault fault = NoFault; 247 248 %(op_decl)s; 249 %(op_rd)s; 250 %(code)s; 251 252 //Write the resulting state to the execution context 253 if(fault == NoFault) 254 { 255 %(cc_code)s; 256 %(op_wb)s; 257 } 258 return fault; 259 } 260}}; 261 262let {{ 263 def doIntFormat(code, ccCode, name, Name, opt_flags): 264 (usesImm, code, immCode, 265 rString, iString) = splitOutImm(code) 266 iop = InstObjParams(name, Name, 'IntOp', code, 267 opt_flags, ("cc_code", ccCode)) 268 header_output = BasicDeclare.subst(iop) 269 decoder_output = BasicConstructor.subst(iop) 270 exec_output = IntOpExecute.subst(iop) 271 if usesImm: 272 imm_iop = InstObjParams(name, Name + 'Imm', 'IntOpImm' + iString, 273 immCode, opt_flags, ("cc_code", ccCode)) 274 header_output += BasicDeclare.subst(imm_iop) 275 decoder_output += BasicConstructor.subst(imm_iop) 276 exec_output += IntOpExecute.subst(imm_iop) 277 decode_block = ROrImmDecode.subst(iop) 278 else: 279 decode_block = BasicDecode.subst(iop) 280 return (header_output, decoder_output, exec_output, decode_block) 281 282 calcCcCode = ''' 283 uint16_t _ic, _iv, _iz, _in, _xc, _xv, _xz, _xn; 284 285 _in = (Rd >> 31) & 1; 286 _iz = ((Rd & 0xFFFFFFFF) == 0); 287 _xn = (Rd >> 63) & 1; 288 _xz = (Rd == 0); 289 _iv = %(ivValue)s & 1; 290 _ic = %(icValue)s & 1; 291 _xv = %(xvValue)s & 1; 292 _xc = %(xcValue)s & 1; 293 294 Ccr = _ic << 0 | _iv << 1 | _iz << 2 | _in << 3 | 295 _xc << 4 | _xv << 5 | _xz << 6 | _xn << 7; 296 297 298 DPRINTF(Sparc, "in = %%d\\n", _in); 299 DPRINTF(Sparc, "iz = %%d\\n", _iz); 300 DPRINTF(Sparc, "xn = %%d\\n", _xn); 301 DPRINTF(Sparc, "xz = %%d\\n", _xz); 302 DPRINTF(Sparc, "iv = %%d\\n", _iv); 303 DPRINTF(Sparc, "ic = %%d\\n", _ic); 304 DPRINTF(Sparc, "xv = %%d\\n", _xv); 305 DPRINTF(Sparc, "xc = %%d\\n", _xc); 306 ''' 307}}; 308 309// Primary format for integer operate instructions: 310def format IntOp(code, *opt_flags) {{ 311 ccCode = '' 312 (header_output, 313 decoder_output, 314 exec_output, 315 decode_block) = doIntFormat(code, ccCode, 316 name, Name, opt_flags) 317}}; 318 319// Primary format for integer operate instructions: 320def format IntOpCc(code, icValue, ivValue, xcValue, xvValue, *opt_flags) {{ 321 ccCode = calcCcCode % vars() 322 (header_output, 323 decoder_output, 324 exec_output, 325 decode_block) = doIntFormat(code, ccCode, 326 name, Name, opt_flags) 327}}; 328 329// Primary format for integer operate instructions: 330def format IntOpCcRes(code, *opt_flags) {{ 331 ccCode = calcCcCode % {"icValue":"0", 332 "ivValue":"0", 333 "xcValue":"0", 334 "xvValue":"0"} 335 (header_output, 336 decoder_output, 337 exec_output, 338 decode_block) = doIntFormat(code, ccCode, 339 name, Name, opt_flags) 340}}; 341 342def format SetHi(code, *opt_flags) {{ 343 iop = InstObjParams(name, Name, 'SetHi', 344 code, opt_flags, ("cc_code", '')) 345 header_output = BasicDeclare.subst(iop) 346 decoder_output = BasicConstructor.subst(iop) 347 exec_output = IntOpExecute.subst(iop) 348 decode_block = SetHiDecode.subst(iop) 349}}; 350 351