7 #ifndef OPENMPCD_CUDA_MPCSOLUTE_IMPLEMENTATIONDETAILS_STARPOLYMERS_IMPLEMENTATION_HPP
8 #define OPENMPCD_CUDA_MPCSOLUTE_IMPLEMENTATIONDETAILS_STARPOLYMERS_IMPLEMENTATION_HPP
22 namespace ImplementationDetails
24 namespace StarPolymers
30 const std::size_t armCountPerStar,
31 const std::size_t particleCountPerArm,
32 const bool hasMagneticParticles)
37 armCountPerStar * (particleCountPerArm + hasMagneticParticles);
43 const std::size_t starCount,
44 const std::size_t armCountPerStar,
45 const std::size_t particleCountPerArm,
46 const bool hasMagneticParticles)
49 armCountPerStar, particleCountPerArm, hasMagneticParticles);
51 return starCount * particleCountPerStar;
57 const std::size_t particleID,
58 const std::size_t starCount,
59 const std::size_t armCountPerStar,
60 const std::size_t particleCountPerArm,
61 const bool hasMagneticParticles,
62 std::size_t*
const starID,
63 bool*
const isCoreParticle,
64 std::size_t*
const armID,
65 bool*
const isMagneticParticle,
66 std::size_t*
const particleIDInArm)
82 starCount, armCountPerStar, particleCountPerArm,
83 hasMagneticParticles),
86 const std::size_t particleCountPerStar =
88 armCountPerStar, particleCountPerArm, hasMagneticParticles);
90 *starID = particleID / particleCountPerStar;
91 const std::size_t particleIDWithinStar = particleID % particleCountPerStar;
93 if(particleIDWithinStar == 0)
95 *isCoreParticle =
true;
96 *isMagneticParticle =
false;
100 *isCoreParticle =
false;
102 const std::size_t particleCountPerExtendedArm =
103 particleCountPerArm + hasMagneticParticles;
105 *armID = (particleIDWithinStar - 1) / particleCountPerExtendedArm;
106 *particleIDInArm = (particleIDWithinStar - 1) % particleCountPerExtendedArm;
107 *isMagneticParticle = *particleIDInArm == particleCountPerArm;
113 const std::size_t particleID,
114 const std::size_t starCount,
115 const std::size_t armCountPerStar,
116 const std::size_t particleCountPerArm,
117 const bool hasMagneticParticles)
119 std::size_t starID, armID, particleIDInArm;
120 bool isCoreParticle, isMagneticParticle;
124 starCount, armCountPerStar, particleCountPerArm, hasMagneticParticles,
125 &starID, &isCoreParticle, &armID, &isMagneticParticle,
131 if(isMagneticParticle)
140 const std::size_t particleID1,
141 const std::size_t particleID2,
142 const std::size_t starCount,
143 const std::size_t armCountPerStar,
144 const std::size_t particleCountPerArm,
145 const bool hasMagneticParticles)
148 particleID1 != particleID2,
151 std::size_t starID1, armID1, particleIDInArm1;
152 bool isCoreParticle1, isMagneticParticle1;
154 std::size_t starID2, armID2, particleIDInArm2;
155 bool isCoreParticle2, isMagneticParticle2;
159 starCount, armCountPerStar, particleCountPerArm, hasMagneticParticles,
160 &starID1, &isCoreParticle1, &armID1, &isMagneticParticle1,
165 starCount, armCountPerStar, particleCountPerArm, hasMagneticParticles,
166 &starID2, &isCoreParticle2, &armID2, &isMagneticParticle2,
169 if(starID1 != starID2)
172 #ifdef OPENMPCD_COMPILER_GCC
173 #pragma GCC diagnostic push
174 #pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
177 return particleIDInArm2 == 0;
179 return particleIDInArm1 == 0;
180 #ifdef OPENMPCD_COMPILER_GCC
181 #pragma GCC diagnostic pop
187 if(particleIDInArm1 + 1 == particleIDInArm2)
189 if(particleIDInArm2 + 1 == particleIDInArm1)
200 #ifndef __CUDA_ARCH__
205 const std::size_t lower =
206 min(
static_cast<std::size_t
>(type1),
static_cast<std::size_t
>(type2));
207 const std::size_t upper =
208 max(
static_cast<std::size_t
>(type1),
static_cast<std::size_t
>(type2));
211 const std::size_t tmp = (upper << 1) + lower;
252 const T epsilon_core,
const T epsilon_arm,
const T epsilon_magnetic,
253 const T sigma_core,
const T sigma_arm,
const T sigma_magnetic,
254 const T D_core,
const T D_arm,
const T D_magnetic,
255 const T magneticPrefactor,
const Vector3D<T> dipoleOrientation,
260 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>**
const
272 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>
275 const std::size_t indexCC =
278 const std::size_t indexCA =
281 const std::size_t indexCM =
284 const std::size_t indexAA =
287 const std::size_t indexAM =
290 const std::size_t indexMM =
295 const T epsilon_CC = epsilon_core;
296 const T epsilon_CA =
sqrt(epsilon_core * epsilon_arm);
297 const T epsilon_CM =
sqrt(epsilon_core * epsilon_magnetic);
298 const T epsilon_AA = epsilon_arm;
299 const T epsilon_AM =
sqrt(epsilon_arm * epsilon_magnetic);
300 const T epsilon_MM = epsilon_magnetic;
302 const T sigma_CC = sigma_core;
303 const T sigma_CA = 0.5 * (sigma_core + sigma_arm);
304 const T sigma_CM = 0.5 * (sigma_core + sigma_magnetic);
305 const T sigma_AA = sigma_arm;
306 const T sigma_AM = 0.5 * (sigma_arm + sigma_magnetic);
307 const T sigma_MM = sigma_magnetic;
309 const T D_CC = D_core;
310 const T D_CA = 0.5 * (D_core + D_arm);
311 const T D_CM = 0.5 * (D_core + D_magnetic);
312 const T D_AA = D_arm;
313 const T D_AM = 0.5 * (D_arm + D_magnetic);
314 const T D_MM = D_magnetic;
316 WCAPotentials[indexCC] =
new WCA(epsilon_CC, sigma_CC, D_CC);
317 WCAPotentials[indexCA] =
new WCA(epsilon_CA, sigma_CA, D_CA);
318 WCAPotentials[indexCM] =
new WCA(epsilon_CM, sigma_CM, D_CM);
319 WCAPotentials[indexAA] =
new WCA(epsilon_AA, sigma_AA, D_AA);
320 WCAPotentials[indexAM] =
new WCA(epsilon_AM, sigma_AM, D_AM);
321 WCAPotentials[indexMM] =
new WCA(epsilon_MM, sigma_MM, D_MM);
323 const T l_0_CA = D_CA;
324 const T l_0_AA = D_AA;
325 const T l_0_AM = D_AM;
327 const T R_CA = 1.5 * sigma_CA;
328 const T R_AA = 1.5 * sigma_AA;
329 const T R_AM = 1.5 * sigma_AM;
331 const T K_CA = 30 * epsilon_CA / (sigma_CA * sigma_CA);
332 const T K_AA = 30 * epsilon_AA / (sigma_AA * sigma_AA);
333 const T K_AM = 30 * epsilon_AM / (sigma_AM * sigma_AM);
335 FENEPotentials[indexCA] =
new FENE(K_CA, l_0_CA, R_CA);
336 FENEPotentials[indexAA] =
new FENE(K_AA, l_0_AA, R_AA);
337 FENEPotentials[indexAM] =
new FENE(K_AM, l_0_AM, R_AM);
339 #ifdef OPENMPCD_DEBUG
340 FENEPotentials[indexCC] = NULL;
341 FENEPotentials[indexCM] = NULL;
342 FENEPotentials[indexMM] = NULL;
345 *magneticPotential =
new Magnetic(magneticPrefactor, dipoleOrientation);
350 const T epsilon_core,
const T epsilon_arm,
const T epsilon_magnetic,
351 const T sigma_core,
const T sigma_arm,
const T sigma_magnetic,
352 const T D_core,
const T D_arm,
const T D_magnetic,
353 const T magneticPrefactor,
const Vector3D<T> dipoleOrientation,
358 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>***
const
370 createInteractionsOnDevice_kernel<<<1, 1>>>(
371 epsilon_core, epsilon_arm, epsilon_magnetic,
372 sigma_core, sigma_arm, sigma_magnetic,
373 D_core, D_arm, D_magnetic,
374 magneticPrefactor, dipoleOrientation,
375 *WCAPotentials, *FENEPotentials, *magneticPotential
397 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>**
const
405 for(std::size_t i = 0; i < 6; ++i)
409 delete WCAPotentials[i];
412 const std::size_t indexCA =
415 const std::size_t indexAA =
418 const std::size_t indexAM =
426 #ifdef OPENMPCD_DEBUG
427 const std::size_t indexCC =
430 const std::size_t indexCM =
433 const std::size_t indexMM =
442 delete FENEPotentials[indexCA];
443 delete FENEPotentials[indexAA];
444 delete FENEPotentials[indexAM];
446 delete *magneticPotential;
455 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>**
const
459 destroyInteractionsOnDevice_kernel<<<1, 1>>>(
460 WCAPotentials, FENEPotentials, magneticPotential);
472 const std::size_t particleID1,
473 const std::size_t particleID2,
476 const std::size_t starCount,
477 const std::size_t armCountPerStar,
478 const std::size_t particleCountPerArm,
479 const bool hasMagneticParticles,
484 MagneticDipoleDipoleInteraction_ConstantIdenticalDipoles<T>**
const
492 starCount, armCountPerStar, particleCountPerArm,
493 hasMagneticParticles);
498 starCount, armCountPerStar, particleCountPerArm,
499 hasMagneticParticles);
501 const std::size_t particleTypeCombinationIndex =
505 WCAPotentials[particleTypeCombinationIndex]->
506 forceOnR1DueToR2(position1, position2);
515 magneticPotential[0]->forceOnR1DueToR2(position1, position2);
516 return forceOnParticle1;
521 particleID1, particleID2,
522 starCount, armCountPerStar, particleCountPerArm,
523 hasMagneticParticles);
526 return forceOnParticle1;
529 FENEPotentials[particleTypeCombinationIndex]->
530 forceOnR1DueToR2(position1, position2);
532 return forceOnParticle1;
541 #endif //OPENMPCD_CUDA_MPCSOLUTE_IMPLEMENTATIONDETAILS_STARPOLYMERS_IMPLEMENTATION_HPP