Skip to content

Commit 9c33a87

Browse files
[RISCV][GISEL] Legalize G_ZEXT, G_SEXT, and G_ANYEXT for scalable vector types
1 parent 07d3f2a commit 9c33a87

File tree

5 files changed

+4805
-6
lines changed

5 files changed

+4805
-6
lines changed

llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp

Lines changed: 37 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -139,20 +139,21 @@ RISCVLegalizerInfo::RISCVLegalizerInfo(const RISCVSubtarget &ST)
139139
.clampScalar(0, s32, sXLen)
140140
.minScalarSameAs(1, 0);
141141

142+
auto &ExtActions =
143+
getActionDefinitionsBuilder({G_ZEXT, G_SEXT, G_ANYEXT})
144+
.legalIf(all(typeIsLegalIntOrFPVec(0, IntOrFPVecTys, ST),
145+
typeIsLegalIntOrFPVec(1, IntOrFPVecTys, ST)));
142146
if (ST.is64Bit()) {
143-
getActionDefinitionsBuilder({G_ZEXT, G_SEXT, G_ANYEXT})
144-
.legalFor({{sXLen, s32}})
145-
.maxScalar(0, sXLen);
146-
147+
ExtActions.legalFor({{sXLen, s32}});
147148
getActionDefinitionsBuilder(G_SEXT_INREG)
148149
.customFor({sXLen})
149150
.maxScalar(0, sXLen)
150151
.lower();
151152
} else {
152-
getActionDefinitionsBuilder({G_ZEXT, G_SEXT, G_ANYEXT}).maxScalar(0, sXLen);
153-
154153
getActionDefinitionsBuilder(G_SEXT_INREG).maxScalar(0, sXLen).lower();
155154
}
155+
ExtActions.customIf(typeIsLegalBoolVec(1, BoolVecTys, ST))
156+
.maxScalar(0, sXLen);
156157

157158
// Merge/Unmerge
158159
for (unsigned Op : {G_MERGE_VALUES, G_UNMERGE_VALUES}) {
@@ -576,6 +577,32 @@ bool RISCVLegalizerInfo::legalizeVScale(MachineInstr &MI,
576577
auto VScale = MIB.buildLShr(XLenTy, VLENB, MIB.buildConstant(XLenTy, 3));
577578
MIB.buildMul(Dst, VScale, MIB.buildConstant(XLenTy, Val));
578579
}
580+
MI.eraseFromParent();
581+
return true;
582+
}
583+
584+
// Custom-lower extensions from mask vectors by using a vselect either with 1
585+
// for zero/any-extension or -1 for sign-extension:
586+
// (vXiN = (s|z)ext vXi1:vmask) -> (vXiN = vselect vmask, (-1 or 1), 0)
587+
// Note that any-extension is lowered identically to zero-extension.
588+
bool RISCVLegalizerInfo::legalizeExt(MachineInstr &MI,
589+
MachineIRBuilder &MIB) const {
590+
591+
unsigned Opc = MI.getOpcode();
592+
assert(Opc == TargetOpcode::G_ZEXT || Opc == TargetOpcode::G_SEXT ||
593+
Opc == TargetOpcode::G_ANYEXT);
594+
595+
MachineRegisterInfo &MRI = *MIB.getMRI();
596+
Register Dst = MI.getOperand(0).getReg();
597+
Register Src = MI.getOperand(1).getReg();
598+
599+
LLT DstTy = MRI.getType(Dst);
600+
int64_t ExtTrueVal = Opc == TargetOpcode::G_SEXT ? -1 : 1;
601+
LLT DstEltTy = DstTy.getElementType();
602+
auto SplatZero = MIB.buildSplatVector(DstTy, MIB.buildConstant(DstEltTy, 0));
603+
auto SplatTrue =
604+
MIB.buildSplatVector(DstTy, MIB.buildConstant(DstEltTy, ExtTrueVal));
605+
MIB.buildSelect(Dst, Src, SplatTrue, SplatZero);
579606

580607
MI.eraseFromParent();
581608
return true;
@@ -640,6 +667,10 @@ bool RISCVLegalizerInfo::legalizeCustom(
640667
return legalizeVAStart(MI, MIRBuilder);
641668
case TargetOpcode::G_VSCALE:
642669
return legalizeVScale(MI, MIRBuilder);
670+
case TargetOpcode::G_ZEXT:
671+
case TargetOpcode::G_SEXT:
672+
case TargetOpcode::G_ANYEXT:
673+
return legalizeExt(MI, MIRBuilder);
643674
}
644675

645676
llvm_unreachable("expected switch to return");

llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ class RISCVLegalizerInfo : public LegalizerInfo {
4343

4444
bool legalizeVAStart(MachineInstr &MI, MachineIRBuilder &MIRBuilder) const;
4545
bool legalizeVScale(MachineInstr &MI, MachineIRBuilder &MIB) const;
46+
bool legalizeExt(MachineInstr &MI, MachineIRBuilder &MIRBuilder) const;
4647
};
4748
} // end namespace llvm
4849
#endif

0 commit comments

Comments
 (0)