@@ -63,6 +63,8 @@ def SBFRevSub : Predicate<"Subtarget->getReverseSubImm()">;
63
63
def SBFNoRevSub : Predicate<"!Subtarget->getReverseSubImm()">;
64
64
def SBFCallxSrc : Predicate<"Subtarget->getCallXRegSrc()">, AssemblerPredicate<(all_of FeatureCallxRegSrc)>;
65
65
def NoSBFCallxSrc : Predicate<"!Subtarget->getCallXRegSrc()">;
66
+ def SBFPqrInstr : Predicate<"Subtarget->getHasPqrClass()">;
67
+ def SBFNoPqrInstr : Predicate<"!Subtarget->getHasPqrClass()">;
66
68
67
69
def brtarget : Operand<OtherVT> {
68
70
let PrintMethod = "printBrTargetOperand";
@@ -136,10 +138,13 @@ def SBF_CC_LEU : PatLeaf<(i64 imm),
136
138
// +----------------+--------+--------------------+
137
139
// (MSB) (LSB)
138
140
class TYPE_ALU_JMP<bits<4> op, bits<1> srctype,
139
- dag outs, dag ins, string asmstr, list<dag> pattern>
141
+ dag outs, dag ins, string asmstr, list<dag> pattern,
142
+ bit IsPqr64 = 0>
140
143
: InstSBF<outs, ins, asmstr, pattern> {
141
144
142
- let Inst{63-60} = op;
145
+ // In the PQR class, instructions that deal with 64-bit registers have a different OpCode.
146
+ // To obtain it, we add one to its base value.
147
+ let Inst{63-60} = !if(IsPqr64, !add(op, 1), op);
143
148
let Inst{59} = srctype;
144
149
}
145
150
@@ -211,9 +216,11 @@ defm JSLE : J<SBF_JSLE, "jsle", SBF_CC_LE>;
211
216
}
212
217
213
218
// ALU instructions
214
- class ALU_RI<SBFOpClass Class, SBFArithOp Opc,
215
- dag outs, dag ins, string asmstr, list<dag> pattern>
216
- : TYPE_ALU_JMP<Opc.Value, SBF_K.Value, outs, ins, asmstr, pattern> {
219
+ class MATH_RI<SBFOpClass Class, SBFArithOp Opc,
220
+ dag outs, dag ins, string asmstr,
221
+ list<dag> pattern, bit isPqr64 = 0>
222
+ : TYPE_ALU_JMP<Opc.Value, SBF_K.Value, outs, ins,
223
+ asmstr, pattern, isPqr64> {
217
224
bits<4> dst;
218
225
bits<32> imm;
219
226
@@ -222,9 +229,11 @@ class ALU_RI<SBFOpClass Class, SBFArithOp Opc,
222
229
let SBFClass = Class;
223
230
}
224
231
225
- class ALU_RR<SBFOpClass Class, SBFArithOp Opc,
226
- dag outs, dag ins, string asmstr, list<dag> pattern>
227
- : TYPE_ALU_JMP<Opc.Value, SBF_X.Value, outs, ins, asmstr, pattern> {
232
+ class MATH_RR<SBFOpClass Class, SBFArithOp Opc,
233
+ dag outs, dag ins, string asmstr,
234
+ list<dag> pattern, bit isPqr64 = 0>
235
+ : TYPE_ALU_JMP<Opc.Value, SBF_X.Value, outs, ins,
236
+ asmstr, pattern, isPqr64> {
228
237
bits<4> dst;
229
238
bits<4> src;
230
239
@@ -233,25 +242,14 @@ class ALU_RR<SBFOpClass Class, SBFArithOp Opc,
233
242
let SBFClass = Class;
234
243
}
235
244
236
- multiclass ALU<SBFArithOp Opc, string Mnemonic, SDNode OpNode, bit UseImmPat = 1> {
237
- def _rr : ALU_RR<SBF_ALU64, Opc,
238
- (outs GPR:$dst),
239
- (ins GPR:$src2, GPR:$src),
240
- Mnemonic # "64 $dst, $src",
241
- [(set GPR:$dst, (OpNode i64:$src2, i64:$src))]>;
242
- def _ri : ALU_RI<SBF_ALU64, Opc,
243
- (outs GPR:$dst),
244
- (ins GPR:$src2, i64imm:$imm),
245
- Mnemonic # "64 $dst, $imm",
246
- !if(UseImmPat,
247
- [(set GPR:$dst,
248
- (OpNode GPR:$src2, i64immSExt32:$imm))], [])>;
249
- def _rr_32 : ALU_RR<SBF_ALU, Opc,
245
+ multiclass MATH_32<SBFArithOp Opc, string Mnemonic,
246
+ SBFOpClass Class, SDNode OpNode, bit UseImmPat = 1> {
247
+ def _rr_32 : MATH_RR<Class, Opc,
250
248
(outs GPR32:$dst),
251
249
(ins GPR32:$src2, GPR32:$src),
252
250
Mnemonic # "32 $dst, $src",
253
251
[(set GPR32:$dst, (OpNode i32:$src2, i32:$src))]>;
254
- def _ri_32 : ALU_RI<SBF_ALU , Opc,
252
+ def _ri_32 : MATH_RI<Class , Opc,
255
253
(outs GPR32:$dst),
256
254
(ins GPR32:$src2, i32imm:$imm),
257
255
Mnemonic # "32 $dst, $imm",
@@ -260,6 +258,40 @@ multiclass ALU<SBFArithOp Opc, string Mnemonic, SDNode OpNode, bit UseImmPat = 1
260
258
(OpNode GPR32:$src2, i32immSExt32:$imm))], [])>;
261
259
}
262
260
261
+ multiclass MATH_64<SBFArithOp Opc, string Mnemonic,
262
+ SBFOpClass Class, SDNode OpNode, bit UseImmPat = 1> {
263
+
264
+ defvar isPqr64 = !if(!eq(Class, SBF_PQR), 1, 0);
265
+
266
+ def _rr : MATH_RR<Class, Opc,
267
+ (outs GPR:$dst),
268
+ (ins GPR:$src2, GPR:$src),
269
+ Mnemonic # "64 $dst, $src",
270
+ [(set GPR:$dst, (OpNode i64:$src2, i64:$src))],
271
+ isPqr64>;
272
+
273
+ def _ri : MATH_RI<Class, Opc,
274
+ (outs GPR:$dst),
275
+ (ins GPR:$src2, i64imm:$imm),
276
+ Mnemonic # "64 $dst, $imm",
277
+ !if(UseImmPat,
278
+ [(set GPR:$dst,
279
+ (OpNode GPR:$src2, i64immSExt32:$imm))], []),
280
+ isPqr64>;
281
+ }
282
+
283
+ multiclass ALU<SBFArithOp Opc, string Mnemonic,
284
+ SDNode OpNode, bit UseImmPat = 1> {
285
+ defm "" : MATH_64<Opc, Mnemonic, SBF_ALU64, OpNode, UseImmPat>;
286
+
287
+ defm "" : MATH_32<Opc, Mnemonic, SBF_ALU, OpNode, UseImmPat>;
288
+ }
289
+
290
+ multiclass PQR<SBFArithOp Opc, string Mnemonic, SDNode OpNode> {
291
+ defm "" : MATH_64<Opc, Mnemonic, SBF_PQR, OpNode>;
292
+ defm "" : MATH_32<Opc, Mnemonic, SBF_PQR, OpNode>;
293
+ }
294
+
263
295
let Constraints = "$dst = $src2" in {
264
296
let isAsCheapAsAMove = 1 in {
265
297
defm ADD : ALU<SBF_ADD, "add", add>;
@@ -272,13 +304,13 @@ let Constraints = "$dst = $src2" in {
272
304
defm SRA : ALU<SBF_ARSH, "arsh", sra>;
273
305
274
306
let Predicates = [SBFNoLddw] in {
275
- def HOR : ALU_RI <SBF_ALU64, SBF_HOR,
307
+ def HOR : MATH_RI <SBF_ALU64, SBF_HOR,
276
308
(outs GPR:$dst),
277
309
(ins GPR:$src2, i32imm:$imm),
278
310
"hor64 $dst, $imm",
279
311
[]>;
280
312
let DecoderNamespace = "SBFv2" in {
281
- def HOR_addr : ALU_RI <SBF_ALU64, SBF_HOR,
313
+ def HOR_addr : MATH_RI <SBF_ALU64, SBF_HOR,
282
314
(outs GPR:$dst),
283
315
(ins GPR:$src2, u64imm:$imm),
284
316
"hor64 $dst, $imm",
@@ -288,11 +320,20 @@ let Constraints = "$dst = $src2" in {
288
320
}
289
321
}
290
322
291
- defm MUL : ALU<SBF_MUL, "mul", mul>;
292
- defm DIV : ALU<SBF_DIV, "div", udiv>;
293
323
294
- let Predicates = [SBFSubtargetSolana] in {
295
- defm SDIV : ALU<SBF_SDIV, "sdiv", sdiv>;
324
+ let Predicates = [SBFNoPqrInstr] in {
325
+ defm MUL : ALU<SBF_MUL, "mul", mul>;
326
+ defm DIV : ALU<SBF_DIV, "div", udiv>;
327
+ }
328
+
329
+ let Predicates = [SBFPqrInstr] in {
330
+ defm UHMUL : MATH_64<PQR_UHMUL, "uhmul", SBF_PQR, mulhu>;
331
+ defm UDIV : PQR<PQR_UDIV, "udiv", udiv>;
332
+ defm UREM : PQR<PQR_UREM, "urem", urem>;
333
+ defm LMUL : PQR<PQR_LMUL, "lmul", mul>;
334
+ defm SHMUL : MATH_64<PQR_SHMUL, "shmul", SBF_PQR, mulhs>;
335
+ defm SDIV_pqr : PQR<PQR_SDIV, "sdiv", sdiv>;
336
+ defm SREM : PQR<PQR_SREM, "srem", srem>;
296
337
}
297
338
}
298
339
@@ -355,22 +396,22 @@ class LD_IMM64<bits<4> Pseudo, string Mnemonic>
355
396
356
397
let isReMaterializable = 1, isAsCheapAsAMove = 1 in {
357
398
def LD_imm64 : LD_IMM64<0, "lddw">, Requires<[SBFHasLddw]>;
358
- def MOV_rr : ALU_RR <SBF_ALU64, SBF_MOV,
399
+ def MOV_rr : MATH_RR <SBF_ALU64, SBF_MOV,
359
400
(outs GPR:$dst),
360
401
(ins GPR:$src),
361
402
"mov64 $dst, $src",
362
403
[]>;
363
- def MOV_ri : ALU_RI <SBF_ALU64, SBF_MOV,
404
+ def MOV_ri : MATH_RI <SBF_ALU64, SBF_MOV,
364
405
(outs GPR:$dst),
365
406
(ins i64imm:$imm),
366
407
"mov64 $dst, $imm",
367
408
[(set GPR:$dst, (i64 i64immSExt32:$imm))]>;
368
- def MOV_rr_32 : ALU_RR <SBF_ALU, SBF_MOV,
409
+ def MOV_rr_32 : MATH_RR <SBF_ALU, SBF_MOV,
369
410
(outs GPR32:$dst),
370
411
(ins GPR32:$src),
371
412
"mov32 $dst, $src",
372
413
[]>;
373
- def MOV_ri_32 : ALU_RI <SBF_ALU, SBF_MOV,
414
+ def MOV_ri_32 : MATH_RI <SBF_ALU, SBF_MOV,
374
415
(outs GPR32:$dst),
375
416
(ins i32imm:$imm),
376
417
"mov32 $dst, $imm",
@@ -468,7 +509,7 @@ let isCodeGenOnly = 1 in {
468
509
"$dst = core_alu32_mem($opcode, $src, $offset)",
469
510
[]>;
470
511
let Constraints = "$dst = $src" in {
471
- def CORE_SHIFT : ALU_RR <SBF_ALU64, SBF_LSH,
512
+ def CORE_SHIFT : MATH_RR <SBF_ALU64, SBF_LSH,
472
513
(outs GPR:$dst),
473
514
(ins u64imm:$opcode, GPR:$src, u64imm:$offset),
474
515
"$dst = core_shift($opcode, $src, $offset)",
@@ -896,16 +937,16 @@ let Constraints = "$dst = $src" in {
896
937
}
897
938
898
939
let isCodeGenOnly = 1 in {
899
- def MOV_32_64 : ALU_RR <SBF_ALU, SBF_MOV,
940
+ def MOV_32_64 : MATH_RR <SBF_ALU, SBF_MOV,
900
941
(outs GPR:$dst), (ins GPR32:$src),
901
942
"mov32 $dst, $src", []>;
902
- def MOV_32_64_addr : ALU_RI <SBF_ALU, SBF_MOV,
943
+ def MOV_32_64_addr : MATH_RI <SBF_ALU, SBF_MOV,
903
944
(outs GPR:$dst), (ins u64imm:$imm),
904
945
"mov32 $dst, $imm", []>, Requires<[SBFNoLddw]>;
905
946
}
906
947
907
948
let DecoderNamespace = "SBFv2", Predicates = [SBFNoLddw] in {
908
- def MOV_32_64_imm : ALU_RI <SBF_ALU, SBF_MOV,
949
+ def MOV_32_64_imm : MATH_RI <SBF_ALU, SBF_MOV,
909
950
(outs GPR:$dst), (ins i32imm:$imm),
910
951
"mov32 $dst, $imm", []>;
911
952
}
0 commit comments