diff --git a/COPYING b/COPYING index ae7026c24d347f09623206d5007d6be123b89482..35f922bee40533d7b28dda5feae4080323d47440 100644 --- a/COPYING +++ b/COPYING @@ -1,35 +1,39 @@ Copyright holders: 2003--2010 Peter Bastian -2004--2012 Markus Blatt +2004--2013 Markus Blatt +2013 Andreas Buhr 2011--2013 Ansgar Burchardt 2004--2005 Adrian Burri -2006--2012 Andreas Dedner +2006--2013 Andreas Dedner 2003 Marc Droske -2003--2012 Christian Engwer +2003--2013 Christian Engwer 2004--2012 Jorrit Fahlke 2008--2013 Bernd Flemisch -2005--2012 Carsten Gräser -2010--2012 Christoph Grüninger +2013 Christoph Gersbacher +2005--2013 Carsten Gräser +2010--2013 Christoph Grüninger 2006 Bernhard Haasdonk 2012--2013 Olaf Ippisch -2012 Arne Morten Kvarving +2013 Dominic Kempf 2009 Leonard Kern -2005--2007 Sreejith Pulloor Kuttanikkad +2013 Torbjörn Klatt 2003--2013 Robert Klöfkorn +2005--2007 Sreejith Pulloor Kuttanikkad +2012--2013 Arne Morten Kvarving 2010--2013 Andreas Lauser 2007--2011 Sven Marnach -2012 Tobias Malkmus +2012--2013 Tobias Malkmus 2010 Rene Milk -2011--2012 Steffen Müthing +2011--2013 Steffen Müthing 2003--2006 Thimo Neubauer 2011 Rebecca Neumann -2008--2012 Martin Nolte +2008--2013 Martin Nolte 2004--2005 Mario Ohlberger 2008--2013 Elias Pipping 2011 Dan Popovic 2009 Atgeirr Rasmussen -2003--2012 Oliver Sander +2003--2013 Oliver Sander 2006--2011 Uli Sack 2006 Klaus Schneider 2004 Roland Schulz diff --git a/Makefile.am b/Makefile.am index 3281582d234b7c250a6a30ddda5531f176e50fad..82eb6bc75b86c4e4bc82c7dfabdd83e068cf3f5b 100644 --- a/Makefile.am +++ b/Makefile.am @@ -1,7 +1,7 @@ # $Id$ # we need the module file to be able to build via dunecontrol -EXTRA_DIST= CMakeLists.txt dune.module dune-common-config.cmake.in dune-common-version.cmake.in +EXTRA_DIST= CMakeLists.txt dune.module # don't follow the full GNU-standard # we need automake 1.9 or newer diff --git a/am/CMakeLists.txt b/am/CMakeLists.txt index 47e3e52d80ae9fa13dc209b0eae115220617c10b..71acd33ea6a1953aeb4e355408b7b930b2e86c77 100644 --- a/am/CMakeLists.txt +++ b/am/CMakeLists.txt @@ -10,5 +10,5 @@ install(PROGRAMS sourcescheck top-rules webstuff - DESTINATION ${CMAKE_INSTALL_DATADIR}/am + DESTINATION ${CMAKE_INSTALL_DATADIR}/dune-common/am ) diff --git a/am/Makefile.am b/am/Makefile.am index 4b80086c781444941aa377eca009a395ed6f66bb..5bcd5381401f3e692a5b16654fb9514a1efac7fe 100644 --- a/am/Makefile.am +++ b/am/Makefile.am @@ -1,10 +1,13 @@ # $Id$ -EXTRA_DIST = CMakeLists.txt inkscape.am webstuff global-rules sourcescheck \ +am_DATA = inkscape.am webstuff global-rules sourcescheck \ no-check-without-lib latex checklog doxygen top-rules \ headercheck documentation +# Not all file names seem to be treated equal by _DATA. +# inkscape.am no-check-without-lib have to be listed in +# EXTRA_DIST to be included into the tarball. +EXTRA_DIST = CMakeLists.txt inkscape.am no-check-without-lib amdir = $(datadir)/dune-common/am -am_DATA = $(EXTRA_DIST) include $(top_srcdir)/am/global-rules diff --git a/am/doxygen b/am/doxygen index 7e4a005fec32ed17a21ef380b3609b2e80ce2b0d..3630f3539f7f63a40517639580240d094e288f7b 100644 --- a/am/doxygen +++ b/am/doxygen @@ -47,14 +47,14 @@ $(srcdir)/Doxyfile.in: FORCE # build doxygen when 'make doc' is called # what files does the doxygen-generated stuff depend on (find-syntax) -DOXYGEN_DEPENDON = -name \*.cc -o -name \*.hh -o -name \*.png -o -name Doxyfile -o -name modules +DOXYGEN_DEPENDON = -name \*.cc -o -name \*.hh -o -name \*.png -o -name modules # check dependency ourself to be robust $(DOXYGENTAG): FORCE Doxyfile $(DOXYGENHEADER) $(DOXYGENFOOTER) set -e; \ DTAG=$(DOXYGENTAG); \ if test -f $(srcdir)/$(DOXYGENTAG); then DTAG=$(srcdir)/$(DOXYGENTAG); fi; \ if ! test -e "$$DTAG" || \ - test x"`find $(top_srcdir) \( $(DOXYGEN_DEPENDON) \) -a -cnewer $$DTAG -print`" != x; \ + test x"`find $(top_srcdir) \( $(DOXYGEN_DEPENDON) \) -a -newer $$DTAG -print | grep -v cmake/modules`" != x; \ then \ echo Running doxygen. This may take a while... ; \ $(DOXYGEN) Doxyfile > doxygen.log <&-; \ diff --git a/bin/CMakeLists.txt b/bin/CMakeLists.txt index 3213d8412da3601d11c452060d43c4d150b866b7..f0986faacf27541e636c3057de922272da1456bb 100644 --- a/bin/CMakeLists.txt +++ b/bin/CMakeLists.txt @@ -3,6 +3,7 @@ install(PROGRAMS dunedoxynize duneproject dunecontrol + git-whitespace-hook mpi-config dune-autogen DESTINATION ${CMAKE_INSTALL_BINDIR}) diff --git a/bin/Makefile.am b/bin/Makefile.am index e3bdcd124628318766a27ec03daf8ea915ce621c..521dafb03618348ddbd04958d928d276228e98eb 100644 --- a/bin/Makefile.am +++ b/bin/Makefile.am @@ -3,10 +3,12 @@ # put scripts into dist-tarball EXTRA_DIST = am2cmake.py CMakeLists.txt duneproject dunecontrol \ dunedoxynize \ + git-whitespace-hook \ mpi-config dune-autogen \ xfail-compile-tests # ... and install some -bin_SCRIPTS = dunedoxynize duneproject dunecontrol mpi-config dune-autogen +bin_SCRIPTS = am2cmake.py dunedoxynize duneproject dunecontrol mpi-config dune-autogen \ + git-whitespace-hook include $(top_srcdir)/am/global-rules diff --git a/bin/am2cmake.py b/bin/am2cmake.py index 80e34c12398138a12340e9626d82509d0ff2b168..094829f7fdd02dbb56040ba680eb7ec629de73b2 100755 --- a/bin/am2cmake.py +++ b/bin/am2cmake.py @@ -24,7 +24,8 @@ class rem_proc: " if(${i} STREQUAL \"test\")\n", " set(opt EXCLUDE_FROM_ALL)\n", " endif(${i} STREQUAL \"test\")\n", - " add_subdirectory(${i} ${opt})\n"+self.foreach_end()]) + " add_subdirectory(${i} ${opt})\n", + " unset(opt)\n"+self.foreach_end()]) def process(self): s="" @@ -729,8 +730,7 @@ def create_cmake_dirs_and_file(dirname, module_name): module_name.capitalize()) print 'module_name %s' % module_name print 'upper_name %s' % upper_name - dirs={'modules': os.path.join(dirname, 'cmake', 'modules'), - 'pkg': os.path.join(dirname, 'cmake', 'pkg')} + dirs={'modules': os.path.join(dirname, 'cmake', 'modules')} cdirs=[] for dir in dirs.values(): try: @@ -743,46 +743,6 @@ def create_cmake_dirs_and_file(dirname, module_name): output=open(os.path.join(dirs['modules'], upper_name+'Macros.cmake'), 'w') output.write(text) output.close() - lines=['if(NOT @DUNE_MOD_NAME@_FOUND)\n', - '#compute installation prefix relative to this file\n', - 'get_filename_component(_dir "${CMAKE_CURRENT_LIST_FILE}" PATH)\n', - 'get_filename_component(_prefix "${_dir}/../../.." ABSOLUTE)\n', - '\n', - '#import the target\n', - 'if(EXISTS "${_prefix}/lib/cmake/@DUNE_MOD_NAME@-targets.cmake")\n', - ' include("${_prefix}/lib/cmake/@DUNE_MOD_NAME@-targets.cmake")\n', - 'endif(EXISTS "${_prefix}/lib/cmake/@DUNE_MOD_NAME@-targets.cmake")\n', - '\n', - '#report other information\n', - 'set(@DUNE_MOD_NAME@_PREFIX "${_prefix}")\n', - 'set(@DUNE_MOD_NAME@_INCLUDE_DIRS "${_prefix}/include")\n', - 'set(@DUNE_MOD_NAME@_CXX_FLAGS "@CMAKE_CXX_FLAGS@")\n', - 'set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG "@CMAKE_CXX_FLAGS_DEBUG@")\n', - 'set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL "@CMAKE_CXX_FLAGS_MINSIZEREL@")\n', - 'set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE "@CMAKE_CXX_FLAGS_RELEASE@")\n', - 'set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO "@CMAKE_CXX_FLAGS_RELWITHDEBINFO@")\n', - 'set(@DUNE_MOD_NAME@_LIBRARIES "")\n', - 'set(@DUNE_MOD_NAME@_DEPENDS "@DUNE_DEPENDS@")\n', - 'set(@DUNE_MOD_NAME@_SUGGESTS "@DUNE_SUGGESTS@")\n', - 'set(@DUNE_MOD_NAME@_MODULE_PATH "\${_prefix}/@DUNE_INSTALL_MODULEDIR@")\n', - 'endif(NOT @DUNE_MOD_NAME@_FOUND)\n'] - text = ''.join(lines) - output=open(os.path.join(dirs['pkg'], module_name+'-config.cmake.in'), 'w') - output.write(text) - output.close() - l=[lines[0]] - l.extend([lines[5], - 'if(EXISTS "@CMAKE_BINARY_DIR@/@DUNE_MOD_NAME@-targets.cmake")\n' - ' include("@CMAKE_BINARY_DIR@/@DUNE_MOD_NAME@-targets.cmake")\n', - 'endif(EXISTS "@CMAKE_BINARY_DIR@/@DUNE_MOD_NAME@-targets.cmake")\n\n', - '#report other information\n', - 'set(@DUNE_MOD_NAME@_PREFIX "@CMAKE_SOURCE_DIR@")\n', - 'set(@DUNE_MOD_NAME@_INCLUDE_DIRS "@CMAKE_SOURCE_DIR@")\n']) - l.extend(lines[13:]) - l[-2]='set(@DUNE_MOD_NAME@_MODULE_PATH "@CMAKE_SOURCE_DIR@/cmake/modules")\n' - output=open(os.path.join(dirname, module_name+'-config.cmake.in'), 'w') - output.write(''.join(l)) - output.close() # CMakeLists.txt in module directory # list files *.cmake all_cmake_files=[] @@ -793,16 +753,6 @@ def create_cmake_dirs_and_file(dirname, module_name): lines.extend(['install(FILES "${modules}" DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/cmake/modules)\n']) output.write(''.join(lines)) output.close() - output=open(os.path.join(dirname, module_name+'-version.cmake.in'), 'w') - lines=['set(PACKAGE_VERSION "@DUNE_MOD_VERSION@")\n\n', - 'if(NOT "${PACKAGE_FIND_VERSION}" VERSION_GREATER "@DUNE_MOD_VERSION@")\n', - ' set (PACKAGE_VERSION_COMPATIBLE 1) # compatible with older\n', - ' if ("${PACKAGE_FIND_VERSION}" VERSION_EQUAL "@DUNE_MOD_VERSION@")\n' - ' set(PACKAGE_VERSION_EXACT 1) #exact match for this version\n', - ' endif()\n', - 'endif()\n'] - output.write(''.join(lines)) - output.close() def am_2_cmake(amfile, cmakefile, module_root=False): diff --git a/bin/dune-autogen b/bin/dune-autogen index 84e19d83ec3c68fc00a32ea14ffa24936cbc807a..40772eefbe439418cbf0bc3739c2a1eab91c57ab 100755 --- a/bin/dune-autogen +++ b/bin/dune-autogen @@ -68,6 +68,9 @@ for OPT in "$@"; do echo "Found am directory $OPT/am" am_dir="$OPT/am" fi + if test -d "$OPT/share/dune/aclocal"; then + ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $OPT/share/dune/aclocal" + fi if test -d "$OPT/share/aclocal"; then ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $OPT/share/aclocal" fi diff --git a/bin/dunecontrol b/bin/dunecontrol index 49fa6526c49c83374129c549765c5cb8f7c5f2a7..9d8fe614c6c4129a74967f94ef0003abe2603aa6 100755 --- a/bin/dunecontrol +++ b/bin/dunecontrol @@ -78,17 +78,6 @@ if test "x$DEBUG" = "xyes"; then set -v fi -export PREFIX_DIR="`canonicalpath "$0"`/.." - -# create PKG_CONFIG_PATH for installed dune modules -if test -d "$PREFIX_DIR/lib/pkgconfig"; then - export PKG_CONFIG_PATH="$PKG_CONFIG_PATH:$PREFIX_DIR/lib/pkgconfig" -fi - -# Read the modules find part -. "$PREFIX_DIR/lib/dunemodules.lib" - -############################################### onbuildfailure() { echo "Terminating $(basename "$0") due to previous errors!" >&2 @@ -161,7 +150,7 @@ build_module() { load_opts() { local command=$1 local COMMAND=$(echo $command | tr '[:lower:]' '[:upper:]') - CMD_FLAGS="$(eval echo \$${COMMAND}_FLAGS)" + CMD_FLAGS=$(eval echo \$${COMMAND}_FLAGS) local CMD_FLAGS_FROM_FILE="" if test "$command" = "NONE"; then BUILDDIR=$DUNE_BUILDDIR @@ -218,6 +207,65 @@ load_opts() { fi } +space=" " +tab=" " +BLANK="$space$tab" +NOBLANK="^$space^$tab" + +if test -z $GREP; then + GREP=grep +fi +# Uses the current compiler to extract information about the +# multiarch triplets and sets the export variable MULTIARCH_LIBDIR +# according to it. +# If not compiler is specified then cc or gcc is used. +extract_multiarch(){ + local my_cxx_compiler + if test "x$MULTIARCH_LIBDIR" != "x"; then + return + fi + if test "x$USE_CMAKE" = "xyes"; then + load_opts "cmake" + my_cxx_compiler=`echo $CMAKE_FLAGS | $GREP CXX | sed "s/.*CXX=[\"']\?\([$NOBLANK^'^\"]*\)[\"']\?.*/\1/"` + fi + if test "x$my_cxx_compiler" == "x"; then + load_opts "configure" + my_cxx_compiler=`echo $CONFIGURE_FLAGS | $GREP CXX| sed "s/.*CXX=[\"']\?\([$NOBLANK^'^\"]*\)[\"']\?.*/\1/"` + fi + if test "x$my_cxx_compiler" == "x"; then + set +e #error in the multiarch detection should not be fatal. + $(which cc &>/dev/null) + if test $? -eq "0"; then + my_cxx_compiler=cc + else + my_cxx_compiler=gcc + fi + fi + multiarch=$($my_cxx_compiler --print-multiarch 2>/dev/null) + if test $? -gt 0; then + multiarch=$($my_cxx_compiler -v 2>&1| $GREP target | sed "s/.*target=\([a-z0-9_-]\+\)/\1/") + fi + set -e # set to old value. + export MULTIARCH_LIBDIR="lib/$multiarch" +} + +export PREFIX_DIR="`canonicalpath "$0"`/.." + +extract_multiarch + +# create PKG_CONFIG_PATH for installed dune modules +for i in $MULTIARCH_LIBDIR lib64 lib32 lib; do + if test -d "$PREFIX_DIR/$i/pkgconfig"; then + export PKG_CONFIG_PATH="$PKG_CONFIG_PATH:$PREFIX_DIR/$i/pkgconfig" + fi +done + +# Read the modules find part +. "$PREFIX_DIR/lib/dunemodules.lib" + +############################################### + + ############################################### ### ### Commands @@ -326,7 +374,7 @@ run_default_status () { fi if test $verbose -eq 1; then - test "$is_svn" && svn status $update | grep -E "^M|^A|^D|^C|^U" + test "$is_svn" && svn status $update | $GREP -E "^M|^A|^D|^C|^U" test "$is_git" && git status -uno elif test $verbose -eq 2; then test "$is_svn" && svn status $update @@ -335,14 +383,14 @@ run_default_status () { if test "$is_svn" ; then - changed=$(svn status | grep -E "^M|^A|^D" | wc -l) - collisions=$(svn status | grep -E "^C"| wc -l) - pending=$(svn status $update | grep -E "^...... \* " | wc -l) + changed=$(svn status | $GREP -E "^M|^A|^D" | wc -l) + collisions=$(svn status | $GREP -E "^C"| wc -l) + pending=$(svn status $update | $GREP -E "^...... \* " | wc -l) fi if test "$is_git" ; then - changed=$(git status --porcelain | grep -E "^ *M|^ *A|^ *D|^ *R|^ *C" | wc -l) - collisions=$(git status --porcelain | grep -E "^ *U"| wc -l) - pending=$(git status | grep -E "^\# Your branch is ahead |^\# Your branch is behind " | wc -l) + changed=$(git status --porcelain | $GREP -E "^ *M|^ *A|^ *D|^ *R|^ *C" | wc -l) + collisions=$(git status --porcelain | $GREP -E "^ *U"| wc -l) + pending=$(git status | $GREP -E "^\# Your branch is ahead |^\# Your branch is behind " | wc -l) fi color=$green text="no changes" @@ -535,8 +583,8 @@ run_default_autogen () { local M4_PATH="" if test -f configure.ac && \ ( test -d .svn || test -d .git || test -d CVS || test -f stamp-vc ); then - sort_modules $FOUND_MODULES - for m in $FOUND_MODULES; do + sort_modules $MODULES + for m in $MODULES; do path="$(eval "echo \$PATH_$m")" MODULE_PATHS="$MODULE_PATHS\"$path\" " done @@ -555,6 +603,7 @@ run_default_autogen () { } run_default_configure () { + extract_multiarch PARAMS="$CMD_FLAGS" if test "x$USE_CMAKE" = "xyes" && test -e "$(eval "echo \$PATH_$module")/CMakeLists.txt"; then LOCAL_USE_CMAKE=yes @@ -581,12 +630,11 @@ run_default_configure () { fi if test x$module = x$m; then continue; fi # skip myself name=$(eval "echo \$NAME_$m") - if test -d "$path/m4"; then - ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $path/m4" - fi - if test -d "$path/share/aclocal"; then - ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $path/share/aclocal" - fi + for dir in $path/m4 $path/share/dune/aclocal $path/share/aclocal; do + if test -d "$dir"; then + ACLOCAL_FLAGS="$ACLOCAL_FLAGS -I $dir" + fi + done if test -d "$path/$BUILDDIR"; then PARAMS="$PARAMS \"--with-$name=$path/$BUILDDIR\"" else @@ -596,11 +644,14 @@ run_default_configure () { if test -d "$path/$BUILDDIR"; then CMAKE_PARAMS="$CMAKE_PARAMS \"-D""$name""_DIR=$path/$BUILDDIR\"" else - if test -d "$path/lib/cmake/$name"; then - CMAKE_PARAMS="$CMAKE_PARAMS \"-D""$name""_DIR=$path/lib/cmake/$name\"" - else - CMAKE_PARAMS="$CMAKE_PARAMS \"-D""$name""_DIR=$path\"" - fi + TMP_PARAMS="\"-D""$name""_DIR=$path\"" + for i in $MULTIARCH_LIBDIR lib lib64 lib32; do + if test -d "$path/$i/cmake/$name"; then + TMP_PARAMS="\"-D""$name""_DIR=$path/$i/cmake/$name\"" + break; + fi + done + CMAKE_PARAMS="$CMAKE_PARAMS $TMP_PARAMS" fi fi done @@ -614,8 +665,8 @@ run_default_configure () { # such that they are honored by cmake. flags="CXX CC CXXFLAGS CFLAGS CPPFLAGS LDFLAGS F77 FFLAGS FLIBS FC FCFLAGS FCLIBS LIBS" for i in $flags; do - cflags=`echo "$PARAMS" | sed "s/.*\($i=\"[^\"]*\"\|$i='[^']*'\|$i=[^\s^ ]*\).*/\1/"` - if test "$cflags" != "$PARAMS"; then + cflags=`echo "$PARAMS" | $GREP $i= | sed "s/.*\($i=\"[^\"]\+\"\|$i='[^']\+'\|$i=[$NOBLANK]\+\).*/\1/"` + if test -n "$cflags" ; then PREPARAMS="$PREPARAMS $cflags" fi done @@ -1136,7 +1187,7 @@ EOF *) set +e if test "x$USE_CMAKE" = "xno"; then - echo "$PREFIX_DIR" |grep "[ ]" >/dev/null + echo "$PREFIX_DIR" |$GREP "[ ]" >/dev/null if test "$?" -eq "0"; then echo "ERROR: The prefix directory path ($PREFIX_DIR) contains spaces. This is not" echo " supported when using autotools." diff --git a/bin/duneproject b/bin/duneproject index 5f73aab819e81c660d0c64a2845df4c841ee0bae..2a00c842289dc0fd768d4dac06e90030ce775b12 100755 --- a/bin/duneproject +++ b/bin/duneproject @@ -445,9 +445,7 @@ cat> "$PROJECT/Makefile.am" << M_DELIM # we need the module file to be able to build via dunecontrol EXTRA_DIST = dune.module \\ CMakeLists.txt \\ - config.h.cmake \\ - $PROJECT-config.cmake.in \\ - $PROJECT-version.cmake.in + config.h.cmake SUBDIRS = src m4 dune doc cmake @@ -481,9 +479,9 @@ if(NOT (dune-common_DIR OR dune-common_ROOT OR endif() #find dune-common and set the module path -find_package(dune-common) -list(APPEND CMAKE_MODULE_PATH \${dune-common_MODULE_PATH} - "\${PROJECT_SOURCE_DIR}/cmake/modules") +find_package(dune-common REQUIRED) +list(APPEND CMAKE_MODULE_PATH "\${PROJECT_SOURCE_DIR}/cmake/modules" + \${dune-common_MODULE_PATH}) #include the dune macros include(DuneMacros) @@ -578,28 +576,6 @@ cat> "$PROJECT/config.h.cmake" <<EOF EOF ## done -################# $PROJECT-config.cmake.in ##################### - -echo "- $PROJECT/$PROJECT""-config.cmake.in" -cat> "$PROJECT/$PROJECT""-config.cmake.in" <<EOF -if(NOT @DUNE_MOD_NAME@_FOUND) -#import the target -#include("@CMAKE_BINARY_DIR@/@DUNE_MOD_NAME@-targets.cmake") - -#report other information -set(@DUNE_MOD_NAME@_PREFIX "@CMAKE_SOURCE_DIR@") -set(@DUNE_MOD_NAME@_INCLUDE_DIRS "@CMAKE_SOURCE_DIR@") -set(@DUNE_MOD_NAME@_CXX_FLAGS "@CMAKE_CXX_FLAGS@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG "@CMAKE_CXX_FLAGS_DEBUG@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL "@CMAKE_CXX_FLAGS_MINSIZEREL@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE "@CMAKE_CXX_FLAGS_RELEASE@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO "@CMAKE_CXX_FLAGS_RELWITHDEBINFO@") -set(@DUNE_MOD_NAME@_LIBRARIES "") # list exported libraries here -set(@DUNE_MOD_NAME@_DEPENDS "@DUNE_DEPENDS@") -set(@DUNE_MOD_NAME@_SUGGESTS "@DUNE_SUGGESTS@") -endif(NOT @DUNE_MOD_NAME@_FOUND) -EOF - ############################################################### ################## The source subdirectory #################### ############################################################### @@ -704,7 +680,7 @@ echo "- $PROJECT/m4/Makefile.am" cat> "$PROJECT/m4/Makefile.am" << CC_DELIM M4FILES = $MODULE.m4 -aclocaldir = \$(datadir)/aclocal +aclocaldir = \$(datadir)/dune/aclocal aclocal_DATA = \$(M4FILES) EXTRA_DIST = \$(M4FILES) CMakeLists.txt @@ -716,7 +692,7 @@ CC_DELIM echo "- $PROJECT/m4/CMakeLists.txt" cat> "$PROJECT/m4/CMakeLists.txt" << CC_DELIM -install(PROGRAMS $MODULE.m4 DESTINATION share/aclocal) +install(PROGRAMS $MODULE.m4 DESTINATION share/dune/aclocal) CC_DELIM @@ -905,7 +881,6 @@ CC_DELIM ######################################################### mkdir "$PROJECT/cmake" -mkdir "$PROJECT/cmake/pkg" ################# cmake/Makefile.am ##################### @@ -916,55 +891,6 @@ SUBDIRS = pkg include \$(top_srcdir)/am/global-rules EOF -################# cmake/pkg/Makefile.am ##################### - -echo "- $PROJECT/cmake/pkg/Makefile.am" -cat> "$PROJECT/cmake/pkg/Makefile.am" <<EOF -EXTRA_DIST = $PROJECT-config.cmake.in - -include \$(top_srcdir)/am/global-rules -EOF - -################# cmake/pkg/$PROJECT-config.cmake.in ##################### - -echo "- $PROJECT/cmake/pkg/$PROJECT""-config.cmake.in" -cat> "$PROJECT/cmake/pkg/$PROJECT""-config.cmake.in" <<EOF -if(NOT @DUNE_MOD_NAME@_FOUND) -#compute installation prefix relative to this file -get_filename_component(_dir "\${CMAKE_CURRENT_LIST_FILE}" PATH) -get_filename_component(_prefix "\${_dir}/../../.." ABSOLUTE) - -#import the target -#include("\${_prefix}/lib/cmake/@DUNE_MOD_NAME@-targets.cmake") - -#report other information -set(@DUNE_MOD_NAME@_INCLUDE_DIRS "\${_prefix}/include") -set(@DUNE_MOD_NAME@_CXX_FLAGS "@CMAKE_CXX_FLAGS@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG "@CMAKE_CXX_FLAGS_DEBUG@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL "@CMAKE_CXX_FLAGS_MINSIZEREL@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE "@CMAKE_CXX_FLAGS_RELEASE@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO "@CMAKE_CXX_FLAGS_RELWITHDEBINFO@") -set(@DUNE_MOD_NAME@_MODULE_PATH "\${_prefix}/@DUNE_INSTALL_MODULEDIR@") -set(@DUNE_MOD_NAME@_LIBRARIES "") # list libraries -set(@DUNE_MOD_NAME@_DEPENDS "@DUNE_DEPENDS@") -set(@DUNE_MOD_NAME@_SUGGESTS "@DUNE_SUGGESTS@") -endif(NOT @DUNE_MOD_NAME@_FOUND) -EOF - -################# $PROJECT-version.cmake.in ##################### - -echo "- $PROJECT/$PROJECT""-version.cmake.in" -cat> "$PROJECT/$PROJECT""-version.cmake.in" <<EOF -set(PACKAGE_VERSION "@DUNE_MOD_VERSION@") - -if(NOT "\${PACKAGE_FIND_VERSION}" VERSION_GREATER "@DUNE_MOD_VERSION@") - set (PACKAGE_VERSION_COMPATIBLE 1) # compatible with older - if ("\${PACKAGE_FIND_VERSION}" VERSION_EQUAL "@DUNE_MOD_VERSION@") - set(PACKAGE_VERSION_EXACT 1) #exact match for this version - endif() -endif() -EOF - ################# stamp-regenerate-config-h ##################### echo "- $PROJECT/stamp-regenerate-config-h" diff --git a/cmake/modules/CMakeLists.txt b/cmake/modules/CMakeLists.txt index 3dcce83eb9adf3819be100c5c04822f8ac9aa7e8..cfae2981b6048fcba34f69108bde166c1426ea00 100644 --- a/cmake/modules/CMakeLists.txt +++ b/cmake/modules/CMakeLists.txt @@ -6,6 +6,7 @@ set(modules CheckCXX11Features.cmake CheckSharedPtr.cmake DuneBoost.cmake + DuneCMakePackageConfigHelpers.cmake DuneCommonMacros.cmake DuneCxaDemangle.cmake DuneDoc.cmake diff --git a/cmake/modules/DuneCMakePackageConfigHelpers.cmake b/cmake/modules/DuneCMakePackageConfigHelpers.cmake new file mode 100644 index 0000000000000000000000000000000000000000..330babc6f4b3b93aef9bdc0818429c5ba9fc2caa --- /dev/null +++ b/cmake/modules/DuneCMakePackageConfigHelpers.cmake @@ -0,0 +1,39 @@ +# +# A poor mans version of CMakePackageConfigHelpers.cmake for as a substitute +# for old Cmake versions. +# +# Provides the function +# configure_package_config_file infile outfile INSTALL_DESTINATION relative_install_path +# [PATH_VARS relative_path_varname1 ...]) +# +# all paths are assumed to be relative! +# +find_file(CMakePkgConfigHelpersMacroFile CMakePackageConfigHelpers.cmake PATHS ${CMAKE_ROOT}/Modules ${CMAKE_MODULE_PATH}) + +if(CMakePkgConfigHelpersMacroFile) + include(CMakePackageConfigHelpers) +else(CMakePkgConfigHelpersMacroFile) + function(configure_package_config_file infile outfile) + include(CMakeParseArguments) + cmake_parse_arguments(PMPKG "" "INSTALL_DESTINATION" "PATH_VARS" "${ARGN}") + if(NOT PMPKG_INSTALL_DESTINATION) + message(FATAL_ERROR "configure_package_config_file needs an option INSTALL_DESTINATION with a relative path") + endif(NOT PMPKG_INSTALL_DESTINATION) + # asume that PMPKG_INSTALL_DESTINATION is relative + string(REGEX REPLACE "[^/]+" ".." prefix_path ${PMPKG_INSTALL_DESTINATION}) + set(PACKAGE_INIT "# Set prefix to source dir +get_filename_component(PACKAGE_PREFIX_DIR \"\${CMAKE_CURRENT_LIST_DIR}/${prefix_path}\" ABSOLUTE) +macro(set_and_check _var _file) + set(\${_var} \"\${_file}\") + if(NOT EXISTS \"\${_file}\") + message(FATAL_ERROR \"File or directory \${_file} referenced by variable \${_var} does not exist !\") + endif() +endmacro()") + if(PMPKG_PATH_VARS) + foreach(varname ${PMPKG_PATH_VARS}) + set(PACKAGE_${varname} "\${PACKAGE_PREFIX_DIR}/${${varname}}") + endforeach(varname "${PMPKG_PATH_VARS}") + endif(PMPKG_PATH_VARS) + configure_file(${infile} ${outfile} @ONLY) + endfunction(configure_package_config_file infile outfile) +endif(CMakePkgConfigHelpersMacroFile) diff --git a/cmake/modules/DuneMPI.cmake b/cmake/modules/DuneMPI.cmake index 991ce5a0fdb1fba962a50bed1c9127f07bcee7f7..adeeb312a65f441ca04e86da0726db5247133b97 100644 --- a/cmake/modules/DuneMPI.cmake +++ b/cmake/modules/DuneMPI.cmake @@ -21,7 +21,7 @@ find_package(MPI) find_package(Threads) if(MPI_CXX_FOUND) - set(HAVE_MPI MPI_CXX_FOUND) + set(HAVE_MPI ${MPI_CXX_FOUND}) # We do not support the CXX bindings of MPI set(MPI_DUNE_COMPILE_FLAGS ${MPI_C_COMPILE_FLAGS} CACHE STRING "Compile flags used by DUNE when compiling MPI programs") diff --git a/cmake/modules/DuneMacros.cmake b/cmake/modules/DuneMacros.cmake index 7cb1c937573312daea6cf9c09f7214add8ae360e..cb86f604fc8f30629a9afc8f86febc62b972768a 100644 --- a/cmake/modules/DuneMacros.cmake +++ b/cmake/modules/DuneMacros.cmake @@ -87,12 +87,14 @@ macro(dune_module_to_uppercase _upper _module) endmacro(dune_module_to_uppercase _upper _module) macro(find_dune_package module) - if(NOT (${module}_DIR OR ${module}_ROOT OR - "${CMAKE_PREFIX_PATH}" MATCHES ".*${module}.*")) - string(REPLACE ${ProjectName} ${module} ${module}_DIR - ${PROJECT_BINARY_DIR}) - endif() - find_package(${ARGV} NO_CMAKE_PACKAGE_REGISTRY) + if(NOT ${module}_FOUND) + if(NOT (${module}_DIR OR ${module}_ROOT OR + "${CMAKE_PREFIX_PATH}" MATCHES ".*${module}.*")) + string(REPLACE ${ProjectName} ${module} ${module}_DIR + ${PROJECT_BINARY_DIR}) + endif() + find_package(${ARGV} NO_CMAKE_PACKAGE_REGISTRY) + endif(NOT ${module}_FOUND) endmacro(find_dune_package module) macro(extract_line HEADER OUTPUT FILE_CONTENT) @@ -137,7 +139,7 @@ endfunction(convert_deps_to_list var) macro(dune_module_information MODULE_DIR) file(READ "${MODULE_DIR}/dune.module" DUNE_MODULE) - # find version string + # find version strings extract_line("Version:" MODULE_LINE "${DUNE_MODULE}") if(NOT MODULE_LINE) message(FATAL_ERROR "${MODULE_DIR}/dune.module is missing a version.") @@ -212,10 +214,7 @@ macro(dune_process_dependency_leafs modules versions is_required next_level_deps math(EXPR length "${mlength}-1") foreach(i RANGE 0 ${length}) list(GET mmodules ${i} _mod) - find_dune_package(${_mod} ${REQUIRED}) - if(${_mod}_MODULE_PATH) - list(APPEND CMAKE_MODULE_PATH ${${_mod}_MODULE_PATH}) - endif(${_mod}_MODULE_PATH) + find_dune_package(${_mod} ${is_required}) set(${_mod}_SEARCHED ON) if(NOT "${is_required}" STREQUAL "") set(${_mod}_REQUIRED ON) @@ -226,6 +225,12 @@ macro(dune_process_dependency_leafs modules versions is_required next_level_deps set(${next_level_sugs} ${${_mod}_SUGGESTS} ${${next_level_sugs}}) endforeach(i RANGE 0 ${length}) endif(mlength GREATER 0) + if(${next_level_sugs}) + list(REMOVE_DUPLICATES ${next_level_sugs}) + endif(${next_level_sugs}) + if(${next_level_deps}) + list(REMOVE_DUPLICATES ${next_level_deps}) + endif(${next_level_deps}) endmacro(dune_process_dependency_leafs) function(remove_processed_modules modules versions is_required) @@ -247,8 +252,7 @@ function(remove_processed_modules modules versions is_required) set(${versions} ${${versions}} PARENT_SCOPE) endfunction(remove_processed_modules modules versions is_required) -macro(dune_create_dependency_leafs depends depends_versions suggests suggests_versions - global_depends global_suggests) +macro(dune_create_dependency_leafs depends depends_versions suggests suggests_versions) set(deps "") set(sugs "") #Process dependencies @@ -260,47 +264,64 @@ macro(dune_create_dependency_leafs depends depends_versions suggests suggests_ve dune_process_dependency_leafs("${suggests}" "${suggests_versions}" "" deps sugs) endif(NOT "${suggests}" STREQUAL "") split_module_version("${deps}" next_mod_depends next_depends_versions) - #remove_processed_modules(next_mod_depends next_depends_versions REQUIRED) - set(${global_depends} "${${global_depends}}" ${next_mod_depends}) split_module_version("${sugs}" next_mod_suggests next_suggests_versions) - #remove_processed_modules(next_mod_suggests next_suggests_versions "") - set(${global_suggests} "${${global_suggests}}" ${next_mod_suggests}) + set(ALL_DEPENDENCIES ${ALL_DEPENDENCIES} ${next_mod_depends} ${next_mod_suggests}) # Move to next level if(next_mod_suggests OR next_mod_depends) dune_create_dependency_leafs("${next_mod_depends}" "${next_depends_versions}" - "${next_mod_suggests}" "${next_suggests_versions}" global_depends global_suggests) + "${next_mod_suggests}" "${next_suggests_versions}") endif(next_mod_suggests OR next_mod_depends) endmacro(dune_create_dependency_leafs) macro(dune_create_dependency_tree) + if(${dune-common_MODULE_PATH}) + list(REMOVE_ITEM CMAKE_MODULE_PATH ${dune-common_MODULE_PATH}) + endif(${dune-common_MODULE_PATH}) + list(FIND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake/modules start) set(ALL_DEPENDENCIES "") if(DEPENDS_MODULE OR SUGGESTS_MODULE) - set(global_depends ${DEPENDS_MODULE}) - set(global_suggests ${SUGGESTS_MODULE}) - foreach(_mod ${DEPENDS_MODULE}) - find_dune_package(${_mod} REQUIRED) - if(${_mod}_MODULE_PATH) - list(APPEND CMAKE_MODULE_PATH ${${_mod}_MODULE_PATH}) - endif(${_mod}_MODULE_PATH) - set(${_mod}_REQUIRED ON) - endforeach(_mod ${DEPENDS_MODULE}) - foreach(_mod ${SUGGESTS_MODULE}) - find_dune_package(${_mod}) - if(${_mod}_MODULE_PATH) - list(APPEND CMAKE_MODULE_PATH ${${_mod}_MODULE_PATH}) - endif(${_mod}_MODULE_PATH) - set(${_mod}_REQUIRED ON) - endforeach(_mod ${SUGGESTS_MODULE}) + set(ALL_DEPENDENCIES ${DEPENDS_MODULE} ${SUGGESTS_MODULE}) dune_create_dependency_leafs("${DEPENDS_MODULE}" "${DEPENDS_VERSIONS}" - "${SUGGESTS_MODULE}" "${SUGGESTS_VERSIONS}" global_depends - global_suggests) - set(ALL_DEPENDENCIES "${global_depends}" "${global_suggests}") + "${SUGGESTS_MODULE}" "${SUGGESTS_VERSIONS}") endif(DEPENDS_MODULE OR SUGGESTS_MODULE) - # reverse ALL_DEPENDENCIES - list(REVERSE ALL_DEPENDENCIES) - list(REMOVE_DUPLICATES ALL_DEPENDENCIES) - list(REMOVE_DUPLICATES CMAKE_MODULE_PATH) -endmacro(dune_create_dependency_tree _immediates) + set(_my_path "") + if(ALL_DEPENDENCIES) + set(NEW_ALL_DEPS "") + list(LENGTH ALL_DEPENDENCIES length) + if(length GREATER 0) + math(EXPR length "${length}-1") + list(GET ALL_DEPENDENCIES ${length} _mod) + set(${_mod}_cmake_path_processed 1) + set(_my_path ${${_mod}_MODULE_PATH}) + list(APPEND NEW_ALL_DEPS ${_mod}) + math(EXPR length "${length}-1") + if(length GREATER 0) + foreach(i RANGE ${length} 0 -1) + list(GET ALL_DEPENDENCIES ${i} _mod) + if(NOT ${_mod}_cmake_path_processed) + set(${_mod}_cmake_path_processed 1) + if(${_mod}_MODULE_PATH) + list(INSERT _my_path 0 ${${_mod}_MODULE_PATH}) + list(APPEND NEW_ALL_DEPS ${_mod}) + endif(${_mod}_MODULE_PATH) + endif(NOT ${_mod}_cmake_path_processed) + endforeach(i RANGE ${length} 0 -1) + endif(length GREATER 0) + list(LENGTH CMAKE_MODULE_PATH length) + math(EXPR length "${length}-1") + if(start EQUAL -1) + list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake/modules ${_my_path}) + else(start EQUAL -1) + if(start EQUAL ${length}) + list(APPEND CMAKE_MODULE_PATH ${_my_path}) + else(start EQUAL ${length}) + list(INSERT CMAKE_MODULE_PATH ${start} ${_my_path}) + endif(start EQUAL ${length}) + endif(start EQUAL -1) + endif(length GREATER 0) + set(ALL_DEPENDENCIES ${NEW_ALL_DEPS}) + endif(ALL_DEPENDENCIES) +endmacro(dune_create_dependency_tree) # Converts a module name given by _dune_module into a string _macro_name # where all dashes (-) are removed and letters after a dash are capitalized @@ -381,6 +402,9 @@ macro(dune_project) set(ProjectVersion "${DUNE_MOD_VERSION}") set(ProjectMaintainerEmail "${DUNE_MAINTAINER}") + define_property(GLOBAL PROPERTY DUNE_MODULE_LIBRARIES + BRIEF_DOCS "List of libraries of the module. DO NOT EDIT!" + FULL_DOCS "List of libraries of the module. Used to generate CMake's package configuration files. DO NOT EDIT!") dune_create_dependency_tree() # assert the project names matches @@ -502,10 +526,15 @@ macro(dune_project) if(NOT DUNE_INSTALL_MODULEDIR) set(DUNE_INSTALL_MODULEDIR "" CACHE PATH - "Installation directory for CMake modules. Default is \${CMAKE_INSTALL_DATAROOTDIR}/cmake/modules when not set explicitely") - set(DUNE_INSTALL_MODULEDIR ${CMAKE_INSTALL_DATAROOTDIR}/cmake/modules) + "Installation directory for CMake modules. Default is \${CMAKE_INSTALL_DATAROOTDIR}/dune/cmake/modules when not set explicitely") + set(DUNE_INSTALL_MODULEDIR ${CMAKE_INSTALL_DATAROOTDIR}/dune/cmake/modules) endif(NOT DUNE_INSTALL_MODULEDIR) - + if(NOT DUNE_INSTALL_NONOBJECTLIBDIR) + set(DUNE_INSTALL_NONOBJECTLIBDIR "" + CACHE PATH + "Installation directory for libraries that are not architecture dependent. Default is lib when not set explicitely") + set(DUNE_INSTALL_NONOBJECTLIBDIR lib) + endif(NOT DUNE_INSTALL_NONOBJECTLIBDIR) # set up make headercheck include(Headercheck) setup_headercheck() @@ -572,15 +601,88 @@ macro(finalize_dune_project) #configure all headerchecks finalize_headercheck() + #create cmake-config files for installation tree + include(DuneCMakePackageConfigHelpers) + include(GNUInstallDirs) + set(DOXYSTYLE_DIR ${CMAKE_INSTALL_DATAROOTDIR}/dune-common/doc/doxygen/) + set(SCRIPT_DIR ${CMAKE_INSTALL_DATAROOTDIR}/dune/cmake/scripts) + + if(NOT EXISTS ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in) + # Generate a standard cmake package configuration file + file(WRITE ${PROJECT_BINARY_DIR}/CMakeFiles/${DUNE_MOD_NAME}-config.cmake.in +"if(NOT @DUNE_MOD_NAME@_FOUND) +@PACKAGE_INIT@ + +#report other information +set_and_check(@DUNE_MOD_NAME@_PREFIX \"\${PACKAGE_PREFIX_DIR}\") +set_and_check(@DUNE_MOD_NAME@_INCLUDE_DIRS \"@PACKAGE_CMAKE_INSTALL_INCLUDEDIR@\") +set(@DUNE_MOD_NAME@_CXX_FLAGS \"@CMAKE_CXX_FLAGS@\") +set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG \"@CMAKE_CXX_FLAGS_DEBUG@\") +set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL \"@CMAKE_CXX_FLAGS_MINSIZEREL@\") +set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE \"@CMAKE_CXX_FLAGS_RELEASE@\") +set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO \"@CMAKE_CXX_FLAGS_RELWITHDEBINFO@\") +set(@DUNE_MOD_NAME@_DEPENDS \"@DUNE_DEPENDS@\") +set(@DUNE_MOD_NAME@_SUGGESTS \"@DUNE_SUGGESTS@\") +set(@DUNE_MOD_NAME@_MODULE_PATH \"@PACKAGE_DUNE_INSTALL_MODULEDIR@\") +set(@DUNE_MOD_NAME@_LIBRARIES \"@DUNE_MODULE_LIBRARIES@\") +#import the target +if(@DUNE_MOD_NAME@_LIBRARIES) + get_filename_component(_dir \"\${CMAKE_CURRENT_LIST_FILE}\" PATH) + include(\"\${_dir}/@DUNE_MOD_NAME@-targets.cmake\") +endif(@DUNE_MOD_NAME@_LIBRARIES) +endif(NOT @DUNE_MOD_NAME@_FOUND)") + set(CONFIG_SOURCE_FILE ${PROJECT_BINARY_DIR}/CMakeFiles/${DUNE_MOD_NAME}-config.cmake.in) + else(NOT EXISTS ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in) + set(CONFIG_SOURCE_FILE ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in) + endif(NOT EXISTS ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in) + get_property(DUNE_MODULE_LIBRARIES GLOBAL PROPERTY DUNE_MODULE_LIBRARIES) + + # compute under which libdir the package configuration files are to be installed. + # If the module installs an object library we use CMAKE_INSTALL_LIBDIR + # to capture the multiarch triplet of Debian/Ubuntu. + # Otherwise we fall back to DUNE_INSTALL_NONOBJECTLIB which is lib + # if not set otherwise. + get_property(DUNE_MODULE_LIBRARIES GLOBAL PROPERTY DUNE_MODULE_LIBRARIES) + if(DUNE_MODULE_LIBRARIES) + set(DUNE_INSTALL_LIBDIR ${CMAKE_INSTALL_LIBDIR}) + else(DUNE_MODULE_LIBRARIES) + set(DUNE_INSTALL_LIBDIR ${DUNE_INSTALL_NONOBJECTLIBDIR}) + endif(DUNE_MODULE_LIBRARIES) + +message(" configure_package_config_file(${CONFIG_SOURCE_FILE} + ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake + INSTALL_DESTINATION ${DUNE_INSTALL_LIBDIR}/cmake/${DUNE_MOD_NAME} + PATH_VARS CMAKE_INSTALL_DATAROOTDIR DUNE_INSTALL_MODULEDIR CMAKE_INSTALL_INCLUDEDIR + DOXYSTYLE_DIR SCRIPT_DIR)") + configure_package_config_file(${CONFIG_SOURCE_FILE} + ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake + INSTALL_DESTINATION ${DUNE_INSTALL_LIBDIR}/cmake/${DUNE_MOD_NAME} + PATH_VARS CMAKE_INSTALL_DATAROOTDIR DUNE_INSTALL_MODULEDIR CMAKE_INSTALL_INCLUDEDIR + DOXYSTYLE_DIR SCRIPT_DIR) + + #create cmake-config files for build tree + set(PACKAGE_CMAKE_INSTALL_INCLUDEDIR ${PROJECT_SOURCE_DIR}) + set(PACKAGE_CMAKE_INSTALL_DATAROOTDIR ${PROJECT_BINARY_DIR}) + set(PACKAGE_DOXYSTYLE_DIR ${PROJECT_SOURCE_DIR}/doc/doxygen) + set(PACKAGE_SCRIPT_DIR ${PROJECT_SOURCE_DIR}/cmake/scripts) + set(PACKAGE_DUNE_INSTALL_MODULEDIR ${PROJECT_SOURCE_DIR}/cmake/modules) + set(PACKAGE_PREFIX_DIR ${PROJECT_BINARY_DIR}) + set(PACKAGE_INIT "# Set prefix to source dir +set(PACKAGE_PREFIX_DIR ${PROJECT_SOURCE_DIR}) +macro(set_and_check _var _file) + set(\${_var} \"\${_file}\") + if(NOT EXISTS \"\${_file}\") + message(FATAL_ERROR \"File or directory \${_file} referenced by variable \${_var} does not exist !\") + endif() +endmacro()") configure_file( - ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-config.cmake.in + ${CONFIG_SOURCE_FILE} ${PROJECT_BINARY_DIR}/${DUNE_MOD_NAME}-config.cmake @ONLY) - #create cmake-config files for installation tree - configure_file( - ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in - ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake @ONLY) + #configure_file( + # ${PROJECT_SOURCE_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake.in + # ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake @ONLY) list(LENGTH DEPENDS_MODULE mlength) math(EXPR len2 "${mlength}-1") if(mlength GREATER 0) @@ -603,23 +705,41 @@ macro(finalize_dune_project) #file(APPEND ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake # "\ninclude(${DUNE_MOD_NAME_CMAKE}Macros)\n") endif(${DUNE_MOD_NAME_CMAKE}_FOUND) + if(NOT EXISTS ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-version.cmake.in) + file(WRITE ${PROJECT_BINARY_DIR}/CMakeFiles/${DUNE_MOD_NAME}-version.cmake.in +"set(PACKAGE_VERSION \"@DUNE_MOD_VERSION@\") + +if(NOT \"\${PACKAGE_FIND_VERSION}\" VERSION_GREATER \"@DUNE_MOD_VERSION@\") + set (PACKAGE_VERSION_COMPATIBLE 1) # compatible with older + if (\"\${PACKAGE_FIND_VERSION}\" VERSION_EQUAL \"@DUNE_MOD_VERSION@\") + set(PACKAGE_VERSION_EXACT 1) #exact match for this version + endif() +endif() +") + set(CONFIG_VERSION_FILE ${PROJECT_BINARY_DIR}/CMakeFiles/${DUNE_MOD_NAME}-version.cmake.in) + else(NOT EXISTS ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-version.cmake.in) + set(CONFIG_VERSION_FILE ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-version.cmake.in) + endif(NOT EXISTS ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-version.cmake.in) configure_file( - ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}-version.cmake.in + ${CONFIG_VERSION_FILE} ${PROJECT_BINARY_DIR}/${DUNE_MOD_NAME}-version.cmake @ONLY) #install dune.module file - install(FILES dune.module DESTINATION lib/dunecontrol/${DUNE_MOD_NAME}) + install(FILES dune.module DESTINATION ${DUNE_INSTALL_NONOBJECTLIBDIR}/dunecontrol/${DUNE_MOD_NAME}) - #install cmake-config files + # install cmake-config files install(FILES ${PROJECT_BINARY_DIR}/cmake/pkg/${DUNE_MOD_NAME}-config.cmake ${PROJECT_BINARY_DIR}/${DUNE_MOD_NAME}-version.cmake - DESTINATION lib/cmake/${DUNE_MOD_NAME}) + DESTINATION ${DUNE_INSTALL_LIBDIR}/cmake/${DUNE_MOD_NAME}) #install config.h if(EXISTS ${CMAKE_SOURCE_DIR}/config.h.cmake) install(FILES config.h.cmake DESTINATION share/${DUNE_MOD_NAME}) endif(EXISTS ${CMAKE_SOURCE_DIR}/config.h.cmake) + #install pkg-config files + create_and_install_pkconfig(${DUNE_INSTALL_LIBDIR}) + if("${ARGC}" EQUAL "1") message(STATUS "Adding custom target for config.h generation") dune_regenerate_config_cmake() @@ -728,6 +848,8 @@ macro(dune_add_library basename) dune_expand_object_libraries(DUNE_LIB_SOURCES DUNE_LIB_ADD_LIBS DUNE_LIB_COMPILE_FLAGS) #create lib add_library(${basename} ${DUNE_LIB_SOURCES}) + get_property(_prop GLOBAL PROPERTY DUNE_MODULE_LIBRARIES) + set_property(GLOBAL PROPERTY DUNE_MODULE_LIBRARIES ${_prop} ${basename}) # link with specified libraries. if(DUNE_LIB_ADD_LIBS) dune_target_link_libraries(${basename} ${DUNE_LIB_ADD_LIBS}) @@ -787,9 +909,9 @@ macro(dune_add_library basename) endif(NOT _MODULE_EXPORT_USED) # install targets to use the libraries in other modules. install(TARGETS ${_created_libs} - EXPORT ${DUNE_MOD_NAME}-targets DESTINATION lib) + EXPORT ${DUNE_MOD_NAME}-targets DESTINATION ${CMAKE_INSTALL_LIBDIR}) install(EXPORT ${DUNE_MOD_NAME}-targets - DESTINATION lib/cmake) + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/${DUNE_MOD_NAME}) # export libraries for use in build tree export(TARGETS ${_created_libs} ${_append} @@ -937,4 +1059,4 @@ macro(add_dune_all_flags targets) APPEND_STRING PROPERTY COMPILE_FLAGS ${FLAGSTR}) endforeach() -endmacro(add_dune_all_flags targets) \ No newline at end of file +endmacro(add_dune_all_flags targets) diff --git a/cmake/modules/DunePkgConfig.cmake b/cmake/modules/DunePkgConfig.cmake index 0b6e3fa87b032c3c710e30a92c82159e8b7164f5..a917b33e5a38f639f8cffb2da203bfd3b0c0d703 100644 --- a/cmake/modules/DunePkgConfig.cmake +++ b/cmake/modules/DunePkgConfig.cmake @@ -5,37 +5,39 @@ find_package(PkgConfig) -# set some variables that are used in the pkg-config file -set( prefix ${CMAKE_INSTALL_PREFIX}) -set(exec_prefix "\${prefix}") -set(libdir "\${exec_prefix}/lib") -set(includedir "\${prefix}/include") -set(PACKAGE_NAME ${DUNE_MOD_NAME}) -set(VERSION ${DUNE_MOD_VERSION}) -set(CC ${CMAKE_C_COMPILER}) -set(CXX "${CMAKE_CXX_COMPILER} ${CXX_STD11_FLAGS}") +function(create_and_install_pkconfig installlibdir) + # set some variables that are used in the pkg-config file + include(GNUInstallDirs) + set( prefix ${CMAKE_INSTALL_PREFIX}) + set(exec_prefix "\${prefix}") + set(libdir "\${exec_prefix}/${installlibdir}") + set(includedir "\${prefix}/${CMAKE_INSTALL_INCLUDEDIR}") + set(PACKAGE_NAME ${DUNE_MOD_NAME}) + set(VERSION ${DUNE_MOD_VERSION}) + set(CC ${CMAKE_C_COMPILER}) + set(CXX "${CMAKE_CXX_COMPILER} ${CXX_STD11_FLAGS}") -if(DUNE_DEPENDS) - foreach(_DUNE_DEPEND ${DUNE_DEPENDS}) - string(REGEX REPLACE "\\(" "" REQF1 ${_DUNE_DEPEND}) - string(REGEX REPLACE "\\)" "" LR ${REQF1}) - if(REQUIRES) - set(REQUIRES "${REQUIRES} ${LR}") - else() - set(REQUIRES ${LR}) - endif(REQUIRES) - endforeach(_DUNE_DEPEND ${DUNE_DEPENDS}) -endif(DUNE_DEPENDS) + if(DUNE_DEPENDS) + foreach(_DUNE_DEPEND ${DUNE_DEPENDS}) + string(REGEX REPLACE "\\(" "" REQF1 ${_DUNE_DEPEND}) + string(REGEX REPLACE "\\)" "" LR ${REQF1}) + if(REQUIRES) + set(REQUIRES "${REQUIRES} ${LR}") + else() + set(REQUIRES ${LR}) + endif(REQUIRES) + endforeach(_DUNE_DEPEND ${DUNE_DEPENDS}) + endif(DUNE_DEPENDS) -#create pkg-config file -configure_file( - ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}.pc.in - ${PROJECT_BINARY_DIR}/${DUNE_MOD_NAME}.pc - @ONLY -) + #create pkg-config file + configure_file( + ${PROJECT_SOURCE_DIR}/${DUNE_MOD_NAME}.pc.in + ${PROJECT_BINARY_DIR}/${DUNE_MOD_NAME}.pc + @ONLY + ) -# install pkgconfig file -if(PKG_CONFIG_FOUND) + # install pkgconfig file install(FILES ${CMAKE_CURRENT_BINARY_DIR}/${DUNE_MOD_NAME}.pc - DESTINATION lib/pkgconfig) -endif(PKG_CONFIG_FOUND) + DESTINATION ${installlibdir}/pkgconfig) + +endfunction(create_and_install_pkconfig) diff --git a/cmake/modules/FindGMP.cmake b/cmake/modules/FindGMP.cmake index 40da914e242ff24b991bac948de32f815945b791..49bd9a6e8f37c4b12356326462c113224bb2a5f9 100644 --- a/cmake/modules/FindGMP.cmake +++ b/cmake/modules/FindGMP.cmake @@ -46,7 +46,7 @@ find_library(GMPXX_LIB gmpxx) # check if library works if(GMP_LIB AND GMPXX_LIB) include(CheckSymbolExists) - check_symbol_exists(__gmpz_abs ${GMP_LIB} GMPXX_LIB_WORKS) + check_library_exists(${GMP_LIB} __gmpz_abs "" GMPXX_LIB_WORKS) endif(GMP_LIB AND GMPXX_LIB) cmake_pop_check_state() @@ -88,4 +88,4 @@ if(HAVE_GMP) foreach(dir ${GMP_INCLUDE_DIR}) set_property(GLOBAL APPEND PROPERTY ALL_PKG_FLAGS "-I${dir}") endforeach() -endif() \ No newline at end of file +endif() diff --git a/cmake/modules/FindUMFPack.cmake b/cmake/modules/FindUMFPack.cmake index f1c44ac3aacde230914162a04129bb0b52ce4d2d..322c4d00f3459640f2a7ec901abf3e3b9ddbba55 100644 --- a/cmake/modules/FindUMFPack.cmake +++ b/cmake/modules/FindUMFPack.cmake @@ -92,7 +92,7 @@ else(UMFPACK_FOUND) endif(UMFPACK_FOUND) #set HAVE_UMFPACK for config.h -set(HAVE_UMFPACK UMFPACK_FOUND) +set(HAVE_UMFPACK ${UMFPACK_FOUND}) #add all umfpack related flags to ALL_PKG_FLAGS, this must happen regardless of a target using add_dune_umfpack_flags if(UMFPACK_FOUND) diff --git a/cmake/modules/Headercheck.cmake b/cmake/modules/Headercheck.cmake index ff6fec07a757ada3956d024612093f7a2cdf5be2..611926be09d9462c00c3f51f38b5cd1b61527fff 100644 --- a/cmake/modules/Headercheck.cmake +++ b/cmake/modules/Headercheck.cmake @@ -64,7 +64,8 @@ macro(finalize_headercheck) add_dependencies(headercheck headercheck_${targname}) #add PKG_ALL_FLAGS and the directory where the header is located - set_property(TARGET headercheck_${targname} APPEND_STRING PROPERTY COMPILE_FLAGS "-DHEADERCHECK -I${PROJECT_SOURCE_DIR}/${relpath} -I${CMAKE_BINARY_DIR}") + set_property(TARGET headercheck_${targname} + APPEND_STRING PROPERTY COMPILE_FLAGS "-DHEADERCHECK -I${PROJECT_SOURCE_DIR}${relpath} -I${CMAKE_BINARY_DIR}") set_property(TARGET headercheck_${targname} PROPERTY ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/headercheck/${relpath}") add_dune_all_flags(headercheck_${targname}) unset(headercheck_${targname}_LIB_DEPENDS CACHE) diff --git a/cmake/modules/Makefile.am b/cmake/modules/Makefile.am index 4676f1ea43e6da471f6263bef414c5608c6cd260..917612ce2536cc5e0356cd9ad33785005c5befaa 100644 --- a/cmake/modules/Makefile.am +++ b/cmake/modules/Makefile.am @@ -1,8 +1,12 @@ MODULES = \ + AddGMPFlags.cmake \ + AddMETISFlags.cmake \ + AddParMETISFlags.cmake \ + AddUMFPackFlags.cmake \ CheckCXX11Features.cmake \ CheckSharedPtr.cmake \ - AddUMFPackFlags.cmake \ DuneBoost.cmake \ + DuneCMakePackageConfigHelpers.cmake \ DuneCommonMacros.cmake \ DuneCxaDemangle.cmake \ DuneDoc.cmake \ @@ -22,9 +26,10 @@ MODULES = \ FindUMFPack.cmake \ Headercheck.cmake \ LanguageSupport.cmake \ + UseInkscape.cmake \ UseLATEX.cmake -modulesdir = $(datadir)/cmake/modules +modulesdir = $(datadir)/dune/cmake/modules dist_modules_DATA = ${MODULES} include $(top_srcdir)/am/global-rules diff --git a/cmake/pkg/dune-common-config.cmake.in b/cmake/pkg/dune-common-config.cmake.in index 5c5459ac5199b924427fdfca599d43031b25c764..acf7c84bf8e91983cb0cc3d7e77798c685cf3810 100644 --- a/cmake/pkg/dune-common-config.cmake.in +++ b/cmake/pkg/dune-common-config.cmake.in @@ -1,24 +1,22 @@ if(NOT @DUNE_MOD_NAME@_FOUND) -#compute installation prefix relative to this file -get_filename_component(_dir "${CMAKE_CURRENT_LIST_FILE}" PATH) -get_filename_component(_prefix "${_dir}/../../.." ABSOLUTE) +@PACKAGE_INIT@ #import the target -include("${_prefix}/lib/cmake/@DUNE_MOD_NAME@-targets.cmake") +get_filename_component(_dir "${CMAKE_CURRENT_LIST_FILE}" PATH) +include("${_dir}/@DUNE_MOD_NAME@-targets.cmake") #report other information -set(@DUNE_MOD_NAME@_PREFIX "${_prefix}") -set(@DUNE_MOD_NAME@_INCLUDE_DIRS "${_prefix}/include") +set_and_check(@DUNE_MOD_NAME@_PREFIX "${PACKAGE_PREFIX_DIR}") +set_and_check(@DUNE_MOD_NAME@_INCLUDE_DIRS "@PACKAGE_CMAKE_INSTALL_INCLUDEDIR@") set(@DUNE_MOD_NAME@_CXX_FLAGS "@CMAKE_CXX_FLAGS@") set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG "@CMAKE_CXX_FLAGS_DEBUG@") set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL "@CMAKE_CXX_FLAGS_MINSIZEREL@") set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE "@CMAKE_CXX_FLAGS_RELEASE@") set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO "@CMAKE_CXX_FLAGS_RELWITHDEBINFO@") set(@DUNE_MOD_NAME@_LIBRARIES "dunecommon") -set(@DUNE_MOD_NAME@_SCRIPT_DIR "${_prefix}/share/cmake/scripts") -set(@DUNE_MOD_NAME@_SCRIPT_SOURCE_DIR "${_prefix}/share/cmake/scripts") -set(DOXYSTYLE_FILE "${_prefix}/share/doc/dune-common/doxygen/Doxystyle") +set_and_check(@DUNE_MOD_NAME@_SCRIPT_DIR "@PACKAGE_SCRIPT_DIR@") +set_and_check(DOXYSTYLE_FILE "@PACKAGE_DOXYSTYLE_DIR@/Doxystyle") set(@DUNE_MOD_NAME@_DEPENDS "@DUNE_DEPENDS@") set(@DUNE_MOD_NAME@_SUGGESTS "@DUNE_SUGGESTS@") -set(@DUNE_MOD_NAME@_MODULE_PATH "${_prefix}/@DUNE_INSTALL_MODULEDIR@") +set_and_check(@DUNE_MOD_NAME@_MODULE_PATH "@PACKAGE_DUNE_INSTALL_MODULEDIR@") endif(NOT @DUNE_MOD_NAME@_FOUND) diff --git a/cmake/scripts/CMakeLists.txt b/cmake/scripts/CMakeLists.txt index 166c957fc03e6a0ec4b76f5724b1b4869ea1042c..9c2a5c8c9d017b831b0844522fe3e57c90d170fc 100644 --- a/cmake/scripts/CMakeLists.txt +++ b/cmake/scripts/CMakeLists.txt @@ -6,4 +6,4 @@ set(modules RunDoxygen.cmake) install(FILES ${modules} ${CMAKE_CURRENT_SOURCE_DIR}/BuildTests.cmake.in - DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/cmake/scripts) + DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/dune/cmake/scripts) diff --git a/cmake/scripts/Makefile.am b/cmake/scripts/Makefile.am index 21f4372c63193be2151df8d8129295760f4909d8..2128c4a907436739bca99d942ee6297538fe6c86 100644 --- a/cmake/scripts/Makefile.am +++ b/cmake/scripts/Makefile.am @@ -5,7 +5,7 @@ MODULES = BuildTests.cmake.in \ InstallFile.cmake \ RunDoxygen.cmake -modulesdir = $(datadir)/cmake/scripts +modulesdir = $(datadir)/dune/cmake/scripts dist_modules_DATA = ${MODULES} include $(top_srcdir)/am/global-rules diff --git a/doc/CMakeLists.txt b/doc/CMakeLists.txt index 3714c7a1071c3e0d6be298fb952c6f59978fc849..fc17e9fde7bb936a6417db1ee92265637b4ca905 100644 --- a/doc/CMakeLists.txt +++ b/doc/CMakeLists.txt @@ -2,5 +2,6 @@ add_subdirectory("doxygen") add_subdirectory("buildsystem") add_subdirectory("comm") install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/example.opts - DESTINATION ${CMAKE_INSTALL_DOCDIR} - ) + DESTINATION ${CMAKE_INSTALL_DOCDIR}) +install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/dunecontrol.1 + DESTINATION ${CMAKE_INSTALL_MANDIR}/man1) diff --git a/doc/Makefile.am b/doc/Makefile.am index 11e6206cefb5be027db1310c0973195c01dbfc78..35730d5b2f087c42e78b701d604f35c1ddc6e9d8 100644 --- a/doc/Makefile.am +++ b/doc/Makefile.am @@ -11,13 +11,11 @@ BASEDIR=.. EXTRAINSTALL=example.opts # install the html pages -docdir=$(datadir)/doc/dune-common DOCFILES = $(PAGES) DOCFILES_EXTRA = example.opts EXTRA_DIST = CMakeLists.txt $(PAGES) example.opts -man_MANS = dunecontrol.1 dist_man_MANS = dunecontrol.1 # include rules for wml -> html transformation diff --git a/doc/comm/Makefile.am b/doc/comm/Makefile.am index 722b61b35d961b34760fb388e861a4697efb2492..176ec746a32fb63cd8c3a47f2705f3d847b9a55a 100644 --- a/doc/comm/Makefile.am +++ b/doc/comm/Makefile.am @@ -4,6 +4,8 @@ SUBDIRS = figures MPIPROGRAMS = indexset poosc08 poosc08_test +EXTRA_DIST = CMakeLists.txt + # programs just to build when "make check" is used check_PROGRAMS = $(MPIPROGRAMS) # list of tests to run (indicestest is special case) @@ -11,16 +13,16 @@ TESTS = $(MPIPROGRAMS) if BUILD_DOCS DOCFILES = communication.pdf - EXTRA_DIST = $(DOCFILES) + EXTRA_DIST += $(DOCFILES) EXTRAINSTALL = $(DOCFILES) endif # setting like in dune-web -CURDIR=doc/istl/comm +CURDIR=doc/comm BASEDIR=../../.. # install the docs -docdir=$(datadir)/doc/dune-istl/comm +docdir=$(datadir)/doc/dune-common/comm include $(top_srcdir)/am/latex include $(top_srcdir)/am/webstuff diff --git a/doc/comm/poosc08_test.cc b/doc/comm/poosc08_test.cc index 2bef041751b845bf4383af03c67f766ca58e1daa..2fe7eae54adf8c0b3bd36fb6a1f140f316225665 100644 --- a/doc/comm/poosc08_test.cc +++ b/doc/comm/poosc08_test.cc @@ -43,7 +43,7 @@ struct CopyData { template<class T> -void doCalculations(T& t){} +void doCalculations(T&){} #if HAVE_MPI void test() diff --git a/doc/doxygen/CMakeLists.txt b/doc/doxygen/CMakeLists.txt index c4e01f1c3e1f9da69ea6fab790f3da1cd956fed2..73868a60618f26714bbd93b6e52230ca69f70124 100644 --- a/doc/doxygen/CMakeLists.txt +++ b/doc/doxygen/CMakeLists.txt @@ -1,3 +1,3 @@ # quickhack for creating the Doxyfile.in and Doxyfile add_doxygen_target() -install(FILES Doxystyle DESTINATION ${CMAKE_INSTALL_DOCDIR}/doxygen) +install(FILES Doxystyle DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/dune-common/doc/doxygen) diff --git a/doc/doxygen/Doxystyle b/doc/doxygen/Doxystyle index c29eb5633a4c3aadbb6260d8f3cc848797b7b1e3..a26fa813f28c6e6eaade5669a5e7a03c25439668 100644 --- a/doc/doxygen/Doxystyle +++ b/doc/doxygen/Doxystyle @@ -152,8 +152,8 @@ TEMPLATE_RELATIONS = YES CLASS_GRAPH = YES COLLABORATION_GRAPH = NO GROUP_GRAPHS = YES -INCLUDE_GRAPH = YES -INCLUDED_BY_GRAPH = YES +INCLUDE_GRAPH = NO +INCLUDED_BY_GRAPH = NO GRAPHICAL_HIERARCHY = NO DOT_MULTI_TARGETS = NO GENERATE_LEGEND = NO diff --git a/dune-common-config.cmake.in b/dune-common-config.cmake.in deleted file mode 100644 index 1344876e4f78cf49963c2abfedb72cb3f6f27c97..0000000000000000000000000000000000000000 --- a/dune-common-config.cmake.in +++ /dev/null @@ -1,19 +0,0 @@ -if(NOT @DUNE_MOD_NAME@_FOUND) -#import the target -include("@CMAKE_BINARY_DIR@/@DUNE_MOD_NAME@-targets.cmake") - -#report other information -set(@DUNE_MOD_NAME@_PREFIX "@CMAKE_SOURCE_DIR@") -set(@DUNE_MOD_NAME@_INCLUDE_DIRS "@CMAKE_SOURCE_DIR@") -set(@DUNE_MOD_NAME@_CXX_FLAGS "@CMAKE_CXX_FLAGS@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_DEBUG "@CMAKE_CXX_FLAGS_DEBUG@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_MINSIZEREL "@CMAKE_CXX_FLAGS_MINSIZEREL@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELEASE "@CMAKE_CXX_FLAGS_RELEASE@") -set(@DUNE_MOD_NAME@_CXX_FLAGS_RELWITHDEBINFO "@CMAKE_CXX_FLAGS_RELWITHDEBINFO@") -set(@DUNE_MOD_NAME@_LIBRARIES "dunecommon") -set(@DUNE_MOD_NAME@_SCRIPT_DIR "@CMAKE_SOURCE_DIR@/cmake/scripts") -set(DOXYSTYLE_FILE "@CMAKE_SOURCE_DIR@/doc/doxygen/Doxystyle") -set(@DUNE_MOD_NAME@_DEPENDS "@DUNE_DEPENDS@") -set(@DUNE_MOD_NAME@_SUGGESTS "@DUNE_SUGGESTS@") -set(@DUNE_MOD_NAME@_MODULE_PATH "@CMAKE_SOURCE_DIR@/cmake/modules") -endif(NOT @DUNE_MOD_NAME@_FOUND) \ No newline at end of file diff --git a/dune-common-version.cmake.in b/dune-common-version.cmake.in deleted file mode 100644 index a1c2199d972b8943a646d4feb40d12e9e239b141..0000000000000000000000000000000000000000 --- a/dune-common-version.cmake.in +++ /dev/null @@ -1,8 +0,0 @@ -set(PACKAGE_VERSION "@DUNE_MOD_VERSION@") - -if(NOT "${PACKAGE_FIND_VERSION}" VERSION_GREATER "@DUNE_MOD_VERSION@") - set (PACKAGE_VERSION_COMPATIBLE 1) # compatible with older - if ("${PACKAGE_FIND_VERSION}" VERSION_EQUAL "@DUNE_MOD_VERSION@") - set(PACKAGE_VERSION_EXACT 1) #exact match for this version - endif() -endif() diff --git a/dune/common/CMakeLists.txt b/dune/common/CMakeLists.txt index 91ebd9e37bd038bb825cd4943ef1da03c8245ab0..fe02a259f0e2376da8be667bdfff4dd05fa848c8 100644 --- a/dune/common/CMakeLists.txt +++ b/dune/common/CMakeLists.txt @@ -100,4 +100,6 @@ DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/dune/common) # Install some test headers, because they get used by tests in other modules # We do this here as test will not be considered for make install -install(FILES test/iteratortest.hh DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/dune/common/test) +install(FILES test/iteratortest.hh + test/checkmatrixinterface.hh + DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/dune/common/test) diff --git a/dune/common/array.hh b/dune/common/array.hh index cf2cf3ae0aec507eb138fe9c904e80ee9b3d81c8..42e6ed1edf07a689db634af8f1bd47c6ea27058a 100644 --- a/dune/common/array.hh +++ b/dune/common/array.hh @@ -253,6 +253,22 @@ namespace Dune return result; } + //! Create an array and fill it with copies of the provided value. + /** + * \note This method is Dune-specific and not part of any C++ standard. + */ + template<typename T, std::size_t n> + array<T,n> fill_array(const T& t) + { + array<T,n> r; + r.fill(t); +#if HAVE_RVALUE_REFERENCES + return std::move(r); +#else + return r; +#endif + } + /** @} */ } // end namespace Dune diff --git a/dune/common/debugallocator.hh b/dune/common/debugallocator.hh index 3a925464747ef6c02c861da790796d0a98847b87..bf92468176dd96bcc9c301f4ee78de23be836e3b 100644 --- a/dune/common/debugallocator.hh +++ b/dune/common/debugallocator.hh @@ -3,6 +3,7 @@ #ifndef DUNE_DEBUG_ALLOCATOR_HH #define DUNE_DEBUG_ALLOCATOR_HH +#include <dune/common/unused.hh> #include <exception> #include <typeinfo> #include <vector> @@ -252,6 +253,7 @@ namespace Dune pointer allocate(size_type n, DebugAllocator<void>::const_pointer hint = 0) { + DUNE_UNUSED_PARAMETER(hint); return DebugMemory::alloc_man.allocate<T>(n); } diff --git a/dune/common/densematrix.hh b/dune/common/densematrix.hh index 04241b1f4b63eb4be592c8148bb75488278af7a4..ee253e396953dfc87fe24b4fb638e1cfa7b26725 100644 --- a/dune/common/densematrix.hh +++ b/dune/common/densematrix.hh @@ -15,6 +15,7 @@ #include <dune/common/static_assert.hh> #include <dune/common/classname.hh> #include <dune/common/math.hh> +#include <dune/common/unused.hh> namespace Dune @@ -719,6 +720,9 @@ namespace Dune #ifdef DUNE_FMatrix_WITH_CHECKING if (i<0 || i>=rows()) DUNE_THROW(FMatrixError,"row index out of range"); if (j<0 || j>=cols()) DUNE_THROW(FMatrixError,"column index out of range"); +#else + DUNE_UNUSED_PARAMETER(i); + DUNE_UNUSED_PARAMETER(j); #endif return true; } @@ -733,7 +737,7 @@ namespace Dune void swap(int i, int j); template<typename T> - void operator()(const T&, int k, int i) + void operator()(const T&, int, int) {} std::vector<size_type> & pivot_; @@ -756,10 +760,10 @@ namespace Dune ElimDet(field_type& sign) : sign_(sign) { sign_ = 1; } - void swap(int i, int j) + void swap(int, int) { sign_ *= -1; } - void operator()(const field_type&, int k, int i) + void operator()(const field_type&, int, int) {} field_type& sign_; diff --git a/dune/common/diagonalmatrix.hh b/dune/common/diagonalmatrix.hh index 6b2ce2b3aeb56692b5f84af5a3602fa85d7f9a40..51b750ecdce8e31de006673af298570959aa20ed 100644 --- a/dune/common/diagonalmatrix.hh +++ b/dune/common/diagonalmatrix.hh @@ -20,6 +20,7 @@ #include <dune/common/fvector.hh> #include <dune/common/genericiterator.hh> #include <dune/common/typetraits.hh> +#include <dune/common/unused.hh> namespace Dune { @@ -696,6 +697,8 @@ namespace Dune { #ifdef DUNE_FMatrix_WITH_CHECKING if (i!=row_) DUNE_THROW(FMatrixError,"index is not contained in pattern"); +#else + DUNE_UNUSED_PARAMETER(i); #endif return *p_; } diff --git a/dune/common/fassign.hh b/dune/common/fassign.hh index 8f8bb0aeef7cc79075e8cd01c6695578d8efc76b..b6c675d73291b3c6c0ee2a33998b7e6fbb86af51 100644 --- a/dune/common/fassign.hh +++ b/dune/common/fassign.hh @@ -5,6 +5,7 @@ #include <dune/common/fvector.hh> #include <dune/common/fmatrix.hh> +#include <dune/common/unused.hh> namespace Dune { @@ -103,6 +104,7 @@ namespace Dune { */ fvector_assigner & append (Zero z) { + DUNE_UNUSED_PARAMETER(z); while (c!=s) v[c++] = 0; return *this; } @@ -226,6 +228,7 @@ namespace Dune { */ fmatrix_assigner & append (Zero z) { + DUNE_UNUSED_PARAMETER(z); while (c!=m) A[r][c++] = 0; return *this; } @@ -233,6 +236,7 @@ namespace Dune { */ fmatrix_assigner & append (NextRow nr) { + DUNE_UNUSED_PARAMETER(nr); end_row(); r++; return *this; diff --git a/dune/common/fvector.hh b/dune/common/fvector.hh index e07db97b813c288848ba7d49ea4cc4981eac4778..76c77bc2c2739774e631958dd4ddc0ca964d2f41 100644 --- a/dune/common/fvector.hh +++ b/dune/common/fvector.hh @@ -18,6 +18,7 @@ #include "array.hh" #include "densevector.hh" #include "static_assert.hh" +#include "unused.hh" namespace Dune { @@ -142,6 +143,7 @@ namespace Dune { template<class C> FieldVector (const DenseVector<C> & x, typename Dune::enable_if<IsFieldVectorSizeCorrect<C,SIZE>::value>::type* dummy=0 ) { + DUNE_UNUSED_PARAMETER(dummy); // do a run-time size check, for the case that x is not a FieldVector assert(x.size() == SIZE); for (size_type i = 0; i<SIZE; i++) diff --git a/dune/common/hash.hh b/dune/common/hash.hh index b47532fc272d3594d66de62b82684098225974ae..251276eb142b85b557c98219296650bfe369e1c3 100644 --- a/dune/common/hash.hh +++ b/dune/common/hash.hh @@ -4,6 +4,7 @@ #define DUNE_COMMON_HASH_HH #include <dune/common/typetraits.hh> +#include <dune/common/static_assert.hh> #if HAVE_STD_HASH #include <functional> @@ -338,10 +339,12 @@ namespace Dune { // hash_combiner has to be specialized for the size (in bytes) of std::size_t. // Specialized versions should provide a method // - // template <typename T> - // void operator()(std::size_t& seed, const T& arg) const; + // template <typename typeof_size_t, typename T> + // void operator()(typeof_size_t& seed, const T& arg) const; // // that will be called by the interface function hash_combine() described further below. + // The redundant template parameter typeof_size_t is needed to avoid warnings for the + // unused 64-bit specialization on 32-bit systems. // // There is no default implementation! template<int sizeof_size_t> @@ -353,9 +356,11 @@ namespace Dune { struct hash_combiner<8> { - template<typename T> - void operator()(std::size_t& seed, const T& arg) const + template<typename typeof_size_t, typename T> + void operator()(typeof_size_t& seed, const T& arg) const { + dune_static_assert(sizeof(typeof_size_t)==8, "hash_combiner::operator() instantiated with nonmatching type and size"); + // The following algorithm for combining two 64-bit hash values is inspired by a similar // function in CityHash (http://cityhash.googlecode.com/svn-history/r2/trunk/src/city.h), // which is in turn based on ideas from the MurmurHash library. The basic idea is easy to @@ -370,11 +375,11 @@ namespace Dune { // an application that is frequent in PDELab's ordering framework. Dune::hash<T> hasher; - const std::size_t kMul = 0x9ddfea08eb382d69ULL; - std::size_t h = hasher(arg); - std::size_t a = (seed ^ h) * kMul; + const typeof_size_t kMul = 0x9ddfea08eb382d69ULL; + typeof_size_t h = hasher(arg); + typeof_size_t a = (seed ^ h) * kMul; a ^= (a >> 47); - std::size_t b = (h ^ a) * kMul; + typeof_size_t b = (h ^ a) * kMul; b ^= (b >> 47); b *= kMul; seed = b; @@ -388,9 +393,11 @@ namespace Dune { struct hash_combiner<4> { - template<typename T> - void operator()(std::size_t& seed, const T& arg) const + template<typename typeof_size_t, typename T> + void operator()(typeof_size_t& seed, const T& arg) const { + dune_static_assert(sizeof(typeof_size_t)==4, "hash_combiner::operator() instantiated with nonmatching type and size"); + // The default algorithm above requires a 64-bit std::size_t. The following algorithm is a // 32-bit compatible fallback, again inspired by CityHash and MurmurHash // (http://cityhash.googlecode.com/svn-history/r2/trunk/src/city.cc). @@ -399,11 +406,11 @@ namespace Dune { // taken from CityHash, in particular from the file referenced above. Dune::hash<T> hasher; - const std::size_t c1 = 0xcc9e2d51; - const std::size_t c2 = 0x1b873593; - const std::size_t c3 = 0xe6546b64; - std::size_t h = hasher(arg); - std::size_t a = seed * c1; + const typeof_size_t c1 = 0xcc9e2d51; + const typeof_size_t c2 = 0x1b873593; + const typeof_size_t c3 = 0xe6546b64; + typeof_size_t h = hasher(arg); + typeof_size_t a = seed * c1; a = (a >> 17) | (a << (32 - 17)); a *= c2; h ^= a; diff --git a/dune/common/mallocallocator.hh b/dune/common/mallocallocator.hh index daca655b8323e11462a1134d54196afb87c640e2..8b27c073708fe07fb7984babf3c1ca1cf3925807 100644 --- a/dune/common/mallocallocator.hh +++ b/dune/common/mallocallocator.hh @@ -7,6 +7,7 @@ #include <cstdlib> #include <new> #include <utility> +#include <dune/common/unused.hh> /** * @file @@ -53,6 +54,7 @@ namespace Dune pointer allocate(size_type n, const void* hint = 0) { + DUNE_UNUSED_PARAMETER(hint); if (n > this->max_size()) throw std::bad_alloc(); @@ -65,6 +67,7 @@ namespace Dune //! deallocate n objects of type T at address p void deallocate(pointer p, size_type n) { + DUNE_UNUSED_PARAMETER(n); std::free(p); } diff --git a/dune/common/parallel/CMakeLists.txt b/dune/common/parallel/CMakeLists.txt index 298789bce5fd502d012a6d844dd46edec0182e2d..609c7844b7127d16d5d5f72a5134af439928b2bc 100644 --- a/dune/common/parallel/CMakeLists.txt +++ b/dune/common/parallel/CMakeLists.txt @@ -15,5 +15,6 @@ install(FILES plocalindex.hh remoteindices.hh selection.hh + variablesizecommunicator.hh DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/dune/common/parallel) diff --git a/dune/common/parallel/Makefile.am b/dune/common/parallel/Makefile.am index 461560291b5d556e4acb99a94684891c5af2e49f..6c14fd0633a4dfc7852ec5cc90da8b104a971b41 100644 --- a/dune/common/parallel/Makefile.am +++ b/dune/common/parallel/Makefile.am @@ -16,7 +16,8 @@ parallelinclude_HEADERS = \ mpitraits.hh \ plocalindex.hh \ remoteindices.hh \ - selection.hh + selection.hh \ + variablesizecommunicator.hh include $(top_srcdir)/am/global-rules diff --git a/dune/common/parallel/collectivecommunication.hh b/dune/common/parallel/collectivecommunication.hh index 0099287c52e382fdd4004f15149d1c716f2be31c..d3c469a4f194d03e2710965200e30af01fa65a7e 100644 --- a/dune/common/parallel/collectivecommunication.hh +++ b/dune/common/parallel/collectivecommunication.hh @@ -18,9 +18,12 @@ /*! \defgroup ParallelCommunication Parallel Communication \ingroup Common + \brief Abstractions for paralle computing + Dune offers an abstraction to the basic methods of parallel communication. It allows to switch parallel features on and off, - without changing the code. + without changing the code. This is done using either CollectiveCommunication + or MPICollectiveCommunication. */ diff --git a/dune/common/parallel/communicator.hh b/dune/common/parallel/communicator.hh index 69c4fc1b78744b0956d67885ddefc1e588d4cd97..808f11a6dff86443da4ae2c0a5a7d1f48e919161 100644 --- a/dune/common/parallel/communicator.hh +++ b/dune/common/parallel/communicator.hh @@ -16,8 +16,8 @@ namespace Dune { - /** @defgroup Common_Parallel Communication for distributed computing - * @ingroup Common + /** @defgroup Common_Parallel Parallel Computing based on Indexsets + * @ingroup ParallelCommunication * @brief Provides classes for syncing distributed indexed * data structures. * @@ -75,9 +75,13 @@ namespace Dune * * Based on the information about the distributed index sets, data * independent interfaces between different sets of the index sets - * can be setup using the class Interface. For the actual communication it - * data dependant communicators can be setup using BufferedCommunicator or - * DatatypeCommunicator. + * can be setup using the class Interface. For the actual communication + * data dependant communicators can be setup using BufferedCommunicator, + * DatatypeCommunicator VariableSizeCommunicator based on the interface + * information. In contrast to the former + * the latter is independant of the class Interface can work on a map + * from process number to a pair of index lists describing which local indices + * are send and received from that processs, respectively. */ /** @addtogroup Common_Parallel * @@ -898,6 +902,8 @@ namespace Dune template<class V> inline int CommPolicy<V>::getSize(const V& v, int index) { + DUNE_UNUSED_PARAMETER(v); + DUNE_UNUSED_PARAMETER(index); return 1; } @@ -1232,7 +1238,7 @@ namespace Dune template<class Data> inline int BufferedCommunicator::MessageSizeCalculator<Data,SizeOne>::operator() - (const Data& data, const InterfaceInformation& info) const + (const Data&, const InterfaceInformation& info) const { return operator()(info); } @@ -1285,7 +1291,7 @@ namespace Dune template<class Data, class GatherScatter, bool FORWARD> - inline void BufferedCommunicator::MessageGatherer<Data,GatherScatter,FORWARD,SizeOne>::operator()(const InterfaceMap& interfaces, const Data& data, Type* buffer, size_t bufferSize) const + inline void BufferedCommunicator::MessageGatherer<Data,GatherScatter,FORWARD,SizeOne>::operator()(const InterfaceMap& interfaces, const Data& data, Type* buffer, size_t) const { typedef typename InterfaceMap::const_iterator const_iterator; diff --git a/dune/common/parallel/indexset.hh b/dune/common/parallel/indexset.hh index faa75bc8bebfcb9696e1fbdac921657432a7093b..09ab75eeb41ae537af19c51d6d4341ccddb019a5 100644 --- a/dune/common/parallel/indexset.hh +++ b/dune/common/parallel/indexset.hh @@ -7,6 +7,7 @@ #include <algorithm> #include <dune/common/arraylist.hh> #include <dune/common/exceptions.hh> +#include <dune/common/unused.hh> #include <iostream> #include "localindex.hh" @@ -613,6 +614,8 @@ namespace Dune struct LocalIndexComparator { static bool compare(const T& t1, const T& t2){ + DUNE_UNUSED_PARAMETER(t1); + DUNE_UNUSED_PARAMETER(t2); return false; } }; diff --git a/dune/common/parallel/indicessyncer.hh b/dune/common/parallel/indicessyncer.hh index 00c083737b29f430c9a378af79c833f68930791b..3dc513310241c7690e37c1a8611f7d9056a08a4e 100644 --- a/dune/common/parallel/indicessyncer.hh +++ b/dune/common/parallel/indicessyncer.hh @@ -9,6 +9,7 @@ #include <dune/common/stdstreams.hh> #include <dune/common/tuples.hh> #include <dune/common/sllist.hh> +#include <dune/common/unused.hh> #include <cassert> #include <cmath> #include <limits> @@ -143,6 +144,7 @@ namespace Dune */ std::size_t operator()(const GlobalIndex& global) { + DUNE_UNUSED_PARAMETER(global); return std::numeric_limits<size_t>::max(); } }; diff --git a/dune/common/parallel/interface.hh b/dune/common/parallel/interface.hh index dbc1f69c437cf373989ce44c0523798c0d7a05ca..f80a7f987dfe47019b84d642a3b0816a0d1c1970 100644 --- a/dune/common/parallel/interface.hh +++ b/dune/common/parallel/interface.hh @@ -208,9 +208,11 @@ namespace Dune { public: - typedef InterfaceInformation Information; - - typedef std::map<int,std::pair<Information,Information> > InformationMap; + /** + * @brief The type of the map form process number to InterfaceInformation for + * sending and receiving to and from it. + */ + typedef std::map<int,std::pair<InterfaceInformation,InterfaceInformation> > InformationMap; /** * @brief Builds the interface. diff --git a/dune/common/parallel/mpihelper.hh b/dune/common/parallel/mpihelper.hh index fedc945151da24f19f1d4647ee719825bb70cd5c..01325b249712f18b67e58f74ee6f9b4d53055313 100644 --- a/dune/common/parallel/mpihelper.hh +++ b/dune/common/parallel/mpihelper.hh @@ -129,6 +129,7 @@ namespace Dune */ DUNE_EXPORT static FakeMPIHelper& instance(int argc, char** argv) { + (void)argc; (void)argv; // create singleton instance static FakeMPIHelper singleton; return singleton; diff --git a/dune/common/parallel/test/CMakeLists.txt b/dune/common/parallel/test/CMakeLists.txt index b6134ad913186bcfaeef7c56ed65f8f64566f93f..6d851da6edec3f58b05f1b252413879716102b26 100644 --- a/dune/common/parallel/test/CMakeLists.txt +++ b/dune/common/parallel/test/CMakeLists.txt @@ -1,4 +1,4 @@ -set(MPITESTPROGS indicestest indexsettest syncertest selectiontest) +set(MPITESTPROGS indicestest indexsettest syncertest selectiontest variablesizecommunicatortest) add_directory_test_target(_test_target) # We do not want want to build the tests during make all, @@ -21,7 +21,12 @@ add_executable("syncertest" syncertest.cc) target_link_libraries("syncertest" "dunecommon") add_dune_mpi_flags(syncertest) +add_executable("variablesizecommunicatortest" variablesizecommunicatortest.cc) +target_link_libraries("variablesizecommunicatortest" "dunecommon") +add_dune_mpi_flags(variablesizecommunicatortest) + add_test(indexsettest indexsettest) add_test(selectiontest selectiontest) add_test(indicestest indicestest) add_test(syncertest syncertest) +add_test(variablesizecommunicatortest variablesizecommunicatortest) diff --git a/dune/common/parallel/test/Makefile.am b/dune/common/parallel/test/Makefile.am index 23b658707cb697e11993a7fbfb1d0cdc0f7d3756..b8a01e3d7cec0c4f54264825925b0b2c51b68652 100644 --- a/dune/common/parallel/test/Makefile.am +++ b/dune/common/parallel/test/Makefile.am @@ -1,6 +1,10 @@ # $Id$ -MPITESTS = indicestest indexsettest syncertest selectiontest +MPITESTS = indicestest \ + indexsettest \ + syncertest \ + selectiontest \ + variablesizecommunicatortest # which tests where program to build and run are equal NORMALTESTS = @@ -44,6 +48,19 @@ syncertest_LDADD = \ $(DUNEMPILIBS) \ $(LDADD) + +variablesizecommunicatortest_SOURCES = variablesizecommunicatortest.cc +variablesizecommunicatortest_CPPFLAGS = $(AM_CPPFLAGS) \ + $(DUNEMPICPPFLAGS) \ + $(DUNE_COMMON_CPPFLAGS) +variablesizecommunicatortest_LDFLAGS = $(AM_LDFLAGS) \ + $(DUNEMPILDFLAGS) \ + $(DUNE_COMMON_LDFLAGS) +variablesizecommunicatortest_LDADD = \ + $(DUNE_COMMON_LDFLAGS) $(DUNE_COMMON_LIBS) \ + $(DUNEMPILIBS) \ + $(LDADD) + include $(top_srcdir)/am/global-rules EXTRA_DIST = CMakeLists.txt diff --git a/dune/common/parallel/test/indexsettest.cc b/dune/common/parallel/test/indexsettest.cc index 45510314b986dd10991a5cc0c87f9bec5f62f52d..24b320aca04813a115fc982bc64438df7a62c860 100644 --- a/dune/common/parallel/test/indexsettest.cc +++ b/dune/common/parallel/test/indexsettest.cc @@ -77,7 +77,7 @@ int testDeleteIndices() return ret; } -int main(int argc, char **argv) +int main(int, char **) { std::exit(testDeleteIndices()); } diff --git a/dune/common/parallel/test/indicestest.cc b/dune/common/parallel/test/indicestest.cc index 4345d673264c463ce6c77d35c21559be91b04aff..4fbc23b310dc0029360c9fb4b5b5be8b773c54f8 100644 --- a/dune/common/parallel/test/indicestest.cc +++ b/dune/common/parallel/test/indicestest.cc @@ -657,6 +657,7 @@ public: }; void MPI_err_handler(MPI_Comm *comm, int *err_code, ...){ + DUNE_UNUSED_PARAMETER(comm); char *err_string=new char[MPI_MAX_ERROR_STRING]; int err_length; MPI_Error_string(*err_code, err_string, &err_length); diff --git a/dune/common/parallel/test/syncertest.cc b/dune/common/parallel/test/syncertest.cc index 1c15b5eaa719e729a0ae8f4584f7d6dd71dc20ce..5a7b6efc608a908dbbf1dec27582f57a00baf028 100644 --- a/dune/common/parallel/test/syncertest.cc +++ b/dune/common/parallel/test/syncertest.cc @@ -335,6 +335,7 @@ public: }; void MPI_err_handler(MPI_Comm *comm, int *err_code, ...){ + DUNE_UNUSED_PARAMETER(comm); char *err_string=new char[MPI_MAX_ERROR_STRING]; int err_length; MPI_Error_string(*err_code, err_string, &err_length); diff --git a/dune/common/parallel/test/variablesizecommunicatortest.cc b/dune/common/parallel/test/variablesizecommunicatortest.cc new file mode 100644 index 0000000000000000000000000000000000000000..6bb634d9339136fecb904f9c79068d9c69b1bb8c --- /dev/null +++ b/dune/common/parallel/test/variablesizecommunicatortest.cc @@ -0,0 +1,189 @@ +#include"config.h" +#include<iostream> +#if HAVE_MPI +#include<mpi.h> +#endif +struct MyDataHandle +{ + MyDataHandle(int r) + : rank(r) + { + } + int rank; + + typedef double DataType; + + bool fixedsize() + { + return true; + } + template<class B> + void gather(B& buffer, int i) + { + std::cout<<rank<<": Gathering "<<i<<std::endl; + double d=i; + buffer.write(d); + buffer.write(d); + buffer.write(d); + } + template<class B> + void scatter(B& buffer, int i, int size) + { + std::cout<<rank<<": Scattering "<<size<<" entries for "<<i<<": "; + for(;size>0;--size) + { + double index; + buffer.read(index); + std::cout<<index<<" "; + } + std::cout<<std::endl; + } + std::size_t size(int i) + { + DUNE_UNUSED_PARAMETER(i); + return 3; + } +}; + +struct VarDataHandle +{ + VarDataHandle(int r) + : rank(r) + {} + int rank; + typedef double DataType; + bool fixedsize() + { + return false; + } + + template<class B> + void gather(B& buffer, int i) + { + std::size_t s=i%5; + std::cout<<rank<<": Gathering "<<s<<" entries for index "<<i<<std::endl; + for(std::size_t j=0; j<s; j++) + buffer.write(static_cast<double>(i+j)); + } + template<class B> + void scatter(B& buffer, int i, int size) + { + std::cout<<rank<<": Scattering "<<size<<" entries for "<<i<<": "; + for(;size>0;--size) + { + double index; + buffer.read(index); + std::cout<<index<<" "; + } + std::cout<<std::endl; + } + std::size_t size(int i) + { + return i%5; + } + +}; + +#include<dune/common/parallel/variablesizecommunicator.hh> + +int main(int argc, char** argv) +{ +#if HAVE_MPI + MPI_Init(&argc, &argv); + int procs, rank; + MPI_Comm_rank(MPI_COMM_WORLD, &rank); + MPI_Comm_size(MPI_COMM_WORLD, &procs); + if(procs==1) + { + typedef Dune::VariableSizeCommunicator<>::InterfaceMap Interface; + Dune::InterfaceInformation send, recv; + send.reserve(6); + for(std::size_t i=0; i<=10; i+=2) + send.add(i); + + recv.reserve(6); + for(std::size_t i=10; i<=10; i-=2) + recv.add(i); + Interface inf; + inf[0]=std::make_pair(send, recv); + Dune::VariableSizeCommunicator<> comm(MPI_COMM_SELF, inf, 6); + MyDataHandle handle(0); + comm.forward(handle); + std::cout<<"===================== backward ========================="<<std::endl; + comm.backward(handle); + std::cout<<"================== variable size ======================="<<std::endl; + VarDataHandle vhandle(0); + comm.forward(vhandle); + std::cout<<"===================== backward ========================="<<std::endl; + comm.backward(vhandle); + } + else + { + int N=100000; + int num_per_proc=N/procs; + int start, end; + if(rank<N%procs) + { + start=rank*(num_per_proc+1); + end=(rank+1)*(num_per_proc+1); + } + else + { + start=(N%procs)+rank*(num_per_proc); + end=start+num_per_proc; + } + if(rank==procs-1) + assert(N==end); + typedef Dune::VariableSizeCommunicator<>::InterfaceMap Interface; + Interface inf; + if(rank) + { + Dune::InterfaceInformation send, recv; + send.reserve(2); + recv.reserve(2); + send.add(start-1); + send.add(start); + recv.add(start-1); + recv.add(start); + inf[rank-1]=std::make_pair(send, recv); + } + if(rank<procs-1) + { + + Dune::InterfaceInformation send, recv; + send.reserve(2); + recv.reserve(2); + send.add(end-1); + send.add(end); + recv.add(end-1); + recv.add(end); + inf[rank+1]=std::make_pair(send, recv); + } + Dune::VariableSizeCommunicator<> comm(MPI_COMM_WORLD, inf, 6); + MyDataHandle handle(rank); + comm.forward(handle); + MPI_Barrier(MPI_COMM_WORLD); + if(rank==0) + std::cout<<"===================== backward ========================="<<std::endl; + MPI_Barrier(MPI_COMM_WORLD); + comm.backward(handle); + MPI_Barrier(MPI_COMM_WORLD); + if(rank==0) + std::cout<<"================== variable size ======================="<<std::endl; + MPI_Barrier(MPI_COMM_WORLD); + + VarDataHandle vhandle(rank); + MPI_Barrier(MPI_COMM_WORLD); + comm.forward(vhandle); + MPI_Barrier(MPI_COMM_WORLD); + if(rank==0) + std::cout<<"===================== backward ========================="<<std::endl; + comm.backward(vhandle); + } + + MPI_Finalize(); +#else + std::cerr<<"Skipping as MPI seems not be available"<<std::endl; + return 77; +#endif +} diff --git a/dune/common/parallel/variablesizecommunicator.hh b/dune/common/parallel/variablesizecommunicator.hh new file mode 100644 index 0000000000000000000000000000000000000000..5fac8da398c3bb75aa040ca9c6163c91b7b1ead5 --- /dev/null +++ b/dune/common/parallel/variablesizecommunicator.hh @@ -0,0 +1,1155 @@ +// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- +// vi: set et ts=4 sw=2 sts=2: +#ifndef DUNE_COMMON_PARALLEL_VARIABLESIZECOMMUNICATOR_HH // Still fits the line! +#define DUNE_COMMON_PARALLEL_VARIABLESIZECOMMUNICATOR_HH + +#if HAVE_MPI +// MPI header +#include <mpi.h> +#include <vector> +#include <map> +#include <functional> +#include <dune/common/unused.hh> +#include "interface.hh" +#include "mpitraits.hh" + +/** + * @addtogroup Common_Parallel + * + * @{ + */ +/** + * @file + * @brief A communicator that only needs to know the number of elements per + * index at the sender side. + * @author Markus Blatt + * @} + */ +namespace Dune +{ + +namespace +{ +/** + * @brief A message buffer. + * @tparam T The type of data that the buffer will hold. + */ +template<class T, class Allocator=std::allocator<T> > +class MessageBuffer +{ +public: + /** + * @brief Constructs a message. + * @param size The number of elements that buffer should hold, + */ + explicit MessageBuffer(int size) + : buffer_(new T[size]), size_(size), position_(0) + {} + /** + * @brief Copy constructor. + * @param o The instance to copy. + */ + explicit MessageBuffer(const MessageBuffer& o) + : buffer_(new T[o.size_]), size_(o.size_), position_(o.position_) + { + } + /** @brief Destructor. */ + ~MessageBuffer() + { + delete[] buffer_; + } + /** + * @brief Write an item to the buffer. + * @param data The data item to write. + */ + void write(const T& data) + { + buffer_[position_++]=data; + } + + /** + * @brief Reads a data item from the buffer + * @param[out] data Reference to where to store the read data. + */ + void read(T& data) + { + data=buffer_[position_++]; + } + + /** + * @brief Reset the buffer. + * + * On return the buffer will be positioned at the start again. + */ + void reset() + { + position_=0; + } + + /** + * @brief Test whether the whole buffer was read. + * @return True if we read or wrot until the end of the buffer. + */ + bool finished() + { + return position_==size_; + } + + /** + * @brief Tests whether the buffer has enough space left to read/write data. + * @param notItems The number of items to read or write. + * @return True if there is enough space for noItems items. + */ + bool hasSpaceForItems(int noItems) + { + return position_+noItems<=size_; + } + /** + * @brief Get the size of the buffer. + * @return The number of elements the buffer can hold. + */ + std::size_t size() const + { + return size_; + } + /** + * @brief Converts the buffer to a C array. + * @return The underlying C array. + */ + operator T*() + { + return buffer_; + } + +private: + /** + * @brief Pointer to the current insertion point of the buffer. + */ + T* buffer_; + /** + * @brief The size of the buffer + */ + std::size_t size_; + /** + * @brief The current position in the buffer. + */ + std::size_t position_; +}; + +/** + * @brief A tracker for the current position in a communication interface. + */ +class InterfaceTracker +{ +public: + /** + * @brief Constructor. + * @param rank The other rank that the interface communicates with. + * @param info A list of local indices belonging to this interface. + */ + InterfaceTracker(int rank, InterfaceInformation info, std::size_t fixedsize=0, + bool allocateSizes=false) + : fixedSize(fixedsize),rank_(rank), index_(), interface_(info), sizes_(), + sizesAllocated_(allocateSizes) + { + if(allocateSizes) + { + sizes_.resize(info.size()); + } + } + + /** + * @brief Moves to the next index in the interface. + */ + void moveToNextIndex() + { + index_++; + assert(index_<=interface_.size()); + skipZeroIndices(); + } + /** + * @brief Increment index various times. + * @param i The number of times to increment. + */ + void increment(std::size_t i) + { + index_+=i; + assert(index_<=interface_.size()); + } + /** + * @brief Checks whether all indices have been visited. + * @return True if all indices have been visited. + */ + bool finished() const + { + return index_==interface_.size(); + } + + void skipZeroIndices() + { + // skip indices with size zero! + while(sizes_.size() && index_!=interface_.size() &&!size()) + ++index_; + } + + /** + * @brief Get the current local index of the interface. + * @return The current local index of the interface. + */ + std::size_t index() const + { + return interface_[index_]; + } + /** + * @brief Get the size at the current index. + */ + std::size_t size() const + { + assert(sizes_.size()); + return sizes_[index_]; + } + /** + * @brief Get a pointer to the array with the sizes. + */ + std::size_t* getSizesPointer() + { + return &sizes_[0]; + } + /** + * @brief Returns whether the interface is empty. + * @return True if there are no entries in the interface. + */ + bool empty() const + { + return !interface_.size(); + } + + /** + * @brief Checks whether there are still indices waiting to be processed. + * @return True if there are still indices waiting to be processed. + */ + std::size_t indicesLeft() const + { + return interface_.size()-index_; + } + /** + * @brief The number of data items per index if it is fixed, 0 otherwise. + */ + std::size_t fixedSize; + /** + * @brief Get the process rank that this communication interface is with. + */ + int rank() const + { + return rank_; + } + /** + * @brief Get the offset to the first index. + */ + std::size_t offset() const + { + return index_; + } +private: + /** @brief The process rank that this communication interface is with. */ + int rank_; + /** @brief The other rank that this interface communcates with. */ + std::size_t index_; + /** @brief The list of local indices of this interface. */ + InterfaceInformation interface_; + std::vector<std::size_t> sizes_; + bool sizesAllocated_; +}; + + +} // end unnamed namespace + +/** + * @addtogroup Common_Parallel + * + * @{ + */ +/** + * @brief A buffered communicator where the amount of data sent does not have to be known a priori. + * + * In contrast to BufferedCommunicator the amount of data is determined by the container + * whose entries are sent and not known at the receiving side a priori. + */ +template<class Allocator=std::allocator<std::pair<InterfaceInformation,InterfaceInformation> > > +class VariableSizeCommunicator +{ +public: + /** + * @brief The type of the map form process number to InterfaceInformation for + * sending and receiving to and from it. + */ + typedef std::map<int,std::pair<InterfaceInformation,InterfaceInformation>, + std::less<int>, + typename Allocator::template rebind<std::pair<const int,std::pair<InterfaceInformation,InterfaceInformation> > >::other> InterfaceMap; + +#ifndef DUNE_PARALLEL_MAX_COMMUNICATION_BUFFER_SIZE + /** + * @brief Creates a communicator with the default maximum buffer size. + * + * The default size ist either what the macro DUNE_MAX_COMMUNICATION_BUFFER_SIZE + * is set to or 32768 if is not set. + */ + VariableSizeCommunicator(MPI_Comm comm, const InterfaceMap& inf) + : maxBufferSize_(32768), interface_(&inf) + { + MPI_Comm_dup(comm, &communicator_); + } + /** + * @brief Creates a communicator with the default maximum buffer size. + * @param inf The communication interface. + */ + VariableSizeCommunicator(const Interface& inf) + : maxBufferSize_(32768), interface_(&inf.interfaces()) + { + MPI_Comm_dup(inf.communicator(), &communicator_); + } +#else + /** + * @brief Creates a communicator with the default maximum buffer size. + * + * The default size ist either what the macro DUNE_MAX_COMMUNICATION_BUFFER_SIZE + * is set to or 32768 if is not set. + */ + VariableSizeCommunicator(MPI_Comm comm, InterfaceMap& inf) + : maxBufferSize_(DUNE_PARALLEL_MAX_COMMUNICATION_BUFFER_SIZE), + interface_(&inf) + { + MPI_Comm_dup(comm, &communicator_); + } + /** + * @brief Creates a communicator with the default maximum buffer size. + * @param inf The communication interface. + */ + VariableSizeCommunicator(const Interface& inf) + : maxBufferSize_(DUNE_PARALLEL_MAX_COMMUNICATION_BUFFER_SIZE), + interface_(&inf.interfaces()) + { + MPI_Comm_dup(inf.communicator(), &communicator_); + } +#endif + /** + * @brief Creates a communicator with a specific maximum buffer size. + * @param comm The MPI communicator to use. + * @param inf The communication interface. + * @param max_buffer_size The maximum buffer size allowed. + */ + VariableSizeCommunicator(MPI_Comm comm, const InterfaceMap& inf, std::size_t max_buffer_size) + : maxBufferSize_(max_buffer_size), interface_(&inf) + { + MPI_Comm_dup(comm, &communicator_); + } + + /** + * @brief Creates a communicator with a specific maximum buffer size. + * @param inf The communication interface. + * @param max_buffer_size The maximum buffer size allowed. + */ + VariableSizeCommunicator(const Interface& inf, std::size_t max_buffer_size) + : maxBufferSize_(max_buffer_size), interface_(&inf.interfaces()) + { + MPI_Comm_dup(inf.communicator(), &communicator_); + } + + ~VariableSizeCommunicator() + { + MPI_Comm_free(&communicator_); + } + + + /** + * @brief Communicate forward. + * + * @tparam DataHandle The type of the handle describing the data. This type has to adhere + * to the following interface: + * \code{.cpp} + * // returns whether the number of data items per entry is fixed + * bool fixedsize(); + * // get the number of data items for an entry with index i + * std::size_t size(std::size_t i); + * // gather the data at index i + * template<class MessageBuffer> + * void gather(MessageBuffer& buf, std::size_t i); + * // scatter the n data items to index i + * template<class MessageBuffer> + * void scatter(MessageBuffer& buf, std::size_t i, std::size_t n); + * \endcode + * @param handle A handle responsible for describing the data, gathering, and scattering it. + */ + template<class DataHandle> + void forward(DataHandle& handle) + { + communicate<true>(handle); + } + + /** + * @brief Communicate backwards. + * + * @tparam DataHandle The type of the handle describing the data. This type has to adhere + * to the following interface: + * \code{.cpp} + * // returns whether the number of data items per entry is fixed + * bool fixedsize(); + * // get the number of data items for an entry with index i + * std::size_t size(std::size_t i); + * // gather the data at index i + * template<class MessageBuffer> + * void gather(MessageBuffer& buf, std::size_t i); + * // scatter the n data items to index i + * template<class MessageBuffer> + * void scatter(MessageBuffer& buf, std::size_t i, std::size_t n); + * \endcode + * @param handle A handle responsible for describing the data, gathering, and scattering it. + */ + template<class DataHandle> + void backward(DataHandle& handle) + { + communicate<false>(handle); + } + +private: + template<bool FORWARD, class DataHandle> + void communicateSizes(DataHandle& handle, + std::vector<InterfaceTracker>& recv_trackers); + + /** + * @brief Communicates data according to the interface. + * @tparam forward If true sends data forwards, otherwise backwards along the interface. + * @tparame DataHandle The type of the data handle @see forward for a description of the interface. + * @param handle The handle describing the data and responsible for gather and scatter operations. + */ + template<bool forward,class DataHandle> + void communicate(DataHandle& handle); + /** + * @brief Initialize the the trackers along the interface for the communication. + * @tparam FORWARD If true we send in the forward direction. + * @tparam DataHandle DataHandle The type of the data handle. + * @param handle The handle describing the data and responsible for gather + * and scatter operations. + * @param[out] send_trackers The trackers for the sending side. + * @param[out] recv_trackers The trackers for the receiving side. + */ + template<bool FORWARD, class DataHandle> + void setupInterfaceTrackers(DataHandle& handle, + std::vector<InterfaceTracker>& send_trackers, + std::vector<InterfaceTracker>& recv_trackers); + /** + * @brief Communicate data with a fixed amount of data per entry. + * @tparam FORWARD If true we send in the forward direction. + * @tparam DataHandle DataHandle The type of the data handle. + * @param handle The handle describing the data and responsible for gather + * and scatter operations. + */ + template<bool FORWARD, class DataHandle> + void communicateFixedSize(DataHandle& handle); + /** + * @brief Communicate data with a variable amount of data per entry. + * @tparam FORWARD If true we send in the forward direction. + * @tparam DataHandle DataHandle The type of the data handle. + * @param handle The handle describing the data and responsible for gather + * and scatter operations. + */ + template<bool FORWARD, class DataHandle> + void communicateVariableSize(DataHandle& handle); + /** + * @brief The maximum size if the buffers used for gather and scatter. + * + * @note If this process has n neighbours, then a maximum of 2n buffers of this size + * is allocate. Memory needed will be n*sizeof(std::size_t)+n*sizeof(Datahandle::DataType) + */ + std::size_t maxBufferSize_; + /** + * @brief description of the interface. + * + * This is a map of the neighboring process number to a pair of local index lists. + * The first is a list of indices to gather data for sending from and the second is a list of + * indices to scatter received data to during forward. + */ + const InterfaceMap* interface_; + /** + * @brief The communicator. + * + * This is a cloned communicator to ensure there are no interferences. + */ + MPI_Comm communicator_; +}; + +/** @} */ +namespace +{ +/** + * @brief A data handle for comunicating the sizes of variable sized data. + */ +template<class DataHandle> +class SizeDataHandle +{ +public: + typedef std::size_t DataType; + + SizeDataHandle(DataHandle& data, + std::vector<InterfaceTracker>& trackers) + : data_(data), trackers_(trackers), index_() + {} + bool fixedsize() + { + return true; + } + std::size_t size(std::size_t i) + { + DUNE_UNUSED_PARAMETER(i); + return 1; + } + template<class B> + void gather(B& buf, int i) + { + buf.write(data_.size(i)); + } + void setReceivingIndex(std::size_t i) + { + index_=i; + } + std::size_t* getSizesPointer() + { + return trackers_[index_].getSizesPointer(); + } + +private: + DataHandle& data_; + std::vector<InterfaceTracker>& trackers_; + int index_; +}; + +template<class T> +void setReceivingIndex(T&, int) +{} + +template<class T> +void setReceivingIndex(SizeDataHandle<T>& t, int i) +{ + t.setReceivingIndex(i); +} + + +/** + * @brief Template meta program for choosing then send or receive interface + * information based on the direction. + * @tparam FORWARD If true the communication happens in the forward direction. + */ +template<bool FORWARD> +struct InterfaceInformationChooser +{ + /** + * @brief Get the interface information for the sending side. + */ + static const InterfaceInformation& + getSend(const std::pair<InterfaceInformation,InterfaceInformation>& info) + { + return info.first; + } + + /** + * @brief Get the interface information for the receiving side. + */ + static const InterfaceInformation& + getReceive(const std::pair<InterfaceInformation,InterfaceInformation>& info) + { + return info.second; + } +}; + +template<> +struct InterfaceInformationChooser<false> +{ + static const InterfaceInformation& + getSend(const std::pair<InterfaceInformation,InterfaceInformation>& info) + { + return info.second; + } + + static const InterfaceInformation& + getReceive(const std::pair<InterfaceInformation,InterfaceInformation>& info) + { + return info.first; + } +}; + +/** + * @brief A functor that packs entries into the message buffer. + * @tparam DataHandle The type of the data handle that describes + * the communicated data. + */ +template<class DataHandle> +struct PackEntries +{ + + int operator()(DataHandle& handle, InterfaceTracker& tracker, + MessageBuffer<typename DataHandle::DataType>& buffer, + int i) const + { + return operator()(handle,tracker,buffer); + } + + /** + * @brief packs data. + * @param handle The handle describing the data and the gather and scatter operations. + * @param tracker The tracker of the interface to tell us where we are. + * @param buffer The buffer to use for packing. + * @return The number data entries that we packed. + */ + int operator()(DataHandle& handle, InterfaceTracker& tracker, + MessageBuffer<typename DataHandle::DataType>& buffer) const + { + if(tracker.fixedSize) // fixed size if variable is >0! + { + + std::size_t noIndices=std::min(buffer.size()/tracker.fixedSize, tracker.indicesLeft()); + for(std::size_t i=0; i< noIndices; ++i) + { + handle.gather(buffer, tracker.index()); + tracker.moveToNextIndex(); + } + return noIndices*tracker.fixedSize; + } + else + { + int packed=0; + tracker.skipZeroIndices(); + while(!tracker.finished()) + if(buffer.hasSpaceForItems(handle.size(tracker.index()))) + { + handle.gather(buffer, tracker.index()); + packed+=handle.size(tracker.index()); + tracker.moveToNextIndex(); + } + else + break; + assert(packed); + return packed; + } + } +}; + +/** + * @brief A functor that unpacks entries from the message buffer. + * @tparam DataHandle The type of the data handle that describes + * the communicated data. + */ +template<class DataHandle> +struct UnpackEntries{ + + /** + * @brief packs data. + * @param handle The handle describing the data and the gather and scatter operations. + * @param tracker The tracker of the interface to tell us where we are. + * @param buffer The buffer to use for packing. + * @return The number data entries that we packed. + */ + bool operator()(DataHandle& handle, InterfaceTracker& tracker, + MessageBuffer<typename DataHandle::DataType>& buffer, + int count=0) + { + if(tracker.fixedSize) // fixed size if variable is >0! + { + std::size_t noIndices=std::min(buffer.size()/tracker.fixedSize, tracker.indicesLeft()); + + for(std::size_t i=0; i< noIndices; ++i) + { + handle.scatter(buffer, tracker.index(), tracker.fixedSize); + tracker.moveToNextIndex(); + } + return tracker.finished(); + } + else + { + assert(count); + for(int unpacked=0;unpacked<count;) + { + assert(!tracker.finished()); + assert(buffer.hasSpaceForItems(tracker.size())); + handle.scatter(buffer, tracker.index(), tracker.size()); + unpacked+=tracker.size(); + tracker.moveToNextIndex(); + } + return tracker.finished(); + } + } +}; + + +/** + * @brief A functor that unpacks std::size_t from the message buffer. + */ +template<class DataHandle> +struct UnpackSizeEntries{ + + /** + * @brief packs data. + * @param handle The handle describing the data and the gather and scatter operations. + * @param tracker The tracker of the interface to tell us where we are. + * @param buffer The buffer to use for packing. + * @return The number data entries that we packed. + */ + bool operator()(SizeDataHandle<DataHandle>& handle, InterfaceTracker& tracker, + MessageBuffer<typename SizeDataHandle<DataHandle>::DataType>& buffer) const + { + std::size_t noIndices=std::min(buffer.size(), tracker.indicesLeft()); + std::copy(static_cast<std::size_t*>(buffer), static_cast<std::size_t*>(buffer)+noIndices, + handle.getSizesPointer()+tracker.offset()); + tracker.increment(noIndices); + return noIndices; + } + bool operator()(SizeDataHandle<DataHandle>& handle, InterfaceTracker& tracker, + MessageBuffer<typename SizeDataHandle<DataHandle>::DataType>& buffer, int) const + { + return operator()(handle,tracker,buffer); + } +}; + +/** + * @brief Sends the size in case of communicating a fixed amount of data per entry. + * @param[in] send_trackers The trackers for the sending side. + * @param[out] send_requests The request for the asynchronous send operations. + * @param[in] recv_trackers The trackers for the receiving side. + * @param[out] recv_requests The request for the asynchronous receive operations. + */ +void sendFixedSize(std::vector<InterfaceTracker>& send_trackers, + std::vector<MPI_Request>& send_requests, + std::vector<InterfaceTracker>& recv_trackers, + std::vector<MPI_Request>& recv_requests, + MPI_Comm communicator) +{ + typedef std::vector<InterfaceTracker>::iterator TIter; + std::vector<MPI_Request>::iterator mIter=recv_requests.begin(); + + for(TIter iter=recv_trackers.begin(), end=recv_trackers.end(); iter!=end; + ++iter, ++mIter) + { + MPI_Irecv(&(iter->fixedSize), 1, MPITraits<std::size_t>::getType(), + iter->rank(), 933881, communicator, &(*mIter)); + } + + // Send our size to all neighbours using non-blocking synchronous communication. + std::vector<MPI_Request>::iterator mIter1=send_requests.begin(); + for(TIter iter=send_trackers.begin(), end=send_trackers.end(); + iter!=end; + ++iter, ++mIter1) + { + MPI_Issend(&(iter->fixedSize), 1, MPITraits<std::size_t>::getType(), + iter->rank(), 933881, communicator, &(*mIter1)); + } +} + + +/** + * @brief Functor for setting up send requests. + * @tparam DataHandle The type of the data handle for describing the data. + */ +template<class DataHandle> +struct SetupSendRequest{ + void operator()(DataHandle& handle, + InterfaceTracker& tracker, + MessageBuffer<typename DataHandle::DataType>& buffer, + MPI_Request& request, + MPI_Comm comm) const + { + buffer.reset(); + int size=PackEntries<DataHandle>()(handle, tracker, buffer); + // Skip indices of zero size. + while(!tracker.finished() && !handle.size(tracker.index())) + tracker.moveToNextIndex(); + if(size) + MPI_Issend(buffer, size, MPITraits<typename DataHandle::DataType>::getType(), + tracker.rank(), 933399, comm, &request); + } +}; + + +/** + * @brief Functor for setting up receive requests. + * @tparam DataHandle The type of the data handle for describing the data. + */ +template<class DataHandle> +struct SetupRecvRequest{ + void operator()(DataHandle& /*handle*/, + InterfaceTracker& tracker, + MessageBuffer<typename DataHandle::DataType>& buffer, + MPI_Request& request, + MPI_Comm comm) const + { + buffer.reset(); + if(tracker.indicesLeft()) + MPI_Irecv(buffer, buffer.size(), MPITraits<typename DataHandle::DataType>::getType(), + tracker.rank(), 933399, comm, &request); + } +}; + +/** + * @brief A functor that does nothing. + */ +template<class DataHandle> +struct NullPackUnpackFunctor +{ + int operator()(DataHandle&, InterfaceTracker&, + MessageBuffer<typename DataHandle::DataType>&, int) + { + return 0; + } + int operator()(DataHandle&, InterfaceTracker&, + MessageBuffer<typename DataHandle::DataType>&) + { + return 0; + } +}; + +/** + * @brief Check whether some of the requests finished and continue send/receive operation. + * @tparam DataHandle The type of the data handle describing the data. + * @tparam BufferFunctor A functor that packs or unpacks data from the buffer. + * E.g. NullPackUnpackFunctor. + * @tparam CommunicationFuntor A functor responsible for continuing the communication. + * @param handle The data handle describing the data. + * @param trackers The trackers indicating the current position in the communication. + * @param requests The requests to test whether they finished. + * @param requests2 The requests to use for setting up the continuing communication. Might + * be the same as requests. + * @param comm The MPI communicator to use. + * @param buffer_func The functor that does the packing or unpacking of the data. + */ +template<class DataHandle, class BufferFunctor, class CommunicationFunctor> +std::size_t checkAndContinue(DataHandle& handle, + std::vector<InterfaceTracker>& trackers, + std::vector<MPI_Request>& requests, + std::vector<MPI_Request>& requests2, + std::vector<MessageBuffer<typename DataHandle::DataType> >& buffers, + MPI_Comm comm, + BufferFunctor buffer_func, + CommunicationFunctor comm_func, + bool valid=true, + bool getCount=false) +{ + std::size_t size=requests.size(); + std::vector<MPI_Status> statuses(size); + int no_completed; + std::vector<int> indices(size, -1); // the indices for which the communication finished. + + MPI_Testsome(size, &(requests[0]), &no_completed, &(indices[0]), &(statuses[0])); + indices.resize(no_completed); + for(std::vector<int>::iterator index=indices.begin(), end=indices.end(); + index!=end; ++index) + { + InterfaceTracker& tracker=trackers[*index]; + setReceivingIndex(handle, *index); + if(getCount) + { + // Get the number of entries received + int count; + MPI_Get_count(&(statuses[index-indices.begin()]), + MPITraits<typename DataHandle::DataType>::getType(), + &count); + // Communication completed, we can reuse the buffers, e.g. unpack or repack + buffer_func(handle, tracker, buffers[*index], count); + }else + buffer_func(handle, tracker, buffers[*index]); + tracker.skipZeroIndices(); + if(!tracker.finished()){ + // Maybe start another communication. + comm_func(handle, tracker, buffers[*index], requests2[*index], comm); + tracker.skipZeroIndices(); + if(valid) + no_completed-=!tracker.finished(); // communication not finished, decrement counter for finished ones. + } + } + return no_completed; + +} + +/** + * @brief Receive the size per data entry and set up requests for receiving the data. + * @tparam DataHandle The type of the data handle. + * @param trackers The trackers indicating the indices where we send and from which rank. + * @param size_requests The requests for receiving the size. + * @param data_requests The requests for sending the data. + * @param buffers The buffers to use for sending. + * @param comm The mpi communicator to use. + */ +template<class DataHandle> +std::size_t receiveSizeAndSetupReceive(DataHandle& handle, + std::vector<InterfaceTracker>& trackers, + std::vector<MPI_Request>& size_requests, + std::vector<MPI_Request>& data_requests, + std::vector<MessageBuffer<typename DataHandle::DataType> >& buffers, + MPI_Comm comm) +{ + return checkAndContinue(handle, trackers, size_requests, data_requests, buffers, comm, + NullPackUnpackFunctor<DataHandle>(), SetupRecvRequest<DataHandle>(), false); +} + +/** + * @brief Check whether send request completed and continue sending if necessary. + * @tparam DataHandle The type of the data handle. + * @param trackers The trackers indicating the indices where we send and from which rank. + * @param requests The requests for the asynchronous communication. + * @param buffers The buffers to use for sending. + * @param comm The mpi communicator to use. + */ +template<class DataHandle> +std::size_t checkSendAndContinueSending(DataHandle& handle, + std::vector<InterfaceTracker>& trackers, + std::vector<MPI_Request>& requests, + std::vector<MessageBuffer<typename DataHandle::DataType> >& buffers, + MPI_Comm comm) +{ + return checkAndContinue(handle, trackers, requests, requests, buffers, comm, + NullPackUnpackFunctor<DataHandle>(), SetupSendRequest<DataHandle>()); +} + +/** + * @brief Check whether receive request completed and continue receiving if necessary. + * @tparam DataHandle The type of the data handle. + * @param trackers The trackers indicating the indices where we receive and from which rank. + * @param requests The requests for the asynchronous communication. + * @param buffers The buffers to use for receiving. + * @param comm The mpi communicator to use. + */ +template<class DataHandle> +std::size_t checkReceiveAndContinueReceiving(DataHandle& handle, + std::vector<InterfaceTracker>& trackers, + std::vector<MPI_Request>& requests, + std::vector<MessageBuffer<typename DataHandle::DataType> >& buffers, + MPI_Comm comm) +{ + return checkAndContinue(handle, trackers, requests, requests, buffers, comm, + UnpackEntries<DataHandle>(), SetupRecvRequest<DataHandle>(), + true, !handle.fixedsize()); +} + + +bool validRecvRequests(const std::vector<MPI_Request> reqs) +{ + for(std::vector<MPI_Request>::const_iterator i=reqs.begin(), end=reqs.end(); + i!=end; ++i) + if(*i!=MPI_REQUEST_NULL) + return true; + return false; +} + +/** + * @brief Sets up all the send requests for the data. + * @tparam DataHandle The type of the data handle. + * @tparam Functor The type of the functor to set up the request. + * @param handle The data handle describing the data. + * @param trackers The trackers for the communication interfaces. + * @param buffers The buffers for the comunication. One for each neighbour. + * @param requests The send requests for each neigbour. + * @param setupFunctor The functor responsible for setting up the request. + */ +template<class DataHandle, class Functor> +std::size_t setupRequests(DataHandle& handle, + std::vector<InterfaceTracker>& trackers, + std::vector<MessageBuffer<typename DataHandle::DataType> >& buffers, + std::vector<MPI_Request>& requests, + const Functor& setupFunctor, + MPI_Comm communicator) +{ + typedef typename std::vector<InterfaceTracker>::iterator TIter; + typename std::vector<MessageBuffer<typename DataHandle::DataType> >::iterator + biter=buffers.begin(); + typename std::vector<MPI_Request>::iterator riter=requests.begin(); + std::size_t complete=0; + for(TIter titer=trackers.begin(), end=trackers.end(); titer!=end; ++titer, ++biter, ++riter) + { + setupFunctor(handle, *titer, *biter, *riter, communicator); + complete+=titer->finished(); + } + return complete; +} +} // end unnamed namespace + +template<class Allocator> +template<bool FORWARD, class DataHandle> +void VariableSizeCommunicator<Allocator>::setupInterfaceTrackers(DataHandle& handle, + std::vector<InterfaceTracker>& send_trackers, + std::vector<InterfaceTracker>& recv_trackers) +{ + if(interface_->size()==0) + return; + send_trackers.reserve(interface_->size()); + recv_trackers.reserve(interface_->size()); + + int fixedsize=0; + if(handle.fixedsize()) + ++fixedsize; + + + typedef typename InterfaceMap::const_iterator IIter; + for(IIter inf=interface_->begin(), end=interface_->end(); inf!=end; ++inf) + { + + if(handle.fixedsize() && InterfaceInformationChooser<FORWARD>::getSend(inf->second).size()) + fixedsize=handle.size(InterfaceInformationChooser<FORWARD>::getSend(inf->second)[0]); + assert(!handle.fixedsize()||fixedsize>0); + send_trackers.push_back(InterfaceTracker(inf->first, + InterfaceInformationChooser<FORWARD>::getSend(inf->second), fixedsize)); + recv_trackers.push_back(InterfaceTracker(inf->first, + InterfaceInformationChooser<FORWARD>::getReceive(inf->second), fixedsize, fixedsize==0)); + } +} + +template<class Allocator> +template<bool FORWARD, class DataHandle> +void VariableSizeCommunicator<Allocator>::communicateFixedSize(DataHandle& handle) +{ + std::vector<MPI_Request> size_send_req(interface_->size()); + std::vector<MPI_Request> size_recv_req(interface_->size()); + + std::vector<InterfaceTracker> send_trackers; + std::vector<InterfaceTracker> recv_trackers; + setupInterfaceTrackers<FORWARD>(handle,send_trackers, recv_trackers); + sendFixedSize(send_trackers, size_send_req, recv_trackers, size_recv_req, communicator_); + + std::vector<MPI_Request> data_send_req(interface_->size(), MPI_REQUEST_NULL); + std::vector<MPI_Request> data_recv_req(interface_->size(), MPI_REQUEST_NULL); + typedef typename DataHandle::DataType DataType; + std::vector<MessageBuffer<DataType> > send_buffers(interface_->size(), MessageBuffer<DataType>(maxBufferSize_)), + recv_buffers(interface_->size(), MessageBuffer<DataType>(maxBufferSize_)); + + + setupRequests(handle, send_trackers, send_buffers, data_send_req, + SetupSendRequest<DataHandle>(), communicator_); + + std::size_t no_size_to_recv, no_to_send, no_to_recv, old_size; + no_size_to_recv = no_to_send = no_to_recv = old_size = interface_->size(); + + // Skip empty interfaces. + typedef typename std::vector<InterfaceTracker>::const_iterator Iter; + for(Iter i=recv_trackers.begin(), end=recv_trackers.end(); i!=end; ++i) + if(i->empty()) + --no_to_recv; + for(Iter i=send_trackers.begin(), end=send_trackers.end(); i!=end; ++i) + if(i->empty()) + --no_to_send; + + while(no_size_to_recv+no_to_send+no_to_recv) + { + // Receive the fixedsize and setup receives accordingly + if(no_size_to_recv) + no_size_to_recv -= receiveSizeAndSetupReceive(handle,recv_trackers, size_recv_req, + data_recv_req, recv_buffers, + communicator_); + + // Check send completion and initiate other necessary sends + if(no_to_send) + no_to_send -= checkSendAndContinueSending(handle, send_trackers, data_send_req, + send_buffers, communicator_); + if(validRecvRequests(data_recv_req)) + // Receive data and setup new unblocking receives if necessary + no_to_recv -= checkReceiveAndContinueReceiving(handle, recv_trackers, data_recv_req, + recv_buffers, communicator_); + } + + // Wait for completion of sending the size. + //std::vector<MPI_Status> statuses(interface_->size(), MPI_STATUSES_IGNORE); + MPI_Waitall(size_send_req.size(), &(size_send_req[0]), MPI_STATUSES_IGNORE); + +} + +template<class Allocator> +template<bool FORWARD, class DataHandle> +void VariableSizeCommunicator<Allocator>::communicateSizes(DataHandle& handle, + std::vector<InterfaceTracker>& data_recv_trackers) +{ + std::vector<InterfaceTracker> send_trackers; + std::vector<InterfaceTracker> recv_trackers; + std::size_t size = interface_->size(); + std::vector<MPI_Request> send_requests(size); + std::vector<MPI_Request> recv_requests(size); + std::vector<MessageBuffer<std::size_t> > + send_buffers(size, MessageBuffer<std::size_t>(maxBufferSize_)), + recv_buffers(size, MessageBuffer<std::size_t>(maxBufferSize_)); + SizeDataHandle<DataHandle> size_handle(handle,data_recv_trackers); + setupInterfaceTrackers<FORWARD>(size_handle,send_trackers, recv_trackers); + std::size_t size_to_send=size, size_to_recv=size; + + // Skip empty interfaces. + typedef typename std::vector<InterfaceTracker>::const_iterator Iter; + for(Iter i=recv_trackers.begin(), end=recv_trackers.end(); i!=end; ++i) + if(i->empty()) + --size_to_recv; + + size_to_send -= setupRequests(size_handle, send_trackers, send_buffers, send_requests, + SetupSendRequest<SizeDataHandle<DataHandle> >(), communicator_); + setupRequests(size_handle, recv_trackers, recv_buffers, recv_requests, + SetupRecvRequest<SizeDataHandle<DataHandle> >(), communicator_); + + + while(size_to_send+size_to_recv) + { + if(size_to_send) + size_to_send -= + checkSendAndContinueSending(size_handle, send_trackers, send_requests, + send_buffers, communicator_); + if(size_to_recv) + // Could have done this using checkSendAndContinueSending + // But the call below is more efficient as UnpackSizeEntries + // uses std::copy. + size_to_recv -= + checkAndContinue(size_handle, recv_trackers, recv_requests, recv_requests, + recv_buffers, communicator_, UnpackSizeEntries<DataHandle>(), + SetupRecvRequest<SizeDataHandle<DataHandle> >()); + } +} + +template<class Allocator> +template<bool FORWARD, class DataHandle> +void VariableSizeCommunicator<Allocator>::communicateVariableSize(DataHandle& handle) +{ + + std::vector<InterfaceTracker> send_trackers; + std::vector<InterfaceTracker> recv_trackers; + setupInterfaceTrackers<FORWARD>(handle, send_trackers, recv_trackers); + + std::vector<MPI_Request> send_requests(interface_->size(), MPI_REQUEST_NULL); + std::vector<MPI_Request> recv_requests(interface_->size(), MPI_REQUEST_NULL); + typedef typename DataHandle::DataType DataType; + std::vector<MessageBuffer<DataType> > + send_buffers(interface_->size(), MessageBuffer<DataType>(maxBufferSize_)), + recv_buffers(interface_->size(), MessageBuffer<DataType>(maxBufferSize_)); + + communicateSizes<FORWARD>(handle, recv_trackers); + std::size_t no_to_send, no_to_recv; + no_to_send = no_to_recv = interface_->size(); + // Setup requests for sending and receiving. + no_to_send -= setupRequests(handle, send_trackers, send_buffers, send_requests, + SetupSendRequest<DataHandle>(), communicator_); + setupRequests(handle, recv_trackers, recv_buffers, recv_requests, + SetupRecvRequest<DataHandle>(), communicator_); + + while(no_to_send+no_to_recv) + { + // Check send completion and initiate other necessary sends + if(no_to_send) + no_to_send -= checkSendAndContinueSending(handle, send_trackers, send_requests, + send_buffers, communicator_); + if(no_to_recv) + // Receive data and setup new unblocking receives if necessary + no_to_recv -= checkReceiveAndContinueReceiving(handle, recv_trackers, recv_requests, + recv_buffers, communicator_); + } +} + +template<class Allocator> +template<bool FORWARD, class DataHandle> +void VariableSizeCommunicator<Allocator>::communicate(DataHandle& handle) +{ + if(handle.fixedsize()) + communicateFixedSize<FORWARD>(handle); + else + communicateVariableSize<FORWARD>(handle); +} +} // end namespace Dune +#endif +#endif diff --git a/dune/common/shared_ptr.hh b/dune/common/shared_ptr.hh index 0bdf02d90496709a7b48bf828f94e4db39f4593a..e5f6e5424c2d9cf8b0fc9a89e094a74a31c5ad40 100644 --- a/dune/common/shared_ptr.hh +++ b/dune/common/shared_ptr.hh @@ -233,7 +233,7 @@ namespace Dune } template<class T> - inline shared_ptr<T>::shared_ptr(nullptr_t n) + inline shared_ptr<T>::shared_ptr(nullptr_t) { rep_ = 0; count_ = 0; @@ -487,7 +487,7 @@ namespace Dune template<class T> struct null_deleter { - void operator() (T* p) const {} + void operator() (T*) const {} }; /** diff --git a/dune/common/test/check_fvector_size.cc b/dune/common/test/check_fvector_size.cc index 128cf11303d3a0338f79db393b29ac00396123ef..d327f2c06b86fc78c708e756b3568c67f57a94e0 100644 --- a/dune/common/test/check_fvector_size.cc +++ b/dune/common/test/check_fvector_size.cc @@ -3,7 +3,7 @@ #include <config.h> #include <dune/common/dynvector.hh> -int main(int argc, char * argv[]) +int main(int, char **) { Dune::DynamicVector<double> one(1); diff --git a/dune/common/test/checkmatrixinterface.hh b/dune/common/test/checkmatrixinterface.hh index 7c8c59a395687dae8b358878871c780329d31f0c..6144ea0afbf69f8815d83bc77d60fb6f5c115eca 100644 --- a/dune/common/test/checkmatrixinterface.hh +++ b/dune/common/test/checkmatrixinterface.hh @@ -152,13 +152,13 @@ namespace CheckMatrixInterface typedef Dune::FieldVector< K, rows > range_type; template< class Matrix > - static domain_type domain ( const Matrix &matrix, value_type v = value_type() ) + static domain_type domain ( const Matrix &, value_type v = value_type() ) { return domain_type( v ); } template< class Matrix > - static range_type range ( const Matrix &matrix, value_type v = value_type() ) + static range_type range ( const Matrix &, value_type v = value_type() ) { return range_type( v ); } @@ -199,9 +199,9 @@ namespace CheckMatrixInterface template< class Matrix, class Traits > struct CheckIfSquareMatrix< Matrix, Traits, false > { - static void apply ( const Matrix &matrix ) {} + static void apply ( const Matrix &) {} - static void apply ( Matrix &matrix ) {} + static void apply ( Matrix &) {} }; template< class Matrix, class Traits > diff --git a/dune/common/test/fassigntest.cc b/dune/common/test/fassigntest.cc index f364558bb6683e0275455defd81b6406cf35545a..9b20745247510ecbfca06c5bb2d350dd0e661154 100644 --- a/dune/common/test/fassigntest.cc +++ b/dune/common/test/fassigntest.cc @@ -8,7 +8,7 @@ using namespace Dune; -int main(int argc, char** argv) try +int main(int, char**) try { Dune::FieldVector<double,3> pos; diff --git a/dune/common/test/iteratortest.hh b/dune/common/test/iteratortest.hh index 71642bb7e759a5f7a75e31441bf75be01bf66b14..7dca2bc7fbebd3bc15ca84b425f88ff9a71af256 100644 --- a/dune/common/test/iteratortest.hh +++ b/dune/common/test/iteratortest.hh @@ -201,7 +201,7 @@ template<bool> struct TestSorting { template<class Container, typename IteratorTag> - static void testSorting(Container& c, IteratorTag tag) + static void testSorting(Container&, IteratorTag) {} template<class Container> static void testSorting(Container& c, std::random_access_iterator_tag) @@ -253,7 +253,7 @@ int testIterator(Container& c, Opt& opt) } template<class Iter, class Opt> -void testAssignment(Iter begin, Iter end, Opt& opt) +void testAssignment(Iter begin, Iter end, Opt&) { //std::cout << "Assignment: "; for(; begin!=end; begin++) diff --git a/dune/common/test/poolallocatortest.cc b/dune/common/test/poolallocatortest.cc index 7b8072277b488456fcd7481c3d7ee715c71c2c86..21a513d88c6b04f5b60a9a7bde43d383f7554b1c 100644 --- a/dune/common/test/poolallocatortest.cc +++ b/dune/common/test/poolallocatortest.cc @@ -119,7 +119,7 @@ int testPool() return ret; } -int main(int argc, char **argv) +int main(int, char **) { int ret=0; diff --git a/dune/common/test/testdebugallocator.cc b/dune/common/test/testdebugallocator.cc index 4bc14593b54b3eeae629fe0d1d67730112791597..0e3839972c03a33dc69871e4118af62f5a667051 100644 --- a/dune/common/test/testdebugallocator.cc +++ b/dune/common/test/testdebugallocator.cc @@ -87,7 +87,7 @@ void new_delete_tests() z4 = 0; } -int main(int argc, char** argv) +int main(int, char**) { basic_tests(); allocator_tests(); diff --git a/dune/common/test/testfconstruct.cc b/dune/common/test/testfconstruct.cc index b24370cd206eebde5b6e34b385121f85e6007b96..a35feafd6dcc80413138401564fd99d842114387 100644 --- a/dune/common/test/testfconstruct.cc +++ b/dune/common/test/testfconstruct.cc @@ -8,7 +8,7 @@ using namespace Dune; -int main(int argc, char** argv) { +int main(int, char**) { Dune::FieldVector<double,3> pos; pos <<= 1, 0, 0; diff --git a/dune/common/test/tuplestest.cc b/dune/common/test/tuplestest.cc index c67c5b41cca3d83eded450cfc91b3ac8ccb05c90..acc7172bafad9fac02d9ae5ed0f87988022dc1f9 100644 --- a/dune/common/test/tuplestest.cc +++ b/dune/common/test/tuplestest.cc @@ -260,7 +260,7 @@ int tuple_tr1_test() } -int main(int argc, char** argv) +int main(int, char**) { tuple<float,int,double,char,std::string> tuple_; std::cout << "=== testing tuple: " << className(tuple_) << std::endl; diff --git a/dune/common/test/utilitytest.cc b/dune/common/test/utilitytest.cc index a649fc54ff4103a19ab873313fab1480e49a1a2f..3016704b83a2d6135629f5af34870d8d91132317 100644 --- a/dune/common/test/utilitytest.cc +++ b/dune/common/test/utilitytest.cc @@ -21,15 +21,15 @@ struct Counter { Counter() : result_(0) {} template <class T1> - void visit(T1 elem) { ++result_; } + void visit(T1) { ++result_; } template <class T1, class T2> - void visit(T1 elem, T2 elem1) { ++(++result_); } + void visit(T1, T2) { ++(++result_); } int result_; }; -int main(int argc, char** argv) +int main(int, char**) { typedef Dune::tuple<int*,double*,long*,char*> PointerTuple; diff --git a/dune/common/tuples.hh b/dune/common/tuples.hh index ce3f505465a30fab764013126cb9d426b3321320..abb3625abf3519a9c9ea05548ba03579c1a5d88b 100644 --- a/dune/common/tuples.hh +++ b/dune/common/tuples.hh @@ -8,6 +8,7 @@ #include "typetraits.hh" #include "static_assert.hh" +#include "unused.hh" #ifdef HAVE_TUPLE #include <tuple> @@ -613,6 +614,7 @@ namespace Dune { template<class T> static std::ostream& put(std::ostream& os, const T& t, const char* delim=", ") { + DUNE_UNUSED_PARAMETER(delim); return os<<Dune::get<0>(t); } diff --git a/dune/common/tupleutility.hh b/dune/common/tupleutility.hh index 9fd019de50faa3db38d753aaa5cc021cfe8bae2d..e704c7f79f814886a71b3200b60017ce063d6c79 100644 --- a/dune/common/tupleutility.hh +++ b/dune/common/tupleutility.hh @@ -1312,7 +1312,7 @@ namespace Dune { template<typename T1,typename F> struct Visitor<0,T1,F> { - static inline void visit(F& func, T1& t1) + static inline void visit(F&, T1&) {} }; @@ -1329,7 +1329,7 @@ namespace Dune { template<typename T1, typename T2, typename F> struct PairVisitor<0,T1,T2,F> { - static inline void visit(F& func, T1& t1, T2& t2) + static inline void visit(F&, T1&, T2&) {} }; } diff --git a/dune/common/unused.hh b/dune/common/unused.hh index e9c2fec28550ea89d166a917d6036a707a1fe653..6345ec0774b2d90d09db4f73009c6a8146c14a42 100644 --- a/dune/common/unused.hh +++ b/dune/common/unused.hh @@ -14,4 +14,6 @@ #define DUNE_UNUSED __attribute__((unused)) #endif +/// A macro to mark intentional unused function parameters with. +#define DUNE_UNUSED_PARAMETER(parm) static_cast<void>(parm) #endif diff --git a/lib/dunecommonam2cmake.lib b/lib/dunecommonam2cmake.lib index 2571e67dd9b86931322aaf046753a8e1949cf29e..eeaec25f18df31a81c316739a5d1f66dff5e0189 100644 --- a/lib/dunecommonam2cmake.lib +++ b/lib/dunecommonam2cmake.lib @@ -6,7 +6,10 @@ ### to CMake options for dune-common ### ########################################## - +space=" " +tab=" " +BLANK="$space$tab" +NOBLANK="^$space^$tab" dune_common_options_am2cmake() { @@ -29,24 +32,24 @@ dune_common_options_am2cmake() # Check for --disable-gxx0xcheck echo $PARAMS | grep \\-\\-disable-gxx0xcheck > /dev/null if test "$?" -eq 0 ; then - CMAKE_PARAMS="$CMAKE_PARAMS -DDISABLE_GXX0XCHECK:Bool=TRUE" + CMAKE_PARAMS="$CMAKE_PARAMS -DDISABLE_GXX0XCHECK:BOOL=TRUE" fi # Check for --disable-gxx0xcheck echo $PARAMS | grep \\-\\-disable-tr1-headers > /dev/null if test "$?" -eq 0 ; then - CMAKE_PARAMS="$CMAKE_PARAMS -DDISABLE_TR1_HEADERS:Bool=TRUE" + CMAKE_PARAMS="$CMAKE_PARAMS -DDISABLE_TR1_HEADERS:BOOL=TRUE" fi # Check for --with-minimal-debug-level - local arg=`echo "$PARAMS"| sed "s/.*--with-minimal-debug-level=\(\S*\).*/\1/"` - if test "x$arg" != "x$PARAMS"; then + local arg=`echo "$PARAMS"| grep \\\\--with-minimal-debug-level= | sed "s/.*--with-minimal-debug-level=\([$NOBLANK]*\).*/\1/"` + if test "x$arg" != "x"; then CMAKE_PARAMS="$CMAKE_PARAMS -DMINIMAL_DEBUG_LEVEL:String=$arg" fi #Check for --prefix - local arg=`echo "$PARAMS"| sed "s/.*--prefix=\(\S*\).*/\1/"` - if test "x$arg" != "x$PARAMS"; then + local arg=`echo "$PARAMS"| grep \\\\--prefix= | sed "s/.*--prefix=\([$NOBLANK]*\).*/\1/"` + if test "x$arg" != "x"; then CMAKE_PARAMS="$CMAKE_PARAMS -DCMAKE_INSTALL_PREFIX=$arg" fi } diff --git a/lib/dunemodules.lib b/lib/dunemodules.lib index cbf5eabe360bdb3e8812ad90e40ad6f4a7d7ee51..face91ff0282fc38becd6360f0b1fed758a8dd25 100644 --- a/lib/dunemodules.lib +++ b/lib/dunemodules.lib @@ -36,6 +36,7 @@ vtab="" # embedded newline. Instead one can often get away with using $BLANK SPACE="$space$formfeed$newline$cr$tab$vtab" BLANK="$space$tab" +NOBLANK="^$space^$tab" # # read paramters from a $CONTROL file @@ -66,10 +67,10 @@ parse_control() { exit 1 fi # read dune.module file - local deps="$($GREP "^[$BLANK]*Depends:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" - local sugs="$($GREP "^[$BLANK]*Suggests:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" - local vers="$($GREP "^[$BLANK]*Version:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" - local main="$($GREP "^[$BLANK]*Maintainer:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" + local deps="$($GREP "^[BLANK]*Depends:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" + local sugs="$($GREP "^[BLANK]*Suggests:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" + local vers="$($GREP "^[BLANK]*Version:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" + local main="$($GREP "^[BLANK]*Maintainer:" "$1" | cut -d ':' -f2 | eval $PARSER_TRIM)" # check whether the module is installed. # - installed modules can be found via pkg-config # - pkg-config --var=prefix should be the same as $path @@ -600,7 +601,7 @@ default_am2cmake_options(){ continue fi # process --with-$lowercase=<arg> - local arg=`echo $PARAMS| sed "s/.*--with-$lowercase=\(\S*\).*/\1/"` + local arg=`echo $PARAMS| sed "s/.*--with-$lowercase=\([$NOBLANK]*\).*/\1/"` local arg=`eval echo $arg` # expand tilde to prevent problems if test "x$arg" = "xno"; then CMAKE_PARAMS="$CMAKE_PARAMS -DCMAKE_DISABLE_FIND_PACKAGE_$package=TRUE" @@ -629,9 +630,9 @@ default_am2cmake_libraries(){ continue fi export "$lowercase"-lib_processed=1 - term="s/.*--with-""$lowercase""-lib=\(\S*\).*/\1/" - arg=`echo "$PARAMS" | sed "$term"` - if test "x$arg" != "x" && test "x$PARAMS" != "x$arg"; then + term="s/.*--with-""$lowercase""-lib=\([$NOBLANK]*\).*/\1/" + arg=`echo "$PARAMS" | grep \\-\\-with-$lowercase | sed "$term"` + if test "x$arg" != "x"; then CMAKE_PARAMS="$CMAKE_PARAMS -D$uppercase""_LIBRARY=$arg" fi done diff --git a/m4/CMakeLists.txt b/m4/CMakeLists.txt index 60aac3a728997de320ffad5779b3b37533cfd0b1..8abe6e396b9e80c7c947bb23752fe203be7def1d 100644 --- a/m4/CMakeLists.txt +++ b/m4/CMakeLists.txt @@ -13,6 +13,7 @@ install(PROGRAMS cxx0x_static_assert.m4 cxx0x_variadic.m4 cxx0x_variadic_constructor_sfinae.m4 + cxx11_constexpr.m4 cxx11_initializer_list.m4 cxx11_conditional.m4 dune.m4 @@ -22,6 +23,7 @@ install(PROGRAMS dune_check_lib.m4 dune_common.m4 dune_compiler.m4 + dune_cxa_demangle.m4 dune_fortran.m4 dune_deprecated.m4 dune_deprecated_cppflags.m4 @@ -45,5 +47,5 @@ install(PROGRAMS shared_ptr.m4 umfpack.m4 xdr.m4 - DESTINATION share/aclocal + DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/dune/aclocal ) diff --git a/m4/Makefile.am b/m4/Makefile.am index e779c580cd66002af598303579b464aad496c56d..62d78d4a1e4bd355d1bb10fb4379dac7134018d8 100644 --- a/m4/Makefile.am +++ b/m4/Makefile.am @@ -27,6 +27,7 @@ ALLM4S = \ dune_check_lib.m4 \ dune_common.m4 \ dune_compiler.m4 \ + dune_cxa_demangle.m4 \ dune_fortran.m4 \ dune_deprecated.m4 \ dune_deprecated_cppflags.m4 \ @@ -51,7 +52,7 @@ ALLM4S = \ umfpack.m4 \ xdr.m4 -aclocaldir = $(datadir)/aclocal +aclocaldir = $(datadir)/dune/aclocal aclocal_DATA = $(ALLM4S) EXTRA_DIST = CMakeLists.txt $(ALLM4S) diff --git a/m4/parmetis.m4 b/m4/parmetis.m4 index cfba2eb90f71f1cde195ae7fb49050c29096b101..9e50fa1ad871a5019bee7ce79b245566ff7a990e 100644 --- a/m4/parmetis.m4 +++ b/m4/parmetis.m4 @@ -48,8 +48,8 @@ AC_DEFUN([DUNE_PATH_PARMETIS],[ AC_MSG_RESULT(yes) else - if test -n "$PARMETIS" ; then - AC_MSG_ERROR(no) + if test -n "$PARMETIS" && test "$PARMETIS" != "no" ; then + AC_MSG_ERROR(ParMETIS was part of the configure call but could not be found in $PARMETIS) else AC_MSG_RESULT(no) fi