diff options
-rw-r--r-- | polly/CMakeLists.txt | 4 | ||||
-rwxr-xr-x | polly/Makefile.config.in | 6 | ||||
-rw-r--r-- | polly/autoconf/configure.ac | 8 | ||||
-rw-r--r-- | polly/cmake/FindPluto.cmake | 19 | ||||
-rwxr-xr-x | polly/configure | 94 | ||||
-rwxr-xr-x | polly/include/polly/Config/config.h.cmake | 1 | ||||
-rw-r--r-- | polly/include/polly/Config/config.h.in | 3 | ||||
-rw-r--r-- | polly/include/polly/LinkAllPasses.h | 9 | ||||
-rwxr-xr-x | polly/lib/CMakeLists.txt | 9 | ||||
-rw-r--r-- | polly/lib/Pluto.cpp | 186 | ||||
-rw-r--r-- | polly/lib/RegisterPasses.cpp | 14 |
11 files changed, 349 insertions, 4 deletions
diff --git a/polly/CMakeLists.txt b/polly/CMakeLists.txt index 368c2ed3e32..37b8c18e06e 100644 --- a/polly/CMakeLists.txt +++ b/polly/CMakeLists.txt @@ -74,6 +74,7 @@ set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${POLLY_SOURCE_DIR}/cmake") FIND_PACKAGE(Cloog REQUIRED) FIND_PACKAGE(Isl REQUIRED) FIND_PACKAGE(Gmp REQUIRED) +FIND_PACKAGE(Pluto) FIND_PACKAGE(CUDA) option(POLLY_ENABLE_OPENSCOP "Enable Openscop library for scop import/export" ON) @@ -89,6 +90,9 @@ endif(POLLY_ENABLE_SCOPLIB) if (CLOOG_FOUND) INCLUDE_DIRECTORIES( ${CLOOG_INCLUDE_DIR} ) endif(CLOOG_FOUND) +if (PLUTO_FOUND) + INCLUDE_DIRECTORIES( ${PLUTO_INCLUDE_DIR} ) +endif(PLUTO_FOUND) INCLUDE_DIRECTORIES( ${ISL_INCLUDE_DIR} ) INCLUDE_DIRECTORIES( ${GMP_INCLUDE_DIR} ) diff --git a/polly/Makefile.config.in b/polly/Makefile.config.in index f0791c56d5c..44a2fb9b771 100755 --- a/polly/Makefile.config.in +++ b/polly/Makefile.config.in @@ -37,10 +37,10 @@ CUDALIB_FOUND := @cuda_found@ # Set include directroys POLLY_INC := @gmp_inc@ @isl_inc@ \ @cloog_inc@ @openscop_inc@ @scoplib_inc@ @cuda_inc@\ - -I$(POLLY_SRC_ROOT)/lib/JSON/include + @pluto_inc@ -I$(POLLY_SRC_ROOT)/lib/JSON/include POLLY_LD := @gmp_ld@ @isl_ld@ @cloog_ld@ @openscop_ld@ @scoplib_ld@ \ - @scoplib_rpath@ @cuda_ld@ + @scoplib_rpath@ @cuda_ld@ @pluto_ld@ POLLY_LIB := @gmp_lib@ @isl_lib@ @cloog_lib@ @openscop_lib@ @scoplib_lib@ \ - @cuda_lib@ + @cuda_lib@ @pluto_lib@ diff --git a/polly/autoconf/configure.ac b/polly/autoconf/configure.ac index a6d8084f295..778005585fe 100644 --- a/polly/autoconf/configure.ac +++ b/polly/autoconf/configure.ac @@ -93,6 +93,14 @@ CXXFLAGS=$saved_CXXFLAGS AS_IF([test "x$cloog_found" = "xyes"], [AC_DEFINE([CLOOG_FOUND],[1],[Define if cloog found])]) +dnl Check that we have libpluto. +saved_CXXFLAGS=$CXXFLAGS +CXXFLAGS="$CXXFLAGS $gmp_inc $isl_inc" +find_lib_and_headers([pluto], [pluto/libpluto.h], [pluto]) +CXXFLAGS=$saved_CXXFLAGS +AS_IF([test "x$pluto_found" = "xyes"], + [AC_DEFINE([PLUTO_FOUND],[1],[Define if pluto found])]) + dnl Check that we have openscop. find_lib_and_headers([openscop], [openscop/scop.h], [openscop]) AS_IF([test "x$openscop_found" = "xyes"], diff --git a/polly/cmake/FindPluto.cmake b/polly/cmake/FindPluto.cmake new file mode 100644 index 00000000000..78d8563b822 --- /dev/null +++ b/polly/cmake/FindPluto.cmake @@ -0,0 +1,19 @@ +FIND_PATH(PLUTO_INCLUDE_DIR pluto/libpluto.h) + +FIND_LIBRARY(PLUTO_LIBRARY NAMES pluto) + +IF (PLUTO_INCLUDE_DIR AND PLUTO_LIBRARY) + SET(PLUTO_FOUND TRUE) +ENDIF (PLUTO_INCLUDE_DIR AND PLUTO_LIBRARY) + + +IF (PLUTO_FOUND) + IF (NOT PLUTO_FIND_QUIETLY) + MESSAGE(STATUS "Found Pluto: ${PLUTO_LIBRARY}") + ENDIF (NOT PLUTO_FIND_QUIETLY) +ELSE (PLUTO_FOUND) + IF (PLUTO_FIND_REQUIRED) + MESSAGE(FATAL_ERROR "Could not find Pluto") + ENDIF (PLUTO_FIND_REQUIRED) +ENDIF (PLUTO_FOUND) + diff --git a/polly/configure b/polly/configure index 6b701f248d4..707f4da4e09 100755 --- a/polly/configure +++ b/polly/configure @@ -580,6 +580,10 @@ openscop_ld openscop_lib openscop_inc openscop_found +pluto_ld +pluto_lib +pluto_inc +pluto_found cloog_ld cloog_lib cloog_inc @@ -647,6 +651,7 @@ with_llvmobj with_gmp with_isl with_cloog +with_pluto with_openscop with_scoplib with_cuda @@ -1275,6 +1280,7 @@ Optional Packages: --with-gmp prefix of gmp --with-isl prefix of isl --with-cloog prefix of cloog + --with-pluto prefix of pluto --with-openscop prefix of openscop --with-scoplib prefix of scoplib --with-cuda prefix of cuda @@ -2730,6 +2736,94 @@ $as_echo "#define CLOOG_FOUND 1" >>confdefs.h fi +saved_CXXFLAGS=$CXXFLAGS +CXXFLAGS="$CXXFLAGS $gmp_inc $isl_inc" + + ac_ext=cpp +ac_cpp='$CXXCPP $CPPFLAGS' +ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_cxx_compiler_gnu + + OLD_CXXFLAGS=$CXXFLAGS; + OLD_LDFLAGS=$LDFLAGS; + OLD_LIBS=$LIBS; + + LIBS="$LIBS -lpluto"; + + # Get include path and lib path + +# Check whether --with-pluto was given. +if test "${with_pluto+set}" = set; then : + withval=$with_pluto; given_inc_path="$withval/include"; CXXFLAGS="-I$given_inc_path $CXXFLAGS"; + given_lib_path="$withval/lib"; LDFLAGS="-L$given_lib_path $LDFLAGS" +else + given_inc_path=inc_not_give_pluto; + given_lib_path=lib_not_give_pluto + +fi + + # Check for library and headers works + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pluto: pluto/libpluto.h in $given_inc_path, and libpluto in $given_lib_path" >&5 +$as_echo_n "checking for pluto: pluto/libpluto.h in $given_inc_path, and libpluto in $given_lib_path... " >&6; } + + # try to compile a file that includes a header of the library + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include <pluto/libpluto.h> +int +main () +{ +; + ; + return 0; +} +_ACEOF +if ac_fn_cxx_try_link "$LINENO"; then : + { $as_echo "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +$as_echo "ok" >&6; } + pluto_found="yes" + + if test "x$given_inc_path" != "xinc_not_give_pluto"; then : + pluto_inc="-I$given_inc_path" + +fi + pluto_lib="-lpluto" + + if test "x$given_lib_path" != "xlib_not_give_pluto"; then : + pluto_ld="-L$given_lib_path" + +fi +else + if test "x" = "xrequired"; then : + as_fn_error $? "pluto required but not found" "$LINENO" 5 +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +$as_echo "not found" >&6; } +fi + +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + # reset original CXXFLAGS + CXXFLAGS=$OLD_CXXFLAGS + LDFLAGS=$OLD_LDFLAGS; + LIBS=$OLD_LIBS + ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + +CXXFLAGS=$saved_CXXFLAGS +if test "x$pluto_found" = "xyes"; then : + +$as_echo "#define PLUTO_FOUND 1" >>confdefs.h + +fi + ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' diff --git a/polly/include/polly/Config/config.h.cmake b/polly/include/polly/Config/config.h.cmake index d972e4d6002..d78929f4f22 100755 --- a/polly/include/polly/Config/config.h.cmake +++ b/polly/include/polly/Config/config.h.cmake @@ -16,6 +16,7 @@ #cmakedefine CLOOG_FOUND #cmakedefine ISL_CODEGEN_FOUND #cmakedefine OPENSCOP_FOUND +#cmakedefine PLUTO_FOUND #cmakedefine SCOPLIB_FOUND #cmakedefine CUDALIB_FOUND diff --git a/polly/include/polly/Config/config.h.in b/polly/include/polly/Config/config.h.in index 076b900211b..4f6b49a1da5 100644 --- a/polly/include/polly/Config/config.h.in +++ b/polly/include/polly/Config/config.h.in @@ -33,5 +33,8 @@ /* Define to the version of this package. */ #undef PACKAGE_VERSION +/* Define if pluto found */ +#undef PLUTO_FOUND + /* Define if scoplib found */ #undef SCOPLIB_FOUND diff --git a/polly/include/polly/LinkAllPasses.h b/polly/include/polly/LinkAllPasses.h index cb725ac8ce7..935a5c330e8 100644 --- a/polly/include/polly/LinkAllPasses.h +++ b/polly/include/polly/LinkAllPasses.h @@ -45,6 +45,9 @@ namespace polly { Pass *createIndVarSimplifyPass(); Pass *createJSONExporterPass(); Pass *createJSONImporterPass(); +#ifdef PLUTO_FOUND + Pass *createPlutoOptimizerPass(); +#endif Pass *createRegionSimplifyPass(); Pass *createScopDetectionPass(); Pass *createScopInfoPass(); @@ -98,6 +101,9 @@ namespace { createRegionSimplifyPass(); createScopDetectionPass(); createScopInfoPass(); +#ifdef PLUTO_FOUND + createPlutoOptimizerPass(); +#endif createIslScheduleOptimizerPass(); createTempScopInfoPass(); @@ -126,6 +132,9 @@ namespace llvm { void initializeJSONExporterPass(llvm::PassRegistry&); void initializeJSONImporterPass(llvm::PassRegistry&); void initializeIslScheduleOptimizerPass(llvm::PassRegistry&); +#ifdef PLUTO_FOUND + void initializePlutoOptimizerPass(llvm::PassRegistry&); +#endif #ifdef SCOPLIB_FOUND void initializePoccPass(llvm::PassRegistry&); #endif diff --git a/polly/lib/CMakeLists.txt b/polly/lib/CMakeLists.txt index b7e0346a1c3..e79e791658f 100755 --- a/polly/lib/CMakeLists.txt +++ b/polly/lib/CMakeLists.txt @@ -11,6 +11,10 @@ if (SCOPLIB_FOUND) set(POLLY_SCOPLIB_FILES Pocc.cpp) endif (SCOPLIB_FOUND) +if (PLUTO_FOUND) + set(POLLY_PLUTO_FILES Pluto.cpp) +endif (PLUTO_FOUND) + set(LLVM_USED_LIBS PollyAnalysis PollyCodeGen @@ -30,6 +34,7 @@ add_polly_library(LLVMPolly RegisterPasses.cpp ScheduleOptimizer.cpp ${POLLY_SCOPLIB_FILES} + ${POLLY_PLUTO_FILES} ) add_dependencies(LLVMPolly @@ -44,3 +49,7 @@ set_target_properties(LLVMPolly PROPERTIES LINKER_LANGUAGE CXX PREFIX "") + +if (PLUTO_FOUND) + target_link_libraries(LLVMPolly ${PLUTO_LIBRARY}) +endif(PLUTO_FOUND) diff --git a/polly/lib/Pluto.cpp b/polly/lib/Pluto.cpp new file mode 100644 index 00000000000..5e78a54d292 --- /dev/null +++ b/polly/lib/Pluto.cpp @@ -0,0 +1,186 @@ +//===- Pluto.cpp - Calculate an optimized schedule ---------------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// Use libpluto to optimize the schedule. +// +//===----------------------------------------------------------------------===// + +#include "polly/Config/config.h" + +#ifdef PLUTO_FOUND +#include "polly/CodeGen/CodeGeneration.h" +#include "polly/Dependences.h" +#include "polly/LinkAllPasses.h" +#include "polly/ScopInfo.h" + +#define DEBUG_TYPE "polly-opt-pluto" +#include "llvm/Support/Debug.h" +#include "llvm/Support/CommandLine.h" + +#include "pluto/libpluto.h" +#include "isl/map.h" + + +using namespace llvm; +using namespace polly; + +static cl::opt<bool> +EnableTiling("polly-pluto-tile", + cl::desc("Enable tiling"), + cl::Hidden, cl::init(false)); + +namespace { +/// Convert an int into a string. +static std::string convertInt(int number) +{ + if (number == 0) + return "0"; + std::string temp = ""; + std::string returnvalue = ""; + while (number > 0) + { + temp += number % 10 + 48; + number /= 10; + } + for (unsigned i = 0; i < temp.length(); i++) + returnvalue+=temp[temp.length() - i - 1]; + return returnvalue; +} + + + class PlutoOptimizer : public ScopPass { + + public: + static char ID; + explicit PlutoOptimizer() : ScopPass(ID) {} + + virtual bool runOnScop(Scop &S); + void printScop(llvm::raw_ostream &OS) const; + void getAnalysisUsage(AnalysisUsage &AU) const; + static void extendScattering(Scop &S, unsigned NewDimensions); + }; +} + +char PlutoOptimizer::ID = 0; + +static int getSingleMap(__isl_take isl_map *map, void *user) { + isl_map **singleMap = (isl_map **) user; + *singleMap = map; + + return 0; +} + +void PlutoOptimizer::extendScattering(Scop &S, unsigned NewDimensions) { + for (Scop::iterator SI = S.begin(), SE = S.end(); SI != SE; ++SI) { + ScopStmt *Stmt = *SI; + unsigned OldDimensions = Stmt->getNumScattering(); + isl_space *Space; + isl_map *Map, *New; + + Space = isl_space_alloc(Stmt->getIslCtx(), 0, OldDimensions, NewDimensions); + Map = isl_map_universe(Space); + + for (unsigned i = 0; i < OldDimensions; i++) + Map = isl_map_equate(Map, isl_dim_in, i, isl_dim_out, i); + + for (unsigned i = OldDimensions; i < NewDimensions; i++) + Map = isl_map_fix_si(Map, isl_dim_out, i, 0); + + + Map = isl_map_align_params(Map, S.getParamSpace()); + New = isl_map_apply_range(Stmt->getScattering(), Map); + Stmt->setScattering(New); + } +} + +bool PlutoOptimizer::runOnScop(Scop &S) { + isl_union_set *Domain; + isl_union_map *Deps, *ToPlutoNames, *Schedule; + PlutoOptions *Options; + + Dependences *D = &getAnalysis<Dependences>(); + + int DependencesKinds = Dependences::TYPE_RAW | Dependences::TYPE_WAR + | Dependences::TYPE_WAW; + + Deps = D->getDependences(DependencesKinds); + Domain = S.getDomains(); + ToPlutoNames = isl_union_map_empty(S.getParamSpace()); + + int counter = 0; + for (Scop::iterator SI = S.begin(), SE = S.end(); SI != SE; ++SI) { + ScopStmt *Stmt = *SI; + std::string Name = "S_" + convertInt(counter); + isl_map *Identity = isl_map_identity(isl_space_map_from_domain_and_range( + Stmt->getDomainSpace(), Stmt->getDomainSpace())); + Identity = isl_map_set_tuple_name(Identity, isl_dim_out, Name.c_str()); + ToPlutoNames = isl_union_map_add_map(ToPlutoNames, Identity); + counter++; + } + + Deps = isl_union_map_apply_domain(Deps, isl_union_map_copy(ToPlutoNames)); + Deps = isl_union_map_apply_range(Deps, isl_union_map_copy(ToPlutoNames)); + Domain = isl_union_set_apply(Domain, isl_union_map_copy(ToPlutoNames)); + + Options = pluto_options_alloc(); + Options->fuse = 0; + Options->tile = EnableTiling; + + Schedule = pluto_schedule(Domain, Deps, Options); + pluto_options_free(Options); + + isl_union_set_free(Domain); + isl_union_map_free(Deps); + + Schedule = isl_union_map_apply_domain(Schedule, + isl_union_map_reverse(ToPlutoNames)); + + for (Scop::iterator SI = S.begin(), SE = S.end(); SI != SE; ++SI) { + ScopStmt *Stmt = *SI; + isl_set *Domain = Stmt->getDomain(); + isl_union_map *StmtBand; + StmtBand = isl_union_map_intersect_domain(isl_union_map_copy(Schedule), + isl_union_set_from_set(Domain)); + isl_map *StmtSchedule; + isl_union_map_foreach_map(StmtBand, getSingleMap, &StmtSchedule); + Stmt->setScattering(StmtSchedule); + isl_union_map_free(StmtBand); + } + + isl_union_map_free(Schedule); + + unsigned MaxScatDims = 0; + + for (Scop::iterator SI = S.begin(), SE = S.end(); SI != SE; ++SI) + MaxScatDims = std::max((*SI)->getNumScattering(), MaxScatDims); + + extendScattering(S, MaxScatDims); + return false; +} + +void PlutoOptimizer::printScop(raw_ostream &OS) const { +} + +void PlutoOptimizer::getAnalysisUsage(AnalysisUsage &AU) const { + ScopPass::getAnalysisUsage(AU); + AU.addRequired<Dependences>(); +} + +INITIALIZE_PASS_BEGIN(PlutoOptimizer, "polly-opt-pluto", + "Polly - Optimize schedule of SCoP (Pluto)", false, false) +INITIALIZE_PASS_DEPENDENCY(Dependences) +INITIALIZE_PASS_DEPENDENCY(ScopInfo) +INITIALIZE_PASS_END(PlutoOptimizer, "polly-opt-pluto", + "Polly - Optimize schedule of SCoP (Pluto)", false, false) + +Pass* polly::createPlutoOptimizerPass() { + return new PlutoOptimizer(); +} + +#endif // PLUTO_FOUND diff --git a/polly/lib/RegisterPasses.cpp b/polly/lib/RegisterPasses.cpp index 410700cc134..e54131897e0 100644 --- a/polly/lib/RegisterPasses.cpp +++ b/polly/lib/RegisterPasses.cpp @@ -48,6 +48,9 @@ enum OptimizerChoice { #ifdef SCOPLIB_FOUND OPTIMIZER_POCC, #endif +#ifdef PLUTO_FOUND + OPTIMIZER_PLUTO, +#endif OPTIMIZER_ISL }; @@ -56,6 +59,9 @@ Optimizer("polly-optimizer", cl::desc("Select the scheduling optimizer"), cl::values( clEnumValN(OPTIMIZER_NONE, "none", "No optimizer"), +#ifdef PLUTO_FOUND + clEnumValN(OPTIMIZER_PLUTO, "pluto", "The Pluto scheduling optimizer"), +#endif #ifdef SCOPLIB_FOUND clEnumValN(OPTIMIZER_POCC, "pocc", "The PoCC scheduling optimizer"), #endif @@ -220,11 +226,17 @@ static void registerPollyPasses(llvm::PassManagerBase &PM) { break; /* Do nothing */ #ifdef SCOPLIB_FOUND - case OPTIMIZER_POCC + case OPTIMIZER_POCC: PM.add(polly::createPoccPass()); break; #endif +#ifdef PLUTO_FOUND + case OPTIMIZER_PLUTO: + PM.add(polly::createPlutoOptimizerPass()); + break; +#endif + case OPTIMIZER_ISL: PM.add(polly::createIslScheduleOptimizerPass()); break; |