| OLD | NEW |
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef V8_TYPES_H_ | 5 #ifndef V8_TYPES_H_ |
| 6 #define V8_TYPES_H_ | 6 #define V8_TYPES_H_ |
| 7 | 7 |
| 8 #include "src/factory.h" |
| 8 #include "src/handles.h" | 9 #include "src/handles.h" |
| 9 #include "src/ostreams.h" | 10 #include "src/ostreams.h" |
| 10 | 11 |
| 11 namespace v8 { | 12 namespace v8 { |
| 12 namespace internal { | 13 namespace internal { |
| 13 | 14 |
| 14 // SUMMARY | 15 // SUMMARY |
| 15 // | 16 // |
| 16 // A simple type system for compiler-internal use. It is based entirely on | 17 // A simple type system for compiler-internal use. It is based entirely on |
| 17 // union types, and all subtyping hence amounts to set inclusion. Besides the | 18 // union types, and all subtyping hence amounts to set inclusion. Besides the |
| (...skipping 229 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 247 class TypeImpl : public Config::Base { | 248 class TypeImpl : public Config::Base { |
| 248 public: | 249 public: |
| 249 // Auxiliary types. | 250 // Auxiliary types. |
| 250 | 251 |
| 251 class BitsetType; // Internal | 252 class BitsetType; // Internal |
| 252 class StructuralType; // Internal | 253 class StructuralType; // Internal |
| 253 class UnionType; // Internal | 254 class UnionType; // Internal |
| 254 | 255 |
| 255 class ClassType; | 256 class ClassType; |
| 256 class ConstantType; | 257 class ConstantType; |
| 258 class RangeType; |
| 257 class ContextType; | 259 class ContextType; |
| 258 class ArrayType; | 260 class ArrayType; |
| 259 class FunctionType; | 261 class FunctionType; |
| 260 | 262 |
| 261 typedef typename Config::template Handle<TypeImpl>::type TypeHandle; | 263 typedef typename Config::template Handle<TypeImpl>::type TypeHandle; |
| 262 typedef typename Config::template Handle<ClassType>::type ClassHandle; | 264 typedef typename Config::template Handle<ClassType>::type ClassHandle; |
| 263 typedef typename Config::template Handle<ConstantType>::type ConstantHandle; | 265 typedef typename Config::template Handle<ConstantType>::type ConstantHandle; |
| 266 typedef typename Config::template Handle<RangeType>::type RangeHandle; |
| 264 typedef typename Config::template Handle<ContextType>::type ContextHandle; | 267 typedef typename Config::template Handle<ContextType>::type ContextHandle; |
| 265 typedef typename Config::template Handle<ArrayType>::type ArrayHandle; | 268 typedef typename Config::template Handle<ArrayType>::type ArrayHandle; |
| 266 typedef typename Config::template Handle<FunctionType>::type FunctionHandle; | 269 typedef typename Config::template Handle<FunctionType>::type FunctionHandle; |
| 267 typedef typename Config::template Handle<UnionType>::type UnionHandle; | 270 typedef typename Config::template Handle<UnionType>::type UnionHandle; |
| 268 typedef typename Config::Region Region; | 271 typedef typename Config::Region Region; |
| 269 | 272 |
| 270 // Constructors. | 273 // Constructors. |
| 271 | 274 |
| 272 #define DEFINE_TYPE_CONSTRUCTOR(type, value) \ | 275 #define DEFINE_TYPE_CONSTRUCTOR(type, value) \ |
| 273 static TypeImpl* type() { return BitsetType::New(BitsetType::k##type); } \ | 276 static TypeImpl* type() { return BitsetType::New(BitsetType::k##type); } \ |
| 274 static TypeHandle type(Region* region) { \ | 277 static TypeHandle type(Region* region) { \ |
| 275 return BitsetType::New(BitsetType::k##type, region); \ | 278 return BitsetType::New(BitsetType::k##type, region); \ |
| 276 } | 279 } |
| 277 BITSET_TYPE_LIST(DEFINE_TYPE_CONSTRUCTOR) | 280 BITSET_TYPE_LIST(DEFINE_TYPE_CONSTRUCTOR) |
| 278 #undef DEFINE_TYPE_CONSTRUCTOR | 281 #undef DEFINE_TYPE_CONSTRUCTOR |
| 279 | 282 |
| 280 static TypeHandle Class(i::Handle<i::Map> map, Region* region) { | 283 static TypeHandle Class(i::Handle<i::Map> map, Region* region) { |
| 281 return ClassType::New(map, region); | 284 return ClassType::New(map, region); |
| 282 } | 285 } |
| 283 static TypeHandle Constant(i::Handle<i::Object> value, Region* region) { | 286 static TypeHandle Constant(i::Handle<i::Object> value, Region* region) { |
| 287 // TODO(neis): return RangeType for numerical values |
| 284 return ConstantType::New(value, region); | 288 return ConstantType::New(value, region); |
| 285 } | 289 } |
| 290 static TypeHandle Range(double min, double max, Region* region) { |
| 291 return RangeType::New(min, max, region); |
| 292 } |
| 286 static TypeHandle Context(TypeHandle outer, Region* region) { | 293 static TypeHandle Context(TypeHandle outer, Region* region) { |
| 287 return ContextType::New(outer, region); | 294 return ContextType::New(outer, region); |
| 288 } | 295 } |
| 289 static TypeHandle Array(TypeHandle element, Region* region) { | 296 static TypeHandle Array(TypeHandle element, Region* region) { |
| 290 return ArrayType::New(element, region); | 297 return ArrayType::New(element, region); |
| 291 } | 298 } |
| 292 static FunctionHandle Function( | 299 static FunctionHandle Function( |
| 293 TypeHandle result, TypeHandle receiver, int arity, Region* region) { | 300 TypeHandle result, TypeHandle receiver, int arity, Region* region) { |
| 294 return FunctionType::New(result, receiver, arity, region); | 301 return FunctionType::New(result, receiver, arity, region); |
| 295 } | 302 } |
| (...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 368 | 375 |
| 369 // Inspection. | 376 // Inspection. |
| 370 | 377 |
| 371 bool IsClass() { | 378 bool IsClass() { |
| 372 return Config::is_class(this) | 379 return Config::is_class(this) |
| 373 || Config::is_struct(this, StructuralType::kClassTag); | 380 || Config::is_struct(this, StructuralType::kClassTag); |
| 374 } | 381 } |
| 375 bool IsConstant() { | 382 bool IsConstant() { |
| 376 return Config::is_struct(this, StructuralType::kConstantTag); | 383 return Config::is_struct(this, StructuralType::kConstantTag); |
| 377 } | 384 } |
| 385 bool IsRange() { |
| 386 return Config::is_struct(this, StructuralType::kRangeTag); |
| 387 } |
| 378 bool IsContext() { | 388 bool IsContext() { |
| 379 return Config::is_struct(this, StructuralType::kContextTag); | 389 return Config::is_struct(this, StructuralType::kContextTag); |
| 380 } | 390 } |
| 381 bool IsArray() { | 391 bool IsArray() { |
| 382 return Config::is_struct(this, StructuralType::kArrayTag); | 392 return Config::is_struct(this, StructuralType::kArrayTag); |
| 383 } | 393 } |
| 384 bool IsFunction() { | 394 bool IsFunction() { |
| 385 return Config::is_struct(this, StructuralType::kFunctionTag); | 395 return Config::is_struct(this, StructuralType::kFunctionTag); |
| 386 } | 396 } |
| 387 | 397 |
| 388 ClassType* AsClass() { return ClassType::cast(this); } | 398 ClassType* AsClass() { return ClassType::cast(this); } |
| 389 ConstantType* AsConstant() { return ConstantType::cast(this); } | 399 ConstantType* AsConstant() { return ConstantType::cast(this); } |
| 400 RangeType* AsRange() { return RangeType::cast(this); } |
| 390 ContextType* AsContext() { return ContextType::cast(this); } | 401 ContextType* AsContext() { return ContextType::cast(this); } |
| 391 ArrayType* AsArray() { return ArrayType::cast(this); } | 402 ArrayType* AsArray() { return ArrayType::cast(this); } |
| 392 FunctionType* AsFunction() { return FunctionType::cast(this); } | 403 FunctionType* AsFunction() { return FunctionType::cast(this); } |
| 393 | 404 |
| 394 int NumClasses(); | 405 int NumClasses(); |
| 395 int NumConstants(); | 406 int NumConstants(); |
| 396 | 407 |
| 397 template<class T> class Iterator; | 408 template<class T> class Iterator; |
| 398 Iterator<i::Map> Classes() { | 409 Iterator<i::Map> Classes() { |
| 399 if (this->IsBitset()) return Iterator<i::Map>(); | 410 if (this->IsBitset()) return Iterator<i::Map>(); |
| (...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 513 template<class Config> | 524 template<class Config> |
| 514 class TypeImpl<Config>::StructuralType : public TypeImpl<Config> { | 525 class TypeImpl<Config>::StructuralType : public TypeImpl<Config> { |
| 515 protected: | 526 protected: |
| 516 template<class> friend class TypeImpl; | 527 template<class> friend class TypeImpl; |
| 517 friend struct ZoneTypeConfig; // For tags. | 528 friend struct ZoneTypeConfig; // For tags. |
| 518 friend struct HeapTypeConfig; | 529 friend struct HeapTypeConfig; |
| 519 | 530 |
| 520 enum Tag { | 531 enum Tag { |
| 521 kClassTag, | 532 kClassTag, |
| 522 kConstantTag, | 533 kConstantTag, |
| 534 kRangeTag, |
| 523 kContextTag, | 535 kContextTag, |
| 524 kArrayTag, | 536 kArrayTag, |
| 525 kFunctionTag, | 537 kFunctionTag, |
| 526 kUnionTag | 538 kUnionTag |
| 527 }; | 539 }; |
| 528 | 540 |
| 529 int Length() { | 541 int Length() { |
| 530 return Config::struct_length(Config::as_struct(this)); | 542 return Config::struct_length(Config::as_struct(this)); |
| 531 } | 543 } |
| 532 TypeHandle Get(int i) { | 544 TypeHandle Get(int i) { |
| (...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 649 } | 661 } |
| 650 | 662 |
| 651 static ConstantType* cast(TypeImpl* type) { | 663 static ConstantType* cast(TypeImpl* type) { |
| 652 ASSERT(type->IsConstant()); | 664 ASSERT(type->IsConstant()); |
| 653 return static_cast<ConstantType*>(type); | 665 return static_cast<ConstantType*>(type); |
| 654 } | 666 } |
| 655 }; | 667 }; |
| 656 | 668 |
| 657 | 669 |
| 658 // ----------------------------------------------------------------------------- | 670 // ----------------------------------------------------------------------------- |
| 671 // Range types. |
| 672 |
| 673 template<class Config> |
| 674 class TypeImpl<Config>::RangeType : public StructuralType { |
| 675 public: |
| 676 TypeHandle Bound() { return this->Get(0); } |
| 677 double Min() { return this->template GetValue<i::HeapNumber>(1)->value(); } |
| 678 double Max() { return this->template GetValue<i::HeapNumber>(2)->value(); } |
| 679 |
| 680 static RangeHandle New( |
| 681 double min, double max, TypeHandle bound, Region* region) { |
| 682 ASSERT(SEMANTIC(bound->AsBitset() | BitsetType::kNumber) |
| 683 == SEMANTIC(BitsetType::kNumber)); |
| 684 ASSERT(!std::isnan(min) && !std::isnan(max) && min <= max); |
| 685 RangeHandle type = Config::template cast<RangeType>( |
| 686 StructuralType::New(StructuralType::kRangeTag, 3, region)); |
| 687 type->Set(0, bound); |
| 688 Factory* factory = Config::isolate(region)->factory(); |
| 689 type->SetValue(1, factory->NewHeapNumber(min)); |
| 690 type->SetValue(2, factory->NewHeapNumber(max)); |
| 691 return type; |
| 692 } |
| 693 |
| 694 static RangeHandle New(double min, double max, Region* region) { |
| 695 TypeHandle bound = BitsetType::New(BitsetType::kNumber, region); |
| 696 return New(min, max, bound, region); |
| 697 } |
| 698 |
| 699 static RangeType* cast(TypeImpl* type) { |
| 700 ASSERT(type->IsRange()); |
| 701 return static_cast<RangeType*>(type); |
| 702 } |
| 703 }; |
| 704 |
| 705 |
| 706 // ----------------------------------------------------------------------------- |
| 659 // Context types. | 707 // Context types. |
| 660 | 708 |
| 661 template<class Config> | 709 template<class Config> |
| 662 class TypeImpl<Config>::ContextType : public StructuralType { | 710 class TypeImpl<Config>::ContextType : public StructuralType { |
| 663 public: | 711 public: |
| 664 TypeHandle Bound() { return this->Get(0); } | 712 TypeHandle Bound() { return this->Get(0); } |
| 665 TypeHandle Outer() { return this->Get(1); } | 713 TypeHandle Outer() { return this->Get(1); } |
| 666 | 714 |
| 667 static ContextHandle New(TypeHandle outer, TypeHandle bound, Region* region) { | 715 static ContextHandle New(TypeHandle outer, TypeHandle bound, Region* region) { |
| 668 ContextHandle type = Config::template cast<ContextType>( | 716 ContextHandle type = Config::template cast<ContextType>( |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 784 // Zone-allocated types; they are either (odd) integers to represent bitsets, or | 832 // Zone-allocated types; they are either (odd) integers to represent bitsets, or |
| 785 // (even) pointers to structures for everything else. | 833 // (even) pointers to structures for everything else. |
| 786 | 834 |
| 787 struct ZoneTypeConfig { | 835 struct ZoneTypeConfig { |
| 788 typedef TypeImpl<ZoneTypeConfig> Type; | 836 typedef TypeImpl<ZoneTypeConfig> Type; |
| 789 class Base {}; | 837 class Base {}; |
| 790 typedef void* Struct; | 838 typedef void* Struct; |
| 791 typedef i::Zone Region; | 839 typedef i::Zone Region; |
| 792 template<class T> struct Handle { typedef T* type; }; | 840 template<class T> struct Handle { typedef T* type; }; |
| 793 | 841 |
| 842 // TODO(neis): This will be removed again once we have struct_get_double(). |
| 843 static inline i::Isolate* isolate(Region* region) { |
| 844 return region->isolate(); |
| 845 } |
| 846 |
| 794 template<class T> static inline T* handle(T* type); | 847 template<class T> static inline T* handle(T* type); |
| 795 template<class T> static inline T* cast(Type* type); | 848 template<class T> static inline T* cast(Type* type); |
| 796 | 849 |
| 797 static inline bool is_bitset(Type* type); | 850 static inline bool is_bitset(Type* type); |
| 798 static inline bool is_class(Type* type); | 851 static inline bool is_class(Type* type); |
| 799 static inline bool is_struct(Type* type, int tag); | 852 static inline bool is_struct(Type* type, int tag); |
| 800 | 853 |
| 801 static inline int as_bitset(Type* type); | 854 static inline int as_bitset(Type* type); |
| 802 static inline i::Handle<i::Map> as_class(Type* type); | 855 static inline i::Handle<i::Map> as_class(Type* type); |
| 803 static inline Struct* as_struct(Type* type); | 856 static inline Struct* as_struct(Type* type); |
| (...skipping 22 matching lines...) Expand all Loading... |
| 826 // Heap-allocated types; either smis for bitsets, maps for classes, boxes for | 879 // Heap-allocated types; either smis for bitsets, maps for classes, boxes for |
| 827 // constants, or fixed arrays for unions. | 880 // constants, or fixed arrays for unions. |
| 828 | 881 |
| 829 struct HeapTypeConfig { | 882 struct HeapTypeConfig { |
| 830 typedef TypeImpl<HeapTypeConfig> Type; | 883 typedef TypeImpl<HeapTypeConfig> Type; |
| 831 typedef i::Object Base; | 884 typedef i::Object Base; |
| 832 typedef i::FixedArray Struct; | 885 typedef i::FixedArray Struct; |
| 833 typedef i::Isolate Region; | 886 typedef i::Isolate Region; |
| 834 template<class T> struct Handle { typedef i::Handle<T> type; }; | 887 template<class T> struct Handle { typedef i::Handle<T> type; }; |
| 835 | 888 |
| 889 // TODO(neis): This will be removed again once we have struct_get_double(). |
| 890 static inline i::Isolate* isolate(Region* region) { |
| 891 return region; |
| 892 } |
| 893 |
| 836 template<class T> static inline i::Handle<T> handle(T* type); | 894 template<class T> static inline i::Handle<T> handle(T* type); |
| 837 template<class T> static inline i::Handle<T> cast(i::Handle<Type> type); | 895 template<class T> static inline i::Handle<T> cast(i::Handle<Type> type); |
| 838 | 896 |
| 839 static inline bool is_bitset(Type* type); | 897 static inline bool is_bitset(Type* type); |
| 840 static inline bool is_class(Type* type); | 898 static inline bool is_class(Type* type); |
| 841 static inline bool is_struct(Type* type, int tag); | 899 static inline bool is_struct(Type* type, int tag); |
| 842 | 900 |
| 843 static inline int as_bitset(Type* type); | 901 static inline int as_bitset(Type* type); |
| 844 static inline i::Handle<i::Map> as_class(Type* type); | 902 static inline i::Handle<i::Map> as_class(Type* type); |
| 845 static inline i::Handle<Struct> as_struct(Type* type); | 903 static inline i::Handle<Struct> as_struct(Type* type); |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 923 bool Narrows(BoundsImpl that) { | 981 bool Narrows(BoundsImpl that) { |
| 924 return that.lower->Is(this->lower) && this->upper->Is(that.upper); | 982 return that.lower->Is(this->lower) && this->upper->Is(that.upper); |
| 925 } | 983 } |
| 926 }; | 984 }; |
| 927 | 985 |
| 928 typedef BoundsImpl<ZoneTypeConfig> Bounds; | 986 typedef BoundsImpl<ZoneTypeConfig> Bounds; |
| 929 | 987 |
| 930 } } // namespace v8::internal | 988 } } // namespace v8::internal |
| 931 | 989 |
| 932 #endif // V8_TYPES_H_ | 990 #endif // V8_TYPES_H_ |
| OLD | NEW |