Home | History | Annotate | Download | only in parser
      1 /*
      2  * Copyright (C) 2008 Apple Inc. All rights reserved.
      3  *
      4  * Redistribution and use in source and binary forms, with or without
      5  * modification, are permitted provided that the following conditions
      6  * are met:
      7  * 1. Redistributions of source code must retain the above copyright
      8  *    notice, this list of conditions and the following disclaimer.
      9  * 2. Redistributions in binary form must reproduce the above copyright
     10  *    notice, this list of conditions and the following disclaimer in the
     11  *    documentation and/or other materials provided with the distribution.
     12  *
     13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
     14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
     17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
     18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
     19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
     20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
     21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     24  */
     25 
     26 #ifndef ResultType_h
     27 #define ResultType_h
     28 
     29 namespace JSC {
     30 
     31     struct ResultType {
     32         friend struct OperandTypes;
     33 
     34         typedef char Type;
     35         static const Type TypeReusable = 1;
     36         static const Type TypeInt32    = 2;
     37 
     38         static const Type TypeMaybeNumber = 0x04;
     39         static const Type TypeMaybeString = 0x08;
     40         static const Type TypeMaybeNull   = 0x10;
     41         static const Type TypeMaybeBool   = 0x20;
     42         static const Type TypeMaybeOther  = 0x40;
     43 
     44         static const Type TypeBits = TypeMaybeNumber | TypeMaybeString | TypeMaybeNull | TypeMaybeBool | TypeMaybeOther;
     45 
     46         explicit ResultType(Type type)
     47             : m_type(type)
     48         {
     49         }
     50 
     51         bool isReusable()
     52         {
     53             return m_type & TypeReusable;
     54         }
     55 
     56         bool isInt32()
     57         {
     58             return m_type & TypeInt32;
     59         }
     60 
     61         bool definitelyIsNumber()
     62         {
     63             return (m_type & TypeBits) == TypeMaybeNumber;
     64         }
     65 
     66         bool definitelyIsString()
     67         {
     68             return (m_type & TypeBits) == TypeMaybeString;
     69         }
     70 
     71         bool mightBeNumber()
     72         {
     73             return m_type & TypeMaybeNumber;
     74         }
     75 
     76         bool isNotNumber()
     77         {
     78             return !mightBeNumber();
     79         }
     80 
     81         static ResultType nullType()
     82         {
     83             return ResultType(TypeMaybeNull);
     84         }
     85 
     86         static ResultType booleanType()
     87         {
     88             return ResultType(TypeMaybeBool);
     89         }
     90 
     91         static ResultType numberType()
     92         {
     93             return ResultType(TypeMaybeNumber);
     94         }
     95 
     96         static ResultType numberTypeCanReuse()
     97         {
     98             return ResultType(TypeReusable | TypeMaybeNumber);
     99         }
    100 
    101         static ResultType numberTypeCanReuseIsInt32()
    102         {
    103             return ResultType(TypeReusable | TypeInt32 | TypeMaybeNumber);
    104         }
    105 
    106         static ResultType stringOrNumberTypeCanReuse()
    107         {
    108             return ResultType(TypeReusable | TypeMaybeNumber | TypeMaybeString);
    109         }
    110 
    111         static ResultType stringType()
    112         {
    113             return ResultType(TypeMaybeString);
    114         }
    115 
    116         static ResultType unknownType()
    117         {
    118             return ResultType(TypeBits);
    119         }
    120 
    121         static ResultType forAdd(ResultType op1, ResultType op2)
    122         {
    123             if (op1.definitelyIsNumber() && op2.definitelyIsNumber())
    124                 return numberTypeCanReuse();
    125             if (op1.definitelyIsString() || op2.definitelyIsString())
    126                 return stringType();
    127             return stringOrNumberTypeCanReuse();
    128         }
    129 
    130         static ResultType forBitOp()
    131         {
    132             return numberTypeCanReuseIsInt32();
    133         }
    134 
    135     private:
    136         Type m_type;
    137     };
    138 
    139     struct OperandTypes
    140     {
    141         OperandTypes(ResultType first = ResultType::unknownType(), ResultType second = ResultType::unknownType())
    142         {
    143             // We have to initialize one of the int to ensure that
    144             // the entire struct is initialized.
    145             m_u.i = 0;
    146             m_u.rds.first = first.m_type;
    147             m_u.rds.second = second.m_type;
    148         }
    149 
    150         union {
    151             struct {
    152                 ResultType::Type first;
    153                 ResultType::Type second;
    154             } rds;
    155             int i;
    156         } m_u;
    157 
    158         ResultType first()
    159         {
    160             return ResultType(m_u.rds.first);
    161         }
    162 
    163         ResultType second()
    164         {
    165             return ResultType(m_u.rds.second);
    166         }
    167 
    168         int toInt()
    169         {
    170             return m_u.i;
    171         }
    172         static OperandTypes fromInt(int value)
    173         {
    174             OperandTypes types;
    175             types.m_u.i = value;
    176             return types;
    177         }
    178     };
    179 
    180 } // namespace JSC
    181 
    182 #endif // ResultType_h
    183