1//=-- SMEInstrFormats.td - AArch64 SME Instruction classes -*- tablegen -*--=// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8// 9// AArch64 Scalable Matrix Extension (SME) Instruction Class Definitions. 10// 11//===----------------------------------------------------------------------===// 12 13//===----------------------------------------------------------------------===// 14// SME Outer Products 15//===----------------------------------------------------------------------===// 16 17class sme_fp_outer_product_inst<bit S, bit sz, MatrixTileOperand za_ty, 18 ZPRRegOp zpr_ty, string mnemonic> 19 : I<(outs za_ty:$ZAda), 20 (ins PPR3bAny:$Pn, PPR3bAny:$Pm, zpr_ty:$Zn, zpr_ty:$Zm), 21 mnemonic, "\t$ZAda, $Pn/m, $Pm/m, $Zn, $Zm", 22 "", []>, 23 Sched<[]> { 24 bits<5> Zm; 25 bits<3> Pm; 26 bits<3> Pn; 27 bits<5> Zn; 28 let Inst{31-23} = 0b100000001; 29 let Inst{22} = sz; 30 let Inst{21} = 0b0; 31 let Inst{20-16} = Zm; 32 let Inst{15-13} = Pm; 33 let Inst{12-10} = Pn; 34 let Inst{9-5} = Zn; 35 let Inst{4} = S; 36 let Inst{3} = 0b0; 37} 38 39class sme_outer_product_fp32<bit S, string mnemonic> 40 : sme_fp_outer_product_inst<S, 0b0, TileOp32, ZPR32, mnemonic> { 41 bits<2> ZAda; 42 let Inst{1-0} = ZAda; 43 let Inst{2} = 0b0; 44} 45 46class sme_outer_product_fp64<bit S, string mnemonic> 47 : sme_fp_outer_product_inst<S, 0b1, TileOp64, ZPR64, mnemonic> { 48 bits<3> ZAda; 49 let Inst{2-0} = ZAda; 50} 51 52class sme_int_outer_product_inst<bit u0, bit u1, bit S, bit sz, 53 MatrixTileOperand za_ty, ZPRRegOp zpr_ty, 54 string mnemonic> 55 : I<(outs za_ty:$ZAda), 56 (ins PPR3bAny:$Pn, PPR3bAny:$Pm, zpr_ty:$Zn, zpr_ty:$Zm), 57 mnemonic, "\t$ZAda, $Pn/m, $Pm/m, $Zn, $Zm", 58 "", []>, 59 Sched<[]> { 60 bits<5> Zm; 61 bits<3> Pm; 62 bits<3> Pn; 63 bits<5> Zn; 64 let Inst{31-25} = 0b1010000; 65 let Inst{24} = u0; 66 let Inst{23} = 0b1; 67 let Inst{22} = sz; 68 let Inst{21} = u1; 69 let Inst{20-16} = Zm; 70 let Inst{15-13} = Pm; 71 let Inst{12-10} = Pn; 72 let Inst{9-5} = Zn; 73 let Inst{4} = S; 74 let Inst{3} = 0b0; 75} 76 77class sme_int_outer_product_i32<bits<3> opc, string mnemonic> 78 : sme_int_outer_product_inst<opc{2}, opc{1}, opc{0}, 0b0, TileOp32, ZPR8, 79 mnemonic> { 80 bits<2> ZAda; 81 let Inst{1-0} = ZAda; 82 let Inst{2} = 0b0; 83} 84 85class sme_int_outer_product_i64<bits<3> opc, string mnemonic> 86 : sme_int_outer_product_inst<opc{2}, opc{1}, opc{0}, 0b1, TileOp64, ZPR16, 87 mnemonic> { 88 bits<3> ZAda; 89 let Inst{2-0} = ZAda; 90} 91 92class sme_outer_product_widening_inst<bit op, bit S, string mnemonic> 93 : I<(outs TileOp32:$ZAda), 94 (ins PPR3bAny:$Pn, PPR3bAny:$Pm, ZPR16:$Zn, ZPR16:$Zm), 95 mnemonic, "\t$ZAda, $Pn/m, $Pm/m, $Zn, $Zm", 96 "", []>, 97 Sched<[]> { 98 bits<5> Zm; 99 bits<3> Pm; 100 bits<3> Pn; 101 bits<5> Zn; 102 bits<2> ZAda; 103 let Inst{31-22} = 0b1000000110; 104 let Inst{21} = op; 105 let Inst{20-16} = Zm; 106 let Inst{15-13} = Pm; 107 let Inst{12-10} = Pn; 108 let Inst{9-5} = Zn; 109 let Inst{4} = S; 110 let Inst{3-2} = 0b00; 111 let Inst{1-0} = ZAda; 112} 113 114multiclass sme_bf16_outer_product<bit S, string mnemonic> { 115 def : sme_outer_product_widening_inst<0b0, S, mnemonic>; 116} 117 118multiclass sme_f16_outer_product<bit S, string mnemonic> { 119 def : sme_outer_product_widening_inst<0b1, S, mnemonic>; 120} 121 122//===----------------------------------------------------------------------===// 123// SME Add Vector to Tile 124//===----------------------------------------------------------------------===// 125 126class sme_add_vector_to_tile_inst<bit op, bit V, MatrixTileOperand tile_ty, 127 ZPRRegOp zpr_ty, string mnemonic> 128 : I<(outs tile_ty:$ZAda), 129 (ins PPR3bAny:$Pn, PPR3bAny:$Pm, zpr_ty:$Zn), 130 mnemonic, "\t$ZAda, $Pn/m, $Pm/m, $Zn", 131 "", []>, Sched<[]> { 132 bits<3> Pm; 133 bits<3> Pn; 134 bits<5> Zn; 135 let Inst{31-23} = 0b110000001; 136 let Inst{22} = op; 137 let Inst{21-17} = 0b01000; 138 let Inst{16} = V; 139 let Inst{15-13} = Pm; 140 let Inst{12-10} = Pn; 141 let Inst{9-5} = Zn; 142 let Inst{4-3} = 0b00; 143} 144 145class sme_add_vector_to_tile_u32<bit V, string mnemonic> 146 : sme_add_vector_to_tile_inst<0b0, V, TileOp32, ZPR32, mnemonic> { 147 bits<2> ZAda; 148 let Inst{2} = 0b0; 149 let Inst{1-0} = ZAda; 150} 151 152class sme_add_vector_to_tile_u64<bit V, string mnemonic> 153 : sme_add_vector_to_tile_inst<0b1, V, TileOp64, ZPR64, mnemonic> { 154 bits<3> ZAda; 155 let Inst{2-0} = ZAda; 156} 157 158//===----------------------------------------------------------------------===// 159// SME Contiguous Loads 160//===----------------------------------------------------------------------===// 161 162class sme_mem_ld_ss_base<bit Q, bit V, bits<2> msz, dag outs, dag ins, 163 string mnemonic, string argstr> 164 : I<outs, ins, mnemonic, argstr, "", []>, Sched<[]> { 165 bits<5> Rm; 166 bits<2> Rv; 167 bits<3> Pg; 168 bits<5> Rn; 169 let Inst{31-25} = 0b1110000; 170 let Inst{24} = Q; 171 let Inst{23-22} = msz; 172 let Inst{21} = 0b0; 173 let Inst{20-16} = Rm; 174 let Inst{15} = V; 175 let Inst{14-13} = Rv; 176 let Inst{12-10} = Pg; 177 let Inst{9-5} = Rn; 178 let Inst{4} = 0b0; 179 180 let mayLoad = 1; 181} 182 183class sme_mem_ld_ss_inst_BHSD<bits<2> msz, string mnemonic, 184 MatrixTileVectorOperand tile_ty, bit is_col, 185 Operand imm_ty, RegisterOperand gpr_ty> 186 : sme_mem_ld_ss_base< 187 0b0, is_col, msz, (outs tile_ty:$ZAt), 188 (ins MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, GPR64sp:$Rn, 189 gpr_ty:$Rm), 190 mnemonic, "\t\\{$ZAt[$Rv, $imm]\\}, $Pg/z, [$Rn, $Rm]">; 191 192class sme_mem_ld_ss_inst_Q<string mnemonic, MatrixTileVectorOperand tile_ty, 193 bit is_col> 194 : sme_mem_ld_ss_base< 195 0b1, is_col, 0b11, (outs tile_ty:$ZAt), 196 (ins MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, GPR64sp:$Rn, 197 GPR64shifted128:$Rm), 198 mnemonic, "\t\\{$ZAt[$Rv]\\}, $Pg/z, [$Rn, $Rm]">; 199 200multiclass sme_mem_ss_aliases_BHSD<string mnemonic, Instruction inst, 201 MatrixTileVectorOperand tile_ty, Operand imm_ty, 202 RegisterOperand gpr_ty, 203 string pg_suffix=""> { 204 def : InstAlias<mnemonic # "\t$ZAt[$Rv, $imm], $Pg" # pg_suffix # ", [$Rn, $Rm]", 205 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, GPR64sp:$Rn, gpr_ty:$Rm), 0>; 206 // Default XZR offset aliases 207 def : InstAlias<mnemonic # "\t\\{$ZAt[$Rv, $imm]\\}, $Pg" # pg_suffix # ", [$Rn]", 208 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, GPR64sp:$Rn, XZR), 1>; 209 def : InstAlias<mnemonic # "\t$ZAt[$Rv, $imm], $Pg" # pg_suffix # ", [$Rn]", 210 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, GPR64sp:$Rn, XZR), 0>; 211} 212 213multiclass sme_mem_ss_aliases_Q<string mnemonic, Instruction inst, 214 MatrixTileVectorOperand tile_ty, 215 string pg_suffix=""> { 216 def : InstAlias<mnemonic # "\t$ZAt[$Rv], $Pg" # pg_suffix # ", [$Rn, $Rm]", 217 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, GPR64sp:$Rn, GPR64shifted128:$Rm), 0>; 218 // Default XZR offset aliases 219 def : InstAlias<mnemonic # "\t\\{$ZAt[$Rv]\\}, $Pg" # pg_suffix # ", [$Rn]", 220 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, GPR64sp:$Rn, XZR), 2>; 221 def : InstAlias<mnemonic # "\t$ZAt[$Rv], $Pg" # pg_suffix # ", [$Rn]", 222 (inst tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, GPR64sp:$Rn, XZR), 0>; 223} 224 225multiclass sme_mem_ss_aliases<string mnemonic, string inst, bit is_col, 226 string pg_suffix=""> { 227 defm : sme_mem_ss_aliases_BHSD<mnemonic # "b", !cast<Instruction>(inst # _B), 228 !if(is_col, TileVectorOpV8, TileVectorOpH8), 229 imm0_15, GPR64shifted8, pg_suffix>; 230 defm : sme_mem_ss_aliases_BHSD<mnemonic # "h", !cast<Instruction>(inst # _H), 231 !if(is_col, TileVectorOpV16, TileVectorOpH16), 232 imm0_7, GPR64shifted16, pg_suffix>; 233 defm : sme_mem_ss_aliases_BHSD<mnemonic # "w", !cast<Instruction>(inst # _S), 234 !if(is_col, TileVectorOpV32, TileVectorOpH32), 235 imm0_3, GPR64shifted32, pg_suffix>; 236 defm : sme_mem_ss_aliases_BHSD<mnemonic # "d", !cast<Instruction>(inst # _D), 237 !if(is_col, TileVectorOpV64, TileVectorOpH64), 238 imm0_1, GPR64shifted64, pg_suffix>; 239 defm : sme_mem_ss_aliases_Q <mnemonic # "q", !cast<Instruction>(inst # _Q), 240 !if(is_col, TileVectorOpV128, TileVectorOpH128), 241 pg_suffix>; 242} 243 244multiclass sme_mem_ld_ss_aliases<string inst, bit is_col> { 245 defm NAME : sme_mem_ss_aliases<"ld1", inst, is_col, "/z">; 246} 247 248multiclass sme_mem_ld_v_ss<string mnemonic, bit is_col> { 249 def _B : sme_mem_ld_ss_inst_BHSD<0b00, mnemonic # "b", 250 !if(is_col, TileVectorOpV8, 251 TileVectorOpH8), 252 is_col, imm0_15, GPR64shifted8> { 253 bits<4> imm; 254 let Inst{3-0} = imm; 255 } 256 def _H : sme_mem_ld_ss_inst_BHSD<0b01, mnemonic # "h", 257 !if(is_col, TileVectorOpV16, 258 TileVectorOpH16), 259 is_col, imm0_7, GPR64shifted16> { 260 bits<1> ZAt; 261 bits<3> imm; 262 let Inst{3} = ZAt; 263 let Inst{2-0} = imm; 264 } 265 def _S : sme_mem_ld_ss_inst_BHSD<0b10, mnemonic # "w", 266 !if(is_col, TileVectorOpV32, 267 TileVectorOpH32), 268 is_col, imm0_3, GPR64shifted32> { 269 bits<2> ZAt; 270 bits<2> imm; 271 let Inst{3-2} = ZAt; 272 let Inst{1-0} = imm; 273 } 274 def _D : sme_mem_ld_ss_inst_BHSD<0b11, mnemonic # "d", 275 !if(is_col, TileVectorOpV64, 276 TileVectorOpH64), 277 is_col, imm0_1, GPR64shifted64> { 278 bits<3> ZAt; 279 bits<1> imm; 280 let Inst{3-1} = ZAt; 281 let Inst{0} = imm; 282 } 283 def _Q : sme_mem_ld_ss_inst_Q<mnemonic # "q", 284 !if(is_col, TileVectorOpV128, 285 TileVectorOpH128), 286 is_col> { 287 bits<4> ZAt; 288 let Inst{3-0} = ZAt; 289 } 290 291 defm : sme_mem_ld_ss_aliases<NAME, is_col>; 292} 293 294multiclass sme_mem_ld_ss<string mnemonic> { 295 defm _H : sme_mem_ld_v_ss<mnemonic, /*is_col=*/0b0>; 296 defm _V : sme_mem_ld_v_ss<mnemonic, /*is_col=*/0b1>; 297} 298 299//===----------------------------------------------------------------------===// 300// SME Contiguous Stores 301//===----------------------------------------------------------------------===// 302 303class sme_mem_st_ss_base<bit Q, bit V, bits<2> msz, dag ins, 304 string mnemonic, string argstr> 305 : I<(outs), ins, mnemonic, argstr, "", []>, Sched<[]> { 306 bits<5> Rm; 307 bits<2> Rv; 308 bits<3> Pg; 309 bits<5> Rn; 310 let Inst{31-25} = 0b1110000; 311 let Inst{24} = Q; 312 let Inst{23-22} = msz; 313 let Inst{21} = 0b1; 314 let Inst{20-16} = Rm; 315 let Inst{15} = V; 316 let Inst{14-13} = Rv; 317 let Inst{12-10} = Pg; 318 let Inst{9-5} = Rn; 319 let Inst{4} = 0b0; 320 321 let mayStore = 1; 322 let hasSideEffects = 1; 323} 324 325class sme_mem_st_ss_inst_BHSD<bits<2> msz, string mnemonic, 326 MatrixTileVectorOperand tile_ty, bit is_col, 327 Operand imm_ty, RegisterOperand gpr_ty> 328 : sme_mem_st_ss_base< 329 0b0, is_col, msz, 330 (ins tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, 331 GPR64sp:$Rn, gpr_ty:$Rm), 332 mnemonic, "\t\\{$ZAt[$Rv, $imm]\\}, $Pg, [$Rn, $Rm]">; 333 334class sme_mem_st_ss_inst_Q<string mnemonic, MatrixTileVectorOperand tile_ty, 335 bit is_col> 336 : sme_mem_st_ss_base< 337 0b1, is_col, 0b11, 338 (ins tile_ty:$ZAt, MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, 339 GPR64sp:$Rn, GPR64shifted128:$Rm), 340 mnemonic, "\t\\{$ZAt[$Rv]\\}, $Pg, [$Rn, $Rm]">; 341 342multiclass sme_mem_st_ss_aliases<string inst, bit is_col> { 343 defm NAME : sme_mem_ss_aliases<"st1", inst, is_col>; 344} 345 346multiclass sme_mem_st_v_ss<string mnemonic, bit is_col> { 347 def _B : sme_mem_st_ss_inst_BHSD<0b00, mnemonic # "b", 348 !if(is_col, TileVectorOpV8, 349 TileVectorOpH8), 350 is_col, imm0_15, GPR64shifted8> { 351 bits<4> imm; 352 let Inst{3-0} = imm; 353 } 354 def _H : sme_mem_st_ss_inst_BHSD<0b01, mnemonic # "h", 355 !if(is_col, TileVectorOpV16, 356 TileVectorOpH16), 357 is_col, imm0_7, GPR64shifted16> { 358 bits<1> ZAt; 359 bits<3> imm; 360 let Inst{3} = ZAt; 361 let Inst{2-0} = imm; 362 } 363 def _S : sme_mem_st_ss_inst_BHSD<0b10, mnemonic # "w", 364 !if(is_col, TileVectorOpV32, 365 TileVectorOpH32), 366 is_col, imm0_3, GPR64shifted32> { 367 bits<2> ZAt; 368 bits<2> imm; 369 let Inst{3-2} = ZAt; 370 let Inst{1-0} = imm; 371 } 372 def _D : sme_mem_st_ss_inst_BHSD<0b11, mnemonic # "d", 373 !if(is_col, TileVectorOpV64, 374 TileVectorOpH64), 375 is_col, imm0_1, GPR64shifted64> { 376 bits<3> ZAt; 377 bits<1> imm; 378 let Inst{3-1} = ZAt; 379 let Inst{0} = imm; 380 } 381 def _Q : sme_mem_st_ss_inst_Q<mnemonic # "q", 382 !if(is_col, TileVectorOpV128, 383 TileVectorOpH128), 384 is_col> { 385 bits<4> ZAt; 386 let Inst{3-0} = ZAt; 387 } 388 389 defm : sme_mem_st_ss_aliases<NAME, is_col>; 390} 391 392multiclass sme_mem_st_ss<string mnemonic> { 393 defm _H : sme_mem_st_v_ss<mnemonic, /*is_col=*/0b0>; 394 defm _V : sme_mem_st_v_ss<mnemonic, /*is_col=*/0b1>; 395} 396 397//===----------------------------------------------------------------------===// 398// SME Save and Restore Array 399//===----------------------------------------------------------------------===// 400 401class sme_spill_fill_inst<bit isStore, dag outs, dag ins, string opcodestr> 402 : I<outs, ins, opcodestr, "\t$ZAt[$Rv, $imm4], [$Rn, $offset, mul vl]", "", 403 []>, 404 Sched<[]> { 405 bits<2> Rv; 406 bits<5> Rn; 407 bits<4> imm4; 408 let Inst{31-22} = 0b1110000100; 409 let Inst{21} = isStore; 410 let Inst{20-15} = 0b000000; 411 let Inst{14-13} = Rv; 412 let Inst{12-10} = 0b000; 413 let Inst{9-5} = Rn; 414 let Inst{4} = 0b0; 415 let Inst{3-0} = imm4; 416 417 let mayLoad = !not(isStore); 418 let mayStore = isStore; 419} 420 421multiclass sme_spill_fill<bit isStore, dag outs, dag ins, string opcodestr> { 422 def NAME : sme_spill_fill_inst<isStore, outs, ins, opcodestr>; 423 424 def : InstAlias<opcodestr # "\t$ZAt[$Rv, $imm4], [$Rn]", 425 (!cast<Instruction>(NAME) MatrixOp:$ZAt, 426 MatrixIndexGPR32Op12_15:$Rv, imm0_15:$imm4, GPR64sp:$Rn, 0), 1>; 427} 428 429multiclass sme_spill<string opcodestr> { 430 defm NAME : sme_spill_fill<0b1, (outs), 431 (ins MatrixOp:$ZAt, MatrixIndexGPR32Op12_15:$Rv, 432 imm0_15:$imm4, GPR64sp:$Rn, 433 imm0_15:$offset), 434 opcodestr>; 435} 436 437multiclass sme_fill<string opcodestr> { 438 defm NAME : sme_spill_fill<0b0, (outs MatrixOp:$ZAt), 439 (ins MatrixIndexGPR32Op12_15:$Rv, 440 imm0_15:$imm4, GPR64sp:$Rn, 441 imm0_15:$offset), 442 opcodestr>; 443} 444 445//===----------------------------------------------------------------------===// 446// Move instructions 447//===----------------------------------------------------------------------===// 448 449class sme_vector_to_tile_base<bit Q, bit V, bits<2> sz, dag outs, dag ins, 450 string mnemonic, string argstr> 451 : I<outs, ins, mnemonic, argstr, "", []>, Sched<[]> { 452 bits<2> Rv; 453 bits<3> Pg; 454 bits<5> Zn; 455 let Inst{31-24} = 0b11000000; 456 let Inst{23-22} = sz; 457 let Inst{21-17} = 0b00000; 458 let Inst{16} = Q; 459 let Inst{15} = V; 460 let Inst{14-13} = Rv; 461 let Inst{12-10} = Pg; 462 let Inst{9-5} = Zn; 463 let Inst{4} = 0b0; 464} 465 466class sme_vector_to_tile_inst<bits<2> sz, MatrixTileVectorOperand tile_ty, 467 bit is_col, Operand imm_ty, ZPRRegOp zpr_ty, 468 string mnemonic> 469 : sme_vector_to_tile_base<0b0, is_col, sz, (outs tile_ty:$ZAd), 470 (ins MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, zpr_ty:$Zn), 471 mnemonic, "\t$ZAd[$Rv, $imm], $Pg/m, $Zn">; 472 473class sme_vector_to_tile_inst_Q<MatrixTileVectorOperand tile_ty, 474 bit is_col, string mnemonic> 475 : sme_vector_to_tile_base<0b1, is_col, 0b11, (outs tile_ty:$ZAd), 476 (ins MatrixIndexGPR32Op12_15:$Rv, PPR3bAny:$Pg, ZPR128:$Zn), 477 mnemonic, "\t$ZAd[$Rv], $Pg/m, $Zn">; 478 479multiclass sme_vector_to_tile_aliases<Instruction inst, 480 MatrixTileVectorOperand tile_ty, 481 ZPRRegOp zpr_ty, Operand imm_ty> { 482 def : InstAlias<"mov\t$ZAd[$Rv, $imm], $Pg/m, $Zn", 483 (inst tile_ty:$ZAd, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm, PPR3bAny:$Pg, zpr_ty:$Zn), 1>; 484} 485 486multiclass sme_vector_v_to_tile<string mnemonic, bit is_col> { 487 def _B : sme_vector_to_tile_inst<0b00, !if(is_col, TileVectorOpV8, 488 TileVectorOpH8), 489 is_col, imm0_15, ZPR8, mnemonic> { 490 bits<4> imm; 491 let Inst{3-0} = imm; 492 } 493 def _H : sme_vector_to_tile_inst<0b01, !if(is_col, TileVectorOpV16, 494 TileVectorOpH16), 495 is_col, imm0_7, ZPR16, mnemonic> { 496 bits<1> ZAd; 497 bits<3> imm; 498 let Inst{3} = ZAd; 499 let Inst{2-0} = imm; 500 } 501 def _S : sme_vector_to_tile_inst<0b10, !if(is_col, TileVectorOpV32, 502 TileVectorOpH32), 503 is_col, imm0_3, ZPR32, mnemonic> { 504 bits<2> ZAd; 505 bits<2> imm; 506 let Inst{3-2} = ZAd; 507 let Inst{1-0} = imm; 508 } 509 def _D : sme_vector_to_tile_inst<0b11, !if(is_col, TileVectorOpV64, 510 TileVectorOpH64), 511 is_col, imm0_1, ZPR64, mnemonic> { 512 bits<3> ZAd; 513 bits<1> imm; 514 let Inst{3-1} = ZAd; 515 let Inst{0} = imm; 516 } 517 def _Q : sme_vector_to_tile_inst_Q<!if(is_col, TileVectorOpV128, 518 TileVectorOpH128), 519 is_col, mnemonic> { 520 bits<4> ZAd; 521 bits<1> imm; 522 let Inst{3-0} = ZAd; 523 } 524 525 defm : sme_vector_to_tile_aliases<!cast<Instruction>(NAME # _B), 526 !if(is_col, TileVectorOpV8, 527 TileVectorOpH8), 528 ZPR8, imm0_15>; 529 defm : sme_vector_to_tile_aliases<!cast<Instruction>(NAME # _H), 530 !if(is_col, TileVectorOpV16, 531 TileVectorOpH16), 532 ZPR16, imm0_7>; 533 defm : sme_vector_to_tile_aliases<!cast<Instruction>(NAME # _S), 534 !if(is_col, TileVectorOpV32, 535 TileVectorOpH32), 536 ZPR32, imm0_3>; 537 defm : sme_vector_to_tile_aliases<!cast<Instruction>(NAME # _D), 538 !if(is_col, TileVectorOpV64, 539 TileVectorOpH64), 540 ZPR64, imm0_1>; 541 542 def : InstAlias<"mov\t$ZAd[$Rv], $Pg/m, $Zn", 543 (!cast<Instruction>(NAME # _Q) !if(is_col, 544 TileVectorOpV128, 545 TileVectorOpH128):$ZAd, 546 MatrixIndexGPR32Op12_15:$Rv, 547 PPR3bAny:$Pg, ZPR128:$Zn), 1>; 548} 549 550multiclass sme_vector_to_tile<string mnemonic> { 551 defm _H : sme_vector_v_to_tile<mnemonic, /*is_col=*/0b0>; 552 defm _V : sme_vector_v_to_tile<mnemonic, /*is_col=*/0b1>; 553} 554 555class sme_tile_to_vector_base<bit Q, bit V, bits<2> sz, dag outs, dag ins, 556 string mnemonic, string argstr> 557 : I<outs, ins, mnemonic, argstr, "", []>, Sched<[]> { 558 bits<2> Rv; 559 bits<3> Pg; 560 bits<5> Zd; 561 let Inst{31-24} = 0b11000000; 562 let Inst{23-22} = sz; 563 let Inst{21-17} = 0b00001; 564 let Inst{16} = Q; 565 let Inst{15} = V; 566 let Inst{14-13} = Rv; 567 let Inst{12-10} = Pg; 568 let Inst{9} = 0b0; 569 let Inst{4-0} = Zd; 570} 571 572class sme_tile_to_vector_inst<bits<2> sz, ZPRRegOp zpr_ty, 573 MatrixTileVectorOperand tile_ty, 574 bit is_col, Operand imm_ty, string mnemonic> 575 : sme_tile_to_vector_base<0b0, is_col, sz, (outs zpr_ty:$Zd), 576 (ins PPR3bAny:$Pg, tile_ty:$ZAn, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm), 577 mnemonic, "\t$Zd, $Pg/m, $ZAn[$Rv, $imm]">; 578 579class sme_tile_to_vector_inst_Q<MatrixTileVectorOperand tile_ty, 580 bit is_col, string mnemonic> 581 : sme_tile_to_vector_base<0b1, is_col, 0b11, (outs ZPR128:$Zd), 582 (ins PPR3bAny:$Pg, tile_ty:$ZAn, MatrixIndexGPR32Op12_15:$Rv), 583 mnemonic, "\t$Zd, $Pg/m, $ZAn[$Rv]">; 584 585multiclass sme_tile_to_vector_aliases<Instruction inst, ZPRRegOp zpr_ty, 586 MatrixTileVectorOperand tile_ty, 587 Operand imm_ty > { 588 def : InstAlias<"mov\t$Zd, $Pg/m, $ZAn[$Rv, $imm]", 589 (inst zpr_ty:$Zd, PPR3bAny:$Pg, tile_ty:$ZAn, MatrixIndexGPR32Op12_15:$Rv, imm_ty:$imm), 1>; 590} 591 592multiclass sme_tile_to_vector_v<string mnemonic, bit is_col> { 593 def _B : sme_tile_to_vector_inst<0b00, ZPR8, !if(is_col, TileVectorOpV8, 594 TileVectorOpH8), 595 is_col, imm0_15, mnemonic> { 596 bits<4> imm; 597 let Inst{8-5} = imm; 598 } 599 def _H : sme_tile_to_vector_inst<0b01, ZPR16, !if(is_col, TileVectorOpV16, 600 TileVectorOpH16), 601 is_col, imm0_7, mnemonic> { 602 bits<1> ZAn; 603 bits<3> imm; 604 let Inst{8} = ZAn; 605 let Inst{7-5} = imm; 606 } 607 def _S : sme_tile_to_vector_inst<0b10, ZPR32, !if(is_col, TileVectorOpV32, 608 TileVectorOpH32), 609 is_col, imm0_3, mnemonic> { 610 bits<2> ZAn; 611 bits<2> imm; 612 let Inst{8-7} = ZAn; 613 let Inst{6-5} = imm; 614 } 615 def _D : sme_tile_to_vector_inst<0b11, ZPR64, !if(is_col, TileVectorOpV64, 616 TileVectorOpH64), 617 is_col, imm0_1, mnemonic> { 618 bits<3> ZAn; 619 bits<1> imm; 620 let Inst{8-6} = ZAn; 621 let Inst{5} = imm; 622 } 623 def _Q : sme_tile_to_vector_inst_Q<!if(is_col, TileVectorOpV128, 624 TileVectorOpH128), 625 is_col, mnemonic> { 626 bits<4> ZAn; 627 let Inst{8-5} = ZAn; 628 } 629 630 defm : sme_tile_to_vector_aliases<!cast<Instruction>(NAME # _B), ZPR8, 631 !if(is_col, TileVectorOpV8, 632 TileVectorOpH8), imm0_15>; 633 defm : sme_tile_to_vector_aliases<!cast<Instruction>(NAME # _H), ZPR16, 634 !if(is_col, TileVectorOpV16, 635 TileVectorOpH16), imm0_7>; 636 defm : sme_tile_to_vector_aliases<!cast<Instruction>(NAME # _S), ZPR32, 637 !if(is_col, TileVectorOpV32, 638 TileVectorOpH32), imm0_3>; 639 defm : sme_tile_to_vector_aliases<!cast<Instruction>(NAME # _D), ZPR64, 640 !if(is_col, TileVectorOpV64, 641 TileVectorOpH64), imm0_1>; 642 643 def : InstAlias<"mov\t$Zd, $Pg/m, $ZAn[$Rv]", 644 (!cast<Instruction>(NAME # _Q) ZPR128:$Zd, PPR3bAny:$Pg, 645 !if(is_col, 646 TileVectorOpV128, 647 TileVectorOpH128):$ZAn, 648 MatrixIndexGPR32Op12_15:$Rv), 1>; 649} 650 651multiclass sme_tile_to_vector<string mnemonic> { 652 defm _H : sme_tile_to_vector_v<mnemonic, /*is_col=*/0b0>; 653 defm _V : sme_tile_to_vector_v<mnemonic, /*is_col=*/0b1>; 654} 655 656//===----------------------------------------------------------------------===// 657// SME Zero 658//===----------------------------------------------------------------------===// 659 660class sme_zero_inst<string mnemonic> 661 : I<(outs MatrixTileList:$imm), (ins), 662 mnemonic, "\t$imm", "", []>, Sched<[]> { 663 bits<8> imm; 664 let Inst{31-8} = 0b110000000000100000000000; 665 let Inst{7-0} = imm; 666} 667 668multiclass sme_zero<string mnemonic> { 669 def NAME : sme_zero_inst<mnemonic>; 670 671 def : InstAlias<"zero\t\\{za\\}", (!cast<Instruction>(NAME) 0b11111111), 1>; 672 def : InstAlias<"zero\t\\{za0.h\\}", (!cast<Instruction>(NAME) 0b01010101), 1>; 673 def : InstAlias<"zero\t\\{za1.h\\}", (!cast<Instruction>(NAME) 0b10101010), 1>; 674 def : InstAlias<"zero\t\\{za0.s\\}", (!cast<Instruction>(NAME) 0b00010001), 1>; 675 def : InstAlias<"zero\t\\{za1.s\\}", (!cast<Instruction>(NAME) 0b00100010), 1>; 676 def : InstAlias<"zero\t\\{za2.s\\}", (!cast<Instruction>(NAME) 0b01000100), 1>; 677 def : InstAlias<"zero\t\\{za3.s\\}", (!cast<Instruction>(NAME) 0b10001000), 1>; 678 def : InstAlias<"zero\t\\{za0.s,za1.s\\}", (!cast<Instruction>(NAME) 0b00110011), 1>; 679 def : InstAlias<"zero\t\\{za0.s,za3.s\\}", (!cast<Instruction>(NAME) 0b10011001), 1>; 680 def : InstAlias<"zero\t\\{za1.s,za2.s\\}", (!cast<Instruction>(NAME) 0b01100110), 1>; 681 def : InstAlias<"zero\t\\{za2.s,za3.s\\}", (!cast<Instruction>(NAME) 0b11001100), 1>; 682 def : InstAlias<"zero\t\\{za0.s,za1.s,za2.s\\}", (!cast<Instruction>(NAME) 0b01110111), 1>; 683 def : InstAlias<"zero\t\\{za0.s,za1.s,za3.s\\}", (!cast<Instruction>(NAME) 0b10111011), 1>; 684 def : InstAlias<"zero\t\\{za0.s,za2.s,za3.s\\}", (!cast<Instruction>(NAME) 0b11011101), 1>; 685 def : InstAlias<"zero\t\\{za1.s,za2.s,za3.s\\}", (!cast<Instruction>(NAME) 0b11101110), 1>; 686} 687 688//===----------------------------------------------------------------------===// 689// SVE2 Instructions 690//===----------------------------------------------------------------------===// 691 692class sve2_int_perm_revd<string asm> 693 : I<(outs ZPR128:$Zd), (ins ZPR128:$_Zd, PPR3bAny:$Pg, ZPR128:$Zn), 694 asm, "\t$Zd, $Pg/m, $Zn", "", []>, 695 Sched<[]> { 696 bits<5> Zd; 697 bits<3> Pg; 698 bits<5> Zn; 699 let Inst{31-24} = 0b00000101; 700 let Inst{23-22} = 0b00; // size 701 let Inst{21-13} = 0b101110100; 702 let Inst{12-10} = Pg; 703 let Inst{9-5} = Zn; 704 let Inst{4-0} = Zd; 705 706 let Constraints = "$Zd = $_Zd"; 707 let DestructiveInstType = DestructiveUnary; 708 let ElementSize = ZPR128.ElementSize; 709} 710 711class sve2_clamp<string asm, bits<2> sz, bit U, ZPRRegOp zpr_ty> 712 : I<(outs zpr_ty:$Zd), (ins zpr_ty:$Zn, zpr_ty:$Zm, zpr_ty:$_Zd), 713 asm, "\t$Zd, $Zn, $Zm", "", []>, 714 Sched<[]> { 715 bits<5> Zm; 716 bits<5> Zn; 717 bits<5> Zd; 718 let Inst{31-24} = 0b01000100; 719 let Inst{23-22} = sz; 720 let Inst{21} = 0b0; 721 let Inst{20-16} = Zm; 722 let Inst{15-11} = 0b11000; 723 let Inst{10} = U; 724 let Inst{9-5} = Zn; 725 let Inst{4-0} = Zd; 726 727 let Constraints = "$Zd = $_Zd"; 728 let DestructiveInstType = DestructiveOther; 729 let ElementSize = zpr_ty.ElementSize; 730} 731 732multiclass sve2_clamp<string asm, bit U> { 733 def _B : sve2_clamp<asm, 0b00, U, ZPR8>; 734 def _H : sve2_clamp<asm, 0b01, U, ZPR16>; 735 def _S : sve2_clamp<asm, 0b10, U, ZPR32>; 736 def _D : sve2_clamp<asm, 0b11, U, ZPR64>; 737} 738 739class sve2_int_perm_dup_p<string asm, PPRRegOp ppr_ty, Operand imm_ty> 740 : I<(outs ppr_ty:$Pd), (ins PPRAny:$Pg, ppr_ty:$Pn, 741 MatrixIndexGPR32Op12_15:$Rm, imm_ty:$imm), 742 asm, "\t$Pd, $Pg/z, $Pn[$Rm, $imm]", "", []>, 743 Sched<[]> { 744 bits<2> Rm; 745 bits<4> Pg; 746 bits<4> Pn; 747 bits<4> Pd; 748 let Inst{31-24} = 0b00100101; 749 let Inst{21} = 0b1; 750 let Inst{17-16} = Rm; 751 let Inst{15-14} = 0b01; 752 let Inst{13-10} = Pg; 753 let Inst{9} = 0b0; 754 let Inst{8-5} = Pn; 755 let Inst{4} = 0b0; 756 let Inst{3-0} = Pd; 757} 758 759multiclass sve2_int_perm_dup_p<string asm> { 760 def _B : sve2_int_perm_dup_p<asm, PPR8, imm0_15> { 761 bits<4> imm; 762 let Inst{23-22} = imm{3-2}; 763 let Inst{20-19} = imm{1-0}; 764 let Inst{18} = 0b1; 765 } 766 def _H : sve2_int_perm_dup_p<asm, PPR16, imm0_7> { 767 bits<3> imm; 768 let Inst{23-22} = imm{2-1}; 769 let Inst{20} = imm{0}; 770 let Inst{19-18} = 0b10; 771 } 772 def _S : sve2_int_perm_dup_p<asm, PPR32, imm0_3> { 773 bits<2> imm; 774 let Inst{23-22} = imm{1-0}; 775 let Inst{20-18} = 0b100; 776 } 777 def _D : sve2_int_perm_dup_p<asm, PPR64, imm0_1> { 778 bits<1> imm; 779 let Inst{23} = imm; 780 let Inst{22} = 0b1; 781 let Inst{20-18} = 0b000; 782 } 783 784 def : InstAlias<"dup\t$Pd, $Pg/z, $Pn[$Rm]", 785 (!cast<Instruction>(NAME # _B) PPR8:$Pd, PPRAny:$Pg, PPR8:$Pn, MatrixIndexGPR32Op12_15:$Rm, 0), 1>; 786 def : InstAlias<"dup\t$Pd, $Pg/z, $Pn[$Rm]", 787 (!cast<Instruction>(NAME # _H) PPR16:$Pd, PPRAny:$Pg, PPR16:$Pn, MatrixIndexGPR32Op12_15:$Rm, 0), 1>; 788 def : InstAlias<"dup\t$Pd, $Pg/z, $Pn[$Rm]", 789 (!cast<Instruction>(NAME # _S) PPR32:$Pd, PPRAny:$Pg, PPR32:$Pn, MatrixIndexGPR32Op12_15:$Rm, 0), 1>; 790 def : InstAlias<"dup\t$Pd, $Pg/z, $Pn[$Rm]", 791 (!cast<Instruction>(NAME # _D) PPR64:$Pd, PPRAny:$Pg, PPR64:$Pn, MatrixIndexGPR32Op12_15:$Rm, 0), 1>; 792} 793