Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
tsoc
openmm
Commits
27ff4f1b
"platforms/reference/tests/TestReferenceCheckpoints.cpp" did not exist on "0b662b4991e37286331dd4b5755d53f2b79fd1dd"
Commit
27ff4f1b
authored
May 15, 2009
by
Peter Eastman
Browse files
Improved how the constraint matrices for C-SHAKE get built
parent
043c7b6c
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
96 additions
and
121 deletions
+96
-121
platforms/cuda/src/kernels/gpu.cpp
platforms/cuda/src/kernels/gpu.cpp
+96
-3
platforms/cuda/src/kernels/gputypes.h
platforms/cuda/src/kernels/gputypes.h
+0
-1
platforms/cuda/src/kernels/kCShake.cu
platforms/cuda/src/kernels/kCShake.cu
+0
-117
No files found.
platforms/cuda/src/kernels/gpu.cpp
View file @
27ff4f1b
...
@@ -48,8 +48,11 @@ using namespace std;
...
@@ -48,8 +48,11 @@ using namespace std;
#include "cudaKernels.h"
#include "cudaKernels.h"
#include "hilbert.h"
#include "hilbert.h"
#include "openmm/OpenMMException.h"
#include "openmm/OpenMMException.h"
#include "jama_svd.h"
using
OpenMM
::
OpenMMException
;
using
OpenMM
::
OpenMMException
;
using
TNT
::
Array2D
;
using
JAMA
::
SVD
;
struct
ShakeCluster
{
struct
ShakeCluster
{
int
centralID
;
int
centralID
;
...
@@ -464,7 +467,7 @@ static void markShakeClusterInvalid(ShakeCluster& cluster, map<int, ShakeCluster
...
@@ -464,7 +467,7 @@ static void markShakeClusterInvalid(ShakeCluster& cluster, map<int, ShakeCluster
}
}
}
}
static
void
findRigidClusters
(
gpuContext
gpu
,
const
vector
<
int
>&
firstAtom
,
const
vector
<
int
>&
secondAtom
,
vector
<
int
>&
constraintIndices
)
static
void
findRigidClusters
(
gpuContext
gpu
,
const
vector
<
int
>&
firstAtom
,
const
vector
<
int
>&
secondAtom
,
const
vector
<
float
>&
invMass1
,
const
vector
<
float
>&
invMass2
,
const
vector
<
float
>&
distance
,
vector
<
int
>&
constraintIndices
)
{
{
vector
<
map
<
int
,
int
>
>
atomConstraints
(
firstAtom
.
size
());
vector
<
map
<
int
,
int
>
>
atomConstraints
(
firstAtom
.
size
());
for
(
int
i
=
0
;
i
<
(
int
)
constraintIndices
.
size
();
i
++
)
{
for
(
int
i
=
0
;
i
<
(
int
)
constraintIndices
.
size
();
i
++
)
{
...
@@ -583,7 +586,97 @@ static void findRigidClusters(gpuContext gpu, const vector<int>& firstAtom, cons
...
@@ -583,7 +586,97 @@ static void findRigidClusters(gpuContext gpu, const vector<int>& firstAtom, cons
while
(
gpu
->
sim
.
clusterShakeBlockSize
<
maxClusterSize
)
while
(
gpu
->
sim
.
clusterShakeBlockSize
<
maxClusterSize
)
gpu
->
sim
.
clusterShakeBlockSize
*=
2
;
gpu
->
sim
.
clusterShakeBlockSize
*=
2
;
psRigidClusterConstraintIndex
->
Upload
();
psRigidClusterConstraintIndex
->
Upload
();
gpu
->
hasInitializedRigidClusters
=
false
;
// Build the inverse coupling matrix for each cluster.
unsigned
int
elementIndex
=
0
;
for
(
unsigned
int
i
=
0
;
i
<
rigidClusters
.
size
();
i
++
)
{
// Compute the constraint coupling matrix for this cluster.
const
vector
<
int
>&
cluster
=
rigidClusters
[
i
];
unsigned
int
size
=
cluster
.
size
();
Array2D
<
double
>
matrix
(
size
,
size
);
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
{
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
{
if
(
j
==
k
)
{
matrix
[
j
][
j
]
=
1.0
;
continue
;
}
double
scale
;
int
atomj0
=
firstAtom
[
cluster
[
j
]];
int
atomj1
=
secondAtom
[
cluster
[
j
]];
int
atomk0
=
firstAtom
[
cluster
[
k
]];
int
atomk1
=
secondAtom
[
cluster
[
k
]];
int
atoma
,
atomb
;
if
(
atomj0
==
atomk0
)
{
atoma
=
atomj1
;
atomb
=
atomk1
;
scale
=
invMass1
[
cluster
[
j
]]
/
(
invMass1
[
cluster
[
j
]]
+
invMass2
[
cluster
[
j
]]);
}
else
if
(
atomj1
==
atomk1
)
{
atoma
=
atomj0
;
atomb
=
atomk0
;
scale
=
invMass2
[
cluster
[
j
]]
/
(
invMass1
[
cluster
[
j
]]
+
invMass2
[
cluster
[
j
]]);
}
else
if
(
atomj0
==
atomk1
)
{
atoma
=
atomj1
;
atomb
=
atomk0
;
scale
=
invMass1
[
cluster
[
j
]]
/
(
invMass1
[
cluster
[
j
]]
+
invMass2
[
cluster
[
j
]]);
}
else
if
(
atomj1
==
atomk0
)
{
atoma
=
atomj0
;
atomb
=
atomk1
;
scale
=
invMass2
[
cluster
[
j
]]
/
(
invMass1
[
cluster
[
j
]]
+
invMass2
[
cluster
[
j
]]);
}
else
{
matrix
[
j
][
k
]
=
0.0
;
continue
;
// These constraints are not connected.
}
// Find the third constraint forming a triangle with these two.
for
(
int
m
=
0
;
m
<
size
;
m
++
)
{
int
other
=
cluster
[
m
];
if
((
firstAtom
[
other
]
==
atoma
&&
secondAtom
[
other
]
==
atomb
)
||
(
firstAtom
[
other
]
==
atomb
&&
secondAtom
[
other
]
==
atoma
))
{
double
d1
=
distance
[
cluster
[
j
]];
double
d2
=
distance
[
cluster
[
k
]];
double
d3
=
distance
[
other
];
matrix
[
j
][
k
]
=
scale
*
(
d1
*
d1
+
d2
*
d2
-
d3
*
d3
)
/
(
2.0
*
d1
*
d2
);
break
;
}
}
}
}
// Invert it using SVD.
Array2D
<
double
>
u
,
v
;
Array1D
<
double
>
w
;
SVD
<
double
>
svd
(
matrix
);
svd
.
getU
(
u
);
svd
.
getV
(
v
);
svd
.
getSingularValues
(
w
);
double
singularValueCutoff
=
0.01
*
w
[
0
];
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
w
[
j
]
=
(
w
[
j
]
<
singularValueCutoff
?
0.0
:
1.0
/
w
[
j
]);
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
{
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
{
matrix
[
j
][
k
]
=
0.0
;
for
(
int
m
=
0
;
m
<
(
int
)
size
;
m
++
)
matrix
[
j
][
k
]
+=
v
[
j
][
m
]
*
w
[
m
]
*
u
[
k
][
m
];
}
}
// Record the inverted matrix.
(
*
gpu
->
psRigidClusterMatrixIndex
)[
i
]
=
elementIndex
;
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
(
*
gpu
->
psRigidClusterMatrix
)[
elementIndex
++
]
=
(
float
)(
matrix
[
k
][
j
]
*
distance
[
cluster
[
j
]]
/
distance
[
cluster
[
k
]]);
}
(
*
gpu
->
psRigidClusterMatrixIndex
)[
gpu
->
sim
.
rigidClusters
]
=
elementIndex
;
gpu
->
psRigidClusterMatrix
->
Upload
();
gpu
->
psRigidClusterMatrixIndex
->
Upload
();
}
}
extern
"C"
extern
"C"
...
@@ -791,7 +884,7 @@ void gpuSetConstraintParameters(gpuContext gpu, const vector<int>& atom1, const
...
@@ -791,7 +884,7 @@ void gpuSetConstraintParameters(gpuContext gpu, const vector<int>& atom1, const
// Identify rigid clusters of atoms.
// Identify rigid clusters of atoms.
findRigidClusters
(
gpu
,
atom1
,
atom2
,
lincsConstraints
);
findRigidClusters
(
gpu
,
atom1
,
atom2
,
invMass1
,
invMass2
,
distance
,
lincsConstraints
);
// Record the connections between constraints.
// Record the connections between constraints.
...
...
platforms/cuda/src/kernels/gputypes.h
View file @
27ff4f1b
...
@@ -75,7 +75,6 @@ struct _gpuContext {
...
@@ -75,7 +75,6 @@ struct _gpuContext {
bool
bRecalculateBornRadii
;
bool
bRecalculateBornRadii
;
bool
bOutputBufferPerWarp
;
bool
bOutputBufferPerWarp
;
bool
bIncludeGBSA
;
bool
bIncludeGBSA
;
bool
hasInitializedRigidClusters
;
unsigned
long
seed
;
unsigned
long
seed
;
SM_VERSION
sm_version
;
SM_VERSION
sm_version
;
CUDPPHandle
cudpp
;
CUDPPHandle
cudpp
;
...
...
platforms/cuda/src/kernels/kCShake.cu
View file @
27ff4f1b
...
@@ -27,12 +27,9 @@
...
@@ -27,12 +27,9 @@
#include <cuda.h>
#include <cuda.h>
#include <vector_functions.h>
#include <vector_functions.h>
#include <vector>
#include <vector>
#include "jama_svd.h"
#include "gputypes.h"
#include "gputypes.h"
using
namespace
std
;
using
namespace
std
;
using
TNT
::
Array2D
;
using
JAMA
::
SVD
;
static
__constant__
cudaGmxSimulation
cSim
;
static
__constant__
cudaGmxSimulation
cSim
;
...
@@ -204,127 +201,13 @@ __global__ void kApplyCShake_kernel(float4* atomPositions, bool addOldPosition)
...
@@ -204,127 +201,13 @@ __global__ void kApplyCShake_kernel(float4* atomPositions, bool addOldPosition)
cSim
.
pSyncCounter
[
blockIdx
.
x
]
=
-
1
;
cSim
.
pSyncCounter
[
blockIdx
.
x
]
=
-
1
;
}
}
static
void
initInverseMatrices
(
gpuContext
gpu
,
bool
useNewPositions
)
{
// Build the inverse constraint matrix for each cluster.
gpu
->
psPosq4
->
Download
();
gpu
->
psVelm4
->
Download
();
if
(
useNewPositions
)
gpu
->
psPosqP4
->
Download
();
unsigned
int
elementIndex
=
0
;
for
(
unsigned
int
i
=
0
;
i
<
gpu
->
sim
.
rigidClusters
;
i
++
)
{
// Compute the constraint coupling matrix for this cluster.
unsigned
int
startIndex
=
(
*
gpu
->
psRigidClusterConstraintIndex
)[
i
];
unsigned
int
endIndex
=
(
*
gpu
->
psRigidClusterConstraintIndex
)[
i
+
1
];
unsigned
int
size
=
endIndex
-
startIndex
;
vector
<
float3
>
r
(
size
);
for
(
unsigned
int
j
=
0
;
j
<
size
;
j
++
)
{
int2
atoms
=
(
*
gpu
->
psLincsAtoms
)[
startIndex
+
j
];
float4
pos1
,
pos2
;
if
(
useNewPositions
)
{
float4
oldpos1
=
(
*
gpu
->
psPosq4
)[
atoms
.
x
];
float4
oldpos2
=
(
*
gpu
->
psPosq4
)[
atoms
.
y
];
pos1
=
(
*
gpu
->
psPosqP4
)[
atoms
.
x
];
pos2
=
(
*
gpu
->
psPosqP4
)[
atoms
.
y
];
pos1
.
x
+=
oldpos1
.
x
;
pos1
.
y
+=
oldpos1
.
y
;
pos1
.
z
+=
oldpos1
.
z
;
pos2
.
x
+=
oldpos2
.
x
;
pos2
.
y
+=
oldpos2
.
y
;
pos2
.
z
+=
oldpos2
.
z
;
}
else
{
pos1
=
(
*
gpu
->
psPosq4
)[
atoms
.
x
];
pos2
=
(
*
gpu
->
psPosq4
)[
atoms
.
y
];
}
r
[
j
]
=
make_float3
(
pos1
.
x
-
pos2
.
x
,
pos1
.
y
-
pos2
.
y
,
pos1
.
z
-
pos2
.
z
);
float
invLength
=
1.0
f
/
sqrt
(
r
[
j
].
x
*
r
[
j
].
x
+
r
[
j
].
y
*
r
[
j
].
y
+
r
[
j
].
z
*
r
[
j
].
z
);
r
[
j
].
x
*=
invLength
;
r
[
j
].
y
*=
invLength
;
r
[
j
].
z
*=
invLength
;
}
Array2D
<
double
>
matrix
(
size
,
size
);
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
{
int2
atomsj
=
(
*
gpu
->
psLincsAtoms
)[
startIndex
+
j
];
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
{
int2
atomsk
=
(
*
gpu
->
psLincsAtoms
)[
startIndex
+
k
];
float
invMassj0
=
(
*
gpu
->
psVelm4
)[
atomsj
.
x
].
w
;
float
invMassj1
=
(
*
gpu
->
psVelm4
)[
atomsj
.
y
].
w
;
double
dot
=
r
[
j
].
x
*
r
[
k
].
x
+
r
[
j
].
y
*
r
[
k
].
y
+
r
[
j
].
z
*
r
[
k
].
z
;
if
(
atomsj
.
x
==
atomsk
.
x
)
dot
*=
invMassj0
/
(
invMassj0
+
invMassj1
);
else
if
(
atomsj
.
y
==
atomsk
.
y
)
dot
*=
invMassj1
/
(
invMassj0
+
invMassj1
);
else
if
(
atomsj
.
x
==
atomsk
.
y
)
dot
*=
-
invMassj0
/
(
invMassj0
+
invMassj1
);
else
if
(
atomsj
.
y
==
atomsk
.
x
)
dot
*=
-
invMassj1
/
(
invMassj0
+
invMassj1
);
else
dot
=
0.0
;
matrix
[
j
][
k
]
=
dot
;
}
matrix
[
j
][
j
]
=
1.0
;
}
// Invert it using SVD.
Array2D
<
double
>
u
,
v
;
Array1D
<
double
>
w
;
SVD
<
double
>
svd
(
matrix
);
svd
.
getU
(
u
);
svd
.
getV
(
v
);
svd
.
getSingularValues
(
w
);
double
singularValueCutoff
=
0.01
*
w
[
0
];
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
w
[
j
]
=
(
w
[
j
]
<
singularValueCutoff
?
0.0
:
1.0
/
w
[
j
]);
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
{
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
{
matrix
[
j
][
k
]
=
0.0
;
for
(
int
m
=
0
;
m
<
(
int
)
size
;
m
++
)
matrix
[
j
][
k
]
+=
v
[
j
][
m
]
*
w
[
m
]
*
u
[
k
][
m
];
}
}
// Record the inverted matrix.
(
*
gpu
->
psRigidClusterMatrixIndex
)[
i
]
=
elementIndex
;
for
(
int
j
=
0
;
j
<
(
int
)
size
;
j
++
)
{
float
distance1
=
(
*
gpu
->
psLincsDistance
)[
startIndex
+
j
].
w
;
for
(
int
k
=
0
;
k
<
(
int
)
size
;
k
++
)
{
float
distance2
=
(
*
gpu
->
psLincsDistance
)[
startIndex
+
k
].
w
;
(
*
gpu
->
psRigidClusterMatrix
)[
elementIndex
++
]
=
(
float
)(
matrix
[
k
][
j
]
*
distance1
/
distance2
);
}
}
}
(
*
gpu
->
psRigidClusterMatrixIndex
)[
gpu
->
sim
.
rigidClusters
]
=
elementIndex
;
gpu
->
psRigidClusterMatrix
->
Upload
();
gpu
->
psRigidClusterMatrixIndex
->
Upload
();
}
void
kApplyFirstCShake
(
gpuContext
gpu
)
void
kApplyFirstCShake
(
gpuContext
gpu
)
{
{
// printf("kApplyFirstCShake\n");
// printf("kApplyFirstCShake\n");
if
(
gpu
->
sim
.
lincsConstraints
>
0
)
if
(
gpu
->
sim
.
lincsConstraints
>
0
)
{
{
if
(
!
gpu
->
hasInitializedRigidClusters
)
{
// Build preliminary constraint matrices for use on this call.
initInverseMatrices
(
gpu
,
false
);
}
kApplyCShake_kernel
<<<
gpu
->
sim
.
blocks
,
gpu
->
sim
.
lincs_threads_per_block
,
4
*
gpu
->
sim
.
lincs_threads_per_block
>>>
(
gpu
->
sim
.
pPosqP
,
true
);
kApplyCShake_kernel
<<<
gpu
->
sim
.
blocks
,
gpu
->
sim
.
lincs_threads_per_block
,
4
*
gpu
->
sim
.
lincs_threads_per_block
>>>
(
gpu
->
sim
.
pPosqP
,
true
);
LAUNCHERROR
(
"kApplyCShake"
);
LAUNCHERROR
(
"kApplyCShake"
);
if
(
!
gpu
->
hasInitializedRigidClusters
)
{
// Rebuild the constraint matrices, now that we know all constraints are really satisfied.
initInverseMatrices
(
gpu
,
true
);
gpu
->
hasInitializedRigidClusters
=
true
;
}
}
}
}
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment