00001 #ifndef __ROSEAttributesList_H__ 00002 #define __ROSEAttributesList_H__ 00003 00004 //#include "setup.h" 00005 00006 //#include <list> 00007 //#include <vector> 00008 #include <map> 00009 00010 // Include the ROSE lex specific definitions of tokens 00011 #include "general_token_defs.h" 00012 00013 // #ifdef CAN_NOT_COMPILE_WITH_ROSE 00014 // #warning "CAN_NOT_COMPILE_WITH_ROSE IS defined" 00015 // #else 00016 // #warning "CAN_NOT_COMPILE_WITH_ROSE is NOT defined" 00017 // #endif 00018 00019 // DQ (2/28/2010): Skip this if we are compiling ROSE using ROSE. 00020 // This is being used in place of the CAN_NOT_COMPILE_WITH_ROSE macro. 00021 // Note that CAN_NOT_COMPILE_WITH_ROSE is set by the following projects: 00022 // 1) projects/DocumentationGenerator 00023 // 2) projects/haskellport 00024 // in their Makefile.am files. I think that using CXX_IS_ROSE_ANALYSIS 00025 // will be equivalent (used to indicate the a ROSE translator is being 00026 // used to compile the ROSE source code). 00027 // However, it might be that this is equivalent to the USE_ROSE macro, 00028 // which is set for all ROSE translators when they compile any code. 00029 // DQ (12/22/2008): I would appreciate it if this were a better name... 00030 // #if !CAN_NOT_COMPILE_WITH_ROSE 00031 // #ifndef USE_ROSE 00032 00033 // DQ (5/21/2010): I have built a separate macro for tuning off the compilation of WAVE 00034 // since it is done only for the purpose of allowing ROSE based projects: 00035 // 1) projects/DocumentationGenerator 00036 // 2) projects/haskellport 00037 // to process the ROSE files cleanly. ROSE can however process and compile ROSE 00038 // (including a slightly modified version of WAVE that EDG will accept) and we 00039 // separately test this in noightly tests. The previous 5/18/2010 fix to permit 00040 // the Haskell support to skip processign WAVE turned this off and broke the nightly 00041 // tests of ROSE compiling ROSE. This use of the macro ROSE_SKIP_COMPILATION_OF_WAVE 00042 // it menat to be turned on by ROSE based tools that need to process the ROSE code 00043 // and which currently fail (because of Wave) and so turn of the processing of Wave 00044 // for those tools. 00045 // #ifdef USE_ROSE 00046 // #define ROSE_SKIP_COMPILATION_OF_WAVE 00047 // #endif 00048 00049 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00050 #if _MSC_VER < 1600 // 1600 == VC++ 10.0 00051 #include <boost/preprocessor/iteration/iterate.hpp> // Liao, 7/10/2009, required by GCC 4.4.0 for a #define line of BOOST_PP_ITERATION_DEPTH 00052 #ifdef _MSC_VER 00053 #include <boost/wave.hpp> // CH (4/7/2010): Put this header here to avoid compiling error about mismatch between defination and declaration 00054 #endif 00055 #include <boost/wave/cpplexer/cpp_lex_token.hpp> // token class 00056 #include <boost/wave/cpplexer/cpp_lex_iterator.hpp> // lexer type 00057 #else 00058 // #warning "Setting CAN_NOT_COMPILE_WITH_ROSE to value = 1" 00059 // #define CAN_NOT_COMPILE_WITH_ROSE 1 00060 // tps (12/4/2009) : This is not found in VC++ 10.0 and Boost 1.4 00061 #pragma message ("Boost preprocessor and wave not included yet for VC++ 10.0") 00062 00063 #endif 00064 #endif 00065 00066 //template boost::wave::cpplexer::impl::token_data<std::string, boost::wave::util::file_position_type>::delete(std::size_t) ; 00067 // DQ (10/16/2002): Required for compiling with SUN 5.2 C++ compiler 00068 #ifndef NAMESPACE_IS_BROKEN 00069 // DQ (12/30/2005): This is a Bad Bad thing to do (I can explain) 00070 // it hides names in the global namespace and causes errors in 00071 // otherwise valid and useful code. Where it is needed it should 00072 // appear only in *.C files (and only ones not included for template 00073 // instantiation reasons) else they effect user who use ROSE unexpectedly. 00074 // using namespace std; 00075 #endif 00076 00077 class PreprocessingInfo; 00078 class ROSEAttributesList; 00079 //AS(01/04/07) Global map of filenames to PreprocessingInfo*'s as it is inefficient 00080 //to get this by a traversal of the AST 00081 extern std::map<std::string,ROSEAttributesList* > mapFilenameToAttributes; 00082 00083 00084 // DQ (4/19/2006): Forward declaration so that PreprocessingInfo can 00085 // contain a pointer to a Sg_File_Info object. 00086 class Sg_File_Info; 00087 00088 // DQ (1/21/2008): Need forward declaration 00089 class SgFile; 00090 00091 // #if !CAN_NOT_COMPILE_WITH_ROSE 00092 // #ifndef USE_ROSE 00093 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00094 00095 typedef boost::wave::cpplexer::lex_token<> token_type; 00096 typedef std::vector<token_type> token_container; 00097 typedef std::list<token_type> token_list_container; 00098 typedef std::vector<std::list<token_type> > token_container_container; 00099 00100 #endif 00101 00103 class PreprocessingInfo 00104 { 00105 public: 00106 // DQ (10/15/2002) moved this to nested scope to avoid global name pollution :-). 00109 enum RelativePositionType 00110 { 00111 defaultValue = 0, // let the zero value be an error value 00112 undef = 1, // Position of the directive is only going to be defined 00113 // when the preprocessing object is copied into the AST, 00114 // it remains undefined before that 00115 before = 2, // Directive goes before the correponding code segment 00116 after = 3, // Directive goes after the correponding code segment 00117 inside = 4, // Directive goes inside the correponding code segment (as in between "{" and "}" of an empty basic block) 00118 00119 // DQ (7/19/2008): Added additional fields so that we could use this enum type in the AstUnparseAttribute 00120 // replace = 5, // Support for replacing the IR node in the unparsing of any associated subtree 00121 before_syntax = 6, // We still have to specify the syntax 00122 after_syntax = 7 // We still have to specify the syntax 00123 }; 00124 00125 // Enum type to help classify the type for string that has been saved. 00126 // This helps in the unparsing to make sure that line feeds are introduced properly. 00127 // 00128 // Rama (08/17/07): Adding a CpreprocessorDeadIfDeclaration and its support 00129 // in various files. 00130 enum DirectiveType 00131 { 00132 // This is treated as an error 00133 CpreprocessorUnknownDeclaration, 00134 00135 // These are a classification for comments 00136 C_StyleComment, 00137 CplusplusStyleComment, 00138 FortranStyleComment, 00139 00140 // FMZ(5/14/2010): Added freeform comments (started with "!") 00141 F90StyleComment, 00142 00143 // DQ (11/20/2008): Added classification for blank line (a language independent form of comment). 00144 CpreprocessorBlankLine, 00145 00146 // These used to be translated into IR nodes (and will be in the future). 00147 CpreprocessorIncludeDeclaration, 00148 CpreprocessorIncludeNextDeclaration, 00149 CpreprocessorDefineDeclaration, 00150 CpreprocessorUndefDeclaration, 00151 CpreprocessorIfdefDeclaration, 00152 CpreprocessorIfndefDeclaration, 00153 CpreprocessorIfDeclaration, 00154 CpreprocessorDeadIfDeclaration, 00155 CpreprocessorElseDeclaration, 00156 CpreprocessorElifDeclaration, 00157 CpreprocessorEndifDeclaration, 00158 CpreprocessorLineDeclaration, 00159 CpreprocessorErrorDeclaration, 00160 00161 // DQ (10/19/2005): Added CPP warning directive 00162 CpreprocessorWarningDeclaration, 00163 CpreprocessorEmptyDeclaration, 00164 00165 // AS (11/18/05): Added macro support (these are generated by the Wave 00166 // support, but need to be better documented as to what they mean). 00167 CSkippedToken, 00168 CMacroCall, 00169 00170 // AS & LIAO (8/12/2008): A PreprocessingInfo that is a 00171 // hand made MacroCall that will expand into a valid statement. 00172 CMacroCallStatement, 00173 00174 // DQ (11/28/2008): What does this mean! 00175 // A line replacement will replace a sub-tree in the AST 00176 // after a node with position (filename,line) 00177 LineReplacement, 00178 00179 // The is the 'extern "C" {' construct. Note that this is not captured in 00180 // the EDG AST and it is required to be captured as part of the CPP and 00181 // comment preprocessing. 00182 ClinkageSpecificationStart, 00183 ClinkageSpecificationEnd, 00184 00185 // DQ (11/17/2008): Added support for #ident 00186 CpreprocessorIdentDeclaration, 00187 00188 // DQ (11/17/2008): This handles the case CPP declarations (called "linemarkers") 00189 // (see Google for more details) such as: "# 1 "test2008_05.F90"", "# 1 "<built-in>"", 00190 // "# 1 "<command line>"" "# 1 "test2008_05.F90"" 00191 // The first token is the line number, 00192 // the second token is the filename (or string), 00193 // the optional tokens (zero or more) are flags: 00194 // '1' indicates the start of a new file. 00195 // '2' indicates returning to a file (having included another file). 00196 // '3' indicates that the following text comes from a system header file, so certain warnings should be supressed. 00197 // '4' indicates that the following text should be treated as being wrapped in an implicit 'extern "C"' block 00198 CpreprocessorCompilerGeneratedLinemarker, 00199 00200 LastDirectiveType 00201 }; 00202 00203 // DQ (7/10/2004): Make the data private 00204 private: 00205 00206 // DQ (4/19/2006): Use the SgFileInfo object to hold the more complete 00207 // information about the filename, line number, and column number. 00208 Sg_File_Info* file_info; 00209 // int lineNumber; 00210 // int columnNumber; 00211 00212 // Use string class to improve implementation 00213 // char* stringPointer; 00214 std::string internalString; 00215 00216 int numberOfLines; 00217 00218 // enum value representing a classification of the different types of directives 00219 DirectiveType whatSortOfDirective; 00220 00221 // Corresponding enum value 00222 RelativePositionType relativePosition; 00223 00224 // DQ (11/28/2008): Support for CPP generated linemarkers 00225 int lineNumberForCompilerGeneratedLinemarker; 00226 std::string filenameForCompilerGeneratedLinemarker; 00227 std::string optionalflagsForCompilerGeneratedLinemarker; 00228 00229 // This is part of Wave support in ROSE. 00230 // #ifndef USE_ROSE 00231 public: 00232 /* 00233 // AS using the lexer_token from boost_wave in order to store structures 00234 typedef boost::wave::cpplexer::lex_token<> token_type; 00235 typedef std::vector<token_type> token_container; 00236 typedef std::list<token_type> token_list_container; 00237 typedef std::vector<std::list<token_type> > token_container_container; 00238 */ 00239 private: 00240 // FIXME: To support Jochens AST binary save work the tokenSteam must 00241 // have a pointer type. 00242 00243 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00244 // A stream of tokens representing the current prerpocessing info 00245 // object. This is equivalent to the internal string, but of cause 00246 // contains more information since it is a tokenized stream. 00247 token_container* tokenStream; 00248 00249 public: 00250 typedef struct r_include_directive 00251 { 00252 // The parameter 'directive' contains the (expanded) file name found after 00253 // the #include directive. This has the format '<file>', '"file"' or 'file'. 00254 token_type directive; 00255 // The paths plus name to the include directive filename 00256 std::string absname; 00257 std::string relname; 00258 } rose_include_directive; 00259 00260 // Internal representation of a macro #define directive 00261 typedef struct r_macro_def 00262 { 00263 bool is_functionlike; 00264 bool is_predefined; 00265 token_type macro_name; 00266 token_container paramaters; 00267 token_list_container definition; 00268 r_macro_def() : macro_name(), paramaters(),definition() {} 00269 } rose_macro_definition; 00270 00271 // Internal representation of a macro call 00272 // e.g #define MACRO_CALL int x; 00273 // MACRO_CALL 00274 typedef struct r_macro_call 00275 { 00276 bool is_functionlike; 00277 PreprocessingInfo* macro_def; 00278 token_type macro_call; 00279 token_container_container arguments; 00280 token_container expanded_macro; 00281 00282 // Get string representation of the expanded macro 00283 std::string get_expanded_string() 00284 { 00285 std::ostringstream os; 00286 token_container::const_iterator iter; 00287 for (iter=expanded_macro.begin(); iter!=expanded_macro.end(); iter++) 00288 os << (*iter).get_value(); 00289 return os.str(); 00290 } 00291 00292 r_macro_call() : macro_call(), arguments(),expanded_macro() {} 00293 } rose_macro_call; 00294 00295 private: 00296 // AS add macro definition 00297 rose_macro_definition* macroDef; 00298 // AS add macro call 00299 rose_macro_call* macroCall; 00300 // AS include directive 00301 rose_include_directive* includeDirective; 00302 00303 #endif 00304 00305 // member functions 00306 public: 00307 ~PreprocessingInfo(); 00308 PreprocessingInfo(); 00309 00310 // #ifndef USE_ROSE 00311 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00312 // AS (112105) Added constructors to support macros 00313 PreprocessingInfo(token_container, DirectiveType, RelativePositionType); 00314 PreprocessingInfo(rose_macro_call*, RelativePositionType); 00315 PreprocessingInfo(rose_macro_definition*, RelativePositionType); 00316 PreprocessingInfo(token_type, token_list_container, bool, DirectiveType,RelativePositionType); 00317 PreprocessingInfo(rose_include_directive*, RelativePositionType); 00318 #endif 00319 00320 // This constructor is called from the C++ code generated from the lex file (preproc.lex) 00321 // PreprocessingInfo(DirectiveType, const char *inputStringPointer, int line_no , int col_no, 00322 // int nol, RelativePositionType relPos, bool copiedFlag, bool unparsedFlag) ROSE_DEPRECATED_FUNCTION; 00323 00324 // DQ (7/19/2008): I have removed the bool copiedFlag and bool unparsedFlag parameters because they are not used 00325 // and are present only because in an older implementation of the unparser it would make the PreprocessingInfo 00326 // as unparsed (and maybe copied) but this sort of side-effect of the unparser was later removed to make the 00327 // unparsing side-effect free. 00328 // DQ (4/19/2006): Use the SgFileInfo object to hold the more complete 00329 // information about the filename, line number, and column number. 00330 // DQ (3/15/2006): Build constructor that uses C++ string as input (to replace the char* based constructor) 00331 // PreprocessingInfo(DirectiveType, const std::string inputString, int line_no , int col_no, 00332 // int nol, RelativePositionType relPos, bool copiedFlag, bool unparsedFlag); 00333 // PreprocessingInfo(DirectiveType, const std::string & inputString, 00334 // const std::string & filenameString, int line_no , int col_no, 00335 // int nol, RelativePositionType relPos, bool copiedFlag, bool unparsedFlag ); 00336 PreprocessingInfo(DirectiveType, const std::string & inputString, 00337 const std::string & filenameString, int line_no , int col_no, 00338 int nol, RelativePositionType relPos ); 00339 00340 // Copy constructor 00341 PreprocessingInfo(const PreprocessingInfo &prepInfo); 00342 00343 void display(const std::string & label) const; 00344 00345 // Access functions 00346 int getLineNumber() const; 00347 int getColumnNumber() const; 00348 std::string getString() const; 00349 void setString ( const std::string & s ); 00350 int getStringLength() const; 00351 DirectiveType getTypeOfDirective() const; 00352 RelativePositionType getRelativePosition(void) const; 00353 void setRelativePosition(RelativePositionType relPos); 00354 00355 // Number of lines occupied by this comment (count the number of line feeds) 00356 int getNumberOfLines() const; 00357 int getColumnNumberOfEndOfString() const; // only correct for single line directives 00358 00359 // Used in unparse to string mechanism 00360 // char* removeLeadingWhiteSpace (const char* inputStringPointer); 00361 00362 // DQ (8/6/2006): Modified to make these static functions 00363 // useful for debugging 00364 static std::string directiveTypeName (const DirectiveType & directive); 00365 static std::string relativePositionName (const RelativePositionType & position); 00366 00367 // JH (01/03/2006) methods for packing the PreprocessingInfo data, in order to store it into 00368 // a file and rebuild it! 00369 unsigned int packed_size () const; 00370 00371 // JH (01/032006) This pack methods might cause memory leaks. Think of deleting them after stored to file ... 00372 char* packed() const; 00373 void unpacked( char* storePointer ); 00374 00375 // DQ (4/19/2006): Added Sg_File_Info objects to each PreprocessingInfo object 00376 Sg_File_Info* get_file_info() const; 00377 void set_file_info( Sg_File_Info* info ); 00378 00379 00380 // DQ (11/28/2008): Support for CPP generated linemarkers 00381 int get_lineNumberForCompilerGeneratedLinemarker(); 00382 std::string get_filenameForCompilerGeneratedLinemarker(); 00383 std::string get_optionalflagsForCompilerGeneratedLinemarker(); 00384 00385 // DQ (11/28/2008): Support for CPP generated linemarkers 00386 void set_lineNumberForCompilerGeneratedLinemarker( int x ); 00387 void set_filenameForCompilerGeneratedLinemarker( std::string x ); 00388 void set_optionalflagsForCompilerGeneratedLinemarker( std::string x ); 00389 00390 // #ifndef USE_ROSE 00391 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00392 // Wave specific member functions. 00393 public: 00394 // Access functions to get the macro call or macro definition. 00395 // These are NULL if the type is not CMacroCall or 00396 // CpreprocessorDefineDeclaration 00397 rose_macro_call* get_macro_call(); 00398 rose_macro_definition* get_macro_def(); 00399 rose_include_directive* get_include_directive(); 00400 00401 const token_container* get_token_stream(); 00402 void push_front_token_stream(token_type tok); 00403 void push_back_token_stream(token_type tok); 00404 00405 #endif 00406 }; 00407 00408 // DQ (10/15/2002) Changed list element from "PreprocessingInfo" to 00409 // "PreprocessingInfo*" to avoid redundant copying of internal data. 00410 // Define a new data type for the container that stores the 00411 // PreprocessingInfo objects attached to an AST node 00412 typedef Rose_STL_Container<PreprocessingInfo*> AttachedPreprocessingInfoType; 00413 00414 class ROSEAttributesList 00415 { 00416 private: 00417 // DQ replaced use of old list class with STL 00418 std::vector<PreprocessingInfo*> attributeList; 00419 00420 LexTokenStreamTypePointer rawTokenStream; 00421 00422 // [DT] 3/15/2000 -- Name of file from which the directives come. 00423 // char fileName[256]; 00424 std::string fileName; 00425 00426 // 3/16/2000 -- Index into the list. Not sure if this is really 00427 // necessary. See implementation in unparser.C. 00428 // 00429 // This is where the current line number is stored while we 00430 // go off and unparse a different include file. This really should have 00431 // been stored in a static structure (I think) rather than in this list. 00432 int index; 00433 00434 public: 00435 // DQ (11/19/2008): Added language selection support for handling comments 00436 enum languageTypeEnum 00437 { 00438 e_unknown_language = 0, 00439 e_C_language = 1, 00440 e_Cxx_language = 2, 00441 e_Fortran77_language = 3, 00442 e_Fortran9x_language = 4, 00443 e_lastLanguage 00444 }; 00445 00446 ROSEAttributesList(); 00447 ~ROSEAttributesList(); 00448 // DQ (4/19/2006): Adding SgFileInfo objects so we need to pass in a filename string 00449 // void addElement(PreprocessingInfo::DirectiveType, const char *pLine, int lineNumber, int columnNumber, int numberOfLines); 00450 void addElement(PreprocessingInfo::DirectiveType, const std::string & pLine, const std::string & filename, int lineNumber, int columnNumber, int numberOfLines); 00451 #if 1 00452 // DQ (5/9/2007): This is required for WAVE support. 00453 // DQ (4/13/2007): I would like to remove this function, but it is used by WAVE support within ROSE. 00454 void addElement( PreprocessingInfo &pRef ); 00455 #endif 00456 // void addElements( ROSEAttributesList &); 00457 void moveElements( ROSEAttributesList &); 00458 00459 #if 1 00460 // DQ (5/9/2007): This is required for WAVE support. 00461 // DQ (4/13/2007): I would like to remove this function 00462 void insertElement( PreprocessingInfo & pRef ); 00463 #endif 00464 00465 // [DT] 3/15/2000 -- Interface to fileName member. 00466 void setFileName(const std::string & fName); 00467 std::string getFileName(); 00468 00469 // 3/16/2000 -- Interface to index member. 00470 void setIndex(int i); 00471 int getIndex(); 00472 00473 PreprocessingInfo* operator[](int i); 00474 int size(void); 00475 int getLength(void); 00476 void deepClean(void); 00477 void clean(void); 00478 00479 // Access function for list 00480 std::vector<PreprocessingInfo*> & getList() { return attributeList; }; 00481 00482 void display ( const std::string & label ); // DQ 02/18/2001 -- For debugging. 00483 00484 // DQ (1/21/2008): Added access function to save the raw token stream from the lex pass. 00485 void set_rawTokenStream( LexTokenStreamTypePointer s ); 00486 LexTokenStreamTypePointer get_rawTokenStream(); 00487 00488 // This function processes the token stream to generate the input for what weaves the 00489 // CPP directives and comments into the AST. All other tokens are ignore in this pass. 00490 void generatePreprocessorDirectivesAndCommentsForAST( const std::string & filename ); 00491 00492 // DQ (11/26/2008): This is old code! 00493 // Collection comments and CPP directives for fixed format (easier case) 00494 // void collectFixedFormatPreprocessorDirectivesAndCommentsForAST( const std::string & filename ); 00495 00496 // DQ (11/16/2008): Adding support for recognition of CPP directives outside of the lex tokenization. 00497 void collectPreprocessorDirectivesAndCommentsForAST( const std::string & filename, languageTypeEnum languageType ); 00498 00499 // DQ (11/17/2008): Refactored the code. 00500 bool isFortran77Comment( const std::string & line ); 00501 bool isFortran90Comment( const std::string & line ); 00502 bool isCppDirective( const std::string & line, PreprocessingInfo::DirectiveType & cppDeclarationKind, std::string & restOfTheLine ); 00503 }; 00504 00505 // 00506 // [DT] 3/16/2000 -- Want to have preprocessing info for 00507 // each file included from the main source file. 00508 // 00509 class ROSEAttributesListContainer 00510 { 00511 private: 00512 // DQ replaced use of old list class with STL 00513 // std::vector<ROSEAttributesList*> attributeListList; 00514 // std::map<std::string,ROSEAttributesList*>* attrMap; 00515 std::map<std::string, ROSEAttributesList*> attributeListMap; 00516 00517 public: 00518 ROSEAttributesListContainer(); 00519 ~ROSEAttributesListContainer(); 00520 // void addList ( ROSEAttributesList* listPointer ); 00521 void addList ( std::string fileName, ROSEAttributesList* listPointer ); 00522 // void addList(ROSEAttributesList &aRef); 00523 // void insertList(ROSEAttributesList &aRef); 00524 // ROSEAttributesList* operator[](int i); 00525 // ROSEAttributesList* findList ( const std::string & fName ); 00526 00527 // Check to see if the ROSEAttributesList for the fName (filename) is in the container 00528 bool isInList ( const std::string & fName ); 00529 00530 // int size(void); 00531 // int getLength(void); 00532 void dumpContents(void); // [DT] 3/16/2000 -- For debugging. 00533 void deepClean(void); 00534 void clean(void); 00535 ROSEAttributesList & operator[]( const std::string & fName); 00536 00537 // Access function for list 00538 // std::vector<ROSEAttributesList*> & getList() { return attributeListList; }; 00539 std::map<std::string, ROSEAttributesList*> & getList() { return attributeListMap; }; 00540 void display ( const std::string & label ); // DQ 02/18/2001 -- For debugging. 00541 }; 00542 00543 00544 // #ifndef USE_ROSE 00545 #ifndef ROSE_SKIP_COMPILATION_OF_WAVE 00546 00547 extern token_container wave_tokenStream; 00548 00549 #endif 00550 00551 #endif
1.4.7