2 * Copyright (C) 2015 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.
31 #include "DFGCommon.h"
32 #include "DFGInsertionSet.h"
33 #include <wtf/PrintStream.h>
35 namespace JSC
{ namespace DFG
{
39 static const size_t jsConstantTag
= 0;
40 static const size_t doubleConstantTag
= 1;
41 static const size_t int52ConstantTag
= 2;
43 static const uintptr_t tagMask
= 0x3;
44 static const uintptr_t pointerMask
= ~tagMask
;
46 explicit LazyNode(Node
* node
= nullptr)
48 , m_value(reinterpret_cast<uintptr_t>(nullptr))
50 if (node
&& node
->isConstant())
51 setFrozenValue(node
->constant(), node
->op());
54 explicit LazyNode(FrozenValue
* value
, NodeType op
= JSConstant
)
56 , m_value(reinterpret_cast<uintptr_t>(nullptr))
58 setFrozenValue(value
, op
);
61 LazyNode(std::nullptr_t
)
63 , m_value(reinterpret_cast<uintptr_t>(nullptr))
67 LazyNode(WTF::HashTableDeletedValueType
)
68 : m_node(reinterpret_cast<Node
*>(-1))
72 void setNode(Node
* node
)
75 if (node
&& node
->isConstant())
76 setFrozenValue(node
->constant(), node
->op());
79 bool isHashTableDeletedValue() const { return m_node
== reinterpret_cast<Node
*>(-1); }
81 bool isNode() const { return m_node
; }
88 switch (m_value
& tagMask
) {
91 case doubleConstantTag
:
92 return DoubleConstant
;
93 case int52ConstantTag
:
96 RELEASE_ASSERT_NOT_REACHED();
102 ASSERT(m_node
|| !asValue());
106 FrozenValue
* asValue() const
108 return reinterpret_cast<FrozenValue
*>(m_value
& pointerMask
);
111 unsigned hash() const
114 return WTF::PtrHash
<FrozenValue
*>::hash(asValue());
115 return WTF::PtrHash
<Node
*>::hash(m_node
);
118 bool operator==(const LazyNode
& other
) const
120 if (asValue() || other
.asValue())
121 return m_value
== other
.m_value
;
122 return m_node
== other
.m_node
;
125 bool operator!=(const LazyNode
& other
) const
127 return !(*this == other
);
130 Node
* ensureIsNode(InsertionSet
& insertionSet
, BasicBlock
* block
, unsigned nodeIndex
)
133 m_node
= insertionSet
.insertConstant(nodeIndex
, block
->at(nodeIndex
)->origin
, asValue(), op());
138 Node
* operator->() const { return asNode(); }
140 Node
& operator*() const { return *asNode(); }
142 bool operator!() const { return !asValue() && !asNode(); }
144 explicit operator bool() const { return !!*this; }
146 void dump(PrintStream
& out
) const;
149 void setFrozenValue(FrozenValue
* value
, NodeType op
)
152 m_value
= reinterpret_cast<uintptr_t>(value
);
153 ASSERT(m_value
== (m_value
& pointerMask
));
156 m_value
|= jsConstantTag
;
159 m_value
|= doubleConstantTag
;
162 m_value
|= int52ConstantTag
;
165 RELEASE_ASSERT_NOT_REACHED();
174 } } // namespace JSC::DFG
178 template<typename T
> struct HashTraits
;
179 template<> struct HashTraits
<JSC::DFG::LazyNode
> : SimpleClassHashTraits
<JSC::DFG::LazyNode
> {
180 static const bool emptyValueIsZero
= true;
185 #endif // ENABLE(DFG_JIT)
187 #endif // DFGLazyNode_h