brintos

brintos / llvm-project-archived public Read only

0
0
Text · 7.2 KiB · 40b6f02 Raw
226 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; RUN: llc -mtriple=amdgcn -mcpu=tahiti < %s | FileCheck -enable-var-scope -check-prefix=SI %s3;4; Most SALU instructions ignore control flow, so we need to make sure5; they don't overwrite values from other blocks.6 7; If the branch decision is made based on a value in an SGPR then all8; threads will execute the same code paths, so we don't need to worry9; about instructions in different blocks overwriting each other.10 11define amdgpu_kernel void @sgpr_if_else_salu_br(ptr addrspace(1) %out, i32 %a, i32 %b, i32 %c, i32 %d, i32 %e) {12; SI-LABEL: sgpr_if_else_salu_br:13; SI:       ; %bb.0: ; %entry14; SI-NEXT:    s_load_dwordx4 s[0:3], s[4:5], 0xb15; SI-NEXT:    s_load_dword s6, s[4:5], 0xf16; SI-NEXT:    s_waitcnt lgkmcnt(0)17; SI-NEXT:    s_cmp_lg_u32 s0, 018; SI-NEXT:    s_cbranch_scc0 .LBB0_419; SI-NEXT:  ; %bb.1: ; %else20; SI-NEXT:    s_add_i32 s3, s3, s621; SI-NEXT:    s_cbranch_execnz .LBB0_322; SI-NEXT:  .LBB0_2: ; %if23; SI-NEXT:    s_sub_i32 s3, s1, s224; SI-NEXT:  .LBB0_3: ; %endif25; SI-NEXT:    s_load_dwordx2 s[4:5], s[4:5], 0x926; SI-NEXT:    s_add_i32 s0, s3, s027; SI-NEXT:    s_mov_b32 s7, 0xf00028; SI-NEXT:    s_mov_b32 s6, -129; SI-NEXT:    v_mov_b32_e32 v0, s030; SI-NEXT:    s_waitcnt lgkmcnt(0)31; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 032; SI-NEXT:    s_endpgm33; SI-NEXT:  .LBB0_4:34; SI-NEXT:    ; implicit-def: $sgpr335; SI-NEXT:    s_branch .LBB0_236 37entry:38  %0 = icmp eq i32 %a, 039  br i1 %0, label %if, label %else40 41if:42  %1 = sub i32 %b, %c43  br label %endif44 45else:46  %2 = add i32 %d, %e47  br label %endif48 49endif:50  %3 = phi i32 [%1, %if], [%2, %else]51  %4 = add i32 %3, %a52  store i32 %4, ptr addrspace(1) %out53  ret void54}55 56define amdgpu_kernel void @sgpr_if_else_salu_br_opt(ptr addrspace(1) %out, [8 x i32], i32 %a, [8 x i32], i32 %b, [8 x i32], i32 %c, [8 x i32], i32 %d, [8 x i32], i32 %e) {57; SI-LABEL: sgpr_if_else_salu_br_opt:58; SI:       ; %bb.0: ; %entry59; SI-NEXT:    s_load_dword s2, s[4:5], 0x1360; SI-NEXT:    s_waitcnt lgkmcnt(0)61; SI-NEXT:    s_cmp_lg_u32 s2, 062; SI-NEXT:    s_cbranch_scc0 .LBB1_463; SI-NEXT:  ; %bb.1: ; %else64; SI-NEXT:    s_load_dword s0, s[4:5], 0x2e65; SI-NEXT:    s_load_dword s1, s[4:5], 0x3766; SI-NEXT:    s_waitcnt lgkmcnt(0)67; SI-NEXT:    s_add_i32 s3, s0, s168; SI-NEXT:    s_cbranch_execnz .LBB1_369; SI-NEXT:  .LBB1_2: ; %if70; SI-NEXT:    s_load_dword s0, s[4:5], 0x1c71; SI-NEXT:    s_load_dword s1, s[4:5], 0x2572; SI-NEXT:    s_waitcnt lgkmcnt(0)73; SI-NEXT:    s_add_i32 s3, s0, s174; SI-NEXT:  .LBB1_3: ; %endif75; SI-NEXT:    s_load_dwordx2 s[4:5], s[4:5], 0x976; SI-NEXT:    s_add_i32 s0, s3, s277; SI-NEXT:    s_mov_b32 s7, 0xf00078; SI-NEXT:    s_mov_b32 s6, -179; SI-NEXT:    v_mov_b32_e32 v0, s080; SI-NEXT:    s_waitcnt lgkmcnt(0)81; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 082; SI-NEXT:    s_endpgm83; SI-NEXT:  .LBB1_4:84; SI-NEXT:    ; implicit-def: $sgpr385; SI-NEXT:    s_branch .LBB1_286 87entry:88  %cmp0 = icmp eq i32 %a, 089  br i1 %cmp0, label %if, label %else90 91if:92  %add0 = add i32 %b, %c93  br label %endif94 95else:96  %add1 = add i32 %d, %e97  br label %endif98 99endif:100  %phi = phi i32 [%add0, %if], [%add1, %else]101  %add2 = add i32 %phi, %a102  store i32 %add2, ptr addrspace(1) %out103  ret void104}105 106; The two S_ADD instructions should write to different registers, since107; different threads will take different control flow paths.108define amdgpu_kernel void @sgpr_if_else_valu_br(ptr addrspace(1) %out, float %a, i32 %b, i32 %c, i32 %d, i32 %e) {109; SI-LABEL: sgpr_if_else_valu_br:110; SI:       ; %bb.0: ; %entry111; SI-NEXT:    s_load_dwordx4 s[0:3], s[4:5], 0xc112; SI-NEXT:    v_cvt_f32_u32_e32 v0, v0113; SI-NEXT:    ; implicit-def: $sgpr8114; SI-NEXT:    v_cmp_lg_f32_e32 vcc, 0, v0115; SI-NEXT:    s_and_saveexec_b64 s[6:7], vcc116; SI-NEXT:    s_xor_b64 s[6:7], exec, s[6:7]117; SI-NEXT:    s_cbranch_execz .LBB2_2118; SI-NEXT:  ; %bb.1: ; %else119; SI-NEXT:    s_waitcnt lgkmcnt(0)120; SI-NEXT:    s_add_i32 s8, s2, s3121; SI-NEXT:  .LBB2_2: ; %Flow122; SI-NEXT:    s_waitcnt lgkmcnt(0)123; SI-NEXT:    s_or_saveexec_b64 s[2:3], s[6:7]124; SI-NEXT:    v_mov_b32_e32 v0, s8125; SI-NEXT:    s_xor_b64 exec, exec, s[2:3]126; SI-NEXT:  ; %bb.3: ; %if127; SI-NEXT:    s_add_i32 s0, s0, s1128; SI-NEXT:    v_mov_b32_e32 v0, s0129; SI-NEXT:  ; %bb.4: ; %endif130; SI-NEXT:    s_or_b64 exec, exec, s[2:3]131; SI-NEXT:    s_load_dwordx2 s[0:1], s[4:5], 0x9132; SI-NEXT:    s_mov_b32 s3, 0xf000133; SI-NEXT:    s_mov_b32 s2, -1134; SI-NEXT:    s_waitcnt lgkmcnt(0)135; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0136; SI-NEXT:    s_endpgm137entry:138  %tid = call i32 @llvm.amdgcn.workitem.id.x() #0139  %tid_f = uitofp i32 %tid to float140  %tmp1 = fcmp ueq float %tid_f, 0.0141  br i1 %tmp1, label %if, label %else142 143if:144  %tmp2 = add i32 %b, %c145  br label %endif146 147else:148  %tmp3 = add i32 %d, %e149  br label %endif150 151endif:152  %tmp4 = phi i32 [%tmp2, %if], [%tmp3, %else]153  store i32 %tmp4, ptr addrspace(1) %out154  ret void155}156 157define amdgpu_kernel void @sgpr_if_else_valu_cmp_phi_br(ptr addrspace(1) %out, ptr addrspace(1) %a, ptr addrspace(1) %b) {158; SI-LABEL: sgpr_if_else_valu_cmp_phi_br:159; SI:       ; %bb.0: ; %entry160; SI-NEXT:    s_load_dwordx4 s[0:3], s[4:5], 0x9161; SI-NEXT:    s_load_dwordx2 s[4:5], s[4:5], 0xd162; SI-NEXT:    s_mov_b32 s6, 0163; SI-NEXT:    v_cmp_ne_u32_e32 vcc, 0, v0164; SI-NEXT:    v_lshlrev_b32_e32 v0, 2, v0165; SI-NEXT:    ; implicit-def: $sgpr8_sgpr9166; SI-NEXT:    s_and_saveexec_b64 s[10:11], vcc167; SI-NEXT:    s_xor_b64 s[10:11], exec, s[10:11]168; SI-NEXT:    s_cbranch_execz .LBB3_2169; SI-NEXT:  ; %bb.1: ; %else170; SI-NEXT:    s_mov_b32 s7, 0xf000171; SI-NEXT:    v_mov_b32_e32 v1, 0172; SI-NEXT:    s_waitcnt lgkmcnt(0)173; SI-NEXT:    buffer_load_dword v0, v[0:1], s[4:7], 0 addr64174; SI-NEXT:    s_waitcnt vmcnt(0)175; SI-NEXT:    v_cmp_gt_i32_e64 s[8:9], 0, v0176; SI-NEXT:    ; implicit-def: $vgpr0177; SI-NEXT:  .LBB3_2: ; %Flow178; SI-NEXT:    s_waitcnt lgkmcnt(0)179; SI-NEXT:    s_andn2_saveexec_b64 s[4:5], s[10:11]180; SI-NEXT:    s_cbranch_execz .LBB3_4181; SI-NEXT:  ; %bb.3: ; %if182; SI-NEXT:    s_mov_b32 s15, 0xf000183; SI-NEXT:    s_mov_b32 s14, 0184; SI-NEXT:    s_mov_b64 s[12:13], s[2:3]185; SI-NEXT:    v_mov_b32_e32 v1, 0186; SI-NEXT:    buffer_load_dword v0, v[0:1], s[12:15], 0 addr64187; SI-NEXT:    s_andn2_b64 s[2:3], s[8:9], exec188; SI-NEXT:    s_waitcnt vmcnt(0)189; SI-NEXT:    v_cmp_eq_u32_e32 vcc, 0, v0190; SI-NEXT:    s_and_b64 s[6:7], vcc, exec191; SI-NEXT:    s_or_b64 s[8:9], s[2:3], s[6:7]192; SI-NEXT:  .LBB3_4: ; %endif193; SI-NEXT:    s_or_b64 exec, exec, s[4:5]194; SI-NEXT:    s_mov_b32 s3, 0xf000195; SI-NEXT:    s_mov_b32 s2, -1196; SI-NEXT:    v_cndmask_b32_e64 v0, 0, -1, s[8:9]197; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0198; SI-NEXT:    s_endpgm199entry:200  %tid = call i32 @llvm.amdgcn.workitem.id.x() #0201  %tmp1 = icmp eq i32 %tid, 0202  br i1 %tmp1, label %if, label %else203 204if:205  %gep.if = getelementptr i32, ptr addrspace(1) %a, i32 %tid206  %a.val = load i32, ptr addrspace(1) %gep.if207  %cmp.if = icmp eq i32 %a.val, 0208  br label %endif209 210else:211  %gep.else = getelementptr i32, ptr addrspace(1) %b, i32 %tid212  %b.val = load i32, ptr addrspace(1) %gep.else213  %cmp.else = icmp slt i32 %b.val, 0214  br label %endif215 216endif:217  %tmp4 = phi i1 [%cmp.if, %if], [%cmp.else, %else]218  %ext = sext i1 %tmp4 to i32219  store i32 %ext, ptr addrspace(1) %out220  ret void221}222 223declare i32 @llvm.amdgcn.workitem.id.x() #0224 225attributes #0 = { readnone }226