Merge remote-tracking branch 'gerrit/release-4-5-patches' into release-4-6
authorRoland Schulz <roland@utk.edu>
Tue, 3 Apr 2012 17:02:10 +0000 (13:02 -0400)
committerRoland Schulz <roland@utk.edu>
Tue, 3 Apr 2012 17:02:10 +0000 (13:02 -0400)
Conflicts:
CMakeLists.txt

Change-Id: I67d65e260f68442841d8b901d77780b8d1505340

1  2 
CMakeLists.txt
src/kernel/gen_ad.c
src/kernel/pdb2top.c
src/kernel/pgutil.c
src/tools/gmx_energy.c
src/tools/gmx_msd.c

diff --combined CMakeLists.txt
index 7c1229f2b1676eef01def9aad743fdd18f45cc1c,086b798036cf7056e0ce95e9397007afa05d1a56..8653d21c0d688bae7b1747af311f107d3719448b
@@@ -1,4 -1,6 +1,6 @@@
 -cmake_minimum_required(VERSION 2.6)
 +cmake_minimum_required(VERSION 2.8)
+ # Keep CMake suitably quiet on Cygwin
+ set(CMAKE_LEGACY_CYGWIN_WIN32 0) # Remove when CMake >= 2.8.4 is required
  
  project(Gromacs)
  include(Dart)
