cppPreprocessor.h 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235
  1. /**
  2. * PANDA 3D SOFTWARE
  3. * Copyright (c) Carnegie Mellon University. All rights reserved.
  4. *
  5. * All use of this software is subject to the terms of the revised BSD
  6. * license. You should have received a copy of this license along
  7. * with this source code in a file named "LICENSE."
  8. *
  9. * @file cppPreprocessor.h
  10. * @author drose
  11. * @date 1999-10-22
  12. */
  13. #ifndef CPPPREPROCESSOR_H
  14. #define CPPPREPROCESSOR_H
  15. #include "dtoolbase.h"
  16. #include "cppManifest.h"
  17. #include "cppToken.h"
  18. #include "cppFile.h"
  19. #include "cppCommentBlock.h"
  20. #include "dSearchPath.h"
  21. #include "vector_string.h"
  22. #include <map>
  23. #include <list>
  24. #include <vector>
  25. #include <unordered_map>
  26. class CPPScope;
  27. class CPPTemplateParameterList;
  28. class CPPExpression;
  29. // #define CPP_VERBOSE_LEX
  30. /**
  31. *
  32. */
  33. class CPPPreprocessor {
  34. public:
  35. CPPPreprocessor();
  36. bool preprocess_file(const Filename &filename);
  37. void set_verbose(int verbose);
  38. int get_verbose() const;
  39. void copy_filepos(const CPPPreprocessor &other);
  40. CPPFile get_file() const;
  41. int get_line_number() const;
  42. int get_col_number() const;
  43. CPPToken get_next_token();
  44. CPPToken peek_next_token();
  45. #ifdef CPP_VERBOSE_LEX
  46. CPPToken get_next_token0();
  47. int _token_index;
  48. #endif
  49. void warning(const std::string &message) const;
  50. void warning(const std::string &message, const YYLTYPE &loc) const;
  51. void error(const std::string &message) const;
  52. void error(const std::string &message, const YYLTYPE &loc) const;
  53. void show_line(const YYLTYPE &loc) const;
  54. CPPCommentBlock *get_comment_before(int line, CPPFile file);
  55. CPPCommentBlock *get_comment_on(int line, CPPFile file);
  56. int get_warning_count() const;
  57. int get_error_count() const;
  58. typedef std::unordered_map<std::string, CPPManifest *> Manifests;
  59. Manifests _manifests;
  60. typedef std::vector<CPPManifest *> ManifestStack;
  61. std::map<std::string, ManifestStack> _manifest_stack;
  62. std::vector<CPPFile::Source> _quote_include_kind;
  63. DSearchPath _quote_include_path;
  64. DSearchPath _angle_include_path;
  65. bool _noangles;
  66. CPPComments _comments;
  67. typedef std::set<CPPFile> ParsedFiles;
  68. ParsedFiles _parsed_files;
  69. typedef std::set<std::string> Includes;
  70. Includes _quote_includes;
  71. Includes _angle_includes;
  72. std::set<Filename> _explicit_files;
  73. // This is normally true, to indicate that the preprocessor should decode
  74. // identifiers like foo::bar<snarf> into a single IDENTIFIER,
  75. // TYPENAME_IDENTIFIER, or SCOPING token for yacc's convenience. When
  76. // false, it leaves them alone and returns a sequence of SIMPLE_IDENTIFIER
  77. // and SCOPE tokens instead.
  78. bool _resolve_identifiers;
  79. // The default _verbose level is 1, which will output normal error and
  80. // warning messages but nothing else. Set this to 0 to make the warning
  81. // messages go away (although the counts will still be incremented), or set
  82. // it higher to get more debugging information.
  83. int _verbose;
  84. // The location of the last token.
  85. cppyyltype _last_token_loc;
  86. protected:
  87. bool init_cpp(const CPPFile &file);
  88. bool init_const_expr(const std::string &expr);
  89. bool init_type(const std::string &type);
  90. bool push_file(const CPPFile &file);
  91. bool push_string(const std::string &input);
  92. bool push_expansion(const std::string &input, const CPPManifest *manifest,
  93. const YYLTYPE &loc);
  94. public:
  95. void expand_manifests(std::string &expr, bool expand_undefined = false,
  96. const CPPManifest::Ignores &ignores = CPPManifest::Ignores()) const;
  97. CPPExpression *parse_expr(const std::string &expr, CPPScope *current_scope,
  98. CPPScope *global_scope, const YYLTYPE &loc);
  99. private:
  100. CPPToken internal_get_next_token();
  101. int check_digraph(int c);
  102. int check_trigraph(int c);
  103. int skip_whitespace(int c);
  104. int skip_comment(int c);
  105. int skip_c_comment(int c);
  106. int skip_cpp_comment(int c);
  107. int skip_digit_separator(int c);
  108. int process_directive(int c);
  109. int get_preprocessor_command(int c, std::string &command);
  110. int get_preprocessor_args(int c, std::string &args);
  111. void handle_define_directive(const std::string &args, const YYLTYPE &loc);
  112. void handle_undef_directive(const std::string &args, const YYLTYPE &loc);
  113. void handle_ifdef_directive(const std::string &args, const YYLTYPE &loc);
  114. void handle_ifndef_directive(const std::string &args, const YYLTYPE &loc);
  115. void handle_if_directive(const std::string &args, const YYLTYPE &loc);
  116. void handle_include_directive(const std::string &args, const YYLTYPE &loc);
  117. void handle_pragma_directive(const std::string &args, const YYLTYPE &loc);
  118. void handle_error_directive(const std::string &args, const YYLTYPE &loc);
  119. void skip_false_if_block(bool consider_elifs);
  120. bool is_manifest_defined(const std::string &manifest_name) const;
  121. bool find_include(Filename &filename, bool angle_quotes, CPPFile::Source &source) const;
  122. CPPToken get_quoted_char(int c);
  123. CPPToken get_quoted_string(int c);
  124. CPPToken get_identifier(int c);
  125. CPPToken get_literal(int token, YYLTYPE loc, const std::string &str,
  126. const YYSTYPE &result = YYSTYPE());
  127. CPPToken expand_manifest(const CPPManifest *manifest, const YYLTYPE &loc);
  128. void r_expand_manifests(std::string &expr, bool expand_undefined,
  129. const YYLTYPE &loc, std::set<const CPPManifest *> &expanded);
  130. void extract_manifest_args(const std::string &name, int num_args,
  131. int va_arg, vector_string &args);
  132. void expand_defined_function(std::string &expr, size_t q, size_t &p) const;
  133. void expand_has_include_function(std::string &expr, size_t q, size_t &p) const;
  134. CPPToken get_number(int c);
  135. int scan_escape_sequence(int c);
  136. std::string scan_quoted(int c);
  137. std::string scan_raw(int c);
  138. bool should_ignore_manifest(const CPPManifest *manifest) const;
  139. bool should_ignore_preprocessor() const;
  140. int get();
  141. int peek();
  142. void unget(int c);
  143. CPPTemplateParameterList *
  144. nested_parse_template_instantiation(CPPTemplateScope *scope);
  145. void skip_to_end_nested();
  146. void skip_to_angle_bracket();
  147. class InputFile {
  148. public:
  149. InputFile();
  150. ~InputFile();
  151. bool open(const CPPFile &file);
  152. bool connect_input(const std::string &input);
  153. int get();
  154. int peek();
  155. const CPPManifest *_manifest;
  156. CPPFile _file;
  157. std::string _input;
  158. std::istream *_in;
  159. int _line_number;
  160. int _col_number;
  161. int _next_line_number;
  162. int _next_col_number;
  163. bool _lock_position;
  164. bool _ignore_manifest;
  165. int _prev_last_c;
  166. };
  167. // This must be a list and not a vector because we don't have a good copy
  168. // constructor defined for InputFile.
  169. typedef std::list<InputFile> Files;
  170. Files _files;
  171. enum State {
  172. S_normal, S_eof, S_nested, S_end_nested
  173. };
  174. State _state;
  175. int _paren_nesting;
  176. bool _parsing_template_params;
  177. bool _parsing_attribute;
  178. bool _start_of_line;
  179. int _unget;
  180. int _last_c;
  181. bool _last_cpp_comment;
  182. bool _save_comments;
  183. std::vector<CPPToken> _saved_tokens;
  184. mutable int _warning_count;
  185. mutable int _error_count;
  186. bool _error_abort;
  187. };
  188. #endif