@@ -54,31 +54,16 @@ DEFINE_FLAG(bool,
54
54
DECLARE_FLAG (bool , inline_alloc);
55
55
DECLARE_FLAG (bool , use_slow_path);
56
56
57
- class SubclassFinder {
57
+ class SubtypeFinder {
58
58
public:
59
- SubclassFinder (Zone* zone,
60
- GrowableArray<intptr_t >* cids,
61
- bool include_abstract)
59
+ SubtypeFinder (Zone* zone,
60
+ GrowableArray<intptr_t >* cids,
61
+ bool include_abstract)
62
62
: array_handles_(zone),
63
63
class_handles_ (zone),
64
64
cids_(cids),
65
65
include_abstract_(include_abstract) {}
66
66
67
- void ScanSubClasses (const Class& klass) {
68
- if (include_abstract_ || !klass.is_abstract ()) {
69
- cids_->Add (klass.id ());
70
- }
71
- ScopedHandle<GrowableObjectArray> array (&array_handles_);
72
- ScopedHandle<Class> subclass (&class_handles_);
73
- *array = klass.direct_subclasses ();
74
- if (!array->IsNull ()) {
75
- for (intptr_t i = 0 ; i < array->Length (); ++i) {
76
- *subclass ^= array->At (i);
77
- ScanSubClasses (*subclass);
78
- }
79
- }
80
- }
81
-
82
67
void ScanImplementorClasses (const Class& klass) {
83
68
// An implementor of [klass] is
84
69
// * the [klass] itself.
@@ -134,36 +119,9 @@ const CidRangeVector& HierarchyInfo::SubtypeRangesForClass(
134
119
CidRangeVector& ranges = (*cid_ranges)[klass.id ()];
135
120
if (ranges.length () == 0 ) {
136
121
if (!FLAG_precompiled_mode) {
137
- BuildRangesForJIT (table, &ranges, klass, /* use_subtype_test=*/ true ,
138
- include_abstract, exclude_null);
139
- } else {
140
- BuildRangesFor (table, &ranges, klass, /* use_subtype_test=*/ true ,
141
- include_abstract, exclude_null);
142
- }
143
- }
144
- return ranges;
145
- }
146
-
147
- const CidRangeVector& HierarchyInfo::SubclassRangesForClass (
148
- const Class& klass) {
149
- ClassTable* table = thread ()->isolate_group ()->class_table ();
150
- const intptr_t cid_count = table->NumCids ();
151
- if (cid_subclass_ranges_ == nullptr ) {
152
- cid_subclass_ranges_.reset (new CidRangeVector[cid_count]);
153
- }
154
-
155
- CidRangeVector& ranges = cid_subclass_ranges_[klass.id ()];
156
- if (ranges.length () == 0 ) {
157
- if (!FLAG_precompiled_mode) {
158
- BuildRangesForJIT (table, &ranges, klass,
159
- /* use_subtype_test=*/ true ,
160
- /* include_abstract=*/ false ,
161
- /* exclude_null=*/ false );
122
+ BuildRangesForJIT (table, &ranges, klass, include_abstract, exclude_null);
162
123
} else {
163
- BuildRangesFor (table, &ranges, klass,
164
- /* use_subtype_test=*/ false ,
165
- /* include_abstract=*/ false ,
166
- /* exclude_null=*/ false );
124
+ BuildRangesFor (table, &ranges, klass, include_abstract, exclude_null);
167
125
}
168
126
}
169
127
return ranges;
@@ -175,18 +133,12 @@ const CidRangeVector& HierarchyInfo::SubclassRangesForClass(
175
133
void HierarchyInfo::BuildRangesFor (ClassTable* table,
176
134
CidRangeVector* ranges,
177
135
const Class& klass,
178
- bool use_subtype_test,
179
136
bool include_abstract,
180
137
bool exclude_null) {
181
138
Zone* zone = thread ()->zone ();
182
- ClassTable* class_table = thread ()->isolate_group ()->class_table ();
183
-
184
- // Only really used if `use_subtype_test == true`.
185
139
const Type& dst_type = Type::Handle (zone, Type::RawCast (klass.RareType ()));
186
140
AbstractType& cls_type = AbstractType::Handle (zone);
187
-
188
141
Class& cls = Class::Handle (zone);
189
- AbstractType& super_type = AbstractType::Handle (zone);
190
142
const intptr_t cid_count = table->NumCids ();
191
143
192
144
// Iterate over all cids to find the ones to be included in the ranges.
@@ -210,24 +162,14 @@ void HierarchyInfo::BuildRangesFor(ClassTable* table,
210
162
if (!include_abstract && cls.is_abstract ()) continue ;
211
163
if (cls.IsTopLevel ()) continue ;
212
164
213
- // We are either interested in [CidRange]es of subclasses or subtypes.
165
+ // We are interested in [CidRange]es of subtypes.
214
166
bool test_succeeded = false ;
215
167
if (cid == kNullCid ) {
216
168
ASSERT (exclude_null);
217
169
test_succeeded = false ;
218
- } else if (use_subtype_test) {
170
+ } else {
219
171
cls_type = cls.RareType ();
220
172
test_succeeded = cls_type.IsSubtypeOf (dst_type, Heap::kNew );
221
- } else {
222
- while (!cls.IsObjectClass ()) {
223
- if (cls.ptr () == klass.ptr ()) {
224
- test_succeeded = true ;
225
- break ;
226
- }
227
- super_type = cls.super_type ();
228
- const intptr_t type_class_id = super_type.type_class_id ();
229
- cls = class_table->At (type_class_id);
230
- }
231
173
}
232
174
233
175
if (test_succeeded) {
@@ -245,41 +187,31 @@ void HierarchyInfo::BuildRangesFor(ClassTable* table,
245
187
}
246
188
}
247
189
248
- // Construct last range (either close open one, or add invalid) .
190
+ // Construct last range if there is a open one .
249
191
if (start != -1 ) {
250
192
ASSERT (start <= end);
251
193
CidRange range (start, end);
252
194
ranges->Add (range);
253
- } else if (ranges->length () == 0 ) {
254
- CidRange range;
255
- ASSERT (range.IsIllegalRange ());
256
- ranges->Add (range);
257
195
}
258
196
}
259
197
260
198
void HierarchyInfo::BuildRangesForJIT (ClassTable* table,
261
199
CidRangeVector* ranges,
262
200
const Class& dst_klass,
263
- bool use_subtype_test,
264
201
bool include_abstract,
265
202
bool exclude_null) {
266
203
if (dst_klass.InVMIsolateHeap ()) {
267
- BuildRangesFor (table, ranges, dst_klass, use_subtype_test, include_abstract,
268
- exclude_null);
204
+ BuildRangesFor (table, ranges, dst_klass, include_abstract, exclude_null);
269
205
return ;
270
206
}
271
207
272
208
Zone* zone = thread ()->zone ();
273
209
GrowableArray<intptr_t > cids;
274
- SubclassFinder finder (zone, &cids, include_abstract);
210
+ SubtypeFinder finder (zone, &cids, include_abstract);
275
211
{
276
212
SafepointReadRwLocker ml (thread (),
277
213
thread ()->isolate_group ()->program_lock ());
278
- if (use_subtype_test) {
279
- finder.ScanImplementorClasses (dst_klass);
280
- } else {
281
- finder.ScanSubClasses (dst_klass);
282
- }
214
+ finder.ScanImplementorClasses (dst_klass);
283
215
}
284
216
285
217
// Sort all collected cids.
@@ -429,17 +361,6 @@ bool HierarchyInfo::CanUseGenericSubtypeRangeCheckFor(
429
361
ASSERT (type_class.NumTypeParameters () > 0 &&
430
362
type.arguments () != TypeArguments::null ());
431
363
432
- // If the type class is implemented the different implementations might have
433
- // their type argument vector stored at different offsets and we can therefore
434
- // not perform our optimized [CidRange]-based implementation.
435
- //
436
- // TODO(kustermann): If the class is implemented but all implementations
437
- // store the instantator type argument vector at the same offset we can
438
- // still do it!
439
- if (type_class.is_implemented ()) {
440
- return false ;
441
- }
442
-
443
364
const TypeArguments& ta =
444
365
TypeArguments::Handle (zone, Type::Cast (type).arguments ());
445
366
ASSERT (ta.Length () == num_type_arguments);
@@ -477,11 +398,10 @@ bool HierarchyInfo::InstanceOfHasClassRange(const AbstractType& type,
477
398
/* exclude_null=*/ true );
478
399
if (ranges.length () == 1 ) {
479
400
const CidRangeValue& range = ranges[0 ];
480
- if (!range.IsIllegalRange ()) {
481
- *lower_limit = range.cid_start ;
482
- *upper_limit = range.cid_end ;
483
- return true ;
484
- }
401
+ ASSERT (!range.IsIllegalRange ());
402
+ *lower_limit = range.cid_start ;
403
+ *upper_limit = range.cid_end ;
404
+ return true ;
485
405
}
486
406
}
487
407
return false ;
0 commit comments