2 * Copyright (C) 2012, 2013 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 LazyOperandValueProfile_h
27 #define LazyOperandValueProfile_h
29 #include "ConcurrentJITLock.h"
30 #include "ValueProfile.h"
31 #include "VirtualRegister.h"
32 #include <wtf/HashMap.h>
33 #include <wtf/Noncopyable.h>
34 #include <wtf/SegmentedVector.h>
38 class ScriptExecutable
;
40 class LazyOperandValueProfileKey
{
42 LazyOperandValueProfileKey()
43 : m_bytecodeOffset(0) // 0 = empty value
44 , m_operand(VirtualRegister()) // not a valid operand index in our current scheme
48 LazyOperandValueProfileKey(WTF::HashTableDeletedValueType
)
49 : m_bytecodeOffset(1) // 1 = deleted value
50 , m_operand(VirtualRegister()) // not a valid operand index in our current scheme
54 LazyOperandValueProfileKey(unsigned bytecodeOffset
, VirtualRegister operand
)
55 : m_bytecodeOffset(bytecodeOffset
)
58 ASSERT(m_operand
.isValid());
61 bool operator!() const
63 return !m_operand
.isValid();
66 bool operator==(const LazyOperandValueProfileKey
& other
) const
68 return m_bytecodeOffset
== other
.m_bytecodeOffset
69 && m_operand
== other
.m_operand
;
74 return WTF::intHash(m_bytecodeOffset
) + m_operand
.offset();
77 unsigned bytecodeOffset() const
80 return m_bytecodeOffset
;
83 VirtualRegister
operand() const
89 bool isHashTableDeletedValue() const
91 return !m_operand
.isValid() && m_bytecodeOffset
;
94 unsigned m_bytecodeOffset
;
95 VirtualRegister m_operand
;
98 struct LazyOperandValueProfileKeyHash
{
99 static unsigned hash(const LazyOperandValueProfileKey
& key
) { return key
.hash(); }
101 const LazyOperandValueProfileKey
& a
,
102 const LazyOperandValueProfileKey
& b
) { return a
== b
; }
103 static const bool safeToCompareToEmptyOrDeleted
= true;
110 template<typename T
> struct DefaultHash
;
111 template<> struct DefaultHash
<JSC::LazyOperandValueProfileKey
> {
112 typedef JSC::LazyOperandValueProfileKeyHash Hash
;
115 template<typename T
> struct HashTraits
;
116 template<> struct HashTraits
<JSC::LazyOperandValueProfileKey
> : public GenericHashTraits
<JSC::LazyOperandValueProfileKey
> {
117 static void constructDeletedValue(JSC::LazyOperandValueProfileKey
& slot
) { new (NotNull
, &slot
) JSC::LazyOperandValueProfileKey(HashTableDeletedValue
); }
118 static bool isDeletedValue(const JSC::LazyOperandValueProfileKey
& value
) { return value
.isHashTableDeletedValue(); }
125 struct LazyOperandValueProfile
: public MinimalValueProfile
{
126 LazyOperandValueProfile()
127 : MinimalValueProfile()
128 , m_operand(VirtualRegister())
132 explicit LazyOperandValueProfile(const LazyOperandValueProfileKey
& key
)
133 : MinimalValueProfile(key
.bytecodeOffset())
134 , m_operand(key
.operand())
138 LazyOperandValueProfileKey
key() const
140 return LazyOperandValueProfileKey(m_bytecodeOffset
, m_operand
);
143 VirtualRegister m_operand
;
145 typedef SegmentedVector
<LazyOperandValueProfile
, 8> List
;
148 class LazyOperandValueProfileParser
;
150 class CompressedLazyOperandValueProfileHolder
{
151 WTF_MAKE_NONCOPYABLE(CompressedLazyOperandValueProfileHolder
);
153 CompressedLazyOperandValueProfileHolder();
154 ~CompressedLazyOperandValueProfileHolder();
156 void computeUpdatedPredictions(const ConcurrentJITLocker
&);
158 LazyOperandValueProfile
* add(
159 const ConcurrentJITLocker
&, const LazyOperandValueProfileKey
& key
);
162 friend class LazyOperandValueProfileParser
;
163 std::unique_ptr
<LazyOperandValueProfile::List
> m_data
;
166 class LazyOperandValueProfileParser
{
167 WTF_MAKE_NONCOPYABLE(LazyOperandValueProfileParser
);
169 explicit LazyOperandValueProfileParser();
170 ~LazyOperandValueProfileParser();
173 const ConcurrentJITLocker
&, CompressedLazyOperandValueProfileHolder
& holder
);
175 LazyOperandValueProfile
* getIfPresent(
176 const LazyOperandValueProfileKey
& key
) const;
178 SpeculatedType
prediction(
179 const ConcurrentJITLocker
&, const LazyOperandValueProfileKey
& key
) const;
181 HashMap
<LazyOperandValueProfileKey
, LazyOperandValueProfile
*> m_map
;
186 #endif // LazyOperandValueProfile_h