NodeQuerySynthesizedAttributeType querySolverGrammarElementFromVariantVector ( SgNode * astNode, VariantVector targetVariantVector ) { // This function extracts type nodes that would not be traversed so that they can // accumulated to a list. The specific nodes collected into the list is controlled // by targetVariantVector. ROSE_ASSERT (astNode != NULL); NodeQuerySynthesizedAttributeType returnNodeList; Rose_STL_Container<SgNode*> nodesToVisitTraverseOnlyOnce; pushNewNode (&returnNodeList,targetVariantVector,astNode); vector<SgNode*> succContainer = astNode->get_traversalSuccessorContainer(); vector<pair<SgNode*,string> > allNodesInSubtree = astNode->returnDataMemberPointers(); if( succContainer.size() != allNodesInSubtree.size() ) for(vector<pair<SgNode*,string> >::iterator iItr = allNodesInSubtree.begin(); iItr!= allNodesInSubtree.end(); ++iItr ) if( isSgType(iItr->first) != NULL ) if(std::find(succContainer.begin(),succContainer.end(),iItr->first) == succContainer.end() ) pushNewNode (&returnNodeList,targetVariantVector,iItr->first); return returnNodeList; } /* End function querySolverUnionFields() */
NodeQuerySynthesizedAttributeType queryNodeClassDeclarationFromTypedefName (SgNode * astNode, SgNode * nameNode) { NodeQuerySynthesizedAttributeType returnList; ROSE_ASSERT (nameNode != NULL); ROSE_ASSERT (nameNode != NULL); //finds the name which should be matched to SgName *sageName = isSgName (nameNode); ROSE_ASSERT (sageName != NULL); string nameToMatch = sageName->str (); ROSE_ASSERT (nameToMatch.length () > 0); if (isSgType (astNode) != NULL) { /*SgTypedefType* sageTypedefType = isSgTypedefType(astNode); string name = TransformationSupport::getTypeName(sageTypedefType); ROSE_ASSERT( nameToMatch.length() > 0 ); cout << nameToMatch << endl; */ #ifdef DEBUG_CGRAPHPP cout << TransformationSupport::getTypeName (isSgType (astNode)) << endl; #endif if (TransformationSupport::getTypeName (isSgType (astNode)) == nameToMatch) { returnList.push_back (astNode); } /* if(nameToMatch == name){ SgClassDeclaration *sageClassDeclaration = isSgClassDeclaration (sageTypedefType->get_declaration()); ROSE_ASSERT( sageClassDeclaration != NULL ); returnList.push_back(sageClassDeclaration); }*/ } return returnList; }
vector<SgType*> typeInterpreter::typeVectorFromTypedef(SgTypedefDeclaration* typedefDeclaration){ vector<SgType*> typeVector; ROSE_ASSERT (typedefDeclaration != NULL); SgType* baseType = NULL; SgType* previousBaseType = NULL; do { previousBaseType = baseType; baseType = findBaseType(isSgType(typedefDeclaration)); ROSE_ASSERT(baseType != NULL); typeVector.push_back(baseType); }while( baseType != previousBaseType ); return typeVector; };
int main(int argc, char* argv[]) { SgProject* proj = frontend(argc,argv); SgFunctionDeclaration* mainDecl = SageInterface::findMain(proj); SgFunctionDefinition* mainDef = mainDecl->get_definition(); // std::vector<SgNode*> dotExps = NodeQuery::querySubTree(mainDef, V_SgDotExp); std::vector<SgNode*> varRefs = NodeQuery::querySubTree(mainDef,V_SgVarRefExp); int classExps = 0; for (unsigned int i = 0; i < varRefs.size(); i++) { if (isSgClassType(isSgVarRefExp(varRefs[i])->get_type())) { SgClassType* ct = isSgClassType(isSgVarRefExp(varRefs[i])->get_type()); std::cout << "name of ref: " << isSgVarRefExp(varRefs[i])->get_symbol()->get_name().getString() << std::endl; if (SageInterface::isStructType(ct)) { SgDeclarationStatement* decl = isSgType(ct)->getAssociatedDeclaration(); SgDeclarationStatement* defining_decl = decl->get_definingDeclaration(); if (!(defining_decl->isNameOnly())) { if (isSgClassDeclaration(defining_decl)) { if (isSgClassDeclaration(defining_decl)->get_definition()) { SgDeclarationStatementPtrList member_stats = isSgClassDeclaration(defining_decl)->get_definition()->get_members(); SgDeclarationStatementPtrList::iterator j = member_stats.begin(); for (; j != member_stats.end(); j++) { SgDeclarationStatement* d = isSgDeclarationStatement(*j); std::cout << "decl stat name: " << d->class_name() << std::endl; SgInitializedNamePtrList init_lst = isSgVariableDeclaration(d)->get_variables(); SgInitializedNamePtrList::iterator k = init_lst.begin(); std::cout << "variables in initialized name ptr list..." << std::endl; for (; k != init_lst.end(); k++) { std::cout << isSgInitializedName(*k)->get_name().getString() << std::endl; std::cout << isSgInitializedName(*k)->get_type()->class_name() << std::endl; } } classExps+=1; } } } } } } std::cout << "num class_exp: " << classExps << std::endl; return 0; }
TypeTraversalSynthesizedAttribute TypeTraversal::evaluateSynthesizedAttribute ( SgNode* astNode, TypeTraversalInheritedAttribute inheritedAttribute, SynthesizedAttributesList childAttributes ) { #if 0 printf ("In TypeTraversal::evaluateSynthesizedAttribute(): astNode = %p = %s \n",astNode,astNode->class_name().c_str()); #endif SgType* type = isSgType(astNode); if (type != NULL) { transformType(type); } TypeTraversalSynthesizedAttribute localResult; return localResult; }
// DQ (4/7/2004): Added to support more general lookup of data in the AST (vector of variants) void* querySolverGrammarElementFromVariantVector ( SgNode * astNode, VariantVector targetVariantVector, NodeQuerySynthesizedAttributeType* returnNodeList ) { // This function extracts type nodes that would not be traversed so that they can // accumulated to a list. The specific nodes collected into the list is controlled // by targetVariantVector. ROSE_ASSERT (astNode != NULL); #if 0 printf ("Inside of void* querySolverGrammarElementFromVariantVector() astNode = %p = %s \n",astNode,astNode->class_name().c_str()); #endif Rose_STL_Container<SgNode*> nodesToVisitTraverseOnlyOnce; pushNewNode (returnNodeList,targetVariantVector,astNode); vector<SgNode*> succContainer = astNode->get_traversalSuccessorContainer(); vector<pair<SgNode*,string> > allNodesInSubtree = astNode->returnDataMemberPointers(); #if 0 printf ("succContainer.size() = %zu \n",succContainer.size()); printf ("allNodesInSubtree.size() = %zu \n",allNodesInSubtree.size()); #endif if ( succContainer.size() != allNodesInSubtree.size() ) { for (vector<pair<SgNode*,string> >::iterator iItr = allNodesInSubtree.begin(); iItr!= allNodesInSubtree.end(); ++iItr ) { #if 0 if ( iItr->first != NULL ) { // printf ("iItr->first = %p = %s \n",iItr->first,iItr->first->class_name().c_str()); printf ("iItr->first = %p \n",iItr->first); printf ("iItr->first = %p = %s \n",iItr->first,iItr->first->class_name().c_str()); } #endif // DQ (7/27/2014): Check if this is always non-NULL. // ROSE_ASSERT(iItr->first != NULL); #if 0 if (iItr->first != NULL) { // printf ("In querySolverGrammarElementFromVariantVector(): iItr->first->variantT() = %d class_name = %s \n",iItr->first->variantT(),iItr->first->class_name().c_str()); printf ("In querySolverGrammarElementFromVariantVector(): iItr->first = %p \n",iItr->first); printf ("In querySolverGrammarElementFromVariantVector(): iItr->first->class_name = %s \n",iItr->first->class_name().c_str()); printf ("In querySolverGrammarElementFromVariantVector(): iItr->first->variantT() = %d \n",(int)iItr->first->variantT()); } else { printf ("In querySolverGrammarElementFromVariantVector(): iItr->first == NULL \n"); } #endif SgType* type = isSgType(iItr->first); if ( type != NULL ) { // DQ (1/13/2011): If we have not already seen this entry then we have to chase down possible nested types. // if (std::find(succContainer.begin(),succContainer.end(),iItr->first) == succContainer.end() ) if (std::find(succContainer.begin(),succContainer.end(),type) == succContainer.end() ) { // DQ (1/30/2010): Push the current type onto the list first, then any internal types... pushNewNode (returnNodeList,targetVariantVector,type); // Are there any other places where nested types can be found...? // if ( isSgPointerType(iItr->first) != NULL || isSgArrayType(iItr->first) != NULL || isSgReferenceType(iItr->first) != NULL || isSgTypedefType(iItr->first) != NULL || isSgFunctionType(iItr->first) != NULL || isSgModifierType(iItr->first) != NULL) // if (type->containsInternalTypes() == true) if (type->containsInternalTypes() == true) { #if 0 printf ("If we have not already seen this entry then we have to chase down possible nested types. \n"); // ROSE_ASSERT(false); #endif Rose_STL_Container<SgType*> typeVector = type->getInternalTypes(); #if 0 printf ("----- typeVector.size() = %zu \n",typeVector.size()); #endif Rose_STL_Container<SgType*>::iterator i = typeVector.begin(); while(i != typeVector.end()) { #if 0 printf ("----- internal type = %s \n",(*i)->class_name().c_str()); #endif // DQ (1/16/2011): This causes a test in tests/roseTests/programAnalysisTests/variableLivenessTests // to fail with error "Error :: Number of nodes = 37 should be : 36" // Add this type to the return list of types. pushNewNode (returnNodeList,targetVariantVector,*i); i++; } } // DQ (1/30/2010): Move this code to the top of the basic block. // pushNewNode (returnNodeList,targetVariantVector,iItr->first); // pushNewNode (returnNodeList,targetVariantVector,type); } } } } #if 0 // This code cannot be put here. Since the same SgVarRefExp will also be found during variable substitution phase. // We don't want to replace the original SgVarRefExp!! // Liao 1/19/2011. query the dim_info of SgArrayType associated with SgPntrArrRefExp // e.g. assuming a subtree has a reference to an array, then the variables used to declare the array dimensions should also be treated as referenced/used by the subtree // even though the reference is indirect. // AST should look like: // SgPntrArrRefExp -> SgVarRefExp (lhs) -> SgVariableSymbol(symbol) -> SgInitializedName -> SgArrayType (typeptr) -> SgExprListExp (dim_info) // AST outlining needs to find indirect use of a variable to work properly if (std::find(targetVariantVector.begin(), targetVariantVector.end(), V_SgVarRefExp) != targetVariantVector.end()) // Only do this if SgVarRefExp is of interest { if (SgPntrArrRefExp * arr_exp = isSgPntrArrRefExp(astNode)) { printf("Debug: queryVariant.C Found SgPntrArrRefExp :%p\n", arr_exp); Rose_STL_Container<SgNode*> refList = NodeQuery::querySubTree(arr_exp->get_lhs_operand(),V_SgVarRefExp); // find the array reference from the lhs operand, which could be a complex arithmetic expression SgVarRefExp* array_ref = NULL; for (Rose_STL_Container<SgNode*>::iterator iter = refList.begin(); iter !=refList.end(); iter ++) { SgVarRefExp* cur_ref = isSgVarRefExp(*iter); ROSE_ASSERT (cur_ref != NULL); SgVariableSymbol * sym = cur_ref->get_symbol(); ROSE_ASSERT (sym != NULL); SgInitializedName * i_name = sym->get_declaration(); ROSE_ASSERT (i_name != NULL); SgArrayType * a_type = isSgArrayType(i_name->get_typeptr()); if (a_type) { Rose_STL_Container<SgNode*> dim_ref_list = NodeQuery::querySubTree(a_type->get_dim_info(),V_SgVarRefExp); for (Rose_STL_Container<SgNode*>::iterator iter2 = dim_ref_list.begin(); iter2 != dim_ref_list.end(); iter2++) { SgVarRefExp* dim_ref = isSgVarRefExp(*iter2); printf("Debug: queryVariant.C Found indirect SgVarRefExp as part of array dimension declaration:%s\n", dim_ref->get_symbol()->get_name().str()); pushNewNode (returnNodeList, targetVariantVector, *iter2); } } } } // end if SgPntrArrRefExp } // end if find() #endif return NULL; } /* End function querySolverUnionFields() */
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; }