[llvm] r306404 - [SelectionDAG] set dereferenceable flag in MergeConsecutiveStores to fix assetion failure

Hiroshi Inoue via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 27 05:43:08 PDT 2017


Author: inouehrs
Date: Tue Jun 27 05:43:08 2017
New Revision: 306404

URL: http://llvm.org/viewvc/llvm-project?rev=306404&view=rev
Log:
[SelectionDAG] set dereferenceable flag in MergeConsecutiveStores to fix assetion failure

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 instructions to be merged are dereferenceable.

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


Added:
    llvm/trunk/test/CodeGen/PowerPC/merge_stores_dereferenceable.ll
Modified:
    llvm/trunk/lib/CodeGen/SelectionDAG/DAGCombiner.cpp

Modified: llvm/trunk/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/DAGCombiner.cpp?rev=306404&r1=306403&r2=306404&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/SelectionDAG/DAGCombiner.cpp (original)
+++ llvm/trunk/lib/CodeGen/SelectionDAG/DAGCombiner.cpp Tue Jun 27 05:43:08 2017
@@ -12829,6 +12829,7 @@ bool DAGCombiner::MergeConsecutiveStores
     // 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 @@ bool DAGCombiner::MergeConsecutiveStores
       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 @@ bool DAGCombiner::MergeConsecutiveStores
     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 @@ bool DAGCombiner::MergeConsecutiveStores
       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,

Added: llvm/trunk/test/CodeGen/PowerPC/merge_stores_dereferenceable.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/PowerPC/merge_stores_dereferenceable.ll?rev=306404&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/PowerPC/merge_stores_dereferenceable.ll (added)
+++ llvm/trunk/test/CodeGen/PowerPC/merge_stores_dereferenceable.ll Tue Jun 27 05:43:08 2017
@@ -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
+}
+




More information about the llvm-commits mailing list