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 default: 656 M5_UNREACHABLE; 657 } 658 case 0x1: 659 switch(size_ar){ 660 case 0x0: 661 if (A_rt == 0x1f) 662 return new STCLRB(machInst, rt, rnsp, rs); 663 else 664 return new LDCLRB(machInst, rt, rnsp, rs); 665 case 0x1 : 666 if (A_rt == 0x1f) 667 return new STCLRLB(machInst, rt, rnsp, rs); 668 else 669 return new LDCLRLB(machInst, rt, rnsp, rs); 670 case 0x2: 671 return new LDCLRAB(machInst, rt, rnsp, rs); 672 case 0x3: 673 return new LDCLRLAB(machInst, rt, rnsp, rs); 674 case 0x4: 675 if (A_rt == 0x1f) 676 return new STCLRH(machInst, rt, rnsp, rs); 677 else 678 return new LDCLRH(machInst, rt, rnsp, rs); 679 case 0x5 : 680 if (A_rt == 0x1f) 681 return new STCLRLH(machInst, rt, rnsp, rs); 682 else 683 return new LDCLRLH(machInst, rt, rnsp, rs); 684 case 0x6: 685 return new LDCLRAH(machInst, rt, rnsp, rs); 686 case 0x7: 687 return new LDCLRLAH(machInst, rt, rnsp, rs); 688 case 0x8: 689 if (A_rt == 0x1f) 690 return new STCLR(machInst, rt, rnsp, rs); 691 else 692 return new LDCLR(machInst, rt, rnsp, rs); 693 case 0x9 : 694 if (A_rt == 0x1f) 695 return new STCLRL(machInst, rt, rnsp, rs); 696 else 697 return new LDCLRL(machInst, rt, rnsp, rs); 698 case 0xa: 699 return new LDCLRA(machInst, rt, rnsp, rs); 700 case 0xb: 701 return new LDCLRLA(machInst, rt, rnsp, rs); 702 case 0xc: 703 if (A_rt == 0x1f) 704 return new STCLR64(machInst, rt, rnsp, rs); 705 else 706 return new LDCLR64(machInst, rt, rnsp, rs); 707 case 0xd : 708 if (A_rt == 0x1f) 709 return new STCLRL64(machInst, rt, rnsp, rs); 710 else 711 return new LDCLRL64(machInst, rt, rnsp, rs); 712 case 0xe: 713 return new LDCLRA64(machInst, rt, rnsp, rs); 714 case 0xf: 715 return new LDCLRLA64(machInst, rt, rnsp, rs); 716 default: 717 M5_UNREACHABLE; 718 } 719 case 0x2: 720 switch(size_ar){ 721 case 0x0: 722 if (A_rt == 0x1f) 723 return new STEORB(machInst, rt, rnsp, rs); 724 else 725 return new LDEORB(machInst, rt, rnsp, rs); 726 case 0x1 : 727 if (A_rt == 0x1f) 728 return new STEORLB(machInst, rt, rnsp, rs); 729 else 730 return new LDEORLB(machInst, rt, rnsp, rs); 731 case 0x2: 732 return new LDEORAB(machInst, rt, rnsp, rs); 733 case 0x3: 734 return new LDEORLAB(machInst, rt, rnsp, rs); 735 case 0x4: 736 if (A_rt == 0x1f) 737 return new STEORH(machInst, rt, rnsp, rs); 738 else 739 return new LDEORH(machInst, rt, rnsp, rs); 740 case 0x5 : 741 if (A_rt == 0x1f) 742 return new STEORLH(machInst, rt, rnsp, rs); 743 else 744 return new LDEORLH(machInst, rt, rnsp, rs); 745 case 0x6: 746 return new LDEORAH(machInst, rt, rnsp, rs); 747 case 0x7: 748 return new LDEORLAH(machInst, rt, rnsp, rs); 749 case 0x8: 750 if (A_rt == 0x1f) 751 return new STEOR(machInst, rt, rnsp, rs); 752 else 753 return new LDEOR(machInst, rt, rnsp, rs); 754 case 0x9 : 755 if (A_rt == 0x1f) 756 return new STEORL(machInst, rt, rnsp, rs); 757 else 758 return new LDEORL(machInst, rt, rnsp, rs); 759 case 0xa: 760 return new LDEORA(machInst, rt, rnsp, rs); 761 case 0xb: 762 return new LDEORLA(machInst, rt, rnsp, rs); 763 case 0xc: 764 if (A_rt == 0x1f) 765 return new STEOR64(machInst, rt, rnsp, rs); 766 else 767 return new LDEOR64(machInst, rt, rnsp, rs); 768 case 0xd : 769 if (A_rt == 0x1f) 770 return new STEORL64(machInst, rt, rnsp, rs); 771 else 772 return new LDEORL64(machInst, rt, rnsp, rs); 773 case 0xe: 774 return new LDEORA64(machInst, rt, rnsp, rs); 775 case 0xf: 776 return new LDEORLA64(machInst, rt, rnsp, rs); 777 default: 778 M5_UNREACHABLE; 779 } 780 case 0x3: 781 switch(size_ar){ 782 case 0x0: 783 if (A_rt == 0x1f) 784 return new STSETB(machInst, rt, rnsp, rs); 785 else 786 return new LDSETB(machInst, rt, rnsp, rs); 787 case 0x1 : 788 if (A_rt == 0x1f) 789 return new STSETLB(machInst, rt, rnsp, rs); 790 else 791 return new LDSETLB(machInst, rt, rnsp, rs); 792 case 0x2: 793 return new LDSETAB(machInst, rt, rnsp, rs); 794 case 0x3: 795 return new LDSETLAB(machInst, rt, rnsp, rs); 796 case 0x4: 797 if (A_rt == 0x1f) 798 return new STSETH(machInst, rt, rnsp, rs); 799 else 800 return new LDSETH(machInst, rt, rnsp, rs); 801 case 0x5 : 802 if (A_rt == 0x1f) 803 return new STSETLH(machInst, rt, rnsp, rs); 804 else 805 return new LDSETLH(machInst, rt, rnsp, rs); 806 case 0x6: 807 return new LDSETAH(machInst, rt, rnsp, rs); 808 case 0x7: 809 return new LDSETLAH(machInst, rt, rnsp, rs); 810 case 0x8: 811 if (A_rt == 0x1f) 812 return new STSET(machInst, rt, rnsp, rs); 813 else 814 return new LDSET(machInst, rt, rnsp, rs); 815 case 0x9 : 816 if (A_rt == 0x1f) 817 return new STSETL(machInst, rt, rnsp, rs); 818 else 819 return new LDSETL(machInst, rt, rnsp, rs); 820 case 0xa: 821 return new LDSETA(machInst, rt, rnsp, rs); 822 case 0xb: 823 return new LDSETLA(machInst, rt, rnsp, rs); 824 case 0xc: 825 if (A_rt == 0x1f) 826 return new STSET64(machInst, rt, rnsp, rs); 827 else 828 return new LDSET64(machInst, rt, rnsp, rs); 829 case 0xd : 830 if (A_rt == 0x1f) 831 return new STSETL64(machInst, rt, rnsp, rs); 832 else 833 return new LDSETL64(machInst, rt, rnsp, rs); 834 case 0xe: 835 return new LDSETA64(machInst, rt, rnsp, rs); 836 case 0xf: 837 return new LDSETLA64(machInst, rt, rnsp, rs); 838 default: 839 M5_UNREACHABLE; 840 } 841 case 0x4: 842 switch(size_ar){ 843 case 0x0: 844 if (A_rt == 0x1f) 845 return new STSMAXB(machInst, rt, rnsp, rs); 846 else 847 return new LDSMAXB(machInst, rt, rnsp, rs); 848 case 0x1 : 849 if (A_rt == 0x1f) 850 return new STSMAXLB(machInst, rt, rnsp, rs); 851 else 852 return new LDSMAXLB(machInst, rt, rnsp, rs); 853 case 0x2: 854 return new LDSMAXAB(machInst, rt, rnsp, rs); 855 case 0x3: 856 return new LDSMAXLAB(machInst, rt, rnsp, rs); 857 case 0x4: 858 if (A_rt == 0x1f) 859 return new STSMAXH(machInst, rt, rnsp, rs); 860 else 861 return new LDSMAXH(machInst, rt, rnsp, rs); 862 case 0x5 : 863 if (A_rt == 0x1f) 864 return new STSMAXLH(machInst, rt, rnsp, rs); 865 else 866 return new LDSMAXLH(machInst, rt, rnsp, rs); 867 case 0x6: 868 return new LDSMAXAH(machInst, rt, rnsp, rs); 869 case 0x7: 870 return new LDSMAXLAH(machInst, rt, rnsp, rs); 871 case 0x8: 872 if (A_rt == 0x1f) 873 return new STSMAX(machInst, rt, rnsp, rs); 874 else 875 return new LDSMAX(machInst, rt, rnsp, rs); 876 case 0x9 : 877 if (A_rt == 0x1f) 878 return new STSMAXL(machInst, rt, rnsp, rs); 879 else 880 return new LDSMAXL(machInst, rt, rnsp, rs); 881 case 0xa: 882 return new LDSMAXA(machInst, rt, rnsp, rs); 883 case 0xb: 884 return new LDSMAXLA(machInst, rt, rnsp, rs); 885 case 0xc: 886 if (A_rt == 0x1f) 887 return new STSMAX64(machInst, rt, rnsp, rs); 888 else 889 return new LDSMAX64(machInst, rt, rnsp, rs); 890 case 0xd : 891 if (A_rt == 0x1f) 892 return new STSMAXL64(machInst, rt, rnsp, rs); 893 else 894 return new LDSMAXL64(machInst, rt, rnsp, rs); 895 case 0xe: 896 return new LDSMAXA64(machInst, rt, rnsp, rs); 897 case 0xf: 898 return new LDSMAXLA64(machInst, rt, rnsp, rs); 899 default: 900 M5_UNREACHABLE; 901 } 902 case 0x5: 903 switch(size_ar){ 904 case 0x0: 905 if (A_rt == 0x1f) 906 return new STSMINB(machInst, rt, rnsp, rs); 907 else 908 return new LDSMINB(machInst, rt, rnsp, rs); 909 case 0x1 : 910 if (A_rt == 0x1f) 911 return new STSMINLB(machInst, rt, rnsp, rs); 912 else 913 return new LDSMINLB(machInst, rt, rnsp, rs); 914 case 0x2: 915 return new LDSMINAB(machInst, rt, rnsp, rs); 916 case 0x3: 917 return new LDSMINLAB(machInst, rt, rnsp, rs); 918 case 0x4: 919 if (A_rt == 0x1f) 920 return new STSMINH(machInst, rt, rnsp, rs); 921 else 922 return new LDSMINH(machInst, rt, rnsp, rs); 923 case 0x5 : 924 if (A_rt == 0x1f) 925 return new STSMINLH(machInst, rt, rnsp, rs); 926 else 927 return new LDSMINLH(machInst, rt, rnsp, rs); 928 case 0x6: 929 return new LDSMINAH(machInst, rt, rnsp, rs); 930 case 0x7: 931 return new LDSMINLAH(machInst, rt, rnsp, rs); 932 case 0x8: 933 if (A_rt == 0x1f) 934 return new STSMIN(machInst, rt, rnsp, rs); 935 else 936 return new LDSMIN(machInst, rt, rnsp, rs); 937 case 0x9 : 938 if (A_rt == 0x1f) 939 return new STSMINL(machInst, rt, rnsp, rs); 940 else 941 return new LDSMINL(machInst, rt, rnsp, rs); 942 case 0xa: 943 return new LDSMINA(machInst, rt, rnsp, rs); 944 case 0xb: 945 return new LDSMINLA(machInst, rt, rnsp, rs); 946 case 0xc: 947 if (A_rt == 0x1f) 948 return new STSMIN64(machInst, rt, rnsp, rs); 949 else 950 return new LDSMIN64(machInst, rt, rnsp, rs); 951 case 0xd : 952 if (A_rt == 0x1f) 953 return new STSMINL64(machInst, rt, rnsp, rs); 954 else 955 return new LDSMINL64(machInst, rt, rnsp, rs); 956 case 0xe: 957 return new LDSMINA64(machInst, rt, rnsp, rs); 958 case 0xf: 959 return new LDSMINLA64(machInst, rt, rnsp, rs); 960 default: 961 M5_UNREACHABLE; 962 } 963 case 0x6: 964 switch(size_ar){ 965 case 0x0: 966 if (A_rt == 0x1f) 967 return new STUMAXB(machInst, rt, rnsp, rs); 968 else 969 return new LDUMAXB(machInst, rt, rnsp, rs); 970 case 0x1 : 971 if (A_rt == 0x1f) 972 return new STUMAXLB(machInst, rt, rnsp, rs); 973 else 974 return new LDUMAXLB(machInst, rt, rnsp, rs); 975 case 0x2: 976 return new LDUMAXAB(machInst, rt, rnsp, rs); 977 case 0x3: 978 return new LDUMAXLAB(machInst, rt, rnsp, rs); 979 case 0x4: 980 if (A_rt == 0x1f) 981 return new STUMAXH(machInst, rt, rnsp, rs); 982 else 983 return new LDUMAXH(machInst, rt, rnsp, rs); 984 case 0x5 : 985 if (A_rt == 0x1f) 986 return new STUMAXLH(machInst, rt, rnsp, rs); 987 else 988 return new LDUMAXLH(machInst, rt, rnsp, rs); 989 case 0x6: 990 return new LDUMAXAH(machInst, rt, rnsp, rs); 991 case 0x7: 992 return new LDUMAXLAH(machInst, rt, rnsp, rs); 993 case 0x8: 994 if (A_rt == 0x1f) 995 return new STUMAX(machInst, rt, rnsp, rs); 996 else 997 return new LDUMAX(machInst, rt, rnsp, rs); 998 case 0x9 : 999 if (A_rt == 0x1f) 1000 return new STUMAXL(machInst, rt, rnsp, rs); 1001 else 1002 return new LDUMAXL(machInst, rt, rnsp, rs); 1003 case 0xa: 1004 return new LDUMAXA(machInst, rt, rnsp, rs); 1005 case 0xb: 1006 return new LDUMAXLA(machInst, rt, rnsp, rs); 1007 case 0xc: 1008 if (A_rt == 0x1f) 1009 return new STUMAX64(machInst, rt, rnsp, rs); 1010 else 1011 return new LDUMAX64(machInst, rt, rnsp, rs); 1012 case 0xd : 1013 if (A_rt == 0x1f) 1014 return new STUMAXL64(machInst, rt, rnsp, rs); 1015 else 1016 return new LDUMAXL64(machInst, rt, rnsp, rs); 1017 case 0xe: 1018 return new LDUMAXA64(machInst, rt, rnsp, rs); 1019 case 0xf: 1020 return new LDUMAXLA64(machInst, rt, rnsp, rs); 1021 default: 1022 M5_UNREACHABLE; 1023 } 1024 case 0x7: 1025 switch(size_ar){ 1026 case 0x0: 1027 if (A_rt == 0x1f) 1028 return new STUMINB(machInst, rt, rnsp, rs); 1029 else 1030 return new LDUMINB(machInst, rt, rnsp, rs); 1031 case 0x1 : 1032 if (A_rt == 0x1f) 1033 return new STUMINLB(machInst, rt, rnsp, rs); 1034 else 1035 return new LDUMINLB(machInst, rt, rnsp, rs); 1036 case 0x2: 1037 return new LDUMINAB(machInst, rt, rnsp, rs); 1038 case 0x3: 1039 return new LDUMINLAB(machInst, rt, rnsp, rs); 1040 case 0x4: 1041 if (A_rt == 0x1f) 1042 return new STUMINH(machInst, rt, rnsp, rs); 1043 else 1044 return new LDUMINH(machInst, rt, rnsp, rs); 1045 case 0x5 : 1046 if (A_rt == 0x1f) 1047 return new STUMINLH(machInst, rt, rnsp, rs); 1048 else 1049 return new LDUMINLH(machInst, rt, rnsp, rs); 1050 case 0x6: 1051 return new LDUMINAH(machInst, rt, rnsp, rs); 1052 case 0x7: 1053 return new LDUMINLAH(machInst, rt, rnsp, rs); 1054 case 0x8: 1055 if (A_rt == 0x1f) 1056 return new STUMIN(machInst, rt, rnsp, rs); 1057 else 1058 return new LDUMIN(machInst, rt, rnsp, rs); 1059 case 0x9 : 1060 if (A_rt == 0x1f) 1061 return new STUMINL(machInst, rt, rnsp, rs); 1062 else 1063 return new LDUMINL(machInst, rt, rnsp, rs); 1064 case 0xa: 1065 return new LDUMINA(machInst, rt, rnsp, rs); 1066 case 0xb: 1067 return new LDUMINLA(machInst, rt, rnsp, rs); 1068 case 0xc: 1069 if (A_rt == 0x1f) 1070 return new STUMIN64(machInst, rt, rnsp, rs); 1071 else 1072 return new LDUMIN64(machInst, rt, rnsp, rs); 1073 case 0xd : 1074 if (A_rt == 0x1f) 1075 return new STUMINL64(machInst, rt, rnsp, rs); 1076 else 1077 return new LDUMINL64(machInst, rt, rnsp, rs); 1078 case 0xe: 1079 return new LDUMINA64(machInst, rt, rnsp, rs); 1080 case 0xf: 1081 return new LDUMINLA64(machInst, rt, rnsp, rs); 1082 default: 1083 M5_UNREACHABLE; 1084 } 1085 default: 1086 return new Unknown64(machInst); 1087 } 1088 } 1089} 1090}}; 1091 1092 1093output decoder {{ 1094namespace Aarch64 1095{ 1096 1097 StaticInstPtr 1098 decodeLoadsStores(ExtMachInst machInst) 1099 { 1100 // bit 27,25=10 1101 switch (bits(machInst, 29, 28)) { 1102 case 0x0: 1103 if (bits(machInst, 26) == 0) { 1104 if (bits(machInst, 24) != 0) 1105 return new Unknown64(machInst); 1106 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1107 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1108 IntRegIndex rnsp = makeSP(rn); 1109 IntRegIndex rt2 = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 1110 IntRegIndex rs = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1111 uint8_t opc = (bits(machInst, 15) << 0) | 1112 (bits(machInst, 23, 21) << 1); 1113 uint8_t size = bits(machInst, 31, 30); 1114 switch (opc) { 1115 case 0x0: 1116 switch (size) { 1117 case 0x0: 1118 return new STXRB64(machInst, rt, rnsp, rs); 1119 case 0x1: 1120 return new STXRH64(machInst, rt, rnsp, rs); 1121 case 0x2: 1122 return new STXRW64(machInst, rt, rnsp, rs); 1123 case 0x3: 1124 return new STXRX64(machInst, rt, rnsp, rs); 1125 default: 1126 M5_UNREACHABLE; 1127 } 1128 case 0x1: 1129 switch (size) { 1130 case 0x0: 1131 return new STLXRB64(machInst, rt, rnsp, rs); 1132 case 0x1: 1133 return new STLXRH64(machInst, rt, rnsp, rs); 1134 case 0x2: 1135 return new STLXRW64(machInst, rt, rnsp, rs); 1136 case 0x3: 1137 return new STLXRX64(machInst, rt, rnsp, rs); 1138 default: 1139 M5_UNREACHABLE; 1140 } 1141 case 0x2: 1142 switch (size) { 1143 case 0x0: 1144 return new CASP32(machInst, rt, rnsp, rs); 1145 case 0x1: 1146 return new CASP64(machInst, rt, rnsp, rs); 1147 case 0x2: 1148 return new STXPW64(machInst, rs, rt, rt2, rnsp); 1149 case 0x3: 1150 return new STXPX64(machInst, rs, rt, rt2, rnsp); 1151 default: 1152 M5_UNREACHABLE; 1153 } 1154 1155 case 0x3: 1156 switch (size) { 1157 case 0x0: 1158 return new CASPL32(machInst, rt, rnsp, rs); 1159 case 0x1: 1160 return new CASPL64(machInst, rt, rnsp, rs); 1161 case 0x2: 1162 return new STLXPW64(machInst, rs, rt, rt2, rnsp); 1163 case 0x3: 1164 return new STLXPX64(machInst, rs, rt, rt2, rnsp); 1165 default: 1166 M5_UNREACHABLE; 1167 } 1168 1169 case 0x4: 1170 switch (size) { 1171 case 0x0: 1172 return new LDXRB64(machInst, rt, rnsp, rs); 1173 case 0x1: 1174 return new LDXRH64(machInst, rt, rnsp, rs); 1175 case 0x2: 1176 return new LDXRW64(machInst, rt, rnsp, rs); 1177 case 0x3: 1178 return new LDXRX64(machInst, rt, rnsp, rs); 1179 default: 1180 M5_UNREACHABLE; 1181 } 1182 case 0x5: 1183 switch (size) { 1184 case 0x0: 1185 return new LDAXRB64(machInst, rt, rnsp, rs); 1186 case 0x1: 1187 return new LDAXRH64(machInst, rt, rnsp, rs); 1188 case 0x2: 1189 return new LDAXRW64(machInst, rt, rnsp, rs); 1190 case 0x3: 1191 return new LDAXRX64(machInst, rt, rnsp, rs); 1192 default: 1193 M5_UNREACHABLE; 1194 } 1195 case 0x6: 1196 switch (size) { 1197 case 0x0: 1198 return new CASPA32(machInst, rt, rnsp, rs); 1199 case 0x1: 1200 return new CASPA64(machInst, rt, rnsp, rs); 1201 case 0x2: 1202 return new LDXPW64(machInst, rt, rt2, rnsp); 1203 case 0x3: 1204 return new LDXPX64(machInst, rt, rt2, rnsp); 1205 default: 1206 M5_UNREACHABLE; 1207 } 1208 case 0x7: 1209 switch (size) { 1210 case 0x0: 1211 return new CASPAL32(machInst, rt, rnsp, rs); 1212 case 0x1: 1213 return new CASPAL64(machInst, rt, rnsp, rs); 1214 case 0x2: 1215 return new LDAXPW64(machInst, rt, rt2, rnsp); 1216 case 0x3: 1217 return new LDAXPX64(machInst, rt, rt2, rnsp); 1218 default: 1219 M5_UNREACHABLE; 1220 } 1221 case 0x9: 1222 switch (size) { 1223 case 0x0: 1224 return new STLRB64(machInst, rt, rnsp); 1225 case 0x1: 1226 return new STLRH64(machInst, rt, rnsp); 1227 case 0x2: 1228 return new STLRW64(machInst, rt, rnsp); 1229 case 0x3: 1230 return new STLRX64(machInst, rt, rnsp); 1231 default: 1232 M5_UNREACHABLE; 1233 } 1234 case 0xa: 1235 switch (size) { 1236 case 0x0: 1237 return new CASB(machInst, rt, rnsp, rs); 1238 case 0x1: 1239 return new CASH(machInst, rt, rnsp, rs); 1240 case 0x2: 1241 return new CAS32(machInst, rt, rnsp, rs); 1242 case 0x3: 1243 return new CAS64(machInst, rt, rnsp, rs); 1244 default: 1245 M5_UNREACHABLE; 1246 } 1247 case 0xb: 1248 switch (size) { 1249 case 0x0: 1250 return new CASLB(machInst, rt, rnsp, rs); 1251 case 0x1: 1252 return new CASLH(machInst, rt, rnsp, rs); 1253 case 0x2: 1254 return new CASL32(machInst, rt, rnsp, rs); 1255 case 0x3: 1256 return new CASL64(machInst, rt, rnsp, rs); 1257 default: 1258 M5_UNREACHABLE; 1259 } 1260 case 0xd: 1261 switch (size) { 1262 case 0x0: 1263 return new LDARB64(machInst, rt, rnsp); 1264 case 0x1: 1265 return new LDARH64(machInst, rt, rnsp); 1266 case 0x2: 1267 return new LDARW64(machInst, rt, rnsp); 1268 case 0x3: 1269 return new LDARX64(machInst, rt, rnsp); 1270 default: 1271 M5_UNREACHABLE; 1272 } 1273 case 0xe: 1274 switch (size) { 1275 case 0x0: 1276 return new CASAB(machInst, rt, rnsp, rs); 1277 case 0x1: 1278 return new CASAH(machInst, rt, rnsp, rs); 1279 case 0x2: 1280 return new CASA32(machInst, rt, rnsp, rs); 1281 case 0x3: 1282 return new CASA64(machInst, rt, rnsp, rs); 1283 default: 1284 M5_UNREACHABLE; 1285 } 1286 case 0xf: 1287 switch (size) { 1288 case 0x0: 1289 return new CASALB(machInst, rt, rnsp, rs); 1290 case 0x1: 1291 return new CASALH(machInst, rt, rnsp, rs); 1292 case 0x2: 1293 return new CASAL32(machInst, rt, rnsp, rs); 1294 case 0x3: 1295 return new CASAL64(machInst, rt, rnsp, rs); 1296 default: 1297 M5_UNREACHABLE; 1298 } 1299 default: 1300 return new Unknown64(machInst); 1301 } 1302 } else if (bits(machInst, 31)) { 1303 return new Unknown64(machInst); 1304 } else { 1305 return decodeNeonMem(machInst); 1306 } 1307 case 0x1: 1308 { 1309 if (bits(machInst, 24) != 0) 1310 return new Unknown64(machInst); 1311 uint8_t switchVal = (bits(machInst, 26) << 0) | 1312 (bits(machInst, 31, 30) << 1); 1313 int64_t imm = sext<19>(bits(machInst, 23, 5)) << 2; 1314 IntRegIndex rt = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1315 switch (switchVal) { 1316 case 0x0: 1317 return new LDRWL64_LIT(machInst, rt, imm); 1318 case 0x1: 1319 return new LDRSFP64_LIT(machInst, rt, imm); 1320 case 0x2: 1321 return new LDRXL64_LIT(machInst, rt, imm); 1322 case 0x3: 1323 return new LDRDFP64_LIT(machInst, rt, imm); 1324 case 0x4: 1325 return new LDRSWL64_LIT(machInst, rt, imm); 1326 case 0x5: 1327 return new BigFpMemLit("ldr", machInst, rt, imm); 1328 case 0x6: 1329 return new PRFM64_LIT(machInst, rt, imm); 1330 default: 1331 return new Unknown64(machInst); 1332 } 1333 } 1334 case 0x2: 1335 { 1336 uint8_t opc = bits(machInst, 31, 30); 1337 if (opc >= 3) 1338 return new Unknown64(machInst); 1339 uint32_t size = 0; 1340 bool fp = bits(machInst, 26); 1341 bool load = bits(machInst, 22); 1342 if (fp) { 1343 size = 4 << opc; 1344 } else { 1345 if ((opc == 1) && !load) 1346 return new Unknown64(machInst); 1347 size = (opc == 0 || opc == 1) ? 4 : 8; 1348 } 1349 uint8_t type = bits(machInst, 24, 23); 1350 int64_t imm = sext<7>(bits(machInst, 21, 15)) * size; 1351 1352 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1353 IntRegIndex rt = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1354 IntRegIndex rt2 = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 1355 1356 bool noAlloc = (type == 0); 1357 bool signExt = !noAlloc && !fp && opc == 1; 1358 PairMemOp::AddrMode mode; 1359 const char *mnemonic = NULL; 1360 switch (type) { 1361 case 0x0: 1362 case 0x2: 1363 mode = PairMemOp::AddrMd_Offset; 1364 break; 1365 case 0x1: 1366 mode = PairMemOp::AddrMd_PostIndex; 1367 break; 1368 case 0x3: 1369 mode = PairMemOp::AddrMd_PreIndex; 1370 break; 1371 default: 1372 return new Unknown64(machInst); 1373 } 1374 if (load) { 1375 if (noAlloc) 1376 mnemonic = "ldnp"; 1377 else if (signExt) 1378 mnemonic = "ldpsw"; 1379 else 1380 mnemonic = "ldp"; 1381 } else { 1382 if (noAlloc) 1383 mnemonic = "stnp"; 1384 else 1385 mnemonic = "stp"; 1386 } 1387 1388 return new LdpStp(mnemonic, machInst, size, fp, load, noAlloc, 1389 signExt, false, false, imm, mode, rn, rt, rt2); 1390 } 1391 // bit 29:27=111, 25=0 1392 case 0x3: 1393 { 1394 uint8_t switchVal = (bits(machInst, 23, 22) << 0) | 1395 (bits(machInst, 26) << 2) | 1396 (bits(machInst, 31, 30) << 3); 1397 if (bits(machInst, 24) == 1) { 1398 uint64_t imm12 = bits(machInst, 21, 10); 1399 IntRegIndex rt = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1400 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1401 IntRegIndex rnsp = makeSP(rn); 1402 switch (switchVal) { 1403 case 0x00: 1404 return new STRB64_IMM(machInst, rt, rnsp, imm12); 1405 case 0x01: 1406 return new LDRB64_IMM(machInst, rt, rnsp, imm12); 1407 case 0x02: 1408 return new LDRSBX64_IMM(machInst, rt, rnsp, imm12); 1409 case 0x03: 1410 return new LDRSBW64_IMM(machInst, rt, rnsp, imm12); 1411 case 0x04: 1412 return new STRBFP64_IMM(machInst, rt, rnsp, imm12); 1413 case 0x05: 1414 return new LDRBFP64_IMM(machInst, rt, rnsp, imm12); 1415 case 0x06: 1416 return new BigFpMemImm("str", machInst, false, 1417 rt, rnsp, imm12 << 4); 1418 case 0x07: 1419 return new BigFpMemImm("ldr", machInst, true, 1420 rt, rnsp, imm12 << 4); 1421 case 0x08: 1422 return new STRH64_IMM(machInst, rt, rnsp, imm12 << 1); 1423 case 0x09: 1424 return new LDRH64_IMM(machInst, rt, rnsp, imm12 << 1); 1425 case 0x0a: 1426 return new LDRSHX64_IMM(machInst, rt, rnsp, imm12 << 1); 1427 case 0x0b: 1428 return new LDRSHW64_IMM(machInst, rt, rnsp, imm12 << 1); 1429 case 0x0c: 1430 return new STRHFP64_IMM(machInst, rt, rnsp, imm12 << 1); 1431 case 0x0d: 1432 return new LDRHFP64_IMM(machInst, rt, rnsp, imm12 << 1); 1433 case 0x10: 1434 return new STRW64_IMM(machInst, rt, rnsp, imm12 << 2); 1435 case 0x11: 1436 return new LDRW64_IMM(machInst, rt, rnsp, imm12 << 2); 1437 case 0x12: 1438 return new LDRSW64_IMM(machInst, rt, rnsp, imm12 << 2); 1439 case 0x14: 1440 return new STRSFP64_IMM(machInst, rt, rnsp, imm12 << 2); 1441 case 0x15: 1442 return new LDRSFP64_IMM(machInst, rt, rnsp, imm12 << 2); 1443 case 0x18: 1444 return new STRX64_IMM(machInst, rt, rnsp, imm12 << 3); 1445 case 0x19: 1446 return new LDRX64_IMM(machInst, rt, rnsp, imm12 << 3); 1447 case 0x1a: 1448 return new PRFM64_IMM(machInst, rt, rnsp, imm12 << 3); 1449 case 0x1c: 1450 return new STRDFP64_IMM(machInst, rt, rnsp, imm12 << 3); 1451 case 0x1d: 1452 return new LDRDFP64_IMM(machInst, rt, rnsp, imm12 << 3); 1453 default: 1454 return new Unknown64(machInst); 1455 } 1456 } else if (bits(machInst, 21) == 1) { 1457 uint8_t group = bits(machInst, 11, 10); 1458 switch (group) { 1459 case 0x0: 1460 { 1461 if ((switchVal & 0x7) == 0x2 && 1462 bits(machInst, 20, 12) == 0x1fc) { 1463 IntRegIndex rt = (IntRegIndex)(uint32_t) 1464 bits(machInst, 4, 0); 1465 IntRegIndex rn = (IntRegIndex)(uint32_t) 1466 bits(machInst, 9, 5); 1467 IntRegIndex rnsp = makeSP(rn); 1468 uint8_t size = bits(machInst, 31, 30); 1469 switch (size) { 1470 case 0x0: 1471 return new LDAPRB64(machInst, rt, rnsp); 1472 case 0x1: 1473 return new LDAPRH64(machInst, rt, rnsp); 1474 case 0x2: 1475 return new LDAPRW64(machInst, rt, rnsp); 1476 case 0x3: 1477 return new LDAPRX64(machInst, rt, rnsp); 1478 default: 1479 M5_UNREACHABLE; 1480 } 1481 } else { 1482 return decodeAtomicArithOp(machInst); 1483 } 1484 } 1485 case 0x2: 1486 { 1487 if (!bits(machInst, 14)) 1488 return new Unknown64(machInst); 1489 IntRegIndex rt = (IntRegIndex)(uint32_t) 1490 bits(machInst, 4, 0); 1491 IntRegIndex rn = (IntRegIndex)(uint32_t) 1492 bits(machInst, 9, 5); 1493 IntRegIndex rnsp = makeSP(rn); 1494 IntRegIndex rm = (IntRegIndex)(uint32_t) 1495 bits(machInst, 20, 16); 1496 ArmExtendType type = 1497 (ArmExtendType)(uint32_t)bits(machInst, 15, 13); 1498 uint8_t s = bits(machInst, 12); 1499 switch (switchVal) { 1500 case 0x00: 1501 return new STRB64_REG(machInst, rt, rnsp, rm, 1502 type, 0); 1503 case 0x01: 1504 return new LDRB64_REG(machInst, rt, rnsp, rm, 1505 type, 0); 1506 case 0x02: 1507 return new LDRSBX64_REG(machInst, rt, rnsp, rm, 1508 type, 0); 1509 case 0x03: 1510 return new LDRSBW64_REG(machInst, rt, rnsp, rm, 1511 type, 0); 1512 case 0x04: 1513 return new STRBFP64_REG(machInst, rt, rnsp, rm, 1514 type, 0); 1515 case 0x05: 1516 return new LDRBFP64_REG(machInst, rt, rnsp, rm, 1517 type, 0); 1518 case 0x6: 1519 return new BigFpMemReg("str", machInst, false, 1520 rt, rnsp, rm, type, s * 4); 1521 case 0x7: 1522 return new BigFpMemReg("ldr", machInst, true, 1523 rt, rnsp, rm, type, s * 4); 1524 case 0x08: 1525 return new STRH64_REG(machInst, rt, rnsp, rm, 1526 type, s); 1527 case 0x09: 1528 return new LDRH64_REG(machInst, rt, rnsp, rm, 1529 type, s); 1530 case 0x0a: 1531 return new LDRSHX64_REG(machInst, rt, rnsp, rm, 1532 type, s); 1533 case 0x0b: 1534 return new LDRSHW64_REG(machInst, rt, rnsp, rm, 1535 type, s); 1536 case 0x0c: 1537 return new STRHFP64_REG(machInst, rt, rnsp, rm, 1538 type, s); 1539 case 0x0d: 1540 return new LDRHFP64_REG(machInst, rt, rnsp, rm, 1541 type, s); 1542 case 0x10: 1543 return new STRW64_REG(machInst, rt, rnsp, rm, 1544 type, s * 2); 1545 case 0x11: 1546 return new LDRW64_REG(machInst, rt, rnsp, rm, 1547 type, s * 2); 1548 case 0x12: 1549 return new LDRSW64_REG(machInst, rt, rnsp, rm, 1550 type, s * 2); 1551 case 0x14: 1552 return new STRSFP64_REG(machInst, rt, rnsp, rm, 1553 type, s * 2); 1554 case 0x15: 1555 return new LDRSFP64_REG(machInst, rt, rnsp, rm, 1556 type, s * 2); 1557 case 0x18: 1558 return new STRX64_REG(machInst, rt, rnsp, rm, 1559 type, s * 3); 1560 case 0x19: 1561 return new LDRX64_REG(machInst, rt, rnsp, rm, 1562 type, s * 3); 1563 case 0x1a: 1564 return new PRFM64_REG(machInst, rt, rnsp, rm, 1565 type, s * 3); 1566 case 0x1c: 1567 return new STRDFP64_REG(machInst, rt, rnsp, rm, 1568 type, s * 3); 1569 case 0x1d: 1570 return new LDRDFP64_REG(machInst, rt, rnsp, rm, 1571 type, s * 3); 1572 default: 1573 return new Unknown64(machInst); 1574 1575 } 1576 } 1577 default: 1578 return new Unknown64(machInst); 1579 } 1580 } else { 1581 // bit 29:27=111, 25:24=00, 21=0 1582 switch (bits(machInst, 11, 10)) { 1583 case 0x0: 1584 { 1585 IntRegIndex rt = 1586 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1587 IntRegIndex rn = 1588 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1589 IntRegIndex rnsp = makeSP(rn); 1590 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1591 switch (switchVal) { 1592 case 0x00: 1593 return new STURB64_IMM(machInst, rt, rnsp, imm); 1594 case 0x01: 1595 return new LDURB64_IMM(machInst, rt, rnsp, imm); 1596 case 0x02: 1597 return new LDURSBX64_IMM(machInst, rt, rnsp, imm); 1598 case 0x03: 1599 return new LDURSBW64_IMM(machInst, rt, rnsp, imm); 1600 case 0x04: 1601 return new STURBFP64_IMM(machInst, rt, rnsp, imm); 1602 case 0x05: 1603 return new LDURBFP64_IMM(machInst, rt, rnsp, imm); 1604 case 0x06: 1605 return new BigFpMemImm("stur", machInst, false, 1606 rt, rnsp, imm); 1607 case 0x07: 1608 return new BigFpMemImm("ldur", machInst, true, 1609 rt, rnsp, imm); 1610 case 0x08: 1611 return new STURH64_IMM(machInst, rt, rnsp, imm); 1612 case 0x09: 1613 return new LDURH64_IMM(machInst, rt, rnsp, imm); 1614 case 0x0a: 1615 return new LDURSHX64_IMM(machInst, rt, rnsp, imm); 1616 case 0x0b: 1617 return new LDURSHW64_IMM(machInst, rt, rnsp, imm); 1618 case 0x0c: 1619 return new STURHFP64_IMM(machInst, rt, rnsp, imm); 1620 case 0x0d: 1621 return new LDURHFP64_IMM(machInst, rt, rnsp, imm); 1622 case 0x10: 1623 return new STURW64_IMM(machInst, rt, rnsp, imm); 1624 case 0x11: 1625 return new LDURW64_IMM(machInst, rt, rnsp, imm); 1626 case 0x12: 1627 return new LDURSW64_IMM(machInst, rt, rnsp, imm); 1628 case 0x14: 1629 return new STURSFP64_IMM(machInst, rt, rnsp, imm); 1630 case 0x15: 1631 return new LDURSFP64_IMM(machInst, rt, rnsp, imm); 1632 case 0x18: 1633 return new STURX64_IMM(machInst, rt, rnsp, imm); 1634 case 0x19: 1635 return new LDURX64_IMM(machInst, rt, rnsp, imm); 1636 case 0x1a: 1637 return new PRFUM64_IMM(machInst, rt, rnsp, imm); 1638 case 0x1c: 1639 return new STURDFP64_IMM(machInst, rt, rnsp, imm); 1640 case 0x1d: 1641 return new LDURDFP64_IMM(machInst, rt, rnsp, imm); 1642 default: 1643 return new Unknown64(machInst); 1644 } 1645 } 1646 // bit 29:27=111, 25:24=00, 21=0, 11:10=01 1647 case 0x1: 1648 { 1649 IntRegIndex rt = 1650 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1651 IntRegIndex rn = 1652 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1653 IntRegIndex rnsp = makeSP(rn); 1654 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1655 switch (switchVal) { 1656 case 0x00: 1657 return new STRB64_POST(machInst, rt, rnsp, imm); 1658 case 0x01: 1659 return new LDRB64_POST(machInst, rt, rnsp, imm); 1660 case 0x02: 1661 return new LDRSBX64_POST(machInst, rt, rnsp, imm); 1662 case 0x03: 1663 return new LDRSBW64_POST(machInst, rt, rnsp, imm); 1664 case 0x04: 1665 return new STRBFP64_POST(machInst, rt, rnsp, imm); 1666 case 0x05: 1667 return new LDRBFP64_POST(machInst, rt, rnsp, imm); 1668 case 0x06: 1669 return new BigFpMemPost("str", machInst, false, 1670 rt, rnsp, imm); 1671 case 0x07: 1672 return new BigFpMemPost("ldr", machInst, true, 1673 rt, rnsp, imm); 1674 case 0x08: 1675 return new STRH64_POST(machInst, rt, rnsp, imm); 1676 case 0x09: 1677 return new LDRH64_POST(machInst, rt, rnsp, imm); 1678 case 0x0a: 1679 return new LDRSHX64_POST(machInst, rt, rnsp, imm); 1680 case 0x0b: 1681 return new LDRSHW64_POST(machInst, rt, rnsp, imm); 1682 case 0x0c: 1683 return new STRHFP64_POST(machInst, rt, rnsp, imm); 1684 case 0x0d: 1685 return new LDRHFP64_POST(machInst, rt, rnsp, imm); 1686 case 0x10: 1687 return new STRW64_POST(machInst, rt, rnsp, imm); 1688 case 0x11: 1689 return new LDRW64_POST(machInst, rt, rnsp, imm); 1690 case 0x12: 1691 return new LDRSW64_POST(machInst, rt, rnsp, imm); 1692 case 0x14: 1693 return new STRSFP64_POST(machInst, rt, rnsp, imm); 1694 case 0x15: 1695 return new LDRSFP64_POST(machInst, rt, rnsp, imm); 1696 case 0x18: 1697 return new STRX64_POST(machInst, rt, rnsp, imm); 1698 case 0x19: 1699 return new LDRX64_POST(machInst, rt, rnsp, imm); 1700 case 0x1c: 1701 return new STRDFP64_POST(machInst, rt, rnsp, imm); 1702 case 0x1d: 1703 return new LDRDFP64_POST(machInst, rt, rnsp, imm); 1704 default: 1705 return new Unknown64(machInst); 1706 } 1707 } 1708 case 0x2: 1709 { 1710 IntRegIndex rt = 1711 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1712 IntRegIndex rn = 1713 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1714 IntRegIndex rnsp = makeSP(rn); 1715 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1716 switch (switchVal) { 1717 case 0x00: 1718 return new STTRB64_IMM(machInst, rt, rnsp, imm); 1719 case 0x01: 1720 return new LDTRB64_IMM(machInst, rt, rnsp, imm); 1721 case 0x02: 1722 return new LDTRSBX64_IMM(machInst, rt, rnsp, imm); 1723 case 0x03: 1724 return new LDTRSBW64_IMM(machInst, rt, rnsp, imm); 1725 case 0x08: 1726 return new STTRH64_IMM(machInst, rt, rnsp, imm); 1727 case 0x09: 1728 return new LDTRH64_IMM(machInst, rt, rnsp, imm); 1729 case 0x0a: 1730 return new LDTRSHX64_IMM(machInst, rt, rnsp, imm); 1731 case 0x0b: 1732 return new LDTRSHW64_IMM(machInst, rt, rnsp, imm); 1733 case 0x10: 1734 return new STTRW64_IMM(machInst, rt, rnsp, imm); 1735 case 0x11: 1736 return new LDTRW64_IMM(machInst, rt, rnsp, imm); 1737 case 0x12: 1738 return new LDTRSW64_IMM(machInst, rt, rnsp, imm); 1739 case 0x18: 1740 return new STTRX64_IMM(machInst, rt, rnsp, imm); 1741 case 0x19: 1742 return new LDTRX64_IMM(machInst, rt, rnsp, imm); 1743 default: 1744 return new Unknown64(machInst); 1745 } 1746 } 1747 case 0x3: 1748 { 1749 IntRegIndex rt = 1750 (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 1751 IntRegIndex rn = 1752 (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 1753 IntRegIndex rnsp = makeSP(rn); 1754 uint64_t imm = sext<9>(bits(machInst, 20, 12)); 1755 switch (switchVal) { 1756 case 0x00: 1757 return new STRB64_PRE(machInst, rt, rnsp, imm); 1758 case 0x01: 1759 return new LDRB64_PRE(machInst, rt, rnsp, imm); 1760 case 0x02: 1761 return new LDRSBX64_PRE(machInst, rt, rnsp, imm); 1762 case 0x03: 1763 return new LDRSBW64_PRE(machInst, rt, rnsp, imm); 1764 case 0x04: 1765 return new STRBFP64_PRE(machInst, rt, rnsp, imm); 1766 case 0x05: 1767 return new LDRBFP64_PRE(machInst, rt, rnsp, imm); 1768 case 0x06: 1769 return new BigFpMemPre("str", machInst, false, 1770 rt, rnsp, imm); 1771 case 0x07: 1772 return new BigFpMemPre("ldr", machInst, true, 1773 rt, rnsp, imm); 1774 case 0x08: 1775 return new STRH64_PRE(machInst, rt, rnsp, imm); 1776 case 0x09: 1777 return new LDRH64_PRE(machInst, rt, rnsp, imm); 1778 case 0x0a: 1779 return new LDRSHX64_PRE(machInst, rt, rnsp, imm); 1780 case 0x0b: 1781 return new LDRSHW64_PRE(machInst, rt, rnsp, imm); 1782 case 0x0c: 1783 return new STRHFP64_PRE(machInst, rt, rnsp, imm); 1784 case 0x0d: 1785 return new LDRHFP64_PRE(machInst, rt, rnsp, imm); 1786 case 0x10: 1787 return new STRW64_PRE(machInst, rt, rnsp, imm); 1788 case 0x11: 1789 return new LDRW64_PRE(machInst, rt, rnsp, imm); 1790 case 0x12: 1791 return new LDRSW64_PRE(machInst, rt, rnsp, imm); 1792 case 0x14: 1793 return new STRSFP64_PRE(machInst, rt, rnsp, imm); 1794 case 0x15: 1795 return new LDRSFP64_PRE(machInst, rt, rnsp, imm); 1796 case 0x18: 1797 return new STRX64_PRE(machInst, rt, rnsp, imm); 1798 case 0x19: 1799 return new LDRX64_PRE(machInst, rt, rnsp, imm); 1800 case 0x1c: 1801 return new STRDFP64_PRE(machInst, rt, rnsp, imm); 1802 case 0x1d: 1803 return new LDRDFP64_PRE(machInst, rt, rnsp, imm); 1804 default: 1805 return new Unknown64(machInst); 1806 } 1807 } 1808 default: 1809 M5_UNREACHABLE; 1810 } 1811 } 1812 } 1813 default: 1814 M5_UNREACHABLE; 1815 } 1816 return new FailUnimplemented("Unhandled Case1", machInst); 1817 } 1818} 1819}}; 1820 1821output decoder {{ 1822namespace Aarch64 1823{ 1824 StaticInstPtr 1825 decodeDataProcReg(ExtMachInst machInst) 1826 { 1827 uint8_t switchVal = (bits(machInst, 28) << 1) | 1828 (bits(machInst, 24) << 0); 1829 switch (switchVal) { 1830 case 0x0: 1831 { 1832 uint8_t switchVal = (bits(machInst, 21) << 0) | 1833 (bits(machInst, 30, 29) << 1); 1834 ArmShiftType type = (ArmShiftType)(uint8_t)bits(machInst, 23, 22); 1835 uint8_t imm6 = bits(machInst, 15, 10); 1836 bool sf = bits(machInst, 31); 1837 if (!sf && (imm6 & 0x20)) 1838 return new Unknown64(machInst); 1839 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1840 IntRegIndex rdzr = makeZero(rd); 1841 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1842 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1843 1844 switch (switchVal) { 1845 case 0x0: 1846 return new AndXSReg(machInst, rdzr, rn, rm, imm6, type); 1847 case 0x1: 1848 return new BicXSReg(machInst, rdzr, rn, rm, imm6, type); 1849 case 0x2: 1850 return new OrrXSReg(machInst, rdzr, rn, rm, imm6, type); 1851 case 0x3: 1852 return new OrnXSReg(machInst, rdzr, rn, rm, imm6, type); 1853 case 0x4: 1854 return new EorXSReg(machInst, rdzr, rn, rm, imm6, type); 1855 case 0x5: 1856 return new EonXSReg(machInst, rdzr, rn, rm, imm6, type); 1857 case 0x6: 1858 return new AndXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1859 case 0x7: 1860 return new BicXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1861 default: 1862 M5_UNREACHABLE; 1863 } 1864 } 1865 case 0x1: 1866 { 1867 uint8_t switchVal = bits(machInst, 30, 29); 1868 if (bits(machInst, 21) == 0) { 1869 ArmShiftType type = 1870 (ArmShiftType)(uint8_t)bits(machInst, 23, 22); 1871 if (type == ROR) 1872 return new Unknown64(machInst); 1873 uint8_t imm6 = bits(machInst, 15, 10); 1874 if (!bits(machInst, 31) && bits(imm6, 5)) 1875 return new Unknown64(machInst); 1876 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1877 IntRegIndex rdzr = makeZero(rd); 1878 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1879 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1880 switch (switchVal) { 1881 case 0x0: 1882 return new AddXSReg(machInst, rdzr, rn, rm, imm6, type); 1883 case 0x1: 1884 return new AddXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1885 case 0x2: 1886 return new SubXSReg(machInst, rdzr, rn, rm, imm6, type); 1887 case 0x3: 1888 return new SubXSRegCc(machInst, rdzr, rn, rm, imm6, type); 1889 default: 1890 M5_UNREACHABLE; 1891 } 1892 } else { 1893 if (bits(machInst, 23, 22) != 0 || bits(machInst, 12, 10) > 0x4) 1894 return new Unknown64(machInst); 1895 ArmExtendType type = 1896 (ArmExtendType)(uint8_t)bits(machInst, 15, 13); 1897 uint8_t imm3 = bits(machInst, 12, 10); 1898 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1899 IntRegIndex rdsp = makeSP(rd); 1900 IntRegIndex rdzr = makeZero(rd); 1901 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1902 IntRegIndex rnsp = makeSP(rn); 1903 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1904 1905 switch (switchVal) { 1906 case 0x0: 1907 return new AddXEReg(machInst, rdsp, rnsp, rm, type, imm3); 1908 case 0x1: 1909 return new AddXERegCc(machInst, rdzr, rnsp, rm, type, imm3); 1910 case 0x2: 1911 return new SubXEReg(machInst, rdsp, rnsp, rm, type, imm3); 1912 case 0x3: 1913 return new SubXERegCc(machInst, rdzr, rnsp, rm, type, imm3); 1914 default: 1915 M5_UNREACHABLE; 1916 } 1917 } 1918 } 1919 case 0x2: 1920 { 1921 if (bits(machInst, 21) == 1) 1922 return new Unknown64(machInst); 1923 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1924 IntRegIndex rdzr = makeZero(rd); 1925 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1926 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1927 switch (bits(machInst, 23, 22)) { 1928 case 0x0: 1929 { 1930 if (bits(machInst, 15, 10)) 1931 return new Unknown64(machInst); 1932 uint8_t switchVal = bits(machInst, 30, 29); 1933 switch (switchVal) { 1934 case 0x0: 1935 return new AdcXSReg(machInst, rdzr, rn, rm, 0, LSL); 1936 case 0x1: 1937 return new AdcXSRegCc(machInst, rdzr, rn, rm, 0, LSL); 1938 case 0x2: 1939 return new SbcXSReg(machInst, rdzr, rn, rm, 0, LSL); 1940 case 0x3: 1941 return new SbcXSRegCc(machInst, rdzr, rn, rm, 0, LSL); 1942 default: 1943 M5_UNREACHABLE; 1944 } 1945 } 1946 case 0x1: 1947 { 1948 if ((bits(machInst, 4) == 1) || 1949 (bits(machInst, 10) == 1) || 1950 (bits(machInst, 29) == 0)) { 1951 return new Unknown64(machInst); 1952 } 1953 ConditionCode cond = 1954 (ConditionCode)(uint8_t)bits(machInst, 15, 12); 1955 uint8_t flags = bits(machInst, 3, 0); 1956 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1957 if (bits(machInst, 11) == 0) { 1958 IntRegIndex rm = 1959 (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1960 if (bits(machInst, 30) == 0) { 1961 return new CcmnReg64(machInst, rn, rm, cond, flags); 1962 } else { 1963 return new CcmpReg64(machInst, rn, rm, cond, flags); 1964 } 1965 } else { 1966 uint8_t imm5 = bits(machInst, 20, 16); 1967 if (bits(machInst, 30) == 0) { 1968 return new CcmnImm64(machInst, rn, imm5, cond, flags); 1969 } else { 1970 return new CcmpImm64(machInst, rn, imm5, cond, flags); 1971 } 1972 } 1973 } 1974 case 0x2: 1975 { 1976 if (bits(machInst, 29) == 1 || 1977 bits(machInst, 11) == 1) { 1978 return new Unknown64(machInst); 1979 } 1980 uint8_t switchVal = (bits(machInst, 10) << 0) | 1981 (bits(machInst, 30) << 1); 1982 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 1983 IntRegIndex rdzr = makeZero(rd); 1984 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 1985 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 1986 ConditionCode cond = 1987 (ConditionCode)(uint8_t)bits(machInst, 15, 12); 1988 switch (switchVal) { 1989 case 0x0: 1990 return new Csel64(machInst, rdzr, rn, rm, cond); 1991 case 0x1: 1992 return new Csinc64(machInst, rdzr, rn, rm, cond); 1993 case 0x2: 1994 return new Csinv64(machInst, rdzr, rn, rm, cond); 1995 case 0x3: 1996 return new Csneg64(machInst, rdzr, rn, rm, cond); 1997 default: 1998 M5_UNREACHABLE; 1999 } 2000 } 2001 case 0x3: 2002 if (bits(machInst, 30) == 0) { 2003 if (bits(machInst, 29) != 0) 2004 return new Unknown64(machInst); 2005 uint8_t switchVal = bits(machInst, 15, 10); 2006 switch (switchVal) { 2007 case 0x2: 2008 return new Udiv64(machInst, rdzr, rn, rm); 2009 case 0x3: 2010 return new Sdiv64(machInst, rdzr, rn, rm); 2011 case 0x8: 2012 return new Lslv64(machInst, rdzr, rn, rm); 2013 case 0x9: 2014 return new Lsrv64(machInst, rdzr, rn, rm); 2015 case 0xa: 2016 return new Asrv64(machInst, rdzr, rn, rm); 2017 case 0xb: 2018 return new Rorv64(machInst, rdzr, rn, rm); 2019 case 0x10: 2020 return new Crc32b64(machInst, rdzr, rn, rm); 2021 case 0x11: 2022 return new Crc32h64(machInst, rdzr, rn, rm); 2023 case 0x12: 2024 return new Crc32w64(machInst, rdzr, rn, rm); 2025 case 0x13: 2026 return new Crc32x64(machInst, rdzr, rn, rm); 2027 case 0x14: 2028 return new Crc32cb64(machInst, rdzr, rn, rm); 2029 case 0x15: 2030 return new Crc32ch64(machInst, rdzr, rn, rm); 2031 case 0x16: 2032 return new Crc32cw64(machInst, rdzr, rn, rm); 2033 case 0x17: 2034 return new Crc32cx64(machInst, rdzr, rn, rm); 2035 default: 2036 return new Unknown64(machInst); 2037 } 2038 } else { 2039 if (bits(machInst, 20, 16) != 0 || 2040 bits(machInst, 29) != 0) { 2041 return new Unknown64(machInst); 2042 } 2043 uint8_t switchVal = bits(machInst, 15, 10); 2044 switch (switchVal) { 2045 case 0x0: 2046 return new Rbit64(machInst, rdzr, rn); 2047 case 0x1: 2048 return new Rev1664(machInst, rdzr, rn); 2049 case 0x2: 2050 if (bits(machInst, 31) == 0) 2051 return new Rev64(machInst, rdzr, rn); 2052 else 2053 return new Rev3264(machInst, rdzr, rn); 2054 case 0x3: 2055 if (bits(machInst, 31) != 1) 2056 return new Unknown64(machInst); 2057 return new Rev64(machInst, rdzr, rn); 2058 case 0x4: 2059 return new Clz64(machInst, rdzr, rn); 2060 case 0x5: 2061 return new Cls64(machInst, rdzr, rn); 2062 default: 2063 return new Unknown64(machInst); 2064 } 2065 } 2066 default: 2067 M5_UNREACHABLE; 2068 } 2069 } 2070 case 0x3: 2071 { 2072 if (bits(machInst, 30, 29) != 0x0 || 2073 (bits(machInst, 23, 21) != 0 && bits(machInst, 31) == 0)) 2074 return new Unknown64(machInst); 2075 IntRegIndex rd = (IntRegIndex)(uint8_t)bits(machInst, 4, 0); 2076 IntRegIndex rdzr = makeZero(rd); 2077 IntRegIndex rn = (IntRegIndex)(uint8_t)bits(machInst, 9, 5); 2078 IntRegIndex ra = (IntRegIndex)(uint8_t)bits(machInst, 14, 10); 2079 IntRegIndex rm = (IntRegIndex)(uint8_t)bits(machInst, 20, 16); 2080 switch (bits(machInst, 23, 21)) { 2081 case 0x0: 2082 if (bits(machInst, 15) == 0) 2083 return new Madd64(machInst, rdzr, ra, rn, rm); 2084 else 2085 return new Msub64(machInst, rdzr, ra, rn, rm); 2086 case 0x1: 2087 if (bits(machInst, 15) == 0) 2088 return new Smaddl64(machInst, rdzr, ra, rn, rm); 2089 else 2090 return new Smsubl64(machInst, rdzr, ra, rn, rm); 2091 case 0x2: 2092 if (bits(machInst, 15) != 0) 2093 return new Unknown64(machInst); 2094 return new Smulh64(machInst, rdzr, rn, rm); 2095 case 0x5: 2096 if (bits(machInst, 15) == 0) 2097 return new Umaddl64(machInst, rdzr, ra, rn, rm); 2098 else 2099 return new Umsubl64(machInst, rdzr, ra, rn, rm); 2100 case 0x6: 2101 if (bits(machInst, 15) != 0) 2102 return new Unknown64(machInst); 2103 return new Umulh64(machInst, rdzr, rn, rm); 2104 default: 2105 return new Unknown64(machInst); 2106 } 2107 } 2108 default: 2109 M5_UNREACHABLE; 2110 } 2111 return new FailUnimplemented("Unhandled Case2", machInst); 2112 } 2113} 2114}}; 2115 2116output decoder {{ 2117namespace Aarch64 2118{ 2119 template <typename DecoderFeatures> 2120 StaticInstPtr 2121 decodeAdvSIMD(ExtMachInst machInst) 2122 { 2123 if (bits(machInst, 24) == 1) { 2124 if (bits(machInst, 10) == 0) { 2125 return decodeNeonIndexedElem<DecoderFeatures>(machInst); 2126 } else if (bits(machInst, 23) == 1) { 2127 return new Unknown64(machInst); 2128 } else { 2129 if (bits(machInst, 22, 19)) { 2130 return decodeNeonShiftByImm(machInst); 2131 } else { 2132 return decodeNeonModImm(machInst); 2133 } 2134 } 2135 } else if (bits(machInst, 21) == 1) { 2136 if (bits(machInst, 10) == 1) { 2137 return decodeNeon3Same<DecoderFeatures>(machInst); 2138 } else if (bits(machInst, 11) == 0) { 2139 return decodeNeon3Diff(machInst); 2140 } else if (bits(machInst, 20, 17) == 0x0) { 2141 return decodeNeon2RegMisc(machInst); 2142 } else if (bits(machInst, 20, 17) == 0x4) { 2143 return decodeCryptoAES(machInst); 2144 } else if (bits(machInst, 20, 17) == 0x8) { 2145 return decodeNeonAcrossLanes(machInst); 2146 } else { 2147 return new Unknown64(machInst); 2148 } 2149 } else if (bits(machInst, 24) || 2150 bits(machInst, 21) || 2151 bits(machInst, 15)) { 2152 return new Unknown64(machInst); 2153 } else if (bits(machInst, 10) == 1) { 2154 if (bits(machInst, 23, 22)) 2155 return new Unknown64(machInst); 2156 return decodeNeonCopy(machInst); 2157 } else if (bits(machInst, 29) == 1) { 2158 return decodeNeonExt(machInst); 2159 } else if (bits(machInst, 11) == 1) { 2160 return decodeNeonZipUzpTrn(machInst); 2161 } else if (bits(machInst, 23, 22) == 0x0) { 2162 return decodeNeonTblTbx(machInst); 2163 } else { 2164 return new Unknown64(machInst); 2165 } 2166 return new FailUnimplemented("Unhandled Case3", machInst); 2167 } 2168} 2169}}; 2170 2171 2172output decoder {{ 2173namespace Aarch64 2174{ 2175 StaticInstPtr 2176 // bit 30=0, 28:25=1111 2177 decodeFp(ExtMachInst machInst) 2178 { 2179 if (bits(machInst, 24) == 1) { 2180 if (bits(machInst, 31) || bits(machInst, 29)) 2181 return new Unknown64(machInst); 2182 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2183 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2184 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2185 IntRegIndex ra = (IntRegIndex)(uint32_t)bits(machInst, 14, 10); 2186 uint8_t switchVal = (bits(machInst, 23, 21) << 1) | 2187 (bits(machInst, 15) << 0); 2188 switch (switchVal) { 2189 case 0x0: // FMADD Sd = Sa + Sn*Sm 2190 return new FMAddS(machInst, rd, rn, rm, ra); 2191 case 0x1: // FMSUB Sd = Sa + (-Sn)*Sm 2192 return new FMSubS(machInst, rd, rn, rm, ra); 2193 case 0x2: // FNMADD Sd = (-Sa) + (-Sn)*Sm 2194 return new FNMAddS(machInst, rd, rn, rm, ra); 2195 case 0x3: // FNMSUB Sd = (-Sa) + Sn*Sm 2196 return new FNMSubS(machInst, rd, rn, rm, ra); 2197 case 0x4: // FMADD Dd = Da + Dn*Dm 2198 return new FMAddD(machInst, rd, rn, rm, ra); 2199 case 0x5: // FMSUB Dd = Da + (-Dn)*Dm 2200 return new FMSubD(machInst, rd, rn, rm, ra); 2201 case 0x6: // FNMADD Dd = (-Da) + (-Dn)*Dm 2202 return new FNMAddD(machInst, rd, rn, rm, ra); 2203 case 0x7: // FNMSUB Dd = (-Da) + Dn*Dm 2204 return new FNMSubD(machInst, rd, rn, rm, ra); 2205 default: 2206 return new Unknown64(machInst); 2207 } 2208 } else if (bits(machInst, 21) == 0) { 2209 bool s = bits(machInst, 29); 2210 if (s) 2211 return new Unknown64(machInst); 2212 uint8_t switchVal = bits(machInst, 20, 16); 2213 uint8_t type = bits(machInst, 23, 22); 2214 uint8_t scale = bits(machInst, 15, 10); 2215 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2216 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2217 if (bits(machInst, 18, 17) == 3 && scale != 0) 2218 return new Unknown64(machInst); 2219 // 30:24=0011110, 21=0 2220 switch (switchVal) { 2221 case 0x00: 2222 return new FailUnimplemented("fcvtns", machInst); 2223 case 0x01: 2224 return new FailUnimplemented("fcvtnu", machInst); 2225 case 0x02: 2226 switch ( (bits(machInst, 31) << 2) | type ) { 2227 case 0: // SCVTF Sd = convertFromInt(Wn/(2^fbits)) 2228 return new FcvtSFixedFpSW(machInst, rd, rn, scale); 2229 case 1: // SCVTF Dd = convertFromInt(Wn/(2^fbits)) 2230 return new FcvtSFixedFpDW(machInst, rd, rn, scale); 2231 case 4: // SCVTF Sd = convertFromInt(Xn/(2^fbits)) 2232 return new FcvtSFixedFpSX(machInst, rd, rn, scale); 2233 case 5: // SCVTF Dd = convertFromInt(Xn/(2^fbits)) 2234 return new FcvtSFixedFpDX(machInst, rd, rn, scale); 2235 default: 2236 return new Unknown64(machInst); 2237 } 2238 case 0x03: 2239 switch ( (bits(machInst, 31) << 2) | type ) { 2240 case 0: // UCVTF Sd = convertFromInt(Wn/(2^fbits)) 2241 return new FcvtUFixedFpSW(machInst, rd, rn, scale); 2242 case 1: // UCVTF Dd = convertFromInt(Wn/(2^fbits)) 2243 return new FcvtUFixedFpDW(machInst, rd, rn, scale); 2244 case 4: // UCVTF Sd = convertFromInt(Xn/(2^fbits)) 2245 return new FcvtUFixedFpSX(machInst, rd, rn, scale); 2246 case 5: // UCVTF Dd = convertFromInt(Xn/(2^fbits)) 2247 return new FcvtUFixedFpDX(machInst, rd, rn, scale); 2248 default: 2249 return new Unknown64(machInst); 2250 } 2251 case 0x04: 2252 return new FailUnimplemented("fcvtas", machInst); 2253 case 0x05: 2254 return new FailUnimplemented("fcvtau", machInst); 2255 case 0x08: 2256 return new FailUnimplemented("fcvtps", machInst); 2257 case 0x09: 2258 return new FailUnimplemented("fcvtpu", machInst); 2259 case 0x0e: 2260 return new FailUnimplemented("fmov elem. to 64", machInst); 2261 case 0x0f: 2262 return new FailUnimplemented("fmov 64 bit", machInst); 2263 case 0x10: 2264 return new FailUnimplemented("fcvtms", machInst); 2265 case 0x11: 2266 return new FailUnimplemented("fcvtmu", machInst); 2267 case 0x18: 2268 switch ( (bits(machInst, 31) << 2) | type ) { 2269 case 0: // FCVTZS Wd = convertToIntExactTowardZero(Sn*(2^fbits)) 2270 return new FcvtFpSFixedSW(machInst, rd, rn, scale); 2271 case 1: // FCVTZS Wd = convertToIntExactTowardZero(Dn*(2^fbits)) 2272 return new FcvtFpSFixedDW(machInst, rd, rn, scale); 2273 case 4: // FCVTZS Xd = convertToIntExactTowardZero(Sn*(2^fbits)) 2274 return new FcvtFpSFixedSX(machInst, rd, rn, scale); 2275 case 5: // FCVTZS Xd = convertToIntExactTowardZero(Dn*(2^fbits)) 2276 return new FcvtFpSFixedDX(machInst, rd, rn, scale); 2277 default: 2278 return new Unknown64(machInst); 2279 } 2280 case 0x19: 2281 switch ( (bits(machInst, 31) << 2) | type ) { 2282 case 0: // FCVTZU Wd = convertToIntExactTowardZero(Sn*(2^fbits)) 2283 return new FcvtFpUFixedSW(machInst, rd, rn, scale); 2284 case 1: // FCVTZU Wd = convertToIntExactTowardZero(Dn*(2^fbits)) 2285 return new FcvtFpUFixedDW(machInst, rd, rn, scale); 2286 case 4: // FCVTZU Xd = convertToIntExactTowardZero(Sn*(2^fbits)) 2287 return new FcvtFpUFixedSX(machInst, rd, rn, scale); 2288 case 5: // FCVTZU Xd = convertToIntExactTowardZero(Dn*(2^fbits)) 2289 return new FcvtFpUFixedDX(machInst, rd, rn, scale); 2290 default: 2291 return new Unknown64(machInst); 2292 } 2293 default: 2294 return new Unknown64(machInst); 2295 } 2296 } else { 2297 // 30=0, 28:24=11110, 21=1 2298 uint8_t type = bits(machInst, 23, 22); 2299 uint8_t imm8 = bits(machInst, 20, 13); 2300 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2301 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2302 switch (bits(machInst, 11, 10)) { 2303 case 0x0: 2304 if (bits(machInst, 12) == 1) { 2305 if (bits(machInst, 31) || 2306 bits(machInst, 29) || 2307 bits(machInst, 9, 5)) { 2308 return new Unknown64(machInst); 2309 } 2310 // 31:29=000, 28:24=11110, 21=1, 12:10=100 2311 if (type == 0) { 2312 // FMOV S[d] = imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,5) 2313 // :imm8<5:0>:Zeros(19) 2314 uint32_t imm = vfp_modified_imm(imm8, 2315 FpDataType::Fp32); 2316 return new FmovImmS(machInst, rd, imm); 2317 } else if (type == 1) { 2318 // FMOV D[d] = imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,8) 2319 // :imm8<5:0>:Zeros(48) 2320 uint64_t imm = vfp_modified_imm(imm8, 2321 FpDataType::Fp64); 2322 return new FmovImmD(machInst, rd, imm); 2323 } else { 2324 return new Unknown64(machInst); 2325 } 2326 } else if (bits(machInst, 13) == 1) { 2327 if (bits(machInst, 31) || 2328 bits(machInst, 29) || 2329 bits(machInst, 15, 14) || 2330 bits(machInst, 23) || 2331 bits(machInst, 2, 0)) { 2332 return new Unknown64(machInst); 2333 } 2334 uint8_t switchVal = (bits(machInst, 4, 3) << 0) | 2335 (bits(machInst, 22) << 2); 2336 IntRegIndex rm = (IntRegIndex)(uint32_t) 2337 bits(machInst, 20, 16); 2338 // 28:23=000111100, 21=1, 15:10=001000, 2:0=000 2339 switch (switchVal) { 2340 case 0x0: 2341 // FCMP flags = compareQuiet(Sn,Sm) 2342 return new FCmpRegS(machInst, rn, rm); 2343 case 0x1: 2344 // FCMP flags = compareQuiet(Sn,0.0) 2345 return new FCmpImmS(machInst, rn, 0); 2346 case 0x2: 2347 // FCMPE flags = compareSignaling(Sn,Sm) 2348 return new FCmpERegS(machInst, rn, rm); 2349 case 0x3: 2350 // FCMPE flags = compareSignaling(Sn,0.0) 2351 return new FCmpEImmS(machInst, rn, 0); 2352 case 0x4: 2353 // FCMP flags = compareQuiet(Dn,Dm) 2354 return new FCmpRegD(machInst, rn, rm); 2355 case 0x5: 2356 // FCMP flags = compareQuiet(Dn,0.0) 2357 return new FCmpImmD(machInst, rn, 0); 2358 case 0x6: 2359 // FCMPE flags = compareSignaling(Dn,Dm) 2360 return new FCmpERegD(machInst, rn, rm); 2361 case 0x7: 2362 // FCMPE flags = compareSignaling(Dn,0.0) 2363 return new FCmpEImmD(machInst, rn, 0); 2364 default: 2365 return new Unknown64(machInst); 2366 } 2367 } else if (bits(machInst, 14) == 1) { 2368 if (bits(machInst, 31) || bits(machInst, 29)) 2369 return new Unknown64(machInst); 2370 uint8_t opcode = bits(machInst, 20, 15); 2371 // Bits 31:24=00011110, 21=1, 14:10=10000 2372 switch (opcode) { 2373 case 0x0: 2374 if (type == 0) 2375 // FMOV Sd = Sn 2376 return new FmovRegS(machInst, rd, rn); 2377 else if (type == 1) 2378 // FMOV Dd = Dn 2379 return new FmovRegD(machInst, rd, rn); 2380 break; 2381 case 0x1: 2382 if (type == 0) 2383 // FABS Sd = abs(Sn) 2384 return new FAbsS(machInst, rd, rn); 2385 else if (type == 1) 2386 // FABS Dd = abs(Dn) 2387 return new FAbsD(machInst, rd, rn); 2388 break; 2389 case 0x2: 2390 if (type == 0) 2391 // FNEG Sd = -Sn 2392 return new FNegS(machInst, rd, rn); 2393 else if (type == 1) 2394 // FNEG Dd = -Dn 2395 return new FNegD(machInst, rd, rn); 2396 break; 2397 case 0x3: 2398 if (type == 0) 2399 // FSQRT Sd = sqrt(Sn) 2400 return new FSqrtS(machInst, rd, rn); 2401 else if (type == 1) 2402 // FSQRT Dd = sqrt(Dn) 2403 return new FSqrtD(machInst, rd, rn); 2404 break; 2405 case 0x4: 2406 if (type == 1) 2407 // FCVT Sd = convertFormat(Dn) 2408 return new FcvtFpDFpS(machInst, rd, rn); 2409 else if (type == 3) 2410 // FCVT Sd = convertFormat(Hn) 2411 return new FcvtFpHFpS(machInst, rd, rn); 2412 break; 2413 case 0x5: 2414 if (type == 0) 2415 // FCVT Dd = convertFormat(Sn) 2416 return new FCvtFpSFpD(machInst, rd, rn); 2417 else if (type == 3) 2418 // FCVT Dd = convertFormat(Hn) 2419 return new FcvtFpHFpD(machInst, rd, rn); 2420 break; 2421 case 0x7: 2422 if (type == 0) 2423 // FCVT Hd = convertFormat(Sn) 2424 return new FcvtFpSFpH(machInst, rd, rn); 2425 else if (type == 1) 2426 // FCVT Hd = convertFormat(Dn) 2427 return new FcvtFpDFpH(machInst, rd, rn); 2428 break; 2429 case 0x8: 2430 if (type == 0) // FRINTN Sd = roundToIntegralTiesToEven(Sn) 2431 return new FRIntNS(machInst, rd, rn); 2432 else if (type == 1) // FRINTN Dd = roundToIntegralTiesToEven(Dn) 2433 return new FRIntND(machInst, rd, rn); 2434 break; 2435 case 0x9: 2436 if (type == 0) // FRINTP Sd = roundToIntegralTowardPlusInf(Sn) 2437 return new FRIntPS(machInst, rd, rn); 2438 else if (type == 1) // FRINTP Dd = roundToIntegralTowardPlusInf(Dn) 2439 return new FRIntPD(machInst, rd, rn); 2440 break; 2441 case 0xa: 2442 if (type == 0) // FRINTM Sd = roundToIntegralTowardMinusInf(Sn) 2443 return new FRIntMS(machInst, rd, rn); 2444 else if (type == 1) // FRINTM Dd = roundToIntegralTowardMinusInf(Dn) 2445 return new FRIntMD(machInst, rd, rn); 2446 break; 2447 case 0xb: 2448 if (type == 0) // FRINTZ Sd = roundToIntegralTowardZero(Sn) 2449 return new FRIntZS(machInst, rd, rn); 2450 else if (type == 1) // FRINTZ Dd = roundToIntegralTowardZero(Dn) 2451 return new FRIntZD(machInst, rd, rn); 2452 break; 2453 case 0xc: 2454 if (type == 0) // FRINTA Sd = roundToIntegralTiesToAway(Sn) 2455 return new FRIntAS(machInst, rd, rn); 2456 else if (type == 1) // FRINTA Dd = roundToIntegralTiesToAway(Dn) 2457 return new FRIntAD(machInst, rd, rn); 2458 break; 2459 case 0xe: 2460 if (type == 0) // FRINTX Sd = roundToIntegralExact(Sn) 2461 return new FRIntXS(machInst, rd, rn); 2462 else if (type == 1) // FRINTX Dd = roundToIntegralExact(Dn) 2463 return new FRIntXD(machInst, rd, rn); 2464 break; 2465 case 0xf: 2466 if (type == 0) // FRINTI Sd = roundToIntegral(Sn) 2467 return new FRIntIS(machInst, rd, rn); 2468 else if (type == 1) // FRINTI Dd = roundToIntegral(Dn) 2469 return new FRIntID(machInst, rd, rn); 2470 break; 2471 default: 2472 return new Unknown64(machInst); 2473 } 2474 return new Unknown64(machInst); 2475 } else if (bits(machInst, 15) == 1) { 2476 return new Unknown64(machInst); 2477 } else { 2478 if (bits(machInst, 29)) 2479 return new Unknown64(machInst); 2480 uint8_t rmode = bits(machInst, 20, 19); 2481 uint8_t switchVal1 = bits(machInst, 18, 16); 2482 uint8_t switchVal2 = (type << 1) | bits(machInst, 31); 2483 // 30:24=0011110, 21=1, 15:10=000000 2484 switch (switchVal1) { 2485 case 0x0: 2486 switch ((switchVal2 << 2) | rmode) { 2487 case 0x0: //FCVTNS Wd = convertToIntExactTiesToEven(Sn) 2488 return new FcvtFpSIntWSN(machInst, rd, rn); 2489 case 0x1: //FCVTPS Wd = convertToIntExactTowardPlusInf(Sn) 2490 return new FcvtFpSIntWSP(machInst, rd, rn); 2491 case 0x2: //FCVTMS Wd = convertToIntExactTowardMinusInf(Sn) 2492 return new FcvtFpSIntWSM(machInst, rd, rn); 2493 case 0x3: //FCVTZS Wd = convertToIntExactTowardZero(Sn) 2494 return new FcvtFpSIntWSZ(machInst, rd, rn); 2495 case 0x4: //FCVTNS Xd = convertToIntExactTiesToEven(Sn) 2496 return new FcvtFpSIntXSN(machInst, rd, rn); 2497 case 0x5: //FCVTPS Xd = convertToIntExactTowardPlusInf(Sn) 2498 return new FcvtFpSIntXSP(machInst, rd, rn); 2499 case 0x6: //FCVTMS Xd = convertToIntExactTowardMinusInf(Sn) 2500 return new FcvtFpSIntXSM(machInst, rd, rn); 2501 case 0x7: //FCVTZS Xd = convertToIntExactTowardZero(Sn) 2502 return new FcvtFpSIntXSZ(machInst, rd, rn); 2503 case 0x8: //FCVTNS Wd = convertToIntExactTiesToEven(Dn) 2504 return new FcvtFpSIntWDN(machInst, rd, rn); 2505 case 0x9: //FCVTPS Wd = convertToIntExactTowardPlusInf(Dn) 2506 return new FcvtFpSIntWDP(machInst, rd, rn); 2507 case 0xA: //FCVTMS Wd = convertToIntExactTowardMinusInf(Dn) 2508 return new FcvtFpSIntWDM(machInst, rd, rn); 2509 case 0xB: //FCVTZS Wd = convertToIntExactTowardZero(Dn) 2510 return new FcvtFpSIntWDZ(machInst, rd, rn); 2511 case 0xC: //FCVTNS Xd = convertToIntExactTiesToEven(Dn) 2512 return new FcvtFpSIntXDN(machInst, rd, rn); 2513 case 0xD: //FCVTPS Xd = convertToIntExactTowardPlusInf(Dn) 2514 return new FcvtFpSIntXDP(machInst, rd, rn); 2515 case 0xE: //FCVTMS Xd = convertToIntExactTowardMinusInf(Dn) 2516 return new FcvtFpSIntXDM(machInst, rd, rn); 2517 case 0xF: //FCVTZS Xd = convertToIntExactTowardZero(Dn) 2518 return new FcvtFpSIntXDZ(machInst, rd, rn); 2519 default: 2520 return new Unknown64(machInst); 2521 } 2522 case 0x1: 2523 switch ((switchVal2 << 2) | rmode) { 2524 case 0x0: //FCVTNU Wd = convertToIntExactTiesToEven(Sn) 2525 return new FcvtFpUIntWSN(machInst, rd, rn); 2526 case 0x1: //FCVTPU Wd = convertToIntExactTowardPlusInf(Sn) 2527 return new FcvtFpUIntWSP(machInst, rd, rn); 2528 case 0x2: //FCVTMU Wd = convertToIntExactTowardMinusInf(Sn) 2529 return new FcvtFpUIntWSM(machInst, rd, rn); 2530 case 0x3: //FCVTZU Wd = convertToIntExactTowardZero(Sn) 2531 return new FcvtFpUIntWSZ(machInst, rd, rn); 2532 case 0x4: //FCVTNU Xd = convertToIntExactTiesToEven(Sn) 2533 return new FcvtFpUIntXSN(machInst, rd, rn); 2534 case 0x5: //FCVTPU Xd = convertToIntExactTowardPlusInf(Sn) 2535 return new FcvtFpUIntXSP(machInst, rd, rn); 2536 case 0x6: //FCVTMU Xd = convertToIntExactTowardMinusInf(Sn) 2537 return new FcvtFpUIntXSM(machInst, rd, rn); 2538 case 0x7: //FCVTZU Xd = convertToIntExactTowardZero(Sn) 2539 return new FcvtFpUIntXSZ(machInst, rd, rn); 2540 case 0x8: //FCVTNU Wd = convertToIntExactTiesToEven(Dn) 2541 return new FcvtFpUIntWDN(machInst, rd, rn); 2542 case 0x9: //FCVTPU Wd = convertToIntExactTowardPlusInf(Dn) 2543 return new FcvtFpUIntWDP(machInst, rd, rn); 2544 case 0xA: //FCVTMU Wd = convertToIntExactTowardMinusInf(Dn) 2545 return new FcvtFpUIntWDM(machInst, rd, rn); 2546 case 0xB: //FCVTZU Wd = convertToIntExactTowardZero(Dn) 2547 return new FcvtFpUIntWDZ(machInst, rd, rn); 2548 case 0xC: //FCVTNU Xd = convertToIntExactTiesToEven(Dn) 2549 return new FcvtFpUIntXDN(machInst, rd, rn); 2550 case 0xD: //FCVTPU Xd = convertToIntExactTowardPlusInf(Dn) 2551 return new FcvtFpUIntXDP(machInst, rd, rn); 2552 case 0xE: //FCVTMU Xd = convertToIntExactTowardMinusInf(Dn) 2553 return new FcvtFpUIntXDM(machInst, rd, rn); 2554 case 0xF: //FCVTZU Xd = convertToIntExactTowardZero(Dn) 2555 return new FcvtFpUIntXDZ(machInst, rd, rn); 2556 default: 2557 return new Unknown64(machInst); 2558 } 2559 case 0x2: 2560 if (rmode != 0) 2561 return new Unknown64(machInst); 2562 switch (switchVal2) { 2563 case 0: // SCVTF Sd = convertFromInt(Wn) 2564 return new FcvtWSIntFpS(machInst, rd, rn); 2565 case 1: // SCVTF Sd = convertFromInt(Xn) 2566 return new FcvtXSIntFpS(machInst, rd, rn); 2567 case 2: // SCVTF Dd = convertFromInt(Wn) 2568 return new FcvtWSIntFpD(machInst, rd, rn); 2569 case 3: // SCVTF Dd = convertFromInt(Xn) 2570 return new FcvtXSIntFpD(machInst, rd, rn); 2571 default: 2572 return new Unknown64(machInst); 2573 } 2574 case 0x3: 2575 switch (switchVal2) { 2576 case 0: // UCVTF Sd = convertFromInt(Wn) 2577 return new FcvtWUIntFpS(machInst, rd, rn); 2578 case 1: // UCVTF Sd = convertFromInt(Xn) 2579 return new FcvtXUIntFpS(machInst, rd, rn); 2580 case 2: // UCVTF Dd = convertFromInt(Wn) 2581 return new FcvtWUIntFpD(machInst, rd, rn); 2582 case 3: // UCVTF Dd = convertFromInt(Xn) 2583 return new FcvtXUIntFpD(machInst, rd, rn); 2584 default: 2585 return new Unknown64(machInst); 2586 } 2587 case 0x4: 2588 if (rmode != 0) 2589 return new Unknown64(machInst); 2590 switch (switchVal2) { 2591 case 0: // FCVTAS Wd = convertToIntExactTiesToAway(Sn) 2592 return new FcvtFpSIntWSA(machInst, rd, rn); 2593 case 1: // FCVTAS Xd = convertToIntExactTiesToAway(Sn) 2594 return new FcvtFpSIntXSA(machInst, rd, rn); 2595 case 2: // FCVTAS Wd = convertToIntExactTiesToAway(Dn) 2596 return new FcvtFpSIntWDA(machInst, rd, rn); 2597 case 3: // FCVTAS Wd = convertToIntExactTiesToAway(Dn) 2598 return new FcvtFpSIntXDA(machInst, rd, rn); 2599 default: 2600 return new Unknown64(machInst); 2601 } 2602 case 0x5: 2603 switch (switchVal2) { 2604 case 0: // FCVTAU Wd = convertToIntExactTiesToAway(Sn) 2605 return new FcvtFpUIntWSA(machInst, rd, rn); 2606 case 1: // FCVTAU Xd = convertToIntExactTiesToAway(Sn) 2607 return new FcvtFpUIntXSA(machInst, rd, rn); 2608 case 2: // FCVTAU Wd = convertToIntExactTiesToAway(Dn) 2609 return new FcvtFpUIntWDA(machInst, rd, rn); 2610 case 3: // FCVTAU Xd = convertToIntExactTiesToAway(Dn) 2611 return new FcvtFpUIntXDA(machInst, rd, rn); 2612 default: 2613 return new Unknown64(machInst); 2614 } 2615 case 0x06: 2616 switch (switchVal2) { 2617 case 0: // FMOV Wd = Sn 2618 if (rmode != 0) 2619 return new Unknown64(machInst); 2620 return new FmovRegCoreW(machInst, rd, rn); 2621 case 3: // FMOV Xd = Dn 2622 if (rmode != 0) 2623 return new Unknown64(machInst); 2624 return new FmovRegCoreX(machInst, rd, rn); 2625 case 5: // FMOV Xd = Vn<127:64> 2626 if (rmode != 1) 2627 return new Unknown64(machInst); 2628 return new FmovURegCoreX(machInst, rd, rn); 2629 default: 2630 return new Unknown64(machInst); 2631 } 2632 break; 2633 case 0x07: 2634 switch (switchVal2) { 2635 case 0: // FMOV Sd = Wn 2636 if (rmode != 0) 2637 return new Unknown64(machInst); 2638 return new FmovCoreRegW(machInst, rd, rn); 2639 case 3: // FMOV Xd = Dn 2640 if (rmode != 0) 2641 return new Unknown64(machInst); 2642 return new FmovCoreRegX(machInst, rd, rn); 2643 case 5: // FMOV Xd = Vn<127:64> 2644 if (rmode != 1) 2645 return new Unknown64(machInst); 2646 return new FmovUCoreRegX(machInst, rd, rn); 2647 default: 2648 return new Unknown64(machInst); 2649 } 2650 break; 2651 default: // Warning! missing cases in switch statement above, that still need to be added 2652 return new Unknown64(machInst); 2653 } 2654 } 2655 M5_UNREACHABLE; 2656 case 0x1: 2657 { 2658 if (bits(machInst, 31) || 2659 bits(machInst, 29) || 2660 bits(machInst, 23)) { 2661 return new Unknown64(machInst); 2662 } 2663 IntRegIndex rm = (IntRegIndex)(uint32_t) bits(machInst, 20, 16); 2664 IntRegIndex rn = (IntRegIndex)(uint32_t) bits(machInst, 9, 5); 2665 uint8_t imm = (IntRegIndex)(uint32_t) bits(machInst, 3, 0); 2666 ConditionCode cond = 2667 (ConditionCode)(uint8_t)(bits(machInst, 15, 12)); 2668 uint8_t switchVal = (bits(machInst, 4) << 0) | 2669 (bits(machInst, 22) << 1); 2670 // 31:23=000111100, 21=1, 11:10=01 2671 switch (switchVal) { 2672 case 0x0: 2673 // FCCMP flags = if cond the compareQuiet(Sn,Sm) else #nzcv 2674 return new FCCmpRegS(machInst, rn, rm, cond, imm); 2675 case 0x1: 2676 // FCCMP flags = if cond then compareSignaling(Sn,Sm) 2677 // else #nzcv 2678 return new FCCmpERegS(machInst, rn, rm, cond, imm); 2679 case 0x2: 2680 // FCCMP flags = if cond then compareQuiet(Dn,Dm) else #nzcv 2681 return new FCCmpRegD(machInst, rn, rm, cond, imm); 2682 case 0x3: 2683 // FCCMP flags = if cond then compareSignaling(Dn,Dm) 2684 // else #nzcv 2685 return new FCCmpERegD(machInst, rn, rm, cond, imm); 2686 default: 2687 return new Unknown64(machInst); 2688 } 2689 } 2690 case 0x2: 2691 { 2692 if (bits(machInst, 31) || 2693 bits(machInst, 29) || 2694 bits(machInst, 23)) { 2695 return new Unknown64(machInst); 2696 } 2697 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2698 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2699 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2700 uint8_t switchVal = (bits(machInst, 15, 12) << 0) | 2701 (bits(machInst, 22) << 4); 2702 switch (switchVal) { 2703 case 0x00: // FMUL Sd = Sn * Sm 2704 return new FMulS(machInst, rd, rn, rm); 2705 case 0x10: // FMUL Dd = Dn * Dm 2706 return new FMulD(machInst, rd, rn, rm); 2707 case 0x01: // FDIV Sd = Sn / Sm 2708 return new FDivS(machInst, rd, rn, rm); 2709 case 0x11: // FDIV Dd = Dn / Dm 2710 return new FDivD(machInst, rd, rn, rm); 2711 case 0x02: // FADD Sd = Sn + Sm 2712 return new FAddS(machInst, rd, rn, rm); 2713 case 0x12: // FADD Dd = Dn + Dm 2714 return new FAddD(machInst, rd, rn, rm); 2715 case 0x03: // FSUB Sd = Sn - Sm 2716 return new FSubS(machInst, rd, rn, rm); 2717 case 0x13: // FSUB Dd = Dn - Dm 2718 return new FSubD(machInst, rd, rn, rm); 2719 case 0x04: // FMAX Sd = max(Sn, Sm) 2720 return new FMaxS(machInst, rd, rn, rm); 2721 case 0x14: // FMAX Dd = max(Dn, Dm) 2722 return new FMaxD(machInst, rd, rn, rm); 2723 case 0x05: // FMIN Sd = min(Sn, Sm) 2724 return new FMinS(machInst, rd, rn, rm); 2725 case 0x15: // FMIN Dd = min(Dn, Dm) 2726 return new FMinD(machInst, rd, rn, rm); 2727 case 0x06: // FMAXNM Sd = maxNum(Sn, Sm) 2728 return new FMaxNMS(machInst, rd, rn, rm); 2729 case 0x16: // FMAXNM Dd = maxNum(Dn, Dm) 2730 return new FMaxNMD(machInst, rd, rn, rm); 2731 case 0x07: // FMINNM Sd = minNum(Sn, Sm) 2732 return new FMinNMS(machInst, rd, rn, rm); 2733 case 0x17: // FMINNM Dd = minNum(Dn, Dm) 2734 return new FMinNMD(machInst, rd, rn, rm); 2735 case 0x08: // FNMUL Sd = -(Sn * Sm) 2736 return new FNMulS(machInst, rd, rn, rm); 2737 case 0x18: // FNMUL Dd = -(Dn * Dm) 2738 return new FNMulD(machInst, rd, rn, rm); 2739 default: 2740 return new Unknown64(machInst); 2741 } 2742 } 2743 case 0x3: 2744 { 2745 if (bits(machInst, 31) || bits(machInst, 29)) 2746 return new Unknown64(machInst); 2747 uint8_t type = bits(machInst, 23, 22); 2748 IntRegIndex rd = (IntRegIndex)(uint32_t)bits(machInst, 4, 0); 2749 IntRegIndex rn = (IntRegIndex)(uint32_t)bits(machInst, 9, 5); 2750 IntRegIndex rm = (IntRegIndex)(uint32_t)bits(machInst, 20, 16); 2751 ConditionCode cond = 2752 (ConditionCode)(uint8_t)(bits(machInst, 15, 12)); 2753 if (type == 0) // FCSEL Sd = if cond then Sn else Sm 2754 return new FCSelS(machInst, rd, rn, rm, cond); 2755 else if (type == 1) // FCSEL Dd = if cond then Dn else Dm 2756 return new FCSelD(machInst, rd, rn, rm, cond); 2757 else 2758 return new Unknown64(machInst); 2759 } 2760 default: 2761 M5_UNREACHABLE; 2762 } 2763 } 2764 M5_UNREACHABLE; 2765 } 2766} 2767}}; 2768 2769output decoder {{ 2770namespace Aarch64 2771{ 2772 StaticInstPtr 2773 decodeAdvSIMDScalar(ExtMachInst machInst) 2774 { 2775 if (bits(machInst, 24) == 1) { 2776 if (bits(machInst, 10) == 0) { 2777 return decodeNeonScIndexedElem(machInst); 2778 } else if (bits(machInst, 23) == 0) { 2779 return decodeNeonScShiftByImm(machInst); 2780 } 2781 } else if (bits(machInst, 21) == 1) { 2782 if (bits(machInst, 10) == 1) { 2783 return decodeNeonSc3Same(machInst); 2784 } else if (bits(machInst, 11) == 0) { 2785 return decodeNeonSc3Diff(machInst); 2786 } else if (bits(machInst, 20, 17) == 0x0) { 2787 return decodeNeonSc2RegMisc(machInst); 2788 } else if (bits(machInst, 20, 17) == 0x4) { 2789 return decodeCryptoTwoRegSHA(machInst); 2790 } else if (bits(machInst, 20, 17) == 0x8) { 2791 return decodeNeonScPwise(machInst); 2792 } else { 2793 return new Unknown64(machInst); 2794 } 2795 } else if (bits(machInst, 23, 22) == 0 && 2796 bits(machInst, 15) == 0) { 2797 if (bits(machInst, 10) == 1) { 2798 return decodeNeonScCopy(machInst); 2799 } else { 2800 return decodeCryptoThreeRegSHA(machInst); 2801 } 2802 } else { 2803 return new Unknown64(machInst); 2804 } 2805 return new FailUnimplemented("Unhandled Case6", machInst); 2806 } 2807} 2808}}; 2809 2810output decoder {{ 2811namespace Aarch64 2812{ 2813 template <typename DecoderFeatures> 2814 StaticInstPtr 2815 decodeFpAdvSIMD(ExtMachInst machInst) 2816 { 2817 2818 if (bits(machInst, 28) == 0) { 2819 if (bits(machInst, 31) == 0) { 2820 return decodeAdvSIMD<DecoderFeatures>(machInst); 2821 } else { 2822 return new Unknown64(machInst); 2823 } 2824 } else if (bits(machInst, 30) == 0) { 2825 return decodeFp(machInst); 2826 } else if (bits(machInst, 31) == 0) { 2827 return decodeAdvSIMDScalar(machInst); 2828 } else { 2829 return new Unknown64(machInst); 2830 } 2831 } 2832} 2833}}; 2834 2835let {{ 2836 decoder_output =''' 2837namespace Aarch64 2838{''' 2839 for decoderFlavour, type_dict in decoders.iteritems(): 2840 decoder_output +=''' 2841template StaticInstPtr decodeFpAdvSIMD<%(df)sDecoder>(ExtMachInst machInst); 2842''' % { "df" : decoderFlavour } 2843 decoder_output +=''' 2844}''' 2845}}; 2846 2847output decoder {{ 2848namespace Aarch64 2849{ 2850 StaticInstPtr 2851 decodeGem5Ops(ExtMachInst machInst) 2852 { 2853 const uint32_t m5func = bits(machInst, 23, 16); 2854 switch (m5func) { 2855 case M5OP_ARM: return new Arm(machInst); 2856 case M5OP_QUIESCE: return new Quiesce(machInst); 2857 case M5OP_QUIESCE_NS: return new QuiesceNs64(machInst); 2858 case M5OP_QUIESCE_CYCLE: return new QuiesceCycles64(machInst); 2859 case M5OP_QUIESCE_TIME: return new QuiesceTime64(machInst); 2860 case M5OP_RPNS: return new Rpns64(machInst); 2861 case M5OP_WAKE_CPU: return new WakeCPU64(machInst); 2862 case M5OP_DEPRECATED1: return new Deprecated_ivlb(machInst); 2863 case M5OP_DEPRECATED2: return new Deprecated_ivle(machInst); 2864 case M5OP_DEPRECATED3: return new Deprecated_exit (machInst); 2865 case M5OP_EXIT: return new M5exit64(machInst); 2866 case M5OP_FAIL: return new M5fail64(machInst); 2867 case M5OP_LOAD_SYMBOL: return new Loadsymbol(machInst); 2868 case M5OP_INIT_PARAM: return new Initparam64(machInst); 2869 case M5OP_RESET_STATS: return new Resetstats64(machInst); 2870 case M5OP_DUMP_STATS: return new Dumpstats64(machInst); 2871 case M5OP_DUMP_RESET_STATS: return new Dumpresetstats64(machInst); 2872 case M5OP_CHECKPOINT: return new M5checkpoint64(machInst); 2873 case M5OP_WRITE_FILE: return new M5writefile64(machInst); 2874 case M5OP_READ_FILE: return new M5readfile64(machInst); 2875 case M5OP_DEBUG_BREAK: return new M5break(machInst); 2876 case M5OP_SWITCH_CPU: return new M5switchcpu(machInst); 2877 case M5OP_ADD_SYMBOL: return new M5addsymbol64(machInst); 2878 case M5OP_PANIC: return new M5panic(machInst); 2879 case M5OP_WORK_BEGIN: return new M5workbegin64(machInst); 2880 case M5OP_WORK_END: return new M5workend64(machInst); 2881 default: return new Unknown64(machInst); 2882 } 2883 } 2884} 2885}}; 2886 2887def format Aarch64() {{ 2888 decode_block = ''' 2889 { 2890 using namespace Aarch64; 2891 if (bits(machInst, 27) == 0x0) { 2892 if (bits(machInst, 28) == 0x0) { 2893 if (bits(machInst, 26, 25) != 0x2) { 2894 return new Unknown64(machInst); 2895 } 2896 if (bits(machInst, 31) == 0x0) { 2897 switch (bits(machInst, 30, 29)) { 2898 case 0x0: 2899 case 0x1: 2900 case 0x2: 2901 return decodeSveInt(machInst); 2902 case 0x3: 2903 return decodeSveFp(machInst); 2904 } 2905 } else { 2906 return decodeSveMem(machInst); 2907 } 2908 } else if (bits(machInst, 26) == 0) 2909 // bit 28:26=100 2910 return decodeDataProcImm(machInst); 2911 else 2912 // bit 28:26=101 2913 return decodeBranchExcSys(machInst); 2914 } else if (bits(machInst, 25) == 0) { 2915 // bit 27=1, 25=0 2916 return decodeLoadsStores(machInst); 2917 } else if (bits(machInst, 26) == 0) { 2918 // bit 27:25=101 2919 return decodeDataProcReg(machInst); 2920 } else if (bits(machInst, 24) == 1 && 2921 bits(machInst, 31, 28) == 0xF) { 2922 return decodeGem5Ops(machInst); 2923 } else { 2924 // bit 27:25=111 2925 switch(decoderFlavour){ 2926 default: 2927 return decodeFpAdvSIMD<GenericDecoder>(machInst); 2928 } 2929 } 2930 } 2931 ''' 2932}}; 2933