[PATCH] D34679: [SelectionDAG] set dereferenceable flag in MergeConsecutiveStores to fix assetion failure

Hiroshi Inoue via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 27 04:15:11 PDT 2017


inouehrs created this revision.

When SelectionDAG merges consecutive stores and loads in MergeConsecutiveStores, it does not set dereferenceable flag for a created load instruction. This results in an assertion failure if SelectionDAG commonizes this load instruction with other load instructions, as well as it may miss optimization opportunities.

This patch sat dereferenceable flag for the newly created load instruction if all the load instruction to be merged are dereferenceable.


https://reviews.llvm.org/D34679

Files:
  lib/CodeGen/SelectionDAG/DAGCombiner.cpp
  test/CodeGen/PowerPC/merge_stores_dereferenceable.ll


Index: test/CodeGen/PowerPC/merge_stores_dereferenceable.ll
===================================================================
--- /dev/null
+++ test/CodeGen/PowerPC/merge_stores_dereferenceable.ll
@@ -0,0 +1,24 @@
+; RUN: llc -verify-machineinstrs -mcpu=pwr8 -mtriple=powerpc64le-unknown-linux-gnu < %s | FileCheck %s
+
+; This code causes an assertion failure if dereferenceable flag is not properly set when in merging consecutive stores
+; CHECK-LABEL: func:
+; CHECK: lxvd2x [[REG1:[0-9]+]], {{[0-9]+}}, {{[0-9]+}}
+; CHECK-NOT: lxvd2x
+; CHECK: stxvd2x [[REG1:[0-9]+]], {{[0-9]+}}, {{[0-9]+}}
+
+define <2 x i64> @func(i64* %pdst) {
+entry:
+  %a = alloca [4 x i64], align 8
+  %psrc0 = bitcast [4 x i64]* %a to i64*
+  %psrc1 = getelementptr inbounds i64, i64* %psrc0, i64 1
+  %d0 = load i64, i64* %psrc0
+  %d1 = load i64, i64* %psrc1
+  %pdst0 = getelementptr inbounds i64, i64* %pdst, i64 0
+  %pdst1 = getelementptr inbounds i64, i64* %pdst, i64 1
+  store i64 %d0, i64* %pdst0, align 8
+  store i64 %d1, i64* %pdst1, align 8
+  %psrcd = bitcast [4 x i64]* %a to <2 x i64>*
+  %vec = load <2 x i64>, <2 x i64>* %psrcd
+  ret <2 x i64> %vec
+}
+
Index: lib/CodeGen/SelectionDAG/DAGCombiner.cpp
===================================================================
--- lib/CodeGen/SelectionDAG/DAGCombiner.cpp
+++ lib/CodeGen/SelectionDAG/DAGCombiner.cpp
@@ -12829,6 +12829,7 @@
     // This variable refers to the size and not index in the array.
     unsigned LastLegalVectorType = 1;
     unsigned LastLegalIntegerType = 1;
+    bool isDereferenceable = true;
     bool DoIntegerTruncate = false;
     StartAddress = LoadNodes[0].OffsetFromBase;
     SDValue FirstChain = FirstLoad->getChain();
@@ -12841,6 +12842,10 @@
       if (CurrAddress - StartAddress != (ElementSizeBytes * i))
         break;
       LastConsecutiveLoad = i;
+
+      if (isDereferenceable && !LoadNodes[i].MemNode->isDereferenceable())
+        isDereferenceable = false;
+
       // Find a legal type for the vector store.
       EVT StoreTy = EVT::getVectorVT(Context, MemVT, i + 1);
       bool IsFastSt, IsFastLd;
@@ -12926,11 +12931,16 @@
     SDValue NewStoreChain = getMergeStoreChains(StoreNodes, NumElem);
     AddToWorklist(NewStoreChain.getNode());
 
+    MachineMemOperand::Flags MMOFlags = isDereferenceable ? 
+                                          MachineMemOperand::MODereferenceable:
+                                          MachineMemOperand::MONone;
+
     SDValue NewLoad, NewStore;
     if (UseVectorTy || !DoIntegerTruncate) {
       NewLoad = DAG.getLoad(JointMemOpVT, LoadDL, FirstLoad->getChain(),
                             FirstLoad->getBasePtr(),
-                            FirstLoad->getPointerInfo(), FirstLoadAlign);
+                            FirstLoad->getPointerInfo(), FirstLoadAlign,
+                            MMOFlags);
       NewStore = DAG.getStore(NewStoreChain, StoreDL, NewLoad,
                               FirstInChain->getBasePtr(),
                               FirstInChain->getPointerInfo(), FirstStoreAlign);
@@ -12940,7 +12950,7 @@
       NewLoad =
           DAG.getExtLoad(ISD::EXTLOAD, LoadDL, ExtendedTy, FirstLoad->getChain(),
                          FirstLoad->getBasePtr(), FirstLoad->getPointerInfo(),
-                         JointMemOpVT, FirstLoadAlign);
+                         JointMemOpVT, FirstLoadAlign, MMOFlags);
       NewStore = DAG.getTruncStore(NewStoreChain, StoreDL, NewLoad,
                                    FirstInChain->getBasePtr(),
                                    FirstInChain->getPointerInfo(), JointMemOpVT,


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D34679.104129.patch
Type: text/x-patch
Size: 3606 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20170627/504ffb07/attachment-0001.bin>


More information about the llvm-commits mailing list