@@@ -12,7 -14,7 +14,7 @@@ mark_as_advanced(DART_ROOT
  # machine with no git. 
  #
  # NOTE: when releasing the "-dev" suffix needs to be stripped off!
 -set(PROJECT_VERSION "4.5.5-dev")
 +set(PROJECT_VERSION "4.6-dev")
  set(CUSTOM_VERSION_STRING ""
      CACHE STRING "Custom version string (if empty, use hard-coded default)")
  mark_as_advanced(CUSTOM_VERSION_STRING)
@@@ -22,8 -24,8 +24,8 @@@ endif (CUSTOM_VERSION_STRING
  set(SOVERSION 6)
  # It is a bit irritating, but this has to be set separately for now!
  SET(CPACK_PACKAGE_VERSION_MAJOR "4")
 -SET(CPACK_PACKAGE_VERSION_MINOR "5")
 -SET(CPACK_PACKAGE_VERSION_PATCH "5")
 +SET(CPACK_PACKAGE_VERSION_MINOR "6")
 +#SET(CPACK_PACKAGE_VERSION_PATCH "0")
  
  
  # Cmake modules/macros are in a subdirectory to keep this file cleaner
@@@ -109,7 -111,7 +111,7 @@@ gmx_c_flags(
  ########################################################################
  option(GMX_DOUBLE "Use double precision (much slower, use only if you really need it)" OFF)
  option(GMX_MPI    "Build a parallel (message-passing) version of GROMACS" OFF)
 -option(GMX_THREADS    "Build a parallel (thread-based) version of GROMACS (cannot be combined with MPI yet)" ON)
 +option(GMX_THREAD_MPI  "Build a thread-MPI-based multithreaded version of GROMACS (not compatible with MPI)" ON)
  option(GMX_SOFTWARE_INVSQRT "Use GROMACS software 1/sqrt" ON)
  mark_as_advanced(GMX_SOFTWARE_INVSQRT)
  option(GMX_POWERPC_INVSQRT "Use PowerPC hardware 1/sqrt" OFF)
@@@ -121,7 -123,7 +123,7 @@@ set(GMX_ACCELERATION "auto
      CACHE STRING "Accelerated kernels. Pick one of: auto, none, SSE, BlueGene, Power6, ia64, altivec, fortran")
  
  set(GMX_FFT_LIBRARY "fftw3" 
 -    CACHE STRING "FFT library choices: fftw3,fftw2,mkl,fftpack[built-in]")
 +    CACHE STRING "FFT library choices: fftw3,mkl,fftpack[built-in]")
  option(GMX_DISABLE_FFTW_MEASURE 
         "Do not optimize FFTW setups (not needed with SSE)" OFF)
  mark_as_advanced(GMX_DISABLE_FFTW_MEASURE)
@@@ -132,8 -134,8 +134,8 @@@ mark_as_advanced(GMX_BROKEN_CALLOC
  option(BUILD_SHARED_LIBS "Enable shared libraries (can be problematic with MPI, Windows)" ${SHARED_LIBS_DEFAULT})
  option(GMX_MPI_IN_PLACE "Enable MPI_IN_PLACE for MPIs that have it defined" ON)
  mark_as_advanced(GMX_MPI_IN_PLACE)
 -option(GMX_DLOPEN "Compile with dlopen, needed to read VMD supported file formats" ON)
 -mark_as_advanced(GMX_DLOPEN)
 +option(GMX_LOAD_PLUGINS "Compile with plugin support, needed to read VMD supported file formats" ON)
 +mark_as_advanced(GMX_LOAD_PLUGINS)
  
  
  option(GMX_IA32_ASM "Add SSE assembly files for IA32" OFF)
@@@ -141,8 -143,6 +143,8 @@@ mark_as_advanced(GMX_IA32_ASM
  option(GMX_X86_64_ASM "Add SSE assembly files for X86_64" OFF)
  mark_as_advanced(GMX_X86_64_ASM)
  
 +option(GMX_OPENMP "Enable OpenMP-based mutithreading. " ON)
 +
  option(USE_VERSION_H "Generate development version string/information" ON)
  mark_as_advanced(USE_VERSION_H)
  
@@@ -175,18 -175,13 +177,18 @@@ if (GMX_DEFAULT_SUFFIX
      set (GMX_LIBS_SUFFIX "_gpu")
    endif(GMX_OPENMM)
    mark_as_advanced(FORCE GMX_BINARY_SUFFIX GMX_LIBS_SUFFIX)
 -  message(STATUS "Using default binary suffix: \"${GMX_BINARY_SUFFIX}\"")    
 -  message(STATUS "Using default library suffix: \"${GMX_LIBS_SUFFIX}\"") 
 +  if (NOT SUFFIX_QUIETLY)
 +    message(STATUS "Using default binary suffix: \"${GMX_BINARY_SUFFIX}\"")
 +    message(STATUS "Using default library suffix: \"${GMX_LIBS_SUFFIX}\"")
 +  endif (NOT SUFFIX_QUIETLY)
  else(GMX_DEFAULT_SUFFIX)
    mark_as_advanced(CLEAR GMX_BINARY_SUFFIX GMX_LIBS_SUFFIX)
 -  message(STATUS "Using manually set binary suffix: \"${GMX_BINARY_SUFFIX}\"")    
 -  message(STATUS "Using manually set library suffix: \"${GMX_LIBS_SUFFIX}\"")
 +  if (NOT SUFFIX_QUIETLY)
 +    message(STATUS "Using manually set binary suffix: \"${GMX_BINARY_SUFFIX}\"")
 +    message(STATUS "Using manually set library suffix: \"${GMX_LIBS_SUFFIX}\"")
 +  endif (NOT SUFFIX_QUIETLY)
  endif(GMX_DEFAULT_SUFFIX)
 +set(SUFFIX_QUIETLY TRUE CACHE INTERNAL "")
  
  set(PKG_CFLAGS "")
  if(GMX_DOUBLE)
@@@ -202,7 -197,65 +204,7 @@@ endif(GMX_POWERPC_INVSQRT
  ########################################################################
  #Process MPI settings
  ########################################################################
 -include(CheckCSourceCompiles) # for gmxTestMPI_IN_PLACE
 -if(GMX_MPI)
 -    if(GMX_THREADS)
 -        #message(FATAL_ERROR "Thread-based parallelization conflicts with MPI.")
 -        set(GMX_THREADS OFF CACHE BOOL 
 -            "Thread-based parallelization conflicts with MPI." FORCE)
 -    endif(GMX_THREADS)
 -    find_package(MPI)
 -    if(MPI_FOUND)
 -        set(GROMACS_C_FLAGS ${GROMACS_FLAGS} ${MPI_COMPILE_FLAGS})
 -      set(GROMACS_LINKER_FLAGS ${GROMACS_LINKER_FLAGS} ${MPI_LINK_FLAGS})
 -        
 -        include_directories(${MPI_INCLUDE_PATH})
 -        list(APPEND GMX_EXTRA_LIBRARIES ${MPI_LIBRARIES})
 -        if(GMX_FAHCORE)
 -            add_definitions( -DMPI ) #for FAHCORE
 -        endif(GMX_FAHCORE)
 -        include(gmxTestMPI_IN_PLACE)
 -        if (GMX_MPI_IN_PLACE)
 -            gmx_test_mpi_in_place(MPI_IN_PLACE_EXISTS)
 -        endif (GMX_MPI_IN_PLACE)
 -
 -      # test for unsuitable versions of OpenMPI
 -      exec_program(${MPIEXEC}
 -        ARGS --version
 -        OUTPUT_VARIABLE MPI_TYPE
 -        RETURN_VALUE MPI_EXEC_RETURN)
 -      if(MPI_EXEC_RETURN EQUAL 0)
 -        if(MPI_TYPE MATCHES "Open MPI|OpenRTE")
 -          string(REGEX MATCH "[0-9]+\\.[0-9]*\\.?[0-9]*" MPI_VERSION ${MPI_TYPE})
 -          if(MPI_VERSION VERSION_LESS "1.4.1")
 -            MESSAGE(WARNING "
 -            There are known problems with OpenMPI version < 1.4.1.
 -            Please consider updating your OpenMPI.")
 -          endif(MPI_VERSION VERSION_LESS "1.4.1")
 -          unset(MPI_VERSION)
 -        else(MPI_TYPE MATCHES "Open MPI|OpenRTE")
 -          # This is not OpenMPI, so give the old generic warning message
 -          MESSAGE(WARNING "
 -            There are known problems with some MPI implementations:
 -                     MVAPICH2 version <= 1.4.1
 -            Please consider updating your MPI if applicable.")
 -        endif(MPI_TYPE MATCHES "Open MPI|OpenRTE")
 -        unset(MPI_TYPE)
 -      endif(MPI_EXEC_RETURN EQUAL 0)
 -    else(MPI_FOUND)
 -        message(FATAL_ERROR "MPI support requested, but no MPI compiler found.")
 -    endif(MPI_FOUND)
 -    include(gmxTestCatamount)
 -    gmx_test_catamount(GMX_CRAY_XT3)
 -    if(GMX_CRAY_XT3)
 -        set(PKG_CFLAGS "${PKG_CFLAGS} -DGMX_CRAY_XT3")
 -        set(GMX_NO_SYSTEM 1)
 -        set(GMX_NO_NICE 1)
 -    endif(GMX_CRAY_XT3)
 -    set(GMX_LIB_MPI 1)
 -    set(PKG_CFLAGS "${PKG_CFLAGS} -DGMX_LIB_MPI")
 -endif(GMX_MPI)
 -
 +include(gmxManageMPI)
  
  #######################################################################
  # Check for options incompatible with OpenMM build                    #
@@@ -219,16 -272,11 +221,16 @@@ if(GMX_OPENMM
      if(GMX_MPI)
          message(FATAL_ERROR "The OpenMM build is not compatible with MPI!")
      endif(GMX_MPI)
 -    if(GMX_THREADS)
 -        message(STATUS "Threads are  not compatible with OpenMM build, disabled!")
 -        set(GMX_THREADS OFF CACHE BOOL 
 -              "Threads are not compatible with OpenMM build, disabled!" FORCE)
 -    endif(GMX_THREADS)
 +    if(GMX_THREAD_MPI)
 +        message(STATUS "Thread-MPI not compatible with OpenMM, disabled!")
 +        set(GMX_THREAD_MPI OFF CACHE BOOL
 +              "Thread-MPI not compatible with OpenMM build, disabled!" FORCE)
 +    endif(GMX_THREAD_MPI)
 +    if(GMX_OPENMP)
 +        message(STATUS "OpenMP multithreading not compatible with OpenMM, disabled")
 +        set(GMX_OPENMP OFF CACHE BOOL
 +            "OpenMP multithreading not compatible with OpenMM, disabled!" FORCE)
 +    endif()
      if(GMX_SOFTWARE_INVSQRT)
          set(GMX_SOFTWARE_INVSQRT OFF CACHE STRING 
                  "The OpenMM build does not need GROMACS software 1/sqrt!" FORCE)
      endif()
      # mark as advanced the unused variables
      mark_as_advanced(FORCE GMX_ACCELERATION GMX_MPI GMX_FFT_LIBRARY 
 -        GMX_QMMM_PROGRAM GMX_THREADS GMX_DOUBLE)
 +        GMX_QMMM_PROGRAM GMX_THREAD_MPI GMX_DOUBLE)
  else(GMX_OPENMM)
       mark_as_advanced(CLEAR GMX_ACCELERATION GMX_MPI GMX_FFT_LIBRARY 
 -        GMX_QMMM_PROGRAM GMX_THREADS GMX_DOUBLE)   
 +        GMX_QMMM_PROGRAM GMX_THREAD_MPI GMX_DOUBLE)
  endif(GMX_OPENMM)
  
  
@@@ -400,13 -448,16 +402,13 @@@ if (GMX_X11
        endif(X11_FOUND)
  endif(GMX_X11)
  
 -if(GMX_THREADS)
 -    set(PKG_CFLAGS "${PKG_CFLAGS} -DGMX_THREADS")
 +if(GMX_THREAD_MPI)
 +    set(PKG_CFLAGS "${PKG_CFLAGS} -DGMX_THREAD_MPI")
      include(ThreadMPI)
      set(THREAD_MPI_LIB thread_mpi)
      set(GMX_MPI 1)
      string(TOUPPER ${GMX_FFT_LIBRARY} ${GMX_FFT_LIBRARY})
 -    if(${GMX_FFT_LIBRARY} STREQUAL "FFTW2")
 -        message(FATAL_ERROR "FFTW2 can't be used with threads. Try fftw3 or mkl.")
 -    endif()
 -endif(GMX_THREADS)
 +endif(GMX_THREAD_MPI)
  
  if(GMX_OPENMM)
      set(CUDA_BUILD_EMULATION OFF)
      find_package(OpenMM) 
  endif(GMX_OPENMM)
  
 +if(GMX_OPENMP)
 +    find_package(OpenMP REQUIRED)
 +    set(GROMACS_C_FLAGS "${OpenMP_C_FLAGS} ${GROMACS_C_FLAGS}")
 +    set(GROMACS_CXX_FLAGS "${OpenMP_CXX_FLAGS} ${GROMACS_CXX_FLAGS}")
 +    add_definitions(-DGMX_OPENMP)
 +endif()
 +
  if(APPLE)
     find_library(ACCELERATE_FRAMEWORK Accelerate)
     list(APPEND GMX_EXTRA_LIBRARIES ${ACCELERATE_FRAMEWORK})
@@@ -438,28 -482,25 +440,28 @@@ endif(CYGWIN
  if(EXISTS "${CMAKE_SOURCE_DIR}/.git")
      if(USE_VERSION_H)
          # We need at least git v1.5.1 be able to parse git's date output. If not 
 -        # fund or the version is too small, we can't generate version information.
 -        find_package(Git 1.5.1)
 -        # this should at some point become VERSION_LESS
 -        if(NOT Git_FOUND OR Git_VERSION STRLESS "1.5.1")
 -            message("No compatible git version found, won't be able to generate proper development version information.")
 -            set(USE_VERSION_H OFF)
 +        # found or the version is too small, we can't generate version information.
 +        find_package(Git)
 +
 +      # Find out the git version
 +      if(GIT_FOUND AND NOT GIT_VERSION)
 +        execute_process(COMMAND ${GIT_EXECUTABLE} "--version"
 +            OUTPUT_VARIABLE _exec_out
 +            OUTPUT_STRIP_TRAILING_WHITESPACE)
 +        string(REGEX REPLACE "git version (.*)" "\\1" GIT_VERSION ${_exec_out})
 +        set(GIT_VERSION ${GIT_VERSION} CACHE STRING "Git version")
 +        mark_as_advanced(GIT_VERSION)
 +      endif()
 +
 +        if(NOT GIT_FOUND OR GIT_VERSION VERSION_LESS "1.5.1")
 +          message("No compatible git version found, won't be able to generate proper development version information.")
 +          set(USE_VERSION_H OFF)
          endif()
      endif()
  else()
      set(USE_VERSION_H OFF)
  endif()
  
 -if (GMX_DLOPEN)
 -    list(APPEND GMX_EXTRA_LIBRARIES ${CMAKE_DL_LIBS})
 -    set(PKG_DL_LIBS "-l${CMAKE_DL_LIBS}")
 -else(GMX_DLOPEN)
 -    set(PKG_DL_LIBS)
 -endif (GMX_DLOPEN)
 -
  ########################################################################
  # Generate development version info for cache
  ########################################################################
@@@ -487,6 -528,7 +489,6 @@@ gmx_test_large_files(GMX_LARGEFILES
  check_function_exists(fseeko     HAVE_FSEEKO)
  
  include(gmxTestSignal)
 -gmx_test_retsigtype(RETSIGTYPE)
  gmx_test_sigusr1(HAVE_SIGUSR1)
  
  include(gmxTestInline)
@@@ -594,7 -636,7 +596,7 @@@ elseif(${GMX_ACCELERATION} STREQUAL "BL
      set(GMX_SOFTWARE_INVSQRT OFF CACHE BOOL "Do not use software reciprocal square root on BlueGene" FORCE)
      set(GMX_POWERPC_INVSQRT ON CACHE BOOL "Use hardware reciprocal square root on BlueGene" FORCE)
      set(GMX_X11 OFF CACHE BOOL "X11 not compatible with BlueGene, disabled!" FORCE)
 -    set(GMX_THREADS OFF CACHE BOOL "Threads not compatible with BlueGene, disabled!" FORCE)
 +    set(GMX_THREAD_MPI OFF CACHE BOOL "Thread-MPI not compatible with BlueGene, disabled!" FORCE)
      set(GMX_MPI ON CACHE BOOL "Use MPI on BlueGene" FORCE)
  elseif(${GMX_ACCELERATION} STREQUAL "POWER6")
      set(GMX_POWER6 1)
@@@ -614,9 -656,9 +616,9 @@@ else(${GMX_ACCELERATION} STREQUAL "NONE
  endif(${GMX_ACCELERATION} STREQUAL "NONE")
  
  if(GMX_FORTRAN OR GMX_POWER6)
 -    if (GMX_THREADS)
 -        message(FATAL_ERROR "FORTRAN/POWER6 is incompatible with threads and only provides a speed-up on certain IBM compilers. Disable FORTRAN (or threads if you really want to use FORTRAN kernels).")
 -    endif(GMX_THREADS)
 +    if (GMX_THREAD_MPI)
 +        message(FATAL_ERROR "FORTRAN/POWER6 is incompatible with thread-MPI and only provides a speed-up on certain IBM compilers. Disable FORTRAN (or threads if you really want to use FORTRAN kernels).")
 +    endif(GMX_THREAD_MPI)
      enable_language(Fortran)
      include(FortranCInterface)
      discover_fortran_mangling(prefix isupper suffix extra_under_score found)
@@@ -671,20 -713,49 +673,20 @@@ string(TOUPPER ${GMX_FFT_LIBRARY} ${GMX
  set(PKG_FFT "")
  set(PKG_FFT_LIBS "")
  if(${GMX_FFT_LIBRARY} STREQUAL "FFTW3")
 -#    MESSAGE(STATUS "Using external FFT library - fftw3")
      if(GMX_DOUBLE)
 -        find_package(FFTW3 REQUIRED)
 -              include_directories(${FFTW3_INCLUDE_DIR})
 -        set(FFT_LIBRARIES ${FFTW3_LIBRARIES})
 -        set(PKG_FFT "fftw3")
 +        find_package(FFTW 3 COMPONENTS fftw)
      else(GMX_DOUBLE)
 -        find_package(FFTW3F REQUIRED)
 -        include_directories(${FFTW3F_INCLUDE_DIR})
 -        set(FFT_LIBRARIES ${FFTW3F_LIBRARIES})
 -        set(PKG_FFT "fftw3f")
 +        find_package(FFTW 3 COMPONENTS fftwf)
      endif(GMX_DOUBLE)
 -
 -    if(NOT FFTW3_FOUND AND NOT FFTW3F_FOUND)
 -        MESSAGE(FATAL_ERROR "Cannot find fftw3 (with correct precision). Fix it, choose another FFT library, or use the Gromacs built-in fftpack (slower)!")
 -    endif(NOT FFTW3_FOUND AND NOT FFTW3F_FOUND)
 +    if(NOT FFTW_FOUND)
 +      MESSAGE(FATAL_ERROR "Cannot find FFTW3 (with correct precision - libfftw3f for single precision GROMACS or libfftw3 for double precision GROMACS). Fix it, choose another FFT library, or use the Gromacs built-in fftpack (slower)!")
 +    endif(NOT FFTW_FOUND)
 +    include_directories(${FFTW_INCLUDE_DIRS})
 +    set(FFT_LIBRARIES ${FFTW_LIBRARIES})
 +    set(PKG_FFT "${FFTW_PKG}")
  
      set(GMX_FFT_FFTW3 1)
  
 -elseif(${GMX_FFT_LIBRARY} STREQUAL "FFTW2")
 -#    MESSAGE(STATUS "Using external FFT library - fftw2")
 -    if(GMX_DOUBLE)
 -        find_package(FFTW2 REQUIRED)
 -    else(GMX_DOUBLE)
 -        find_package(FFTW2F REQUIRED)
 -    endif(GMX_DOUBLE)
 -
 -    if(NOT FFTW2_FOUND)
 -                 MESSAGE(FATAL_ERROR "Cannot find fftw2 (with correct precision). Fix it, choose another FFT library, or use the Gromacs built-in fftpack (slower)!")
 -    endif(NOT FFTW2_FOUND)
 -    include_directories(${FFTW2_INCLUDE_DIR})
 -    set(FFT_LIBRARIES ${FFTW2_LIBRARIES})
 -    set(PKG_FFT_LIBS ${FFTW2_LIBRARIES})
 -
 -    if("${FFTW2_LIBRARIES}" MATCHES "dfftw")
 -        set(FFTW2_NAME_DFFTW 1)
 -    elseif("${FFTW2_LIBRARIES}" MATCHES "sfftw")
 -        set(FFTW2_NAME_SFFTW 1)
 -    else("${FFTW2_LIBRARIES}" MATCHES "dfftw")
 -        set(FFTW2_NAME_FFTW 1) 
 -    endif("${FFTW2_LIBRARIES}" MATCHES "dfftw")
 -
 -    set(GMX_FFT_FFTW2 1)
  elseif(${GMX_FFT_LIBRARY} STREQUAL "MKL")
  #    MESSAGE(STATUS "Using external FFT library - Intel MKL")
      find_package(MKL REQUIRED)
@@@ -702,7 -773,7 +704,7 @@@ elseif(${GMX_FFT_LIBRARY} STREQUAL "FFT
      MESSAGE(STATUS "Using internal FFT library - fftpack")
      set(GMX_FFT_FFTPACK 1)
  else(${GMX_FFT_LIBRARY} STREQUAL "FFTW3")
 -    MESSAGE(FATAL_ERROR "Invalid FFT library setting: ${GMX_FFT_LIBRARY}. Choose one of: fftw3, fftw2, mkl, acml, fftpack")
 +    MESSAGE(FATAL_ERROR "Invalid FFT library setting: ${GMX_FFT_LIBRARY}. Choose one of: fftw3, mkl, fftpack")
  endif(${GMX_FFT_LIBRARY} STREQUAL "FFTW3")
  
  # MKL has BLAS/LAPACK routines
@@@ -736,70 -807,6 +738,70 @@@ endif(HAVE_MKL OR ACCELERATE_FRAMEWORK
  mark_as_advanced(GMX_EXTERNAL_LAPACK)
  mark_as_advanced(GMX_EXTERNAL_BLAS)
  
 +set(GMX_USE_PLUGINS OFF CACHE INTERNAL "Whether GROMACS will really try to compile support for VMD plugins")
 +set(GMX_VMD_PLUGIN_PATH)
 +mark_as_advanced(GMX_VMD_PLUGIN_PATH)
 +
 +if(GMX_LOAD_PLUGINS)
 +  if(CYGWIN OR NOT WIN32)
 +    # Native Windows does not have, nor need dlopen
 +    # Note that WIN32 is set with Cygwin, but Cygwin needs dlopen to use plug-ins
 +    include(gmxTestdlopen)
 +    gmx_test_dlopen(HAVE_DLOPEN)
 +  endif()
 +
 +  find_package(VMD)
 +
 +  # Test for unsuitable versions of VMD
 +
 +  if(VMD_FOUND AND NOT GMX_VMD_PLUGIN_PATH)
 +    message(STATUS "Checking for suitable VMD version")
 +    exec_program(${VMD_EXECUTABLE}
 +      ARGS --help
 +      OUTPUT_VARIABLE VMD_HELP
 +      RETURN_VALUE VMD_EXEC_RETURN)
 +
 +    if(VMD_EXEC_RETURN EQUAL 0)
 +      # This is the accepted idiom for subexpression matching, unfortunately
 +      string(REGEX REPLACE ".*VMD for .*, version ([0-9]+\\.[0-9]*\\.?[0-9]*).*" "\\1" VMD_VERSION ${VMD_HELP})
 +      string(REGEX REPLACE ".*VMD for (.*), version .*" "\\1" VMD_ARCH ${VMD_HELP})
 +
 +      if(VMD_VERSION VERSION_LESS "1.8")
 +        MESSAGE(WARNING "Found VMD version ${VMD_VERSION}, but GROMACS needs at least 1.8")
 +        unset(VMD_EXECUTABLE)
 +        set(VMD_FOUND FALSE)
 +      else()
 +        message(STATUS "VMD version ${VMD_VERSION} is suitable")
 +        if(DEFINED ENV{VMDDIR})
 +          # This permits GROMACS to avoid hard-coding a fall-back
 +          # path that it can tell right now would be useless.
 +          set(GMX_VMD_PLUGIN_PATH "$ENV{VMDDIR}/plugins/${VMD_ARCH}/molfile" CACHE PATH "Path to VMD plugins for molfile I/O")
 +        else()
 +          set(GMX_VMD_PLUGIN_PATH "/usr/local/lib/vmd/plugins/*/molfile" CACHE PATH "Path to VMD plugins for molfile I/O")
 +        endif()
 +      endif()
 +
 +      # clean up
 +      unset(VMD_HELP)
 +      unset(VMD_VERSION)
 +      unset(VMD_ARCH)
 +    endif()
 +  endif()
 +
 +  # so, should we use plug-ins?
 +  if((WIN32 AND NOT CYGWIN) OR (HAVE_DLOPEN AND BUILD_SHARED_LIBS))
 +    if (NOT VMD_QUIETLY)
 +      MESSAGE(STATUS "Found the ability to use plug-ins when building shared libaries, so will compile to use plug-ins (e.g. to read VMD-supported file formats).")
 +    endif(NOT VMD_QUIETLY)
 +    set(GMX_USE_PLUGINS ON)
 +    list(APPEND GMX_EXTRA_LIBRARIES ${CMAKE_DL_LIBS}) # magic cross-platform pre-set variable for dlopen library
 +    set(PKG_DL_LIBS "-l${CMAKE_DL_LIBS}")
 +  else()
 +    set(PKG_DL_LIBS)
 +  endif()
 +endif(GMX_LOAD_PLUGINS)
 +set(VMD_QUIETLY TRUE CACHE INTERNAL "")
 +
  # Math and thread libraries must often come after all others when linking...
  if(HAVE_LIBM)
      list(APPEND       GMX_EXTRA_LIBRARIES m)
diff --combined src/kernel/gen_ad.c
index 041a06cb164d113491edf2f766053688398b5531,a3234252f95c08574211410e51e6521fe37a383a..977f71efd9115566255111e70be851b99afe2ebb
@@@ -110,6 -110,20 +110,6 @@@ static int dcomp(const void *d1, const 
      return (p1->AL-p2->AL);
  }
  
 -
 -static gmx_bool aeq(t_param *p1, t_param *p2)
 -{
 -  if (p1->AJ!=p2->AJ)
 -    return FALSE;
 -  else if (((p1->AI==p2->AI) && (p1->AK==p2->AK)) ||
 -           ((p1->AI==p2->AK) && (p1->AK==p2->AI)))
 -    return TRUE;
 -  else
 -    return FALSE;
 -}
 -
 -
 -
  static gmx_bool deq(t_param *p1, t_param *p2)
  {
    if (((p1->AJ==p2->AJ) && (p1->AK==p2->AK)) ||
@@@ -272,6 -286,11 +272,6 @@@ static int eq_imp(atom_id a1[],atom_id 
    return TRUE;
  }
  
 -static gmx_bool ideq(t_param *p1, t_param *p2)
 -{
 -  return eq_imp(p1->a,p2->a);
 -}
 -
  static int idcomp(const void *a,const void *b)
  {
    t_param *pa,*pb;
@@@ -305,6 -324,22 +305,6 @@@ static void sort_id(int nr,t_param ps[]
      qsort(ps,nr,(size_t)sizeof(ps[0]),idcomp);
  }
  
 -static void dump_param(FILE *fp,char *title,int n,t_param ps[])
 -{
 - int i,j;
 -  
 -  fprintf(fp,"%s: %d entries\n",title,n);
 -  for(i=0; (i<n); i++) {
 -    fprintf(fp,"%3d:  A=[ ",i);
 -    for(j=0; (j<MAXATOMLIST); j++)
 -      fprintf(fp," %5d",ps[i].a[j]);
 -    fprintf(fp,"]  C=[");
 -    for(j=0; (j<MAXFORCEPARAM); j++)
 -      fprintf(fp," %10.5e",ps[i].c[j]);
 -    fprintf(fp,"]\n");  
 -  }
 -}
 -
  static int n_hydro(atom_id a[],char ***atomname)
  {
    int i,nh=0;
@@@ -417,7 -452,7 +417,7 @@@ static int get_impropers(t_atoms *atoms
        bStop=FALSE;
        for(k=0; (k<4) && !bStop; k++) {
          ai[k] = search_atom(idihs->b[j].a[k],start,
-                             atoms->nr,atoms->atom,atoms->atomname,
+                           atoms,
                              "improper",bAllowMissing);
          if (ai[k] == NO_ATID)
            bStop = TRUE;
@@@ -500,10 -535,10 +500,10 @@@ static void gen_excls(t_atoms *atoms, t
        
        for(e=0; e<hbexcl->nb; e++) {
        anm = hbexcl->b[e].a[0];
-       i1 = search_atom(anm,astart,atoms->nr,atoms->atom,atoms->atomname,
+       i1 = search_atom(anm,astart,atoms,
                         "exclusion",bAllowMissing);
        anm = hbexcl->b[e].a[1];
-       i2 = search_atom(anm,astart,atoms->nr,atoms->atom,atoms->atomname,
+       i2 = search_atom(anm,astart,atoms,
                         "exclusion",bAllowMissing);
        if (i1!=NO_ATID && i2!=NO_ATID) {
          if (i1 > i2) {
diff --combined src/kernel/pdb2top.c
index 7d09edc2f200fa0bb7eb864dbcfff1177fc418e3,98b5d13347601f7353edcff672f91b28219ce2f5..ca2f0ca61d50b774b532fa30d4549cdae678fa79
@@@ -410,7 -410,7 +410,7 @@@ void choose_watermodel(const char *wmse
              sfree(model[nwm]);
          }
      }
 -    fclose(fp);
 +    ffclose(fp);
      fprintf(stderr,"%2d: %s\n",nwm+1,"None");
  
      do
@@@ -553,7 -553,6 +553,7 @@@ void print_top_comment(FILE *out
    else
    {
        strncpy(ffdir_parent,ffdir,STRLEN-1);
 +      ffdir_parent[STRLEN-1]='\0'; /*make sure it is 0-terminated even for long string*/
        p=strrchr(ffdir_parent,'/');
  
        *p='\0';
@@@ -704,20 -703,23 +704,23 @@@ void write_top(FILE *out, char *pr,cha
  }
  
  static atom_id search_res_atom(const char *type,int resind,
-                              int natom,t_atom at[],
-                              char ** const *aname,
+                    t_atoms *atoms,
                               const char *bondtype,gmx_bool bAllowMissing)
  {
    int i;
  
-   for(i=0; (i<natom); i++)
-     if (at[i].resind == resind)
-       return search_atom(type,i,natom,at,aname,bondtype,bAllowMissing);
+   for(i=0; (i<atoms->nr); i++)
+   {
+     if (atoms->atom[i].resind == resind)
+     {
+       return search_atom(type,i,atoms,bondtype,bAllowMissing);
+     }
+   }
    
    return NO_ATID;
  }
  
- static void do_ssbonds(t_params *ps,int natoms,t_atom atom[],char **aname[],
+ static void do_ssbonds(t_params *ps,t_atoms *atoms,
                       int nssbonds,t_ssbond *ssbonds,gmx_bool bAllowMissing)
  {
    int     i,ri,rj;
    for(i=0; (i<nssbonds); i++) {
      ri = ssbonds[i].res1;
      rj = ssbonds[i].res2;
-     ai = search_res_atom(ssbonds[i].a1,ri,natoms,atom,aname,
+     ai = search_res_atom(ssbonds[i].a1,ri,atoms,
                         "special bond",bAllowMissing);
-     aj = search_res_atom(ssbonds[i].a2,rj,natoms,atom,aname,
+     aj = search_res_atom(ssbonds[i].a2,rj,atoms,
                         "special bond",bAllowMissing);
      if ((ai == NO_ATID) || (aj == NO_ATID))
        gmx_fatal(FARGS,"Trying to make impossible special bond (%s-%s)!",
    }
  }
  
 -static gmx_bool inter_res_bond(const t_rbonded *b)
 -{
 -    return (b->AI[0] == '-' || b->AI[0] == '+' ||
 -            b->AJ[0] == '-' || b->AJ[0] == '+');
 -}
 -
  static void at2bonds(t_params *psb, t_hackblock *hb,
-                      int natoms, t_atom atom[], char **aname[], 
-                      int nres, rvec x[], 
+                      t_atoms *atoms,
+                      rvec x[],
                       real long_bond_dist, real short_bond_dist,
                       gmx_bool bAllowMissing)
  {
  
    fprintf(stderr,"Making bonds...\n");
    i=0;
-   for(resind=0; (resind < nres) && (i<natoms); resind++) {
+   for(resind=0; (resind < atoms->nres) && (i<atoms->nr); resind++) {
      /* add bonds from list of bonded interactions */
      for(j=0; j < hb[resind].rb[ebtsBONDS].nb; j++) {
        /* Unfortunately we can not issue errors or warnings
         * for missing atoms in bonds, as the hydrogens and terminal atoms
         * have not been added yet.
         */
-       ai=search_atom(hb[resind].rb[ebtsBONDS].b[j].AI,i,natoms,atom,aname,
+       ai=search_atom(hb[resind].rb[ebtsBONDS].b[j].AI,i,atoms,
                     ptr,TRUE);
-       aj=search_atom(hb[resind].rb[ebtsBONDS].b[j].AJ,i,natoms,atom,aname,
+       aj=search_atom(hb[resind].rb[ebtsBONDS].b[j].AJ,i,atoms,
                     ptr,TRUE);
        if (ai != NO_ATID && aj != NO_ATID) {
            dist2 = distance2(x[ai],x[aj]);
        }
      }
      /* add bonds from list of hacks (each added atom gets a bond) */
-     while( (i<natoms) && (atom[i].resind == resind) ) {
+     while( (i<atoms->nr) && (atoms->atom[i].resind == resind) ) {
        for(j=0; j < hb[resind].nhack; j++)
        if ( ( hb[resind].hack[j].tp > 0 ||
               hb[resind].hack[j].oname==NULL ) &&
-            strcmp(hb[resind].hack[j].AI,*(aname[i])) == 0 ) {
+            strcmp(hb[resind].hack[j].AI,*(atoms->atomname[i])) == 0 ) {
          switch(hb[resind].hack[j].tp) {
          case 9:          /* COOH terminus */
            add_param(psb,i,i+1,NULL,NULL);     /* C-O  */
@@@ -1345,14 -1353,11 +1348,11 @@@ static void gen_cmap(t_params *psb, t_r
  {
      int residx,i,j,k;
      const char *ptr;
-     int natoms = atoms->nr;
-     t_atom *atom = atoms->atom;
-     char ***aname = atoms->atomname;
      t_resinfo *resinfo = atoms->resinfo;
      int nres = atoms->nres;
      gmx_bool bAddCMAP;
      atom_id cmap_atomid[NUM_CMAP_ATOMS];
 -    int cmap_chainnum, this_residue_index;
 +    int cmap_chainnum=-1, this_residue_index;
  
        if (debug)
                ptr = "cmap";
              for(k = 0; k < NUM_CMAP_ATOMS && bAddCMAP; k++)
              {
                  cmap_atomid[k] = search_atom(restp[residx].rb[ebtsCMAP].b[j].a[k],
-                                              i,natoms,atom,aname,ptr,TRUE);
+                                              i,atoms,ptr,TRUE);
                  bAddCMAP = bAddCMAP && (cmap_atomid[k] != NO_ATID);
                  if (!bAddCMAP)
                  {
                       * into the atom array. */
                      break;
                  }
-                 this_residue_index = atom[cmap_atomid[k]].resind;
+                 this_residue_index = atoms->atom[cmap_atomid[k]].resind;
                  if (0 == k)
                  {
                      cmap_chainnum = resinfo[this_residue_index].chainnum;
                
                if(residx<nres-1)
                {
-                       while(atom[i].resind<residx+1)
+                       while(atoms->atom[i].resind<residx+1)
                        {
                                i++;
                        }
@@@ -1467,12 -1472,12 +1467,12 @@@ void pdb2top(FILE *top_file, char *posr
    
    /* Make bonds */
    at2bonds(&(plist[F_BONDS]), hb, 
-            atoms->nr, atoms->atom, atoms->atomname, atoms->nres, *x, 
+            atoms, *x,
             long_bond_dist, short_bond_dist, bAllowMissing);
    
    /* specbonds: disulphide bonds & heme-his */
    do_ssbonds(&(plist[F_BONDS]),
-            atoms->nr, atoms->atom, atoms->atomname, nssbonds, ssbonds,
+            atoms, nssbonds, ssbonds,
             bAllowMissing);
    
    nmissat = name2type(atoms, &cgnr, atype, restp, rt);
diff --combined src/kernel/pgutil.c
index 337c8fb21c0ef5658785f32b5932afe06835e1ae,e948dea471b19053e92e5ba9d5435c0d2d5ae47a..db8423932bf926fb2b1bdc50423ccf80af1f15a2
  #endif
  #include "string2.h"
  #include "pgutil.h"
 -#include "string.h"
 +#include <string.h>
  #include "gmx_fatal.h"
  
  #define BUFSIZE 1024
  static void atom_not_found(int fatal_errno,const char *file,int line,
                           const char *atomname,int resind,
+                            const char *resname,
                           const char *bondtype,gmx_bool bAllowMissing)
  {
      char message_buffer[BUFSIZE];
          if (0 != strcmp(bondtype, "atom"))
          {
              snprintf(message_buffer, 1024,
-                      "Atom %s is used in an interaction of type %s in the topology\n"
-                      "database, but an atom of that name was not found in residue\n"
-                      "number %d.\n",
-                      atomname,bondtype,resind+1);
+                      "Residue %d named %s of a molecule in the input file was mapped\n"
+                      "to an entry in the topology database, but the atom %s used in\n"
+                      "an interaction of type %s in that entry is not found in the\n"
+                      "input file. Perhaps your atom and/or residue naming needs to be\n"
+                      "fixed.\n",
+                      resind+1, resname, atomname, bondtype);
          }
          else
          {
              snprintf(message_buffer, 1024,
-                      "Atom %s is used in the topology database, but an atom of that\n"
-                      "name was not found in residue number %d.\n",
-                      atomname,resind+1);
+                      "Residue %d named %s of a molecule in the input file was mapped\n"
+                      "to an entry in the topology database, but the atom %s used in\n"
+                      "that entry is not found in the input file. Perhaps your atom\n"
+                      "and/or residue naming needs to be fixed.\n",
+                      resind+1, resname, atomname);
          }
          if (bAllowMissing)
          {
      }
  }
        
- atom_id search_atom(const char *type,int start,int natoms,t_atom at[],
-                   char ** const * anm,
+ atom_id search_atom(const char *type,int start,
+                     t_atoms *atoms,
                    const char *bondtype,gmx_bool bAllowMissing)
  {
    int     i,resind=-1;
    gmx_bool    bPrevious,bNext;
+   int natoms = atoms->nr;
+   t_atom *at = atoms->atom;
+   char ** const * anm = atoms->atomname;
  
    bPrevious = (strchr(type,'-') != NULL);
    bNext     = (strchr(type,'+') != NULL);
        return (atom_id) i;
      }
      if (!(bNext && at[start].resind==at[natoms-1].resind))
-       atom_not_found(FARGS,type,at[start].resind,bondtype,bAllowMissing);
+     {
+         atom_not_found(FARGS,type,at[start].resind,*atoms->resinfo[resind].name,bondtype,bAllowMissing);
+     }
    }
    else {
      /* The previous residue */
        if (gmx_strcasecmp(type,*(anm[i]))==0)
        return (atom_id) i;
      if (start > 0)
-       atom_not_found(FARGS,type,at[start].resind,bondtype,bAllowMissing);
+     {
+         atom_not_found(FARGS,type,at[start].resind,*atoms->resinfo[resind].name,bondtype,bAllowMissing);
+     }
    }
    return NO_ATID;
  }
diff --combined src/tools/gmx_energy.c
index f5ea9c57f7d120a0dc3f1ce05798e7dcbf61418a,42204e3b1647c60fab7e3078b56c6d5ed0914846..ccbfa431f43f216b4f26ebe436f0f6c4e08c6099
@@@ -136,6 -136,14 +136,6 @@@ static int *select_it(int nre,char *nm[
    return set;
  }
  
 -static int strcount(const char *s1,const char *s2)
 -{
 -  int n=0;
 -  while (s1 && s2 && (toupper(s1[n]) == toupper(s2[n])))
 -    n++;
 -  return n;
 -}
 -
  static void chomp(char *buf)
  {
    int len = strlen(buf);
@@@ -2386,6 -2394,7 +2386,7 @@@ int gmx_energy(int argc,char *argv[]
          }
        }
        }
+       teller++;
      }
    } while (bCont && (timecheck == 0));
    
diff --combined src/tools/gmx_msd.c
index a529b1f3b00b360ed403b09bf9e7c4304e8cc4dc,5e3516ce6a9f376600d09326287480f1d28c74e4..c536fb845b7baed6c25b0af076ef2133352f6a36
@@@ -160,6 -160,16 +160,6 @@@ t_corr *init_corr(int nrgrp,int type,in
    return curr;
  }
  
 -static void done_corr(t_corr *curr)
 -{
 -  int i;
 -  
 -  sfree(curr->n_offs);
 -  for(i=0; (i<curr->nrestart); i++)
 -    sfree(curr->x0[i]);
 -  sfree(curr->x0);
 -}
 -
  static void corr_print(t_corr *curr,gmx_bool bTen,const char *fn,const char *title,
                         const char *yaxis,
                       real msdtime,real beginfit,real endfit,
@@@ -400,6 -410,10 +400,10 @@@ static void prep_data(gmx_bool bMol,in
  
          for(m=DIM-1; m>=0; m--) 
          {
+             if (hbox[m] == 0)
+             {
+                 continue;
+             }
              while(xcur[ind][m]-xprev[ind][m] <= -hbox[m])
                  rvec_inc(xcur[ind],box[m]);
              while(xcur[ind][m]-xprev[ind][m] >  hbox[m])