diff --git a/llvm/lib/IR/ConstantFold.cpp b/llvm/lib/IR/ConstantFold.cpp --- a/llvm/lib/IR/ConstantFold.cpp +++ b/llvm/lib/IR/ConstantFold.cpp @@ -1751,9 +1751,15 @@ case Instruction::FPToSI: break; // We can't evaluate floating point casts or truncations. + case Instruction::BitCast: + // If this is a global value cast, check to see if the RHS is also a + // GlobalValue. + if (const GlobalValue *GV = dyn_cast(CE1Op0)) + if (const GlobalValue *GV2 = dyn_cast(V2)) + return areGlobalsPotentiallyEqual(GV, GV2); + LLVM_FALLTHROUGH; case Instruction::UIToFP: case Instruction::SIToFP: - case Instruction::BitCast: case Instruction::ZExt: case Instruction::SExt: // We can't evaluate floating point casts or truncations. diff --git a/llvm/test/Transforms/InstCombine/icmp-bitcast-glob.ll b/llvm/test/Transforms/InstCombine/icmp-bitcast-glob.ll new file mode 100644 --- /dev/null +++ b/llvm/test/Transforms/InstCombine/icmp-bitcast-glob.ll @@ -0,0 +1,30 @@ +; RUN: opt < %s -instcombine -S | FileCheck %s + +declare i32 @f32(i32**, i32**) + +declare i32 @f64(i64**, i64**) + +define i1 @icmp_func() { +; CHECK-LABEL: @icmp_func( +; CHECK: ret i1 false + %cmp = icmp eq i32 (i8*, i8*)* bitcast (i32 (i32**, i32**)* @f32 to i32 (i8*, i8*)*), bitcast (i32 (i64**, i64**)* @f64 to i32 (i8*, i8*)*) + ret i1 %cmp +} + +define i1 @icmp_fptr(i32 (i8*, i8*)*) { +; CHECK-LABEL: @icmp_fptr( +; CHECK: %cmp = icmp ne i32 (i8*, i8*)* %0, bitcast (i32 (i32**, i32**)* @f32 to i32 (i8*, i8*)*) +; CHECK: ret i1 %cmp + %cmp = icmp ne i32 (i8*, i8*)* bitcast (i32 (i32**, i32**)* @f32 to i32 (i8*, i8*)*), %0 + ret i1 %cmp +} + +@b = external global i32 + +define i32 @icmp_glob(i32 %x, i32 %y) { +; CHECK-LABEL: define i32 @icmp_glob(i32 %x, i32 %y) +; CHECK-NEXT: ret i32 %y +; + %sel = select i1 icmp eq (i32* bitcast (i32 (i32, i32)* @icmp_glob to i32*), i32* @b), i32 %x, i32 %y + ret i32 %sel +} diff --git a/llvm/test/Transforms/InstCombine/pr32686.ll b/llvm/test/Transforms/InstCombine/pr32686.ll --- a/llvm/test/Transforms/InstCombine/pr32686.ll +++ b/llvm/test/Transforms/InstCombine/pr32686.ll @@ -1,7 +1,7 @@ ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py ; RUN: opt -S -instcombine %s | FileCheck %s -@a = external global i8 +@a = common global i8 0, align 1 @b = external global i32 define void @tinkywinky() { diff --git a/llvm/test/Transforms/SCCP/ip-ranges-select.ll b/llvm/test/Transforms/SCCP/ip-ranges-select.ll --- a/llvm/test/Transforms/SCCP/ip-ranges-select.ll +++ b/llvm/test/Transforms/SCCP/ip-ranges-select.ll @@ -107,7 +107,7 @@ ret i1 %res } -@GV = external global i32 +@GV = common global i32 0, align 4 define i32 @f3_constantexpr_cond(i32 %x, i32 %y) { ; CHECK-LABEL: define i32 @f3_constantexpr_cond(i32 %x, i32 %y) diff --git a/llvm/test/Transforms/SCCP/undef-resolve.ll b/llvm/test/Transforms/SCCP/undef-resolve.ll --- a/llvm/test/Transforms/SCCP/undef-resolve.ll +++ b/llvm/test/Transforms/SCCP/undef-resolve.ll @@ -254,7 +254,7 @@ ret i64 %e } -@GV = external global i32 +@GV = common global i32 0, align 4 define i32 @test11(i1 %tobool) { ; CHECK-LABEL: @test11(