Skip to content

Commit 1c87d5c

Browse files
committed
[AArch64][GlobalISel] Lower fminnm/fmaxnm through Global ISel
Whilst this might technically not be correct if a combine treats signed zeroes differently, where the neon operations are more defined than the minnum/maxnum nodes. It mirrors what SDAG does, which allows us to lower aarch64_neon_fminnm and aarch64_neon_fmaxnm through the existing selection patterns.
1 parent 44089c2 commit 1c87d5c

File tree

3 files changed

+50
-20
lines changed

3 files changed

+50
-20
lines changed

llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1406,7 +1406,9 @@ bool AArch64LegalizerInfo::legalizeIntrinsic(LegalizerHelper &Helper,
14061406
case Intrinsic::aarch64_neon_umax:
14071407
case Intrinsic::aarch64_neon_umin:
14081408
case Intrinsic::aarch64_neon_fmax:
1409-
case Intrinsic::aarch64_neon_fmin: {
1409+
case Intrinsic::aarch64_neon_fmin:
1410+
case Intrinsic::aarch64_neon_fmaxnm:
1411+
case Intrinsic::aarch64_neon_fminnm: {
14101412
MachineIRBuilder MIB(MI);
14111413
if (IntrinsicID == Intrinsic::aarch64_neon_smax)
14121414
MIB.buildSMax(MI.getOperand(0), MI.getOperand(2), MI.getOperand(3));
@@ -1422,6 +1424,12 @@ bool AArch64LegalizerInfo::legalizeIntrinsic(LegalizerHelper &Helper,
14221424
else if (IntrinsicID == Intrinsic::aarch64_neon_fmin)
14231425
MIB.buildInstr(TargetOpcode::G_FMINIMUM, {MI.getOperand(0)},
14241426
{MI.getOperand(2), MI.getOperand(3)});
1427+
else if (IntrinsicID == Intrinsic::aarch64_neon_fmaxnm)
1428+
MIB.buildInstr(TargetOpcode::G_FMAXNUM, {MI.getOperand(0)},
1429+
{MI.getOperand(2), MI.getOperand(3)});
1430+
else if (IntrinsicID == Intrinsic::aarch64_neon_fminnm)
1431+
MIB.buildInstr(TargetOpcode::G_FMINNUM, {MI.getOperand(0)},
1432+
{MI.getOperand(2), MI.getOperand(3)});
14251433
MI.eraseFromParent();
14261434
return true;
14271435
}

llvm/test/CodeGen/AArch64/arm64-vmax.ll

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
22
; RUN: llc < %s -mtriple=arm64-eabi -aarch64-neon-syntax=apple | FileCheck %s
3-
; RUN: llc < %s -global-isel -global-isel-abort=1 -mtriple=arm64-eabi -aarch64-neon-syntax=apple | FileCheck %s
3+
; RUN: llc < %s -global-isel -mtriple=arm64-eabi -aarch64-neon-syntax=apple | FileCheck %s
44

55
define <8 x i8> @smax_8b(ptr %A, ptr %B) nounwind {
66
; CHECK-LABEL: smax_8b:

llvm/test/CodeGen/AArch64/arm64-vminmaxnm.ll

Lines changed: 40 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,57 +1,75 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 4
12
; RUN: llc < %s -mtriple=arm64-eabi -aarch64-neon-syntax=apple | FileCheck %s
3+
; RUN: llc < %s -mtriple=arm64-eabi -aarch64-neon-syntax=apple -global-isel | FileCheck %s
24

35
define <2 x float> @f1(<2 x float> %a, <2 x float> %b) nounwind readnone ssp {
4-
; CHECK: fmaxnm.2s v0, v0, v1
5-
; CHECK: ret
6+
; CHECK-LABEL: f1:
7+
; CHECK: // %bb.0:
8+
; CHECK-NEXT: fmaxnm.2s v0, v0, v1
9+
; CHECK-NEXT: ret
610
%vmaxnm2.i = tail call <2 x float> @llvm.aarch64.neon.fmaxnm.v2f32(<2 x float> %a, <2 x float> %b) nounwind
711
ret <2 x float> %vmaxnm2.i
812
}
913

1014
define <4 x float> @f2(<4 x float> %a, <4 x float> %b) nounwind readnone ssp {
11-
; CHECK: fmaxnm.4s v0, v0, v1
12-
; CHECK: ret
15+
; CHECK-LABEL: f2:
16+
; CHECK: // %bb.0:
17+
; CHECK-NEXT: fmaxnm.4s v0, v0, v1
18+
; CHECK-NEXT: ret
1319
%vmaxnm2.i = tail call <4 x float> @llvm.aarch64.neon.fmaxnm.v4f32(<4 x float> %a, <4 x float> %b) nounwind
1420
ret <4 x float> %vmaxnm2.i
1521
}
1622

1723
define <2 x double> @f3(<2 x double> %a, <2 x double> %b) nounwind readnone ssp {
18-
; CHECK: fmaxnm.2d v0, v0, v1
19-
; CHECK: ret
24+
; CHECK-LABEL: f3:
25+
; CHECK: // %bb.0:
26+
; CHECK-NEXT: fmaxnm.2d v0, v0, v1
27+
; CHECK-NEXT: ret
2028
%vmaxnm2.i = tail call <2 x double> @llvm.aarch64.neon.fmaxnm.v2f64(<2 x double> %a, <2 x double> %b) nounwind
2129
ret <2 x double> %vmaxnm2.i
2230
}
2331

2432
define <2 x float> @f4(<2 x float> %a, <2 x float> %b) nounwind readnone ssp {
25-
; CHECK: fminnm.2s v0, v0, v1
26-
; CHECK: ret
33+
; CHECK-LABEL: f4:
34+
; CHECK: // %bb.0:
35+
; CHECK-NEXT: fminnm.2s v0, v0, v1
36+
; CHECK-NEXT: ret
2737
%vminnm2.i = tail call <2 x float> @llvm.aarch64.neon.fminnm.v2f32(<2 x float> %a, <2 x float> %b) nounwind
2838
ret <2 x float> %vminnm2.i
2939
}
3040

3141
define <4 x float> @f5(<4 x float> %a, <4 x float> %b) nounwind readnone ssp {
32-
; CHECK: fminnm.4s v0, v0, v1
33-
; CHECK: ret
42+
; CHECK-LABEL: f5:
43+
; CHECK: // %bb.0:
44+
; CHECK-NEXT: fminnm.4s v0, v0, v1
45+
; CHECK-NEXT: ret
3446
%vminnm2.i = tail call <4 x float> @llvm.aarch64.neon.fminnm.v4f32(<4 x float> %a, <4 x float> %b) nounwind
3547
ret <4 x float> %vminnm2.i
3648
}
3749

3850
define <2 x double> @f6(<2 x double> %a, <2 x double> %b) nounwind readnone ssp {
39-
; CHECK: fminnm.2d v0, v0, v1
40-
; CHECK: ret
51+
; CHECK-LABEL: f6:
52+
; CHECK: // %bb.0:
53+
; CHECK-NEXT: fminnm.2d v0, v0, v1
54+
; CHECK-NEXT: ret
4155
%vminnm2.i = tail call <2 x double> @llvm.aarch64.neon.fminnm.v2f64(<2 x double> %a, <2 x double> %b) nounwind
4256
ret <2 x double> %vminnm2.i
4357
}
4458

4559
define float @f7(float %a, float %b) nounwind readnone ssp {
46-
; CHECK: fmaxnm s0, s0, s1
47-
; CHECK: ret
60+
; CHECK-LABEL: f7:
61+
; CHECK: // %bb.0:
62+
; CHECK-NEXT: fmaxnm s0, s0, s1
63+
; CHECK-NEXT: ret
4864
%vmaxnm2.i = tail call float @llvm.aarch64.neon.fmaxnm.f32(float %a, float %b) nounwind
4965
ret float %vmaxnm2.i
5066
}
5167

5268
define double @f8(double %a, double %b) nounwind readnone ssp {
53-
; CHECK: fminnm d0, d0, d1
54-
; CHECK: ret
69+
; CHECK-LABEL: f8:
70+
; CHECK: // %bb.0:
71+
; CHECK-NEXT: fminnm d0, d0, d1
72+
; CHECK-NEXT: ret
5573
%vmaxnm2.i = tail call double @llvm.aarch64.neon.fminnm.f64(double %a, double %b) nounwind
5674
ret double %vmaxnm2.i
5775
}
@@ -67,14 +85,18 @@ declare double @llvm.aarch64.neon.fminnm.f64(double, double) nounwind readnone
6785

6886
define double @test_fmaxnmv(<2 x double> %in) {
6987
; CHECK-LABEL: test_fmaxnmv:
70-
; CHECK: fmaxnmp.2d d0, v0
88+
; CHECK: // %bb.0:
89+
; CHECK-NEXT: fmaxnmp.2d d0, v0
90+
; CHECK-NEXT: ret
7191
%max = call double @llvm.aarch64.neon.fmaxnmv.f64.v2f64(<2 x double> %in)
7292
ret double %max
7393
}
7494

7595
define double @test_fminnmv(<2 x double> %in) {
7696
; CHECK-LABEL: test_fminnmv:
77-
; CHECK: fminnmp.2d d0, v0
97+
; CHECK: // %bb.0:
98+
; CHECK-NEXT: fminnmp.2d d0, v0
99+
; CHECK-NEXT: ret
78100
%min = call double @llvm.aarch64.neon.fminnmv.f64.v2f64(<2 x double> %in)
79101
ret double %min
80102
}

0 commit comments

Comments
 (0)