cmake/FindBLAS.cmake !filter
cmake/FindLAPACK.cmake !filter
cmake/ThreadMPI.cmake !filter
+cmake/FindPythonLibrary.cmake !filter
+cmake/FindNumPy.cmake !filter
+cmake/FindSIP.* !filter
cmake/Platform/BluegeneQ*.cmake !filter
cmake/*.c -filter -gmx-doxygen
cmake/*.cpp -filter -gmx-doxygen
endif()
set(GMX_GPU_DETECTION_DONE TRUE CACHE INTERNAL "Whether GPU detection has already been done")
+#######################
+## Python bindings
+#######################
+
+# We only set option here, actual detection goes to
+# src/python/CMakeLists.txt due to bugs in FindSIP
+option(GMX_PYTHON_BINDINGS "Enable GROMACS Python API bindings" OFF)
+
+
#######################
## uninstall target
#######################
--- /dev/null
+# - Find the NumPy libraries
+# This module finds if NumPy is installed, and sets the following variables
+# indicating where it is.
+#
+# TODO: Update to provide the libraries and paths for linking npymath lib.
+#
+# NUMPY_FOUND - was NumPy found
+# NUMPY_VERSION - the version of NumPy found as a string
+# NUMPY_VERSION_MAJOR - the major version number of NumPy
+# NUMPY_VERSION_MINOR - the minor version number of NumPy
+# NUMPY_VERSION_PATCH - the patch version number of NumPy
+# NUMPY_VERSION_DECIMAL - e.g. version 1.6.1 is 10601
+# NUMPY_INCLUDE_DIRS - path to the NumPy include files
+
+#============================================================================
+# Copyright 2012 Continuum Analytics, Inc.
+#
+# MIT License
+#
+# Permission is hereby granted, free of charge, to any person obtaining
+# a copy of this software and associated documentation files
+# (the "Software"), to deal in the Software without restriction, including
+# without limitation the rights to use, copy, modify, merge, publish,
+# distribute, sublicense, and/or sell copies of the Software, and to permit
+# persons to whom the Software is furnished to do so, subject to
+# the following conditions:
+#
+# The above copyright notice and this permission notice shall be included
+# in all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+# OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+# ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+# OTHER DEALINGS IN THE SOFTWARE.
+#
+#============================================================================
+
+# Finding NumPy involves calling the Python interpreter
+if(NumPy_FIND_REQUIRED)
+ find_package(PythonInterp REQUIRED)
+else()
+ find_package(PythonInterp)
+endif()
+
+if(NOT PYTHONINTERP_FOUND)
+ set(NUMPY_FOUND FALSE)
+ return()
+endif()
+
+execute_process(COMMAND "${PYTHON_EXECUTABLE}" "-c"
+ "import numpy as n; print(n.__version__); print(n.get_include());"
+ RESULT_VARIABLE _NUMPY_SEARCH_SUCCESS
+ OUTPUT_VARIABLE _NUMPY_VALUES_OUTPUT
+ ERROR_VARIABLE _NUMPY_ERROR_VALUE
+ OUTPUT_STRIP_TRAILING_WHITESPACE)
+
+if(NOT _NUMPY_SEARCH_SUCCESS MATCHES 0)
+ if(NumPy_FIND_REQUIRED)
+ message(FATAL_ERROR
+ "NumPy import failure:\n${_NUMPY_ERROR_VALUE}")
+ endif()
+ set(NUMPY_FOUND FALSE)
+ return()
+endif()
+
+# Convert the process output into a list
+string(REGEX REPLACE ";" "\\\\;" _NUMPY_VALUES ${_NUMPY_VALUES_OUTPUT})
+string(REGEX REPLACE "\n" ";" _NUMPY_VALUES ${_NUMPY_VALUES})
+# Just in case there is unexpected output from the Python command.
+list(GET _NUMPY_VALUES -2 NUMPY_VERSION)
+list(GET _NUMPY_VALUES -1 NUMPY_INCLUDE_DIRS)
+
+string(REGEX MATCH "^[0-9]+\\.[0-9]+\\.[0-9]+" _VER_CHECK "${NUMPY_VERSION}")
+if("${_VER_CHECK}" STREQUAL "")
+ # The output from Python was unexpected. Raise an error always
+ # here, because we found NumPy, but it appears to be corrupted somehow.
+ message(FATAL_ERROR
+ "Requested version and include path from NumPy, got instead:\n${_NUMPY_VALUES_OUTPUT}\n")
+ return()
+endif()
+
+# Make sure all directory separators are '/'
+string(REGEX REPLACE "\\\\" "/" NUMPY_INCLUDE_DIRS ${NUMPY_INCLUDE_DIRS})
+
+# Get the major and minor version numbers
+string(REGEX REPLACE "\\." ";" _NUMPY_VERSION_LIST ${NUMPY_VERSION})
+list(GET _NUMPY_VERSION_LIST 0 NUMPY_VERSION_MAJOR)
+list(GET _NUMPY_VERSION_LIST 1 NUMPY_VERSION_MINOR)
+list(GET _NUMPY_VERSION_LIST 2 NUMPY_VERSION_PATCH)
+string(REGEX MATCH "[0-9]*" NUMPY_VERSION_PATCH ${NUMPY_VERSION_PATCH})
+math(EXPR NUMPY_VERSION_DECIMAL
+ "(${NUMPY_VERSION_MAJOR} * 10000) + (${NUMPY_VERSION_MINOR} * 100) + ${NUMPY_VERSION_PATCH}")
+
+find_package_message(NUMPY
+ "Found NumPy: version \"${NUMPY_VERSION}\" ${NUMPY_INCLUDE_DIRS}"
+ "${NUMPY_INCLUDE_DIRS}${NUMPY_VERSION}")
+
+set(NUMPY_FOUND TRUE)
+
--- /dev/null
+# Find Python
+# ~~~~~~~~~~~
+# Find the Python interpreter and related Python directories.
+#
+# This file defines the following variables:
+#
+# PYTHON_EXECUTABLE - The path and filename of the Python interpreter.
+#
+# PYTHON_SHORT_VERSION - The version of the Python interpreter found,
+# excluding the patch version number. (e.g. 2.5 and not 2.5.1))
+#
+# PYTHON_LONG_VERSION - The version of the Python interpreter found as a human
+# readable string.
+#
+# PYTHON_SITE_PACKAGES_INSTALL_DIR - this cache variable can be used for installing
+# own python modules. You may want to adjust this to be the
+# same as ${PYTHON_SITE_PACKAGES_DIR}, but then admin
+# privileges may be required for installation.
+#
+# PYTHON_SITE_PACKAGES_DIR - Location of the Python site-packages directory.
+#
+# PYTHON_INCLUDE_PATH - Directory holding the python.h include file.
+#
+# PYTHON_LIBRARY, PYTHON_LIBRARIES- Location of the Python library.
+
+# Copyright (c) 2007, Simon Edwards <simon@simonzone.com>
+# Copyright (c) 2012, Luca Beltrame <lbeltrame@kde.org>
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+
+include(FindPackageHandleStandardArgs)
+
+find_package(PythonInterp)
+
+if (PYTHONINTERP_FOUND)
+
+ option(INSTALL_PYTHON_FILES_IN_PYTHON_PREFIX "Install the Python files in the Python packages dir" FALSE)
+
+ # Set the Python libraries to what we actually found for interpreters
+ set(Python_ADDITIONAL_VERSIONS "${PYTHON_VERSION_MAJOR}.${PYTHON_VERSION_MINOR}")
+ # These are kept for compatibility
+ set(PYTHON_SHORT_VERSION "${PYTHON_VERSION_MAJOR}.${PYTHON_VERSION_MINOR}")
+ set(PYTHON_LONG_VERSION ${PYTHON_VERSION_STRING})
+
+ find_package(PythonLibs QUIET)
+
+ if(PYTHONLIBS_FOUND)
+ set(PYTHON_LIBRARY ${PYTHON_LIBRARIES})
+ endif(PYTHONLIBS_FOUND)
+
+ # Auto detect Python site-packages directory
+ execute_process(COMMAND ${PYTHON_EXECUTABLE} -c "from distutils.sysconfig import get_python_lib; print(get_python_lib(True))"
+ OUTPUT_VARIABLE PYTHON_SITE_PACKAGES_DIR
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+
+ message(STATUS "Python system site-packages directory: ${PYTHON_SITE_PACKAGES_DIR}")
+ if(INSTALL_PYTHON_FILES_IN_PYTHON_PREFIX)
+ set(PYTHON_SITE_PACKAGES_INSTALL_DIR ${PYTHON_SITE_PACKAGES_DIR})
+ else()
+ execute_process(COMMAND ${PYTHON_EXECUTABLE} -c "from distutils.sysconfig import get_python_lib; print(get_python_lib(True, prefix='${CMAKE_INSTALL_PREFIX}'))"
+ OUTPUT_VARIABLE PYTHON_SITE_PACKAGES_INSTALL_DIR
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+ endif()
+
+ if(NOT PYTHON_SITE_PACKAGES_INSTALL_DIR STREQUAL PYTHON_SITE_PACKAGES_DIR)
+ message(STATUS "The Python files will be installed to ${PYTHON_SITE_PACKAGES_INSTALL_DIR}. Make sure to add them to the Python search path (e.g. by setting PYTHONPATH)")
+ endif()
+
+endif(PYTHONINTERP_FOUND)
+
+find_package_handle_standard_args(PythonLibrary DEFAULT_MSG PYTHON_LIBRARY)
+
--- /dev/null
+# Find SIP
+# ~~~~~~~~
+#
+# SIP website: http://www.riverbankcomputing.co.uk/sip/index.php
+#
+# Find the installed version of SIP. FindSIP should be called after Python
+# has been found.
+#
+# This file defines the following variables:
+#
+# SIP_VERSION - The version of SIP found expressed as a 6 digit hex number
+# suitable for comparison as a string.
+#
+# SIP_VERSION_STR - The version of SIP found as a human readable string.
+#
+# SIP_EXECUTABLE - Path and filename of the SIP command line executable.
+#
+# SIP_INCLUDE_DIR - Directory holding the SIP C++ header file.
+#
+# SIP_DEFAULT_SIP_DIR - Default directory where .sip files should be installed
+# into.
+
+# Copyright (c) 2007, Simon Edwards <simon@simonzone.com>
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+
+
+
+IF(SIP_VERSION)
+ # Already in cache, be silent
+ SET(SIP_FOUND TRUE)
+ELSE(SIP_VERSION)
+
+ FIND_FILE(_find_sip_py FindSIP.py PATHS ${CMAKE_MODULE_PATH})
+
+ EXECUTE_PROCESS(COMMAND ${PYTHON_EXECUTABLE} ${_find_sip_py} OUTPUT_VARIABLE sip_config)
+ IF(sip_config)
+ STRING(REGEX REPLACE "^sip_version:([^\n]+).*$" "\\1" SIP_VERSION ${sip_config})
+ STRING(REGEX REPLACE ".*\nsip_version_str:([^\n]+).*$" "\\1" SIP_VERSION_STR ${sip_config})
+ STRING(REGEX REPLACE ".*\nsip_bin:([^\n]+).*$" "\\1" SIP_EXECUTABLE ${sip_config})
+ IF(NOT SIP_DEFAULT_SIP_DIR)
+ STRING(REGEX REPLACE ".*\ndefault_sip_dir:([^\n]+).*$" "\\1" SIP_DEFAULT_SIP_DIR ${sip_config})
+ ENDIF(NOT SIP_DEFAULT_SIP_DIR)
+ STRING(REGEX REPLACE ".*\nsip_inc_dir:([^\n]+).*$" "\\1" SIP_INCLUDE_DIR ${sip_config})
+ FILE(TO_CMAKE_PATH ${SIP_DEFAULT_SIP_DIR} SIP_DEFAULT_SIP_DIR)
+ FILE(TO_CMAKE_PATH ${SIP_INCLUDE_DIR} SIP_INCLUDE_DIR)
+ IF(EXISTS ${SIP_EXECUTABLE})
+ SET(SIP_FOUND TRUE)
+ ELSE()
+ MESSAGE(STATUS "Found SIP configuration but the sip executable could not be found.")
+ ENDIF()
+ ENDIF(sip_config)
+
+ IF(SIP_FOUND)
+ IF(NOT SIP_FIND_QUIETLY)
+ MESSAGE(STATUS "Found SIP version: ${SIP_VERSION_STR}")
+ ENDIF(NOT SIP_FIND_QUIETLY)
+ ELSE(SIP_FOUND)
+ IF(SIP_FIND_REQUIRED)
+ MESSAGE(FATAL_ERROR "Could not find SIP")
+ ENDIF(SIP_FIND_REQUIRED)
+ ENDIF(SIP_FOUND)
+
+ENDIF(SIP_VERSION)
+
--- /dev/null
+# FindSIP.py
+#
+# Copyright (c) 2007, Simon Edwards <simon@simonzone.com>
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+
+import sys
+import sipconfig
+
+sipcfg = sipconfig.Configuration()
+print("sip_version:%06.0x" % sipcfg.sip_version)
+print("sip_version_str:%s" % sipcfg.sip_version_str)
+print("sip_bin:%s" % sipcfg.sip_bin)
+print("default_sip_dir:%s" % sipcfg.default_sip_dir)
+print("sip_inc_dir:%s" % sipcfg.sip_inc_dir)
+
--- /dev/null
+# By Simon Edwards <simon@simonzone.com>
+# This file is in the public domain.
+import py_compile, sys
+sys.exit(py_compile.main())
+
--- /dev/null
+# Python macros
+# ~~~~~~~~~~~~~
+# Copyright (c) 2007, Simon Edwards <simon@simonzone.com>
+# Copyright (c) 2012, Luca Beltrame <lbeltrame@kde.org>
+# Copyright (c) 2012, Rolf Eike Beer <eike@sf-mail.de>
+#
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+#
+# This file defines the following macros:
+#
+# PYTHON_INSTALL (SOURCE_FILE DESTINATION_DIR)
+# Install the SOURCE_FILE, which is a Python .py file, into the
+# destination directory during install. The file will be byte compiled
+# and both the .py file and .pyc file will be installed.
+
+set(PYTHON_MACROS_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR})
+
+macro(PYTHON_INSTALL SOURCE_FILE DESTINATION_DIR)
+
+ find_file(_python_compile_py PythonCompile.py PATHS ${CMAKE_MODULE_PATH})
+
+ # Install the source file.
+ install(FILES ${SOURCE_FILE} DESTINATION ${DESTINATION_DIR})
+
+ # Byte compile and install the .pyc file, unless explicitly prevented by env..
+ if("$ENV{PYTHONDONTWRITEBYTECODE}" STREQUAL "")
+ get_filename_component(_absfilename ${SOURCE_FILE} ABSOLUTE)
+ get_filename_component(_filename ${SOURCE_FILE} NAME)
+ get_filename_component(_filenamebase ${SOURCE_FILE} NAME_WE)
+ get_filename_component(_basepath ${SOURCE_FILE} PATH)
+
+ if(WIN32)
+ # remove drive letter
+ string(REGEX REPLACE "^[a-zA-Z]:/" "/" _basepath "${_basepath}")
+ endif(WIN32)
+
+ set(_bin_py ${CMAKE_CURRENT_BINARY_DIR}/${_basepath}/${_filename})
+
+ # Python 3.2 changed the pyc file location
+ if(PYTHON_VERSION_STRING VERSION_GREATER 3.1)
+ # To get the right version for suffix
+ set(_bin_pyc "${CMAKE_CURRENT_BINARY_DIR}/${_basepath}/__pycache__/${_filenamebase}.cpython-${PYTHON_VERSION_MAJOR}${PYTHON_VERSION_MINOR}.pyc")
+ set(_py_install_dir "${DESTINATION_DIR}/__pycache__/")
+ else()
+ set(_bin_pyc "${CMAKE_CURRENT_BINARY_DIR}/${_basepath}/${_filenamebase}.pyc")
+ set(_py_install_dir "${DESTINATION_DIR}")
+ endif()
+
+ file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/${_basepath})
+
+ # Setting because it will be displayed later, in compile_python_files
+ set(_message "Byte-compiling ${_bin_py} to ${_bin_pyc}")
+
+ string(REPLACE "/" "_" _rule_name "${_basepath}/${_bin_pyc}")
+ add_custom_target("${_rule_name}" ALL)
+
+ get_filename_component(_abs_bin_py ${_bin_py} ABSOLUTE)
+ if(_abs_bin_py STREQUAL _absfilename) # Don't copy the file onto itself.
+ add_custom_command(
+ TARGET "${_rule_name}"
+ COMMAND "${CMAKE_COMMAND}" -E echo "${_message}"
+ COMMAND "${PYTHON_EXECUTABLE}" "${_python_compile_py}" "${_bin_py}"
+ DEPENDS "${_absfilename}"
+ )
+ else()
+ add_custom_command(
+ TARGET "${_rule_name}"
+ COMMAND "${CMAKE_COMMAND}" -E echo "${_message}"
+ COMMAND "${CMAKE_COMMAND}" -E copy "${_absfilename}" "${_bin_py}"
+ COMMAND "${PYTHON_EXECUTABLE}" "${_python_compile_py}" "${_bin_py}"
+ DEPENDS "${_absfilename}"
+ )
+ endif()
+
+ install(FILES ${_bin_pyc} DESTINATION "${_py_install_dir}")
+ unset(_py_install_dir)
+ unset(_message)
+
+ endif("$ENV{PYTHONDONTWRITEBYTECODE}" STREQUAL "")
+
+endmacro(PYTHON_INSTALL)
+
--- /dev/null
+# Macros for SIP
+# ~~~~~~~~~~~~~~
+# Copyright (c) 2007, Simon Edwards <simon@simonzone.com>
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+#
+# SIP website: http://www.riverbankcomputing.co.uk/sip/index.php
+#
+# This file defines the following macros:
+#
+# ADD_SIP_PYTHON_MODULE (MODULE_NAME MODULE_SIP [library1, libaray2, ...])
+# Specifies a SIP file to be built into a Python module and installed.
+# MODULE_NAME is the name of Python module including any path name. (e.g.
+# os.sys, Foo.bar etc). MODULE_SIP the path and filename of the .sip file
+# to process and compile. libraryN are libraries that the Python module,
+# which is typically a shared library, should be linked to. The built
+# module will also be install into Python's site-packages directory.
+#
+# The behaviour of the ADD_SIP_PYTHON_MODULE macro can be controlled by a
+# number of variables:
+#
+# SIP_INCLUDES - List of directories which SIP will scan through when looking
+# for included .sip files. (Corresponds to the -I option for SIP.)
+#
+# SIP_TAGS - List of tags to define when running SIP. (Corresponds to the -t
+# option for SIP.)
+#
+# SIP_CONCAT_PARTS - An integer which defines the number of parts the C++ code
+# of each module should be split into. Defaults to 8. (Corresponds to the
+# -j option for SIP.)
+#
+# SIP_DISABLE_FEATURES - List of feature names which should be disabled
+# running SIP. (Corresponds to the -x option for SIP.)
+#
+# SIP_EXTRA_OPTIONS - Extra command line options which should be passed on to
+# SIP.
+
+SET(SIP_INCLUDES)
+SET(SIP_TAGS)
+SET(SIP_CONCAT_PARTS 8)
+SET(SIP_DISABLE_FEATURES)
+SET(SIP_EXTRA_OPTIONS)
+
+MACRO(ADD_SIP_PYTHON_MODULE MODULE_NAME MODULE_SIP)
+
+ SET(EXTRA_LINK_LIBRARIES ${ARGN})
+
+ STRING(REPLACE "." "/" _x ${MODULE_NAME})
+ GET_FILENAME_COMPONENT(_parent_module_path ${_x} PATH)
+ GET_FILENAME_COMPONENT(_child_module_name ${_x} NAME)
+
+ GET_FILENAME_COMPONENT(_module_path ${MODULE_SIP} PATH)
+
+ if(_module_path STREQUAL "")
+ set(CMAKE_CURRENT_SIP_OUTPUT_DIR "${CMAKE_CURRENT_BINARY_DIR}")
+ else(_module_path STREQUAL "")
+ set(CMAKE_CURRENT_SIP_OUTPUT_DIR "${CMAKE_CURRENT_BINARY_DIR}/${_module_path}")
+ endif(_module_path STREQUAL "")
+
+ GET_FILENAME_COMPONENT(_abs_module_sip ${MODULE_SIP} ABSOLUTE)
+
+ # We give this target a long logical target name.
+ # (This is to avoid having the library name clash with any already
+ # install library names. If that happens then cmake dependancy
+ # tracking get confused.)
+ STRING(REPLACE "." "_" _logical_name ${MODULE_NAME})
+ SET(_logical_name "python_module_${_logical_name}")
+
+ FILE(MAKE_DIRECTORY ${CMAKE_CURRENT_SIP_OUTPUT_DIR}) # Output goes in this dir.
+
+ SET(_sip_includes)
+ FOREACH (_inc ${SIP_INCLUDES})
+ GET_FILENAME_COMPONENT(_abs_inc ${_inc} ABSOLUTE)
+ LIST(APPEND _sip_includes -I ${_abs_inc})
+ ENDFOREACH (_inc )
+
+ SET(_sip_tags)
+ FOREACH (_tag ${SIP_TAGS})
+ LIST(APPEND _sip_tags -t ${_tag})
+ ENDFOREACH (_tag)
+
+ SET(_sip_x)
+ FOREACH (_x ${SIP_DISABLE_FEATURES})
+ LIST(APPEND _sip_x -x ${_x})
+ ENDFOREACH (_x ${SIP_DISABLE_FEATURES})
+
+ SET(_message "-DMESSAGE=Generating CPP code for module ${MODULE_NAME}")
+ SET(_sip_output_files)
+ FOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )
+ IF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
+ SET(_sip_output_files ${_sip_output_files} ${CMAKE_CURRENT_SIP_OUTPUT_DIR}/sip${_child_module_name}part${CONCAT_NUM}.cpp )
+ ENDIF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
+ ENDFOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )
+
+ IF(NOT WIN32)
+ SET(TOUCH_COMMAND touch)
+ ELSE(NOT WIN32)
+ SET(TOUCH_COMMAND echo)
+ # instead of a touch command, give out the name and append to the files
+ # this is basically what the touch command does.
+ FOREACH(filename ${_sip_output_files})
+ FILE(APPEND filename "")
+ ENDFOREACH(filename ${_sip_output_files})
+ ENDIF(NOT WIN32)
+ ADD_CUSTOM_COMMAND(
+ OUTPUT ${_sip_output_files}
+ COMMAND ${CMAKE_COMMAND} -E echo ${message}
+ COMMAND ${TOUCH_COMMAND} ${_sip_output_files}
+ COMMAND ${SIP_EXECUTABLE} ${_sip_tags} ${_sip_x} ${SIP_EXTRA_OPTIONS} -j ${SIP_CONCAT_PARTS} -c ${CMAKE_CURRENT_SIP_OUTPUT_DIR} ${_sip_includes} ${_abs_module_sip}
+ DEPENDS ${_abs_module_sip} ${SIP_EXTRA_FILES_DEPEND}
+ )
+ # not sure if type MODULE could be uses anywhere, limit to cygwin for now
+ IF (CYGWIN)
+ ADD_LIBRARY(${_logical_name} MODULE ${_sip_output_files} )
+ ELSE (CYGWIN)
+ ADD_LIBRARY(${_logical_name} SHARED ${_sip_output_files} )
+ ENDIF (CYGWIN)
+ TARGET_LINK_LIBRARIES(${_logical_name} ${PYTHON_LIBRARY})
+ TARGET_LINK_LIBRARIES(${_logical_name} ${EXTRA_LINK_LIBRARIES})
+ SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES PREFIX "" OUTPUT_NAME ${_child_module_name})
+
+ INSTALL(TARGETS ${_logical_name} DESTINATION "${PYTHON_SITE_PACKAGES_INSTALL_DIR}/${_parent_module_path}")
+
+ENDMACRO(ADD_SIP_PYTHON_MODULE)
+
if (NOT GMX_FAHCORE)
add_subdirectory(contrib)
endif()
+
+if (GMX_PYTHON_BINDINGS)
+ add_subdirectory(python)
+endif()
*/
virtual void writeOutput() = 0;
+ typedef std::vector<TrajectoryAnalysisModule*> Batch;
+ virtual const Batch getBatch() { return Batch(); }
+
+ virtual const std::vector<char*> getArgv(int) { return std::vector<char*>(); }
+
/*! \brief
* Returns the name of the analysis module.
*
void parseOptions(TrajectoryAnalysisSettings *settings,
TrajectoryAnalysisRunnerCommon *common,
SelectionCollection *selections,
- int *argc, char *argv[]);
+ int *argc, char *argv[], bool full=true);
TrajectoryAnalysisModule *module_;
bool bUseDefaultGroups_;
TrajectoryAnalysisSettings *settings,
TrajectoryAnalysisRunnerCommon *common,
SelectionCollection *selections,
- int *argc, char *argv[])
+ int *argc, char *argv[], bool full)
{
FileNameOptionManager fileoptManager;
SelectionOptionManager seloptManager(selections);
options.addManager(&fileoptManager);
options.addManager(&seloptManager);
- IOptionsContainer &commonOptions = options.addGroup();
+ if (full) {
+ IOptionsContainer &commonOptions = options.addGroup();
+ }
IOptionsContainer &moduleOptions = options.addGroup();
module_->initOptions(&moduleOptions, settings);
- common->initOptions(&commonOptions);
+ if (full) {
+ common->initOptions(&commonOptions);
+ }
selections->initOptions(&commonOptions);
{
options.finish();
}
- common->optionsFinished();
+ if (full) {
+ common->optionsFinished();
+ }
module_->optionsFinished(settings);
common->initIndexGroups(selections, bUseDefaultGroups_);
const bool bInteractive = StandardInputStream::instance().isInteractive();
seloptManager.parseRequestedFromStdin(bInteractive);
- common->doneIndexGroups(selections);
+ common->doneIndexGroups(selections);
common->initTopology(selections);
+
selections->compile();
}
const TopologyInformation &topology = common.topologyInformation();
module->initAnalysis(settings, topology);
+ TrajectoryAnalysisModule::Batch batch = module->getBatch();
+ std::vector<SelectionCollection*> batchSelections;
+ std::vector<Impl*> impls;
+ for (size_t i = 0; i < batch.size(); i++) {
+ TrajectoryAnalysisModule *bmodule = batch[i];
+ batchSelections.push_back(new SelectionCollection());
+ impls.push_back(new Impl(bmodule));
+ std::vector<char*> modArgv = module->getArgv(i);
+ int modArgc = modArgv.size();
+ impls.back()->parseOptions(&settings, &common, batchSelections.back(), &modArgc, modArgv.data(), false);
+
+ batch[i]->initAnalysis(settings, topology);
+ }
+
// Load first frame.
common.initFirstFrame();
module->initAfterFirstFrame(settings, common.frame());
AnalysisDataParallelOptions dataOptions;
TrajectoryAnalysisModuleDataPointer pdata(
module->startFrames(dataOptions, selections));
+
+ std::vector<AnalysisDataParallelOptions> batchOptions;
+ std::vector<TrajectoryAnalysisModuleDataPointer> batchDataPointers;
+ for (size_t i = 0; i < batch.size(); i++) {
+ batch[i]->initAfterFirstFrame(settings, common.frame());
+
+ batchOptions.push_back(AnalysisDataParallelOptions());
+ batchDataPointers.push_back(batch[i]->startFrames(
+ batchOptions.back(), *batchSelections[i]));
+ }
+
do
{
common.initFrame();
set_pbc(ppbc, topology.ePBC(), frame.box);
}
+ for (size_t i = 0; i < batch.size(); i++) {
+ batchSelections[i]->evaluate(&frame, ppbc);
+ batch[i]->analyzeFrame(nframes, frame, ppbc, batchDataPointers[i].get());
+ batch[i]->finishFrameSerial(nframes);
+ }
selections.evaluate(&frame, ppbc);
module->analyzeFrame(nframes, frame, ppbc, pdata.get());
module->finishFrameSerial(nframes);
++nframes;
}
while (common.readNextFrame());
+ for (size_t i = 0; i < batch.size(); i++) {
+ batch[i]->finishFrames(batchDataPointers[i].get());
+ if (batchDataPointers[i].get() != NULL) {
+ batchDataPointers[i]->finish();
+ }
+ batchDataPointers[i].reset();
+ }
+
module->finishFrames(pdata.get());
if (pdata.get() != NULL)
{
}
// Restore the maximal groups for dynamic selections.
+ for (size_t i = 0; i < batch.size(); i++) {
+ batchSelections[i]->evaluateFinal(nframes);
+ batch[i]->finishAnalysis(nframes);
+ batch[i]->writeOutput();
+
+ delete batchSelections[i];
+ delete impls[i];
+ }
+
selections.evaluateFinal(nframes);
module->finishAnalysis(nframes);
*/
RunnerCommandLineModule(const char *name, const char *description,
ModuleFactoryMethod factory)
- : name_(name), description_(description), factory_(factory)
+ : name_(name), description_(description), hasFunction_(true), factory_(factory), functor_(NULL)
+ {
+ }
+
+ /*! \brief
+ * Overloaded constructor accepting a functor instead of function pointer.
+ */
+ RunnerCommandLineModule(const char *name, const char *description,
+ ModuleFactoryFunctor *factory)
+ : name_(name), description_(description), hasFunction_(false), factory_(NULL), functor_(factory)
{
}
virtual void writeHelp(const CommandLineHelpContext &context) const;
private:
- const char *name_;
- const char *description_;
- ModuleFactoryMethod factory_;
+ const char *name_;
+ const char *description_;
+ bool hasFunction_;
+ ModuleFactoryMethod factory_;
+ ModuleFactoryFunctor *functor_;
GMX_DISALLOW_COPY_AND_ASSIGN(RunnerCommandLineModule);
};
int TrajectoryAnalysisCommandLineRunner::Impl::RunnerCommandLineModule::run(
int argc, char *argv[])
{
- TrajectoryAnalysisModulePointer module(factory_());
+ TrajectoryAnalysisModulePointer module(hasFunction_? factory_() : (*functor_)());
TrajectoryAnalysisCommandLineRunner runner(module.get());
return runner.run(argc, argv);
}
void TrajectoryAnalysisCommandLineRunner::Impl::RunnerCommandLineModule::writeHelp(
const CommandLineHelpContext &context) const
{
- TrajectoryAnalysisModulePointer module(factory_());
+ TrajectoryAnalysisModulePointer module(hasFunction_? factory_() : (*functor_)());
TrajectoryAnalysisCommandLineRunner runner(module.get());
runner.writeHelp(context);
}
return CommandLineModuleManager::runAsMainSingleModule(argc, argv, &module);
}
+// static
+int
+TrajectoryAnalysisCommandLineRunner::runAsMain(
+ int argc, char *argv[], ModuleFactoryFunctor *factory)
+{
+ Impl::RunnerCommandLineModule module(NULL, NULL, factory);
+ return CommandLineModuleManager::runAsMainSingleModule(argc, argv, &module);
+}
+
// static
void
TrajectoryAnalysisCommandLineRunner::registerModule(
*/
typedef TrajectoryAnalysisModulePointer (*ModuleFactoryMethod)();
+ /*! \brief
+ * Factory functor class for creating a trajectory analysis module.
+ *
+ * Old compilers that still must be supported do not have std::function,
+ * so we have to implement runAsMain overload accepting a functor instead
+ * of a function pointer.
+ *
+ * This abstract class should be subclassed to be used. The main usage is for
+ * python bindings.
+ */
+ class ModuleFactoryFunctor {
+ public:
+ /*! \brief
+ * operator() that returns a pointer to valid TrajectoryAnalysisModule
+ */
+ virtual TrajectoryAnalysisModulePointer operator() () = 0;
+ virtual ~ModuleFactoryFunctor() {};
+ };
+
/*! \brief
* Implements a main() method that runs a given module.
*
*/
void writeHelp(const CommandLineHelpContext &context);
+ //! Implements the template runAsMain() method.
+ static int runAsMain(int argc, char *argv[],
+ ModuleFactoryMethod factory);
+ //! Overload of runAsMain accepting functor.
+ static int runAsMain(int argc, char *argv[],
+ ModuleFactoryFunctor *factory);
private:
/*! \brief
* Creates a trajectory analysis module of a given type.
return TrajectoryAnalysisModulePointer(new ModuleType());
}
- //! Implements the template runAsMain() method.
- static int runAsMain(int argc, char *argv[],
- ModuleFactoryMethod factory);
class Impl;
}
}
-
void
TrajectoryAnalysisRunnerCommon::initTopology(SelectionCollection *selections)
{
- // Return immediately if the topology has already been loaded.
- if (impl_->topInfo_.hasTopology())
- {
- return;
- }
-
const TrajectoryAnalysisSettings &settings = impl_->settings_;
const bool bRequireTop
= settings.hasFlag(TrajectoryAnalysisSettings::efRequireTop)
}
// Load the topology if requested.
- if (!impl_->topfile_.empty())
+ if (!impl_->topfile_.empty() && !impl_->topInfo_.hasTopology())
{
char title[STRLEN];
--- /dev/null
+#
+# This file is part of the GROMACS molecular simulation package.
+#
+# Copyright (c) 2014, by the GROMACS development team, led by
+# Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+# and including many others, as listed in the AUTHORS file in the
+# top-level source directory and at http://www.gromacs.org.
+#
+# GROMACS is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public License
+# as published by the Free Software Foundation; either version 2.1
+# of the License, or (at your option) any later version.
+#
+# GROMACS is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with GROMACS; if not, see
+# http://www.gnu.org/licenses, or write to the Free Software Foundation,
+# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+#
+# If you want to redistribute modifications to GROMACS, please
+# consider that scientific software is very special. Version
+# control is crucial - bugs must be traceable. We will be happy to
+# consider code for inclusion in the official distribution, but
+# derived work must not be called official GROMACS. Details are found
+# in the README & COPYING files - if they are missing, get the
+# official version at http://www.gromacs.org.
+#
+# To help us fund GROMACS development, we humbly ask that you cite
+# the research papers on the package. Check out http://www.gromacs.org.
+#
+
+find_package(PythonLibrary REQUIRED)
+find_package(NumPy REQUIRED)
+find_package(SIP REQUIRED)
+
+include(SIPMacros)
+include(PythonMacros)
+
+include_directories(
+ ${PYTHON_INCLUDE_PATH}
+ ${SIP_INCLUDE_DIR}
+ ${GROMACS_INCLUDE_DIRS}
+ ${CMAKE_SOURCE_DIR}/src/python/include
+ ${NUMPY_INCLUDE_DIRS}
+)
+
+add_definitions(-DNPY_NO_DEPRECATED_API=NPY_1_7_API_VERSION)
+
+set(SIP_INCLUDES ${CMAKE_BINARY_DIR} sip)
+set(SIP_EXTRA_OPTIONS ${SIP_EXTRA_OPTIONS} -e -o)
+
+file(GLOB common_files_sip sip/*.sip)
+
+file(GLOB options_files_sip sip/options/*.sip)
+set(SIP_EXTRA_FILES_DEPEND ${options_files_sip} ${common_files_sip})
+add_sip_python_module(gromacs.Options sip/options/Options.sip libgromacs)
+
+file(GLOB topology_files_sip sip/topology/*.sip)
+set(SIP_EXTRA_FILES_DEPEND ${topology_files_sip} ${common_files_sip})
+add_sip_python_module(gromacs.Topology
+ sip/topology/Topology.sip libgromacs)
+
+# This is needed for NumPy, which does not like code in many files
+set(SIP_CONCAT_PARTS 1)
+
+file(GLOB selection_files_sip sip/selection/*.sip)
+set(SIP_EXTRA_FILES_DEPEND ${selection_files_sip} ${common_files_sip})
+add_sip_python_module(gromacs.Selection
+ sip/selection/Selection.sip libgromacs)
+
+file(GLOB trajectoryanalysis_files_sip sip/trajectoryanalysis/*.sip)
+set(SIP_EXTRA_FILES_DEPEND ${trajectoryanalysis_files_sip} ${common_files_sip})
+add_sip_python_module(gromacs.TrajectoryAnalysis
+ sip/trajectoryanalysis/TrajectoryAnalysis.sip libgromacs)
+
+python_install(__init__.py ${PYTHON_SITE_PACKAGES_INSTALL_DIR}/gromacs)
+
+install(DIRECTORY runner DESTINATION ${PYTHON_SITE_PACKAGES_INSTALL_DIR}/gromacs)
+python_install(runner/__init__.py ${PYTHON_SITE_PACKAGES_INSTALL_DIR}/gromacs)
+python_install(runner/pipeline.py ${PYTHON_SITE_PACKAGES_INSTALL_DIR}/gromacs)
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+#ifndef NUMPY_CONV_H
+#define NUMPY_CONV_H
+
+#include <Python.h>
+#include <numpy/ndarrayobject.h>
+
+PyObject* array2dToNumpy(int dim1, int dim2, const void *data) {
+ npy_intp dims[] = {dim1, dim2};
+ #ifdef GMX_DOUBLE
+ return PyArray_SimpleNewFromData(2, dims, NPY_DOUBLE, (double*) data);
+ #else
+ return PyArray_SimpleNewFromData(2, dims, NPY_FLOAT, (float*) data);
+ #endif
+}
+
+PyObject* array1dToNumpy(int dim, const void *data) {
+ npy_intp n_dim = dim;
+ #ifdef GMX_DOUBLE
+ return PyArray_SimpleNewFromData(1, &n_dim, NPY_DOUBLE, (double*) data);
+ #else
+ return PyArray_SimpleNewFromData(1, &n_dim, NPY_FLOAT, (float*) data);
+ #endif
+}
+
+PyObject* iarray1dToNumpy(int dim, const int *data) {
+ npy_intp n_dim = dim;
+ return PyArray_SimpleNewFromData(1, &n_dim, NPY_INT, (int*) data);
+}
+#endif
--- /dev/null
+
+from gromacs import TrajectoryAnalysis
+from runner.pipeline import GromacsPipeline, runPipeline
+
+class Test(TrajectoryAnalysis.TrajectoryAnalysisModule):
+
+ def __init__(self):
+ super(Test, self).__init__("test", "test")
+
+ def initOptions(self, options, settings):
+ settings.setHelpText(self.description())
+
+ def getBatch(self):
+ return self.modules
+
+ def getArgv(self, i):
+ return self.options[i]
+
+ def initAnalysis(self, settings, top):
+ pass
+
+ def analyzeFrame(self, frnr, frame, pbc, data):
+ print("Analyzing frame in Test module")
+
+ def finishAnalysis(self, nframes):
+ pass
+
+ def writeOutput(self):
+ pass
+
+modules = [
+ ("Angle", "-group1 System -oav angles.xvg"),
+ (Test(), ""),
+ (TrajectoryAnalysis.SasaInfo.create(), "-surface DNA"),
+]
+
+pipeline = runPipeline(name="Pipeline", modules=modules, keep_datasets=True)
+dataset = pipeline.modules[0].datasetFromIndex(1)
+for i in range(dataset.frameCount()):
+ print('frame =', i, ', columnCount =', dataset.columnCount(), ', y =', dataset.getDataFrame(i).y(0))
--- /dev/null
+
+from gromacs import Options, TrajectoryAnalysis
+import sys, shlex
+
+class GromacsPipeline(TrajectoryAnalysis.TrajectoryAnalysisModule):
+
+ def __init__(self,
+ name="PythonPipeline",
+ description="Pipeline of modules created with Python",
+ modules=[],
+ keep_datasets=False,
+ ):
+ super(GromacsPipeline, self).__init__(name, description)
+
+ self.optionsHolder = Options.PyOptionsHolder()
+
+ self.modules = []
+ self.options = []
+
+ for module, options in modules:
+ if not isinstance(module, TrajectoryAnalysis.TrajectoryAnalysisModule):
+ info_name = module + "Info"
+ if not hasattr(TrajectoryAnalysis, info_name):
+ raise ValueError("There is no module named {}".format(name))
+
+ module = getattr(TrajectoryAnalysis, info_name).create()
+
+ options_list = [name] + shlex.split(options)
+
+ if keep_datasets:
+ for i in range(module.datasetCount()):
+ module.datasetFromIndex(i).requestStorage(-1)
+
+ self.modules.append(module)
+ self.options.append(options_list)
+
+ def initOptions(self, options, settings):
+ settings.setHelpText(self.description())
+
+ def getBatch(self):
+ return self.modules
+
+ def getArgv(self, i):
+ return self.options[i]
+
+ def initAnalysis(self, settings, top):
+ pass
+
+ def analyzeFrame(self, frnr, frame, pbc, data):
+ pass
+
+ def finishAnalysis(self, nframes):
+ pass
+
+ def writeOutput(self):
+ pass
+
+ def run(self, argv):
+ if argv is None:
+ argv = sys.argv
+
+ TrajectoryAnalysis.runAsMain(self, argv)
+
+def runPipeline(argv=None, *args, **kwargs):
+ pipeline = GromacsPipeline(*args, **kwargs)
+ pipeline.run(argv)
+
+ return pipeline
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%Exception std::out_of_range(SIP_IndexError) {
+
+%TypeHeaderCode
+#include <stdexcept>
+%End
+
+%RaiseCode
+ SIP_BLOCK_THREADS
+ PyErr_SetString(PyExc_IndexError, sipExceptionRef.what());
+ SIP_UNBLOCK_THREADS
+%End
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%Module gromacs.Options
+
+%DefaultEncoding "UTF-8"
+
+%Import selection/Selection.sip
+
+%Include options.sip
+%Include abstractoption.sip
+%Include pyoptionsholder.sip
+
+// This has to be here, instead of 'gromacs.Selection', because otherwise we'll get circular dependencies between sip modules
+%Include selectionoption.sip
+%Include basicoptions.sip
+%Include filenameoption.sip
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+class AbstractOption /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/options/abstractoption.h>
+using gmx::AbstractOption;
+%End
+};
+
+template<T, U> class OptionTemplate : AbstractOption /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/options/abstractoption.h>
+using namespace gmx;
+%End
+public:
+ U& description(const char * /KeepReference/);
+ U& hidden(bool = true);
+ U& required(bool = true);
+ U& allowMultiple(bool = true);
+ // FIXME
+ // These function do not work, because they store pointer to argument, which then is garbage collected in python.
+ // Different combinations of Factory, KeepReference and Transfer annotations do not help.
+ // Use third argument of PyOptionsHolder's methods instead.
+ U& defaultValue(const T&);
+ U& defaultValueIfSet(const T&);
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%ModuleHeaderCode
+typedef gmx::OptionTemplate<double, gmx::DoubleOption> DoubleOptionTemplate;
+typedef gmx::OptionTemplate<int, gmx::IntegerOption> IntegerOptionTemplate;
+typedef gmx::OptionTemplate<std::string, gmx::StringOption> StringOptionTemplate;
+typedef gmx::OptionTemplate<bool, gmx::BooleanOption> BooleanOptionTemplate;
+%End
+
+class std::string;
+typedef OptionTemplate<double, DoubleOption> DoubleOptionTemplate;
+typedef OptionTemplate<int, IntegerOption> IntegerOptionTemplate;
+typedef OptionTemplate<std::string, StringOption> StringOptionTemplate;
+typedef OptionTemplate<bool, BooleanOption> BooleanOptionTemplate;
+
+class DoubleOption : DoubleOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/options/basicoptions.h"
+using gmx::DoubleOption;
+%End
+};
+class IntegerOption : IntegerOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/options/basicoptions.h"
+using gmx::IntegerOption;
+%End
+};
+class StringOption : StringOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/options/basicoptions.h"
+using gmx::StringOption;
+%End
+public:
+ StringOption& defaultValue(const char *);
+ %MethodCode
+ sipRes = &sipCpp->defaultValue(std::string(a0));
+ %End
+};
+class BooleanOption : BooleanOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/options/basicoptions.h"
+using gmx::BooleanOption;
+%End
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%ModuleHeaderCode
+#include "gromacs/options/filenameoption.h"
+#include "gromacs/fileio/filenm.h"
+typedef gmx::OptionTemplate<std::string, gmx::FileNameOption> FileNameOptionTemplate;
+using namespace gmx; // needed for compilation of enum
+%End
+
+typedef OptionTemplate<std::string, FileNameOption> FileNameOptionTemplate;
+
+enum OptionFileType {
+ eftUnknown, eftTopology, eftTrajectory, eftPDB,
+ eftIndex, eftPlot, eftGenericData, eftOptionFileType_NR
+};
+
+enum {
+ efMDP,
+ efTRX, efTRO, efTRN, efTRR, efCOMPRESSED, efXTC, efTNG,
+ efEDR,
+ efSTX, efSTO, efGRO, efG96, efPDB, efBRK, efENT, efESP, efPQR,
+ efCPT,
+ efLOG, efXVG, efOUT,
+ efNDX,
+ efTOP, efITP,
+ efTPS, efTPR,
+ efTEX, efRTP, efATP, efHDB,
+ efDAT, efDLG,
+ efMAP, efEPS, efMAT, efM2P,
+ efMTX,
+ efEDI,
+ efCUB,
+ efXPM,
+ efRND,
+ efNR
+};
+
+class FileNameOption : FileNameOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/options/filenameoption.h"
+using gmx::FileNameOption;
+%End
+public:
+ FileNameOption& filetype(OptionFileType);
+ FileNameOption& legacyType(int);
+ FileNameOption& inputFile();
+ FileNameOption& outputFile();
+ FileNameOption& inputOutputFile();
+ FileNameOption& readWriteFlags(bool, bool);
+ FileNameOption& libraryFile(bool = true);
+ FileNameOption& defaultBasename(const char* /KeepReference/);
+ FileNameOption& defaultType(int);
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+class IOptionManager /NoDefaultCtors/ {
+%TypeHeaderCode
+
+#include <gromacs/options/options.h>
+using gmx::IOptionManager;
+%End
+
+protected:
+ virtual ~IOptionManager();
+};
+
+class Options {
+%TypeHeaderCode
+
+#include <gromacs/options/options.h>
+using gmx::Options;
+%End
+
+public:
+ Options(const char *name, const char *title);
+ void addManager (IOptionManager *manager);
+ void addSubSection (Options *section);
+ void addOption(const AbstractOption &settings);
+
+ bool isSet(const char *name) const;
+ void finish();
+private:
+ Options(const Options &other);
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%ModuleHeaderCode
+#include <exception>
+#include "gromacs/options/basicoptions.h"
+#include "gromacs/options/filenameoption.h"
+#include "gromacs/selection/selectionoption.h"
+#include <map>
+#include <string>
+
+class PyOptionsHolder {
+public:
+ class DuplicateOption : public std::exception {
+ public:
+ virtual const char* what() const throw();
+ };
+ class StringList {
+ public:
+ StringList(const std::vector<std::string>*);
+ StringList(const std::string*, size_t);
+ const char* operator[] (size_t);
+ private:
+ const std::string *list;
+ size_t size;
+ const std::vector<std::string> *vector;
+ };
+ gmx::DoubleOption doubleOption(const char*, size_t = 1, double* = NULL);
+ gmx::IntegerOption integerOption(const char*, size_t = 1, int* = NULL);
+ gmx::StringOption stringOption(const char*, size_t = 1, const char* = NULL);
+ gmx::BooleanOption booleanOption(const char*, size_t = 1, bool = 0);
+ gmx::SelectionOption selectionOption(const char*, size_t = 1);
+ gmx::FileNameOption fileNameOption(const char*, size_t = 1);
+ PyObject* get_value(const char*);
+ ~PyOptionsHolder();
+private:
+ struct option_value {
+ void *value;
+ const char *type;
+ int *count;
+ bool vector;
+ const char *name;
+ };
+ std::map<std::string, option_value> storage;
+ template<typename T, typename U> U createStorage(const char*, const char*, int, const T* = 0);
+ template<typename T> PyObject* buildValue(const char*, const option_value&, const sipTypeDef* = NULL, size_t = 0);
+ template<typename T> void deleteStorage(const option_value&);
+};
+%End
+
+%ModuleCode
+#include "gromacs/utility/gmxassert.h"
+
+const char* PyOptionsHolder::DuplicateOption::what() const throw() {
+ return "This option is already defined";
+}
+
+PyOptionsHolder::StringList::StringList(const std::vector<std::string> *vector) :
+ list(NULL), size(vector->size()), vector(vector)
+{}
+
+PyOptionsHolder::StringList::StringList(const std::string *list, size_t size) :
+ list(list), size(size), vector(NULL)
+{}
+
+const char* PyOptionsHolder::StringList::operator[](size_t i) {
+ if (i >= size)
+ return NULL;
+ return vector ? (*vector)[i].data() : list[i].data();
+}
+
+template<typename T, typename U> U PyOptionsHolder::createStorage(const char *name, const char *type, int count, const T *def) {
+ if (storage.count(name))
+ throw DuplicateOption();
+
+ U option(name);
+
+ option_value value;
+ value.type = type;
+ value.count = new int;
+ value.name = name;
+
+ if (count == 0) { // std::vector of values
+ std::vector<T> *store = new std::vector<T>();
+ option.storeVector(store);
+ option.multiValue();
+ option.storeCount(value.count);
+
+ *value.count = 0;
+ if (def) {
+ store->push_back(*def);
+ *value.count = 1;
+ }
+
+ value.value = store;
+ value.vector = true;
+ } else { // exactly `count` values
+ T *store = new T[count];
+ if (def)
+ store[0] = *def;
+
+ option.store(store);
+ if (count > 1)
+ option.valueCount(count);
+
+ value.value = store;
+ value.vector = false;
+ *value.count = count;
+ }
+
+ storage[name] = value;
+ return option;
+}
+
+gmx::DoubleOption PyOptionsHolder::doubleOption(const char *name, size_t count, double *def) {
+ gmx::DoubleOption option = createStorage<double, gmx::DoubleOption>(name, "d", count, def);
+
+ return option;
+}
+
+gmx::IntegerOption PyOptionsHolder::integerOption(const char *name, size_t count, int *def) {
+ gmx::IntegerOption option = createStorage<int, gmx::IntegerOption>(name, "i", count, def);
+
+ return option;
+}
+
+gmx::StringOption PyOptionsHolder::stringOption(const char *name, size_t count, const char* def) {
+ std::string *s_def = NULL;
+ if (def)
+ s_def = new std::string(def);
+
+ gmx::StringOption option = createStorage<std::string, gmx::StringOption>(name, "A", count, s_def);
+ delete s_def;
+
+ return option;
+}
+
+// FIXME: Unify with the rest
+gmx::BooleanOption PyOptionsHolder::booleanOption(const char *name, size_t count, bool def) {
+ if (storage.count(name))
+ throw DuplicateOption();
+
+ bool *store = new bool;
+ *store = def;
+ gmx::BooleanOption option(name);
+ option.store(store);
+ option_value value = {store, "b"};
+ storage[name] = value;
+
+ return option;
+}
+
+gmx::SelectionOption PyOptionsHolder::selectionOption(const char *name, size_t count) {
+ gmx::SelectionOption option = createStorage<gmx::Selection, gmx::SelectionOption>(name, "S", count);
+
+ return option;
+}
+
+gmx::FileNameOption PyOptionsHolder::fileNameOption(const char *name, size_t count) {
+ gmx::FileNameOption option = createStorage<std::string, gmx::FileNameOption>(name, "f", count);
+
+ return option;
+}
+
+template<typename T> PyObject* PyOptionsHolder::buildValue(const char *sipType, const PyOptionsHolder::option_value &value, const sipTypeDef *td, size_t size) {
+ int count = *value.count;
+ T *store = !value.vector ? (T*) value.value : ((std::vector<T>*) value.value)->data();
+
+ if (count == 1 && !value.vector) {
+ if (td)
+ return sipConvertFromType(store, td, NULL);
+ else
+ return sipBuildResult(NULL, sipType, *store);
+ } else {
+ if (td)
+ return sipConvertToTypedArray(store, td, NULL, size, count, SIP_READ_ONLY);
+ else
+ return sipConvertToArray(store, sipType, count, SIP_READ_ONLY);
+ }
+}
+
+
+PyObject* PyOptionsHolder::get_value(const char *name) {
+ if (!storage.count(name))
+ return NULL;
+
+ option_value v = storage[name];
+ switch (*v.type) {
+ case 'd': // double
+ return buildValue<double>("d", v);
+ break;
+ case 'i': // int
+ return buildValue<int>("i", v);
+ break;
+ case 'A': // std::string
+ case 'f': // FileNameOption
+ if (v.vector)
+ return sipConvertFromType(new PyOptionsHolder::StringList(((std::vector<std::string>*) v.value)), sipType_PyOptionsHolder_StringList, Py_None);
+ else if (*v.count == 1)
+ return sipBuildResult(NULL, "A", ((std::string*) v.value)->data());
+ else
+ return sipConvertFromType(new PyOptionsHolder::StringList((std::string*) v.value, *v.count), sipType_PyOptionsHolder_StringList, Py_None);
+ break;
+ case 'b': // bool
+ // TODO: support vector bool options
+ return sipBuildResult(NULL, v.type, *((bool*) v.value));
+ break;
+ case 'S': // Selection
+ return buildValue<gmx::Selection>(NULL, v, sipType_Selection, sizeof(gmx::Selection));
+ break;
+ }
+
+ GMX_ASSERT(false, "Some type is not handled in PyOptionsHolder.get_value");
+ return NULL;
+}
+
+template<typename T> void PyOptionsHolder::deleteStorage(const PyOptionsHolder::option_value &value) {
+ if (value.vector)
+ delete (std::vector<T> *) value.value;
+ else
+ delete[] (T*) value.value;
+
+ delete value.count;
+}
+
+PyOptionsHolder::~PyOptionsHolder() {
+ for (std::map<std::string, option_value>::iterator it = storage.begin(); it != storage.end(); it++)
+ switch (*(it->second.type)) {
+ case 'd': // double
+ deleteStorage<double>(it->second);
+ break;
+ case 'i': // int
+ deleteStorage<int>(it->second);
+ break;
+ case 'A': // std::string
+ case 'f': // FileNameOption (the storage type is still std::string)
+ deleteStorage<std::string>(it->second);
+ break;
+ case 'b': // bool
+ delete (bool*) it->second.value;
+ break;
+ case 'S': // Selection
+ deleteStorage<gmx::Selection>(it->second);
+ break;
+ }
+}
+%End
+
+%Exception PyOptionsHolder::DuplicateOption {
+%RaiseCode
+ SIP_BLOCK_THREADS;
+ PyErr_SetString(PyExc_ValueError, sipExceptionRef.what());
+ SIP_UNBLOCK_THREADS;
+%End
+};
+
+class PyOptionsHolder {
+%TypeHeaderCode
+#include "gromacs/options/basicoptions.h"
+%End
+
+public:
+ class StringList /NoDefaultCtors/ {
+ public:
+ const char* operator[] (int);
+ %MethodCode
+ sipRes = (*sipCpp)[a0];
+
+ if (!sipRes) {
+ SIP_BLOCK_THREADS;
+ PyErr_SetString(PyExc_IndexError, "Index out of range");
+ SIP_UNBLOCK_THREADS;
+ sipIsErr = 1;
+ }
+ %End
+ };
+ // These methods are given twice to workaround sip setting 0 for when '*def = NULL' option is not given
+ DoubleOption doubleOption(const char *name /KeepReference/, int count = 1) throw (PyOptionsHolder::DuplicateOption);
+ DoubleOption doubleOption(const char *name /KeepReference/, int count, const double *def) throw (PyOptionsHolder::DuplicateOption);
+
+ IntegerOption integerOption(const char *name /KeepReference/, int count = 1) throw (PyOptionsHolder::DuplicateOption);
+ IntegerOption integerOption(const char *name /KeepReference/, int count, const int *def) throw (PyOptionsHolder::DuplicateOption);
+
+ StringOption stringOption(const char *name /KeepReference/, int count = 1) throw (PyOptionsHolder::DuplicateOption);
+ StringOption stringOption(const char *name /KeepReference/, int count, const char *def) throw (PyOptionsHolder::DuplicateOption);
+
+ BooleanOption booleanOption(const char *name /KeepReference/, int count = 1, bool def = 0) throw (PyOptionsHolder::DuplicateOption);
+
+ SelectionOption selectionOption(const char *name /KeepReference/, int count = 1) throw (PyOptionsHolder::DuplicateOption);
+
+ FileNameOption fileNameOption(const char *name /KeepReference/, int count = 1) throw (PyOptionsHolder::DuplicateOption);
+ SIP_PYOBJECT __getitem__(const char *name);
+ %MethodCode
+ sipRes = sipCpp->get_value(a0);
+
+ if (!sipRes) {
+ SIP_BLOCK_THREADS;
+ PyErr_SetString(PyExc_KeyError, "Invalid option name");
+ SIP_UNBLOCK_THREADS;
+ sipIsErr = 1;
+ }
+ %End
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%ModuleHeaderCode
+#include "gromacs/options/abstractoption.h"
+#include "gromacs/selection/selectionoption.h"
+typedef gmx::OptionTemplate<gmx::Selection, gmx::SelectionOption> SelectionOptionTemplate;
+%End
+
+typedef OptionTemplate<Selection, SelectionOption> SelectionOptionTemplate;
+
+class SelectionOption : SelectionOptionTemplate /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/selection/selectionoption.h"
+using namespace gmx;
+%End
+
+public:
+ SelectionOption& evaluateVelocities();
+ SelectionOption& evaluateForces();
+ SelectionOption& onlyAtoms();
+ SelectionOption& onlyStatic();
+ SelectionOption& dynamicMask();
+ SelectionOption& allowEmpty();
+ SelectionOption& defaultSelectionText(const char*);
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%Module gromacs.Selection
+
+%DefaultEncoding "UTF-8"
+
+%Include selection.sip
+
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%PostInitialisationCode
+import_array();
+%End
+
+enum e_index_t {
+ INDEX_UNKNOWN,
+ INDEX_ATOM,
+ INDEX_RES,
+ INDEX_MOL,
+ INDEX_ALL
+};
+
+class SelectionPosition /NoDefaultCtors/ {
+%TypeHeaderCode
+#include "gromacs/selection/selection.h"
+using namespace gmx;
+%End
+
+public:
+ e_index_t type();
+ SIP_PYOBJECT x();
+ %MethodCode
+ sipRes = array1dToNumpy(3, sipCpp->x());
+ %End
+ SIP_PYOBJECT v();
+ %MethodCode
+ sipRes = array1dToNumpy(3, sipCpp->v());
+ %End
+ SIP_PYOBJECT f();
+ %MethodCode
+ sipRes = array1dToNumpy(3, sipCpp->f());
+ %End
+ double mass();
+ double charge();
+ int atomCount();
+ SIP_PYOBJECT atomIndices();
+ %MethodCode
+ sipRes = iarray1dToNumpy(sipCpp->atomIndices().size(), sipCpp->atomIndices().data());
+ %End
+ bool selected();
+ int refId();
+ int mappedId();
+};
+
+enum e_coverfrac_t {
+ CFRAC_NONE,
+ CFRAC_SOLIDANGLE
+};
+
+class Selection {
+%TypeHeaderCode
+#include "gromacs/selection/selection.h"
+#include "numpy_conv.h"
+using namespace gmx;
+%End
+
+public:
+ bool isValid();
+ bool __eq__(const Selection&);
+ bool __ne__(const Selection&);
+ const char* name();
+ const char* selectionText();
+ bool isDynamic();
+ e_index_t type();
+ bool hasOnlyAtoms();
+ int atomCount();
+ SIP_PYOBJECT atomIndices();
+ %MethodCode
+ sipRes = iarray1dToNumpy(sipCpp->atomIndices().size(), sipCpp->atomIndices().data());
+ %End
+ int posCount();
+ SelectionPosition position(int);
+ SIP_PYOBJECT coordinates();
+ %MethodCode
+ sipRes = array2dToNumpy(sipCpp->coordinates().size(), 3, sipCpp->coordinates().data());
+ %End
+ bool hasVelocities();
+ SIP_PYOBJECT velocities();
+ %MethodCode
+ sipRes = array2dToNumpy(sipCpp->velocities().size(), 3, sipCpp->velocities().data());
+ %End
+ bool hasForces();
+ SIP_PYOBJECT forces();
+ %MethodCode
+ sipRes = array2dToNumpy(sipCpp->forces().size(), 3, sipCpp->forces().data());
+ %End
+ SIP_PYOBJECT masses();
+ %MethodCode
+ sipRes = array1dToNumpy(sipCpp->masses().size(), sipCpp->masses().data());
+ %End
+ SIP_PYOBJECT charges();
+ %MethodCode
+ sipRes = array1dToNumpy(sipCpp->charges().size(), sipCpp->charges().data());
+ %End
+ SIP_PYOBJECT refIds();
+ %MethodCode
+ sipRes = iarray1dToNumpy(sipCpp->refIds().size(), sipCpp->refIds().data());
+ %End
+ SIP_PYOBJECT mappedIds();
+ %MethodCode
+ sipRes = iarray1dToNumpy(sipCpp->mappedIds().size(), sipCpp->mappedIds().data());
+ %End
+ bool isCoveredFractionDynamic();
+ double coveredFraction();
+ bool initCoveredFraction(e_coverfrac_t);
+ void setEvaluateVelocities(bool);
+ void setEvaluateForces(bool);
+ void setOriginalId(int, int);
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%MappedType std::string
+{
+%TypeHeaderCode
+#include <string>
+%End
+
+%ConvertToTypeCode
+if (sipIsErr == NULL)
+ return PyBytes_Check(sipPy);
+
+ *sipCppPtr = new std::string(PyBytes_AsString(sipPy), PyBytes_Size(sipPy));
+
+ return sipGetState(sipTransferObj);
+%End
+
+%ConvertFromTypeCode
+return PyBytes_FromStringAndSize(sipCpp->data(),sipCpp->length());
+%End
+
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%Module gromacs.Topology
+
+%DefaultEncoding "UTF-8"
+
+%Include pstringlistwrapper.sip
+
+%Include atoms.sip
+%Include topology.sip
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+struct t_atom {
+
+%TypeHeaderCode
+#include <gromacs/topology/atoms.h>
+%End
+
+ double m; double q; /* Mass and charge */
+ double mB; double qB; /* Mass and charge for Free Energy calc */
+ unsigned short type; /* Atom type */
+ unsigned short typeB; /* Atom type for Free Energy calc */
+ int ptype; /* Particle type */
+ int resind; /* Index into resinfo (in t_atoms) */
+ int atomnumber; /* Atomic Number or NOTSET */
+ char *elem /NoSetter/; /* Element name */
+};
+
+struct t_resinfo {
+
+%TypeHeaderCode
+#include <gromacs/topology/atoms.h>
+%End
+
+ SIP_PYOBJECT /* char** */ name /NoSetter/ { /* Pointer to the residue name */
+ %GetCode
+ sipPy = sipBuildResult(NULL, "A", (sipCpp->name) ? *(sipCpp->name) : NULL);
+ %End
+ };
+ int nr; /* Residue number */
+ unsigned char ic; /* Code for insertion of residues */
+ int chainnum; /* Iincremented at TER or new chain id */
+ char chainid; /* Chain identifier written/read to pdb */
+ SIP_PYOBJECT /* char** */ rtp /NoSetter/ { /* rtp building block name (optional) */
+ %GetCode
+ sipPy = sipBuildResult(NULL, "A", (sipCpp->rtp) ? *(sipCpp->rtp) : NULL);
+ %End
+ };
+};
+
+struct t_pdbinfo {
+
+%TypeHeaderCode
+#include <gromacs/topology/atoms.h>
+%End
+
+ int type; /* PDB record name */
+ int atomnr; /* PDB atom number */
+ char altloc; /* Alternate location indicator */
+ char *atomnm /NoSetter/; /* True atom name including leading spaces */
+ double occup; /* Occupancy */
+ double bfac; /* B-factor */
+ bool bAnisotropic; /* (an)isotropic switch */
+ SIP_PYOBJECT /* int * */ uij /NoSetter/ {
+ %GetCode
+ sipPy = sipConvertToArray(sipCpp->uij, "i", 6, SIP_READ_ONLY);
+ %End
+ };
+};
+
+struct t_grps {
+
+%TypeHeaderCode
+#include <gromacs/topology/atoms.h>
+%End
+
+ int nr; /* Number of different groups */
+ SIP_PYOBJECT /* int* */ nm_ind /NoSetter/ {
+ %GetCode
+ sipPy = sipConvertToArray(sipCpp->nm_ind, "i", sipCpp->nr, SIP_READ_ONLY);
+ %End
+ };
+};
+
+
+struct t_atoms {
+
+%TypeHeaderCode
+#include <gromacs/topology/atoms.h>
+// Sip creates 'copy_[typename]' functions. In this case it coincides with function from atoms.h, so we need to rename it.
+#define copy_t_atoms copy_t_atoms_sip
+%End
+
+ int nr; /* Nr of atoms */
+ t_atom *atom /NoSetter/ {
+ %GetCode
+ sipPy = sipConvertToTypedArray(sipCpp->atom, sipType_t_atom, NULL, sizeof(t_atom), sipCpp->nr, SIP_READ_ONLY);
+ %End
+ };
+ PStringListWrapper atomname /NoSetter/ {
+ %GetCode
+ PStringListWrapper *wrapper = new PStringListWrapper(sipCpp->atomname, sipCpp->nr);
+ sipPy = sipConvertFromType(wrapper, sipType_PStringListWrapper, Py_None);
+ %End
+ };
+ PStringListWrapper atomtype /NoSetter/ {
+ %GetCode
+ PStringListWrapper *wrapper = new PStringListWrapper(sipCpp->atomtype, sipCpp->nr);
+ sipPy = sipConvertFromType(wrapper, sipType_PStringListWrapper, Py_None);
+ %End
+ };
+ PStringListWrapper atomtypeB /NoSetter/ {
+ %GetCode
+ PStringListWrapper *wrapper = new PStringListWrapper(sipCpp->atomname, sipCpp->nr);
+ sipPy = sipConvertFromType(wrapper, sipType_PStringListWrapper, Py_None);
+ %End
+ };
+
+ int nres;
+ t_resinfo *resinfo /NoSetter/ {
+ %GetCode
+ sipPy = sipConvertToTypedArray(sipCpp->resinfo, sipType_t_resinfo, NULL, sizeof(t_resinfo), sipCpp->nres, SIP_READ_ONLY);
+ %End
+ };
+ // FIXME: how many pdbinfo's are there?
+ t_pdbinfo *pdbinfo /NoSetter/ {
+ %GetCode
+ sipPy = sipConvertToTypedArray(sipCpp->pdbinfo, sipType_t_pdbinfo, NULL, sizeof(t_pdbinfo), sipCpp->nres, SIP_READ_ONLY);
+ %End
+ };
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+// This class is needed to transparently map 'atomname' and similar fields of struct t_atoms.
+// Avoids copying and mapping entire array to python.
+
+%ModuleHeaderCode
+class PStringListWrapper {
+public:
+ PStringListWrapper(char ***stringList, size_t size);
+ const char* operator[] (size_t i);
+private:
+ char ***stringList;
+ size_t size;
+};
+%End
+
+%ModuleCode
+PStringListWrapper::PStringListWrapper(char ***stringList, size_t size) :
+ stringList(stringList), size(size)
+ {}
+const char* PStringListWrapper::operator[] (size_t i) {
+ if (i >= size)
+ return NULL;
+ return *stringList[i];
+}
+%End
+
+class PStringListWrapper /NoDefaultCtors/ {
+public:
+ const char* operator[] (int i);
+ %MethodCode
+ sipRes = (*sipCpp)[a0];
+
+ if (!sipRes) {
+ SIP_BLOCK_THREADS;
+ PyErr_SetString(PyExc_IndexError, "Index out of range");
+ SIP_UNBLOCK_THREADS;
+ sipIsErr = 1;
+ }
+ %End
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+struct t_topology
+{
+
+%TypeHeaderCode
+#include <gromacs/topology/topology.h>
+%End
+
+ SIP_PYOBJECT name /NoSetter/ { // Name of the topology
+ %GetCode
+ // name is stored as char**, when the outer pointer is null, let sip wrap it as None
+ sipPy = sipBuildResult(NULL, "A", (sipCpp->name) ? *(sipCpp->name) : NULL);
+ %End
+ };
+ //t_idef idef; [> The interaction function definition <]
+ t_atoms atoms; /* The atoms */
+ //t_atomtypes atomtypes; [> Atomtype properties <]
+ //t_block cgs; [> The charge groups <]
+ //t_block mols; [> The molecules <]
+ //t_blocka excls; [> The exclusions <]
+ //t_symtab symtab; [> The symbol table <]
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%Module gromacs.TrajectoryAnalysis
+
+%DefaultEncoding "UTF-8"
+
+%Import options/Options.sip
+%Import topology/Topology.sip
+
+%Include definitions.sip
+
+%Include analysissettings.sip
+%Include analysisdata.sip
+%Include analysismodule.sip
+
+%Include modules.sip
+
+%ModuleCode
+#include "gromacs/trajectoryanalysis/analysismodule.h"
+#include "gromacs/trajectoryanalysis/cmdlinerunner.h"
+#include "gromacs/utility/exceptions.h"
+
+class PyFactory : public gmx::TrajectoryAnalysisCommandLineRunner::ModuleFactoryFunctor {
+public:
+ PyFactory(PyObject *mod) : mod(mod) {} ;
+ gmx::TrajectoryAnalysisModulePointer operator () () {
+ int iserr = 0;
+ int can = sipCanConvertToType(mod, sipType_TrajectoryAnalysisModule, 0);
+ // TODO: throw if can't
+ gmx::TrajectoryAnalysisModule *module = (gmx::TrajectoryAnalysisModule*) sipConvertToType(
+ mod, sipType_TrajectoryAnalysisModule, NULL, 0, NULL, &iserr);
+ return TrajectoryAnalysisModulePointer(module);
+ }
+private:
+ PyObject *mod;
+};
+
+void runAsMain(PyObject *mod, PyObject *py_argv) {
+ int argc = PyList_GET_SIZE(py_argv);
+
+ char **argv = new char *[argc + 1];
+ bool to_free[argc];
+ std::fill(to_free, to_free+argc, false);
+
+ // Convert the list.
+ // TODO: Use something better than AsLatin1String to avoid unicode errors
+ for (int a = 0; a < argc; ++a)
+ {
+ PyObject *arg_obj = PyList_GET_ITEM(py_argv, a);
+ const char *arg = sipString_AsLatin1String(&arg_obj);
+
+ if (arg)
+ {
+ arg = strdup(arg);
+ Py_DECREF(arg_obj);
+ to_free[a] = true;
+ }
+ else
+ {
+ arg = "unknown";
+ }
+
+ argv[a] = const_cast<char *>(arg);
+ }
+
+ argv[argc] = NULL;
+
+ PyFactory factory(mod);
+ TrajectoryAnalysisCommandLineRunner::runAsMain(argc, argv, &factory);
+
+ for (int i = 0; i < argc; i++)
+ if (to_free[i])
+ free(argv[i]);
+ delete[] argv;
+}
+
+%End
+
+void runAsMain(SIP_PYOBJECT mod, SIP_PYLIST argv);
--- /dev/null
+
+class AbstractAnalysisData /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/analysisdata/abstractdata.h>
+%End
+public:
+ bool isMultipoint() const;
+ int dataSetCount() const;
+ int columnCount(int dataSet) const;
+ int columnCount() const;
+ virtual int frameCount() const = 0;
+ AnalysisDataFrameRef tryGetDataFrame(int index) const;
+ AnalysisDataFrameRef getDataFrame(int index) const;
+ bool requestStorage(int nframes);
+};
+
+class AnalysisDataFrameRef /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/analysisdata/dataframe.h>
+%End
+public:
+ bool isValid() const;
+ //const AnalysidDataFrameHeader& header() const;
+ int frameIndex() const;
+ double x() const;
+ double dx() const;
+ int pointSetCount() const;
+ AnalysisDataPointSetRef pointSet(int index) const;
+ double y(int i) const;
+ double dy(int i) const;
+ bool present(int i) const;
+ bool allPresent() const;
+};
+
+class AnalysisDataFrameHeader /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/analysisdata/dataframe.h>
+%End
+public:
+ bool isValid() const;
+ int index() const;
+ double x() const;
+ double dx() const;
+};
+
+class AnalysisDataPointSetRef /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <gromacs/analysisdata/dataframe.h>
+%End
+public:
+ const AnalysisDataFrameHeader& header() const;
+ int frameIndex() const;
+ double x() const;
+ double dx() const;
+ int dataSetIndex() const;
+ int firstColumn() const;
+ int columnCount() const;
+ int lastColumn() const;
+ //const std::vector<AnalysisDataValue>& values() const;
+ double y(int i) const;
+ double dy(int i) const;
+ bool present(int i) const;
+ bool allPresent() const;
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+%PostInitialisationCode
+ import_array();
+%End
+
+struct t_trxframe {
+
+%TypeHeaderCode
+#include <gromacs/fileio/trx.h>
+#include "numpy_conv.h"
+%End
+
+ int flags;
+ int not_ok;
+ bool bDouble;
+ int natoms;
+ double t0;
+ double tf;
+ double tpf;
+ double tppf;
+ bool bTitle;
+ const char *title;
+ bool bStep;
+ int step;
+ bool bTime;
+ double time;
+ bool bLambda;
+ bool bFepState;
+ double lambda;
+ int fep_state;
+ bool bAtoms;
+ t_atoms *atoms;
+ bool bPrec;
+ double prec;
+ bool bX;
+ SIP_PYOBJECT x /NoSetter/ {
+ %GetCode
+ sipPy = array2dToNumpy(sipCpp->natoms, 3, sipCpp->x);
+ %End
+ };
+ bool bV;
+ SIP_PYOBJECT v /NoSetter/ {
+ %GetCode
+ sipPy = array2dToNumpy(sipCpp->natoms, 3, sipCpp->v);
+ %End
+ };
+ bool bF;
+ SIP_PYOBJECT f /NoSetter/ {
+ %GetCode
+ sipPy = array2dToNumpy(sipCpp->natoms, 3, sipCpp->f);
+ %End
+ };
+ bool bBox;
+ SIP_PYOBJECT box /NoSetter/ {
+ %GetCode
+ sipPy = array2dToNumpy(3, 3, sipCpp->box);
+ %End
+ };
+ bool bPBC;
+ int ePBC;
+ // TODO
+ /*t_gmxvmdplugin* *vmdplugin; */
+};
+
+struct t_pbc {
+
+%TypeHeaderCode
+#include <gromacs/pbcutil/pbc.h>
+#include "numpy_conv.h"
+%End
+ int ePBC;
+ int ndim_ePBC;
+ int ePBCDX;
+ int dim;
+ SIP_PYOBJECT box /NoSetter/ {
+ %GetCode
+ sipPy = array2dToNumpy(3, 3, sipCpp->box);
+ %End
+ };
+ SIP_PYOBJECT fbox_diag /NoSetter/ {
+ %GetCode
+ sipPy = array1dToNumpy(3, sipCpp->fbox_diag);
+ %End
+ };
+ SIP_PYOBJECT hbox_diag /NoSetter/ {
+ %GetCode
+ sipPy = array1dToNumpy(3, sipCpp->hbox_diag);
+ %End
+ };
+ SIP_PYOBJECT mhbox_diag /NoSetter/ {
+ %GetCode
+ sipPy = array1dToNumpy(3, sipCpp->mhbox_diag);
+ %End
+ };
+ double max_cutoff2;
+ bool bLimitDistance;
+ double limit_distance2;
+ int ntric_vec;
+ /*ivec tric_shift[MAX_NTRICVEC];*/
+ /*rvec tric_vec[MAX_NTRICVEC];*/
+};
+
+class TrajectoryAnalysisModuleData /NoDefaultCtors/ {
+
+%TypeHeaderCode
+#include <gromacs/trajectoryanalysis/analysismodule.h>
+using namespace gmx;
+%End
+
+public:
+ virtual void finish() = 0;
+};
+
+%ModuleHeaderCode
+#include "gromacs/utility/exceptions.h"
+%End
+
+%VirtualErrorHandler vehandler
+ SIP_RELEASE_GIL(sipGILState);
+
+ GMX_THROW(gmx::InternalError("Python virtual overload raised an exception, see traceback"));
+%End
+
+%Include vector.sip
+
+class TrajectoryAnalysisModule /VirtualErrorHandler=vehandler/ {
+
+%TypeHeaderCode
+#include <gromacs/trajectoryanalysis/analysismodule.h>
+using namespace gmx;
+%End
+public:
+ virtual void initOptions(Options *options, TrajectoryAnalysisSettings *settings) = 0;
+ virtual void optionsFinished(Options *options, TrajectoryAnalysisSettings *settings);
+ virtual void initAnalysis(const TrajectoryAnalysisSettings &settings, const TopologyInformation &top) = 0;
+ virtual void initAfterFirstFrame(const TrajectoryAnalysisSettings &settings, const t_trxframe &fr);
+// virtual TrajectoryAnalysisModuleDataPointer startFrames (const AnalysisDataParallelOptions &opt, const SelectionCollection &selections);
+ virtual void analyzeFrame(int frnr, const t_trxframe &fr, t_pbc *pbc, TrajectoryAnalysisModuleData *pdata) = 0;
+ virtual void finishFrames(TrajectoryAnalysisModuleData *pdata);
+ virtual void finishAnalysis(int nframes) = 0;
+ virtual void writeOutput() = 0;
+ virtual const std::vector<TrajectoryAnalysisModule*> getBatch();
+ virtual const std::vector<char*> getArgv(int);
+ const char* name() const;
+ const char* description() const;
+ int datasetCount() const;
+// const std::vector<std::string> datasetNames() const;
+ AbstractAnalysisData& datasetFromIndex(int index) const;
+ AbstractAnalysisData& datasetFromName(const char *name) const;
+protected:
+ TrajectoryAnalysisModule(const char *name, const char *description);
+private:
+ TrajectoryAnalysisModule(const TrajectoryAnalysisModule &other);
+};
+
+%Exception gmx::InconsistentInputError(SIP_Exception) {
+
+%TypeHeaderCode
+#include <gromacs/utility/exceptions.h>
+using namespace std;
+%End
+
+%RaiseCode
+ const char *detail = sipExceptionRef.what();
+
+ SIP_BLOCK_THREADS
+ PyErr_SetString(sipException_gmx_InconsistentInputError, detail);
+ SIP_UNBLOCK_THREADS
+%End
+};
--- /dev/null
+/*
+ * This file is part of the GROMACS molecular simulation package.
+ *
+ * Copyright (c) 2014, by the GROMACS development team, led by
+ * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
+ * and including many others, as listed in the AUTHORS file in the
+ * top-level source directory and at http://www.gromacs.org.
+ *
+ * GROMACS is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ *
+ * GROMACS is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GROMACS; if not, see
+ * http://www.gnu.org/licenses, or write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * If you want to redistribute modifications to GROMACS, please
+ * consider that scientific software is very special. Version
+ * control is crucial - bugs must be traceable. We will be happy to
+ * consider code for inclusion in the official distribution, but
+ * derived work must not be called official GROMACS. Details are found
+ * in the README & COPYING files - if they are missing, get the
+ * official version at http://www.gromacs.org.
+ *
+ * To help us fund GROMACS development, we humbly ask that you cite
+ * the research papers on the package. Check out http://www.gromacs.org.
+ */
+
+class TrajectoryAnalysisSettings {
+%TypeHeaderCode
+#include <gromacs/trajectoryanalysis/analysissettings.h>
+using namespace gmx;
+%End
+
+public:
+ enum {
+ efRequireTop = 1,
+ efUseTopX = 2,
+ efNoUserPBC = 16,
+ efNoUserRmPBC = 32
+ };
+
+ TrajectoryAnalysisSettings();
+ /*
+ const TimeUnitManager& timeUnitManager() const;
+ TimeUnit timeUnit();
+ const AnalysisDataPlotSettings& plotSettings() const;
+ */
+ unsigned long flags() const;
+ bool hasFlag(unsigned long flag) const;
+ bool hasPBC() const;
+ bool hasRmPBC() const;
+ int frflags() const;
+ void setFlags(unsigned long flags);
+ void setFlag(unsigned long flag, bool bSet = true);
+ void setPBC(bool bPBC);
+ void setRmPBC(bool bRmPBC);
+ void setFrameFlags(int frflags);
+ void setHelpText(const char *helpText);
+ %MethodCode
+ const char *const helpText[] = {a0};
+ sipCpp->setHelpText(helpText);
+ %End
+private:
+ TrajectoryAnalysisSettings(const TrajectoryAnalysisSettings &other);
+};
+
+class TopologyInformation {
+%TypeHeaderCode
+#include <gromacs/trajectoryanalysis/analysissettings.h>
+using namespace gmx;
+%End
+public:
+ bool hasTopology() const;
+ bool hasFullTopology() const;
+ t_topology* topology() const;
+private:
+ TopologyInformation(const TopologyInformation &other);
+ ~TopologyInformation();
+};
--- /dev/null
+
+template <T> class shared_ptr /NoDefaultCtors/ {
+%TypeHeaderCode
+#include <boost/shared_ptr.hpp>
+using namespace boost;
+%End
+};
+
+typedef shared_ptr<TrajectoryAnalysisModule> TrajectoryAnalysisModulePointer;
+
+template <TYPE>
+%MappedType py_shared_ptr<TYPE> /NoRelease/ {
+%TypeHeaderCode
+#include <boost/shared_ptr.hpp>
+template <typename T> using py_shared_ptr = boost::shared_ptr<T>;
+%End
+
+%ConvertFromTypeCode
+ PyObject *wrp = sipConvertFromType(sipCpp->get(), sipType_TYPE, NULL);
+ PyObject *ptr = sipConvertFromNewType(sipCpp, sipType_TYPEPointer, wrp);
+
+ return wrp;
+%End
+
+%ConvertToTypeCode
+ // Make it impossible to convert into this type
+ if (!sipIsErr)
+ return 0;
+
+ GMX_ASSERT(true, "Converting something into shared_ptr. This should not happen!");
+ return 0;
+%End
+};
+
+class AngleInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/angle.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class DistanceInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/distance.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class FreeVolumeInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/freevolume.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class PairDistanceInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/pairdist.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class RdfInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/rdf.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class SasaInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/sasa.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
+
+class SelectInfo {
+%TypeHeaderCode
+#include "gromacs/trajectoryanalysis/modules/select.h"
+using namespace gmx::analysismodules;
+%End
+private:
+public:
+ static const char* name /NoSetter/;
+ static const char* shortDescription /NoSetter/;
+ static py_shared_ptr<TrajectoryAnalysisModule> create() /Factory/;
+};
--- /dev/null
+// SIP support for std::vector
+// by Giovanni Bajo <rasky <at> develer.com>
+// Public domain
+
+// ****************************************************
+// SIP generic implementation for std::vector<>
+// ****************************************************
+// ALas, this template-based generic implementation is valid only
+// if the element type is a SIP-wrapped type. For basic types (int, double, etc.)
+// we are forced to cut & paste to provide a specialization.
+
+template<TYPE*>
+%MappedType std::vector<TYPE*>
+{
+%TypeHeaderCode
+#include <vector>
+%End
+
+%ConvertFromTypeCode
+ PyObject *l = PyList_New(sipCpp -> size());
+
+ // Create the Python list of the correct length.
+ if (!l)
+ return NULL;
+
+ // Go through each element in the C++ instance and convert it to a
+ // wrapped P2d.
+ for (int i = 0; i < (int)sipCpp->size(); ++i) {
+ TYPE *cpp = sipCpp->at(i);
+ PyObject *pobj = sipConvertFromInstance(cpp, sipClass_TYPE, sipTransferObj);
+
+ // Get the Python wrapper for the Type instance, creating a new
+ // one if necessary, and handle any ownership transfer.
+ if (!pobj) {
+ // There was an error so garbage collect the Python list.
+ Py_DECREF(l);
+ return NULL;
+ }
+
+ // Add the wrapper to the list.
+ PyList_SET_ITEM(l, i, pobj);
+ }
+
+ // Return the Python list.
+ return l;
+%End
+
+%ConvertToTypeCode
+ // Check if type is compatible
+ if (!sipIsErr) {
+ // Must be any iterable
+ PyObject *i = PyObject_GetIter(sipPy);
+ bool iterable = (i != NULL);
+ Py_XDECREF(i);
+ return iterable;
+ }
+
+ // Iterate over the object
+ PyObject *iterator = PyObject_GetIter(sipPy);
+ PyObject *item;
+
+ std::vector<TYPE*> *V = new std::vector<TYPE*>();
+
+ while ((item = PyIter_Next(iterator)))
+ {
+ if (!sipCanConvertToInstance(item, sipClass_TYPE, SIP_NOT_NONE)) {
+ PyErr_Format(PyExc_TypeError, "object in iterable cannot be converted to TYPE");
+ *sipIsErr = 1;
+ break;
+ }
+
+ int state;
+ TYPE* p = reinterpret_cast<TYPE*>(
+ sipConvertToInstance(item, sipClass_TYPE, 0, SIP_NOT_NONE, &state, sipIsErr));
+
+ if (!*sipIsErr)
+ V->push_back(p);
+
+ sipReleaseInstance(p, sipClass_TYPE, state);
+ Py_DECREF(item);
+ }
+
+ Py_DECREF(iterator);
+
+ if (*sipIsErr) {
+ delete V;
+ return 0;
+ }
+
+ *sipCppPtr = V;
+ return sipGetState(sipTransferObj);
+%End
+};
+
+// ****************************************************
+// Specialization for std::vector<char*>
+// ****************************************************
+
+%MappedType std::vector<char*>
+{
+%TypeHeaderCode
+#include <vector>
+%End
+
+%ConvertFromTypeCode
+ PyObject *l;
+
+ // Create the Python list of the correct length.
+ if ((l = PyList_New(sipCpp -> size())) == NULL)
+ return NULL;
+
+ // Go through each element in the C++ instance and convert it to a
+ // wrapped object.
+ for (int i = 0; i < (int)sipCpp -> size(); ++i)
+ {
+ // Add the wrapper to the list.
+ PyList_SET_ITEM(l, i, sipBuildResult(NULL, "A", sipCpp->at(i)));
+ }
+
+ // Return the Python list.
+ return l;
+%End
+
+%ConvertToTypeCode
+ // Check if type is compatible
+ if (sipIsErr == NULL)
+ {
+ // Must be any iterable
+ PyObject *i = PyObject_GetIter(sipPy);
+ bool iterable = (i != NULL);
+ Py_XDECREF(i);
+ return iterable;
+ }
+
+ // Iterate over the object
+ PyObject *iterator = PyObject_GetIter(sipPy);
+ PyObject *item;
+
+ // Maximum number of elements
+ int len = PyObject_Size(sipPy);
+ std::vector<char*> *V = new std::vector<char*>();
+ V->reserve(len);
+
+ if (len)
+ {
+ while ((item = PyIter_Next(iterator)))
+ {
+ if (!PyUnicode_Check(item))
+ {
+ PyErr_Format(PyExc_TypeError, "object in iterable is not a string");
+ *sipIsErr = 1;
+ break;
+ }
+ //FIXME: memory leak here
+ const char* str = strdup(sipString_AsLatin1String(&item));
+
+ V->push_back(const_cast<char*>(str));
+
+ Py_DECREF(item);
+ }
+
+ Py_DECREF(iterator);
+
+ if (*sipIsErr)
+ {
+ delete V;
+ return 0;
+ }
+ }
+
+ *sipCppPtr = V;
+ return sipGetState(sipTransferObj);
+%End
+};
+
+/*
+// ****************************************************
+// Specialization for std::vector<double>
+// ****************************************************
+
+%MappedType std::vector<double>
+{
+%TypeHeaderCode
+#include <vector>
+%End
+
+%ConvertFromTypeCode
+ PyObject *l;
+
+ // Create the Python list of the correct length.
+ if ((l = PyList_New(sipCpp -> size())) == NULL)
+ return NULL;
+
+ // Go through each element in the C++ instance and convert it to a
+ // wrapped object.
+ for (int i = 0; i < (int)sipCpp -> size(); ++i)
+ {
+ // Add the wrapper to the list.
+ PyList_SET_ITEM(l, i, PyFloat_FromDouble(sipCpp -> at(i)));
+ }
+
+ // Return the Python list.
+ return l;
+%End
+
+%ConvertToTypeCode
+ // Check if type is compatible
+ if (sipIsErr == NULL)
+ {
+ // Must be any iterable
+ PyObject *i = PyObject_GetIter(sipPy);
+ bool iterable = (i != NULL);
+ Py_XDECREF(i);
+ return iterable;
+ }
+
+ // Iterate over the object
+ PyObject *iterator = PyObject_GetIter(sipPy);
+ PyObject *item;
+
+ // Maximum number of elements
+ int len = PyObject_Size(sipPy);
+ std::vector<double> *V = new std::vector<double>();
+ V->reserve(len);
+
+ if (len)
+ {
+ while ((item = PyIter_Next(iterator)))
+ {
+ if (!PyNumber_Check(item))
+ {
+ PyErr_Format(PyExc_TypeError, "object in iterable is not a number");
+ *sipIsErr = 1;
+ break;
+ }
+
+ PyObject *f = PyNumber_Float(item);
+ V->push_back(PyFloat_AsDouble(f));
+
+ Py_DECREF(f);
+ Py_DECREF(item);
+ }
+
+ Py_DECREF(iterator);
+
+ if (*sipIsErr)
+ {
+ delete V;
+ return 0;
+ }
+ }
+
+ *sipCppPtr = V;
+ return sipGetState(sipTransferObj);
+%End
+};
+
+// ****************************************************
+// Specialization for std::vector<int>
+// ****************************************************
+
+%MappedType std::vector<int>
+{
+%TypeHeaderCode
+#include <vector>
+%End
+
+%ConvertFromTypeCode
+ PyObject *l;
+
+ // Create the Python list of the correct length.
+ if ((l = PyList_New((SIP_SSIZE_T)sipCpp -> size())) == NULL)
+ return NULL;
+
+ // Go through each element in the C++ instance and convert it to a
+ // wrapped object.
+ for (int i = 0; i < (int)sipCpp -> size(); ++i)
+ {
+ // Add the wrapper to the list.
+ PyList_SET_ITEM(l, i, PyInt_FromLong(sipCpp -> at(i)));
+ }
+
+ // Return the Python list.
+ return l;
+%End
+
+%ConvertToTypeCode
+ // Check if type is compatible
+ if (sipIsErr == NULL)
+ {
+ // Must be any iterable
+ PyObject *i = PyObject_GetIter(sipPy);
+ bool iterable = (i != NULL);
+ Py_XDECREF(i);
+ return iterable;
+ }
+
+ // Iterate over the object
+ PyObject *iterator = PyObject_GetIter(sipPy);
+ PyObject *item;
+
+ // Maximum number of elements
+ int len = PyObject_Size(sipPy);
+ std::vector<int> *V = new std::vector<int>();
+ V->reserve(len);
+
+ if (len)
+ {
+ while ((item = PyIter_Next(iterator)))
+ {
+ if (!PyInt_Check(item))
+ {
+ PyErr_Format(PyExc_TypeError, "object in iterable cannot be converted to float");
+ *sipIsErr = 1;
+ break;
+ }
+
+ int val = PyInt_AsLong(item);
+ V->push_back(val);
+
+ Py_DECREF(item);
+ }
+
+ Py_DECREF(iterator);
+
+ if (*sipIsErr)
+ {
+ delete V;
+ return 0;
+ }
+ }
+
+ *sipCppPtr = V;
+ return sipGetState(sipTransferObj);
+%End
+};
+
+
+// ****************************************************
+// Specialization for std::vector<unsigned int>
+// ****************************************************
+
+%MappedType std::vector<unsigned int>
+{
+%TypeHeaderCode
+#include <vector>
+%End
+
+%ConvertFromTypeCode
+ PyObject *l;
+
+ // Create the Python list of the correct length.
+ if ((l = PyList_New(sipCpp -> size())) == NULL)
+ return NULL;
+
+ // Go through each element in the C++ instance and convert it to a
+ // wrapped object.
+ for (int i = 0; i < (int)sipCpp -> size(); ++i)
+ {
+ // Add the wrapper to the list.
+ PyList_SET_ITEM(l, i, PyInt_FromLong(sipCpp -> at(i)));
+ }
+
+ // Return the Python list.
+ return l;
+%End
+
+%ConvertToTypeCode
+ // Check if type is compatible
+ if (sipIsErr == NULL)
+ {
+ // Must be any iterable
+ PyObject *i = PyObject_GetIter(sipPy);
+ bool iterable = (i != NULL);
+ Py_XDECREF(i);
+ return iterable;
+ }
+
+ // Iterate over the object
+ PyObject *iterator = PyObject_GetIter(sipPy);
+ PyObject *item;
+
+ // Maximum number of elements
+ Py_ssize_t size = PyObject_Size(sipPy);
+ if (size == -1) {
+ Py_DECREF(iterator);
+ return 0;
+ }
+
+ unsigned int len = size;
+ std::vector<unsigned int> *V = new std::vector<unsigned int>();
+ V->reserve(len);
+
+ if (len)
+ {
+ while ((item = PyIter_Next(iterator)))
+ {
+ if (!PyInt_Check(item))
+ {
+ PyErr_Format(PyExc_TypeError, "object in iterable cannot be converted to float");
+ *sipIsErr = 1;
+ break;
+ }
+
+ unsigned int val = PyInt_AsLong(item);
+ V->push_back(val);
+
+ Py_DECREF(item);
+ }
+
+ Py_DECREF(iterator);
+
+ if (*sipIsErr)
+ {
+ delete V;
+ return 0;
+ }
+ }
+
+ *sipCppPtr = V;
+ return sipGetState(sipTransferObj);
+%End
+};*/
--- /dev/null
+import sys
+from gromacs import Options, TrajectoryAnalysis
+
+class M(TrajectoryAnalysis.TrajectoryAnalysisModule):
+ def __init__(self):
+ super(M, self).__init__("a", "a")
+
+ def initOptions(self, options, settings):
+ print('python: initOptions')
+
+ settings.setHelpText('A stupid test module')
+
+ self.optionsHolder = Options.PyOptionsHolder()
+
+ options.addOption(self.optionsHolder.selectionOption('sel').required())
+ options.addOption(self.optionsHolder.fileNameOption('file').defaultBasename('test').description('filename from python to rule them all').outputFile().required().filetype(Options.eftGenericData))
+ settings.setFlag(TrajectoryAnalysis.TrajectoryAnalysisSettings.efRequireTop)
+
+ self.angle = TrajectoryAnalysis.AngleInfo.create()
+
+ print('python: inited')
+
+ def getBatch(self):
+ print('python: getBatch')
+ return [self.angle]
+
+ def getArgv(self, i):
+ print('python: getArgv')
+ if i == 0:
+ #First element of list should be module name -- gets discarded by parser anyway
+ return ["gangle", "-group1", "Backbone", "-oav", "angles.xvg"]
+
+ def initAnalysis(self, settings, top):
+ print('python: initAnalysis')
+ print('There are {} atoms'.format(top.topology().atoms.nr))
+ print('Topology name: {}'.format(top.topology().name))
+
+ #Tell GROMACS to keep last frame in storage, required in analyzeFrame()
+ self.angle.datasetFromIndex(1).requestStorage(1)
+
+ def analyzeFrame(self, frnr, frame, pbc, data):
+ sel = self.optionsHolder['sel']
+
+ dataset = self.angle.datasetFromIndex(1)
+
+ print('frame =', frnr, ', columnCount =', dataset.columnCount(), ', y =', dataset.getDataFrame(frnr).y(0))
+
+ def finishAnalysis(self, nframes):
+ print('python: Analyzed {} frames'.format(nframes))
+
+ def writeOutput(self):
+ print('python: writeOutput')
+ print('file = {}'.format(self.optionsHolder['file']))
+
+ fo = open(self.optionsHolder['file'], 'w')
+ fo.write('Test output\n')
+
+TrajectoryAnalysis.runAsMain(M(), sys.argv)