]> git.saurik.com Git - apple/javascriptcore.git/blame - runtime/PropertySlot.h
JavaScriptCore-521.tar.gz
[apple/javascriptcore.git] / runtime / PropertySlot.h
CommitLineData
9dae56ea
A
1/*
2 * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved.
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
13 *
14 * You should have received a copy of the GNU Library General Public License
15 * along with this library; see the file COPYING.LIB. If not, write to
16 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
18 *
19 */
20
21#ifndef PropertySlot_h
22#define PropertySlot_h
23
24#include "Identifier.h"
25#include "JSValue.h"
26#include "JSImmediate.h"
27#include "Register.h"
28#include <wtf/Assertions.h>
29#include <wtf/NotFound.h>
30
31namespace JSC {
32
33 class ExecState;
34 class JSObject;
35
36#define JSC_VALUE_SLOT_MARKER 0
37#define JSC_REGISTER_SLOT_MARKER reinterpret_cast<GetValueFunc>(1)
38
39 class PropertySlot {
40 public:
41 PropertySlot()
42 : m_offset(WTF::notFound)
43 {
44 clearBase();
45 clearValue();
46 }
47
48 explicit PropertySlot(const JSValuePtr base)
49 : m_slotBase(base)
50 , m_offset(WTF::notFound)
51 {
52 clearValue();
53 }
54
55 typedef JSValuePtr (*GetValueFunc)(ExecState*, const Identifier&, const PropertySlot&);
56
57 JSValuePtr getValue(ExecState* exec, const Identifier& propertyName) const
58 {
59 if (m_getValue == JSC_VALUE_SLOT_MARKER)
60 return *m_data.valueSlot;
61 if (m_getValue == JSC_REGISTER_SLOT_MARKER)
62 return (*m_data.registerSlot).jsValue(exec);
63 return m_getValue(exec, propertyName, *this);
64 }
65
66 JSValuePtr getValue(ExecState* exec, unsigned propertyName) const
67 {
68 if (m_getValue == JSC_VALUE_SLOT_MARKER)
69 return *m_data.valueSlot;
70 if (m_getValue == JSC_REGISTER_SLOT_MARKER)
71 return (*m_data.registerSlot).jsValue(exec);
72 return m_getValue(exec, Identifier::from(exec, propertyName), *this);
73 }
74
75 bool isCacheable() const { return m_offset != WTF::notFound; }
76 size_t cachedOffset() const
77 {
78 ASSERT(isCacheable());
79 return m_offset;
80 }
81
82 void putValue(JSValuePtr value)
83 {
84 if (m_getValue == JSC_VALUE_SLOT_MARKER) {
85 *m_data.valueSlot = value;
86 return;
87 }
88 ASSERT(m_getValue == JSC_REGISTER_SLOT_MARKER);
89 *m_data.registerSlot = JSValuePtr(value);
90 }
91
92 void setValueSlot(JSValuePtr* valueSlot)
93 {
94 ASSERT(valueSlot);
95 m_getValue = JSC_VALUE_SLOT_MARKER;
96 clearBase();
97 m_data.valueSlot = valueSlot;
98 }
99
100 void setValueSlot(JSValuePtr slotBase, JSValuePtr* valueSlot)
101 {
102 ASSERT(valueSlot);
103 m_getValue = JSC_VALUE_SLOT_MARKER;
104 m_slotBase = slotBase;
105 m_data.valueSlot = valueSlot;
106 }
107
108 void setValueSlot(JSValuePtr slotBase, JSValuePtr* valueSlot, size_t offset)
109 {
110 ASSERT(valueSlot);
111 m_getValue = JSC_VALUE_SLOT_MARKER;
112 m_slotBase = slotBase;
113 m_data.valueSlot = valueSlot;
114 m_offset = offset;
115 }
116
117 void setValue(JSValuePtr value)
118 {
119 ASSERT(value);
120 m_getValue = JSC_VALUE_SLOT_MARKER;
121 clearBase();
122 m_value = value;
123 m_data.valueSlot = &m_value;
124 }
125
126 void setRegisterSlot(Register* registerSlot)
127 {
128 ASSERT(registerSlot);
129 m_getValue = JSC_REGISTER_SLOT_MARKER;
130 clearBase();
131 m_data.registerSlot = registerSlot;
132 }
133
134 void setCustom(JSValuePtr slotBase, GetValueFunc getValue)
135 {
136 ASSERT(slotBase);
137 ASSERT(getValue);
138 m_getValue = getValue;
139 m_slotBase = slotBase;
140 }
141
142 void setCustomIndex(JSValuePtr slotBase, unsigned index, GetValueFunc getValue)
143 {
144 ASSERT(slotBase);
145 ASSERT(getValue);
146 m_getValue = getValue;
147 m_slotBase = slotBase;
148 m_data.index = index;
149 }
150
151 void setGetterSlot(JSObject* getterFunc)
152 {
153 ASSERT(getterFunc);
154 m_getValue = functionGetter;
155 m_data.getterFunc = getterFunc;
156 }
157
158 void setUndefined()
159 {
160 clearBase();
161 setValue(jsUndefined());
162 }
163
164 JSValuePtr slotBase() const
165 {
166 ASSERT(m_slotBase);
167 return m_slotBase;
168 }
169
170 void setBase(JSValuePtr base)
171 {
172 ASSERT(m_slotBase);
173 ASSERT(base);
174 m_slotBase = base;
175 }
176
177 void clearBase()
178 {
179#ifndef NDEBUG
180 m_slotBase = noValue();
181#endif
182 }
183
184 void clearValue()
185 {
186#ifndef NDEBUG
187 m_value = noValue();
188#endif
189 }
190
191 unsigned index() const { return m_data.index; }
192
193 private:
194 static JSValuePtr functionGetter(ExecState*, const Identifier&, const PropertySlot&);
195
196 GetValueFunc m_getValue;
197
198 JSValuePtr m_slotBase;
199 union {
200 JSObject* getterFunc;
201 JSValuePtr* valueSlot;
202 Register* registerSlot;
203 unsigned index;
204 } m_data;
205
206 JSValuePtr m_value;
207
208 size_t m_offset;
209 };
210
211} // namespace JSC
212
213#endif // PropertySlot_h