| 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/conversions.h" | 8 #include "src/conversions.h" |
| 9 #include "src/factory.h" | 9 #include "src/factory.h" |
| 10 #include "src/handles.h" | 10 #include "src/handles.h" |
| (...skipping 412 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 423 static TypeHandle Of(double value, Region* region) { | 423 static TypeHandle Of(double value, Region* region) { |
| 424 return Config::from_bitset(BitsetType::Lub(value), region); | 424 return Config::from_bitset(BitsetType::Lub(value), region); |
| 425 } | 425 } |
| 426 static TypeHandle Of(i::Object* value, Region* region) { | 426 static TypeHandle Of(i::Object* value, Region* region) { |
| 427 return Config::from_bitset(BitsetType::Lub(value), region); | 427 return Config::from_bitset(BitsetType::Lub(value), region); |
| 428 } | 428 } |
| 429 static TypeHandle Of(i::Handle<i::Object> value, Region* region) { | 429 static TypeHandle Of(i::Handle<i::Object> value, Region* region) { |
| 430 return Of(*value, region); | 430 return Of(*value, region); |
| 431 } | 431 } |
| 432 | 432 |
| 433 // Extraction of components. |
| 434 static TypeHandle Representation(TypeHandle t, Region* region); |
| 435 static TypeHandle Semantic(TypeHandle t, Region* region); |
| 436 |
| 433 // Predicates. | 437 // Predicates. |
| 434 | |
| 435 bool IsInhabited() { return BitsetType::IsInhabited(this->BitsetLub()); } | 438 bool IsInhabited() { return BitsetType::IsInhabited(this->BitsetLub()); } |
| 436 | 439 |
| 437 bool Is(TypeImpl* that) { return this == that || this->SlowIs(that); } | 440 bool Is(TypeImpl* that) { return this == that || this->SlowIs(that); } |
| 438 template<class TypeHandle> | 441 template<class TypeHandle> |
| 439 bool Is(TypeHandle that) { return this->Is(*that); } | 442 bool Is(TypeHandle that) { return this->Is(*that); } |
| 440 | 443 |
| 441 bool Maybe(TypeImpl* that); | 444 bool Maybe(TypeImpl* that); |
| 442 template<class TypeHandle> | 445 template<class TypeHandle> |
| 443 bool Maybe(TypeHandle that) { return this->Maybe(*that); } | 446 bool Maybe(TypeHandle that) { return this->Maybe(*that); } |
| 444 | 447 |
| (...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 556 bool IsAny() { return this == Any(); } | 559 bool IsAny() { return this == Any(); } |
| 557 bool IsBitset() { return Config::is_bitset(this); } | 560 bool IsBitset() { return Config::is_bitset(this); } |
| 558 bool IsUnion() { return Config::is_struct(this, StructuralType::kUnionTag); } | 561 bool IsUnion() { return Config::is_struct(this, StructuralType::kUnionTag); } |
| 559 | 562 |
| 560 bitset AsBitset() { | 563 bitset AsBitset() { |
| 561 DCHECK(this->IsBitset()); | 564 DCHECK(this->IsBitset()); |
| 562 return static_cast<BitsetType*>(this)->Bitset(); | 565 return static_cast<BitsetType*>(this)->Bitset(); |
| 563 } | 566 } |
| 564 UnionType* AsUnion() { return UnionType::cast(this); } | 567 UnionType* AsUnion() { return UnionType::cast(this); } |
| 565 | 568 |
| 569 bitset Representation(); |
| 570 |
| 566 // Auxiliary functions. | 571 // Auxiliary functions. |
| 572 bool SemanticMaybe(TypeImpl* that); |
| 567 | 573 |
| 568 bitset BitsetGlb() { return BitsetType::Glb(this); } | 574 bitset BitsetGlb() { return BitsetType::Glb(this); } |
| 569 bitset BitsetLub() { return BitsetType::Lub(this); } | 575 bitset BitsetLub() { return BitsetType::Lub(this); } |
| 570 | 576 |
| 571 bool SlowIs(TypeImpl* that); | 577 bool SlowIs(TypeImpl* that); |
| 578 bool SemanticIs(TypeImpl* that); |
| 572 | 579 |
| 573 static bool IsInteger(double x) { | 580 static bool IsInteger(double x) { |
| 574 return nearbyint(x) == x && !i::IsMinusZero(x); // Allows for infinities. | 581 return nearbyint(x) == x && !i::IsMinusZero(x); // Allows for infinities. |
| 575 } | 582 } |
| 576 static bool IsInteger(i::Object* x) { | 583 static bool IsInteger(i::Object* x) { |
| 577 return x->IsNumber() && IsInteger(x->Number()); | 584 return x->IsNumber() && IsInteger(x->Number()); |
| 578 } | 585 } |
| 579 | 586 |
| 580 struct Limits { | 587 struct Limits { |
| 581 double min; | 588 double min; |
| 582 double max; | 589 double max; |
| 583 bitset representation; | 590 Limits(double min, double max) : min(min), max(max) {} |
| 584 Limits(double min, double max, bitset representation) | 591 explicit Limits(RangeType* range) : min(range->Min()), max(range->Max()) {} |
| 585 : min(min), max(max), representation(representation) {} | 592 static Limits Empty(Region* region) { return Limits(1, 0); } |
| 586 explicit Limits(RangeType* range) | |
| 587 : min(range->Min()), | |
| 588 max(range->Max()), | |
| 589 representation(REPRESENTATION(range->Bound())) {} | |
| 590 static Limits Empty(Region* region) { | |
| 591 return Limits(1, 0, BitsetType::kNone); | |
| 592 } | |
| 593 }; | 593 }; |
| 594 | 594 |
| 595 static bool IsEmpty(Limits lim); | 595 static bool IsEmpty(Limits lim); |
| 596 static Limits Intersect(Limits lhs, Limits rhs); | 596 static Limits Intersect(Limits lhs, Limits rhs); |
| 597 static Limits Union(Limits lhs, Limits rhs); | 597 static Limits Union(Limits lhs, Limits rhs); |
| 598 static bool Overlap(RangeType* lhs, RangeType* rhs); | 598 static bool Overlap(RangeType* lhs, RangeType* rhs); |
| 599 static bool Contains(RangeType* lhs, RangeType* rhs); | 599 static bool Contains(RangeType* lhs, RangeType* rhs); |
| 600 static bool Contains(RangeType* range, ConstantType* constant); | 600 static bool Contains(RangeType* range, ConstantType* constant); |
| 601 static bool Contains(RangeType* range, i::Object* val); | 601 static bool Contains(RangeType* range, i::Object* val); |
| 602 | 602 |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 642 bitset Bitset() { return Config::as_bitset(this); } | 642 bitset Bitset() { return Config::as_bitset(this); } |
| 643 | 643 |
| 644 static TypeImpl* New(bitset bits) { | 644 static TypeImpl* New(bitset bits) { |
| 645 if (FLAG_enable_slow_asserts) CheckNumberBits(bits); | 645 if (FLAG_enable_slow_asserts) CheckNumberBits(bits); |
| 646 return Config::from_bitset(bits); | 646 return Config::from_bitset(bits); |
| 647 } | 647 } |
| 648 static TypeHandle New(bitset bits, Region* region) { | 648 static TypeHandle New(bitset bits, Region* region) { |
| 649 if (FLAG_enable_slow_asserts) CheckNumberBits(bits); | 649 if (FLAG_enable_slow_asserts) CheckNumberBits(bits); |
| 650 return Config::from_bitset(bits, region); | 650 return Config::from_bitset(bits, region); |
| 651 } | 651 } |
| 652 // TODO(neis): Eventually allow again for types with empty semantics | |
| 653 // part and modify intersection and possibly subtyping accordingly. | |
| 654 | 652 |
| 655 static bool IsInhabited(bitset bits) { | 653 static bool IsInhabited(bitset bits) { |
| 656 return bits & kSemantic; | 654 return SEMANTIC(bits) != kNone && REPRESENTATION(bits) != kNone; |
| 655 } |
| 656 |
| 657 static bool SemanticIsInhabited(bitset bits) { |
| 658 return SEMANTIC(bits) != kNone; |
| 657 } | 659 } |
| 658 | 660 |
| 659 static bool Is(bitset bits1, bitset bits2) { | 661 static bool Is(bitset bits1, bitset bits2) { |
| 660 return (bits1 | bits2) == bits2; | 662 return (bits1 | bits2) == bits2; |
| 661 } | 663 } |
| 662 | 664 |
| 663 static double Min(bitset); | 665 static double Min(bitset); |
| 664 static double Max(bitset); | 666 static double Max(bitset); |
| 665 | 667 |
| 666 static bitset Glb(TypeImpl* type); // greatest lower bound that's a bitset | 668 static bitset Glb(TypeImpl* type); // greatest lower bound that's a bitset |
| (...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 848 typename Config::template Handle<typename Config::Range>::type range = | 850 typename Config::template Handle<typename Config::Range>::type range = |
| 849 Config::range_create(region); | 851 Config::range_create(region); |
| 850 | 852 |
| 851 bitset bits = SEMANTIC(BitsetType::Lub(min, max)) | representation_bits; | 853 bitset bits = SEMANTIC(BitsetType::Lub(min, max)) | representation_bits; |
| 852 Config::range_set_bitset(range, bits); | 854 Config::range_set_bitset(range, bits); |
| 853 Config::range_set_double(range, 0, min, region); | 855 Config::range_set_double(range, 0, min, region); |
| 854 Config::range_set_double(range, 1, max, region); | 856 Config::range_set_double(range, 1, max, region); |
| 855 return Config::template cast<RangeType>(Config::from_range(range)); | 857 return Config::template cast<RangeType>(Config::from_range(range)); |
| 856 } | 858 } |
| 857 | 859 |
| 858 static RangeHandle New(Limits lim, Region* region) { | 860 static RangeHandle New(Limits lim, bitset representation, Region* region) { |
| 859 return New(lim.min, lim.max, BitsetType::New(lim.representation, region), | 861 return New(lim.min, lim.max, BitsetType::New(representation, region), |
| 860 region); | 862 region); |
| 861 } | 863 } |
| 862 | 864 |
| 863 static RangeType* cast(TypeImpl* type) { | 865 static RangeType* cast(TypeImpl* type) { |
| 864 DCHECK(type->IsRange()); | 866 DCHECK(type->IsRange()); |
| 865 return static_cast<RangeType*>(type); | 867 return static_cast<RangeType*>(type); |
| 866 } | 868 } |
| 867 }; | 869 }; |
| 868 // TODO(neis): Also cache min and max values. | 870 // TODO(neis): Also cache min and max values. |
| 869 // TODO(neis): Allow restricting the representation. | |
| 870 | 871 |
| 871 | 872 |
| 872 // ----------------------------------------------------------------------------- | 873 // ----------------------------------------------------------------------------- |
| 873 // Context types. | 874 // Context types. |
| 874 | 875 |
| 875 template<class Config> | 876 template<class Config> |
| 876 class TypeImpl<Config>::ContextType : public StructuralType { | 877 class TypeImpl<Config>::ContextType : public StructuralType { |
| 877 public: | 878 public: |
| 878 TypeHandle Outer() { return this->Get(0); } | 879 TypeHandle Outer() { return this->Get(0); } |
| 879 | 880 |
| (...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1149 bool Narrows(BoundsImpl that) { | 1150 bool Narrows(BoundsImpl that) { |
| 1150 return that.lower->Is(this->lower) && this->upper->Is(that.upper); | 1151 return that.lower->Is(this->lower) && this->upper->Is(that.upper); |
| 1151 } | 1152 } |
| 1152 }; | 1153 }; |
| 1153 | 1154 |
| 1154 typedef BoundsImpl<ZoneTypeConfig> Bounds; | 1155 typedef BoundsImpl<ZoneTypeConfig> Bounds; |
| 1155 | 1156 |
| 1156 } } // namespace v8::internal | 1157 } } // namespace v8::internal |
| 1157 | 1158 |
| 1158 #endif // V8_TYPES_H_ | 1159 #endif // V8_TYPES_H_ |
| OLD | NEW |