Commit b53cd947 authored by Mark Friedrichs's avatar Mark Friedrichs
Browse files

Latest mods

parent ff88ddad
#ifndef OPENMM_BROOKKERNELS_H_
#define OPENMM_BROOKKERNELS_H_
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright (c) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman, Mark Friedrichs *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include "kernels.h"
#include "SimTKUtilities/SimTKOpenMMRealType.h"
class BrookStochasticDynamics;
class BrookShakeAlgorithm;
namespace OpenMM {
/**
* This kernel is invoked by StandardMMForceField to calculate the forces acting on the system.
*/
class BrookCalcStandardMMForceFieldKernel : public CalcStandardMMForceFieldKernel {
public:
BrookCalcStandardMMForceFieldKernel(std::string name, const Platform& platform) : CalcStandardMMForceFieldKernel(name, platform) {
}
~BrookCalcStandardMMForceFieldKernel();
/**
* Initialize the kernel, setting up the values of all the force field parameters.
*
* @param bondIndices the two atoms connected by each bond term
* @param bondParameters the force parameters (length, k) for each bond term
* @param angleIndices the three atoms connected by each angle term
* @param angleParameters the force parameters (angle, k) for each angle term
* @param periodicTorsionIndices the four atoms connected by each periodic torsion term
* @param periodicTorsionParameters the force parameters (k, phase, periodicity) for each periodic torsion term
* @param rbTorsionIndices the four atoms connected by each Ryckaert-Bellemans torsion term
* @param rbTorsionParameters the coefficients (in order of increasing powers) for each Ryckaert-Bellemans torsion term
* @param bonded14Indices each element contains the indices of two atoms whose nonbonded interactions should be reduced since
* they form a bonded 1-4 pair
* @param lj14Scale the factor by which van der Waals interactions should be reduced for bonded 1-4 pairs
* @param coulomb14Scale the factor by which Coulomb interactions should be reduced for bonded 1-4 pairs
* @param exclusions the i'th element lists the indices of all atoms with which the i'th atom should not interact through
* nonbonded forces. Bonded 1-4 pairs are also included in this list, since they should be omitted from
* the standard nonbonded calculation.
* @param nonbondedParameters the nonbonded force parameters (charge, sigma, epsilon) for each atom
*/
void initialize(const std::vector<std::vector<int> >& bondIndices, const std::vector<std::vector<double> >& bondParameters,
const std::vector<std::vector<int> >& angleIndices, const std::vector<std::vector<double> >& angleParameters,
const std::vector<std::vector<int> >& periodicTorsionIndices, const std::vector<std::vector<double> >& periodicTorsionParameters,
const std::vector<std::vector<int> >& rbTorsionIndices, const std::vector<std::vector<double> >& rbTorsionParameters,
const std::vector<std::vector<int> >& bonded14Indices, double lj14Scale, double coulomb14Scale,
const std::vector<std::set<int> >& exclusions, const std::vector<std::vector<double> >& nonbondedParameters);
/**
* Execute the kernel to calculate the forces.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @param forces a Stream of type Double3 containing the force (x, y, z) on each atom. On entry, this contains the forces that
* have been calculated so far. The kernel should add its own forces to the values already in the stream.
*/
void executeForces(const Stream& positions, Stream& forces);
/**
* Execute the kernel to calculate the energy.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @return the potential energy due to the StandardMMForceField
*/
double executeEnergy(const Stream& positions);
private:
int numAtoms, numBonds, numAngles, numPeriodicTorsions, numRBTorsions, num14;
int **bondIndexArray, **angleIndexArray, **periodicTorsionIndexArray, **rbTorsionIndexArray, **exclusionArray, **bonded14IndexArray;
RealOpenMM **bondParamArray, **angleParamArray, **periodicTorsionParamArray, **rbTorsionParamArray, **atomParamArray, **bonded14ParamArray;
};
/**
* This kernel is invoked by GBSAOBCForceField to calculate the forces acting on the system.
*/
class BrookCalcGBSAOBCForceFieldKernel : public CalcGBSAOBCForceFieldKernel {
public:
BrookCalcGBSAOBCForceFieldKernel(std::string name, const Platform& platform) : CalcGBSAOBCForceFieldKernel(name, platform) {
}
/**
* Initialize the kernel, setting up the values of all the force field parameters.
*
* @param bornRadii the initial value of the Born radius for each atom
* @param atomParameters the force parameters (charge, atomic radius, scaling factor) for each atom
* @param solventDielectric the dielectric constant of the solvent
* @param soluteDielectric the dielectric constant of the solute
*/
void initialize(const std::vector<double>& bornRadii, const std::vector<std::vector<double> >& atomParameters,
double solventDielectric, double soluteDielectric);
/**
* Execute the kernel to calculate the forces.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @param forces a Stream of type Double3 containing the force (x, y, z) on each atom. On entry, this contains the forces that
* have been calculated so far. The kernel should add its own forces to the values already in the stream.
*/
void executeForces(const Stream& positions, Stream& forces);
/**
* Execute the kernel to calculate the energy.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @return the potential energy due to the GBSAOBCForceField
*/
double executeEnergy(const Stream& positions);
};
/**
* This kernel is invoked by VerletIntegrator to take one time step.
*/
class BrookIntegrateVerletStepKernel : public IntegrateVerletStepKernel {
public:
BrookIntegrateVerletStepKernel(std::string name, const Platform& platform) : IntegrateVerletStepKernel(name, platform) {
}
/**
* Initialize the kernel, setting up all parameters related to integrator.
*
* @param masses the mass of each atom
* @param constraintIndices each element contains the indices of two atoms whose distance should be constrained
* @param constraintLengths the required distance between each pair of constrained atoms
*/
void initialize(const std::vector<double>& masses, const std::vector<std::vector<int> >& constraintIndices,
const std::vector<double>& constraintLengths);
/**
* Execute the kernel.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @param velocities a Stream of type Double3 containing the velocity (x, y, z) of each atom
* @param forces a Stream of type Double3 containing the force (x, y, z) on each atom
* @param stepSize the integration step size
*/
void execute(Stream& positions, Stream& velocities, const Stream& forces, double stepSize);
};
/**
* This kernel is invoked by LangevinIntegrator to take one time step.
*/
class BrookIntegrateLangevinStepKernel : public IntegrateLangevinStepKernel {
public:
BrookIntegrateLangevinStepKernel(std::string name, const Platform& platform) : IntegrateLangevinStepKernel(name, platform),
dynamics(0), shake(0), masses(0), shakeParameters(0), constraintIndices(0) {
}
~BrookIntegrateLangevinStepKernel();
/**
* Initialize the kernel, setting up all parameters related to integrator.
*
* @param masses the mass of each atom
* @param constraintIndices each element contains the indices of two atoms whose distance should be constrained
* @param constraintLengths the required distance between each pair of constrained atoms
*/
void initialize(const std::vector<double>& masses, const std::vector<std::vector<int> >& constraintIndices,
const std::vector<double>& constraintLengths);
/**
* Execute the kernel.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @param velocities a Stream of type Double3 containing the velocity (x, y, z) of each atom
* @param forces a Stream of type Double3 containing the force (x, y, z) on each atom
* @param temperature the temperature of the heat bath
* @param friction the friction coefficient coupling the system to the heat bath
* @param stepSize the integration step size
*/
void execute(Stream& positions, Stream& velocities, const Stream& forces, double temperature, double friction, double stepSize);
private:
BrookStochasticDynamics* dynamics;
BrookShakeAlgorithm* shake;
RealOpenMM* masses;
RealOpenMM** shakeParameters;
int** constraintIndices;
int numConstraints;
double prevTemp, prevFriction, prevStepSize;
};
/**
* This kernel is invoked by BrownianIntegrator to take one time step.
*/
class BrookIntegrateBrownianStepKernel : public IntegrateBrownianStepKernel {
public:
BrookIntegrateBrownianStepKernel(std::string name, const Platform& platform) : IntegrateBrownianStepKernel(name, platform) {
}
/**
* Initialize the kernel, setting up all parameters related to integrator.
*
* @param masses the mass of each atom
* @param constraintIndices each element contains the indices of two atoms whose distance should be constrained
* @param constraintLengths the required distance between each pair of constrained atoms
*/
void initialize(const std::vector<double>& masses, const std::vector<std::vector<int> >& constraintIndices,
const std::vector<double>& constraintLengths);
/**
* Execute the kernel.
*
* @param positions a Stream of type Double3 containing the position (x, y, z) of each atom
* @param velocities a Stream of type Double3 containing the velocity (x, y, z) of each atom
* @param forces a Stream of type Double3 containing the force (x, y, z) on each atom
* @param temperature the temperature of the heat bath
* @param friction the friction coefficient coupling the system to the heat bath
* @param stepSize the integration step size
*/
void execute(Stream& positions, Stream& velocities, const Stream& forces, double temperature, double friction, double stepSize);
};
/**
* This kernel is invoked by AndersenThermostat at the start of each time step to adjust the atom velocities.
*/
class BrookApplyAndersenThermostatKernel : public ApplyAndersenThermostatKernel {
public:
BrookApplyAndersenThermostatKernel(std::string name, const Platform& platform) : ApplyAndersenThermostatKernel(name, platform) {
}
/**
* Initialize the kernel, setting up the values of unchanging parameters.
*
* @param masses the mass of each atom
*/
void initialize(const std::vector<double>& masses);
/**
* Execute the kernel.
*
* @param velocities a Stream of type Double3 containing the velocity (x, y, z) of each atom
* @param temperature the temperature of the heat bath
* @param collisionFrequency the frequency at which atom collide with particles in the heat bath
* @param stepSize the integration step size
*/
void execute(Stream& velocities, double temperature, double collisionFrequency, double stepSize);
};
/**
* This kernel is invoked to calculate the kinetic energy of the system.
*/
class BrookCalcKineticEnergyKernel : public CalcKineticEnergyKernel {
public:
BrookCalcKineticEnergyKernel(std::string name, const Platform& platform) : CalcKineticEnergyKernel(name, platform) {
}
/**
* Initialize the kernel, setting up the atomic masses.
*
* @param masses the mass of each atom
*/
void initialize(const std::vector<double>& masses);
/**
* Execute the kernel.
*
* @param velocities a Stream of type Double3 containing the velocity (x, y, z) of each atom
* @return the kinetic energy of the system
*/
double execute(const Stream& velocities);
private:
std::vector<double> masses;
};
} // namespace OpenMM
#endif /*OPENMM_BROOKKERNELS_H_*/
......@@ -29,7 +29,6 @@
* USE OR OTHER DEALINGS IN THE SOFTWARE. *
* -------------------------------------------------------------------------- */
#include <math.h>
#include <sstream>
#include "BrookNonBonded.h"
#include "BrookPlatform.h"
......@@ -56,26 +55,26 @@ BrookNonBonded::BrookNonBonded( ){
// ---------------------------------------------------------------------------------------
_atomSizeCeiling = -1;
_outerUnroll = 4;
_innerUnroll = 4;
_outerUnroll = 4;
_innerUnroll = 4;
_partialForceStreamWidth = 64;
_partialForceStreamHeight = -1;
_partialForceStreamSize = -1;
_duplicationFactor = 4;
_duplicationFactor = 4;
_exclusionStreamWidth = -1;
_exclusionStreamHeight = -1;
_exclusionStreamSize = -1;
_jStreamWidth = -1;
_jStreamWidth = 16;
_jStreamHeight = -1;
_jStreamSize = -1;
_exclusionStream = NULL;
_sigmaStream = NULL;
_epsilonStream = NULL;
for( int ii = 0; ii < LastStreamIndex; ii++ ){
_nonbondedStreams[ii] = NULL;
}
for( int ii = 0; ii < getNumberOfForceStreams(); ii++ ){
_nonbondedForceStreams[ii] = NULL;
......@@ -97,9 +96,9 @@ BrookNonBonded::~BrookNonBonded( ){
// ---------------------------------------------------------------------------------------
delete _exclusionStream;
delete _sigmaStream;
delete _epsilonStream;
for( int ii = 0; ii < LastStreamIndex; ii++ ){
delete _nonbondedStreams[ii];
}
for( int ii = 0; ii < getNumberOfForceStreams(); ii++ ){
delete _nonbondedForceStreams[ii];
......@@ -166,6 +165,12 @@ int BrookNonBonded::setOuterLoopUnroll( int outerUnroll ){
int BrookNonBonded::getAtomSizeCeiling( void ) const {
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookNonBonded::getAtomSizeCeiling";
// ---------------------------------------------------------------------------------------
if( _atomSizeCeiling < 0 ){
BrookNonBonded* localThis = const_cast<BrookNonBonded* const>(this);
localThis->_atomSizeCeiling = localThis->getNumberOfAtoms() % localThis->getOuterLoopUnroll();
......@@ -188,32 +193,6 @@ int BrookNonBonded::getDuplicationFactor( void ) const {
return _duplicationFactor;
}
/**
* Get j-stream width
*
* @param platform platform
*
* @return j-stream width
*
*/
int BrookNonBonded::getJStreamWidth( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getJStreamWidth";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
// get j-stream width
if( _jStreamWidth < 0 ){
//_getJStreamDimensions( platform );
}
return _jStreamWidth;
}
/**
* Get j-stream width
*
......@@ -226,39 +205,12 @@ int BrookNonBonded::getJStreamWidth( void ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getJStreamWidth";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
return _jStreamWidth;
}
/**
* Get j-stream height
*
* @param platform platform
*
* @return j-stream height
*
*/
int BrookNonBonded::getJStreamHeight( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getJStreamHeight";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
// get j-stream height
if( _jStreamHeight < 0 ){
//_getJStreamDimensions( platform );
}
return _jStreamHeight;
}
/**
* Get j-stream height
*
......@@ -271,39 +223,12 @@ int BrookNonBonded::getJStreamHeight( void ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getJStreamHeight";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
return _jStreamHeight;
}
/**
* Get j-stream size
*
* @param platform platform
*
* @return j-stream size
*
*/
int BrookNonBonded::getJStreamSize( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getJStreamSize";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
// get j-stream size
if( _jStreamSize < 0 ){
//_getJStreamDimensions( platform );
}
return _jStreamSize;
}
/**
* Get j-stream size
*
......@@ -329,7 +254,6 @@ int BrookNonBonded::getPartialForceStreamWidth( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getPartialForceStreamWidth";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
......@@ -374,7 +298,6 @@ int BrookNonBonded::getPartialForceStreamHeight( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getPartialForceStreamHeight";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
......@@ -398,7 +321,6 @@ int BrookNonBonded::getPartialForceStreamHeight( void ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getPartialForceStreamHeight";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
......@@ -419,7 +341,6 @@ int BrookNonBonded::getPartialForceStreamSize( const Platform& platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookNonBonded::getPartialForceStreamSize";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
......@@ -471,8 +392,8 @@ int BrookNonBonded::getExclusionStreamWidth( void ) const {
*
*/
BrookFloatStreamImpl* BrookNonBonded::getExclusionStream( void ) const {
return _exclusionStream;
BrookFloatStreamInternal* BrookNonBonded::getExclusionStream( void ) const {
return _nonbondedStreams[ExclusionStream];
}
/**
......@@ -482,8 +403,8 @@ BrookFloatStreamImpl* BrookNonBonded::getExclusionStream( void ) const {
*
*/
BrookFloatStreamImpl* BrookNonBonded::getVdwStream( void ) const {
return _vdwStream;
BrookFloatStreamInternal* BrookNonBonded::getOuterVdwStream( void ) const {
return _nonbondedStreams[OuterVdwStream];
}
/**
......@@ -493,8 +414,8 @@ BrookFloatStreamImpl* BrookNonBonded::getVdwStream( void ) const {
*
*/
BrookFloatStreamImpl* BrookNonBonded::getChargeStream( void ) const {
return _chargeStream;
BrookFloatStreamInternal* BrookNonBonded::getChargeStream( void ) const {
return _nonbondedStreams[ChargeStream];
}
/**
......@@ -504,8 +425,8 @@ BrookFloatStreamImpl* BrookNonBonded::getChargeStream( void ) const {
*
*/
BrookFloatStreamImpl* BrookNonBonded::getSigmaStream( void ) const {
return _sigmaStream;
BrookFloatStreamInternal* BrookNonBonded::getInnerSigmaStream( void ) const {
return _nonbondedStreams[InnerSigmaStream];
}
/**
......@@ -515,8 +436,8 @@ BrookFloatStreamImpl* BrookNonBonded::getSigmaStream( void ) const {
*
*/
BrookFloatStreamImpl* BrookNonBonded::getEpsilonStream( void ) const {
return _epsilonStream;
BrookFloatStreamInternal* BrookNonBonded::getInnerEpsilonStream( void ) const {
return _nonbondedStreams[InnerEpsilonStream];
}
/**
......@@ -526,7 +447,7 @@ BrookFloatStreamImpl* BrookNonBonded::getEpsilonStream( void ) const {
*
*/
BrookFloatStreamImpl** BrookNonBonded::getForceStreams( void ){
BrookFloatStreamInternal** BrookNonBonded::getForceStreams( void ){
return _nonbondedForceStreams;
}
......@@ -543,7 +464,7 @@ int BrookNonBonded::isForceStreamSet( int index ) const {
}
/**
* Initialize stream dimensions and streams
* Initialize stream dimensions
*
* @param numberOfAtoms number of atoms
* @param platform platform
......@@ -552,49 +473,79 @@ int BrookNonBonded::isForceStreamSet( int index ) const {
*
*/
int BrookNonBonded::initializeStreams( int numberOfAtoms, const Platform& platform ){
int BrookNonBonded::initializeStreamSizes( int numberOfAtoms, const Platform& platform ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializeStreamSizes";
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
int atomStreamSize = getAtomStreamSize( platform );
int atomStreamWidth = getAtomStreamWidth( platform );
initializeExclusionStreamSize( atomStreamSize, atomStreamWidth );
initializeJStreamSize( atomStreamSize, atomStreamWidth );
initializeOuterVdwStreamSize( atomStreamSize, atomStreamWidth );
initializePartialForceStreamSize( atomStreamSize, atomStreamWidth );
return DefaultReturnValue;
}
/**
* Initialize streams
*
* @param platform platform
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
*/
int BrookNonBonded::initializeStreams( const Platform& platform ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializeStreams";
static const double dangleValue = 0.0;
// static const int debug = 1;
// ---------------------------------------------------------------------------------------
int atomStreamSize = getAtomStreamSize( platform );
_exclusionStreamWidth = atomStreamSize;
const BrookStreamFactory& brookStreamFactory = dynamic_cast<const BrookStreamFactory&> (platform.getDefaultStreamFactory());
int innerUnroll = getInnerLoopUnroll();
if( innerUnroll < 1 ){
std::stringstream message;
message << methodName << " innerUnrolls=" << innerUnroll << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
// exclusion
const BrookPlatform brookPlatform = dynamic_cast<const BrookPlatform&> (platform);
const BrookStreamFactory& brookStreamFactory = dynamic_cast<const BrookStreamFactory&> (platform.getDefaultStreamFactory() );
_nonbondedStreams[ExclusionStream] = new BrookFloatStreamInternal( BrookStreamFactory::NonBondedExclusionStream,
getExclusionStreamSize(), getExclusionStreamWidth(),
BrookStreamInternal::Float, dangleValue );
_exclusionStreamHeight = _exclusionStreamWidth/innerUnroll;
_exclusionStreamSize = _exclusionStreamWidth*_exclusionStreamHeight;
StreamImpl* exStream = brookStreamFactory.createStreamImpl( BrookStreamFactory::NonBondedExclusionStream, _exclusionStreamSize, Stream::Float, platform );
_exclusionStream = dynamic_cast<BrookFloatStreamImpl*> ( exStream );
// outer vdw
_nonbondedStreams[OuterVdwStream] = new BrookFloatStreamInternal( BrookStreamFactory::OuterVdwStream, getAtomStreamSize(),
getAtomStreamWidth(), BrookStreamInternal::Float2, dangleValue );
StreamImpl* vStream = brookStreamFactory.createStreamImpl( BrookStreamFactory::NonBondedVdwStream, atomStreamSize, Stream::Float3, platform );
_vdwStream = dynamic_cast<BrookFloatStreamImpl*> ( vStream );
// inner sigma & epsilon
StreamImpl* cStream = brookStreamFactory.createStreamImpl( BrookStreamFactory::NonBondedVdwStream, atomStreamSize, Stream::Float3, platform );
_chargeStream = dynamic_cast<BrookFloatStreamImpl*> ( cStream );
_nonbondedStreams[InnerSigmaStream] = new BrookFloatStreamInternal( BrookStreamFactory::InnerSigmaStream, getJStreamSize(),
getJStreamWidth(), BrookStreamInternal::Float4, dangleValue );
if( getLog() ){
int atomStreamWidth = getAtomStreamWidth( platform );
int atomStreamHeight = getAtomStreamHeight( platform );
(void) fprintf( getLog(), "%s initializeVdwStream: stream dimensions: [%d %d] size=%d\n", methodName.c_str(), atomStreamWidth, atomStreamHeight, atomStreamSize );
}
_nonbondedStreams[InnerEpsilonStream] = new BrookFloatStreamInternal( BrookStreamFactory::InnerEpsilonStream, getJStreamSize(),
getJStreamWidth(), BrookStreamInternal::Float4, dangleValue );
// charge stream
if( getLog() ){
(void) fprintf( getLog(), "%s initializeExclusionStream: stream dimensions: [%d %d] size=%d\n", methodName.c_str(), _exclusionStreamWidth, _exclusionStreamHeight, _exclusionStreamSize );
_nonbondedStreams[ChargeStream] = new BrookFloatStreamInternal( BrookStreamFactory::NonBondedChargeStream, getAtomStreamSize(),
getAtomStreamWidth(), BrookStreamInternal::Float, dangleValue );
// partial force stream
std::string partialForceStream = BrookStreamFactory::PartialForceStream;
for( int ii = 0; ii < getNumberOfForceStreams(); ii++ ){
std::stringstream name;
name << partialForceStream << ii;
_nonbondedForceStreams[ii] = new BrookFloatStreamInternal( name.str(), getPartialForceStreamSize(),
getPartialForceStreamWidth(), BrookStreamInternal::Float4, dangleValue );
}
return DefaultReturnValue;
......@@ -621,7 +572,7 @@ int BrookNonBonded::setExclusion( int i, int j, int exclusionStreamWidth, BrookO
// ---------------------------------------------------------------------------------------
int index = ( (j/4)* exclusionStreamWidth + i ); //iindex is the x coordinate!
int index = ( (j/4)* exclusionStreamWidth + i ); // index is the x coordinate!
int joffset = j % 4;
BrookOpenMMFloat flag;
......@@ -718,7 +669,7 @@ int BrookNonBonded::initializeExclusions( const std::vector<std::set<int> >& exc
// load stream
_exclusionStream->loadFromArray( exclusions );
_nonbondedStreams[ExclusionStream]->loadFromArray( exclusions );
delete[] exclusions;
return DefaultReturnValue;
......@@ -797,7 +748,8 @@ int BrookNonBonded::initializeVdwAndCharge( const vector<vector<double> >& nonbo
int trackingIndex = 0;
for( unsigned int ii = 0; ii < nonbondedParameters.size(); ii++ ){
vector<double> nonbondedParameterVector = nonbondedParameters[ii];
vector<double> nonbondedParameterVector
= nonbondedParameters[ii];
double c6 = nonbondedParameterVector[0];
double c12 = nonbondedParameterVector[1];
......@@ -822,8 +774,8 @@ int BrookNonBonded::initializeVdwAndCharge( const vector<vector<double> >& nonbo
// load stream
_vdwStream->loadFromArray( vdwParameters );
_chargeStream->loadFromArray( charges );
_nonbondedStreams[OuterVdwStream]->loadFromArray( vdwParameters );
_nonbondedStreams[ChargeStream]->loadFromArray( charges );
delete[] vdwParameters;
delete[] charges;
......@@ -845,7 +797,7 @@ int BrookNonBonded::initializeVdwAndCharge( const vector<vector<double> >& nonbo
* */
int BrookNonBonded::setup( int numberOfAtoms, const std::vector<std::vector<double> >& nonbondedParameters,
const std::vector<std::set<int> >& exclusions, const BrookPlatform& platform ){
const std::vector<std::set<int> >& exclusions, const Platform& platform ){
// ---------------------------------------------------------------------------------------
......@@ -856,7 +808,8 @@ int BrookNonBonded::setup( int numberOfAtoms, const std::vector<std::vector<doub
setNumberOfAtoms( numberOfAtoms );
initializeStreams( numberOfAtoms, platform );
initializeStreamSizes( numberOfAtoms, platform );
initializeStreams( platform );
initializeExclusions( exclusions, platform );
initializeVdwAndCharge( nonbondedParameters, platform );
......@@ -866,6 +819,180 @@ int BrookNonBonded::setup( int numberOfAtoms, const std::vector<std::vector<doub
}
/*
* Setup of stream dimensions for exclusion stream
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* */
int BrookNonBonded::initializeExclusionStreamSize( int atomStreamSize, int atomStreamWidth ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializeExclusionStreamSize";
//static const int debug = 1;
// ---------------------------------------------------------------------------------------
_exclusionStreamWidth = atomStreamSize;
int innerUnroll = getInnerLoopUnroll();
if( innerUnroll < 1 ){
std::stringstream message;
message << methodName << " innerUnrolls=" << innerUnroll << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
_exclusionStreamHeight = _exclusionStreamWidth/innerUnroll;
_exclusionStreamSize = _exclusionStreamWidth*_exclusionStreamHeight;
return DefaultReturnValue;
}
/*
* Setup of j-stream dimensions
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* @throw OpenMMException if jStreamWidth < 1 || innerUnroll < 1
*
* */
int BrookNonBonded::initializeJStreamSize( int atomStreamSize, int atomStreamWidth ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializeJStreamSize";
// ---------------------------------------------------------------------------------------
// validate stream width & inner unroll
int jStreamWidth = getJStreamWidth();
if( jStreamWidth < 1 ){
std::stringstream message;
message << methodName << " jStreamWidth=" << jStreamWidth << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
int innerUnroll = getInnerLoopUnroll();
if( innerUnroll < 1 ){
std::stringstream message;
message << methodName << " innerUnroll=" << innerUnroll << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
// set dimesnions
_jStreamSize = atomStreamSize/innerUnroll;
_jStreamHeight = _jStreamSize/jStreamWidth;
_jStreamHeight += ( (_jStreamSize % _jStreamWidth) ? 1 : 0 );
_jStreamSize = jStreamWidth*_jStreamHeight;
return DefaultReturnValue;
}
/*
* Setup of outer vdw stream size
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* @throw OpenMMException if jStreamWidth < 1 || innerUnroll < 1
*
* */
int BrookNonBonded::initializeOuterVdwStreamSize( int atomStreamSize, int atomStreamWidth ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializeOuterVdwStreamSize";
// ---------------------------------------------------------------------------------------
// validate stream width & inner unroll
/*
int jStreamWidth = getJStreamWidth();
if( jStreamWidth < 1 ){
std::stringstream message;
message << methodName << " jStreamWidth=" << jStreamWidth << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
int innerUnroll = getInnerLoopUnroll();
if( innerUnroll < 1 ){
std::stringstream message;
message << methodName << " innerUnroll=" << innerUnroll << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
// set dimesnions
_jStreamSize = atomStreamSize/innerUnroll;
_jStreamHeight = _jStreamSize/jStreamWidth;
_jStreamHeight += ( (_jStreamSize % _jStreamWidth) ? 1 : 0 );
_jStreamSize = jStreamWidth*_jStreamHeight;
*/
return DefaultReturnValue;
}
/*
* Setup of stream dimensions for partial force streams
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* */
int BrookNonBonded::initializePartialForceStreamSize( int atomStreamSize, int atomStreamWidth ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::initializePartialForceStreamSize";
//static const int debug = 1;
// ---------------------------------------------------------------------------------------
int innerUnroll = getInnerLoopUnroll();
if( innerUnroll < 1 ){
std::stringstream message;
message << methodName << " innerUnrolls=" << innerUnroll << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
if( _partialForceStreamWidth < 1 ){
std::stringstream message;
message << methodName << " partial force stream width=" << _partialForceStreamWidth << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
_partialForceStreamSize = atomStreamSize*getDuplicationFactor()/innerUnroll;
_partialForceStreamHeight = _partialForceStreamSize/_partialForceStreamWidth;
_partialForceStreamHeight += ( (_partialForceStreamSize % _partialForceStreamWidth) ? 1 : 0);
return DefaultReturnValue;
}
/*
* Setup of j-stream dimensions
*
* Get contents of object
*
*
......@@ -875,11 +1002,11 @@ int BrookNonBonded::setup( int numberOfAtoms, const std::vector<std::vector<doub
*
* */
std::string BrookNonBonded::getContents( int level ) const {
std::string BrookNonBonded::getContentsString( int level ) const {
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookNonBonded::getContents";
static const std::string methodName = "BrookNonBonded::getContentsString";
static const unsigned int MAX_LINE_CHARS = 256;
char value[MAX_LINE_CHARS];
......@@ -951,19 +1078,35 @@ std::string BrookNonBonded::getContents( int level ) const {
(void) LOCAL_SPRINTF( value, "%d", getExclusionStreamSize() );
message << _getLine( tab, "Exclusion stream size:", value );
message << _getLine( tab, "Log:", (getLog() ? Set : NotSet) );
message << _getLine( tab, "ExclusionStream:", (getExclusionStream() ? Set : NotSet) );
message << _getLine( tab, "VdwStream:", (getVdwStream() ? Set : NotSet) );
message << _getLine( tab, "ChargeStream:", (getChargeStream() ? Set : NotSet) );
message << _getLine( tab, "SigmaStream:", (getSigmaStream() ? Set : NotSet) );
message << _getLine( tab, "EpsilonStream:", (getEpsilonStream() ? Set : NotSet) );
message << _getLine( tab, "Log:", (getLog() ? Set : NotSet) );
message << _getLine( tab, "ExclusionStream:", (getExclusionStream() ? Set : NotSet) );
message << _getLine( tab, "VdwStream:", (getOuterVdwStream() ? Set : NotSet) );
message << _getLine( tab, "ChargeStream:", (getChargeStream() ? Set : NotSet) );
message << _getLine( tab, "SigmaStream:", (getInnerSigmaStream() ? Set : NotSet) );
message << _getLine( tab, "EpsilonStream:", (getInnerEpsilonStream() ? Set : NotSet) );
for( int ii = 0; ii < LastStreamIndex; ii++ ){
message << std::endl;
if( _nonbondedStreams[ii] ){
message << _nonbondedStreams[ii]->getContentsString( );
}
}
// force streams
for( int ii = 0; ii < getNumberOfForceStreams(); ii++ ){
char description[256];
(void) LOCAL_SPRINTF( description, "PartialForceStream %d", ii );
message << _getLine( tab, description, (isForceStreamSet(ii) ? Set : NotSet) );
}
for( int ii = 0; ii < getNumberOfForceStreams(); ii++ ){
message << std::endl;
if( _nonbondedForceStreams[ii] ){
message << _nonbondedForceStreams[ii]->getContentsString( );
}
}
#undef LOCAL_SPRINTF
return message.str();
......
#ifndef BrookNonBonded_H_
#define BrookNonBonded_H_
#ifndef OPENMM_BROOK_NONBONDED_H_
#define OPENMM_BROOK_NONBONDED_H_
/* -------------------------------------------------------------------------- *
* OpenMM *
......@@ -35,8 +35,8 @@
#include <vector>
#include <set>
#include "BrookFloatStreamImpl.h"
#include "BrookIntStreamImpl.h"
#include "BrookFloatStreamInternal.h"
#include "BrookIntStreamInternal.h"
#include "BrookPlatform.h"
#include "BrookCommon.h"
......@@ -54,7 +54,7 @@ class BrookNonBonded : public BrookCommon {
static const int DefaultReturnValue = 0;
static const int ErrorReturnValue = -1;
BrookNonBonded( );
BrookNonBonded( );
~BrookNonBonded();
......@@ -250,7 +250,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl* getExclusionStream( void ) const;
BrookFloatStreamInternal* getExclusionStream( void ) const;
/**
* Get vdw stream
......@@ -259,7 +259,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl* getVdwStream( void ) const;
BrookFloatStreamInternal* getOuterVdwStream( void ) const;
/**
* Get charge stream
......@@ -268,7 +268,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl* getChargeStream( void ) const;
BrookFloatStreamInternal* getChargeStream( void ) const;
/**
* Get sigma-eps stream
......@@ -277,7 +277,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl* getSigmaStream( void ) const;
BrookFloatStreamInternal* getInnerSigmaStream( void ) const;
/**
* Get epsilon stream
......@@ -286,7 +286,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl* getEpsilonStream( void ) const;
BrookFloatStreamInternal* getInnerEpsilonStream( void ) const;
/**
* Get force streams
......@@ -295,7 +295,7 @@ class BrookNonBonded : public BrookCommon {
*
*/
BrookFloatStreamImpl** getForceStreams( void );
BrookFloatStreamInternal** getForceStreams( void );
/**
* Return true if force[index] stream is set
......@@ -320,7 +320,7 @@ class BrookNonBonded : public BrookCommon {
* */
int setup( int numberOfAtoms, const std::vector<std::vector<double> >& nonbondedParameters,
const std::vector<std::set<int> >& exclusions, const BrookPlatform& platform );
const std::vector<std::set<int> >& exclusions, const Platform& platform );
/*
* Get contents of object
......@@ -331,7 +331,7 @@ class BrookNonBonded : public BrookCommon {
*
* */
std::string getContents( int level ) const;
std::string getContentsString( int level = 0 ) const;
private:
......@@ -339,6 +339,17 @@ class BrookNonBonded : public BrookCommon {
static const int NumberOfForceStreams = 4;
// streams indices
enum {
ExclusionStream,
OuterVdwStream,
ChargeStream,
InnerSigmaStream,
InnerEpsilonStream,
LastStreamIndex
};
// atom ceiling
int _atomSizeCeiling;
......@@ -370,15 +381,23 @@ class BrookNonBonded : public BrookCommon {
int _jStreamHeight;
int _jStreamSize;
// streams
// internal streams
BrookFloatStreamImpl* _exclusionStream;
BrookFloatStreamImpl* _vdwStream;
BrookFloatStreamImpl* _chargeStream;
BrookFloatStreamImpl* _sigmaStream;
BrookFloatStreamImpl* _epsilonStream;
BrookFloatStreamImpl* _nonbondedForceStreams[NumberOfForceStreams];
BrookFloatStreamInternal* _nonbondedStreams[LastStreamIndex];
BrookFloatStreamInternal* _nonbondedForceStreams[NumberOfForceStreams];
/*
* Setup of stream dimensions for exclusion stream
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* */
int initializeExclusionStreamSize( int atomStreamSize, int atomStreamWidth );
/**
* Initialize exclusion stream dimensions and stream
*
......@@ -416,6 +435,18 @@ class BrookNonBonded : public BrookCommon {
int initializeExclusions( const std::vector<std::set<int> >& exclusionsVector, const Platform& platform );
/**
* Initialize stream dimensions
*
* @param numberOfAtoms number of atoms
* @param platform platform
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
*/
int initializeStreamSizes( int numberOfAtoms, const Platform& platform );
/**
* Initialize stream dimensions and streams
*
......@@ -425,8 +456,36 @@ class BrookNonBonded : public BrookCommon {
*
*/
int initializeStreams( int numberOfAtoms, const Platform& platform );
int initializeStreams( const Platform& platform );
/*
* Setup of j-stream dimensions
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* @throw OpenMMException if jStreamWidth < 1 || innerUnroll < 1
*
* */
int initializeJStreamSize( int atomStreamSize, int atomStreamWidth );
/*
* Setup of outer vdw stream size
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* @throw OpenMMException if jStreamWidth < 1 || innerUnroll < 1
*
* */
int initializeOuterVdwStreamSize( int atomStreamSize, int atomStreamWidth );
/**
* Set sigma & epsilon given c6 & c12 (geometric rule)
*
......@@ -453,8 +512,20 @@ class BrookNonBonded : public BrookCommon {
int initializeVdwAndCharge( const std::vector<std::vector<double> >& nonbondedParameters, const Platform& platform );
/*
* Setup of stream dimensions for partial force streams
*
* @param atomStreamSize atom stream size
* @param atomStreamWidth atom stream width
*
* @return ErrorReturnValue if error, else DefaultReturnValue
*
* */
int initializePartialForceStreamSize( int atomStreamSize, int atomStreamWidth );
};
} // namespace OpenMM
#endif /*OPENMM_BROOKKERNELS_H_*/
#endif /* OPENMM_BROOK_NONBONDED_H_ */
......@@ -31,56 +31,232 @@
#include "BrookPlatform.h"
#include "BrookKernelFactory.h"
//#include "BrookKernels.h"
#include "OpenMMException.h"
#include "kernels.h"
#include "SimTKUtilities/SimTKOpenMMRealType.h"
#include <brook/brook.hpp>
#include <stdlib.h>
#include <sstream>
#include <cctype>
#include <algorithm>
using namespace OpenMM;
/**
* Register BrookPlatform
*
* @return BrookPlatform instance
*
*/
BrookPlatform* registerBrookPlatform( void ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::registerBrookPlatform";
// ---------------------------------------------------------------------------------------
BrookPlatform* platform = new BrookPlatform();
Platform::registerPlatform(platform);
return platform;
}
BrookPlatform* staticPlatform = registerBrookPlatform( );
/**
* BrookPlatform constructor
*
*/
BrookPlatform::BrookPlatform( ){
_defaultAtomStreamWidth = DefaultAtomStreamWidth;
_initializeFactory();
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::BrookPlatform(0)";
// ---------------------------------------------------------------------------------------
_atomStreamWidth = DefaultAtomStreamWidth;
_log = NULL;
// get Brook runtime
char* runtime = getenv( "brt_runtime" );
_initializeKernelFactory( );
_setBrookRuntime( runtime );
}
BrookPlatform::BrookPlatform( int defaultAtomStreamWidth ){
_defaultAtomStreamWidth = defaultAtomStreamWidth;
_initializeFactory();
/**
* BrookPlatform constructor
*
* @param defaultAtomStreamWidth stream width
* @param runtime Brook runtime (cal/cpu)
* @param log log file reference
*
*/
BrookPlatform::BrookPlatform( int atomStreamWidth, const std::string& runtime, FILE* log ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::BrookPlatform(2)";
// ---------------------------------------------------------------------------------------
_log = log;
_atomStreamWidth = atomStreamWidth;
_initializeKernelFactory( );
_setBrookRuntime( runtime );
}
/**
* BrookPlatform destructor
*
*/
BrookPlatform::~BrookPlatform( ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::BrookPlatform";
// ---------------------------------------------------------------------------------------
}
void BrookPlatform::_initializeFactory( void ){
//BrookKernelFactory* factory = new BrookKernelFactory();
/*
/**
* Initialize kernel factory
*
*/
void BrookPlatform::_initializeKernelFactory( void ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::_initializeKernelFactory";
// ---------------------------------------------------------------------------------------
BrookKernelFactory* factory = new BrookKernelFactory();
registerKernelFactory( CalcStandardMMForceFieldKernel::Name(), factory);
registerKernelFactory( CalcGBSAOBCForceFieldKernel::Name(), factory);
// registerKernelFactory( CalcGBSAOBCForceFieldKernel::Name(), factory);
registerKernelFactory( IntegrateVerletStepKernel::Name(), factory);
registerKernelFactory( IntegrateLangevinStepKernel::Name(), factory);
registerKernelFactory( IntegrateBrownianStepKernel::Name(), factory);
registerKernelFactory( ApplyAndersenThermostatKernel::Name(), factory);
//registerKernelFactory( IntegrateLangevinStepKernel::Name(), factory);
//registerKernelFactory( IntegrateBrownianStepKernel::Name(), factory);
//registerKernelFactory( ApplyAndersenThermostatKernel::Name(), factory);
registerKernelFactory( CalcKineticEnergyKernel::Name(), factory);
*/
}
/**
* Set & validate runtime
*
* @param runtime Brook runtime (cal/cpu)
*
* @throws exception if runtime is invalid
*/
void BrookPlatform::_setBrookRuntime( const std::string& runtime ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookPlatform::_setBrookRuntime";
// ---------------------------------------------------------------------------------------
// set & validate runtime
_runtime = runtime;
std::transform( _runtime.begin(), _runtime.end(), _runtime.begin(), tolower);
if( _runtime != "cal" && _runtime != "cpu" ){
std::stringstream message;
message << methodName << " Brook runtime=" << _runtime << " not recognized.";
throw OpenMMException( message.str() );
}
if( getLog() ){
(void) fprintf( getLog(), "%s Brook initializing to runtime=<%s>", methodName.c_str(), _runtime.c_str() );
(void) fflush( getLog() );
}
brook::initialize( _runtime.c_str(), NULL );
}
/**
* Return platform name
*
* @return "Brook"
*/
std::string BrookPlatform::getName() const {
return "Brook";
}
/**
* Return platform speed
*
* @return speed
*/
double BrookPlatform::getSpeed() const {
return 10.0;
}
/**
* Return true if BrookPlatform supports double precison
*
* @return true if BrookPlatform supports double precison
*/
bool BrookPlatform::supportsDoublePrecision( void ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::supportsDoublePrecision";
// ---------------------------------------------------------------------------------------
return (sizeof(RealOpenMM) >= sizeof(double));
}
/**
* Return Stream factory
*
*/
const StreamFactory& BrookPlatform::getDefaultStreamFactory( void ) const {
return defaultStreamFactory;
return _defaultStreamFactory;
}
int BrookPlatform::getStreamSize( int size, int streamWidth, int* outputHeight ) const {
/**
*
* Static method
*
* Return stream size and height given size of array and stream width
*
* @param size size of array
* @param streamWidth stream width
* @param outputHeight output stream height
*
* @return stream size; -1 if streamWidth < 1 || size < 1
*
*/
int BrookPlatform::getStreamSize( int size, int streamWidth, int* outputHeight ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookPlatform::getStreamSize";
// ---------------------------------------------------------------------------------------
if( streamWidth < 1 ){
if( streamWidth < 1 || size < 1){
return -1;
}
......@@ -93,3 +269,29 @@ int BrookPlatform::getStreamSize( int size, int streamWidth, int* outputHeight )
}
return height*streamWidth;
}
/**
* Get log file reference
*
* @return log file reference
*
*/
FILE* BrookPlatform::getLog( void ) const {
return _log;
}
/**
* Set log file reference
*
* @param log file reference
*
* @return DefaultReturnValue
*
*/
int BrookPlatform::setLog( FILE* log ){
_log = log;
return BrookPlatform::DefaultErrorValue;
}
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright (c) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include "BrookRemoveCMMotionKernel.h"
#include "BrookStreamInternal.h"
using namespace OpenMM;
using namespace std;
/**
* BrookRemoveCMMotionKernel constructor
*
* @param name name of the stream to create
* @param platform platform
*
*/
BrookRemoveCMMotionKernel::BrookRemoveCMMotionKernel( std::string name, const Platform& platform ) :
RemoveCMMotionKernel( name, platform ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookRemoveCMMotionKernel::BrookRemoveCMMotionKernel";
// ---------------------------------------------------------------------------------------
}
/**
* BrookRemoveCMMotionKernel destructor
*
*/
BrookRemoveCMMotionKernel::~BrookRemoveCMMotionKernel( ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookRemoveCMMotionKernel::~BrookRemoveCMMotionKernel";
// ---------------------------------------------------------------------------------------
}
/**
* Initialize the kernel
*
* @param masses array of atom masses
*
*/
void BrookRemoveCMMotionKernel::initialize( const vector<double>& masses ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookRemoveCMMotionKernel::initialize";
// ---------------------------------------------------------------------------------------
/*
this->masses.resize(masses.size());
for (size_t i = 0; i < masses.size(); ++i)
this->masses[i] = masses[i];
*/
return;
}
/**
* Execute kernel
*
* @param velocities array of atom velocities
*
*/
void BrookRemoveCMMotionKernel::execute( Stream& velocities ){
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookRemoveCMMotionKernel::execute";
// ---------------------------------------------------------------------------------------
/*
RealOpenMM** velData = ((BrookFloatStreamImpl&) velocities.getImpl()).getData();
// Calculate the center of mass momentum.
RealOpenMM momentum[] = {0.0, 0.0, 0.0};
for (size_t i = 0; i < masses.size(); ++i) {
momentum[0] += static_cast<RealOpenMM>( masses[i]*velData[i][0] );
momentum[1] += static_cast<RealOpenMM>( masses[i]*velData[i][1] );
momentum[2] += static_cast<RealOpenMM>( masses[i]*velData[i][2] );
}
// Adjust the atom velocities.
momentum[0] /= static_cast<RealOpenMM>( masses.size() );
momentum[1] /= static_cast<RealOpenMM>( masses.size() );
momentum[2] /= static_cast<RealOpenMM>( masses.size() );
for (size_t i = 0; i < masses.size(); ++i) {
velData[i][0] -= static_cast<RealOpenMM>( momentum[0]/masses[i] );
velData[i][1] -= static_cast<RealOpenMM>( momentum[1]/masses[i] );
velData[i][2] -= static_cast<RealOpenMM>( momentum[2]/masses[i] );
}
*/
return;
}
#ifndef OPENMM_BROOK_REMOVE_CM_MOTION_KERNEL_H_
#define OPENMM_BROOK_REMOVE_CM_MOTION_KERNEL_H_
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright ( c ) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman, Mark Friedrichs *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include "kernels.h"
namespace OpenMM {
/**
* Brook class for removing center-of-mass motion
*/
class BrookRemoveCMMotionKernel : public RemoveCMMotionKernel {
public:
/**
* BrookRemoveCMMotionKernel constructor
*
* @param name name of the stream to create
* @param platform platform
*
*/
BrookRemoveCMMotionKernel( std::string name, const Platform& platform );
/**
* BrookRemoveCMMotionKernel destructor
*
*/
~BrookRemoveCMMotionKernel();
/**
* Initialize the kernel
*
* @param masses mass of each atom
*
*/
void initialize( const std::vector<double>& masses );
/**
* Execute the kernel.
*
* @param velocities stream of atom velocities
*
*/
void execute( Stream& velocities );
private:
};
} // namespace OpenMM
#endif /* OPENMM_BROOK_REMOVE_CM_MOTION_KERNEL_H_ */
......@@ -32,8 +32,7 @@
#include <sstream>
#include "OpenMMException.h"
#include "BrookStreamFactory.h"
#include "BrookFloatStreamImpl.h"
#include "BrookIntStreamImpl.h"
#include "BrookStreamImpl.h"
using namespace OpenMM;
......@@ -52,8 +51,13 @@ const std::string BrookStreamFactory::BondedInverseMapStreams = "BondedInvers
// non-bonded streams
const std::string BrookStreamFactory::NonBondedExclusionStream = "NonBondedExclusionStream";
const std::string BrookStreamFactory::NonBondedVdwStream = "NonBondedVdwStream";
const std::string BrookStreamFactory::OuterVdwStream = "OuterVdwStream";
const std::string BrookStreamFactory::InnerSigmaStream = "InnerSigmaStream";
const std::string BrookStreamFactory::InnerEpsilonStream = "InnerEpsilonStream";
const std::string BrookStreamFactory::NonBondedChargeStream = "NonBondedChargeStream";
const std::string BrookStreamFactory::PartialForceStream = "PartialForceStream";
const double DefaultDangleValue = 1.0e+38;
/**
* BrookStreamFactory constructor
*
......@@ -62,23 +66,15 @@ const std::string BrookStreamFactory::NonBondedVdwStream = "NonBondedVdw
BrookStreamFactory::BrookStreamFactory( void ){
double defaultDangleValue = 1.0e+38;
int defaultStreamWidth = 32;
// ---------------------------------------------------------------------------------------
_streamInfoMap[AtomPositions] = new BrookStreamInfo( AtomPositions, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[AtomVelocities] = new BrookStreamInfo( AtomVelocities, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[AtomForces] = new BrookStreamInfo( AtomForces, defaultStreamWidth, defaultDangleValue );
//static const std::string methodName = "BrookStreamFactory::BrookStreamFactory";
// bonded streams
// ---------------------------------------------------------------------------------------
_streamInfoMap[BondedAtomIndicesStream] = new BrookStreamInfo( BondedAtomIndicesStream, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[BondedParametersStream] = new BrookStreamInfo( BondedParametersStream, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[UnrolledForceStream] = new BrookStreamInfo( UnrolledForceStream, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[BondedChargeStream] = new BrookStreamInfo( BondedChargeStream, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[BondedInverseMapStreams] = new BrookStreamInfo( BondedInverseMapStreams, defaultStreamWidth, defaultDangleValue );
_defaultDangleValue = 1.0e+38;
_defaultAtomStreamWidth = 32;
_streamInfoMap[NonBondedExclusionStream] = new BrookStreamInfo( NonBondedExclusionStream, defaultStreamWidth, defaultDangleValue );
_streamInfoMap[NonBondedVdwStream] = new BrookStreamInfo( NonBondedVdwStream, defaultStreamWidth, defaultDangleValue );
}
/**
......@@ -87,117 +83,127 @@ BrookStreamFactory::BrookStreamFactory( void ){
*/
BrookStreamFactory::~BrookStreamFactory( void ){
//_streamInfoMap[UnrolledForceStream] = new BrookStreamInfo( UnrolledForceStream, 32, defaultDangleValue );
}
/**
* Get BrookStreamInfo reference given stream name
* Get atom stream width
*
* @return atomStreamWidth
*
* @param name stream name
*/
int BrookStreamFactory::getDefaultAtomStreamWidth( void ) const {
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookStreamFactory::getDefaultAtomStreamWidth";
// ---------------------------------------------------------------------------------------
return _defaultAtomStreamWidth;
}
/**
* Set atom stream width
*
* @return BrookStreamInfo -- look up streamInfo object given name; return NULL if name not recognized
* @param atomStreamWidth atom stream width
*
* @return DefaultReturnValue
*
* @throw OpenMMException if atomStreamWidth < 1
*
*/
BrookStreamInfo* BrookStreamFactory::getBrookStreamInfo( std::string name ) const {
int BrookStreamFactory::setDefaultAtomStreamWidth( int atomStreamWidth ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookStreamFactory::setDefaultAtomStreamWidth";
if( _streamInfoMap.find( name ) == _streamInfoMap.end() ){
return NULL;
// ---------------------------------------------------------------------------------------
// validate atom stream width
if( atomStreamWidth < 1 ){
std::stringstream message;
message << methodName << " atomStreamWidth=" << atomStreamWidth << " is less than 1.";
throw OpenMMException( message.str() );
return ErrorReturnValue;
}
return _streamInfoMap.find( name )->second;
_defaultAtomStreamWidth = atomStreamWidth;
return DefaultReturnValue;
}
/**
* Create StreamImpl
*
* @param name stream name
* @param size stream size
* @param type data type (float, float2, ...)
* @param platform platform reference
* @param context context (currently ignored)
* get default dangle value
*
* @return StreamImpl
* @return default dangle value
*
*/
StreamImpl* BrookStreamFactory::createStreamImpl( std::string name, int size, Stream::DataType type,
const Platform& platform, OpenMMContextImpl& context ) const {
double BrookStreamFactory::getDefaultDangleValue( void ) const {
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookStreamFactory::getDefaultDangleValue";
return BrookStreamFactory::createStreamImplCommon( name, size, type, platform );
// ---------------------------------------------------------------------------------------
return _defaultDangleValue;
}
/**
* Create StreamImpl
*
* @param name stream name
* @param size stream size
* @param type data type (float, float2, ...)
* @param platform platform reference
* Set default dangle value
*
* @return StreamImpl
* @param DefaultDangleValue default dangle value
*
* @return DefaultReturnValue
*
*/
StreamImpl* BrookStreamFactory::createStreamImpl( std::string name, int size, Stream::DataType type,
const Platform& platform ) const {
int BrookStreamFactory::setDefaultDangleValue( double defaultDangleValue ){
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookStreamFactory::setDefaultDangleValue";
// ---------------------------------------------------------------------------------------
_defaultDangleValue = defaultDangleValue;
return DefaultReturnValue;
return BrookStreamFactory::createStreamImplCommon( name, size, type, platform );
}
/**
* Create StreamImpl
* Create StreamInternal
*
* @param name stream name
* @param size stream size
* @param type data type (float, float2, ...)
* @param platform platform reference
* @param context context (currently ignored)
*
* @return StreamImpl
* @return StreamInternal
*/
StreamImpl* BrookStreamFactory::createStreamImplCommon( std::string name, int size, Stream::DataType type,
const Platform& platform ) const {
StreamImpl* BrookStreamFactory::createStreamImpl( std::string name, int size, Stream::DataType type,
const Platform& platform, OpenMMContextImpl& context ) const {
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookStreamFactory::createStreamImplCommon";
//static const int debug = 0;
//static const std::string methodName = "BrookStreamFactory::createStreamImpl";
// ---------------------------------------------------------------------------------------
// get stream width & dangle value
BrookStreamInfo* streamInfo = getBrookStreamInfo( name );
if( streamInfo == NULL ){
std::stringstream message;
message << methodName << " stream=" << name << " not registered.";
throw OpenMMException( message.str() );
}
// stream width hould be based on name & value set in platform; for now only atom stream types
int streamWidth = streamInfo->getStreamWidth();
double dangleValue = streamInfo->getDangleValue();
switch ( type ){
case Stream::Float:
case Stream::Float2:
case Stream::Float3:
case Stream::Float4:
case Stream::Double:
case Stream::Double2:
case Stream::Double3:
case Stream::Double4:
return new BrookFloatStreamImpl( name, size, type, platform, streamWidth, dangleValue );
break;
case Stream::Integer:
case Stream::Integer2:
case Stream::Integer3:
case Stream::Integer4:
return new BrookIntStreamImpl( name, size, type, platform );
break;
}
int streamWidth = getDefaultAtomStreamWidth();
std::stringstream message;
message << methodName << " type=" << type << " for stream=" << name << " is invalid.";
throw OpenMMException( message.str() );
return new BrookStreamImpl( name, size, streamWidth, type, platform );
}
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright (c) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include <sstream>
#include "OpenMMException.h"
#include "BrookStreamImpl.h"
using namespace OpenMM;
using namespace std;
/**
* BrookStreamImpl constructor
*
* @param name stream name
* @param size stream size
* @param streamWidth stream width
* @param type StreamImpl data type (float, float2, ...)
* @param platform platform reference
*
*/
BrookStreamImpl::BrookStreamImpl( const std::string& name, int size, int streamWidth, Stream::DataType type, const Platform& platform ) :
StreamImpl( name, size, type, platform ){
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookStreamImpl::BrookStreamImpl";
// ---------------------------------------------------------------------------------------
int isFloat;
BrookStreamInternal::DataType internalType = getTypeMap( type, &isFloat );
if( isFloat == 1 || isFloat == 2 ){
double dangleValue = 0.0;
_brookStreamInternal = new BrookFloatStreamInternal( name, size, streamWidth, internalType, dangleValue );
} else if( isFloat == 0 ){
int dangleValue = 0;
_brookStreamInternal = new BrookIntStreamInternal( name, size, streamWidth, internalType, dangleValue );
} else {
std::stringstream message;
message << methodName << " type=" << type << " for stream=" << name << " is invalid.";
throw OpenMMException( message.str() );
}
}
/**
* BrookStreamImpl destructor
*
*/
BrookStreamImpl::~BrookStreamImpl( ){
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookStreamImpl::~BrookStreamImpl";
// ---------------------------------------------------------------------------------------
}
/**
* BrookStreamImpl constructor
*
* @param type StreamImpl data type (float, float2, ...)
* @param isFloat on output = 1 if float
* 2 if double
* 0 if integer
*
* @return BrookStreamInternal::DataType mapping to Stream::DataType type
* if no match, return BrookStreamInternal::Unknown
*
*/
BrookStreamInternal::DataType BrookStreamImpl::getTypeMap( Stream::DataType type, int* isFloat ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookStreamImpl::getTypeMap";
// ---------------------------------------------------------------------------------------
*isFloat = 0;
BrookStreamInternal::DataType internalType = BrookStreamInternal::Unknown;
switch ( type ){
case Stream::Float:
internalType = BrookStreamInternal::Float;
*isFloat = 1;
break;
case Stream::Float2:
internalType = BrookStreamInternal::Float2;
*isFloat = 1;
break;
case Stream::Float3:
internalType = BrookStreamInternal::Float3;
*isFloat = 1;
break;
case Stream::Float4:
internalType = BrookStreamInternal::Float4;
*isFloat = 1;
break;
case Stream::Double:
internalType = BrookStreamInternal::Double;
*isFloat = 2;
break;
case Stream::Double2:
internalType = BrookStreamInternal::Double2;
*isFloat = 2;
break;
case Stream::Double3:
internalType = BrookStreamInternal::Double3;
*isFloat = 2;
break;
case Stream::Double4:
internalType = BrookStreamInternal::Double4;
*isFloat = 2;
break;
case Stream::Integer:
internalType = BrookStreamInternal::Integer;
*isFloat = 0;
break;
case Stream::Integer2:
internalType = BrookStreamInternal::Integer2;
*isFloat = 0;
break;
case Stream::Integer3:
internalType = BrookStreamInternal::Integer3;
*isFloat = 0;
break;
case Stream::Integer4:
internalType = BrookStreamInternal::Integer4;
*isFloat = 0;
break;
}
return internalType;
}
/**
* Get width
*
* @return width
*/
int BrookStreamImpl::getWidth( void ) const {
return _brookStreamInternal->getWidth();
}
/**
* Get stream width
*
* @return stream width
*/
int BrookStreamImpl::getStreamWidth( void ) const {
return _brookStreamInternal->getStreamWidth();
}
/**
* Get stream height
*
* @return stream height
*/
int BrookStreamImpl::getStreamHeight( void ) const {
return _brookStreamInternal->getStreamHeight();
}
/**
* Get stream size
*
* @return stream size
*/
int BrookStreamImpl::getStreamSize( void ) const {
return _brookStreamInternal->getStreamSize();
}
/**
* Copy the contents of an array into this stream.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
void BrookStreamImpl::loadFromArray( const void* array ){
return _brookStreamInternal->loadFromArray( array );
}
/**
* Copy the contents of this stream into an array.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
void BrookStreamImpl::saveToArray( void* array ){
return _brookStreamInternal->saveToArray( array );
}
/**
* Set every element of this stream to the same value.
*
* @param a pointer to the value. It is assumed to be of the correct data type for this stream.
*/
void BrookStreamImpl::fillWithValue( void* value ){
return _brookStreamInternal->fillWithValue( value );
}
/**
* Get Brook stream
*
* @return Brook stream reference
*/
brook::stream& BrookStreamImpl::getBrookStream( void ){
return _brookStreamInternal->getBrookStream( );
}
#ifndef OPENMM_BROOK_STREAM_IMPL_H_
#define OPENMM_BROOK_STREAM_IMPL_H_
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright ( c ) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman, Mark Friedrichs *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include "StreamImpl.h"
#include "BrookFloatStreamInternal.h"
#include "BrookIntStreamInternal.h"
namespace OpenMM {
/**
* This is the base class of Float and Double streams in the Brook Platform.
*/
class BrookStreamImpl : public StreamImpl {
public:
/**
* BrookStreamImpl constructor
*
* @param name name of the stream to create
* @param size number of elements in the stream
* @param streamWidth stream width
* @param type data type of each element in the stream
* @param platform platform
*
*/
BrookStreamImpl( const std::string& name, int size, int streamWidth, Stream::DataType type, const Platform& platform );
/**
* BrookStreamImpl destructor
*
*/
~BrookStreamImpl( );
/**
* BrookStreamImpl constructor
*
* @param type StreamImpl data type (float, float2, ...)
* @param isFloat on output = 1 if float
* 2 if double
* 0 if integer
*
* @return BrookStreamInternal::DataType mapping to Stream::DataType type
* if no match, return BrookStreamInternal::Unknown
*
*/
BrookStreamInternal::DataType getTypeMap( Stream::DataType type, int* isFloat ) const;
/**
* Copy the contents of an array into this stream.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
void loadFromArray( const void* array );
/**
* Copy the contents of this stream into an array.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
void saveToArray( void* array );
/**
* Set every element of this stream to the same value.
*
* @param a pointer to the value. It is assumed to be of the correct data type for this stream.
*/
void fillWithValue( void* value );
/**
* Get Brook stream
*
* @return Brook stream reference
*/
brook::stream& getBrookStream( void );
/**
* Get width
*
* @return width
*/
int getWidth( void ) const;
/**
* Get stream width
*
* @return stream width
*/
int getStreamWidth( void ) const;
/**
* Get stream height
*
* @return stream height
*/
int getStreamHeight( void ) const;
/**
* Get stream size
*
* @return stream size
*/
int getStreamSize( void ) const;
/*
* Get contents of object
*
*
* @param level level of dump
*
* @return string containing contents
*
* */
//const std::string getContentsString( int level = 0 ) const;
protected:
BrookStreamInternal* _brookStreamInternal;
};
} // namespace OpenMM
#endif /* OPENMM_BROOK_STREAM_IMPL_H_ */
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright (c) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include <sstream>
#include "OpenMMException.h"
#include "BrookStreamInternal.h"
using namespace OpenMM;
using namespace std;
BrookStreamInternal::BrookStreamInternal( const std::string& name, int size, int streamWidth, BrookStreamInternal::DataType type ) :
_name(name), _size(size), _streamWidth(streamWidth), _type(type) {
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookStreamInternal::BrookStreamInternal";
// ---------------------------------------------------------------------------------------
_streamHeight = _size/_streamWidth + ( (_size % _streamWidth) ? 1 : 0);
_streamSize = _streamWidth*_streamHeight;
_baseType = BrookStreamInternal::Unknown;
// _aStream = 0;
}
BrookStreamInternal::~BrookStreamInternal( ){
// ---------------------------------------------------------------------------------------
//static const std::string methodName = "BrookStreamInternal::~BrookStreamInternal";
// ---------------------------------------------------------------------------------------
}
/**
* Get name
*
* @return name
*/
const std::string& BrookStreamInternal::getName( void ) const {
return _name;
}
/**
* Get size
*
* @return size
*/
int BrookStreamInternal::getSize( void ) const {
return _size;
}
/**
* Get data type
*
* @return data type
*/
BrookStreamInternal::DataType BrookStreamInternal::getDataType( void ) const {
return _type;
}
/**
* Get base data type
*
* @return base data type ( float, double, int )
*/
BrookStreamInternal::DataType BrookStreamInternal::getBaseDataType( void ) const {
return _baseType;
}
/**
* Get width
*
* @return width
*/
int BrookStreamInternal::getWidth( void ) const {
return _width;
}
/**
* Get stream width
*
* @return stream width
*/
int BrookStreamInternal::getStreamWidth( void ) const {
return _streamWidth;
}
/**
* Get stream height
*
* @return stream height
*/
int BrookStreamInternal::getStreamHeight( void ) const {
return _streamHeight;
}
/**
* Get Brook stream
*
* @return Brook stream
*/
brook::stream& BrookStreamInternal::getBrookStream( void ){
return _aStream;
}
/**
* Get stream size
*
* @return stream size
*/
int BrookStreamInternal::getStreamSize( void ) const {
return _streamSize;
}
/**
* Get type string
*
* @param type BrookStreamInternal data type (float, float2, ...)
*
* @return string matching type or "Unknown"
*
*/
std::string BrookStreamInternal::getTypeString( BrookStreamInternal::DataType type ) const {
// ---------------------------------------------------------------------------------------
// static const std::string methodName = "BrookStreamImpl::getTypeString";
// ---------------------------------------------------------------------------------------
std::string typeString;
switch ( type ){
case BrookStreamInternal::Float:
typeString = "Float";
break;
case BrookStreamInternal::Float2:
typeString = "Float2";
break;
case BrookStreamInternal::Float3:
typeString = "Float3";
break;
case BrookStreamInternal::Float4:
typeString = "Float4";
break;
case BrookStreamInternal::Double:
typeString = "Double";
break;
case BrookStreamInternal::Double2:
typeString = "Double2";
break;
case BrookStreamInternal::Double3:
typeString = "Double3";
break;
case BrookStreamInternal::Double4:
typeString = "Double4";
break;
case BrookStreamInternal::Integer:
typeString = "Integer";
break;
case BrookStreamInternal::Integer2:
typeString = "Integer2";
break;
case BrookStreamInternal::Integer3:
typeString = "Integer3";
break;
case BrookStreamInternal::Integer4:
typeString = "Integer4";
break;
default:
typeString = "Unknown";
break;
}
return typeString;
}
/*
* Get contents of object
*
* @param tab tab
* @param description description
* @param value value
*
* @return string containing contents
*
* */
std::string BrookStreamInternal::_getLine( const std::string& tab,
const std::string& description,
const std::string& value ) const {
// ---------------------------------------------------------------------------------------
static const std::string methodName = "BrookStreamInternal::_getLine";
static const unsigned int MAX_LINE_CHARS = 256;
char line[MAX_LINE_CHARS];
// ---------------------------------------------------------------------------------------
std::stringstream message;
memset( line, ' ', MAX_LINE_CHARS );
#ifdef WIN32
(void) sprintf_s( line, MAX_LINE_CHARS, "%s %-40s %s", tab.c_str(), description.c_str(), value.c_str() );
#else
(void) sprintf( line, "%s %-40s %s", tab.c_str(), description.c_str(), value.c_str() );
#endif
message << std::string( line ) << std::endl;
return message.str();
}
#ifndef OPENMM_BROOK_STREAM_INTERNAL_H_
#define OPENMM_BROOK_STREAM_INTERNAL_H_
/* -------------------------------------------------------------------------- *
* OpenMM *
* -------------------------------------------------------------------------- *
* This is part of the OpenMM molecular simulation toolkit originating from *
* Simbios, the NIH National Center for Physics-Based Simulation of *
* Biological Structures at Stanford, funded under the NIH Roadmap for *
* Medical Research, grant U54 GM072970. See https://simtk.org. *
* *
* Portions copyright ( c ) 2008 Stanford University and the Authors. *
* Authors: Peter Eastman, Mark Friedrichs *
* Contributors: *
* *
* 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, CONTRIBUTORS 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. *
* -------------------------------------------------------------------------- */
#include <brook/brook.hpp>
#include "SimTKUtilities/SimTKOpenMMRealType.h"
namespace OpenMM {
/**
* This is the implementation of Float and Double streams in the Brook Platform.
*/
class BrookStreamInternal {
public:
/**
* This is an enumeration of the allowed data types for a Stream.
*/
enum DataType { Float, Float2, Float3, Float4, Double, Double2, Double3, Double4, Integer, Integer2, Integer3, Integer4, Unknown };
/**
* BrookStreamInternal constructor
*
* @param name name of the stream to create
* @param size number of elements in the stream
* @param streamWidth stream width
* @param type data type of each element in the stream
*
*/
BrookStreamInternal( const std::string& name, int size, int streamWidth, BrookStreamInternal::DataType type );
/**
* BrookStreamInternal destructor
*
*/
~BrookStreamInternal( );
/**
* Get the name of this stream.
*/
const std::string& getName( void ) const;
/**
* Get the number of elements in this stream.
*/
int getSize( void ) const;
/**
* Get the data type of each element in the stream.
*/
BrookStreamInternal::DataType getDataType( void ) const;
/**
* Get base data type of each element in the stream ( float, double, int )
*/
BrookStreamInternal::DataType getBaseDataType( void ) const;
/**
* Copy the contents of an array into this stream.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
virtual void loadFromArray(const void* array) = 0;
/**
* Copy the contents of an array into this stream.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
virtual void loadFromArray( const void* array, BrookStreamInternal::DataType baseType ) = 0;
/**
* Copy the contents of this stream into an array.
*
* @param array a pointer to the start of the array. The array is assumed to have the same length as this stream,
* and to contain elements of the correct data type for this stream. If the stream has a compound data type, all
* the values should be packed into a single array: all the values for the first element, followed by all the values
* for the next element, etc.
*/
virtual void saveToArray(void* array) = 0;
/**
* Set every element of this stream to the same value.
*
* @param a pointer to the value. It is assumed to be of the correct data type for this stream.
*/
virtual void fillWithValue(void* value) = 0;
/**
* Get type string
*
* @param type BrookStreamInternal data type (float, float2, ...)
*
* @return string matching type or "Unknown"
*
*/
std::string getTypeString( BrookStreamInternal::DataType type ) const;
/**
* Get Brook stream reference
*
* @return Brook stream reference
*/
brook::stream& getBrookStream( void );
/**
* Get width
*
* @return width
*/
int getWidth( void ) const;
/**
* Get stream width
*
* @return stream width
*/
int getStreamWidth( void ) const;
/**
* Get stream height
*
* @return stream height
*/
int getStreamHeight( void ) const;
/**
* Get stream size
*
* @return stream size
*/
int getStreamSize( void ) const;
/*
* Get contents of object
*
*
* @param level level of dump
*
* @return string containing contents
*
* */
const std::string getContentsString( int level = 0 ) const;
protected:
std::string _name;
BrookStreamInternal::DataType _type;
BrookStreamInternal::DataType _baseType;
int _size;
int _width;
int _streamWidth;
int _streamHeight;
int _streamSize;
brook::stream _aStream;
/*
* Get contents of object
*
* @param tab tab
* @param description description
* @param value value
*
* @return string containing contents
*
* */
std::string _getLine( const std::string& tab, const std::string& description,
const std::string& value ) const;
};
} // namespace OpenMM
#endif /* OPENMM_BROOK_STREAM_INTERNAL_H_ */
/****************************************************************
* This file is part of the gpu acceleration library for gromacs.
* Author: V. Vishal
* Copyright (C) Pande Group, Stanford, 2006
*****************************************************************/
#include <stdio.h>
#include <brook/brook.hpp>
// #include "typedefs.h"
#include "invmap.h"
/*
* Helper functions for building inverse maps for
* torsions, impropers and angles.
*
* */
/*
* For each atom, calculates the positions at which it's
* forces are to be picked up from and stores the position
* in the appropriate index.
*
* Input: number of dihedrals, the atom indices, and a flag indicating
* whether we're doing i(0), j(1), k(2) or l(3)
* Output: an array of counts per atom
* arrays of inversemaps
* nimaps - the number of invmaps actually used.
*
* */
int
gpuCalcInvMap(
int posflag, //0-niatoms-1
int niatoms, //3 for angles, 4 for torsions, impropers
int nints, //number of interactions
int natoms, //number of atoms
int *atoms, //gromacs interaction list
int nmaps, //maximum number of inverse maps
int counts[], //output counts of how many places each atom occurs
float4 *invmaps[], //output array of nmaps inverse maps
int *nimaps //output max number of inverse maps actually used
)
{
int i, j;
int atom;
int mapnum, mapcomp;
for ( i = 0; i < natoms; i++ )
counts[i] = 0;
for ( i = 0; i < nmaps; i++ ) {
for ( j = 0; j < natoms; j++ ) {
invmaps[i][j] = float4( -1.0, -1.0, -1.0, -1.0 );
}
}
//This will hold the number of imaps actually used
*nimaps = -1;
//Now note down the positions where each atom occurs
for ( i = 0; i < nints; i++ ) {
//This is our atom
atom = atoms[ (niatoms + 1) * i + posflag + 1 ];
//Special for merged bondeds
if ( atom == -1 ) {
continue;
}
//Check to make sure we're inside the limits
if ( counts[atom] > nmaps * 4 ) {
printf( "Atom %d has too many proper dihedrals(%d, max %d)\n",
atom, counts[atom], nmaps * 4 );
return 0;
}
//Which invmap will this go into
mapnum = counts[atom] / 4;
if ( mapnum > *nimaps )
*nimaps = mapnum;
//Which component will it be
mapcomp = counts[atom] % 4;
//Set it
//This is silly, but otherwise I have to declare it as float*
//and things get even more confusing. :)
switch (mapcomp) {
case 0: invmaps[mapnum][atom].x = (float) i; break;
case 1: invmaps[mapnum][atom].y = (float) i; break;
case 2: invmaps[mapnum][atom].z = (float) i; break;
case 3: invmaps[mapnum][atom].w = (float) i; break;
}
counts[atom]++;
}
(*nimaps)++;
return 1;
}
void
gpuPrintInvMaps( int nmaps, int natoms, int counts[], float4 *invmap[], FILE* logFile )
{
int i;
int j;
for ( i = 0; i < natoms; i++ ) {
fprintf( logFile, "%d %d ", i, counts[i] );
for ( j = 0; j < nmaps; j++ ) {
fprintf( logFile, "%6.0f %6.0f %6.0f %6.0f", invmap[j][i].x, invmap[j][i].y,
invmap[j][i].z, invmap[j][i].w );
}
fprintf( logFile, "\n");
}
}
/* We are still plagued by kernel call overheads. This is for a big fat
* merged inverse gather kernel:
* Since we have 32 bit floats, we have 23 bits of mantissa or the largest
* integer we can represent is 2^23. So it should be quite safe to add
* 100000 * n to the index where n is the stream in which we should do the
* lookup. This assumes that nints < 100000, preferably nints << 100000
* which should always be true
* */
int
gpuCalcInvMap_merged(
int nints, //number of interactions
int natoms, //number of atoms
int *atoms, //ijkl,ijkl,ijkl...
int nmaps, //maximum number of inverse maps
int counts[], //output counts of how many places each atom occurs
float4 *invmaps[], //output array of nmaps inverse maps
int *nimaps //output max number of inverse maps actually used
)
{
int i, j;
int atom;
int mapnum, mapcomp;
int pos;
for ( i = 0; i < natoms; i++ )
counts[i] = 0;
for ( i = 0; i < nmaps; i++ ) {
for ( j = 0; j < natoms; j++ ) {
invmaps[i][j] = float4( -1.0, -1.0, -1.0, -1.0 );
}
}
//This will hold the number of imaps actually used
*nimaps = -1;
//For each atom
for ( i = 0; i < nints; i++ ) {
for ( j = 0; j < 4; j++ ) {
atom = atoms[ i * 4 + j ];
if ( atom == -1 ) {
//Nothing to be done for this atom, go to next
continue;
}
//Which map
mapnum = counts[ atom ] / 4;
//Make sure we have space
if ( mapnum >= nmaps ) {
printf( "Atom %d has too many bondeds(%d, max %d)\n",
atom, counts[atom], nmaps * 4 );
return 0;
}
if ( mapnum > *nimaps ) {
*nimaps = mapnum;
}
//Which component
mapcomp = counts[ atom ] % 4;
//Encode target stream and position
pos = 100000 * j + i;
switch ( mapcomp ) {
case 0: invmaps[mapnum][atom].x = (float) pos; break;
case 1: invmaps[mapnum][atom].y = (float) pos; break;
case 2: invmaps[mapnum][atom].z = (float) pos; break;
case 3: invmaps[mapnum][atom].w = (float) pos; break;
}
counts[ atom ]++;
}
}
(*nimaps)++;
return 1;
}
/* Repacks the invmap streams for more efficient access in the
* merged inverse gather kernel
*
* buf should be nimaps * natoms large.
* */
int
gpuRepackInvMap_merged( int natoms, int nmaps, int *counts,
float4 *invmaps[], float4 *buf )
{
int i, j;
int nmaps_i;
for ( i = 0; i < natoms; i++ ) {
for ( j = 0; j < nmaps; j++ ) {
buf[ i + j*natoms ] = float4( -1.0f, -1.0f, -1.0f, -1.0f );
}
}
for ( i = 0; i < natoms; i++ ) {
nmaps_i = counts[i] / 4;
if ( counts[i] % 4 )
nmaps_i++;
for ( j = 0; j < nmaps_i; j++ ) {
buf[ i + j * natoms ] = invmaps[j][i];
}
}
return 1;
}
#ifndef __INVMAP_H__
#define __INVMAP_H__
/*
* For each atom, calculates the positions at which it's
* forces are to be picked up from and stores the position
* in the appropriate index.
*
* Input: number of dihedrals, the atom indices, and a flag indicating
* whether we're doing i(0), j(1), k(2) or l(3)
* Output: an array of counts per atom
* arrays of inversemaps
* nimaps - the number of invmaps actually used.
*
* */
int
gpuCalcInvMap(
int posflag, //0-niatoms-1
int niatoms, //3 for angles, 4 for torsions, impropers
int nints, //number of interactions
int natoms, //number of atoms
int *atoms, //gromacs interaction list
int nmaps, //maximum number of inverse maps
int counts[], //output counts of how many places each atom occurs
float4 *invmaps[], //output array of nmaps inverse maps
int *nimaps //output max number of inverse maps actually used
);
void
gpuPrintInvMaps( int nmaps, int natoms, int counts[], float4 *invmap[], FILE* logFile );
/* We are still plagued by kernel call overheads. This is for a big fat
* merged inverse gather kernel:
* Since we have 32 bit floats, we have 23 bits of mantissa or the largest
* integer we can represent is 2^23. So it should be quite safe to add
* 100000 * n to the index where n is the stream in which we should do the
* lookup. This assumes that nints < 100000, preferably nints << 100000
* which should always be true
* */
int
gpuCalcInvMap_merged(
int nints, //number of interactions
int natoms, //number of atoms
int *atoms, //ijkl,ijkl,ijkl...
int nmaps, //maximum number of inverse maps
int counts[], //output counts of how many places each atom occurs
float4 *invmaps[], //output array of nmaps inverse maps
int *nimaps //output max number of inverse maps actually used
);
/* Repacks the invmap streams for more efficient access in the
* merged inverse gather kernel
*
* buf should be nimaps * natoms large.
* */
int
gpuRepackInvMap_merged( int natoms, int nmaps, int *counts,
float4 *invmaps[], float4 *buf );
#endif //__INVMAP_H__
/****************************************************************
* This file is part of the gpu acceleration library for gromacs.
* Author: V. Vishal
* Copyright (C) Pande Group, Stanford, 2006
*****************************************************************/
//Harmonic angles kernel
//Input is a stream of triplets i, j, k
//parms is float2( theta0, kA )
//Output is three streams of forces fi, fj, fk
//Again, this is kept simple for now, can be optimized
//later as necessary
kernel void kangles_harmonic(
float xstrwidth,
float3 atoms<>,
float2 parms<>,
float4 posq[][],
out float3 fi<>,
out float3 fj<>,
out float3 fk<>
) {
float theta;
float dx, dx2, fs;
float st, dvdt, cik, sth, nrkj2, nrij2, cii, ckk, costheta, sintheta;
float rij2, rkj2;
float2 idx;
float2 ai, aj, ak;
float3 xi, xj, xk, rij, rkj;
ai.y = floor( atoms.x / xstrwidth );
ai.x = atoms.x - ai.y * xstrwidth;
aj.y = floor( atoms.y / xstrwidth );
aj.x = atoms.y - aj.y * xstrwidth;
ak.y = floor( atoms.z / xstrwidth );
ak.x = atoms.z - ak.y * xstrwidth;
rij = posq[ ai ].xyz - posq[ aj ].xyz; //3
rkj = posq[ ak ].xyz - posq[ aj ].xyz; //3
rij2 = dot( rij, rij ); //5
rkj2 = dot( rkj, rkj ); //5
costheta = dot( rij, rkj ) / sqrt( rij2 * rkj2 ); //8
costheta = clamp( costheta, -1.0, 1.0 );
theta = acos( costheta ); //1 flop, ouch
sintheta = sqrt( 1 - costheta * costheta ); //3
dx = theta - parms.x; //1
dx2 = dx * dx; //1
/*scalar force = dv/dtheta*/
fs = -parms.y * dx; //1
st = fs / sintheta; //1
st = clamp( st, -1000000.0, 1000000.0 ); //Does this work on the gpu for st=inf?
sth = st * costheta; //1
nrkj2 = dot( rkj, rkj ); //5
nrij2 = dot( rij, rij ); //5
cik = st * rsqrt( nrkj2 * nrij2 ); //3
cii = sth / nrij2; //1
ckk = sth / nrkj2; //1
fi = -( cik * rkj - cii * rij ); //7
fk = -( cik * rij - ckk * rkj ); //7
fj = -fi - fk; //3
//Total flops: 64
}
/****************************************************************
* This file is part of the gpu acceleration library for gromacs.
* Author: V. Vishal
* Copyright (C) Pande Group, Stanford, 2006
*****************************************************************/
//Harmonic bonds kernel
//Input is a stream of i, j pairs
//parms is float2( b0, kA )
//Output is two streams of forces fi, fj
//Can be optimized as necessary
kernel void kbonds_harmonic(
float xstrwidth, //atom stream width
float2 atoms<>,
float2 parms<>,
float4 posq[][],
out float3 fi<>,
out float3 fj<>
) {
float2 ai, aj;
float3 rij;
float rinv;
ai.y = floor( atoms.x / xstrwidth );
ai.x = atoms.x - ai.y * xstrwidth;
aj.y = floor( atoms.y / xstrwidth );
aj.x = atoms.y - aj.y * xstrwidth;
rij = posq[ai].xyz - posq[aj].xyz; //3
rinv = rsqrt( dot(rij, rij) ); //6
fi = -parms.y * ( 1.0f - parms.x * rinv ) * rij; //6
fj = -fi;
//Total: 15 flops
}
/* Portions copyright (c) 2006 Stanford University and Simbios.
* Contributors: Pande Group
*
* 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, CONTRIBUTORS 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.
*/
/**---------------------------------------------------------------------------------------
This kernel calculates the linear momentum
@param mass stream of masses
@param velocities stream of velocities
@param linearMomentum output stream of linear momentum
--------------------------------------------------------------------------------------- */
kernel void kCalculateLinearMomentum( float mass<>, float3 velocities<>, out float3 linearMomentum<> ){
linearMomentum = mass*velocities;
}
/**---------------------------------------------------------------------------------------
This kernel scales the linear momentum
@param scale scale factor
@param linearMomentumIn input linearMomentum
@param linearMomentumOut output linearMomentum
--------------------------------------------------------------------------------------- */
kernel void kScale( float scale, float3 linearMomentumIn<>, out float3 linearMomentumOut<> ){
linearMomentumOut = scale*linearMomentumIn;
}
/**---------------------------------------------------------------------------------------
This kernel calculates the total linear momentum via a reduction
@param momentum momentum
@param linearMomentum total momentum
Note: treating the output linearMomentum as non-stream did not compile, even though
I found examples in Brook testing code that had that construct -- MSF 3/6/08
--------------------------------------------------------------------------------------- */
reduce void kReduceLinearMomentum( float3 momentum<>, reduce float3 linearMomentum<> ){
linearMomentum += momentum;
}
/**---------------------------------------------------------------------------------------
This kernel calculates the total linear momentum via a reduction
@param atomStrWidth atom stream width
@param numberOfAtoms number of atoms
@param momentum momentum
@param linearMomentum total momentum
--------------------------------------------------------------------------------------- */
kernel void kSumLinearMomentum( float atomStrWidth, float numberOfAtoms, float3 momentum[][],
out float3 linearMomentum<> ){
float atomCount;
float2 atomIndex;
atomCount = 0.0f;
linearMomentum = float3( 0.0f, 0.0f, 0.0f );
atomIndex.y = 0.0f;
atomIndex.x = 0.0f;
while( atomCount < numberOfAtoms ){
linearMomentum += momentum[atomIndex];
atomIndex.x += 1.0f;
if( atomIndex.x == atomStrWidth ){
atomIndex.x = 0.0f;
atomIndex.y += 1.0f;
}
atomCount += 1.0f;
}
}
/**---------------------------------------------------------------------------------------
This kernel calculates the total linear momentum via a reduction
@param momentum momentum
@param linearMomentum total momentum
Note: treating the output linearMomentum as non-stream did not compile, even though
I found examples in Brook testing code that had that construct -- MSF 3/6/08
--------------------------------------------------------------------------------------- */
reduce void kSum( float3 array<>, reduce float3 sum<> ){
//sum += array;
//sum += array.x + array.y + array.z;
//sum += float3( 1.0, 1.0, 1.0 );
/*
sum.x += 1.0;
sum.y += 1.0;
sum.z += 1.0;
*/
sum += array;
//sum += 1.0;
}
/**---------------------------------------------------------------------------------------
This kernel subtracts the (total linear momentum)/totalMass from the velocities
@param linearMomentum normalized linear momentum
@param velocities stream of velocities
@param velocitiesOut output stream of velocities
--------------------------------------------------------------------------------------- */
kernel void kRemoveLinearMomentum( float3 linearMomentum[], float3 velocities<>, out float3 velocitiesOut<> ){
velocitiesOut = velocities - linearMomentum[0];
}
/****************************************************************
* This file is part of the gpu acceleration library for gromacs.
* Author: V. Vishal
* Copyright (C) Pande Group, Stanford, 2006
*****************************************************************/
//Inverse of above
kernel void kgetxyz( float4 instr<>, out float3 outstr<> ) {
outstr = instr.xyz;
}
//Zeroes out a stream
kernel void kzerof3( out float3 outstr<> ) {
outstr = float3( 0.0f, 0.0f, 0.0f );
}
//Zeros out a stream
kernel void kzerof4( out float4 outstr<> ) {
outstr = float4( 0.0f, 0.0f, 0.0f, 0.0f );
}
kernel void ksetf4( float4 val, out float4 outstr<> ) {
outstr = val;
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment