00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039 #ifndef CBZ_AST_H
00040 #define CBZ_AST_H
00041
00042
00043
00044
00045 #define REF
00046 #define TREE
00047
00048 #include "register.h"
00049
00076 class Node
00077 {
00078
00079 private:
00080
00086 NodeType _typ;
00087
00095 Coord _coord;
00096
00105 bool _parenthesized;
00106
00114 annote_list _annotations;
00115
00122 FlowVal * _gen;
00123
00130 FlowVal * _kill;
00131
00138
00140 int _uid;
00141
00143 static int _count;
00144
00146 static int _t_count[50];
00147
00149 static int _uid_count;
00150
00152
00153 public:
00154
00162
00164 static node_list nodes;
00165
00167 static map <Node *, bool> deleted_nodes;
00168
00170 bool mark;
00171
00173
00184 Node(NodeType typ, const Coord coord, bool parenthesized = false);
00185
00195 Node(const Node & other);
00196
00203 virtual ~Node();
00204
00209
00218 inline NodeType typ() const { return _typ; }
00219
00232 inline Coord coord() const { return _coord; }
00233
00245 inline void coord(const Coord coord) { _coord = coord; }
00246
00252 inline bool parenthesized() const { return _parenthesized; }
00253
00264 inline void parenthesized(bool paren) { _parenthesized = paren; }
00265
00276 inline annote_list & annotations() { return _annotations; }
00277
00286 inline FlowVal * gen() const { return _gen; }
00287
00299 inline void gen(FlowVal * g) { _gen = g; }
00300
00309 inline FlowVal * kill() const { return _kill; }
00310
00322 inline void kill(FlowVal * k) { _kill = k; }
00323
00325
00332 static void report();
00333
00344 virtual typeNode * type() const { return 0; }
00345
00356 virtual typeNode * base_type(bool TdefIndir) const;
00357
00361 typeNode * datatype() const;
00362
00365 typeNode * datatype_superior() const;
00366
00377
00388 virtual void visit(Visitor * the_visitor) =0;
00389
00398 virtual void walk(Walker & the_walker) =0;
00399
00408 virtual Node * change(Changer & the_changer, bool redispatch = false) =0;
00409
00411
00423 virtual void dataflow(FlowVal * v, FlowProblem & fp) =0;
00424
00432 virtual Node * clone() const =0;
00433
00443 virtual void output(output_context & ct, Node * par) =0;
00444 };
00445
00469 class unitNode : public Node
00470 {
00471
00472 private:
00473
00479 TREE def_list _defs;
00480
00486 int _symbol_level;
00487
00494 Identifiers_table * _types;
00495
00502 Tags_table * _tags;
00503
00510 instruction_list _instructions;
00511
00516 string _input_file;
00517
00523 string _output_file;
00524
00529 int _errors;
00530
00535 int _warnings;
00536
00542 TREE decl_list _undef_funcs;
00543
00544
00545
00546
00555 TREE suespec_list _suespecs;
00556
00562 FILE * _open_input_file(str_list * cpp_flags);
00563
00564 public:
00565
00575 unitNode(string input_file, string output_file,
00576 const Coord coord = Coord::Unknown);
00577
00583 virtual ~unitNode();
00584
00593 void parse(str_list * cpp_flags, bool abortOnError = true);
00594
00599 void fixup();
00600
00605
00606
00607
00608 inline def_list & defs() { return _defs; }
00609 inline const def_list & defs() const { return _defs; }
00610
00611 inline int symbol_level() const { return _symbol_level; }
00612 inline Identifiers_table * types() const { return _types; }
00613 inline Tags_table * tags() const { return _tags; }
00614 inline instruction_list & instructions() { return _instructions; }
00615
00616 inline string & input_file() { return _input_file; }
00617 inline string & output_file() { return _output_file; }
00618
00619 inline int errors() const { return _errors; }
00620 inline void inc_errors() { ++_errors; }
00621
00622 inline int warnings() const { return _warnings; }
00623 inline void inc_warnings() { ++_warnings; }
00624
00625 inline decl_list & undef_funcs() { return _undef_funcs; }
00626
00627 inline suespec_list & suespecs() { return _suespecs; }
00628
00630
00631
00632
00633
00643 void merge_in(def_list * defs) {
00644 _defs.splice(_defs.end(), * defs); delete defs; }
00645
00652 void enter_scope();
00653
00660 void exit_scope();
00661
00666
00667 virtual void visit(Visitor * the_visitor);
00668 virtual void walk(Walker & the_walker);
00669 virtual Node * change(Changer & the_changer, bool redispatch = false);
00670
00672
00673
00674
00675 virtual void dataflow(FlowVal * v, FlowProblem & fp);
00676
00677
00678
00679 virtual Node * clone() const { return new unitNode ( *this ); }
00680
00681
00682
00683 virtual void output(output_context & ct, Node * par);
00684 };
00685
00694 class defNode : public Node
00695 {
00696 private:
00697
00704 text_list _pragmas;
00705
00706 public:
00707
00713 defNode(NodeType typ, const Coord coord);
00714
00719
00720 inline text_list & pragmas() { return _pragmas; }
00721
00723
00729 virtual ~defNode();
00730 };
00731
00742 class declNode : public defNode
00743 {
00744
00745 public:
00746
00755 typedef enum {
00756 UNKNOWN,
00757 TOP,
00759 BLOCK,
00760 FORMAL,
00761 SU,
00762 ENUM,
00763 PROC
00764 } Decl_location;
00765
00772 typedef enum {
00773 NONE, AUTO, EXTERN, REGISTER, STATIC, TYPEDEF
00774 } Storage_class;
00775
00787 struct Storage_location
00788 {
00790 Storage_location()
00791 {
00792
00793 _type = storageloc_unknown;
00794 _stack_offset = 0;
00795 }
00796
00798 enum
00799 {
00800 storageloc_unknown,
00801 storageloc_register,
00802 storageloc_stack,
00803 storageloc_mem_global,
00804 storageloc_advanced,
00806 } _type;
00807
00809 Register _register;
00810
00813 int _stack_offset;
00814 };
00815
00821
00825 static string storage_class_name(Storage_class sc);
00826
00830 static string decl_location_name(Decl_location dl);
00831
00832
00833
00834 private:
00835
00840 TREE typeNode * _type;
00841
00846 string _name;
00847
00853 Decl_location _decl_location;
00854
00860 Storage_class _storage_class;
00861
00867 Storage_location _storage_location;
00868
00874 bool _is_redundant_extern;
00875
00881 TREE exprNode * _init;
00882
00888 TREE exprNode * _bitsize;
00889
00895 int _references;
00896
00902 REF id_list _ref_list;
00903
00908 TREE attrib_list _attribs;
00909
00910 public:
00911
00939 declNode(const char * name, Storage_class sc, typeNode * the_type,
00940 exprNode * init, exprNode * bitsize,
00941 const Coord coord = Coord::Unknown);
00942
00949
00963 declNode(idNode * id, Storage_class sc, typeNode * the_type,
00964 exprNode * init, exprNode * bitsize);
00965
00977 declNode(idNode * name, exprNode * value);
00978
00988 declNode(typeNode * the_type, Storage_class sc);
00989
00991
00997 virtual ~declNode();
00998
01003
01007 inline typeNode * type() const { return _type; }
01008
01013 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; }
01014
01020 inline void type(typeNode * the_type) { _type = the_type; }
01021
01025 inline string & name() { return _name; }
01026
01030 inline void name(string name) { _name = name; }
01031
01035 inline Decl_location decl_location() const { return _decl_location; }
01036
01040 inline void decl_location(Decl_location loc) { _decl_location = loc; }
01041
01045 inline Storage_class storage_class() const { return _storage_class; }
01046
01050 inline void storage_class(Storage_class sc) { _storage_class = sc; }
01051
01058 inline bool is_redundant_extern() const { return _is_redundant_extern; }
01059
01063 inline void set_redundant_extern(bool v) { _is_redundant_extern = v; }
01064
01068 inline void inc_references() { _references++; }
01069
01073 inline exprNode * init() const { return _init; }
01074
01081 void init(exprNode * init) { _init = init; }
01082
01085 inline exprNode * bitsize() const { return _bitsize; }
01086
01092 inline void bitsize(exprNode * bitsize) { _bitsize = bitsize; }
01093
01097 inline int references() const { return _references; }
01098
01102 inline void references(int references) { _references = references; }
01103
01104 inline id_list & ref_list() { return _ref_list; }
01105 inline const id_list & ref_list() const { return _ref_list; }
01106
01110 inline attrib_list & attribs() { return _attribs; }
01111
01115 inline const attrib_list & attribs() const { return _attribs; }
01116
01120 void merge_attribs(attrib_list * attribs);
01121
01125 inline Storage_location & storage_location() { return _storage_location; }
01126
01127
01129
01155
01156
01157
01158 void set_type(typeNode * the_type, Storage_class sc, ScopeState redeclare);
01159 declNode * set_type_and(typeNode * the_type, Storage_class sc, ScopeState redeclare);
01160 declNode * set_type_and(declNode * the_decltype, Storage_class sc, ScopeState redeclare);
01161
01162
01163
01164 void inherit_type(decl_list * others, ScopeState redeclare);
01165 declNode * inherit_type_and(decl_list * others, ScopeState redeclare);
01166
01167
01168
01169 void modify_type(typeNode * the_type);
01170 declNode * modify_type_and(typeNode * the_type);
01171 declNode * modify_type_and(declNode * the_type);
01172
01173
01174
01175 void set_init(exprNode * init);
01176 declNode * set_init_and(exprNode * init);
01177
01178
01179
01180 void add_parameter_types(decl_list * types);
01181 declNode * add_parameter_types_and(decl_list * types);
01182
01183
01184
01185 void finish(Storage_class sc);
01186 declNode * finish_and(Storage_class sc);
01187
01189
01190
01191
01192 typeNode * base_type(bool TdefIndir) const;
01193
01200 typeNode * no_tdef_type();
01201
01210 virtual declNode * original() { return this; }
01211
01216
01217 virtual void visit(Visitor * the_visitor);
01218 virtual void walk(Walker & the_walker);
01219 virtual Node * change(Changer & the_changer, bool redispatch = false);
01220
01222
01223
01224
01225 virtual void dataflow(FlowVal * v, FlowProblem & fp);
01226
01227
01228
01229 virtual Node * clone() const { return new declNode ( *this ); }
01230
01231
01232
01233 virtual void output(output_context & ct, Node * par);
01234 };
01235
01252 class subdeclNode : public declNode
01253 {
01254 private:
01255
01256 REF declNode * _original;
01257 int _index;
01258
01259 public:
01260
01271 subdeclNode(declNode * orig, int index);
01272
01278 virtual ~subdeclNode();
01279
01284
01285 virtual declNode * original() { return _original->original(); }
01286 int index() const { return _index; }
01287
01289
01298 string name_with_index();
01299
01304
01305 virtual void visit(Visitor * the_visitor);
01306 virtual void walk(Walker & the_walker);
01307 virtual Node * change(Changer & the_changer, bool redispatch = false);
01308
01310
01311
01312
01313 virtual Node * clone() const { return new subdeclNode ( *this ); }
01314
01315
01316
01317 virtual void output(output_context & ct, Node * par);
01318 };
01319
01329 class procNode : public defNode
01330 {
01331
01332 private:
01333
01342 TREE declNode * _decl;
01343
01348 TREE blockNode * _body;
01349
01354 instruction_list _instructions;
01355
01360 LirBlockList _lir_blocks;
01361
01372 int _last_stack_local;
01373
01378 unsigned int _stack_frame_size;
01379
01386 static procNode * _current;
01387
01388
01398
01399 FlowVal * _at_entry;
01400 FlowVal * _at_exit;
01401
01403
01404
01405
01406
01407
01408 labelNode * _return_label;
01409 declNode * _return_decl;
01410
01411 public:
01412
01419 procNode(declNode * decl, blockNode * body,
01420 const Coord coord = Coord::Unknown);
01421
01432 procNode(bool old_style, declNode * decl);
01433
01439 virtual ~procNode();
01440
01445
01446
01453 inline declNode * decl() const { return _decl; }
01454
01462 inline declNode * get_decl() { declNode * out = _decl; _decl = 0; return out; }
01463
01470 inline void decl(declNode * decl) { _decl = decl; }
01471
01474 inline blockNode * body() const { return _body; }
01475
01479 inline blockNode * get_body() { blockNode * out = _body; _body = 0; return out; }
01480
01486 inline void body(blockNode * body) { _body = body; }
01487
01490 inline instruction_list & instructions() { return _instructions; }
01491
01494 inline LirBlockList & lir_blocks() { return _lir_blocks; }
01495
01498 void set_initial_stack_local_offset( int offset );
01499
01508 int alloc_stack_local( declNode * decl );
01509
01514 int get_locals_size() { return abs( _last_stack_local ); }
01515
01518 unsigned int stack_frame_size() { return _stack_frame_size; }
01519 void stack_frame_size( unsigned int size ) { _stack_frame_size = size; }
01520
01521
01522
01526 inline FlowVal * at_entry() const { return _at_entry; }
01527
01531 inline void at_entry(FlowVal * ae) { _at_entry = ae; }
01532
01536 inline FlowVal * at_exit() const { return _at_exit; }
01537
01541 inline void at_exit(FlowVal * ae) { _at_exit = ae; }
01542
01544
01545 void return_label(labelNode * label) { _return_label = label; }
01546 labelNode * return_label() { return _return_label; }
01547 void return_decl(declNode * decl) { _return_decl = decl; }
01548 declNode * return_decl() { return _return_decl; }
01549
01561
01566 basicblockNode * entry() const;
01567
01572 basicblockNode * exit() const;
01573
01575
01582
01583
01584
01585 void define(blockNode * body);
01586 procNode * define_and(blockNode * body);
01587
01588 static procNode * current() { return _current; }
01589
01591
01592
01593
01594 typeNode * base_type(bool TdefIndir) const;
01595
01600
01601 virtual void visit(Visitor * the_visitor);
01602 virtual void walk(Walker & the_walker);
01603 virtual Node * change(Changer & the_changer, bool redispatch = false);
01604
01606
01607
01608
01609 virtual void dataflow(FlowVal * v, FlowProblem & fp);
01610
01611
01612
01613 virtual Node * clone() const { return new procNode ( *this ); }
01614
01615
01616
01617 virtual void output(output_context & ct, Node * par);
01618 };
01619
01631 class typeNode : public Node
01632 {
01633
01634 public:
01635
01642 typedef enum {
01643 NONE = 0x0,
01644 CONST = 0x1,
01645 VOLATILE = 0x2,
01646 INLINE = 0x4,
01648 COMPATIBLE = 0x3
01649 } Type_qualifiers;
01650
01659 static string type_qualifiers_name(Type_qualifiers tq);
01660
01673 static typeNode * integral_promotions(typeNode * old_type);
01674
01694 static pair<typeNode *, typeNode *> usual_arithmetic_conversions(typeNode * left,
01695 typeNode * right);
01696
01697 private:
01698
01704 TREE typeNode * _type;
01705
01710 Type_qualifiers _type_qualifiers;
01711
01712
01718 int _alloc_size;
01719
01725 int _alloc_align;
01726
01727 public:
01728
01739 typeNode(NodeType typ, Type_qualifiers tq, typeNode * subtype,
01740 const Coord coord);
01741
01747 virtual ~typeNode();
01748
01753
01756 inline typeNode * type() const { return _type; }
01757
01761 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; }
01762
01768 inline void type(typeNode * the_type) { _type = the_type; }
01769
01772 inline Type_qualifiers type_qualifiers() const { return _type_qualifiers; }
01773
01776 inline void type_qualifiers(Type_qualifiers the_tq) { _type_qualifiers = the_tq; }
01777
01779 inline string type_qualifiers_name() { return type_qualifiers_name(type_qualifiers()); }
01780
01783 inline void add_type_qualifiers(Type_qualifiers the_tq)
01784 { _type_qualifiers = Type_qualifiers(_type_qualifiers | the_tq); }
01785
01789 inline typeNode * add_type_qualifiers_and(Type_qualifiers the_tq)
01790 { add_type_qualifiers(the_tq); return this; }
01791
01794 inline void remove_type_qualifiers(Type_qualifiers the_tq)
01795 { _type_qualifiers = Type_qualifiers(_type_qualifiers & ~the_tq); }
01796
01798 inline int alloc_size(void) const { return _alloc_size; }
01799
01801 inline void alloc_size(int size) { _alloc_size = size; }
01802
01804 inline int alloc_align(void) const { return _alloc_align; }
01805
01807 inline void alloc_align(int align) { _alloc_align = align; }
01808
01810
01817
01818 void finish();
01819 typeNode * finish_and();
01820
01821
01822
01823
01824 void set_base_type(typeNode * base);
01825 typeNode * set_base_type_and(typeNode * base);
01826
01827
01828
01829 void verify_sue_complete();
01830
01832
01843
01852 bool operator==(typeNode & second) {
01853 return equal_to(this, & second, true, true); }
01854
01864 bool operator<=(typeNode & second) {
01865 return equal_to(this, & second, false, false); }
01866
01874 bool operator!=(typeNode & second) {
01875 return ! ( (*this) == second ); }
01876
01878
01900 static bool equal_to(typeNode * first, typeNode * second,
01901 bool strict_toplevel, bool strict_recursive);
01902
01916 virtual bool qualified_equal_to(typeNode * other,
01917 bool strict_toplevel, bool strict_recursive);
01918
01928 typeNode * unwind_tdefs(Type_qualifiers & the_tq);
01929
01930 typeNode * no_tdef_type();
01931
01938 typeNode * follow_tdefs();
01939
01946
01947 virtual bool is_char() const { return false; }
01948 virtual bool is_int() const { return false; }
01949 virtual bool is_float() const { return false; }
01950 virtual bool is_void() const { return false; }
01951 virtual bool is_ellipsis() const { return false; }
01952
01953 virtual bool is_integer() const { return false; }
01954 virtual bool is_arithmetic() const { return false; }
01955 virtual bool is_scalar() const { return false; }
01956 virtual bool is_aggregate() const { return false; }
01957 virtual bool is_derived() const { return false; }
01958 virtual bool is_pointer() const { return false; }
01959
01961
01968 virtual typeNode * usual_unary_conversion_type() { return this; }
01969
01970
01971
01972 virtual typeNode * base_type(bool TdefIndir) const {
01973 return (typeNode *)this; }
01974
01975
01976
01977 typeNode * deep_base_type();
01978
01979
01980
01981
01982 virtual void dataflow(FlowVal * v, FlowProblem & fp) { }
01983
01984
01985
01986 virtual void output(output_context & ct, Node * par);
01987
02000 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q) =0;
02001 };
02002
02012 class primNode : public typeNode
02013 {
02014
02015 private:
02016
02022 basic_type _basic;
02023
02024 public:
02025
02034 primNode(Type_qualifiers tq, basic_type basic,
02035 const Coord coord = Coord::Unknown);
02036
02046 primNode(Type_qualifiers tq,
02047 const Coord coord = Coord::Unknown);
02048
02057 primNode(const Coord coord);
02058
02067 primNode(basic_type basic, const Coord coord = Coord::Unknown);
02068
02074 virtual ~primNode();
02075
02080
02081
02082
02083 inline const basic_type & basic() const { return _basic; }
02084 inline basic_type & basic() { return _basic; }
02085 inline void basic(basic_type basic) { _basic = basic; }
02086
02088
02093
02094
02095 void finish();
02096 primNode * finish_and();
02097
02098
02099
02100 void merge_in(primNode * other);
02101 primNode * merge_in_and(primNode * other);
02102
02104
02111
02112 virtual bool is_int() const { return _basic.is_int(); }
02113 virtual bool is_char() const { return _basic.is_char(); }
02114 virtual bool is_float() const { return _basic.is_float(); }
02115 virtual bool is_void() const { return _basic.is_void(); }
02116 virtual bool is_ellipsis() const { return _basic.is_ellipsis(); }
02117
02118 virtual bool is_integer() const { return _basic.is_integer(); }
02119 virtual bool is_arithmetic() const { return _basic.is_arithmetic(); }
02120 virtual bool is_scalar() const { return _basic.is_scalar(); }
02121
02123
02124
02125
02126 bool qualified_equal_to(typeNode * node2,
02127 bool strict_toplevel, bool strict_recursive);
02128
02133
02134 virtual void visit(Visitor * the_visitor);
02135 virtual void walk(Walker & the_walker);
02136 virtual Node * change(Changer & the_changer, bool redispatch = false);
02137
02139
02140
02141
02142 virtual Node * clone() const { return new primNode ( *this ); }
02143
02144
02145
02146 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02147 };
02148
02165 class tdefNode : public typeNode
02166 {
02167
02168 private:
02169
02175 string _name;
02176
02184 REF typeNode * _def;
02185
02186 public:
02187
02197 tdefNode(Type_qualifiers tq, const char * name,
02198 const Coord coord = Coord::Unknown);
02199
02211 tdefNode(idNode * the_id, Type_qualifiers tq, typeNode * the_type);
02212
02218 virtual ~tdefNode();
02219
02224
02227 inline string & name() { return _name; }
02228
02231 inline void name(string name) { _name = name; }
02232
02235 inline typeNode * def() const { return _def; }
02236
02242 inline void def(typeNode * d) { _def = d; }
02243
02245
02246
02247
02248 typeNode * base_type(bool TdefIndir) const;
02249
02250
02251
02256
02257 virtual void visit(Visitor * the_visitor);
02258 virtual void walk(Walker & the_walker);
02259 virtual Node * change(Changer & the_changer, bool redispatch = false);
02260
02262
02263
02264
02265 virtual Node * clone() const { return new tdefNode ( *this ); }
02266
02267
02268
02269 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02270 };
02271
02281 class ptrNode : public typeNode
02282 {
02283
02284 private:
02285
02286 public:
02287
02297 ptrNode(Type_qualifiers tq, typeNode * the_type,
02298 const Coord coord = Coord::Unknown);
02299
02305 virtual ~ptrNode();
02306
02307
02308
02309 bool qualified_equal_to(typeNode * node2,
02310 bool strict_toplevel, bool strict_recursive);
02311
02318
02319 virtual bool is_scalar() const { return true; }
02320 virtual bool is_derived() const { return true; }
02321 virtual bool is_pointer() const { return true; }
02322
02324
02329
02330 virtual void visit(Visitor * the_visitor);
02331 virtual void walk(Walker & the_walker);
02332 virtual Node * change(Changer & the_changer, bool redispatch = false);
02333
02335
02336
02337
02338 virtual Node * clone() const { return new ptrNode ( *this ); }
02339
02340
02341
02342 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02343 };
02344
02367 class arrayNode : public typeNode
02368 {
02369
02370 private:
02371
02381 TREE exprNode * _dim;
02382
02391 int _size;
02392
02393 public:
02394
02405 arrayNode(Type_qualifiers tq, typeNode * the_type, exprNode * the_dim,
02406 const Coord coord = Coord::Unknown);
02407
02413 virtual ~arrayNode();
02414
02419
02420 inline exprNode * dim() const { return _dim; }
02421 inline exprNode * get_dim() { exprNode * out = _dim; _dim = 0; return out; }
02422 inline void dim(exprNode * the_dim) { _dim = the_dim; }
02423
02424 inline int size() const { return _size; }
02425 inline void size(int the_size) { _size = the_size; }
02426
02428
02435
02436 virtual bool is_aggregate() const { return true; }
02437 virtual bool is_derived() const { return true; }
02438 virtual bool is_pointer() const { return true; }
02439
02440
02441
02442
02443 virtual bool is_scalar() const { return _dim == NULL; }
02444
02445 bool is_string() const;
02446
02448
02449
02450
02451 bool qualified_equal_to(typeNode * node2,
02452 bool strict_toplevel, bool strict_recursive);
02453
02458
02459 virtual void visit(Visitor * the_visitor);
02460 virtual void walk(Walker & the_walker);
02461 virtual Node * change(Changer & the_changer, bool redispatch = false);
02462
02464
02465
02466
02467 virtual Node * clone() const { return new arrayNode ( *this ); }
02468
02469
02470
02471 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02472 };
02473
02484 class funcNode : public typeNode
02485 {
02486
02487 private:
02488
02507 TREE decl_list _args;
02508
02513 bool _is_knr;
02514
02515 public:
02516
02527 funcNode(Type_qualifiers tq, decl_list * args, typeNode * returns,
02528 const Coord coord = Coord::Unknown);
02529
02535 virtual ~funcNode();
02536
02541
02542 inline decl_list & args() { return _args; }
02543 inline const decl_list & args() const { return _args; }
02544
02545 inline typeNode * returns() const { return type(); }
02546 inline void returns(typeNode * returns) { type(returns); }
02547
02548 inline bool is_knr() const { return _is_knr; }
02549 inline void is_knr (bool v) { _is_knr = v; }
02550
02552
02553
02554
02555 bool qualified_equal_to(typeNode * node2,
02556 bool strict_toplevel, bool strict_recursive);
02557
02564
02565 virtual bool is_derived() const { return true; }
02566 virtual bool is_pointer() const { return true; }
02567
02569
02574 bool is_void_args();
02575
02583 bool check_conversions();
02584
02594 bool is_compatible_with(funcNode * nfunc);
02595
02607 void add_parameter_types(decl_list * types);
02608
02613
02614 virtual void visit(Visitor * the_visitor);
02615 virtual void walk(Walker & the_walker);
02616 virtual Node * change(Changer & the_changer, bool redispatch = false);
02617
02619
02620
02621
02622 virtual Node * clone() const { return new funcNode ( *this ); }
02623
02624
02625
02626 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02627 };
02628
02662 class sueNode : public typeNode
02663 {
02664
02665 private:
02666
02672 REF suespecNode * _spec;
02673
02678 bool _elaborated;
02679
02680 public:
02681
02690 sueNode(NodeType typ, const Coord coord);
02691
02697 virtual ~sueNode();
02698
02703
02704 inline bool elaborated() const { return _elaborated; }
02705 inline void elaborated(bool elab) { _elaborated = elab; }
02706
02707 inline suespecNode * spec() const { return _spec; }
02708 inline void spec(suespecNode * s) { _spec = s; }
02709
02711
02715
02716
02717
02718 void set_name_fields(idNode *id, decl_list * fields,
02719 const Coord left_coord,
02720 const Coord the_right_coord);
02721
02722 sueNode * set_name_fields_and(idNode *id, decl_list * fields,
02723 const Coord left_coord,
02724 const Coord the_right_coord);
02725
02726
02727
02728 void set_name(idNode * id, const Coord coord);
02729 sueNode * set_name_and(idNode * id, const Coord coord);
02730
02731
02732
02733 void force_new(const Coord coord);
02734 sueNode * force_new_and(const Coord coord);
02735
02736
02737
02738 bool same_tag_as(sueNode * other);
02739 void tag_conflict(sueNode * new_sue);
02740
02742
02743
02744
02745 bool qualified_equal_to(typeNode * node2,
02746 bool strict_toplevel, bool strict_recursive);
02747
02748
02749
02750
02751
02752 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
02753 };
02754
02769 class structNode : public sueNode
02770 {
02771
02772 private:
02773
02774 public:
02775
02784 structNode(const Coord coord = Coord::Unknown);
02785
02791 virtual ~structNode();
02792
02799
02800 virtual bool is_aggregate() const { return true; }
02801
02803
02808
02809 virtual void visit(Visitor * the_visitor);
02810 virtual void walk(Walker & the_walker);
02811 virtual Node * change(Changer & the_changer, bool redispatch = false);
02812
02814
02815
02816
02817 virtual Node * clone() const { return new structNode ( *this ); }
02818 };
02819
02834 class unionNode : public sueNode
02835 {
02836
02837 private:
02838
02839 public:
02840
02849 unionNode(const Coord coord = Coord::Unknown);
02850
02856 virtual ~unionNode();
02857
02862
02863 virtual void visit(Visitor * the_visitor);
02864 virtual void walk(Walker & the_walker);
02865 virtual Node * change(Changer & the_changer, bool redispatch = false);
02866
02868
02869
02870
02871 virtual Node * clone() const { return new unionNode ( *this ); }
02872 };
02873
02888 class enumNode : public sueNode
02889 {
02890
02891 private:
02892
02893 public:
02894
02903 enumNode(const Coord coord = Coord::Unknown);
02904
02917 enumNode(idNode *id, decl_list * values,
02918 const Coord enum_coord, const Coord left_coord,
02919 const Coord right_coord);
02920
02926 virtual ~enumNode();
02927
02934
02935 virtual bool is_int() const { return true; }
02936 virtual bool is_integer() const { return true; }
02937 virtual bool is_arithmetic() const { return true; }
02938 virtual bool is_scalar() const { return true; }
02939
02941
02946
02947 virtual void visit(Visitor * the_visitor);
02948 virtual void walk(Walker & the_walker);
02949 virtual Node * change(Changer & the_changer, bool redispatch = false);
02950
02952
02953
02954
02955 virtual Node * clone() const { return new enumNode ( *this ); }
02956 };
02957
02974 class suespecNode : public typeNode
02975 {
02976
02977 private:
02978
02986 string _name;
02987
02994 TREE decl_list _fields;
02995
03003 bool _complete;
03004
03012 bool _visited;
03013
03024 int _scope_output;
03025
03030 int _size;
03031
03036 int _align;
03037
03043 NodeType _owner;
03044
03045 public:
03046
03059 suespecNode(const char * name, decl_list * fields, NodeType owner,
03060 unitNode * the_unit,
03061 const Coord coord);
03062
03068 virtual ~suespecNode();
03069
03074
03075 inline bool complete() const { return _complete; }
03076 inline void complete(bool comp) { _complete = comp; }
03077
03078 inline bool visited() const { return _visited; }
03079 inline void visited(bool v) { _visited = v; }
03080
03081 inline bool scope_output() const { return _scope_output; }
03082 inline void scope_output(int v) { _scope_output = v; }
03083
03084 inline int size() const { return _size; }
03085 inline void size(int size) { _size = size; }
03086
03087 inline int align() const { return _align; }
03088 inline void align(int align) { _align = align; }
03089
03090 inline string & name() { return _name; }
03091 inline void name(string name) { _name = name; }
03092
03093 inline decl_list & fields() { return _fields; }
03094 inline const decl_list & fields() const { return _fields; }
03095
03096 inline NodeType owner() const { return _owner; }
03097
03099
03100
03101
03112 bool same_tag_as(suespecNode * other);
03113
03122 void update(decl_list * fields, sueNode * sue, const Coord right);
03123
03133 declNode * find_field(const string & name);
03134
03139
03140 virtual void visit(Visitor * the_visitor);
03141 virtual void walk(Walker & the_walker);
03142 virtual Node * change(Changer & the_changer, bool redispatch = false);
03143
03145
03146
03147
03148 virtual Node * clone() const { return new suespecNode ( *this ); }
03149
03150
03151
03152 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q);
03153 };
03154
03155
03173 class exprNode : public Node
03174 {
03175 public:
03176
03189 static exprNode * integral_promotions(exprNode * old_expr);
03190
03205 static pair<exprNode *, exprNode *>
03206 usual_arithmetic_conversions(exprNode * left,
03207 exprNode * right);
03208
03209 private:
03210
03215 TREE typeNode * _type;
03216
03224 constant _value;
03225
03226 public:
03227
03237 exprNode(NodeType typ, typeNode * type, const Coord coord);
03238
03244 virtual ~exprNode();
03245
03250
03251 virtual typeNode * type() const { return _type; }
03252 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; }
03253 virtual void type(typeNode *type) { _type = type; }
03254
03255 inline const constant & value() const { return _value; }
03256 inline constant & value() { return _value; }
03257 inline void value(const constant & newval) { _value = newval; }
03258
03260
03261
03262
03263 virtual typeNode * base_type(bool TdefIndir) const;
03264
03265
03266
03267
03268
03269
03270
03271
03272
03273
03274
03275
03276
03277
03278
03288 virtual void eval() =0;
03289
03298 virtual bool is_lvalue() { return true; }
03299
03300 typeNode * no_tdef_type() { return type()->follow_tdefs(); }
03301
03302
03303
03304 virtual void output(output_context & ct, Node * par);
03305
03326 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc) =0;
03327
03340 virtual int precedence(Assoc & assoc);
03341
03354 bool parens(int outer_prec, Assoc outer_assoc);
03355 };
03356
03364 class indexNode : public exprNode {
03365 public:
03366 indexNode(NodeType typ, typeNode * type, const Coord coord);
03367 };
03368
03378 class constNode : public indexNode
03379 {
03380
03381 private:
03382
03392 string _text;
03393
03394 public:
03395
03405 constNode(constant value, const char * text = "",
03406 const Coord coord = Coord::Unknown);
03407
03413 virtual ~constNode();
03414
03419
03420 inline string & text() { return _text; }
03421
03423
03428 typeNode * usual_unary_conversion_type()
03429 { return type()->usual_unary_conversion_type(); }
03430
03431
03432
03433 virtual void eval();
03434
03439
03440 virtual void visit(Visitor * the_visitor);
03441 virtual void walk(Walker & the_walker);
03442 virtual Node * change(Changer & the_changer, bool redispatch = false);
03443
03445
03446
03447
03448 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03449
03450
03451
03452 virtual Node * clone() const { return new constNode ( *this ); }
03453
03454
03455
03456 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
03457 };
03458
03470 class idNode : public indexNode
03471 {
03472
03473 private:
03474
03479 string _name;
03480
03488 REF declNode * _decl;
03489
03490 public:
03491
03500 idNode(const char * text, const Coord coord = Coord::Unknown);
03501
03511 idNode(declNode * the_decl, const Coord coord = Coord::Unknown);
03512
03518 virtual ~idNode();
03519
03524
03525 inline string & name() { return _name; }
03526 inline const string & name() const { return _name; }
03527 inline void name(string nm) { _name = nm; }
03528
03529 inline declNode * decl() const { return _decl; }
03530 void decl(declNode *decl);
03531
03533
03534
03535
03536 typeNode * base_type(bool TdefIndir) const;
03537
03538
03539
03540
03541
03542
03543
03544
03545 virtual void eval();
03546
03551
03552 virtual void visit(Visitor * the_visitor);
03553 virtual void walk(Walker & the_walker);
03554 virtual Node * change(Changer & the_changer, bool redispatch = false);
03555
03557
03558
03559
03560 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03561
03562
03563
03564 virtual Node * clone() const { return new idNode ( *this ); }
03565
03566
03567
03568 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
03569 };
03570
03588 class binaryNode : public exprNode
03589 {
03590
03591 private:
03592
03600 Operator * _op;
03601
03604 TREE exprNode * _left;
03605
03608 TREE exprNode * _right;
03609
03610 public:
03611
03630 binaryNode(unsigned int op_id, exprNode * left, exprNode * right,
03631 const Coord coord = Coord::Unknown);
03632
03638 virtual ~binaryNode();
03639
03644
03645 inline Operator * op() const { return _op; }
03646 inline void op(Operator * op) { _op = op; }
03647
03648 inline exprNode * left() const { return _left; }
03649 inline exprNode * get_left() { exprNode * out = _left; _left = 0; return out; }
03650 inline void left(exprNode * left) { _left = left; }
03651
03652 inline exprNode * right() const { return _right; }
03653 inline exprNode * get_right() { exprNode * out = _right; _right = 0; return out; }
03654 inline void right(exprNode * right) { _right = right; }
03655
03657
03658
03659
03660
03661
03662
03663
03664 virtual void eval();
03665
03670
03671 virtual void visit(Visitor * the_visitor);
03672 virtual void walk(Walker & the_walker);
03673 virtual Node * change(Changer & the_changer, bool redispatch = false);
03674
03676
03677
03678
03679 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03680
03681
03682
03683 virtual Node * clone() const { return new binaryNode ( *this ); }
03684
03685
03686
03687 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
03688 virtual int precedence(Assoc & assoc);
03689 };
03690
03699 class unaryNode : public exprNode
03700 {
03701
03702 private:
03703
03711 Operator * _op;
03712
03715 TREE exprNode * _expr;
03716
03721 TREE typeNode * _sizeof_type;
03722
03723 public:
03724
03742 unaryNode(unsigned int op_id, exprNode * expr,
03743 const Coord coord = Coord::Unknown);
03744
03753 unaryNode(unsigned int op_id, typeNode * the_type,
03754 const Coord coord = Coord::Unknown);
03755
03761 virtual ~unaryNode();
03762
03767
03768 inline Operator * op() const { return _op; }
03769 inline void op(Operator * op) { _op = op; }
03770
03771 inline exprNode * expr() const { return _expr; }
03772 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
03773 inline void expr(exprNode * expr) { _expr = expr; }
03774
03775
03776
03777 inline typeNode * sizeof_type() const { return _sizeof_type; }
03778 inline typeNode * get_sizeof_type()
03779 { typeNode * out = _sizeof_type; _sizeof_type = 0; return out; }
03780 inline void sizeof_type(typeNode *sizeof_type)
03781 { _sizeof_type = sizeof_type; }
03782
03784
03785
03786
03787
03788
03789
03790
03791 virtual void eval();
03792
03797
03798 virtual void visit(Visitor * the_visitor);
03799 virtual void walk(Walker & the_walker);
03800 virtual Node * change(Changer & the_changer, bool redispatch = false);
03801
03803
03804
03805
03806 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03807
03808
03809
03810 virtual Node * clone() const { return new unaryNode ( *this ); }
03811
03812
03813
03814 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
03815 virtual int precedence(Assoc & assoc);
03816 };
03817
03833 class castNode : public exprNode
03834 {
03835
03836 private:
03837
03840 TREE exprNode * _expr;
03841
03848 bool _implicit;
03849
03850 public:
03851
03861 castNode(typeNode * type, exprNode * expr, bool implicit = false,
03862 const Coord coord = Coord::Unknown);
03863
03869 virtual ~castNode();
03870
03875
03876 inline exprNode * expr() const { return _expr; }
03877 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
03878 inline void expr(exprNode * expr) { _expr = expr; }
03879
03880 inline bool is_implicit() const { return _implicit; }
03882
03883
03884
03885 virtual void eval();
03886
03891
03892 virtual void visit(Visitor * the_visitor);
03893 virtual void walk(Walker & the_walker);
03894 virtual Node * change(Changer & the_changer, bool redispatch = false);
03895
03897
03898
03899
03900 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03901
03902
03903
03904 virtual Node * clone() const { return new castNode ( *this ); }
03905
03906
03907
03908 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
03909 virtual int precedence(Assoc & assoc);
03910 };
03911
03912
03922 class commaNode : public exprNode
03923 {
03924
03925 private:
03926
03932 TREE expr_list _exprs;
03933
03934 public:
03935
03944 commaNode(expr_list * exprs, const Coord coord = Coord::Unknown);
03945
03952 commaNode(const Coord coord = Coord::Unknown);
03953
03959 virtual ~commaNode();
03960
03965
03966 inline expr_list & exprs() { return _exprs; }
03967 inline const expr_list & exprs() const { return _exprs; }
03968
03970
03971
03972
03973 typeNode * base_type(bool TdefIndir) const;
03974
03975
03976
03977 virtual void eval();
03978
03983
03984 virtual void visit(Visitor * the_visitor);
03985 virtual void walk(Walker & the_walker);
03986 virtual Node * change(Changer & the_changer, bool redispatch = false);
03987
03989
03990
03991
03992 virtual void dataflow(FlowVal * v, FlowProblem & fp);
03993
03994
03995
03996 virtual Node * clone() const { return new commaNode ( *this ); }
03997
03998
03999
04000 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
04001 virtual int precedence(Assoc & assoc);
04002 };
04003
04011 class ternaryNode : public exprNode
04012 {
04013
04014 private:
04015
04018 TREE exprNode * _cond;
04019
04022 TREE exprNode * _true_br;
04023
04026 TREE exprNode * _false_br;
04027
04030 Coord _colon_coord;
04031
04032 public:
04033
04045 ternaryNode(exprNode * cond, exprNode * true_br, exprNode * false_br,
04046 const Coord qmark_coord = Coord::Unknown,
04047 const Coord colon_coord = Coord::Unknown);
04048
04054 virtual ~ternaryNode();
04055
04060
04061 inline exprNode * cond() const { return _cond; }
04062 inline exprNode * get_cond() { exprNode * out = _cond; _cond = 0; return out; }
04063 inline void cond(exprNode * cond) { _cond = cond; }
04064
04065 inline exprNode * true_br() const { return _true_br; }
04066 inline exprNode * get_true_br() { exprNode * out = _true_br; _true_br = 0; return out; }
04067 inline void true_br(exprNode * true_br) { _true_br = true_br; }
04068
04069 inline exprNode * false_br() const { return _false_br; }
04070 inline exprNode * get_false_br() { exprNode * out = _false_br; _false_br = 0; return out; }
04071 inline void false_br(exprNode * false_br) { _false_br = false_br; }
04072
04074
04075
04076
04077 virtual void eval();
04078
04083
04084 virtual void visit(Visitor * the_visitor);
04085 virtual void walk(Walker & the_walker);
04086 virtual Node * change(Changer & the_changer, bool redispatch = false);
04087
04089
04090
04091
04092 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04093
04094
04095
04096 virtual Node * clone() const { return new ternaryNode ( *this ); }
04097
04098
04099
04100 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
04101 virtual int precedence(Assoc & assoc);
04102 };
04103
04131 class callNode : public exprNode
04132 {
04133
04134 private:
04135
04138 TREE exprNode * _name;
04139
04145 TREE expr_list _args;
04146
04156 REF procNode * _proc;
04157
04158 public:
04159
04170 callNode(exprNode * name, expr_list * args,
04171 const Coord coord = Coord::Unknown);
04172
04178 virtual ~callNode();
04179
04184
04185 inline exprNode * name() const { return _name; }
04186 inline exprNode * get_name() { exprNode * out = _name; _name = 0; return out; }
04187 inline void name(exprNode * name) { _name = name; }
04188
04189 inline expr_list & args() { return _args; }
04190 inline const expr_list & args() const { return _args; }
04191
04192 inline procNode * proc() const { return _proc; }
04193 inline void proc(procNode * proc) { _proc = proc; }
04194
04196
04197
04198
04199 typeNode * base_type(bool TdefIndir) const;
04200
04201
04202
04203
04204
04205
04206
04207 virtual void eval();
04208
04213
04214 virtual void visit(Visitor * the_visitor);
04215 virtual void walk(Walker & the_walker);
04216 virtual Node * change(Changer & the_changer, bool redispatch = false);
04217
04219
04220
04221
04222 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04223
04224
04225
04226 virtual Node * clone() const { return new callNode ( *this ); }
04227
04228
04229
04230 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
04231 };
04232
04248 class initializerNode : public exprNode
04249 {
04250
04251 private:
04252
04253 TREE expr_list _exprs;
04254
04255 public:
04256
04257
04258
04259 initializerNode(expr_list * exprs, const Coord coord = Coord::Unknown);
04260
04266 virtual ~initializerNode();
04267
04272
04273 inline expr_list & exprs() { return _exprs; }
04274 inline const expr_list & exprs() const { return _exprs; }
04275 inline void add_expr(exprNode * the_expr) { _exprs.push_back(the_expr); }
04276
04278
04279
04280
04281 virtual void eval();
04282
04287
04288 virtual void visit(Visitor * the_visitor);
04289 virtual void walk(Walker & the_walker);
04290 virtual Node * change(Changer & the_changer, bool redispatch = false);
04291
04293
04294
04295
04296 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04297
04298
04299
04300 virtual Node * clone() const { return new initializerNode ( *this ); }
04301
04302
04303
04304 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc);
04305 };
04306
04314 class stmtNode : public Node
04315 {
04316
04317 private:
04318
04324 FlowVal * _at_exit;
04325
04334 string _comment;
04335
04342 text_list _pragmas;
04343
04344 public:
04345
04354 stmtNode(NodeType typ, const Coord coord);
04355
04361 virtual ~stmtNode();
04362
04367
04368 inline string & comment() { return _comment; }
04369
04370
04371
04372 inline FlowVal * at_exit() const { return _at_exit; }
04373 inline void at_exit(FlowVal * ae) { _at_exit = ae; }
04374
04375
04376
04377 inline text_list & pragmas() { return _pragmas; }
04378
04380
04381
04382
04383 virtual void output(output_context & ct, Node * par);
04384
04395 virtual void output_stmt(output_context & ct, Node * par) =0;
04396
04397 void output_comment(output_context & ct);
04398 };
04399
04418 class blockNode : public stmtNode
04419 {
04420
04421 public:
04422
04452 static blockNode * toBlock(stmtNode * stmt, Coord coord);
04453
04454 private:
04455
04460 TREE decl_list _decls;
04461
04466 TREE stmt_list _stmts;
04467
04470 Coord _right_brace;
04471
04472
04473 public:
04474
04487 blockNode(decl_list * decls, stmt_list * stmts,
04488 const Coord left_coord = Coord::Unknown,
04489 const Coord right_brace = Coord::Unknown);
04490
04496 virtual ~blockNode();
04497
04502
04503 inline decl_list & decls() { return _decls; }
04504 inline const decl_list & decls() const { return _decls; }
04505
04506 inline stmt_list & stmts() { return _stmts; }
04507 inline const stmt_list & stmts() const { return _stmts; }
04508
04509 inline Coord right_brace() const { return _right_brace; }
04510 inline void right_brace(const Coord right_brace) { _right_brace = right_brace; }
04511
04513
04514
04515
04516 typeNode * base_type(bool TdefIndir) const;
04517
04522
04523 virtual void visit(Visitor * the_visitor);
04524 virtual void walk(Walker & the_walker);
04525 virtual Node * change(Changer & the_changer, bool redispatch = false);
04526
04528
04529
04530
04531 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04532
04533
04534
04535 virtual Node * clone() const { return new blockNode ( *this ); }
04536
04537
04538 virtual void output_stmt(output_context & ct, Node * par);
04539
04540 };
04541
04542 class algorithm_info
04543 {
04544 };
04545
04571 class basicblockNode : public blockNode {
04572
04573 private:
04574
04577 basicblock_list _preds;
04578
04581 basicblock_list _succs;
04582
04587 basicblockNode * _parent;
04588
04594 basicblock_list _children;
04595
04601 algorithm_info * _info;
04602
04609 int _dfn;
04610
04617 FlowVal * _at_entry;
04618
04626 FlowVal * _at_exit;
04627
04628 public:
04629
04641 basicblockNode(decl_list * decls, stmt_list * stmts,
04642 const Coord left_coord = Coord::Unknown,
04643 const Coord right_brace = Coord::Unknown);
04644
04650 virtual ~basicblockNode();
04651
04656
04657 inline basicblock_list & preds() { return _preds; }
04658 inline const basicblock_list & preds() const { return _preds; }
04659
04660 inline basicblock_list & succs() { return _succs; }
04661 inline const basicblock_list & succs() const { return _succs; }
04662
04663 inline basicblockNode * parent() const { return _parent; }
04664 inline void parent(basicblockNode *par) { _parent = par; }
04665
04666 inline basicblock_list & children() { return _children; }
04667 inline const basicblock_list & children() const { return _children; }
04668
04669 inline algorithm_info * info() const { return _info; }
04670 inline void info(algorithm_info * i) { _info = i; }
04671
04672 inline int dfn() const { return _dfn; }
04673 inline void dfn(int d) { _dfn = d; }
04674
04675
04676
04677 inline FlowVal * at_entry() const { return _at_entry; }
04678 inline void at_entry(FlowVal * ae) { _at_entry = ae; }
04679
04680 inline FlowVal * at_exit() const { return _at_exit; }
04681 inline void at_exit(FlowVal * ae) { _at_exit = ae; }
04682
04684
04689
04690 virtual void visit(Visitor * the_visitor);
04691 virtual void walk(Walker & the_walker);
04692 virtual Node * change(Changer & the_changer, bool redispatch = false);
04693
04695
04696
04697
04698
04699
04700 virtual Node * clone() const { return new basicblockNode ( *this ); }
04701
04702 };
04703
04704
04705
04715 class exprstmtNode : public stmtNode
04716 {
04717
04718 private:
04719
04722 TREE exprNode * _expr;
04723
04724 public:
04725
04732 exprstmtNode(exprNode * expr);
04733
04739 virtual ~exprstmtNode();
04740
04745
04746 inline exprNode * expr() const { return _expr; }
04747 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
04748 inline void expr(exprNode * expr) { _expr = expr; }
04749
04751
04752
04753
04754 typeNode * base_type(bool TdefIndir) const;
04755
04756
04761
04762 virtual void visit(Visitor * the_visitor);
04763 virtual void walk(Walker & the_walker);
04764 virtual Node * change(Changer & the_changer, bool redispatch = false);
04765
04767
04768
04769
04770 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04771
04772
04773
04774 virtual Node * clone() const { return new exprstmtNode ( *this ); }
04775
04776
04777
04778 virtual void output_stmt(output_context & ct, Node * par);
04779 };
04780
04794 class targetNode : public stmtNode
04795 {
04796
04797 private:
04798
04801 TREE blockNode * _stmt;
04802
04808 FlowVal * _at_entry;
04809
04810 public:
04811
04819 targetNode(NodeType typ, stmtNode * stmt, const Coord coord);
04820
04826 virtual ~targetNode();
04827
04832
04833 inline blockNode * stmt() const { return _stmt; }
04834 inline blockNode * get_stmt() { blockNode * out = _stmt; _stmt = 0; return out; }
04835 inline void stmt(blockNode * stmt) { _stmt = stmt; }
04836
04837
04838
04839 inline FlowVal * at_entry() const { return _at_entry; }
04840 inline void at_entry(FlowVal * ae) { _at_entry = ae; }
04841
04843 };
04844
04859 class labelNode : public targetNode
04860 {
04861
04862 private:
04863
04866 string _name;
04867
04873 REF goto_list _references;
04874
04875 public:
04876
04886 labelNode(const char * name, stmtNode * stmt,
04887 const Coord coord = Coord::Unknown);
04888
04892
04901 labelNode(idNode * ident, stmtNode * stmt);
04902
04910 labelNode(idNode * ident);
04911
04913
04919 virtual ~labelNode();
04920
04925
04926 inline string & name() { return _name; }
04927 inline void name(string name) { _name = name; }
04928
04929 inline goto_list & references() { return _references; }
04930 inline const goto_list & references() const { return _references; }
04931
04933
04934
04935
04936 bool is_undeclared() const;
04937
04942
04943 virtual void visit(Visitor * the_visitor);
04944 virtual void walk(Walker & the_walker);
04945 virtual Node * change(Changer & the_changer, bool redispatch = false);
04946
04948
04949
04950
04951 virtual void dataflow(FlowVal * v, FlowProblem & fp);
04952
04953
04954
04955 virtual Node * clone() const { return new labelNode ( *this ); }
04956
04957
04958
04959 virtual void output_stmt(output_context & ct, Node * par);
04960 };
04961
04976 class caseNode : public targetNode
04977 {
04978
04979 private:
04980
04985 TREE exprNode * _expr;
04986
04993 REF switchNode * _container;
04994
04995 public:
04996
05007 caseNode(exprNode * expr, stmtNode * stmt, switchNode * the_container,
05008 const Coord coord = Coord::Unknown);
05009
05020 caseNode(exprNode * expr, stmtNode * stmt,
05021 const Coord coord = Coord::Unknown);
05022
05028 virtual ~caseNode();
05029
05034
05035 inline exprNode * expr() const { return _expr; }
05036 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
05037 inline void expr(exprNode * expr) { _expr = expr; }
05038
05039 inline switchNode * container() const { return _container; }
05040 void container(switchNode * container);
05041
05043
05048
05049 virtual void visit(Visitor * the_visitor);
05050 virtual void walk(Walker & the_walker);
05051 virtual Node * change(Changer & the_changer, bool redispatch = false);
05052
05054
05055
05056
05057 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05058
05059
05060
05061 virtual Node * clone() const { return new caseNode ( *this ); }
05062
05063
05064
05065 virtual void output_stmt(output_context & ct, Node * par);
05066 };
05067
05080 class selectionNode : public stmtNode
05081 {
05082
05083 private:
05084
05087 TREE exprNode * _expr;
05088
05091 TREE blockNode * _stmt;
05092
05093 public:
05094
05106 selectionNode(NodeType typ, exprNode * expr, stmtNode * stmt,
05107 const Coord coord);
05108
05114 virtual ~selectionNode();
05115
05120
05121 inline exprNode * expr() const { return _expr; }
05122 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
05123 inline void expr(exprNode * expr) { _expr = expr; }
05124
05125 inline blockNode * stmt() const { return _stmt; }
05126 inline blockNode * get_stmt() { blockNode * out = _stmt; _stmt = 0; return out; }
05127 inline void stmt(blockNode * stmt) { _stmt = stmt; }
05128
05130 };
05131
05143 class ifNode : public selectionNode
05144 {
05145
05146 private:
05147
05150 TREE blockNode * _false_br;
05151
05154 Coord _else_coord;
05155
05156 public:
05157
05170 ifNode(exprNode * expr, stmtNode * true_br, stmtNode * false_br,
05171 const Coord if_coord = Coord::Unknown,
05172 const Coord else_coord = Coord::Unknown);
05173
05179 virtual ~ifNode();
05180
05185
05186 inline blockNode * true_br() const { return selectionNode::stmt(); }
05187 inline blockNode * get_true_br() { return selectionNode::get_stmt(); }
05188 inline void true_br(blockNode * true_br) { selectionNode::stmt(true_br); }
05189
05190 inline blockNode * false_br() const { return _false_br; }
05191 inline blockNode * get_false_br() { blockNode * out = _false_br; _false_br = 0; return out; }
05192 inline void false_br(blockNode * false_br) { _false_br = false_br; }
05193
05194 inline Coord else_coord() const { return _else_coord; }
05195 inline void else_coord(const Coord the_coord) { _else_coord = the_coord; }
05196
05198
05203
05204 virtual void visit(Visitor * the_visitor);
05205 virtual void walk(Walker & the_walker);
05206 virtual Node * change(Changer & the_changer, bool redispatch = false);
05207
05209
05210
05211
05212 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05213
05214
05215
05216 virtual Node * clone() const { return new ifNode ( *this ); }
05217
05218
05219
05220 virtual void output_stmt(output_context & ct, Node * par);
05221 };
05222
05235 class switchNode : public selectionNode
05236 {
05237
05238 private:
05239
05245 REF target_list _cases;
05246
05249 bool _has_default;
05250
05256 FlowVal * _at_top;
05257
05258 public:
05259
05269 switchNode(exprNode * expr, stmtNode * stmt,
05270 const Coord coord = Coord::Unknown);
05271
05277 virtual ~switchNode();
05278
05283
05284 inline target_list & cases() { return _cases; }
05285 inline const target_list & cases() const { return _cases; }
05286
05287 inline bool has_default() const { return _has_default; }
05288 inline void has_default(bool has_default) { _has_default = has_default; }
05289
05290 inline FlowVal * at_top() const { return _at_top; }
05291 inline void at_top(FlowVal * at) { _at_top = at; }
05292
05294
05299
05300 virtual void visit(Visitor * the_visitor);
05301 virtual void walk(Walker & the_walker);
05302 virtual Node * change(Changer & the_changer, bool redispatch = false);
05303
05305
05306
05307
05308 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05309
05310
05311
05312 virtual Node * clone() const { return new switchNode ( *this ); }
05313
05314
05315
05316 virtual void output_stmt(output_context & ct, Node * par);
05317 };
05318
05327 class loopNode : public stmtNode
05328 {
05329
05330 private:
05331
05334 TREE exprNode * _cond;
05335
05338 TREE blockNode * _body;
05339
05345 FlowVal * _at_loop_head;
05346
05352 FlowVal * _at_loop_tail;
05353
05354 public:
05355
05367 loopNode(NodeType typ, exprNode * cond, stmtNode * body, const Coord coord);
05368
05376 loopNode(NodeType typ, const Coord coord);
05377
05383 virtual ~loopNode();
05384
05389
05390 inline exprNode * cond() const { return _cond; }
05391 inline exprNode * get_cond() { exprNode * out = _cond; _cond = 0; return out; }
05392 inline void cond(exprNode * cond) { _cond = cond; }
05393
05394 inline blockNode * body() const { return _body; }
05395 inline blockNode * get_body() { blockNode * out = _body; _body = 0; return out; }
05396 inline void body(blockNode * body) { _body = body; }
05397
05398
05399
05400 inline FlowVal * at_loop_head() const { return _at_loop_head; }
05401 inline void at_loop_head(FlowVal * ae) { _at_loop_head = ae; }
05402
05403 inline FlowVal * at_loop_tail() const { return _at_loop_tail; }
05404 inline void at_loop_tail(FlowVal * ae) { _at_loop_tail = ae; }
05405
05407 };
05408
05417 class whileNode : public loopNode
05418 {
05419
05420 private:
05421
05422 public:
05423
05432 whileNode(exprNode * cond, stmtNode * body,
05433 const Coord coord = Coord::Unknown);
05434
05440 virtual ~whileNode();
05441
05446
05447 virtual void visit(Visitor * the_visitor);
05448 virtual void walk(Walker & the_walker);
05449 virtual Node * change(Changer & the_changer, bool redispatch = false);
05450
05452
05453
05454
05455 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05456
05457
05458
05459 virtual Node * clone() const { return new whileNode ( *this ); }
05460
05461
05462
05463 virtual void output_stmt(output_context & ct, Node * par);
05464 };
05465
05474 class doNode : public loopNode
05475 {
05476
05477 private:
05478
05481 Coord _while_coord;
05482
05483 public:
05484
05494 doNode(stmtNode * body, exprNode * cond,
05495 const Coord coord = Coord::Unknown,
05496 const Coord while_coord = Coord::Unknown);
05497
05503 virtual ~doNode();
05504
05509
05510 inline Coord while_coord() const { return _while_coord; }
05511 inline void while_coord(const Coord while_coord) { _while_coord = while_coord; }
05512
05514
05519
05520 virtual void visit(Visitor * the_visitor);
05521 virtual void walk(Walker & the_walker);
05522 virtual Node * change(Changer & the_changer, bool redispatch = false);
05523
05525
05526
05527
05528 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05529
05530
05531
05532 virtual Node * clone() const { return new doNode ( *this ); }
05533
05534
05535
05536 virtual void output_stmt(output_context & ct, Node * par);
05537 };
05538
05560 class forNode : public loopNode
05561 {
05562
05563 private:
05564
05567 TREE exprNode * _init;
05568
05571 TREE exprNode * _next;
05572
05573
05574
05575
05576
05577 public:
05578
05589 forNode(exprNode * init, exprNode * cond, exprNode * next,
05590 stmtNode * body, const Coord coord = Coord::Unknown);
05591
05597 virtual ~forNode();
05598
05603
05604 inline exprNode * init() const { return _init; }
05605 inline exprNode * get_init() { exprNode * out = _init; _init = 0; return out; }
05606 inline void init(exprNode * init) { _init = init; }
05607
05608 inline exprNode * next() const { return _next; }
05609 inline exprNode * get_next() { exprNode * out = _next; _next = 0; return out; }
05610 inline void next(exprNode * next) { _next = next; }
05611
05613
05618
05619 virtual void visit(Visitor * the_visitor);
05620 virtual void walk(Walker & the_walker);
05621 virtual Node * change(Changer & the_changer, bool redispatch = false);
05622
05624
05625
05626
05627 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05628
05629
05630
05631 virtual Node * clone() const { return new forNode ( *this ); }
05632
05633
05634
05635 virtual void output_stmt(output_context & ct, Node * par);
05636 };
05637
05648 class jumpNode : public stmtNode
05649 {
05650
05651 private:
05652
05653 public:
05654
05664 jumpNode(NodeType typ, const Coord coord);
05665
05671 virtual ~jumpNode();
05672
05673 };
05674
05687 class gotoNode : public jumpNode
05688 {
05689
05690 private:
05691
05697 REF labelNode * _label;
05698
05701 string _name;
05702
05703 public:
05704
05713 gotoNode(labelNode * label, const Coord coord = Coord::Unknown,
05714 NodeType typ = Goto);
05715
05725 gotoNode(idNode * ident, const Coord coord);
05726
05732 virtual ~gotoNode();
05733
05738
05739 inline labelNode * label() const { return _label; }
05740 void label(labelNode * label);
05741
05742 inline string & name() { return _name; }
05743 inline void name(string name) { _name = name; }
05744
05746
05751
05752 virtual void visit(Visitor * the_visitor);
05753 virtual void walk(Walker & the_walker);
05754 virtual Node * change(Changer & the_changer, bool redispatch = false);
05755
05757
05758
05759
05760 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05761
05762
05763
05764 virtual Node * clone() const { return new gotoNode ( *this ); }
05765
05766
05767
05768 virtual void output_stmt(output_context & ct, Node * par);
05769 };
05770
05782 class continueNode : public jumpNode
05783 {
05784
05785 private:
05786
05792 REF loopNode * _container;
05793
05794 public:
05795
05804 continueNode(loopNode * container, const Coord coord = Coord::Unknown);
05805
05813 continueNode(const Coord coord = Coord::Unknown);
05814
05820 virtual ~continueNode();
05821
05826
05827 inline loopNode * container() const { return _container; }
05828 inline void container(loopNode * container) { _container = container; }
05829
05831
05836
05837 virtual void visit(Visitor * the_visitor);
05838 virtual void walk(Walker & the_walker);
05839 virtual Node * change(Changer & the_changer, bool redispatch = false);
05840
05842
05843
05844
05845 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05846
05847
05848
05849 virtual Node * clone() const { return new continueNode ( *this ); }
05850
05851
05852
05853 virtual void output_stmt(output_context & ct, Node * par);
05854 };
05855
05867 class breakNode : public jumpNode
05868 {
05869
05870 private:
05871
05878 REF stmtNode * _container;
05879
05880 public:
05881
05890 breakNode(stmtNode * container, const Coord coord = Coord::Unknown);
05891
05899 breakNode(const Coord coord = Coord::Unknown);
05900
05906 virtual ~breakNode();
05907
05912
05913 inline stmtNode * container() const { return _container; }
05914 inline void container(stmtNode * container) { _container = container; }
05915
05917
05922
05923 virtual void visit(Visitor * the_visitor);
05924 virtual void walk(Walker & the_walker);
05925 virtual Node * change(Changer & the_changer, bool redispatch = false);
05926
05928
05929
05930
05931 virtual void dataflow(FlowVal * v, FlowProblem & fp);
05932
05933
05934
05935 virtual Node * clone() const { return new breakNode ( *this ); }
05936
05937
05938
05939 virtual void output_stmt(output_context & ct, Node * par);
05940 };
05941
05951 class returnNode : public jumpNode
05952 {
05953
05954 private:
05955
05958 TREE exprNode * _expr;
05959
05962 REF procNode * _proc;
05963
05968 bool _is_proc_exit;
05969
05970 public:
05971
05982 returnNode(exprNode * expr, procNode * proc,
05983 const Coord coord = Coord::Unknown);
05984
05985 returnNode(exprNode * expr, procNode * proc, bool proc_exit,
05986 const Coord coord = Coord::Unknown);
05987
05993 virtual ~returnNode();
05994
05999
06000 inline exprNode * expr() const { return _expr; }
06001 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; }
06002 inline void expr(exprNode * expr) { _expr = expr; }
06003
06004 inline procNode * proc() const { return _proc; }
06005 inline void proc(procNode * proc) { _proc = proc; }
06006
06007 bool proc_exit() { return _is_proc_exit; }
06008 private:
06009 void proc_exit(bool proc_exit) { _is_proc_exit = proc_exit; }
06010 public:
06011
06013
06018
06019 virtual void visit(Visitor * the_visitor);
06020 virtual void walk(Walker & the_walker);
06021 virtual Node * change(Changer & the_changer, bool redispatch = false);
06022
06024
06025
06026
06027 virtual void dataflow(FlowVal * v, FlowProblem & fp);
06028
06029
06030
06031 virtual Node * clone() const;
06032
06033
06034
06035 virtual void output_stmt(output_context & ct, Node * par);
06036 };
06037
06044 class attribNode : public stmtNode
06045 {
06046
06047 private:
06048
06049 TREE exprNode * _arg;
06050 string _name;
06051
06052 public:
06053
06054
06055
06056 attribNode(const char * name, exprNode * arg,
06057 const Coord coord = Coord::Unknown);
06058
06059
06060
06061 attribNode(idNode * id, exprNode * arg);
06062
06068 virtual ~attribNode();
06069
06074
06075 inline string & name() { return _name; }
06076 inline void name(string name) { _name = name; }
06077
06078 inline exprNode * arg() const { return _arg; }
06079 inline exprNode * get_arg() { exprNode * out = _arg; _arg = 0; return out; }
06080 inline void arg(exprNode * arg) { _arg = arg; }
06081
06083
06088
06089 virtual void visit(Visitor * the_visitor);
06090 virtual void walk(Walker & the_walker);
06091 virtual Node * change(Changer & the_changer, bool redispatch = false);
06092
06094
06095
06096
06097 virtual void dataflow(FlowVal * v, FlowProblem & fp) {}
06098
06099
06100
06101 virtual Node * clone() const { return new attribNode ( *this ); }
06102
06103
06104
06105 virtual void output_stmt(output_context & ct, Node * par);
06106 };
06107
06126 class operandNode : public exprNode {
06127 private:
06128 bool _star;
06129 bool _addr;
06130 typeNode * _cast;
06131 indexNode * _var;
06132 id_list _fields;
06133 indexNode * _index;
06134 public:
06135 operandNode(indexNode * the_var, const Coord coord = Coord::Unknown);
06136 operandNode(indexNode * the_var, bool star, bool addr,
06137 const Coord coord = Coord::Unknown);
06138 operandNode(indexNode * the_var, bool star, bool addr, id_list * fields,
06139 indexNode * array_index, const Coord coord = Coord::Unknown);
06140
06141 void addr(bool addr) { _addr = addr; }
06142 bool addr() const { return _addr; }
06143 void star(bool star) { _star = star; }
06144 bool star() const { return _star; }
06145 void cast(typeNode * cast) { _cast = cast; }
06146 typeNode * cast(void) { return _cast; }
06147 const typeNode * cast(void) const { return _cast; }
06148 inline id_list & fields() { return _fields; }
06149 inline const id_list & fields() const { return _fields; }
06150 void index(indexNode * index) { _index = index; }
06151 indexNode * index(void) { return _index; }
06152 const indexNode * index(void) const { return _index; }
06153 void var(indexNode * var) { _var = var; }
06154 indexNode * var(void) { return _var; }
06155 const indexNode * var(void) const { return _var; }
06156
06157
06158
06159
06160 virtual typeNode * type() const;
06161 virtual void type(typeNode *);
06162 virtual typeNode * noncast_type(bool convertArrays = true) const;
06163
06164 virtual void eval();
06165 virtual void visit(Visitor * the_visitor);
06166 virtual void walk(Walker & the_walker);
06167 virtual Node * change(Changer & the_changer, bool redispatch = false);
06168 virtual void dataflow(FlowVal * v, FlowProblem & fp);
06169 virtual Node * clone() const { return new operandNode(*this); }
06170 virtual void output_expr(output_context & ct, Node * parent, int prec,
06171 Assoc assoc);
06172 };
06173
06174
06185 class conditiongotoNode : public gotoNode {
06186 private:
06187 indexNode * _oper1;
06188 indexNode * _oper2;
06189 Operator * _op;
06190 public:
06191
06192 conditiongotoNode(labelNode * label, indexNode * left, unsigned int op_id,
06193 indexNode * right, const Coord coord = Coord::Unknown);
06194
06195 void left(indexNode * left) { _oper1 = left; }
06196 indexNode * left(void) { return _oper1; }
06197 void right(indexNode * right) { _oper2 = right; }
06198 indexNode * right(void) { return _oper2; }
06199 void op(Operator * op);
06200
06201 Operator * op(void) { return _op; }
06202
06203 virtual void visit(Visitor * the_visitor);
06204 virtual void walk(Walker & the_walker);
06205 virtual Node * change(Changer & the_changer, bool redispatch = false);
06206 virtual void dataflow(FlowVal * v, FlowProblem & fp);
06207 virtual Node * clone() const { return new conditiongotoNode(*this); }
06208 virtual void output_stmt(output_context & ct, Node * par);
06209 };
06210
06211
06212
06236 class threeAddrNode : public stmtNode {
06237 private:
06238 operandNode * _lhs;
06239 operandNode * _rhs1;
06240 Operator * _op;
06241 operandNode * _rhs2;
06242 typeNode * _sizeof_type;
06243 operand_list _arg_list;
06244 public:
06245
06246 threeAddrNode(operandNode * lhs, operandNode * rhs,
06247 const Coord coord = Coord::Unknown);
06248
06249 threeAddrNode(operandNode * lhs, unsigned int op_id,
06250 operandNode * rhs, const Coord coord = Coord::Unknown);
06251
06252 threeAddrNode(operandNode * lhs, typeNode * type,
06253 const Coord coord = Coord::Unknown);
06254
06255 threeAddrNode(operandNode * lhs, operandNode * rhs1, unsigned int op_id,
06256 operandNode * rhs2, const Coord coord = Coord::Unknown);
06257
06258 threeAddrNode(operandNode * lhs, operandNode * func,
06259 operand_list * arg_list, const Coord coord = Coord::Unknown);
06260
06261 threeAddrNode(operandNode * func, operand_list * arg_list,
06262 const Coord coord = Coord::Unknown);
06263
06264 void lhs(operandNode * lhs) { _lhs = lhs; }
06265 operandNode * lhs(void) { return _lhs; }
06266 void rhs1(operandNode * rhs1) { _rhs1 = rhs1; }
06267 operandNode * rhs1(void) { return _rhs1; }
06268 void op(Operator * op) { _op = op; }
06269
06270 Operator * op(void) { return _op; }
06271
06272 void rhs2(operandNode * rhs2) { _rhs2 = rhs2; }
06273 operandNode * rhs2(void) { return _rhs2; }
06274 void sizeof_type(typeNode * type) { _sizeof_type = type; }
06275 typeNode * sizeof_type(void) { return _sizeof_type; }
06276 inline operand_list & arg_list() { return _arg_list; }
06277 inline const operand_list & arg_list() const { return _arg_list; }
06278
06279 virtual void visit(Visitor * the_visitor);
06280 virtual void walk(Walker & the_walker);
06281 virtual Node * change(Changer & the_changer, bool redispatch = false);
06282 virtual void dataflow(FlowVal * v, FlowProblem & fp);
06283 virtual Node * clone() const { return new threeAddrNode(*this); }
06284 virtual void output_stmt(output_context & ct, Node * par);
06285 };
06286
06293 class textNode : public Node
06294 {
06295
06296 private:
06297
06298 string _text;
06299 bool _start_new_line;
06300
06301 public:
06302
06303
06304
06305 textNode(const char * text, bool start_new_line,
06306 const Coord coord = Coord::Unknown);
06307
06313 virtual ~textNode();
06314
06319
06320 inline string & text() { return _text; }
06321 inline void text(string text) { _text = text; }
06322
06323 inline bool start_new_line() const { return _start_new_line; }
06324 inline void start_new_line(bool start_new_line) { _start_new_line = start_new_line; }
06325
06327
06332
06333 virtual void visit(Visitor * the_visitor);
06334 virtual void walk(Walker & the_walker);
06335 virtual Node * change(Changer & the_changer, bool redispatch = false);
06336
06338
06339
06340
06341 virtual void dataflow(FlowVal * v, FlowProblem & fp) {}
06342
06343
06344
06345 virtual Node * clone() const { return new textNode ( *this ); }
06346
06347
06348
06349 virtual void output(output_context & ct, Node * par);
06350 };
06351
06352
06353
06354
06355
06356 template< class T >
06357 void dataflow_forward_list(list< T > & l, FlowVal * v, FlowProblem & fp)
06358 {
06359 for (typename list< T >::iterator p = l.begin();
06360 p != l.end();
06361 ++p)
06362 (*p)->dataflow(v, fp);
06363 }
06364
06365 template< class T >
06366 void dataflow_reverse_list(list< T > & l, FlowVal * v, FlowProblem & fp)
06367 {
06368 for (typename list< T >::reverse_iterator p = l.rbegin();
06369 p != l.rend();
06370 ++p)
06371 (*p)->dataflow(v, fp);
06372 }
06373
06374 template< class T >
06375 void output_list(list< T > & l, output_context & ct, Node * par)
06376 {
06377 for (typename list< T >::iterator p = l.begin();
06378 p != l.end();
06379 ++p)
06380 (*p)->output(ct, par);
06381 }
06382
06383 template< class T >
06384 void output_delim_list(list< T > & l, output_context & ct, Node * par, char delim)
06385 {
06386 for (typename list< T >::iterator p = l.begin();
06387 p != l.end();
06388 ++p)
06389 {
06390 if (p != l.begin()) {
06391 ct << delim;
06392 ct.space();
06393 ct.continue_line();
06394 }
06395 (*p)->output(ct, par);
06396 }
06397 }
06398
06399 template< class T >
06400 void delete_list(list< T > & l)
06401 {
06402 for (typename list< T >::iterator p = l.begin();
06403 p != l.end();
06404 ++p)
06405 delete (*p);
06406 }
06407
06408 #endif // CBZ_AST_H