]> sourceware.org Git - systemtap.git/blob - staptree.h
Merge remote-tracking branch 'origin/master' into inode-uprobes
[systemtap.git] / staptree.h
1 // -*- C++ -*-
2 // Copyright (C) 2005-2011 Red Hat Inc.
3 // Copyright (C) 2006 Intel Corporation.
4 //
5 // This file is part of systemtap, and is free software. You can
6 // redistribute it and/or modify it under the terms of the GNU General
7 // Public License (GPL); either version 2, or (at your option) any
8 // later version.
9
10 #ifndef STAPTREE_H
11 #define STAPTREE_H
12
13 #include <map>
14 #include <stack>
15 #include <set>
16 #include <string>
17 #include <vector>
18 #include <iostream>
19 #include <stdexcept>
20 #include <cassert>
21 extern "C" {
22 #include <stdint.h>
23 }
24
25 struct token; // parse.h
26 struct systemtap_session; // session.h
27
28 struct semantic_error: public std::runtime_error
29 {
30 const token* tok1;
31 std::string msg2;
32 const token* tok2;
33 semantic_error *chain;
34
35 ~semantic_error () throw () {}
36 semantic_error (const std::string& msg, const token* t1=0):
37 runtime_error (msg), tok1 (t1), tok2 (0), chain (0) {}
38 semantic_error (const std::string& msg, const token* t1,
39 const std::string& m2, const token* t2):
40 runtime_error (msg), tok1 (t1), msg2 (m2), tok2 (t2), chain (0) {}
41 };
42
43 // ------------------------------------------------------------------------
44
45 /* struct statistic_decl moved to session.h */
46
47 // ------------------------------------------------------------------------
48
49 enum exp_type
50 {
51 pe_unknown,
52 pe_long, // int64_t
53 pe_string, // std::string
54 pe_stats
55 };
56
57 std::ostream& operator << (std::ostream& o, const exp_type& e);
58
59 struct token;
60 struct visitor;
61 struct update_visitor;
62
63 struct expression
64 {
65 exp_type type;
66 const token* tok;
67 expression ();
68 virtual ~expression ();
69 virtual void print (std::ostream& o) const = 0;
70 virtual void visit (visitor* u) = 0;
71 };
72
73 std::ostream& operator << (std::ostream& o, const expression& k);
74
75
76 struct literal: public expression
77 {
78 };
79
80
81 struct literal_string: public literal
82 {
83 std::string value;
84 literal_string (const std::string& v);
85 void print (std::ostream& o) const;
86 void visit (visitor* u);
87 };
88
89
90 struct literal_number: public literal
91 {
92 int64_t value;
93 bool print_hex;
94 literal_number (int64_t v, bool hex=false);
95 void print (std::ostream& o) const;
96 void visit (visitor* u);
97 };
98
99
100 struct embedded_expr: public expression
101 {
102 std::string code;
103 void print (std::ostream& o) const;
104 void visit (visitor* u);
105 };
106
107
108 struct binary_expression: public expression
109 {
110 expression* left;
111 std::string op;
112 expression* right;
113 void print (std::ostream& o) const;
114 void visit (visitor* u);
115 };
116
117
118 struct unary_expression: public expression
119 {
120 std::string op;
121 expression* operand;
122 void print (std::ostream& o) const;
123 void visit (visitor* u);
124 };
125
126
127 struct pre_crement: public unary_expression
128 {
129 void visit (visitor* u);
130 };
131
132
133 struct post_crement: public unary_expression
134 {
135 void print (std::ostream& o) const;
136 void visit (visitor* u);
137 };
138
139
140 struct logical_or_expr: public binary_expression
141 {
142 void visit (visitor* u);
143 };
144
145
146 struct logical_and_expr: public binary_expression
147 {
148 void visit (visitor* u);
149 };
150
151
152 struct arrayindex;
153 struct array_in: public expression
154 {
155 arrayindex* operand;
156 void print (std::ostream& o) const;
157 void visit (visitor* u);
158 };
159
160
161 struct comparison: public binary_expression
162 {
163 void visit (visitor* u);
164 };
165
166
167 struct concatenation: public binary_expression
168 {
169 void visit (visitor* u);
170 };
171
172
173 struct ternary_expression: public expression
174 {
175 expression* cond;
176 expression* truevalue;
177 expression* falsevalue;
178 void print (std::ostream& o) const;
179 void visit (visitor* u);
180 };
181
182
183 struct assignment: public binary_expression
184 {
185 void visit (visitor* u);
186 };
187
188 struct symbol;
189 struct hist_op;
190 struct indexable
191 {
192 // This is a helper class which, type-wise, acts as a disjoint union
193 // of symbols and histograms. You can ask it whether it's a
194 // histogram or a symbol, and downcast accordingly.
195 void print_indexable (std::ostream& o) const;
196 void visit_indexable (visitor* u);
197 virtual bool is_symbol(symbol *& sym_out);
198 virtual bool is_hist_op(hist_op *& hist_out);
199 virtual bool is_const_symbol(const symbol *& sym_out) const;
200 virtual bool is_const_hist_op(const hist_op *& hist_out) const;
201 virtual const token *get_tok() const = 0;
202 virtual ~indexable() {}
203 };
204
205 // Perform a downcast to one out-value and NULL the other, throwing an
206 // exception if neither downcast succeeds. This is (sadly) about the
207 // best we can accomplish in C++.
208 void
209 classify_indexable(indexable* ix,
210 symbol *& array_out,
211 hist_op *& hist_out);
212
213 void
214 classify_const_indexable(const indexable* ix,
215 symbol const *& array_out,
216 hist_op const *& hist_out);
217
218 class vardecl;
219 struct symbol:
220 public expression,
221 public indexable
222 {
223 std::string name;
224 vardecl *referent;
225 symbol ();
226 void print (std::ostream& o) const;
227 void visit (visitor* u);
228 // overrides of type 'indexable'
229 const token *get_tok() const;
230 bool is_const_symbol(const symbol *& sym_out) const;
231 bool is_symbol(symbol *& sym_out);
232 };
233
234
235 struct target_symbol: public symbol
236 {
237 enum component_type
238 {
239 comp_struct_member,
240 comp_literal_array_index,
241 comp_expression_array_index,
242 comp_pretty_print, // must be final
243 };
244
245 struct component
246 {
247 const token* tok;
248 component_type type;
249 std::string member; // comp_struct_member, comp_pretty_print
250 int64_t num_index; // comp_literal_array_index
251 expression* expr_index; // comp_expression_array_index
252
253 component(const token* t, const std::string& m, bool pprint=false):
254 tok(t),
255 type(pprint ? comp_pretty_print : comp_struct_member),
256 member(m), num_index(0), expr_index(0)
257 {}
258 component(const token* t, int64_t n):
259 tok(t), type(comp_literal_array_index), num_index(n),
260 expr_index(0) {}
261 component(const token* t, expression* e):
262 tok(t), type(comp_expression_array_index), num_index(0),
263 expr_index(e) {}
264 void print (std::ostream& o) const;
265 };
266
267 bool addressof;
268 std::vector<component> components;
269 semantic_error* saved_conversion_error; // hand-made linked list
270 target_symbol(): addressof(false), saved_conversion_error (0) {}
271 void chain (const semantic_error& er);
272 void print (std::ostream& o) const;
273 void visit (visitor* u);
274 void visit_components (visitor* u);
275 void visit_components (update_visitor* u);
276 void assert_no_components(const std::string& tapset, bool pretty_ok=false);
277 };
278
279 std::ostream& operator << (std::ostream& o, const target_symbol::component& c);
280
281
282 struct cast_op: public target_symbol
283 {
284 expression *operand;
285 std::string type_name, module;
286 void print (std::ostream& o) const;
287 void visit (visitor* u);
288 };
289
290
291 struct defined_op: public expression
292 {
293 target_symbol *operand;
294 void print (std::ostream& o) const;
295 void visit (visitor* u);
296 };
297
298
299 struct entry_op: public expression
300 {
301 expression *operand;
302 void print (std::ostream& o) const;
303 void visit (visitor* u);
304 };
305
306
307 struct arrayindex: public expression
308 {
309 std::vector<expression*> indexes;
310 indexable *base;
311 arrayindex ();
312 void print (std::ostream& o) const;
313 void visit (visitor* u);
314 };
315
316
317 class functiondecl;
318 struct functioncall: public expression
319 {
320 std::string function;
321 std::vector<expression*> args;
322 functiondecl *referent;
323 functioncall ();
324 void print (std::ostream& o) const;
325 void visit (visitor* u);
326 };
327
328
329 struct print_format: public expression
330 {
331 bool print_to_stream;
332 bool print_with_format;
333 bool print_with_delim;
334 bool print_with_newline;
335 bool print_char;
336
337 // XXX match runtime/vsprintf.c's print_flag
338 // ... for use with number() & number_size()
339 enum format_flag
340 {
341 fmt_flag_zeropad = 1,
342 fmt_flag_sign = 2,
343 fmt_flag_plus = 4,
344 fmt_flag_space = 8,
345 fmt_flag_left = 16,
346 fmt_flag_special = 32,
347 fmt_flag_large = 64,
348 };
349
350 enum conversion_type
351 {
352 conv_unspecified,
353 conv_pointer,
354 conv_number,
355 conv_string,
356 conv_char,
357 conv_memory,
358 conv_memory_hex,
359 conv_literal,
360 conv_binary
361 };
362
363 enum width_type
364 {
365 width_unspecified,
366 width_static,
367 width_dynamic
368 };
369
370 enum precision_type
371 {
372 prec_unspecified,
373 prec_static,
374 prec_dynamic
375 };
376
377 struct format_component
378 {
379 unsigned long flags;
380 unsigned base;
381 unsigned width;
382 unsigned precision;
383 width_type widthtype;
384 precision_type prectype;
385 conversion_type type;
386 std::string literal_string;
387 bool is_empty() const
388 {
389 return flags == 0
390 && widthtype == width_unspecified
391 && prectype == prec_unspecified
392 && type == conv_unspecified
393 && literal_string.empty();
394 }
395 void clear()
396 {
397 flags = 0;
398 widthtype = width_unspecified;
399 prectype = prec_unspecified;
400 type = conv_unspecified;
401 literal_string.clear();
402 }
403 inline void set_flag(format_flag f) { flags |= f; }
404 inline bool test_flag(format_flag f) const { return flags & f; }
405 };
406
407 std::string raw_components;
408 std::vector<format_component> components;
409 format_component delimiter;
410 std::vector<expression*> args;
411 hist_op *hist;
412
413 static std::string components_to_string(std::vector<format_component> const & components);
414 static std::vector<format_component> string_to_components(std::string const & str);
415 static print_format* create(const token *t);
416
417 void print (std::ostream& o) const;
418 void visit (visitor* u);
419
420 private:
421 print_format(bool stream, bool format, bool delim, bool newline, bool _char):
422 print_to_stream(stream), print_with_format(format),
423 print_with_delim(delim), print_with_newline(newline),
424 print_char(_char), hist(NULL)
425 {}
426 };
427
428
429 enum stat_component_type
430 {
431 sc_average,
432 sc_count,
433 sc_sum,
434 sc_min,
435 sc_max,
436 };
437
438 struct stat_op: public expression
439 {
440 stat_component_type ctype;
441 expression* stat;
442 void print (std::ostream& o) const;
443 void visit (visitor* u);
444 };
445
446 enum histogram_type
447 {
448 hist_linear,
449 hist_log
450 };
451
452 struct hist_op: public indexable
453 {
454 const token* tok;
455 histogram_type htype;
456 expression* stat;
457 std::vector<int64_t> params;
458 void print (std::ostream& o) const;
459 void visit (visitor* u);
460 // overrides of type 'indexable'
461 const token *get_tok() const;
462 bool is_const_hist_op(const hist_op *& hist_out) const;
463 bool is_hist_op(hist_op *& hist_out);
464 };
465
466 // ------------------------------------------------------------------------
467
468
469 struct symboldecl // unique object per (possibly implicit)
470 // symbol declaration
471 {
472 const token* tok;
473 const token* systemtap_v_conditional; //checking systemtap compatibility
474 std::string name;
475 exp_type type;
476 symboldecl ();
477 virtual ~symboldecl ();
478 virtual void print (std::ostream &o) const = 0;
479 virtual void printsig (std::ostream &o) const = 0;
480 };
481
482
483 std::ostream& operator << (std::ostream& o, const symboldecl& k);
484
485
486 struct vardecl: public symboldecl
487 {
488 void print (std::ostream& o) const;
489 void printsig (std::ostream& o) const;
490 vardecl ();
491 void set_arity (int arity, const token* t);
492 bool compatible_arity (int a);
493 const token* arity_tok; // site where arity was first resolved
494 int arity; // -1: unknown; 0: scalar; >0: array
495 int maxsize; // upperbound on size for arrays
496 std::vector<exp_type> index_types; // for arrays only
497 literal *init; // for global scalars only
498 bool skip_init; // for probe locals only, don't init on entry
499 bool wrap;
500 };
501
502
503 struct vardecl_builtin: public vardecl
504 {
505 };
506
507
508 struct statement;
509 struct functiondecl: public symboldecl
510 {
511 std::vector<vardecl*> formal_args;
512 std::vector<vardecl*> locals;
513 std::vector<vardecl*> unused_locals;
514 statement* body;
515 bool synthetic;
516 functiondecl ();
517 void print (std::ostream& o) const;
518 void printsig (std::ostream& o) const;
519 void join (systemtap_session& s); // for synthetic functions only
520 };
521
522
523 // ------------------------------------------------------------------------
524
525
526 struct statement
527 {
528 virtual void print (std::ostream& o) const = 0;
529 virtual void visit (visitor* u) = 0;
530 const token* tok;
531 statement ();
532 statement (const token* tok);
533 virtual ~statement ();
534 };
535
536 std::ostream& operator << (std::ostream& o, const statement& k);
537
538
539 struct embeddedcode: public statement
540 {
541 std::string code;
542 void print (std::ostream& o) const;
543 void visit (visitor* u);
544 };
545
546
547 struct block: public statement
548 {
549 std::vector<statement*> statements;
550 void print (std::ostream& o) const;
551 void visit (visitor* u);
552 block () {}
553 block (statement* car, statement* cdr);
554 virtual ~block () {}
555 };
556
557
558 struct try_block: public statement
559 {
560 statement* try_block; // may be 0
561 statement* catch_block; // may be 0
562 symbol* catch_error_var; // may be 0
563 void print (std::ostream& o) const;
564 void visit (visitor* u);
565 };
566
567
568 struct expr_statement;
569 struct for_loop: public statement
570 {
571 expr_statement* init; // may be 0
572 expression* cond;
573 expr_statement* incr; // may be 0
574 statement* block;
575 void print (std::ostream& o) const;
576 void visit (visitor* u);
577 };
578
579
580 struct foreach_loop: public statement
581 {
582 // this part is a specialization of arrayindex
583 std::vector<symbol*> indexes;
584 indexable *base;
585 int sort_direction; // -1: decreasing, 0: none, 1: increasing
586 unsigned sort_column; // 0: value, 1..N: index
587 symbol* value; // optional iteration value
588 expression* limit; // optional iteration limit
589
590 statement* block;
591 void print (std::ostream& o) const;
592 void visit (visitor* u);
593 };
594
595
596 struct null_statement: public statement
597 {
598 void print (std::ostream& o) const;
599 void visit (visitor* u);
600 null_statement (const token* tok);
601 };
602
603
604 struct expr_statement: public statement
605 {
606 expression* value; // executed for side-effects
607 void print (std::ostream& o) const;
608 void visit (visitor* u);
609 };
610
611
612 struct if_statement: public statement
613 {
614 expression* condition;
615 statement* thenblock;
616 statement* elseblock; // may be 0
617 void print (std::ostream& o) const;
618 void visit (visitor* u);
619 };
620
621
622 struct return_statement: public expr_statement
623 {
624 void print (std::ostream& o) const;
625 void visit (visitor* u);
626 };
627
628
629 struct delete_statement: public expr_statement
630 {
631 void print (std::ostream& o) const;
632 void visit (visitor* u);
633 };
634
635
636 struct break_statement: public statement
637 {
638 void print (std::ostream& o) const;
639 void visit (visitor* u);
640 };
641
642
643 struct continue_statement: public statement
644 {
645 void print (std::ostream& o) const;
646 void visit (visitor* u);
647 };
648
649
650 struct next_statement: public statement
651 {
652 void print (std::ostream& o) const;
653 void visit (visitor* u);
654 };
655
656
657 struct probe;
658 struct derived_probe;
659 struct probe_alias;
660 struct embeddedcode;
661 struct stapfile
662 {
663 std::string name;
664 std::vector<probe*> probes;
665 std::vector<probe_alias*> aliases;
666 std::vector<functiondecl*> functions;
667 std::vector<vardecl*> globals;
668 std::vector<embeddedcode*> embeds;
669 std::string file_contents;
670 bool privileged;
671 stapfile (): file_contents (""),
672 privileged (false) {}
673 void print (std::ostream& o) const;
674 };
675
676
677 struct probe_point
678 {
679 struct component // XXX: sort of a restricted functioncall
680 {
681 std::string functor;
682 literal* arg; // optional
683 component ();
684 const token* tok; // points to component's functor
685 component(std::string const & f, literal * a = NULL);
686 };
687 std::vector<component*> components;
688 bool optional;
689 bool sufficient;
690 expression* condition;
691 void print (std::ostream& o, bool print_extras=true) const;
692 probe_point ();
693 probe_point(const probe_point& pp);
694 probe_point(std::vector<component*> const & comps);
695 std::string str(bool print_extras=true) const;
696 };
697
698 std::ostream& operator << (std::ostream& o, const probe_point& k);
699
700
701 struct probe
702 {
703 std::vector<probe_point*> locations;
704 statement* body;
705 const token* tok;
706 const token* systemtap_v_conditional; //checking systemtap compatibility
707 std::vector<vardecl*> locals;
708 std::vector<vardecl*> unused_locals;
709 static unsigned last_probeidx;
710 probe ();
711 probe (const probe& p, probe_point *l);
712 void print (std::ostream& o) const;
713 virtual void printsig (std::ostream &o) const;
714 virtual void collect_derivation_chain (std::vector<probe*> &probes_list);
715 virtual void collect_derivation_pp_chain (std::vector<probe_point*> &) {}
716 virtual const probe_alias *get_alias () const { return 0; }
717 virtual probe* create_alias(probe_point* l, probe_point* a);
718 virtual const probe* basest () const { return this; }
719 virtual const probe* almost_basest () const { return 0; }
720 virtual ~probe() {}
721 bool privileged;
722 std::string name;
723 };
724
725 struct probe_alias: public probe
726 {
727 probe_alias(std::vector<probe_point*> const & aliases);
728 std::vector<probe_point*> alias_names;
729 virtual void printsig (std::ostream &o) const;
730 bool epilogue_style;
731 };
732
733
734 // A derived visitor instance is used to visit the entire
735 // statement/expression tree.
736 struct visitor
737 {
738 // Machinery for differentiating lvalue visits from non-lvalue.
739 std::vector<expression *> active_lvalues;
740 bool is_active_lvalue(expression *e);
741 void push_active_lvalue(expression *e);
742 void pop_active_lvalue();
743
744 virtual ~visitor () {}
745 virtual void visit_block (block *s) = 0;
746 virtual void visit_try_block (try_block *s) = 0;
747 virtual void visit_embeddedcode (embeddedcode *s) = 0;
748 virtual void visit_null_statement (null_statement *s) = 0;
749 virtual void visit_expr_statement (expr_statement *s) = 0;
750 virtual void visit_if_statement (if_statement* s) = 0;
751 virtual void visit_for_loop (for_loop* s) = 0;
752 virtual void visit_foreach_loop (foreach_loop* s) = 0;
753 virtual void visit_return_statement (return_statement* s) = 0;
754 virtual void visit_delete_statement (delete_statement* s) = 0;
755 virtual void visit_next_statement (next_statement* s) = 0;
756 virtual void visit_break_statement (break_statement* s) = 0;
757 virtual void visit_continue_statement (continue_statement* s) = 0;
758 virtual void visit_literal_string (literal_string* e) = 0;
759 virtual void visit_literal_number (literal_number* e) = 0;
760 virtual void visit_embedded_expr (embedded_expr* e) = 0;
761 virtual void visit_binary_expression (binary_expression* e) = 0;
762 virtual void visit_unary_expression (unary_expression* e) = 0;
763 virtual void visit_pre_crement (pre_crement* e) = 0;
764 virtual void visit_post_crement (post_crement* e) = 0;
765 virtual void visit_logical_or_expr (logical_or_expr* e) = 0;
766 virtual void visit_logical_and_expr (logical_and_expr* e) = 0;
767 virtual void visit_array_in (array_in* e) = 0;
768 virtual void visit_comparison (comparison* e) = 0;
769 virtual void visit_concatenation (concatenation* e) = 0;
770 virtual void visit_ternary_expression (ternary_expression* e) = 0;
771 virtual void visit_assignment (assignment* e) = 0;
772 virtual void visit_symbol (symbol* e) = 0;
773 virtual void visit_target_symbol (target_symbol* e) = 0;
774 virtual void visit_arrayindex (arrayindex* e) = 0;
775 virtual void visit_functioncall (functioncall* e) = 0;
776 virtual void visit_print_format (print_format* e) = 0;
777 virtual void visit_stat_op (stat_op* e) = 0;
778 virtual void visit_hist_op (hist_op* e) = 0;
779 virtual void visit_cast_op (cast_op* e) = 0;
780 virtual void visit_defined_op (defined_op* e) = 0;
781 virtual void visit_entry_op (entry_op* e) = 0;
782 };
783
784
785 // A simple kind of visitor, which travels down to the leaves of the
786 // statement/expression tree, up to but excluding following vardecls
787 // and functioncalls.
788 struct traversing_visitor: public visitor
789 {
790 void visit_block (block *s);
791 void visit_try_block (try_block *s);
792 void visit_embeddedcode (embeddedcode *s);
793 void visit_null_statement (null_statement *s);
794 void visit_expr_statement (expr_statement *s);
795 void visit_if_statement (if_statement* s);
796 void visit_for_loop (for_loop* s);
797 void visit_foreach_loop (foreach_loop* s);
798 void visit_return_statement (return_statement* s);
799 void visit_delete_statement (delete_statement* s);
800 void visit_next_statement (next_statement* s);
801 void visit_break_statement (break_statement* s);
802 void visit_continue_statement (continue_statement* s);
803 void visit_literal_string (literal_string* e);
804 void visit_literal_number (literal_number* e);
805 void visit_embedded_expr (embedded_expr* e);
806 void visit_binary_expression (binary_expression* e);
807 void visit_unary_expression (unary_expression* e);
808 void visit_pre_crement (pre_crement* e);
809 void visit_post_crement (post_crement* e);
810 void visit_logical_or_expr (logical_or_expr* e);
811 void visit_logical_and_expr (logical_and_expr* e);
812 void visit_array_in (array_in* e);
813 void visit_comparison (comparison* e);
814 void visit_concatenation (concatenation* e);
815 void visit_ternary_expression (ternary_expression* e);
816 void visit_assignment (assignment* e);
817 void visit_symbol (symbol* e);
818 void visit_target_symbol (target_symbol* e);
819 void visit_arrayindex (arrayindex* e);
820 void visit_functioncall (functioncall* e);
821 void visit_print_format (print_format* e);
822 void visit_stat_op (stat_op* e);
823 void visit_hist_op (hist_op* e);
824 void visit_cast_op (cast_op* e);
825 void visit_defined_op (defined_op* e);
826 void visit_entry_op (entry_op* e);
827 };
828
829
830 // A kind of traversing visitor, which also follows function calls.
831 // It uses an internal set object to prevent infinite recursion.
832 struct functioncall_traversing_visitor: public traversing_visitor
833 {
834 std::set<functiondecl*> traversed;
835 functiondecl* current_function;
836 functioncall_traversing_visitor(): current_function(0) {}
837 void visit_functioncall (functioncall* e);
838 };
839
840
841 // A kind of traversing visitor, which also follows function calls,
842 // and stores the vardecl* referent of each variable read and/or
843 // written and other such sundry side-effect data. It's used by
844 // the elaboration-time optimizer pass.
845 struct varuse_collecting_visitor: public functioncall_traversing_visitor
846 {
847 systemtap_session& session;
848 std::set<vardecl*> read;
849 std::set<vardecl*> written;
850 std::set<vardecl*> used;
851 bool embedded_seen;
852 bool current_lvalue_read;
853 expression* current_lvalue;
854 expression* current_lrvalue;
855 varuse_collecting_visitor(systemtap_session& s):
856 session (s),
857 embedded_seen (false),
858 current_lvalue_read (false),
859 current_lvalue(0),
860 current_lrvalue(0) {}
861 void visit_embeddedcode (embeddedcode *s);
862 void visit_embedded_expr (embedded_expr *e);
863 void visit_try_block (try_block *s);
864 void visit_delete_statement (delete_statement *s);
865 void visit_print_format (print_format *e);
866 void visit_assignment (assignment *e);
867 void visit_arrayindex (arrayindex *e);
868 void visit_target_symbol (target_symbol *e);
869 void visit_symbol (symbol *e);
870 void visit_pre_crement (pre_crement *e);
871 void visit_post_crement (post_crement *e);
872 void visit_foreach_loop (foreach_loop *s);
873 void visit_cast_op (cast_op* e);
874 void visit_defined_op (defined_op* e);
875 void visit_entry_op (entry_op* e);
876
877 bool side_effect_free ();
878 bool side_effect_free_wrt (const std::set<vardecl*>& vars);
879 };
880
881
882
883 // A kind of visitor that throws an semantic_error exception
884 // whenever a non-overridden method is called.
885 struct throwing_visitor: public visitor
886 {
887 std::string msg;
888 throwing_visitor (const std::string& m);
889 throwing_visitor ();
890
891 virtual void throwone (const token* t);
892
893 void visit_block (block *s);
894 void visit_try_block (try_block *s);
895 void visit_embeddedcode (embeddedcode *s);
896 void visit_null_statement (null_statement *s);
897 void visit_expr_statement (expr_statement *s);
898 void visit_if_statement (if_statement* s);
899 void visit_for_loop (for_loop* s);
900 void visit_foreach_loop (foreach_loop* s);
901 void visit_return_statement (return_statement* s);
902 void visit_delete_statement (delete_statement* s);
903 void visit_next_statement (next_statement* s);
904 void visit_break_statement (break_statement* s);
905 void visit_continue_statement (continue_statement* s);
906 void visit_literal_string (literal_string* e);
907 void visit_literal_number (literal_number* e);
908 void visit_embedded_expr (embedded_expr* e);
909 void visit_binary_expression (binary_expression* e);
910 void visit_unary_expression (unary_expression* e);
911 void visit_pre_crement (pre_crement* e);
912 void visit_post_crement (post_crement* e);
913 void visit_logical_or_expr (logical_or_expr* e);
914 void visit_logical_and_expr (logical_and_expr* e);
915 void visit_array_in (array_in* e);
916 void visit_comparison (comparison* e);
917 void visit_concatenation (concatenation* e);
918 void visit_ternary_expression (ternary_expression* e);
919 void visit_assignment (assignment* e);
920 void visit_symbol (symbol* e);
921 void visit_target_symbol (target_symbol* e);
922 void visit_arrayindex (arrayindex* e);
923 void visit_functioncall (functioncall* e);
924 void visit_print_format (print_format* e);
925 void visit_stat_op (stat_op* e);
926 void visit_hist_op (hist_op* e);
927 void visit_cast_op (cast_op* e);
928 void visit_defined_op (defined_op* e);
929 void visit_entry_op (entry_op* e);
930 };
931
932 // A visitor similar to a traversing_visitor, but with the ability to rewrite
933 // parts of the tree through require/provide.
934
935 struct update_visitor: public visitor
936 {
937 template <typename T> T* require (T* src, bool clearok=false)
938 {
939 T* dst = NULL;
940 if (src != NULL)
941 {
942 src->visit(this);
943 assert(!targets.empty());
944 dst = static_cast<T*>(targets.top()); // XXX: danger will robinson: not typesafe!
945 targets.pop();
946 assert(clearok || dst);
947 }
948 return dst;
949 }
950
951 template <typename T> void provide (T* src)
952 {
953 targets.push(static_cast<void*>(src)); // XXX: not typesafe!
954 }
955
956 template <typename T> void replace (T*& src, bool clearok=false)
957 {
958 src = require(src, clearok);
959 }
960
961 virtual ~update_visitor() { assert(targets.empty()); }
962
963 virtual void visit_block (block *s);
964 virtual void visit_try_block (try_block *s);
965 virtual void visit_embeddedcode (embeddedcode *s);
966 virtual void visit_null_statement (null_statement *s);
967 virtual void visit_expr_statement (expr_statement *s);
968 virtual void visit_if_statement (if_statement* s);
969 virtual void visit_for_loop (for_loop* s);
970 virtual void visit_foreach_loop (foreach_loop* s);
971 virtual void visit_return_statement (return_statement* s);
972 virtual void visit_delete_statement (delete_statement* s);
973 virtual void visit_next_statement (next_statement* s);
974 virtual void visit_break_statement (break_statement* s);
975 virtual void visit_continue_statement (continue_statement* s);
976 virtual void visit_literal_string (literal_string* e);
977 virtual void visit_literal_number (literal_number* e);
978 virtual void visit_embedded_expr (embedded_expr* e);
979 virtual void visit_binary_expression (binary_expression* e);
980 virtual void visit_unary_expression (unary_expression* e);
981 virtual void visit_pre_crement (pre_crement* e);
982 virtual void visit_post_crement (post_crement* e);
983 virtual void visit_logical_or_expr (logical_or_expr* e);
984 virtual void visit_logical_and_expr (logical_and_expr* e);
985 virtual void visit_array_in (array_in* e);
986 virtual void visit_comparison (comparison* e);
987 virtual void visit_concatenation (concatenation* e);
988 virtual void visit_ternary_expression (ternary_expression* e);
989 virtual void visit_assignment (assignment* e);
990 virtual void visit_symbol (symbol* e);
991 virtual void visit_target_symbol (target_symbol* e);
992 virtual void visit_arrayindex (arrayindex* e);
993 virtual void visit_functioncall (functioncall* e);
994 virtual void visit_print_format (print_format* e);
995 virtual void visit_stat_op (stat_op* e);
996 virtual void visit_hist_op (hist_op* e);
997 virtual void visit_cast_op (cast_op* e);
998 virtual void visit_defined_op (defined_op* e);
999 virtual void visit_entry_op (entry_op* e);
1000
1001 private:
1002 std::stack<void *> targets;
1003 };
1004
1005 template <> indexable*
1006 update_visitor::require <indexable> (indexable* src, bool clearok);
1007
1008 // A visitor which performs a deep copy of the root node it's applied
1009 // to. NB: It does not copy any of the variable or function
1010 // declarations; those fields are set to NULL, assuming you want to
1011 // re-infer the declarations in a new context (the one you're copying
1012 // to).
1013
1014 struct deep_copy_visitor: public update_visitor
1015 {
1016 template <typename T> static T* deep_copy (T* e)
1017 {
1018 deep_copy_visitor v;
1019 return v.require (e);
1020 }
1021
1022 virtual void visit_block (block *s);
1023 virtual void visit_try_block (try_block *s);
1024 virtual void visit_embeddedcode (embeddedcode *s);
1025 virtual void visit_null_statement (null_statement *s);
1026 virtual void visit_expr_statement (expr_statement *s);
1027 virtual void visit_if_statement (if_statement* s);
1028 virtual void visit_for_loop (for_loop* s);
1029 virtual void visit_foreach_loop (foreach_loop* s);
1030 virtual void visit_return_statement (return_statement* s);
1031 virtual void visit_delete_statement (delete_statement* s);
1032 virtual void visit_next_statement (next_statement* s);
1033 virtual void visit_break_statement (break_statement* s);
1034 virtual void visit_continue_statement (continue_statement* s);
1035 virtual void visit_literal_string (literal_string* e);
1036 virtual void visit_literal_number (literal_number* e);
1037 virtual void visit_embedded_expr (embedded_expr* e);
1038 virtual void visit_binary_expression (binary_expression* e);
1039 virtual void visit_unary_expression (unary_expression* e);
1040 virtual void visit_pre_crement (pre_crement* e);
1041 virtual void visit_post_crement (post_crement* e);
1042 virtual void visit_logical_or_expr (logical_or_expr* e);
1043 virtual void visit_logical_and_expr (logical_and_expr* e);
1044 virtual void visit_array_in (array_in* e);
1045 virtual void visit_comparison (comparison* e);
1046 virtual void visit_concatenation (concatenation* e);
1047 virtual void visit_ternary_expression (ternary_expression* e);
1048 virtual void visit_assignment (assignment* e);
1049 virtual void visit_symbol (symbol* e);
1050 virtual void visit_target_symbol (target_symbol* e);
1051 virtual void visit_arrayindex (arrayindex* e);
1052 virtual void visit_functioncall (functioncall* e);
1053 virtual void visit_print_format (print_format* e);
1054 virtual void visit_stat_op (stat_op* e);
1055 virtual void visit_hist_op (hist_op* e);
1056 virtual void visit_cast_op (cast_op* e);
1057 virtual void visit_defined_op (defined_op* e);
1058 virtual void visit_entry_op (entry_op* e);
1059 };
1060
1061 #endif // STAPTREE_H
1062
1063 /* vim: set sw=2 ts=8 cino=>4,n-2,{2,^-2,t0,(0,u0,w1,M1 : */
This page took 0.081632 seconds and 6 git commands to generate.