void getSgIfStmt(SgIfStmt* ifstat) { bool truthBool; //#ifdef PATH truthBool= pathNodeTruthValue[ifstat]; //#endif scopeStatNum++; std::stringstream ifstatindexstream; ifstatindexstream << scopeStatNum; std::string ifstatindex = ifstatindexstream.str(); SgStatement* conditional = ifstat->get_conditional(); ROSE_ASSERT(isSgStatement(conditional)); std::string conditionalString = getSgStatement(conditional); if (conditionalString == "") { std::cout << "empty conditional string!" << std::endl; ROSE_ASSERT(false); } SgStatement* ifBody; std::string ifBodyString; if (!truthBool) { ifBody = ifstat->get_false_body(); } else { ifBody = ifstat->get_true_body(); } if (ifBody == NULL) { ifBodyString = "; empty body\n"; } else { ROSE_ASSERT(isSgStatement(ifBody)); ifBodyString = getSgStatement(ifBody); } /*std::cout << "should be basic block..." << ifBody->class_name() << std::endl; ROSE_ASSERT(isSgBasicBlock(ifBody)); getSgBasicBlock(isSgBasicBlock(ifBody));*/ std::string fullIfStat; std::string assrt1, assrt2, assrt3; if (truthBool) { assrt3 = "(assert (= " + conditionalString + " true))\n"; } else { assrt3 = "(assert (= " + conditionalString + " false))\n"; } expressions.push_back(assrt3); return; }
// obtain read or write variables processed by all nested loops, if any void getVariablesProcessedByInnerLoops (SgScopeStatement* current_loop_body, bool isRead, std::set<SgInitializedName*>& var_set) { // AST query to find all loops // add all read/write variables into the var_set VariantVector vv; vv.push_back(V_SgForStatement); vv.push_back(V_SgFortranDo); Rose_STL_Container<SgNode*> nodeList = NodeQuery::querySubTree(current_loop_body, vv); for (Rose_STL_Container<SgNode *>::iterator i = nodeList.begin(); i != nodeList.end(); i++) { SgStatement* loop = isSgStatement(*i); if (debug) cout<< "Found nested loop at line:"<< loop->get_file_info()->get_line()<<endl; std::set<SgInitializedName*> src_var_set ; if (isRead) src_var_set = LoopLoadVariables[loop]; else src_var_set = LoopStoreVariables[loop]; std::set<SgInitializedName*>::iterator j; if (debug) cout<< "\t Insert processed variable:"<<endl; for (j= src_var_set.begin(); j!= src_var_set.end(); j++) { var_set.insert(*j); if (debug) cout<< "\t \t "<<(*j)->get_name()<<endl; } } }
void visitorTraversal::visit(SgNode* n) { // There are three types ir IR nodes that can be queried for scope: // - SgStatement, and // - SgInitializedName SgStatement* statement = isSgStatement(n); if (statement != NULL) { SgScopeStatement* scope = statement->get_scope(); ROSE_ASSERT(scope != NULL); printf ("SgStatement = %12p = %30s has scope = %12p = %s (total number = %d) \n", statement,statement->class_name().c_str(), scope,scope->class_name().c_str(),(int)scope->numberOfNodes()); } SgInitializedName* initializedName = isSgInitializedName(n); if (initializedName != NULL) { SgScopeStatement* scope = initializedName->get_scope(); ROSE_ASSERT(scope != NULL); printf ("SgInitializedName = %12p = %30s has scope = %12p = %s (total number = %d)\n", initializedName,initializedName->get_name().str(), scope,scope->class_name().c_str(),(int)scope->numberOfNodes()); } }
inline void printNode(ostream& o, const NodeT& n) { string id = n.id(); string nodeColor = "black"; if (isSgStatement(n.getNode())) nodeColor = "blue"; else if (isSgExpression(n.getNode())) nodeColor = "green"; else if (isSgInitializedName(n.getNode())) nodeColor = "red"; o << id << " [label=\"" << escapeString(Debug ? n.toStringForDebugging() : n.toString()) << "\", color=\"" << nodeColor << "\", style=\"" << (n.isInteresting() ? "solid" : "dotted") << "\"];\n"; }
void MyTraversal::visit ( SgNode* astNode ) { SgStatement * stmt=isSgStatement(astNode); if(stmt) { string unparse=stmt->unparseToString(); printf("found statement %s %s\n", stmt->sage_class_name(), unparse.c_str()); } }
SgStatement *findSafeInsertPoint(SgNode *node) { SgStatement *insertPoint = SageInterface::getEnclosingStatement(node); SgStatement *es = isSgExprStatement(insertPoint); SgStatement *esParent = es ? isSgStatement(es->get_parent()) : 0; if (es && (isSgSwitchStatement(esParent) || isSgIfStmt(esParent))) { // Make sure insertion point is outside of the condition of an if-stmt // or the selector of a switch-stmt. insertPoint = esParent; } else { if (esParent) { assert(isSgBasicBlock(esParent)); } } return insertPoint; }
foreach (SgFunctionCallExp *nfce, callExprs) { SgFunctionDeclaration *CFD = nfce->getAssociatedFunctionDeclaration(); std::string fname = CFD->get_name().getString(); size_t pos = 0; if (((pos = fname.find("RecvReturnPause_")) != std::string::npos) || ((pos = fname.find("WriteMemPause")) != std::string::npos && lastStmt != nfce->get_parent()) || ((pos = fname.find("SendReturn_")) != std::string::npos && lastStmt != nfce->get_parent()) && pos == 0) { SgStatement *brkStmt = SageBuilder::buildBreakStmt(); SgStatement *parent = isSgStatement(nfce->get_parent()); SageInterface::insertStatementAfter(parent, brkStmt); } }
void RemovalOfNodes::visit(SgNode* node){ // If the AST node doesn't have the attribute keep, then delete the node. if(!node->attribute.exists("keep")){ SgStatement *stmt = isSgStatement(node); if(stmt!=NULL){ //LowLevelRewrite::remove(stmt); MiddleLevelRewrite::remove(stmt); //Still removes #include-statments when removes global variables #ifdef DEBUG_REMOVAL writeMessage(node); #endif } } // free memory of the ast attribute... // else if(node->attribute.exists("keep")){ // node->attribute.remove("keep"); // } }
int main(int argc, char *argv[]){ SgProject* sgproject = frontend(argc, argv); // SgProject *sgproject_copy = static_cast<SgProject*>(sgproject->copy(SgTREE_COPY)); // This copy of the sgproject fails due to the copy function of the SgFile fails (aborts) SgFile &file = sgproject->get_file(0); // SgFile *file_copy = static_cast<SgFile*>(file.copy(SgTREE_COPY)); // Calling the copy function of SgFile fails: // Before aborting the execution, the following error message is displayed: // "This is the default constructor, use SgFile (argc,argv) instead" SgGlobal *root = file.get_root(); SgGlobal *root_copy = static_cast<SgGlobal*>(root->copy(SgTREE_COPY)); // Copying the SgGlobal object is OK // removing the return statement...from the copy! list<SgNode*> returnstmt_list = NodeQuery::querySubTree(root_copy, V_SgReturnStmt); SgStatement* stmt = isSgStatement(*returnstmt_list.begin()); LowLevelRewrite::remove(stmt); sgproject->unparse(); // should output unmodified sgproject and it does. The deep copy // mechanism works for the SgGlobal object. // moving the output file to a new file, so that we can unparse the sgproject again without // overwriting the results char *outputfile = file.get_unparse_output_filename(); string move = "mv " + string(outputfile) + " orig_" + string(outputfile); system(move.c_str()); // want to output modified sgproject file.set_root(root_copy); //sgproject->set_file(file); sgproject->unparse(); // or use: file.unparse();? // Unparsing the sgproject after adding the root_copy to the file-object (I want // to unparse the modified copy...), gives me an error message: // /home/hauge2/ROSE/src/backend/unparser/unparse_stmt.C:1047: void Unparser::unparseFuncDefnStmt(SgStatement*, SgUnparse_Info&): Assertion `funcdefn_stmt->get_declaration() != __null' failed. return 0; }
MySynthesizedAttribute MyTraversal::evaluateRewriteSynthesizedAttribute ( SgNode* astNode, MyInheritedAttribute inheritedAttribute, SubTreeSynthesizedAttributes synthesizedAttributeList ) { MySynthesizedAttribute returnAttribute; switch(astNode->variantT()) { case V_SgForStatement: { SgForStatement *forStat = isSgForStatement(astNode); cout << " found V_SgForStatement " << printPosition(astNode) << "" << endl; for(size_t i=0; i<mAllFors.size(); i++) { if((mAllFors[i]->blocked)&&(astNode == mAllFors[i]->forStmt)) { ostringstream newFor; newFor << "for("; newFor << (*(forStat->get_init_stmt().begin()))->unparseToString(); newFor << forStat->get_test_expr()->unparseToString() << ";" ; newFor << mAllFors[i]->varName << "+=" << mAllFors[i]->blockSize << ")\n" ; newFor << forStat->get_loop_body()->unparseToString(); cout << " is blocked loop..." << endl; returnAttribute.replace( astNode, newFor.str() ); } } } break; case V_SgVarRefExp: { cout << " found V_SgVarRefExp " << printPosition(astNode) << astNode->unparseToString() << endl; forBlockVector fors = inheritedAttribute.getForScopes(); // replace variable occurrences in the loop kernel if(inheritedAttribute.getLoopKernel()) { for(size_t i=0;i<fors.size(); i++) { if( ( strcmp( astNode->unparseToString().c_str(), fors[i]->varName.c_str() )==0 ) && ( isSgVarRefExp(astNode)->get_type() == fors[i]->varType ) ) { string blockedVarName("blocked_"); blockedVarName += fors[i]->varName; AstRestructure::unparserReplace( isSgVarRefExp(astNode), blockedVarName ); cout << " replacing with '"<<blockedVarName<<"' " << endl; } } } } break; default: break; } // node type bool synth = false; for( SubTreeSynthesizedAttributes::iterator i=synthesizedAttributeList.begin(); i!= synthesizedAttributeList.end(); i++ ) { if( (*i).getVarRefFound() ) synth = true; } if( synth ) { returnAttribute.setVarRefFound( true ); if(isSgStatement( astNode )) { cout << " new statement " << printPosition(astNode) << " : '" << astNode->unparseToString() << "' " << endl; returnAttribute.setVarRefFound( false ); //if(!isSgReturnStmt( astNode )) { // DEBUG, this should work!??!? returnAttribute.replace( astNode, astNode->unparseToString(), HighLevelCollectionTypedefs::LocalScope ); //} } } if(isSgScopeStatement(astNode)) { // dont replace variable in higher scopes... if(mReplaceVariable > 0) { mReplaceVariable--; cerr << "end of scope " << mReplaceVariable << endl; } } //if(astNode == mpLoopBody) { // FIXME why doesnt replace basic block work? if( (astNode->get_parent() == mpLoopBody)&&(inheritedAttribute.getLoopKernel()) ) { // we're back at the loop kernel block, now replace and insert new loops... insertTransformedLoopBody( astNode, returnAttribute, inheritedAttribute.getForScopes() ); } return returnAttribute; }
void FixupSelfReferentialMacrosInAST::visit ( SgNode* node ) { // DQ (3/11/2006): Set NULL pointers where we would like to have none. // printf ("In FixupSelfReferentialMacrosInAST::visit(): node = %s \n",node->class_name().c_str()); ROSE_ASSERT(node != NULL); switch (node->variantT()) { case V_SgInitializedName: { SgInitializedName* initializedName = isSgInitializedName(node); ROSE_ASSERT(initializedName != NULL); SgType* type = initializedName->get_type()->stripType(); SgClassType* classType = isSgClassType(type); if (classType != NULL) { SgClassDeclaration* targetClassDeclaration = isSgClassDeclaration(classType->get_declaration()); SgName className = targetClassDeclaration->get_name(); // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a class declaration name = %s \n",className.str()); // For sudo_exec_pty.c also look for siginfo if (className == "sigaction" || className == "siginfo") { // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a sigaction type \n"); // Note we could also check that the declaration came from a known header file. SgStatement* associatedStatement = isSgStatement(initializedName->get_parent()); if (associatedStatement != NULL) { // Add a macro to undefine the "#define sa_handler __sigaction_handler.sa_handler" macro. // printf ("In FixupSelfReferentialMacrosInAST::visit(): Add a macro to undefine the macro #define sa_handler __sigaction_handler.sa_handler \n"); // PreprocessingInfo* macro = new PreprocessingInfo(DirectiveType, const std::string & inputString,const std::string & filenameString, int line_no , int col_no,int nol, RelativePositionType relPos ); PreprocessingInfo::DirectiveType directiveType = PreprocessingInfo::CpreprocessorUndefDeclaration; // We are puting out all macros anytime we see either type. This might be too much... // From the sigaction.h file (included by signal.h): addMacro(associatedStatement,"#undef sa_handler\n",directiveType); addMacro(associatedStatement,"#undef sa_sigaction\n",directiveType); // From the siginfo.h file (included by signal.h): addMacro(associatedStatement,"#undef si_pid\n", directiveType); addMacro(associatedStatement,"#undef si_uid\n", directiveType); addMacro(associatedStatement,"#undef si_timerid\n",directiveType); addMacro(associatedStatement,"#undef si_overrun\n",directiveType); addMacro(associatedStatement,"#undef si_status\n", directiveType); addMacro(associatedStatement,"#undef si_utime\n", directiveType); addMacro(associatedStatement,"#undef si_stime\n", directiveType); addMacro(associatedStatement,"#undef si_value\n", directiveType); addMacro(associatedStatement,"#undef si_int\n", directiveType); addMacro(associatedStatement,"#undef si_ptr\n", directiveType); addMacro(associatedStatement,"#undef si_addr\n", directiveType); addMacro(associatedStatement,"#undef si_band\n", directiveType); addMacro(associatedStatement,"#undef si_fd\n", directiveType); } } } } default: { // printf ("Not handled in FixupSelfReferentialMacrosInAST::visit(%s) \n",node->class_name().c_str()); } } }
MySynthesizedAttribute MyTraversal::evaluateRewriteSynthesizedAttribute ( SgNode* astNode, MyInheritedAttribute inheritedAttribute, SubTreeSynthesizedAttributes synthesizedAttributeList ) { MySynthesizedAttribute returnAttribute; switch(astNode->variantT()) { case V_SgVarRefExp: { cout << " found V_SgVarRefExp " << astNode->unparseToString() << endl; if(mReplaceVariable) { if( ( strcmp( astNode->unparseToString().c_str(), VARIABLE_NAME )==0 ) && ( isSgTypeInt(isSgVarRefExp(astNode)->get_type()) ) ) { returnAttribute.setVarRefFound( true ); AstRestructure::unparserReplace( isSgVarRefExp(astNode), "newInt" ); cout << " replacing with 'newInt' " << endl; } } } break; case V_SgVariableDeclaration: { SgVariableDeclaration *varDecl = isSgVariableDeclaration(astNode); cout << " found V_SgVariableDeclaration " << astNode->unparseToString() << endl; // replace only integer variables called "i" if( (varDecl->get_traversalSuccessorContainer().size() > 0) && isSgInitializedName( varDecl->get_traversalSuccessorContainer()[0]) && ( strcmp(isSgInitializedName(varDecl->get_traversalSuccessorContainer()[0])->get_name().str(), VARIABLE_NAME )==0 ) && ( isSgTypeInt(isSgInitializedName(varDecl->get_traversalSuccessorContainer()[0])->get_type()) ) ) { // found declaration of "int i" string newDeclaration("int newInt = i + 100;"); returnAttribute.insert( varDecl, newDeclaration, HighLevelCollectionTypedefs::LocalScope, HighLevelCollectionTypedefs::AfterCurrentPosition ); assert( mReplaceVariable==0 ); // if it's true, there is another "int i", and this transformation wont work... mReplaceVariable = 1; cout << " inserted: '" << newDeclaration <<"' , starting variable replacement " << endl; } } break; default: break; } // node type bool synth = false; for( SubTreeSynthesizedAttributes::iterator i=synthesizedAttributeList.begin(); i!= synthesizedAttributeList.end(); i++ ) { if( (*i).getVarRefFound() ) synth = true; } if( synth ) { returnAttribute.setVarRefFound( true ); if(isSgStatement( astNode )) { cout << " new statement " << " : '" << astNode->unparseToString() << "' " << endl; returnAttribute.setVarRefFound( false ); //if(!isSgReturnStmt( astNode )) { // DEBUG, this should work!??!? returnAttribute.replace( astNode, astNode->unparseToString(), HighLevelCollectionTypedefs::LocalScope ); //} } } if(isSgScopeStatement(astNode)) { // dont replace variable in higher scopes... if(mReplaceVariable > 0) { mReplaceVariable--; cerr << "end of scope " << mReplaceVariable << endl; } } return returnAttribute; }
string globalUnparseToString ( SgNode* astNode, SgUnparse_Info* inputUnparseInfoPointer ) { // This global function permits any SgNode (including it's subtree) to be turned into a string // DQ (3/2/2006): Let's make sure we have a valid IR node! ROSE_ASSERT(astNode != NULL); string returnString; // all options are now defined to be false. When these options can be passed in // from the prompt, these options will be set accordingly. bool _auto = false; bool linefile = false; bool useOverloadedOperators = false; bool num = false; // It is an error to have this always turned off (e.g. pointer = this; will not unparse correctly) bool _this = true; bool caststring = false; bool _debug = false; bool _class = false; bool _forced_transformation_format = false; bool _unparse_includes = false; // printf ("In globalUnparseToString(): astNode->sage_class_name() = %s \n",astNode->sage_class_name()); Unparser_Opt roseOptions( _auto, linefile, useOverloadedOperators, num, _this, caststring, _debug, _class, _forced_transformation_format, _unparse_includes ); int lineNumber = 0; // Zero indicates that ALL lines should be unparsed // Initialize the Unparser using a special string stream inplace of the usual file stream ostringstream outputString; SgLocatedNode* locatedNode = isSgLocatedNode(astNode); string fileNameOfStatementsToUnparse; if (locatedNode == NULL) { // printf ("WARNING: applying AST -> string for non expression/statement AST objects \n"); fileNameOfStatementsToUnparse = "defaultFileNameInGlobalUnparseToString"; } else { ROSE_ASSERT (locatedNode != NULL); // DQ (5/31/2005): Get the filename from a traversal back through the parents to the SgFile // fileNameOfStatementsToUnparse = locatedNode->getFileName(); // fileNameOfStatementsToUnparse = rose::getFileNameByTraversalBackToFileNode(locatedNode); if (locatedNode->get_parent() == NULL) { // DQ (7/29/2005): // Allow this function to be called with disconnected AST fragments not connected to // a previously generated AST. This happens in Qing's interface where AST fragements // are built and meant to be unparsed. Only the parent of the root of the AST // fragement is expected to be NULL. fileNameOfStatementsToUnparse = locatedNode->getFileName(); } else { fileNameOfStatementsToUnparse = rose::getFileNameByTraversalBackToFileNode(locatedNode); } } ROSE_ASSERT (fileNameOfStatementsToUnparse.size() > 0); Unparser roseUnparser ( &outputString, fileNameOfStatementsToUnparse, roseOptions, lineNumber ); // Information that is passed down through the tree (inherited attribute) // Use the input SgUnparse_Info object if it is available. SgUnparse_Info* inheritedAttributeInfoPointer = NULL; if (inputUnparseInfoPointer != NULL) { // printf ("Using the input inputUnparseInfoPointer object \n"); // Use the user provided SgUnparse_Info object inheritedAttributeInfoPointer = inputUnparseInfoPointer; } else { // DEFINE DEFAULT BEHAVIOUR FOR THE CASE WHEN NO inputUnparseInfoPointer (== NULL) IS // PASSED AS ARGUMENT TO THE FUNCTION // printf ("Building a new Unparse_Info object \n"); // If no input parameter has been specified then allocate one // inheritedAttributeInfoPointer = new SgUnparse_Info (NO_UNPARSE_INFO); inheritedAttributeInfoPointer = new SgUnparse_Info(); ROSE_ASSERT (inheritedAttributeInfoPointer != NULL); // MS: 09/30/2003: comments de-activated in unparsing ROSE_ASSERT (inheritedAttributeInfoPointer->SkipComments() == false); // Skip all comments in unparsing inheritedAttributeInfoPointer->set_SkipComments(); ROSE_ASSERT (inheritedAttributeInfoPointer->SkipComments() == true); // Skip all whitespace in unparsing (removed in generated string) inheritedAttributeInfoPointer->set_SkipWhitespaces(); ROSE_ASSERT (inheritedAttributeInfoPointer->SkipWhitespaces() == true); // Skip all directives (macros are already substituted by the front-end, so this has no effect on those) inheritedAttributeInfoPointer->set_SkipCPPDirectives(); ROSE_ASSERT (inheritedAttributeInfoPointer->SkipCPPDirectives() == true); } ROSE_ASSERT (inheritedAttributeInfoPointer != NULL); SgUnparse_Info & inheritedAttributeInfo = *inheritedAttributeInfoPointer; // Turn ON the error checking which triggers an error if the default SgUnparse_Info constructor is called // SgUnparse_Info::forceDefaultConstructorToTriggerError = true; #if 1 // DQ (10/19/2004): Cleaned up this code, remove this dead code after we are sure that this worked properly // Actually, this code is required to be this way, since after this branch the current function returns and // some data must be cleaned up differently! So put this back and leave it this way, and remove the // "Implementation Note". // Both SgProject and SgFile are handled via recursive calls if ( (isSgProject(astNode) != NULL) || (isSgFile(astNode) != NULL) ) { // printf ("Implementation Note: Put these cases (unparsing the SgProject and SgFile into the cases for nodes derived from SgSupport below! \n"); // Handle recursive call for SgProject if (isSgProject(astNode) != NULL) { SgProject* project = isSgProject(astNode); ROSE_ASSERT(project != NULL); for (int i = 0; i < project->numberOfFiles(); i++) { SgFile* file = &(project->get_file(i)); ROSE_ASSERT(file != NULL); string unparsedFileString = globalUnparseToString(file,inputUnparseInfoPointer); string prefixString = string("/* TOP:") + string(rose::getFileName(file)) + string(" */ \n"); string suffixString = string("\n/* BOTTOM:") + string(rose::getFileName(file)) + string(" */ \n\n"); returnString += prefixString + unparsedFileString + suffixString; } } // Handle recursive call for SgFile if (isSgFile(astNode) != NULL) { SgFile* file = isSgFile(astNode); ROSE_ASSERT(file != NULL); SgGlobal* globalScope = file->get_root(); ROSE_ASSERT(globalScope != NULL); returnString = globalUnparseToString(globalScope,inputUnparseInfoPointer); } } else #endif { // DQ (1/12/2003): Only now try to trap use of SgUnparse_Info default constructor // Turn ON the error checking which triggers an error if the default SgUnparse_Info constructor is called SgUnparse_Info::set_forceDefaultConstructorToTriggerError(true); if (isSgStatement(astNode) != NULL) { SgStatement* stmt = isSgStatement(astNode); roseUnparser.unparseStatement ( stmt, inheritedAttributeInfo ); } if (isSgExpression(astNode) != NULL) { SgExpression* expr = isSgExpression(astNode); roseUnparser.unparseExpression ( expr, inheritedAttributeInfo ); } if (isSgType(astNode) != NULL) { SgType* type = isSgType(astNode); roseUnparser.unparseType ( type, inheritedAttributeInfo ); } if (isSgSymbol(astNode) != NULL) { SgSymbol* symbol = isSgSymbol(astNode); roseUnparser.unparseSymbol ( symbol, inheritedAttributeInfo ); } if (isSgSupport(astNode) != NULL) { // Handle different specific cases derived from SgSupport // (e.g. template parameters and template arguments). switch (astNode->variantT()) { #if 0 case V_SgProject: { SgProject* project = isSgProject(astNode); ROSE_ASSERT(project != NULL); for (int i = 0; i < project->numberOfFiles(); i++) { SgFile* file = &(project->get_file(i)); ROSE_ASSERT(file != NULL); string unparsedFileString = globalUnparseToString(file,inputUnparseInfoPointer); string prefixString = string("/* TOP:") + string(rose::getFileName(file)) + string(" */ \n"); string suffixString = string("\n/* BOTTOM:") + string(rose::getFileName(file)) + string(" */ \n\n"); returnString += prefixString + unparsedFileString + suffixString; } break; } case V_SgFile: { SgFile* file = isSgFile(astNode); ROSE_ASSERT(file != NULL); SgGlobal* globalScope = file->get_root(); ROSE_ASSERT(globalScope != NULL); returnString = globalUnparseToString(globalScope,inputUnparseInfoPointer); break; } #endif case V_SgTemplateParameter: { SgTemplateParameter* templateParameter = isSgTemplateParameter(astNode); roseUnparser.unparseTemplateParameter(templateParameter,inheritedAttributeInfo); break; } case V_SgTemplateArgument: { SgTemplateArgument* templateArgument = isSgTemplateArgument(astNode); roseUnparser.unparseTemplateArgument(templateArgument,inheritedAttributeInfo); break; } case V_SgInitializedName: { // QY: not sure how to implement this // DQ (7/23/2004): This should unparse as a declaration // (type and name with initializer). break; } case V_Sg_File_Info: { // DQ (5/11/2006): Not sure how or if we shoul implement this break; } // Perhaps the support for SgFile and SgProject shoud be moved to this location? default: printf ("Error: default reached in node derived from SgSupport astNode = %s \n",astNode->sage_class_name()); ROSE_ABORT(); } } // Turn OFF the error checking which triggers an if the default SgUnparse_Info constructor is called SgUnparse_Info::set_forceDefaultConstructorToTriggerError(false); // MS: following is the rewritten code of the above outcommented // code to support ostringstream instead of ostrstream. returnString = outputString.str(); // Call function to tighten up the code to make it more dense if (inheritedAttributeInfo.SkipWhitespaces() == true) { returnString = roseUnparser.removeUnwantedWhiteSpace ( returnString ); } // delete the allocated SgUnparse_Info object if (inputUnparseInfoPointer == NULL) delete inheritedAttributeInfoPointer; } return returnString; }
InheritedAttribute visitorTraversal::evaluateInheritedAttribute(SgNode* n, InheritedAttribute inheritedAttribute) { Sg_File_Info* s = n->get_startOfConstruct(); Sg_File_Info* e = n->get_endOfConstruct(); Sg_File_Info* f = n->get_file_info(); for(int x=0; x < inheritedAttribute.depth; ++x) { printf(" "); } if(s != NULL && e != NULL && !isSgLabelStatement(n)) { printf ("%s (%d, %d, %d)->(%d, %d): %s",n->sage_class_name(),s->get_file_id()+1,s->get_raw_line(),s->get_raw_col(),e->get_raw_line(),e->get_raw_col(), verbose ? n->unparseToString().c_str() : "" ); if(isSgAsmDwarfConstruct(n)) { printf(" [DWARF construct name: %s]", isSgAsmDwarfConstruct(n)->get_name().c_str()); } SgExprStatement * exprStmt = isSgExprStatement(n); if(exprStmt != NULL) { printf(" [expr type: %s]", exprStmt->get_expression()->sage_class_name()); SgFunctionCallExp * fcall = isSgFunctionCallExp(exprStmt->get_expression()); if(fcall != NULL) { SgExpression * funcExpr = fcall->get_function(); if(funcExpr != NULL) { printf(" [function expr: %s]", funcExpr->class_name().c_str()); } SgFunctionDeclaration * fdecl = fcall->getAssociatedFunctionDeclaration(); if(fdecl != NULL) { printf(" [called function: %s]", fdecl->get_name().str()); } } } if(isSgFunctionDeclaration(n)) { printf(" [declares function: %s]", isSgFunctionDeclaration(n)->get_name().str()); } SgStatement * sgStmt = isSgStatement(n); if(sgStmt != NULL) { printf(" [scope: %s, %p]", sgStmt->get_scope()->sage_class_name(), sgStmt->get_scope()); } //SgLabelStatement * lblStmt = isSgLabelStatement(n); //if(lblStmt != NULL) { // SgStatement * lblStmt2 = lblStmt->get_statement(); //} } else if (f != NULL) { SgInitializedName * iname = isSgInitializedName(n); if(iname != NULL) { SgType* inameType = iname->get_type(); printf("%s (%d, %d, %d): %s [type: %s", n->sage_class_name(),f->get_file_id()+1,f->get_raw_line(),f->get_raw_col(),n->unparseToString().c_str(),inameType->class_name().c_str()); SgDeclarationStatement * ds = isSgDeclarationStatement(iname->get_parent()); if(ds != NULL) { if(ds->get_declarationModifier().get_storageModifier().isStatic()) { printf(" static"); } } SgArrayType * art = isSgArrayType(iname->get_type()); if(art != NULL) { printf(" %d", art->get_rank()); } printf("]"); if(isSgAsmDwarfConstruct(n)) { printf(" [DWARF construct name: %s]", isSgAsmDwarfConstruct(n)->get_name().c_str()); } } else { printf("%s (%d, %d, %d): %s", n->sage_class_name(),f->get_file_id()+1,f->get_raw_line(),f->get_raw_col(), verbose ? n->unparseToString().c_str() : ""); } } else { printf("%s : %s", n->sage_class_name(), verbose ? n->unparseToString().c_str() : ""); if(isSgAsmDwarfConstruct(n)) { printf(" [DWARF construct name: %s]", isSgAsmDwarfConstruct(n)->get_name().c_str()); } } printf(" succ# %lu", n->get_numberOfTraversalSuccessors()); printf("\n"); return InheritedAttribute(inheritedAttribute.depth+1); }
void POETAstInterface::unparse(POETCode_ext* n, std::ostream& out, int align) { static SgUnparse_Info info; static Unparser* roseUnparser = 0; static POETCode* linebreak=ASTFactory::inst()->new_string("\n"); static POETCode* comma=ASTFactory::inst()->new_string(","); static bool template_only=false; static POETCode* left_over = 0; SgNode * input = (SgNode*)n->get_content(); POETCode* res = POETAstInterface::find_Ast2POET(input); if (res == n) { if (template_only && input->variantT() == V_SgFunctionDeclaration) { left_over = LIST(n,left_over); } else { std::string res = input->unparseToCompleteString(); out << res; } } else { if (roseUnparser == 0) { /* QY/2013: copied from the global unparseFile to use a different ostream and delegate*/ bool UseAutoKeyword = false; bool generateLineDirectives = true; bool useOverloadedOperators = false; bool num = false; bool _this = true; bool caststring = false; bool _debug = false; bool _class = false; bool _forced_transformation_format = false; bool _unparse_includes = false; Unparser_Opt roseOptions( UseAutoKeyword, generateLineDirectives, useOverloadedOperators, num, _this, caststring, _debug, _class, _forced_transformation_format, _unparse_includes ); roseUnparser = new Unparser(&out, "", roseOptions); } switch (input->variantT()) { case V_SgSourceFile: { SgSourceFile* f = isSgSourceFile(input); info.set_current_scope(f->get_globalScope()); template_only = true; code_gen(out, n->get_children(), 0, 0, align); template_only = false; if (left_over != 0) { code_gen(out, left_over, 0, 0, align); left_over = 0; } break; } case V_SgFunctionDeclaration: if (template_only) { left_over = LIST(n, left_over); break; } case V_SgTemplateInstantiationFunctionDecl: { SgFunctionDeclaration* d = isSgFunctionDeclaration(input); roseUnparser->u_exprStmt->unparseAttachedPreprocessingInfo(d,info,PreprocessingInfo::before); POETCode_ext_delegate repl(n, out); roseUnparser->repl = &repl; roseUnparser->u_exprStmt->unparseFuncDeclStmt(d, info); break; } case V_SgFunctionDefinition: { SgStatement* d = isSgStatement(input); POETCode_ext_delegate repl(n, out); roseUnparser->repl = &repl; roseUnparser->u_exprStmt->unparseStatement(d, info); assert(n->get_children() != n); out << "{"; code_gen(out, linebreak, 0, 0, align + 2); code_gen(out, n->get_children(), 0, linebreak, align+2); code_gen(out, linebreak, 0, 0, align); out << "}"; break; } case V_SgPragmaDeclaration: { out << "#pragma "; POETTuple* c = dynamic_cast<POETTuple*>(n->get_children()); assert(c != 0); code_gen(out, c->get_entry(0)); roseUnparser->cur << " "; roseUnparser->cur.insert_newline(1,align); code_gen(out, c->get_entry(1), 0, 0, align); break; } case V_SgForStatement: { out << "for (" ; POETTuple* c = dynamic_cast<POETTuple*>(n->get_children()); assert(c != 0); code_gen(out, c->get_entry(0)); code_gen(out, c->get_entry(1)); out << ";"; code_gen(out, c->get_entry(2)); out << ")"; break; } case V_SgExprStatement: code_gen(out, n->get_children(), 0, 0, align); out << ";"; break; case V_SgTemplateInstantiationMemberFunctionDecl: break; default: std::cerr << "Unsupported unparsing for : " << input->class_name() << input->unparseToString() << "\n"; //assert(0); } } }
/** Visits AST nodes in post-order. This is function-evaluation order. */ bool FunctionEvaluationOrderTraversal::evaluateSynthesizedAttribute(SgNode* astNode, FunctionCallInheritedAttribute parentAttribute, SynthesizedAttributesList) { SgFunctionCallExp* functionCall = isSgFunctionCallExp(astNode); if (functionCall == NULL) return false; //dummy return value FunctionCallInfo functionCallInfo(functionCall); // Can't lift function call arguments from the following: // 1. For loop test and increment // 2. While loop test // 3. Do-While loop test // 4. Either arms of ternary op // 5. RHS of any short circuit expression // An alternative is to use comma operators and use assignemnt op as done by the original author. // for(;foo(bar());) ==> T i; for(;i=bar();foo(i);) // But using assignement op is not always safe and it requires us to always have a default constructor // There is also an issue when the return type is a reference and we'll have to use & op to get a pointer // but if & op is overloaded we may not get the pointer. // Taking all these in view, I am simpling not lifting such expressions. if (parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_FOR_TEST || parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_FOR_INCREMENT || parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_WHILE_CONDITION || parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_DO_WHILE_CONDITION) { // ***** FOR UNSAFE TRANSFORMATION ******* //Temporary variables should be declared before the stmt ROSE_ASSERT(isSgStatement(parentAttribute.currentScope)); functionCallInfo.tempVarDeclarationLocation = isSgStatement(parentAttribute.currentScope); functionCallInfo.tempVarDeclarationInsertionMode = FunctionCallInfo::INSERT_BEFORE; nonNormalizableFunctionCalls.push_back(functionCallInfo); return false; } // In future, if the function call is assured to be side effect free, then we can lift it from short circuit and conditional expressions if(parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_CONDITIONAL_EXP_TRUE_ARM || parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_CONDITIONAL_EXP_FALSE_ARM || parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_SHORT_CIRCUIT_EXP_RHS){ if(!IsFunctionCallSideEffectFree(functionCall)) { // ***** FOR UNSAFE TRANSFORMATION ******* //Temporary variables should be declared before the stmt ROSE_ASSERT(parentAttribute.lastStatement); functionCallInfo.tempVarDeclarationLocation = parentAttribute.lastStatement; functionCallInfo.tempVarDeclarationInsertionMode = FunctionCallInfo::INSERT_BEFORE; nonNormalizableFunctionCalls.push_back(functionCallInfo); return false; } } //Handle for loops (being inside the body of a for loop doesn't need special handling) if (parentAttribute.scopeStatus == FunctionCallInheritedAttribute::INSIDE_FOR_INIT) { SgForStatement* forLoop = isSgForStatement(parentAttribute.currentScope); ROSE_ASSERT(forLoop != NULL); //Temporary variables should be declared before the loop functionCallInfo.tempVarDeclarationLocation = forLoop; functionCallInfo.tempVarDeclarationInsertionMode = FunctionCallInfo::INSERT_BEFORE; } else if (parentAttribute.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE) { //Assume we're in a basic block. Then just insert right before the current statement ROSE_ASSERT(parentAttribute.scopeStatus = FunctionCallInheritedAttribute::IN_SAFE_PLACE); functionCallInfo.tempVarDeclarationLocation = parentAttribute.lastStatement; functionCallInfo.tempVarDeclarationInsertionMode = FunctionCallInfo::INSERT_BEFORE; } else { //Unhandled condition?! ROSE_ASSERT(false); } normalizableFunctionCalls.push_back(functionCallInfo); return false; //dummy return value }
/** Visits AST nodes in pre-order */ FunctionCallInheritedAttribute FunctionEvaluationOrderTraversal::evaluateInheritedAttribute(SgNode* astNode, FunctionCallInheritedAttribute parentAttribute) { FunctionCallInheritedAttribute result = parentAttribute; SgForStatement* parentForLoop = isSgForStatement(parentAttribute.currentScope); SgWhileStmt* parentWhileLoop = isSgWhileStmt(parentAttribute.currentScope); SgDoWhileStmt* parentDoWhileLoop = isSgDoWhileStmt(parentAttribute.currentScope); SgConditionalExp* parentSgConditionalExp = astNode->get_parent() ? isSgConditionalExp(astNode->get_parent()) : NULL; SgAndOp* parentAndOp = astNode->get_parent() ?isSgAndOp(astNode->get_parent()) : NULL; SgOrOp* parentOrOp = astNode->get_parent() ? isSgOrOp(astNode->get_parent()) : NULL; if (isSgForStatement(astNode)) result.currentScope = isSgForStatement(astNode); else if (isSgWhileStmt(astNode)) result.currentScope = isSgWhileStmt(astNode); else if (isSgDoWhileStmt(astNode)) result.currentScope = isSgDoWhileStmt(astNode); //else if (isSgConditionalExp(astNode)) // result.currentScope = isSgConditionalExp(astNode); //else if (isSgAndOp(astNode)) // result.currentScope = isSgAndOp(astNode); //else if (isSgOrOp(astNode)) // result.currentScope = isSgOrOp(astNode); else if (isSgForInitStatement(astNode)) { ROSE_ASSERT(result.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE); result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_FOR_INIT; ROSE_ASSERT(isSgForStatement(result.currentScope)); } else if (parentForLoop != NULL && parentForLoop->get_test() == astNode) { ROSE_ASSERT(result.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE); result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_FOR_TEST; } else if (parentForLoop != NULL && parentForLoop->get_increment() == astNode) { ROSE_ASSERT(result.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE); result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_FOR_INCREMENT; } else if (parentWhileLoop != NULL && parentWhileLoop->get_condition() == astNode) { ROSE_ASSERT(result.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE); result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_WHILE_CONDITION; } else if (parentDoWhileLoop != NULL && parentDoWhileLoop->get_condition() == astNode) { ROSE_ASSERT(result.scopeStatus == FunctionCallInheritedAttribute::IN_SAFE_PLACE); result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_DO_WHILE_CONDITION; } else if( parentSgConditionalExp != NULL && parentSgConditionalExp->get_true_exp() == astNode) { // if the scope status was safe, turn it into unsafe if (IsStatusSafe(result.scopeStatus)) result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_CONDITIONAL_EXP_TRUE_ARM; } else if(parentSgConditionalExp != NULL && parentSgConditionalExp->get_false_exp() == astNode) { // if the scope status was safe, turn it into unsafe if (IsStatusSafe(result.scopeStatus)) result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_CONDITIONAL_EXP_FALSE_ARM; } else if( parentOrOp != NULL && parentOrOp->get_rhs_operand () == astNode) { // if the scope status was safe, turn it into unsafe if (IsStatusSafe(result.scopeStatus)) result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_SHORT_CIRCUIT_EXP_RHS; } else if( parentAndOp != NULL && parentAndOp->get_rhs_operand () == astNode) { // if the scope status was safe, turn it into unsafe if (IsStatusSafe(result.scopeStatus)) result.scopeStatus = FunctionCallInheritedAttribute::INSIDE_SHORT_CIRCUIT_EXP_RHS; } //We can't insert variables before an expression statement that appears inside if(), switch, throw, etc. if (isSgExprStatement(astNode) && !isSgBasicBlock(astNode->get_parent())) { //We can't insert a variable declaration at these locations. Use the parent statement } else if (isSgStatement(astNode)) { result.lastStatement = isSgStatement(astNode); } return result; }
void FixupSelfReferentialMacrosInAST::visit ( SgNode* node ) { // DQ (3/11/2006): Set NULL pointers where we would like to have none. // printf ("In FixupSelfReferentialMacrosInAST::visit(): node = %s \n",node->class_name().c_str()); ROSE_ASSERT(node != NULL); switch (node->variantT()) { case V_SgInitializedName: { SgInitializedName* initializedName = isSgInitializedName(node); ROSE_ASSERT(initializedName != NULL); SgType* type = initializedName->get_type()->stripType(); SgClassType* classType = isSgClassType(type); if (classType != NULL) { SgClassDeclaration* targetClassDeclaration = isSgClassDeclaration(classType->get_declaration()); SgName className = targetClassDeclaration->get_name(); // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a class declaration name = %s \n",className.str()); // For sudo_exec_pty.c also look for siginfo if (className == "sigaction" || className == "siginfo") { // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a sigaction type \n"); // Note we could also check that the declaration came from a known header file. SgStatement* associatedStatement = isSgStatement(initializedName->get_parent()); if (associatedStatement != NULL) { // Add a macro to undefine the "#define sa_handler __sigaction_handler.sa_handler" macro. // printf ("In FixupSelfReferentialMacrosInAST::visit(): Add a macro to undefine the macro #define sa_handler __sigaction_handler.sa_handler \n"); // PreprocessingInfo* macro = new PreprocessingInfo(DirectiveType, const std::string & inputString,const std::string & filenameString, int line_no , int col_no,int nol, RelativePositionType relPos ); PreprocessingInfo::DirectiveType directiveType = PreprocessingInfo::CpreprocessorUndefDeclaration; // We are puting out all macros anytime we see either type. This might be too much... // From the sigaction.h file (included by signal.h): addMacro(associatedStatement,"#undef sa_handler\n",directiveType); addMacro(associatedStatement,"#undef sa_sigaction\n",directiveType); // From the siginfo.h file (included by signal.h): addMacro(associatedStatement,"#undef si_pid\n", directiveType); addMacro(associatedStatement,"#undef si_uid\n", directiveType); addMacro(associatedStatement,"#undef si_timerid\n",directiveType); addMacro(associatedStatement,"#undef si_overrun\n",directiveType); addMacro(associatedStatement,"#undef si_status\n", directiveType); addMacro(associatedStatement,"#undef si_utime\n", directiveType); addMacro(associatedStatement,"#undef si_stime\n", directiveType); addMacro(associatedStatement,"#undef si_value\n", directiveType); addMacro(associatedStatement,"#undef si_int\n", directiveType); addMacro(associatedStatement,"#undef si_ptr\n", directiveType); addMacro(associatedStatement,"#undef si_addr\n", directiveType); addMacro(associatedStatement,"#undef si_band\n", directiveType); addMacro(associatedStatement,"#undef si_fd\n", directiveType); } } } } default: { // printf ("Not handled in FixupSelfReferentialMacrosInAST::visit(%s) \n",node->class_name().c_str()); } } #if 0 // DQ (12/30/2013): Comments and CPP directives have not yet been attached to the AST, so we can't process them here. // SgLocatedNode* locatedNode = isSgLocatedNode(node); // if (locatedNode != NULL) SgStatement* stmt = isSgStatement(node); if (stmt != NULL) { // Find all #define statements and look for self referencing macros int numberOfComments = -1; if (stmt->getAttachedPreprocessingInfo() != NULL) numberOfComments = stmt->getAttachedPreprocessingInfo()->size(); std::string s = std::string(" --- startOfConstruct: file = " ) + stmt->get_startOfConstruct()->get_filenameString() + " raw filename = " + stmt->get_startOfConstruct()->get_raw_filename() + " raw line = " + StringUtility::numberToString(stmt->get_startOfConstruct()->get_raw_line()) + " raw column = " + StringUtility::numberToString(stmt->get_startOfConstruct()->get_raw_col()) + " #comments = " + StringUtility::numberToString(numberOfComments) + " \n "; AttachedPreprocessingInfoType* comments = stmt->getAttachedPreprocessingInfo(); if (comments != NULL) { printf ("Found attached comments (at %p of type: %s): \n",stmt,stmt->class_name().c_str()); AttachedPreprocessingInfoType::iterator i; for (i = comments->begin(); i != comments->end(); i++) { ROSE_ASSERT ( (*i) != NULL ); printf (" Attached Comment (relativePosition=%s): %s\n", ((*i)->getRelativePosition() == PreprocessingInfo::before) ? "before" : "after", (*i)->getString().c_str()); printf ("Comment/Directive getNumberOfLines = %d getColumnNumberOfEndOfString = %d \n",(*i)->getNumberOfLines(),(*i)->getColumnNumberOfEndOfString()); (*i)->get_file_info()->display("comment/directive location"); } } else { printf ("No attached comments (at %p of type: %s): \n",stmt,stmt->class_name().c_str()); } } #endif }
// Count the load and store bytes for the // I think we can only return expressions to calculate the value, not the actual values, // since sizeof(type) is machine dependent // Consider both scalar and array accesses by default. Consider both floating point and integer types by default. // return a pair of expressions: // load_byte_exp, and // store_byte_exp // Algorithm: // 1. Call side effect analysis to find read/write variables, some reference may trigger both read and write accesses // Accesses to the same array/scalar variable are grouped into one read (or write) access // e.g. array[i][j], array[i][j+1], array[i][j-1], etc are counted a single access // 2. Group accesses based on the types (same type? increment the same counter to shorten expression length) // 4. Iterate on the results to generate expression like 2*sizeof(float) + 5* sizeof(double) // As an approximate, we use simple analysis here assuming no function calls. std::pair <SgExpression*, SgExpression*> CountLoadStoreBytes (SgLocatedNode* input, bool includeScalars /* = true */, bool includeIntType /* = true */) { std::pair <SgExpression*, SgExpression*> result; assert (input != NULL); // the input is essentially the loop body, a scope statement SgScopeStatement* scope = isSgScopeStatement(input); // We need to record the associated loop info. //SgStatement* loop= NULL; SgForStatement* forloop = isSgForStatement(scope->get_scope()); SgFortranDo* doloop = isSgFortranDo(scope->get_scope()); if (forloop) { //loop = forloop; } else if (doloop) { //loop = doloop; } else { cerr<<"Error in CountLoadStoreBytes (): input is not loop body type:"<< input->class_name()<<endl; assert(false); } //Plan A: use and extend Qing's side effect analysis std::set<SgInitializedName*> readVars; std::set<SgInitializedName*> writeVars; bool success = SageInterface::collectReadWriteVariables (isSgStatement(input), readVars, writeVars); if (success!= true) { cout<<"Warning: CountLoadStoreBytes(): failed to collect load/store, mostly due to existence of function calls inside of loop body @ "<<input->get_file_info()->get_line()<<endl; } std::set<SgInitializedName*>::iterator it; if (debug) cout<<"debug: found read variables (SgInitializedName) count = "<<readVars.size()<<endl; for (it=readVars.begin(); it!=readVars.end(); it++) { SgInitializedName* iname = (*it); if (debug) cout<<scalar_or_array (iname->get_type()) <<" "<<iname->get_name()<<"@"<<iname->get_file_info()->get_line()<<endl; } if (!includeScalars ) readVars = filterVariables (readVars); if (debug) cout<<"debug: found write variables (SgInitializedName) count = "<<writeVars.size()<<endl; for (it=writeVars.begin(); it!=writeVars.end(); it++) { SgInitializedName* iname = (*it); if (debug) cout<<scalar_or_array(iname->get_type()) <<" "<<iname->get_name()<<"@"<<iname->get_file_info()->get_line()<<endl; } if (!includeScalars ) writeVars = filterVariables (writeVars); result.first = calculateBytes (readVars, scope, true); result.second = calculateBytes (writeVars, scope, false); return result; }
ClastToSage::ClastToSage(SgScopeStatement* scopScope, clast_stmt* root, scoplib_scop_p scoplibScop, PolyRoseOptions& options) { //SgScopeStatement* scope = isSgScopeStatement((SgNode*) scoplibScop->usr); _polyoptions = options; SgScopeStatement* scope = scopScope; ROSE_ASSERT(scope); m_scopRoot = NULL; /// OLD: m_scope = scope; m_scoplib_scop = scoplibScop; m_verbose = _polyoptions.isVerbose(); // 0- Retrive meta information stored as an annotation of the // SageAST root. SgStatement* scopRoot = isSgStatement((SgNode*)(scoplibScop->usr)); ScopRootAnnotation* annot = (ScopRootAnnotation*)(scopRoot->getAttribute("ScopRoot")); ROSE_ASSERT(annot); _fakeSymbolMap = annot->fakeSymbolMap; // 1- Collect all iterators in the clast. They are of the from 'cXX' // where XX is an integer. _scoplibIterators = collectAllIterators(root); // 2- Map clast iterator to new variables that does not conflict // with existing names, and register the symbols in the symbol // table. _sageIterators = createNewIterators(_scoplibIterators, scope); // 3- Create the basic block containing the transformed scop. SgBasicBlock* bb = buildBasicBlock(root); // 4- Update the variable scope with the new bb, and insert the // declaration statement in the AST. std::map<const char*, SgVariableDeclaration*>::iterator iter; Rose_STL_Container<SgNode*> varRefs = NodeQuery::querySubTree(bb,V_SgVarRefExp); for(iter = _sageIterators.begin(); iter != _sageIterators.end(); ++iter) { // Deal with the symbol tables. SgInitializedNamePtrList& l = iter->second->get_variables(); for (SgInitializedNamePtrList::iterator i = l.begin(); i != l.end(); i++) { (*i)->set_scope(bb); SgVariableSymbol* sym = new SgVariableSymbol(*i); bb->insert_symbol((*i)->get_name(), sym); // Ugly hack: replace the old symbol with the new entry in // the symbol table. for (Rose_STL_Container<SgNode *>::iterator j = varRefs.begin(); j != varRefs.end(); j++) { SgVarRefExp *vRef = isSgVarRefExp((*j)); if (vRef->get_symbol()->get_name() == (*i)->get_name()) vRef->set_symbol(sym); } } // Insert the declaration statement in the BB. bb->prepend_statement(iter->second); } // Post-process for pragma insertion. if (options.getGeneratePragmas()) insertPragmas(bb); m_scopRoot = bb; }
void FixupSelfReferentialMacrosInAST::visit ( SgNode* node ) { // DQ (3/11/2006): Set NULL pointers where we would like to have none. // printf ("In FixupSelfReferentialMacrosInAST::visit(): node = %s \n",node->class_name().c_str()); ROSE_ASSERT(node != NULL); switch (node->variantT()) { case V_SgInitializedName: { SgInitializedName* initializedName = isSgInitializedName(node); ROSE_ASSERT(initializedName != NULL); SgType* type = initializedName->get_type()->stripType(); SgClassType* classType = isSgClassType(type); if (classType != NULL) { SgClassDeclaration* targetClassDeclaration = isSgClassDeclaration(classType->get_declaration()); SgName className = targetClassDeclaration->get_name(); // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a class declaration name = %s \n",className.str()); if (className == "sigaction") { // printf ("In FixupSelfReferentialMacrosInAST::visit(): Found a sigaction type \n"); // Note we could also check that the declaration came from a known header file. SgStatement* associatedStatement = isSgStatement(initializedName->get_parent()); if (associatedStatement != NULL) { // Add a macro to undefine the "#define sa_handler __sigaction_handler.sa_handler" macro. // printf ("In FixupSelfReferentialMacrosInAST::visit(): Add a macro to undefine the macro #define sa_handler __sigaction_handler.sa_handler \n"); // PreprocessingInfo* macro = new PreprocessingInfo(DirectiveType, const std::string & inputString,const std::string & filenameString, int line_no , int col_no,int nol, RelativePositionType relPos ); PreprocessingInfo::DirectiveType directiveType = PreprocessingInfo::CpreprocessorUndefDeclaration; std::string macroString = "#undef sa_handler\n"; std::string filenameString = "macro_call_fixupSelfReferentialMacrosInAST"; int line_no = 1; int col_no = 1; int nol = 1; PreprocessingInfo::RelativePositionType relPos = PreprocessingInfo::before; PreprocessingInfo* macro = new PreprocessingInfo(directiveType,macroString,filenameString,line_no,col_no,nol,relPos); // printf ("Attaching CPP directive %s to IR node %p as attributes. \n",PreprocessingInfo::directiveTypeName(macro->getTypeOfDirective()).c_str(),associatedStatement); associatedStatement->addToAttachedPreprocessingInfo(macro); #if 0 printf ("Exiting as a test! \n"); ROSE_ASSERT(false); #endif } } } } default: { // printf ("Not handled in FixupSelfReferentialMacrosInAST::visit(%s) \n",node->class_name().c_str()); } } }
/* * The function * findScope() * takes as a parameter a SgNode* which is a SgStatement*. It returns a SgNodePtrVector of all * preceding scopes the SgStatement is in. * */ SgNodePtrVector findScopes (SgNode * astNode) { ROSE_ASSERT (isSgStatement (astNode)); SgNodePtrVector returnVector; SgScopeStatement *currentScope; if (isSgScopeStatement (astNode)) { currentScope = isSgScopeStatement (astNode); ROSE_ASSERT (currentScope != NULL); returnVector.push_back (astNode); } else { SgStatement *sageStatement = isSgStatement (astNode); ROSE_ASSERT (sageStatement != NULL); currentScope = sageStatement->get_scope (); ROSE_ASSERT (currentScope != NULL); returnVector.push_back (currentScope); } while (currentScope->variantT () != V_SgGlobal) { currentScope = currentScope->get_scope (); ROSE_ASSERT (currentScope != NULL); returnVector.push_back (currentScope); } //Must also include the Global Scopes of the other files in the project if (currentScope->variantT () == V_SgGlobal) { SgFile *sageFile = isSgFile ((currentScope)->get_parent ()); ROSE_ASSERT (sageFile != NULL); SgProject *sageProject = isSgProject (sageFile->get_parent ()); ROSE_ASSERT (sageProject != NULL); //Get a list of all files in the current project const SgFilePtrList sageFilePtrList = sageProject->get_fileList (); //Iterate over the list of files to find all Global Scopes SgNodePtrVector globalScopes; for (unsigned int i = 0; i < sageFilePtrList.size (); i += 1) { const SgFile *sageFile = isSgFile (sageFilePtrList[i]); ROSE_ASSERT (sageFile != NULL); if( isSgSourceFile(sageFile) != NULL ) { SgGlobal *sageGlobal = isSgSourceFile(sageFile)->get_globalScope (); ROSE_ASSERT (sageGlobal != NULL); returnVector.push_back (sageGlobal); } } } return returnVector; };
void flattenScopes(SgFunctionDefinition * fDef) { // * 3.3: find all variables in the function,give them a unique name and move them to the bgeinning of the function, this is allowed because this is for C only!!!. This would not work for classes which must be constructed // rename variables list<SgNode*> varDeclList=NodeQuery::querySubTree(fDef,V_SgInitializedName); for (list<SgNode*>::iterator varDecl=varDeclList.begin();varDecl!=varDeclList.end();varDecl++) { tring varName=isSgInitializedName(*varDecl)->get_name().getString(); char numberCString[255]; sprintf(numberCString,"%i",idNr); string newVarName=string("PML")+string(numberCString)+string("_")+varName; idNr++; isSgInitializedName(*varDecl)->set_name(SgName(newVarName.c_str())); } list<SgNode*> newDeclList; varDeclList.clear(); varDeclList=NodeQuery::querySubTree(procFuncVec[procNr],V_SgVariableDeclaration); // the move the variable declaration to the function begin and replace the old declaration site with a definition for (list<SgNode*>::iterator varDecl=varDeclList.begin();varDecl!=varDeclList.end();varDecl++) { SgVariableDeclaration * varDeclStmt=isSgVariableDeclaration(*varDecl); SgVariableDefinition * varDef=varDeclStmt->get_definition(); SgInitializedName *iniName=isSgInitializedName(varDef->get_vardefn()); if (iniName->get_initializer () !=NULL) { // cout <<"VarDecl >"<<iniName->get_name().getString()<<"< has initilizer >"<<iniName->get_initializer ()->unparseToString()<<"<"<<endl; // determine if it is safe to separate initializer from decl // for now true if (1) { Sg_File_Info * fi=Sg_File_Info::generateDefaultFileInfoForTransformationNode(); SgVarRefExp * varRef=new SgVarRefExp (Sg_File_Info::generateDefaultFileInfoForTransformationNode(),new SgVariableSymbol(iniName)); SgType * type=isSgAssignInitializer(iniName->get_initializer())->get_type (); SgAssignInitializer * sai=isSgAssignInitializer(iniName->get_initializer()); if (sai==NULL) { cerr<<"isSgAssignInitializer(iniName->get_initializer())=NULL"<<endl; exit(-1); } SgExpression *lhs,*rhs; lhs=varRef; rhs=sai->get_operand (); if (lhs==NULL) { cerr<<"lhs=NULL"<<endl; exit(-1); } if (rhs==NULL) { cerr<<"rhs=NULL"<<endl; exit(-1); } SgAssignOp * assignment=new SgAssignOp(Sg_File_Info::generateDefaultFileInfoForTransformationNode(),lhs,rhs); SgExprStatement * expr=new SgExprStatement(fi,assignment); if (expr==NULL) { cerr<<"construction of expr failed"<<endl; } isSgAssignInitializer(iniName->get_initializer ())->set_operand(NULL); free(iniName->get_initializer ()); iniName->set_initializer (NULL); // put the iniName in the list newDeclList.push_back(varDeclStmt); if (isSgStatement(varDeclStmt)==NULL) { cerr<<"isSgStatement(varDeclStmt)==NULL"<<endl; } LowLevelRewrite::replace(isSgStatement(varDeclStmt),isSgStatement(expr)); } } else { cout <<"VarDecl >"<<iniName->get_name().getString()<<"> is uninitialized"<<endl; newDeclList.push_back(varDeclStmt); LowLevelRewrite::remove(isSgStatement(varDeclStmt)); } } for (list<SgNode*>::iterator varDecl=newDeclList.begin();varDecl!=newDeclList.end();varDecl++) { fDef->prepend_statement(isSgStatement(*varDecl)); } return ; }