|
1 // -*- c-basic-offset: 2 -*- |
|
2 /* |
|
3 * This file is part of the KDE libraries |
|
4 * Copyright (C) 1999-2000 Harri Porten (porten@kde.org) |
|
5 * Copyright (C) 2001 Peter Kelly (pmk@post.com) |
|
6 * Copyright (C) 2003, 2004, 2005, 2006, 2007 Apple Inc. All rights reserved. |
|
7 * |
|
8 * This library is free software; you can redistribute it and/or |
|
9 * modify it under the terms of the GNU Library General Public |
|
10 * License as published by the Free Software Foundation; either |
|
11 * version 2 of the License, or (at your option) any later version. |
|
12 * |
|
13 * This library is distributed in the hope that it will be useful, |
|
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
|
16 * Library General Public License for more details. |
|
17 * |
|
18 * You should have received a copy of the GNU Library General Public License |
|
19 * along with this library; see the file COPYING.LIB. If not, write to |
|
20 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, |
|
21 * Boston, MA 02110-1301, USA. |
|
22 * |
|
23 */ |
|
24 |
|
25 #ifndef NODES_H_ |
|
26 #define NODES_H_ |
|
27 |
|
28 #include "Parser.h" |
|
29 #include "internal.h" |
|
30 #include <wtf/ListRefPtr.h> |
|
31 #include <wtf/Vector.h> |
|
32 |
|
33 #if PLATFORM(X86) && COMPILER(GCC) |
|
34 #define KJS_FAST_CALL __attribute__((regparm(3))) |
|
35 #else |
|
36 #define KJS_FAST_CALL |
|
37 #endif |
|
38 |
|
39 #if COMPILER(GCC) |
|
40 #define KJS_NO_INLINE __attribute__((noinline)) |
|
41 #else |
|
42 #define KJS_NO_INLINE |
|
43 #endif |
|
44 |
|
45 namespace KJS { |
|
46 |
|
47 class ProgramNode; |
|
48 class PropertyNameNode; |
|
49 class PropertyListNode; |
|
50 class RegExp; |
|
51 class SourceElementsNode; |
|
52 class SourceStream; |
|
53 |
|
54 enum Operator { OpEqual, |
|
55 OpEqEq, |
|
56 OpNotEq, |
|
57 OpStrEq, |
|
58 OpStrNEq, |
|
59 OpPlusEq, |
|
60 OpMinusEq, |
|
61 OpMultEq, |
|
62 OpDivEq, |
|
63 OpPlusPlus, |
|
64 OpMinusMinus, |
|
65 OpLess, |
|
66 OpLessEq, |
|
67 OpGreater, |
|
68 OpGreaterEq, |
|
69 OpAndEq, |
|
70 OpXOrEq, |
|
71 OpOrEq, |
|
72 OpModEq, |
|
73 OpAnd, |
|
74 OpOr, |
|
75 OpBitAnd, |
|
76 OpBitXOr, |
|
77 OpBitOr, |
|
78 OpLShift, |
|
79 OpRShift, |
|
80 OpURShift, |
|
81 OpIn, |
|
82 OpInstanceOf |
|
83 }; |
|
84 |
|
85 class Node { |
|
86 public: |
|
87 Node() KJS_FAST_CALL; |
|
88 virtual ~Node(); |
|
89 |
|
90 virtual JSValue *evaluate(ExecState *exec) KJS_FAST_CALL = 0; |
|
91 UString toString() const KJS_FAST_CALL; |
|
92 virtual void streamTo(SourceStream&) const KJS_FAST_CALL = 0; |
|
93 virtual void processVarDecls(ExecState*) KJS_FAST_CALL {} |
|
94 int lineNo() const KJS_FAST_CALL { return m_line; } |
|
95 |
|
96 void ref() KJS_FAST_CALL; |
|
97 void deref() KJS_FAST_CALL; |
|
98 unsigned refcount() KJS_FAST_CALL; |
|
99 static void clearNewNodes() KJS_FAST_CALL; |
|
100 |
|
101 virtual Node *nodeInsideAllParens() KJS_FAST_CALL; |
|
102 |
|
103 virtual bool isLocation() const KJS_FAST_CALL { return false; } |
|
104 virtual bool isResolveNode() const KJS_FAST_CALL { return false; } |
|
105 virtual bool isBracketAccessorNode() const KJS_FAST_CALL { return false; } |
|
106 virtual bool isDotAccessorNode() const KJS_FAST_CALL { return false; } |
|
107 virtual bool isGroupNode() const KJS_FAST_CALL { return false; } |
|
108 |
|
109 virtual void breakCycle() KJS_FAST_CALL { } |
|
110 |
|
111 protected: |
|
112 Completion createErrorCompletion(ExecState *, ErrorType, const char *msg) KJS_FAST_CALL; |
|
113 Completion createErrorCompletion(ExecState *, ErrorType, const char *msg, const Identifier &) KJS_FAST_CALL; |
|
114 |
|
115 JSValue *throwError(ExecState *, ErrorType, const char *msg) KJS_FAST_CALL; |
|
116 JSValue* throwError(ExecState *, ErrorType, const char* msg, const char*) KJS_FAST_CALL; |
|
117 JSValue *throwError(ExecState *, ErrorType, const char *msg, JSValue *, Node *) KJS_FAST_CALL; |
|
118 JSValue *throwError(ExecState *, ErrorType, const char *msg, const Identifier &) KJS_FAST_CALL; |
|
119 JSValue *throwError(ExecState *, ErrorType, const char *msg, JSValue *, const Identifier &) KJS_FAST_CALL; |
|
120 JSValue *throwError(ExecState *, ErrorType, const char *msg, JSValue *, Node *, Node *) KJS_FAST_CALL; |
|
121 JSValue *throwError(ExecState *, ErrorType, const char *msg, JSValue *, Node *, const Identifier &) KJS_FAST_CALL; |
|
122 |
|
123 JSValue *throwUndefinedVariableError(ExecState *, const Identifier &) KJS_FAST_CALL; |
|
124 |
|
125 void handleException(ExecState*) KJS_FAST_CALL; |
|
126 void handleException(ExecState*, JSValue*) KJS_FAST_CALL; |
|
127 |
|
128 int m_line; |
|
129 private: |
|
130 // disallow assignment |
|
131 Node& operator=(const Node&) KJS_FAST_CALL; |
|
132 Node(const Node &other) KJS_FAST_CALL; |
|
133 }; |
|
134 |
|
135 class StatementNode : public Node { |
|
136 public: |
|
137 StatementNode() KJS_FAST_CALL; |
|
138 void setLoc(int line0, int line1) KJS_FAST_CALL; |
|
139 int firstLine() const KJS_FAST_CALL { return lineNo(); } |
|
140 int lastLine() const KJS_FAST_CALL { return m_lastLine; } |
|
141 bool hitStatement(ExecState*) KJS_FAST_CALL; |
|
142 virtual Completion execute(ExecState *exec) KJS_FAST_CALL = 0; |
|
143 void pushLabel(const Identifier &id) KJS_FAST_CALL { ls.push(id); } |
|
144 virtual void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
145 protected: |
|
146 LabelStack ls; |
|
147 private: |
|
148 JSValue *evaluate(ExecState*) KJS_FAST_CALL { return jsUndefined(); } |
|
149 int m_lastLine; |
|
150 }; |
|
151 |
|
152 class NullNode : public Node { |
|
153 public: |
|
154 NullNode() KJS_FAST_CALL {} |
|
155 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
156 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
157 }; |
|
158 |
|
159 class BooleanNode : public Node { |
|
160 public: |
|
161 BooleanNode(bool v) KJS_FAST_CALL : value(v) {} |
|
162 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
163 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
164 private: |
|
165 bool value; |
|
166 }; |
|
167 |
|
168 class NumberNode : public Node { |
|
169 public: |
|
170 NumberNode(double v) KJS_FAST_CALL : value(v) {} |
|
171 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
172 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
173 private: |
|
174 double value; |
|
175 }; |
|
176 |
|
177 class StringNode : public Node { |
|
178 public: |
|
179 StringNode(const UString *v) KJS_FAST_CALL { value = *v; } |
|
180 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
181 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
182 private: |
|
183 UString value; |
|
184 }; |
|
185 |
|
186 class RegExpNode : public Node { |
|
187 public: |
|
188 RegExpNode(const UString &p, const UString &f) KJS_FAST_CALL |
|
189 : pattern(p), flags(f) { } |
|
190 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
191 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
192 private: |
|
193 UString pattern, flags; |
|
194 }; |
|
195 |
|
196 class ThisNode : public Node { |
|
197 public: |
|
198 ThisNode() KJS_FAST_CALL {} |
|
199 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
200 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
201 }; |
|
202 |
|
203 class ResolveNode : public Node { |
|
204 public: |
|
205 ResolveNode(const Identifier &s) KJS_FAST_CALL : ident(s) { } |
|
206 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
207 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
208 |
|
209 virtual bool isLocation() const KJS_FAST_CALL { return true; } |
|
210 virtual bool isResolveNode() const KJS_FAST_CALL { return true; } |
|
211 const Identifier& identifier() const KJS_FAST_CALL { return ident; } |
|
212 |
|
213 private: |
|
214 Identifier ident; |
|
215 }; |
|
216 |
|
217 class GroupNode : public Node { |
|
218 public: |
|
219 GroupNode(Node *g) KJS_FAST_CALL : group(g) { } |
|
220 virtual JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
221 virtual Node *nodeInsideAllParens() KJS_FAST_CALL; |
|
222 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
223 virtual bool isGroupNode() const KJS_FAST_CALL { return true; } |
|
224 private: |
|
225 RefPtr<Node> group; |
|
226 }; |
|
227 |
|
228 class ElementNode : public Node { |
|
229 public: |
|
230 // list pointer is tail of a circular list, cracked in the ArrayNode ctor |
|
231 ElementNode(int e, Node *n) KJS_FAST_CALL : next(this), elision(e), node(n) { Parser::noteNodeCycle(this); } |
|
232 ElementNode(ElementNode *l, int e, Node *n) KJS_FAST_CALL |
|
233 : next(l->next), elision(e), node(n) { l->next = this; } |
|
234 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
235 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
236 PassRefPtr<ElementNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
237 virtual void breakCycle() KJS_FAST_CALL; |
|
238 private: |
|
239 friend class ArrayNode; |
|
240 ListRefPtr<ElementNode> next; |
|
241 int elision; |
|
242 RefPtr<Node> node; |
|
243 }; |
|
244 |
|
245 class ArrayNode : public Node { |
|
246 public: |
|
247 ArrayNode(int e) KJS_FAST_CALL : elision(e), opt(true) { } |
|
248 ArrayNode(ElementNode *ele) KJS_FAST_CALL |
|
249 : element(ele->next.release()), elision(0), opt(false) { Parser::removeNodeCycle(element.get()); } |
|
250 ArrayNode(int eli, ElementNode *ele) KJS_FAST_CALL |
|
251 : element(ele->next.release()), elision(eli), opt(true) { Parser::removeNodeCycle(element.get()); } |
|
252 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
253 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
254 private: |
|
255 RefPtr<ElementNode> element; |
|
256 int elision; |
|
257 bool opt; |
|
258 }; |
|
259 |
|
260 class PropertyNameNode : public Node { |
|
261 public: |
|
262 PropertyNameNode(double d) KJS_FAST_CALL : numeric(d) { } |
|
263 PropertyNameNode(const Identifier &s) KJS_FAST_CALL : str(s) { } |
|
264 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
265 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
266 private: |
|
267 double numeric; |
|
268 Identifier str; |
|
269 }; |
|
270 |
|
271 class PropertyNode : public Node { |
|
272 public: |
|
273 enum Type { Constant, Getter, Setter }; |
|
274 PropertyNode(PropertyNameNode *n, Node *a, Type t) KJS_FAST_CALL |
|
275 : name(n), assign(a), type(t) { } |
|
276 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
277 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
278 friend class PropertyListNode; |
|
279 private: |
|
280 RefPtr<PropertyNameNode> name; |
|
281 RefPtr<Node> assign; |
|
282 Type type; |
|
283 }; |
|
284 |
|
285 class PropertyListNode : public Node { |
|
286 public: |
|
287 // list pointer is tail of a circular list, cracked in the ObjectLiteralNode ctor |
|
288 PropertyListNode(PropertyNode *n) KJS_FAST_CALL |
|
289 : node(n), next(this) { Parser::noteNodeCycle(this); } |
|
290 PropertyListNode(PropertyNode *n, PropertyListNode *l) KJS_FAST_CALL |
|
291 : node(n), next(l->next) { l->next = this; } |
|
292 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
293 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
294 PassRefPtr<PropertyListNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
295 virtual void breakCycle() KJS_FAST_CALL; |
|
296 private: |
|
297 friend class ObjectLiteralNode; |
|
298 RefPtr<PropertyNode> node; |
|
299 ListRefPtr<PropertyListNode> next; |
|
300 }; |
|
301 |
|
302 class ObjectLiteralNode : public Node { |
|
303 public: |
|
304 ObjectLiteralNode() KJS_FAST_CALL { } |
|
305 ObjectLiteralNode(PropertyListNode *l) KJS_FAST_CALL : list(l->next.release()) { Parser::removeNodeCycle(list.get()); } |
|
306 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
307 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
308 private: |
|
309 RefPtr<PropertyListNode> list; |
|
310 }; |
|
311 |
|
312 class BracketAccessorNode : public Node { |
|
313 public: |
|
314 BracketAccessorNode(Node *e1, Node *e2) KJS_FAST_CALL : expr1(e1), expr2(e2) {} |
|
315 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
316 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
317 |
|
318 virtual bool isLocation() const KJS_FAST_CALL { return true; } |
|
319 virtual bool isBracketAccessorNode() const KJS_FAST_CALL { return true; } |
|
320 Node *base() KJS_FAST_CALL { return expr1.get(); } |
|
321 Node *subscript() KJS_FAST_CALL { return expr2.get(); } |
|
322 |
|
323 private: |
|
324 RefPtr<Node> expr1; |
|
325 RefPtr<Node> expr2; |
|
326 }; |
|
327 |
|
328 class DotAccessorNode : public Node { |
|
329 public: |
|
330 DotAccessorNode(Node *e, const Identifier &s) KJS_FAST_CALL : expr(e), ident(s) { } |
|
331 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
332 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
333 |
|
334 virtual bool isLocation() const KJS_FAST_CALL { return true; } |
|
335 virtual bool isDotAccessorNode() const KJS_FAST_CALL { return true; } |
|
336 Node *base() const KJS_FAST_CALL { return expr.get(); } |
|
337 const Identifier& identifier() const KJS_FAST_CALL { return ident; } |
|
338 |
|
339 private: |
|
340 RefPtr<Node> expr; |
|
341 Identifier ident; |
|
342 }; |
|
343 |
|
344 class ArgumentListNode : public Node { |
|
345 public: |
|
346 // list pointer is tail of a circular list, cracked in the ArgumentsNode ctor |
|
347 ArgumentListNode(Node *e) KJS_FAST_CALL : next(this), expr(e) { Parser::noteNodeCycle(this); } |
|
348 ArgumentListNode(ArgumentListNode *l, Node *e) KJS_FAST_CALL |
|
349 : next(l->next), expr(e) { l->next = this; } |
|
350 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
351 List evaluateList(ExecState*) KJS_FAST_CALL; |
|
352 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
353 PassRefPtr<ArgumentListNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
354 virtual void breakCycle() KJS_FAST_CALL; |
|
355 private: |
|
356 friend class ArgumentsNode; |
|
357 ListRefPtr<ArgumentListNode> next; |
|
358 RefPtr<Node> expr; |
|
359 }; |
|
360 |
|
361 class ArgumentsNode : public Node { |
|
362 public: |
|
363 ArgumentsNode() KJS_FAST_CALL { } |
|
364 ArgumentsNode(ArgumentListNode *l) KJS_FAST_CALL |
|
365 : list(l->next.release()) { Parser::removeNodeCycle(list.get()); } |
|
366 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
367 List evaluateList(ExecState *exec) KJS_FAST_CALL { return list ? list->evaluateList(exec) : List(); } |
|
368 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
369 private: |
|
370 RefPtr<ArgumentListNode> list; |
|
371 }; |
|
372 |
|
373 class NewExprNode : public Node { |
|
374 public: |
|
375 NewExprNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
376 NewExprNode(Node *e, ArgumentsNode *a) KJS_FAST_CALL : expr(e), args(a) {} |
|
377 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
378 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
379 private: |
|
380 RefPtr<Node> expr; |
|
381 RefPtr<ArgumentsNode> args; |
|
382 }; |
|
383 |
|
384 class FunctionCallValueNode : public Node { |
|
385 public: |
|
386 FunctionCallValueNode(Node *e, ArgumentsNode *a) KJS_FAST_CALL : expr(e), args(a) {} |
|
387 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
388 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
389 private: |
|
390 RefPtr<Node> expr; |
|
391 RefPtr<ArgumentsNode> args; |
|
392 }; |
|
393 |
|
394 class FunctionCallResolveNode : public Node { |
|
395 public: |
|
396 FunctionCallResolveNode(const Identifier& i, ArgumentsNode *a) KJS_FAST_CALL : ident(i), args(a) {} |
|
397 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
398 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
399 private: |
|
400 Identifier ident; |
|
401 RefPtr<ArgumentsNode> args; |
|
402 }; |
|
403 |
|
404 class FunctionCallBracketNode : public Node { |
|
405 public: |
|
406 FunctionCallBracketNode(Node *b, Node *s, ArgumentsNode *a) KJS_FAST_CALL : base(b), subscript(s), args(a) {} |
|
407 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
408 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
409 protected: |
|
410 RefPtr<Node> base; |
|
411 RefPtr<Node> subscript; |
|
412 RefPtr<ArgumentsNode> args; |
|
413 }; |
|
414 |
|
415 class FunctionCallParenBracketNode : public FunctionCallBracketNode { |
|
416 public: |
|
417 FunctionCallParenBracketNode(Node *b, Node *s, ArgumentsNode *a) KJS_FAST_CALL : FunctionCallBracketNode(b, s, a) {} |
|
418 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
419 }; |
|
420 |
|
421 class FunctionCallDotNode : public Node { |
|
422 public: |
|
423 FunctionCallDotNode(Node *b, const Identifier &i, ArgumentsNode *a) KJS_FAST_CALL : base(b), ident(i), args(a) {} |
|
424 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
425 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
426 protected: |
|
427 RefPtr<Node> base; |
|
428 Identifier ident; |
|
429 RefPtr<ArgumentsNode> args; |
|
430 }; |
|
431 |
|
432 class FunctionCallParenDotNode : public FunctionCallDotNode { |
|
433 public: |
|
434 FunctionCallParenDotNode(Node *b, const Identifier &i, ArgumentsNode *a) KJS_FAST_CALL : FunctionCallDotNode(b, i, a) {} |
|
435 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
436 }; |
|
437 |
|
438 class PostfixResolveNode : public Node { |
|
439 public: |
|
440 PostfixResolveNode(const Identifier& i, Operator o) KJS_FAST_CALL : m_ident(i), m_oper(o) {} |
|
441 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
442 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
443 private: |
|
444 Identifier m_ident; |
|
445 Operator m_oper; |
|
446 }; |
|
447 |
|
448 class PostfixBracketNode : public Node { |
|
449 public: |
|
450 PostfixBracketNode(Node *b, Node *s, Operator o) KJS_FAST_CALL : m_base(b), m_subscript(s), m_oper(o) {} |
|
451 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
452 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
453 private: |
|
454 RefPtr<Node> m_base; |
|
455 RefPtr<Node> m_subscript; |
|
456 Operator m_oper; |
|
457 }; |
|
458 |
|
459 class PostfixDotNode : public Node { |
|
460 public: |
|
461 PostfixDotNode(Node *b, const Identifier& i, Operator o) KJS_FAST_CALL : m_base(b), m_ident(i), m_oper(o) {} |
|
462 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
463 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
464 private: |
|
465 RefPtr<Node> m_base; |
|
466 Identifier m_ident; |
|
467 Operator m_oper; |
|
468 }; |
|
469 |
|
470 class PostfixErrorNode : public Node { |
|
471 public: |
|
472 PostfixErrorNode(Node* e, Operator o) KJS_FAST_CALL : m_expr(e), m_oper(o) {} |
|
473 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
474 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
475 private: |
|
476 RefPtr<Node> m_expr; |
|
477 Operator m_oper; |
|
478 }; |
|
479 |
|
480 class DeleteResolveNode : public Node { |
|
481 public: |
|
482 DeleteResolveNode(const Identifier& i) KJS_FAST_CALL : m_ident(i) {} |
|
483 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
484 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
485 private: |
|
486 Identifier m_ident; |
|
487 }; |
|
488 |
|
489 class DeleteBracketNode : public Node { |
|
490 public: |
|
491 DeleteBracketNode(Node *base, Node *subscript) KJS_FAST_CALL : m_base(base), m_subscript(subscript) {} |
|
492 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
493 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
494 private: |
|
495 RefPtr<Node> m_base; |
|
496 RefPtr<Node> m_subscript; |
|
497 }; |
|
498 |
|
499 class DeleteDotNode : public Node { |
|
500 public: |
|
501 DeleteDotNode(Node *base, const Identifier& i) KJS_FAST_CALL : m_base(base), m_ident(i) {} |
|
502 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
503 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
504 private: |
|
505 RefPtr<Node> m_base; |
|
506 Identifier m_ident; |
|
507 }; |
|
508 |
|
509 class DeleteValueNode : public Node { |
|
510 public: |
|
511 DeleteValueNode(Node *e) KJS_FAST_CALL : m_expr(e) {} |
|
512 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
513 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
514 private: |
|
515 RefPtr<Node> m_expr; |
|
516 }; |
|
517 |
|
518 class VoidNode : public Node { |
|
519 public: |
|
520 VoidNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
521 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
522 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
523 private: |
|
524 RefPtr<Node> expr; |
|
525 }; |
|
526 |
|
527 class TypeOfResolveNode : public Node { |
|
528 public: |
|
529 TypeOfResolveNode(const Identifier& i) KJS_FAST_CALL : m_ident(i) {} |
|
530 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
531 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
532 private: |
|
533 Identifier m_ident; |
|
534 }; |
|
535 |
|
536 class TypeOfValueNode : public Node { |
|
537 public: |
|
538 TypeOfValueNode(Node *e) KJS_FAST_CALL : m_expr(e) {} |
|
539 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
540 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
541 private: |
|
542 RefPtr<Node> m_expr; |
|
543 }; |
|
544 |
|
545 class PrefixResolveNode : public Node { |
|
546 public: |
|
547 PrefixResolveNode(const Identifier& i, Operator o) KJS_FAST_CALL : m_ident(i), m_oper(o) {} |
|
548 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
549 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
550 private: |
|
551 Identifier m_ident; |
|
552 Operator m_oper; |
|
553 }; |
|
554 |
|
555 class PrefixBracketNode : public Node { |
|
556 public: |
|
557 PrefixBracketNode(Node *b, Node *s, Operator o) KJS_FAST_CALL : m_base(b), m_subscript(s), m_oper(o) {} |
|
558 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
559 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
560 private: |
|
561 RefPtr<Node> m_base; |
|
562 RefPtr<Node> m_subscript; |
|
563 Operator m_oper; |
|
564 }; |
|
565 |
|
566 class PrefixDotNode : public Node { |
|
567 public: |
|
568 PrefixDotNode(Node *b, const Identifier& i, Operator o) KJS_FAST_CALL : m_base(b), m_ident(i), m_oper(o) {} |
|
569 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
570 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
571 private: |
|
572 RefPtr<Node> m_base; |
|
573 Identifier m_ident; |
|
574 Operator m_oper; |
|
575 }; |
|
576 |
|
577 class PrefixErrorNode : public Node { |
|
578 public: |
|
579 PrefixErrorNode(Node* e, Operator o) KJS_FAST_CALL : m_expr(e), m_oper(o) {} |
|
580 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
581 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
582 private: |
|
583 RefPtr<Node> m_expr; |
|
584 Operator m_oper; |
|
585 }; |
|
586 |
|
587 class UnaryPlusNode : public Node { |
|
588 public: |
|
589 UnaryPlusNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
590 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
591 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
592 private: |
|
593 RefPtr<Node> expr; |
|
594 }; |
|
595 |
|
596 class NegateNode : public Node { |
|
597 public: |
|
598 NegateNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
599 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
600 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
601 private: |
|
602 RefPtr<Node> expr; |
|
603 }; |
|
604 |
|
605 class BitwiseNotNode : public Node { |
|
606 public: |
|
607 BitwiseNotNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
608 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
609 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
610 private: |
|
611 RefPtr<Node> expr; |
|
612 }; |
|
613 |
|
614 class LogicalNotNode : public Node { |
|
615 public: |
|
616 LogicalNotNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
617 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
618 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
619 private: |
|
620 RefPtr<Node> expr; |
|
621 }; |
|
622 |
|
623 class MultNode : public Node { |
|
624 public: |
|
625 MultNode(Node *t1, Node *t2, char op) KJS_FAST_CALL : term1(t1), term2(t2), oper(op) {} |
|
626 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
627 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
628 private: |
|
629 RefPtr<Node> term1; |
|
630 RefPtr<Node> term2; |
|
631 char oper; |
|
632 }; |
|
633 |
|
634 class AddNode : public Node { |
|
635 public: |
|
636 AddNode(Node *t1, Node *t2, char op) KJS_FAST_CALL : term1(t1), term2(t2), oper(op) {} |
|
637 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
638 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
639 private: |
|
640 RefPtr<Node> term1; |
|
641 RefPtr<Node> term2; |
|
642 char oper; |
|
643 }; |
|
644 |
|
645 class ShiftNode : public Node { |
|
646 public: |
|
647 ShiftNode(Node *t1, Operator o, Node *t2) KJS_FAST_CALL |
|
648 : term1(t1), term2(t2), oper(o) {} |
|
649 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
650 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
651 private: |
|
652 RefPtr<Node> term1; |
|
653 RefPtr<Node> term2; |
|
654 Operator oper; |
|
655 }; |
|
656 |
|
657 class RelationalNode : public Node { |
|
658 public: |
|
659 RelationalNode(Node *e1, Operator o, Node *e2) KJS_FAST_CALL : |
|
660 expr1(e1), expr2(e2), oper(o) {} |
|
661 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
662 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
663 private: |
|
664 RefPtr<Node> expr1; |
|
665 RefPtr<Node> expr2; |
|
666 Operator oper; |
|
667 }; |
|
668 |
|
669 class EqualNode : public Node { |
|
670 public: |
|
671 EqualNode(Node *e1, Operator o, Node *e2) KJS_FAST_CALL |
|
672 : expr1(e1), expr2(e2), oper(o) {} |
|
673 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
674 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
675 private: |
|
676 RefPtr<Node> expr1; |
|
677 RefPtr<Node> expr2; |
|
678 Operator oper; |
|
679 }; |
|
680 |
|
681 class BitOperNode : public Node { |
|
682 public: |
|
683 BitOperNode(Node *e1, Operator o, Node *e2) KJS_FAST_CALL : |
|
684 expr1(e1), expr2(e2), oper(o) {} |
|
685 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
686 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
687 private: |
|
688 RefPtr<Node> expr1; |
|
689 RefPtr<Node> expr2; |
|
690 Operator oper; |
|
691 }; |
|
692 |
|
693 /** |
|
694 * expr1 && expr2, expr1 || expr2 |
|
695 */ |
|
696 class BinaryLogicalNode : public Node { |
|
697 public: |
|
698 BinaryLogicalNode(Node *e1, Operator o, Node *e2) KJS_FAST_CALL : |
|
699 expr1(e1), expr2(e2), oper(o) {} |
|
700 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
701 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
702 private: |
|
703 RefPtr<Node> expr1; |
|
704 RefPtr<Node> expr2; |
|
705 Operator oper; |
|
706 }; |
|
707 |
|
708 /** |
|
709 * The ternary operator, "logical ? expr1 : expr2" |
|
710 */ |
|
711 class ConditionalNode : public Node { |
|
712 public: |
|
713 ConditionalNode(Node *l, Node *e1, Node *e2) KJS_FAST_CALL : |
|
714 logical(l), expr1(e1), expr2(e2) {} |
|
715 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
716 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
717 private: |
|
718 RefPtr<Node> logical; |
|
719 RefPtr<Node> expr1; |
|
720 RefPtr<Node> expr2; |
|
721 }; |
|
722 |
|
723 class AssignResolveNode : public Node { |
|
724 public: |
|
725 AssignResolveNode(const Identifier &ident, Operator oper, Node *right) KJS_FAST_CALL |
|
726 : m_ident(ident), m_oper(oper), m_right(right) {} |
|
727 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
728 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
729 protected: |
|
730 Identifier m_ident; |
|
731 Operator m_oper; |
|
732 RefPtr<Node> m_right; |
|
733 }; |
|
734 |
|
735 class AssignBracketNode : public Node { |
|
736 public: |
|
737 AssignBracketNode(Node *base, Node *subscript, Operator oper, Node *right) KJS_FAST_CALL |
|
738 : m_base(base), m_subscript(subscript), m_oper(oper), m_right(right) {} |
|
739 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
740 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
741 protected: |
|
742 RefPtr<Node> m_base; |
|
743 RefPtr<Node> m_subscript; |
|
744 Operator m_oper; |
|
745 RefPtr<Node> m_right; |
|
746 }; |
|
747 |
|
748 class AssignDotNode : public Node { |
|
749 public: |
|
750 AssignDotNode(Node *base, const Identifier& ident, Operator oper, Node *right) KJS_FAST_CALL |
|
751 : m_base(base), m_ident(ident), m_oper(oper), m_right(right) {} |
|
752 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
753 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
754 protected: |
|
755 RefPtr<Node> m_base; |
|
756 Identifier m_ident; |
|
757 Operator m_oper; |
|
758 RefPtr<Node> m_right; |
|
759 }; |
|
760 |
|
761 class AssignErrorNode : public Node { |
|
762 public: |
|
763 AssignErrorNode(Node* left, Operator oper, Node* right) KJS_FAST_CALL |
|
764 : m_left(left), m_oper(oper), m_right(right) {} |
|
765 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
766 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
767 protected: |
|
768 RefPtr<Node> m_left; |
|
769 Operator m_oper; |
|
770 RefPtr<Node> m_right; |
|
771 }; |
|
772 |
|
773 class CommaNode : public Node { |
|
774 public: |
|
775 CommaNode(Node *e1, Node *e2) KJS_FAST_CALL : expr1(e1), expr2(e2) {} |
|
776 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
777 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
778 private: |
|
779 RefPtr<Node> expr1; |
|
780 RefPtr<Node> expr2; |
|
781 }; |
|
782 |
|
783 class AssignExprNode : public Node { |
|
784 public: |
|
785 AssignExprNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
786 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
787 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
788 private: |
|
789 RefPtr<Node> expr; |
|
790 }; |
|
791 |
|
792 class VarDeclNode: public Node { |
|
793 public: |
|
794 enum Type { Variable, Constant }; |
|
795 VarDeclNode(const Identifier &id, AssignExprNode *in, Type t) KJS_FAST_CALL; |
|
796 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
797 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
798 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
799 private: |
|
800 JSValue* handleSlowCase(ExecState*, const ScopeChain&, JSValue*) KJS_FAST_CALL KJS_NO_INLINE; |
|
801 Type varType; |
|
802 Identifier ident; |
|
803 RefPtr<AssignExprNode> init; |
|
804 }; |
|
805 |
|
806 class VarDeclListNode : public Node { |
|
807 public: |
|
808 // list pointer is tail of a circular list, cracked in the ForNode/VarStatementNode ctor |
|
809 VarDeclListNode(VarDeclNode *v) KJS_FAST_CALL : next(this), var(v) { Parser::noteNodeCycle(this); } |
|
810 VarDeclListNode(VarDeclListNode *l, VarDeclNode *v) KJS_FAST_CALL |
|
811 : next(l->next), var(v) { l->next = this; } |
|
812 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
813 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
814 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
815 PassRefPtr<VarDeclListNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
816 virtual void breakCycle() KJS_FAST_CALL; |
|
817 private: |
|
818 friend class ForNode; |
|
819 friend class VarStatementNode; |
|
820 ListRefPtr<VarDeclListNode> next; |
|
821 RefPtr<VarDeclNode> var; |
|
822 }; |
|
823 |
|
824 class VarStatementNode : public StatementNode { |
|
825 public: |
|
826 VarStatementNode(VarDeclListNode *l) KJS_FAST_CALL : next(l->next.release()) { Parser::removeNodeCycle(next.get()); } |
|
827 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
828 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
829 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
830 private: |
|
831 RefPtr<VarDeclListNode> next; |
|
832 }; |
|
833 |
|
834 class BlockNode : public StatementNode { |
|
835 public: |
|
836 BlockNode(SourceElementsNode *s) KJS_FAST_CALL; |
|
837 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
838 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
839 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
840 protected: |
|
841 RefPtr<SourceElementsNode> source; |
|
842 }; |
|
843 |
|
844 class EmptyStatementNode : public StatementNode { |
|
845 public: |
|
846 EmptyStatementNode() KJS_FAST_CALL { } // debug |
|
847 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
848 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
849 }; |
|
850 |
|
851 class ExprStatementNode : public StatementNode { |
|
852 public: |
|
853 ExprStatementNode(Node *e) KJS_FAST_CALL : expr(e) { } |
|
854 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
855 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
856 private: |
|
857 RefPtr<Node> expr; |
|
858 }; |
|
859 |
|
860 class IfNode : public StatementNode { |
|
861 public: |
|
862 IfNode(Node *e, StatementNode *s1, StatementNode *s2) KJS_FAST_CALL |
|
863 : expr(e), statement1(s1), statement2(s2) {} |
|
864 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
865 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
866 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
867 private: |
|
868 RefPtr<Node> expr; |
|
869 RefPtr<StatementNode> statement1; |
|
870 RefPtr<StatementNode> statement2; |
|
871 }; |
|
872 |
|
873 class DoWhileNode : public StatementNode { |
|
874 public: |
|
875 DoWhileNode(StatementNode *s, Node *e) KJS_FAST_CALL : statement(s), expr(e) {} |
|
876 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
877 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
878 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
879 private: |
|
880 RefPtr<StatementNode> statement; |
|
881 RefPtr<Node> expr; |
|
882 }; |
|
883 |
|
884 class WhileNode : public StatementNode { |
|
885 public: |
|
886 WhileNode(Node *e, StatementNode *s) KJS_FAST_CALL : expr(e), statement(s) {} |
|
887 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
888 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
889 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
890 private: |
|
891 RefPtr<Node> expr; |
|
892 RefPtr<StatementNode> statement; |
|
893 }; |
|
894 |
|
895 class ForNode : public StatementNode { |
|
896 public: |
|
897 ForNode(Node *e1, Node *e2, Node *e3, StatementNode *s) KJS_FAST_CALL : |
|
898 expr1(e1), expr2(e2), expr3(e3), statement(s) {} |
|
899 ForNode(VarDeclListNode *e1, Node *e2, Node *e3, StatementNode *s) KJS_FAST_CALL : |
|
900 expr1(e1->next.release()), expr2(e2), expr3(e3), statement(s) { Parser::removeNodeCycle(expr1.get()); } |
|
901 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
902 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
903 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
904 private: |
|
905 RefPtr<Node> expr1; |
|
906 RefPtr<Node> expr2; |
|
907 RefPtr<Node> expr3; |
|
908 RefPtr<StatementNode> statement; |
|
909 }; |
|
910 |
|
911 class ForInNode : public StatementNode { |
|
912 public: |
|
913 ForInNode(Node *l, Node *e, StatementNode *s) KJS_FAST_CALL; |
|
914 ForInNode(const Identifier &i, AssignExprNode *in, Node *e, StatementNode *s) KJS_FAST_CALL; |
|
915 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
916 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
917 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
918 private: |
|
919 Identifier ident; |
|
920 RefPtr<AssignExprNode> init; |
|
921 RefPtr<Node> lexpr; |
|
922 RefPtr<Node> expr; |
|
923 RefPtr<VarDeclNode> varDecl; |
|
924 RefPtr<StatementNode> statement; |
|
925 }; |
|
926 |
|
927 class ContinueNode : public StatementNode { |
|
928 public: |
|
929 ContinueNode() KJS_FAST_CALL { } |
|
930 ContinueNode(const Identifier &i) KJS_FAST_CALL : ident(i) { } |
|
931 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
932 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
933 private: |
|
934 Identifier ident; |
|
935 }; |
|
936 |
|
937 class BreakNode : public StatementNode { |
|
938 public: |
|
939 BreakNode() KJS_FAST_CALL { } |
|
940 BreakNode(const Identifier &i) KJS_FAST_CALL : ident(i) { } |
|
941 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
942 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
943 private: |
|
944 Identifier ident; |
|
945 }; |
|
946 |
|
947 class ReturnNode : public StatementNode { |
|
948 public: |
|
949 ReturnNode(Node *v) KJS_FAST_CALL : value(v) {} |
|
950 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
951 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
952 private: |
|
953 RefPtr<Node> value; |
|
954 }; |
|
955 |
|
956 class WithNode : public StatementNode { |
|
957 public: |
|
958 WithNode(Node *e, StatementNode *s) KJS_FAST_CALL : expr(e), statement(s) {} |
|
959 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
960 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
961 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
962 private: |
|
963 RefPtr<Node> expr; |
|
964 RefPtr<StatementNode> statement; |
|
965 }; |
|
966 |
|
967 class LabelNode : public StatementNode { |
|
968 public: |
|
969 LabelNode(const Identifier &l, StatementNode *s) KJS_FAST_CALL : label(l), statement(s) { } |
|
970 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
971 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
972 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
973 private: |
|
974 Identifier label; |
|
975 RefPtr<StatementNode> statement; |
|
976 }; |
|
977 |
|
978 class ThrowNode : public StatementNode { |
|
979 public: |
|
980 ThrowNode(Node *e) KJS_FAST_CALL : expr(e) {} |
|
981 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
982 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
983 private: |
|
984 RefPtr<Node> expr; |
|
985 }; |
|
986 |
|
987 class TryNode : public StatementNode { |
|
988 public: |
|
989 TryNode(StatementNode *b, const Identifier &e, StatementNode *c, StatementNode *f) KJS_FAST_CALL |
|
990 : tryBlock(b), exceptionIdent(e), catchBlock(c), finallyBlock(f) { } |
|
991 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
992 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
993 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
994 private: |
|
995 RefPtr<StatementNode> tryBlock; |
|
996 Identifier exceptionIdent; |
|
997 RefPtr<StatementNode> catchBlock; |
|
998 RefPtr<StatementNode> finallyBlock; |
|
999 }; |
|
1000 |
|
1001 class ParameterNode : public Node { |
|
1002 public: |
|
1003 // list pointer is tail of a circular list, cracked in the FuncDeclNode/FuncExprNode ctor |
|
1004 ParameterNode(const Identifier &i) KJS_FAST_CALL : id(i), next(this) { Parser::noteNodeCycle(this); } |
|
1005 ParameterNode(ParameterNode *next, const Identifier &i) KJS_FAST_CALL |
|
1006 : id(i), next(next->next) { next->next = this; } |
|
1007 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
1008 Identifier ident() KJS_FAST_CALL { return id; } |
|
1009 ParameterNode *nextParam() KJS_FAST_CALL { return next.get(); } |
|
1010 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1011 PassRefPtr<ParameterNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
1012 virtual void breakCycle() KJS_FAST_CALL; |
|
1013 private: |
|
1014 friend class FuncDeclNode; |
|
1015 friend class FuncExprNode; |
|
1016 Identifier id; |
|
1017 ListRefPtr<ParameterNode> next; |
|
1018 }; |
|
1019 |
|
1020 class Parameter { |
|
1021 public: |
|
1022 Parameter() KJS_FAST_CALL { } |
|
1023 Parameter(const Identifier& n) KJS_FAST_CALL : name(n) { } |
|
1024 Identifier name; |
|
1025 }; |
|
1026 |
|
1027 // inherited by ProgramNode |
|
1028 class FunctionBodyNode : public BlockNode { |
|
1029 public: |
|
1030 FunctionBodyNode(SourceElementsNode *) KJS_FAST_CALL; |
|
1031 virtual void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1032 int sourceId() KJS_FAST_CALL { return m_sourceId; } |
|
1033 const UString& sourceURL() KJS_FAST_CALL { return m_sourceURL; } |
|
1034 |
|
1035 void addParam(const Identifier& ident) KJS_FAST_CALL; |
|
1036 size_t numParams() const KJS_FAST_CALL { return m_parameters.size(); } |
|
1037 Identifier paramName(size_t pos) const KJS_FAST_CALL { return m_parameters[pos].name; } |
|
1038 UString paramString() const KJS_FAST_CALL; |
|
1039 Vector<Parameter>& parameters() KJS_FAST_CALL { return m_parameters; } |
|
1040 private: |
|
1041 UString m_sourceURL; |
|
1042 int m_sourceId; |
|
1043 Vector<Parameter> m_parameters; |
|
1044 }; |
|
1045 |
|
1046 class FuncExprNode : public Node { |
|
1047 public: |
|
1048 FuncExprNode(const Identifier &i, FunctionBodyNode *b, ParameterNode *p = 0) KJS_FAST_CALL |
|
1049 : ident(i), param(p ? p->next.release() : 0), body(b) { if (p) { Parser::removeNodeCycle(param.get()); } addParams(); } |
|
1050 virtual JSValue *evaluate(ExecState*) KJS_FAST_CALL; |
|
1051 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1052 private: |
|
1053 void addParams() KJS_FAST_CALL; |
|
1054 // Used for streamTo |
|
1055 friend class PropertyNode; |
|
1056 Identifier ident; |
|
1057 RefPtr<ParameterNode> param; |
|
1058 RefPtr<FunctionBodyNode> body; |
|
1059 }; |
|
1060 |
|
1061 class FuncDeclNode : public StatementNode { |
|
1062 public: |
|
1063 FuncDeclNode(const Identifier &i, FunctionBodyNode *b) KJS_FAST_CALL |
|
1064 : ident(i), body(b) { addParams(); } |
|
1065 FuncDeclNode(const Identifier &i, ParameterNode *p, FunctionBodyNode *b) KJS_FAST_CALL |
|
1066 : ident(i), param(p->next.release()), body(b) { Parser::removeNodeCycle(param.get()); addParams(); } |
|
1067 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
1068 virtual void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1069 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1070 private: |
|
1071 void addParams() KJS_FAST_CALL; |
|
1072 Identifier ident; |
|
1073 RefPtr<ParameterNode> param; |
|
1074 RefPtr<FunctionBodyNode> body; |
|
1075 }; |
|
1076 |
|
1077 // A linked list of source element nodes |
|
1078 class SourceElementsNode : public StatementNode { |
|
1079 public: |
|
1080 static int count; |
|
1081 // list pointer is tail of a circular list, cracked in the BlockNode (or subclass) ctor |
|
1082 SourceElementsNode(StatementNode*) KJS_FAST_CALL; |
|
1083 SourceElementsNode(SourceElementsNode *s1, StatementNode *s2) KJS_FAST_CALL; |
|
1084 |
|
1085 Completion execute(ExecState*) KJS_FAST_CALL; |
|
1086 void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1087 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
1088 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1089 PassRefPtr<SourceElementsNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
1090 virtual void breakCycle() KJS_FAST_CALL; |
|
1091 private: |
|
1092 friend class BlockNode; |
|
1093 friend class CaseClauseNode; |
|
1094 RefPtr<StatementNode> node; |
|
1095 ListRefPtr<SourceElementsNode> next; |
|
1096 }; |
|
1097 |
|
1098 class CaseClauseNode : public Node { |
|
1099 public: |
|
1100 CaseClauseNode(Node *e) KJS_FAST_CALL : expr(e) { } |
|
1101 CaseClauseNode(Node *e, SourceElementsNode *s) KJS_FAST_CALL |
|
1102 : expr(e), source(s->next.release()) { Parser::removeNodeCycle(source.get()); } |
|
1103 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
1104 Completion evalStatements(ExecState*) KJS_FAST_CALL; |
|
1105 void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1106 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
1107 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1108 private: |
|
1109 RefPtr<Node> expr; |
|
1110 RefPtr<SourceElementsNode> source; |
|
1111 }; |
|
1112 |
|
1113 class ClauseListNode : public Node { |
|
1114 public: |
|
1115 // list pointer is tail of a circular list, cracked in the CaseBlockNode ctor |
|
1116 ClauseListNode(CaseClauseNode *c) KJS_FAST_CALL : clause(c), next(this) { Parser::noteNodeCycle(this); } |
|
1117 ClauseListNode(ClauseListNode *n, CaseClauseNode *c) KJS_FAST_CALL |
|
1118 : clause(c), next(n->next) { n->next = this; } |
|
1119 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
1120 CaseClauseNode *getClause() const KJS_FAST_CALL { return clause.get(); } |
|
1121 ClauseListNode *getNext() const KJS_FAST_CALL { return next.get(); } |
|
1122 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
1123 void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1124 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1125 PassRefPtr<ClauseListNode> releaseNext() KJS_FAST_CALL { return next.release(); } |
|
1126 virtual void breakCycle() KJS_FAST_CALL; |
|
1127 private: |
|
1128 friend class CaseBlockNode; |
|
1129 RefPtr<CaseClauseNode> clause; |
|
1130 ListRefPtr<ClauseListNode> next; |
|
1131 }; |
|
1132 |
|
1133 class CaseBlockNode : public Node { |
|
1134 public: |
|
1135 CaseBlockNode(ClauseListNode *l1, CaseClauseNode *d, ClauseListNode *l2) KJS_FAST_CALL; |
|
1136 JSValue* evaluate(ExecState*) KJS_FAST_CALL; |
|
1137 Completion evalBlock(ExecState *exec, JSValue *input) KJS_FAST_CALL; |
|
1138 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
1139 void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1140 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1141 private: |
|
1142 RefPtr<ClauseListNode> list1; |
|
1143 RefPtr<CaseClauseNode> def; |
|
1144 RefPtr<ClauseListNode> list2; |
|
1145 }; |
|
1146 |
|
1147 class SwitchNode : public StatementNode { |
|
1148 public: |
|
1149 SwitchNode(Node *e, CaseBlockNode *b) KJS_FAST_CALL : expr(e), block(b) { } |
|
1150 virtual Completion execute(ExecState*) KJS_FAST_CALL; |
|
1151 virtual void processVarDecls(ExecState*) KJS_FAST_CALL; |
|
1152 virtual void processFuncDecl(ExecState*) KJS_FAST_CALL; |
|
1153 virtual void streamTo(SourceStream&) const KJS_FAST_CALL; |
|
1154 private: |
|
1155 RefPtr<Node> expr; |
|
1156 RefPtr<CaseBlockNode> block; |
|
1157 }; |
|
1158 |
|
1159 class ProgramNode : public FunctionBodyNode { |
|
1160 public: |
|
1161 ProgramNode(SourceElementsNode *s) KJS_FAST_CALL; |
|
1162 }; |
|
1163 |
|
1164 } // namespace |
|
1165 |
|
1166 #endif |