1; RUN: llc -verify-machineinstrs -march=amdgcn < %s | FileCheck -check-prefix=GCN %s 2; RUN: llc -verify-machineinstrs -march=amdgcn -mcpu=tonga < %s | FileCheck -check-prefix=GCN %s 3 4; When a frame index offset is more than 12-bits, make sure we don't store 5; it in mubuf's offset field. 6 7; Also, make sure we use the same register for storing the scratch buffer addresss 8; for both stores. This register is allocated by the register scavenger, so we 9; should be able to reuse the same regiser for each scratch buffer access. 10 11; GCN-LABEL: {{^}}legal_offset_fi: 12; GCN: buffer_store_dword v{{[0-9]+}}, off, s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+$}} 13; GCN: v_mov_b32_e32 [[OFFSET:v[0-9]+]], 0x8000 14; GCN: buffer_store_dword v{{[0-9]+}}, [[OFFSET]], s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}} 15 16define void @legal_offset_fi(i32 addrspace(1)* %out, i32 %cond, i32 %if_offset, i32 %else_offset) { 17entry: 18 %scratch0 = alloca [8192 x i32] 19 %scratch1 = alloca [8192 x i32] 20 21 %scratchptr0 = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 0 22 store i32 1, i32* %scratchptr0 23 24 %scratchptr1 = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 0 25 store i32 2, i32* %scratchptr1 26 27 %cmp = icmp eq i32 %cond, 0 28 br i1 %cmp, label %if, label %else 29 30if: 31 %if_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %if_offset 32 %if_value = load i32, i32* %if_ptr 33 br label %done 34 35else: 36 %else_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %else_offset 37 %else_value = load i32, i32* %else_ptr 38 br label %done 39 40done: 41 %value = phi i32 [%if_value, %if], [%else_value, %else] 42 store i32 %value, i32 addrspace(1)* %out 43 ret void 44 45 ret void 46 47} 48 49; GCN-LABEL: {{^}}legal_offset_fi_offset: 50; GCN-DAG: buffer_store_dword v{{[0-9]+}}, v{{[0-9]+}}, s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}} 51; GCN-DAG: v_add_i32_e32 [[OFFSET:v[0-9]+]], vcc, 0x8000 52; GCN: buffer_store_dword v{{[0-9]+}}, [[OFFSET]], s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}} 53 54define void @legal_offset_fi_offset(i32 addrspace(1)* %out, i32 %cond, i32 addrspace(1)* %offsets, i32 %if_offset, i32 %else_offset) { 55entry: 56 %scratch0 = alloca [8192 x i32] 57 %scratch1 = alloca [8192 x i32] 58 59 %offset0 = load i32, i32 addrspace(1)* %offsets 60 %scratchptr0 = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %offset0 61 store i32 %offset0, i32* %scratchptr0 62 63 %offsetptr1 = getelementptr i32, i32 addrspace(1)* %offsets, i32 1 64 %offset1 = load i32, i32 addrspace(1)* %offsetptr1 65 %scratchptr1 = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %offset1 66 store i32 %offset1, i32* %scratchptr1 67 68 %cmp = icmp eq i32 %cond, 0 69 br i1 %cmp, label %if, label %else 70 71if: 72 %if_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %if_offset 73 %if_value = load i32, i32* %if_ptr 74 br label %done 75 76else: 77 %else_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %else_offset 78 %else_value = load i32, i32* %else_ptr 79 br label %done 80 81done: 82 %value = phi i32 [%if_value, %if], [%else_value, %else] 83 store i32 %value, i32 addrspace(1)* %out 84 ret void 85} 86 87; GCN-LABEL: {{^}}neg_vaddr_offset: 88; GCN: buffer_store_dword v{{[0-9]+}}, v{{[0-9]+}}, s[{{[0-9]+:[0-9]+}}], s{{[0-9]+}} offen offset:16{{$}} 89define void @neg_vaddr_offset(i32 %offset) { 90entry: 91 %array = alloca [8192 x i32] 92 %ptr_offset = add i32 %offset, 4 93 %ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 %ptr_offset 94 store i32 0, i32* %ptr 95 ret void 96} 97 98; GCN-LABEL: {{^}}pos_vaddr_offset: 99; GCN: buffer_store_dword v{{[0-9]+}}, off, s[{{[0-9]+:[0-9]+}}], s{{[0-9]+}} offset:16 100define void @pos_vaddr_offset(i32 addrspace(1)* %out, i32 %offset) { 101entry: 102 %array = alloca [8192 x i32] 103 %ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 4 104 store i32 0, i32* %ptr 105 %load_ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 %offset 106 %val = load i32, i32* %load_ptr 107 store i32 %val, i32 addrspace(1)* %out 108 ret void 109} 110