1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 2; RUN: llc -mtriple=amdgcn -mcpu=gfx1200 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX12,SDAG %s 3; RUN: llc -global-isel -mtriple=amdgcn -mcpu=gfx1200 -verify-machineinstrs < %s | FileCheck -check-prefixes=GFX12,GISEL %s 4 5define amdgpu_ps float @test_minmax_f32(float %a, float %b, float %c) { 6; GFX12-LABEL: test_minmax_f32: 7; GFX12: ; %bb.0: 8; GFX12-NEXT: v_maximumminimum_f32 v0, v0, v1, v2 9; GFX12-NEXT: ; return to shader part epilog 10 %max = call float @llvm.maximum.f32(float %a, float %b) 11 %minmax = call float @llvm.minimum.f32(float %max, float %c) 12 ret float %minmax 13} 14 15define amdgpu_ps void @s_test_minmax_f32(float inreg %a, float inreg %b, float inreg %c, ptr addrspace(1) inreg %out) { 16; SDAG-LABEL: s_test_minmax_f32: 17; SDAG: ; %bb.0: 18; SDAG-NEXT: s_maximum_f32 s0, s0, s1 19; SDAG-NEXT: s_mov_b32 s5, s4 20; SDAG-NEXT: s_mov_b32 s4, s3 21; SDAG-NEXT: s_delay_alu instid0(SALU_CYCLE_1) | instskip(NEXT) | instid1(SALU_CYCLE_3) 22; SDAG-NEXT: s_minimum_f32 s0, s0, s2 23; SDAG-NEXT: v_dual_mov_b32 v0, 0 :: v_dual_mov_b32 v1, s0 24; SDAG-NEXT: global_store_b32 v0, v1, s[4:5] 25; SDAG-NEXT: s_endpgm 26; 27; GISEL-LABEL: s_test_minmax_f32: 28; GISEL: ; %bb.0: 29; GISEL-NEXT: s_maximum_f32 s0, s0, s1 30; GISEL-NEXT: s_mov_b32 s6, s3 31; GISEL-NEXT: s_mov_b32 s7, s4 32; GISEL-NEXT: v_mov_b32_e32 v1, 0 33; GISEL-NEXT: s_minimum_f32 s0, s0, s2 34; GISEL-NEXT: s_delay_alu instid0(SALU_CYCLE_3) 35; GISEL-NEXT: v_mov_b32_e32 v0, s0 36; GISEL-NEXT: global_store_b32 v1, v0, s[6:7] 37; GISEL-NEXT: s_endpgm 38 %smax = call float @llvm.maximum.f32(float %a, float %b) 39 %sminmax = call float @llvm.minimum.f32(float %smax, float %c) 40 store float %sminmax, ptr addrspace(1) %out 41 ret void 42} 43 44define amdgpu_ps float @test_minmax_commuted_f32(float %a, float %b, float %c) { 45; GFX12-LABEL: test_minmax_commuted_f32: 46; GFX12: ; %bb.0: 47; GFX12-NEXT: v_maximumminimum_f32 v0, v0, v1, v2 48; GFX12-NEXT: ; return to shader part epilog 49 %max = call float @llvm.maximum.f32(float %a, float %b) 50 %minmax = call float @llvm.minimum.f32(float %c, float %max) 51 ret float %minmax 52} 53 54define amdgpu_ps float @test_maxmin_f32(float %a, float %b, float %c) { 55; GFX12-LABEL: test_maxmin_f32: 56; GFX12: ; %bb.0: 57; GFX12-NEXT: v_minimummaximum_f32 v0, v0, v1, v2 58; GFX12-NEXT: ; return to shader part epilog 59 %min = call float @llvm.minimum.f32(float %a, float %b) 60 %maxmin = call float @llvm.maximum.f32(float %min, float %c) 61 ret float %maxmin 62} 63 64define amdgpu_ps float @test_maxmin_commuted_f32(float %a, float %b, float %c) { 65; GFX12-LABEL: test_maxmin_commuted_f32: 66; GFX12: ; %bb.0: 67; GFX12-NEXT: v_minimummaximum_f32 v0, v0, v1, v2 68; GFX12-NEXT: ; return to shader part epilog 69 %min = call float @llvm.minimum.f32(float %a, float %b) 70 %maxmin = call float @llvm.maximum.f32(float %c, float %min) 71 ret float %maxmin 72} 73 74define amdgpu_ps half @test_minmax_f16(half %a, half %b, half %c) { 75; GFX12-LABEL: test_minmax_f16: 76; GFX12: ; %bb.0: 77; GFX12-NEXT: v_maximumminimum_f16 v0, v0, v1, v2 78; GFX12-NEXT: ; return to shader part epilog 79 %max = call half @llvm.maximum.f16(half %a, half %b) 80 %minmax = call half @llvm.minimum.f16(half %max, half %c) 81 ret half %minmax 82} 83 84define amdgpu_ps half @test_minmax_commuted_f16(half %a, half %b, half %c) { 85; GFX12-LABEL: test_minmax_commuted_f16: 86; GFX12: ; %bb.0: 87; GFX12-NEXT: v_maximumminimum_f16 v0, v0, v1, v2 88; GFX12-NEXT: ; return to shader part epilog 89 %max = call half @llvm.maximum.f16(half %a, half %b) 90 %minmax = call half @llvm.minimum.f16(half %c, half %max) 91 ret half %minmax 92} 93 94define amdgpu_ps half @test_maxmin_commuted_f16(half %a, half %b, half %c) { 95; GFX12-LABEL: test_maxmin_commuted_f16: 96; GFX12: ; %bb.0: 97; GFX12-NEXT: v_minimummaximum_f16 v0, v0, v1, v2 98; GFX12-NEXT: ; return to shader part epilog 99 %min = call half @llvm.minimum.f16(half %a, half %b) 100 %maxmin = call half @llvm.maximum.f16(half %c, half %min) 101 ret half %maxmin 102} 103 104define amdgpu_ps void @s_test_minmax_f16(half inreg %a, half inreg %b, half inreg %c, ptr addrspace(1) inreg %out) { 105; SDAG-LABEL: s_test_minmax_f16: 106; SDAG: ; %bb.0: 107; SDAG-NEXT: s_maximum_f16 s0, s0, s1 108; SDAG-NEXT: s_mov_b32 s5, s4 109; SDAG-NEXT: s_mov_b32 s4, s3 110; SDAG-NEXT: s_delay_alu instid0(SALU_CYCLE_1) | instskip(NEXT) | instid1(SALU_CYCLE_3) 111; SDAG-NEXT: s_minimum_f16 s0, s0, s2 112; SDAG-NEXT: v_dual_mov_b32 v0, 0 :: v_dual_mov_b32 v1, s0 113; SDAG-NEXT: global_store_b16 v0, v1, s[4:5] 114; SDAG-NEXT: s_endpgm 115; 116; GISEL-LABEL: s_test_minmax_f16: 117; GISEL: ; %bb.0: 118; GISEL-NEXT: s_maximum_f16 s0, s0, s1 119; GISEL-NEXT: s_mov_b32 s6, s3 120; GISEL-NEXT: s_mov_b32 s7, s4 121; GISEL-NEXT: v_mov_b32_e32 v1, 0 122; GISEL-NEXT: s_minimum_f16 s0, s0, s2 123; GISEL-NEXT: s_delay_alu instid0(SALU_CYCLE_3) 124; GISEL-NEXT: v_mov_b32_e32 v0, s0 125; GISEL-NEXT: global_store_b16 v1, v0, s[6:7] 126; GISEL-NEXT: s_endpgm 127 %smax = call half @llvm.maximum.f16(half %a, half %b) 128 %sminmax = call half @llvm.minimum.f16(half %smax, half %c) 129 store half %sminmax, ptr addrspace(1) %out 130 ret void 131} 132 133declare half @llvm.minimum.f16(half, half) 134declare half @llvm.maximum.f16(half, half) 135declare float @llvm.minimum.f32(float, float) 136declare float @llvm.maximum.f32(float, float) 137