tbonds working, tests passed - sphere - GPU-based 3D discrete element method al… | |
git clone git://src.adamsgaard.dk/sphere | |
Log | |
Files | |
Refs | |
LICENSE | |
--- | |
commit b67be3fda4d26ef813cb6af47cbae812adf68e7a | |
parent c530064dfebbdf97dafcdd137bfcdb90c63d954d | |
Author: Anders Damsgaard <[email protected]> | |
Date: Mon, 11 Mar 2013 21:54:36 +0100 | |
bonds working, tests passed | |
Diffstat: | |
M src/cohesion.cuh | 105 +++++++++++++++++++----------… | |
M src/device.cu | 7 +++++++ | |
M src/sphere.cpp | 5 ++++- | |
M tests/bond_tests.py | 63 +++++++++++++++++------------… | |
M tests/pytestutils.py | 12 ++++++++++++ | |
5 files changed, 120 insertions(+), 72 deletions(-) | |
--- | |
diff --git a/src/cohesion.cuh b/src/cohesion.cuh | |
t@@ -32,21 +32,23 @@ __global__ void bondsLinear( | |
if (bond.x >= devC_np) | |
return; | |
- const Float4 delta_t0_4 = dev_bonds_delta[idx]; | |
- const Float4 omega_t0_4 = dev_bonds_omega[idx]; | |
+ const Float4 delta0_4 = dev_bonds_delta[idx]; | |
+ const Float4 omega0_4 = dev_bonds_omega[idx]; | |
// Convert tangential vectors to Float3's | |
- const Float3 delta_t0_uncor = MAKE_FLOAT3( | |
- delta_t0_4.x, | |
- delta_t0_4.y, | |
- delta_t0_4.z); | |
- const Float delta_t0_n = delta_t0_4.w; | |
- | |
- const Float3 omega_t0_uncor = MAKE_FLOAT3( | |
- omega_t0_4.x, | |
- omega_t0_4.y, | |
- omega_t0_4.z); | |
- const Float omega_t0_n = omega_t0_4.w; | |
+ // Uncorrected tangential component of displacement | |
+ Float3 delta0_t = MAKE_FLOAT3( | |
+ delta0_4.x, | |
+ delta0_4.y, | |
+ delta0_4.z); | |
+ const Float delta0_n = delta0_4.w; | |
+ | |
+ // Uncorrected tangential component of rotation | |
+ Float3 omega0_t = MAKE_FLOAT3( | |
+ omega0_4.x, | |
+ omega0_4.y, | |
+ omega0_4.z); | |
+ const Float omega0_n = omega0_4.w; | |
// Read particle data | |
const Float4 x_i = dev_x[bond.x]; | |
t@@ -59,9 +61,6 @@ __global__ void bondsLinear( | |
const Float3 angvel_i = MAKE_FLOAT3(angvel4_i.x, angvel4_i.y, angvel4_i.z); | |
const Float3 angvel_j = MAKE_FLOAT3(angvel4_j.x, angvel4_j.y, angvel4_j.z); | |
- // Initialize force- and torque vectors | |
- Float3 f, t, f_n, f_t, t_n, t_t; | |
- | |
//// Bond geometry and inertia | |
t@@ -89,16 +88,16 @@ __global__ void bondsLinear( | |
const Float overlap = fmin(0.0, x_length - (x_i.w + x_j.w)); | |
// Normal vector of contact (points from i to j) | |
- const Float3 n = x/x_length; | |
+ Float3 n = x/x_length; | |
//// Force | |
// Correct tangential displacement vector for rotation of the contact plane | |
//const Float3 delta_t0 = delta_t0_uncor - dot(delta_t0_uncor, n); | |
- const Float3 delta_t0 = delta_t0_uncor - (n * dot(n, delta_t0_uncor)); | |
+ delta0_t = delta0_t - (n * dot(n, delta0_t)); | |
- // Contact displacement | |
+ // Contact displacement, Luding 2008 eq. 10 | |
const Float3 ddelta = ( | |
MAKE_FLOAT3( | |
vel_i.x - vel_j.x, | |
t@@ -113,68 +112,84 @@ __global__ void bondsLinear( | |
const Float ddelta_n = -dot(ddelta, n); | |
// Normal component of the total displacement | |
- const Float delta_n = delta_t0_n + ddelta_n; | |
+ const Float delta_n = delta0_n + ddelta_n; | |
// Tangential component of the displacement increment | |
- //const Float3 ddelta_t = ddelta - dot(ddelta, n); | |
+ // Luding 2008, eq. 9 | |
const Float3 ddelta_t = ddelta - n * dot(n, ddelta); | |
// Tangential component of the total displacement | |
- const Float3 delta_t = delta_t0 + ddelta_t; | |
+ const Float3 delta_t = delta0_t + ddelta_t; | |
// Normal force: Visco-elastic contact model | |
// The elastic component caused by the overlap is subtracted. | |
//f_n = devC_params.k_n * A * delta_n * n; | |
- f_n = (devC_params.k_n * A * delta_n + devC_params.gamma_n * ddelta_n/devC… | |
+ const Float3 f_n = (devC_params.k_n * A * delta_n + devC_params.gamma_n * … | |
//f_n += devC_params.k_n * overlap * n; | |
// Tangential force: Visco-elastic contact model | |
//f_t = -devC_params.k_t * A * delta_t; | |
- f_t = -devC_params.k_t * A * delta_t - devC_params.gamma_t * ddelta_t/devC… | |
+ const Float3 f_t = -devC_params.k_t * A * delta_t - devC_params.gamma_t * … | |
// Force vector | |
- f = f_n + f_t; | |
+ const Float3 f = f_n + f_t; | |
//// Torque | |
// Correct tangential rotational vector for rotation of the contact plane | |
- //Float3 omega_t0 = omega_t0_uncor - dot(omega_t0_uncor, n); | |
- Float3 omega_t0 = omega_t0_uncor - (n * dot(n, omega_t0_uncor)); | |
+ omega0_t = omega0_t - (-n) * dot(omega0_t, -n); | |
+ //omega0_t = omega0_t - (n * dot(n, omega0_t)); | |
// Contact rotational velocity | |
Float3 domega = MAKE_FLOAT3( | |
angvel_j.x - angvel_i.x, | |
angvel_j.y - angvel_i.y, | |
angvel_j.z - angvel_i.z) * devC_dt; | |
+ /*const Float3 domega = MAKE_FLOAT3( | |
+ angvel_i.x - angvel_j.x, | |
+ angvel_i.y - angvel_j.y, | |
+ angvel_i.z - angvel_j.z) * devC_dt;*/ | |
// Normal component of the rotational increment | |
- //const Float domega_n = dot(domega, n); | |
- const Float domega_n = -dot(n, domega); | |
+ const Float domega_n = dot(domega, -n); | |
+ //const Float domega_n = dot(-n, domega); | |
+ //const Float domega_n = -dot(n, domega); | |
- // Normal component of the total displacement | |
- const Float omega_n = omega_t0_n + domega_n; | |
+ // Normal component of the total rotation | |
+ const Float omega_n = omega0_n + domega_n; | |
- // Tangential component of the displacement increment | |
- //const Float3 domega_t = domega - dot(domega, n); | |
- const Float3 domega_t = domega - n * dot(n, domega); | |
+ // Tangential component of the rotational increment | |
+ //const Float3 domega_t = domega - (-n) * dot(domega, -n); | |
+ const Float3 domega_t = domega - domega_n * (-n); | |
+ //const Float3 domega_t = domega - n * dot(n, domega); | |
- // Tangential component of the total displacement | |
- const Float3 omega_t = omega_t0 + domega_t; | |
+ // Tangential component of the total rotation | |
+ const Float3 omega_t = omega0_t + domega_t; | |
// Twisting torque: Visco-elastic contact model | |
- t_n = -devC_params.k_t * J * omega_n * n; | |
+ //const Float3 t_n = -devC_params.k_t * J * omega_n * n; | |
+ const Float3 t_n = -devC_params.k_t * J * omega_n * -n; | |
+ //t_n = devC_params.k_t * J * omega_n * n; | |
//t_n = (devC_params.k_t * J * omega_n + devC_params.gamma_t * domega_n/de… | |
// Bending torque: Visco-elastic contact model | |
//t_t = -devC_params.k_n * I * omega_t; | |
+ //const Float3 t_t = devC_params.k_n * I * omega_t; | |
+ const Float3 t_t = -devC_params.k_n * I * omega_t; | |
//t_t = -devC_params.k_n * I * omega_t - devC_params.gamma_n * domega_t/de… | |
- t_t = devC_params.k_n * I * omega_t - devC_params.gamma_n * domega_t/devC_… | |
+ //t_t = devC_params.k_n * I * omega_t - devC_params.gamma_n * domega_t/dev… | |
// Torque vector | |
- t = t_n + t_t; | |
- | |
+ //t = t_n + t_t; | |
+ //Float3 t_i = t_n + cross(-(x_i.w + overlap*0.5) * n, t_t); | |
+ //Float3 t_j = t_n + cross(-(x_j.w + overlap*0.5) * n, t_t); | |
+ //const Float3 t_i = t_n + cross(-(x_i.w + overlap*0.5) * n, f_t + t_t); | |
+ //const Float3 t_j = t_n + cross(-(x_j.w + overlap*0.5) * n, f_t - t_t); | |
+ const Float3 t_j = t_n + t_t; | |
+ //const Float3 t_i = t_n - t_t; //t_n - t_t; | |
+ //const Float3 t_j = t_n + t_t; | |
//// Save values | |
__syncthreads(); | |
t@@ -186,8 +201,14 @@ __global__ void bondsLinear( | |
// Save forces and torques to the particle pairs | |
dev_force[bond.x] += MAKE_FLOAT4(f.x, f.y, f.z, 0.0); | |
dev_force[bond.y] -= MAKE_FLOAT4(f.x, f.y, f.z, 0.0); | |
- dev_torque[bond.x] += MAKE_FLOAT4(t.x, t.y, t.z, 0.0); | |
- dev_torque[bond.y] -= MAKE_FLOAT4(t.x, t.y, t.z, 0.0); | |
+ //dev_torque[bond.x] += MAKE_FLOAT4(t.x, t.y, t.z, 0.0); | |
+ //dev_torque[bond.y] += MAKE_FLOAT4(t.x, t.y, t.z, 0.0); | |
+ //dev_torque[bond.x] += MAKE_FLOAT4(t_i.x, t_i.y, t_i.z, 0.0); | |
+ dev_torque[bond.x] -= MAKE_FLOAT4(t_j.x, t_j.y, t_j.z, 0.0); | |
+ dev_torque[bond.y] += MAKE_FLOAT4(t_j.x, t_j.y, t_j.z, 0.0); | |
+ //dev_torque[bond.y] += MAKE_FLOAT4(t_j.x, t_j.y, t_j.z, 0.0); | |
+ //dev_torque[bond.y] -= MAKE_FLOAT4(t_j.x, t_j.y, t_j.z, 0.0); | |
+ //dev_torque[bond.y] -= MAKE_FLOAT4(t.x, t.y, t.z, 0.0); | |
// make sure to remove write conflicts | |
} | |
diff --git a/src/device.cu b/src/device.cu | |
t@@ -800,6 +800,13 @@ __host__ void DEM::startTime() | |
stopTimer(&kernel_tic, &kernel_toc, &kernel_elapsed, &t_integrateW… | |
checkForCudaErrors("Post integrateWalls"); | |
+ /*for (int a=0; a<params.nb0; ++a) | |
+ std::cout << "bond " << a << ":\n" | |
+ << k.bonds_delta[a].x << ", " | |
+ << k.bonds_delta[a].y << ", " | |
+ << k.bonds_delta[a].z << ", " | |
+ << k.bonds_delta[a].w << std::endl; | |
+ break;*/ | |
// Update timers and counters | |
time.current += time.dt; | |
diff --git a/src/sphere.cpp b/src/sphere.cpp | |
t@@ -627,14 +627,17 @@ void DEM::forcechains(const std::string format, const in… | |
cout << "set term epslatex size 8.6 cm, 5.6 cm\n"; | |
cout << "set out 'plots/" << s << "-fc.tex'\n"; | |
} else if (format == "epslatex-color") { | |
- cout << "set term epslatex color size 8.6 cm, 5.6 cm\n"; | |
+ //cout << "set term epslatex color size 12 cm, 8.6 cm\n"; | |
+ cout << "set term epsla color size 8.6 cm, 5.6 cm\n"; | |
cout << "set out 'plots/" << s << "-fc.tex'\n"; | |
} | |
cout << "set xlabel '\\sffamily $x_1$, [m]'\n"; | |
if (threedim == 1) { | |
cout << "set ylabel '\\sffamily $x_2$, [m]'\n" | |
<< "set zlabel '\\sffamily $x_3$, [m]' offset 2\n"; | |
+ //<< "set zlabel '\\sffamily $x_3$, [m]' offset 0\n"; | |
} else | |
+ //cout << "set ylabel '\\sffamily $x_3$, [m]' offset 0\n"; | |
cout << "set ylabel '\\sffamily $x_3$, [m]' offset 2\n"; | |
cout << "set cblabel '\\sffamily $||\\boldsymbol{f}_n||$, [N]'\n" | |
diff --git a/tests/bond_tests.py b/tests/bond_tests.py | |
t@@ -27,7 +27,7 @@ s2_1 = numpy.ones((2,1))*smallval | |
# Inter-particle distances to try (neg. for overlap) | |
distances = [0.2, 0.0, -0.2] | |
-#distances = [-0.2] | |
+#distances = [0.2] | |
for d in distances: | |
t@@ -39,7 +39,6 @@ for d in distances: | |
# setup particles, bond, and simulation | |
sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
- #sb.x[1,:] = numpy.array((2.2, 2.0, 2.0)) | |
sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.radius = numpy.ones(sb.np)*radii | |
sb.initGridAndWorldsize(margin = 10, periodic = 1, contactmodel = 2, g = n… | |
t@@ -51,6 +50,8 @@ for d in distances: | |
#visualize(sb.sid, "energy") | |
print("# Stability test") | |
+ sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
+ sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.zeroKinematics() | |
sb.initTemporal(total=0.2, file_dt=0.01) | |
#sb.initTemporal(total=0.01, file_dt=0.0001) | |
t@@ -67,9 +68,10 @@ for d in distances: | |
#printKinematics(sb) | |
print("# Normal expansion") | |
+ sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
+ sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.zeroKinematics() | |
- #sb.initTemporal(total=0.2, file_dt=0.01) | |
- sb.initTemporal(total=0.2, file_dt=0.001) | |
+ sb.initTemporal(total=0.2, file_dt=0.01) | |
sb.vel[1,0] = 1e-4 | |
Ekinrot0 = sb.energy("kin") + sb.energy("rot") | |
sb.writebin(verbose=False) | |
t@@ -105,6 +107,8 @@ for d in distances: | |
#printKinematics(sb) | |
print("# Shear") | |
+ sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
+ sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.zeroKinematics() | |
sb.initTemporal(total=0.2, file_dt=0.01) | |
sb.vel[1,2] = 1e-4 | |
t@@ -135,53 +139,54 @@ for d in distances: | |
#visualize(sb.sid, "energy") | |
- print("# Bend") | |
+ #''' | |
+ print("# Twist") | |
+ sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
+ sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.zeroKinematics() | |
sb.initTemporal(total=0.2, file_dt=0.01) | |
- sb.angvel[1,1] = 1e-4 | |
+ #sb.initTemporal(total=0.001, file_dt=0.00001) | |
+ sb.angvel[1,0] = 1e-4 | |
Ekinrot0 = sb.energy("kin") + sb.energy("rot") | |
sb.writebin(verbose=False) | |
sb.run(verbose=False) | |
sb.readlast(verbose=False) | |
compareFloats(Ekinrot0, sb.energy("kin") + sb.energy("rot") + sb.energy("b… | |
- print("vel[:,0]"), | |
- if (sb.vel[0,0] <= 0.0) or (sb.vel[1,0] >= 0.0): | |
- print(failed()) | |
- else : | |
- print(passed()) | |
- compareNumpyArrays(sb.vel[:,1], z2_1, "vel[:,1]") | |
- print("vel[:,2]"), | |
- if ((sb.vel[0,2] <= 0.0) or (sb.vel[1,2] >= 0.0)): | |
- print(failed()) | |
- else : | |
- print(passed()) | |
- compareNumpyArrays(sb.angvel[:,0:2:2], z2_2, "angvel[:,0:2:2]") | |
- print("angvel[:,1]"), | |
- if ((sb.angvel[0,1] <= 0.0) or (sb.angvel[1,1] <= 0.0)): | |
+ #compareNumpyArrays(sb.vel, z2_3, "vel\t") | |
+ print("angvel[:,0]"), | |
+ if ((sb.angvel[0,0] <= 0.0) or (sb.angvel[1,0] <= 0.0)): | |
+ raise Exception("Failed") | |
print(failed()) | |
else : | |
print(passed()) | |
+ compareNumpyArrays(sb.angvel[:,1:2], z2_2, "angvel[:,1:2]") | |
#printKinematics(sb) | |
#visualize(sb.sid, "energy") | |
+ | |
- | |
- print("# Twist") | |
+ #''' | |
+ print("# Bend") | |
+ sb.x[0,:] = numpy.array((2.0, 2.0, 2.0)) | |
+ sb.x[1,:] = numpy.array((2.0+2.0*radii+d, 2.0, 2.0)) | |
sb.zeroKinematics() | |
sb.initTemporal(total=0.2, file_dt=0.01) | |
- sb.angvel[1,0] = 1e-4 | |
+ sb.angvel[0,1] = -1e-4 | |
+ sb.angvel[1,1] = 1e-4 | |
Ekinrot0 = sb.energy("kin") + sb.energy("rot") | |
sb.writebin(verbose=False) | |
sb.run(verbose=False) | |
sb.readlast(verbose=False) | |
compareFloats(Ekinrot0, sb.energy("kin") + sb.energy("rot") + sb.energy("b… | |
- compareNumpyArrays(sb.vel, z2_3, "vel\t") | |
+ #compareNumpyArrays(sb.vel, z2_3, "vel\t") | |
+ #compareNumpyArrays(sb.angvel[:,0:2:2], z2_2, "angvel[:,0:2:2]") | |
print("angvel[:,1]"), | |
- if ((sb.angvel[0,1] <= 0.0) or (sb.angvel[0,1] <= 0.0)): | |
+ if ((sb.angvel[0,1] == 0.0) or (sb.angvel[1,1] == 0.0)): | |
+ raise Exception("Failed") | |
print(failed()) | |
else : | |
print(passed()) | |
- compareNumpyArrays(sb.angvel[:,0:2:2], z2_2, "angvel[:,0:2:2]") | |
- printKinematics(sb) | |
- visualize(sb.sid, "energy") | |
+ #printKinematics(sb) | |
+ #visualize(sb.sid, "energy") | |
+ #''' | |
-#cleanup(sb) | |
+cleanup(sb) | |
diff --git a/tests/pytestutils.py b/tests/pytestutils.py | |
t@@ -2,11 +2,13 @@ | |
from sphere import * | |
import subprocess | |
+import sys | |
def passed(): | |
return "\tPassed" | |
def failed(): | |
+ raise Exception("Failed") | |
return "\tFailed" | |
def compare(first, second, string): | |
t@@ -20,6 +22,16 @@ def compareFloats(first, second, string, criterion=1e-5): | |
print(string + passed()) | |
else : | |
print(string + failed()) | |
+ print("First: " + str(first)) | |
+ print("Second: " + str(second)) | |
+ print("Difference: " + str(second-first)) | |
+ | |
+def compareNumpyArrays(first, second, string): | |
+ if ((first == second).all()): | |
+ print(string + passed()) | |
+ else : | |
+ print(string + failed()) | |
+ | |
def cleanup(spherebin): | |
'Remove temporary files' |