2 * Copyright (C) 2012, 2013, 2014 Apple Inc. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
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.
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.
26 #ifndef DFGNodeFlags_h
27 #define DFGNodeFlags_h
31 #include <wtf/PrintStream.h>
32 #include <wtf/StdLibExtras.h>
34 namespace JSC
{ namespace DFG
{
36 // Entries in the NodeType enum (below) are composed of an id, a result type (possibly none)
37 // and some additional informative flags (must generate, is constant, etc).
38 #define NodeResultMask 0x0007
39 #define NodeResultJS 0x0001
40 #define NodeResultNumber 0x0002
41 #define NodeResultDouble 0x0003
42 #define NodeResultInt32 0x0004
43 #define NodeResultInt52 0x0005
44 #define NodeResultBoolean 0x0006
45 #define NodeResultStorage 0x0007
47 #define NodeMustGenerate 0x0008 // set on nodes that have side effects, and may not trivially be removed by DCE.
48 #define NodeHasVarArgs 0x0010
49 #define NodeClobbersWorld 0x0020
50 #define NodeMightClobber 0x0040
52 #define NodeBehaviorMask 0x0780
53 #define NodeMayOverflowInBaseline 0x0080
54 #define NodeMayOverflowInDFG 0x0100
55 #define NodeMayNegZeroInBaseline 0x0200
56 #define NodeMayNegZeroInDFG 0x0400
58 #define NodeBytecodeBackPropMask 0xf800
59 #define NodeBytecodeUseBottom 0x0000
60 #define NodeBytecodeUsesAsNumber 0x0800 // The result of this computation may be used in a context that observes fractional, or bigger-than-int32, results.
61 #define NodeBytecodeNeedsNegZero 0x1000 // The result of this computation may be used in a context that observes -0.
62 #define NodeBytecodeUsesAsOther 0x2000 // The result of this computation may be used in a context that distinguishes between NaN and other things (like undefined).
63 #define NodeBytecodeUsesAsValue (NodeBytecodeUsesAsNumber | NodeBytecodeNeedsNegZero | NodeBytecodeUsesAsOther)
64 #define NodeBytecodeUsesAsInt 0x4000 // The result of this computation is known to be used in a context that prefers, but does not require, integer values.
65 #define NodeBytecodeUsesAsArrayIndex 0x8000 // The result of this computation is known to be used in a context that strongly prefers integer values, to the point that we should avoid using doubles if at all possible.
67 #define NodeArithFlagsMask (NodeBehaviorMask | NodeBytecodeBackPropMask)
69 #define NodeDoesNotExit 0x10000 // This flag is negated to make it natural for the default to be that a node does exit.
71 #define NodeRelevantToOSR 0x20000
73 #define NodeIsFlushed 0x40000 // Used by Graph::computeIsFlushed(), will tell you which local nodes are backwards-reachable from a Flush.
75 typedef uint32_t NodeFlags
;
77 static inline bool bytecodeUsesAsNumber(NodeFlags flags
)
79 return !!(flags
& NodeBytecodeUsesAsNumber
);
82 static inline bool bytecodeCanTruncateInteger(NodeFlags flags
)
84 return !bytecodeUsesAsNumber(flags
);
87 static inline bool bytecodeCanIgnoreNegativeZero(NodeFlags flags
)
89 return !(flags
& NodeBytecodeNeedsNegZero
);
92 enum RareCaseProfilingSource
{
93 BaselineRareCase
, // Comes from slow case counting in the baseline JIT.
94 DFGRareCase
, // Comes from OSR exit profiles.
98 static inline bool nodeMayOverflow(NodeFlags flags
, RareCaseProfilingSource source
)
102 case BaselineRareCase
:
103 mask
= NodeMayOverflowInBaseline
;
106 mask
= NodeMayOverflowInDFG
;
109 mask
= NodeMayOverflowInBaseline
| NodeMayOverflowInDFG
;
112 return !!(flags
& mask
);
115 static inline bool nodeMayNegZero(NodeFlags flags
, RareCaseProfilingSource source
)
119 case BaselineRareCase
:
120 mask
= NodeMayNegZeroInBaseline
;
123 mask
= NodeMayNegZeroInDFG
;
126 mask
= NodeMayNegZeroInBaseline
| NodeMayNegZeroInDFG
;
129 return !!(flags
& mask
);
132 static inline bool nodeCanSpeculateInt32(NodeFlags flags
, RareCaseProfilingSource source
)
134 if (nodeMayOverflow(flags
, source
))
135 return !bytecodeUsesAsNumber(flags
);
137 if (nodeMayNegZero(flags
, source
))
138 return bytecodeCanIgnoreNegativeZero(flags
);
143 static inline bool nodeCanSpeculateInt52(NodeFlags flags
, RareCaseProfilingSource source
)
145 if (nodeMayNegZero(flags
, source
))
146 return bytecodeCanIgnoreNegativeZero(flags
);
151 // FIXME: Get rid of this.
152 // https://bugs.webkit.org/show_bug.cgi?id=131689
153 static inline NodeFlags
canonicalResultRepresentation(NodeFlags flags
)
156 case NodeResultDouble
:
157 case NodeResultInt52
:
158 case NodeResultStorage
:
165 void dumpNodeFlags(PrintStream
&, NodeFlags
);
166 MAKE_PRINT_ADAPTOR(NodeFlagsDump
, NodeFlags
, dumpNodeFlags
);
168 } } // namespace JSC::DFG
170 #endif // ENABLE(DFG_JIT)
172 #endif // DFGNodeFlags_h