refactoring module analysis

This commit is contained in:
ALEXks
2025-02-10 17:16:15 +03:00
parent f135cd6d06
commit 7e17c62bbb
13 changed files with 4003 additions and 688 deletions

File diff suppressed because it is too large Load Diff

View File

@@ -94,7 +94,9 @@ set(UTILS _src/Utils/AstWrapper.h
_src/Utils/types.h
_src/Utils/utils.cpp
_src/Utils/utils.h
_src/Utils/version.h)
_src/Utils/version.h
_src/Utils/module_utils.h
_src/Utils/module_utils.cpp)
set(OMEGA _src/SageAnalysisTool/OmegaForSage/add-assert.cpp
_src/SageAnalysisTool/OmegaForSage/affine.cpp

View File

@@ -832,15 +832,22 @@ static pair<templateDir, string>
return make_pair(retDir, lastReturn);
}
static pair<string, string> getModuleRename(const map<string, set<SgSymbol*>>& byUse, const DIST::Array* array,
const string& filename, const pair<int, int>& lineRange)
static pair<string, string> getModuleRename(const set<SgStatement*>& allocatableStmts, const DIST::Array* array)
{
auto declS = array->GetDeclSymbol(filename, lineRange, getAllFilesInProject())->GetOriginal();
for (auto& elem : byUse)
for (auto& localS : setToMapWithSortByStr(elem.second))
if (OriginalSymbol(localS.second) == declS)
return make_pair(elem.first, localS.second->identifier());
return make_pair("", "");
if (array->GetLocation().first == DIST::l_MODULE)
{
set<string> arrayNames;
for (auto& alloc : allocatableStmts)
if (alloc->variant() == ALLOCATE_STMT)
arrayNames.insert(getNameByUse(alloc, array->GetShortName(), array->GetLocation().second));
if (arrayNames.size() > 1 || arrayNames.size() == 0)
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
return make_pair(array->GetShortName(), *arrayNames.begin());
}
else
return make_pair("", "");
}
static pair<DIST::Array*, string>
@@ -848,10 +855,7 @@ getNewDirective(const string &fullArrayName,
const vector<string> &distrRules,
const vector<string> &alignRules,
const DataDirective &dataDir,
const map<string, set<SgSymbol*>> &byUse,
const string& filename,
const pair<int, int>& lineRange,
bool alignToRealign)
const set<SgStatement*>& allocatableStmts)
{
string out = "";
DIST::Array* outA = NULL;
@@ -873,7 +877,7 @@ getNewDirective(const string &fullArrayName,
if (dataDir.alignRules[i].alignArray->GetName() == fullArrayName)
{
string rule = alignRules[i];
if (alignToRealign)
if (allocatableStmts.size())
{
auto it = rule.find("ALIGN");
while (it != string::npos)
@@ -881,8 +885,8 @@ getNewDirective(const string &fullArrayName,
rule = rule.replace(it, 5, "REALIGN");
it = rule.find("ALIGN", it + 7);
}
auto renamePair = getModuleRename(byUse, dataDir.alignRules[i].alignArray, filename, lineRange);
auto renamePair = getModuleRename(allocatableStmts, dataDir.alignRules[i].alignArray);
if (renamePair.first != "")
{
it = rule.find(renamePair.first);
@@ -1722,29 +1726,12 @@ void insertDistributionToFile(SgFile *file, const char *fin_name, const DataDire
if (distrArrays.find(fullArrayName) != distrArrays.end())
{
map<string, set<SgSymbol*>> byUseInFunc;
const vector<SgStatement*> &allocatableStmtsCopy = getAttributes<SgStatement*, SgStatement*>(st, set<int>{ ALLOCATE_STMT });
set<SgStatement*> allocatableStmts;
if (allocatableStmtsCopy.size())
{
allocatableStmts = filterAllocateStats(file, allocatableStmtsCopy, currSymb->identifier());
for (auto &alloc : allocatableStmts)
{
if (alloc->fileName() != currFilename)
if (!alloc->switchToFile())
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
auto byUse = moduleRefsByUseInFunction(alloc);
for (auto &byUseElem : byUse)
byUseInFunc[byUseElem.first].insert(byUseElem.second.begin(), byUseElem.second.end());
SgFile::switchToFile(currFilename);
}
}
pair<DIST::Array*, string> dirWithArray = getNewDirective(fullArrayName, distrRules, alignRules, dataDir, byUseInFunc, filename, lineRange, allocatableStmts.size() != 0);
pair<DIST::Array*, string> dirWithArray = getNewDirective(fullArrayName, distrRules, alignRules, dataDir, allocatableStmts);
string toInsert = dirWithArray.second;
if (toInsert != "")

View File

@@ -166,155 +166,6 @@ void DvmhRegionInserter::updateParallelFunctions(const map<string, vector<LoopGr
}
}
static void findByUse(map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUse, const string& varName,
const set<string>& locNames, vector<string> &altNames)
{
for (auto& elem : modByUse)
{
if (locNames.count(elem.first))
{
for (auto& byUse : elem.second)
{
SgSymbol* toCmp = byUse.second ? byUse.second : byUse.first;
checkNull(toCmp, convertFileName(__FILE__).c_str(), __LINE__);
if (toCmp->identifier() == varName)
altNames.push_back(byUse.first->identifier());
}
}
}
}
static void fillInfo(SgStatement *start,
set<string> &useMod,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUse,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUseOnly)
{
for (SgStatement* st = start; st != start->lastNodeOfStmt(); st = st->lexNext())
{
if (isSgExecutableStatement(st))
break;
if (st->variant() == CONTAINS_STMT)
break;
if (st != start && (st->variant() == PROC_HEDR || st->variant() == FUNC_HEDR))
break;
fillUseStatement(st, useMod, modByUse, modByUseOnly);
}
}
static SgStatement* findModWithName(const vector<SgStatement*> &modules, const string &name)
{
for (auto& elem : modules)
if (elem->variant() == MODULE_STMT)
if (elem->symbol()->identifier() == name)
return elem;
return NULL;
}
static string getNameByUse(SgStatement *place, const string &varName, const string &locName)
{
SgStatement* func = getFuncStat(place);
if (func == NULL)
return varName;
else
{
map<string, set<string>> graphUse;
set<string> useMod;
map<string, vector<pair<SgSymbol*, SgSymbol*>>> modByUse;
map<string, vector<pair<SgSymbol*, SgSymbol*>>> modByUseOnly;
fillInfo(func, useMod, modByUse, modByUseOnly);
SgStatement* cp = func->controlParent();
if (isSgProgHedrStmt(cp) || cp->variant() == MODULE_STMT) // if function in contains region
fillInfo(cp, useMod, modByUse, modByUseOnly);
set<string> useModDone;
bool needRepeat = true;
vector<SgStatement*> modules;
findModulesInFile(func->getFile(), modules);
while (needRepeat)
{
needRepeat = false;
set<string> newUseMod;
for (auto& useM : useMod)
{
if (useModDone.find(useM) == useModDone.end())
{
auto modSt = findModWithName(modules, useM);
if (modSt == NULL || useM == "dvmh_template_mod")
continue;
checkNull(modSt, convertFileName(__FILE__).c_str(), __LINE__);
set<string> tmpUse;
fillInfo(modSt, tmpUse, modByUse, modByUseOnly);
useModDone.insert(useM);
for (auto& use : tmpUse)
{
newUseMod.insert(use);
if (use != "dvmh_template_mod")
graphUse[use].insert(useM);
}
}
}
for (auto& newU : newUseMod)
{
if (useModDone.find(newU) == useModDone.end())
{
useModDone.insert(newU);
needRepeat = true;
}
}
}
vector<string> altNames;
findByUse(modByUse, varName, { locName }, altNames);
findByUse(modByUseOnly, varName, { locName }, altNames);
if (altNames.size() == 0)
{
set<string> locations = { locName };
bool changed = true;
while (changed)
{
changed = false;
for (auto& loc : locations)
{
if (graphUse.find(loc) != graphUse.end())
{
for (auto& use : graphUse[loc])
{
if (locations.find(use) == locations.end())
{
locations.insert(use);
changed = true;
}
}
}
}
}
findByUse(modByUse, varName, locations, altNames);
findByUse(modByUseOnly, varName, locations, altNames);
}
if (altNames.size() == 0)
return varName;
else if (altNames.size() >= 1)
{
set<string> setAlt(altNames.begin(), altNames.end());
return *setAlt.begin();
}
else
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
}
}
static SgStatement* skipDvmhRegionInterval(SgStatement *start)
{
if (start->variant() != ACC_REGION_DIR)

View File

@@ -2296,123 +2296,6 @@ void checkForRecursion(SgFile *file, map<string, vector<FuncInfo*>> &allFuncInfo
}
}
static void fillUseStmt(SgStatement *stat, map<string, set<SgSymbol*>> &byUse)
{
if (stat->variant() != USE_STMT)
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
SgExpression* ex = stat->expr(0);
if (ex && ex->variant() == ONLY_NODE)
{
for (auto exI = ex->lhs(); exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgExpression* ren = exI->lhs();
if (ren->lhs()->symbol() && ren->rhs() && ren->rhs()->symbol())
byUse[ren->rhs()->symbol()->identifier()].insert(ren->lhs()->symbol());
}
}
}
else if (ex && ex->lhs())
{
for (auto exI = ex; exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgExpression* ren = exI->lhs();
if (ren->lhs()->symbol() && ren->rhs() && ren->rhs()->symbol())
byUse[ren->rhs()->symbol()->identifier()].insert(ren->lhs()->symbol());
}
}
}
}
map<string, set<SgSymbol*>> moduleRefsByUseInFunction(SgStatement *stIn)
{
checkNull(stIn, convertFileName(__FILE__).c_str(), __LINE__);
map<string, set<SgSymbol*>> byUse;
int var = stIn->variant();
while (var != PROG_HEDR && var != PROC_HEDR && var != FUNC_HEDR)
{
stIn = stIn->controlParent();
if (stIn == NULL)
return byUse;
var = stIn->variant();
}
auto mapOfUses = createMapOfModuleUses(stIn->getFile());
set<string> useMods;
for (SgStatement *stat = stIn->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
{
if (stat->variant() == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
}
const int cpOfSt = stIn->controlParent()->variant();
//contains of func
if (cpOfSt == PROG_HEDR || cpOfSt == PROC_HEDR || cpOfSt == FUNC_HEDR)
{
for (SgStatement *stat = stIn->controlParent()->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
{
if (stat->variant() == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
}
}
bool chages = true;
while (chages)
{
chages = false;
set<string> newUseMods(useMods);
for (auto &elem : useMods)
{
auto it = mapOfUses.find(elem);
if (it != mapOfUses.end())
{
for (auto &elem2 : it->second)
{
if (newUseMods.find(elem2) == newUseMods.end())
{
newUseMods.insert(elem2);
chages = true;
}
}
}
}
useMods = newUseMods;
}
vector<SgStatement*> modules;
findModulesInFile(stIn->getFile(), modules);
for (auto &mod : modules)
{
if (useMods.find(mod->symbol()->identifier()) != useMods.end())
{
for (SgStatement *stat = mod->lexNext(); stat != mod->lastNodeOfStmt(); stat = stat->lexNext())
{
const int var = stat->variant();
if (var == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
else if (var == PROC_HEDR || var == FUNC_HEDR)
break;
}
}
}
return byUse;
}
void propagateWritesToArrays(map<string, vector<FuncInfo*>> &allFuncInfo)
{
map<string, FuncInfo*> funcByName;

View File

@@ -45,7 +45,6 @@ int CheckFunctionsToInline(SgProject *proj, const std::map<std::string, int> &fi
void checkForRecursion(SgFile *file, std::map<std::string, std::vector<FuncInfo*>> &allFuncInfo, std::vector<Messages> &messagesForFile);
bool isPassFullArray(SgExpression *ex);
void doMacroExpand(SgFile *file, std::vector<Messages> &messages);
std::map<std::string, std::set<SgSymbol*>> moduleRefsByUseInFunction(SgStatement *stIn);
void propagateWritesToArrays(std::map<std::string, std::vector<FuncInfo*>> &allFuncInfo);
void detectCopies(std::map<std::string, std::vector<FuncInfo*>> &allFuncInfo);
void fillInterfaceBlock(std::map<std::string, std::vector<FuncInfo*>>& allFuncInfo);

View File

@@ -879,46 +879,6 @@ void initTags()
#include "tag.h"
}
void findModulesInFile(SgFile *file, vector<SgStatement*> &modules)
{
SgStatement *first = file->firstStatement();
set<SgStatement*> functions;
int funcNum = file->numberOfFunctions();
for (int i = 0; i < funcNum; ++i)
functions.insert(file->functions(i));
while (first)
{
if (first->variant() == MODULE_STMT)
{
modules.push_back(first);
first = first->lastNodeOfStmt();
}
else
{
if (functions.size())
{
auto it = functions.find(first);
if (it != functions.end())
first = (*it)->lastNodeOfStmt();
}
}
first = first->lexNext();
}
}
void getModulesAndFunctions(SgFile *file, vector<SgStatement*> &modulesAndFunctions)
{
findModulesInFile(file, modulesAndFunctions);
int funcNum = file->numberOfFunctions();
for (int i = 0; i < funcNum; ++i)
modulesAndFunctions.push_back(file->functions(i));
}
void tryToFindPrivateInAttributes(SgStatement *st, set<string> &privates, bool onlyReduction, bool onlyUsers)
{
set<Symbol*> privatesVars;
@@ -2365,76 +2325,6 @@ objT& getObjectForFileFromMap(const char *fileName, map<string, objT> &mapObject
template vector<SpfInterval*>& getObjectForFileFromMap(const char *fileName, map<string, vector<SpfInterval*>>&);
template PredictorStats& getObjectForFileFromMap(const char *fileName, map<string, PredictorStats>&);
SgSymbol* getFromModule(const map<string, set<SgSymbol*>> &byUse, SgSymbol *orig, bool processAsModule)
{
if (!processAsModule)
{
checkNull(orig->scope(), convertFileName(__FILE__).c_str(), __LINE__);
if (orig->scope()->variant() != MODULE_STMT)
return orig;
}
if (byUse.size())
{
for (auto& elem : byUse)
{
for (auto& localS : setToMapWithSortByStr(elem.second))
if (OriginalSymbol(localS.second)->thesymb == orig->thesymb)
return localS.second;
}
}
return orig;
}
map<string, set<string>> createMapOfModuleUses(SgFile *file)
{
map<string, set<string>> retValMap;
vector<SgStatement*> modules;
findModulesInFile(file, modules);
for (int z = 0; z < modules.size(); ++z)
{
SgStatement *curr = modules[z];
string modName = curr->symbol()->identifier();
for (SgStatement *st = curr->lexNext(); st != curr->lastNodeOfStmt(); st = st->lexNext())
{
if (st->variant() == USE_STMT)
retValMap[modName].insert(st->symbol()->identifier());
else if (st->variant() == PROC_HEDR || st->variant() == FUNC_HEDR)
break;
}
}
bool repeat = true;
while (repeat)
{
repeat = false;
for (auto &elem : retValMap)
{
set<string> toAdd(elem.second);
for (auto &inUse : elem.second)
{
auto it = retValMap.find(inUse);
if (it != retValMap.end())
{
for (auto &inUseToAdd : it->second)
{
if (toAdd.find(inUseToAdd) == toAdd.end())
{
toAdd.insert(inUseToAdd);
repeat = true;
}
}
}
}
elem.second = toAdd;
}
}
return retValMap;
}
void printSymbolTable(SgFile *file, string filter, const set<int>& vars)
{
for (auto s = file->firstSymbol(); s; s = s->next())
@@ -2574,96 +2464,6 @@ SgStatement* duplicateProcedure(SgStatement *toDup, const string *newName, bool
return toMove;
}
void fillModuleUse(SgFile *file, map<string, set<string>> &moduleUses, map<string, string> &moduleDecls)
{
const string currFN = file->filename();
for (SgStatement* st = file->firstStatement(); st; st = st->lexNext())
{
if (st->fileName() == currFN)
{
if (st->variant() == USE_STMT)
moduleUses[currFN].insert(st->symbol()->identifier());
if (st->variant() == MODULE_STMT)
{
string moduleN = st->symbol()->identifier();
auto it = moduleDecls.find(moduleN);
if (it != moduleDecls.end())
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
moduleDecls[moduleN] = currFN;
}
}
}
}
void filterModuleUse(map<string, set<string>>& moduleUsesByFile, map<string, string>& moduleDecls)
{
for (auto& elem : moduleUsesByFile)
{
set<string> newSet;
for (auto& setElem : elem.second)
{
auto it = moduleDecls.find(setElem);
if (it == moduleDecls.end())
newSet.insert(setElem);
else if (elem.first != it->second)
newSet.insert(setElem);
}
elem.second = newSet;
}
/*map<string, set<string>> modIncludeMod;
for (auto& mod : moduleDecls)
{
string name = mod.first;
string file = mod.second;
auto it = moduleUsesByFile.find(file);
if (it != moduleUsesByFile.end())
modIncludeMod[name] = it->second;
}
bool change = true;
while (change)
{
change = false;
for (auto& mod : modIncludeMod)
{
set<string> newSet = mod.second;
for (auto& included : mod.second)
{
auto it = modIncludeMod.find(included);
if (it == modIncludeMod.end())
continue;
for (auto& elem : it->second)
{
if (newSet.find(elem) == newSet.end())
{
newSet.insert(elem);
change = true;
}
}
}
mod.second = newSet;
}
}
for (auto& elem : moduleUsesByFile)
{
set<string> newSet = elem.second;
for (auto& setElem : elem.second)
{
auto it = modIncludeMod.find(setElem);
if (it != modIncludeMod.end())
for (auto& toRem : it->second)
newSet.erase(toRem);
}
elem.second = newSet;
}*/
}
SgExpression* makeExprList(const vector<SgExpression*>& items, bool withSort)
{
SgExpression* list = NULL;
@@ -2847,59 +2647,6 @@ int getNextFreeLabel()
return -1;
}
static void addUseStatements(SgStatement* currF, SgStatement* obj, vector<SgStatement*>& useStats,
const vector<SgStatement*>& funcContains)
{
for (auto& funcSt : funcContains)
{
if (currF == funcSt)
{
SgStatement* last = obj->lastNodeOfStmt();
for (SgStatement* st = obj->lexNext(); st != last; st = st->lexNext())
{
if (st->variant() == USE_STMT)
useStats.push_back(st);
else if (st->variant() == CONTAINS_STMT)
break;
}
break;
}
}
}
void fillUsedModulesInFunction(SgStatement *st, vector<SgStatement*> &useStats)
{
checkNull(st, convertFileName(__FILE__).c_str(), __LINE__);
int var = st->variant();
while (var != PROG_HEDR && var != PROC_HEDR && var != FUNC_HEDR)
{
st = st->controlParent();
checkNull(st, convertFileName(__FILE__).c_str(), __LINE__);
var = st->variant();
}
for (SgStatement *stat = st->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
if (stat->variant() == USE_STMT)
useStats.push_back(stat);
for (int i = 0; i < current_file->numberOfFunctions(); ++i)
{
vector<SgStatement*> funcContains;
findContainsFunctions(current_file->functions(i), funcContains);
addUseStatements(st, current_file->functions(i), useStats, funcContains);
}
vector<SgStatement*> modules;
findModulesInFile(st->getFile(), modules);
for (auto &module : modules)
{
vector<SgStatement*> funcContains;
findContainsFunctions(module, funcContains, true);
addUseStatements(st, module, useStats, funcContains);
}
}
static void recFillUsedVars(SgExpression *exp, map<string, SgSymbol*> &vars)
{
if (exp)

View File

@@ -5,6 +5,7 @@
#include "../Distribution/Distribution.h"
#include "../GraphCall/graph_calls.h"
#include "../DynamicAnalysis/gcov_info.h"
#include "module_utils.h"
SgStatement* declaratedInStmt(SgSymbol *toFind, std::vector<SgStatement*> *allDecls = NULL, bool printInternal = true, SgStatement* scope = NULL);
@@ -15,8 +16,7 @@ std::string removeIncludeStatsAndUnparse(SgFile *file, const char *fileName, con
SgSymbol* findSymbolOrCreate(SgFile *file, const std::string toFind, SgType *type = NULL, SgStatement *scope = NULL);
void recExpressionPrint(SgExpression *exp);
void removeSubstrFromStr(std::string &str, const std::string &del);
void getModulesAndFunctions(SgFile *file, std::vector<SgStatement*> &modulesAndFunctions);
void findModulesInFile(SgFile *file, std::vector<SgStatement*> &modules);
void tryToFindPrivateInAttributes(SgStatement* st, std::set<std::string>& privatesVars, bool onlyReduction = false, bool onlyUsers = false);
void fillNonDistrArraysAsPrivate(SgStatement *st,
@@ -60,15 +60,11 @@ const CommonBlock* isArrayInCommon(const std::map<std::string, CommonBlock*> &co
std::vector<DIST::Array*> fillArraysFromDir(Statement *st);
SgSymbol* getFromModule(const std::map<std::string, std::set<SgSymbol*>> &byUse, SgSymbol *orig, bool processAsModule = false);
std::map<std::string, std::set<std::string>> createMapOfModuleUses(SgFile* file);
void printSymbolTable(SgFile* file, std::string filter = "", const std::set<int>& vars = {});
SgStatement* getFuncStat(SgStatement *st, const std::set<int> additional = std::set<int>());
std::map<SgStatement*, std::vector<DefUseList>> createDefUseMapByPlace();
SgStatement* duplicateProcedure(SgStatement* toDup, const std::string* newName, bool withAttributes = false, bool withComment = false, bool withSameLines = true, bool dontInsert = false);
void fillModuleUse(SgFile* file, std::map<std::string, std::set<std::string>>& moduleUses, std::map<std::string, std::string>& moduleDecls);
void filterModuleUse(std::map<std::string, std::set<std::string>>& moduleUses, std::map<std::string, std::string>& moduleDecls);
SgExpression* makeExprList(const std::vector<SgExpression*>& items, bool withSort = true);
std::string unparseProjectToString(SgFile* file, const int curr_regime);
@@ -77,7 +73,6 @@ std::vector<SgStatement*> makeDeclaration(const std::vector<SgSymbol*>& symbolsT
int getNextFreeLabel();
void fillUsedModulesInFunction(SgStatement *st, std::vector<SgStatement*> &useStats);
void fillVisibleInUseVariables(SgStatement *useSt, std::map<std::string, SgSymbol*> &vars);
std::string preprocDataString(std::string data, bool full = true);
@@ -91,7 +86,13 @@ void getVariables(SgExpression* ex, std::set<SgSymbol*>& variables, const std::s
template<typename T>
std::set<T> getAllVariables(SgStatement* stFrom, SgStatement* stTo, const std::set<int>& variants);
SgProject* createProject(const char* proj_name, std::vector<ParallelRegion*>& parallelRegions, std::vector<ParallelRegion*>& subs_parallelRegions, std::map<std::string, std::vector<SgStatement*>>& hiddenData, std::map<std::string, int>& filesNameWithoutExt, std::map<std::string, std::set<std::string>>& moduleUsesByFile, std::map<std::string, std::string>& moduleDecls, std::map<std::string, std::map<SgStatement*, std::vector<SgStatement*>>>& exctactedModuleStats, bool printSymbTable);
SgProject* createProject(const char* proj_name, std::vector<ParallelRegion*>& parallelRegions,
std::vector<ParallelRegion*>& subs_parallelRegions,
std::map<std::string, std::vector<SgStatement*>>& hiddenData,
std::map<std::string, int>& filesNameWithoutExt,
std::map<std::string, std::set<std::string>>& moduleUsesByFile,
std::map<std::string, std::string>& moduleDecls,
std::map<std::string, std::map<SgStatement*, std::vector<SgStatement*>>>& exctactedModuleStats, bool printSymbTable);
bool isArrayType(SgType* type);
bool isArrayRef(SgExpression* ex);

View File

@@ -0,0 +1,676 @@
#include <vector>
#include <set>
#include <map>
#include <string>
#include "dvm.h"
#include "errors.h"
#include "utils.h"
#include "../GraphCall/graph_calls_func.h"
#include "module_utils.h"
using std::vector;
using std::set;
using std::string;
using std::map;
using std::pair;
using std::make_pair;
void findModulesInFile(SgFile* file, vector<SgStatement*>& modules)
{
SgStatement* first = file->firstStatement();
set<SgStatement*> functions;
int funcNum = file->numberOfFunctions();
for (int i = 0; i < funcNum; ++i)
functions.insert(file->functions(i));
while (first)
{
if (first->variant() == MODULE_STMT)
{
modules.push_back(first);
first = first->lastNodeOfStmt();
}
else
{
if (functions.size())
{
auto it = functions.find(first);
if (it != functions.end())
first = (*it)->lastNodeOfStmt();
}
}
first = first->lexNext();
}
}
void getModulesAndFunctions(SgFile* file, vector<SgStatement*>& modulesAndFunctions)
{
findModulesInFile(file, modulesAndFunctions);
int funcNum = file->numberOfFunctions();
for (int i = 0; i < funcNum; ++i)
modulesAndFunctions.push_back(file->functions(i));
}
SgSymbol* getFromModule(const map<string, set<SgSymbol*>>& byUse, SgSymbol* orig, bool processAsModule)
{
if (!processAsModule)
{
checkNull(orig->scope(), convertFileName(__FILE__).c_str(), __LINE__);
if (orig->scope()->variant() != MODULE_STMT)
return orig;
}
if (byUse.size())
{
for (auto& elem : byUse)
{
for (auto& localS : setToMapWithSortByStr(elem.second))
if (OriginalSymbol(localS.second)->thesymb == orig->thesymb)
return localS.second;
}
}
return orig;
}
map<string, set<string>> createMapOfModuleUses(SgFile* file)
{
map<string, set<string>> retValMap;
vector<SgStatement*> modules;
findModulesInFile(file, modules);
for (int z = 0; z < modules.size(); ++z)
{
SgStatement* curr = modules[z];
string modName = curr->symbol()->identifier();
for (SgStatement* st = curr->lexNext(); st != curr->lastNodeOfStmt(); st = st->lexNext())
{
if (st->variant() == USE_STMT)
retValMap[modName].insert(st->symbol()->identifier());
else if (st->variant() == PROC_HEDR || st->variant() == FUNC_HEDR)
break;
}
}
bool repeat = true;
while (repeat)
{
repeat = false;
for (auto& elem : retValMap)
{
set<string> toAdd(elem.second);
for (auto& inUse : elem.second)
{
auto it = retValMap.find(inUse);
if (it != retValMap.end())
{
for (auto& inUseToAdd : it->second)
{
if (toAdd.find(inUseToAdd) == toAdd.end())
{
toAdd.insert(inUseToAdd);
repeat = true;
}
}
}
}
elem.second = toAdd;
}
}
return retValMap;
}
void fillModuleUse(SgFile* file, map<string, set<string>>& moduleUses, map<string, string>& moduleDecls)
{
const string currFN = file->filename();
for (SgStatement* st = file->firstStatement(); st; st = st->lexNext())
{
if (st->fileName() == currFN)
{
if (st->variant() == USE_STMT)
moduleUses[currFN].insert(st->symbol()->identifier());
if (st->variant() == MODULE_STMT)
{
string moduleN = st->symbol()->identifier();
auto it = moduleDecls.find(moduleN);
if (it != moduleDecls.end())
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
moduleDecls[moduleN] = currFN;
}
}
}
}
void filterModuleUse(map<string, set<string>>& moduleUsesByFile, map<string, string>& moduleDecls)
{
for (auto& elem : moduleUsesByFile)
{
set<string> newSet;
for (auto& setElem : elem.second)
{
auto it = moduleDecls.find(setElem);
if (it == moduleDecls.end())
newSet.insert(setElem);
else if (elem.first != it->second)
newSet.insert(setElem);
}
elem.second = newSet;
}
/*map<string, set<string>> modIncludeMod;
for (auto& mod : moduleDecls)
{
string name = mod.first;
string file = mod.second;
auto it = moduleUsesByFile.find(file);
if (it != moduleUsesByFile.end())
modIncludeMod[name] = it->second;
}
bool change = true;
while (change)
{
change = false;
for (auto& mod : modIncludeMod)
{
set<string> newSet = mod.second;
for (auto& included : mod.second)
{
auto it = modIncludeMod.find(included);
if (it == modIncludeMod.end())
continue;
for (auto& elem : it->second)
{
if (newSet.find(elem) == newSet.end())
{
newSet.insert(elem);
change = true;
}
}
}
mod.second = newSet;
}
}
for (auto& elem : moduleUsesByFile)
{
set<string> newSet = elem.second;
for (auto& setElem : elem.second)
{
auto it = modIncludeMod.find(setElem);
if (it != modIncludeMod.end())
for (auto& toRem : it->second)
newSet.erase(toRem);
}
elem.second = newSet;
}*/
}
static void addUseStatements(SgStatement* currF, SgStatement* obj, vector<SgStatement*>& useStats,
const vector<SgStatement*>& funcContains)
{
for (auto& funcSt : funcContains)
{
if (currF == funcSt)
{
SgStatement* last = obj->lastNodeOfStmt();
for (SgStatement* st = obj->lexNext(); st != last; st = st->lexNext())
{
if (st->variant() == USE_STMT)
useStats.push_back(st);
else if (st->variant() == CONTAINS_STMT)
break;
}
break;
}
}
}
void fillUsedModulesInFunction(SgStatement* st, vector<SgStatement*>& useStats)
{
checkNull(st, convertFileName(__FILE__).c_str(), __LINE__);
int var = st->variant();
while (var != PROG_HEDR && var != PROC_HEDR && var != FUNC_HEDR)
{
st = st->controlParent();
checkNull(st, convertFileName(__FILE__).c_str(), __LINE__);
var = st->variant();
}
for (SgStatement* stat = st->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
if (stat->variant() == USE_STMT)
useStats.push_back(stat);
for (int i = 0; i < current_file->numberOfFunctions(); ++i)
{
vector<SgStatement*> funcContains;
findContainsFunctions(current_file->functions(i), funcContains);
addUseStatements(st, current_file->functions(i), useStats, funcContains);
}
vector<SgStatement*> modules;
findModulesInFile(st->getFile(), modules);
for (auto& module : modules)
{
vector<SgStatement*> funcContains;
findContainsFunctions(module, funcContains, true);
addUseStatements(st, module, useStats, funcContains);
}
}
static void findByUse(map<string, vector<pair<SgSymbol*, SgSymbol*>>>& modByUse, const string& varName,
const set<string>& locNames, vector<string>& altNames)
{
for (auto& elem : modByUse)
{
if (locNames.count(elem.first))
{
for (auto& byUse : elem.second)
{
SgSymbol* toCmp = byUse.second ? byUse.second : byUse.first;
checkNull(toCmp, convertFileName(__FILE__).c_str(), __LINE__);
if (toCmp->identifier() == varName)
altNames.push_back(byUse.first->identifier());
}
}
}
}
static void fillInfo(SgStatement* start,
set<string>& useMod,
map<string, vector<pair<SgSymbol*, SgSymbol*>>>& modByUse,
map<string, vector<pair<SgSymbol*, SgSymbol*>>>& modByUseOnly)
{
for (SgStatement* st = start; st != start->lastNodeOfStmt(); st = st->lexNext())
{
if (isSgExecutableStatement(st))
break;
if (st->variant() == CONTAINS_STMT)
break;
if (st != start && (st->variant() == PROC_HEDR || st->variant() == FUNC_HEDR))
break;
fillUseStatement(st, useMod, modByUse, modByUseOnly);
}
}
static SgStatement* findModWithName(const vector<SgStatement*>& modules, const string& name)
{
for (auto& elem : modules)
if (elem->variant() == MODULE_STMT)
if (elem->symbol()->identifier() == name)
return elem;
return NULL;
}
string getNameByUse(SgStatement* place, const string& varName, const string& locName)
{
int old_id = -1;
string oldFileName = "";
if (place->getFileId() != current_file_id)
{
old_id = current_file_id;
oldFileName = current_file->filename();
if (!place->switchToFile())
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
}
SgStatement* func = getFuncStat(place, { MODULE_STMT });
string returnVal = varName;
if (func != NULL)
{
map<string, set<string>> graphUse;
set<string> useMod;
map<string, vector<pair<SgSymbol*, SgSymbol*>>> modByUse;
map<string, vector<pair<SgSymbol*, SgSymbol*>>> modByUseOnly;
fillInfo(func, useMod, modByUse, modByUseOnly);
SgStatement* cp = func->controlParent();
if (isSgProgHedrStmt(cp) || cp->variant() == MODULE_STMT) // if function in contains region
fillInfo(cp, useMod, modByUse, modByUseOnly);
set<string> useModDone;
bool needRepeat = true;
vector<SgStatement*> modules;
findModulesInFile(func->getFile(), modules);
while (needRepeat)
{
needRepeat = false;
set<string> newUseMod;
for (auto& useM : useMod)
{
if (useModDone.find(useM) == useModDone.end())
{
auto modSt = findModWithName(modules, useM);
if (modSt == NULL || useM == "dvmh_template_mod")
continue;
checkNull(modSt, convertFileName(__FILE__).c_str(), __LINE__);
set<string> tmpUse;
fillInfo(modSt, tmpUse, modByUse, modByUseOnly);
useModDone.insert(useM);
for (auto& use : tmpUse)
{
newUseMod.insert(use);
if (use != "dvmh_template_mod")
graphUse[use].insert(useM);
}
}
}
for (auto& newU : newUseMod)
{
if (useModDone.find(newU) == useModDone.end())
{
useModDone.insert(newU);
needRepeat = true;
}
}
}
vector<string> altNames;
findByUse(modByUse, varName, { locName }, altNames);
findByUse(modByUseOnly, varName, { locName }, altNames);
if (altNames.size() == 0)
{
set<string> locations = { locName };
bool changed = true;
while (changed)
{
changed = false;
for (auto& loc : locations)
{
if (graphUse.find(loc) != graphUse.end())
{
for (auto& use : graphUse[loc])
{
if (locations.find(use) == locations.end())
{
locations.insert(use);
changed = true;
}
}
}
}
}
findByUse(modByUse, varName, locations, altNames);
findByUse(modByUseOnly, varName, locations, altNames);
}
if (altNames.size() == 0)
returnVal = varName;
else if (altNames.size() >= 1)
{
set<string> setAlt(altNames.begin(), altNames.end());
returnVal = *setAlt.begin();
}
else
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
}
if (old_id != -1)
{
if (SgFile::switchToFile(oldFileName) == -1)
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
}
return returnVal;
}
void fixUseOnlyStmt(SgFile *file, const vector<ParallelRegion*> &regs)
{
for (int z = 0; z < file->numberOfFunctions(); ++z)
{
vector<SgStatement*> modules;
findModulesInFile(file, modules);
map<string, SgStatement*> mod;
for (auto &elem : modules)
mod[elem->symbol()->identifier()] = elem;
if (modules.size())
{
SgStatement *func = file->functions(z);
bool hasTemplateUse = false;
set<DIST::Array*> needToAdd;
for (auto st = func; st != func->lastNodeOfStmt(); st = st->lexNext())
{
if (isSgExecutableStatement(st))
break;
if (st->variant() == USE_STMT)
{
SgExpression *ex = st->expr(0);
string modName = st->symbol()->identifier();
auto it = mod.find(modName);
if (modName == "dvmh_Template_Mod")
{
hasTemplateUse = true;
break;
}
if (ex && ex->variant() == ONLY_NODE && it != mod.end())
{
set<string> allS;
for (auto exI = ex->lhs(); exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
if (exI->lhs()->lhs()->symbol())
allS.insert(exI->lhs()->lhs()->symbol()->identifier());
if (exI->lhs()->rhs() && exI->lhs()->rhs()->symbol())
allS.insert(exI->lhs()->rhs()->symbol()->identifier());
}
}
for (auto &parReg : regs)
{
const DataDirective &dataDir = parReg->GetDataDir();
for (auto &rule : dataDir.distrRules)
{
DIST::Array *curr = rule.first;
auto location = curr->GetLocation();
if (location.first == 2 && location.second == modName)
needToAdd.insert(curr);
}
for (auto& rule : dataDir.alignRules)
{
DIST::Array* curr = rule.alignArray;
auto location = curr->GetLocation();
if (location.first == 2 && location.second == modName)
needToAdd.insert(curr);
}
}
}
}
}
if (!hasTemplateUse && needToAdd.size())
{
SgStatement* useSt = new SgStatement(USE_STMT);
useSt->setSymbol(*findSymbolOrCreate(file, "dvmh_Template_Mod"));
useSt->setlineNumber(getNextNegativeLineNumber());
func->insertStmtAfter(*useSt, *func);
}
}
}
}
void fillUseStatement(SgStatement *st, set<string> &useMod,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUse,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUseOnly)
{
if (st->variant() == USE_STMT)
{
SgExpression *ex = st->expr(0);
string modName = st->symbol()->identifier();
convertToLower(modName);
useMod.insert(modName);
if (ex)
{
SgExpression *start = ex;
bool only = false;
if (ex->variant() == ONLY_NODE)
{
start = ex->lhs();
only = true;
}
for (auto exI = start; exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgSymbol *left = NULL, *right = NULL;
if (exI->lhs()->lhs()->symbol())
left = exI->lhs()->lhs()->symbol();
if (exI->lhs()->rhs() && exI->lhs()->rhs()->symbol())
right = exI->lhs()->rhs()->symbol();
if (only)
modByUseOnly[modName].push_back(std::make_pair(left, right));
else
modByUse[modName].push_back(std::make_pair(left, right));
}
}
}
}
}
static void fillUseStmt(SgStatement* stat, map<string, set<SgSymbol*>>& byUse)
{
if (stat->variant() != USE_STMT)
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
SgExpression* ex = stat->expr(0);
if (ex && ex->variant() == ONLY_NODE)
{
for (auto exI = ex->lhs(); exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgExpression* ren = exI->lhs();
if (ren->lhs()->symbol() && ren->rhs() && ren->rhs()->symbol())
byUse[ren->rhs()->symbol()->identifier()].insert(ren->lhs()->symbol());
}
}
}
else if (ex && ex->lhs())
{
for (auto exI = ex; exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgExpression* ren = exI->lhs();
if (ren->lhs()->symbol() && ren->rhs() && ren->rhs()->symbol())
byUse[ren->rhs()->symbol()->identifier()].insert(ren->lhs()->symbol());
}
}
}
}
map<string, set<SgSymbol*>> moduleRefsByUseInFunction(SgStatement* stIn)
{
checkNull(stIn, convertFileName(__FILE__).c_str(), __LINE__);
map<string, set<SgSymbol*>> byUse;
int var = stIn->variant();
while (var != PROG_HEDR && var != PROC_HEDR && var != FUNC_HEDR)
{
stIn = stIn->controlParent();
if (stIn == NULL)
return byUse;
var = stIn->variant();
}
auto mapOfUses = createMapOfModuleUses(stIn->getFile());
set<string> useMods;
for (SgStatement* stat = stIn->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
{
if (stat->variant() == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
}
const int cpOfSt = stIn->controlParent()->variant();
//contains of func
if (cpOfSt == PROG_HEDR || cpOfSt == PROC_HEDR || cpOfSt == FUNC_HEDR)
{
for (SgStatement* stat = stIn->controlParent()->lexNext(); !isSgExecutableStatement(stat); stat = stat->lexNext())
{
if (stat->variant() == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
}
}
bool chages = true;
while (chages)
{
chages = false;
set<string> newUseMods(useMods);
for (auto& elem : useMods)
{
auto it = mapOfUses.find(elem);
if (it != mapOfUses.end())
{
for (auto& elem2 : it->second)
{
if (newUseMods.find(elem2) == newUseMods.end())
{
newUseMods.insert(elem2);
chages = true;
}
}
}
}
useMods = newUseMods;
}
vector<SgStatement*> modules;
findModulesInFile(stIn->getFile(), modules);
for (auto& mod : modules)
{
if (useMods.find(mod->symbol()->identifier()) != useMods.end())
{
for (SgStatement* stat = mod->lexNext(); stat != mod->lastNodeOfStmt(); stat = stat->lexNext())
{
const int var = stat->variant();
if (var == USE_STMT)
{
fillUseStmt(stat, byUse);
useMods.insert(stat->symbol()->identifier());
}
else if (var == PROC_HEDR || var == FUNC_HEDR)
break;
}
}
}
return byUse;
}

View File

@@ -1,3 +1,3 @@
#pragma once
#define VERSION_SPF "2388"
#define VERSION_SPF "2389"

View File

@@ -60,128 +60,6 @@ void VarDeclCorrecter(SgFile *file)
}
}
void fixUseOnlyStmt(SgFile *file, const vector<ParallelRegion*> &regs)
{
for (int z = 0; z < file->numberOfFunctions(); ++z)
{
vector<SgStatement*> modules;
findModulesInFile(file, modules);
map<string, SgStatement*> mod;
for (auto &elem : modules)
mod[elem->symbol()->identifier()] = elem;
if (modules.size())
{
SgStatement *func = file->functions(z);
bool hasTemplateUse = false;
set<DIST::Array*> needToAdd;
for (auto st = func; st != func->lastNodeOfStmt(); st = st->lexNext())
{
if (isSgExecutableStatement(st))
break;
if (st->variant() == USE_STMT)
{
SgExpression *ex = st->expr(0);
string modName = st->symbol()->identifier();
auto it = mod.find(modName);
if (modName == "dvmh_Template_Mod")
{
hasTemplateUse = true;
break;
}
if (ex && ex->variant() == ONLY_NODE && it != mod.end())
{
set<string> allS;
for (auto exI = ex->lhs(); exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
if (exI->lhs()->lhs()->symbol())
allS.insert(exI->lhs()->lhs()->symbol()->identifier());
if (exI->lhs()->rhs() && exI->lhs()->rhs()->symbol())
allS.insert(exI->lhs()->rhs()->symbol()->identifier());
}
}
for (auto &parReg : regs)
{
const DataDirective &dataDir = parReg->GetDataDir();
for (auto &rule : dataDir.distrRules)
{
DIST::Array *curr = rule.first;
auto location = curr->GetLocation();
if (location.first == 2 && location.second == modName)
needToAdd.insert(curr);
}
for (auto& rule : dataDir.alignRules)
{
DIST::Array* curr = rule.alignArray;
auto location = curr->GetLocation();
if (location.first == 2 && location.second == modName)
needToAdd.insert(curr);
}
}
}
}
}
if (!hasTemplateUse && needToAdd.size())
{
SgStatement* useSt = new SgStatement(USE_STMT);
useSt->setSymbol(*findSymbolOrCreate(file, "dvmh_Template_Mod"));
useSt->setlineNumber(getNextNegativeLineNumber());
func->insertStmtAfter(*useSt, *func);
}
}
}
}
void fillUseStatement(SgStatement *st, set<string> &useMod,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUse,
map<string, vector<pair<SgSymbol*, SgSymbol*>>> &modByUseOnly)
{
if (st->variant() == USE_STMT)
{
SgExpression *ex = st->expr(0);
string modName = st->symbol()->identifier();
convertToLower(modName);
useMod.insert(modName);
if (ex)
{
SgExpression *start = ex;
bool only = false;
if (ex->variant() == ONLY_NODE)
{
start = ex->lhs();
only = true;
}
for (auto exI = start; exI; exI = exI->rhs())
{
if (exI->lhs()->variant() == RENAME_NODE)
{
SgSymbol *left = NULL, *right = NULL;
if (exI->lhs()->lhs()->symbol())
left = exI->lhs()->lhs()->symbol();
if (exI->lhs()->rhs() && exI->lhs()->rhs()->symbol())
right = exI->lhs()->rhs()->symbol();
if (only)
modByUseOnly[modName].push_back(std::make_pair(left, right));
else
modByUse[modName].push_back(std::make_pair(left, right));
}
}
}
}
}
struct ModuleInfo
{
set<string> useMod;

View File

@@ -38,7 +38,6 @@ void resolveFunctionCalls(SgFile* file, const std::set<std::string>& toResolve,
bool checkAndMoveFormatOperators(SgFile* file, std::vector<Messages> &currMessage, bool withError = true);
int VerifyFile(SgFile *file);
void fixUseOnlyStmt(SgFile *file, const std::vector<ParallelRegion*> &regs);
void correctModuleProcNames(SgFile *file, const std::set<std::string>& globalF);
void correctModuleSymbols(SgFile *file);
void replaceStructuresToSimpleTypes(SgFile* file);
@@ -48,7 +47,6 @@ bool checkArgumentsDeclaration(SgProject *project, const std::map<std::string, s
void replaceDerivedAssigns(SgFile *file, SgStatement *stToCopy, SgStatement *insertB, const std::map<std::string, SgStatement*> &derivedTypesDecl);
bool isDerivedAssign(SgStatement *st);
std::map<std::string, SgStatement*> createDerivedTypeDeclMap(SgStatement *forS);
void fillUseStatement(SgStatement* st, std::set<std::string>& useMod, std::map<std::string, std::vector<std::pair<SgSymbol*, SgSymbol*>>>& modByUse, std::map<std::string, std::vector<std::pair<SgSymbol*, SgSymbol*>>>& modByUseOnly);
void removeExecutableFromModuleDeclaration(SgFile* current, const std::set<std::string>& filesInProj, std::vector<SgStatement*>& hiddenData);
bool needToReplaceInterfaceName(SgStatement* interf);