@@ -1771,6 +1771,37 @@ bool IRTranslator::translateMemFunc(const CallInst &CI,
1771
1771
return true ;
1772
1772
}
1773
1773
1774
+ bool IRTranslator::translateVectorInterleave2Intrinsic (
1775
+ const CallInst &CI, MachineIRBuilder &MIRBuilder) {
1776
+ // Canonicalize interleave2 to G_SHUFFLE_VECTOR (similar to SelectionDAG)
1777
+ Register Op0 = getOrCreateVReg (*CI.getOperand (0 ));
1778
+ Register Op1 = getOrCreateVReg (*CI.getOperand (1 ));
1779
+ Register Res = getOrCreateVReg (CI);
1780
+
1781
+ LLT OpTy = MRI->getType (Op0);
1782
+ MIRBuilder.buildShuffleVector (Res, Op0, Op1,
1783
+ createInterleaveMask (OpTy.getNumElements (), 2 ));
1784
+
1785
+ return true ;
1786
+ }
1787
+
1788
+ bool IRTranslator::translateVectorDeinterleave2Intrinsic (
1789
+ const CallInst &CI, MachineIRBuilder &MIRBuilder) {
1790
+ // Canonicalize deinterleave2 shuffles that extract sub-vectors (similar to
1791
+ // SelectionDAG)
1792
+ Register Op = getOrCreateVReg (*CI.getOperand (0 ));
1793
+ auto Undef = MIRBuilder.buildUndef (MRI->getType (Op));
1794
+ ArrayRef<Register> Res = getOrCreateVRegs (CI);
1795
+
1796
+ LLT ResTy = MRI->getType (Res[0 ]);
1797
+ MIRBuilder.buildShuffleVector (Res[0 ], Op, Undef,
1798
+ createStrideMask (0 , 2 , ResTy.getNumElements ()));
1799
+ MIRBuilder.buildShuffleVector (Res[1 ], Op, Undef,
1800
+ createStrideMask (1 , 2 , ResTy.getNumElements ()));
1801
+
1802
+ return true ;
1803
+ }
1804
+
1774
1805
void IRTranslator::getStackGuard (Register DstReg,
1775
1806
MachineIRBuilder &MIRBuilder) {
1776
1807
const TargetRegisterInfo *TRI = MF->getSubtarget ().getRegisterInfo ();
@@ -2476,46 +2507,18 @@ bool IRTranslator::translateKnownIntrinsic(const CallInst &CI, Intrinsic::ID ID,
2476
2507
return true ;
2477
2508
}
2478
2509
2479
- case Intrinsic::experimental_vector_interleave2: {
2480
- Value *Src0 = CI.getOperand (0 );
2481
- Value *Src1 = CI.getOperand (1 );
2482
-
2483
- // Canonicalize fixed-width vector types to G_SHUFFLE_VECTOR
2484
- // (similar to SelectionDAG)
2485
- LLT OpType = getLLTForType (*Src0->getType (), MIRBuilder.getDataLayout ());
2486
- if (!OpType.isFixedVector ())
2487
- break ;
2488
-
2489
- Register Op0 = getOrCreateVReg (*Src0);
2490
- Register Op1 = getOrCreateVReg (*Src1);
2491
- Register Res = getOrCreateVReg (CI);
2492
-
2493
- MIRBuilder.buildShuffleVector (
2494
- Res, Op0, Op1, createInterleaveMask (OpType.getNumElements (), 2 ));
2495
-
2496
- return true ;
2497
- }
2498
-
2510
+ case Intrinsic::experimental_vector_interleave2:
2499
2511
case Intrinsic::experimental_vector_deinterleave2: {
2500
- Value *Src = CI.getOperand (0 );
2501
-
2502
- // Canonicalize fixed-width vector types to shuffles that extract
2503
- // sub-vectors (similar to SelectionDAG)
2504
- ArrayRef<Register> Res = getOrCreateVRegs (CI);
2505
- LLT ResTy = MRI->getType (Res[0 ]);
2512
+ // Both intrinsics have at least one operand.
2513
+ Value *Op0 = CI.getOperand (0 );
2514
+ LLT ResTy = getLLTForType (*Op0->getType (), MIRBuilder.getDataLayout ());
2506
2515
if (!ResTy.isFixedVector ())
2507
- break ;
2508
-
2509
- Register Op = getOrCreateVReg (*Src);
2510
- LLT OpType = getLLTForType (*Src->getType (), MIRBuilder.getDataLayout ());
2516
+ return false ;
2511
2517
2512
- auto Undef = MIRBuilder.buildUndef (OpType);
2513
- MIRBuilder.buildShuffleVector (
2514
- Res[0 ], Op, Undef, createStrideMask (0 , 2 , ResTy.getNumElements ()));
2515
- MIRBuilder.buildShuffleVector (
2516
- Res[1 ], Op, Undef, createStrideMask (1 , 2 , ResTy.getNumElements ()));
2518
+ if (CI.getIntrinsicID () == Intrinsic::experimental_vector_interleave2)
2519
+ return translateVectorInterleave2Intrinsic (CI, MIRBuilder);
2517
2520
2518
- return true ;
2521
+ return translateVectorDeinterleave2Intrinsic (CI, MIRBuilder) ;
2519
2522
}
2520
2523
2521
2524
#define INSTRUCTION (NAME, NARG, ROUND_MODE, INTRINSIC ) \
0 commit comments