[llvm] r330844 - [ICP] Do not attempt type matching for variable length arguments.

Taewook Oh via llvm-commits llvm-commits at lists.llvm.org
Wed Apr 25 10:19:21 PDT 2018


Author: twoh
Date: Wed Apr 25 10:19:21 2018
New Revision: 330844

URL: http://llvm.org/viewvc/llvm-project?rev=330844&view=rev
Log:
[ICP] Do not attempt type matching for variable length arguments.

Summary:
When performing indirect call promotion, current implementation inspects "all" parameters of the callsite and attemps to match with the formal argument type of the callee function. However, it is not possible to find the type for variable length arguments, and the compiler crashes when it attemps to match the type for variable lenght argument.

It seems that the bug is introduced with D40658. Prior to that, the type matching is performed only for the parameters whose ID is less than callee->getFunctionNumParams(). The attached test case will crash without the patch.

Reviewers: mssimpso, davidxl, davide

Reviewed By: mssimpso

Subscribers: llvm-commits

Differential Revision: https://reviews.llvm.org/D46026

Added:
    llvm/trunk/test/Transforms/PGOProfile/indirect_call_promotion_vla.ll
Modified:
    llvm/trunk/lib/Transforms/Utils/CallPromotionUtils.cpp

Modified: llvm/trunk/lib/Transforms/Utils/CallPromotionUtils.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Utils/CallPromotionUtils.cpp?rev=330844&r1=330843&r2=330844&view=diff
==============================================================================
--- llvm/trunk/lib/Transforms/Utils/CallPromotionUtils.cpp (original)
+++ llvm/trunk/lib/Transforms/Utils/CallPromotionUtils.cpp Wed Apr 25 10:19:21 2018
@@ -389,12 +389,14 @@ Instruction *llvm::promoteCall(CallSite
   // Inspect the arguments of the call site. If an argument's type doesn't
   // match the corresponding formal argument's type in the callee, bitcast it
   // to the correct type.
-  for (Use &U : CS.args()) {
-    unsigned ArgNo = CS.getArgumentNo(&U);
-    Type *FormalTy = Callee->getFunctionType()->getParamType(ArgNo);
-    Type *ActualTy = U.get()->getType();
+  auto CalleeType = Callee->getFunctionType();
+  auto CalleeParamNum = CalleeType->getNumParams();
+  for (unsigned ArgNo = 0; ArgNo < CalleeParamNum; ++ArgNo) {
+    auto *Arg = CS.getArgument(ArgNo); 
+    Type *FormalTy = CalleeType->getParamType(ArgNo);
+    Type *ActualTy = Arg->getType();
     if (FormalTy != ActualTy) {
-      auto *Cast = CastInst::Create(Instruction::BitCast, U.get(), FormalTy, "",
+      auto *Cast = CastInst::Create(Instruction::BitCast, Arg, FormalTy, "",
                                     CS.getInstruction());
       CS.setArgument(ArgNo, Cast);
     }

Added: llvm/trunk/test/Transforms/PGOProfile/indirect_call_promotion_vla.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/PGOProfile/indirect_call_promotion_vla.ll?rev=330844&view=auto
==============================================================================
--- llvm/trunk/test/Transforms/PGOProfile/indirect_call_promotion_vla.ll (added)
+++ llvm/trunk/test/Transforms/PGOProfile/indirect_call_promotion_vla.ll Wed Apr 25 10:19:21 2018
@@ -0,0 +1,28 @@
+; RUN: opt < %s -pgo-icall-prom -S | FileCheck %s
+
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-unknown-linux-gnu"
+
+%struct.A = type { i8 }
+%struct.B = type { i8 }
+ at foo = common global i32 (%struct.A*, ...)* null, align 8
+
+define i32 @func1(%struct.B* %x, ...) {
+entry:
+  ret i32 0
+}
+
+define i32 @bar(%struct.A* %x) {
+entry:
+  %tmp = load i32 (%struct.A*, ...)*, i32 (%struct.A*, ...)** @foo, align 8
+; CHECK:   [[CMP:%[0-9]+]] = icmp eq i32 (%struct.A*, ...)* %tmp, bitcast (i32 (%struct.B*, ...)* @func1 to i32 (%struct.A*, ...)*)
+; CHECK:   br i1 [[CMP]], label %if.true.direct_targ, label %if.false.orig_indirect, !prof [[BRANCH_WEIGHT:![0-9]+]]
+; CHECK: if.true.direct_targ:
+; CHECK:   [[DIRCALL_RET:%[0-9]+]] = call i32 (%struct.B*, ...) @func1
+; CHECK:   br label %if.end.icp
+  %call = call i32 (%struct.A*, ...) %tmp(%struct.A* %x, i32 0), !prof !1
+  ret i32 %call
+}
+
+; CHECK: [[BRANCH_WEIGHT]] = !{!"branch_weights", i32 1500, i32 100}
+!1 = !{!"VP", i32 0, i64 1600, i64 -2545542355363006406, i64 1500}




More information about the llvm-commits mailing list