diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp b/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.cpp @@ -1378,6 +1378,12 @@ case RISCV::XOR: case RISCV::MUL: case RISCV::MULW: + case RISCV::FMIN_H: + case RISCV::FMIN_S: + case RISCV::FMIN_D: + case RISCV::FMAX_H: + case RISCV::FMAX_S: + case RISCV::FMAX_D: return true; } diff --git a/llvm/test/CodeGen/RISCV/machine-combiner.ll b/llvm/test/CodeGen/RISCV/machine-combiner.ll --- a/llvm/test/CodeGen/RISCV/machine-combiner.ll +++ b/llvm/test/CodeGen/RISCV/machine-combiner.ll @@ -1,5 +1,5 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py -; RUN: llc -mtriple=riscv64 -mattr=+d -verify-machineinstrs -mcpu=sifive-u74 \ +; RUN: llc -mtriple=riscv64 -mattr=+d,+zfh -verify-machineinstrs -mcpu=sifive-u74 \ ; RUN: -O1 -riscv-enable-machine-combiner=true < %s | \ ; RUN: FileCheck %s @@ -731,3 +731,88 @@ %t2 = mul i64 %t1, %a3 ret i64 %t2 } + +define half @test_fmin_f16(half %a0, half %a1, half %a2, half %a3) { +; CHECK-LABEL: test_fmin_f16: +; CHECK: # %bb.0: +; CHECK-NEXT: fmin.h ft0, fa0, fa1 +; CHECK-NEXT: fmin.h ft1, fa2, fa3 +; CHECK-NEXT: fmin.h fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call half @llvm.minnum.f16(half %a0, half %a1) + %t1 = call half @llvm.minnum.f16(half %t0, half %a2) + %t2 = call half @llvm.minnum.f16(half %t1, half %a3) + ret half %t2 +} + +define float @test_fmin_f32(float %a0, float %a1, float %a2, float %a3) { +; CHECK-LABEL: test_fmin_f32: +; CHECK: # %bb.0: +; CHECK-NEXT: fmin.s ft0, fa0, fa1 +; CHECK-NEXT: fmin.s ft1, fa2, fa3 +; CHECK-NEXT: fmin.s fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call float @llvm.minnum.f32(float %a0, float %a1) + %t1 = call float @llvm.minnum.f32(float %t0, float %a2) + %t2 = call float @llvm.minnum.f32(float %t1, float %a3) + ret float %t2 +} + +define double @test_fmin_f64(double %a0, double %a1, double %a2, double %a3) { +; CHECK-LABEL: test_fmin_f64: +; CHECK: # %bb.0: +; CHECK-NEXT: fmin.d ft0, fa0, fa1 +; CHECK-NEXT: fmin.d ft1, fa2, fa3 +; CHECK-NEXT: fmin.d fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call double @llvm.minnum.f64(double %a0, double %a1) + %t1 = call double @llvm.minnum.f64(double %t0, double %a2) + %t2 = call double @llvm.minnum.f64(double %t1, double %a3) + ret double %t2 +} + +define half @test_fmax_f16(half %a0, half %a1, half %a2, half %a3) { +; CHECK-LABEL: test_fmax_f16: +; CHECK: # %bb.0: +; CHECK-NEXT: fmax.h ft0, fa0, fa1 +; CHECK-NEXT: fmax.h ft1, fa2, fa3 +; CHECK-NEXT: fmax.h fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call half @llvm.maxnum.f16(half %a0, half %a1) + %t1 = call half @llvm.maxnum.f16(half %t0, half %a2) + %t2 = call half @llvm.maxnum.f16(half %t1, half %a3) + ret half %t2 +} + +define float @test_fmax_f32(float %a0, float %a1, float %a2, float %a3) { +; CHECK-LABEL: test_fmax_f32: +; CHECK: # %bb.0: +; CHECK-NEXT: fmax.s ft0, fa0, fa1 +; CHECK-NEXT: fmax.s ft1, fa2, fa3 +; CHECK-NEXT: fmax.s fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call float @llvm.maxnum.f32(float %a0, float %a1) + %t1 = call float @llvm.maxnum.f32(float %t0, float %a2) + %t2 = call float @llvm.maxnum.f32(float %t1, float %a3) + ret float %t2 +} + +define double @test_fmax_f64(double %a0, double %a1, double %a2, double %a3) { +; CHECK-LABEL: test_fmax_f64: +; CHECK: # %bb.0: +; CHECK-NEXT: fmax.d ft0, fa0, fa1 +; CHECK-NEXT: fmax.d ft1, fa2, fa3 +; CHECK-NEXT: fmax.d fa0, ft0, ft1 +; CHECK-NEXT: ret + %t0 = call double @llvm.maxnum.f64(double %a0, double %a1) + %t1 = call double @llvm.maxnum.f64(double %t0, double %a2) + %t2 = call double @llvm.maxnum.f64(double %t1, double %a3) + ret double %t2 +} + +declare half @llvm.minnum.f16(half, half) +declare float @llvm.minnum.f32(float, float) +declare double @llvm.minnum.f64(double, double) +declare half @llvm.maxnum.f16(half, half) +declare float @llvm.maxnum.f32(float, float) +declare double @llvm.maxnum.f64(double, double)