[PATCH] D84220: [IPSCCP] Fix a bug that the "returned" attribute is not cleared when function is optimized to return undef

Congzhe Cao via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Jul 31 09:22:12 PDT 2020


congzhe updated this revision to Diff 282245.
congzhe added a comment.

comments addressed:

1. keep a set of zapped functions to avoid removing the attribute for a function more than one times, since a single function can have multiple returns to zap.

2. also remove the returned attribte for call sites that correspond to the zapped functions

3. updated the test file to reflect the changes


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D84220/new/

https://reviews.llvm.org/D84220

Files:
  llvm/lib/Transforms/Scalar/SCCP.cpp
  llvm/test/Transforms/SCCP/ipsccp-clear-returned.ll


Index: llvm/test/Transforms/SCCP/ipsccp-clear-returned.ll
===================================================================
--- /dev/null
+++ llvm/test/Transforms/SCCP/ipsccp-clear-returned.ll
@@ -0,0 +1,24 @@
+; if IPSCCP determines a function returns undef,
+; then the "returned" attribute of input arguments
+; should be cleared.
+
+; RUN: opt < %s -ipsccp -S | FileCheck %s
+define i32 @main() {
+; CHECK-LABEL: @main
+entry:
+; CHECK-NEXT: entry:
+  %call = call i32 @func_return_undef(i32 returned 1)
+; CHECK: call i32 @func_return_undef(i32 1)
+; CHECK-NOT: returned
+  ret i32 %call
+; CHECK: ret i32 1
+}
+
+define internal i32 @func_return_undef(i32 returned %arg) {
+; CHECK: {{define.*@func_return_undef}}
+; CHECK-NOT: returned
+entry:
+; CHECK-NEXT: entry:
+; CHECK-NEXT: {{ret.*undef}}
+ret i32 %arg
+}
Index: llvm/lib/Transforms/Scalar/SCCP.cpp
===================================================================
--- llvm/lib/Transforms/Scalar/SCCP.cpp
+++ llvm/lib/Transforms/Scalar/SCCP.cpp
@@ -34,6 +34,7 @@
 #include "llvm/Analysis/ValueLattice.h"
 #include "llvm/Analysis/ValueLatticeUtils.h"
 #include "llvm/IR/BasicBlock.h"
+#include "llvm/IR/AbstractCallSite.h"
 #include "llvm/IR/Constant.h"
 #include "llvm/IR/Constants.h"
 #include "llvm/IR/DataLayout.h"
@@ -2035,11 +2036,29 @@
   }
 
   // Zap all returns which we've identified as zap to change.
+  SmallPtrSet<Function*, 8> FuncZappedReturn;
   for (unsigned i = 0, e = ReturnsToZap.size(); i != e; ++i) {
     Function *F = ReturnsToZap[i]->getParent()->getParent();
     ReturnsToZap[i]->setOperand(0, UndefValue::get(F->getReturnType()));
+    // Record all functions that are zapped
+    if (FuncZappedReturn.find(F) == FuncZappedReturn.end())
+      FuncZappedReturn.insert(F);
+  }
+
+  // Remove the returned attribute for zapped functions and the
+  // corresponding call sites
+  for (Function *F : FuncZappedReturn) {
+    for (Argument &A : F->args())
+      F->removeParamAttr(A.getArgNo(), Attribute::Returned);
+    for (Use &U : F->uses()) {
+      CallBase *CB = dyn_cast<CallBase>(U.getUser());
+      if (!CB)
+        continue;
+      for (auto &arg : CB->args()) {
+        CB->removeParamAttr(CB->getArgOperandNo(&arg), Attribute::Returned);
+      }
+    }
   }
-
   // If we inferred constant or undef values for globals variables, we can
   // delete the global and any stores that remain to it.
   for (auto &I : make_early_inc_range(Solver.getTrackedGlobals())) {


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D84220.282245.patch
Type: text/x-patch
Size: 2536 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20200731/62d320af/attachment.bin>


More information about the llvm-commits mailing list