Skip to content

Commit 5fb3ae5

Browse files
committed
[SelectionDAG] Re-calculate scoped AA metadata when merging stores.
Reviewed By: jeroen.dobbelaere Differential Revision: https://reviews.llvm.org/D102821
1 parent 624e4d0 commit 5fb3ae5

File tree

4 files changed

+91
-4
lines changed

4 files changed

+91
-4
lines changed

llvm/include/llvm/IR/Metadata.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -711,6 +711,11 @@ struct AAMDNodes {
711711
/// Given two sets of AAMDNodes applying to potentially different locations,
712712
/// determine the best AAMDNodes that apply to both.
713713
AAMDNodes merge(const AAMDNodes &Other) const;
714+
715+
/// Determine the best AAMDNodes after concatenating two different locations
716+
/// together. Different from `merge`, where different locations should
717+
/// overlap each other, `concat` puts non-overlapping locations together.
718+
AAMDNodes concat(const AAMDNodes &Other) const;
714719
};
715720

716721
// Specialize DenseMapInfo for AAMDNodes.

llvm/lib/Analysis/TypeBasedAliasAnalysis.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -530,6 +530,14 @@ AAMDNodes AAMDNodes::merge(const AAMDNodes &Other) const {
530530
return Result;
531531
}
532532

533+
AAMDNodes AAMDNodes::concat(const AAMDNodes &Other) const {
534+
AAMDNodes Result;
535+
Result.TBAA = Result.TBAAStruct = nullptr;
536+
Result.Scope = MDNode::getMostGenericAliasScope(Scope, Other.Scope);
537+
Result.NoAlias = MDNode::intersect(NoAlias, Other.NoAlias);
538+
return Result;
539+
}
540+
533541
AAMDNodes Instruction::getAAMetadata() const {
534542
AAMDNodes Result;
535543
Result.TBAA = getMetadata(LLVMContext::MD_tbaa);

llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -16970,6 +16970,22 @@ bool DAGCombiner::mergeStoresOfConstantsOrVecElts(
1697016970
unsigned SizeInBits = NumStores * ElementSizeBits;
1697116971
unsigned NumMemElts = MemVT.isVector() ? MemVT.getVectorNumElements() : 1;
1697216972

16973+
Optional<MachineMemOperand::Flags> Flags;
16974+
AAMDNodes AAInfo;
16975+
for (unsigned I = 0; I != NumStores; ++I) {
16976+
StoreSDNode *St = cast<StoreSDNode>(StoreNodes[I].MemNode);
16977+
if (!Flags) {
16978+
Flags = St->getMemOperand()->getFlags();
16979+
AAInfo = St->getAAInfo();
16980+
continue;
16981+
}
16982+
// Skip merging if there's an inconsistent flag.
16983+
if (Flags != St->getMemOperand()->getFlags())
16984+
return false;
16985+
// Concatenate AA metadata.
16986+
AAInfo = AAInfo.concat(St->getAAInfo());
16987+
}
16988+
1697316989
EVT StoreTy;
1697416990
if (UseVector) {
1697516991
unsigned Elts = NumStores * NumMemElts;
@@ -17087,9 +17103,9 @@ bool DAGCombiner::mergeStoresOfConstantsOrVecElts(
1708717103
// make sure we use trunc store if it's necessary to be legal.
1708817104
SDValue NewStore;
1708917105
if (!UseTrunc) {
17090-
NewStore =
17091-
DAG.getStore(NewChain, DL, StoredVal, FirstInChain->getBasePtr(),
17092-
FirstInChain->getPointerInfo(), FirstInChain->getAlign());
17106+
NewStore = DAG.getStore(NewChain, DL, StoredVal, FirstInChain->getBasePtr(),
17107+
FirstInChain->getPointerInfo(),
17108+
FirstInChain->getAlign(), Flags.getValue(), AAInfo);
1709317109
} else { // Must be realized as a trunc store
1709417110
EVT LegalizedStoredValTy =
1709517111
TLI.getTypeToTransformTo(*DAG.getContext(), StoredVal.getValueType());
@@ -17101,7 +17117,7 @@ bool DAGCombiner::mergeStoresOfConstantsOrVecElts(
1710117117
NewStore = DAG.getTruncStore(
1710217118
NewChain, DL, ExtendedStoreVal, FirstInChain->getBasePtr(),
1710317119
FirstInChain->getPointerInfo(), StoredVal.getValueType() /*TVT*/,
17104-
FirstInChain->getAlign(), FirstInChain->getMemOperand()->getFlags());
17120+
FirstInChain->getAlign(), Flags.getValue(), AAInfo);
1710517121
}
1710617122

1710717123
// Replace all merged stores with the new store.
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
; RUN: llc %s -mtriple=aarch64-eabi -stop-after=finalize-isel -o - | FileCheck --check-prefix=MIR %s
2+
3+
; Ensure the scoped AA metadata is still retained after store merging.
4+
5+
; MIR-DAG: ![[DOMAIN:[0-9]+]] = distinct !{!{{[0-9]+}}, !"domain"}
6+
; MIR-DAG: ![[SCOPE0:[0-9]+]] = distinct !{!{{[0-9]+}}, ![[DOMAIN]], !"scope 0"}
7+
; MIR-DAG: ![[SCOPE1:[0-9]+]] = distinct !{!{{[0-9]+}}, ![[DOMAIN]], !"scope 1"}
8+
; MIR-DAG: ![[SCOPE2:[0-9]+]] = distinct !{!{{[0-9]+}}, ![[DOMAIN]], !"scope 2"}
9+
; MIR-DAG: ![[SCOPE3:[0-9]+]] = distinct !{!{{[0-9]+}}, ![[DOMAIN]], !"scope 3"}
10+
; MIR-DAG: ![[SET0:[0-9]+]] = !{![[SCOPE0]]}
11+
; MIR-DAG: ![[SET1:[0-9]+]] = !{![[SCOPE1]]}
12+
; MIR-DAG: ![[SET2:[0-9]+]] = !{![[SCOPE2]]}
13+
; MIR-DAG: ![[SET3:[0-9]+]] = !{![[SCOPE3]]}
14+
15+
define void @blam0(<3 x float>* %g0, <3 x float>* %g1) {
16+
; MIR-LABEL: name: blam0
17+
; MIR: LDRDui %0, 0 :: (load (s64) from %ir.g0, align 4, !alias.scope ![[SET0]], !noalias ![[SET1]])
18+
; MIR: STRDui killed %5, %1, 0 :: (store (s64) into %ir.tmp41, align 4, !alias.scope ![[SET1]], !noalias ![[SET0]])
19+
%tmp4 = getelementptr inbounds <3 x float>, <3 x float>* %g1, i64 0, i64 0
20+
%tmp5 = load <3 x float>, <3 x float>* %g0, align 4, !alias.scope !0, !noalias !1
21+
%tmp6 = extractelement <3 x float> %tmp5, i64 0
22+
store float %tmp6, float* %tmp4, align 4, !alias.scope !1, !noalias !0
23+
%tmp7 = getelementptr inbounds float, float* %tmp4, i64 1
24+
%tmp8 = load <3 x float>, <3 x float>* %g0, align 4, !alias.scope !0, !noalias !1
25+
%tmp9 = extractelement <3 x float> %tmp8, i64 1
26+
store float %tmp9, float* %tmp7, align 4, !alias.scope !1, !noalias !0
27+
ret void;
28+
}
29+
30+
; Ensure new scoped AA metadata are calculated after merging stores.
31+
define void @blam1(<3 x float>* %g0, <3 x float>* %g1) {
32+
; MIR-LABEL: name: blam1
33+
; MIR: machineMetadataNodes:
34+
; MIR-DAG: ![[MMSET0:[0-9]+]] = !{![[SCOPE2]], ![[SCOPE1]]}
35+
; MIR-DAG: ![[MMSET1:[0-9]+]] = !{}
36+
; MIR: body:
37+
; MIR: LDRDui %0, 0 :: (load (s64) from %ir.g0, align 4, !alias.scope ![[SET0]], !noalias ![[SET1]])
38+
; MIR: STRDui killed %5, %1, 0 :: (store (s64) into %ir.tmp41, align 4, !alias.scope ![[MMSET0]], !noalias ![[MMSET1]])
39+
%tmp4 = getelementptr inbounds <3 x float>, <3 x float>* %g1, i64 0, i64 0
40+
%tmp5 = load <3 x float>, <3 x float>* %g0, align 4, !alias.scope !0, !noalias !1
41+
%tmp6 = extractelement <3 x float> %tmp5, i64 0
42+
store float %tmp6, float* %tmp4, align 4, !alias.scope !1, !noalias !0
43+
%tmp7 = getelementptr inbounds float, float* %tmp4, i64 1
44+
%tmp8 = load <3 x float>, <3 x float>* %g0, align 4, !alias.scope !0, !noalias !1
45+
%tmp9 = extractelement <3 x float> %tmp8, i64 1
46+
store float %tmp9, float* %tmp7, align 4, !alias.scope !5, !noalias !6
47+
ret void;
48+
}
49+
50+
!0 = !{!2}
51+
!1 = !{!3}
52+
!2 = !{!2, !4, !"scope 0"}
53+
!3 = !{!3, !4, !"scope 1"}
54+
!4 = !{!4, !"domain"}
55+
!5 = !{!7}
56+
!6 = !{!8}
57+
!7 = !{!7, !4, !"scope 2"}
58+
!8 = !{!8, !4, !"scope 3"}

0 commit comments

Comments
 (0)