Index: lib/Transforms/InstCombine/InstCombineCalls.cpp =================================================================== --- lib/Transforms/InstCombine/InstCombineCalls.cpp +++ lib/Transforms/InstCombine/InstCombineCalls.cpp @@ -4233,6 +4233,11 @@ ValueHandleBase::ValueIsDeleted(Caller); } + // Drop references from bitcast constant expression to the callee. + if (auto *Op = dyn_cast(Caller->getOperand(0))) + if (Op->hasOneUse()) + Op->dropAllReferences(); + eraseInstFromFunction(*Caller); return true; } Index: test/Transforms/Inline/inline-constexpr-cast-call.ll =================================================================== --- test/Transforms/Inline/inline-constexpr-cast-call.ll +++ test/Transforms/Inline/inline-constexpr-cast-call.ll @@ -0,0 +1,22 @@ +; RUN: opt < %s -instcombine -inline -inline-threshold=0 + +; CHECK: define i32 @main() { +; CHECK: %1 = call i32 @rand() +; CHECK: %2 = call i32 @rand() +; CHECK: %3 = add nsw i32 %1, %2 +; CHECK: ret i32 %3 +; CHECK: } + +define internal i32 @foo() #0 { + %1 = call i32 @rand() #2 + %2 = call i32 @rand() #2 + %3 = add nsw i32 %1, %2 + ret i32 %3 +} + +declare i32 @rand() #1 + +define i32 @main() #0 { + %1 = tail call i32 (...) bitcast (i32 ()* @foo to i32 (...)*)() #2 + ret i32 %1 +}