[AArch64][GlobalISel] More FCmp legalization. (#78734)
This fills out the fcmp handling to be more like the other instructions,
adding better support for fp16 and some larger vectors.
Select of f16 values is still not handled optimally in places as the
select is only legal for s32 values, not s16. This would be correct for
integer but not necessarily for fp. It is as if we need to do
legalization -> regbankselect -> extra legaliation -> selection.
diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp
index 4b675e8..6c06afa 100644
--- a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp
+++ b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp
@@ -1556,6 +1556,15 @@
MI.eraseFromParent();
return Legalized;
}
+ case TargetOpcode::G_FCMP:
+ if (TypeIdx != 0)
+ return UnableToLegalize;
+
+ Observer.changingInstr(MI);
+ narrowScalarDst(MI, NarrowTy, 0, TargetOpcode::G_ZEXT);
+ Observer.changedInstr(MI);
+ return Legalized;
+
case TargetOpcode::G_SEXT_INREG: {
if (TypeIdx != 0)
return UnableToLegalize;
@@ -5317,14 +5326,18 @@
Observer.changedInstr(MI);
return Legalized;
}
- case TargetOpcode::G_ICMP: {
- // TODO: the symmetric MoreTy works for targets like, e.g. NEON.
- // For targets, like e.g. MVE, the result is a predicated vector (i1).
- // This will need some refactoring.
+ case TargetOpcode::G_ICMP:
+ case TargetOpcode::G_FCMP: {
+ if (TypeIdx != 1)
+ return UnableToLegalize;
+
Observer.changingInstr(MI);
moreElementsVectorSrc(MI, MoreTy, 2);
moreElementsVectorSrc(MI, MoreTy, 3);
- moreElementsVectorDst(MI, MoreTy, 0);
+ LLT CondTy = LLT::fixed_vector(
+ MoreTy.getNumElements(),
+ MRI.getType(MI.getOperand(0).getReg()).getElementType());
+ moreElementsVectorDst(MI, CondTy, 0);
Observer.changedInstr(MI);
return Legalized;
}