1 //===- llvm/unittests/IR/MemoryModelRelaxationAnnotationsTest.cpp ---------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #include "llvm/IR/MemoryModelRelaxationAnnotations.h"
10 #include "llvm/ADT/STLExtras.h"
11 #include "llvm/IR/Metadata.h"
12 #include "llvm/IR/Module.h"
13 #include "gtest/gtest.h"
19 void checkMMRA(const MMRAMetadata
&MMRA
,
20 ArrayRef
<MMRAMetadata::TagT
> Expected
) {
21 EXPECT_EQ(MMRA
.size(), Expected
.size());
22 for (const auto &E
: Expected
)
23 EXPECT_TRUE(MMRA
.hasTag(E
.first
, E
.second
));
26 MMRAMetadata
createFromMD(LLVMContext
&Ctx
,
27 ArrayRef
<MMRAMetadata::TagT
> Expected
) {
28 SmallVector
<Metadata
*> MD
;
29 for (const auto &Tag
: Expected
)
30 MD
.push_back(MMRAMetadata::getTagMD(Ctx
, Tag
));
31 return MDTuple::get(Ctx
, MD
);
34 TEST(MMRATest
, MDParse
) {
40 MDTuple::get(Ctx
, {MDString::get(Ctx
, "foo"), MDString::get(Ctx
, "bar")});
41 MMRAMetadata
FooBarMMRA(FooBar
);
43 checkMMRA(FooBarMMRA
, {{"foo", "bar"}});
46 // !{!{!"foo", "!bar"}, !{!"bux", !"qux"}}
48 MDTuple::get(Ctx
, {MDString::get(Ctx
, "bux"), MDString::get(Ctx
, "qux")});
49 MDNode
*Nested
= MDTuple::get(Ctx
, {FooBar
, BuxQux
});
50 MMRAMetadata
NestedMMRA(Nested
);
52 checkMMRA(NestedMMRA
, {{"foo", "bar"}, {"bux", "qux"}});
55 TEST(MMRATest
, GetMD
) {
58 EXPECT_EQ(MMRAMetadata::getMD(Ctx
, {}), nullptr);
60 MDTuple
*SingleMD
= MMRAMetadata::getMD(Ctx
, {{"foo", "bar"}});
61 EXPECT_EQ(SingleMD
->getNumOperands(), 2u);
62 EXPECT_EQ(cast
<MDString
>(SingleMD
->getOperand(0))->getString(), "foo");
63 EXPECT_EQ(cast
<MDString
>(SingleMD
->getOperand(1))->getString(), "bar");
65 MDTuple
*MultiMD
= MMRAMetadata::getMD(Ctx
, {{"foo", "bar"}, {"bux", "qux"}});
66 EXPECT_EQ(MultiMD
->getNumOperands(), 2u);
68 MDTuple
*FooBar
= cast
<MDTuple
>(MultiMD
->getOperand(0));
69 EXPECT_EQ(cast
<MDString
>(FooBar
->getOperand(0))->getString(), "foo");
70 EXPECT_EQ(cast
<MDString
>(FooBar
->getOperand(1))->getString(), "bar");
71 MDTuple
*BuxQux
= cast
<MDTuple
>(MultiMD
->getOperand(1));
72 EXPECT_EQ(cast
<MDString
>(BuxQux
->getOperand(0))->getString(), "bux");
73 EXPECT_EQ(cast
<MDString
>(BuxQux
->getOperand(1))->getString(), "qux");
76 TEST(MMRATest
, Utility
) {
79 createFromMD(Ctx
, {{"foo", "0"}, {"foo", "1"}, {"bar", "x"}});
81 EXPECT_TRUE(MMRA
.hasTagWithPrefix("foo"));
82 EXPECT_TRUE(MMRA
.hasTagWithPrefix("bar"));
83 EXPECT_FALSE(MMRA
.hasTagWithPrefix("x"));
85 EXPECT_TRUE(MMRA
.hasTag("foo", "0"));
86 EXPECT_TRUE(MMRA
.hasTag("foo", "1"));
87 EXPECT_TRUE(MMRA
.hasTag("bar", "x"));
90 TEST(MMRATest
, Operators
) {
93 MMRAMetadata A
= createFromMD(Ctx
, {{"foo", "0"}, {"bar", "x"}});
94 MMRAMetadata B
= createFromMD(Ctx
, {{"foo", "0"}, {"bar", "y"}});
96 // ensure we have different objects by creating copies.
97 EXPECT_EQ(MMRAMetadata(A
), MMRAMetadata(A
));
100 EXPECT_EQ(MMRAMetadata(B
), MMRAMetadata(B
));
101 EXPECT_TRUE((bool)B
);
105 EXPECT_EQ(MMRAMetadata(), MMRAMetadata());
106 EXPECT_NE(A
, MMRAMetadata());
107 EXPECT_NE(B
, MMRAMetadata());
110 EXPECT_FALSE((bool)Empty
);
113 TEST(MMRATest
, Compatibility
) {
116 MMRAMetadata Foo0
= createFromMD(Ctx
, {{"foo", "0"}});
117 MMRAMetadata Foo1
= createFromMD(Ctx
, {{"foo", "1"}});
118 MMRAMetadata Foo10
= createFromMD(Ctx
, {{"foo", "0"}, {"foo", "1"}});
120 MMRAMetadata Bar
= createFromMD(Ctx
, {{"bar", "y"}});
124 // Other set has no tag with same prefix
125 EXPECT_TRUE(Foo0
.isCompatibleWith(Bar
));
126 EXPECT_TRUE(Bar
.isCompatibleWith(Foo0
));
128 EXPECT_TRUE(Foo0
.isCompatibleWith(Empty
));
129 EXPECT_TRUE(Empty
.isCompatibleWith(Foo0
));
131 EXPECT_TRUE(Empty
.isCompatibleWith(MMRAMetadata()));
132 EXPECT_TRUE(MMRAMetadata().isCompatibleWith(Empty
));
134 // Other set has conflicting tags.
135 EXPECT_FALSE(Foo1
.isCompatibleWith(Foo0
));
136 EXPECT_FALSE(Foo0
.isCompatibleWith(Foo1
));
138 // Both have common tags.
139 EXPECT_TRUE(Foo0
.isCompatibleWith(Foo0
));
140 EXPECT_TRUE(Foo0
.isCompatibleWith(Foo10
));
141 EXPECT_TRUE(Foo10
.isCompatibleWith(Foo0
));
143 EXPECT_TRUE(Foo1
.isCompatibleWith(Foo1
));
144 EXPECT_TRUE(Foo1
.isCompatibleWith(Foo10
));
145 EXPECT_TRUE(Foo10
.isCompatibleWith(Foo1
));
147 // Try with more prefixes now:
148 MMRAMetadata Multiple0
=
149 createFromMD(Ctx
, {{"foo", "y"}, {"foo", "x"}, {"bar", "z"}});
150 MMRAMetadata Multiple1
=
151 createFromMD(Ctx
, {{"foo", "z"}, {"foo", "x"}, {"bar", "y"}});
152 MMRAMetadata Multiple2
=
153 createFromMD(Ctx
, {{"foo", "z"}, {"foo", "x"}, {"bux", "y"}});
155 // Multiple0 and Multiple1 are not compatible because "bar" is getting in the
157 EXPECT_FALSE(Multiple0
.isCompatibleWith(Multiple1
));
158 EXPECT_FALSE(Multiple1
.isCompatibleWith(Multiple0
));
160 EXPECT_TRUE(Multiple0
.isCompatibleWith(Empty
));
161 EXPECT_TRUE(Empty
.isCompatibleWith(Multiple0
));
162 EXPECT_TRUE(Multiple1
.isCompatibleWith(Empty
));
163 EXPECT_TRUE(Empty
.isCompatibleWith(Multiple1
));
165 // Multiple2 is compatible with both 1/0 because there is always "foo:x" in
166 // common, and the other prefixes are unique to each set.
167 EXPECT_TRUE(Multiple2
.isCompatibleWith(Multiple0
));
168 EXPECT_TRUE(Multiple0
.isCompatibleWith(Multiple2
));
169 EXPECT_TRUE(Multiple2
.isCompatibleWith(Multiple1
));
170 EXPECT_TRUE(Multiple1
.isCompatibleWith(Multiple2
));
173 TEST(MMRATest
, Combine
) {
176 MMRAMetadata Foo0
= createFromMD(Ctx
, {{"foo", "0"}});
177 MMRAMetadata Foo10
= createFromMD(Ctx
, {{"foo", "0"}, {"foo", "1"}});
178 MMRAMetadata Bar0
= createFromMD(Ctx
, {{"bar", "0"}});
179 MMRAMetadata BarFoo0
= createFromMD(Ctx
, {{"bar", "0"}, {"foo", "0"}});
182 // foo is common to both sets
183 MMRAMetadata Combined
= MMRAMetadata::combine(Ctx
, Foo0
, Foo10
);
184 EXPECT_EQ(Combined
, Foo10
);
189 MMRAMetadata Combined
= MMRAMetadata::combine(Ctx
, Foo0
, Bar0
);
190 EXPECT_TRUE(Combined
.empty());
194 // only foo is common.
195 MMRAMetadata Combined
= MMRAMetadata::combine(Ctx
, BarFoo0
, Foo0
);
196 EXPECT_EQ(Combined
, Foo0
);
200 // only bar is common.
201 MMRAMetadata Combined
= MMRAMetadata::combine(Ctx
, BarFoo0
, Bar0
);
202 EXPECT_EQ(Combined
, Bar0
);
206 // only foo is common
207 MMRAMetadata Combined
= MMRAMetadata::combine(Ctx
, BarFoo0
, Foo10
);
208 EXPECT_EQ(Combined
, Foo10
);