[PATCH] D34862: [CGP] Relax a bit restriction for optimizeMemoryInst to extend scope

Serguei Katkov via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Thu Jun 29 21:40:13 PDT 2017


skatkov created this revision.

CodeGenPrepare::optimizeMemoryInst contains a check that we do nothing
if all instructions combining the address for memory instruction is in the same
block as memory instruction itself.

However if any of these instruction are placed after memory instruction then
address calculation will not be folded to memory instruction.

The added test case shows an example.


https://reviews.llvm.org/D34862

Files:
  lib/CodeGen/CodeGenPrepare.cpp
  test/CodeGen/X86/sink-gep-before-mem-inst.ll


Index: test/CodeGen/X86/sink-gep-before-mem-inst.ll
===================================================================
--- /dev/null
+++ test/CodeGen/X86/sink-gep-before-mem-inst.ll
@@ -0,0 +1,25 @@
+; RUN: opt < %s -S -codegenprepare -mtriple=x86_64-unknown-linux-gnu | FileCheck %s
+
+define i64 @test.after(i8 addrspace(1)* readonly align 8) {
+; CHECK-LABEL: test.after
+; CHECK: sunkaddr
+entry:
+  %.0 = getelementptr inbounds i8, i8 addrspace(1)* %0, i64 8
+  %addr = bitcast i8 addrspace(1)* %.0 to i32 addrspace(1)*
+  br label %header
+
+header:
+  %addr.in.loop = phi i32 addrspace(1)* [ %addr, %entry ], [ %addr.after, %header ]
+  %local_2_ = phi i64 [ 0, %entry ], [ %.9, %header ]
+  %.7 = load i32, i32 addrspace(1)* %addr.in.loop, align 8
+  fence acquire
+  %.1 = getelementptr inbounds i8, i8 addrspace(1)* %0, i64 8
+  %addr.after = bitcast i8 addrspace(1)* %.1 to i32 addrspace(1)*
+  %.8 = sext i32 %.7 to i64
+  %.9 = add i64 %local_2_, %.8
+  %not. = icmp sgt i64 %.9, 999
+  br i1 %not., label %exit, label %header
+
+exit:
+  ret i64 %.9
+}
Index: lib/CodeGen/CodeGenPrepare.cpp
===================================================================
--- lib/CodeGen/CodeGenPrepare.cpp
+++ lib/CodeGen/CodeGenPrepare.cpp
@@ -4227,11 +4227,20 @@
 
 } // end anonymous namespace
 
-/// Return true if the specified values are defined in a
-/// different basic block than BB.
-static bool IsNonLocalValue(Value *V, BasicBlock *BB) {
-  if (Instruction *I = dyn_cast<Instruction>(V))
-    return I->getParent() != BB;
+/// Return true if the specified value is defined in a
+/// different basic block than I or is defined in the same BB but after BI.
+static bool IsNonLocalValueOrAfter(Value *V, Instruction *BI) {
+  BasicBlock *BB = BI->getParent();
+  if (Instruction *I = dyn_cast<Instruction>(V)) {
+    if (I->getParent() != BB)
+      return true;
+    for (Instruction &BBI : *BB) {
+      if (&BBI == I)
+        return false;
+      if (&BBI == BI)
+        return true;
+    }
+  }
   return false;
 }
 
@@ -4343,7 +4352,7 @@
 
   // If all the instructions matched are already in this BB, don't do anything.
   if (none_of(AddrModeInsts, [&](Value *V) {
-        return IsNonLocalValue(V, MemoryInst->getParent());
+        return IsNonLocalValueOrAfter(V, MemoryInst);
       })) {
     DEBUG(dbgs() << "CGP: Found      local addrmode: " << AddrMode << "\n");
     return false;


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D34862.104814.patch
Type: text/x-patch
Size: 2412 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20170630/28d61b5e/attachment.bin>


More information about the llvm-commits mailing list