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

Side by Side Diff: test/cctest/test-types.cc

Issue 237143002: Re-reland "More tests for Union & Intersect" (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Fixing handlification of tests Created 6 years, 8 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 | Annotate | Revision Log
« no previous file with comments | « src/types.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 15 matching lines...) Expand all
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 27
28 #include <vector> 28 #include <vector>
29 29
30 #include "cctest.h" 30 #include "cctest.h"
31 #include "types.h" 31 #include "types.h"
32 #include "utils/random-number-generator.h" 32 #include "utils/random-number-generator.h"
33 33
34 using namespace v8::internal; 34 using namespace v8::internal;
35 35
36 // Testing auxiliaries (breaking the Type abstraction).
37 struct ZoneRep {
38 typedef void* Struct;
39
40 static bool IsStruct(Type* t, int tag) {
41 return !IsBitset(t) && reinterpret_cast<intptr_t>(AsStruct(t)[0]) == tag;
42 }
43 static bool IsBitset(Type* t) { return reinterpret_cast<intptr_t>(t) & 1; }
44 static bool IsClass(Type* t) { return IsStruct(t, 0); }
45 static bool IsConstant(Type* t) { return IsStruct(t, 1); }
46 static bool IsUnion(Type* t) { return IsStruct(t, 2); }
47
48 static Struct* AsStruct(Type* t) {
49 return reinterpret_cast<Struct*>(t);
50 }
51 static int AsBitset(Type* t) {
52 return static_cast<int>(reinterpret_cast<intptr_t>(t) >> 1);
53 }
54 static Map* AsClass(Type* t) {
55 return *static_cast<Map**>(AsStruct(t)[3]);
56 }
57 static Object* AsConstant(Type* t) {
58 return *static_cast<Object**>(AsStruct(t)[3]);
59 }
60 static Struct* AsUnion(Type* t) {
61 return AsStruct(t);
62 }
63 static int Length(Struct* structured) {
64 return static_cast<int>(reinterpret_cast<intptr_t>(structured[1]));
65 }
66
67 static Zone* ToRegion(Zone* zone, Isolate* isolate) { return zone; }
68 };
69
70
71 struct HeapRep {
72 typedef FixedArray Struct;
73
74 static bool IsStruct(Handle<HeapType> t, int tag) {
75 return t->IsFixedArray() && Smi::cast(AsStruct(t)->get(0))->value() == tag;
76 }
77 static bool IsBitset(Handle<HeapType> t) { return t->IsSmi(); }
78 static bool IsClass(Handle<HeapType> t) { return t->IsMap(); }
79 static bool IsConstant(Handle<HeapType> t) { return t->IsBox(); }
80 static bool IsUnion(Handle<HeapType> t) { return IsStruct(t, 2); }
81
82 static Struct* AsStruct(Handle<HeapType> t) { return FixedArray::cast(*t); }
83 static int AsBitset(Handle<HeapType> t) { return Smi::cast(*t)->value(); }
84 static Map* AsClass(Handle<HeapType> t) { return Map::cast(*t); }
85 static Object* AsConstant(Handle<HeapType> t) {
86 return Box::cast(*t)->value();
87 }
88 static Struct* AsUnion(Handle<HeapType> t) { return AsStruct(t); }
89 static int Length(Struct* structured) { return structured->length() - 1; }
90
91 static Isolate* ToRegion(Zone* zone, Isolate* isolate) { return isolate; }
92 };
93
94
36 template<class Type, class TypeHandle, class Region> 95 template<class Type, class TypeHandle, class Region>
37 class Types { 96 class Types {
38 public: 97 public:
39 Types(Region* region, Isolate* isolate) : region_(region) { 98 Types(Region* region, Isolate* isolate) : region_(region) {
40 static const size_t kMaxTypes = 300;
41 types.reserve(kMaxTypes);
42
43 #define DECLARE_TYPE(name, value) \ 99 #define DECLARE_TYPE(name, value) \
44 name = Type::name(region); \ 100 name = Type::name(region); \
45 types.push_back(name); 101 types.push_back(name);
46 BITSET_TYPE_LIST(DECLARE_TYPE) 102 BITSET_TYPE_LIST(DECLARE_TYPE)
47 #undef DECLARE_TYPE 103 #undef DECLARE_TYPE
48 104
49 object_map = isolate->factory()->NewMap(JS_OBJECT_TYPE, 3 * kPointerSize); 105 object_map = isolate->factory()->NewMap(JS_OBJECT_TYPE, 3 * kPointerSize);
50 array_map = isolate->factory()->NewMap(JS_ARRAY_TYPE, 4 * kPointerSize); 106 array_map = isolate->factory()->NewMap(JS_ARRAY_TYPE, 4 * kPointerSize);
51 uninitialized_map = isolate->factory()->uninitialized_map(); 107 uninitialized_map = isolate->factory()->uninitialized_map();
52 ObjectClass = Type::Class(object_map, region); 108 ObjectClass = Type::Class(object_map, region);
(...skipping 23 matching lines...) Expand all
76 values.push_back(smi); 132 values.push_back(smi);
77 values.push_back(signed32); 133 values.push_back(signed32);
78 values.push_back(object1); 134 values.push_back(object1);
79 values.push_back(object2); 135 values.push_back(object2);
80 values.push_back(array); 136 values.push_back(array);
81 values.push_back(uninitialized); 137 values.push_back(uninitialized);
82 for (ValueVector::iterator it = values.begin(); it != values.end(); ++it) { 138 for (ValueVector::iterator it = values.begin(); it != values.end(); ++it) {
83 types.push_back(Type::Constant(*it, region)); 139 types.push_back(Type::Constant(*it, region));
84 } 140 }
85 141
86 while (types.size() < kMaxTypes) { 142 for (int i = 0; i < 100; ++i) {
87 size_t i = rng.NextInt(static_cast<int>(types.size())); 143 types.push_back(Fuzz());
88 size_t j = rng.NextInt(static_cast<int>(types.size()));
89 if (i != j) types.push_back(Type::Union(types[i], types[j], region));
90 } 144 }
91 } 145 }
92 146
93 RandomNumberGenerator rng;
94
95 #define DECLARE_TYPE(name, value) TypeHandle name; 147 #define DECLARE_TYPE(name, value) TypeHandle name;
96 BITSET_TYPE_LIST(DECLARE_TYPE) 148 BITSET_TYPE_LIST(DECLARE_TYPE)
97 #undef DECLARE_TYPE 149 #undef DECLARE_TYPE
98 150
99 TypeHandle ObjectClass; 151 TypeHandle ObjectClass;
100 TypeHandle ArrayClass; 152 TypeHandle ArrayClass;
101 TypeHandle UninitializedClass; 153 TypeHandle UninitializedClass;
102 154
103 TypeHandle SmiConstant; 155 TypeHandle SmiConstant;
104 TypeHandle Signed32Constant; 156 TypeHandle Signed32Constant;
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
146 } 198 }
147 TypeHandle Intersect(TypeHandle t1, TypeHandle t2) { 199 TypeHandle Intersect(TypeHandle t1, TypeHandle t2) {
148 return Type::Intersect(t1, t2, region_); 200 return Type::Intersect(t1, t2, region_);
149 } 201 }
150 202
151 template<class Type2, class TypeHandle2> 203 template<class Type2, class TypeHandle2>
152 TypeHandle Convert(TypeHandle2 t) { 204 TypeHandle Convert(TypeHandle2 t) {
153 return Type::template Convert<Type2>(t, region_); 205 return Type::template Convert<Type2>(t, region_);
154 } 206 }
155 207
208 TypeHandle Fuzz(int depth = 5) {
209 switch (rng_.NextInt(depth == 0 ? 3 : 20)) {
210 case 0: { // bitset
211 int n = 0
212 #define COUNT_BITSET_TYPES(type, value) + 1
213 BITSET_TYPE_LIST(COUNT_BITSET_TYPES)
214 #undef COUNT_BITSET_TYPES
215 ;
216 int i = rng_.NextInt(n);
217 #define PICK_BITSET_TYPE(type, value) \
218 if (i-- == 0) return Type::type(region_);
219 BITSET_TYPE_LIST(PICK_BITSET_TYPE)
220 #undef PICK_BITSET_TYPE
221 UNREACHABLE();
222 }
223 case 1: { // class
224 int i = rng_.NextInt(static_cast<int>(maps.size()));
225 return Type::Class(maps[i], region_);
226 }
227 case 2: { // constant
228 int i = rng_.NextInt(static_cast<int>(values.size()));
229 return Type::Constant(values[i], region_);
230 }
231 default: { // union
232 int n = rng_.NextInt(10);
233 TypeHandle type = None;
234 for (int i = 0; i < n; ++i) {
235 type = Type::Union(type, Fuzz(depth - 1), region_);
236 }
237 return type;
238 }
239 }
240 UNREACHABLE();
241 }
242
156 private: 243 private:
157 Region* region_; 244 Region* region_;
245 RandomNumberGenerator rng_;
158 }; 246 };
159 247
160 248
161 // Testing auxiliaries (breaking the Type abstraction).
162 struct ZoneRep {
163 typedef void* Struct;
164
165 static bool IsStruct(Type* t, int tag) {
166 return !IsBitset(t) && reinterpret_cast<intptr_t>(AsStruct(t)[0]) == tag;
167 }
168 static bool IsBitset(Type* t) { return reinterpret_cast<intptr_t>(t) & 1; }
169 static bool IsClass(Type* t) { return IsStruct(t, 0); }
170 static bool IsConstant(Type* t) { return IsStruct(t, 1); }
171 static bool IsUnion(Type* t) { return IsStruct(t, 2); }
172
173 static Struct* AsStruct(Type* t) {
174 return reinterpret_cast<Struct*>(t);
175 }
176 static int AsBitset(Type* t) {
177 return static_cast<int>(reinterpret_cast<intptr_t>(t) >> 1);
178 }
179 static Map* AsClass(Type* t) {
180 return *static_cast<Map**>(AsStruct(t)[3]);
181 }
182 static Object* AsConstant(Type* t) {
183 return *static_cast<Object**>(AsStruct(t)[3]);
184 }
185 static Struct* AsUnion(Type* t) {
186 return AsStruct(t);
187 }
188 static int Length(Struct* structured) {
189 return static_cast<int>(reinterpret_cast<intptr_t>(structured[1]));
190 }
191
192 static Zone* ToRegion(Zone* zone, Isolate* isolate) { return zone; }
193 };
194
195
196 struct HeapRep {
197 typedef FixedArray Struct;
198
199 static bool IsStruct(Handle<HeapType> t, int tag) {
200 return t->IsFixedArray() && Smi::cast(AsStruct(t)->get(0))->value() == tag;
201 }
202 static bool IsBitset(Handle<HeapType> t) { return t->IsSmi(); }
203 static bool IsClass(Handle<HeapType> t) { return t->IsMap(); }
204 static bool IsConstant(Handle<HeapType> t) { return t->IsBox(); }
205 static bool IsUnion(Handle<HeapType> t) { return IsStruct(t, 2); }
206
207 static Struct* AsStruct(Handle<HeapType> t) { return FixedArray::cast(*t); }
208 static int AsBitset(Handle<HeapType> t) { return Smi::cast(*t)->value(); }
209 static Map* AsClass(Handle<HeapType> t) { return Map::cast(*t); }
210 static Object* AsConstant(Handle<HeapType> t) {
211 return Box::cast(*t)->value();
212 }
213 static Struct* AsUnion(Handle<HeapType> t) { return AsStruct(t); }
214 static int Length(Struct* structured) { return structured->length() - 1; }
215
216 static Isolate* ToRegion(Zone* zone, Isolate* isolate) { return isolate; }
217 };
218
219
220 template<class Type, class TypeHandle, class Region, class Rep> 249 template<class Type, class TypeHandle, class Region, class Rep>
221 struct Tests : Rep { 250 struct Tests : Rep {
222 typedef Types<Type, TypeHandle, Region> TypesInstance; 251 typedef Types<Type, TypeHandle, Region> TypesInstance;
223 typedef typename TypesInstance::TypeVector::iterator TypeIterator; 252 typedef typename TypesInstance::TypeVector::iterator TypeIterator;
224 typedef typename TypesInstance::MapVector::iterator MapIterator; 253 typedef typename TypesInstance::MapVector::iterator MapIterator;
225 typedef typename TypesInstance::ValueVector::iterator ValueIterator; 254 typedef typename TypesInstance::ValueVector::iterator ValueIterator;
226 255
227 Isolate* isolate; 256 Isolate* isolate;
228 HandleScope scope; 257 HandleScope scope;
229 Zone zone; 258 Zone zone;
230 TypesInstance T; 259 TypesInstance T;
231 260
232 Tests() : 261 Tests() :
233 isolate(CcTest::i_isolate()), 262 isolate(CcTest::i_isolate()),
234 scope(isolate), 263 scope(isolate),
235 zone(isolate), 264 zone(isolate),
236 T(Rep::ToRegion(&zone, isolate), isolate) { 265 T(Rep::ToRegion(&zone, isolate), isolate) {
237 } 266 }
238 267
268 bool Equal(TypeHandle type1, TypeHandle type2) {
269 return
270 type1->Is(type2) && type2->Is(type1) &&
271 Rep::IsBitset(type1) == Rep::IsBitset(type2) &&
272 Rep::IsClass(type1) == Rep::IsClass(type2) &&
273 Rep::IsConstant(type1) == Rep::IsConstant(type2) &&
274 Rep::IsUnion(type1) == Rep::IsUnion(type2) &&
275 type1->NumClasses() == type2->NumClasses() &&
276 type1->NumConstants() == type2->NumConstants() &&
277 (!Rep::IsBitset(type1) ||
278 Rep::AsBitset(type1) == Rep::AsBitset(type2)) &&
279 (!Rep::IsClass(type1) ||
280 Rep::AsClass(type1) == Rep::AsClass(type2)) &&
281 (!Rep::IsConstant(type1) ||
282 Rep::AsConstant(type1) == Rep::AsConstant(type2)) &&
283 (!Rep::IsUnion(type1) ||
284 Rep::Length(Rep::AsUnion(type1)) == Rep::Length(Rep::AsUnion(type2)));
285 }
286
239 void CheckEqual(TypeHandle type1, TypeHandle type2) { 287 void CheckEqual(TypeHandle type1, TypeHandle type2) {
240 CHECK_EQ(Rep::IsBitset(type1), Rep::IsBitset(type2)); 288 CHECK(Equal(type1, type2));
241 CHECK_EQ(Rep::IsClass(type1), Rep::IsClass(type2));
242 CHECK_EQ(Rep::IsConstant(type1), Rep::IsConstant(type2));
243 CHECK_EQ(Rep::IsUnion(type1), Rep::IsUnion(type2));
244 CHECK_EQ(type1->NumClasses(), type2->NumClasses());
245 CHECK_EQ(type1->NumConstants(), type2->NumConstants());
246 if (Rep::IsBitset(type1)) {
247 CHECK_EQ(Rep::AsBitset(type1), Rep::AsBitset(type2));
248 } else if (Rep::IsClass(type1)) {
249 CHECK_EQ(Rep::AsClass(type1), Rep::AsClass(type2));
250 } else if (Rep::IsConstant(type1)) {
251 CHECK_EQ(Rep::AsConstant(type1), Rep::AsConstant(type2));
252 } else if (Rep::IsUnion(type1)) {
253 CHECK_EQ(
254 Rep::Length(Rep::AsUnion(type1)), Rep::Length(Rep::AsUnion(type2)));
255 }
256 CHECK(type1->Is(type2));
257 CHECK(type2->Is(type1));
258 } 289 }
259 290
260 void CheckSub(TypeHandle type1, TypeHandle type2) { 291 void CheckSub(TypeHandle type1, TypeHandle type2) {
261 CHECK(type1->Is(type2)); 292 CHECK(type1->Is(type2));
262 CHECK(!type2->Is(type1)); 293 CHECK(!type2->Is(type1));
263 if (Rep::IsBitset(type1) && Rep::IsBitset(type2)) { 294 if (Rep::IsBitset(type1) && Rep::IsBitset(type2)) {
264 CHECK_NE(Rep::AsBitset(type1), Rep::AsBitset(type2)); 295 CHECK_NE(Rep::AsBitset(type1), Rep::AsBitset(type2));
265 } 296 }
266 } 297 }
267 298
(...skipping 26 matching lines...) Expand all
294 } 325 }
295 326
296 void Bitset() { 327 void Bitset() {
297 // None and Any are bitsets. 328 // None and Any are bitsets.
298 CHECK(this->IsBitset(T.None)); 329 CHECK(this->IsBitset(T.None));
299 CHECK(this->IsBitset(T.Any)); 330 CHECK(this->IsBitset(T.Any));
300 331
301 CHECK_EQ(0, this->AsBitset(T.None)); 332 CHECK_EQ(0, this->AsBitset(T.None));
302 CHECK_EQ(-1, this->AsBitset(T.Any)); 333 CHECK_EQ(-1, this->AsBitset(T.Any));
303 334
304 // Union(T1, T2) is a bitset for all bitsets T1,T2 335 // Union(T1, T2) is bitset for bitsets T1,T2
305 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 336 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
306 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 337 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
307 TypeHandle type1 = *it1; 338 TypeHandle type1 = *it1;
308 TypeHandle type2 = *it2; 339 TypeHandle type2 = *it2;
340 TypeHandle union12 = T.Union(type1, type2);
309 CHECK(!(this->IsBitset(type1) && this->IsBitset(type2)) || 341 CHECK(!(this->IsBitset(type1) && this->IsBitset(type2)) ||
310 this->IsBitset(T.Union(type1, type2))); 342 this->IsBitset(union12));
311 } 343 }
312 } 344 }
313 345
314 // Union(T1, T2) is a bitset if T2 is a bitset and T1->Is(T2) 346 // Intersect(T1, T2) is bitset for bitsets T1,T2
315 // (and vice versa).
316 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 347 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
317 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 348 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
318 TypeHandle type1 = *it1; 349 TypeHandle type1 = *it1;
319 TypeHandle type2 = *it2; 350 TypeHandle type2 = *it2;
320 CHECK(!(this->IsBitset(type2) && type1->Is(type2)) || 351 TypeHandle intersect12 = T.Intersect(type1, type2);
321 this->IsBitset(T.Union(type1, type2))); 352 CHECK(!(this->IsBitset(type1) && this->IsBitset(type2)) ||
322 CHECK(!(this->IsBitset(type1) && type2->Is(type1)) || 353 this->IsBitset(intersect12));
323 this->IsBitset(T.Union(type1, type2)));
324 } 354 }
325 } 355 }
326 356
327 // Union(T1, T2) is bitwise disjunction for all bitsets T1,T2 357 // Union(T1, T2) is bitset if T2 is bitset and T1->Is(T2)
328 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 358 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
329 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 359 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
330 TypeHandle type1 = *it1; 360 TypeHandle type1 = *it1;
331 TypeHandle type2 = *it2; 361 TypeHandle type2 = *it2;
362 TypeHandle union12 = T.Union(type1, type2);
363 CHECK(!(this->IsBitset(type2) && type1->Is(type2)) ||
364 this->IsBitset(union12));
365 }
366 }
367
368 // Union(T1, T2) is bitwise disjunction for bitsets T1,T2
369 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
370 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
371 TypeHandle type1 = *it1;
372 TypeHandle type2 = *it2;
373 TypeHandle union12 = T.Union(type1, type2);
332 if (this->IsBitset(type1) && this->IsBitset(type2)) { 374 if (this->IsBitset(type1) && this->IsBitset(type2)) {
333 CHECK_EQ( 375 CHECK_EQ(
334 this->AsBitset(type1) | this->AsBitset(type2), 376 this->AsBitset(type1) | this->AsBitset(type2),
335 this->AsBitset(T.Union(type1, type2))); 377 this->AsBitset(union12));
336 } 378 }
337 } 379 }
338 } 380 }
339 381
340 // Intersect(T1, T2) is bitwise conjunction for all bitsets T1,T2 382 // Intersect(T1, T2) is bitwise conjunction for bitsets T1,T2
341 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 383 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
342 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 384 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
343 TypeHandle type1 = *it1; 385 TypeHandle type1 = *it1;
344 TypeHandle type2 = *it2; 386 TypeHandle type2 = *it2;
387 TypeHandle intersect12 = T.Intersect(type1, type2);
345 if (this->IsBitset(type1) && this->IsBitset(type2)) { 388 if (this->IsBitset(type1) && this->IsBitset(type2)) {
346 CHECK_EQ( 389 CHECK_EQ(
347 this->AsBitset(type1) & this->AsBitset(type2), 390 this->AsBitset(type1) & this->AsBitset(type2),
348 this->AsBitset(T.Intersect(type1, type2))); 391 this->AsBitset(intersect12));
349 } 392 }
350 } 393 }
351 } 394 }
352 } 395 }
353 396
354 void Class() { 397 void Class() {
355 // Constructor 398 // Constructor
356 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 399 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
357 Handle<i::Map> map = *mt; 400 Handle<i::Map> map = *mt;
358 CHECK(this->IsClass(T.Class(map))); 401 TypeHandle type = T.Class(map);
402 CHECK(this->IsClass(type));
359 } 403 }
360 404
361 // Map attribute 405 // Map attribute
362 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 406 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
363 Handle<i::Map> map = *mt; 407 Handle<i::Map> map = *mt;
364 CHECK(*map == *T.Class(map)->AsClass()); 408 TypeHandle type = T.Class(map);
409 CHECK(*map == *type->AsClass());
365 } 410 }
366 411
367 // Functionality & Injectivity 412 // Functionality & Injectivity: Class(M1) = Class(M2) iff M1 = M2
368 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) { 413 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) {
369 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) { 414 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) {
370 Handle<i::Map> map1 = *mt1; 415 Handle<i::Map> map1 = *mt1;
371 Handle<i::Map> map2 = *mt2; 416 Handle<i::Map> map2 = *mt2;
372 CHECK(T.Class(map1)->Is(T.Class(map2)) == (*map1 == *map2)); 417 TypeHandle type1 = T.Class(map1);
418 TypeHandle type2 = T.Class(map2);
419 CHECK(Equal(type1, type2) == (*map1 == *map2));
373 } 420 }
374 } 421 }
375 } 422 }
376 423
377 void Constant() { 424 void Constant() {
378 // Constructor 425 // Constructor
379 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 426 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
380 Handle<i::Object> value = *vt; 427 Handle<i::Object> value = *vt;
381 CHECK(this->IsConstant(T.Constant(value))); 428 TypeHandle type = T.Constant(value);
429 CHECK(this->IsConstant(type));
382 } 430 }
383 431
384 // Value attribute 432 // Value attribute
385 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 433 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
386 Handle<i::Object> value = *vt; 434 Handle<i::Object> value = *vt;
387 CHECK(*value == *T.Constant(value)->AsConstant()); 435 TypeHandle type = T.Constant(value);
436 CHECK(*value == *type->AsConstant());
388 } 437 }
389 438
390 // Functionality & Injectivity 439 // Functionality & Injectivity: Constant(V1) = Constant(v2) iff V1 = V2
391 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) { 440 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) {
392 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) { 441 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) {
393 Handle<i::Object> val1 = *vt1; 442 Handle<i::Object> value1 = *vt1;
394 Handle<i::Object> val2 = *vt2; 443 Handle<i::Object> value2 = *vt2;
395 CHECK(T.Constant(val1)->Is(T.Constant(val2)) == (*val1 == *val2)); 444 TypeHandle type1 = T.Constant(value1);
445 TypeHandle type2 = T.Constant(value2);
446 CHECK(Equal(type1, type2) == (*value1 == *value2));
396 } 447 }
397 } 448 }
398 } 449 }
399 450
400 void Of() { 451 void Of() {
401 // Constant(V)->Is(Of(V)) for all V 452 // Constant(V)->Is(Of(V))
402 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 453 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
403 Handle<i::Object> value = *vt; 454 Handle<i::Object> value = *vt;
404 CHECK(T.Constant(value)->Is(T.Of(value))); 455 TypeHandle const_type = T.Constant(value);
456 TypeHandle of_type = T.Of(value);
457 CHECK(const_type->Is(of_type));
405 } 458 }
406 459
407 // Constant(V)->Is(T) implies Of(V)->Is(T) or T->Maybe(Constant(V)) 460 // Constant(V)->Is(T) iff Of(V)->Is(T) or T->Maybe(Constant(V))
408 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 461 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
409 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 462 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
410 Handle<i::Object> value = *vt; 463 Handle<i::Object> value = *vt;
411 TypeHandle type = *it; 464 TypeHandle type = *it;
412 CHECK(!T.Constant(value)->Is(type) || 465 TypeHandle const_type = T.Constant(value);
413 T.Of(value)->Is(type) || type->Maybe(T.Constant(value))); 466 TypeHandle of_type = T.Of(value);
467 CHECK(const_type->Is(type) ==
468 (of_type->Is(type) || type->Maybe(const_type)));
414 } 469 }
415 } 470 }
416 } 471 }
417 472
418 void NowOf() { 473 void NowOf() {
419 // Constant(V)->NowIs(NowOf(V)) for all V 474 // Constant(V)->NowIs(NowOf(V))
420 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 475 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
421 Handle<i::Object> value = *vt; 476 Handle<i::Object> value = *vt;
422 CHECK(T.Constant(value)->NowIs(T.NowOf(value))); 477 TypeHandle const_type = T.Constant(value);
478 TypeHandle nowof_type = T.NowOf(value);
479 CHECK(const_type->NowIs(nowof_type));
423 } 480 }
424 481
425 // NowOf(V)->Is(Of(V)) for all V 482 // NowOf(V)->Is(Of(V))
426 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 483 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
427 Handle<i::Object> value = *vt; 484 Handle<i::Object> value = *vt;
428 CHECK(T.NowOf(value)->Is(T.Of(value))); 485 TypeHandle nowof_type = T.NowOf(value);
486 TypeHandle of_type = T.Of(value);
487 CHECK(nowof_type->Is(of_type));
488 }
489
490 // Constant(V)->NowIs(T) iff NowOf(V)->NowIs(T) or T->Maybe(Constant(V))
491 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
492 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
493 Handle<i::Object> value = *vt;
494 TypeHandle type = *it;
495 TypeHandle const_type = T.Constant(value);
496 TypeHandle nowof_type = T.NowOf(value);
497 CHECK(const_type->NowIs(type) ==
498 (nowof_type->NowIs(type) || type->Maybe(const_type)));
499 }
429 } 500 }
430 501
431 // Constant(V)->Is(T) implies NowOf(V)->Is(T) or T->Maybe(Constant(V)) 502 // Constant(V)->Is(T) implies NowOf(V)->Is(T) or T->Maybe(Constant(V))
432 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 503 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
433 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 504 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
434 Handle<i::Object> value = *vt; 505 Handle<i::Object> value = *vt;
435 TypeHandle type = *it; 506 TypeHandle type = *it;
436 CHECK(!T.Constant(value)->Is(type) || 507 TypeHandle const_type = T.Constant(value);
437 T.NowOf(value)->Is(type) || type->Maybe(T.Constant(value))); 508 TypeHandle nowof_type = T.NowOf(value);
438 } 509 CHECK(!const_type->Is(type) ||
439 } 510 (nowof_type->Is(type) || type->Maybe(const_type)));
440
441 // Constant(V)->NowIs(T) implies NowOf(V)->NowIs(T) or T->Maybe(Constant(V))
442 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
443 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
444 Handle<i::Object> value = *vt;
445 TypeHandle type = *it;
446 CHECK(!T.Constant(value)->NowIs(type) ||
447 T.NowOf(value)->NowIs(type) || type->Maybe(T.Constant(value)));
448 } 511 }
449 } 512 }
450 } 513 }
451 514
452 void Is() { 515 void Is() {
453 // T->Is(None) implies T = None for all T 516 // Least Element (Bottom): None->Is(T)
517 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
518 TypeHandle type = *it;
519 CHECK(T.None->Is(type));
520 }
521
522 // Greatest Element (Top): T->Is(Any)
523 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
524 TypeHandle type = *it;
525 CHECK(type->Is(T.Any));
526 }
527
528 // Bottom Uniqueness: T->Is(None) implies T = None
454 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 529 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
455 TypeHandle type = *it; 530 TypeHandle type = *it;
456 if (type->Is(T.None)) CheckEqual(type, T.None); 531 if (type->Is(T.None)) CheckEqual(type, T.None);
457 } 532 }
458 533
459 // None->Is(T) for all T 534 // Top Uniqueness: Any->Is(T) implies T = Any
460 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
461 TypeHandle type = *it;
462 CHECK(T.None->Is(type));
463 }
464
465 // Any->Is(T) implies T = Any for all T
466 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 535 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
467 TypeHandle type = *it; 536 TypeHandle type = *it;
468 if (T.Any->Is(type)) CheckEqual(type, T.Any); 537 if (T.Any->Is(type)) CheckEqual(type, T.Any);
469 } 538 }
470 539
471 // T->Is(Any) for all T 540 // Reflexivity: T->Is(T)
472 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
473 TypeHandle type = *it;
474 CHECK(type->Is(T.Any));
475 }
476
477 // Reflexivity
478 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 541 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
479 TypeHandle type = *it; 542 TypeHandle type = *it;
480 CHECK(type->Is(type)); 543 CHECK(type->Is(type));
481 } 544 }
482 545
483 // Transitivity 546 // Transitivity: T1->Is(T2) and T2->Is(T3) implies T1->Is(T3)
484 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 547 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
485 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 548 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
486 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) { 549 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
487 TypeHandle type1 = *it1; 550 TypeHandle type1 = *it1;
488 TypeHandle type2 = *it2; 551 TypeHandle type2 = *it2;
489 TypeHandle type3 = *it3; 552 TypeHandle type3 = *it3;
490 CHECK(!(type1->Is(type2) && type2->Is(type3)) || type1->Is(type3)); 553 CHECK(!(type1->Is(type2) && type2->Is(type3)) || type1->Is(type3));
491 } 554 }
492 } 555 }
493 } 556 }
494 557
558 // Antisymmetry: T1->Is(T2) and T2->Is(T1) iff T1 = T2
559 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
560 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
561 TypeHandle type1 = *it1;
562 TypeHandle type2 = *it2;
563 CHECK((type1->Is(type2) && type2->Is(type1)) == Equal(type1, type2));
564 }
565 }
566
495 // Constant(V1)->Is(Constant(V2)) iff V1 = V2 567 // Constant(V1)->Is(Constant(V2)) iff V1 = V2
496 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) { 568 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) {
497 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) { 569 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) {
498 Handle<i::Object> val1 = *vt1; 570 Handle<i::Object> value1 = *vt1;
499 Handle<i::Object> val2 = *vt2; 571 Handle<i::Object> value2 = *vt2;
500 CHECK(T.Constant(val1)->Is(T.Constant(val2)) == (*val1 == *val2)); 572 TypeHandle const_type1 = T.Constant(value1);
573 TypeHandle const_type2 = T.Constant(value2);
574 CHECK(const_type1->Is(const_type2) == (*value1 == *value2));
501 } 575 }
502 } 576 }
503 577
504 // Class(M1)->Is(Class(M2)) iff M1 = M2 578 // Class(M1)->Is(Class(M2)) iff M1 = M2
505 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) { 579 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) {
506 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) { 580 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) {
507 Handle<i::Map> map1 = *mt1; 581 Handle<i::Map> map1 = *mt1;
508 Handle<i::Map> map2 = *mt2; 582 Handle<i::Map> map2 = *mt2;
509 CHECK(T.Class(map1)->Is(T.Class(map2)) == (*map1 == *map2)); 583 TypeHandle class_type1 = T.Class(map1);
584 TypeHandle class_type2 = T.Class(map2);
585 CHECK(class_type1->Is(class_type2) == (*map1 == *map2));
510 } 586 }
511 } 587 }
512 588
513 // Constant(V)->Is(Class(M)) for no V,M 589 // Constant(V)->Is(Class(M)) never
514 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 590 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
515 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 591 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
516 Handle<i::Map> map = *mt; 592 Handle<i::Map> map = *mt;
517 Handle<i::Object> value = *vt; 593 Handle<i::Object> value = *vt;
518 CHECK(!T.Constant(value)->Is(T.Class(map))); 594 TypeHandle constant_type = T.Constant(value);
595 TypeHandle class_type = T.Class(map);
596 CHECK(!constant_type->Is(class_type));
519 } 597 }
520 } 598 }
521 599
522 // Class(M)->Is(Constant(V)) for no V,M 600 // Class(M)->Is(Constant(V)) never
523 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 601 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
524 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 602 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
525 Handle<i::Map> map = *mt; 603 Handle<i::Map> map = *mt;
526 Handle<i::Object> value = *vt; 604 Handle<i::Object> value = *vt;
527 CHECK(!T.Class(map)->Is(T.Constant(value))); 605 TypeHandle constant_type = T.Constant(value);
606 TypeHandle class_type = T.Class(map);
607 CHECK(!class_type->Is(constant_type));
528 } 608 }
529 } 609 }
530 610
531 // Basic types 611 // Basic types
532 CheckUnordered(T.Boolean, T.Null); 612 CheckUnordered(T.Boolean, T.Null);
533 CheckUnordered(T.Undefined, T.Null); 613 CheckUnordered(T.Undefined, T.Null);
534 CheckUnordered(T.Boolean, T.Undefined); 614 CheckUnordered(T.Boolean, T.Undefined);
535 615
536 CheckSub(T.SignedSmall, T.Number); 616 CheckSub(T.SignedSmall, T.Number);
537 CheckSub(T.Signed32, T.Number); 617 CheckSub(T.Signed32, T.Number);
(...skipping 13 matching lines...) Expand all
551 CheckUnordered(T.String, T.Symbol); 631 CheckUnordered(T.String, T.Symbol);
552 CheckUnordered(T.InternalizedString, T.Symbol); 632 CheckUnordered(T.InternalizedString, T.Symbol);
553 633
554 CheckSub(T.Object, T.Receiver); 634 CheckSub(T.Object, T.Receiver);
555 CheckSub(T.Array, T.Object); 635 CheckSub(T.Array, T.Object);
556 CheckSub(T.Function, T.Object); 636 CheckSub(T.Function, T.Object);
557 CheckSub(T.Proxy, T.Receiver); 637 CheckSub(T.Proxy, T.Receiver);
558 CheckUnordered(T.Object, T.Proxy); 638 CheckUnordered(T.Object, T.Proxy);
559 CheckUnordered(T.Array, T.Function); 639 CheckUnordered(T.Array, T.Function);
560 640
561 CheckSub(T.UninitializedClass, T.Internal);
562 CheckSub(T.UninitializedConstant, T.Internal);
563 CheckUnordered(T.UninitializedClass, T.Null);
564 CheckUnordered(T.UninitializedClass, T.Undefined);
565 CheckUnordered(T.UninitializedConstant, T.Null);
566 CheckUnordered(T.UninitializedConstant, T.Undefined);
567
568 // Structural types 641 // Structural types
569 CheckSub(T.ObjectClass, T.Object); 642 CheckSub(T.ObjectClass, T.Object);
570 CheckSub(T.ArrayClass, T.Object); 643 CheckSub(T.ArrayClass, T.Object);
644 CheckSub(T.UninitializedClass, T.Internal);
571 CheckUnordered(T.ObjectClass, T.ArrayClass); 645 CheckUnordered(T.ObjectClass, T.ArrayClass);
646 CheckUnordered(T.UninitializedClass, T.Null);
647 CheckUnordered(T.UninitializedClass, T.Undefined);
572 648
573 CheckSub(T.SmiConstant, T.SignedSmall); 649 CheckSub(T.SmiConstant, T.SignedSmall);
574 CheckSub(T.SmiConstant, T.Signed32); 650 CheckSub(T.SmiConstant, T.Signed32);
575 CheckSub(T.SmiConstant, T.Number); 651 CheckSub(T.SmiConstant, T.Number);
576 CheckSub(T.ObjectConstant1, T.Object); 652 CheckSub(T.ObjectConstant1, T.Object);
577 CheckSub(T.ObjectConstant2, T.Object); 653 CheckSub(T.ObjectConstant2, T.Object);
578 CheckSub(T.ArrayConstant, T.Object); 654 CheckSub(T.ArrayConstant, T.Object);
579 CheckSub(T.ArrayConstant, T.Array); 655 CheckSub(T.ArrayConstant, T.Array);
656 CheckSub(T.UninitializedConstant, T.Internal);
580 CheckUnordered(T.ObjectConstant1, T.ObjectConstant2); 657 CheckUnordered(T.ObjectConstant1, T.ObjectConstant2);
581 CheckUnordered(T.ObjectConstant1, T.ArrayConstant); 658 CheckUnordered(T.ObjectConstant1, T.ArrayConstant);
659 CheckUnordered(T.UninitializedConstant, T.Null);
660 CheckUnordered(T.UninitializedConstant, T.Undefined);
582 661
583 CheckUnordered(T.ObjectConstant1, T.ObjectClass); 662 CheckUnordered(T.ObjectConstant1, T.ObjectClass);
584 CheckUnordered(T.ObjectConstant2, T.ObjectClass); 663 CheckUnordered(T.ObjectConstant2, T.ObjectClass);
585 CheckUnordered(T.ObjectConstant1, T.ArrayClass); 664 CheckUnordered(T.ObjectConstant1, T.ArrayClass);
586 CheckUnordered(T.ObjectConstant2, T.ArrayClass); 665 CheckUnordered(T.ObjectConstant2, T.ArrayClass);
587 CheckUnordered(T.ArrayConstant, T.ObjectClass); 666 CheckUnordered(T.ArrayConstant, T.ObjectClass);
588 } 667 }
589 668
590 void NowIs() { 669 void NowIs() {
591 // T->NowIs(None) implies T = None for all T 670 // Least Element (Bottom): None->NowIs(T)
671 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
672 TypeHandle type = *it;
673 CHECK(T.None->NowIs(type));
674 }
675
676 // Greatest Element (Top): T->NowIs(Any)
677 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
678 TypeHandle type = *it;
679 CHECK(type->NowIs(T.Any));
680 }
681
682 // Bottom Uniqueness: T->NowIs(None) implies T = None
592 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 683 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
593 TypeHandle type = *it; 684 TypeHandle type = *it;
594 if (type->NowIs(T.None)) CheckEqual(type, T.None); 685 if (type->NowIs(T.None)) CheckEqual(type, T.None);
595 } 686 }
596 687
597 // None->NowIs(T) for all T 688 // Top Uniqueness: Any->NowIs(T) implies T = Any
598 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
599 TypeHandle type = *it;
600 CHECK(T.None->NowIs(type));
601 }
602
603 // Any->NowIs(T) implies T = Any for all T
604 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 689 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
605 TypeHandle type = *it; 690 TypeHandle type = *it;
606 if (T.Any->NowIs(type)) CheckEqual(type, T.Any); 691 if (T.Any->NowIs(type)) CheckEqual(type, T.Any);
607 } 692 }
608 693
609 // T->NowIs(Any) for all T 694 // Reflexivity: T->NowIs(T)
610 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
611 TypeHandle type = *it;
612 CHECK(type->NowIs(T.Any));
613 }
614
615 // Reflexivity
616 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 695 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
617 TypeHandle type = *it; 696 TypeHandle type = *it;
618 CHECK(type->NowIs(type)); 697 CHECK(type->NowIs(type));
619 } 698 }
620 699
621 // Transitivity 700 // Transitivity: T1->NowIs(T2) and T2->NowIs(T3) implies T1->NowIs(T3)
622 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 701 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
623 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 702 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
624 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) { 703 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
625 TypeHandle type1 = *it1; 704 TypeHandle type1 = *it1;
626 TypeHandle type2 = *it2; 705 TypeHandle type2 = *it2;
627 TypeHandle type3 = *it3; 706 TypeHandle type3 = *it3;
628 CHECK(!type1->NowIs(type2) || 707 CHECK(!(type1->NowIs(type2) && type2->NowIs(type3)) ||
629 !type2->NowIs(type3) ||
630 type1->NowIs(type3)); 708 type1->NowIs(type3));
631 } 709 }
632 } 710 }
633 } 711 }
634 712
635 // T1->Is(T2) implies T1->NowIs(T2) for all T1,T2 713 // Antisymmetry: T1->NowIs(T2) and T2->NowIs(T1) iff T1 = T2
636 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 714 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
637 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 715 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
638 TypeHandle type1 = *it1; 716 TypeHandle type1 = *it1;
717 TypeHandle type2 = *it2;
718 CHECK((type1->NowIs(type2) && type2->NowIs(type1)) ==
719 Equal(type1, type2));
720 }
721 }
722
723 // T1->Is(T2) implies T1->NowIs(T2)
724 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
725 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
726 TypeHandle type1 = *it1;
639 TypeHandle type2 = *it2; 727 TypeHandle type2 = *it2;
640 CHECK(!type1->Is(type2) || type1->NowIs(type2)); 728 CHECK(!type1->Is(type2) || type1->NowIs(type2));
641 } 729 }
642 } 730 }
643 731
644 // Constant(V1)->NowIs(Constant(V2)) iff V1 = V2 732 // Constant(V1)->NowIs(Constant(V2)) iff V1 = V2
645 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) { 733 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) {
646 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) { 734 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) {
647 Handle<i::Object> val1 = *vt1; 735 Handle<i::Object> value1 = *vt1;
648 Handle<i::Object> val2 = *vt2; 736 Handle<i::Object> value2 = *vt2;
649 CHECK(T.Constant(val1)->NowIs(T.Constant(val2)) == (*val1 == *val2)); 737 TypeHandle const_type1 = T.Constant(value1);
738 TypeHandle const_type2 = T.Constant(value2);
739 CHECK(const_type1->NowIs(const_type2) == (*value1 == *value2));
650 } 740 }
651 } 741 }
652 742
653 // Class(M1)->NowIs(Class(M2)) iff M1 = M2 743 // Class(M1)->NowIs(Class(M2)) iff M1 = M2
654 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) { 744 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) {
655 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) { 745 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) {
656 Handle<i::Map> map1 = *mt1; 746 Handle<i::Map> map1 = *mt1;
657 Handle<i::Map> map2 = *mt2; 747 Handle<i::Map> map2 = *mt2;
658 CHECK(T.Class(map1)->NowIs(T.Class(map2)) == (*map1 == *map2)); 748 TypeHandle class_type1 = T.Class(map1);
749 TypeHandle class_type2 = T.Class(map2);
750 CHECK(class_type1->NowIs(class_type2) == (*map1 == *map2));
659 } 751 }
660 } 752 }
661 753
662 // Constant(V)->NowIs(Class(M)) iff V has map M 754 // Constant(V)->NowIs(Class(M)) iff V has map M
663 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 755 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
664 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 756 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
665 Handle<i::Map> map = *mt; 757 Handle<i::Map> map = *mt;
666 Handle<i::Object> value = *vt; 758 Handle<i::Object> value = *vt;
759 TypeHandle const_type = T.Constant(value);
760 TypeHandle class_type = T.Class(map);
667 CHECK((value->IsHeapObject() && 761 CHECK((value->IsHeapObject() &&
668 i::HeapObject::cast(*value)->map() == *map) 762 i::HeapObject::cast(*value)->map() == *map)
669 == T.Constant(value)->NowIs(T.Class(map))); 763 == const_type->NowIs(class_type));
670 } 764 }
671 } 765 }
672 766
673 // Class(M)->NowIs(Constant(V)) for no V,M 767 // Class(M)->NowIs(Constant(V)) never
674 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 768 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
675 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 769 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
676 Handle<i::Map> map = *mt; 770 Handle<i::Map> map = *mt;
677 Handle<i::Object> value = *vt; 771 Handle<i::Object> value = *vt;
678 CHECK(!T.Class(map)->NowIs(T.Constant(value))); 772 TypeHandle const_type = T.Constant(value);
773 TypeHandle class_type = T.Class(map);
774 CHECK(!class_type->NowIs(const_type));
679 } 775 }
680 } 776 }
681 } 777 }
682 778
683 void Contains() { 779 void Contains() {
684 // T->Contains(V) iff Constant(V)->Is(T) for all T,V 780 // T->Contains(V) iff Constant(V)->Is(T)
685 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 781 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
686 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 782 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
687 TypeHandle type = *it; 783 TypeHandle type = *it;
688 Handle<i::Object> value = *vt; 784 Handle<i::Object> value = *vt;
689 CHECK(type->Contains(value) == T.Constant(value)->Is(type)); 785 TypeHandle const_type = T.Constant(value);
786 CHECK(type->Contains(value) == const_type->Is(type));
690 } 787 }
691 } 788 }
692 789
693 // Of(V)->Is(T) implies T->Contains(V) for all T,V 790 // Of(V)->Is(T) implies T->Contains(V)
694 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 791 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
695 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 792 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
696 TypeHandle type = *it; 793 TypeHandle type = *it;
697 Handle<i::Object> value = *vt; 794 Handle<i::Object> value = *vt;
698 CHECK(!T.Of(value)->Is(type) || type->Contains(value)); 795 TypeHandle of_type = T.Of(value);
796 CHECK(!of_type->Is(type) || type->Contains(value));
699 } 797 }
700 } 798 }
701 } 799 }
702 800
703 void NowContains() { 801 void NowContains() {
704 // T->NowContains(V) iff Constant(V)->NowIs(T) for all T,V 802 // T->NowContains(V) iff Constant(V)->NowIs(T)
705 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 803 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
706 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 804 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
707 TypeHandle type = *it; 805 TypeHandle type = *it;
708 Handle<i::Object> value = *vt; 806 Handle<i::Object> value = *vt;
709 CHECK(type->NowContains(value) == T.Constant(value)->NowIs(type)); 807 TypeHandle const_type = T.Constant(value);
808 CHECK(type->NowContains(value) == const_type->NowIs(type));
710 } 809 }
711 } 810 }
712 811
713 // T->Contains(V) implies T->NowContains(V) for all T,V 812 // T->Contains(V) implies T->NowContains(V)
714 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 813 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
715 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 814 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
716 TypeHandle type = *it; 815 TypeHandle type = *it;
717 Handle<i::Object> value = *vt; 816 Handle<i::Object> value = *vt;
718 CHECK(!type->Contains(value) || type->NowContains(value)); 817 CHECK(!type->Contains(value) || type->NowContains(value));
719 } 818 }
720 } 819 }
721 820
722 // NowOf(V)->Is(T) implies T->NowContains(V) for all T,V 821 // NowOf(V)->Is(T) implies T->NowContains(V)
723 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 822 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
724 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 823 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
725 TypeHandle type = *it; 824 TypeHandle type = *it;
726 Handle<i::Object> value = *vt; 825 Handle<i::Object> value = *vt;
727 CHECK(!T.NowOf(value)->NowIs(type) || type->NowContains(value)); 826 TypeHandle nowof_type = T.Of(value);
827 CHECK(!nowof_type->NowIs(type) || type->NowContains(value));
728 } 828 }
729 } 829 }
730 830
731 // NowOf(V)->NowIs(T) implies T->NowContains(V) for all T,V 831 // NowOf(V)->NowIs(T) implies T->NowContains(V)
732 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 832 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
733 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 833 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
734 TypeHandle type = *it; 834 TypeHandle type = *it;
735 Handle<i::Object> value = *vt; 835 Handle<i::Object> value = *vt;
736 CHECK(!T.NowOf(value)->NowIs(type) || type->NowContains(value)); 836 TypeHandle nowof_type = T.Of(value);
837 CHECK(!nowof_type->NowIs(type) || type->NowContains(value));
737 } 838 }
738 } 839 }
739 } 840 }
740 841
741 void Maybe() { 842 void Maybe() {
742 // T->Maybe(T) iff T inhabited
743 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
744 TypeHandle type = *it;
745 CHECK(type->Maybe(type) == type->IsInhabited());
746 }
747
748 // T->Maybe(Any) iff T inhabited 843 // T->Maybe(Any) iff T inhabited
749 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 844 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
750 TypeHandle type = *it; 845 TypeHandle type = *it;
751 CHECK(type->Maybe(T.Any) == type->IsInhabited()); 846 CHECK(type->Maybe(T.Any) == type->IsInhabited());
752 } 847 }
753 848
754 // T->Maybe(None) never 849 // T->Maybe(None) never
755 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 850 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
756 TypeHandle type = *it; 851 TypeHandle type = *it;
757 CHECK(!type->Maybe(T.None)); 852 CHECK(!type->Maybe(T.None));
758 } 853 }
759 854
760 // Symmetry 855 // Reflexivity upto Inhabitation: T->Maybe(T) iff T inhabited
856 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
857 TypeHandle type = *it;
858 CHECK(type->Maybe(type) == type->IsInhabited());
859 }
860
861 // Symmetry: T1->Maybe(T2) iff T2->Maybe(T1)
761 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 862 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
762 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 863 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
763 TypeHandle type1 = *it1; 864 TypeHandle type1 = *it1;
764 TypeHandle type2 = *it2; 865 TypeHandle type2 = *it2;
765 CHECK(type1->Maybe(type2) == type2->Maybe(type1)); 866 CHECK(type1->Maybe(type2) == type2->Maybe(type1));
766 } 867 }
767 } 868 }
768 869
769 // T1->Maybe(T2) only if T1, T2 inhabited 870 // T1->Maybe(T2) implies T1, T2 inhabited
770 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 871 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
771 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 872 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
772 TypeHandle type1 = *it1; 873 TypeHandle type1 = *it1;
773 TypeHandle type2 = *it2; 874 TypeHandle type2 = *it2;
774 CHECK(!type1->Maybe(type2) || 875 CHECK(!type1->Maybe(type2) ||
775 (type1->IsInhabited() && type2->IsInhabited())); 876 (type1->IsInhabited() && type2->IsInhabited()));
776 } 877 }
777 } 878 }
778 879
779 // T1->Is(T2) and T1 inhabited implies T1->Maybe(T2) for all T1,T2 880 // T1->Maybe(T2) iff Intersect(T1, T2) inhabited
780 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) { 881 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
781 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) { 882 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
782 TypeHandle type1 = *it1; 883 TypeHandle type1 = *it1;
884 TypeHandle type2 = *it2;
885 TypeHandle intersect12 = T.Intersect(type1, type2);
886 CHECK(type1->Maybe(type2) == intersect12->IsInhabited());
887 }
888 }
889
890 // T1->Is(T2) and T1 inhabited implies T1->Maybe(T2)
891 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
892 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
893 TypeHandle type1 = *it1;
783 TypeHandle type2 = *it2; 894 TypeHandle type2 = *it2;
784 CHECK(!(type1->Is(type2) && type1->IsInhabited()) || 895 CHECK(!(type1->Is(type2) && type1->IsInhabited()) ||
785 type1->Maybe(type2)); 896 type1->Maybe(type2));
786 } 897 }
787 } 898 }
788 899
789 // Constant(V1)->Maybe(Constant(V2)) iff V1 = V2 900 // Constant(V1)->Maybe(Constant(V2)) iff V1 = V2
790 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) { 901 for (ValueIterator vt1 = T.values.begin(); vt1 != T.values.end(); ++vt1) {
791 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) { 902 for (ValueIterator vt2 = T.values.begin(); vt2 != T.values.end(); ++vt2) {
792 Handle<i::Object> val1 = *vt1; 903 Handle<i::Object> value1 = *vt1;
793 Handle<i::Object> val2 = *vt2; 904 Handle<i::Object> value2 = *vt2;
794 CHECK(T.Constant(val1)->Maybe(T.Constant(val2)) == (*val1 == *val2)); 905 TypeHandle const_type1 = T.Constant(value1);
906 TypeHandle const_type2 = T.Constant(value2);
907 CHECK(const_type1->Maybe(const_type2) == (*value1 == *value2));
795 } 908 }
796 } 909 }
797 910
798 // Class(M1)->Maybe(Class(M2)) iff M1 = M2 911 // Class(M1)->Maybe(Class(M2)) iff M1 = M2
799 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) { 912 for (MapIterator mt1 = T.maps.begin(); mt1 != T.maps.end(); ++mt1) {
800 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) { 913 for (MapIterator mt2 = T.maps.begin(); mt2 != T.maps.end(); ++mt2) {
801 Handle<i::Map> map1 = *mt1; 914 Handle<i::Map> map1 = *mt1;
802 Handle<i::Map> map2 = *mt2; 915 Handle<i::Map> map2 = *mt2;
803 CHECK(T.Class(map1)->Maybe(T.Class(map2)) == (*map1 == *map2)); 916 TypeHandle class_type1 = T.Class(map1);
917 TypeHandle class_type2 = T.Class(map2);
918 CHECK(class_type1->Maybe(class_type2) == (*map1 == *map2));
804 } 919 }
805 } 920 }
806 921
807 // Constant(V)->Maybe(Class(M)) for no V,M 922 // Constant(V)->Maybe(Class(M)) never
808 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 923 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
809 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 924 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
810 Handle<i::Map> map = *mt; 925 Handle<i::Map> map = *mt;
811 Handle<i::Object> value = *vt; 926 Handle<i::Object> value = *vt;
812 CHECK(!T.Constant(value)->Maybe(T.Class(map))); 927 TypeHandle const_type = T.Constant(value);
928 TypeHandle class_type = T.Class(map);
929 CHECK(!const_type->Maybe(class_type));
813 } 930 }
814 } 931 }
815 932
816 // Class(M)->Maybe(Constant(V)) for no V,M 933 // Class(M)->Maybe(Constant(V)) never
817 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) { 934 for (MapIterator mt = T.maps.begin(); mt != T.maps.end(); ++mt) {
818 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) { 935 for (ValueIterator vt = T.values.begin(); vt != T.values.end(); ++vt) {
819 Handle<i::Map> map = *mt; 936 Handle<i::Map> map = *mt;
820 Handle<i::Object> value = *vt; 937 Handle<i::Object> value = *vt;
821 CHECK(!T.Class(map)->Maybe(T.Constant(value))); 938 TypeHandle const_type = T.Constant(value);
939 TypeHandle class_type = T.Class(map);
940 CHECK(!class_type->Maybe(const_type));
822 } 941 }
823 } 942 }
824 943
825 // Basic types 944 // Basic types
826 CheckDisjoint(T.Boolean, T.Null, T.Semantic); 945 CheckDisjoint(T.Boolean, T.Null, T.Semantic);
827 CheckDisjoint(T.Undefined, T.Null, T.Semantic); 946 CheckDisjoint(T.Undefined, T.Null, T.Semantic);
828 CheckDisjoint(T.Boolean, T.Undefined, T.Semantic); 947 CheckDisjoint(T.Boolean, T.Undefined, T.Semantic);
829 948
830 CheckOverlap(T.SignedSmall, T.Number, T.Semantic); 949 CheckOverlap(T.SignedSmall, T.Number, T.Semantic);
831 CheckOverlap(T.Float, T.Number, T.Semantic); 950 CheckOverlap(T.Float, T.Number, T.Semantic);
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
869 CheckDisjoint(T.ObjectConstant1, T.ArrayConstant, T.Semantic); 988 CheckDisjoint(T.ObjectConstant1, T.ArrayConstant, T.Semantic);
870 989
871 CheckDisjoint(T.ObjectConstant1, T.ObjectClass, T.Semantic); 990 CheckDisjoint(T.ObjectConstant1, T.ObjectClass, T.Semantic);
872 CheckDisjoint(T.ObjectConstant2, T.ObjectClass, T.Semantic); 991 CheckDisjoint(T.ObjectConstant2, T.ObjectClass, T.Semantic);
873 CheckDisjoint(T.ObjectConstant1, T.ArrayClass, T.Semantic); 992 CheckDisjoint(T.ObjectConstant1, T.ArrayClass, T.Semantic);
874 CheckDisjoint(T.ObjectConstant2, T.ArrayClass, T.Semantic); 993 CheckDisjoint(T.ObjectConstant2, T.ArrayClass, T.Semantic);
875 CheckDisjoint(T.ArrayConstant, T.ObjectClass, T.Semantic); 994 CheckDisjoint(T.ArrayConstant, T.ObjectClass, T.Semantic);
876 } 995 }
877 996
878 void Union() { 997 void Union() {
879 // Bitset-bitset 998 // Identity: Union(T, None) = T
880 CHECK(this->IsBitset(T.Union(T.Object, T.Number))); 999 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
881 CHECK(this->IsBitset(T.Union(T.Object, T.Object))); 1000 TypeHandle type = *it;
882 CHECK(this->IsBitset(T.Union(T.Any, T.None))); 1001 TypeHandle union_type = T.Union(type, T.None);
1002 CheckEqual(union_type, type);
1003 }
883 1004
884 CheckEqual(T.Union(T.None, T.Number), T.Number); 1005 // Domination: Union(T, Any) = Any
885 CheckEqual(T.Union(T.Object, T.Proxy), T.Receiver); 1006 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
886 CheckEqual(T.Union(T.Number, T.String), T.Union(T.String, T.Number)); 1007 TypeHandle type = *it;
887 CheckSub(T.Union(T.Number, T.String), T.Any); 1008 TypeHandle union_type = T.Union(type, T.Any);
1009 CheckEqual(union_type, T.Any);
1010 }
1011
1012 // Idempotence: Union(T, T) = T
1013 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
1014 TypeHandle type = *it;
1015 TypeHandle union_type = T.Union(type, type);
1016 CheckEqual(union_type, type);
1017 }
1018
1019 // Commutativity: Union(T1, T2) = Union(T2, T1)
1020 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1021 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1022 TypeHandle type1 = *it1;
1023 TypeHandle type2 = *it2;
1024 TypeHandle union12 = T.Union(type1, type2);
1025 TypeHandle union21 = T.Union(type2, type1);
1026 CheckEqual(union12, union21);
1027 }
1028 }
1029
1030 // Associativity: Union(T1, Union(T2, T3)) = Union(Union(T1, T2), T3)
1031 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1032 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1033 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1034 TypeHandle type1 = *it1;
1035 TypeHandle type2 = *it2;
1036 TypeHandle type3 = *it3;
1037 TypeHandle union12 = T.Union(type1, type2);
1038 TypeHandle union23 = T.Union(type2, type3);
1039 TypeHandle union1_23 = T.Union(type1, union23);
1040 TypeHandle union12_3 = T.Union(union12, type3);
1041 CheckEqual(union1_23, union12_3);
1042 }
1043 }
1044 }
1045
1046 // Meet: T1->Is(Union(T1, T2)) and T2->Is(Union(T1, T2))
1047 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1048 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1049 TypeHandle type1 = *it1;
1050 TypeHandle type2 = *it2;
1051 TypeHandle union12 = T.Union(type1, type2);
1052 CHECK(type1->Is(union12));
1053 CHECK(type2->Is(union12));
1054 }
1055 }
1056
1057 // Upper Boundedness: T1->Is(T2) implies Union(T1, T2) = T2
1058 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1059 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1060 TypeHandle type1 = *it1;
1061 TypeHandle type2 = *it2;
1062 TypeHandle union12 = T.Union(type1, type2);
1063 if (type1->Is(type2)) CheckEqual(union12, type2);
1064 }
1065 }
1066
1067 // Monotonicity: T1->Is(T2) implies Union(T1, T3)->Is(Union(T2, T3))
1068 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1069 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1070 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1071 TypeHandle type1 = *it1;
1072 TypeHandle type2 = *it2;
1073 TypeHandle type3 = *it3;
1074 TypeHandle union13 = T.Union(type1, type3);
1075 TypeHandle union23 = T.Union(type2, type3);
1076 CHECK(!type1->Is(type2) || union13->Is(union23));
1077 }
1078 }
1079 }
1080
1081 // Monotonicity: T1->Is(T3) and T2->Is(T3) implies Union(T1, T2)->Is(T3)
1082 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1083 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1084 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1085 TypeHandle type1 = *it1;
1086 TypeHandle type2 = *it2;
1087 TypeHandle type3 = *it3;
1088 TypeHandle union12 = T.Union(type1, type2);
1089 CHECK(!(type1->Is(type3) && type2->Is(type3)) || union12->Is(type3));
1090 }
1091 }
1092 }
1093
1094 // Monotonicity: T1->Is(T2) or T1->Is(T3) implies T1->Is(Union(T2, T3))
1095 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1096 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1097 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1098 TypeHandle type1 = *it1;
1099 TypeHandle type2 = *it2;
1100 TypeHandle type3 = *it3;
1101 TypeHandle union23 = T.Union(type2, type3);
1102 CHECK(!(type1->Is(type2) || type1->Is(type3)) || type1->Is(union23));
1103 }
1104 }
1105 }
888 1106
889 // Class-class 1107 // Class-class
890 CHECK(this->IsClass(T.Union(T.ObjectClass, T.ObjectClass)));
891 CHECK(this->IsUnion(T.Union(T.ObjectClass, T.ArrayClass)));
892
893 CheckEqual(T.Union(T.ObjectClass, T.ObjectClass), T.ObjectClass);
894 CheckSub(T.None, T.Union(T.ObjectClass, T.ArrayClass));
895 CheckSub(T.Union(T.ObjectClass, T.ArrayClass), T.Any);
896 CheckSub(T.ObjectClass, T.Union(T.ObjectClass, T.ArrayClass));
897 CheckSub(T.ArrayClass, T.Union(T.ObjectClass, T.ArrayClass));
898 CheckSub(T.Union(T.ObjectClass, T.ArrayClass), T.Object); 1108 CheckSub(T.Union(T.ObjectClass, T.ArrayClass), T.Object);
899 CheckUnordered(T.Union(T.ObjectClass, T.ArrayClass), T.Array); 1109 CheckUnordered(T.Union(T.ObjectClass, T.ArrayClass), T.Array);
900 CheckOverlap(T.Union(T.ObjectClass, T.ArrayClass), T.Array, T.Semantic); 1110 CheckOverlap(T.Union(T.ObjectClass, T.ArrayClass), T.Array, T.Semantic);
901 CheckDisjoint(T.Union(T.ObjectClass, T.ArrayClass), T.Number, T.Semantic); 1111 CheckDisjoint(T.Union(T.ObjectClass, T.ArrayClass), T.Number, T.Semantic);
902 1112
903 // Constant-constant 1113 // Constant-constant
904 CHECK(this->IsConstant(T.Union(T.ObjectConstant1, T.ObjectConstant1)));
905 CHECK(this->IsConstant(T.Union(T.ArrayConstant, T.ArrayConstant)));
906 CHECK(this->IsUnion(T.Union(T.ObjectConstant1, T.ObjectConstant2)));
907
908 CheckEqual(
909 T.Union(T.ObjectConstant1, T.ObjectConstant1),
910 T.ObjectConstant1);
911 CheckEqual(T.Union(T.ArrayConstant, T.ArrayConstant), T.ArrayConstant);
912 CheckSub(T.None, T.Union(T.ObjectConstant1, T.ObjectConstant2));
913 CheckSub(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.Any);
914 CheckSub(T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2));
915 CheckSub(T.ObjectConstant2, T.Union(T.ObjectConstant1, T.ObjectConstant2));
916 CheckSub(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.Object); 1114 CheckSub(T.Union(T.ObjectConstant1, T.ObjectConstant2), T.Object);
1115 CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayConstant), T.Array);
917 CheckUnordered( 1116 CheckUnordered(
918 T.Union(T.ObjectConstant1, T.ObjectConstant2), T.ObjectClass); 1117 T.Union(T.ObjectConstant1, T.ObjectConstant2), T.ObjectClass);
919 CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayConstant), T.Array);
920 CheckOverlap( 1118 CheckOverlap(
921 T.Union(T.ObjectConstant1, T.ArrayConstant), T.Array, T.Semantic); 1119 T.Union(T.ObjectConstant1, T.ArrayConstant), T.Array, T.Semantic);
922 CheckDisjoint( 1120 CheckDisjoint(
923 T.Union(T.ObjectConstant1, T.ArrayConstant), T.Number, T.Semantic); 1121 T.Union(T.ObjectConstant1, T.ArrayConstant), T.Number, T.Semantic);
924 CheckDisjoint( 1122 CheckDisjoint(
925 T.Union(T.ObjectConstant1, T.ArrayConstant), T.ObjectClass, 1123 T.Union(T.ObjectConstant1, T.ArrayConstant), T.ObjectClass, T.Semantic);
926 T.Semantic);
927 1124
928 // Bitset-class 1125 // Bitset-class
929 CHECK(this->IsBitset(T.Union(T.ObjectClass, T.Object)));
930 CHECK(this->IsUnion(T.Union(T.ObjectClass, T.Number)));
931
932 CheckEqual(T.Union(T.ObjectClass, T.Object), T.Object);
933 CheckSub(T.None, T.Union(T.ObjectClass, T.Number));
934 CheckSub(T.Union(T.ObjectClass, T.Number), T.Any);
935 CheckSub( 1126 CheckSub(
936 T.Union(T.ObjectClass, T.SignedSmall), T.Union(T.Object, T.Number)); 1127 T.Union(T.ObjectClass, T.SignedSmall), T.Union(T.Object, T.Number));
937 CheckSub(T.Union(T.ObjectClass, T.Array), T.Object); 1128 CheckSub(T.Union(T.ObjectClass, T.Array), T.Object);
938 CheckUnordered(T.Union(T.ObjectClass, T.String), T.Array); 1129 CheckUnordered(T.Union(T.ObjectClass, T.String), T.Array);
939 CheckOverlap(T.Union(T.ObjectClass, T.String), T.Object, T.Semantic); 1130 CheckOverlap(T.Union(T.ObjectClass, T.String), T.Object, T.Semantic);
940 CheckDisjoint(T.Union(T.ObjectClass, T.String), T.Number, T.Semantic); 1131 CheckDisjoint(T.Union(T.ObjectClass, T.String), T.Number, T.Semantic);
941 1132
942 // Bitset-constant 1133 // Bitset-constant
943 CHECK(this->IsBitset(T.Union(T.SmiConstant, T.Number)));
944 CHECK(this->IsBitset(T.Union(T.ObjectConstant1, T.Object)));
945 CHECK(this->IsUnion(T.Union(T.ObjectConstant2, T.Number)));
946
947 CheckEqual(T.Union(T.SmiConstant, T.Number), T.Number);
948 CheckEqual(T.Union(T.ObjectConstant1, T.Object), T.Object);
949 CheckSub(T.None, T.Union(T.ObjectConstant1, T.Number));
950 CheckSub(T.Union(T.ObjectConstant1, T.Number), T.Any);
951 CheckSub( 1134 CheckSub(
952 T.Union(T.ObjectConstant1, T.Signed32), T.Union(T.Object, T.Number)); 1135 T.Union(T.ObjectConstant1, T.Signed32), T.Union(T.Object, T.Number));
953 CheckSub(T.Union(T.ObjectConstant1, T.Array), T.Object); 1136 CheckSub(T.Union(T.ObjectConstant1, T.Array), T.Object);
954 CheckUnordered(T.Union(T.ObjectConstant1, T.String), T.Array); 1137 CheckUnordered(T.Union(T.ObjectConstant1, T.String), T.Array);
955 CheckOverlap(T.Union(T.ObjectConstant1, T.String), T.Object, T.Semantic); 1138 CheckOverlap(T.Union(T.ObjectConstant1, T.String), T.Object, T.Semantic);
956 CheckDisjoint(T.Union(T.ObjectConstant1, T.String), T.Number, T.Semantic); 1139 CheckDisjoint(T.Union(T.ObjectConstant1, T.String), T.Number, T.Semantic);
957 CheckEqual(T.Union(T.Signed32, T.Signed32Constant), T.Signed32);
958 1140
959 // Class-constant 1141 // Class-constant
960 CHECK(this->IsUnion(T.Union(T.ObjectConstant1, T.ObjectClass)));
961 CHECK(this->IsUnion(T.Union(T.ArrayClass, T.ObjectConstant2)));
962
963 CheckSub(T.None, T.Union(T.ObjectConstant1, T.ArrayClass));
964 CheckSub(T.Union(T.ObjectConstant1, T.ArrayClass), T.Any);
965 CheckSub(T.Union(T.ObjectConstant1, T.ArrayClass), T.Object); 1142 CheckSub(T.Union(T.ObjectConstant1, T.ArrayClass), T.Object);
966 CheckSub(T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ArrayClass));
967 CheckSub(T.ArrayClass, T.Union(T.ObjectConstant1, T.ArrayClass));
968 CheckUnordered(T.ObjectClass, T.Union(T.ObjectConstant1, T.ArrayClass)); 1143 CheckUnordered(T.ObjectClass, T.Union(T.ObjectConstant1, T.ArrayClass));
969 CheckSub( 1144 CheckSub(
970 T.Union(T.ObjectConstant1, T.ArrayClass), T.Union(T.Array, T.Object)); 1145 T.Union(T.ObjectConstant1, T.ArrayClass), T.Union(T.Array, T.Object));
971 CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayClass), T.ArrayConstant); 1146 CheckUnordered(T.Union(T.ObjectConstant1, T.ArrayClass), T.ArrayConstant);
972 CheckDisjoint( 1147 CheckDisjoint(
973 T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectConstant2, 1148 T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectConstant2,
974 T.Semantic); 1149 T.Semantic);
975 CheckDisjoint( 1150 CheckDisjoint(
976 T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectClass, T.Semantic); 1151 T.Union(T.ObjectConstant1, T.ArrayClass), T.ObjectClass, T.Semantic);
977 1152
978 // Bitset-union 1153 // Bitset-union
979 CHECK(this->IsBitset(
980 T.Union(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass))));
981 CHECK(this->IsUnion(
982 T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.Number)));
983
984 CheckEqual(
985 T.Union(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)),
986 T.Object);
987 CheckEqual(
988 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number),
989 T.Union(T.ObjectConstant1, T.Union(T.Number, T.ArrayClass)));
990 CheckSub( 1154 CheckSub(
991 T.Float, 1155 T.Float,
992 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number)); 1156 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number));
993 CheckSub( 1157 CheckSub(
994 T.ObjectConstant1,
995 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Float));
996 CheckSub(
997 T.None,
998 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Float));
999 CheckSub(
1000 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Float),
1001 T.Any);
1002 CheckSub(
1003 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Float), 1158 T.Union(T.Union(T.ArrayClass, T.ObjectConstant1), T.Float),
1004 T.Union(T.ObjectConstant1, T.Union(T.Number, T.ArrayClass))); 1159 T.Union(T.ObjectConstant1, T.Union(T.Number, T.ArrayClass)));
1005 1160
1006 // Class-union 1161 // Class-union
1007 CHECK(this->IsUnion(
1008 T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass)));
1009 CHECK(this->IsUnion(
1010 T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ObjectClass)));
1011
1012 CheckEqual(
1013 T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)),
1014 T.Union(T.ObjectClass, T.ObjectConstant1));
1015 CheckSub(
1016 T.None,
1017 T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)));
1018 CheckSub(
1019 T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)),
1020 T.Any);
1021 CheckSub( 1162 CheckSub(
1022 T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)), 1163 T.Union(T.ObjectClass, T.Union(T.ObjectConstant1, T.ObjectClass)),
1023 T.Object); 1164 T.Object);
1024 CheckEqual( 1165 CheckEqual(
1025 T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass), 1166 T.Union(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass),
1026 T.Union(T.ArrayClass, T.ObjectConstant2)); 1167 T.Union(T.ArrayClass, T.ObjectConstant2));
1027 1168
1028 // Constant-union 1169 // Constant-union
1029 CHECK(this->IsUnion(T.Union(
1030 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2))));
1031 CHECK(this->IsUnion(T.Union(
1032 T.Union(T.ArrayConstant, T.ObjectClass), T.ObjectConstant1)));
1033 CHECK(this->IsUnion(T.Union(
1034 T.Union(T.ArrayConstant, T.ObjectConstant2), T.ObjectConstant1)));
1035
1036 CheckEqual( 1170 CheckEqual(
1037 T.Union( 1171 T.Union(
1038 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)), 1172 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)),
1039 T.Union(T.ObjectConstant2, T.ObjectConstant1)); 1173 T.Union(T.ObjectConstant2, T.ObjectConstant1));
1040 CheckEqual( 1174 CheckEqual(
1041 T.Union( 1175 T.Union(
1042 T.Union(T.ArrayConstant, T.ObjectConstant2), T.ObjectConstant1), 1176 T.Union(T.ArrayConstant, T.ObjectConstant2), T.ObjectConstant1),
1043 T.Union( 1177 T.Union(
1044 T.ObjectConstant2, T.Union(T.ArrayConstant, T.ObjectConstant1))); 1178 T.ObjectConstant2, T.Union(T.ArrayConstant, T.ObjectConstant1)));
1045 1179
1046 // Union-union 1180 // Union-union
1047 CHECK(this->IsBitset(T.Union(
1048 T.Union(T.Number, T.ArrayClass),
1049 T.Union(T.Signed32, T.Array))));
1050 CHECK(this->IsUnion(T.Union(
1051 T.Union(T.Number, T.ArrayClass),
1052 T.Union(T.ObjectClass, T.ArrayClass))));
1053
1054 CheckEqual( 1181 CheckEqual(
1055 T.Union( 1182 T.Union(
1056 T.Union(T.ObjectConstant2, T.ObjectConstant1), 1183 T.Union(T.ObjectConstant2, T.ObjectConstant1),
1057 T.Union(T.ObjectConstant1, T.ObjectConstant2)), 1184 T.Union(T.ObjectConstant1, T.ObjectConstant2)),
1058 T.Union(T.ObjectConstant2, T.ObjectConstant1)); 1185 T.Union(T.ObjectConstant2, T.ObjectConstant1));
1059 CheckEqual( 1186 CheckEqual(
1060 T.Union( 1187 T.Union(
1061 T.Union(T.Number, T.ArrayClass), 1188 T.Union(T.Number, T.ArrayClass),
1062 T.Union(T.SignedSmall, T.Array)), 1189 T.Union(T.SignedSmall, T.Array)),
1063 T.Union(T.Number, T.Array)); 1190 T.Union(T.Number, T.Array));
1064 } 1191 }
1065 1192
1066 void Intersect() { 1193 void Intersect() {
1067 // Bitset-bitset 1194 // Identity: Intersect(T, Any) = T
1068 CHECK(this->IsBitset(T.Intersect(T.Object, T.Number))); 1195 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
1069 CHECK(this->IsBitset(T.Intersect(T.Object, T.Object))); 1196 TypeHandle type = *it;
1070 CHECK(this->IsBitset(T.Intersect(T.Any, T.None))); 1197 TypeHandle intersect_type = T.Intersect(type, T.Any);
1198 CheckEqual(intersect_type, type);
1199 }
1071 1200
1072 CheckEqual(T.Intersect(T.None, T.Number), T.None); 1201 // Domination: Intersect(T, None) = None
1073 CheckSub(T.Intersect(T.Object, T.Proxy), T.Representation); 1202 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
1074 CheckEqual(T.Intersect(T.Name, T.String), T.Intersect(T.String, T.Name)); 1203 TypeHandle type = *it;
1075 CheckEqual(T.Intersect(T.UniqueName, T.String), T.InternalizedString); 1204 TypeHandle intersect_type = T.Intersect(type, T.None);
1205 CheckEqual(intersect_type, T.None);
1206 }
1076 1207
1077 // Class-class 1208 // Idempotence: Intersect(T, T) = T
1078 CHECK(this->IsClass(T.Intersect(T.ObjectClass, T.ObjectClass))); 1209 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
1079 CHECK(this->IsBitset(T.Intersect(T.ObjectClass, T.ArrayClass))); 1210 TypeHandle type = *it;
1211 TypeHandle intersect_type = T.Intersect(type, type);
1212 CheckEqual(intersect_type, type);
1213 }
1080 1214
1081 CheckEqual(T.Intersect(T.ObjectClass, T.ObjectClass), T.ObjectClass); 1215 // Commutativity: Intersect(T1, T2) = Intersect(T2, T1)
1082 CheckEqual(T.Intersect(T.ObjectClass, T.ArrayClass), T.None); 1216 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1217 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1218 TypeHandle type1 = *it1;
1219 TypeHandle type2 = *it2;
1220 TypeHandle intersect12 = T.Intersect(type1, type2);
1221 TypeHandle intersect21 = T.Intersect(type2, type1);
1222 CheckEqual(intersect12, intersect21);
1223 }
1224 }
1083 1225
1084 // Constant-constant 1226 // Associativity:
1085 CHECK(this->IsConstant(T.Intersect(T.ObjectConstant1, T.ObjectConstant1))); 1227 // Intersect(T1, Intersect(T2, T3)) = Intersect(Intersect(T1, T2), T3)
1086 CHECK(this->IsBitset(T.Intersect(T.ObjectConstant1, T.ObjectConstant2))); 1228 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1229 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1230 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1231 TypeHandle type1 = *it1;
1232 TypeHandle type2 = *it2;
1233 TypeHandle type3 = *it3;
1234 TypeHandle intersect12 = T.Intersect(type1, type2);
1235 TypeHandle intersect23 = T.Intersect(type2, type3);
1236 TypeHandle intersect1_23 = T.Intersect(type1, intersect23);
1237 TypeHandle intersect12_3 = T.Intersect(intersect12, type3);
1238 CheckEqual(intersect1_23, intersect12_3);
1239 }
1240 }
1241 }
1087 1242
1088 CheckEqual( 1243 // Join: Intersect(T1, T2)->Is(T1) and Intersect(T1, T2)->Is(T2)
1089 T.Intersect(T.ObjectConstant1, T.ObjectConstant1), T.ObjectConstant1); 1244 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1090 CheckEqual(T.Intersect(T.ObjectConstant1, T.ObjectConstant2), T.None); 1245 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1246 TypeHandle type1 = *it1;
1247 TypeHandle type2 = *it2;
1248 TypeHandle intersect12 = T.Intersect(type1, type2);
1249 CHECK(intersect12->Is(type1));
1250 CHECK(intersect12->Is(type2));
1251 }
1252 }
1253
1254 // Lower Boundedness: T1->Is(T2) implies Intersect(T1, T2) = T1
1255 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1256 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1257 TypeHandle type1 = *it1;
1258 TypeHandle type2 = *it2;
1259 TypeHandle intersect12 = T.Intersect(type1, type2);
1260 if (type1->Is(type2)) CheckEqual(intersect12, type1);
1261 }
1262 }
1263
1264 // Monotonicity: T1->Is(T2) implies Intersect(T1, T3)->Is(Intersect(T2, T3))
1265 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1266 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1267 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1268 TypeHandle type1 = *it1;
1269 TypeHandle type2 = *it2;
1270 TypeHandle type3 = *it3;
1271 TypeHandle intersect13 = T.Intersect(type1, type3);
1272 TypeHandle intersect23 = T.Intersect(type2, type3);
1273 CHECK(!type1->Is(type2) || intersect13->Is(intersect23));
1274 }
1275 }
1276 }
1277
1278 // Monotonicity: T1->Is(T3) or T2->Is(T3) implies Intersect(T1, T2)->Is(T3)
1279 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1280 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1281 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1282 TypeHandle type1 = *it1;
1283 TypeHandle type2 = *it2;
1284 TypeHandle type3 = *it3;
1285 TypeHandle intersect12 = T.Intersect(type1, type2);
1286 CHECK(!(type1->Is(type3) || type2->Is(type3)) ||
1287 intersect12->Is(type3));
1288 }
1289 }
1290 }
1291
1292 // Monotonicity: T1->Is(T2) and T1->Is(T3) implies T1->Is(Intersect(T2, T3))
1293 for (TypeIterator it1 = T.types.begin(); it1 != T.types.end(); ++it1) {
1294 for (TypeIterator it2 = T.types.begin(); it2 != T.types.end(); ++it2) {
1295 for (TypeIterator it3 = T.types.begin(); it3 != T.types.end(); ++it3) {
1296 TypeHandle type1 = *it1;
1297 TypeHandle type2 = *it2;
1298 TypeHandle type3 = *it3;
1299 TypeHandle intersect23 = T.Intersect(type2, type3);
1300 CHECK(!(type1->Is(type2) && type1->Is(type3)) ||
1301 type1->Is(intersect23));
1302 }
1303 }
1304 }
1091 1305
1092 // Bitset-class 1306 // Bitset-class
1093 CHECK(this->IsClass(T.Intersect(T.ObjectClass, T.Object)));
1094 CHECK(this->IsBitset(T.Intersect(T.ObjectClass, T.Number)));
1095
1096 CheckEqual(T.Intersect(T.ObjectClass, T.Object), T.ObjectClass); 1307 CheckEqual(T.Intersect(T.ObjectClass, T.Object), T.ObjectClass);
1097 CheckSub(T.Intersect(T.ObjectClass, T.Array), T.Representation); 1308 CheckSub(T.Intersect(T.ObjectClass, T.Array), T.Representation);
1098 CheckSub(T.Intersect(T.ObjectClass, T.Number), T.Representation); 1309 CheckSub(T.Intersect(T.ObjectClass, T.Number), T.Representation);
1099 1310
1100 // Bitset-constant
1101 CHECK(this->IsBitset(T.Intersect(T.SignedSmall, T.Number)));
1102 CHECK(this->IsConstant(T.Intersect(T.SmiConstant, T.Number)));
1103 CHECK(this->IsConstant(T.Intersect(T.ObjectConstant1, T.Object)));
1104
1105 CheckEqual(T.Intersect(T.SignedSmall, T.Number), T.SignedSmall);
1106 CheckEqual(T.Intersect(T.SmiConstant, T.Number), T.SmiConstant);
1107 CheckEqual(T.Intersect(T.ObjectConstant1, T.Object), T.ObjectConstant1);
1108
1109 // Class-constant 1311 // Class-constant
1110 CHECK(this->IsBitset(T.Intersect(T.ObjectConstant1, T.ObjectClass)));
1111 CHECK(this->IsBitset(T.Intersect(T.ArrayClass, T.ObjectConstant2)));
1112
1113 CheckEqual(T.Intersect(T.ObjectConstant1, T.ObjectClass), T.None); 1312 CheckEqual(T.Intersect(T.ObjectConstant1, T.ObjectClass), T.None);
1114 CheckEqual(T.Intersect(T.ArrayClass, T.ObjectConstant2), T.None); 1313 CheckEqual(T.Intersect(T.ArrayClass, T.ObjectConstant2), T.None);
1115 1314
1116 // Bitset-union 1315 // Bitset-union
1117 CHECK(this->IsUnion(
1118 T.Intersect(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass))));
1119 CHECK(this->IsBitset(
1120 T.Intersect(T.Union(T.ArrayClass, T.ObjectConstant2), T.Number)));
1121
1122 CheckEqual( 1316 CheckEqual(
1123 T.Intersect(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)), 1317 T.Intersect(T.Object, T.Union(T.ObjectConstant1, T.ObjectClass)),
1124 T.Union(T.ObjectConstant1, T.ObjectClass)); 1318 T.Union(T.ObjectConstant1, T.ObjectClass));
1125 CheckEqual( 1319 CheckEqual(
1126 T.Intersect(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number), 1320 T.Intersect(T.Union(T.ArrayClass, T.ObjectConstant1), T.Number),
1127 T.None); 1321 T.None);
1128 1322
1129 // Class-union 1323 // Class-union
1130 CHECK(this->IsClass(
1131 T.Intersect(T.Union(T.ArrayClass, T.ObjectConstant2), T.ArrayClass)));
1132 CHECK(this->IsClass(
1133 T.Intersect(T.Union(T.Object, T.SmiConstant), T.ArrayClass)));
1134 CHECK(this->IsBitset(
1135 T.Intersect(T.Union(T.ObjectClass, T.ArrayConstant), T.ArrayClass)));
1136
1137 CheckEqual( 1324 CheckEqual(
1138 T.Intersect(T.ArrayClass, T.Union(T.ObjectConstant2, T.ArrayClass)), 1325 T.Intersect(T.ArrayClass, T.Union(T.ObjectConstant2, T.ArrayClass)),
1139 T.ArrayClass); 1326 T.ArrayClass);
1140 CheckEqual( 1327 CheckEqual(
1141 T.Intersect(T.ArrayClass, T.Union(T.Object, T.SmiConstant)), 1328 T.Intersect(T.ArrayClass, T.Union(T.Object, T.SmiConstant)),
1142 T.ArrayClass); 1329 T.ArrayClass);
1143 CheckEqual( 1330 CheckEqual(
1144 T.Intersect(T.Union(T.ObjectClass, T.ArrayConstant), T.ArrayClass), 1331 T.Intersect(T.Union(T.ObjectClass, T.ArrayConstant), T.ArrayClass),
1145 T.None); 1332 T.None);
1146 1333
1147 // Constant-union 1334 // Constant-union
1148 CHECK(this->IsConstant(T.Intersect(
1149 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2))));
1150 CHECK(this->IsConstant(T.Intersect(
1151 T.Union(T.Number, T.ObjectClass), T.SmiConstant)));
1152 CHECK(this->IsBitset(T.Intersect(
1153 T.Union(T.ArrayConstant, T.ObjectClass), T.ObjectConstant1)));
1154
1155 CheckEqual( 1335 CheckEqual(
1156 T.Intersect( 1336 T.Intersect(
1157 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)), 1337 T.ObjectConstant1, T.Union(T.ObjectConstant1, T.ObjectConstant2)),
1158 T.ObjectConstant1); 1338 T.ObjectConstant1);
1159 CheckEqual( 1339 CheckEqual(
1160 T.Intersect(T.SmiConstant, T.Union(T.Number, T.ObjectConstant2)), 1340 T.Intersect(T.SmiConstant, T.Union(T.Number, T.ObjectConstant2)),
1161 T.SmiConstant); 1341 T.SmiConstant);
1162 CheckEqual( 1342 CheckEqual(
1163 T.Intersect( 1343 T.Intersect(
1164 T.Union(T.ArrayConstant, T.ObjectClass), T.ObjectConstant1), 1344 T.Union(T.ArrayConstant, T.ObjectClass), T.ObjectConstant1),
1165 T.None); 1345 T.None);
1166 1346
1167 // Union-union 1347 // Union-union
1168 CHECK(this->IsUnion(T.Intersect(
1169 T.Union(T.Number, T.ArrayClass), T.Union(T.Signed32, T.Array))));
1170 CHECK(this->IsBitset(T.Intersect(
1171 T.Union(T.Number, T.ObjectClass), T.Union(T.Signed32, T.Array))));
1172
1173 CheckEqual( 1348 CheckEqual(
1174 T.Intersect( 1349 T.Intersect(
1175 T.Union(T.Number, T.ArrayClass), 1350 T.Union(T.Number, T.ArrayClass),
1176 T.Union(T.SignedSmall, T.Array)), 1351 T.Union(T.SignedSmall, T.Array)),
1177 T.Union(T.SignedSmall, T.ArrayClass)); 1352 T.Union(T.SignedSmall, T.ArrayClass));
1178 CheckEqual( 1353 CheckEqual(
1179 T.Intersect( 1354 T.Intersect(
1180 T.Union(T.Number, T.ObjectClass), 1355 T.Union(T.Number, T.ObjectClass),
1181 T.Union(T.Signed32, T.Array)), 1356 T.Union(T.Signed32, T.Array)),
1182 T.Signed32); 1357 T.Signed32);
(...skipping 10 matching lines...) Expand all
1193 T.ObjectConstant1, 1368 T.ObjectConstant1,
1194 T.Union(T.ArrayConstant, T.ObjectConstant2))), 1369 T.Union(T.ArrayConstant, T.ObjectConstant2))),
1195 T.Union(T.ObjectConstant2, T.ObjectConstant1)); 1370 T.Union(T.ObjectConstant2, T.ObjectConstant1));
1196 } 1371 }
1197 1372
1198 template<class Type2, class TypeHandle2, class Region2, class Rep2> 1373 template<class Type2, class TypeHandle2, class Region2, class Rep2>
1199 void Convert() { 1374 void Convert() {
1200 Types<Type2, TypeHandle2, Region2> T2( 1375 Types<Type2, TypeHandle2, Region2> T2(
1201 Rep2::ToRegion(&zone, isolate), isolate); 1376 Rep2::ToRegion(&zone, isolate), isolate);
1202 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) { 1377 for (TypeIterator it = T.types.begin(); it != T.types.end(); ++it) {
1203 TypeHandle type = *it; 1378 TypeHandle type1 = *it;
1204 CheckEqual(type, 1379 TypeHandle2 type2 = T2.template Convert<Type>(type1);
1205 T.template Convert<Type2>(T2.template Convert<Type>(type))); 1380 TypeHandle type3 = T.template Convert<Type2>(type2);
1381 CheckEqual(type1, type3);
1206 } 1382 }
1207 } 1383 }
1208 }; 1384 };
1209 1385
1210 typedef Tests<Type, Type*, Zone, ZoneRep> ZoneTests; 1386 typedef Tests<Type, Type*, Zone, ZoneRep> ZoneTests;
1211 typedef Tests<HeapType, Handle<HeapType>, Isolate, HeapRep> HeapTests; 1387 typedef Tests<HeapType, Handle<HeapType>, Isolate, HeapRep> HeapTests;
1212 1388
1213 1389
1214 TEST(Bitset) { 1390 TEST(Bitset) {
1215 CcTest::InitializeVM(); 1391 CcTest::InitializeVM();
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
1293 ZoneTests().Intersect(); 1469 ZoneTests().Intersect();
1294 HeapTests().Intersect(); 1470 HeapTests().Intersect();
1295 } 1471 }
1296 1472
1297 1473
1298 TEST(Convert) { 1474 TEST(Convert) {
1299 CcTest::InitializeVM(); 1475 CcTest::InitializeVM();
1300 ZoneTests().Convert<HeapType, Handle<HeapType>, Isolate, HeapRep>(); 1476 ZoneTests().Convert<HeapType, Handle<HeapType>, Isolate, HeapRep>();
1301 HeapTests().Convert<Type, Type*, Zone, ZoneRep>(); 1477 HeapTests().Convert<Type, Type*, Zone, ZoneRep>();
1302 } 1478 }
OLDNEW
« no previous file with comments | « src/types.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698