aarch64.isa revision 14157:0f836da31d9c
1// Copyright (c) 2011-2019 ARM Limited 2// All rights reserved 3// 4// The license below extends only to copyright in the software and shall 5// not be construed as granting a license to any other intellectual 6// property including but not limited to intellectual property relating 7// to a hardware implementation of the functionality of the software 8// licensed hereunder. You may use the software subject to the license 9// terms below provided that you ensure that this notice is replicated 10// unmodified and in its entirety in all distributions of the software, 11// modified or unmodified, in source code or in binary form. 12// 13// Redistribution and use in source and binary forms, with or without 14// modification, are permitted provided that the following conditions are 15// met: redistributions of source code must retain the above copyright 16// notice, this list of conditions and the following disclaimer; 17// redistributions in binary form must reproduce the above copyright 18// notice, this list of conditions and the following disclaimer in the 19// documentation and/or other materials provided with the distribution; 20// neither the name of the copyright holders nor the names of its 21// contributors may be used to endorse or promote products derived from 22// this software without specific prior written permission. 23// 24// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 25// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 26// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 27// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 28// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 29// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 30// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 31// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 32// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 33// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 34// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 35// 36// Authors: Gabe Black 37// Thomas Grocutt 38// Mbou Eyole 39// Giacomo Gabrielli 40 41output header {{ 42namespace Aarch64 43{ 44 StaticInstPtr decodeDataProcImm(ExtMachInst machInst); 45 StaticInstPtr decodeBranchExcSys(ExtMachInst machInst); 46 StaticInstPtr decodeLoadsStores(ExtMachInst machInst); 47 StaticInstPtr decodeDataProcReg(ExtMachInst machInst); 48 49 template <typename DecoderFeatures> 50 StaticInstPtr decodeFpAdvSIMD(ExtMachInst machInst); 51 StaticInstPtr decodeFp(ExtMachInst machInst); 52 template <typename DecoderFeatures> 53 StaticInstPtr decodeAdvSIMD(ExtMachInst machInst); 54 StaticInstPtr decodeAdvSIMDScalar(ExtMachInst machInst); 55 56 StaticInstPtr decodeSveInt(ExtMachInst machInst); 57 StaticInstPtr decodeSveFp(ExtMachInst machInst); 58 StaticInstPtr decodeSveMem(ExtMachInst machInst); 59 60 StaticInstPtr decodeGem5Ops(ExtMachInst machInst); 61} 62}}; 63 64output decoder {{ 65namespace Aarch64 66{ 67 StaticInstPtr 68 decodeDataProcImm(ExtMachInst machInst) 69 { 70 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 71 IntRegIndex rdsp = makeSP(rd); 72 IntRegIndex rdzr = makeZero(rd); 73 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 74 IntRegIndex rnsp = makeSP(rn); 75 76 uint8_t opc = bits(machInst, 30, 29); 77 bool sf = bits(machInst, 31); 78 bool n = bits(machInst, 22); 79 uint8_t immr = bits(machInst, 21, 16); 80 uint8_t imms = bits(machInst, 15, 10); 81 switch (bits(machInst, 25, 23)) { 82 case 0x0: 83 case 0x1: 84 { 85 uint64_t immlo = bits(machInst, 30, 29); 86 uint64_t immhi = bits(machInst, 23, 5); 87 uint64_t imm = (immlo << 0) | (immhi << 2); 88 if (bits(machInst, 31) == 0) 89 return new AdrXImm(machInst, rdzr, INTREG_ZERO, sext<21>(imm)); 90 else 91 return new AdrpXImm(machInst, rdzr, INTREG_ZERO, 92 sext<33>(imm << 12)); 93 } 94 case 0x2: 95 case 0x3: 96 { 97 uint32_t imm12 = bits(machInst, 21, 10); 98 uint8_t shift = bits(machInst, 23, 22); 99 uint32_t imm; 100 if (shift == 0x0) 101 imm = imm12 << 0; 102 else if (shift == 0x1) 103 imm = imm12 << 12; 104 else 105 return new Unknown64(machInst); 106 switch (opc) { 107 case 0x0: 108 return new AddXImm(machInst, rdsp, rnsp, imm); 109 case 0x1: 110 return new AddXImmCc(machInst, rdzr, rnsp, imm); 111 case 0x2: 112 return new SubXImm(machInst, rdsp, rnsp, imm); 113 case 0x3: 114 return new SubXImmCc(machInst, rdzr, rnsp, imm); 115 default: 116 M5_UNREACHABLE; 117 } 118 } 119 case 0x4: 120 { 121 if (!sf && n) 122 return new Unknown64(machInst); 123 // len = MSB(n:NOT(imms)), len < 1 is undefined. 124 uint8_t len = 0; 125 if (n) { 126 len = 6; 127 } else if (imms == 0x3f || imms == 0x3e) { 128 return new Unknown64(machInst); 129 } else { 130 len = findMsbSet(imms ^ 0x3f); 131 } 132 // Generate r, s, and size. 133 uint64_t r = bits(immr, len - 1, 0); 134 uint64_t s = bits(imms, len - 1, 0); 135 uint8_t size = 1 << len; 136 if (s == size - 1) 137 return new Unknown64(machInst); 138 // Generate the pattern with s 1s, rotated by r, with size bits. 139 uint64_t pattern = mask(s + 1); 140 if (r) { 141 pattern = (pattern >> r) | (pattern << (size - r)); 142 pattern &= mask(size); 143 } 144 uint8_t width = sf ? 64 : 32; 145 // Replicate that to fill up the immediate. 146 for (unsigned i = 1; i < (width / size); i *= 2) 147 pattern |= (pattern << (i * size)); 148 uint64_t imm = pattern; 149 150 switch (opc) { 151 case 0x0: 152 return new AndXImm(machInst, rdsp, rn, imm); 153 case 0x1: 154 return new OrrXImm(machInst, rdsp, rn, imm); 155 case 0x2: 156 return new EorXImm(machInst, rdsp, rn, imm); 157 case 0x3: 158 return new AndXImmCc(machInst, rdzr, rn, imm); 159 default: 160 M5_UNREACHABLE; 161 } 162 } 163 case 0x5: 164 { 165 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 166 IntRegIndex rdzr = makeZero(rd); 167 uint32_t imm16 = bits(machInst, 20, 5); 168 uint32_t hw = bits(machInst, 22, 21); 169 switch (opc) { 170 case 0x0: 171 return new Movn(machInst, rdzr, imm16, hw * 16); 172 case 0x1: 173 return new Unknown64(machInst); 174 case 0x2: 175 return new Movz(machInst, rdzr, imm16, hw * 16); 176 case 0x3: 177 return new Movk(machInst, rdzr, imm16, hw * 16); 178 default: 179 M5_UNREACHABLE; 180 } 181 } 182 case 0x6: 183 if ((sf != n) || (!sf && (bits(immr, 5) || bits(imms, 5)))) 184 return new Unknown64(machInst); 185 switch (opc) { 186 case 0x0: 187 return new Sbfm64(machInst, rdzr, rn, immr, imms); 188 case 0x1: 189 return new Bfm64(machInst, rdzr, rn, immr, imms); 190 case 0x2: 191 return new Ubfm64(machInst, rdzr, rn, immr, imms); 192 case 0x3: 193 return new Unknown64(machInst); 194 default: 195 M5_UNREACHABLE; 196 } 197 case 0x7: 198 { 199 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 200 if (opc || bits(machInst, 21)) 201 return new Unknown64(machInst); 202 else 203 return new Extr64(machInst, rdzr, rn, rm, imms); 204 } 205 } 206 return new FailUnimplemented("Unhandled Case8", machInst); 207 } 208} 209}}; 210 211output decoder {{ 212namespace Aarch64 213{ 214 StaticInstPtr 215 decodeBranchExcSys(ExtMachInst machInst) 216 { 217 switch (bits(machInst, 30, 29)) { 218 case 0x0: 219 { 220 int64_t imm = sext<26>(bits(machInst, 25, 0)) << 2; 221 if (bits(machInst, 31) == 0) 222 return new B64(machInst, imm); 223 else 224 return new Bl64(machInst, imm); 225 } 226 case 0x1: 227 { 228 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 229 if (bits(machInst, 25) == 0) { 230 int64_t imm = sext<19>(bits(machInst, 23, 5)) << 2; 231 if (bits(machInst, 24) == 0) 232 return new Cbz64(machInst, imm, rt); 233 else 234 return new Cbnz64(machInst, imm, rt); 235 } else { 236 uint64_t bitmask = 0x1; 237 bitmask <<= bits(machInst, 23, 19); 238 int64_t imm = sext<14>(bits(machInst, 18, 5)) << 2; 239 if (bits(machInst, 31)) 240 bitmask <<= 32; 241 if (bits(machInst, 24) == 0) 242 return new Tbz64(machInst, bitmask, imm, rt); 243 else 244 return new Tbnz64(machInst, bitmask, imm, rt); 245 } 246 } 247 case 0x2: 248 // bit 30:26=10101 249 if (bits(machInst, 31) == 0) { 250 if (bits(machInst, 25, 24) || bits(machInst, 4)) 251 return new Unknown64(machInst); 252 int64_t imm = sext<19>(bits(machInst, 23, 5)) << 2; 253 ConditionCode condCode = 254 (ConditionCode)(uint8_t)(bits(machInst, 3, 0)); 255 return new BCond64(machInst, imm, condCode); 256 } else if (bits(machInst, 25, 24) == 0x0) { 257 258 if (bits(machInst, 4, 2)) 259 return new Unknown64(machInst); 260 261 auto imm16 = bits(machInst, 20, 5); 262 uint8_t decVal = (bits(machInst, 1, 0) << 0) | 263 (bits(machInst, 23, 21) << 2); 264 265 switch (decVal) { 266 case 0x01: 267 return new Svc64(machInst, imm16); 268 case 0x02: 269 return new Hvc64(machInst, imm16); 270 case 0x03: 271 return new Smc64(machInst, imm16); 272 case 0x04: 273 return new Brk64(machInst, imm16); 274 case 0x08: 275 return new Hlt64(machInst, imm16); 276 case 0x15: 277 return new FailUnimplemented("dcps1", machInst); 278 case 0x16: 279 return new FailUnimplemented("dcps2", machInst); 280 case 0x17: 281 return new FailUnimplemented("dcps3", machInst); 282 default: 283 return new Unknown64(machInst); 284 } 285 } else if (bits(machInst, 25, 22) == 0x4) { 286 // bit 31:22=1101010100 287 bool l = bits(machInst, 21); 288 uint8_t op0 = bits(machInst, 20, 19); 289 uint8_t op1 = bits(machInst, 18, 16); 290 uint8_t crn = bits(machInst, 15, 12); 291 uint8_t crm = bits(machInst, 11, 8); 292 uint8_t op2 = bits(machInst, 7, 5); 293 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 294 switch (op0) { 295 case 0x0: 296 if (rt != 0x1f || l) 297 return new Unknown64(machInst); 298 if (crn == 0x2 && op1 == 0x3) { 299 switch (crm) { 300 case 0x0: 301 switch (op2) { 302 case 0x0: 303 return new NopInst(machInst); 304 case 0x1: 305 return new YieldInst(machInst); 306 case 0x2: 307 return new WfeInst(machInst); 308 case 0x3: 309 return new WfiInst(machInst); 310 case 0x4: 311 return new SevInst(machInst); 312 case 0x5: 313 return new SevlInst(machInst); 314 } 315 break; 316 case 0x1: 317 switch (op2) { 318 case 0x0: 319 return new WarnUnimplemented( 320 "pacia", machInst); 321 case 0x2: 322 return new WarnUnimplemented( 323 "pacib", machInst); 324 case 0x4: 325 return new WarnUnimplemented( 326 "autia", machInst); 327 case 0x6: 328 return new WarnUnimplemented( 329 "autib", machInst); 330 } 331 break; 332 case 0x2: 333 switch (op2) { 334 case 0x0: 335 return new WarnUnimplemented( 336 "esb", machInst); 337 case 0x1: 338 return new WarnUnimplemented( 339 "psb csync", machInst); 340 case 0x2: 341 return new WarnUnimplemented( 342 "tsb csync", machInst); 343 case 0x4: 344 return new WarnUnimplemented( 345 "csdb", machInst); 346 } 347 break; 348 case 0x3: 349 switch (op2) { 350 case 0x0: 351 case 0x1: 352 return new WarnUnimplemented( 353 "pacia", machInst); 354 case 0x2: 355 case 0x3: 356 return new WarnUnimplemented( 357 "pacib", machInst); 358 case 0x4: 359 case 0x5: 360 return new WarnUnimplemented( 361 "autia", machInst); 362 case 0x6: 363 case 0x7: 364 return new WarnUnimplemented( 365 "autib", machInst); 366 } 367 break; 368 case 0x4: 369 switch (op2 & 0x1) { 370 case 0x0: 371 return new WarnUnimplemented( 372 "bti", machInst); 373 } 374 break; 375 } 376 return new WarnUnimplemented( 377 "unallocated_hint", machInst); 378 } else if (crn == 0x3 && op1 == 0x3) { 379 switch (op2) { 380 case 0x2: 381 return new Clrex64(machInst); 382 case 0x4: 383 return new Dsb64(machInst); 384 case 0x5: 385 return new Dmb64(machInst); 386 case 0x6: 387 return new Isb64(machInst); 388 default: 389 return new Unknown64(machInst); 390 } 391 } else if (crn == 0x4) { 392 // MSR immediate: moving immediate value to selected 393 // bits of the PSTATE 394 switch (op1 << 3 | op2) { 395 case 0x4: 396 // PAN 397 return new MsrImm64( 398 machInst, MISCREG_PAN, crm); 399 case 0x5: 400 // SP 401 return new MsrImm64( 402 machInst, MISCREG_SPSEL, crm); 403 case 0x1e: 404 // DAIFSet 405 return new MsrImmDAIFSet64( 406 machInst, MISCREG_DAIF, crm); 407 case 0x1f: 408 // DAIFClr 409 return new MsrImmDAIFClr64( 410 machInst, MISCREG_DAIF, crm); 411 default: 412 return new Unknown64(machInst); 413 } 414 } else { 415 return new Unknown64(machInst); 416 } 417 break; 418 case 0x1: 419 case 0x2: 420 case 0x3: 421 { 422 // bit 31:22=1101010100, 20:19=11 423 bool read = l; 424 MiscRegIndex miscReg = 425 decodeAArch64SysReg(op0, op1, crn, crm, op2); 426 if (read) { 427 if ((miscReg == MISCREG_DC_CIVAC_Xt) || 428 (miscReg == MISCREG_DC_CVAC_Xt) || 429 (miscReg == MISCREG_DC_IVAC_Xt) || 430 (miscReg == MISCREG_DC_ZVA_Xt)) { 431 return new Unknown64(machInst); 432 } 433 } 434 // Check for invalid registers 435 if (miscReg == MISCREG_UNKNOWN) { 436 auto full_mnemonic = 437 csprintf("%s op0:%d op1:%d crn:%d crm:%d op2:%d", 438 read ? "mrs" : "msr", 439 op0, op1, crn, crm, op2); 440 441 return new FailUnimplemented(read ? "mrs" : "msr", 442 machInst, full_mnemonic); 443 444 } else if (miscReg == MISCREG_IMPDEF_UNIMPL) { 445 auto full_mnemonic = 446 csprintf("%s op0:%d op1:%d crn:%d crm:%d op2:%d", 447 read ? "mrs" : "msr", 448 op0, op1, crn, crm, op2); 449 450 uint32_t iss = msrMrs64IssBuild( 451 read, op0, op1, crn, crm, op2, rt); 452 453 return new MiscRegImplDefined64( 454 read ? "mrs" : "msr", 455 machInst, miscReg, read, iss, full_mnemonic, 456 miscRegInfo[miscReg][MISCREG_WARN_NOT_FAIL]); 457 458 } else if (miscRegInfo[miscReg][MISCREG_IMPLEMENTED]) { 459 if (miscReg == MISCREG_NZCV) { 460 if (read) 461 return new MrsNZCV64(machInst, rt, (IntRegIndex) miscReg); 462 else 463 return new MsrNZCV64(machInst, (IntRegIndex) miscReg, rt); 464 } 465 uint32_t iss = msrMrs64IssBuild(read, op0, op1, crn, crm, op2, rt); 466 if (read) { 467 StaticInstPtr si = new Mrs64(machInst, rt, miscReg, iss); 468 if (miscRegInfo[miscReg][MISCREG_UNVERIFIABLE]) 469 si->setFlag(StaticInst::IsUnverifiable); 470 return si; 471 } else { 472 switch (miscReg) { 473 case MISCREG_DC_ZVA_Xt: 474 return new Dczva(machInst, rt, miscReg, iss); 475 case MISCREG_DC_CVAU_Xt: 476 return new Dccvau(machInst, rt, miscReg, iss); 477 case MISCREG_DC_CVAC_Xt: 478 return new Dccvac(machInst, rt, miscReg, iss); 479 case MISCREG_DC_CIVAC_Xt: 480 return new Dccivac(machInst, rt, miscReg, iss); 481 case MISCREG_DC_IVAC_Xt: 482 return new Dcivac(machInst, rt, miscReg, iss); 483 default: 484 return new Msr64(machInst, miscReg, rt, iss); 485 } 486 } 487 } else if (miscRegInfo[miscReg][MISCREG_WARN_NOT_FAIL]) { 488 std::string full_mnem = csprintf("%s %s", 489 read ? "mrs" : "msr", miscRegName[miscReg]); 490 return new WarnUnimplemented(read ? "mrs" : "msr", 491 machInst, full_mnem); 492 } else { 493 return new FailUnimplemented(read ? "mrs" : "msr", 494 machInst, 495 csprintf("%s %s", 496 read ? "mrs" : "msr", 497 miscRegName[miscReg])); 498 } 499 } 500 break; 501 default: 502 M5_UNREACHABLE; 503 } 504 } else if (bits(machInst, 25) == 0x1) { 505 uint8_t opc = bits(machInst, 24, 21); 506 uint8_t op2 = bits(machInst, 20, 16); 507 uint8_t op3 = bits(machInst, 15, 10); 508 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 509 uint8_t op4 = bits(machInst, 4, 0); 510 if (op2 != 0x1f || op3 != 0x0 || op4 != 0x0) 511 return new Unknown64(machInst); 512 switch (opc) { 513 case 0x0: 514 return new Br64(machInst, rn); 515 case 0x1: 516 return new Blr64(machInst, rn); 517 case 0x2: 518 return new Ret64(machInst, rn); 519 case 0x4: 520 if (rn != 0x1f) 521 return new Unknown64(machInst); 522 return new Eret64(machInst); 523 case 0x5: 524 if (rn != 0x1f) 525 return new Unknown64(machInst); 526 return new FailUnimplemented("dret", machInst); 527 default: 528 return new Unknown64(machInst); 529 } 530 } 531 M5_FALLTHROUGH; 532 default: 533 return new Unknown64(machInst); 534 } 535 return new FailUnimplemented("Unhandled Case7", machInst); 536 } 537} 538}}; 539 540output decoder {{ 541namespace Aarch64 542{ 543 StaticInstPtr 544 decodeAtomicArithOp(ExtMachInst machInst) 545 { 546 uint8_t opc = bits(machInst, 14, 12); 547 uint8_t o3 = bits(machInst, 15); 548 uint8_t size_ar = bits(machInst, 23, 22)<<0 | bits(machInst, 31, 30)<<2; 549 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 550 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 551 IntRegIndex rnsp = makeSP(rn); 552 IntRegIndex rs = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 553 uint8_t A_rt = bits(machInst, 4, 0)<<0 | bits(machInst, 23)<<5; 554 555 switch(opc) { 556 case 0x0: 557 switch(size_ar){ 558 case 0x0: 559 if (o3 == 1) 560 return new SWPB(machInst, rt, rnsp, rs); 561 else if (A_rt == 0x1f) 562 return new STADDB(machInst, rt, rnsp, rs); 563 else 564 return new LDADDB(machInst, rt, rnsp, rs); 565 case 0x1 : 566 if (o3 == 1) 567 return new SWPLB(machInst, rt, rnsp, rs); 568 else if (A_rt == 0x1f) 569 return new STADDLB(machInst, rt, rnsp, rs); 570 else 571 return new LDADDLB(machInst, rt, rnsp, rs); 572 case 0x2: 573 if (o3 == 1) 574 return new SWPAB(machInst, rt, rnsp, rs); 575 else 576 return new LDADDAB(machInst, rt, rnsp, rs); 577 case 0x3: 578 if (o3 == 1) 579 return new SWPLAB(machInst, rt, rnsp, rs); 580 else 581 return new LDADDLAB(machInst, rt, rnsp, rs); 582 case 0x4: 583 if (o3 == 1) 584 return new SWPH(machInst, rt, rnsp, rs); 585 else if (A_rt == 0x1f) 586 return new STADDH(machInst, rt, rnsp, rs); 587 else 588 return new LDADDH(machInst, rt, rnsp, rs); 589 case 0x5 : 590 if (o3 == 1) 591 return new SWPLH(machInst, rt, rnsp, rs); 592 else if (A_rt == 0x1f) 593 return new STADDLH(machInst, rt, rnsp, rs); 594 else 595 return new LDADDLH(machInst, rt, rnsp, rs); 596 case 0x6: 597 if (o3 == 1) 598 return new SWPAH(machInst, rt, rnsp, rs); 599 else 600 return new LDADDAH(machInst, rt, rnsp, rs); 601 case 0x7: 602 if (o3 == 1) 603 return new SWPLAH(machInst, rt, rnsp, rs); 604 else 605 return new LDADDLAH(machInst, rt, rnsp, rs); 606 case 0x8: 607 if (o3 == 1) 608 return new SWP(machInst, rt, rnsp, rs); 609 else if (A_rt == 0x1f) 610 return new STADD(machInst, rt, rnsp, rs); 611 else 612 return new LDADD(machInst, rt, rnsp, rs); 613 case 0x9 : 614 if (o3 == 1) 615 return new SWPL(machInst, rt, rnsp, rs); 616 else if (A_rt == 0x1f) 617 return new STADDL(machInst, rt, rnsp, rs); 618 else 619 return new LDADDL(machInst, rt, rnsp, rs); 620 case 0xa: 621 if (o3 == 1) 622 return new SWPA(machInst, rt, rnsp, rs); 623 else 624 return new LDADDA(machInst, rt, rnsp, rs); 625 case 0xb: 626 if (o3 == 1) 627 return new SWPLA(machInst, rt, rnsp, rs); 628 else 629 return new LDADDLA(machInst, rt, rnsp, rs); 630 case 0xc: 631 if (o3 == 1) 632 return new SWP64(machInst, rt, rnsp, rs); 633 634 else if (A_rt == 0x1f) 635 return new STADD64(machInst, rt, rnsp, rs); 636 else 637 return new LDADD64(machInst, rt, rnsp, rs); 638 case 0xd : 639 if (o3 == 1) 640 return new SWPL64(machInst, rt, rnsp, rs); 641 else if (A_rt == 0x1f) 642 return new STADDL64(machInst, rt, rnsp, rs); 643 else 644 return new LDADDL64(machInst, rt, rnsp, rs); 645 case 0xe: 646 if (o3 == 1) 647 return new SWPA64(machInst, rt, rnsp, rs); 648 else 649 return new LDADDA64(machInst, rt, rnsp, rs); 650 case 0xf: 651 if (o3 == 1) 652 return new SWPLA64(machInst, rt, rnsp, rs); 653 else 654 return new LDADDLA64(machInst, rt, rnsp, rs); 655 } 656 case 0x1: 657 switch(size_ar){ 658 case 0x0: 659 if (A_rt == 0x1f) 660 return new STCLRB(machInst, rt, rnsp, rs); 661 else 662 return new LDCLRB(machInst, rt, rnsp, rs); 663 case 0x1 : 664 if (A_rt == 0x1f) 665 return new STCLRLB(machInst, rt, rnsp, rs); 666 else 667 return new LDCLRLB(machInst, rt, rnsp, rs); 668 case 0x2: 669 return new LDCLRAB(machInst, rt, rnsp, rs); 670 case 0x3: 671 return new LDCLRLAB(machInst, rt, rnsp, rs); 672 case 0x4: 673 if (A_rt == 0x1f) 674 return new STCLRH(machInst, rt, rnsp, rs); 675 else 676 return new LDCLRH(machInst, rt, rnsp, rs); 677 case 0x5 : 678 if (A_rt == 0x1f) 679 return new STCLRLH(machInst, rt, rnsp, rs); 680 else 681 return new LDCLRLH(machInst, rt, rnsp, rs); 682 case 0x6: 683 return new LDCLRAH(machInst, rt, rnsp, rs); 684 case 0x7: 685 return new LDCLRLAH(machInst, rt, rnsp, rs); 686 case 0x8: 687 if (A_rt == 0x1f) 688 return new STCLR(machInst, rt, rnsp, rs); 689 else 690 return new LDCLR(machInst, rt, rnsp, rs); 691 case 0x9 : 692 if (A_rt == 0x1f) 693 return new STCLRL(machInst, rt, rnsp, rs); 694 else 695 return new LDCLRL(machInst, rt, rnsp, rs); 696 case 0xa: 697 return new LDCLRA(machInst, rt, rnsp, rs); 698 case 0xb: 699 return new LDCLRLA(machInst, rt, rnsp, rs); 700 case 0xc: 701 if (A_rt == 0x1f) 702 return new STCLR64(machInst, rt, rnsp, rs); 703 else 704 return new LDCLR64(machInst, rt, rnsp, rs); 705 case 0xd : 706 if (A_rt == 0x1f) 707 return new STCLRL64(machInst, rt, rnsp, rs); 708 else 709 return new LDCLRL64(machInst, rt, rnsp, rs); 710 case 0xe: 711 return new LDCLRA64(machInst, rt, rnsp, rs); 712 case 0xf: 713 return new LDCLRLA64(machInst, rt, rnsp, rs); 714 } 715 case 0x2: 716 switch(size_ar){ 717 case 0x0: 718 if (A_rt == 0x1f) 719 return new STEORB(machInst, rt, rnsp, rs); 720 else 721 return new LDEORB(machInst, rt, rnsp, rs); 722 case 0x1 : 723 if (A_rt == 0x1f) 724 return new STEORLB(machInst, rt, rnsp, rs); 725 else 726 return new LDEORLB(machInst, rt, rnsp, rs); 727 case 0x2: 728 return new LDEORAB(machInst, rt, rnsp, rs); 729 case 0x3: 730 return new LDEORLAB(machInst, rt, rnsp, rs); 731 case 0x4: 732 if (A_rt == 0x1f) 733 return new STEORH(machInst, rt, rnsp, rs); 734 else 735 return new LDEORH(machInst, rt, rnsp, rs); 736 case 0x5 : 737 if (A_rt == 0x1f) 738 return new STEORLH(machInst, rt, rnsp, rs); 739 else 740 return new LDEORLH(machInst, rt, rnsp, rs); 741 case 0x6: 742 return new LDEORAH(machInst, rt, rnsp, rs); 743 case 0x7: 744 return new LDEORLAH(machInst, rt, rnsp, rs); 745 case 0x8: 746 if (A_rt == 0x1f) 747 return new STEOR(machInst, rt, rnsp, rs); 748 else 749 return new LDEOR(machInst, rt, rnsp, rs); 750 case 0x9 : 751 if (A_rt == 0x1f) 752 return new STEORL(machInst, rt, rnsp, rs); 753 else 754 return new LDEORL(machInst, rt, rnsp, rs); 755 case 0xa: 756 return new LDEORA(machInst, rt, rnsp, rs); 757 case 0xb: 758 return new LDEORLA(machInst, rt, rnsp, rs); 759 case 0xc: 760 if (A_rt == 0x1f) 761 return new STEOR64(machInst, rt, rnsp, rs); 762 else 763 return new LDEOR64(machInst, rt, rnsp, rs); 764 case 0xd : 765 if (A_rt == 0x1f) 766 return new STEORL64(machInst, rt, rnsp, rs); 767 else 768 return new LDEORL64(machInst, rt, rnsp, rs); 769 case 0xe: 770 return new LDEORA64(machInst, rt, rnsp, rs); 771 case 0xf: 772 return new LDEORLA64(machInst, rt, rnsp, rs); 773 } 774 case 0x3: 775 switch(size_ar){ 776 case 0x0: 777 if (A_rt == 0x1f) 778 return new STSETB(machInst, rt, rnsp, rs); 779 else 780 return new LDSETB(machInst, rt, rnsp, rs); 781 case 0x1 : 782 if (A_rt == 0x1f) 783 return new STSETLB(machInst, rt, rnsp, rs); 784 else 785 return new LDSETLB(machInst, rt, rnsp, rs); 786 case 0x2: 787 return new LDSETAB(machInst, rt, rnsp, rs); 788 case 0x3: 789 return new LDSETLAB(machInst, rt, rnsp, rs); 790 case 0x4: 791 if (A_rt == 0x1f) 792 return new STSETH(machInst, rt, rnsp, rs); 793 else 794 return new LDSETH(machInst, rt, rnsp, rs); 795 case 0x5 : 796 if (A_rt == 0x1f) 797 return new STSETLH(machInst, rt, rnsp, rs); 798 else 799 return new LDSETLH(machInst, rt, rnsp, rs); 800 case 0x6: 801 return new LDSETAH(machInst, rt, rnsp, rs); 802 case 0x7: 803 return new LDSETLAH(machInst, rt, rnsp, rs); 804 case 0x8: 805 if (A_rt == 0x1f) 806 return new STSET(machInst, rt, rnsp, rs); 807 else 808 return new LDSET(machInst, rt, rnsp, rs); 809 case 0x9 : 810 if (A_rt == 0x1f) 811 return new STSETL(machInst, rt, rnsp, rs); 812 else 813 return new LDSETL(machInst, rt, rnsp, rs); 814 case 0xa: 815 return new LDSETA(machInst, rt, rnsp, rs); 816 case 0xb: 817 return new LDSETLA(machInst, rt, rnsp, rs); 818 case 0xc: 819 if (A_rt == 0x1f) 820 return new STSET64(machInst, rt, rnsp, rs); 821 else 822 return new LDSET64(machInst, rt, rnsp, rs); 823 case 0xd : 824 if (A_rt == 0x1f) 825 return new STSETL64(machInst, rt, rnsp, rs); 826 else 827 return new LDSETL64(machInst, rt, rnsp, rs); 828 case 0xe: 829 return new LDSETA64(machInst, rt, rnsp, rs); 830 case 0xf: 831 return new LDSETLA64(machInst, rt, rnsp, rs); 832 } 833 case 0x4: 834 switch(size_ar){ 835 case 0x0: 836 if (A_rt == 0x1f) 837 return new STSMAXB(machInst, rt, rnsp, rs); 838 else 839 return new LDSMAXB(machInst, rt, rnsp, rs); 840 case 0x1 : 841 if (A_rt == 0x1f) 842 return new STSMAXLB(machInst, rt, rnsp, rs); 843 else 844 return new LDSMAXLB(machInst, rt, rnsp, rs); 845 case 0x2: 846 return new LDSMAXAB(machInst, rt, rnsp, rs); 847 case 0x3: 848 return new LDSMAXLAB(machInst, rt, rnsp, rs); 849 case 0x4: 850 if (A_rt == 0x1f) 851 return new STSMAXH(machInst, rt, rnsp, rs); 852 else 853 return new LDSMAXH(machInst, rt, rnsp, rs); 854 case 0x5 : 855 if (A_rt == 0x1f) 856 return new STSMAXLH(machInst, rt, rnsp, rs); 857 else 858 return new LDSMAXLH(machInst, rt, rnsp, rs); 859 case 0x6: 860 return new LDSMAXAH(machInst, rt, rnsp, rs); 861 case 0x7: 862 return new LDSMAXLAH(machInst, rt, rnsp, rs); 863 case 0x8: 864 if (A_rt == 0x1f) 865 return new STSMAX(machInst, rt, rnsp, rs); 866 else 867 return new LDSMAX(machInst, rt, rnsp, rs); 868 case 0x9 : 869 if (A_rt == 0x1f) 870 return new STSMAXL(machInst, rt, rnsp, rs); 871 else 872 return new LDSMAXL(machInst, rt, rnsp, rs); 873 case 0xa: 874 return new LDSMAXA(machInst, rt, rnsp, rs); 875 case 0xb: 876 return new LDSMAXLA(machInst, rt, rnsp, rs); 877 case 0xc: 878 if (A_rt == 0x1f) 879 return new STSMAX64(machInst, rt, rnsp, rs); 880 else 881 return new LDSMAX64(machInst, rt, rnsp, rs); 882 case 0xd : 883 if (A_rt == 0x1f) 884 return new STSMAXL64(machInst, rt, rnsp, rs); 885 else 886 return new LDSMAXL64(machInst, rt, rnsp, rs); 887 case 0xe: 888 return new LDSMAXA64(machInst, rt, rnsp, rs); 889 case 0xf: 890 return new LDSMAXLA64(machInst, rt, rnsp, rs); 891 } 892 case 0x5: 893 switch(size_ar){ 894 case 0x0: 895 if (A_rt == 0x1f) 896 return new STSMINB(machInst, rt, rnsp, rs); 897 else 898 return new LDSMINB(machInst, rt, rnsp, rs); 899 case 0x1 : 900 if (A_rt == 0x1f) 901 return new STSMINLB(machInst, rt, rnsp, rs); 902 else 903 return new LDSMINLB(machInst, rt, rnsp, rs); 904 case 0x2: 905 return new LDSMINAB(machInst, rt, rnsp, rs); 906 case 0x3: 907 return new LDSMINLAB(machInst, rt, rnsp, rs); 908 case 0x4: 909 if (A_rt == 0x1f) 910 return new STSMINH(machInst, rt, rnsp, rs); 911 else 912 return new LDSMINH(machInst, rt, rnsp, rs); 913 case 0x5 : 914 if (A_rt == 0x1f) 915 return new STSMINLH(machInst, rt, rnsp, rs); 916 else 917 return new LDSMINLH(machInst, rt, rnsp, rs); 918 case 0x6: 919 return new LDSMINAH(machInst, rt, rnsp, rs); 920 case 0x7: 921 return new LDSMINLAH(machInst, rt, rnsp, rs); 922 case 0x8: 923 if (A_rt == 0x1f) 924 return new STSMIN(machInst, rt, rnsp, rs); 925 else 926 return new LDSMIN(machInst, rt, rnsp, rs); 927 case 0x9 : 928 if (A_rt == 0x1f) 929 return new STSMINL(machInst, rt, rnsp, rs); 930 else 931 return new LDSMINL(machInst, rt, rnsp, rs); 932 case 0xa: 933 return new LDSMINA(machInst, rt, rnsp, rs); 934 case 0xb: 935 return new LDSMINLA(machInst, rt, rnsp, rs); 936 case 0xc: 937 if (A_rt == 0x1f) 938 return new STSMIN64(machInst, rt, rnsp, rs); 939 else 940 return new LDSMIN64(machInst, rt, rnsp, rs); 941 case 0xd : 942 if (A_rt == 0x1f) 943 return new STSMINL64(machInst, rt, rnsp, rs); 944 else 945 return new LDSMINL64(machInst, rt, rnsp, rs); 946 case 0xe: 947 return new LDSMINA64(machInst, rt, rnsp, rs); 948 case 0xf: 949 return new LDSMINLA64(machInst, rt, rnsp, rs); 950 } 951 case 0x6: 952 switch(size_ar){ 953 case 0x0: 954 if (A_rt == 0x1f) 955 return new STUMAXB(machInst, rt, rnsp, rs); 956 else 957 return new LDUMAXB(machInst, rt, rnsp, rs); 958 case 0x1 : 959 if (A_rt == 0x1f) 960 return new STUMAXLB(machInst, rt, rnsp, rs); 961 else 962 return new LDUMAXLB(machInst, rt, rnsp, rs); 963 case 0x2: 964 return new LDUMAXAB(machInst, rt, rnsp, rs); 965 case 0x3: 966 return new LDUMAXLAB(machInst, rt, rnsp, rs); 967 case 0x4: 968 if (A_rt == 0x1f) 969 return new STUMAXH(machInst, rt, rnsp, rs); 970 else 971 return new LDUMAXH(machInst, rt, rnsp, rs); 972 case 0x5 : 973 if (A_rt == 0x1f) 974 return new STUMAXLH(machInst, rt, rnsp, rs); 975 else 976 return new LDUMAXLH(machInst, rt, rnsp, rs); 977 case 0x6: 978 return new LDUMAXAH(machInst, rt, rnsp, rs); 979 case 0x7: 980 return new LDUMAXLAH(machInst, rt, rnsp, rs); 981 case 0x8: 982 if (A_rt == 0x1f) 983 return new STUMAX(machInst, rt, rnsp, rs); 984 else 985 return new LDUMAX(machInst, rt, rnsp, rs); 986 case 0x9 : 987 if (A_rt == 0x1f) 988 return new STUMAXL(machInst, rt, rnsp, rs); 989 else 990 return new LDUMAXL(machInst, rt, rnsp, rs); 991 case 0xa: 992 return new LDUMAXA(machInst, rt, rnsp, rs); 993 case 0xb: 994 return new LDUMAXLA(machInst, rt, rnsp, rs); 995 case 0xc: 996 if (A_rt == 0x1f) 997 return new STUMAX64(machInst, rt, rnsp, rs); 998 else 999 return new LDUMAX64(machInst, rt, rnsp, rs); 1000 case 0xd : 1001 if (A_rt == 0x1f) 1002 return new STUMAXL64(machInst, rt, rnsp, rs); 1003 else 1004 return new LDUMAXL64(machInst, rt, rnsp, rs); 1005 case 0xe: 1006 return new LDUMAXA64(machInst, rt, rnsp, rs); 1007 case 0xf: 1008 return new LDUMAXLA64(machInst, rt, rnsp, rs); 1009 } 1010 case 0x7: 1011 switch(size_ar){ 1012 case 0x0: 1013 if (A_rt == 0x1f) 1014 return new STUMINB(machInst, rt, rnsp, rs); 1015 else 1016 return new LDUMINB(machInst, rt, rnsp, rs); 1017 case 0x1 : 1018 if (A_rt == 0x1f) 1019 return new STUMINLB(machInst, rt, rnsp, rs); 1020 else 1021 return new LDUMINLB(machInst, rt, rnsp, rs); 1022 case 0x2: 1023 return new LDUMINAB(machInst, rt, rnsp, rs); 1024 case 0x3: 1025 return new LDUMINLAB(machInst, rt, rnsp, rs); 1026 case 0x4: 1027 if (A_rt == 0x1f) 1028 return new STUMINH(machInst, rt, rnsp, rs); 1029 else 1030 return new LDUMINH(machInst, rt, rnsp, rs); 1031 case 0x5 : 1032 if (A_rt == 0x1f) 1033 return new STUMINLH(machInst, rt, rnsp, rs); 1034 else 1035 return new LDUMINLH(machInst, rt, rnsp, rs); 1036 case 0x6: 1037 return new LDUMINAH(machInst, rt, rnsp, rs); 1038 case 0x7: 1039 return new LDUMINLAH(machInst, rt, rnsp, rs); 1040 case 0x8: 1041 if (A_rt == 0x1f) 1042 return new STUMIN(machInst, rt, rnsp, rs); 1043 else 1044 return new LDUMIN(machInst, rt, rnsp, rs); 1045 case 0x9 : 1046 if (A_rt == 0x1f) 1047 return new STUMINL(machInst, rt, rnsp, rs); 1048 else 1049 return new LDUMINL(machInst, rt, rnsp, rs); 1050 case 0xa: 1051 return new LDUMINA(machInst, rt, rnsp, rs); 1052 case 0xb: 1053 return new LDUMINLA(machInst, rt, rnsp, rs); 1054 case 0xc: 1055 if (A_rt == 0x1f) 1056 return new STUMIN64(machInst, rt, rnsp, rs); 1057 else 1058 return new LDUMIN64(machInst, rt, rnsp, rs); 1059 case 0xd : 1060 if (A_rt == 0x1f) 1061 return new STUMINL64(machInst, rt, rnsp, rs); 1062 else 1063 return new LDUMINL64(machInst, rt, rnsp, rs); 1064 case 0xe: 1065 return new LDUMINA64(machInst, rt, rnsp, rs); 1066 case 0xf: 1067 return new LDUMINLA64(machInst, rt, rnsp, rs); 1068 } 1069 default: 1070 return new Unknown64(machInst); 1071 } 1072 } 1073} 1074}}; 1075 1076 1077output decoder {{ 1078namespace Aarch64 1079{ 1080 1081 StaticInstPtr 1082 decodeLoadsStores(ExtMachInst machInst) 1083 { 1084 // bit 27,25=10 1085 switch (bits(machInst, 29, 28)) { 1086 case 0x0: 1087 if (bits(machInst, 26) == 0) { 1088 if (bits(machInst, 24) != 0) 1089 return new Unknown64(machInst); 1090 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1091 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1092 IntRegIndex rnsp = makeSP(rn); 1093 IntRegIndex rt2 = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 1094 IntRegIndex rs = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1095 uint8_t opc = (bits(machInst, 15) << 0) | 1096 (bits(machInst, 23, 21) << 1); 1097 uint8_t size = bits(machInst, 31, 30); 1098 switch (opc) { 1099 case 0x0: 1100 switch (size) { 1101 case 0x0: 1102 return new STXRB64(machInst, rt, rnsp, rs); 1103 case 0x1: 1104 return new STXRH64(machInst, rt, rnsp, rs); 1105 case 0x2: 1106 return new STXRW64(machInst, rt, rnsp, rs); 1107 case 0x3: 1108 return new STXRX64(machInst, rt, rnsp, rs); 1109 default: 1110 M5_UNREACHABLE; 1111 } 1112 case 0x1: 1113 switch (size) { 1114 case 0x0: 1115 return new STLXRB64(machInst, rt, rnsp, rs); 1116 case 0x1: 1117 return new STLXRH64(machInst, rt, rnsp, rs); 1118 case 0x2: 1119 return new STLXRW64(machInst, rt, rnsp, rs); 1120 case 0x3: 1121 return new STLXRX64(machInst, rt, rnsp, rs); 1122 default: 1123 M5_UNREACHABLE; 1124 } 1125 case 0x2: 1126 switch (size) { 1127 case 0x0: 1128 return new CASP32(machInst, rt, rnsp, rs); 1129 case 0x1: 1130 return new CASP64(machInst, rt, rnsp, rs); 1131 case 0x2: 1132 return new STXPW64(machInst, rs, rt, rt2, rnsp); 1133 case 0x3: 1134 return new STXPX64(machInst, rs, rt, rt2, rnsp); 1135 default: 1136 M5_UNREACHABLE; 1137 } 1138 1139 case 0x3: 1140 switch (size) { 1141 case 0x0: 1142 return new CASPL32(machInst, rt, rnsp, rs); 1143 case 0x1: 1144 return new CASPL64(machInst, rt, rnsp, rs); 1145 case 0x2: 1146 return new STLXPW64(machInst, rs, rt, rt2, rnsp); 1147 case 0x3: 1148 return new STLXPX64(machInst, rs, rt, rt2, rnsp); 1149 default: 1150 M5_UNREACHABLE; 1151 } 1152 1153 case 0x4: 1154 switch (size) { 1155 case 0x0: 1156 return new LDXRB64(machInst, rt, rnsp, rs); 1157 case 0x1: 1158 return new LDXRH64(machInst, rt, rnsp, rs); 1159 case 0x2: 1160 return new LDXRW64(machInst, rt, rnsp, rs); 1161 case 0x3: 1162 return new LDXRX64(machInst, rt, rnsp, rs); 1163 default: 1164 M5_UNREACHABLE; 1165 } 1166 case 0x5: 1167 switch (size) { 1168 case 0x0: 1169 return new LDAXRB64(machInst, rt, rnsp, rs); 1170 case 0x1: 1171 return new LDAXRH64(machInst, rt, rnsp, rs); 1172 case 0x2: 1173 return new LDAXRW64(machInst, rt, rnsp, rs); 1174 case 0x3: 1175 return new LDAXRX64(machInst, rt, rnsp, rs); 1176 default: 1177 M5_UNREACHABLE; 1178 } 1179 case 0x6: 1180 switch (size) { 1181 case 0x0: 1182 return new CASPA32(machInst, rt, rnsp, rs); 1183 case 0x1: 1184 return new CASPA64(machInst, rt, rnsp, rs); 1185 case 0x2: 1186 return new LDXPW64(machInst, rt, rt2, rnsp); 1187 case 0x3: 1188 return new LDXPX64(machInst, rt, rt2, rnsp); 1189 default: 1190 M5_UNREACHABLE; 1191 } 1192 case 0x7: 1193 switch (size) { 1194 case 0x0: 1195 return new CASPAL32(machInst, rt, rnsp, rs); 1196 case 0x1: 1197 return new CASPAL64(machInst, rt, rnsp, rs); 1198 case 0x2: 1199 return new LDAXPW64(machInst, rt, rt2, rnsp); 1200 case 0x3: 1201 return new LDAXPX64(machInst, rt, rt2, rnsp); 1202 default: 1203 M5_UNREACHABLE; 1204 } 1205 case 0x9: 1206 switch (size) { 1207 case 0x0: 1208 return new STLRB64(machInst, rt, rnsp); 1209 case 0x1: 1210 return new STLRH64(machInst, rt, rnsp); 1211 case 0x2: 1212 return new STLRW64(machInst, rt, rnsp); 1213 case 0x3: 1214 return new STLRX64(machInst, rt, rnsp); 1215 default: 1216 M5_UNREACHABLE; 1217 } 1218 case 0xa: 1219 switch (size) { 1220 case 0x0: 1221 return new CASB(machInst, rt, rnsp, rs); 1222 case 0x1: 1223 return new CASH(machInst, rt, rnsp, rs); 1224 case 0x2: 1225 return new CAS32(machInst, rt, rnsp, rs); 1226 case 0x3: 1227 return new CAS64(machInst, rt, rnsp, rs); 1228 default: 1229 M5_UNREACHABLE; 1230 } 1231 case 0xb: 1232 switch (size) { 1233 case 0x0: 1234 return new CASLB(machInst, rt, rnsp, rs); 1235 case 0x1: 1236 return new CASLH(machInst, rt, rnsp, rs); 1237 case 0x2: 1238 return new CASL32(machInst, rt, rnsp, rs); 1239 case 0x3: 1240 return new CASL64(machInst, rt, rnsp, rs); 1241 default: 1242 M5_UNREACHABLE; 1243 } 1244 case 0xd: 1245 switch (size) { 1246 case 0x0: 1247 return new LDARB64(machInst, rt, rnsp); 1248 case 0x1: 1249 return new LDARH64(machInst, rt, rnsp); 1250 case 0x2: 1251 return new LDARW64(machInst, rt, rnsp); 1252 case 0x3: 1253 return new LDARX64(machInst, rt, rnsp); 1254 default: 1255 M5_UNREACHABLE; 1256 } 1257 case 0xe: 1258 switch (size) { 1259 case 0x0: 1260 return new CASAB(machInst, rt, rnsp, rs); 1261 case 0x1: 1262 return new CASAH(machInst, rt, rnsp, rs); 1263 case 0x2: 1264 return new CASA32(machInst, rt, rnsp, rs); 1265 case 0x3: 1266 return new CASA64(machInst, rt, rnsp, rs); 1267 default: 1268 M5_UNREACHABLE; 1269 } 1270 case 0xf: 1271 switch (size) { 1272 case 0x0: 1273 return new CASALB(machInst, rt, rnsp, rs); 1274 case 0x1: 1275 return new CASALH(machInst, rt, rnsp, rs); 1276 case 0x2: 1277 return new CASAL32(machInst, rt, rnsp, rs); 1278 case 0x3: 1279 return new CASAL64(machInst, rt, rnsp, rs); 1280 default: 1281 M5_UNREACHABLE; 1282 } 1283 default: 1284 return new Unknown64(machInst); 1285 } 1286 } else if (bits(machInst, 31)) { 1287 return new Unknown64(machInst); 1288 } else { 1289 return decodeNeonMem(machInst); 1290 } 1291 case 0x1: 1292 { 1293 if (bits(machInst, 24) != 0) 1294 return new Unknown64(machInst); 1295 uint8_t switchVal = (bits(machInst, 26) << 0) | 1296 (bits(machInst, 31, 30) << 1); 1297 int64_t imm = sext<19>(bits(machInst, 23, 5)) << 2; 1298 IntRegIndex rt = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1299 switch (switchVal) { 1300 case 0x0: 1301 return new LDRWL64_LIT(machInst, rt, imm); 1302 case 0x1: 1303 return new LDRSFP64_LIT(machInst, rt, imm); 1304 case 0x2: 1305 return new LDRXL64_LIT(machInst, rt, imm); 1306 case 0x3: 1307 return new LDRDFP64_LIT(machInst, rt, imm); 1308 case 0x4: 1309 return new LDRSWL64_LIT(machInst, rt, imm); 1310 case 0x5: 1311 return new BigFpMemLit("ldr", machInst, rt, imm); 1312 case 0x6: 1313 return new PRFM64_LIT(machInst, rt, imm); 1314 default: 1315 return new Unknown64(machInst); 1316 } 1317 } 1318 case 0x2: 1319 { 1320 uint8_t opc = bits(machInst, 31, 30); 1321 if (opc >= 3) 1322 return new Unknown64(machInst); 1323 uint32_t size = 0; 1324 bool fp = bits(machInst, 26); 1325 bool load = bits(machInst, 22); 1326 if (fp) { 1327 size = 4 << opc; 1328 } else { 1329 if ((opc == 1) && !load) 1330 return new Unknown64(machInst); 1331 size = (opc == 0 || opc == 1) ? 4 : 8; 1332 } 1333 uint8_t type = bits(machInst, 24, 23); 1334 int64_t imm = sext<7>(bits(machInst, 21, 15)) * size; 1335 1336 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1337 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1338 IntRegIndex rt2 = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 1339 1340 bool noAlloc = (type == 0); 1341 bool signExt = !noAlloc && !fp && opc == 1; 1342 PairMemOp::AddrMode mode; 1343 const char *mnemonic = NULL; 1344 switch (type) { 1345 case 0x0: 1346 case 0x2: 1347 mode = PairMemOp::AddrMd_Offset; 1348 break; 1349 case 0x1: 1350 mode = PairMemOp::AddrMd_PostIndex; 1351 break; 1352 case 0x3: 1353 mode = PairMemOp::AddrMd_PreIndex; 1354 break; 1355 default: 1356 return new Unknown64(machInst); 1357 } 1358 if (load) { 1359 if (noAlloc) 1360 mnemonic = "ldnp"; 1361 else if (signExt) 1362 mnemonic = "ldpsw"; 1363 else 1364 mnemonic = "ldp"; 1365 } else { 1366 if (noAlloc) 1367 mnemonic = "stnp"; 1368 else 1369 mnemonic = "stp"; 1370 } 1371 1372 return new LdpStp(mnemonic, machInst, size, fp, load, noAlloc, 1373 signExt, false, false, imm, mode, rn, rt, rt2); 1374 } 1375 // bit 29:27=111, 25=0 1376 case 0x3: 1377 { 1378 uint8_t switchVal = (bits(machInst, 23, 22) << 0) | 1379 (bits(machInst, 26) << 2) | 1380 (bits(machInst, 31, 30) << 3); 1381 if (bits(machInst, 24) == 1) { 1382 uint64_t imm12 = bits(machInst, 21, 10); 1383 IntRegIndex rt = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1384 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1385 IntRegIndex rnsp = makeSP(rn); 1386 switch (switchVal) { 1387 case 0x00: 1388 return new STRB64_IMM(machInst, rt, rnsp, imm12); 1389 case 0x01: 1390 return new LDRB64_IMM(machInst, rt, rnsp, imm12); 1391 case 0x02: 1392 return new LDRSBX64_IMM(machInst, rt, rnsp, imm12); 1393 case 0x03: 1394 return new LDRSBW64_IMM(machInst, rt, rnsp, imm12); 1395 case 0x04: 1396 return new STRBFP64_IMM(machInst, rt, rnsp, imm12); 1397 case 0x05: 1398 return new LDRBFP64_IMM(machInst, rt, rnsp, imm12); 1399 case 0x06: 1400 return new BigFpMemImm("str", machInst, false, 1401 rt, rnsp, imm12 << 4); 1402 case 0x07: 1403 return new BigFpMemImm("ldr", machInst, true, 1404 rt, rnsp, imm12 << 4); 1405 case 0x08: 1406 return new STRH64_IMM(machInst, rt, rnsp, imm12 << 1); 1407 case 0x09: 1408 return new LDRH64_IMM(machInst, rt, rnsp, imm12 << 1); 1409 case 0x0a: 1410 return new LDRSHX64_IMM(machInst, rt, rnsp, imm12 << 1); 1411 case 0x0b: 1412 return new LDRSHW64_IMM(machInst, rt, rnsp, imm12 << 1); 1413 case 0x0c: 1414 return new STRHFP64_IMM(machInst, rt, rnsp, imm12 << 1); 1415 case 0x0d: 1416 return new LDRHFP64_IMM(machInst, rt, rnsp, imm12 << 1); 1417 case 0x10: 1418 return new STRW64_IMM(machInst, rt, rnsp, imm12 << 2); 1419 case 0x11: 1420 return new LDRW64_IMM(machInst, rt, rnsp, imm12 << 2); 1421 case 0x12: 1422 return new LDRSW64_IMM(machInst, rt, rnsp, imm12 << 2); 1423 case 0x14: 1424 return new STRSFP64_IMM(machInst, rt, rnsp, imm12 << 2); 1425 case 0x15: 1426 return new LDRSFP64_IMM(machInst, rt, rnsp, imm12 << 2); 1427 case 0x18: 1428 return new STRX64_IMM(machInst, rt, rnsp, imm12 << 3); 1429 case 0x19: 1430 return new LDRX64_IMM(machInst, rt, rnsp, imm12 << 3); 1431 case 0x1a: 1432 return new PRFM64_IMM(machInst, rt, rnsp, imm12 << 3); 1433 case 0x1c: 1434 return new STRDFP64_IMM(machInst, rt, rnsp, imm12 << 3); 1435 case 0x1d: 1436 return new LDRDFP64_IMM(machInst, rt, rnsp, imm12 << 3); 1437 default: 1438 return new Unknown64(machInst); 1439 } 1440 } else if (bits(machInst, 21) == 1) { 1441 uint8_t group = bits(machInst, 11, 10); 1442 switch (group) { 1443 case 0x0: 1444 { 1445 if ((switchVal & 0x7) == 0x2 && 1446 bits(machInst, 20, 12) == 0x1fc) { 1447 IntRegIndex rt = (IntRegIndex)(uint32_t) 1448 bits(machInst, 4, 0); 1449 IntRegIndex rn = (IntRegIndex)(uint32_t) 1450 bits(machInst, 9, 5); 1451 IntRegIndex rnsp = makeSP(rn); 1452 uint8_t size = bits(machInst, 31, 30); 1453 switch (size) { 1454 case 0x0: 1455 return new LDAPRB64(machInst, rt, rnsp); 1456 case 0x1: 1457 return new LDAPRH64(machInst, rt, rnsp); 1458 case 0x2: 1459 return new LDAPRW64(machInst, rt, rnsp); 1460 case 0x3: 1461 return new LDAPRX64(machInst, rt, rnsp); 1462 default: 1463 M5_UNREACHABLE; 1464 } 1465 } else { 1466 return decodeAtomicArithOp(machInst); 1467 } 1468 } 1469 case 0x2: 1470 { 1471 if (!bits(machInst, 14)) 1472 return new Unknown64(machInst); 1473 IntRegIndex rt = (IntRegIndex)(uint32_t) 1474 bits(machInst, 4, 0); 1475 IntRegIndex rn = (IntRegIndex)(uint32_t) 1476 bits(machInst, 9, 5); 1477 IntRegIndex rnsp = makeSP(rn); 1478 IntRegIndex rm = (IntRegIndex)(uint32_t) 1479 bits(machInst, 20, 16); 1480 ArmExtendType type = 1481 (ArmExtendType)(uint32_t)bits(machInst, 15, 13); 1482 uint8_t s = bits(machInst, 12); 1483 switch (switchVal) { 1484 case 0x00: 1485 return new STRB64_REG(machInst, rt, rnsp, rm, 1486 type, 0); 1487 case 0x01: 1488 return new LDRB64_REG(machInst, rt, rnsp, rm, 1489 type, 0); 1490 case 0x02: 1491 return new LDRSBX64_REG(machInst, rt, rnsp, rm, 1492 type, 0); 1493 case 0x03: 1494 return new LDRSBW64_REG(machInst, rt, rnsp, rm, 1495 type, 0); 1496 case 0x04: 1497 return new STRBFP64_REG(machInst, rt, rnsp, rm, 1498 type, 0); 1499 case 0x05: 1500 return new LDRBFP64_REG(machInst, rt, rnsp, rm, 1501 type, 0); 1502 case 0x6: 1503 return new BigFpMemReg("str", machInst, false, 1504 rt, rnsp, rm, type, s * 4); 1505 case 0x7: 1506 return new BigFpMemReg("ldr", machInst, true, 1507 rt, rnsp, rm, type, s * 4); 1508 case 0x08: 1509 return new STRH64_REG(machInst, rt, rnsp, rm, 1510 type, s); 1511 case 0x09: 1512 return new LDRH64_REG(machInst, rt, rnsp, rm, 1513 type, s); 1514 case 0x0a: 1515 return new LDRSHX64_REG(machInst, rt, rnsp, rm, 1516 type, s); 1517 case 0x0b: 1518 return new LDRSHW64_REG(machInst, rt, rnsp, rm, 1519 type, s); 1520 case 0x0c: 1521 return new STRHFP64_REG(machInst, rt, rnsp, rm, 1522 type, s); 1523 case 0x0d: 1524 return new LDRHFP64_REG(machInst, rt, rnsp, rm, 1525 type, s); 1526 case 0x10: 1527 return new STRW64_REG(machInst, rt, rnsp, rm, 1528 type, s * 2); 1529 case 0x11: 1530 return new LDRW64_REG(machInst, rt, rnsp, rm, 1531 type, s * 2); 1532 case 0x12: 1533 return new LDRSW64_REG(machInst, rt, rnsp, rm, 1534 type, s * 2); 1535 case 0x14: 1536 return new STRSFP64_REG(machInst, rt, rnsp, rm, 1537 type, s * 2); 1538 case 0x15: 1539 return new LDRSFP64_REG(machInst, rt, rnsp, rm, 1540 type, s * 2); 1541 case 0x18: 1542 return new STRX64_REG(machInst, rt, rnsp, rm, 1543 type, s * 3); 1544 case 0x19: 1545 return new LDRX64_REG(machInst, rt, rnsp, rm, 1546 type, s * 3); 1547 case 0x1a: 1548 return new PRFM64_REG(machInst, rt, rnsp, rm, 1549 type, s * 3); 1550 case 0x1c: 1551 return new STRDFP64_REG(machInst, rt, rnsp, rm, 1552 type, s * 3); 1553 case 0x1d: 1554 return new LDRDFP64_REG(machInst, rt, rnsp, rm, 1555 type, s * 3); 1556 default: 1557 return new Unknown64(machInst); 1558 1559 } 1560 } 1561 default: 1562 return new Unknown64(machInst); 1563 } 1564 } else { 1565 // bit 29:27=111, 25:24=00, 21=0 1566 switch (bits(machInst, 11, 10)) { 1567 case 0x0: 1568 { 1569 IntRegIndex rt = 1570 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1571 IntRegIndex rn = 1572 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1573 IntRegIndex rnsp = makeSP(rn); 1574 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1575 switch (switchVal) { 1576 case 0x00: 1577 return new STURB64_IMM(machInst, rt, rnsp, imm); 1578 case 0x01: 1579 return new LDURB64_IMM(machInst, rt, rnsp, imm); 1580 case 0x02: 1581 return new LDURSBX64_IMM(machInst, rt, rnsp, imm); 1582 case 0x03: 1583 return new LDURSBW64_IMM(machInst, rt, rnsp, imm); 1584 case 0x04: 1585 return new STURBFP64_IMM(machInst, rt, rnsp, imm); 1586 case 0x05: 1587 return new LDURBFP64_IMM(machInst, rt, rnsp, imm); 1588 case 0x06: 1589 return new BigFpMemImm("stur", machInst, false, 1590 rt, rnsp, imm); 1591 case 0x07: 1592 return new BigFpMemImm("ldur", machInst, true, 1593 rt, rnsp, imm); 1594 case 0x08: 1595 return new STURH64_IMM(machInst, rt, rnsp, imm); 1596 case 0x09: 1597 return new LDURH64_IMM(machInst, rt, rnsp, imm); 1598 case 0x0a: 1599 return new LDURSHX64_IMM(machInst, rt, rnsp, imm); 1600 case 0x0b: 1601 return new LDURSHW64_IMM(machInst, rt, rnsp, imm); 1602 case 0x0c: 1603 return new STURHFP64_IMM(machInst, rt, rnsp, imm); 1604 case 0x0d: 1605 return new LDURHFP64_IMM(machInst, rt, rnsp, imm); 1606 case 0x10: 1607 return new STURW64_IMM(machInst, rt, rnsp, imm); 1608 case 0x11: 1609 return new LDURW64_IMM(machInst, rt, rnsp, imm); 1610 case 0x12: 1611 return new LDURSW64_IMM(machInst, rt, rnsp, imm); 1612 case 0x14: 1613 return new STURSFP64_IMM(machInst, rt, rnsp, imm); 1614 case 0x15: 1615 return new LDURSFP64_IMM(machInst, rt, rnsp, imm); 1616 case 0x18: 1617 return new STURX64_IMM(machInst, rt, rnsp, imm); 1618 case 0x19: 1619 return new LDURX64_IMM(machInst, rt, rnsp, imm); 1620 case 0x1a: 1621 return new PRFUM64_IMM(machInst, rt, rnsp, imm); 1622 case 0x1c: 1623 return new STURDFP64_IMM(machInst, rt, rnsp, imm); 1624 case 0x1d: 1625 return new LDURDFP64_IMM(machInst, rt, rnsp, imm); 1626 default: 1627 return new Unknown64(machInst); 1628 } 1629 } 1630 // bit 29:27=111, 25:24=00, 21=0, 11:10=01 1631 case 0x1: 1632 { 1633 IntRegIndex rt = 1634 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1635 IntRegIndex rn = 1636 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1637 IntRegIndex rnsp = makeSP(rn); 1638 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1639 switch (switchVal) { 1640 case 0x00: 1641 return new STRB64_POST(machInst, rt, rnsp, imm); 1642 case 0x01: 1643 return new LDRB64_POST(machInst, rt, rnsp, imm); 1644 case 0x02: 1645 return new LDRSBX64_POST(machInst, rt, rnsp, imm); 1646 case 0x03: 1647 return new LDRSBW64_POST(machInst, rt, rnsp, imm); 1648 case 0x04: 1649 return new STRBFP64_POST(machInst, rt, rnsp, imm); 1650 case 0x05: 1651 return new LDRBFP64_POST(machInst, rt, rnsp, imm); 1652 case 0x06: 1653 return new BigFpMemPost("str", machInst, false, 1654 rt, rnsp, imm); 1655 case 0x07: 1656 return new BigFpMemPost("ldr", machInst, true, 1657 rt, rnsp, imm); 1658 case 0x08: 1659 return new STRH64_POST(machInst, rt, rnsp, imm); 1660 case 0x09: 1661 return new LDRH64_POST(machInst, rt, rnsp, imm); 1662 case 0x0a: 1663 return new LDRSHX64_POST(machInst, rt, rnsp, imm); 1664 case 0x0b: 1665 return new LDRSHW64_POST(machInst, rt, rnsp, imm); 1666 case 0x0c: 1667 return new STRHFP64_POST(machInst, rt, rnsp, imm); 1668 case 0x0d: 1669 return new LDRHFP64_POST(machInst, rt, rnsp, imm); 1670 case 0x10: 1671 return new STRW64_POST(machInst, rt, rnsp, imm); 1672 case 0x11: 1673 return new LDRW64_POST(machInst, rt, rnsp, imm); 1674 case 0x12: 1675 return new LDRSW64_POST(machInst, rt, rnsp, imm); 1676 case 0x14: 1677 return new STRSFP64_POST(machInst, rt, rnsp, imm); 1678 case 0x15: 1679 return new LDRSFP64_POST(machInst, rt, rnsp, imm); 1680 case 0x18: 1681 return new STRX64_POST(machInst, rt, rnsp, imm); 1682 case 0x19: 1683 return new LDRX64_POST(machInst, rt, rnsp, imm); 1684 case 0x1c: 1685 return new STRDFP64_POST(machInst, rt, rnsp, imm); 1686 case 0x1d: 1687 return new LDRDFP64_POST(machInst, rt, rnsp, imm); 1688 default: 1689 return new Unknown64(machInst); 1690 } 1691 } 1692 case 0x2: 1693 { 1694 IntRegIndex rt = 1695 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1696 IntRegIndex rn = 1697 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1698 IntRegIndex rnsp = makeSP(rn); 1699 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1700 switch (switchVal) { 1701 case 0x00: 1702 return new STTRB64_IMM(machInst, rt, rnsp, imm); 1703 case 0x01: 1704 return new LDTRB64_IMM(machInst, rt, rnsp, imm); 1705 case 0x02: 1706 return new LDTRSBX64_IMM(machInst, rt, rnsp, imm); 1707 case 0x03: 1708 return new LDTRSBW64_IMM(machInst, rt, rnsp, imm); 1709 case 0x08: 1710 return new STTRH64_IMM(machInst, rt, rnsp, imm); 1711 case 0x09: 1712 return new LDTRH64_IMM(machInst, rt, rnsp, imm); 1713 case 0x0a: 1714 return new LDTRSHX64_IMM(machInst, rt, rnsp, imm); 1715 case 0x0b: 1716 return new LDTRSHW64_IMM(machInst, rt, rnsp, imm); 1717 case 0x10: 1718 return new STTRW64_IMM(machInst, rt, rnsp, imm); 1719 case 0x11: 1720 return new LDTRW64_IMM(machInst, rt, rnsp, imm); 1721 case 0x12: 1722 return new LDTRSW64_IMM(machInst, rt, rnsp, imm); 1723 case 0x18: 1724 return new STTRX64_IMM(machInst, rt, rnsp, imm); 1725 case 0x19: 1726 return new LDTRX64_IMM(machInst, rt, rnsp, imm); 1727 default: 1728 return new Unknown64(machInst); 1729 } 1730 } 1731 case 0x3: 1732 { 1733 IntRegIndex rt = 1734 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1735 IntRegIndex rn = 1736 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1737 IntRegIndex rnsp = makeSP(rn); 1738 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1739 switch (switchVal) { 1740 case 0x00: 1741 return new STRB64_PRE(machInst, rt, rnsp, imm); 1742 case 0x01: 1743 return new LDRB64_PRE(machInst, rt, rnsp, imm); 1744 case 0x02: 1745 return new LDRSBX64_PRE(machInst, rt, rnsp, imm); 1746 case 0x03: 1747 return new LDRSBW64_PRE(machInst, rt, rnsp, imm); 1748 case 0x04: 1749 return new STRBFP64_PRE(machInst, rt, rnsp, imm); 1750 case 0x05: 1751 return new LDRBFP64_PRE(machInst, rt, rnsp, imm); 1752 case 0x06: 1753 return new BigFpMemPre("str", machInst, false, 1754 rt, rnsp, imm); 1755 case 0x07: 1756 return new BigFpMemPre("ldr", machInst, true, 1757 rt, rnsp, imm); 1758 case 0x08: 1759 return new STRH64_PRE(machInst, rt, rnsp, imm); 1760 case 0x09: 1761 return new LDRH64_PRE(machInst, rt, rnsp, imm); 1762 case 0x0a: 1763 return new LDRSHX64_PRE(machInst, rt, rnsp, imm); 1764 case 0x0b: 1765 return new LDRSHW64_PRE(machInst, rt, rnsp, imm); 1766 case 0x0c: 1767 return new STRHFP64_PRE(machInst, rt, rnsp, imm); 1768 case 0x0d: 1769 return new LDRHFP64_PRE(machInst, rt, rnsp, imm); 1770 case 0x10: 1771 return new STRW64_PRE(machInst, rt, rnsp, imm); 1772 case 0x11: 1773 return new LDRW64_PRE(machInst, rt, rnsp, imm); 1774 case 0x12: 1775 return new LDRSW64_PRE(machInst, rt, rnsp, imm); 1776 case 0x14: 1777 return new STRSFP64_PRE(machInst, rt, rnsp, imm); 1778 case 0x15: 1779 return new LDRSFP64_PRE(machInst, rt, rnsp, imm); 1780 case 0x18: 1781 return new STRX64_PRE(machInst, rt, rnsp, imm); 1782 case 0x19: 1783 return new LDRX64_PRE(machInst, rt, rnsp, imm); 1784 case 0x1c: 1785 return new STRDFP64_PRE(machInst, rt, rnsp, imm); 1786 case 0x1d: 1787 return new LDRDFP64_PRE(machInst, rt, rnsp, imm); 1788 default: 1789 return new Unknown64(machInst); 1790 } 1791 } 1792 default: 1793 M5_UNREACHABLE; 1794 } 1795 } 1796 } 1797 default: 1798 M5_UNREACHABLE; 1799 } 1800 return new FailUnimplemented("Unhandled Case1", machInst); 1801 } 1802} 1803}}; 1804 1805output decoder {{ 1806namespace Aarch64 1807{ 1808 StaticInstPtr 1809 decodeDataProcReg(ExtMachInst machInst) 1810 { 1811 uint8_t switchVal = (bits(machInst, 28) << 1) | 1812 (bits(machInst, 24) << 0); 1813 switch (switchVal) { 1814 case 0x0: 1815 { 1816 uint8_t switchVal = (bits(machInst, 21) << 0) | 1817 (bits(machInst, 30, 29) << 1); 1818 ArmShiftType type = (ArmShiftType)(uint8_t)bits(machInst, 23, 22); 1819 uint8_t imm6 = bits(machInst, 15, 10); 1820 bool sf = bits(machInst, 31); 1821 if (!sf && (imm6 & 0x20)) 1822 return new Unknown64(machInst); 1823 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1824 IntRegIndex rdzr = makeZero(rd); 1825 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1826 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1827 1828 switch (switchVal) { 1829 case 0x0: 1830 return new AndXSReg(machInst, rdzr, rn, rm, imm6, type); 1831 case 0x1: 1832 return new BicXSReg(machInst, rdzr, rn, rm, imm6, type); 1833 case 0x2: 1834 return new OrrXSReg(machInst, rdzr, rn, rm, imm6, type); 1835 case 0x3: 1836 return new OrnXSReg(machInst, rdzr, rn, rm, imm6, type); 1837 case 0x4: 1838 return new EorXSReg(machInst, rdzr, rn, rm, imm6, type); 1839 case 0x5: 1840 return new EonXSReg(machInst, rdzr, rn, rm, imm6, type); 1841 case 0x6: 1842 return new AndXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1843 case 0x7: 1844 return new BicXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1845 default: 1846 M5_UNREACHABLE; 1847 } 1848 } 1849 case 0x1: 1850 { 1851 uint8_t switchVal = bits(machInst, 30, 29); 1852 if (bits(machInst, 21) == 0) { 1853 ArmShiftType type = 1854 (ArmShiftType)(uint8_t)bits(machInst, 23, 22); 1855 if (type == ROR) 1856 return new Unknown64(machInst); 1857 uint8_t imm6 = bits(machInst, 15, 10); 1858 if (!bits(machInst, 31) && bits(imm6, 5)) 1859 return new Unknown64(machInst); 1860 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1861 IntRegIndex rdzr = makeZero(rd); 1862 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1863 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1864 switch (switchVal) { 1865 case 0x0: 1866 return new AddXSReg(machInst, rdzr, rn, rm, imm6, type); 1867 case 0x1: 1868 return new AddXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1869 case 0x2: 1870 return new SubXSReg(machInst, rdzr, rn, rm, imm6, type); 1871 case 0x3: 1872 return new SubXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1873 default: 1874 M5_UNREACHABLE; 1875 } 1876 } else { 1877 if (bits(machInst, 23, 22) != 0 || bits(machInst, 12, 10) > 0x4) 1878 return new Unknown64(machInst); 1879 ArmExtendType type = 1880 (ArmExtendType)(uint8_t)bits(machInst, 15, 13); 1881 uint8_t imm3 = bits(machInst, 12, 10); 1882 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1883 IntRegIndex rdsp = makeSP(rd); 1884 IntRegIndex rdzr = makeZero(rd); 1885 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1886 IntRegIndex rnsp = makeSP(rn); 1887 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1888 1889 switch (switchVal) { 1890 case 0x0: 1891 return new AddXEReg(machInst, rdsp, rnsp, rm, type, imm3); 1892 case 0x1: 1893 return new AddXERegCc(machInst, rdzr, rnsp, rm, type, imm3); 1894 case 0x2: 1895 return new SubXEReg(machInst, rdsp, rnsp, rm, type, imm3); 1896 case 0x3: 1897 return new SubXERegCc(machInst, rdzr, rnsp, rm, type, imm3); 1898 default: 1899 M5_UNREACHABLE; 1900 } 1901 } 1902 } 1903 case 0x2: 1904 { 1905 if (bits(machInst, 21) == 1) 1906 return new Unknown64(machInst); 1907 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1908 IntRegIndex rdzr = makeZero(rd); 1909 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1910 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1911 switch (bits(machInst, 23, 22)) { 1912 case 0x0: 1913 { 1914 if (bits(machInst, 15, 10)) 1915 return new Unknown64(machInst); 1916 uint8_t switchVal = bits(machInst, 30, 29); 1917 switch (switchVal) { 1918 case 0x0: 1919 return new AdcXSReg(machInst, rdzr, rn, rm, 0, LSL); 1920 case 0x1: 1921 return new AdcXSRegCc(machInst, rdzr, rn, rm, 0, LSL); 1922 case 0x2: 1923 return new SbcXSReg(machInst, rdzr, rn, rm, 0, LSL); 1924 case 0x3: 1925 return new SbcXSRegCc(machInst, rdzr, rn, rm, 0, LSL); 1926 default: 1927 M5_UNREACHABLE; 1928 } 1929 } 1930 case 0x1: 1931 { 1932 if ((bits(machInst, 4) == 1) || 1933 (bits(machInst, 10) == 1) || 1934 (bits(machInst, 29) == 0)) { 1935 return new Unknown64(machInst); 1936 } 1937 ConditionCode cond = 1938 (ConditionCode)(uint8_t)bits(machInst, 15, 12); 1939 uint8_t flags = bits(machInst, 3, 0); 1940 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1941 if (bits(machInst, 11) == 0) { 1942 IntRegIndex rm = 1943 (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1944 if (bits(machInst, 30) == 0) { 1945 return new CcmnReg64(machInst, rn, rm, cond, flags); 1946 } else { 1947 return new CcmpReg64(machInst, rn, rm, cond, flags); 1948 } 1949 } else { 1950 uint8_t imm5 = bits(machInst, 20, 16); 1951 if (bits(machInst, 30) == 0) { 1952 return new CcmnImm64(machInst, rn, imm5, cond, flags); 1953 } else { 1954 return new CcmpImm64(machInst, rn, imm5, cond, flags); 1955 } 1956 } 1957 } 1958 case 0x2: 1959 { 1960 if (bits(machInst, 29) == 1 || 1961 bits(machInst, 11) == 1) { 1962 return new Unknown64(machInst); 1963 } 1964 uint8_t switchVal = (bits(machInst, 10) << 0) | 1965 (bits(machInst, 30) << 1); 1966 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1967 IntRegIndex rdzr = makeZero(rd); 1968 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1969 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1970 ConditionCode cond = 1971 (ConditionCode)(uint8_t)bits(machInst, 15, 12); 1972 switch (switchVal) { 1973 case 0x0: 1974 return new Csel64(machInst, rdzr, rn, rm, cond); 1975 case 0x1: 1976 return new Csinc64(machInst, rdzr, rn, rm, cond); 1977 case 0x2: 1978 return new Csinv64(machInst, rdzr, rn, rm, cond); 1979 case 0x3: 1980 return new Csneg64(machInst, rdzr, rn, rm, cond); 1981 default: 1982 M5_UNREACHABLE; 1983 } 1984 } 1985 case 0x3: 1986 if (bits(machInst, 30) == 0) { 1987 if (bits(machInst, 29) != 0) 1988 return new Unknown64(machInst); 1989 uint8_t switchVal = bits(machInst, 15, 10); 1990 switch (switchVal) { 1991 case 0x2: 1992 return new Udiv64(machInst, rdzr, rn, rm); 1993 case 0x3: 1994 return new Sdiv64(machInst, rdzr, rn, rm); 1995 case 0x8: 1996 return new Lslv64(machInst, rdzr, rn, rm); 1997 case 0x9: 1998 return new Lsrv64(machInst, rdzr, rn, rm); 1999 case 0xa: 2000 return new Asrv64(machInst, rdzr, rn, rm); 2001 case 0xb: 2002 return new Rorv64(machInst, rdzr, rn, rm); 2003 case 0x10: 2004 return new Crc32b64(machInst, rdzr, rn, rm); 2005 case 0x11: 2006 return new Crc32h64(machInst, rdzr, rn, rm); 2007 case 0x12: 2008 return new Crc32w64(machInst, rdzr, rn, rm); 2009 case 0x13: 2010 return new Crc32x64(machInst, rdzr, rn, rm); 2011 case 0x14: 2012 return new Crc32cb64(machInst, rdzr, rn, rm); 2013 case 0x15: 2014 return new Crc32ch64(machInst, rdzr, rn, rm); 2015 case 0x16: 2016 return new Crc32cw64(machInst, rdzr, rn, rm); 2017 case 0x17: 2018 return new Crc32cx64(machInst, rdzr, rn, rm); 2019 default: 2020 return new Unknown64(machInst); 2021 } 2022 } else { 2023 if (bits(machInst, 20, 16) != 0 || 2024 bits(machInst, 29) != 0) { 2025 return new Unknown64(machInst); 2026 } 2027 uint8_t switchVal = bits(machInst, 15, 10); 2028 switch (switchVal) { 2029 case 0x0: 2030 return new Rbit64(machInst, rdzr, rn); 2031 case 0x1: 2032 return new Rev1664(machInst, rdzr, rn); 2033 case 0x2: 2034 if (bits(machInst, 31) == 0) 2035 return new Rev64(machInst, rdzr, rn); 2036 else 2037 return new Rev3264(machInst, rdzr, rn); 2038 case 0x3: 2039 if (bits(machInst, 31) != 1) 2040 return new Unknown64(machInst); 2041 return new Rev64(machInst, rdzr, rn); 2042 case 0x4: 2043 return new Clz64(machInst, rdzr, rn); 2044 case 0x5: 2045 return new Cls64(machInst, rdzr, rn); 2046 default: 2047 return new Unknown64(machInst); 2048 } 2049 } 2050 default: 2051 M5_UNREACHABLE; 2052 } 2053 } 2054 case 0x3: 2055 { 2056 if (bits(machInst, 30, 29) != 0x0 || 2057 (bits(machInst, 23, 21) != 0 && bits(machInst, 31) == 0)) 2058 return new Unknown64(machInst); 2059 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 2060 IntRegIndex rdzr = makeZero(rd); 2061 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 2062 IntRegIndex ra = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 2063 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 2064 switch (bits(machInst, 23, 21)) { 2065 case 0x0: 2066 if (bits(machInst, 15) == 0) 2067 return new Madd64(machInst, rdzr, ra, rn, rm); 2068 else 2069 return new Msub64(machInst, rdzr, ra, rn, rm); 2070 case 0x1: 2071 if (bits(machInst, 15) == 0) 2072 return new Smaddl64(machInst, rdzr, ra, rn, rm); 2073 else 2074 return new Smsubl64(machInst, rdzr, ra, rn, rm); 2075 case 0x2: 2076 if (bits(machInst, 15) != 0) 2077 return new Unknown64(machInst); 2078 return new Smulh64(machInst, rdzr, rn, rm); 2079 case 0x5: 2080 if (bits(machInst, 15) == 0) 2081 return new Umaddl64(machInst, rdzr, ra, rn, rm); 2082 else 2083 return new Umsubl64(machInst, rdzr, ra, rn, rm); 2084 case 0x6: 2085 if (bits(machInst, 15) != 0) 2086 return new Unknown64(machInst); 2087 return new Umulh64(machInst, rdzr, rn, rm); 2088 default: 2089 return new Unknown64(machInst); 2090 } 2091 } 2092 default: 2093 M5_UNREACHABLE; 2094 } 2095 return new FailUnimplemented("Unhandled Case2", machInst); 2096 } 2097} 2098}}; 2099 2100output decoder {{ 2101namespace Aarch64 2102{ 2103 template <typename DecoderFeatures> 2104 StaticInstPtr 2105 decodeAdvSIMD(ExtMachInst machInst) 2106 { 2107 if (bits(machInst, 24) == 1) { 2108 if (bits(machInst, 10) == 0) { 2109 return decodeNeonIndexedElem<DecoderFeatures>(machInst); 2110 } else if (bits(machInst, 23) == 1) { 2111 return new Unknown64(machInst); 2112 } else { 2113 if (bits(machInst, 22, 19)) { 2114 return decodeNeonShiftByImm(machInst); 2115 } else { 2116 return decodeNeonModImm(machInst); 2117 } 2118 } 2119 } else if (bits(machInst, 21) == 1) { 2120 if (bits(machInst, 10) == 1) { 2121 return decodeNeon3Same<DecoderFeatures>(machInst); 2122 } else if (bits(machInst, 11) == 0) { 2123 return decodeNeon3Diff(machInst); 2124 } else if (bits(machInst, 20, 17) == 0x0) { 2125 return decodeNeon2RegMisc(machInst); 2126 } else if (bits(machInst, 20, 17) == 0x4) { 2127 return decodeCryptoAES(machInst); 2128 } else if (bits(machInst, 20, 17) == 0x8) { 2129 return decodeNeonAcrossLanes(machInst); 2130 } else { 2131 return new Unknown64(machInst); 2132 } 2133 } else if (bits(machInst, 24) || 2134 bits(machInst, 21) || 2135 bits(machInst, 15)) { 2136 return new Unknown64(machInst); 2137 } else if (bits(machInst, 10) == 1) { 2138 if (bits(machInst, 23, 22)) 2139 return new Unknown64(machInst); 2140 return decodeNeonCopy(machInst); 2141 } else if (bits(machInst, 29) == 1) { 2142 return decodeNeonExt(machInst); 2143 } else if (bits(machInst, 11) == 1) { 2144 return decodeNeonZipUzpTrn(machInst); 2145 } else if (bits(machInst, 23, 22) == 0x0) { 2146 return decodeNeonTblTbx(machInst); 2147 } else { 2148 return new Unknown64(machInst); 2149 } 2150 return new FailUnimplemented("Unhandled Case3", machInst); 2151 } 2152} 2153}}; 2154 2155 2156output decoder {{ 2157namespace Aarch64 2158{ 2159 StaticInstPtr 2160 // bit 30=0, 28:25=1111 2161 decodeFp(ExtMachInst machInst) 2162 { 2163 if (bits(machInst, 24) == 1) { 2164 if (bits(machInst, 31) || bits(machInst, 29)) 2165 return new Unknown64(machInst); 2166 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2167 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2168 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2169 IntRegIndex ra = (IntRegIndex)(uint32_t)bits(machInst, 14, 10); 2170 uint8_t switchVal = (bits(machInst, 23, 21) << 1) | 2171 (bits(machInst, 15) << 0); 2172 switch (switchVal) { 2173 case 0x0: // FMADD Sd = Sa + Sn*Sm 2174 return new FMAddS(machInst, rd, rn, rm, ra); 2175 case 0x1: // FMSUB Sd = Sa + (-Sn)*Sm 2176 return new FMSubS(machInst, rd, rn, rm, ra); 2177 case 0x2: // FNMADD Sd = (-Sa) + (-Sn)*Sm 2178 return new FNMAddS(machInst, rd, rn, rm, ra); 2179 case 0x3: // FNMSUB Sd = (-Sa) + Sn*Sm 2180 return new FNMSubS(machInst, rd, rn, rm, ra); 2181 case 0x4: // FMADD Dd = Da + Dn*Dm 2182 return new FMAddD(machInst, rd, rn, rm, ra); 2183 case 0x5: // FMSUB Dd = Da + (-Dn)*Dm 2184 return new FMSubD(machInst, rd, rn, rm, ra); 2185 case 0x6: // FNMADD Dd = (-Da) + (-Dn)*Dm 2186 return new FNMAddD(machInst, rd, rn, rm, ra); 2187 case 0x7: // FNMSUB Dd = (-Da) + Dn*Dm 2188 return new FNMSubD(machInst, rd, rn, rm, ra); 2189 default: 2190 return new Unknown64(machInst); 2191 } 2192 } else if (bits(machInst, 21) == 0) { 2193 bool s = bits(machInst, 29); 2194 if (s) 2195 return new Unknown64(machInst); 2196 uint8_t switchVal = bits(machInst, 20, 16); 2197 uint8_t type = bits(machInst, 23, 22); 2198 uint8_t scale = bits(machInst, 15, 10); 2199 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2200 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2201 if (bits(machInst, 18, 17) == 3 && scale != 0) 2202 return new Unknown64(machInst); 2203 // 30:24=0011110, 21=0 2204 switch (switchVal) { 2205 case 0x00: 2206 return new FailUnimplemented("fcvtns", machInst); 2207 case 0x01: 2208 return new FailUnimplemented("fcvtnu", machInst); 2209 case 0x02: 2210 switch ( (bits(machInst, 31) << 2) | type ) { 2211 case 0: // SCVTF Sd = convertFromInt(Wn/(2^fbits)) 2212 return new FcvtSFixedFpSW(machInst, rd, rn, scale); 2213 case 1: // SCVTF Dd = convertFromInt(Wn/(2^fbits)) 2214 return new FcvtSFixedFpDW(machInst, rd, rn, scale); 2215 case 4: // SCVTF Sd = convertFromInt(Xn/(2^fbits)) 2216 return new FcvtSFixedFpSX(machInst, rd, rn, scale); 2217 case 5: // SCVTF Dd = convertFromInt(Xn/(2^fbits)) 2218 return new FcvtSFixedFpDX(machInst, rd, rn, scale); 2219 default: 2220 return new Unknown64(machInst); 2221 } 2222 case 0x03: 2223 switch ( (bits(machInst, 31) << 2) | type ) { 2224 case 0: // UCVTF Sd = convertFromInt(Wn/(2^fbits)) 2225 return new FcvtUFixedFpSW(machInst, rd, rn, scale); 2226 case 1: // UCVTF Dd = convertFromInt(Wn/(2^fbits)) 2227 return new FcvtUFixedFpDW(machInst, rd, rn, scale); 2228 case 4: // UCVTF Sd = convertFromInt(Xn/(2^fbits)) 2229 return new FcvtUFixedFpSX(machInst, rd, rn, scale); 2230 case 5: // UCVTF Dd = convertFromInt(Xn/(2^fbits)) 2231 return new FcvtUFixedFpDX(machInst, rd, rn, scale); 2232 default: 2233 return new Unknown64(machInst); 2234 } 2235 case 0x04: 2236 return new FailUnimplemented("fcvtas", machInst); 2237 case 0x05: 2238 return new FailUnimplemented("fcvtau", machInst); 2239 case 0x08: 2240 return new FailUnimplemented("fcvtps", machInst); 2241 case 0x09: 2242 return new FailUnimplemented("fcvtpu", machInst); 2243 case 0x0e: 2244 return new FailUnimplemented("fmov elem. to 64", machInst); 2245 case 0x0f: 2246 return new FailUnimplemented("fmov 64 bit", machInst); 2247 case 0x10: 2248 return new FailUnimplemented("fcvtms", machInst); 2249 case 0x11: 2250 return new FailUnimplemented("fcvtmu", machInst); 2251 case 0x18: 2252 switch ( (bits(machInst, 31) << 2) | type ) { 2253 case 0: // FCVTZS Wd = convertToIntExactTowardZero(Sn*(2^fbits)) 2254 return new FcvtFpSFixedSW(machInst, rd, rn, scale); 2255 case 1: // FCVTZS Wd = convertToIntExactTowardZero(Dn*(2^fbits)) 2256 return new FcvtFpSFixedDW(machInst, rd, rn, scale); 2257 case 4: // FCVTZS Xd = convertToIntExactTowardZero(Sn*(2^fbits)) 2258 return new FcvtFpSFixedSX(machInst, rd, rn, scale); 2259 case 5: // FCVTZS Xd = convertToIntExactTowardZero(Dn*(2^fbits)) 2260 return new FcvtFpSFixedDX(machInst, rd, rn, scale); 2261 default: 2262 return new Unknown64(machInst); 2263 } 2264 case 0x19: 2265 switch ( (bits(machInst, 31) << 2) | type ) { 2266 case 0: // FCVTZU Wd = convertToIntExactTowardZero(Sn*(2^fbits)) 2267 return new FcvtFpUFixedSW(machInst, rd, rn, scale); 2268 case 1: // FCVTZU Wd = convertToIntExactTowardZero(Dn*(2^fbits)) 2269 return new FcvtFpUFixedDW(machInst, rd, rn, scale); 2270 case 4: // FCVTZU Xd = convertToIntExactTowardZero(Sn*(2^fbits)) 2271 return new FcvtFpUFixedSX(machInst, rd, rn, scale); 2272 case 5: // FCVTZU Xd = convertToIntExactTowardZero(Dn*(2^fbits)) 2273 return new FcvtFpUFixedDX(machInst, rd, rn, scale); 2274 default: 2275 return new Unknown64(machInst); 2276 } 2277 default: 2278 return new Unknown64(machInst); 2279 } 2280 } else { 2281 // 30=0, 28:24=11110, 21=1 2282 uint8_t type = bits(machInst, 23, 22); 2283 uint8_t imm8 = bits(machInst, 20, 13); 2284 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2285 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2286 switch (bits(machInst, 11, 10)) { 2287 case 0x0: 2288 if (bits(machInst, 12) == 1) { 2289 if (bits(machInst, 31) || 2290 bits(machInst, 29) || 2291 bits(machInst, 9, 5)) { 2292 return new Unknown64(machInst); 2293 } 2294 // 31:29=000, 28:24=11110, 21=1, 12:10=100 2295 if (type == 0) { 2296 // FMOV S[d] = imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,5) 2297 // :imm8<5:0>:Zeros(19) 2298 uint32_t imm = vfp_modified_imm(imm8, 2299 FpDataType::Fp32); 2300 return new FmovImmS(machInst, rd, imm); 2301 } else if (type == 1) { 2302 // FMOV D[d] = imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,8) 2303 // :imm8<5:0>:Zeros(48) 2304 uint64_t imm = vfp_modified_imm(imm8, 2305 FpDataType::Fp64); 2306 return new FmovImmD(machInst, rd, imm); 2307 } else { 2308 return new Unknown64(machInst); 2309 } 2310 } else if (bits(machInst, 13) == 1) { 2311 if (bits(machInst, 31) || 2312 bits(machInst, 29) || 2313 bits(machInst, 15, 14) || 2314 bits(machInst, 23) || 2315 bits(machInst, 2, 0)) { 2316 return new Unknown64(machInst); 2317 } 2318 uint8_t switchVal = (bits(machInst, 4, 3) << 0) | 2319 (bits(machInst, 22) << 2); 2320 IntRegIndex rm = (IntRegIndex)(uint32_t) 2321 bits(machInst, 20, 16); 2322 // 28:23=000111100, 21=1, 15:10=001000, 2:0=000 2323 switch (switchVal) { 2324 case 0x0: 2325 // FCMP flags = compareQuiet(Sn,Sm) 2326 return new FCmpRegS(machInst, rn, rm); 2327 case 0x1: 2328 // FCMP flags = compareQuiet(Sn,0.0) 2329 return new FCmpImmS(machInst, rn, 0); 2330 case 0x2: 2331 // FCMPE flags = compareSignaling(Sn,Sm) 2332 return new FCmpERegS(machInst, rn, rm); 2333 case 0x3: 2334 // FCMPE flags = compareSignaling(Sn,0.0) 2335 return new FCmpEImmS(machInst, rn, 0); 2336 case 0x4: 2337 // FCMP flags = compareQuiet(Dn,Dm) 2338 return new FCmpRegD(machInst, rn, rm); 2339 case 0x5: 2340 // FCMP flags = compareQuiet(Dn,0.0) 2341 return new FCmpImmD(machInst, rn, 0); 2342 case 0x6: 2343 // FCMPE flags = compareSignaling(Dn,Dm) 2344 return new FCmpERegD(machInst, rn, rm); 2345 case 0x7: 2346 // FCMPE flags = compareSignaling(Dn,0.0) 2347 return new FCmpEImmD(machInst, rn, 0); 2348 default: 2349 return new Unknown64(machInst); 2350 } 2351 } else if (bits(machInst, 14) == 1) { 2352 if (bits(machInst, 31) || bits(machInst, 29)) 2353 return new Unknown64(machInst); 2354 uint8_t opcode = bits(machInst, 20, 15); 2355 // Bits 31:24=00011110, 21=1, 14:10=10000 2356 switch (opcode) { 2357 case 0x0: 2358 if (type == 0) 2359 // FMOV Sd = Sn 2360 return new FmovRegS(machInst, rd, rn); 2361 else if (type == 1) 2362 // FMOV Dd = Dn 2363 return new FmovRegD(machInst, rd, rn); 2364 break; 2365 case 0x1: 2366 if (type == 0) 2367 // FABS Sd = abs(Sn) 2368 return new FAbsS(machInst, rd, rn); 2369 else if (type == 1) 2370 // FABS Dd = abs(Dn) 2371 return new FAbsD(machInst, rd, rn); 2372 break; 2373 case 0x2: 2374 if (type == 0) 2375 // FNEG Sd = -Sn 2376 return new FNegS(machInst, rd, rn); 2377 else if (type == 1) 2378 // FNEG Dd = -Dn 2379 return new FNegD(machInst, rd, rn); 2380 break; 2381 case 0x3: 2382 if (type == 0) 2383 // FSQRT Sd = sqrt(Sn) 2384 return new FSqrtS(machInst, rd, rn); 2385 else if (type == 1) 2386 // FSQRT Dd = sqrt(Dn) 2387 return new FSqrtD(machInst, rd, rn); 2388 break; 2389 case 0x4: 2390 if (type == 1) 2391 // FCVT Sd = convertFormat(Dn) 2392 return new FcvtFpDFpS(machInst, rd, rn); 2393 else if (type == 3) 2394 // FCVT Sd = convertFormat(Hn) 2395 return new FcvtFpHFpS(machInst, rd, rn); 2396 break; 2397 case 0x5: 2398 if (type == 0) 2399 // FCVT Dd = convertFormat(Sn) 2400 return new FCvtFpSFpD(machInst, rd, rn); 2401 else if (type == 3) 2402 // FCVT Dd = convertFormat(Hn) 2403 return new FcvtFpHFpD(machInst, rd, rn); 2404 break; 2405 case 0x7: 2406 if (type == 0) 2407 // FCVT Hd = convertFormat(Sn) 2408 return new FcvtFpSFpH(machInst, rd, rn); 2409 else if (type == 1) 2410 // FCVT Hd = convertFormat(Dn) 2411 return new FcvtFpDFpH(machInst, rd, rn); 2412 break; 2413 case 0x8: 2414 if (type == 0) // FRINTN Sd = roundToIntegralTiesToEven(Sn) 2415 return new FRIntNS(machInst, rd, rn); 2416 else if (type == 1) // FRINTN Dd = roundToIntegralTiesToEven(Dn) 2417 return new FRIntND(machInst, rd, rn); 2418 break; 2419 case 0x9: 2420 if (type == 0) // FRINTP Sd = roundToIntegralTowardPlusInf(Sn) 2421 return new FRIntPS(machInst, rd, rn); 2422 else if (type == 1) // FRINTP Dd = roundToIntegralTowardPlusInf(Dn) 2423 return new FRIntPD(machInst, rd, rn); 2424 break; 2425 case 0xa: 2426 if (type == 0) // FRINTM Sd = roundToIntegralTowardMinusInf(Sn) 2427 return new FRIntMS(machInst, rd, rn); 2428 else if (type == 1) // FRINTM Dd = roundToIntegralTowardMinusInf(Dn) 2429 return new FRIntMD(machInst, rd, rn); 2430 break; 2431 case 0xb: 2432 if (type == 0) // FRINTZ Sd = roundToIntegralTowardZero(Sn) 2433 return new FRIntZS(machInst, rd, rn); 2434 else if (type == 1) // FRINTZ Dd = roundToIntegralTowardZero(Dn) 2435 return new FRIntZD(machInst, rd, rn); 2436 break; 2437 case 0xc: 2438 if (type == 0) // FRINTA Sd = roundToIntegralTiesToAway(Sn) 2439 return new FRIntAS(machInst, rd, rn); 2440 else if (type == 1) // FRINTA Dd = roundToIntegralTiesToAway(Dn) 2441 return new FRIntAD(machInst, rd, rn); 2442 break; 2443 case 0xe: 2444 if (type == 0) // FRINTX Sd = roundToIntegralExact(Sn) 2445 return new FRIntXS(machInst, rd, rn); 2446 else if (type == 1) // FRINTX Dd = roundToIntegralExact(Dn) 2447 return new FRIntXD(machInst, rd, rn); 2448 break; 2449 case 0xf: 2450 if (type == 0) // FRINTI Sd = roundToIntegral(Sn) 2451 return new FRIntIS(machInst, rd, rn); 2452 else if (type == 1) // FRINTI Dd = roundToIntegral(Dn) 2453 return new FRIntID(machInst, rd, rn); 2454 break; 2455 default: 2456 return new Unknown64(machInst); 2457 } 2458 return new Unknown64(machInst); 2459 } else if (bits(machInst, 15) == 1) { 2460 return new Unknown64(machInst); 2461 } else { 2462 if (bits(machInst, 29)) 2463 return new Unknown64(machInst); 2464 uint8_t rmode = bits(machInst, 20, 19); 2465 uint8_t switchVal1 = bits(machInst, 18, 16); 2466 uint8_t switchVal2 = (type << 1) | bits(machInst, 31); 2467 // 30:24=0011110, 21=1, 15:10=000000 2468 switch (switchVal1) { 2469 case 0x0: 2470 switch ((switchVal2 << 2) | rmode) { 2471 case 0x0: //FCVTNS Wd = convertToIntExactTiesToEven(Sn) 2472 return new FcvtFpSIntWSN(machInst, rd, rn); 2473 case 0x1: //FCVTPS Wd = convertToIntExactTowardPlusInf(Sn) 2474 return new FcvtFpSIntWSP(machInst, rd, rn); 2475 case 0x2: //FCVTMS Wd = convertToIntExactTowardMinusInf(Sn) 2476 return new FcvtFpSIntWSM(machInst, rd, rn); 2477 case 0x3: //FCVTZS Wd = convertToIntExactTowardZero(Sn) 2478 return new FcvtFpSIntWSZ(machInst, rd, rn); 2479 case 0x4: //FCVTNS Xd = convertToIntExactTiesToEven(Sn) 2480 return new FcvtFpSIntXSN(machInst, rd, rn); 2481 case 0x5: //FCVTPS Xd = convertToIntExactTowardPlusInf(Sn) 2482 return new FcvtFpSIntXSP(machInst, rd, rn); 2483 case 0x6: //FCVTMS Xd = convertToIntExactTowardMinusInf(Sn) 2484 return new FcvtFpSIntXSM(machInst, rd, rn); 2485 case 0x7: //FCVTZS Xd = convertToIntExactTowardZero(Sn) 2486 return new FcvtFpSIntXSZ(machInst, rd, rn); 2487 case 0x8: //FCVTNS Wd = convertToIntExactTiesToEven(Dn) 2488 return new FcvtFpSIntWDN(machInst, rd, rn); 2489 case 0x9: //FCVTPS Wd = convertToIntExactTowardPlusInf(Dn) 2490 return new FcvtFpSIntWDP(machInst, rd, rn); 2491 case 0xA: //FCVTMS Wd = convertToIntExactTowardMinusInf(Dn) 2492 return new FcvtFpSIntWDM(machInst, rd, rn); 2493 case 0xB: //FCVTZS Wd = convertToIntExactTowardZero(Dn) 2494 return new FcvtFpSIntWDZ(machInst, rd, rn); 2495 case 0xC: //FCVTNS Xd = convertToIntExactTiesToEven(Dn) 2496 return new FcvtFpSIntXDN(machInst, rd, rn); 2497 case 0xD: //FCVTPS Xd = convertToIntExactTowardPlusInf(Dn) 2498 return new FcvtFpSIntXDP(machInst, rd, rn); 2499 case 0xE: //FCVTMS Xd = convertToIntExactTowardMinusInf(Dn) 2500 return new FcvtFpSIntXDM(machInst, rd, rn); 2501 case 0xF: //FCVTZS Xd = convertToIntExactTowardZero(Dn) 2502 return new FcvtFpSIntXDZ(machInst, rd, rn); 2503 default: 2504 return new Unknown64(machInst); 2505 } 2506 case 0x1: 2507 switch ((switchVal2 << 2) | rmode) { 2508 case 0x0: //FCVTNU Wd = convertToIntExactTiesToEven(Sn) 2509 return new FcvtFpUIntWSN(machInst, rd, rn); 2510 case 0x1: //FCVTPU Wd = convertToIntExactTowardPlusInf(Sn) 2511 return new FcvtFpUIntWSP(machInst, rd, rn); 2512 case 0x2: //FCVTMU Wd = convertToIntExactTowardMinusInf(Sn) 2513 return new FcvtFpUIntWSM(machInst, rd, rn); 2514 case 0x3: //FCVTZU Wd = convertToIntExactTowardZero(Sn) 2515 return new FcvtFpUIntWSZ(machInst, rd, rn); 2516 case 0x4: //FCVTNU Xd = convertToIntExactTiesToEven(Sn) 2517 return new FcvtFpUIntXSN(machInst, rd, rn); 2518 case 0x5: //FCVTPU Xd = convertToIntExactTowardPlusInf(Sn) 2519 return new FcvtFpUIntXSP(machInst, rd, rn); 2520 case 0x6: //FCVTMU Xd = convertToIntExactTowardMinusInf(Sn) 2521 return new FcvtFpUIntXSM(machInst, rd, rn); 2522 case 0x7: //FCVTZU Xd = convertToIntExactTowardZero(Sn) 2523 return new FcvtFpUIntXSZ(machInst, rd, rn); 2524 case 0x8: //FCVTNU Wd = convertToIntExactTiesToEven(Dn) 2525 return new FcvtFpUIntWDN(machInst, rd, rn); 2526 case 0x9: //FCVTPU Wd = convertToIntExactTowardPlusInf(Dn) 2527 return new FcvtFpUIntWDP(machInst, rd, rn); 2528 case 0xA: //FCVTMU Wd = convertToIntExactTowardMinusInf(Dn) 2529 return new FcvtFpUIntWDM(machInst, rd, rn); 2530 case 0xB: //FCVTZU Wd = convertToIntExactTowardZero(Dn) 2531 return new FcvtFpUIntWDZ(machInst, rd, rn); 2532 case 0xC: //FCVTNU Xd = convertToIntExactTiesToEven(Dn) 2533 return new FcvtFpUIntXDN(machInst, rd, rn); 2534 case 0xD: //FCVTPU Xd = convertToIntExactTowardPlusInf(Dn) 2535 return new FcvtFpUIntXDP(machInst, rd, rn); 2536 case 0xE: //FCVTMU Xd = convertToIntExactTowardMinusInf(Dn) 2537 return new FcvtFpUIntXDM(machInst, rd, rn); 2538 case 0xF: //FCVTZU Xd = convertToIntExactTowardZero(Dn) 2539 return new FcvtFpUIntXDZ(machInst, rd, rn); 2540 default: 2541 return new Unknown64(machInst); 2542 } 2543 case 0x2: 2544 if (rmode != 0) 2545 return new Unknown64(machInst); 2546 switch (switchVal2) { 2547 case 0: // SCVTF Sd = convertFromInt(Wn) 2548 return new FcvtWSIntFpS(machInst, rd, rn); 2549 case 1: // SCVTF Sd = convertFromInt(Xn) 2550 return new FcvtXSIntFpS(machInst, rd, rn); 2551 case 2: // SCVTF Dd = convertFromInt(Wn) 2552 return new FcvtWSIntFpD(machInst, rd, rn); 2553 case 3: // SCVTF Dd = convertFromInt(Xn) 2554 return new FcvtXSIntFpD(machInst, rd, rn); 2555 default: 2556 return new Unknown64(machInst); 2557 } 2558 case 0x3: 2559 switch (switchVal2) { 2560 case 0: // UCVTF Sd = convertFromInt(Wn) 2561 return new FcvtWUIntFpS(machInst, rd, rn); 2562 case 1: // UCVTF Sd = convertFromInt(Xn) 2563 return new FcvtXUIntFpS(machInst, rd, rn); 2564 case 2: // UCVTF Dd = convertFromInt(Wn) 2565 return new FcvtWUIntFpD(machInst, rd, rn); 2566 case 3: // UCVTF Dd = convertFromInt(Xn) 2567 return new FcvtXUIntFpD(machInst, rd, rn); 2568 default: 2569 return new Unknown64(machInst); 2570 } 2571 case 0x4: 2572 if (rmode != 0) 2573 return new Unknown64(machInst); 2574 switch (switchVal2) { 2575 case 0: // FCVTAS Wd = convertToIntExactTiesToAway(Sn) 2576 return new FcvtFpSIntWSA(machInst, rd, rn); 2577 case 1: // FCVTAS Xd = convertToIntExactTiesToAway(Sn) 2578 return new FcvtFpSIntXSA(machInst, rd, rn); 2579 case 2: // FCVTAS Wd = convertToIntExactTiesToAway(Dn) 2580 return new FcvtFpSIntWDA(machInst, rd, rn); 2581 case 3: // FCVTAS Wd = convertToIntExactTiesToAway(Dn) 2582 return new FcvtFpSIntXDA(machInst, rd, rn); 2583 default: 2584 return new Unknown64(machInst); 2585 } 2586 case 0x5: 2587 switch (switchVal2) { 2588 case 0: // FCVTAU Wd = convertToIntExactTiesToAway(Sn) 2589 return new FcvtFpUIntWSA(machInst, rd, rn); 2590 case 1: // FCVTAU Xd = convertToIntExactTiesToAway(Sn) 2591 return new FcvtFpUIntXSA(machInst, rd, rn); 2592 case 2: // FCVTAU Wd = convertToIntExactTiesToAway(Dn) 2593 return new FcvtFpUIntWDA(machInst, rd, rn); 2594 case 3: // FCVTAU Xd = convertToIntExactTiesToAway(Dn) 2595 return new FcvtFpUIntXDA(machInst, rd, rn); 2596 default: 2597 return new Unknown64(machInst); 2598 } 2599 case 0x06: 2600 switch (switchVal2) { 2601 case 0: // FMOV Wd = Sn 2602 if (rmode != 0) 2603 return new Unknown64(machInst); 2604 return new FmovRegCoreW(machInst, rd, rn); 2605 case 3: // FMOV Xd = Dn 2606 if (rmode != 0) 2607 return new Unknown64(machInst); 2608 return new FmovRegCoreX(machInst, rd, rn); 2609 case 5: // FMOV Xd = Vn<127:64> 2610 if (rmode != 1) 2611 return new Unknown64(machInst); 2612 return new FmovURegCoreX(machInst, rd, rn); 2613 default: 2614 return new Unknown64(machInst); 2615 } 2616 break; 2617 case 0x07: 2618 switch (switchVal2) { 2619 case 0: // FMOV Sd = Wn 2620 if (rmode != 0) 2621 return new Unknown64(machInst); 2622 return new FmovCoreRegW(machInst, rd, rn); 2623 case 3: // FMOV Xd = Dn 2624 if (rmode != 0) 2625 return new Unknown64(machInst); 2626 return new FmovCoreRegX(machInst, rd, rn); 2627 case 5: // FMOV Xd = Vn<127:64> 2628 if (rmode != 1) 2629 return new Unknown64(machInst); 2630 return new FmovUCoreRegX(machInst, rd, rn); 2631 default: 2632 return new Unknown64(machInst); 2633 } 2634 break; 2635 default: // Warning! missing cases in switch statement above, that still need to be added 2636 return new Unknown64(machInst); 2637 } 2638 } 2639 M5_UNREACHABLE; 2640 case 0x1: 2641 { 2642 if (bits(machInst, 31) || 2643 bits(machInst, 29) || 2644 bits(machInst, 23)) { 2645 return new Unknown64(machInst); 2646 } 2647 IntRegIndex rm = (IntRegIndex)(uint32_t) bits(machInst, 20, 16); 2648 IntRegIndex rn = (IntRegIndex)(uint32_t) bits(machInst, 9, 5); 2649 uint8_t imm = (IntRegIndex)(uint32_t) bits(machInst, 3, 0); 2650 ConditionCode cond = 2651 (ConditionCode)(uint8_t)(bits(machInst, 15, 12)); 2652 uint8_t switchVal = (bits(machInst, 4) << 0) | 2653 (bits(machInst, 22) << 1); 2654 // 31:23=000111100, 21=1, 11:10=01 2655 switch (switchVal) { 2656 case 0x0: 2657 // FCCMP flags = if cond the compareQuiet(Sn,Sm) else #nzcv 2658 return new FCCmpRegS(machInst, rn, rm, cond, imm); 2659 case 0x1: 2660 // FCCMP flags = if cond then compareSignaling(Sn,Sm) 2661 // else #nzcv 2662 return new FCCmpERegS(machInst, rn, rm, cond, imm); 2663 case 0x2: 2664 // FCCMP flags = if cond then compareQuiet(Dn,Dm) else #nzcv 2665 return new FCCmpRegD(machInst, rn, rm, cond, imm); 2666 case 0x3: 2667 // FCCMP flags = if cond then compareSignaling(Dn,Dm) 2668 // else #nzcv 2669 return new FCCmpERegD(machInst, rn, rm, cond, imm); 2670 default: 2671 return new Unknown64(machInst); 2672 } 2673 } 2674 case 0x2: 2675 { 2676 if (bits(machInst, 31) || 2677 bits(machInst, 29) || 2678 bits(machInst, 23)) { 2679 return new Unknown64(machInst); 2680 } 2681 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2682 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2683 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2684 uint8_t switchVal = (bits(machInst, 15, 12) << 0) | 2685 (bits(machInst, 22) << 4); 2686 switch (switchVal) { 2687 case 0x00: // FMUL Sd = Sn * Sm 2688 return new FMulS(machInst, rd, rn, rm); 2689 case 0x10: // FMUL Dd = Dn * Dm 2690 return new FMulD(machInst, rd, rn, rm); 2691 case 0x01: // FDIV Sd = Sn / Sm 2692 return new FDivS(machInst, rd, rn, rm); 2693 case 0x11: // FDIV Dd = Dn / Dm 2694 return new FDivD(machInst, rd, rn, rm); 2695 case 0x02: // FADD Sd = Sn + Sm 2696 return new FAddS(machInst, rd, rn, rm); 2697 case 0x12: // FADD Dd = Dn + Dm 2698 return new FAddD(machInst, rd, rn, rm); 2699 case 0x03: // FSUB Sd = Sn - Sm 2700 return new FSubS(machInst, rd, rn, rm); 2701 case 0x13: // FSUB Dd = Dn - Dm 2702 return new FSubD(machInst, rd, rn, rm); 2703 case 0x04: // FMAX Sd = max(Sn, Sm) 2704 return new FMaxS(machInst, rd, rn, rm); 2705 case 0x14: // FMAX Dd = max(Dn, Dm) 2706 return new FMaxD(machInst, rd, rn, rm); 2707 case 0x05: // FMIN Sd = min(Sn, Sm) 2708 return new FMinS(machInst, rd, rn, rm); 2709 case 0x15: // FMIN Dd = min(Dn, Dm) 2710 return new FMinD(machInst, rd, rn, rm); 2711 case 0x06: // FMAXNM Sd = maxNum(Sn, Sm) 2712 return new FMaxNMS(machInst, rd, rn, rm); 2713 case 0x16: // FMAXNM Dd = maxNum(Dn, Dm) 2714 return new FMaxNMD(machInst, rd, rn, rm); 2715 case 0x07: // FMINNM Sd = minNum(Sn, Sm) 2716 return new FMinNMS(machInst, rd, rn, rm); 2717 case 0x17: // FMINNM Dd = minNum(Dn, Dm) 2718 return new FMinNMD(machInst, rd, rn, rm); 2719 case 0x08: // FNMUL Sd = -(Sn * Sm) 2720 return new FNMulS(machInst, rd, rn, rm); 2721 case 0x18: // FNMUL Dd = -(Dn * Dm) 2722 return new FNMulD(machInst, rd, rn, rm); 2723 default: 2724 return new Unknown64(machInst); 2725 } 2726 } 2727 case 0x3: 2728 { 2729 if (bits(machInst, 31) || bits(machInst, 29)) 2730 return new Unknown64(machInst); 2731 uint8_t type = bits(machInst, 23, 22); 2732 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2733 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2734 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2735 ConditionCode cond = 2736 (ConditionCode)(uint8_t)(bits(machInst, 15, 12)); 2737 if (type == 0) // FCSEL Sd = if cond then Sn else Sm 2738 return new FCSelS(machInst, rd, rn, rm, cond); 2739 else if (type == 1) // FCSEL Dd = if cond then Dn else Dm 2740 return new FCSelD(machInst, rd, rn, rm, cond); 2741 else 2742 return new Unknown64(machInst); 2743 } 2744 default: 2745 M5_UNREACHABLE; 2746 } 2747 } 2748 M5_UNREACHABLE; 2749 } 2750} 2751}}; 2752 2753output decoder {{ 2754namespace Aarch64 2755{ 2756 StaticInstPtr 2757 decodeAdvSIMDScalar(ExtMachInst machInst) 2758 { 2759 if (bits(machInst, 24) == 1) { 2760 if (bits(machInst, 10) == 0) { 2761 return decodeNeonScIndexedElem(machInst); 2762 } else if (bits(machInst, 23) == 0) { 2763 return decodeNeonScShiftByImm(machInst); 2764 } 2765 } else if (bits(machInst, 21) == 1) { 2766 if (bits(machInst, 10) == 1) { 2767 return decodeNeonSc3Same(machInst); 2768 } else if (bits(machInst, 11) == 0) { 2769 return decodeNeonSc3Diff(machInst); 2770 } else if (bits(machInst, 20, 17) == 0x0) { 2771 return decodeNeonSc2RegMisc(machInst); 2772 } else if (bits(machInst, 20, 17) == 0x4) { 2773 return decodeCryptoTwoRegSHA(machInst); 2774 } else if (bits(machInst, 20, 17) == 0x8) { 2775 return decodeNeonScPwise(machInst); 2776 } else { 2777 return new Unknown64(machInst); 2778 } 2779 } else if (bits(machInst, 23, 22) == 0 && 2780 bits(machInst, 15) == 0) { 2781 if (bits(machInst, 10) == 1) { 2782 return decodeNeonScCopy(machInst); 2783 } else { 2784 return decodeCryptoThreeRegSHA(machInst); 2785 } 2786 } else { 2787 return new Unknown64(machInst); 2788 } 2789 return new FailUnimplemented("Unhandled Case6", machInst); 2790 } 2791} 2792}}; 2793 2794output decoder {{ 2795namespace Aarch64 2796{ 2797 template <typename DecoderFeatures> 2798 StaticInstPtr 2799 decodeFpAdvSIMD(ExtMachInst machInst) 2800 { 2801 2802 if (bits(machInst, 28) == 0) { 2803 if (bits(machInst, 31) == 0) { 2804 return decodeAdvSIMD<DecoderFeatures>(machInst); 2805 } else { 2806 return new Unknown64(machInst); 2807 } 2808 } else if (bits(machInst, 30) == 0) { 2809 return decodeFp(machInst); 2810 } else if (bits(machInst, 31) == 0) { 2811 return decodeAdvSIMDScalar(machInst); 2812 } else { 2813 return new Unknown64(machInst); 2814 } 2815 } 2816} 2817}}; 2818 2819let {{ 2820 decoder_output =''' 2821namespace Aarch64 2822{''' 2823 for decoderFlavour, type_dict in decoders.iteritems(): 2824 decoder_output +=''' 2825template StaticInstPtr decodeFpAdvSIMD<%(df)sDecoder>(ExtMachInst machInst); 2826''' % { "df" : decoderFlavour } 2827 decoder_output +=''' 2828}''' 2829}}; 2830 2831output decoder {{ 2832namespace Aarch64 2833{ 2834 StaticInstPtr 2835 decodeGem5Ops(ExtMachInst machInst) 2836 { 2837 const uint32_t m5func = bits(machInst, 23, 16); 2838 switch (m5func) { 2839 case M5OP_ARM: return new Arm(machInst); 2840 case M5OP_QUIESCE: return new Quiesce(machInst); 2841 case M5OP_QUIESCE_NS: return new QuiesceNs64(machInst); 2842 case M5OP_QUIESCE_CYCLE: return new QuiesceCycles64(machInst); 2843 case M5OP_QUIESCE_TIME: return new QuiesceTime64(machInst); 2844 case M5OP_RPNS: return new Rpns64(machInst); 2845 case M5OP_WAKE_CPU: return new WakeCPU64(machInst); 2846 case M5OP_DEPRECATED1: return new Deprecated_ivlb(machInst); 2847 case M5OP_DEPRECATED2: return new Deprecated_ivle(machInst); 2848 case M5OP_DEPRECATED3: return new Deprecated_exit (machInst); 2849 case M5OP_EXIT: return new M5exit64(machInst); 2850 case M5OP_FAIL: return new M5fail64(machInst); 2851 case M5OP_LOAD_SYMBOL: return new Loadsymbol(machInst); 2852 case M5OP_INIT_PARAM: return new Initparam64(machInst); 2853 case M5OP_RESET_STATS: return new Resetstats64(machInst); 2854 case M5OP_DUMP_STATS: return new Dumpstats64(machInst); 2855 case M5OP_DUMP_RESET_STATS: return new Dumpresetstats64(machInst); 2856 case M5OP_CHECKPOINT: return new M5checkpoint64(machInst); 2857 case M5OP_WRITE_FILE: return new M5writefile64(machInst); 2858 case M5OP_READ_FILE: return new M5readfile64(machInst); 2859 case M5OP_DEBUG_BREAK: return new M5break(machInst); 2860 case M5OP_SWITCH_CPU: return new M5switchcpu(machInst); 2861 case M5OP_ADD_SYMBOL: return new M5addsymbol64(machInst); 2862 case M5OP_PANIC: return new M5panic(machInst); 2863 case M5OP_WORK_BEGIN: return new M5workbegin64(machInst); 2864 case M5OP_WORK_END: return new M5workend64(machInst); 2865 default: return new Unknown64(machInst); 2866 } 2867 } 2868} 2869}}; 2870 2871def format Aarch64() {{ 2872 decode_block = ''' 2873 { 2874 using namespace Aarch64; 2875 if (bits(machInst, 27) == 0x0) { 2876 if (bits(machInst, 28) == 0x0) { 2877 if (bits(machInst, 26, 25) != 0x2) { 2878 return new Unknown64(machInst); 2879 } 2880 if (bits(machInst, 31) == 0x0) { 2881 switch (bits(machInst, 30, 29)) { 2882 case 0x0: 2883 case 0x1: 2884 case 0x2: 2885 return decodeSveInt(machInst); 2886 case 0x3: 2887 return decodeSveFp(machInst); 2888 } 2889 } else { 2890 return decodeSveMem(machInst); 2891 } 2892 } else if (bits(machInst, 26) == 0) 2893 // bit 28:26=100 2894 return decodeDataProcImm(machInst); 2895 else 2896 // bit 28:26=101 2897 return decodeBranchExcSys(machInst); 2898 } else if (bits(machInst, 25) == 0) { 2899 // bit 27=1, 25=0 2900 return decodeLoadsStores(machInst); 2901 } else if (bits(machInst, 26) == 0) { 2902 // bit 27:25=101 2903 return decodeDataProcReg(machInst); 2904 } else if (bits(machInst, 24) == 1 && 2905 bits(machInst, 31, 28) == 0xF) { 2906 return decodeGem5Ops(machInst); 2907 } else { 2908 // bit 27:25=111 2909 switch(decoderFlavour){ 2910 default: 2911 return decodeFpAdvSIMD<GenericDecoder>(machInst); 2912 } 2913 } 2914 } 2915 ''' 2916}}; 2917