LCOV - code coverage report
Current view: top level - src/compiler - types.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 329 385 85.5 %
Date: 2017-04-26 Functions: 36 45 80.0 %

          Line data    Source code
       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
       3             : // found in the LICENSE file.
       4             : 
       5             : #include <iomanip>
       6             : 
       7             : #include "src/compiler/types.h"
       8             : 
       9             : #include "src/handles-inl.h"
      10             : #include "src/objects-inl.h"
      11             : #include "src/ostreams.h"
      12             : 
      13             : namespace v8 {
      14             : namespace internal {
      15             : namespace compiler {
      16             : 
      17             : // NOTE: If code is marked as being a "shortcut", this means that removing
      18             : // the code won't affect the semantics of the surrounding function definition.
      19             : 
      20             : // static
      21    13727395 : bool Type::IsInteger(i::Object* x) {
      22    18840942 :   return x->IsNumber() && Type::IsInteger(x->Number());
      23             : }
      24             : 
      25             : // -----------------------------------------------------------------------------
      26             : // Range-related helper functions.
      27             : 
      28     3382089 : bool RangeType::Limits::IsEmpty() { return this->min > this->max; }
      29             : 
      30           0 : RangeType::Limits RangeType::Limits::Intersect(Limits lhs, Limits rhs) {
      31             :   DisallowHeapAllocation no_allocation;
      32             :   Limits result(lhs);
      33     3175621 :   if (lhs.min < rhs.min) result.min = rhs.min;
      34     3175621 :   if (lhs.max > rhs.max) result.max = rhs.max;
      35           0 :   return result;
      36             : }
      37             : 
      38           0 : RangeType::Limits RangeType::Limits::Union(Limits lhs, Limits rhs) {
      39             :   DisallowHeapAllocation no_allocation;
      40     3357419 :   if (lhs.IsEmpty()) return rhs;
      41     3357419 :   if (rhs.IsEmpty()) return lhs;
      42             :   Limits result(lhs);
      43     3157769 :   if (lhs.min > rhs.min) result.min = rhs.min;
      44     3157769 :   if (lhs.max < rhs.max) result.max = rhs.max;
      45           0 :   return result;
      46             : }
      47             : 
      48           0 : bool Type::Overlap(RangeType* lhs, RangeType* rhs) {
      49             :   DisallowHeapAllocation no_allocation;
      50             :   return !RangeType::Limits::Intersect(RangeType::Limits(lhs),
      51             :                                        RangeType::Limits(rhs))
      52     2975952 :               .IsEmpty();
      53             : }
      54             : 
      55    28172249 : bool Type::Contains(RangeType* lhs, RangeType* rhs) {
      56             :   DisallowHeapAllocation no_allocation;
      57    28172249 :   return lhs->Min() <= rhs->Min() && rhs->Max() <= lhs->Max();
      58             : }
      59             : 
      60           0 : bool Type::Contains(RangeType* range, i::Object* val) {
      61             :   DisallowHeapAllocation no_allocation;
      62           0 :   return IsInteger(val) && range->Min() <= val->Number() &&
      63           0 :          val->Number() <= range->Max();
      64             : }
      65             : 
      66             : // -----------------------------------------------------------------------------
      67             : // Min and Max computation.
      68             : 
      69    10973641 : double Type::Min() {
      70             :   DCHECK(this->Is(Number()));
      71    11636516 :   if (this->IsBitset()) return BitsetType::Min(this->AsBitset());
      72    10310766 :   if (this->IsUnion()) {
      73       19680 :     double min = +V8_INFINITY;
      74       66320 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
      75      139920 :       min = std::min(min, this->AsUnion()->Get(i)->Min());
      76             :     }
      77       19680 :     return min;
      78             :   }
      79    10291086 :   if (this->IsRange()) return this->AsRange()->Min();
      80       11261 :   if (this->IsOtherNumberConstant())
      81       11261 :     return this->AsOtherNumberConstant()->Value();
      82           0 :   UNREACHABLE();
      83             :   return 0;
      84             : }
      85             : 
      86    11097614 : double Type::Max() {
      87             :   DCHECK(this->Is(Number()));
      88    11933560 :   if (this->IsBitset()) return BitsetType::Max(this->AsBitset());
      89    10261668 :   if (this->IsUnion()) {
      90       17107 :     double max = -V8_INFINITY;
      91       58601 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
      92      124482 :       max = std::max(max, this->AsUnion()->Get(i)->Max());
      93             :     }
      94       17107 :     return max;
      95             :   }
      96    10244561 :   if (this->IsRange()) return this->AsRange()->Max();
      97       10754 :   if (this->IsOtherNumberConstant())
      98       10754 :     return this->AsOtherNumberConstant()->Value();
      99           0 :   UNREACHABLE();
     100             :   return 0;
     101             : }
     102             : 
     103             : // -----------------------------------------------------------------------------
     104             : // Glb and lub computation.
     105             : 
     106             : // The largest bitset subsumed by this type.
     107    92968834 : Type::bitset BitsetType::Glb(Type* type) {
     108             :   DisallowHeapAllocation no_allocation;
     109             :   // Fast case.
     110    92968834 :   if (IsBitset(type)) {
     111    27589525 :     return type->AsBitset();
     112    65379309 :   } else if (type->IsUnion()) {
     113             :     SLOW_DCHECK(type->AsUnion()->Wellformed());
     114    40718664 :     return type->AsUnion()->Get(0)->BitsetGlb() |
     115    40718748 :            type->AsUnion()->Get(1)->BitsetGlb();  // Shortcut.
     116    45019977 :   } else if (type->IsRange()) {
     117             :     bitset glb =
     118    29385393 :         BitsetType::Glb(type->AsRange()->Min(), type->AsRange()->Max());
     119    29386073 :     return glb;
     120             :   } else {
     121             :     return kNone;
     122             :   }
     123             : }
     124             : 
     125             : // The smallest bitset subsuming this type, possibly not a proper one.
     126   275784545 : Type::bitset BitsetType::Lub(Type* type) {
     127             :   DisallowHeapAllocation no_allocation;
     128   446056131 :   if (IsBitset(type)) return type->AsBitset();
     129   105512959 :   if (type->IsUnion()) {
     130             :     // Take the representation from the first element, which is always
     131             :     // a bitset.
     132    15538036 :     int bitset = type->AsUnion()->Get(0)->BitsetLub();
     133    28362971 :     for (int i = 0, n = type->AsUnion()->Length(); i < n; ++i) {
     134             :       // Other elements only contribute their semantic part.
     135    41189286 :       bitset |= type->AsUnion()->Get(i)->BitsetLub();
     136             :     }
     137     7768328 :     return bitset;
     138             :   }
     139    97743941 :   if (type->IsHeapConstant()) return type->AsHeapConstant()->Lub();
     140    71284381 :   if (type->IsOtherNumberConstant())
     141             :     return type->AsOtherNumberConstant()->Lub();
     142    60325730 :   if (type->IsRange()) return type->AsRange()->Lub();
     143        3933 :   if (type->IsTuple()) return kOtherInternal;
     144           0 :   UNREACHABLE();
     145             :   return kNone;
     146             : }
     147             : 
     148     9448420 : Type::bitset BitsetType::Lub(i::Map* map) {
     149             :   DisallowHeapAllocation no_allocation;
     150     9448420 :   switch (map->instance_type()) {
     151             :     case STRING_TYPE:
     152             :     case ONE_BYTE_STRING_TYPE:
     153             :     case CONS_STRING_TYPE:
     154             :     case CONS_ONE_BYTE_STRING_TYPE:
     155             :     case THIN_STRING_TYPE:
     156             :     case THIN_ONE_BYTE_STRING_TYPE:
     157             :     case SLICED_STRING_TYPE:
     158             :     case SLICED_ONE_BYTE_STRING_TYPE:
     159             :     case EXTERNAL_STRING_TYPE:
     160             :     case EXTERNAL_ONE_BYTE_STRING_TYPE:
     161             :     case EXTERNAL_STRING_WITH_ONE_BYTE_DATA_TYPE:
     162             :     case SHORT_EXTERNAL_STRING_TYPE:
     163             :     case SHORT_EXTERNAL_ONE_BYTE_STRING_TYPE:
     164             :     case SHORT_EXTERNAL_STRING_WITH_ONE_BYTE_DATA_TYPE:
     165             :       return kOtherString;
     166             :     case INTERNALIZED_STRING_TYPE:
     167             :     case ONE_BYTE_INTERNALIZED_STRING_TYPE:
     168             :     case EXTERNAL_INTERNALIZED_STRING_TYPE:
     169             :     case EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
     170             :     case EXTERNAL_INTERNALIZED_STRING_WITH_ONE_BYTE_DATA_TYPE:
     171             :     case SHORT_EXTERNAL_INTERNALIZED_STRING_TYPE:
     172             :     case SHORT_EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
     173             :     case SHORT_EXTERNAL_INTERNALIZED_STRING_WITH_ONE_BYTE_DATA_TYPE:
     174     1313541 :       return kInternalizedString;
     175             :     case SYMBOL_TYPE:
     176        1721 :       return kSymbol;
     177             :     case ODDBALL_TYPE: {
     178    15022462 :       Heap* heap = map->GetHeap();
     179     5062084 :       if (map == heap->undefined_map()) return kUndefined;
     180     4225794 :       if (map == heap->null_map()) return kNull;
     181     4187163 :       if (map == heap->boolean_map()) return kBoolean;
     182     1547421 :       if (map == heap->the_hole_map()) return kHole;
     183             :       DCHECK(map == heap->uninitialized_map() ||
     184             :              map == heap->termination_exception_map() ||
     185             :              map == heap->arguments_marker_map() ||
     186             :              map == heap->optimized_out_map() ||
     187             :              map == heap->stale_register_map());
     188      559030 :       return kOtherInternal;
     189             :     }
     190             :     case HEAP_NUMBER_TYPE:
     191           0 :       return kNumber;
     192             :     case JS_OBJECT_TYPE:
     193             :     case JS_ARGUMENTS_TYPE:
     194             :     case JS_ERROR_TYPE:
     195             :     case JS_GLOBAL_OBJECT_TYPE:
     196             :     case JS_GLOBAL_PROXY_TYPE:
     197             :     case JS_API_OBJECT_TYPE:
     198             :     case JS_SPECIAL_API_OBJECT_TYPE:
     199     1253088 :       if (map->is_undetectable()) {
     200             :         // Currently we assume that every undetectable receiver is also
     201             :         // callable, which is what we need to support document.all.  We
     202             :         // could add another Type bit to support other use cases in the
     203             :         // future if necessary.
     204             :         DCHECK(map->is_callable());
     205             :         return kOtherUndetectable;
     206             :       }
     207     1252986 :       if (map->is_callable()) {
     208             :         return kOtherCallable;
     209             :       }
     210     1252976 :       return kOtherObject;
     211             :     case JS_ARRAY_TYPE:
     212      581889 :       return kArray;
     213             :     case JS_VALUE_TYPE:
     214             :     case JS_MESSAGE_OBJECT_TYPE:
     215             :     case JS_DATE_TYPE:
     216             :     case JS_CONTEXT_EXTENSION_OBJECT_TYPE:
     217             :     case JS_GENERATOR_OBJECT_TYPE:
     218             :     case JS_ASYNC_GENERATOR_OBJECT_TYPE:
     219             :     case JS_MODULE_NAMESPACE_TYPE:
     220             :     case JS_ARRAY_BUFFER_TYPE:
     221             :     case JS_REGEXP_TYPE:  // TODO(rossberg): there should be a RegExp type.
     222             :     case JS_TYPED_ARRAY_TYPE:
     223             :     case JS_DATA_VIEW_TYPE:
     224             :     case JS_SET_TYPE:
     225             :     case JS_MAP_TYPE:
     226             :     case JS_SET_ITERATOR_TYPE:
     227             :     case JS_MAP_ITERATOR_TYPE:
     228             :     case JS_STRING_ITERATOR_TYPE:
     229             :     case JS_ASYNC_FROM_SYNC_ITERATOR_TYPE:
     230             : 
     231             :     case JS_TYPED_ARRAY_KEY_ITERATOR_TYPE:
     232             :     case JS_FAST_ARRAY_KEY_ITERATOR_TYPE:
     233             :     case JS_GENERIC_ARRAY_KEY_ITERATOR_TYPE:
     234             :     case JS_UINT8_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     235             :     case JS_INT8_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     236             :     case JS_UINT16_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     237             :     case JS_INT16_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     238             :     case JS_UINT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     239             :     case JS_INT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     240             :     case JS_FLOAT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     241             :     case JS_FLOAT64_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     242             :     case JS_UINT8_CLAMPED_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     243             :     case JS_FAST_SMI_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     244             :     case JS_FAST_HOLEY_SMI_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     245             :     case JS_FAST_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     246             :     case JS_FAST_HOLEY_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     247             :     case JS_FAST_DOUBLE_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     248             :     case JS_FAST_HOLEY_DOUBLE_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     249             :     case JS_GENERIC_ARRAY_KEY_VALUE_ITERATOR_TYPE:
     250             :     case JS_UINT8_ARRAY_VALUE_ITERATOR_TYPE:
     251             :     case JS_INT8_ARRAY_VALUE_ITERATOR_TYPE:
     252             :     case JS_UINT16_ARRAY_VALUE_ITERATOR_TYPE:
     253             :     case JS_INT16_ARRAY_VALUE_ITERATOR_TYPE:
     254             :     case JS_UINT32_ARRAY_VALUE_ITERATOR_TYPE:
     255             :     case JS_INT32_ARRAY_VALUE_ITERATOR_TYPE:
     256             :     case JS_FLOAT32_ARRAY_VALUE_ITERATOR_TYPE:
     257             :     case JS_FLOAT64_ARRAY_VALUE_ITERATOR_TYPE:
     258             :     case JS_UINT8_CLAMPED_ARRAY_VALUE_ITERATOR_TYPE:
     259             :     case JS_FAST_SMI_ARRAY_VALUE_ITERATOR_TYPE:
     260             :     case JS_FAST_HOLEY_SMI_ARRAY_VALUE_ITERATOR_TYPE:
     261             :     case JS_FAST_ARRAY_VALUE_ITERATOR_TYPE:
     262             :     case JS_FAST_HOLEY_ARRAY_VALUE_ITERATOR_TYPE:
     263             :     case JS_FAST_DOUBLE_ARRAY_VALUE_ITERATOR_TYPE:
     264             :     case JS_FAST_HOLEY_DOUBLE_ARRAY_VALUE_ITERATOR_TYPE:
     265             :     case JS_GENERIC_ARRAY_VALUE_ITERATOR_TYPE:
     266             : 
     267             :     case JS_WEAK_MAP_TYPE:
     268             :     case JS_WEAK_SET_TYPE:
     269             :     case JS_PROMISE_CAPABILITY_TYPE:
     270             :     case JS_PROMISE_TYPE:
     271             :       DCHECK(!map->is_callable());
     272             :       DCHECK(!map->is_undetectable());
     273        5086 :       return kOtherObject;
     274             :     case JS_BOUND_FUNCTION_TYPE:
     275             :       DCHECK(!map->is_undetectable());
     276         192 :       return kBoundFunction;
     277             :     case JS_FUNCTION_TYPE:
     278             :       DCHECK(!map->is_undetectable());
     279      625538 :       return kFunction;
     280             :     case JS_PROXY_TYPE:
     281             :       DCHECK(!map->is_undetectable());
     282        1064 :       if (map->is_callable()) return kCallableProxy;
     283         944 :       return kOtherProxy;
     284             :     case MAP_TYPE:
     285             :     case ALLOCATION_SITE_TYPE:
     286             :     case ACCESSOR_INFO_TYPE:
     287             :     case SHARED_FUNCTION_INFO_TYPE:
     288             :     case FUNCTION_TEMPLATE_INFO_TYPE:
     289             :     case ACCESSOR_PAIR_TYPE:
     290             :     case FIXED_ARRAY_TYPE:
     291             :     case FIXED_DOUBLE_ARRAY_TYPE:
     292             :     case BYTE_ARRAY_TYPE:
     293             :     case BYTECODE_ARRAY_TYPE:
     294             :     case TRANSITION_ARRAY_TYPE:
     295             :     case FOREIGN_TYPE:
     296             :     case SCRIPT_TYPE:
     297             :     case CODE_TYPE:
     298             :     case PROPERTY_CELL_TYPE:
     299             :     case MODULE_TYPE:
     300             :     case MODULE_INFO_ENTRY_TYPE:
     301      604243 :       return kOtherInternal;
     302             : 
     303             :     // Remaining instance types are unsupported for now. If any of them do
     304             :     // require bit set types, they should get kOtherInternal.
     305             :     case MUTABLE_HEAP_NUMBER_TYPE:
     306             :     case FREE_SPACE_TYPE:
     307             : #define FIXED_TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
     308             :   case FIXED_##TYPE##_ARRAY_TYPE:
     309             : 
     310             :       TYPED_ARRAYS(FIXED_TYPED_ARRAY_CASE)
     311             : #undef FIXED_TYPED_ARRAY_CASE
     312             :     case FILLER_TYPE:
     313             :     case ACCESS_CHECK_INFO_TYPE:
     314             :     case INTERCEPTOR_INFO_TYPE:
     315             :     case OBJECT_TEMPLATE_INFO_TYPE:
     316             :     case ALLOCATION_MEMENTO_TYPE:
     317             :     case ALIASED_ARGUMENTS_ENTRY_TYPE:
     318             :     case PROMISE_RESOLVE_THENABLE_JOB_INFO_TYPE:
     319             :     case PROMISE_REACTION_JOB_INFO_TYPE:
     320             :     case DEBUG_INFO_TYPE:
     321             :     case STACK_FRAME_INFO_TYPE:
     322             :     case CELL_TYPE:
     323             :     case WEAK_CELL_TYPE:
     324             :     case PROTOTYPE_INFO_TYPE:
     325             :     case TUPLE2_TYPE:
     326             :     case TUPLE3_TYPE:
     327             :     case CONTEXT_EXTENSION_TYPE:
     328             :     case ASYNC_GENERATOR_REQUEST_TYPE:
     329             :     case PADDING_TYPE_1:
     330             :     case PADDING_TYPE_2:
     331             :     case PADDING_TYPE_3:
     332             :     case PADDING_TYPE_4:
     333           0 :       UNREACHABLE();
     334             :       return kNone;
     335             :   }
     336           0 :   UNREACHABLE();
     337             :   return kNone;
     338             : }
     339             : 
     340     9432170 : Type::bitset BitsetType::Lub(i::Object* value) {
     341             :   DisallowHeapAllocation no_allocation;
     342     9432180 :   if (value->IsNumber()) {
     343        1410 :     return Lub(value->Number());
     344             :   }
     345     9430770 :   return Lub(i::HeapObject::cast(value)->map());
     346             : }
     347             : 
     348        1410 : Type::bitset BitsetType::Lub(double value) {
     349             :   DisallowHeapAllocation no_allocation;
     350        1410 :   if (i::IsMinusZero(value)) return kMinusZero;
     351        1410 :   if (std::isnan(value)) return kNaN;
     352        2820 :   if (IsUint32Double(value) || IsInt32Double(value)) return Lub(value, value);
     353             :   return kOtherNumber;
     354             : }
     355             : 
     356             : // Minimum values of plain numeric bitsets.
     357             : const BitsetType::Boundary BitsetType::BoundariesArray[] = {
     358             :     {kOtherNumber, kPlainNumber, -V8_INFINITY},
     359             :     {kOtherSigned32, kNegative32, kMinInt},
     360             :     {kNegative31, kNegative31, -0x40000000},
     361             :     {kUnsigned30, kUnsigned30, 0},
     362             :     {kOtherUnsigned31, kUnsigned31, 0x40000000},
     363             :     {kOtherUnsigned32, kUnsigned32, 0x80000000},
     364             :     {kOtherNumber, kPlainNumber, static_cast<double>(kMaxUInt32) + 1}};
     365             : 
     366             : const BitsetType::Boundary* BitsetType::Boundaries() { return BoundariesArray; }
     367             : 
     368             : size_t BitsetType::BoundariesSize() {
     369             :   // Windows doesn't like arraysize here.
     370             :   // return arraysize(BoundariesArray);
     371             :   return 7;
     372             : }
     373             : 
     374       20001 : Type::bitset BitsetType::ExpandInternals(Type::bitset bits) {
     375             :   DisallowHeapAllocation no_allocation;
     376       20001 :   if (!(bits & kPlainNumber)) return bits;  // Shortcut.
     377             :   const Boundary* boundaries = Boundaries();
     378        9870 :   for (size_t i = 0; i < BoundariesSize(); ++i) {
     379             :     DCHECK(BitsetType::Is(boundaries[i].internal, boundaries[i].external));
     380        9870 :     if (bits & boundaries[i].internal) bits |= boundaries[i].external;
     381             :   }
     382             :   return bits;
     383             : }
     384             : 
     385    10166752 : Type::bitset BitsetType::Lub(double min, double max) {
     386             :   DisallowHeapAllocation no_allocation;
     387             :   int lub = kNone;
     388             :   const Boundary* mins = Boundaries();
     389             : 
     390    89695977 :   for (size_t i = 1; i < BoundariesSize(); ++i) {
     391    94999801 :     if (min < mins[i].min) {
     392    56398445 :       lub |= mins[i - 1].internal;
     393    56398445 :       if (max < mins[i].min) return lub;
     394             :     }
     395             :   }
     396     5994287 :   return lub | mins[BoundariesSize() - 1].internal;
     397             : }
     398             : 
     399    11782755 : Type::bitset BitsetType::NumberBits(bitset bits) { return bits & kPlainNumber; }
     400             : 
     401    29385359 : Type::bitset BitsetType::Glb(double min, double max) {
     402             :   DisallowHeapAllocation no_allocation;
     403             :   int glb = kNone;
     404             :   const Boundary* mins = Boundaries();
     405             : 
     406             :   // If the range does not touch 0, the bound is empty.
     407    29385359 :   if (max < -1 || min > 0) return glb;
     408             : 
     409    91852250 :   for (size_t i = 1; i + 1 < BoundariesSize(); ++i) {
     410    82319545 :     if (min <= mins[i].min) {
     411    70785422 :       if (max + 1 < mins[i + 1].min) break;
     412    60499496 :       glb |= mins[i].external;
     413             :     }
     414             :   }
     415             :   // OtherNumber also contains float numbers, so it can never be
     416             :   // in the greatest lower bound.
     417    19818631 :   return glb & ~(kOtherNumber);
     418             : }
     419             : 
     420     7274804 : double BitsetType::Min(bitset bits) {
     421             :   DisallowHeapAllocation no_allocation;
     422             :   DCHECK(Is(bits, kNumber));
     423             :   const Boundary* mins = Boundaries();
     424     7274804 :   bool mz = bits & kMinusZero;
     425    15319041 :   for (size_t i = 0; i < BoundariesSize(); ++i) {
     426    30596272 :     if (Is(mins[i].internal, bits)) {
     427     7339206 :       return mz ? std::min(0.0, mins[i].min) : mins[i].min;
     428             :     }
     429             :   }
     430       20905 :   if (mz) return 0;
     431        7804 :   return std::numeric_limits<double>::quiet_NaN();
     432             : }
     433             : 
     434     7447587 : double BitsetType::Max(bitset bits) {
     435             :   DisallowHeapAllocation no_allocation;
     436             :   DCHECK(Is(bits, kNumber));
     437             :   const Boundary* mins = Boundaries();
     438     7447587 :   bool mz = bits & kMinusZero;
     439     7447587 :   if (BitsetType::Is(mins[BoundariesSize() - 1].internal, bits)) {
     440             :     return +V8_INFINITY;
     441             :   }
     442    13155730 :   for (size_t i = BoundariesSize() - 1; i-- > 0;) {
     443    26274732 :     if (Is(mins[i].internal, bits)) {
     444     6473162 :       return mz ? std::max(0.0, mins[i + 1].min - 1) : mins[i + 1].min - 1;
     445             :     }
     446             :   }
     447       18364 :   if (mz) return 0;
     448        7814 :   return std::numeric_limits<double>::quiet_NaN();
     449             : }
     450             : 
     451             : // static
     452     1720863 : bool OtherNumberConstantType::IsOtherNumberConstant(double value) {
     453             :   // Not an integer, not NaN, and not -0.
     454     5162589 :   return !std::isnan(value) && !Type::IsInteger(value) &&
     455     1720863 :          !i::IsMinusZero(value);
     456             : }
     457             : 
     458             : // static
     459           0 : bool OtherNumberConstantType::IsOtherNumberConstant(Object* value) {
     460           0 :   return value->IsHeapNumber() &&
     461           0 :          IsOtherNumberConstant(HeapNumber::cast(value)->value());
     462             : }
     463             : 
     464     3980614 : HeapConstantType::HeapConstantType(BitsetType::bitset bitset,
     465             :                                    i::Handle<i::HeapObject> object)
     466     9429868 :     : TypeBase(kHeapConstant), bitset_(bitset), object_(object) {
     467             :   DCHECK(!object->IsHeapNumber());
     468             :   DCHECK_IMPLIES(object->IsString(), object->IsInternalizedString());
     469     3980614 : }
     470             : 
     471             : // -----------------------------------------------------------------------------
     472             : // Predicates.
     473             : 
     474     9784633 : bool Type::SimplyEquals(Type* that) {
     475             :   DisallowHeapAllocation no_allocation;
     476     9784633 :   if (this->IsHeapConstant()) {
     477     6674236 :     return that->IsHeapConstant() &&
     478             :            this->AsHeapConstant()->Value().address() ==
     479     6674236 :                that->AsHeapConstant()->Value().address();
     480             :   }
     481     3110397 :   if (this->IsOtherNumberConstant()) {
     482     4220277 :     return that->IsOtherNumberConstant() &&
     483     1273442 :            this->AsOtherNumberConstant()->Value() ==
     484     4220277 :                that->AsOtherNumberConstant()->Value();
     485             :   }
     486      163562 :   if (this->IsRange()) {
     487      326897 :     if (that->IsHeapConstant() || that->IsOtherNumberConstant()) return false;
     488             :   }
     489         114 :   if (this->IsTuple()) {
     490         114 :     if (!that->IsTuple()) return false;
     491             :     TupleType* this_tuple = this->AsTuple();
     492             :     TupleType* that_tuple = that->AsTuple();
     493         114 :     if (this_tuple->Arity() != that_tuple->Arity()) {
     494             :       return false;
     495             :     }
     496         342 :     for (int i = 0, n = this_tuple->Arity(); i < n; ++i) {
     497         342 :       if (!this_tuple->Element(i)->Equals(that_tuple->Element(i))) return false;
     498             :     }
     499             :     return true;
     500             :   }
     501           0 :   UNREACHABLE();
     502             :   return false;
     503             : }
     504             : 
     505             : // Check if [this] <= [that].
     506   264511890 : bool Type::SlowIs(Type* that) {
     507             :   DisallowHeapAllocation no_allocation;
     508             : 
     509             :   // Fast bitset cases
     510   264511890 :   if (that->IsBitset()) {
     511   179835765 :     return BitsetType::Is(this->BitsetLub(), that->AsBitset());
     512             :   }
     513             : 
     514    84670131 :   if (this->IsBitset()) {
     515    23435983 :     return BitsetType::Is(this->AsBitset(), that->BitsetGlb());
     516             :   }
     517             : 
     518             :   // (T1 \/ ... \/ Tn) <= T  if  (T1 <= T) /\ ... /\ (Tn <= T)
     519    61234267 :   if (this->IsUnion()) {
     520    13581077 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
     521    26303612 :       if (!this->AsUnion()->Get(i)->Is(that)) return false;
     522             :     }
     523             :     return true;
     524             :   }
     525             : 
     526             :   // T <= (T1 \/ ... \/ Tn)  if  (T <= T1) \/ ... \/ (T <= Tn)
     527    51174735 :   if (that->IsUnion()) {
     528    23567724 :     for (int i = 0, n = that->AsUnion()->Length(); i < n; ++i) {
     529    40482512 :       if (this->Is(that->AsUnion()->Get(i))) return true;
     530    18515432 :       if (i > 1 && this->IsRange()) return false;  // Shortcut.
     531             :     }
     532             :     return false;
     533             :   }
     534             : 
     535    41999534 :   if (that->IsRange()) {
     536    45181874 :     return (this->IsRange() && Contains(that->AsRange(), this->AsRange()));
     537             :   }
     538    12888619 :   if (this->IsRange()) return false;
     539             : 
     540     9573052 :   return this->SimplyEquals(that);
     541             : }
     542             : 
     543             : // Check if [this] and [that] overlap.
     544    13141731 : bool Type::Maybe(Type* that) {
     545             :   DisallowHeapAllocation no_allocation;
     546             : 
     547    13941600 :   if (!BitsetType::IsInhabited(this->BitsetLub() & that->BitsetLub()))
     548             :     return false;
     549             : 
     550             :   // (T1 \/ ... \/ Tn) overlaps T  if  (T1 overlaps T) \/ ... \/ (Tn overlaps T)
     551     8440132 :   if (this->IsUnion()) {
     552      218169 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
     553      383620 :       if (this->AsUnion()->Get(i)->Maybe(that)) return true;
     554             :     }
     555             :     return false;
     556             :   }
     557             : 
     558             :   // T overlaps (T1 \/ ... \/ Tn)  if  (T overlaps T1) \/ ... \/ (T overlaps Tn)
     559     8323927 :   if (that->IsUnion()) {
     560      258856 :     for (int i = 0, n = that->AsUnion()->Length(); i < n; ++i) {
     561      396128 :       if (this->Maybe(that->AsUnion()->Get(i))) return true;
     562             :     }
     563             :     return false;
     564             :   }
     565             : 
     566     8209413 :   if (this->IsBitset() && that->IsBitset()) return true;
     567             : 
     568     5105018 :   if (this->IsRange()) {
     569     3912912 :     if (that->IsRange()) {
     570     2975952 :       return Overlap(this->AsRange(), that->AsRange());
     571             :     }
     572      936960 :     if (that->IsBitset()) {
     573             :       bitset number_bits = BitsetType::NumberBits(that->AsBitset());
     574      773585 :       if (number_bits == BitsetType::kNone) {
     575             :         return false;
     576             :       }
     577     1547177 :       double min = std::max(BitsetType::Min(number_bits), this->Min());
     578     1547172 :       double max = std::min(BitsetType::Max(number_bits), this->Max());
     579      773582 :       return min <= max;
     580             :     }
     581             :   }
     582     1355481 :   if (that->IsRange()) {
     583             :     return that->Maybe(this);  // This case is handled above.
     584             :   }
     585             : 
     586      552418 :   if (this->IsBitset() || that->IsBitset()) return true;
     587             : 
     588      210598 :   return this->SimplyEquals(that);
     589             : }
     590             : 
     591             : // Return the range in [this], or [NULL].
     592    28437983 : Type* Type::GetRange() {
     593             :   DisallowHeapAllocation no_allocation;
     594    28437983 :   if (this->IsRange()) return this;
     595    32127610 :   if (this->IsUnion() && this->AsUnion()->Get(1)->IsRange()) {
     596    15448732 :     return this->AsUnion()->Get(1);
     597             :   }
     598             :   return NULL;
     599             : }
     600             : 
     601           0 : bool UnionType::Wellformed() {
     602             :   DisallowHeapAllocation no_allocation;
     603             :   // This checks the invariants of the union representation:
     604             :   // 1. There are at least two elements.
     605             :   // 2. The first element is a bitset, no other element is a bitset.
     606             :   // 3. At most one element is a range, and it must be the second one.
     607             :   // 4. No element is itself a union.
     608             :   // 5. No element (except the bitset) is a subtype of any other.
     609             :   // 6. If there is a range, then the bitset type does not contain
     610             :   //    plain number bits.
     611             :   DCHECK(this->Length() >= 2);       // (1)
     612             :   DCHECK(this->Get(0)->IsBitset());  // (2a)
     613             : 
     614             :   for (int i = 0; i < this->Length(); ++i) {
     615             :     if (i != 0) DCHECK(!this->Get(i)->IsBitset());  // (2b)
     616             :     if (i != 1) DCHECK(!this->Get(i)->IsRange());   // (3)
     617             :     DCHECK(!this->Get(i)->IsUnion());               // (4)
     618             :     for (int j = 0; j < this->Length(); ++j) {
     619             :       if (i != j && i != 0) DCHECK(!this->Get(i)->Is(this->Get(j)));  // (5)
     620             :     }
     621             :   }
     622             :   DCHECK(!this->Get(1)->IsRange() ||
     623             :          (BitsetType::NumberBits(this->Get(0)->AsBitset()) ==
     624             :           BitsetType::kNone));  // (6)
     625           0 :   return true;
     626             : }
     627             : 
     628             : // -----------------------------------------------------------------------------
     629             : // Union and intersection
     630             : 
     631             : static bool AddIsSafe(int x, int y) {
     632    28774589 :   return x >= 0 ? y <= std::numeric_limits<int>::max() - x
     633    57549178 :                 : y >= std::numeric_limits<int>::min() - x;
     634             : }
     635             : 
     636    20284924 : Type* Type::Intersect(Type* type1, Type* type2, Zone* zone) {
     637             :   // Fast case: bit sets.
     638    35467283 :   if (type1->IsBitset() && type2->IsBitset()) {
     639    29098636 :     return BitsetType::New(type1->AsBitset() & type2->AsBitset());
     640             :   }
     641             : 
     642             :   // Fast case: top or bottom types.
     643     5735606 :   if (type1->IsNone() || type2->IsAny()) return type1;  // Shortcut.
     644     5560965 :   if (type2->IsNone() || type1->IsAny()) return type2;  // Shortcut.
     645             : 
     646             :   // Semi-fast case.
     647     5427723 :   if (type1->Is(type2)) return type1;
     648     1533975 :   if (type2->Is(type1)) return type2;
     649             : 
     650             :   // Slow case: create union.
     651             : 
     652             :   // Semantic subtyping check - this is needed for consistency with the
     653             :   // semi-fast case above.
     654      406140 :   if (type1->Is(type2)) {
     655             :     type2 = Any();
     656      406140 :   } else if (type2->Is(type1)) {
     657             :     type1 = Any();
     658             :   }
     659             : 
     660      406139 :   bitset bits = type1->BitsetGlb() & type2->BitsetGlb();
     661      406139 :   int size1 = type1->IsUnion() ? type1->AsUnion()->Length() : 1;
     662      406139 :   int size2 = type2->IsUnion() ? type2->AsUnion()->Length() : 1;
     663      406139 :   if (!AddIsSafe(size1, size2)) return Any();
     664      406138 :   int size = size1 + size2;
     665      406138 :   if (!AddIsSafe(size, 2)) return Any();
     666      406140 :   size += 2;
     667      406140 :   Type* result_type = UnionType::New(size, zone);
     668             :   UnionType* result = result_type->AsUnion();
     669             :   size = 0;
     670             : 
     671             :   // Deal with bitsets.
     672      605780 :   result->Set(size++, BitsetType::New(bits));
     673             : 
     674      406140 :   RangeType::Limits lims = RangeType::Limits::Empty();
     675      406140 :   size = IntersectAux(type1, type2, result, size, &lims, zone);
     676             : 
     677             :   // If the range is not empty, then insert it into the union and
     678             :   // remove the number bits from the bitset.
     679      406137 :   if (!lims.IsEmpty()) {
     680      199642 :     size = UpdateRange(RangeType::New(lims, zone), result, size, zone);
     681             : 
     682             :     // Remove the number bits.
     683             :     bitset number_bits = BitsetType::NumberBits(bits);
     684      199640 :     bits &= ~number_bits;
     685             :     result->Set(0, BitsetType::New(bits));
     686             :   }
     687      406135 :   return NormalizeUnion(result_type, size, zone);
     688             : }
     689             : 
     690      199640 : int Type::UpdateRange(Type* range, UnionType* result, int size, Zone* zone) {
     691      199640 :   if (size == 1) {
     692      200214 :     result->Set(size++, range);
     693             :   } else {
     694             :     // Make space for the range.
     695         225 :     result->Set(size++, result->Get(1));
     696             :     result->Set(1, range);
     697             :   }
     698             : 
     699             :   // Remove any components that just got subsumed.
     700      199989 :   for (int i = 2; i < size;) {
     701         349 :     if (result->Get(i)->Is(range)) {
     702           0 :       result->Set(i, result->Get(--size));
     703             :     } else {
     704         349 :       ++i;
     705             :     }
     706             :   }
     707      199640 :   return size;
     708             : }
     709             : 
     710      137479 : RangeType::Limits Type::ToLimits(bitset bits, Zone* zone) {
     711             :   bitset number_bits = BitsetType::NumberBits(bits);
     712             : 
     713      137479 :   if (number_bits == BitsetType::kNone) {
     714             :     return RangeType::Limits::Empty();
     715             :   }
     716             : 
     717             :   return RangeType::Limits(BitsetType::Min(number_bits),
     718      137479 :                            BitsetType::Max(number_bits));
     719             : }
     720             : 
     721      137481 : RangeType::Limits Type::IntersectRangeAndBitset(Type* range, Type* bitset,
     722             :                                                 Zone* zone) {
     723             :   RangeType::Limits range_lims(range->AsRange());
     724      137481 :   RangeType::Limits bitset_lims = ToLimits(bitset->AsBitset(), zone);
     725      137481 :   return RangeType::Limits::Intersect(range_lims, bitset_lims);
     726             : }
     727             : 
     728      636511 : int Type::IntersectAux(Type* lhs, Type* rhs, UnionType* result, int size,
     729             :                        RangeType::Limits* lims, Zone* zone) {
     730      681309 :   if (lhs->IsUnion()) {
     731      324535 :     for (int i = 0, n = lhs->AsUnion()->Length(); i < n; ++i) {
     732             :       size =
     733      460680 :           IntersectAux(lhs->AsUnion()->Get(i), rhs, result, size, lims, zone);
     734             :     }
     735             :     return size;
     736             :   }
     737      587116 :   if (rhs->IsUnion()) {
     738          66 :     for (int i = 0, n = rhs->AsUnion()->Length(); i < n; ++i) {
     739             :       size =
     740          92 :           IntersectAux(lhs, rhs->AsUnion()->Get(i), result, size, lims, zone);
     741             :     }
     742             :     return size;
     743             :   }
     744             : 
     745      587098 :   if (!BitsetType::IsInhabited(lhs->BitsetLub() & rhs->BitsetLub())) {
     746             :     return size;
     747             :   }
     748             : 
     749      290999 :   if (lhs->IsRange()) {
     750      239853 :     if (rhs->IsBitset()) {
     751      137482 :       RangeType::Limits lim = IntersectRangeAndBitset(lhs, rhs, zone);
     752             : 
     753      137481 :       if (!lim.IsEmpty()) {
     754      137481 :         *lims = RangeType::Limits::Union(lim, *lims);
     755             :       }
     756             :       return size;
     757             :     }
     758      102371 :     if (rhs->IsRange()) {
     759             :       RangeType::Limits lim = RangeType::Limits::Intersect(
     760             :           RangeType::Limits(lhs->AsRange()), RangeType::Limits(rhs->AsRange()));
     761       62188 :       if (!lim.IsEmpty()) {
     762       62169 :         *lims = RangeType::Limits::Union(lim, *lims);
     763             :       }
     764             :     }
     765      102371 :     return size;
     766             :   }
     767       51146 :   if (rhs->IsRange()) {
     768             :     // This case is handled symmetrically above.
     769             :     return IntersectAux(rhs, lhs, result, size, lims, zone);
     770             :   }
     771        6348 :   if (lhs->IsBitset() || rhs->IsBitset()) {
     772        5370 :     return AddToUnion(lhs->IsBitset() ? rhs : lhs, result, size, zone);
     773             :   }
     774         978 :   if (lhs->SimplyEquals(rhs)) {
     775           2 :     return AddToUnion(lhs, result, size, zone);
     776             :   }
     777             :   return size;
     778             : }
     779             : 
     780             : // Make sure that we produce a well-formed range and bitset:
     781             : // If the range is non-empty, the number bits in the bitset should be
     782             : // clear. Moreover, if we have a canonical range (such as Signed32),
     783             : // we want to produce a bitset rather than a range.
     784    10672051 : Type* Type::NormalizeRangeAndBitset(Type* range, bitset* bits, Zone* zone) {
     785             :   // Fast path: If the bitset does not mention numbers, we can just keep the
     786             :   // range.
     787    10672051 :   bitset number_bits = BitsetType::NumberBits(*bits);
     788    10672051 :   if (number_bits == 0) {
     789             :     return range;
     790             :   }
     791             : 
     792             :   // If the range is semantically contained within the bitset, return None and
     793             :   // leave the bitset untouched.
     794             :   bitset range_lub = range->BitsetLub();
     795    13219176 :   if (BitsetType::Is(range_lub, *bits)) {
     796             :     return None();
     797             :   }
     798             : 
     799             :   // Slow path: reconcile the bitset range and the range.
     800     5700994 :   double bitset_min = BitsetType::Min(number_bits);
     801     5700994 :   double bitset_max = BitsetType::Max(number_bits);
     802             : 
     803     5700994 :   double range_min = range->Min();
     804     5700994 :   double range_max = range->Max();
     805             : 
     806             :   // Remove the number bits from the bitset, they would just confuse us now.
     807             :   // NOTE: bits contains OtherNumber iff bits contains PlainNumber, in which
     808             :   // case we already returned after the subtype check above.
     809     5700994 :   *bits &= ~number_bits;
     810             : 
     811     5700994 :   if (range_min <= bitset_min && range_max >= bitset_max) {
     812             :     // Bitset is contained within the range, just return the range.
     813             :     return range;
     814             :   }
     815             : 
     816      484176 :   if (bitset_min < range_min) {
     817             :     range_min = bitset_min;
     818             :   }
     819      484176 :   if (bitset_max > range_max) {
     820             :     range_max = bitset_max;
     821             :   }
     822      484176 :   return RangeType::New(range_min, range_max, zone);
     823             : }
     824             : 
     825     4592951 : Type* Type::NewConstant(double value, Zone* zone) {
     826     4592951 :   if (IsInteger(value)) {
     827     2853064 :     return Range(value, value, zone);
     828     1739887 :   } else if (i::IsMinusZero(value)) {
     829             :     return Type::MinusZero();
     830     1726852 :   } else if (std::isnan(value)) {
     831             :     return Type::NaN();
     832             :   }
     833             : 
     834             :   DCHECK(OtherNumberConstantType::IsOtherNumberConstant(value));
     835     1720863 :   return OtherNumberConstant(value, zone);
     836             : }
     837             : 
     838    10565650 : Type* Type::NewConstant(i::Handle<i::Object> value, Zone* zone) {
     839    10565650 :   if (IsInteger(*value)) {
     840             :     double v = value->Number();
     841     3406292 :     return Range(v, v, zone);
     842     7159371 :   } else if (value->IsHeapNumber()) {
     843     1707250 :     return NewConstant(value->Number(), zone);
     844     5954004 :   } else if (value->IsString() && !value->IsInternalizedString()) {
     845             :     return Type::OtherString();
     846             :   }
     847     5449254 :   return HeapConstant(i::Handle<i::HeapObject>::cast(value), zone);
     848             : }
     849             : 
     850    35632825 : Type* Type::Union(Type* type1, Type* type2, Zone* zone) {
     851             :   // Fast case: bit sets.
     852    53540203 :   if (type1->IsBitset() && type2->IsBitset()) {
     853    19643264 :     return BitsetType::New(type1->AsBitset() | type2->AsBitset());
     854             :   }
     855             : 
     856             :   // Fast case: top or bottom types.
     857    25811193 :   if (type1->IsAny() || type2->IsNone()) return type1;
     858    25146542 :   if (type2->IsAny() || type1->IsNone()) return type2;
     859             : 
     860             :   // Semi-fast case.
     861    21710450 :   if (type1->Is(type2)) return type2;
     862    20043493 :   if (type2->Is(type1)) return type1;
     863             : 
     864             :   // Slow case: create union.
     865    13981156 :   int size1 = type1->IsUnion() ? type1->AsUnion()->Length() : 1;
     866    13981156 :   int size2 = type2->IsUnion() ? type2->AsUnion()->Length() : 1;
     867    13981156 :   if (!AddIsSafe(size1, size2)) return Any();
     868    13981156 :   int size = size1 + size2;
     869    13981156 :   if (!AddIsSafe(size, 2)) return Any();
     870    13981156 :   size += 2;
     871    13981156 :   Type* result_type = UnionType::New(size, zone);
     872             :   UnionType* result = result_type->AsUnion();
     873             :   size = 0;
     874             : 
     875             :   // Compute the new bitset.
     876    13981153 :   bitset new_bitset = type1->BitsetGlb() | type2->BitsetGlb();
     877             : 
     878             :   // Deal with ranges.
     879             :   Type* range = None();
     880    13981153 :   Type* range1 = type1->GetRange();
     881    13981152 :   Type* range2 = type2->GetRange();
     882    13981158 :   if (range1 != NULL && range2 != NULL) {
     883             :     RangeType::Limits lims =
     884             :         RangeType::Limits::Union(RangeType::Limits(range1->AsRange()),
     885     3157769 :                                  RangeType::Limits(range2->AsRange()));
     886     3157769 :     Type* union_range = RangeType::New(lims, zone);
     887     3157769 :     range = NormalizeRangeAndBitset(union_range, &new_bitset, zone);
     888    10823389 :   } else if (range1 != NULL) {
     889     5005190 :     range = NormalizeRangeAndBitset(range1, &new_bitset, zone);
     890     5818199 :   } else if (range2 != NULL) {
     891     2509100 :     range = NormalizeRangeAndBitset(range2, &new_bitset, zone);
     892             :   }
     893    13981151 :   Type* bits = BitsetType::New(new_bitset);
     894    23744608 :   result->Set(size++, bits);
     895    13981151 :   if (!range->IsNone()) result->Set(size++, range);
     896             : 
     897    13981151 :   size = AddToUnion(type1, result, size, zone);
     898    13981156 :   size = AddToUnion(type2, result, size, zone);
     899    13981151 :   return NormalizeUnion(result_type, size, zone);
     900             : }
     901             : 
     902             : // Add [type] to [result] unless [type] is bitset, range, or already subsumed.
     903             : // Return new size of [result].
     904    57085074 : int Type::AddToUnion(Type* type, UnionType* result, int size, Zone* zone) {
     905    97037047 :   if (type->IsBitset() || type->IsRange()) return size;
     906    26122172 :   if (type->IsUnion()) {
     907    39375703 :     for (int i = 0, n = type->AsUnion()->Length(); i < n; ++i) {
     908    58234850 :       size = AddToUnion(type->AsUnion()->Get(i), result, size, zone);
     909             :     }
     910             :     return size;
     911             :   }
     912    29491415 :   for (int i = 0; i < size; ++i) {
     913    76693836 :     if (type->Is(result->Get(i))) return size;
     914             :   }
     915    14016767 :   result->Set(size++, type);
     916    14016767 :   return size;
     917             : }
     918             : 
     919    14387287 : Type* Type::NormalizeUnion(Type* union_type, int size, Zone* zone) {
     920             :   UnionType* unioned = union_type->AsUnion();
     921             :   DCHECK(size >= 1);
     922             :   DCHECK(unioned->Get(0)->IsBitset());
     923             :   // If the union has just one element, return it.
     924    14387287 :   if (size == 1) {
     925     1467900 :     return unioned->Get(0);
     926             :   }
     927             :   bitset bits = unioned->Get(0)->AsBitset();
     928             :   // If the union only consists of a range, we can get rid of the union.
     929    13653337 :   if (size == 2 && bits == BitsetType::kNone) {
     930     1196811 :     if (unioned->Get(1)->IsRange()) {
     931             :       return RangeType::New(unioned->Get(1)->AsRange()->Min(),
     932     2393129 :                             unioned->Get(1)->AsRange()->Max(), zone);
     933             :     }
     934             :   }
     935             :   unioned->Shrink(size);
     936             :   SLOW_DCHECK(unioned->Wellformed());
     937    12456770 :   return union_type;
     938             : }
     939             : 
     940       73228 : int Type::NumConstants() {
     941             :   DisallowHeapAllocation no_allocation;
     942      145118 :   if (this->IsHeapConstant() || this->IsOtherNumberConstant()) {
     943             :     return 1;
     944       71086 :   } else if (this->IsUnion()) {
     945             :     int result = 0;
     946       10222 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
     947       13812 :       if (this->AsUnion()->Get(i)->IsHeapConstant()) ++result;
     948             :     }
     949             :     return result;
     950             :   } else {
     951             :     return 0;
     952             :   }
     953             : }
     954             : 
     955             : // -----------------------------------------------------------------------------
     956             : // Printing.
     957             : 
     958      117852 : const char* BitsetType::Name(bitset bits) {
     959      117852 :   switch (bits) {
     960             : #define RETURN_NAMED_TYPE(type, value) \
     961             :   case k##type:                        \
     962             :     return #type;
     963           0 :     PROPER_BITSET_TYPE_LIST(RETURN_NAMED_TYPE)
     964           0 :     INTERNAL_BITSET_TYPE_LIST(RETURN_NAMED_TYPE)
     965             : #undef RETURN_NAMED_TYPE
     966             : 
     967             :     default:
     968           0 :       return NULL;
     969             :   }
     970             : }
     971             : 
     972      117852 : void BitsetType::Print(std::ostream& os,  // NOLINT
     973             :                        bitset bits) {
     974             :   DisallowHeapAllocation no_allocation;
     975      117852 :   const char* name = Name(bits);
     976      117852 :   if (name != NULL) {
     977      117852 :     os << name;
     978      117852 :     return;
     979             :   }
     980             : 
     981             :   // clang-format off
     982             :   static const bitset named_bitsets[] = {
     983             : #define BITSET_CONSTANT(type, value) k##type,
     984             :     INTERNAL_BITSET_TYPE_LIST(BITSET_CONSTANT)
     985             :     PROPER_BITSET_TYPE_LIST(BITSET_CONSTANT)
     986             : #undef BITSET_CONSTANT
     987             :   };
     988             :   // clang-format on
     989             : 
     990             :   bool is_first = true;
     991           0 :   os << "(";
     992           0 :   for (int i(arraysize(named_bitsets) - 1); bits != 0 && i >= 0; --i) {
     993           0 :     bitset subset = named_bitsets[i];
     994           0 :     if ((bits & subset) == subset) {
     995           0 :       if (!is_first) os << " | ";
     996             :       is_first = false;
     997           0 :       os << Name(subset);
     998           0 :       bits -= subset;
     999             :     }
    1000             :   }
    1001             :   DCHECK(bits == 0);
    1002           0 :   os << ")";
    1003             : }
    1004             : 
    1005      117852 : void Type::PrintTo(std::ostream& os) {
    1006             :   DisallowHeapAllocation no_allocation;
    1007      117852 :   if (this->IsBitset()) {
    1008      117852 :     BitsetType::Print(os, this->AsBitset());
    1009           0 :   } else if (this->IsHeapConstant()) {
    1010           0 :     os << "HeapConstant(" << Brief(*this->AsHeapConstant()->Value()) << ")";
    1011           0 :   } else if (this->IsOtherNumberConstant()) {
    1012           0 :     os << "OtherNumberConstant(" << this->AsOtherNumberConstant()->Value()
    1013           0 :        << ")";
    1014           0 :   } else if (this->IsRange()) {
    1015           0 :     std::ostream::fmtflags saved_flags = os.setf(std::ios::fixed);
    1016             :     std::streamsize saved_precision = os.precision(0);
    1017           0 :     os << "Range(" << this->AsRange()->Min() << ", " << this->AsRange()->Max()
    1018           0 :        << ")";
    1019           0 :     os.flags(saved_flags);
    1020             :     os.precision(saved_precision);
    1021           0 :   } else if (this->IsUnion()) {
    1022           0 :     os << "(";
    1023           0 :     for (int i = 0, n = this->AsUnion()->Length(); i < n; ++i) {
    1024           0 :       Type* type_i = this->AsUnion()->Get(i);
    1025           0 :       if (i > 0) os << " | ";
    1026           0 :       type_i->PrintTo(os);
    1027             :     }
    1028           0 :     os << ")";
    1029           0 :   } else if (this->IsTuple()) {
    1030           0 :     os << "<";
    1031           0 :     for (int i = 0, n = this->AsTuple()->Arity(); i < n; ++i) {
    1032             :       Type* type_i = this->AsTuple()->Element(i);
    1033           0 :       if (i > 0) os << ", ";
    1034           0 :       type_i->PrintTo(os);
    1035             :     }
    1036           0 :     os << ">";
    1037             :   } else {
    1038           0 :     UNREACHABLE();
    1039             :   }
    1040      117852 : }
    1041             : 
    1042             : #ifdef DEBUG
    1043             : void Type::Print() {
    1044             :   OFStream os(stdout);
    1045             :   PrintTo(os);
    1046             :   os << std::endl;
    1047             : }
    1048             : void BitsetType::Print(bitset bits) {
    1049             :   OFStream os(stdout);
    1050             :   Print(os, bits);
    1051             :   os << std::endl;
    1052             : }
    1053             : #endif
    1054             : 
    1055     2253618 : BitsetType::bitset BitsetType::SignedSmall() {
    1056     2253618 :   return i::SmiValuesAre31Bits() ? kSigned31 : kSigned32;
    1057             : }
    1058             : 
    1059       73457 : BitsetType::bitset BitsetType::UnsignedSmall() {
    1060       73457 :   return i::SmiValuesAre31Bits() ? kUnsigned30 : kUnsigned31;
    1061             : }
    1062             : 
    1063             : }  // namespace compiler
    1064             : }  // namespace internal
    1065             : }  // namespace v8

Generated by: LCOV version 1.10