#pragma once #include "../GraphCall/graph_calls_func.h" #include "../GraphLoop/graph_loops_func.h" #include "../ExpressionTransform/expr_transform.h" #include "../ParallelizationRegions/ParRegions.h" #include "../Utils/SgUtils.h" #include "ReadWriteAnalyzer.h" #include "DvmhRegion.h" typedef std::set ArraySet; struct ReadWrite { ArraySet read; ArraySet write; }; typedef std::map UsageByLine; typedef std::map UsageByFile; class DvmhRegionInserter { // input data SgFile *file; std::map loopGraphMap; const std::vector loopGraph; const std::map allFunctions; const std::vector funcsForFile; bool isMpiProgram; ReadWriteAnalyzer& rw_analyzer; std::map> parallel_functions; std::set writesToArraysInParallelLoops; std::set usedArraysInParallelLoops; const std::map>& arrayLinksByFuncCalls; // operating data std::vector regions; // region directives void findEdgesForRegions(const std::vector&); bool hasLimitsToDvmhParallel(const LoopGraph*) const; void insertRegionDirectives(); // actual directives ArraySet symbs_to_arrs(std::set) const; ArraySet get_used_arrs(SgStatement* st, int usage_type) const; ArraySet get_used_arrs_for_block(SgStatement* st, int usage_type) const; SgStatement* processSt(SgStatement *st, const std::vector* regs); void insertActualDirective(SgStatement*, const ArraySet&, int, bool, const std::set* = NULL); void parFuncsInNode(LoopGraph *loop, bool isParallel); bool isLoopParallel(const LoopGraph *loop) const; std::vector getArrayList(Statement* start, Statement* end, bool left = false) const; ArraySet applyUseFilter(const ArraySet& block, const std::set& filter) const; ArraySet excludePrivates(const ArraySet& block) const; ArraySet excludeRemotes(const ArraySet& block, SgStatement* remoteDir) const; void insertForProcCall(SgStatement* st, bool& skipGetActualIfProcCall, bool& skipActualIfProcCall); public: explicit DvmhRegionInserter( SgFile* curFile, const std::vector& curLoopGraph, ReadWriteAnalyzer& rws, const std::map>& arrayLinksByFuncCalls, const std::map& allFunctions, const std::vector& funcsForFile, bool mpi_program ) : file(curFile), loopGraph(curLoopGraph), rw_analyzer(rws), arrayLinksByFuncCalls(arrayLinksByFuncCalls), allFunctions(allFunctions), funcsForFile(funcsForFile), isMpiProgram(mpi_program) { if (loopGraph.size()) createMapLoopGraph(loopGraph, loopGraphMap); } void insertDirectives(const std::vector* regs = NULL); void insertActualDirectives(const std::vector* regs); void updateParallelFunctions(const std::map>& loopGraphs); void createInterfaceBlockForParallelFunctions(bool onlyRoutine = true); void removePrivatesFromParallelLoops(); void addPrivatesToParallelLoops(); void addUsedArrays(std::set& arrays); void addUsedWriteArrays(std::set& arrays); void updateUsedArrays(const std::set& used, const std::set& usedForWrite) { ArraySet newSet = usedForWrite; for (auto& elem : usedForWrite) getRealArrayRefs(elem, elem, newSet, arrayLinksByFuncCalls); writesToArraysInParallelLoops = newSet; newSet = used; for (auto& elem : used) getRealArrayRefs(elem, elem, newSet, arrayLinksByFuncCalls); usedArraysInParallelLoops = newSet; } const std::set getParallelFunctions() const { std::set retVal; for (auto& elem : parallel_functions) retVal.insert(elem.first); return retVal; } static void createInterfaceBlockForOutCall(FuncInfo* func, FuncInfo* callFrom); static void createInterfaceBlockForOutCalls(FuncInfo* func); ~DvmhRegionInserter() { for (auto& reg : regions) delete reg; } }; int insertDvmhRegions(SgProject& project, int files, const std::vector& parallelRegions, std::map>& allFuncInfo, std::map> loopGraph, ReadWriteAnalyzer& rw_analyzer, std::map>& SPF_messages, const std::map> arrayLinksByFuncCalls);