|
||
Main Page | Modules | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages
ast.hGo to the documentation of this file.00001 // $Id: ast.h,v 1.34 2003/11/11 19:23:14 benh Exp $ 00002 // ---------------------------------------------------------------------- 00003 // 00004 // C-Breeze 00005 // C Compiler Framework 00006 // 00007 // Copyright (c) 2000 University of Texas at Austin 00008 // 00009 // Samuel Z. Guyer 00010 // Daniel A. Jimenez 00011 // Calvin Lin 00012 // Adam Brown 00013 // 00014 // Permission is hereby granted, free of charge, to any person 00015 // obtaining a copy of this software and associated documentation 00016 // files (the "Software"), to deal in the Software without 00017 // restriction, including without limitation the rights to use, copy, 00018 // modify, merge, publish, distribute, sublicense, and/or sell copies 00019 // of the Software, and to permit persons to whom the Software is 00020 // furnished to do so, subject to the following conditions: 00021 // 00022 // The above copyright notice and this permission notice shall be 00023 // included in all copies or substantial portions of the Software. 00024 // 00025 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 00026 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 00027 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 00028 // NONINFRINGEMENT. IN NO EVENT SHALL THE UNIVERSITY OF TEXAS AT 00029 // AUSTIN BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 00030 // IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF 00031 // OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 00032 // THE SOFTWARE. 00033 // 00034 // We acknowledge the C-to-C Translator from MIT Laboratory for 00035 // Computer Science for inspiring parts of the C-Breeze design. 00036 // 00037 // ---------------------------------------------------------------------- 00038 00039 #ifndef CBZ_AST_H 00040 #define CBZ_AST_H 00041 00042 00043 // -- REF and TREE are empty defines for information only 00044 00045 #define REF 00046 #define TREE 00047 00074 class Node 00075 { 00076 00077 private: 00078 00084 NodeType _typ; 00085 00093 Coord _coord; 00094 00103 bool _parenthesized; 00104 00112 annote_list _annotations; 00113 00120 FlowVal * _gen; 00121 00128 FlowVal * _kill; 00129 00136 00138 int _uid; 00139 00141 static int _count; 00142 00144 static int _t_count[50]; 00145 00147 static int _uid_count; 00148 00150 00151 public: 00152 00160 00162 static node_list nodes; 00163 00165 static map <Node *, bool> deleted_nodes; 00166 00168 bool mark; 00169 00171 00182 Node(NodeType typ, const Coord coord, bool parenthesized = false); 00183 00193 Node(const Node & other); 00194 00201 virtual ~Node(); 00202 00207 00216 inline NodeType typ() const { return _typ; } 00217 00230 inline Coord coord() const { return _coord; } 00231 00243 inline void coord(const Coord coord) { _coord = coord; } 00244 00250 inline bool parenthesized() const { return _parenthesized; } 00251 00262 inline void parenthesized(bool paren) { _parenthesized = paren; } 00263 00274 inline annote_list & annotations() { return _annotations; } 00275 00284 inline FlowVal * gen() const { return _gen; } 00285 00297 inline void gen(FlowVal * g) { _gen = g; } 00298 00307 inline FlowVal * kill() const { return _kill; } 00308 00320 inline void kill(FlowVal * k) { _kill = k; } 00321 00323 00330 static void report(); 00331 00342 virtual typeNode * type() const { return 0; } 00343 00354 virtual typeNode * base_type(bool TdefIndir) const; 00355 00359 typeNode * datatype() const; 00360 00363 typeNode * datatype_superior() const; 00364 00375 00386 virtual void visit(Visitor * the_visitor) =0; 00387 00396 virtual void walk(Walker & the_walker) =0; 00397 00406 virtual Node * change(Changer & the_changer, bool redispatch = false) =0; 00407 00409 00421 virtual void dataflow(FlowVal * v, FlowProblem & fp) =0; 00422 00430 virtual Node * clone() const =0; 00431 00441 virtual void output(output_context & ct, Node * par) =0; 00442 }; 00443 00467 class unitNode : public Node 00468 { 00469 00470 private: 00471 00477 TREE def_list _defs; 00478 00484 int _symbol_level; 00485 00492 int _pragma_level; 00493 00500 Identifiers_table * _types; 00501 00508 Tags_table * _tags; 00509 00514 string _input_file; 00515 00521 string _output_file; 00522 00527 string _obj_file; 00528 00533 int _errors; 00534 00539 int _warnings; 00540 00546 TREE decl_list _undef_funcs; 00547 00548 // -- Maintain a global list of all struct/enum/union. This means 00549 // that the spec component of a sueNode is never a part of the TREE. 00550 00559 TREE suespec_list _suespecs; 00560 00566 FILE * _open_input_file(str_list * cpp_flags); 00567 00574 text_list _pragmas; 00575 00576 public: 00577 00588 unitNode(string input_file, string output_file, string obj_file, 00589 const Coord coord = Coord::Unknown); 00590 00596 virtual ~unitNode(); 00597 00606 void parse(str_list * cpp_flags, bool abortOnError = true); 00607 00612 void fixup(); 00613 00618 00619 // -- Fields 00620 00621 inline def_list & defs() { return _defs; } 00622 inline const def_list & defs() const { return _defs; } 00623 00624 inline int symbol_level() const { return _symbol_level; } 00625 inline int pragma_level() const { return _pragma_level; } 00626 inline Identifiers_table * types() const { return _types; } 00627 inline Tags_table * tags() const { return _tags; } 00628 00629 inline string & input_file() { return _input_file; } 00630 inline string & output_file() { return _output_file; } 00631 inline string & obj_file() { return _obj_file; } 00632 00633 inline int errors() const { return _errors; } 00634 inline void inc_errors() { ++_errors; } 00635 00636 inline int warnings() const { return _warnings; } 00637 inline void inc_warnings() { ++_warnings; } 00638 00639 inline decl_list & undef_funcs() { return _undef_funcs; } 00640 00641 inline suespec_list & suespecs() { return _suespecs; } 00642 00643 inline text_list & pragmas() { return _pragmas; } 00645 00646 // -- Merge in definitions... 00647 // NOTE: the defs is deleted 00648 00658 void merge_in(def_list * defs) { 00659 _defs.splice(_defs.end(), * defs); delete defs; } 00660 00667 void enter_scope(); 00668 00675 void exit_scope(); 00676 00682 void enter_pragmas(); 00683 00689 void exit_pragmas(); 00690 00695 00696 virtual void visit(Visitor * the_visitor); 00697 virtual void walk(Walker & the_walker); 00698 virtual Node * change(Changer & the_changer, bool redispatch = false); 00699 00701 00702 // -- Dataflow 00703 00704 virtual void dataflow(FlowVal * v, FlowProblem & fp); 00705 00706 // -- Clone 00707 00708 virtual Node * clone() const { return new unitNode ( *this ); } 00709 00710 // -- Output 00711 00712 virtual void output(output_context & ct, Node * par); 00713 }; 00714 00723 class defNode : public Node 00724 { 00725 private: 00726 00733 text_list _pragmas; 00734 00735 public: 00736 00742 defNode(NodeType typ, const Coord coord); 00743 00748 00749 inline text_list & pragmas() { return _pragmas; } 00750 00752 00757 virtual void grab_pragmas(void); 00758 00764 virtual ~defNode(); 00765 }; 00766 00777 class declNode : public defNode 00778 { 00779 00780 public: 00781 00790 typedef enum { 00791 UNKNOWN, 00792 TOP, 00794 BLOCK, 00795 FORMAL, 00796 SU, 00797 ENUM, 00798 PROC 00799 } Decl_location; 00800 00807 typedef enum { 00808 NONE, AUTO, EXTERN, REGISTER, STATIC, TYPEDEF 00809 } Storage_class; 00810 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 bool _is_redundant_extern; 00868 00874 TREE exprNode * _init; 00875 00881 TREE exprNode * _bitsize; 00882 00888 int _references; 00889 00895 REF id_list _ref_list; 00896 00901 TREE attrib_list _attribs; 00902 00903 public: 00904 00932 declNode(const char * name, Storage_class sc, typeNode * the_type, 00933 exprNode * init, exprNode * bitsize, 00934 const Coord coord = Coord::Unknown); 00935 00942 00956 declNode(idNode * id, Storage_class sc, typeNode * the_type, 00957 exprNode * init, exprNode * bitsize); 00958 00970 declNode(idNode * name, exprNode * value); 00971 00981 declNode(typeNode * the_type, Storage_class sc); 00982 00984 00990 virtual ~declNode(); 00991 00996 01000 inline typeNode * type() const { return _type; } 01001 01006 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; } 01007 01013 inline void type(typeNode * the_type) { _type = the_type; } 01014 01018 inline string & name() { return _name; } 01019 01023 inline void name(string name) { _name = name; } 01024 01028 inline Decl_location decl_location() const { return _decl_location; } 01029 01033 inline void decl_location(Decl_location loc) { _decl_location = loc; } 01034 01038 inline Storage_class storage_class() const { return _storage_class; } 01039 01043 inline void storage_class(Storage_class sc) { _storage_class = sc; } 01044 01051 inline bool is_redundant_extern() const { return _is_redundant_extern; } 01052 01056 inline void set_redundant_extern(bool v) { _is_redundant_extern = v; } 01057 01061 inline void inc_references() { _references++; } 01062 01066 inline exprNode * init() const { return _init; } 01067 01074 void init(exprNode * init) { _init = init; } 01075 01078 inline exprNode * bitsize() const { return _bitsize; } 01079 01085 inline void bitsize(exprNode * bitsize) { _bitsize = bitsize; } 01086 01090 inline int references() const { return _references; } 01091 01095 inline void references(int references) { _references = references; } 01096 01097 inline id_list & ref_list() { return _ref_list; } 01098 inline const id_list & ref_list() const { return _ref_list; } 01099 01103 inline attrib_list & attribs() { return _attribs; } 01104 01108 inline const attrib_list & attribs() const { return _attribs; } 01109 01113 void merge_attribs(attrib_list * attribs); 01114 01116 01142 01143 // Was SetDeclType in complex-types.c 01144 01145 void set_type(typeNode * the_type, Storage_class sc, ScopeState redeclare); 01146 declNode * set_type_and(typeNode * the_type, Storage_class sc, ScopeState redeclare); 01147 declNode * set_type_and(declNode * the_decltype, Storage_class sc, ScopeState redeclare); 01148 01149 // Was AppendDecl in complex-types.c 01150 01151 void inherit_type(decl_list * others, ScopeState redeclare); 01152 declNode * inherit_type_and(decl_list * others, ScopeState redeclare); 01153 01154 // Was ModifyType in complex-types.c 01155 01156 void modify_type(typeNode * the_type); 01157 declNode * modify_type_and(typeNode * the_type); 01158 declNode * modify_type_and(declNode * the_type); 01159 01160 // Was SetDeclInit in complex-types.c 01161 01162 void set_init(exprNode * init); 01163 declNode * set_init_and(exprNode * init); 01164 01165 // Was AddParameterTypes in procedure.c 01166 01167 void add_parameter_types(decl_list * types); 01168 declNode * add_parameter_types_and(decl_list * types); 01169 01170 // FinishDecl in complex-types.c 01171 01172 void finish(Storage_class sc); 01173 declNode * finish_and(Storage_class sc); 01174 01176 01177 // -- Data type base 01178 01179 typeNode * base_type(bool TdefIndir) const; 01180 01187 typeNode * no_tdef_type(); 01188 01197 virtual declNode * original() { return this; } 01198 01203 01204 virtual void visit(Visitor * the_visitor); 01205 virtual void walk(Walker & the_walker); 01206 virtual Node * change(Changer & the_changer, bool redispatch = false); 01207 01209 01210 // -- Dataflow 01211 01212 virtual void dataflow(FlowVal * v, FlowProblem & fp); 01213 01214 // -- Clone 01215 01216 virtual Node * clone() const { return new declNode ( *this ); } 01217 01218 // -- Output 01219 01220 virtual void output(output_context & ct, Node * par); 01221 }; 01222 01239 class subdeclNode : public declNode 01240 { 01241 private: 01242 01243 REF declNode * _original; 01244 int _index; 01245 01246 public: 01247 01258 subdeclNode(declNode * orig, int index); 01259 01265 virtual ~subdeclNode(); 01266 01271 01272 virtual declNode * original() { return _original->original(); } 01273 int index() const { return _index; } 01274 01276 01285 string name_with_index(); 01286 01291 01292 virtual void visit(Visitor * the_visitor); 01293 virtual void walk(Walker & the_walker); 01294 virtual Node * change(Changer & the_changer, bool redispatch = false); 01295 01297 01298 // -- Clone 01299 01300 virtual Node * clone() const { return new subdeclNode ( *this ); } 01301 01302 // -- Output 01303 01304 virtual void output(output_context & ct, Node * par); 01305 }; 01306 01316 class procNode : public defNode 01317 { 01318 01319 private: 01320 01329 TREE declNode * _decl; 01330 01335 TREE blockNode * _body; 01336 01343 static procNode * _current; 01344 01345 01355 01356 FlowVal * _at_entry; 01357 FlowVal * _at_exit; 01358 01360 01361 /* These fields are set by the ThreeAddrReturnDismantle. 01362 * They are only valid in dismantled code 01363 */ 01364 01365 labelNode * _return_label; 01366 declNode * _return_decl; 01367 01368 public: 01369 01376 procNode(declNode * decl, blockNode * body, 01377 const Coord coord = Coord::Unknown); 01378 01389 procNode(bool old_style, declNode * decl); 01390 01396 virtual ~procNode(); 01397 01402 01403 01410 inline declNode * decl() const { return _decl; } 01411 01419 inline declNode * get_decl() { declNode * out = _decl; _decl = 0; return out; } 01420 01427 inline void decl(declNode * decl) { _decl = decl; } 01428 01431 inline blockNode * body() const { return _body; } 01432 01436 inline blockNode * get_body() { blockNode * out = _body; _body = 0; return out; } 01437 01443 inline void body(blockNode * body) { _body = body; } 01444 01445 // -- Flow values (for IP analyzer) 01446 01450 inline FlowVal * at_entry() const { return _at_entry; } 01451 01455 inline void at_entry(FlowVal * ae) { _at_entry = ae; } 01456 01460 inline FlowVal * at_exit() const { return _at_exit; } 01461 01465 inline void at_exit(FlowVal * ae) { _at_exit = ae; } 01466 01468 01469 void return_label(labelNode * label) { _return_label = label; } 01470 labelNode * return_label() { return _return_label; } 01471 void return_decl(declNode * decl) { _return_decl = decl; } 01472 declNode * return_decl() { return _return_decl; } 01473 01485 01490 basicblockNode * entry() const; 01491 01496 basicblockNode * exit() const; 01497 01499 01506 01507 // -- DefineProc in procedure.c 01508 01509 void define(blockNode * body); 01510 procNode * define_and(blockNode * body); 01511 01512 static procNode * current() { return _current; } 01513 01515 01516 // -- Data type base 01517 01518 typeNode * base_type(bool TdefIndir) const; 01519 01524 01525 virtual void visit(Visitor * the_visitor); 01526 virtual void walk(Walker & the_walker); 01527 virtual Node * change(Changer & the_changer, bool redispatch = false); 01528 01530 01531 // -- Dataflow 01532 01533 virtual void dataflow(FlowVal * v, FlowProblem & fp); 01534 01535 // -- Clone 01536 01537 virtual Node * clone() const { return new procNode ( *this ); } 01538 01539 // -- Output 01540 01541 virtual void output(output_context & ct, Node * par); 01542 }; 01543 01555 class typeNode : public Node 01556 { 01557 01558 public: 01559 01566 typedef enum { 01567 NONE = 0x0, 01568 CONST = 0x1, 01569 VOLATILE = 0x2, 01570 INLINE = 0x4, 01572 COMPATIBLE = 0x3 01573 } Type_qualifiers; 01574 01583 static string type_qualifiers_name(Type_qualifiers tq); 01584 01597 static typeNode * integral_promotions(typeNode * old_type); 01598 01618 static pair<typeNode *, typeNode *> usual_arithmetic_conversions(typeNode * left, 01619 typeNode * right); 01620 01621 private: 01622 01628 TREE typeNode * _type; 01629 01634 Type_qualifiers _type_qualifiers; 01635 01636 01642 int _alloc_size; 01643 01649 int _alloc_align; 01650 01651 public: 01652 01663 typeNode(NodeType typ, Type_qualifiers tq, typeNode * subtype, 01664 const Coord coord); 01665 01671 virtual ~typeNode(); 01672 01677 01680 inline typeNode * type() const { return _type; } 01681 01685 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; } 01686 01692 inline void type(typeNode * the_type) { _type = the_type; } 01693 01696 inline Type_qualifiers type_qualifiers() const { return _type_qualifiers; } 01697 01700 inline void type_qualifiers(Type_qualifiers the_tq) { _type_qualifiers = the_tq; } 01701 01703 inline string type_qualifiers_name() { return type_qualifiers_name(type_qualifiers()); } 01704 01707 inline void add_type_qualifiers(Type_qualifiers the_tq) 01708 { _type_qualifiers = Type_qualifiers(_type_qualifiers | the_tq); } 01709 01713 inline typeNode * add_type_qualifiers_and(Type_qualifiers the_tq) 01714 { add_type_qualifiers(the_tq); return this; } 01715 01718 inline void remove_type_qualifiers(Type_qualifiers the_tq) 01719 { _type_qualifiers = Type_qualifiers(_type_qualifiers & ~the_tq); } 01720 01722 inline int alloc_size(void) const { return _alloc_size; } 01723 01725 inline void alloc_size(int size) { _alloc_size = size; } 01726 01728 inline int alloc_align(void) const { return _alloc_align; } 01729 01731 inline void alloc_align(int align) { _alloc_align = align; } 01732 01734 01741 01742 void finish(); 01743 typeNode * finish_and(); 01744 01745 // -- Set base type 01746 // Was SetBaseType from complex-types.c 01747 01748 void set_base_type(typeNode * base); 01749 typeNode * set_base_type_and(typeNode * base); 01750 01751 // -- SUE complete 01752 01753 void verify_sue_complete(); 01754 01756 01767 01776 bool operator==(typeNode & second) { 01777 return equal_to(this, & second, true, true); } 01778 01788 bool operator<=(typeNode & second) { 01789 return equal_to(this, & second, false, false); } 01790 01798 bool operator!=(typeNode & second) { 01799 return ! ( (*this) == second ); } 01800 01802 01824 static bool equal_to(typeNode * first, typeNode * second, 01825 bool strict_toplevel, bool strict_recursive); 01826 01840 virtual bool qualified_equal_to(typeNode * other, 01841 bool strict_toplevel, bool strict_recursive); 01842 01852 typeNode * unwind_tdefs(Type_qualifiers & the_tq); 01853 01854 typeNode * no_tdef_type(); 01855 01862 typeNode * follow_tdefs(); 01863 01870 01871 virtual bool is_char() const { return false; } 01872 virtual bool is_int() const { return false; } 01873 virtual bool is_float() const { return false; } 01874 virtual bool is_void() const { return false; } 01875 virtual bool is_ellipsis() const { return false; } 01876 01877 virtual bool is_integer() const { return false; } 01878 virtual bool is_arithmetic() const { return false; } 01879 virtual bool is_scalar() const { return false; } 01880 virtual bool is_aggregate() const { return false; } 01881 virtual bool is_derived() const { return false; } 01882 virtual bool is_pointer() const { return false; } 01883 01885 01892 virtual typeNode * usual_unary_conversion_type() { return this; } 01893 01894 // -- Data type base 01895 01896 virtual typeNode * base_type(bool TdefIndir) const { 01897 return (typeNode *)this; } 01898 01899 // -- Deep base type 01900 01901 typeNode * deep_base_type(); 01902 01903 // -- Dataflow 01904 // Note: All type nodes share a no-op dataflow function 01905 01906 virtual void dataflow(FlowVal * v, FlowProblem & fp) { } 01907 01908 // -- Output 01909 01910 virtual void output(output_context & ct, Node * par); 01911 01924 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q) =0; 01925 }; 01926 01936 class primNode : public typeNode 01937 { 01938 01939 private: 01940 01946 basic_type _basic; 01947 01948 public: 01949 01958 primNode(Type_qualifiers tq, basic_type basic, 01959 const Coord coord = Coord::Unknown); 01960 01970 primNode(Type_qualifiers tq, 01971 const Coord coord = Coord::Unknown); 01972 01981 primNode(const Coord coord); 01982 01991 primNode(basic_type basic, const Coord coord = Coord::Unknown); 01992 01998 virtual ~primNode(); 01999 02004 02005 // Return a reference so basic_type can be modified... 02006 02007 inline const basic_type & basic() const { return _basic; } 02008 inline basic_type & basic() { return _basic; } 02009 inline void basic(basic_type basic) { _basic = basic; } 02010 02012 02017 // -- FinishPrimType from type.c 02018 02019 void finish(); 02020 primNode * finish_and(); 02021 02022 // -- MergePrimTypes from type.c (other is deleted) 02023 02024 void merge_in(primNode * other); 02025 primNode * merge_in_and(primNode * other); 02026 02028 02035 02036 virtual bool is_int() const { return _basic.is_int(); } 02037 virtual bool is_char() const { return _basic.is_char(); } 02038 virtual bool is_float() const { return _basic.is_float(); } 02039 virtual bool is_void() const { return _basic.is_void(); } 02040 virtual bool is_ellipsis() const { return _basic.is_ellipsis(); } 02041 02042 virtual bool is_integer() const { return _basic.is_integer(); } 02043 virtual bool is_arithmetic() const { return _basic.is_arithmetic(); } 02044 virtual bool is_scalar() const { return _basic.is_scalar(); } 02045 02047 02048 // -- Type equal 02049 02050 bool qualified_equal_to(typeNode * node2, 02051 bool strict_toplevel, bool strict_recursive); 02052 02057 02058 virtual void visit(Visitor * the_visitor); 02059 virtual void walk(Walker & the_walker); 02060 virtual Node * change(Changer & the_changer, bool redispatch = false); 02061 02063 02064 // -- Clone 02065 02066 virtual Node * clone() const { return new primNode ( *this ); } 02067 02068 // -- Output 02069 02070 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02071 }; 02072 02089 class tdefNode : public typeNode 02090 { 02091 02092 private: 02093 02099 string _name; 02100 02108 REF typeNode * _def; 02109 02110 public: 02111 02121 tdefNode(Type_qualifiers tq, const char * name, 02122 const Coord coord = Coord::Unknown); 02123 02135 tdefNode(idNode * the_id, Type_qualifiers tq, typeNode * the_type); 02136 02142 virtual ~tdefNode(); 02143 02148 02151 inline string & name() { return _name; } 02152 02155 inline void name(string name) { _name = name; } 02156 02159 inline typeNode * def() const { return _def; } 02160 02166 inline void def(typeNode * d) { _def = d; } 02167 02169 02170 // -- Data type base 02171 02172 typeNode * base_type(bool TdefIndir) const; 02173 02174 // -- Data type predicates 02175 02180 02181 virtual void visit(Visitor * the_visitor); 02182 virtual void walk(Walker & the_walker); 02183 virtual Node * change(Changer & the_changer, bool redispatch = false); 02184 02186 02187 // -- Clone 02188 02189 virtual Node * clone() const { return new tdefNode ( *this ); } 02190 02191 // -- Output 02192 02193 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02194 }; 02195 02205 class ptrNode : public typeNode 02206 { 02207 02208 private: 02209 02210 public: 02211 02221 ptrNode(Type_qualifiers tq, typeNode * the_type, 02222 const Coord coord = Coord::Unknown); 02223 02229 virtual ~ptrNode(); 02230 02231 // -- Type equal 02232 02233 bool qualified_equal_to(typeNode * node2, 02234 bool strict_toplevel, bool strict_recursive); 02235 02242 02243 virtual bool is_scalar() const { return true; } 02244 virtual bool is_derived() const { return true; } 02245 virtual bool is_pointer() const { return true; } 02246 02248 02253 02254 virtual void visit(Visitor * the_visitor); 02255 virtual void walk(Walker & the_walker); 02256 virtual Node * change(Changer & the_changer, bool redispatch = false); 02257 02259 02260 // -- Clone 02261 02262 virtual Node * clone() const { return new ptrNode ( *this ); } 02263 02264 // -- Output 02265 02266 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02267 }; 02268 02291 class arrayNode : public typeNode 02292 { 02293 02294 private: 02295 02305 TREE exprNode * _dim; 02306 02315 int _size; 02316 02317 public: 02318 02329 arrayNode(Type_qualifiers tq, typeNode * the_type, exprNode * the_dim, 02330 const Coord coord = Coord::Unknown); 02331 02337 virtual ~arrayNode(); 02338 02343 02344 inline exprNode * dim() const { return _dim; } 02345 inline exprNode * get_dim() { exprNode * out = _dim; _dim = 0; return out; } 02346 inline void dim(exprNode * the_dim) { _dim = the_dim; } 02347 02348 inline int size() const { return _size; } 02349 inline void size(int the_size) { _size = the_size; } 02350 02352 02359 02360 virtual bool is_aggregate() const { return true; } 02361 virtual bool is_derived() const { return true; } 02362 virtual bool is_pointer() const { return true; } 02363 02364 // an array will be seen as a pointer (thus a scalar) 02365 // if it has no dimension, e.g., is a parameter 02366 02367 virtual bool is_scalar() const { return _dim == NULL; } 02368 02369 bool is_string() const; 02370 02372 02373 // -- Type equal 02374 02375 bool qualified_equal_to(typeNode * node2, 02376 bool strict_toplevel, bool strict_recursive); 02377 02382 02383 virtual void visit(Visitor * the_visitor); 02384 virtual void walk(Walker & the_walker); 02385 virtual Node * change(Changer & the_changer, bool redispatch = false); 02386 02388 02389 // -- Clone 02390 02391 virtual Node * clone() const { return new arrayNode ( *this ); } 02392 02393 // -- Output 02394 02395 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02396 }; 02397 02408 class funcNode : public typeNode 02409 { 02410 02411 private: 02412 02431 TREE decl_list _args; 02432 02437 bool _is_knr; 02438 02439 public: 02440 02451 funcNode(Type_qualifiers tq, decl_list * args, typeNode * returns, 02452 const Coord coord = Coord::Unknown); 02453 02459 virtual ~funcNode(); 02460 02465 02466 inline decl_list & args() { return _args; } 02467 inline const decl_list & args() const { return _args; } 02468 02469 inline typeNode * returns() const { return type(); } 02470 inline void returns(typeNode * returns) { type(returns); } 02471 02472 inline bool is_knr() const { return _is_knr; } 02473 inline void is_knr (bool v) { _is_knr = v; } 02474 02476 02477 // -- Type equal 02478 02479 bool qualified_equal_to(typeNode * node2, 02480 bool strict_toplevel, bool strict_recursive); 02481 02488 02489 virtual bool is_derived() const { return true; } 02490 virtual bool is_pointer() const { return true; } 02491 02493 02498 bool is_void_args(); 02499 02507 bool check_conversions(); 02508 02518 bool is_compatible_with(funcNode * nfunc); 02519 02531 void add_parameter_types(decl_list * types); 02532 02537 02538 virtual void visit(Visitor * the_visitor); 02539 virtual void walk(Walker & the_walker); 02540 virtual Node * change(Changer & the_changer, bool redispatch = false); 02541 02543 02544 // -- Clone 02545 02546 virtual Node * clone() const { return new funcNode ( *this ); } 02547 02548 // -- Output 02549 02550 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02551 }; 02552 02586 class sueNode : public typeNode 02587 { 02588 02589 private: 02590 02596 REF suespecNode * _spec; 02597 02602 bool _elaborated; 02603 02604 public: 02605 02614 sueNode(NodeType typ, const Coord coord); 02615 02621 virtual ~sueNode(); 02622 02627 02628 inline bool elaborated() const { return _elaborated; } 02629 inline void elaborated(bool elab) { _elaborated = elab; } 02630 02631 inline suespecNode * spec() const { return _spec; } 02632 inline void spec(suespecNode * s) { _spec = s; } 02633 02635 02639 02640 // --- Was SetSUdclNameFields from sue.c 02641 02642 void set_name_fields(idNode *id, decl_list * fields, 02643 bool elaborated, 02644 const Coord left_coord, 02645 const Coord the_right_coord); 02646 02647 sueNode * set_name_fields_and(idNode *id, decl_list * fields, 02648 bool elaborated, 02649 const Coord left_coord, 02650 const Coord the_right_coord); 02651 02652 // -- Was SetSUdclName in sue.c 02653 02654 void set_name(idNode * id, const Coord coord); 02655 sueNode * set_name_and(idNode * id, const Coord coord); 02656 02657 // -- ForceNewSU in sue.c 02658 02659 void force_new(const Coord coord); 02660 sueNode * force_new_and(const Coord coord); 02661 02662 // -- Tags 02663 02664 bool same_tag_as(sueNode * other); 02665 void tag_conflict(sueNode * new_sue); // from sue.c 02666 02668 02669 // -- Type equal 02670 02671 bool qualified_equal_to(typeNode * node2, 02672 bool strict_toplevel, bool strict_recursive); 02673 02674 // -- Data type predicates 02675 02676 // -- Output 02677 02678 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 02679 }; 02680 02695 class structNode : public sueNode 02696 { 02697 02698 private: 02699 02700 public: 02701 02710 structNode(const Coord coord = Coord::Unknown); 02711 02717 virtual ~structNode(); 02718 02725 02726 virtual bool is_aggregate() const { return true; } 02727 02729 02734 02735 virtual void visit(Visitor * the_visitor); 02736 virtual void walk(Walker & the_walker); 02737 virtual Node * change(Changer & the_changer, bool redispatch = false); 02738 02740 02741 // -- Clone 02742 02743 virtual Node * clone() const { return new structNode ( *this ); } 02744 }; 02745 02760 class unionNode : public sueNode 02761 { 02762 02763 private: 02764 02765 public: 02766 02775 unionNode(const Coord coord = Coord::Unknown); 02776 02782 virtual ~unionNode(); 02783 02788 02789 virtual void visit(Visitor * the_visitor); 02790 virtual void walk(Walker & the_walker); 02791 virtual Node * change(Changer & the_changer, bool redispatch = false); 02792 02794 02795 // -- Clone 02796 02797 virtual Node * clone() const { return new unionNode ( *this ); } 02798 }; 02799 02814 class enumNode : public sueNode 02815 { 02816 02817 private: 02818 02819 public: 02820 02829 enumNode(const Coord coord = Coord::Unknown); 02830 02843 enumNode(idNode *id, decl_list * values, 02844 const Coord enum_coord, const Coord left_coord, 02845 const Coord right_coord); 02846 02852 virtual ~enumNode(); 02853 02860 02861 virtual bool is_int() const { return true; } 02862 virtual bool is_integer() const { return true; } 02863 virtual bool is_arithmetic() const { return true; } 02864 virtual bool is_scalar() const { return true; } 02865 02867 02872 02873 virtual void visit(Visitor * the_visitor); 02874 virtual void walk(Walker & the_walker); 02875 virtual Node * change(Changer & the_changer, bool redispatch = false); 02876 02878 02879 // -- Clone 02880 02881 virtual Node * clone() const { return new enumNode ( *this ); } 02882 }; 02883 02900 class suespecNode : public typeNode 02901 { 02902 02903 private: 02904 02912 string _name; 02913 02920 TREE decl_list _fields; 02921 02929 bool _complete; 02930 02938 bool _visited; 02939 02950 int _scope_output; 02951 02956 int _size; 02957 02962 int _align; 02963 02969 NodeType _owner; 02970 02971 public: 02972 02985 suespecNode(const char * name, decl_list * fields, NodeType owner, 02986 unitNode * the_unit, 02987 const Coord coord); 02988 02994 virtual ~suespecNode(); 02995 03000 03001 inline bool complete() const { return _complete; } 03002 inline void complete(bool comp) { _complete = comp; } 03003 03004 inline bool visited() const { return _visited; } 03005 inline void visited(bool v) { _visited = v; } 03006 03007 inline bool scope_output() const { return _scope_output; } 03008 inline void scope_output(int v) { _scope_output = v; } 03009 03010 inline int size() const { return _size; } 03011 inline void size(int size) { _size = size; } 03012 03013 inline int align() const { return _align; } 03014 inline void align(int align) { _align = align; } 03015 03016 inline string & name() { return _name; } 03017 inline void name(string name) { _name = name; } 03018 03019 inline decl_list & fields() { return _fields; } 03020 inline const decl_list & fields() const { return _fields; } 03021 03022 inline NodeType owner() const { return _owner; } 03023 03025 03026 // -- Tags and fields 03027 03038 bool same_tag_as(suespecNode * other); 03039 03048 void update(decl_list * fields, sueNode * sue, const Coord right); 03049 03059 declNode * find_field(const string & name); 03060 03065 03066 virtual void visit(Visitor * the_visitor); 03067 virtual void walk(Walker & the_walker); 03068 virtual Node * change(Changer & the_changer, bool redispatch = false); 03069 03071 03072 // -- Clone 03073 03074 virtual Node * clone() const { return new suespecNode ( *this ); } 03075 03076 // -- Output 03077 03078 virtual void output_type(output_context & ct, Node * par, Assoc context, Type_qualifiers q); 03079 }; 03080 03081 03099 class exprNode : public Node 03100 { 03101 public: 03102 03115 static exprNode * integral_promotions(exprNode * old_expr); 03116 03131 static pair<exprNode *, exprNode *> 03132 usual_arithmetic_conversions(exprNode * left, 03133 exprNode * right); 03134 03135 private: 03136 03141 TREE typeNode * _type; 03142 03150 constant _value; 03151 03152 public: 03153 03163 exprNode(NodeType typ, typeNode * type, const Coord coord); 03164 03170 virtual ~exprNode(); 03171 03176 03177 virtual typeNode * type() const { return _type; } 03178 inline typeNode * get_type() { typeNode * out = _type; _type = 0; return out; } 03179 virtual void type(typeNode *type) { _type = type; } 03180 03181 inline const constant & value() const { return _value; } 03182 inline constant & value() { return _value; } 03183 inline void value(const constant & newval) { _value = newval; } 03184 03186 03187 // -- Data type base 03188 03189 virtual typeNode * base_type(bool TdefIndir) const; 03190 03191 // -- Symbol lookup 03192 // LookupPostfixExpression in type.c 03193 03194 // virtual void lookup() { } // -- Default; do nothing 03195 03196 // -- Type conversions 03197 // THESE ARE NOT USED 03198 // exprNode * assignment_conversions(typeNode * to_type); 03199 // exprNode * call_conversions(typeNode * to_type); 03200 // exprNode * return_conversions(typeNode * to_type); 03201 // exprNode * cast_conversions(typeNode * to_type); 03202 // exprNode * usual_unary_conversions(typeNode * to_type, bool f_to_d); 03203 // exprNode * usual_binary_conversions(typeNode * to_type); 03204 03214 virtual void eval() =0; 03215 03224 virtual bool is_lvalue() { return true; } // THIS IS A TBD 03225 03226 typeNode * no_tdef_type() { return type()->follow_tdefs(); } 03227 03228 // -- Output 03229 03230 virtual void output(output_context & ct, Node * par); 03231 03252 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc) =0; 03253 03266 virtual int precedence(Assoc & assoc); 03267 03280 bool parens(int outer_prec, Assoc outer_assoc); 03281 }; 03282 03290 class indexNode : public exprNode { 03291 public: 03292 indexNode(NodeType typ, typeNode * type, const Coord coord); 03293 }; 03294 03304 class constNode : public indexNode 03305 { 03306 03307 private: 03308 03318 string _text; 03319 03320 public: 03321 03331 constNode(constant value, const char * text = "", 03332 const Coord coord = Coord::Unknown); 03333 03339 virtual ~constNode(); 03340 03345 03346 inline string & text() { return _text; } 03347 03349 03354 typeNode * usual_unary_conversion_type() 03355 { return type()->usual_unary_conversion_type(); } 03356 03357 // -- Constant folding 03358 03359 virtual void eval(); 03360 03365 03366 virtual void visit(Visitor * the_visitor); 03367 virtual void walk(Walker & the_walker); 03368 virtual Node * change(Changer & the_changer, bool redispatch = false); 03369 03371 03372 // -- Dataflow 03373 03374 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03375 03376 // -- Clone 03377 03378 virtual Node * clone() const { return new constNode ( *this ); } 03379 03380 // -- Output 03381 03382 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03383 }; 03384 03396 class idNode : public indexNode 03397 { 03398 03399 private: 03400 03405 string _name; 03406 03414 REF declNode * _decl; 03415 03416 public: 03417 03426 idNode(const char * text, const Coord coord = Coord::Unknown); 03427 03437 idNode(declNode * the_decl, const Coord coord = Coord::Unknown); 03438 03444 virtual ~idNode(); 03445 03450 03451 inline string & name() { return _name; } 03452 inline const string & name() const { return _name; } 03453 inline void name(string nm) { _name = nm; } 03454 03455 inline declNode * decl() const { return _decl; } 03456 void decl(declNode *decl); 03457 03459 03460 // -- Data type base 03461 03462 typeNode * base_type(bool TdefIndir) const; 03463 03464 // -- Symbol lookup 03465 03466 // virtual void lookup(); 03467 // idNode * lookup_and(); 03468 03469 // -- Constant folding 03470 03471 virtual void eval(); 03472 03477 03478 virtual void visit(Visitor * the_visitor); 03479 virtual void walk(Walker & the_walker); 03480 virtual Node * change(Changer & the_changer, bool redispatch = false); 03481 03483 03484 // -- Dataflow 03485 03486 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03487 03488 // -- Clone 03489 03490 virtual Node * clone() const { return new idNode ( *this ); } 03491 03492 // -- Output 03493 03494 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03495 }; 03496 03514 class binaryNode : public exprNode 03515 { 03516 03517 private: 03518 03526 Operator * _op; 03527 03530 TREE exprNode * _left; 03531 03534 TREE exprNode * _right; 03535 03536 public: 03537 03556 binaryNode(unsigned int op_id, exprNode * left, exprNode * right, 03557 const Coord coord = Coord::Unknown); 03558 03564 virtual ~binaryNode(); 03565 03570 03571 inline Operator * op() const { return _op; } 03572 inline void op(Operator * op) { _op = op; } 03573 03574 inline exprNode * left() const { return _left; } 03575 inline exprNode * get_left() { exprNode * out = _left; _left = 0; return out; } 03576 inline void left(exprNode * left) { _left = left; } 03577 03578 inline exprNode * right() const { return _right; } 03579 inline exprNode * get_right() { exprNode * out = _right; _right = 0; return out; } 03580 inline void right(exprNode * right) { _right = right; } 03581 03583 03584 // -- Symbol lookup 03585 03586 // virtual void lookup(); 03587 03588 // -- Constant folding 03589 03590 virtual void eval(); 03591 03596 03597 virtual void visit(Visitor * the_visitor); 03598 virtual void walk(Walker & the_walker); 03599 virtual Node * change(Changer & the_changer, bool redispatch = false); 03600 03602 03603 // -- Dataflow 03604 03605 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03606 03607 // -- Clone 03608 03609 virtual Node * clone() const { return new binaryNode ( *this ); } 03610 03611 // -- Output 03612 03613 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03614 virtual int precedence(Assoc & assoc); 03615 }; 03616 03625 class unaryNode : public exprNode 03626 { 03627 03628 private: 03629 03637 Operator * _op; 03638 03641 TREE exprNode * _expr; 03642 03647 TREE typeNode * _sizeof_type; 03648 03649 public: 03650 03668 unaryNode(unsigned int op_id, exprNode * expr, 03669 const Coord coord = Coord::Unknown); 03670 03679 unaryNode(unsigned int op_id, typeNode * the_type, 03680 const Coord coord = Coord::Unknown); 03681 03687 virtual ~unaryNode(); 03688 03693 03694 inline Operator * op() const { return _op; } 03695 inline void op(Operator * op) { _op = op; } 03696 03697 inline exprNode * expr() const { return _expr; } 03698 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; } 03699 inline void expr(exprNode * expr) { _expr = expr; } 03700 03701 // sizeof_type is only used if the operation is "sizeof()" 03702 03703 inline typeNode * sizeof_type() const { return _sizeof_type; } 03704 inline typeNode * get_sizeof_type() 03705 { typeNode * out = _sizeof_type; _sizeof_type = 0; return out; } 03706 inline void sizeof_type(typeNode *sizeof_type) 03707 { _sizeof_type = sizeof_type; } 03708 03710 03711 // -- Symbol lookup 03712 03713 // virtual void lookup(); 03714 03715 // -- Constant folding 03716 03717 virtual void eval(); 03718 03723 03724 virtual void visit(Visitor * the_visitor); 03725 virtual void walk(Walker & the_walker); 03726 virtual Node * change(Changer & the_changer, bool redispatch = false); 03727 03729 03730 // -- Dataflow 03731 03732 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03733 03734 // -- Clone 03735 03736 virtual Node * clone() const { return new unaryNode ( *this ); } 03737 03738 // -- Output 03739 03740 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03741 virtual int precedence(Assoc & assoc); 03742 }; 03743 03759 class castNode : public exprNode 03760 { 03761 03762 private: 03763 03766 TREE exprNode * _expr; 03767 03774 bool _implicit; 03775 03776 public: 03777 03787 castNode(typeNode * type, exprNode * expr, bool implicit = false, 03788 const Coord coord = Coord::Unknown); 03789 03795 virtual ~castNode(); 03796 03801 03802 inline exprNode * expr() const { return _expr; } 03803 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; } 03804 inline void expr(exprNode * expr) { _expr = expr; } 03805 03806 inline bool is_implicit() const { return _implicit; } 03808 03809 // -- Constant folding 03810 03811 virtual void eval(); 03812 03817 03818 virtual void visit(Visitor * the_visitor); 03819 virtual void walk(Walker & the_walker); 03820 virtual Node * change(Changer & the_changer, bool redispatch = false); 03821 03823 03824 // -- Dataflow 03825 03826 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03827 03828 // -- Clone 03829 03830 virtual Node * clone() const { return new castNode ( *this ); } 03831 03832 // -- Output 03833 03834 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03835 virtual int precedence(Assoc & assoc); 03836 }; 03837 03838 03848 class commaNode : public exprNode 03849 { 03850 03851 private: 03852 03858 TREE expr_list _exprs; 03859 03860 public: 03861 03870 commaNode(expr_list * exprs, const Coord coord = Coord::Unknown); 03871 03878 commaNode(const Coord coord = Coord::Unknown); 03879 03885 virtual ~commaNode(); 03886 03891 03892 inline expr_list & exprs() { return _exprs; } 03893 inline const expr_list & exprs() const { return _exprs; } 03894 03896 03897 // -- Data type base 03898 03899 typeNode * base_type(bool TdefIndir) const; 03900 03901 // -- Constant folding 03902 03903 virtual void eval(); 03904 03909 03910 virtual void visit(Visitor * the_visitor); 03911 virtual void walk(Walker & the_walker); 03912 virtual Node * change(Changer & the_changer, bool redispatch = false); 03913 03915 03916 // -- Dataflow 03917 03918 virtual void dataflow(FlowVal * v, FlowProblem & fp); 03919 03920 // -- Clone 03921 03922 virtual Node * clone() const { return new commaNode ( *this ); } 03923 03924 // -- Output 03925 03926 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 03927 virtual int precedence(Assoc & assoc); 03928 }; 03929 03937 class ternaryNode : public exprNode 03938 { 03939 03940 private: 03941 03944 TREE exprNode * _cond; 03945 03948 TREE exprNode * _true_br; 03949 03952 TREE exprNode * _false_br; 03953 03956 Coord _colon_coord; 03957 03958 public: 03959 03971 ternaryNode(exprNode * cond, exprNode * true_br, exprNode * false_br, 03972 const Coord qmark_coord = Coord::Unknown, 03973 const Coord colon_coord = Coord::Unknown); 03974 03980 virtual ~ternaryNode(); 03981 03986 03987 inline exprNode * cond() const { return _cond; } 03988 inline exprNode * get_cond() { exprNode * out = _cond; _cond = 0; return out; } 03989 inline void cond(exprNode * cond) { _cond = cond; } 03990 03991 inline exprNode * true_br() const { return _true_br; } 03992 inline exprNode * get_true_br() { exprNode * out = _true_br; _true_br = 0; return out; } 03993 inline void true_br(exprNode * true_br) { _true_br = true_br; } 03994 03995 inline exprNode * false_br() const { return _false_br; } 03996 inline exprNode * get_false_br() { exprNode * out = _false_br; _false_br = 0; return out; } 03997 inline void false_br(exprNode * false_br) { _false_br = false_br; } 03998 04000 04001 // -- Constant folding 04002 04003 virtual void eval(); 04004 04009 04010 virtual void visit(Visitor * the_visitor); 04011 virtual void walk(Walker & the_walker); 04012 virtual Node * change(Changer & the_changer, bool redispatch = false); 04013 04015 04016 // -- Dataflow 04017 04018 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04019 04020 // -- Clone 04021 04022 virtual Node * clone() const { return new ternaryNode ( *this ); } 04023 04024 // -- Output 04025 04026 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 04027 virtual int precedence(Assoc & assoc); 04028 }; 04029 04057 class callNode : public exprNode 04058 { 04059 04060 private: 04061 04064 TREE exprNode * _name; 04065 04071 TREE expr_list _args; 04072 04082 REF procNode * _proc; 04083 04084 public: 04085 04096 callNode(exprNode * name, expr_list * args, 04097 const Coord coord = Coord::Unknown); 04098 04104 virtual ~callNode(); 04105 04110 04111 inline exprNode * name() const { return _name; } 04112 inline exprNode * get_name() { exprNode * out = _name; _name = 0; return out; } 04113 inline void name(exprNode * name) { _name = name; } 04114 04115 inline expr_list & args() { return _args; } 04116 inline const expr_list & args() const { return _args; } 04117 04118 inline procNode * proc() const { return _proc; } 04119 inline void proc(procNode * proc) { _proc = proc; } 04120 04122 04123 // -- Data type base 04124 04125 typeNode * base_type(bool TdefIndir) const; 04126 04127 // -- Symbol lookup 04128 04129 // virtual void lookup(); 04130 04131 // -- Constant folding 04132 04133 virtual void eval(); 04134 04139 04140 virtual void visit(Visitor * the_visitor); 04141 virtual void walk(Walker & the_walker); 04142 virtual Node * change(Changer & the_changer, bool redispatch = false); 04143 04145 04146 // -- Dataflow 04147 04148 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04149 04150 // -- Clone 04151 04152 virtual Node * clone() const { return new callNode ( *this ); } 04153 04154 // -- Output 04155 04156 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 04157 }; 04158 04174 class initializerNode : public exprNode 04175 { 04176 04177 private: 04178 04179 TREE expr_list _exprs; 04180 04181 public: 04182 04183 // -- Constructors 04184 04185 initializerNode(expr_list * exprs, const Coord coord = Coord::Unknown); 04186 04192 virtual ~initializerNode(); 04193 04198 04199 inline expr_list & exprs() { return _exprs; } 04200 inline const expr_list & exprs() const { return _exprs; } 04201 inline void add_expr(exprNode * the_expr) { _exprs.push_back(the_expr); } 04202 04204 04205 // -- Constant folding 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 // -- Dataflow 04221 04222 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04223 04224 // -- Clone 04225 04226 virtual Node * clone() const { return new initializerNode ( *this ); } 04227 04228 // -- Output 04229 04230 virtual void output_expr(output_context & ct, Node * par, int prec, Assoc assoc); 04231 }; 04232 04240 class stmtNode : public Node 04241 { 04242 04243 private: 04244 04250 FlowVal * _at_exit; 04251 04260 string _comment; 04261 04262 public: 04263 04272 stmtNode(NodeType typ, const Coord coord); 04273 04279 virtual ~stmtNode(); 04280 04285 04286 inline string & comment() { return _comment; } 04287 04288 // -- Dataflow 04289 04290 inline FlowVal * at_exit() const { return _at_exit; } 04291 inline void at_exit(FlowVal * ae) { _at_exit = ae; } 04292 04294 04295 // -- Output 04296 04297 virtual void output(output_context & ct, Node * par); 04298 04309 virtual void output_stmt(output_context & ct, Node * par) =0; 04310 04311 void output_comment(output_context & ct); 04312 }; 04313 04332 class blockNode : public stmtNode 04333 { 04334 04335 public: 04336 04366 static blockNode * toBlock(stmtNode * stmt, Coord coord); 04367 04368 private: 04369 04374 TREE decl_list _decls; 04375 04380 TREE stmt_list _stmts; 04381 04384 Coord _right_brace; 04385 // TREE typeNode * _type; Why does block have a type? 04386 04387 public: 04388 04401 blockNode(decl_list * decls, stmt_list * stmts, 04402 const Coord left_coord = Coord::Unknown, 04403 const Coord right_brace = Coord::Unknown); 04404 04410 virtual ~blockNode(); 04411 04416 04417 inline decl_list & decls() { return _decls; } 04418 inline const decl_list & decls() const { return _decls; } 04419 04420 inline stmt_list & stmts() { return _stmts; } 04421 inline const stmt_list & stmts() const { return _stmts; } 04422 04423 inline Coord right_brace() const { return _right_brace; } 04424 inline void right_brace(const Coord right_brace) { _right_brace = right_brace; } 04425 04427 04428 // -- Data type base 04429 04430 typeNode * base_type(bool TdefIndir) const; 04431 04436 04437 virtual void visit(Visitor * the_visitor); 04438 virtual void walk(Walker & the_walker); 04439 virtual Node * change(Changer & the_changer, bool redispatch = false); 04440 04442 04443 // -- Dataflow 04444 04445 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04446 04447 // -- Clone 04448 04449 virtual Node * clone() const { return new blockNode ( *this ); } 04450 04451 // -- Output 04452 virtual void output_stmt(output_context & ct, Node * par); 04453 04454 }; 04455 04456 class algorithm_info 04457 { 04458 }; 04459 04485 class basicblockNode : public blockNode { 04486 04487 private: 04488 04491 basicblock_list _preds; 04492 04495 basicblock_list _succs; 04496 04501 basicblockNode * _parent; 04502 04508 basicblock_list _children; 04509 04515 algorithm_info * _info; 04516 04523 int _dfn; 04524 04531 FlowVal * _at_entry; 04532 04540 FlowVal * _at_exit; 04541 04542 public: 04543 04555 basicblockNode(decl_list * decls, stmt_list * stmts, 04556 const Coord left_coord = Coord::Unknown, 04557 const Coord right_brace = Coord::Unknown); 04558 04564 virtual ~basicblockNode(); 04565 04570 04571 inline basicblock_list & preds() { return _preds; } 04572 inline const basicblock_list & preds() const { return _preds; } 04573 04574 inline basicblock_list & succs() { return _succs; } 04575 inline const basicblock_list & succs() const { return _succs; } 04576 04577 inline basicblockNode * parent() const { return _parent; } 04578 inline void parent(basicblockNode *par) { _parent = par; } 04579 04580 inline basicblock_list & children() { return _children; } 04581 inline const basicblock_list & children() const { return _children; } 04582 04583 inline algorithm_info * info() const { return _info; } 04584 inline void info(algorithm_info * i) { _info = i; } 04585 04586 inline int dfn() const { return _dfn; } 04587 inline void dfn(int d) { _dfn = d; } 04588 04589 // -- Flow values (for IP analyzer) 04590 04591 inline FlowVal * at_entry() const { return _at_entry; } 04592 inline void at_entry(FlowVal * ae) { _at_entry = ae; } 04593 04594 inline FlowVal * at_exit() const { return _at_exit; } 04595 inline void at_exit(FlowVal * ae) { _at_exit = ae; } 04596 04598 04603 04604 virtual void visit(Visitor * the_visitor); 04605 virtual void walk(Walker & the_walker); 04606 virtual Node * change(Changer & the_changer, bool redispatch = false); 04607 04609 04610 // Dataflow is inherited from blockNode 04611 04612 // -- Clone 04613 04614 virtual Node * clone() const { return new basicblockNode ( *this ); } 04615 04616 }; 04617 04618 04619 04629 class exprstmtNode : public stmtNode 04630 { 04631 04632 private: 04633 04636 TREE exprNode * _expr; 04637 04638 public: 04639 04646 exprstmtNode(exprNode * expr); 04647 04653 virtual ~exprstmtNode(); 04654 04659 04660 inline exprNode * expr() const { return _expr; } 04661 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; } 04662 inline void expr(exprNode * expr) { _expr = expr; } 04663 04665 04666 // -- Data type base 04667 04668 typeNode * base_type(bool TdefIndir) const; 04669 04670 04675 04676 virtual void visit(Visitor * the_visitor); 04677 virtual void walk(Walker & the_walker); 04678 virtual Node * change(Changer & the_changer, bool redispatch = false); 04679 04681 04682 // -- Dataflow 04683 04684 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04685 04686 // -- Clone 04687 04688 virtual Node * clone() const { return new exprstmtNode ( *this ); } 04689 04690 // -- Output 04691 04692 virtual void output_stmt(output_context & ct, Node * par); 04693 }; 04694 04708 class targetNode : public stmtNode 04709 { 04710 04711 private: 04712 04715 TREE blockNode * _stmt; 04716 04722 FlowVal * _at_entry; 04723 04724 public: 04725 04733 targetNode(NodeType typ, stmtNode * stmt, const Coord coord); 04734 04740 virtual ~targetNode(); 04741 04746 04747 inline blockNode * stmt() const { return _stmt; } 04748 inline blockNode * get_stmt() { blockNode * out = _stmt; _stmt = 0; return out; } 04749 inline void stmt(blockNode * stmt) { _stmt = stmt; } 04750 04751 // -- Dataflow 04752 04753 inline FlowVal * at_entry() const { return _at_entry; } 04754 inline void at_entry(FlowVal * ae) { _at_entry = ae; } 04755 04757 }; 04758 04773 class labelNode : public targetNode 04774 { 04775 04776 private: 04777 04780 string _name; 04781 04787 REF goto_list _references; 04788 04789 public: 04790 04800 labelNode(const char * name, stmtNode * stmt, 04801 const Coord coord = Coord::Unknown); 04802 04806 04815 labelNode(idNode * ident, stmtNode * stmt); 04816 04824 labelNode(idNode * ident); 04825 04827 04833 virtual ~labelNode(); 04834 04839 04840 inline string & name() { return _name; } 04841 inline void name(string name) { _name = name; } 04842 04843 inline goto_list & references() { return _references; } 04844 inline const goto_list & references() const { return _references; } 04845 04847 04848 // -- Undeclared 04849 04850 bool is_undeclared() const; 04851 04856 04857 virtual void visit(Visitor * the_visitor); 04858 virtual void walk(Walker & the_walker); 04859 virtual Node * change(Changer & the_changer, bool redispatch = false); 04860 04862 04863 // -- Dataflow 04864 04865 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04866 04867 // -- Clone 04868 04869 virtual Node * clone() const { return new labelNode ( *this ); } 04870 04871 // -- Output 04872 04873 virtual void output_stmt(output_context & ct, Node * par); 04874 }; 04875 04890 class caseNode : public targetNode 04891 { 04892 04893 private: 04894 04899 TREE exprNode * _expr; 04900 04907 REF switchNode * _container; 04908 04909 public: 04910 04921 caseNode(exprNode * expr, stmtNode * stmt, switchNode * the_container, 04922 const Coord coord = Coord::Unknown); 04923 04934 caseNode(exprNode * expr, stmtNode * stmt, 04935 const Coord coord = Coord::Unknown); 04936 04942 virtual ~caseNode(); 04943 04948 04949 inline exprNode * expr() const { return _expr; } 04950 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; } 04951 inline void expr(exprNode * expr) { _expr = expr; } 04952 04953 inline switchNode * container() const { return _container; } 04954 void container(switchNode * container); 04955 04957 04962 04963 virtual void visit(Visitor * the_visitor); 04964 virtual void walk(Walker & the_walker); 04965 virtual Node * change(Changer & the_changer, bool redispatch = false); 04966 04968 04969 // -- Dataflow 04970 04971 virtual void dataflow(FlowVal * v, FlowProblem & fp); 04972 04973 // -- Clone 04974 04975 virtual Node * clone() const { return new caseNode ( *this ); } 04976 04977 // -- Output 04978 04979 virtual void output_stmt(output_context & ct, Node * par); 04980 }; 04981 04994 class selectionNode : public stmtNode 04995 { 04996 04997 private: 04998 05001 TREE exprNode * _expr; 05002 05005 TREE blockNode * _stmt; 05006 05007 public: 05008 05020 selectionNode(NodeType typ, exprNode * expr, stmtNode * stmt, 05021 const Coord coord); 05022 05028 virtual ~selectionNode(); 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 blockNode * stmt() const { return _stmt; } 05040 inline blockNode * get_stmt() { blockNode * out = _stmt; _stmt = 0; return out; } 05041 inline void stmt(blockNode * stmt) { _stmt = stmt; } 05042 05044 }; 05045 05057 class ifNode : public selectionNode 05058 { 05059 05060 private: 05061 05064 TREE blockNode * _false_br; 05065 05068 Coord _else_coord; 05069 05070 public: 05071 05084 ifNode(exprNode * expr, stmtNode * true_br, stmtNode * false_br, 05085 const Coord if_coord = Coord::Unknown, 05086 const Coord else_coord = Coord::Unknown); 05087 05093 virtual ~ifNode(); 05094 05099 05100 inline blockNode * true_br() const { return selectionNode::stmt(); } 05101 inline blockNode * get_true_br() { return selectionNode::get_stmt(); } 05102 inline void true_br(blockNode * true_br) { selectionNode::stmt(true_br); } 05103 05104 inline blockNode * false_br() const { return _false_br; } 05105 inline blockNode * get_false_br() { blockNode * out = _false_br; _false_br = 0; return out; } 05106 inline void false_br(blockNode * false_br) { _false_br = false_br; } 05107 05108 inline Coord else_coord() const { return _else_coord; } 05109 inline void else_coord(const Coord the_coord) { _else_coord = the_coord; } 05110 05112 05117 05118 virtual void visit(Visitor * the_visitor); 05119 virtual void walk(Walker & the_walker); 05120 virtual Node * change(Changer & the_changer, bool redispatch = false); 05121 05123 05124 // -- Dataflow 05125 05126 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05127 05128 // -- Clone 05129 05130 virtual Node * clone() const { return new ifNode ( *this ); } 05131 05132 // -- Output 05133 05134 virtual void output_stmt(output_context & ct, Node * par); 05135 }; 05136 05149 class switchNode : public selectionNode 05150 { 05151 05152 private: 05153 05159 REF target_list _cases; 05160 05163 bool _has_default; 05164 05170 FlowVal * _at_top; 05171 05172 public: 05173 05183 switchNode(exprNode * expr, stmtNode * stmt, 05184 const Coord coord = Coord::Unknown); 05185 05191 virtual ~switchNode(); 05192 05197 05198 inline target_list & cases() { return _cases; } 05199 inline const target_list & cases() const { return _cases; } 05200 05201 inline bool has_default() const { return _has_default; } 05202 inline void has_default(bool has_default) { _has_default = has_default; } 05203 05204 inline FlowVal * at_top() const { return _at_top; } 05205 inline void at_top(FlowVal * at) { _at_top = at; } 05206 05208 05213 05214 virtual void visit(Visitor * the_visitor); 05215 virtual void walk(Walker & the_walker); 05216 virtual Node * change(Changer & the_changer, bool redispatch = false); 05217 05219 05220 // -- Dataflow 05221 05222 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05223 05224 // -- Clone 05225 05226 virtual Node * clone() const { return new switchNode ( *this ); } 05227 05228 // -- Output 05229 05230 virtual void output_stmt(output_context & ct, Node * par); 05231 }; 05232 05241 class loopNode : public stmtNode 05242 { 05243 05244 private: 05245 05248 TREE exprNode * _cond; 05249 05252 TREE blockNode * _body; 05253 05259 FlowVal * _at_loop_head; 05260 05266 FlowVal * _at_loop_tail; 05267 05268 public: 05269 05281 loopNode(NodeType typ, exprNode * cond, stmtNode * body, const Coord coord); 05282 05290 loopNode(NodeType typ, const Coord coord); 05291 05297 virtual ~loopNode(); 05298 05303 05304 inline exprNode * cond() const { return _cond; } 05305 inline exprNode * get_cond() { exprNode * out = _cond; _cond = 0; return out; } 05306 inline void cond(exprNode * cond) { _cond = cond; } 05307 05308 inline blockNode * body() const { return _body; } 05309 inline blockNode * get_body() { blockNode * out = _body; _body = 0; return out; } 05310 inline void body(blockNode * body) { _body = body; } 05311 05312 // -- Dataflow 05313 05314 inline FlowVal * at_loop_head() const { return _at_loop_head; } 05315 inline void at_loop_head(FlowVal * ae) { _at_loop_head = ae; } 05316 05317 inline FlowVal * at_loop_tail() const { return _at_loop_tail; } 05318 inline void at_loop_tail(FlowVal * ae) { _at_loop_tail = ae; } 05319 05321 }; 05322 05331 class whileNode : public loopNode 05332 { 05333 05334 private: 05335 05336 public: 05337 05346 whileNode(exprNode * cond, stmtNode * body, 05347 const Coord coord = Coord::Unknown); 05348 05354 virtual ~whileNode(); 05355 05360 05361 virtual void visit(Visitor * the_visitor); 05362 virtual void walk(Walker & the_walker); 05363 virtual Node * change(Changer & the_changer, bool redispatch = false); 05364 05366 05367 // -- Dataflow 05368 05369 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05370 05371 // -- Clone 05372 05373 virtual Node * clone() const { return new whileNode ( *this ); } 05374 05375 // -- Output 05376 05377 virtual void output_stmt(output_context & ct, Node * par); 05378 }; 05379 05388 class doNode : public loopNode 05389 { 05390 05391 private: 05392 05395 Coord _while_coord; 05396 05397 public: 05398 05408 doNode(stmtNode * body, exprNode * cond, 05409 const Coord coord = Coord::Unknown, 05410 const Coord while_coord = Coord::Unknown); 05411 05417 virtual ~doNode(); 05418 05423 05424 inline Coord while_coord() const { return _while_coord; } 05425 inline void while_coord(const Coord while_coord) { _while_coord = while_coord; } 05426 05428 05433 05434 virtual void visit(Visitor * the_visitor); 05435 virtual void walk(Walker & the_walker); 05436 virtual Node * change(Changer & the_changer, bool redispatch = false); 05437 05439 05440 // -- Dataflow 05441 05442 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05443 05444 // -- Clone 05445 05446 virtual Node * clone() const { return new doNode ( *this ); } 05447 05448 // -- Output 05449 05450 virtual void output_stmt(output_context & ct, Node * par); 05451 }; 05452 05474 class forNode : public loopNode 05475 { 05476 05477 private: 05478 05481 TREE exprNode * _init; 05482 05485 TREE exprNode * _next; 05486 05487 // FlowVal * _loop_val; 05488 // FlowVal * _break_val; 05489 // FlowVal * _continue_val; 05490 05491 public: 05492 05503 forNode(exprNode * init, exprNode * cond, exprNode * next, 05504 stmtNode * body, const Coord coord = Coord::Unknown); 05505 05511 virtual ~forNode(); 05512 05517 05518 inline exprNode * init() const { return _init; } 05519 inline exprNode * get_init() { exprNode * out = _init; _init = 0; return out; } 05520 inline void init(exprNode * init) { _init = init; } 05521 05522 inline exprNode * next() const { return _next; } 05523 inline exprNode * get_next() { exprNode * out = _next; _next = 0; return out; } 05524 inline void next(exprNode * next) { _next = next; } 05525 05527 05532 05533 virtual void visit(Visitor * the_visitor); 05534 virtual void walk(Walker & the_walker); 05535 virtual Node * change(Changer & the_changer, bool redispatch = false); 05536 05538 05539 // -- Dataflow 05540 05541 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05542 05543 // -- Clone 05544 05545 virtual Node * clone() const { return new forNode ( *this ); } 05546 05547 // -- Output 05548 05549 virtual void output_stmt(output_context & ct, Node * par); 05550 }; 05551 05562 class jumpNode : public stmtNode 05563 { 05564 05565 private: 05566 05567 public: 05568 05578 jumpNode(NodeType typ, const Coord coord); 05579 05585 virtual ~jumpNode(); 05586 05587 }; 05588 05601 class gotoNode : public jumpNode 05602 { 05603 05604 private: 05605 05611 REF labelNode * _label; 05612 05615 string _name; 05616 05617 public: 05618 05627 gotoNode(labelNode * label, const Coord coord = Coord::Unknown, 05628 NodeType typ = Goto); 05629 05639 gotoNode(idNode * ident, const Coord coord); 05640 05646 virtual ~gotoNode(); 05647 05652 05653 inline labelNode * label() const { return _label; } 05654 void label(labelNode * label); 05655 05656 inline string & name() { return _name; } 05657 inline void name(string name) { _name = name; } 05658 05660 05665 05666 virtual void visit(Visitor * the_visitor); 05667 virtual void walk(Walker & the_walker); 05668 virtual Node * change(Changer & the_changer, bool redispatch = false); 05669 05671 05672 // -- Dataflow 05673 05674 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05675 05676 // -- Clone 05677 05678 virtual Node * clone() const { return new gotoNode ( *this ); } 05679 05680 // -- Output 05681 05682 virtual void output_stmt(output_context & ct, Node * par); 05683 }; 05684 05696 class continueNode : public jumpNode 05697 { 05698 05699 private: 05700 05706 REF loopNode * _container; 05707 05708 public: 05709 05718 continueNode(loopNode * container, const Coord coord = Coord::Unknown); 05719 05727 continueNode(const Coord coord = Coord::Unknown); 05728 05734 virtual ~continueNode(); 05735 05740 05741 inline loopNode * container() const { return _container; } 05742 inline void container(loopNode * container) { _container = container; } 05743 05745 05750 05751 virtual void visit(Visitor * the_visitor); 05752 virtual void walk(Walker & the_walker); 05753 virtual Node * change(Changer & the_changer, bool redispatch = false); 05754 05756 05757 // -- Dataflow 05758 05759 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05760 05761 // -- Clone 05762 05763 virtual Node * clone() const { return new continueNode ( *this ); } 05764 05765 // -- Output 05766 05767 virtual void output_stmt(output_context & ct, Node * par); 05768 }; 05769 05781 class breakNode : public jumpNode 05782 { 05783 05784 private: 05785 05792 REF stmtNode * _container; 05793 05794 public: 05795 05804 breakNode(stmtNode * container, const Coord coord = Coord::Unknown); 05805 05813 breakNode(const Coord coord = Coord::Unknown); 05814 05820 virtual ~breakNode(); 05821 05826 05827 inline stmtNode * container() const { return _container; } 05828 inline void container(stmtNode * 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 // -- Dataflow 05844 05845 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05846 05847 // -- Clone 05848 05849 virtual Node * clone() const { return new breakNode ( *this ); } 05850 05851 // -- Output 05852 05853 virtual void output_stmt(output_context & ct, Node * par); 05854 }; 05855 05865 class returnNode : public jumpNode 05866 { 05867 05868 private: 05869 05872 TREE exprNode * _expr; 05873 05876 REF procNode * _proc; 05877 05882 bool _is_proc_exit; 05883 05884 public: 05885 05896 returnNode(exprNode * expr, procNode * proc, 05897 const Coord coord = Coord::Unknown); 05898 05899 returnNode(exprNode * expr, procNode * proc, bool proc_exit, 05900 const Coord coord = Coord::Unknown); 05901 05907 virtual ~returnNode(); 05908 05913 05914 inline exprNode * expr() const { return _expr; } 05915 inline exprNode * get_expr() { exprNode * out = _expr; _expr = 0; return out; } 05916 inline void expr(exprNode * expr) { _expr = expr; } 05917 05918 inline procNode * proc() const { return _proc; } 05919 inline void proc(procNode * proc) { _proc = proc; } 05920 05921 bool proc_exit() { return _is_proc_exit; } 05922 private: 05923 void proc_exit(bool proc_exit) { _is_proc_exit = proc_exit; } 05924 public: 05925 05927 05932 05933 virtual void visit(Visitor * the_visitor); 05934 virtual void walk(Walker & the_walker); 05935 virtual Node * change(Changer & the_changer, bool redispatch = false); 05936 05938 05939 // -- Dataflow 05940 05941 virtual void dataflow(FlowVal * v, FlowProblem & fp); 05942 05943 // -- Clone 05944 05945 virtual Node * clone() const; 05946 05947 // -- Output 05948 05949 virtual void output_stmt(output_context & ct, Node * par); 05950 }; 05951 05958 class attribNode : public stmtNode 05959 { 05960 05961 private: 05962 05963 TREE exprNode * _arg; 05964 string _name; 05965 05966 public: 05967 05968 // -- Constructors 05969 05970 attribNode(const char * name, exprNode * arg, 05971 const Coord coord = Coord::Unknown); 05972 05973 // Was ConvertIdToAttrib in ast.c 05974 05975 attribNode(idNode * id, exprNode * arg); 05976 05982 virtual ~attribNode(); 05983 05988 05989 inline string & name() { return _name; } 05990 inline void name(string name) { _name = name; } 05991 05992 inline exprNode * arg() const { return _arg; } 05993 inline exprNode * get_arg() { exprNode * out = _arg; _arg = 0; return out; } 05994 inline void arg(exprNode * arg) { _arg = arg; } 05995 05997 06002 06003 virtual void visit(Visitor * the_visitor); 06004 virtual void walk(Walker & the_walker); 06005 virtual Node * change(Changer & the_changer, bool redispatch = false); 06006 06008 06009 // -- Dataflow 06010 06011 virtual void dataflow(FlowVal * v, FlowProblem & fp) {} 06012 06013 // -- Clone 06014 06015 virtual Node * clone() const { return new attribNode ( *this ); } 06016 06017 // -- Output 06018 06019 virtual void output_stmt(output_context & ct, Node * par); 06020 }; 06021 06040 class operandNode : public exprNode { 06041 private: 06042 bool _star; // *foo 06043 bool _addr; // &foo 06044 typeNode * _cast; 06045 indexNode * _var; 06046 id_list _fields; // for var.foo.bar.baz 06047 indexNode * _index; // this field is intended for array indices. 06048 public: 06049 operandNode(indexNode * the_var, const Coord coord = Coord::Unknown); 06050 operandNode(indexNode * the_var, bool star, bool addr, 06051 const Coord coord = Coord::Unknown); 06052 operandNode(indexNode * the_var, bool star, bool addr, id_list * fields, 06053 indexNode * array_index, const Coord coord = Coord::Unknown); 06054 06055 void addr(bool addr) { _addr = addr; } 06056 bool addr() const { return _addr; } 06057 void star(bool star) { _star = star; } 06058 bool star() const { return _star; } 06059 void cast(typeNode * cast) { _cast = cast; } 06060 typeNode * cast(void) { return _cast; } 06061 const typeNode * cast(void) const { return _cast; } 06062 inline id_list & fields() { return _fields; } 06063 inline const id_list & fields() const { return _fields; } 06064 void index(indexNode * index) { _index = index; } 06065 indexNode * index(void) { return _index; } 06066 const indexNode * index(void) const { return _index; } 06067 void var(indexNode * var) { _var = var; } 06068 indexNode * var(void) { return _var; } 06069 const indexNode * var(void) const { return _var; } 06070 06071 // TODO: do we want these? 06072 /* virtual typeNode * base_type(bool TdefIndir) const; */ 06073 06074 virtual typeNode * type() const; 06075 virtual void type(typeNode *); 06076 virtual typeNode * noncast_type(bool convertArrays = true) const; 06077 06078 virtual void eval(); 06079 virtual void visit(Visitor * the_visitor); 06080 virtual void walk(Walker & the_walker); 06081 virtual Node * change(Changer & the_changer, bool redispatch = false); 06082 virtual void dataflow(FlowVal * v, FlowProblem & fp); 06083 virtual Node * clone() const { return new operandNode(*this); } 06084 virtual void output_expr(output_context & ct, Node * parent, int prec, 06085 Assoc assoc); 06086 }; 06087 06088 06099 class conditiongotoNode : public gotoNode { 06100 private: 06101 indexNode * _oper1; 06102 indexNode * _oper2; 06103 Operator * _op; // must be a relational operator 06104 public: 06105 // if ( left <op_id> right ) goto label 06106 conditiongotoNode(labelNode * label, indexNode * left, unsigned int op_id, 06107 indexNode * right, const Coord coord = Coord::Unknown); 06108 06109 void left(indexNode * left) { _oper1 = left; } 06110 indexNode * left(void) { return _oper1; } 06111 void right(indexNode * right) { _oper2 = right; } 06112 indexNode * right(void) { return _oper2; } 06113 void op(Operator * op); 06114 // TODO: is this safe? can't code change the op_id directly with this? 06115 Operator * op(void) { return _op; } 06116 06117 virtual void visit(Visitor * the_visitor); 06118 virtual void walk(Walker & the_walker); 06119 virtual Node * change(Changer & the_changer, bool redispatch = false); 06120 virtual void dataflow(FlowVal * v, FlowProblem & fp); 06121 virtual Node * clone() const { return new conditiongotoNode(*this); } 06122 virtual void output_stmt(output_context & ct, Node * par); 06123 }; 06124 06125 06126 06150 class threeAddrNode : public stmtNode { 06151 private: 06152 operandNode * _lhs; 06153 operandNode * _rhs1; // if op == FUNC_CALL, this is the function "name" 06154 Operator * _op; // TODO: need to add operator for FUNC_CALL 06155 operandNode * _rhs2; // NULL if op == FUNC_CALL 06156 typeNode * _sizeof_type; // if op == SIZEOF 06157 operand_list _arg_list; // for function calls 06158 public: 06159 // a = b; 06160 threeAddrNode(operandNode * lhs, operandNode * rhs, 06161 const Coord coord = Coord::Unknown); 06162 // a = -b; 06163 threeAddrNode(operandNode * lhs, unsigned int op_id, 06164 operandNode * rhs, const Coord coord = Coord::Unknown); 06165 // a = sizeof(<type>) 06166 threeAddrNode(operandNode * lhs, typeNode * type, 06167 const Coord coord = Coord::Unknown); 06168 // a = b (op) c; 06169 threeAddrNode(operandNode * lhs, operandNode * rhs1, unsigned int op_id, 06170 operandNode * rhs2, const Coord coord = Coord::Unknown); 06171 // a = b(...); 06172 threeAddrNode(operandNode * lhs, operandNode * func, 06173 operand_list * arg_list, const Coord coord = Coord::Unknown); 06174 // a(...); 06175 threeAddrNode(operandNode * func, operand_list * arg_list, 06176 const Coord coord = Coord::Unknown); 06177 06178 void lhs(operandNode * lhs) { _lhs = lhs; } 06179 operandNode * lhs(void) { return _lhs; } 06180 void rhs1(operandNode * rhs1) { _rhs1 = rhs1; } 06181 operandNode * rhs1(void) { return _rhs1; } 06182 void op(Operator * op) { _op = op; } 06183 // TODO: is this safe? can't code change the op_id directly with this? 06184 Operator * op(void) { return _op; } 06185 // TODO: is this safe? if _op is FUNC_CALL, this shouldn't be allowed 06186 void rhs2(operandNode * rhs2) { _rhs2 = rhs2; } 06187 operandNode * rhs2(void) { return _rhs2; } 06188 void sizeof_type(typeNode * type) { _sizeof_type = type; } 06189 typeNode * sizeof_type(void) { return _sizeof_type; } 06190 inline operand_list & arg_list() { return _arg_list; } 06191 inline const operand_list & arg_list() const { return _arg_list; } 06192 06193 virtual void visit(Visitor * the_visitor); 06194 virtual void walk(Walker & the_walker); 06195 virtual Node * change(Changer & the_changer, bool redispatch = false); 06196 virtual void dataflow(FlowVal * v, FlowProblem & fp); 06197 virtual Node * clone() const { return new threeAddrNode(*this); } 06198 virtual void output_stmt(output_context & ct, Node * par); 06199 }; 06200 06207 class textNode : public Node 06208 { 06209 06210 private: 06211 06212 string _text; 06213 bool _start_new_line; 06214 bool _suppress_output; 06215 06216 public: 06217 06218 // -- Constructors 06219 06220 textNode(const char * text, bool start_new_line, 06221 const Coord coord = Coord::Unknown); 06222 06228 virtual ~textNode(); 06229 06234 06235 inline string & text() { return _text; } 06236 inline void text(string text) { _text = text; } 06237 06238 inline bool start_new_line() const { return _start_new_line; } 06239 inline void start_new_line(bool start_new_line) { _start_new_line = start_new_line; } 06240 06241 inline bool suppress_output() const { return _suppress_output; } 06242 inline void suppress_output(bool suppress) { _suppress_output = suppress; } 06243 06245 06250 06251 virtual void visit(Visitor * the_visitor); 06252 virtual void walk(Walker & the_walker); 06253 virtual Node * change(Changer & the_changer, bool redispatch = false); 06254 06256 06257 // -- Dataflow 06258 06259 virtual void dataflow(FlowVal * v, FlowProblem & fp) {} 06260 06261 // -- Clone 06262 06263 virtual Node * clone() const { return new textNode ( *this ); } 06264 06265 // -- Output 06266 06267 virtual void output(output_context & ct, Node * par); 06268 }; 06269 06270 // ------------------------------------------------------------ 06271 // Template functions 06272 // ------------------------------------------------------------ 06273 06274 template< class T > 06275 void dataflow_forward_list(list< T > & l, FlowVal * v, FlowProblem & fp) 06276 { 06277 for (typename list< T >::iterator p = l.begin(); 06278 p != l.end(); 06279 ++p) 06280 (*p)->dataflow(v, fp); 06281 } 06282 06283 template< class T > 06284 void dataflow_reverse_list(list< T > & l, FlowVal * v, FlowProblem & fp) 06285 { 06286 for (typename list< T >::reverse_iterator p = l.rbegin(); 06287 p != l.rend(); 06288 ++p) 06289 (*p)->dataflow(v, fp); 06290 } 06291 06292 template< class T > 06293 void output_list(list< T > & l, output_context & ct, Node * par) 06294 { 06295 for (typename list< T >::iterator p = l.begin(); 06296 p != l.end(); 06297 ++p) 06298 (*p)->output(ct, par); 06299 } 06300 06301 template< class T > 06302 void output_delim_list(list< T > & l, output_context & ct, Node * par, char delim) 06303 { 06304 for (typename list< T >::iterator p = l.begin(); 06305 p != l.end(); 06306 ++p) 06307 { 06308 if (p != l.begin()) { 06309 ct << delim; 06310 ct.space(); 06311 ct.continue_line(); 06312 } 06313 (*p)->output(ct, par); 06314 } 06315 } 06316 06317 template< class T > 06318 void delete_list(list< T > & l) 06319 { 06320 for (typename list< T >::iterator p = l.begin(); 06321 p != l.end(); 06322 ++p) 06323 delete (*p); 06324 } 06325 06326 #endif // CBZ_AST_H |
Generated on February 1, 2006
Back to the C-Breeze home page