1/* 2 * Copyright (c) 2017-2019 ARM Limited 3 * All rights reserved 4 * 5 * The license below extends only to copyright in the software and shall 6 * not be construed as granting a license to any other intellectual 7 * property including but not limited to intellectual property relating 8 * to a hardware implementation of the functionality of the software 9 * licensed hereunder. You may use the software subject to the license 10 * terms below provided that you ensure that this notice is replicated 11 * unmodified and in its entirety in all distributions of the software, 12 * modified or unmodified, in source code or in binary form. 13 * 14 * Redistribution and use in source and binary forms, with or without 15 * modification, are permitted provided that the following conditions are 16 * met: redistributions of source code must retain the above copyright 17 * notice, this list of conditions and the following disclaimer; 18 * redistributions in binary form must reproduce the above copyright 19 * notice, this list of conditions and the following disclaimer in the 20 * documentation and/or other materials provided with the distribution; 21 * neither the name of the copyright holders nor the names of its 22 * contributors may be used to endorse or promote products derived from 23 * this software without specific prior written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 26 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 27 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 28 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 29 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 30 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 31 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 35 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 36 * 37 * Authors: Giacomo Gabrielli 38 */ 39 40#ifndef __ARCH_ARM_INSTS_SVE_HH__ 41#define __ARCH_ARM_INSTS_SVE_HH__ 42 43#include "arch/arm/insts/static_inst.hh" 44 45namespace ArmISA { 46 47enum class SvePredType { 48 NONE, 49 MERGE, 50 ZERO, 51 SELECT 52}; 53 54/// Returns the specifier for the predication type `pt` as a string. 55const char* svePredTypeToStr(SvePredType pt); 56 57/// Index generation instruction, immediate operands 58class SveIndexIIOp : public ArmStaticInst { 59 protected: 60 IntRegIndex dest; 61 int8_t imm1; 62 int8_t imm2; 63 64 SveIndexIIOp(const char* mnem, ExtMachInst _machInst, 65 OpClass __opClass, IntRegIndex _dest, 66 int8_t _imm1, int8_t _imm2) : 67 ArmStaticInst(mnem, _machInst, __opClass), 68 dest(_dest), imm1(_imm1), imm2(_imm2) 69 {} 70 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 71}; 72 73class SveIndexIROp : public ArmStaticInst { 74 protected: 75 IntRegIndex dest; 76 int8_t imm1; 77 IntRegIndex op2; 78 79 SveIndexIROp(const char* mnem, ExtMachInst _machInst, 80 OpClass __opClass, IntRegIndex _dest, 81 int8_t _imm1, IntRegIndex _op2) : 82 ArmStaticInst(mnem, _machInst, __opClass), 83 dest(_dest), imm1(_imm1), op2(_op2) 84 {} 85 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 86}; 87 88class SveIndexRIOp : public ArmStaticInst { 89 protected: 90 IntRegIndex dest; 91 IntRegIndex op1; 92 int8_t imm2; 93 94 SveIndexRIOp(const char* mnem, ExtMachInst _machInst, 95 OpClass __opClass, IntRegIndex _dest, 96 IntRegIndex _op1, int8_t _imm2) : 97 ArmStaticInst(mnem, _machInst, __opClass), 98 dest(_dest), op1(_op1), imm2(_imm2) 99 {} 100 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 101}; 102 103class SveIndexRROp : public ArmStaticInst { 104 protected: 105 IntRegIndex dest; 106 IntRegIndex op1; 107 IntRegIndex op2; 108 109 SveIndexRROp(const char* mnem, ExtMachInst _machInst, 110 OpClass __opClass, IntRegIndex _dest, 111 IntRegIndex _op1, IntRegIndex _op2) : 112 ArmStaticInst(mnem, _machInst, __opClass), 113 dest(_dest), op1(_op1), op2(_op2) 114 {} 115 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 116}; 117 118// Predicate count SVE instruction. 119class SvePredCountOp : public ArmStaticInst { 120 protected: 121 IntRegIndex dest; 122 IntRegIndex gp; 123 bool srcIs32b; 124 bool destIsVec; 125 126 SvePredCountOp(const char* mnem, ExtMachInst _machInst, 127 OpClass __opClass, IntRegIndex _dest, IntRegIndex _gp, 128 bool _srcIs32b = false, bool _destIsVec = false) : 129 ArmStaticInst(mnem, _machInst, __opClass), 130 dest(_dest), gp(_gp), 131 srcIs32b(_srcIs32b), destIsVec(_destIsVec) 132 {} 133 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 134}; 135 136// Predicate count SVE instruction (predicated). 137class SvePredCountPredOp : public ArmStaticInst { 138 protected: 139 IntRegIndex dest; 140 IntRegIndex op1; 141 IntRegIndex gp; 142 143 SvePredCountPredOp(const char* mnem, ExtMachInst _machInst, 144 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 145 IntRegIndex _gp) : 146 ArmStaticInst(mnem, _machInst, __opClass), 147 dest(_dest), op1(_op1), gp(_gp) 148 {} 149 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 150}; 151 152/// While predicate generation SVE instruction. 153class SveWhileOp : public ArmStaticInst { 154 protected: 155 IntRegIndex dest, op1, op2; 156 bool srcIs32b; 157 158 SveWhileOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 159 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 160 bool _srcIs32b) : 161 ArmStaticInst(mnem, _machInst, __opClass), 162 dest(_dest), op1(_op1), op2(_op2), srcIs32b(_srcIs32b) 163 {} 164 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 165}; 166 167/// Compare and terminate loop SVE instruction. 168class SveCompTermOp : public ArmStaticInst { 169 protected: 170 IntRegIndex op1, op2; 171 172 SveCompTermOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 173 IntRegIndex _op1, IntRegIndex _op2) : 174 ArmStaticInst(mnem, _machInst, __opClass), 175 op1(_op1), op2(_op2) 176 {} 177 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 178}; 179 180/// Unary, constructive, predicated (merging) SVE instruction. 181class SveUnaryPredOp : public ArmStaticInst { 182 protected: 183 IntRegIndex dest, op1, gp; 184 185 SveUnaryPredOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 186 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _gp) : 187 ArmStaticInst(mnem, _machInst, __opClass), 188 dest(_dest), op1(_op1), gp(_gp) 189 {} 190 191 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 192}; 193 194/// Unary, constructive, unpredicated SVE instruction. 195class SveUnaryUnpredOp : public ArmStaticInst { 196 protected: 197 IntRegIndex dest, op1; 198 199 SveUnaryUnpredOp(const char* mnem, ExtMachInst _machInst, 200 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1) : 201 ArmStaticInst(mnem, _machInst, __opClass), 202 dest(_dest), op1(_op1) 203 {} 204 205 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 206}; 207 208/// Unary with wide immediate, constructive, unpredicated SVE instruction. 209class SveUnaryWideImmUnpredOp : public ArmStaticInst { 210 protected: 211 IntRegIndex dest; 212 uint64_t imm; 213 214 SveUnaryWideImmUnpredOp(const char* mnem, ExtMachInst _machInst, 215 OpClass __opClass, IntRegIndex _dest, 216 uint64_t _imm) : 217 ArmStaticInst(mnem, _machInst, __opClass), 218 dest(_dest), imm(_imm) 219 {} 220 221 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 222}; 223 224/// Unary with wide immediate, constructive, predicated SVE instruction. 225class SveUnaryWideImmPredOp : public ArmStaticInst { 226 protected: 227 IntRegIndex dest; 228 uint64_t imm; 229 IntRegIndex gp; 230 231 bool isMerging; 232 233 SveUnaryWideImmPredOp(const char* mnem, ExtMachInst _machInst, 234 OpClass __opClass, IntRegIndex _dest, 235 uint64_t _imm, IntRegIndex _gp, bool _isMerging) : 236 ArmStaticInst(mnem, _machInst, __opClass), 237 dest(_dest), imm(_imm), gp(_gp), isMerging(_isMerging) 238 {} 239 240 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 241}; 242 243/// Binary with immediate, destructive, unpredicated SVE instruction. 244class SveBinImmUnpredConstrOp : public ArmStaticInst { 245 protected: 246 IntRegIndex dest, op1; 247 uint64_t imm; 248 249 SveBinImmUnpredConstrOp(const char* mnem, ExtMachInst _machInst, 250 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 251 uint64_t _imm) : 252 ArmStaticInst(mnem, _machInst, __opClass), 253 dest(_dest), op1(_op1), imm(_imm) 254 {} 255 256 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 257}; 258 259/// Binary with immediate, destructive, predicated (merging) SVE instruction. 260class SveBinImmPredOp : public ArmStaticInst { 261 protected: 262 IntRegIndex dest, gp; 263 uint64_t imm; 264 265 SveBinImmPredOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 266 IntRegIndex _dest, uint64_t _imm, IntRegIndex _gp) : 267 ArmStaticInst(mnem, _machInst, __opClass), 268 dest(_dest), gp(_gp), imm(_imm) 269 {} 270 271 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 272}; 273 274/// Binary with wide immediate, destructive, unpredicated SVE instruction. 275class SveBinWideImmUnpredOp : public ArmStaticInst { 276 protected: 277 IntRegIndex dest; 278 uint64_t imm; 279 280 SveBinWideImmUnpredOp(const char* mnem, ExtMachInst _machInst, 281 OpClass __opClass, IntRegIndex _dest, 282 uint64_t _imm) : 283 ArmStaticInst(mnem, _machInst, __opClass), 284 dest(_dest), imm(_imm) 285 {} 286 287 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 288}; 289 290/// Binary, destructive, predicated (merging) SVE instruction. 291class SveBinDestrPredOp : public ArmStaticInst { 292 protected: 293 IntRegIndex dest, op2, gp; 294 295 SveBinDestrPredOp(const char* mnem, ExtMachInst _machInst, 296 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op2, 297 IntRegIndex _gp) : 298 ArmStaticInst(mnem, _machInst, __opClass), 299 dest(_dest), op2(_op2), gp(_gp) 300 {} 301 302 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 303}; 304 305/// Binary, constructive, predicated SVE instruction. 306class SveBinConstrPredOp : public ArmStaticInst { 307 protected: 308 IntRegIndex dest, op1, op2, gp; 309 SvePredType predType; 310 311 SveBinConstrPredOp(const char* mnem, ExtMachInst _machInst, 312 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 313 IntRegIndex _op2, IntRegIndex _gp, 314 SvePredType _predType) : 315 ArmStaticInst(mnem, _machInst, __opClass), 316 dest(_dest), op1(_op1), op2(_op2), gp(_gp), predType(_predType) 317 {} 318 319 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 320}; 321 322/// Binary, unpredicated SVE instruction with indexed operand 323class SveBinUnpredOp : public ArmStaticInst { 324 protected: 325 IntRegIndex dest, op1, op2; 326 327 SveBinUnpredOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 328 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2) : 329 ArmStaticInst(mnem, _machInst, __opClass), 330 dest(_dest), op1(_op1), op2(_op2) 331 {} 332 333 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 334}; 335 336/// Binary, unpredicated SVE instruction 337class SveBinIdxUnpredOp : public ArmStaticInst { 338 protected: 339 IntRegIndex dest, op1, op2; 340 uint8_t index; 341 342 SveBinIdxUnpredOp(const char* mnem, ExtMachInst _machInst, 343 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 344 IntRegIndex _op2, uint8_t _index) : 345 ArmStaticInst(mnem, _machInst, __opClass), 346 dest(_dest), op1(_op1), op2(_op2), index(_index) 347 {} 348 349 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 350}; 351 352/// Predicate logical instruction. 353class SvePredLogicalOp : public ArmStaticInst { 354 protected: 355 IntRegIndex dest, op1, op2, gp; 356 bool isSel; 357 358 SvePredLogicalOp(const char* mnem, ExtMachInst _machInst, 359 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 360 IntRegIndex _op2, IntRegIndex _gp, bool _isSel = false) : 361 ArmStaticInst(mnem, _machInst, __opClass), 362 dest(_dest), op1(_op1), op2(_op2), gp(_gp), isSel(_isSel) 363 {} 364 365 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 366}; 367 368/// Predicate binary permute instruction. 369class SvePredBinPermOp : public ArmStaticInst { 370 protected: 371 IntRegIndex dest, op1, op2; 372 373 SvePredBinPermOp(const char* mnem, ExtMachInst _machInst, 374 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 375 IntRegIndex _op2) : 376 ArmStaticInst(mnem, _machInst, __opClass), 377 dest(_dest), op1(_op1), op2(_op2) 378 {} 379 380 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 381}; 382 383/// SVE compare instructions, predicated (zeroing). 384class SveCmpOp : public ArmStaticInst { 385 protected: 386 IntRegIndex dest, gp, op1, op2; 387 388 SveCmpOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 389 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 390 IntRegIndex _gp) : 391 ArmStaticInst(mnem, _machInst, __opClass), 392 dest(_dest), gp(_gp), op1(_op1), op2(_op2) 393 {} 394 395 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 396}; 397 398/// SVE compare-with-immediate instructions, predicated (zeroing). 399class SveCmpImmOp : public ArmStaticInst { 400 protected: 401 IntRegIndex dest, gp, op1; 402 uint64_t imm; 403 404 SveCmpImmOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 405 IntRegIndex _dest, IntRegIndex _op1, uint64_t _imm, 406 IntRegIndex _gp) : 407 ArmStaticInst(mnem, _machInst, __opClass), 408 dest(_dest), gp(_gp), op1(_op1), imm(_imm) 409 {} 410 411 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 412}; 413 414/// Ternary, destructive, predicated (merging) SVE instruction. 415class SveTerPredOp : public ArmStaticInst { 416 protected: 417 IntRegIndex dest, op1, op2, gp; 418 419 SveTerPredOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 420 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 421 IntRegIndex _gp) : 422 ArmStaticInst(mnem, _machInst, __opClass), 423 dest(_dest), op1(_op1), op2(_op2), gp(_gp) 424 {} 425 426 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 427}; 428 429/// Ternary with immediate, destructive, unpredicated SVE instruction. 430class SveTerImmUnpredOp : public ArmStaticInst { 431 protected: 432 IntRegIndex dest, op2; 433 uint64_t imm; 434 435 SveTerImmUnpredOp(const char* mnem, ExtMachInst _machInst, 436 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op2, 437 uint64_t _imm) : 438 ArmStaticInst(mnem, _machInst, __opClass), 439 dest(_dest), op2(_op2), imm(_imm) 440 {} 441 442 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 443}; 444 445/// SVE reductions. 446class SveReducOp : public ArmStaticInst { 447 protected: 448 IntRegIndex dest, op1, gp; 449 450 SveReducOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 451 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _gp) : 452 ArmStaticInst(mnem, _machInst, __opClass), 453 dest(_dest), op1(_op1), gp(_gp) 454 {} 455 456 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 457}; 458 459/// SVE ordered reductions. 460class SveOrdReducOp : public ArmStaticInst { 461 protected: 462 IntRegIndex dest, op1, gp; 463 464 SveOrdReducOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 465 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _gp) : 466 ArmStaticInst(mnem, _machInst, __opClass), 467 dest(_dest), op1(_op1), gp(_gp) 468 {} 469 470 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 471}; 472 473/// PTRUE, PTRUES. 474class SvePtrueOp : public ArmStaticInst { 475 protected: 476 IntRegIndex dest; 477 uint8_t imm; 478 479 SvePtrueOp(const char* mnem, ExtMachInst _machInst, 480 OpClass __opClass, IntRegIndex _dest, uint8_t _imm) : 481 ArmStaticInst(mnem, _machInst, __opClass), 482 dest(_dest), imm(_imm) 483 {} 484 485 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 486}; 487 488/// Integer compare SVE instruction. 489class SveIntCmpOp : public ArmStaticInst { 490 protected: 491 IntRegIndex dest; 492 IntRegIndex op1, op2; 493 IntRegIndex gp; 494 bool op2IsWide; 495 496 SveIntCmpOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 497 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2, 498 IntRegIndex _gp, bool _op2IsWide = false) : 499 ArmStaticInst(mnem, _machInst, __opClass), 500 dest(_dest), op1(_op1), op2(_op2), gp(_gp), op2IsWide(_op2IsWide) 501 {} 502 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 503}; 504 505/// Integer compare with immediate SVE instruction. 506class SveIntCmpImmOp : public ArmStaticInst { 507 protected: 508 IntRegIndex dest; 509 IntRegIndex op1; 510 int64_t imm; 511 IntRegIndex gp; 512 513 SveIntCmpImmOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 514 IntRegIndex _dest, IntRegIndex _op1, int64_t _imm, 515 IntRegIndex _gp) : 516 ArmStaticInst(mnem, _machInst, __opClass), 517 dest(_dest), op1(_op1), imm(_imm), gp(_gp) 518 {} 519 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 520}; 521 522/// ADR. 523class SveAdrOp : public ArmStaticInst { 524 public: 525 enum SveAdrOffsetFormat { 526 SveAdrOffsetPacked, 527 SveAdrOffsetUnpackedSigned, 528 SveAdrOffsetUnpackedUnsigned 529 }; 530 531 protected: 532 IntRegIndex dest, op1, op2; 533 uint8_t mult; 534 SveAdrOffsetFormat offsetFormat; 535 536 SveAdrOp(const char* mnem, ExtMachInst _machInst, 537 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 538 IntRegIndex _op2, uint8_t _mult, 539 SveAdrOffsetFormat _offsetFormat) : 540 ArmStaticInst(mnem, _machInst, __opClass), 541 dest(_dest), op1(_op1), op2(_op2), mult(_mult), 542 offsetFormat(_offsetFormat) 543 {} 544 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 545}; 546 547/// Element count SVE instruction. 548class SveElemCountOp : public ArmStaticInst { 549 protected: 550 IntRegIndex dest; 551 uint8_t pattern; 552 uint8_t imm; 553 bool dstIsVec; 554 bool dstIs32b; 555 uint8_t esize; 556 557 SveElemCountOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 558 IntRegIndex _dest, uint8_t _pattern, uint8_t _imm, 559 bool _dstIsVec, bool _dstIs32b) : 560 ArmStaticInst(mnem, _machInst, __opClass), 561 dest(_dest), pattern(_pattern), imm(_imm), dstIsVec(_dstIsVec), 562 dstIs32b(_dstIs32b) 563 {} 564 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 565}; 566 567/// Partition break SVE instruction. 568class SvePartBrkOp : public ArmStaticInst { 569 protected: 570 IntRegIndex dest; 571 IntRegIndex gp; 572 IntRegIndex op1; 573 bool isMerging; 574 575 SvePartBrkOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 576 IntRegIndex _dest, IntRegIndex _gp, IntRegIndex _op1, 577 bool _isMerging) : 578 ArmStaticInst(mnem, _machInst, __opClass), 579 dest(_dest), gp(_gp), op1(_op1), isMerging(_isMerging) 580 {} 581 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 582}; 583 584/// Partition break with propagation SVE instruction. 585class SvePartBrkPropOp : public ArmStaticInst { 586 protected: 587 IntRegIndex dest; 588 IntRegIndex op1; 589 IntRegIndex op2; 590 IntRegIndex gp; 591 592 SvePartBrkPropOp(const char* mnem, ExtMachInst _machInst, 593 OpClass __opClass, IntRegIndex _dest, 594 IntRegIndex _op1, IntRegIndex _op2, IntRegIndex _gp) : 595 ArmStaticInst(mnem, _machInst, __opClass), 596 dest(_dest), op1(_op1), op2(_op2), gp(_gp) 597 {} 598 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 599}; 600 601/// Scalar element select SVE instruction. 602class SveSelectOp : public ArmStaticInst { 603 protected: 604 IntRegIndex dest; 605 IntRegIndex op1; 606 IntRegIndex gp; 607 bool conditional; 608 bool scalar; 609 bool simdFp; 610 size_t scalar_width; 611 612 SveSelectOp(const char* mnem, ExtMachInst _machInst, 613 OpClass __opClass, IntRegIndex _dest, 614 IntRegIndex _op1, IntRegIndex _gp, 615 bool _conditional, bool _scalar, 616 bool _simdFp) : 617 ArmStaticInst(mnem, _machInst, __opClass), 618 dest(_dest), op1(_op1), gp(_gp), conditional(_conditional), 619 scalar(_scalar), simdFp(_simdFp) 620 {} 621 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 622}; 623 624/// SVE unary operation on predicate (predicated) 625class SveUnaryPredPredOp : public ArmStaticInst { 626 protected: 627 IntRegIndex dest; 628 IntRegIndex op1; 629 IntRegIndex gp; 630 631 SveUnaryPredPredOp(const char* mnem, ExtMachInst _machInst, 632 OpClass __opClass, IntRegIndex _dest, 633 IntRegIndex _op1, IntRegIndex _gp) : 634 ArmStaticInst(mnem, _machInst, __opClass), 635 dest(_dest), op1(_op1), gp(_gp) 636 {} 637 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 638}; 639 640/// SVE table lookup/permute using vector of element indices (TBL) 641class SveTblOp : public ArmStaticInst { 642 protected: 643 IntRegIndex dest; 644 IntRegIndex op1; 645 IntRegIndex op2; 646 647 SveTblOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 648 IntRegIndex _dest, IntRegIndex _op1, IntRegIndex _op2) : 649 ArmStaticInst(mnem, _machInst, __opClass), 650 dest(_dest), op1(_op1), op2(_op2) 651 {} 652 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 653}; 654 655/// SVE unpack and widen predicate 656class SveUnpackOp : public ArmStaticInst { 657 protected: 658 IntRegIndex dest; 659 IntRegIndex op1; 660 661 SveUnpackOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 662 IntRegIndex _dest, IntRegIndex _op1) : 663 ArmStaticInst(mnem, _machInst, __opClass), 664 dest(_dest), op1(_op1) 665 {} 666 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 667}; 668 669/// SVE predicate test 670class SvePredTestOp : public ArmStaticInst { 671 protected: 672 IntRegIndex op1; 673 IntRegIndex gp; 674 675 SvePredTestOp(const char* mnem, ExtMachInst _machInst, OpClass __opClass, 676 IntRegIndex _op1, IntRegIndex _gp) : 677 ArmStaticInst(mnem, _machInst, __opClass), 678 op1(_op1), gp(_gp) 679 {} 680 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 681}; 682 683/// SVE unary predicate instructions with implicit source operand 684class SvePredUnaryWImplicitSrcOp : public ArmStaticInst { 685 protected: 686 IntRegIndex dest; 687 688 SvePredUnaryWImplicitSrcOp(const char* mnem, ExtMachInst _machInst, 689 OpClass __opClass, IntRegIndex _dest) : 690 ArmStaticInst(mnem, _machInst, __opClass), 691 dest(_dest) 692 {} 693 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 694}; 695 696/// SVE unary predicate instructions, predicated, with implicit source operand 697class SvePredUnaryWImplicitSrcPredOp : public ArmStaticInst { 698 protected: 699 IntRegIndex dest; 700 IntRegIndex gp; 701 702 SvePredUnaryWImplicitSrcPredOp(const char* mnem, ExtMachInst _machInst, 703 OpClass __opClass, IntRegIndex _dest, 704 IntRegIndex _gp) : 705 ArmStaticInst(mnem, _machInst, __opClass), 706 dest(_dest), gp(_gp) 707 {} 708 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 709}; 710 711/// SVE unary predicate instructions with implicit destination operand 712class SvePredUnaryWImplicitDstOp : public ArmStaticInst { 713 protected: 714 IntRegIndex op1; 715 716 SvePredUnaryWImplicitDstOp(const char* mnem, ExtMachInst _machInst, 717 OpClass __opClass, IntRegIndex _op1) : 718 ArmStaticInst(mnem, _machInst, __opClass), 719 op1(_op1) 720 {} 721 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 722}; 723 724/// SVE unary predicate instructions with implicit destination operand 725class SveWImplicitSrcDstOp : public ArmStaticInst { 726 protected: 727 SveWImplicitSrcDstOp(const char* mnem, ExtMachInst _machInst, 728 OpClass __opClass) : 729 ArmStaticInst(mnem, _machInst, __opClass) 730 {} 731 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 732}; 733 734/// SVE vector - immediate binary operation 735class SveBinImmUnpredDestrOp : public ArmStaticInst { 736 protected: 737 IntRegIndex dest; 738 IntRegIndex op1; 739 uint64_t imm; 740 741 SveBinImmUnpredDestrOp(const char* mnem, ExtMachInst _machInst, 742 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 743 uint64_t _imm) : 744 ArmStaticInst(mnem, _machInst, __opClass), 745 dest(_dest), op1(_op1), imm(_imm) 746 {} 747 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 748}; 749 750/// Binary with immediate index, destructive, unpredicated SVE instruction. 751class SveBinImmIdxUnpredOp : public ArmStaticInst { 752 protected: 753 IntRegIndex dest, op1; 754 uint64_t imm; 755 756 SveBinImmIdxUnpredOp(const char* mnem, ExtMachInst _machInst, 757 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 758 uint64_t _imm) : 759 ArmStaticInst(mnem, _machInst, __opClass), 760 dest(_dest), op1(_op1), imm(_imm) 761 {} 762 763 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 764}; 765 766/// Unary unpredicated scalar to vector instruction 767class SveUnarySca2VecUnpredOp : public ArmStaticInst { 768 protected: 769 IntRegIndex dest, op1; 770 bool simdFp; 771 772 SveUnarySca2VecUnpredOp(const char* mnem, ExtMachInst _machInst, 773 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 774 bool _simdFp) : 775 ArmStaticInst(mnem, _machInst, __opClass), 776 dest(_dest), op1(_op1), simdFp(_simdFp) 777 {} 778 779 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 780}; 781 782/// SVE dot product instruction (indexed) 783class SveDotProdIdxOp : public ArmStaticInst { 784 protected: 785 IntRegIndex dest, op1, op2; 786 uint64_t imm; 787 uint8_t esize; 788 789 public: 790 SveDotProdIdxOp(const char* mnem, ExtMachInst _machInst, 791 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 792 IntRegIndex _op2, uint64_t _imm) : 793 ArmStaticInst(mnem, _machInst, __opClass), 794 dest(_dest), op1(_op1), op2(_op2), imm(_imm) 795 {} 796 797 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 798}; 799 800/// SVE dot product instruction (vectors) 801class SveDotProdOp : public ArmStaticInst { 802 protected: 803 IntRegIndex dest, op1, op2; 804 uint8_t esize; 805 806 public: 807 SveDotProdOp(const char* mnem, ExtMachInst _machInst, 808 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 809 IntRegIndex _op2) : 810 ArmStaticInst(mnem, _machInst, __opClass), 811 dest(_dest), op1(_op1), op2(_op2) 812 {} 813 814 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 815}; 816 817/// SVE Complex Instructions (vectors) 818class SveComplexOp : public ArmStaticInst { 819 protected: 820 IntRegIndex dest, op1, op2, gp; 821 uint8_t rot; 822 823 public: 824 SveComplexOp(const char* mnem, ExtMachInst _machInst, 825 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 826 IntRegIndex _op2, IntRegIndex _gp, uint8_t _rot) : 827 ArmStaticInst(mnem, _machInst, __opClass), 828 dest(_dest), op1(_op1), op2(_op2), gp(_gp), rot(_rot) 829 {} 830 831 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 832}; 833 834/// SVE Complex Instructions (indexed) 835class SveComplexIdxOp : public ArmStaticInst { 836 protected: 837 IntRegIndex dest, op1, op2; 838 uint8_t rot, imm; 839 840 public: 841 SveComplexIdxOp(const char* mnem, ExtMachInst _machInst, 842 OpClass __opClass, IntRegIndex _dest, IntRegIndex _op1, 843 IntRegIndex _op2, uint8_t _rot, uint8_t _imm) : 844 ArmStaticInst(mnem, _machInst, __opClass), 845 dest(_dest), op1(_op1), op2(_op2), rot(_rot), imm(_imm) 846 {} 847 848 std::string generateDisassembly(Addr pc, const SymbolTable *symtab) const; 849}; 850 851 852/// Returns the symbolic name associated with pattern `imm` for PTRUE(S) 853/// instructions. 854std::string sveDisasmPredCountImm(uint8_t imm); 855 856/// Returns the actual number of elements active for PTRUE(S) instructions. 857/// @param imm 5-bit immediate encoding the predicate pattern. 858/// @param num_elems Current number of elements per vector (depending on 859/// current vector length and element size). 860unsigned int sveDecodePredCount(uint8_t imm, unsigned int num_elems); 861 862/// Expand 1-bit floating-point immediate to 0.5 or 1.0 (FADD, FSUB, FSUBR). 863/// @param imm 1-bit immediate. 864/// @param size Encoding of the vector element size. 865/// @return Encoding of the expanded value. 866uint64_t sveExpandFpImmAddSub(uint8_t imm, uint8_t size); 867 868/// Expand 1-bit floating-point immediate to 0.0 or 1.0 (FMAX, FMAXNM, FMIN, 869/// FMINNM). 870/// @param imm 1-bit immediate. 871/// @param size Encoding of the vector element size. 872/// @return Encoding of the expanded value. 873uint64_t sveExpandFpImmMaxMin(uint8_t imm, uint8_t size); 874 875/// Expand 1-bit floating-point immediate to 0.5 or 2.0 (FMUL). 876/// @param imm 1-bit immediate. 877/// @param size Encoding of the vector element size. 878/// @return Encoding of the expanded value. 879uint64_t sveExpandFpImmMul(uint8_t imm, uint8_t size); 880 881} // namespace ArmISA 882 883#endif // __ARCH_ARM_INSTS_SVE_HH__ 884