From bdb1394e9cb2619810af246c6656bb364cf9f7a0 Mon Sep 17 00:00:00 2001 From: Giovanni Bussi <giovanni.bussi@gmail.com> Date: Mon, 30 Apr 2018 11:03:09 +0200 Subject: [PATCH] Fix on NAMD-like interface. - when using NAMD-like interface, also update the unique list of atoms. - moved g2l out of dd, since it is also needed when not using MPI (in NAMD-like interface) Partly implemented by @hanatok, see #359 --- src/core/ActionAtomistic.cpp | 2 +- src/core/Atoms.cpp | 51 ++++++++++++++++++++++-------------- src/core/Atoms.h | 2 +- 3 files changed, 34 insertions(+), 21 deletions(-) diff --git a/src/core/ActionAtomistic.cpp b/src/core/ActionAtomistic.cpp index 177a979bf..a848da353 100644 --- a/src/core/ActionAtomistic.cpp +++ b/src/core/ActionAtomistic.cpp @@ -287,7 +287,7 @@ void ActionAtomistic::updateUniqueLocal() { unique_local.clear(); if(atoms.dd && atoms.shuffledAtoms>0) { for(auto pp=unique.begin(); pp!=unique.end(); ++pp) { - if(atoms.dd.g2l[pp->index()]>=0) unique_local.insert(*pp); + if(atoms.g2l[pp->index()]>=0) unique_local.insert(*pp); } } else { unique_local.insert(unique.begin(),unique.end()); diff --git a/src/core/Atoms.cpp b/src/core/Atoms.cpp index 10f15e88b..13eefd36a 100644 --- a/src/core/Atoms.cpp +++ b/src/core/Atoms.cpp @@ -175,7 +175,7 @@ void Atoms::shareAll() { unique.clear(); // keep in unique only those atoms that are local if(dd && shuffledAtoms>0) { - for(int i=0; i<natoms; i++) if(dd.g2l[i]>=0) unique.insert(AtomNumber::index(i)); + for(int i=0; i<natoms; i++) if(g2l[i]>=0) unique.insert(AtomNumber::index(i)); } else { for(int i=0; i<natoms; i++) unique.insert(AtomNumber::index(i)); } @@ -205,10 +205,8 @@ void Atoms::share(const std::set<AtomNumber>& unique) { } else { uniq_index.clear(); uniq_index.reserve(unique.size()); - if(dd && shuffledAtoms>0) { - for(const auto & p : unique) uniq_index.push_back(dd.g2l[p.index()]); - } else { - for(const auto & p : unique) uniq_index.push_back(p.index()); + if(shuffledAtoms>0) { + for(const auto & p : unique) uniq_index.push_back(g2l[p.index()]); } mdatoms->getPositions(unique,uniq_index,positions); } @@ -370,8 +368,8 @@ void Atoms::DomainDecomposition::enable(Communicator& c) { void Atoms::setAtomsNlocal(int n) { gatindex.resize(n); + g2l.resize(natoms,-1); if(dd) { - dd.g2l.resize(natoms,-1); // Since these vectors are sent with MPI by using e.g. // &dd.positionsToBeSent[0] // we make sure they are non-zero-sized so as to @@ -381,7 +379,7 @@ void Atoms::setAtomsNlocal(int n) { dd.positionsToBeReceived.resize(natoms*5,0.0); dd.indexToBeSent.resize(n,0); dd.indexToBeReceived.resize(natoms,0); - }; + } } void Atoms::setAtomsGatindex(int*g,bool fortran) { @@ -392,7 +390,7 @@ void Atoms::setAtomsGatindex(int*g,bool fortran) { } else { for(unsigned i=0; i<gatindex.size(); i++) gatindex[i]=g[i]; } - for(unsigned i=0; i<dd.g2l.size(); i++) dd.g2l[i]=-1; + for(unsigned i=0; i<g2l.size(); i++) g2l[i]=-1; if( gatindex.size()==natoms ) { shuffledAtoms=0; for(unsigned i=0; i<gatindex.size(); i++) { @@ -403,8 +401,8 @@ void Atoms::setAtomsGatindex(int*g,bool fortran) { } if(dd) { dd.Sum(shuffledAtoms); - for(unsigned i=0; i<gatindex.size(); i++) dd.g2l[gatindex[i]]=i; } + for(unsigned i=0; i<gatindex.size(); i++) g2l[gatindex[i]]=i; for(unsigned i=0; i<actions.size(); i++) { // keep in unique only those atoms that are local @@ -416,8 +414,8 @@ void Atoms::setAtomsGatindex(int*g,bool fortran) { void Atoms::setAtomsContiguous(int start) { ddStep=plumed.getStep(); for(unsigned i=0; i<gatindex.size(); i++) gatindex[i]=start+i; - for(unsigned i=0; i<dd.g2l.size(); i++) dd.g2l[i]=-1; - if(dd) for(unsigned i=0; i<gatindex.size(); i++) dd.g2l[gatindex[i]]=i; + for(unsigned i=0; i<g2l.size(); i++) g2l[i]=-1; + for(unsigned i=0; i<gatindex.size(); i++) g2l[gatindex[i]]=i; if(gatindex.size()<natoms) shuffledAtoms=1; for(unsigned i=0; i<actions.size(); i++) { // keep in unique only those atoms that are local @@ -465,14 +463,29 @@ double Atoms::getKbT()const { void Atoms::createFullList(int*n) { - vector<AtomNumber> fullListTmp; - for(unsigned i=0; i<actions.size(); i++) if(actions[i]->isActive()) - fullListTmp.insert(fullListTmp.end(),actions[i]->getUnique().begin(),actions[i]->getUnique().end()); - std::sort(fullListTmp.begin(),fullListTmp.end()); - int nn=std::unique(fullListTmp.begin(),fullListTmp.end())-fullListTmp.begin(); - fullList.resize(nn); - for(int i=0; i<nn; ++i) fullList[i]=fullListTmp[i].index(); - *n=nn; + if(!massAndChargeOK && shareMassAndChargeOnlyAtFirstStep) { + *n=natoms; + fullList.resize(natoms); + for(unsigned i=0; i<natoms; i++) fullList[i]=i; + } else { +// We update here the unique list defined at Atoms::unique. +// This is not very clear, and probably should be coded differently. +// Hopefully this fix the longstanding issue with NAMD. + unique.clear(); + for(unsigned i=0; i<actions.size(); i++) { + if(actions[i]->isActive()) { + if(!actions[i]->getUnique().empty()) { + atomsNeeded=true; + // unique are the local atoms + unique.insert(actions[i]->getUnique().begin(),actions[i]->getUnique().end()); + } + } + } + fullList.resize(0); + fullList.reserve(unique.size()); + for(const auto & p : unique) fullList.push_back(p.index()); + *n=fullList.size(); + } } void Atoms::getFullList(int**x) { diff --git a/src/core/Atoms.h b/src/core/Atoms.h index db5fe381d..65af02105 100644 --- a/src/core/Atoms.h +++ b/src/core/Atoms.h @@ -49,6 +49,7 @@ class Atoms int natoms; std::set<AtomNumber> unique; std::vector<unsigned> uniq_index; + std::vector<int> g2l; std::vector<Vector> positions; std::vector<Vector> forces; std::vector<double> masses; @@ -112,7 +113,6 @@ class Atoms public: bool on; bool async; - std::vector<int> g2l; std::vector<Communicator::Request> mpi_request_positions; std::vector<Communicator::Request> mpi_request_index; -- GitLab