1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 2; RUN: llc < %s -mcpu=generic -mtriple=i686-- -post-RA-scheduler=false | FileCheck %s 3; rdar://7226797 4 5; LLVM should omit the testl and use the flags result from the orl. 6 7define void @or(ptr %A, i32 %IA, i32 %N) nounwind { 8; CHECK-LABEL: or: 9; CHECK: # %bb.0: # %entry 10; CHECK-NEXT: movl {{[0-9]+}}(%esp), %eax 11; CHECK-NEXT: movl {{[0-9]+}}(%esp), %ecx 12; CHECK-NEXT: movl %eax, %edx 13; CHECK-NEXT: andl $3, %edx 14; CHECK-NEXT: xorl $1, %ecx 15; CHECK-NEXT: orl %edx, %ecx 16; CHECK-NEXT: je .LBB0_2 17; CHECK-NEXT: # %bb.1: # %bb 18; CHECK-NEXT: movl $0, (%eax) 19; CHECK-NEXT: .LBB0_2: # %return 20; CHECK-NEXT: retl 21entry: 22 %0 = ptrtoint ptr %A to i32 ; <i32> [#uses=1] 23 %1 = and i32 %0, 3 ; <i32> [#uses=1] 24 %2 = xor i32 %IA, 1 ; <i32> [#uses=1] 25 %3 = or i32 %2, %1 ; <i32> [#uses=1] 26 %4 = icmp eq i32 %3, 0 ; <i1> [#uses=1] 27 br i1 %4, label %return, label %bb 28 29bb: ; preds = %entry 30 store float 0.000000e+00, ptr %A, align 4 31 ret void 32 33return: ; preds = %entry 34 ret void 35} 36 37define void @xor(ptr %A, i32 %IA, i32 %N) nounwind { 38; CHECK-LABEL: xor: 39; CHECK: # %bb.0: # %entry 40; CHECK-NEXT: movl {{[0-9]+}}(%esp), %eax 41; CHECK-NEXT: movl %eax, %ecx 42; CHECK-NEXT: andl $3, %ecx 43; CHECK-NEXT: xorl {{[0-9]+}}(%esp), %ecx 44; CHECK-NEXT: cmpl $1, %ecx 45; CHECK-NEXT: je .LBB1_2 46; CHECK-NEXT: # %bb.1: # %bb 47; CHECK-NEXT: movl $0, (%eax) 48; CHECK-NEXT: .LBB1_2: # %return 49; CHECK-NEXT: retl 50entry: 51 %0 = ptrtoint ptr %A to i32 ; <i32> [#uses=1] 52 %1 = and i32 %0, 3 ; <i32> [#uses=1] 53 %2 = xor i32 %IA, 1 ; <i32> [#uses=1] 54 %3 = xor i32 %2, %1 ; <i32> [#uses=1] 55 %4 = icmp eq i32 %3, 0 ; <i1> [#uses=1] 56 br i1 %4, label %return, label %bb 57 58bb: ; preds = %entry 59 store float 0.000000e+00, ptr %A, align 4 60 ret void 61 62return: ; preds = %entry 63 ret void 64} 65 66define void @and(ptr %A, i32 %IA, i32 %N, ptr %p) nounwind { 67; CHECK-LABEL: and: 68; CHECK: # %bb.0: # %entry 69; CHECK-NEXT: movl {{[0-9]+}}(%esp), %ecx 70; CHECK-NEXT: movl {{[0-9]+}}(%esp), %eax 71; CHECK-NEXT: xorl $1, %eax 72; CHECK-NEXT: andl {{[0-9]+}}(%esp), %eax 73; CHECK-NEXT: andl $3, %eax 74; CHECK-NEXT: movb %al, (%ecx) 75; CHECK-NEXT: je .LBB2_2 76; CHECK-NEXT: # %bb.1: # %bb 77; CHECK-NEXT: movl $0, 0 78; CHECK-NEXT: .LBB2_2: # %return 79; CHECK-NEXT: retl 80entry: 81 store i8 0, ptr %p 82 %0 = ptrtoint ptr %A to i32 ; <i32> [#uses=1] 83 %1 = and i32 %0, 3 ; <i32> [#uses=1] 84 %2 = xor i32 %IA, 1 ; <i32> [#uses=1] 85 %3 = and i32 %2, %1 ; <i32> [#uses=1] 86 %t = trunc i32 %3 to i8 87 store i8 %t, ptr %p 88 %4 = icmp eq i32 %3, 0 ; <i1> [#uses=1] 89 br i1 %4, label %return, label %bb 90 91bb: ; preds = %entry 92 store float 0.000000e+00, ptr null, align 4 93 ret void 94 95return: ; preds = %entry 96 ret void 97} 98 99; Just like @and, but without the trunc+store. This should use a testb 100; instead of an andl. 101define void @test(ptr %A, i32 %IA, i32 %N, ptr %p) nounwind { 102; CHECK-LABEL: test: 103; CHECK: # %bb.0: # %entry 104; CHECK-NEXT: movl {{[0-9]+}}(%esp), %eax 105; CHECK-NEXT: movl {{[0-9]+}}(%esp), %ecx 106; CHECK-NEXT: movb $0, (%ecx) 107; CHECK-NEXT: xorl $1, %eax 108; CHECK-NEXT: andl {{[0-9]+}}(%esp), %eax 109; CHECK-NEXT: testb $3, %al 110; CHECK-NEXT: je .LBB3_2 111; CHECK-NEXT: # %bb.1: # %bb 112; CHECK-NEXT: movl $0, 0 113; CHECK-NEXT: .LBB3_2: # %return 114; CHECK-NEXT: retl 115entry: 116 store i8 0, ptr %p 117 %0 = ptrtoint ptr %A to i32 ; <i32> [#uses=1] 118 %1 = and i32 %0, 3 ; <i32> [#uses=1] 119 %2 = xor i32 %IA, 1 ; <i32> [#uses=1] 120 %3 = and i32 %2, %1 ; <i32> [#uses=1] 121 %4 = icmp eq i32 %3, 0 ; <i1> [#uses=1] 122 br i1 %4, label %return, label %bb 123 124bb: ; preds = %entry 125 store float 0.000000e+00, ptr null, align 4 126 ret void 127 128return: ; preds = %entry 129 ret void 130} 131