The data contained in this repository can be downloaded to your computer using one of several clients.
Please see the documentation of your version control software client for more information.
Please select the desired protocol below to get the URL.
This URL has Read-Only access.
main_repo / deps / v8 / test / cctest / test-types.cc @ f230a1cf
History | View | Annotate | Download (26.7 KB)
1 |
// Copyright 2013 the V8 project authors. All rights reserved.
|
---|---|
2 |
// Redistribution and use in source and binary forms, with or without
|
3 |
// modification, are permitted provided that the following conditions are
|
4 |
// met:
|
5 |
//
|
6 |
// * Redistributions of source code must retain the above copyright
|
7 |
// notice, this list of conditions and the following disclaimer.
|
8 |
// * Redistributions in binary form must reproduce the above
|
9 |
// copyright notice, this list of conditions and the following
|
10 |
// disclaimer in the documentation and/or other materials provided
|
11 |
// with the distribution.
|
12 |
// * Neither the name of Google Inc. nor the names of its
|
13 |
// contributors may be used to endorse or promote products derived
|
14 |
// from this software without specific prior written permission.
|
15 |
//
|
16 |
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
17 |
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
18 |
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
19 |
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
20 |
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
21 |
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
22 |
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
23 |
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
24 |
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
25 |
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
26 |
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
27 |
|
28 |
#include "cctest.h" |
29 |
#include "types.h" |
30 |
|
31 |
using namespace v8::internal; |
32 |
|
33 |
// Testing auxiliaries (breaking the Type abstraction).
|
34 |
static bool IsBitset(Type* type) { return type->IsSmi(); } |
35 |
static bool IsClass(Type* type) { return type->IsMap(); } |
36 |
static bool IsConstant(Type* type) { return type->IsBox(); } |
37 |
static bool IsUnion(Type* type) { return type->IsFixedArray(); } |
38 |
|
39 |
static int AsBitset(Type* type) { return Smi::cast(type)->value(); } |
40 |
static Map* AsClass(Type* type) { return Map::cast(type); } |
41 |
static Object* AsConstant(Type* type) { return Box::cast(type)->value(); } |
42 |
static FixedArray* AsUnion(Type* type) { return FixedArray::cast(type); } |
43 |
|
44 |
|
45 |
static void CheckEqual(Handle<Type> type1, Handle<Type> type2) { |
46 |
CHECK_EQ(IsBitset(*type1), IsBitset(*type2)); |
47 |
CHECK_EQ(IsClass(*type1), IsClass(*type2)); |
48 |
CHECK_EQ(IsConstant(*type1), IsConstant(*type2)); |
49 |
CHECK_EQ(IsUnion(*type1), IsUnion(*type2)); |
50 |
CHECK_EQ(type1->NumClasses(), type2->NumClasses()); |
51 |
CHECK_EQ(type1->NumConstants(), type2->NumConstants()); |
52 |
if (IsBitset(*type1)) {
|
53 |
CHECK_EQ(AsBitset(*type1), AsBitset(*type2)); |
54 |
} else if (IsClass(*type1)) { |
55 |
CHECK_EQ(AsClass(*type1), AsClass(*type2)); |
56 |
} else if (IsConstant(*type1)) { |
57 |
CHECK_EQ(AsConstant(*type1), AsConstant(*type2)); |
58 |
} else if (IsUnion(*type1)) { |
59 |
CHECK_EQ(AsUnion(*type1)->length(), AsUnion(*type2)->length()); |
60 |
} |
61 |
CHECK(type1->Is(type2)); |
62 |
CHECK(type2->Is(type1)); |
63 |
} |
64 |
|
65 |
|
66 |
static void CheckSub(Handle<Type> type1, Handle<Type> type2) { |
67 |
CHECK(type1->Is(type2)); |
68 |
CHECK(!type2->Is(type1)); |
69 |
if (IsBitset(*type1) && IsBitset(*type2)) {
|
70 |
CHECK_NE(AsBitset(*type1), AsBitset(*type2)); |
71 |
} |
72 |
} |
73 |
|
74 |
|
75 |
static void CheckUnordered(Handle<Type> type1, Handle<Type> type2) { |
76 |
CHECK(!type1->Is(type2)); |
77 |
CHECK(!type2->Is(type1)); |
78 |
if (IsBitset(*type1) && IsBitset(*type2)) {
|
79 |
CHECK_NE(AsBitset(*type1), AsBitset(*type2)); |
80 |
} |
81 |
} |
82 |
|
83 |
|
84 |
static void CheckOverlap(Handle<Type> type1, Handle<Type> type2) { |
85 |
CHECK(type1->Maybe(type2)); |
86 |
CHECK(type2->Maybe(type1)); |
87 |
if (IsBitset(*type1) && IsBitset(*type2)) {
|
88 |
CHECK_NE(0, AsBitset(*type1) & AsBitset(*type2));
|
89 |
} |
90 |
} |
91 |
|
92 |
|
93 |
static void CheckDisjoint(Handle<Type> type1, Handle<Type> type2) { |
94 |
CHECK(!type1->Is(type2)); |
95 |
CHECK(!type2->Is(type1)); |
96 |
CHECK(!type1->Maybe(type2)); |
97 |
CHECK(!type2->Maybe(type1)); |
98 |
if (IsBitset(*type1) && IsBitset(*type2)) {
|
99 |
CHECK_EQ(0, AsBitset(*type1) & AsBitset(*type2));
|
100 |
} |
101 |
} |
102 |
|
103 |
|
104 |
class HandlifiedTypes { |
105 |
public:
|
106 |
explicit HandlifiedTypes(Isolate* isolate) :
|
107 |
None(Type::None(), isolate), |
108 |
Any(Type::Any(), isolate), |
109 |
Oddball(Type::Oddball(), isolate), |
110 |
Boolean(Type::Boolean(), isolate), |
111 |
Null(Type::Null(), isolate), |
112 |
Undefined(Type::Undefined(), isolate), |
113 |
Number(Type::Number(), isolate), |
114 |
Smi(Type::Smi(), isolate), |
115 |
Signed32(Type::Signed32(), isolate), |
116 |
Double(Type::Double(), isolate), |
117 |
Name(Type::Name(), isolate), |
118 |
UniqueName(Type::UniqueName(), isolate), |
119 |
String(Type::String(), isolate), |
120 |
InternalizedString(Type::InternalizedString(), isolate), |
121 |
Symbol(Type::Symbol(), isolate), |
122 |
Receiver(Type::Receiver(), isolate), |
123 |
Object(Type::Object(), isolate), |
124 |
Array(Type::Array(), isolate), |
125 |
Function(Type::Function(), isolate), |
126 |
Proxy(Type::Proxy(), isolate), |
127 |
object_map(isolate->factory()->NewMap(JS_OBJECT_TYPE, 3 * kPointerSize)),
|
128 |
array_map(isolate->factory()->NewMap(JS_ARRAY_TYPE, 4 * kPointerSize)),
|
129 |
isolate_(isolate) { |
130 |
smi = handle(Smi::FromInt(666), isolate);
|
131 |
signed32 = isolate->factory()->NewHeapNumber(0x40000000);
|
132 |
object1 = isolate->factory()->NewJSObjectFromMap(object_map); |
133 |
object2 = isolate->factory()->NewJSObjectFromMap(object_map); |
134 |
array = isolate->factory()->NewJSArray(20);
|
135 |
ObjectClass = Class(object_map); |
136 |
ArrayClass = Class(array_map); |
137 |
SmiConstant = Constant(smi); |
138 |
Signed32Constant = Constant(signed32); |
139 |
ObjectConstant1 = Constant(object1); |
140 |
ObjectConstant2 = Constant(object2); |
141 |
ArrayConstant1 = Constant(array); |
142 |
ArrayConstant2 = Constant(array); |
143 |
} |
144 |
|
145 |
Handle<Type> None; |
146 |
Handle<Type> Any; |
147 |
Handle<Type> Oddball; |
148 |
Handle<Type> Boolean; |
149 |
Handle<Type> Null; |
150 |
Handle<Type> Undefined; |
151 |
Handle<Type> Number; |
152 |
Handle<Type> Smi; |
153 |
Handle<Type> Signed32; |
154 |
Handle<Type> Double; |
155 |
Handle<Type> Name; |
156 |
Handle<Type> UniqueName; |
157 |
Handle<Type> String; |
158 |
Handle<Type> InternalizedString; |
159 |
Handle<Type> Symbol; |
160 |
Handle<Type> Receiver; |
161 |
Handle<Type> Object; |
162 |
Handle<Type> Array; |
163 |
Handle<Type> Function; |
164 |
Handle<Type> Proxy; |
165 |
|
166 |
Handle<Type> ObjectClass; |
167 |
Handle<Type> ArrayClass; |
168 |
|
169 |
Handle<Type> SmiConstant; |
170 |
Handle<Type> Signed32Constant; |
171 |
Handle<Type> ObjectConstant1; |
172 |
Handle<Type> ObjectConstant2; |
173 |
Handle<Type> ArrayConstant1; |
174 |
Handle<Type> ArrayConstant2; |
175 |
|
176 |
Handle<Map> object_map; |
177 |
Handle<Map> array_map; |
178 |
|
179 |
Handle<i::Smi> smi; |
180 |
Handle<HeapNumber> signed32; |
181 |
Handle<JSObject> object1; |
182 |
Handle<JSObject> object2; |
183 |
Handle<JSArray> array; |
184 |
|
185 |
Handle<Type> Class(Handle<Map> map) { |
186 |
return handle(Type::Class(map), isolate_);
|
187 |
} |
188 |
Handle<Type> Constant(Handle<i::Object> value) { |
189 |
return handle(Type::Constant(value, isolate_), isolate_);
|
190 |
} |
191 |
Handle<Type> Union(Handle<Type> type1, Handle<Type> type2) { |
192 |
return handle(Type::Union(type1, type2), isolate_);
|
193 |
} |
194 |
Handle<Type> Intersect(Handle<Type> type1, Handle<Type> type2) { |
195 |
return handle(Type::Intersect(type1, type2), isolate_);
|
196 |
} |
197 |
|
198 |
private:
|
199 |
Isolate* isolate_; |
200 |
}; |
201 |
|
202 |
|
203 |
TEST(Bitset) { |
204 |
CcTest::InitializeVM(); |
205 |
Isolate* isolate = CcTest::i_isolate(); |
206 |
HandleScope scope(isolate); |
207 |
HandlifiedTypes T(isolate); |
208 |
|
209 |
CHECK(IsBitset(*T.None)); |
210 |
CHECK(IsBitset(*T.Any)); |
211 |
CHECK(IsBitset(*T.String)); |
212 |
CHECK(IsBitset(*T.Object)); |
213 |
|
214 |
CHECK(IsBitset(Type::Union(T.String, T.Number))); |
215 |
CHECK(IsBitset(Type::Union(T.String, T.Receiver))); |
216 |
CHECK(IsBitset(Type::Optional(T.Object))); |
217 |
|
218 |
CHECK_EQ(0, AsBitset(*T.None));
|
219 |
CHECK_EQ(AsBitset(*T.Number) | AsBitset(*T.String), |
220 |
AsBitset(Type::Union(T.String, T.Number))); |
221 |
CHECK_EQ(AsBitset(*T.Receiver), |
222 |
AsBitset(Type::Union(T.Receiver, T.Object))); |
223 |
CHECK_EQ(AsBitset(*T.String) | AsBitset(*T.Undefined), |
224 |
AsBitset(Type::Optional(T.String))); |
225 |
} |
226 |
|
227 |
|
228 |
TEST(Class) { |
229 |
CcTest::InitializeVM(); |
230 |
Isolate* isolate = CcTest::i_isolate(); |
231 |
HandleScope scope(isolate); |
232 |
HandlifiedTypes T(isolate); |
233 |
|
234 |
CHECK(IsClass(*T.ObjectClass)); |
235 |
CHECK(IsClass(*T.ArrayClass)); |
236 |
|
237 |
CHECK(*T.object_map == AsClass(*T.ObjectClass)); |
238 |
CHECK(*T.array_map == AsClass(*T.ArrayClass)); |
239 |
} |
240 |
|
241 |
|
242 |
TEST(Constant) { |
243 |
CcTest::InitializeVM(); |
244 |
Isolate* isolate = CcTest::i_isolate(); |
245 |
HandleScope scope(isolate); |
246 |
HandlifiedTypes T(isolate); |
247 |
|
248 |
CHECK(IsConstant(*T.SmiConstant)); |
249 |
CHECK(IsConstant(*T.ObjectConstant1)); |
250 |
CHECK(IsConstant(*T.ObjectConstant2)); |
251 |
CHECK(IsConstant(*T.ArrayConstant1)); |
252 |
CHECK(IsConstant(*T.ArrayConstant2)); |
253 |
|
254 |
CHECK(*T.smi == AsConstant(*T.SmiConstant)); |
255 |
CHECK(*T.object1 == AsConstant(*T.ObjectConstant1)); |
256 |
CHECK(*T.object2 == AsConstant(*T.ObjectConstant2)); |
257 |
CHECK(*T.object1 != AsConstant(*T.ObjectConstant2)); |
258 |
CHECK(*T.array == AsConstant(*T.ArrayConstant1)); |
259 |
CHECK(*T.array == AsConstant(*T.ArrayConstant2)); |
260 |
} |
261 |
|
262 |
|
263 |
TEST(Is) { |
264 |
CcTest::InitializeVM(); |
265 |
Isolate* isolate = CcTest::i_isolate(); |
266 |
HandleScope scope(isolate); |
267 |
HandlifiedTypes T(isolate); |
268 |
|
269 |
// Reflexivity
|
270 |
CHECK(T.None->Is(T.None)); |
271 |
CHECK(T.Any->Is(T.Any)); |
272 |
CHECK(T.Object->Is(T.Object)); |
273 |
|
274 |
CHECK(T.ObjectClass->Is(T.ObjectClass)); |
275 |
CHECK(T.ObjectConstant1->Is(T.ObjectConstant1)); |
276 |
CHECK(T.ArrayConstant1->Is(T.ArrayConstant2)); |
277 |
|
278 |
// Symmetry and Transitivity
|
279 |
CheckSub(T.None, T.Number); |
280 |
CheckSub(T.None, T.Any); |
281 |
|
282 |
CheckSub(T.Oddball, T.Any); |
283 |
CheckSub(T.Boolean, T.Oddball); |
284 |
CheckSub(T.Null, T.Oddball); |
285 |
CheckSub(T.Undefined, T.Oddball); |
286 |
CheckUnordered(T.Boolean, T.Null); |
287 |
CheckUnordered(T.Undefined, T.Null); |
288 |
CheckUnordered(T.Boolean, T.Undefined); |
289 |
|
290 |
CheckSub(T.Number, T.Any); |
291 |
CheckSub(T.Smi, T.Number); |
292 |
CheckSub(T.Signed32, T.Number); |
293 |
CheckSub(T.Double, T.Number); |
294 |
CheckSub(T.Smi, T.Signed32); |
295 |
CheckUnordered(T.Smi, T.Double); |
296 |
CheckUnordered(T.Signed32, T.Double); |
297 |
|
298 |
CheckSub(T.Name, T.Any); |
299 |
CheckSub(T.UniqueName, T.Any); |
300 |
CheckSub(T.UniqueName, T.Name); |
301 |
CheckSub(T.String, T.Name); |
302 |
CheckSub(T.InternalizedString, T.String); |
303 |
CheckSub(T.InternalizedString, T.UniqueName); |
304 |
CheckSub(T.InternalizedString, T.Name); |
305 |
CheckSub(T.Symbol, T.UniqueName); |
306 |
CheckSub(T.Symbol, T.Name); |
307 |
CheckUnordered(T.String, T.UniqueName); |
308 |
CheckUnordered(T.String, T.Symbol); |
309 |
CheckUnordered(T.InternalizedString, T.Symbol); |
310 |
|
311 |
CheckSub(T.Receiver, T.Any); |
312 |
CheckSub(T.Object, T.Any); |
313 |
CheckSub(T.Object, T.Receiver); |
314 |
CheckSub(T.Array, T.Object); |
315 |
CheckSub(T.Function, T.Object); |
316 |
CheckSub(T.Proxy, T.Receiver); |
317 |
CheckUnordered(T.Object, T.Proxy); |
318 |
CheckUnordered(T.Array, T.Function); |
319 |
|
320 |
// Structured subtyping
|
321 |
CheckSub(T.None, T.ObjectClass); |
322 |
CheckSub(T.None, T.ObjectConstant1); |
323 |
CheckSub(T.ObjectClass, T.Any); |
324 |
CheckSub(T.ObjectConstant1, T.Any); |
325 |
|
326 |
CheckSub(T.ObjectClass, T.Object); |
327 |
CheckSub(T.ArrayClass, T.Object); |
328 |
CheckUnordered(T.ObjectClass, T.ArrayClass); |
329 |
|
330 |
CheckSub(T.SmiConstant, T.Smi); |
331 |
CheckSub(T.SmiConstant, T.Signed32); |
332 |
CheckSub(T.SmiConstant, T.Number); |
333 |
CheckSub(T.ObjectConstant1, T.Object); |
334 |
CheckSub(T.ObjectConstant2, T.Object); |
335 |
CheckSub(T.ArrayConstant1, T.Object); |
336 |
CheckSub(T.ArrayConstant1, T.Array); |
337 |
CheckUnordered(T.ObjectConstant1, T.ObjectConstant2); |
338 |
CheckUnordered(T.ObjectConstant1, T.ArrayConstant1); |
339 |
|
340 |
CheckUnordered(T.ObjectConstant1, T.ObjectClass); |
341 |
CheckUnordered(T.ObjectConstant2, T.ObjectClass); |
342 |
CheckUnordered(T.ObjectConstant1, T.ArrayClass); |
343 |
CheckUnordered(T.ObjectConstant2, T.ArrayClass); |
344 |
CheckUnordered(T.ArrayConstant1, T.ObjectClass); |
345 |
} |
346 |
|
347 |
|
348 |
TEST(Maybe) { |
349 |
CcTest::InitializeVM(); |
350 |
Isolate* isolate = CcTest::i_isolate(); |
351 |
HandleScope scope(isolate); |
352 |
HandlifiedTypes T(isolate); |
353 |
|
354 |
CheckOverlap(T.Any, T.Any); |
355 |
CheckOverlap(T.Object, T.Object); |
356 |
|
357 |
CheckOverlap(T.Oddball, T.Any); |
358 |
CheckOverlap(T.Boolean, T.Oddball); |
359 |
CheckOverlap(T.Null, T.Oddball); |
360 |
CheckOverlap(T.Undefined, T.Oddball); |
361 |
CheckDisjoint(T.Boolean, T.Null); |
362 |
CheckDisjoint(T.Undefined, T.Null); |
363 |
CheckDisjoint(T.Boolean, T.Undefined); |
364 |
|
365 |
CheckOverlap(T.Number, T.Any); |
366 |
CheckOverlap(T.Smi, T.Number); |
367 |
CheckOverlap(T.Double, T.Number); |
368 |
CheckDisjoint(T.Signed32, T.Double); |
369 |
|
370 |
CheckOverlap(T.Name, T.Any); |
371 |
CheckOverlap(T.UniqueName, T.Any); |
372 |
CheckOverlap(T.UniqueName, T.Name); |
373 |
CheckOverlap(T.String, T.Name); |
374 |
CheckOverlap(T.InternalizedString, T.String); |
375 |
CheckOverlap(T.InternalizedString, T.UniqueName); |
376 |
CheckOverlap(T.InternalizedString, T.Name); |
377 |
CheckOverlap(T.Symbol, T.UniqueName); |
378 |
CheckOverlap(T.Symbol, T.Name); |
379 |
CheckOverlap(T.String, T.UniqueName); |
380 |
CheckDisjoint(T.String, T.Symbol); |
381 |
CheckDisjoint(T.InternalizedString, T.Symbol); |
382 |
|
383 |
CheckOverlap(T.Receiver, T.Any); |
384 |
CheckOverlap(T.Object, T.Any); |
385 |
CheckOverlap(T.Object, T.Receiver); |
386 |
CheckOverlap(T.Array, T.Object); |
387 |
CheckOverlap(T.Function, T.Object); |
388 |
CheckOverlap(T.Proxy, T.Receiver); |
389 |
CheckDisjoint(T.Object, T.Proxy); |
390 |
CheckDisjoint(T.Array, T.Function); |
391 |
|
392 |
CheckOverlap(T.ObjectClass, T.Any); |
393 |
CheckOverlap(T.ObjectConstant1, T.Any); |
394 |
|
395 |
CheckOverlap(T.ObjectClass, T.Object); |
396 |
CheckOverlap(T.ArrayClass, T.Object); |
397 |
CheckOverlap(T.ObjectClass, T.ObjectClass); |
398 |
CheckOverlap(T.ArrayClass, T.ArrayClass); |
399 |
CheckDisjoint(T.ObjectClass, T.ArrayClass); |
400 |
|
401 |
CheckOverlap(T.SmiConstant, T.Smi); |
402 |
CheckOverlap(T.SmiConstant, T.Signed32); |
403 |
CheckOverlap(T.SmiConstant, T.Number); |
404 |
CheckDisjoint(T.SmiConstant, T.Double); |
405 |
CheckOverlap(T.ObjectConstant1, T.Object); |
406 |
CheckOverlap(T.ObjectConstant2, T.Object); |
407 |
CheckOverlap(T.ArrayConstant1, T.Object); |
408 |
CheckOverlap(T.ArrayConstant1, T.Array); |
409 |
CheckOverlap(T.ArrayConstant1, T.ArrayConstant2); |
410 |
CheckOverlap(T.ObjectConstant1, T.ObjectConstant1); |
411 |
CheckDisjoint(T.ObjectConstant1, T.ObjectConstant2); |
412 |
CheckDisjoint(T.ObjectConstant1, T.ArrayConstant1); |
413 |
|
414 |
CheckDisjoint(T.ObjectConstant1, T.ObjectClass); |
415 |
CheckDisjoint(T.ObjectConstant2, T.ObjectClass); |
416 |
CheckDisjoint(T.ObjectConstant1, T.ArrayClass); |
417 |
CheckDisjoint(T.ObjectConstant2, T.ArrayClass); |
418 |
CheckDisjoint(T.ArrayConstant1, T.ObjectClass); |
419 |
} |
420 |
|
421 |
|
422 |
TEST(Union) { |
423 |
CcTest::InitializeVM(); |
424 |
Isolate* isolate = CcTest::i_isolate(); |
425 |
HandleScope scope(isolate); |
426 |
HandlifiedTypes T(isolate); |
427 |
|
428 |
// Bitset-bitset
|
429 |
CHECK(IsBitset(Type::Union(T.Object, T.Number))); |
430 |
CHECK(IsBitset(Type::Union(T.Object, T.Object))); |
431 |
CHECK(IsBitset(Type::Union(T.Any, T.None))); |
432 |
|
433 |
CheckEqual(T.Union(T.None, T.Number), T.Number); |
434 |
CheckEqual(T.Union(T.Object, T.Proxy), T.Receiver); |
435 |
CheckEqual(T.Union(T.Number, T.String), T.Union(T.String, T.Number)); |
436 |
CheckSub(T.Union(T.Number, T.String), T.Any); |
437 |
|
438 |
// Class-class
|
439 |
CHECK(IsClass(Type::Union(T.ObjectClass, T.ObjectClass))); |
440 |
CHECK(IsUnion(Type::Union(T.ObjectClass, T.ArrayClass))); |
441 |
|
442 |
CheckEqual(T.Union(T.ObjectClass, T.ObjectClass), T.ObjectClass); |
443 |
CheckSub(T.None, T.Union(T.ObjectClass, T.ArrayClass)); |
444 |
CheckSub(T.Union(T.ObjectClass, T.ArrayClass), T.Any); |
445 |
CheckSub(T.ObjectClass, T.Union(T.ObjectClass, T.ArrayClass)); |
446 |
CheckSub(T.ArrayClass, T.Union(T.ObjectClass, T.ArrayClass)); |
447 |
CheckSub(T.Union(T.ObjectClass, T.ArrayClass), T.Object); |
448 |
CheckUnordered(T.Union(T.ObjectClass, T.ArrayClass), T.Array); |
449 |
CheckOverlap(T.Union(T.ObjectClass, T.ArrayClass), T.Array); |
450 |
CheckDisjoint(T.Union(T.ObjectClass, T.ArrayClass), T.Number); |
451 |
|
452 |
// Constant-constant
|
453 |
CHECK(IsConstant(Type::Union(T.ObjectConstant1, T.ObjectConstant1))); |
454 |
CHECK(IsConstant(Type::Union(T.ArrayConstant1, T.ArrayConstant1))); |
455 |
CHECK(IsUnion(Type::Union(T.ObjectConstant1, T.ObjectConstant2))); |
456 |
|
457 |
CheckEqual(T.Union(T.ObjectConstant1, T.ObjectConstant1), T.ObjectConstant1); |
458 |
CheckEqual(T.Union(T.ArrayConstant1, T.ArrayConstant1), T.ArrayConstant1); |
459 |
CheckEqual(T.Union(T.ArrayConstant1, T.ArrayConstant1), T.ArrayConstant2); |
460 |
CheckSub(T.None, T.Union(T.ObjectConstant1, T.ObjectConstant2)); |
461 |
CheckSub(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.Any); |
462 |
CheckSub(T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)); |
463 |
CheckSub(T.ObjectConstant2, T.Union(T.ObjectConstant1, T.ObjectConstant2)); |
464 |
CheckSub(T.ArrayConstant2, T.Union(T.ArrayConstant1, T.ObjectConstant2)); |
465 |
CheckSub(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.Object); |
466 |
CheckUnordered(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.ObjectClass); |
467 |
CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayConstant1), T.Array); |
468 |
CheckOverlap(T.Union(T.ObjectConstant1, T.ArrayConstant1), T.Array); |
469 |
CheckOverlap(T.Union(T.ObjectConstant1, T.ArrayConstant1), T.ArrayConstant2); |
470 |
CheckDisjoint(T.Union(T.ObjectConstant1, T.ArrayConstant1), T.Number); |
471 |
CheckDisjoint(T.Union(T.ObjectConstant1, T.ArrayConstant1), T.ObjectClass); |
472 |
|
473 |
// Bitset-class
|
474 |
CHECK(IsBitset(Type::Union(T.ObjectClass, T.Object))); |
475 |
CHECK(IsUnion(Type::Union(T.ObjectClass, T.Number))); |
476 |
|
477 |
CheckEqual(T.Union(T.ObjectClass, T.Object), T.Object); |
478 |
CheckSub(T.None, T.Union(T.ObjectClass, T.Number)); |
479 |
CheckSub(T.Union(T.ObjectClass, T.Number), T.Any); |
480 |
CheckSub(T.Union(T.ObjectClass, T.Smi), T.Union(T.Object, T.Number)); |
481 |
CheckSub(T.Union(T.ObjectClass, T.Array), T.Object); |
482 |
CheckUnordered(T.Union(T.ObjectClass, T.String), T.Array); |
483 |
CheckOverlap(T.Union(T.ObjectClass, T.String), T.Object); |
484 |
CheckDisjoint(T.Union(T.ObjectClass, T.String), T.Number); |
485 |
|
486 |
// Bitset-constant
|
487 |
CHECK(IsBitset(Type::Union(T.SmiConstant, T.Number))); |
488 |
CHECK(IsBitset(Type::Union(T.ObjectConstant1, T.Object))); |
489 |
CHECK(IsUnion(Type::Union(T.ObjectConstant2, T.Number))); |
490 |
|
491 |
CheckEqual(T.Union(T.SmiConstant, T.Number), T.Number); |
492 |
CheckEqual(T.Union(T.ObjectConstant1, T.Object), T.Object); |
493 |
CheckSub(T.None, T.Union(T.ObjectConstant1, T.Number)); |
494 |
CheckSub(T.Union(T.ObjectConstant1, T.Number), T.Any); |
495 |
CheckSub(T.Union(T.ObjectConstant1, T.Signed32), T.Union(T.Object, T.Number)); |
496 |
CheckSub(T.Union(T.ObjectConstant1, T.Array), T.Object); |
497 |
CheckUnordered(T.Union(T.ObjectConstant1, T.String), T.Array); |
498 |
CheckOverlap(T.Union(T.ObjectConstant1, T.String), T.Object); |
499 |
CheckDisjoint(T.Union(T.ObjectConstant1, T.String), T.Number); |
500 |
CheckEqual(T.Union(T.Signed32, T.Signed32Constant), T.Signed32); |
501 |
|
502 |
// Class-constant
|
503 |
CHECK(IsUnion(Type::Union(T.ObjectConstant1, T.ObjectClass))); |
504 |
CHECK(IsUnion(Type::Union(T.ArrayClass, T.ObjectConstant2))); |
505 |
|
506 |
CheckSub(T.None, T.Union(T.ObjectConstant1, T.ArrayClass)); |
507 |
CheckSub(T.Union(T.ObjectConstant1, T.ArrayClass), T.Any); |
508 |
CheckSub(T.Union(T.ObjectConstant1, T.ArrayClass), T.Object); |
509 |
CheckSub(T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ArrayClass)); |
510 |
CheckSub(T.ArrayClass, T.Union(T.ObjectConstant1, T.ArrayClass)); |
511 |
CheckUnordered(T.ObjectClass, T.Union(T.ObjectConstant1, T.ArrayClass)); |
512 |
CheckSub( |
513 |
T.Union(T.ObjectConstant1, T.ArrayClass), T.Union(T.Array, T.Object)); |
514 |
CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayClass), T.ArrayConstant1); |
515 |
CheckDisjoint(T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectConstant2); |
516 |
CheckDisjoint(T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectClass); |
517 |
|
518 |
// Bitset-union
|
519 |
CHECK(IsBitset( |
520 |
Type::Union(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)))); |
521 |
CHECK(IsUnion( |
522 |
Type::Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.Number))); |
523 |
|
524 |
CheckEqual( |
525 |
T.Union(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)), |
526 |
T.Object); |
527 |
CheckEqual( |
528 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number), |
529 |
T.Union(T.ObjectConstant1, T.Union(T.Number, T.ArrayClass))); |
530 |
CheckSub( |
531 |
T.Double, |
532 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number)); |
533 |
CheckSub( |
534 |
T.ObjectConstant1, |
535 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Double)); |
536 |
CheckSub( |
537 |
T.None, |
538 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Double)); |
539 |
CheckSub( |
540 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Double), |
541 |
T.Any); |
542 |
CheckSub( |
543 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Double), |
544 |
T.Union(T.ObjectConstant1, T.Union(T.Number, T.ArrayClass))); |
545 |
|
546 |
// Class-union
|
547 |
CHECK(IsUnion( |
548 |
Type::Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass))); |
549 |
CHECK(IsUnion( |
550 |
Type::Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ObjectClass))); |
551 |
|
552 |
CheckEqual( |
553 |
T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)), |
554 |
T.Union(T.ObjectClass, T.ObjectConstant1)); |
555 |
CheckSub( |
556 |
T.None, |
557 |
T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass))); |
558 |
CheckSub( |
559 |
T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)), |
560 |
T.Any); |
561 |
CheckSub( |
562 |
T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)), |
563 |
T.Object); |
564 |
CheckEqual( |
565 |
T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass), |
566 |
T.Union(T.ArrayClass, T.ObjectConstant2)); |
567 |
|
568 |
// Constant-union
|
569 |
CHECK(IsUnion(Type::Union( |
570 |
T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)))); |
571 |
CHECK(IsUnion(Type::Union( |
572 |
T.Union(T.ArrayConstant1, T.ObjectClass), T.ObjectConstant1))); |
573 |
CHECK(IsUnion(Type::Union( |
574 |
T.Union(T.ArrayConstant1, T.ObjectConstant2), T.ObjectConstant1))); |
575 |
|
576 |
CheckEqual( |
577 |
T.Union(T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)), |
578 |
T.Union(T.ObjectConstant2, T.ObjectConstant1)); |
579 |
CheckEqual( |
580 |
T.Union(T.Union(T.ArrayConstant1, T.ObjectConstant2), T.ObjectConstant1), |
581 |
T.Union(T.ObjectConstant2, T.Union(T.ArrayConstant1, T.ObjectConstant1))); |
582 |
|
583 |
// Union-union
|
584 |
CHECK(IsBitset(Type::Union( |
585 |
T.Union(T.Number, T.ArrayClass), T.Union(T.Signed32, T.Array)))); |
586 |
CHECK(IsUnion(Type::Union( |
587 |
T.Union(T.Number, T.ArrayClass), T.Union(T.ObjectClass, T.ArrayClass)))); |
588 |
|
589 |
CheckEqual( |
590 |
T.Union( |
591 |
T.Union(T.ObjectConstant2, T.ObjectConstant1), |
592 |
T.Union(T.ObjectConstant1, T.ObjectConstant2)), |
593 |
T.Union(T.ObjectConstant2, T.ObjectConstant1)); |
594 |
CheckEqual( |
595 |
T.Union( |
596 |
T.Union(T.ObjectConstant2, T.ArrayConstant1), |
597 |
T.Union(T.ObjectConstant1, T.ArrayConstant2)), |
598 |
T.Union(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.ArrayConstant1)); |
599 |
CheckEqual( |
600 |
T.Union(T.Union(T.Number, T.ArrayClass), T.Union(T.Smi, T.Array)), |
601 |
T.Union(T.Number, T.Array)); |
602 |
} |
603 |
|
604 |
|
605 |
TEST(Intersect) { |
606 |
CcTest::InitializeVM(); |
607 |
Isolate* isolate = CcTest::i_isolate(); |
608 |
HandleScope scope(isolate); |
609 |
HandlifiedTypes T(isolate); |
610 |
|
611 |
// Bitset-bitset
|
612 |
CHECK(IsBitset(Type::Intersect(T.Object, T.Number))); |
613 |
CHECK(IsBitset(Type::Intersect(T.Object, T.Object))); |
614 |
CHECK(IsBitset(Type::Intersect(T.Any, T.None))); |
615 |
|
616 |
CheckEqual(T.Intersect(T.None, T.Number), T.None); |
617 |
CheckEqual(T.Intersect(T.Object, T.Proxy), T.None); |
618 |
CheckEqual(T.Intersect(T.Name, T.String), T.Intersect(T.String, T.Name)); |
619 |
CheckEqual(T.Intersect(T.UniqueName, T.String), T.InternalizedString); |
620 |
|
621 |
// Class-class
|
622 |
CHECK(IsClass(Type::Intersect(T.ObjectClass, T.ObjectClass))); |
623 |
CHECK(IsBitset(Type::Intersect(T.ObjectClass, T.ArrayClass))); |
624 |
|
625 |
CheckEqual(T.Intersect(T.ObjectClass, T.ObjectClass), T.ObjectClass); |
626 |
CheckEqual(T.Intersect(T.ObjectClass, T.ArrayClass), T.None); |
627 |
|
628 |
// Constant-constant
|
629 |
CHECK(IsConstant(Type::Intersect(T.ObjectConstant1, T.ObjectConstant1))); |
630 |
CHECK(IsConstant(Type::Intersect(T.ArrayConstant1, T.ArrayConstant2))); |
631 |
CHECK(IsBitset(Type::Intersect(T.ObjectConstant1, T.ObjectConstant2))); |
632 |
|
633 |
CheckEqual( |
634 |
T.Intersect(T.ObjectConstant1, T.ObjectConstant1), T.ObjectConstant1); |
635 |
CheckEqual( |
636 |
T.Intersect(T.ArrayConstant1, T.ArrayConstant2), T.ArrayConstant1); |
637 |
CheckEqual(T.Intersect(T.ObjectConstant1, T.ObjectConstant2), T.None); |
638 |
|
639 |
// Bitset-class
|
640 |
CHECK(IsClass(Type::Intersect(T.ObjectClass, T.Object))); |
641 |
CHECK(IsBitset(Type::Intersect(T.ObjectClass, T.Number))); |
642 |
|
643 |
CheckEqual(T.Intersect(T.ObjectClass, T.Object), T.ObjectClass); |
644 |
CheckEqual(T.Intersect(T.ObjectClass, T.Array), T.None); |
645 |
CheckEqual(T.Intersect(T.ObjectClass, T.Number), T.None); |
646 |
|
647 |
// Bitset-constant
|
648 |
CHECK(IsBitset(Type::Intersect(T.Smi, T.Number))); |
649 |
CHECK(IsConstant(Type::Intersect(T.SmiConstant, T.Number))); |
650 |
CHECK(IsConstant(Type::Intersect(T.ObjectConstant1, T.Object))); |
651 |
|
652 |
CheckEqual(T.Intersect(T.Smi, T.Number), T.Smi); |
653 |
CheckEqual(T.Intersect(T.SmiConstant, T.Number), T.SmiConstant); |
654 |
CheckEqual(T.Intersect(T.ObjectConstant1, T.Object), T.ObjectConstant1); |
655 |
|
656 |
// Class-constant
|
657 |
CHECK(IsBitset(Type::Intersect(T.ObjectConstant1, T.ObjectClass))); |
658 |
CHECK(IsBitset(Type::Intersect(T.ArrayClass, T.ObjectConstant2))); |
659 |
|
660 |
CheckEqual(T.Intersect(T.ObjectConstant1, T.ObjectClass), T.None); |
661 |
CheckEqual(T.Intersect(T.ArrayClass, T.ObjectConstant2), T.None); |
662 |
|
663 |
// Bitset-union
|
664 |
CHECK(IsUnion( |
665 |
Type::Intersect(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)))); |
666 |
CHECK(IsBitset( |
667 |
Type::Intersect(T.Union(T.ArrayClass, T.ObjectConstant2), T.Number))); |
668 |
|
669 |
CheckEqual( |
670 |
T.Intersect(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)), |
671 |
T.Union(T.ObjectConstant1, T.ObjectClass)); |
672 |
CheckEqual( |
673 |
T.Intersect(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number), |
674 |
T.None); |
675 |
|
676 |
// Class-union
|
677 |
CHECK(IsClass( |
678 |
Type::Intersect(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass))); |
679 |
CHECK(IsClass( |
680 |
Type::Intersect(T.Union(T.Object, T.SmiConstant), T.ArrayClass))); |
681 |
CHECK(IsBitset( |
682 |
Type::Intersect(T.Union(T.ObjectClass, T.ArrayConstant1), T.ArrayClass))); |
683 |
|
684 |
CheckEqual( |
685 |
T.Intersect(T.ArrayClass, T.Union(T.ObjectConstant2, T.ArrayClass)), |
686 |
T.ArrayClass); |
687 |
CheckEqual( |
688 |
T.Intersect(T.ArrayClass, T.Union(T.Object, T.SmiConstant)), |
689 |
T.ArrayClass); |
690 |
CheckEqual( |
691 |
T.Intersect(T.Union(T.ObjectClass, T.ArrayConstant1), T.ArrayClass), |
692 |
T.None); |
693 |
|
694 |
// Constant-union
|
695 |
CHECK(IsConstant(Type::Intersect( |
696 |
T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)))); |
697 |
CHECK(IsConstant(Type::Intersect( |
698 |
T.Union(T.Number, T.ObjectClass), T.SmiConstant))); |
699 |
CHECK(IsBitset(Type::Intersect( |
700 |
T.Union(T.ArrayConstant1, T.ObjectClass), T.ObjectConstant1))); |
701 |
|
702 |
CheckEqual( |
703 |
T.Intersect( |
704 |
T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)), |
705 |
T.ObjectConstant1); |
706 |
CheckEqual( |
707 |
T.Intersect(T.SmiConstant, T.Union(T.Number, T.ObjectConstant2)), |
708 |
T.SmiConstant); |
709 |
CheckEqual( |
710 |
T.Intersect(T.Union(T.ArrayConstant1, T.ObjectClass), T.ObjectConstant1), |
711 |
T.None); |
712 |
|
713 |
// Union-union
|
714 |
CHECK(IsUnion(Type::Intersect( |
715 |
T.Union(T.Number, T.ArrayClass), T.Union(T.Signed32, T.Array)))); |
716 |
CHECK(IsBitset(Type::Intersect( |
717 |
T.Union(T.Number, T.ObjectClass), T.Union(T.Signed32, T.Array)))); |
718 |
|
719 |
CheckEqual( |
720 |
T.Intersect( |
721 |
T.Union(T.Number, T.ArrayClass), |
722 |
T.Union(T.Smi, T.Array)), |
723 |
T.Union(T.Smi, T.ArrayClass)); |
724 |
CheckEqual( |
725 |
T.Intersect( |
726 |
T.Union(T.Number, T.ObjectClass), |
727 |
T.Union(T.Signed32, T.Array)), |
728 |
T.Signed32); |
729 |
CheckEqual( |
730 |
T.Intersect( |
731 |
T.Union(T.ObjectConstant2, T.ObjectConstant1), |
732 |
T.Union(T.ObjectConstant1, T.ObjectConstant2)), |
733 |
T.Union(T.ObjectConstant2, T.ObjectConstant1)); |
734 |
CheckEqual( |
735 |
T.Intersect( |
736 |
T.Union(T.Union(T.ObjectConstant2, T.ObjectConstant1), T.ArrayClass), |
737 |
T.Union( |
738 |
T.ObjectConstant1, T.Union(T.ArrayConstant1, T.ObjectConstant2))), |
739 |
T.Union(T.ObjectConstant2, T.ObjectConstant1)); |
740 |
CheckEqual( |
741 |
T.Intersect( |
742 |
T.Union(T.ObjectConstant2, T.ArrayConstant1), |
743 |
T.Union(T.ObjectConstant1, T.ArrayConstant2)), |
744 |
T.ArrayConstant1); |
745 |
} |