Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(770)

Side by Side Diff: test/unittests/compiler/coalesced-live-ranges-unittest.cc

Issue 1219063017: [turbofan] Unit tests for live range conflicts. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Incorporated feedback. Created 5 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2014 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "src/compiler/coalesced-live-ranges.h"
6 #include "test/unittests/test-utils.h"
7
8 namespace v8 {
9 namespace internal {
10 namespace compiler {
11
12
13 // Utility offering shorthand syntax for building up a range by providing its ID
14 // and pairs (start, end) specifying intervals. Circumvents current incomplete
15 // support for C++ features such as instantiation lists, on OS X and Android.
16 class TestRangeBuilder {
17 public:
18 explicit TestRangeBuilder(Zone* zone) : id_(-1), pairs_(), zone_(zone) {}
19
20 TestRangeBuilder& Id(int id) {
21 id_ = id;
22 return *this;
23 }
24 TestRangeBuilder& Add(int start, int end) {
25 pairs_.push_back({start, end});
26 return *this;
27 }
28
29 LiveRange* Build(int start, int end) { return Add(start, end).Build(); }
30
31 LiveRange* Build() {
32 LiveRange* range = new (zone_) LiveRange(id_, MachineType::kRepTagged);
33 // Traverse the provided interval specifications backwards, because that is
34 // what LiveRange expects.
35 for (int i = static_cast<int>(pairs_.size()) - 1; i >= 0; --i) {
36 auto pair = pairs_[i];
37 LifetimePosition start = LifetimePosition::FromInt(pair.first);
38 LifetimePosition end = LifetimePosition::FromInt(pair.second);
39 CHECK(start < end);
40 range->AddUseInterval(start, end, zone_);
41 }
42
43 pairs_.clear();
44 return range;
45 }
46
47 private:
48 typedef std::pair<int, int> Interval;
49 typedef std::vector<Interval> IntervalList;
50 int id_;
51 IntervalList pairs_;
52 Zone* zone_;
53 };
54
55
56 typedef std::set<int> LiveRangeIDs;
57
58
59 // Utility offering shorthand building of a set of integers. Circumvents current
60 // incomplete support for C++ features such as instantiation lists, on OS X and
61 // Android.
62 class Conflicts {
63 public:
64 Conflicts(int number_of_conflicts, ...) : set_() {
Benedikt Meurer 2015/07/14 04:35:01 Do we really need to use varargs here? You could a
Mircea Trofin 2015/07/14 16:19:18 Agreed, and even easier, since the purpose was sim
65 CHECK(number_of_conflicts > 0);
66 va_list conflict_list;
67 va_start(conflict_list, number_of_conflicts);
68 for (int i = 0; i < number_of_conflicts; ++i) {
69 int val = va_arg(conflict_list, int);
70 set_.insert(val);
71 }
72 va_end(conflict_list);
73 }
74
75 operator LiveRangeIDs&() { return set_; }
Benedikt Meurer 2015/07/14 04:35:01 Same here, there's no need for operator overloadin
Mircea Trofin 2015/07/14 16:19:18 Done.
76 static LiveRangeIDs& None() { return empty_set; }
77
78 private:
79 static LiveRangeIDs empty_set;
80 LiveRangeIDs set_;
81 };
82
83 LiveRangeIDs Conflicts::empty_set;
84
85 class CoalescedLiveRangesTest : public TestWithZone {
86 public:
87 CoalescedLiveRangesTest() : TestWithZone(), ranges_(zone()) {}
88 bool CheckConflictsMatch(const LiveRange* range, const LiveRangeIDs& ids);
89
90 CoalescedLiveRanges& ranges() { return ranges_; }
91 const CoalescedLiveRanges& ranges() const { return ranges_; }
92 bool AllocationsAreValid() const;
93 void RemoveConflicts(LiveRange* range);
94
95 private:
96 CoalescedLiveRanges ranges_;
97 };
98
99
100 void CoalescedLiveRangesTest::RemoveConflicts(LiveRange* range) {
101 ranges().RemoveConflicts(range, [](LiveRange* conflict) {});
102 }
103
104
105 bool CoalescedLiveRangesTest::AllocationsAreValid() const {
106 return ranges().TestOnlyVerifyAllocationsAreValid();
107 }
108
109
110 bool CoalescedLiveRangesTest::CheckConflictsMatch(const LiveRange* range,
111 const LiveRangeIDs& ids) {
112 LiveRangeIDs found_ids;
113
114 ranges().VisitConflicts(range, [&](const LiveRange* conflict) {
115 found_ids.insert(conflict->id());
116 return true;
117 });
118 return found_ids == ids;
119 }
120
121
122 TEST_F(CoalescedLiveRangesTest, VisitEmptyAllocations) {
123 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(1, 5);
124 ASSERT_TRUE(ranges().empty());
125 ASSERT_TRUE(AllocationsAreValid());
126 ASSERT_TRUE(CheckConflictsMatch(range, Conflicts::None()));
127 }
128
129
130 TEST_F(CoalescedLiveRangesTest, CandidateBeforeAfterAllocations) {
131 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(5, 6);
132 ranges().AllocateRange(range);
133 ASSERT_FALSE(ranges().empty());
134 ASSERT_TRUE(AllocationsAreValid());
135 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(1, 2);
136 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts::None()));
137 query = TestRangeBuilder(zone()).Id(3).Build(1, 5);
138 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts::None()));
139 }
140
141
142 TEST_F(CoalescedLiveRangesTest, CandidateBeforeAfterManyAllocations) {
143 LiveRange* range =
144 TestRangeBuilder(zone()).Id(1).Add(5, 7).Add(10, 12).Build();
145 ranges().AllocateRange(range);
146 ASSERT_FALSE(ranges().empty());
147 ASSERT_TRUE(AllocationsAreValid());
148 LiveRange* query =
149 TestRangeBuilder(zone()).Id(2).Add(1, 2).Add(13, 15).Build();
150 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts::None()));
151 query = TestRangeBuilder(zone()).Id(3).Add(1, 5).Add(12, 15).Build();
152 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts::None()));
153 }
154
155
156 TEST_F(CoalescedLiveRangesTest, SelfConflictsWithSelf) {
157 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(1, 5);
158 ranges().AllocateRange(range);
159 ASSERT_FALSE(ranges().empty());
160 ASSERT_TRUE(AllocationsAreValid());
161 ASSERT_TRUE(CheckConflictsMatch(range, Conflicts(1, 1)));
162 range = TestRangeBuilder(zone()).Id(2).Build(8, 10);
163 ranges().AllocateRange(range);
164 ASSERT_TRUE(CheckConflictsMatch(range, Conflicts(1, 2)));
165 }
166
167
168 TEST_F(CoalescedLiveRangesTest, QueryStartsBeforeConflict) {
169 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(2, 5);
170 ranges().AllocateRange(range);
171 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(1, 3);
172 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
173 range = TestRangeBuilder(zone()).Id(3).Build(8, 10);
174 ranges().AllocateRange(range);
175 query = TestRangeBuilder(zone()).Id(4).Build(6, 9);
176 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 3)));
177 }
178
179
180 TEST_F(CoalescedLiveRangesTest, QueryStartsInConflict) {
181 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(2, 5);
182 ranges().AllocateRange(range);
183 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(3, 6);
184 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
185 range = TestRangeBuilder(zone()).Id(3).Build(8, 10);
186 ranges().AllocateRange(range);
187 query = TestRangeBuilder(zone()).Id(4).Build(9, 11);
188 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 3)));
189 }
190
191
192 TEST_F(CoalescedLiveRangesTest, QueryContainedInConflict) {
193 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(1, 5);
194 ranges().AllocateRange(range);
195 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(2, 3);
196 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
197 }
198
199
200 TEST_F(CoalescedLiveRangesTest, QueryContainsConflict) {
201 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(2, 3);
202 ranges().AllocateRange(range);
203 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(1, 5);
204 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
205 }
206
207
208 TEST_F(CoalescedLiveRangesTest, QueryCoversManyIntervalsSameRange) {
209 LiveRange* range =
210 TestRangeBuilder(zone()).Id(1).Add(1, 5).Add(7, 9).Add(20, 25).Build();
211 ranges().AllocateRange(range);
212 LiveRange* query = TestRangeBuilder(zone()).Id(2).Build(2, 8);
213 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
214 }
215
216
217 TEST_F(CoalescedLiveRangesTest, QueryCoversManyIntervalsDifferentRanges) {
218 LiveRange* range =
219 TestRangeBuilder(zone()).Id(1).Add(1, 5).Add(20, 25).Build();
220 ranges().AllocateRange(range);
221 range = TestRangeBuilder(zone()).Id(2).Build(7, 10);
222 ranges().AllocateRange(range);
223 LiveRange* query = TestRangeBuilder(zone()).Id(3).Build(2, 22);
224 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(2, 1, 2)));
225 }
226
227
228 TEST_F(CoalescedLiveRangesTest, QueryFitsInGaps) {
229 LiveRange* range =
230 TestRangeBuilder(zone()).Id(1).Add(1, 5).Add(10, 15).Add(20, 25).Build();
231 ranges().AllocateRange(range);
232 LiveRange* query =
233 TestRangeBuilder(zone()).Id(3).Add(5, 10).Add(16, 19).Add(27, 30).Build();
234 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts::None()));
235 }
236
237
238 TEST_F(CoalescedLiveRangesTest, DeleteConflictBefore) {
239 LiveRange* range = TestRangeBuilder(zone()).Id(1).Add(1, 4).Add(5, 6).Build();
240 ranges().AllocateRange(range);
241 range = TestRangeBuilder(zone()).Id(2).Build(40, 50);
242 ranges().AllocateRange(range);
243 LiveRange* query = TestRangeBuilder(zone()).Id(3).Build(3, 7);
244 RemoveConflicts(query);
245 query = TestRangeBuilder(zone()).Id(4).Build(0, 60);
246 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 2)));
247 }
248
249
250 TEST_F(CoalescedLiveRangesTest, DeleteConflictAfter) {
251 LiveRange* range = TestRangeBuilder(zone()).Id(1).Build(1, 5);
252 ranges().AllocateRange(range);
253 range = TestRangeBuilder(zone()).Id(2).Add(40, 50).Add(60, 70).Build();
254 ranges().AllocateRange(range);
255 LiveRange* query = TestRangeBuilder(zone()).Id(3).Build(45, 60);
256 RemoveConflicts(query);
257 query = TestRangeBuilder(zone()).Id(4).Build(0, 60);
258 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 1)));
259 }
260
261
262 TEST_F(CoalescedLiveRangesTest, DeleteConflictStraddle) {
263 LiveRange* range =
264 TestRangeBuilder(zone()).Id(1).Add(1, 5).Add(10, 20).Build();
265 ranges().AllocateRange(range);
266 range = TestRangeBuilder(zone()).Id(2).Build(40, 50);
267 ranges().AllocateRange(range);
268 LiveRange* query = TestRangeBuilder(zone()).Id(3).Build(4, 15);
269 RemoveConflicts(query);
270 query = TestRangeBuilder(zone()).Id(4).Build(0, 60);
271 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 2)));
272 }
273
274
275 TEST_F(CoalescedLiveRangesTest, DeleteConflictManyOverlapsBefore) {
276 LiveRange* range =
277 TestRangeBuilder(zone()).Id(1).Add(1, 5).Add(6, 10).Add(10, 20).Build();
278 ranges().AllocateRange(range);
279 range = TestRangeBuilder(zone()).Id(2).Build(40, 50);
280 ranges().AllocateRange(range);
281 LiveRange* query = TestRangeBuilder(zone()).Id(3).Build(4, 15);
282 RemoveConflicts(query);
283 query = TestRangeBuilder(zone()).Id(4).Build(0, 60);
284 ASSERT_TRUE(CheckConflictsMatch(query, Conflicts(1, 2)));
285 }
286
287
288 } // namespace compiler
289 } // namespace internal
290 } // namespace v8
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698