File indexing completed on 2024-05-12 15:43:31

0001 /*
0002  *  This file is part of the KDE libraries
0003  *  Copyright (C) 1999-2000 Harri Porten (porten@kde.org)
0004  *
0005  *  This library is free software; you can redistribute it and/or
0006  *  modify it under the terms of the GNU Library General Public
0007  *  License as published by the Free Software Foundation; either
0008  *  version 2 of the License, or (at your option) any later version.
0009  *
0010  *  This library is distributed in the hope that it will be useful,
0011  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
0012  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0013  *  Library General Public License for more details.
0014  *
0015  *  You should have received a copy of the GNU Library General Public License
0016  *  along with this library; see the file COPYING.LIB.  If not, write to
0017  *  the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
0018  *  Boston, MA 02110-1301, USA.
0019  *
0020  */
0021 
0022 #ifndef _KJS_OPERATIONS_H_
0023 #define _KJS_OPERATIONS_H_
0024 
0025 #include "global.h"
0026 #include <math.h>
0027 #include <cmath>
0028 #include <stdio.h>
0029 #include <wtf/MathExtras.h>
0030 
0031 #if HAVE(IEEEFP_H)
0032 #   if HAVE(FUNC_ISINF) || HAVE(FUNC_FINITE)
0033 #       include <ieeefp.h>
0034 #   endif
0035 #endif
0036 
0037 #if HAVE(FLOAT_H)
0038 #   include <float.h>
0039 #endif
0040 
0041 namespace KJS
0042 {
0043 
0044 class ExecState;
0045 class JSValue;
0046 
0047 enum Operator { OpEqual,
0048                 OpEqEq,
0049                 OpPlus,
0050                 OpMinus,
0051                 OpMult,
0052                 OpDiv,
0053                 OpMod,
0054                 OpExp,
0055                 OpNotEq,
0056                 OpStrEq,
0057                 OpStrNEq,
0058                 OpPlusEq,
0059                 OpMinusEq,
0060                 OpMultEq,
0061                 OpDivEq,
0062                 OpExpEq,
0063                 OpPlusPlus,
0064                 OpMinusMinus,
0065                 OpLess,
0066                 OpLessEq,
0067                 OpGreater,
0068                 OpGreaterEq,
0069                 OpAndEq,
0070                 OpXOrEq,
0071                 OpOrEq,
0072                 OpModEq,
0073                 OpAnd,
0074                 OpOr,
0075                 OpBitAnd,
0076                 OpBitXOr,
0077                 OpBitOr,
0078                 OpLShift,
0079                 OpRShift,
0080                 OpURShift,
0081                 OpIn,
0082                 OpInstanceOf
0083               };
0084 
0085 inline bool isNaN(double d);
0086 inline bool isFinite(double d);
0087 inline bool isInf(double d);
0088 inline double signBit(double d);
0089 inline bool isPosInf(double d);
0090 inline bool isNegInf(double d);
0091 
0092 inline int clz32(unsigned int d)
0093 {
0094 #if HAVE(FUNC_BUILTIN_CLZ)
0095     //NOTE: __builtin_clz(0); is undefined
0096     //buschinski: and returns 1 for me, for whatever reason
0097     if (d == 0)
0098         return 32;
0099     return __builtin_clz(d);
0100 #else
0101     int count = 0;
0102     while (d != 0)
0103     {
0104         ++count;
0105         d >>= 1;
0106     }
0107     return 32 - count;
0108 #endif
0109 }
0110 
0111 inline bool isNaN(double d)
0112 {
0113 #if HAVE(FUNC_STD_ISNAN)
0114     return std::isnan(d);
0115 #elif HAVE(FUNC_ISNAN)
0116     return isnan(d) != 0;
0117 #elif HAVE(FLOAT_H)
0118     return _isnan(d) != 0;
0119 #else
0120     return !(d == d);
0121 #endif
0122 }
0123 
0124 inline bool isFinite(double d)
0125 {
0126 #if HAVE(FUNC_STD_ISFINITE)
0127     return std::isfinite(d) != 0;
0128 #elif HAVE(FUNC_FINITE)
0129     return finite(d) != 0;
0130 #elif HAVE(FUNC__FINITE)
0131     return _finite(d) != 0;
0132 #else
0133     return !isNaN(d) && !isInf(d);
0134 #endif
0135 }
0136 
0137 inline bool isInf(double d)
0138 {
0139 #if HAVE(FUNC_STD_ISINF)
0140     return std::isinf(d);
0141 #elif HAVE(FUNC_ISINF)
0142     return isinf(d);
0143 #elif HAVE(FUNC_FINITE)
0144     return finite(d) == 0 && d == d;
0145 #elif HAVE(FUNC__FINITE)
0146     return _finite(d) == 0 && d == d;
0147 #elif HAVE(FUNC__FPCLASS)
0148     int fpClass = _fpclass(d);
0149     return _FPCLASS_PINF == fpClass || _FPCLASS_NINF == fpClass;
0150 #else
0151 # error "Your platform does not provide a Infinity checking function."
0152     return false;
0153 #endif
0154 }
0155 
0156 inline double signBit(double d)
0157 {
0158 #if HAVE(FUNC_STD_SIGNBIT)
0159     return std::signbit(d);
0160 #elif HAVE(FUNC_SIGNBIT)
0161     return signbit(d);
0162 #elif HAVE(FUNC___SIGNBIT)
0163     return __signbit(d);
0164 #elif HAVE(FUNC__COPYSIGN)
0165     return _copysign(1.0, d) < 0 ? 1.0 : 0.0;
0166 #elif HAVE(FUNC_COPYSIGN)
0167     return copysign(1.0, d) < 0 ? 1.0 : 0.0;
0168 #else
0169 # error "Your platform does not provide a signbit/copysign function."
0170     return false;
0171 #endif
0172 }
0173 
0174 inline bool isPosInf(double d)
0175 {
0176 #if HAVE(FPCLASS)
0177     return _FPCLASS_PINF == _fpclass(d);
0178 #else
0179     return isInf(d) && !signBit(d);
0180 #endif
0181 }
0182 
0183 inline bool isNegInf(double d)
0184 {
0185 #if HAVE(FUNC_FPCLASS)
0186     return _FPCLASS_PINF == _fpclass(d);
0187 #else
0188     return isInf(d) && signBit(d);
0189 #endif
0190 }
0191 
0192 bool equal(ExecState *exec, JSValue *v1, JSValue *v2);
0193 bool strictEqual(ExecState *exec, JSValue *v1, JSValue *v2);
0194 // Same as strictEqual, except for "-0" and "0" difference.
0195 // Used in PropertyDescriptor::equalTo and Object::defineOwnProperty to check
0196 // if the value changed and we need to update.
0197 bool sameValue(ExecState *exec, JSValue *v1, JSValue *v2);
0198 /**
0199  * This operator performs an abstract relational comparison of the two
0200  * arguments that can be of arbitrary type. If possible, conversions to the
0201  * string or number type will take place before the comparison.
0202  *
0203  * @return 1 if v1 is "less-than" v2, 0 if the relation is "greater-than-or-
0204  * equal". -1 if the result is undefined.
0205  */
0206 int relation(ExecState *exec, JSValue *v1, JSValue *v2, bool leftFirst = true);
0207 int relation(ExecState *exec, JSValue *v1, double n2);
0208 int maxInt(int d1, int d2);
0209 int minInt(int d1, int d2);
0210 
0211 // differs from standard C libraries pow() functions in a couple of
0212 // aspects
0213 double exponentiation(double base, double exponent);
0214 
0215 }
0216 
0217 #endif