Home | History | Annotate | Download | only in src
      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 #ifndef V8_MACHINE_TYPE_H_
      6 #define V8_MACHINE_TYPE_H_
      7 
      8 #include <iosfwd>
      9 
     10 #include "src/base/bits.h"
     11 #include "src/globals.h"
     12 #include "src/signature.h"
     13 #include "src/zone/zone.h"
     14 
     15 namespace v8 {
     16 namespace internal {
     17 
     18 enum class MachineRepresentation {
     19   kNone,
     20   kBit,
     21   kWord8,
     22   kWord16,
     23   kWord32,
     24   kWord64,
     25   kTaggedSigned,
     26   kTaggedPointer,
     27   kTagged,
     28   // FP representations must be last, and in order of increasing size.
     29   kFloat32,
     30   kFloat64,
     31   kSimd128,
     32   kSimd1x4,  // SIMD boolean vector types.
     33   kSimd1x8,
     34   kSimd1x16,
     35   kFirstFPRepresentation = kFloat32,
     36   kLastRepresentation = kSimd1x16
     37 };
     38 
     39 static_assert(static_cast<int>(MachineRepresentation::kLastRepresentation) <
     40                   kIntSize * kBitsPerByte,
     41               "Bit masks of MachineRepresentation should fit in an int");
     42 
     43 const char* MachineReprToString(MachineRepresentation);
     44 
     45 enum class MachineSemantic {
     46   kNone,
     47   kBool,
     48   kInt32,
     49   kUint32,
     50   kInt64,
     51   kUint64,
     52   kNumber,
     53   kAny
     54 };
     55 
     56 class MachineType {
     57  public:
     58   MachineType()
     59       : representation_(MachineRepresentation::kNone),
     60         semantic_(MachineSemantic::kNone) {}
     61   MachineType(MachineRepresentation representation, MachineSemantic semantic)
     62       : representation_(representation), semantic_(semantic) {}
     63 
     64   bool operator==(MachineType other) const {
     65     return representation() == other.representation() &&
     66            semantic() == other.semantic();
     67   }
     68 
     69   bool operator!=(MachineType other) const { return !(*this == other); }
     70 
     71 
     72   MachineRepresentation representation() const { return representation_; }
     73   MachineSemantic semantic() const { return semantic_; }
     74 
     75   bool IsNone() { return representation() == MachineRepresentation::kNone; }
     76 
     77   bool IsSigned() {
     78     return semantic() == MachineSemantic::kInt32 ||
     79            semantic() == MachineSemantic::kInt64;
     80   }
     81   bool IsUnsigned() {
     82     return semantic() == MachineSemantic::kUint32 ||
     83            semantic() == MachineSemantic::kUint64;
     84   }
     85   static MachineRepresentation PointerRepresentation() {
     86     return (kPointerSize == 4) ? MachineRepresentation::kWord32
     87                                : MachineRepresentation::kWord64;
     88   }
     89   static MachineType UintPtr() {
     90     return (kPointerSize == 4) ? Uint32() : Uint64();
     91   }
     92   static MachineType IntPtr() {
     93     return (kPointerSize == 4) ? Int32() : Int64();
     94   }
     95   static MachineType Int8() {
     96     return MachineType(MachineRepresentation::kWord8, MachineSemantic::kInt32);
     97   }
     98   static MachineType Uint8() {
     99     return MachineType(MachineRepresentation::kWord8, MachineSemantic::kUint32);
    100   }
    101   static MachineType Int16() {
    102     return MachineType(MachineRepresentation::kWord16, MachineSemantic::kInt32);
    103   }
    104   static MachineType Uint16() {
    105     return MachineType(MachineRepresentation::kWord16,
    106                        MachineSemantic::kUint32);
    107   }
    108   static MachineType Int32() {
    109     return MachineType(MachineRepresentation::kWord32, MachineSemantic::kInt32);
    110   }
    111   static MachineType Uint32() {
    112     return MachineType(MachineRepresentation::kWord32,
    113                        MachineSemantic::kUint32);
    114   }
    115   static MachineType Int64() {
    116     return MachineType(MachineRepresentation::kWord64, MachineSemantic::kInt64);
    117   }
    118   static MachineType Uint64() {
    119     return MachineType(MachineRepresentation::kWord64,
    120                        MachineSemantic::kUint64);
    121   }
    122   static MachineType Float32() {
    123     return MachineType(MachineRepresentation::kFloat32,
    124                        MachineSemantic::kNumber);
    125   }
    126   static MachineType Float64() {
    127     return MachineType(MachineRepresentation::kFloat64,
    128                        MachineSemantic::kNumber);
    129   }
    130   static MachineType Simd128() {
    131     return MachineType(MachineRepresentation::kSimd128, MachineSemantic::kNone);
    132   }
    133   static MachineType Simd1x4() {
    134     return MachineType(MachineRepresentation::kSimd1x4, MachineSemantic::kNone);
    135   }
    136   static MachineType Simd1x8() {
    137     return MachineType(MachineRepresentation::kSimd1x8, MachineSemantic::kNone);
    138   }
    139   static MachineType Simd1x16() {
    140     return MachineType(MachineRepresentation::kSimd1x16,
    141                        MachineSemantic::kNone);
    142   }
    143   static MachineType Pointer() {
    144     return MachineType(PointerRepresentation(), MachineSemantic::kNone);
    145   }
    146   static MachineType TaggedPointer() {
    147     return MachineType(MachineRepresentation::kTaggedPointer,
    148                        MachineSemantic::kAny);
    149   }
    150   static MachineType TaggedSigned() {
    151     return MachineType(MachineRepresentation::kTaggedSigned,
    152                        MachineSemantic::kInt32);
    153   }
    154   static MachineType AnyTagged() {
    155     return MachineType(MachineRepresentation::kTagged, MachineSemantic::kAny);
    156   }
    157   static MachineType Bool() {
    158     return MachineType(MachineRepresentation::kBit, MachineSemantic::kBool);
    159   }
    160   static MachineType TaggedBool() {
    161     return MachineType(MachineRepresentation::kTagged, MachineSemantic::kBool);
    162   }
    163   static MachineType None() {
    164     return MachineType(MachineRepresentation::kNone, MachineSemantic::kNone);
    165   }
    166 
    167   // These naked representations should eventually go away.
    168   static MachineType RepWord8() {
    169     return MachineType(MachineRepresentation::kWord8, MachineSemantic::kNone);
    170   }
    171   static MachineType RepWord16() {
    172     return MachineType(MachineRepresentation::kWord16, MachineSemantic::kNone);
    173   }
    174   static MachineType RepWord32() {
    175     return MachineType(MachineRepresentation::kWord32, MachineSemantic::kNone);
    176   }
    177   static MachineType RepWord64() {
    178     return MachineType(MachineRepresentation::kWord64, MachineSemantic::kNone);
    179   }
    180   static MachineType RepFloat32() {
    181     return MachineType(MachineRepresentation::kFloat32, MachineSemantic::kNone);
    182   }
    183   static MachineType RepFloat64() {
    184     return MachineType(MachineRepresentation::kFloat64, MachineSemantic::kNone);
    185   }
    186   static MachineType RepSimd128() {
    187     return MachineType(MachineRepresentation::kSimd128, MachineSemantic::kNone);
    188   }
    189   static MachineType RepSimd1x4() {
    190     return MachineType(MachineRepresentation::kSimd1x4, MachineSemantic::kNone);
    191   }
    192   static MachineType RepSimd1x8() {
    193     return MachineType(MachineRepresentation::kSimd1x8, MachineSemantic::kNone);
    194   }
    195   static MachineType RepSimd1x16() {
    196     return MachineType(MachineRepresentation::kSimd1x16,
    197                        MachineSemantic::kNone);
    198   }
    199   static MachineType RepTagged() {
    200     return MachineType(MachineRepresentation::kTagged, MachineSemantic::kNone);
    201   }
    202   static MachineType RepBit() {
    203     return MachineType(MachineRepresentation::kBit, MachineSemantic::kNone);
    204   }
    205 
    206   static MachineType TypeForRepresentation(const MachineRepresentation& rep,
    207                                            bool isSigned = true) {
    208     switch (rep) {
    209       case MachineRepresentation::kNone:
    210         return MachineType::None();
    211       case MachineRepresentation::kBit:
    212         return MachineType::Bool();
    213       case MachineRepresentation::kWord8:
    214         return isSigned ? MachineType::Int8() : MachineType::Uint8();
    215       case MachineRepresentation::kWord16:
    216         return isSigned ? MachineType::Int16() : MachineType::Uint16();
    217       case MachineRepresentation::kWord32:
    218         return isSigned ? MachineType::Int32() : MachineType::Uint32();
    219       case MachineRepresentation::kWord64:
    220         return isSigned ? MachineType::Int64() : MachineType::Uint64();
    221       case MachineRepresentation::kFloat32:
    222         return MachineType::Float32();
    223       case MachineRepresentation::kFloat64:
    224         return MachineType::Float64();
    225       case MachineRepresentation::kSimd128:
    226         return MachineType::Simd128();
    227       case MachineRepresentation::kSimd1x4:
    228         return MachineType::Simd1x4();
    229       case MachineRepresentation::kSimd1x8:
    230         return MachineType::Simd1x8();
    231       case MachineRepresentation::kSimd1x16:
    232         return MachineType::Simd1x16();
    233       case MachineRepresentation::kTagged:
    234         return MachineType::AnyTagged();
    235       case MachineRepresentation::kTaggedSigned:
    236         return MachineType::TaggedSigned();
    237       case MachineRepresentation::kTaggedPointer:
    238         return MachineType::TaggedPointer();
    239       default:
    240         UNREACHABLE();
    241         return MachineType::None();
    242     }
    243   }
    244 
    245  private:
    246   MachineRepresentation representation_;
    247   MachineSemantic semantic_;
    248 };
    249 
    250 V8_INLINE size_t hash_value(MachineRepresentation rep) {
    251   return static_cast<size_t>(rep);
    252 }
    253 
    254 V8_INLINE size_t hash_value(MachineType type) {
    255   return static_cast<size_t>(type.representation()) +
    256          static_cast<size_t>(type.semantic()) * 16;
    257 }
    258 
    259 V8_EXPORT_PRIVATE std::ostream& operator<<(std::ostream& os,
    260                                            MachineRepresentation rep);
    261 std::ostream& operator<<(std::ostream& os, MachineSemantic type);
    262 V8_EXPORT_PRIVATE std::ostream& operator<<(std::ostream& os, MachineType type);
    263 
    264 inline bool IsFloatingPoint(MachineRepresentation rep) {
    265   return rep >= MachineRepresentation::kFirstFPRepresentation;
    266 }
    267 
    268 inline bool CanBeTaggedPointer(MachineRepresentation rep) {
    269   return rep == MachineRepresentation::kTagged ||
    270          rep == MachineRepresentation::kTaggedPointer;
    271 }
    272 
    273 inline bool CanBeTaggedSigned(MachineRepresentation rep) {
    274   return rep == MachineRepresentation::kTagged ||
    275          rep == MachineRepresentation::kTaggedSigned;
    276 }
    277 
    278 inline bool IsAnyTagged(MachineRepresentation rep) {
    279   return CanBeTaggedPointer(rep) || rep == MachineRepresentation::kTaggedSigned;
    280 }
    281 
    282 // Gets the log2 of the element size in bytes of the machine type.
    283 V8_EXPORT_PRIVATE inline int ElementSizeLog2Of(MachineRepresentation rep) {
    284   switch (rep) {
    285     case MachineRepresentation::kBit:
    286     case MachineRepresentation::kWord8:
    287       return 0;
    288     case MachineRepresentation::kWord16:
    289       return 1;
    290     case MachineRepresentation::kWord32:
    291     case MachineRepresentation::kFloat32:
    292       return 2;
    293     case MachineRepresentation::kWord64:
    294     case MachineRepresentation::kFloat64:
    295       return 3;
    296     case MachineRepresentation::kSimd128:
    297       return 4;
    298     case MachineRepresentation::kTaggedSigned:
    299     case MachineRepresentation::kTaggedPointer:
    300     case MachineRepresentation::kTagged:
    301       return kPointerSizeLog2;
    302     default:
    303       break;
    304   }
    305   UNREACHABLE();
    306   return -1;
    307 }
    308 
    309 typedef Signature<MachineType> MachineSignature;
    310 
    311 }  // namespace internal
    312 }  // namespace v8
    313 
    314 #endif  // V8_MACHINE_TYPE_H_
    315