Synopsis - Cross-Reference

File: /Synopsis/Parsers/Cxx/Walker.hh
  1//
  2// Copyright (C) 2000 Stefan Seefeld
  3// Copyright (C) 2000 Stephen Davies
  4// All rights reserved.
  5// Licensed to the public under the terms of the GNU LGPL (>= 2),
  6// see the file COPYING for details.
  7//
  8
  9#ifndef Walker_hh_
 10#define Walker_hh_
 11
 12#include <Synopsis/PTree.hh>
 13// Stupid occ
 14#undef Scope
 15
 16#include <vector>
 17#include <string>
 18
 19// Forward declarations
 20class Builder;
 21namespace Synopsis {class Buffer;}
 22class Decoder;
 23class TypeIdFormatter;
 24class SXRGenerator;
 25class Lookup;
 26class FileFilter;
 27
 28using namespace Synopsis;
 29
 30namespace ASG
 31{
 32class SourceFile;
 33class Parameter;
 34class Inheritance;
 35class Declaration;
 36class Function;
 37class Scope;
 38}
 39namespace Types
 40{
 41class Type;
 42}
 43
 44//. A walker that creates an ASG. All Translate* methods have been overridden
 45//. to remove the translation code.
 46class Walker : public PTree::Visitor
 47{
 48public:
 49  //. Constructor
 50  Walker(FileFilter*, Builder*, Synopsis::Buffer*);
 51  virtual ~Walker();
 52
 53  //. Sets store links to true.
 54  //. This will cause the whole ptree to be traversed, and any linkable
 55  //. identifiers found will be stored
 56  void set_store_links(SXRGenerator*);
 57
 58  //. Get a name from the ptree
 59  std::string parse_name(PTree::Node *) const;
 60  
 61  //. Get the Buffer object
 62  Synopsis::Buffer* buffer() { return my_buffer;}
 63  //. Get the Builder object
 64  Builder* builder() { return my_builder;}
 65  //. Get the TypeFormatter object
 66  TypeIdFormatter* type_formatter(){ return my_type_formatter;}
 67#if 0
 68  //. Returns true if the current filename from the last getLine or
 69  //. updateLineNumber call is equal to the main source filename
 70  bool is_main_file() { return (my_filename == my_source);}
 71#endif
 72
 73  //. Get the line number of the given Ptree node
 74  int line_of_ptree(PTree::Node *);
 75  //. Update the line number
 76  void update_line_number(PTree::Node *);
 77
 78  void add_comments(ASG::Declaration* decl, PTree::Node *comments);
 79  void add_comments(ASG::Declaration* decl, PTree::CommentedAtom *node);
 80  void add_comments(ASG::Declaration* decl, PTree::Declarator *node);
 81  void add_comments(ASG::Declaration* decl, PTree::Declaration *node);
 82  void add_comments(ASG::Declaration* decl, PTree::NamespaceSpec *node);
 83  //. Traverses left side of tree till it finds a leaf, and if that is a
 84  //. CommentedAtom then it adds those comments as spans
 85  void find_comments(PTree::Node * node);
 86
 87  // Takes the (maybe 0) args list and puts them in my_params
 88  void translate_function_args(PTree::Node * args);
 89  void translate_parameters(PTree::Node * p_params, std::vector<ASG::Parameter*>& params);
 90  void translate_function_name(const PTree::Encoding &encname, std::string& realname, Types::Type*& returnType);
 91  PTree::Node *translate_declarator(PTree::Node *);
 92  PTree::Node *translate_function_declarator(PTree::Node *, bool is_const);
 93  PTree::Node *translate_variable_declarator(PTree::Node *, bool is_const);
 94  void translate_typedef_declarator(PTree::Node *node);
 95  std::vector<ASG::Inheritance*> translate_inheritance_spec(PTree::Node *node);
 96  //. Returns a formatter string of the parameters. The idea is that this
 97  //. string will be appended to the function name to form the 'name' of the
 98  //. function.
 99  std::string format_parameters(std::vector<ASG::Parameter*>& params);
100
101  //. Translates the template parameters and creates the template type.
102  void translate_template_params(PTree::Node *params);
103
104  //. Overridden to catch exceptions
105  void translate(PTree::Node *);
106
107  void visit(PTree::Atom *);
108  void visit(PTree::List *);
109  void visit(PTree::Typedef *);
110  void visit(PTree::TemplateDecl *);
111  void visit(PTree::TemplateInstantiation *);
112  //virtual PTree::Node * TranslateTemplateInstantiation(PTree::Node *, PTree::Node *, PTree::Node *, Class*);
113  void visit(PTree::ExternTemplate *);
114  void visit(PTree::CommentedAtom *);
115  void visit(PTree::Identifier *node) { translate_variable(node);}
116  void visit(PTree::Brace *);
117  void visit(PTree::Block *);
118  void visit(PTree::ClassBody *node) { visit(static_cast<PTree::Brace *>(node));}
119  void visit(PTree::ClassSpec *);
120  void visit(PTree::EnumSpec *);
121  void visit(PTree::MetaclassDecl *);
122  void visit(PTree::LinkageSpec *);
123  void visit(PTree::NamespaceSpec *);
124  void visit(PTree::UsingDirective *);
125  void visit(PTree::Declaration *);
126  void visit(PTree::UsingDeclaration *);
127  void visit(PTree::Name *node) { translate_variable(node);}
128  void visit(PTree::AccessSpec *);
129  void visit(PTree::AccessDecl *);
130  void visit(PTree::UserAccessSpec *);
131  void visit(PTree::IfStatement *);
132  void visit(PTree::SwitchStatement *);
133  void visit(PTree::WhileStatement *);
134  void visit(PTree::DoStatement *);
135  void visit(PTree::ForStatement *);
136  void visit(PTree::TryStatement *);
137  void visit(PTree::BreakStatement *);
138  void visit(PTree::ContinueStatement *);
139  void visit(PTree::ReturnStatement *);
140  void visit(PTree::GotoStatement *);
141  void visit(PTree::CaseStatement *);
142  void visit(PTree::DefaultStatement *);
143  void visit(PTree::LabelStatement *);
144  void visit(PTree::ExprStatement *);
145  void visit(PTree::Expression *);
146  void visit(PTree::AssignExpr *);
147  void visit(PTree::CondExpr *);
148  void visit(PTree::InfixExpr *);
149  void visit(PTree::PmExpr *);
150  void visit(PTree::CastExpr *);
151  void visit(PTree::UnaryExpr *);
152  void visit(PTree::ThrowExpr *);
153  void visit(PTree::SizeofExpr *);
154  void visit(PTree::NewExpr *);
155  void visit(PTree::DeleteExpr *);
156  void visit(PTree::Kwd::This *);
157  void visit(PTree::FstyleCastExpr *);
158  void visit(PTree::ArrayExpr *);
159  void visit(PTree::FuncallExpr *); // and fstyle cast
160  void visit(PTree::PostfixExpr *);
161  void visit(PTree::UserStatementExpr *);
162  void visit(PTree::DotMemberExpr *);
163  void visit(PTree::ArrowMemberExpr *);
164  void visit(PTree::ParenExpr *);
165  void visit(PTree::StaticUserStatementExpr *);
166  
167  PTree::TemplateDecl *translate_class_template(PTree::TemplateDecl *,
168						PTree::ClassSpec *);
169  PTree::TemplateDecl *translate_function_template(PTree::TemplateDecl *,
170						   PTree::Node *);
171  PTree::Node *translate_storage_specifiers(PTree::Node *);
172  PTree::Node *translate_declarators(PTree::Node *);
173  PTree::Node *translate_arg_decl_list(bool, PTree::Node *, PTree::Node *);
174  PTree::Node *translate_initialize_args(PTree::Declarator *, PTree::Node *);
175  PTree::Node *translate_assign_initializer(PTree::Declarator *, PTree::Node *);
176  PTree::Node *translate_function_implementation(PTree::Node *);
177  PTree::Node *translate_function_body(PTree::Node *);
178  //virtual PTree::Node * TranslateClassBody(PTree::Node *, PTree::Node *, Class*);
179  
180  //virtual Class* MakeClassMetaobject(PTree::Node *, PTree::Node *, PTree::Node *);
181  //virtual PTree::Node * TranslateClassSpec(PTree::Node *, PTree::Node *, PTree::Node *, Class*);
182  
183  virtual PTree::Node *translate_type_specifier(PTree::Node *);
184  virtual PTree::Node *translate_typeof(PTree::Node *, PTree::Node * declarations);
185  virtual PTree::Node *translate_new3(PTree::Node *type);
186  void translate_variable(PTree::Node *);
187  
188  ASG::SourceFile* current_file() const { return my_file;}
189  int current_lineno() const { return my_lineno;}
190  static Walker *instance() { return g_walker;}
191private:
192  // the 'current' walker is a debugging aid.
193  static Walker* g_walker;
194
195  Builder* my_builder;
196  FileFilter* my_filter;
197  Synopsis::Buffer* my_buffer;
198  Decoder* my_decoder;
199  Lookup* my_lookup;
200
201  //. A pointer to the currect declaration ptree, if any, used to get the
202  //. return type and modifiers, etc.
203  PTree::Node * my_declaration;
204  bool my_in_typedef;
205  //. True if we have just seen a class-specifier or enum-specifier
206  //. inside a decl-specifier-seq.
207  bool my_defines_class_or_enum;
208
209  //. A pointer to the current template parameters, if any, used to get the
210  //. template parameters and set in the declaration. Should be 0 if not
211  //. in a template.
212  std::vector<ASG::Parameter*>* my_template;
213  //. this reflects the filename containing the currently processed node.
214  std::string my_filename;
215  int my_lineno;
216  //. The current file, set by update_line_number
217  ASG::SourceFile* my_file;
218
219  //. True if should try and extract tail comments before }'s
220  bool my_extract_tails;
221  //. Storage for links. This is only set if we should be storing links, so
222  //. it must be checked before every use
223  SXRGenerator *sxr_;
224  //. True if this TranslateDeclarator should try to store the decl type
225  bool my_store_decl;
226  
227  //. A dummy name used for tail comments
228  std::vector<std::string> my_dummyname;
229  
230  //. An instance of TypeFormatter for formatting types
231  TypeIdFormatter* my_type_formatter;
232  
233  //. The current function, if in a function block
234  ASG::Function* my_function;
235  //. The params found before a function block. These may be different from
236  //. the ones that are in the original declaration(s), but it is these names
237  //. we need for referencing names inside the block, so a reference is stored
238  //. here.
239  std::vector<ASG::Parameter*> my_param_cache;
240  //. The types accumulated for function parameters in function calls
241  std::vector<Types::Type*> my_params;
242  //. The type returned from the expression-type translators
243  Types::Type* my_type;
244  //. The Scope to use for name lookups, or 0 to use enclosing default
245  //. scope rules. This is for when we are at a Variable, and already know it
246  //. must be part of a given class (eg, foo->bar .. bar must be in foo's
247  //. class)
248  ASG::Scope* my_scope;
249  
250  //. The state of postfix translation. This is needed for constructs like
251  //. foo->var versus var or foo->var(). The function call resolution needs
252  //. to be done in the final TranslateVariable, since that's where the last
253  //. name (which is to be linked) is handled.
254  enum Postfix_Flag
255  {
256    Postfix_Var, //.< Lookup as a variable
257    Postfix_Func, //.< Lookup as a function, using my_params for parameters
258  } my_postfix_flag;
259  
260  //. Info about one stored function impl. Function impls must be stored
261  //. till the end of a class.
262  struct FuncImplCache
263  {
264    ASG::Function* func;
265    std::vector<ASG::Parameter*> params;
266    PTree::Node * body;
267  };
268  //. A vector of function impls
269  typedef std::vector<FuncImplCache> FuncImplVec;
270  //. A stack of function impl vectors
271  typedef std::vector<FuncImplVec> FuncImplStack;
272  //. The stack of function impl vectors
273  FuncImplStack my_func_impl_stack;
274  void translate_func_impl_cache(const FuncImplCache &cache);
275  
276  //. Finds the column given the start ptr and the current position. The
277  //. derived column number is processed with the macro call dictionary
278  //. from the current file before returning,
279  //. so -1 may be returned to indicate "inside macro".
280  int find_col(const char* start, const char* find);
281
282  bool my_in_template_decl;
283};
284
285#endif // header guard