12 static inline std::string
numtostr(double num
)
20 /** base class. also works as a noop node. */
24 void setParent(ASTNode
* p
) { if (p
) p
->parent
= this; }
27 ASTNode() : parent(0) {}
28 ASTNode(ASTNode
*p
) : parent(p
) {}
29 virtual const char *getType() const { return "ASTNode"; }
30 virtual std::string
toString() const { return std::string("<BasicAstNode/>"); }
33 class Block
: public ASTNode
{
35 std::vector
<ASTNode
*> list
;
37 const char *getType() const { return "Block"; }
38 std::string
toString() const
41 for (std::vector
<ASTNode
*>::const_iterator it
= list
.begin(); it
!= list
.end(); ++it
)
42 arg
+= (*it
)->toString();
43 return "<block>" + arg
+ "</block>";
47 //////////////////////////////////////////////////////////////////////
49 class Ident
: public ASTNode
53 Ident(std::string ident
)
56 const char *getType() const { return "Ident"; }
57 std::string
toString() const { return "<ident name=\""+name
+"\"/>"; }
61 class Number
: public ASTNode
65 Number(double n
): val(n
) {}
66 const char *getType() const { return "Number"; }
67 std::string
toString() const { return std::string("<number val=\"")+numtostr(val
)+"\"/>"; }
70 //////////////////////////////////////////////////////////////////////
78 class UnaryOperator
: public ASTNode
{
82 UnaryOperator(std::string op
, ASTNode
*e
)
83 : oper(op
), operand(e
)
84 { setParent(operand
); }
85 const char *getType() const { return ("UnaryOperator<" + oper
+ ">").c_str(); }
86 virtual std::string
getName() const { return "unaryOp"; }
87 std::string
toString() const
88 { return "<" + getName() + " op=\"" + oper
+ "\">"
90 + "</" + getName() + ">"; }
93 class Increment
: public UnaryOperator
96 Increment(ASTNode
*node
): UnaryOperator("++", node
) {}
97 const char *getType() const { return "Increment"; }
98 std::string
getName() const { return "incr"; }
101 class Decrement
: public UnaryOperator
{
103 Decrement(ASTNode
*node
): UnaryOperator("--", node
) {}
104 const char *getType() const { return "Decrement"; }
105 std::string
getName() const { return "decr"; }
108 class Negation
: public UnaryOperator
{
111 : UnaryOperator("-", e
)
113 const char *getType() const { return "Negation"; }
114 std::string
getName() const { return "neg"; }
117 class LogicalNot
: public UnaryOperator
{
119 LogicalNot(ASTNode
*e
)
120 : UnaryOperator("!", e
)
122 const char *getType() const { return "LogicalNot"; }
123 std::string
getName() const { return "boolnot"; }
126 class BitwiseNot
: public UnaryOperator
{
128 BitwiseNot(ASTNode
*e
)
129 : UnaryOperator("~", e
)
131 const char *getType() const { return "BinaryNot"; }
132 std::string
getName() const { return "bitnot"; }
139 class BinaryOperator
: public ASTNode
{
141 ASTNode
*left
, *right
;
143 BinaryOperator(std::string op
, ASTNode
*l
, ASTNode
*r
)
144 : oper(op
), left(l
), right(r
)
145 { setParent(left
); setParent(right
); }
146 virtual std::string
getName() const { return "binaryOp"; }
147 const char *getType() const { return ("BinaryOperator<"+oper
+">").c_str(); }
148 std::string
toString() const
149 { return "<" + getName() + " op=\"" + oper
+ "\"><left>"
150 + left
->toString() + "</left><right>"
151 + right
->toString() + "</right></" + getName() + ">"; }
156 class Add
: public BinaryOperator
{
158 Add(ASTNode
*l
, ASTNode
*r
)
159 : BinaryOperator("+", l
, r
) {}
160 const char *getType() const { return "Add"; }
161 std::string
getName() const { return "add"; }
164 class Subtract
: public BinaryOperator
{
166 Subtract(ASTNode
*l
, ASTNode
*r
)
167 : BinaryOperator("-", l
, r
) {}
168 const char *getType() const { return "Subtract"; }
169 std::string
getName() const { return "sub"; }
172 class Multiply
: public BinaryOperator
{
174 Multiply(ASTNode
*l
, ASTNode
*r
)
175 : BinaryOperator("*", l
, r
) {}
176 const char *getType() const { return "Multiply"; }
177 std::string
getName() const { return "mul"; }
180 class Divide
: public BinaryOperator
{
182 Divide(ASTNode
*l
, ASTNode
*r
)
183 : BinaryOperator("/", l
, r
) {}
184 const char *getType() const { return "Divide"; }
185 std::string
getName() const { return "div"; }
188 class Modulo
: public BinaryOperator
{
190 Modulo(ASTNode
*l
, ASTNode
*r
)
191 : BinaryOperator("%", l
, r
) {}
192 const char *getType() const { return "Modulo"; }
193 std::string
getName() const { return "mod"; }
199 class Assign
: public BinaryOperator
{
201 Assign(ASTNode
*l
, ASTNode
*r
)
202 : BinaryOperator("=", l
, r
) {}
203 const char *getType() const { return "Assign"; }
204 std::string
getName() const { return "assign"; }
209 class LessThan
: public BinaryOperator
{
211 LessThan(ASTNode
*l
, ASTNode
*r
)
212 : BinaryOperator("<", l
, r
) {}
213 const char *getType() const { return "LessThan"; }
214 std::string
getName() const { return "lt"; }
217 class GreaterThan
: public BinaryOperator
{
219 GreaterThan(ASTNode
*l
, ASTNode
*r
)
220 : BinaryOperator(">", l
, r
) {}
221 const char *getType() const { return "GreaterThan"; }
222 std::string
getName() const { return "gt"; }
225 class LessEqual
: public BinaryOperator
{
227 LessEqual(ASTNode
*l
, ASTNode
*r
)
228 : BinaryOperator("<=", l
, r
) {}
229 const char *getType() const { return "LessEqual"; }
230 std::string
getName() const { return "lteq"; }
233 class GreaterEqual
: public BinaryOperator
{
235 GreaterEqual(ASTNode
*l
, ASTNode
*r
)
236 : BinaryOperator(">=", l
, r
) {}
237 const char *getType() const { return "GreaterEqual"; }
238 std::string
getName() const { return "gteq"; }
241 class Equal
: public BinaryOperator
{
243 Equal(ASTNode
*l
, ASTNode
*r
)
244 : BinaryOperator("==", l
, r
) {}
245 const char *getType() const { return "Equal"; }
246 std::string
getName() const { return "eq"; }
249 class NotEqual
: public BinaryOperator
{
251 NotEqual(ASTNode
*l
, ASTNode
*r
)
252 : BinaryOperator("!=", l
, r
) {}
253 const char *getType() const { return "NotEqual"; }
254 std::string
getName() const { return "neq"; }
259 class BitwiseAnd
: public BinaryOperator
{
261 BitwiseAnd(ASTNode
*l
, ASTNode
*r
)
262 : BinaryOperator("&", l
, r
) {}
263 const char *getType() const { return "BitwiseAnd"; }
264 std::string
getName() const { return "bitand"; }
267 class BitwiseOr
: public BinaryOperator
{
269 BitwiseOr(ASTNode
*l
, ASTNode
*r
)
270 : BinaryOperator("|", l
, r
) {}
271 const char *getType() const { return "BitwiseOr"; }
272 std::string
getName() const { return "bitor"; }
275 class BitwiseXor
: public BinaryOperator
{
277 BitwiseXor(ASTNode
*l
, ASTNode
*r
)
278 : BinaryOperator("^", l
, r
) {}
279 const char *getType() const { return "BitwiseXor"; }
280 std::string
getName() const { return "bitxor"; }
283 class ShiftLeft
: public BinaryOperator
{
285 ShiftLeft(ASTNode
*l
, ASTNode
*r
)
286 : BinaryOperator("<<", l
, r
) {}
287 const char *getType() const { return "ShiftLeft"; }
288 std::string
getName() const { return "shl"; }
291 class ShiftRight
: public BinaryOperator
{
293 ShiftRight(ASTNode
*l
, ASTNode
*r
)
294 : BinaryOperator(">>", l
, r
) {}
295 const char *getType() const { return "ShiftRight"; }
296 std::string
getName() const { return "shr"; }
301 class LogicalAnd
: public BinaryOperator
{
303 LogicalAnd(ASTNode
*l
, ASTNode
*r
)
304 : BinaryOperator("&&", l
, r
) {}
305 const char *getType() const { return "LogicalAnd"; }
306 std::string
getName() const { return "booland"; }
309 class LogicalOr
: public BinaryOperator
{
311 LogicalOr(ASTNode
*l
, ASTNode
*r
)
312 : BinaryOperator("||", l
, r
) {}
313 const char *getType() const { return "LogicalOr"; }
314 std::string
getName() const { return "boolor"; }
319 class Comma
: public BinaryOperator
{
321 Comma(ASTNode
*l
, ASTNode
*r
)
322 : BinaryOperator(",", l
, r
) {}
323 const char *getType() const { return "Comma"; }
324 std::string
getName() const { return "comma"; }
327 class Semicolon
: public BinaryOperator
{
329 Semicolon(ASTNode
*l
, ASTNode
*r
)
330 : BinaryOperator(";", l
, r
) {}
331 const char *getType() const { return "Semicolon"; }
332 std::string
getName() const { return "semicolon"; }
339 class IfThenElse
: public ASTNode
342 ASTNode
*cond
, *trueexp
, *falseexp
;
343 IfThenElse(ASTNode
*c
, ASTNode
*t
, ASTNode
*f
= 0)
344 : cond(c
), trueexp(t
), falseexp(f
)
350 const char *getType() const { return "IfThenElse"; }
351 std::string
toString() const
353 "<if>" + cond
->toString() + "</if>"
354 + "<then>" + trueexp
->toString() + "</then>"
355 + ( falseexp
? "<else>" + falseexp
->toString() + "</else>" : "")
377 class Loop
: public ASTNode
380 /// loop initialization
382 /// loop precondition
384 /// loop postcondition
386 /// execute before any statements
388 /// execute after any statements
393 Loop(ASTNode
*b
, ASTNode
*i
= 0, ASTNode
*pre
= 0, ASTNode
*post
= 0,
394 ASTNode
*bef
= 0, ASTNode
*aft
= 0)
395 : init(i
), precond(pre
), postcond(post
), before(bef
), after(aft
), body(b
)
406 const char *getType() const { return "Loop"; }
407 std::string
toString() const
409 + ( init
? "<init>" + init
->toString() + "</init>" : "")
410 + ( precond
? "<precond>" + precond
->toString() + "</precond>" : "")
411 + ( postcond
? "<postcond>" + postcond
->toString() + "</postcond>" : "")
412 + ( before
? "<before>" + before
->toString() + "</before>" : "")
413 + ( after
? "<after>" + after
->toString() + "</after>" : "")
414 + "<body>" + body
->toString() + "</body>"
418 class BlockControl
: public ASTNode
{
422 ASTNode
* findParent(std::string type
)
424 if (!parent
) return 0;
425 ASTNode
*cur
= parent
;
426 while (cur
&& cur
->getType() != type
)
431 const char *getType() const { return "BlockControl"; }
432 std::string
toString() const { return "<blockcontrol/>"; }
435 class LoopControl
: public BlockControl
{
438 ASTNode
* findParent() { return BlockControl::findParent("Loop"); }
439 const char *getType() const { return "LoopControl"; }
440 std::string
toString() const { return "<loopcontrol/>"; }
443 class Continue
: public LoopControl
{
446 const char *getType() const { return "Continue"; }
447 std::string
toString() const { return "<continue/>"; }
450 class Break
: public LoopControl
{
453 const char *getType() const { return "Break"; }
454 std::string
toString() const { return "<break/>"; }
457 class Return
: public BlockControl
{
460 Return(ASTNode
*r
) : retval(r
) { setParent(r
);}
461 ASTNode
*findParent() { return BlockControl::findParent("Function"); }
462 const char *getType() const { return "Return"; }
463 std::string
toString() const
464 { if (!retval
) return "<return/>";
465 else return "<return>" + retval
->toString() + "</return>"; }
468 class Label
: public ASTNode
{
472 Label(std::string n
, ASTNode
*r
): name(n
), rest(r
) { setParent(r
); }
473 const char *getType() const { return "Label"; }
474 std::string
toString() const
475 { return "<label name=\"" + name
+ "\">" + rest
->toString() + "</label>"; }
478 class Jump
: public ASTNode
{
481 Jump(const char *d
): dest(d
) {}
482 const char *getType() const { return "Jump"; }
483 std::string
toString() const { return "<jump dest=\"" + dest
+ "\"/>"; }
486 class CallExpr
: public ASTNode
{
488 void extractArgs(Comma
*args
)
492 ASTNode
*call
, *args
;
493 CallExpr(ASTNode
*c
, ASTNode
*a
): call(c
), args(a
)
496 const char *getType() const { return "CallExpr"; }
497 std::string
toString() const
500 return "<callexpr><callee>" + call
->toString() + "</callee><args>" + args
->toString() + "</args></callexpr>";
502 return "<callexpr><callee>" + call
->toString() + "</callee></callexpr>";
507 class Call
: public ASTNode
{
509 void extractArgs(Comma
*args
)
513 std::vector
<ASTNode
*> argv
;
515 Call(std::string n
): name(n
) {}
516 Call(std::string n
, ASTNode
*arg
): name(n
) { setParent(arg
); argv
.push_back(arg
); }
517 const char *getType() const { return "Call"; }
518 std::string
toString() const
520 if (argv
.size() > 0) {
522 for (std::vector
<ASTNode
*>::const_iterator it
= argv
.begin(); it
!= argv
.end(); ++it
)
523 args
+= "<arg>" + (*it
)->toString() + "</arg>";
524 return "<call name=\"" + name
+ "\">" + args
+ "</call>";
526 return "<call name=\"" + name
+ "\"/>";
531 class StartScript
: public Call
{
533 StartScript(std::string n
): Call(n
) {}
534 StartScript(std::string n
, ASTNode
*arg
): Call(n
, arg
) {}
536 const char *getType() const { return "StartScript"; }
537 std::string
toString() const
539 if (argv
.size() > 0) {
541 for (std::vector
<ASTNode
*>::const_iterator it
= argv
.begin(); it
!= argv
.end(); ++it
)
542 args
+= "<arg>" + (*it
)->toString() + "</arg>";
543 return "<startscript name=\"" + name
+ "\">" + args
+ "</startscript>";
545 return "<startscript name=\"" + name
+ "\"/>";
552 class FunctionProto
: public ASTNode
{
556 FunctionProto(std::string n
, ASTNode
*p
): name(n
), params(p
)
558 const char *getType() const { return "FunctionProto"; }
559 std::string
toString() const
561 if (params
) return "<functionproto name=\"" + name
+ "\">"
562 + params
->toString() + "</functionproto>";
563 else return "<functionproto name=\"" + name
+ "\"/>";
572 class GetOp
: public ASTNode
{
576 GetOp(ASTNode
*v
, ASTNode
*a
=0, ASTNode
*b
=0, ASTNode
* c
=0, ASTNode
*d
= 0)
578 { args
[0] = a
; args
[1] = b
; args
[2] = c
; args
[3] = d
;
579 setParent(a
); setParent(b
); setParent(c
); setParent(d
); setParent(v
); }
580 const char *getType() const { return "Get"; }
581 std::string
toString() const
582 { return "<get><val>" + val
->toString() + "</val>"
583 + (args
[0] ? "<a1>" + args
[0]->toString() + "</a1>" : "")
584 + (args
[1] ? "<a2>" + args
[1]->toString() + "</a2>" : "")
585 + (args
[2] ? "<a3>" + args
[2]->toString() + "</a3>" : "")
586 + (args
[3] ? "<a4>" + args
[3]->toString() + "</a4>" : "")
590 class SetOp
: public ASTNode
{
593 SetOp(ASTNode
*k
, ASTNode
*v
) : key(k
), val(v
)
594 { setParent(k
); setParent(v
); }
595 const char *getType() const { return "Get"; }
596 std::string
toString() const
597 { return "<set><key>" + key
->toString() + "</key>"
598 "<value>" + val
->toString() + "</value></set>"; }
602 class Axis
: public ASTNode
{
605 Axis(int a
): axis(a
) {}
606 const char *getType() const { return "Axis"; }
607 std::string
toString() const { char tmp
[] = "x-axis"; tmp
[0] += axis
; return std::string("<axis name=\"") + std::string(tmp
) + std::string("\"/>"); }
610 class TAOperation
: public ASTNode
{
614 TAOperation(std::string n
, ASTNode
*arg1
, ASTNode
*arg2
= 0,
615 ASTNode
*arg3
= 0, ASTNode
*arg4
= 0, ASTNode
*arg5
= 0)
617 { args
[0] = arg1
; args
[1] = arg2
; args
[2] = arg3
; args
[3] = arg4
; args
[4] = arg5
;
618 setParent(arg1
); setParent(arg2
); setParent(arg3
); setParent(arg4
); setParent(arg5
); }
619 const char *getType() const { return "TAOperation"; }
620 std::string
toString() const
621 { return "<operation name=\"" + name
+ "\">"
622 "<a1>" + args
[0]->toString() + "</a1>"
623 + (args
[1] ? "<a2>" + args
[1]->toString() + "</a2>" : "")
624 + (args
[2] ? "<a3>" + args
[2]->toString() + "</a3>" : "")
625 + (args
[3] ? "<a4>" + args
[3]->toString() + "</a4>" : "")
626 + (args
[4] ? "<a5>" + args
[4]->toString() + "</a5>" : "")
631 class Typename
: public ASTNode
{
634 Typename(std::string n
): name(n
) {}
635 const char *getType() const { return "Typename"; }
636 std::string
toString() const
637 { return "<typename name=\"" + name
+ "\"/>"; }
640 class Declaration
: public ASTNode
{
644 Declaration(ASTNode
*t
, ASTNode
*l
): type(t
), list(l
)
645 { setParent(t
); setParent(l
); }
646 const char *getType() const { return "Declaration"; }
647 std::string
toString() const
648 { return "<declaration><type>" + type
->toString() + "</type>"
649 "<list>" + list
->toString() + "</list>"
654 class Pragma
: public ASTNode
{
659 Pragma(std::string n
, double d
): name(n
), number(d
) {}
660 Pragma(std::string n
, std::string v
): name(n
), value(v
), number(0) {}
661 const char *getType() const { return "Pragma"; }
662 std::string
toString() const { return "<pragma name=\"" + name
+ "\" value=\"" + value
+ "\" num=\"" + numtostr(number
) + "\"/>"; }
667 class Function
: public ASTNode
{
671 Function(ASTNode
*fp
, ASTNode
*b
): proto(fp
), instr(b
)
672 { setParent(fp
); setParent(b
); }
673 const char *getType() const { return "Function"; }
674 std::string
toString() const
675 { return "<function>" + proto
->toString() + instr
->toString() + "</function>"; }