yade-dev team mailing list archive
-
yade-dev team
-
Mailing list archive
-
Message #12575
[Branch ~yade-pkg/yade/git-trunk] Rev 3810: Split implementation of ForceContainer in parallel and serial.
------------------------------------------------------------
revno: 3810
committer: Anton Gladky <gladky.anton@xxxxxxxxx>
timestamp: Tue 2016-03-22 22:43:26 +0100
message:
Split implementation of ForceContainer in parallel and serial.
Add ForceContainerSerial.cpp and ForceContainerParallel.cpp,
ForceContainer.hpp is now common for both of them.
removed:
core/ForceContainer.cpp
added:
core/ForceContainerParallel.cpp
core/ForceContainerSerial.cpp
modified:
core/ForceContainer.hpp
--
lp:yade
https://code.launchpad.net/~yade-pkg/yade/git-trunk
Your team Yade developers is subscribed to branch lp:yade.
To unsubscribe from this branch go to https://code.launchpad.net/~yade-pkg/yade/git-trunk/+edit-subscription
=== removed file 'core/ForceContainer.cpp'
--- core/ForceContainer.cpp 2016-03-22 21:43:09 +0000
+++ core/ForceContainer.cpp 1970-01-01 00:00:00 +0000
@@ -1,410 +0,0 @@
-#include <core/ForceContainer.hpp>
-
-#ifdef YADE_OPENMP
-#include <omp.h>
-inline void ForceContainer::ensureSize(Body::id_t id, int threadN) {
- assert(nThreads>omp_get_thread_num());
- const Body::id_t idMaxTmp = max(id, _maxId[threadN]);
- _maxId[threadN] = 0;
- if (threadN<0) {
- resizePerm(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)));
- } else if (sizeOfThreads[threadN]<=(size_t)idMaxTmp) {
- resize(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)),threadN);
- }
-}
-
-inline void ForceContainer::ensureSynced() {
- if(!synced) throw runtime_error("ForceContainer not thread-synchronized; call sync() first!");
-}
-
-ForceContainer::ForceContainer() {
- nThreads=omp_get_max_threads();
- for(int i=0; i<nThreads; i++){
- _forceData.push_back(vvector()); _torqueData.push_back(vvector());
- _moveData.push_back(vvector()); _rotData.push_back(vvector());
- sizeOfThreads.push_back(0);
- _maxId.push_back(0);
- }
-}
-
-const Vector3r& ForceContainer::getForce(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_force[id]:_zero;
-}
-
-void ForceContainer::addForce(Body::id_t id, const Vector3r& f){
- ensureSize(id,omp_get_thread_num());
- synced=false;
- _forceData[omp_get_thread_num()][id]+=f;
-}
-
-const Vector3r& ForceContainer::getTorque(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_torque[id]:_zero;
-}
-
-void ForceContainer::addTorque(Body::id_t id, const Vector3r& t) {
- ensureSize(id,omp_get_thread_num());
- synced=false;
- _torqueData[omp_get_thread_num()][id]+=t;
-}
-
-const Vector3r& ForceContainer::getMove(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_move[id]:_zero;
-}
-
-void ForceContainer::addMove(Body::id_t id, const Vector3r& m) {
- ensureSize(id,omp_get_thread_num());
- synced=false;
- moveRotUsed=true;
- _moveData[omp_get_thread_num()][id]+=m;
-}
-
-const Vector3r& ForceContainer::getRot(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_rot[id]:_zero;
-}
-
-void ForceContainer::addRot(Body::id_t id, const Vector3r& r) {
- ensureSize(id,omp_get_thread_num());
- synced=false;
- moveRotUsed=true;
- _rotData[omp_get_thread_num()][id]+=r;
-}
-
-void ForceContainer::addMaxId(Body::id_t id) {
- _maxId[omp_get_thread_num()]=id;
-}
-
-void ForceContainer::setPermForce(Body::id_t id, const Vector3r& f) {
- ensureSize(id,-1);
- synced=false;
- _permForce[id]=f;
- permForceUsed=true;
-}
-
-void ForceContainer::setPermTorque(Body::id_t id, const Vector3r& t) {
- ensureSize(id,-1);
- synced=false;
- _permTorque[id]=t;
- permForceUsed=true;
-}
-
-const Vector3r& ForceContainer::getPermForce(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_permForce[id]:_zero;
-}
-
-const Vector3r& ForceContainer::getPermTorque(Body::id_t id) {
- ensureSynced();
- return ((size_t)id<size)?_permTorque[id]:_zero;
-}
-
-const Vector3r& ForceContainer::getForceUnsynced(Body::id_t id) {
- assert ((size_t)id<size);
- return _force[id];
-}
-
-const Vector3r& ForceContainer::getTorqueUnsynced(Body::id_t id) {
- assert ((size_t)id<size);
- return _torque[id];
-}
-
-void ForceContainer::addForceUnsynced(Body::id_t id, const Vector3r& f) {
- assert ((size_t)id<size);
- _force[id]+=f;
-}
-
-void ForceContainer::addTorqueUnsynced(Body::id_t id, const Vector3r& m) {
- assert ((size_t)id<size);
- _torque[id]+=m;
-}
-
-Vector3r ForceContainer::getForceSingle(Body::id_t id) {
- Vector3r ret(Vector3r::Zero());
- for(int t=0; t<nThreads; t++) {
- ret+=((size_t)id<sizeOfThreads[t])?_forceData [t][id]:_zero;
- }
- if (permForceUsed) ret+=_permForce[id];
- return ret;
-}
-
-Vector3r ForceContainer::getTorqueSingle(Body::id_t id) {
- Vector3r ret(Vector3r::Zero());
- for(int t=0; t<nThreads; t++) {
- ret+=((size_t)id<sizeOfThreads[t])?_torqueData[t][id]:_zero;
- }
- if (permForceUsed) ret+=_permTorque[id];
- return ret;
-}
-
-Vector3r ForceContainer::getMoveSingle(Body::id_t id) {
- Vector3r ret(Vector3r::Zero());
- for(int t=0; t<nThreads; t++) {
- ret+=((size_t)id<sizeOfThreads[t])?_moveData[t][id]:_zero;
- }
- return ret;
-}
-
-Vector3r ForceContainer::getRotSingle(Body::id_t id) {
- Vector3r ret(Vector3r::Zero());
- for(int t=0; t<nThreads; t++) {
- ret+=((size_t)id<sizeOfThreads[t])?_rotData[t][id]:_zero;
- }
- return ret;
-}
-
-void ForceContainer::syncSizesOfContainers() {
- if (syncedSizes) return;
- //check whether all containers have equal length, and if not resize it
- for(int i=0; i<nThreads; i++){
- if (sizeOfThreads[i]<size) resize(size,i);
- }
- _force.resize(size,Vector3r::Zero());
- _torque.resize(size,Vector3r::Zero());
- _permForce.resize(size,Vector3r::Zero());
- _permTorque.resize(size,Vector3r::Zero());
- _move.resize(size,Vector3r::Zero());
- _rot.resize(size,Vector3r::Zero());
- syncedSizes=true;
-}
-
-void ForceContainer::sync(){
- for(int i=0; i<nThreads; i++){
- if (_maxId[i] > 0) { synced = false;}
- }
- if(synced) return;
- boost::mutex::scoped_lock lock(globalMutex);
- if(synced) return; // if synced meanwhile
-
- for(int i=0; i<nThreads; i++){
- if (_maxId[i] > 0) { ensureSize(_maxId[i],i);}
- }
-
- syncSizesOfContainers();
-
- for(long id=0; id<(long)size; id++){
- Vector3r sumF(Vector3r::Zero()), sumT(Vector3r::Zero());
- for(int thread=0; thread<nThreads; thread++){ sumF+=_forceData[thread][id]; sumT+=_torqueData[thread][id];}
- _force[id]=sumF; _torque[id]=sumT;
- if (permForceUsed) {_force[id]+=_permForce[id]; _torque[id]+=_permTorque[id];}
- }
- if(moveRotUsed){
- for(long id=0; id<(long)size; id++){
- Vector3r sumM(Vector3r::Zero()), sumR(Vector3r::Zero());
- for(int thread=0; thread<nThreads; thread++){ sumM+=_moveData[thread][id]; sumR+=_rotData[thread][id];}
- _move[id]=sumM; _rot[id]=sumR;
- }
- }
- synced=true; syncCount++;
-}
-
-void ForceContainer::resize(size_t newSize, int threadN) {
- _forceData [threadN].resize(newSize,Vector3r::Zero());
- _torqueData[threadN].resize(newSize,Vector3r::Zero());
- _moveData[threadN].resize(newSize,Vector3r::Zero());
- _rotData[threadN].resize(newSize,Vector3r::Zero());
- sizeOfThreads[threadN] = newSize;
- if (size<newSize) size=newSize;
- syncedSizes=false;
-}
-
-void ForceContainer::resizePerm(size_t newSize) {
- _permForce.resize(newSize,Vector3r::Zero());
- _permTorque.resize(newSize,Vector3r::Zero());
- if (size<newSize) size=newSize;
- syncedSizes=false;
-}
-
-void ForceContainer::reset(long iter, bool resetAll) {
- syncSizesOfContainers();
- for(int thread=0; thread<nThreads; thread++){
- memset(&_forceData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
- memset(&_torqueData[thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
- if(moveRotUsed){
- memset(&_moveData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
- memset(&_rotData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
- }
- }
- memset(&_force [0], 0,sizeof(Vector3r)*size);
- memset(&_torque[0], 0,sizeof(Vector3r)*size);
- if(moveRotUsed){
- memset(&_move [0], 0,sizeof(Vector3r)*size);
- memset(&_rot [0], 0,sizeof(Vector3r)*size);
- }
- if (resetAll){
- memset(&_permForce [0], 0,sizeof(Vector3r)*size);
- memset(&_permTorque[0], 0,sizeof(Vector3r)*size);
- permForceUsed = false;
- }
- if (!permForceUsed) synced=true; else synced=false;
- moveRotUsed=false;
- lastReset=iter;
-}
-
-const int& ForceContainer::getNumAllocatedThreads() {
- return nThreads;
-}
-
-const bool& ForceContainer::getMoveRotUsed() {
- return moveRotUsed;
-}
-
-const bool& ForceContainer::getPermForceUsed() {
- return permForceUsed;
-}
-
-#else
-void ForceContainer::ensureSize(Body::id_t id) {
- const Body::id_t idMaxTmp = max(id, _maxId);
- _maxId = 0;
- if(size<=(size_t)idMaxTmp) resize(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)));
-}
-
-const Vector3r& ForceContainer::getForceUnsynced (Body::id_t id) {
- return getForce(id);
-}
-
-const Vector3r& ForceContainer::getTorqueUnsynced(Body::id_t id) {
- return getForce(id);
-}
-
-const Vector3r& ForceContainer::getForce(Body::id_t id) {
- ensureSize(id);
- return _force[id];
-}
-
-void ForceContainer::addForce(Body::id_t id,const Vector3r& f) {
- ensureSize(id);
- _force[id]+=f;
-}
-
-const Vector3r& ForceContainer::getTorque(Body::id_t id) {
- ensureSize(id);
- return _torque[id];
-}
-
-void ForceContainer::addTorque(Body::id_t id,const Vector3r& t) {
- ensureSize(id);
- _torque[id]+=t;
-}
-
-const Vector3r& ForceContainer::getMove(Body::id_t id) {
- ensureSize(id);
- return _move[id];
-}
-
-void ForceContainer::addMove(Body::id_t id,const Vector3r& f) {
- ensureSize(id);
- moveRotUsed=true;
- _move[id]+=f;
-}
-
-const Vector3r& ForceContainer::getRot(Body::id_t id) {
- ensureSize(id);
- return _rot[id];
-}
-
-void ForceContainer::addRot(Body::id_t id,const Vector3r& f) {
- ensureSize(id);
- moveRotUsed=true;
- _rot[id]+=f;
-}
-
-void ForceContainer::setPermForce(Body::id_t id, const Vector3r& f) {
- ensureSize(id);
- _permForce[id]=f;
- permForceUsed=true;
-}
-
-void ForceContainer::setPermTorque(Body::id_t id, const Vector3r& t) {
- ensureSize(id);
- _permTorque[id]=t;
- permForceUsed=true;
-}
-
-void ForceContainer::addMaxId(Body::id_t id) {
- _maxId=id;
-}
-
-const Vector3r& ForceContainer::getPermForce(Body::id_t id) {
- ensureSize(id);
- return _permForce[id];
-}
-
-const Vector3r& ForceContainer::getPermTorque(Body::id_t id) {
- ensureSize(id);
- return _permTorque[id];
-}
-
-const Vector3r ForceContainer::getForceSingle (Body::id_t id) {
- ensureSize(id);
- if (permForceUsed) {
- return _force [id] + _permForce[id];
- } else {
- return _force [id];
- }
-}
-const Vector3r ForceContainer::getTorqueSingle(Body::id_t id) {
- ensureSize(id);
- if (permForceUsed) {
- return _torque[id] + _permTorque[id];
- } else {
- return _torque[id];
- }
-}
-const Vector3r& ForceContainer::getMoveSingle(Body::id_t id) {
- ensureSize(id);
- return _move [id];
-}
-
-const Vector3r& ForceContainer::getRotSingle(Body::id_t id) {
- ensureSize(id);
- return _rot[id];
-}
-
-void ForceContainer::reset(long iter, bool resetAll) {
- memset(&_force [0],0,sizeof(Vector3r)*size);
- memset(&_torque[0],0,sizeof(Vector3r)*size);
- if(moveRotUsed){
- memset(&_move [0],0,sizeof(Vector3r)*size);
- memset(&_rot [0],0,sizeof(Vector3r)*size);
- moveRotUsed=false;
- }
- if (resetAll){
- memset(&_permForce [0], 0,sizeof(Vector3r)*size);
- memset(&_permTorque[0], 0,sizeof(Vector3r)*size);
- permForceUsed = false;
- }
- lastReset=iter;
-}
-
-void ForceContainer::sync() {
- if (_maxId>0) {
- ensureSize(_maxId);
- _maxId=0;
- }
- if (permForceUsed) {
- for(long id=0; id<(long)size; id++) {
- _force[id]+=_permForce[id];
- _torque[id]+=_permTorque[id];
- }
- }
- return;
-}
-
-void ForceContainer::resize(size_t newSize) {
- _force.resize(newSize,Vector3r::Zero());
- _torque.resize(newSize,Vector3r::Zero());
- _permForce.resize(newSize,Vector3r::Zero());
- _permTorque.resize(newSize,Vector3r::Zero());
- _move.resize(newSize,Vector3r::Zero());
- _rot.resize(newSize,Vector3r::Zero());
- size=newSize;
-}
-
-const int ForceContainer::getNumAllocatedThreads() const {return 1;}
-const bool& ForceContainer::getMoveRotUsed() const {return moveRotUsed;}
-const bool& ForceContainer::getPermForceUsed() const {return permForceUsed;}
-#endif
=== modified file 'core/ForceContainer.hpp'
--- core/ForceContainer.hpp 2016-03-22 21:43:09 +0000
+++ core/ForceContainer.hpp 2016-03-22 21:43:26 +0000
@@ -1,17 +1,18 @@
// 2009 © Václav Šmilauer <eudoxos@xxxxxxxx>
#pragma once
-#include<lib/base/Math.hpp>
-#include<core/Body.hpp>
+#include <lib/base/Math.hpp>
+#include <core/Body.hpp>
-#include<boost/static_assert.hpp>
+#include <boost/static_assert.hpp>
// make sure that (void*)&vec[0]==(void*)&vec
BOOST_STATIC_ASSERT(sizeof(Vector3r)==3*sizeof(Real));
#ifdef YADE_OPENMP
+#include <omp.h>
+#endif
-#include<omp.h>
/*! Container for Body External Variables (forces), typically forces and torques from interactions.
* Values should be reset at every iteration by calling ForceContainer::reset();
* If you want to add your own force type, you need to:
@@ -41,16 +42,22 @@
*/
//! This is the parallel flavor of ForceContainer
-class ForceContainer{
+class ForceContainer {
private:
typedef std::vector<Vector3r> vvector;
+#ifdef YADE_OPENMP
std::vector<vvector> _forceData;
std::vector<vvector> _torqueData;
std::vector<vvector> _moveData;
std::vector<vvector> _rotData;
- std::vector<Body::id_t> _maxId;
+ std::vector<Body::id_t> _maxId;
+ std::vector<size_t> sizeOfThreads;
+ void ensureSize(Body::id_t id, int threadN);
+#else
+ void ensureSize(Body::id_t id);
+ Body::id_t _maxId=0;
+#endif
vvector _force, _torque, _move, _rot, _permForce, _permTorque;
- std::vector<size_t> sizeOfThreads;
size_t size = 0;
bool syncedSizes = true;
int nThreads;
@@ -58,9 +65,9 @@
bool moveRotUsed = false;
bool permForceUsed = false;
boost::mutex globalMutex;
- Vector3r _zero = Vector3r::Zero();
+ const Vector3r _zero = Vector3r::Zero();
- void ensureSize(Body::id_t id, int threadN);
+
void ensureSynced();
// dummy function to avoid template resolution failure
@@ -96,82 +103,29 @@
/* To be benchmarked: sum thread data in getForce/getTorque upon request for each body individually instead of by the sync() function globally */
// this function is used from python so that running simulation is not slowed down by sync'ing on occasions
// since Vector3r writes are not atomic, it might (rarely) return wrong value, if the computation is running meanwhile
- Vector3r getForceSingle (Body::id_t id);
- Vector3r getTorqueSingle(Body::id_t id);
- Vector3r getMoveSingle (Body::id_t id);
- Vector3r getRotSingle (Body::id_t id);
-
+ const Vector3r getForceSingle (Body::id_t id);
+ const Vector3r getTorqueSingle(Body::id_t id);
+ const Vector3r getMoveSingle (Body::id_t id);
+ const Vector3r getRotSingle (Body::id_t id);
+
+#ifdef YADE_OPENMP
void syncSizesOfContainers();
+ void resize(size_t newSize, int threadN);
+#else
+ void resize(size_t newSize);
+#endif
/* Sum contributions from all threads, save to _force&_torque.
* Locks globalMutex, since one thread modifies common data (_force&_torque).
* Must be called before get* methods are used. Exception is thrown otherwise, since data are not consistent. */
void sync();
- void resize(size_t newSize, int threadN);
+
void resizePerm(size_t newSize);
/*! Reset all resetable data, also reset summary forces/torques and mark the container clean.
If resetAll, reset also user defined forces and torques*/
// perhaps should be private and friend Scene or whatever the only caller should be
void reset(long iter, bool resetAll=false);
//! say for how many threads we have allocated space
- const int& getNumAllocatedThreads();
- const bool& getMoveRotUsed();
- const bool& getPermForceUsed();
-};
-
-#else
-//! This is the non-parallel flavor of ForceContainer
-class ForceContainer {
- private:
- std::vector<Vector3r> _force;
- std::vector<Vector3r> _torque;
- std::vector<Vector3r> _move;
- std::vector<Vector3r> _rot;
- std::vector<Vector3r> _permForce;
- std::vector<Vector3r> _permTorque;
- Body::id_t _maxId=0;
- size_t size=0;
- bool moveRotUsed = false;
- bool permForceUsed = false;
- void ensureSize(Body::id_t id);
-
- const Vector3r& getForceUnsynced (Body::id_t id);
- const Vector3r& getTorqueUnsynced(Body::id_t id);
-
- // dummy function to avoid template resolution failure
- friend class boost::serialization::access; template<class ArchiveT> void serialize(ArchiveT & ar, unsigned int version){}
- public:
- unsigned long syncCount = 0;
- long lastReset=0;
- ForceContainer() {}
- const Vector3r& getForce(Body::id_t id);
- void addForce(Body::id_t id,const Vector3r& f);
- const Vector3r& getTorque(Body::id_t id);
- void addTorque(Body::id_t id,const Vector3r& t);
- const Vector3r& getMove(Body::id_t id);
- void addMove(Body::id_t id,const Vector3r& f);
- const Vector3r& getRot(Body::id_t id);
- void addRot(Body::id_t id,const Vector3r& f);
- void setPermForce(Body::id_t id, const Vector3r& f);
- void setPermTorque(Body::id_t id, const Vector3r& t);
- void addMaxId(Body::id_t id);
- const Vector3r& getPermForce(Body::id_t id);
- const Vector3r& getPermTorque(Body::id_t id);
- // single getters do the same as globally synced ones in the non-parallel flavor
- const Vector3r getForceSingle (Body::id_t id);
- const Vector3r getTorqueSingle(Body::id_t id);
- const Vector3r& getMoveSingle (Body::id_t id);
- const Vector3r& getRotSingle (Body::id_t id);
-
- //! Set all forces to zero
- void reset(long iter, bool resetAll=false);
- void sync();
- // interaction in which the container was last reset; used by NewtonIntegrator to detect whether ForceResetter was not forgotten
- /*! Resize the container; this happens automatically,
- * but you may want to set the size beforehand to avoid resizes as the simulation grows. */
- void resize(size_t newSize);
const int getNumAllocatedThreads() const;
- const bool& getMoveRotUsed() const;
- const bool& getPermForceUsed() const;
+ const bool getMoveRotUsed() const;
+ const bool getPermForceUsed() const;
};
-
-#endif
=== added file 'core/ForceContainerParallel.cpp'
--- core/ForceContainerParallel.cpp 1970-01-01 00:00:00 +0000
+++ core/ForceContainerParallel.cpp 2016-03-22 21:43:26 +0000
@@ -0,0 +1,251 @@
+#include <core/ForceContainer.hpp>
+
+void ForceContainer::ensureSynced() {
+ if(!synced) throw runtime_error("ForceContainer not thread-synchronized; call sync() first!");
+}
+
+void ForceContainer::addForceUnsynced(Body::id_t id, const Vector3r& f) {
+ assert ((size_t)id<size);
+ _force[id]+=f;
+}
+
+void ForceContainer::addTorqueUnsynced(Body::id_t id, const Vector3r& m) {
+ assert ((size_t)id<size);
+ _torque[id]+=m;
+}
+
+void ForceContainer::resizePerm(size_t newSize) {
+ _permForce.resize(newSize,Vector3r::Zero());
+ _permTorque.resize(newSize,Vector3r::Zero());
+ if (size<newSize) size=newSize;
+ syncedSizes=false;
+}
+
+#ifdef YADE_OPENMP
+#include <omp.h>
+void ForceContainer::ensureSize(Body::id_t id, int threadN) {
+ assert(nThreads>omp_get_thread_num());
+ const Body::id_t idMaxTmp = max(id, _maxId[threadN]);
+ _maxId[threadN] = 0;
+ if (threadN<0) {
+ resizePerm(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)));
+ } else if (sizeOfThreads[threadN]<=(size_t)idMaxTmp) {
+ resize(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)),threadN);
+ }
+}
+
+ForceContainer::ForceContainer() {
+ nThreads=omp_get_max_threads();
+ for(int i=0; i<nThreads; i++){
+ _forceData.push_back(vvector());
+ _torqueData.push_back(vvector());
+ _moveData.push_back(vvector());
+ _rotData.push_back(vvector());
+ sizeOfThreads.push_back(0);
+ _maxId.push_back(0);
+ }
+}
+
+const Vector3r& ForceContainer::getForce(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_force[id]:_zero;
+}
+
+void ForceContainer::addForce(Body::id_t id, const Vector3r& f){
+ ensureSize(id,omp_get_thread_num());
+ synced=false;
+ _forceData[omp_get_thread_num()][id]+=f;
+}
+
+const Vector3r& ForceContainer::getTorque(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_torque[id]:_zero;
+}
+
+void ForceContainer::addTorque(Body::id_t id, const Vector3r& t) {
+ ensureSize(id,omp_get_thread_num());
+ synced=false;
+ _torqueData[omp_get_thread_num()][id]+=t;
+}
+
+const Vector3r& ForceContainer::getMove(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_move[id]:_zero;
+}
+
+void ForceContainer::addMove(Body::id_t id, const Vector3r& m) {
+ ensureSize(id,omp_get_thread_num());
+ synced=false;
+ moveRotUsed=true;
+ _moveData[omp_get_thread_num()][id]+=m;
+}
+
+const Vector3r& ForceContainer::getRot(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_rot[id]:_zero;
+}
+
+void ForceContainer::addRot(Body::id_t id, const Vector3r& r) {
+ ensureSize(id,omp_get_thread_num());
+ synced=false;
+ moveRotUsed=true;
+ _rotData[omp_get_thread_num()][id]+=r;
+}
+
+void ForceContainer::addMaxId(Body::id_t id) {
+ _maxId[omp_get_thread_num()]=id;
+}
+
+void ForceContainer::setPermForce(Body::id_t id, const Vector3r& f) {
+ ensureSize(id,-1);
+ synced=false;
+ _permForce[id]=f;
+ permForceUsed=true;
+}
+
+void ForceContainer::setPermTorque(Body::id_t id, const Vector3r& t) {
+ ensureSize(id,-1);
+ synced=false;
+ _permTorque[id]=t;
+ permForceUsed=true;
+}
+
+const Vector3r& ForceContainer::getPermForce(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_permForce[id]:_zero;
+}
+
+const Vector3r& ForceContainer::getPermTorque(Body::id_t id) {
+ ensureSynced();
+ return ((size_t)id<size)?_permTorque[id]:_zero;
+}
+
+const Vector3r& ForceContainer::getForceUnsynced(Body::id_t id) {
+ assert ((size_t)id<size);
+ return _force[id];
+}
+
+const Vector3r& ForceContainer::getTorqueUnsynced(Body::id_t id) {
+ assert ((size_t)id<size);
+ return _torque[id];
+}
+
+const Vector3r ForceContainer::getForceSingle(Body::id_t id) {
+ Vector3r ret(Vector3r::Zero());
+ for(int t=0; t<nThreads; t++) {
+ ret+=((size_t)id<sizeOfThreads[t])?_forceData [t][id]:_zero;
+ }
+ if (permForceUsed) ret+=_permForce[id];
+ return ret;
+}
+
+const Vector3r ForceContainer::getTorqueSingle(Body::id_t id) {
+ Vector3r ret(Vector3r::Zero());
+ for(int t=0; t<nThreads; t++) {
+ ret+=((size_t)id<sizeOfThreads[t])?_torqueData[t][id]:_zero;
+ }
+ if (permForceUsed) ret+=_permTorque[id];
+ return ret;
+}
+
+const Vector3r ForceContainer::getMoveSingle(Body::id_t id) {
+ Vector3r ret(Vector3r::Zero());
+ for(int t=0; t<nThreads; t++) {
+ ret+=((size_t)id<sizeOfThreads[t])?_moveData[t][id]:_zero;
+ }
+ return ret;
+}
+
+const Vector3r ForceContainer::getRotSingle(Body::id_t id) {
+ Vector3r ret(Vector3r::Zero());
+ for(int t=0; t<nThreads; t++) {
+ ret+=((size_t)id<sizeOfThreads[t])?_rotData[t][id]:_zero;
+ }
+ return ret;
+}
+
+void ForceContainer::sync(){
+ for(int i=0; i<nThreads; i++){
+ if (_maxId[i] > 0) { synced = false;}
+ }
+ if(synced) return;
+ boost::mutex::scoped_lock lock(globalMutex);
+ if(synced) return; // if synced meanwhile
+
+ for(int i=0; i<nThreads; i++){
+ if (_maxId[i] > 0) { ensureSize(_maxId[i],i);}
+ }
+
+ syncSizesOfContainers();
+
+ for(long id=0; id<(long)size; id++){
+ Vector3r sumF(Vector3r::Zero()), sumT(Vector3r::Zero());
+ for(int thread=0; thread<nThreads; thread++){ sumF+=_forceData[thread][id]; sumT+=_torqueData[thread][id];}
+ _force[id]=sumF; _torque[id]=sumT;
+ if (permForceUsed) {_force[id]+=_permForce[id]; _torque[id]+=_permTorque[id];}
+ }
+ if(moveRotUsed){
+ for(long id=0; id<(long)size; id++){
+ Vector3r sumM(Vector3r::Zero()), sumR(Vector3r::Zero());
+ for(int thread=0; thread<nThreads; thread++){ sumM+=_moveData[thread][id]; sumR+=_rotData[thread][id];}
+ _move[id]=sumM; _rot[id]=sumR;
+ }
+ }
+ synced=true; syncCount++;
+}
+
+void ForceContainer::reset(long iter, bool resetAll) {
+ syncSizesOfContainers();
+ for(int thread=0; thread<nThreads; thread++){
+ memset(&_forceData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
+ memset(&_torqueData[thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
+ if(moveRotUsed){
+ memset(&_moveData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
+ memset(&_rotData [thread][0],0,sizeof(Vector3r)*sizeOfThreads[thread]);
+ }
+ }
+ memset(&_force [0], 0,sizeof(Vector3r)*size);
+ memset(&_torque[0], 0,sizeof(Vector3r)*size);
+ if(moveRotUsed){
+ memset(&_move [0], 0,sizeof(Vector3r)*size);
+ memset(&_rot [0], 0,sizeof(Vector3r)*size);
+ }
+ if (resetAll){
+ memset(&_permForce [0], 0,sizeof(Vector3r)*size);
+ memset(&_permTorque[0], 0,sizeof(Vector3r)*size);
+ permForceUsed = false;
+ }
+ if (!permForceUsed) synced=true; else synced=false;
+ moveRotUsed=false;
+ lastReset=iter;
+}
+
+void ForceContainer::resize(size_t newSize, int threadN) {
+ _forceData [threadN].resize(newSize,Vector3r::Zero());
+ _torqueData[threadN].resize(newSize,Vector3r::Zero());
+ _moveData[threadN].resize(newSize,Vector3r::Zero());
+ _rotData[threadN].resize(newSize,Vector3r::Zero());
+ sizeOfThreads[threadN] = newSize;
+ if (size<newSize) size=newSize;
+ syncedSizes=false;
+}
+
+const int ForceContainer::getNumAllocatedThreads() const {return nThreads;}
+const bool ForceContainer::getMoveRotUsed() const {return moveRotUsed;}
+const bool ForceContainer::getPermForceUsed() const {return permForceUsed;}
+
+void ForceContainer::syncSizesOfContainers() {
+ if (syncedSizes) return;
+ //check whether all containers have equal length, and if not resize it
+ for(int i=0; i<nThreads; i++){
+ if (sizeOfThreads[i]<size) resize(size,i);
+ }
+ _force.resize(size,Vector3r::Zero());
+ _torque.resize(size,Vector3r::Zero());
+ _permForce.resize(size,Vector3r::Zero());
+ _permTorque.resize(size,Vector3r::Zero());
+ _move.resize(size,Vector3r::Zero());
+ _rot.resize(size,Vector3r::Zero());
+ syncedSizes=true;
+}
+#endif
=== added file 'core/ForceContainerSerial.cpp'
--- core/ForceContainerSerial.cpp 1970-01-01 00:00:00 +0000
+++ core/ForceContainerSerial.cpp 2016-03-22 21:43:26 +0000
@@ -0,0 +1,157 @@
+#ifndef YADE_OPENMP
+#include <core/ForceContainer.hpp>
+ForceContainer::ForceContainer() {};
+void ForceContainer::ensureSize(Body::id_t id) {
+ const Body::id_t idMaxTmp = max(id, _maxId);
+ _maxId = 0;
+ if(size<=(size_t)idMaxTmp) {
+ resize(min((size_t)1.5*(idMaxTmp+100),(size_t)(idMaxTmp+2000)));
+ };
+}
+
+const Vector3r& ForceContainer::getForce(Body::id_t id) {
+ ensureSize(id);
+ return _force[id];
+}
+
+void ForceContainer::addForce(Body::id_t id,const Vector3r& f) {
+ ensureSize(id);
+ _force[id]+=f;
+}
+
+const Vector3r& ForceContainer::getTorque(Body::id_t id) {
+ ensureSize(id);
+ return _torque[id];
+}
+
+void ForceContainer::addTorque(Body::id_t id,const Vector3r& t) {
+ ensureSize(id);
+ _torque[id]+=t;
+}
+
+const Vector3r& ForceContainer::getMove(Body::id_t id) {
+ ensureSize(id);
+ return _move[id];
+}
+
+void ForceContainer::addMove(Body::id_t id,const Vector3r& f) {
+ ensureSize(id);
+ moveRotUsed=true;
+ _move[id]+=f;
+}
+
+const Vector3r& ForceContainer::getRot(Body::id_t id) {
+ ensureSize(id);
+ return _rot[id];
+}
+
+void ForceContainer::addRot(Body::id_t id,const Vector3r& f) {
+ ensureSize(id);
+ moveRotUsed=true;
+ _rot[id]+=f;
+}
+
+void ForceContainer::addMaxId(Body::id_t id) {
+ _maxId=id;
+}
+
+void ForceContainer::setPermForce(Body::id_t id, const Vector3r& f) {
+ ensureSize(id);
+ _permForce[id]=f;
+ permForceUsed=true;
+}
+
+void ForceContainer::setPermTorque(Body::id_t id, const Vector3r& t) {
+ ensureSize(id);
+ _permTorque[id]=t;
+ permForceUsed=true;
+}
+
+const Vector3r& ForceContainer::getPermForce(Body::id_t id) {
+ ensureSize(id);
+ return _permForce[id];
+}
+
+const Vector3r& ForceContainer::getPermTorque(Body::id_t id) {
+ ensureSize(id);
+ return _permTorque[id];
+}
+
+const Vector3r& ForceContainer::getForceUnsynced (Body::id_t id) {
+ return getForce(id);
+}
+
+const Vector3r& ForceContainer::getTorqueUnsynced(Body::id_t id) {
+ return getForce(id);
+}
+
+const Vector3r ForceContainer::getForceSingle (Body::id_t id) {
+ ensureSize(id);
+ if (permForceUsed) {
+ return _force [id] + _permForce[id];
+ } else {
+ return _force [id];
+ }
+}
+const Vector3r ForceContainer::getTorqueSingle(Body::id_t id) {
+ ensureSize(id);
+ if (permForceUsed) {
+ return _torque[id] + _permTorque[id];
+ } else {
+ return _torque[id];
+ }
+}
+const Vector3r ForceContainer::getMoveSingle(Body::id_t id) {
+ ensureSize(id);
+ return _move [id];
+}
+
+const Vector3r ForceContainer::getRotSingle(Body::id_t id) {
+ ensureSize(id);
+ return _rot[id];
+}
+
+void ForceContainer::sync() {
+ if (_maxId>0) {
+ ensureSize(_maxId);
+ _maxId=0;
+ }
+ if (permForceUsed) {
+ for(long id=0; id<(long)size; id++) {
+ _force[id]+=_permForce[id];
+ _torque[id]+=_permTorque[id];
+ }
+ }
+ return;
+}
+
+void ForceContainer::reset(long iter, bool resetAll) {
+ memset(&_force [0],0,sizeof(Vector3r)*size);
+ memset(&_torque[0],0,sizeof(Vector3r)*size);
+ if(moveRotUsed){
+ memset(&_move [0],0,sizeof(Vector3r)*size);
+ memset(&_rot [0],0,sizeof(Vector3r)*size);
+ moveRotUsed=false;
+ }
+ if (resetAll){
+ memset(&_permForce [0], 0,sizeof(Vector3r)*size);
+ memset(&_permTorque[0], 0,sizeof(Vector3r)*size);
+ permForceUsed = false;
+ }
+ lastReset=iter;
+}
+
+void ForceContainer::resize(size_t newSize) {
+ _force.resize(newSize,Vector3r::Zero());
+ _torque.resize(newSize,Vector3r::Zero());
+ _permForce.resize(newSize,Vector3r::Zero());
+ _permTorque.resize(newSize,Vector3r::Zero());
+ _move.resize(newSize,Vector3r::Zero());
+ _rot.resize(newSize,Vector3r::Zero());
+ size=newSize;
+}
+
+const int ForceContainer::getNumAllocatedThreads() const {return 1;}
+const bool ForceContainer::getMoveRotUsed() const {return moveRotUsed;}
+const bool ForceContainer::getPermForceUsed() const {return permForceUsed;}
+#endif