/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2018,2019,2020, by the GROMACS development team, led by
+ * Copyright (c) 2018,2019,2020,2021, by the GROMACS development team, led by
* Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
* and including many others, as listed in the AUTHORS file in the
* top-level source directory and at http://www.gromacs.org.
#include <algorithm>
#include <memory>
-#include "gromacs/awh/awh.h"
+#include "gromacs/applied_forces/awh/awh.h"
#include "gromacs/commandline/filenm.h"
#include "gromacs/domdec/collect.h"
#include "gromacs/domdec/dlbtiming.h"
#include "gromacs/domdec/domdec.h"
#include "gromacs/domdec/domdec_network.h"
#include "gromacs/domdec/domdec_struct.h"
+#include "gromacs/domdec/localtopologychecker.h"
#include "gromacs/domdec/mdsetup.h"
#include "gromacs/domdec/partition.h"
#include "gromacs/essentialdynamics/edsam.h"
#include "gromacs/gmxlib/network.h"
#include "gromacs/gmxlib/nrnb.h"
#include "gromacs/gpu_utils/gpu_utils.h"
-#include "gromacs/listed_forces/manage_threading.h"
+#include "gromacs/listed_forces/listed_forces.h"
#include "gromacs/math/functions.h"
#include "gromacs/math/utilities.h"
#include "gromacs/math/vec.h"
#include "gromacs/mdlib/force.h"
#include "gromacs/mdlib/force_flags.h"
#include "gromacs/mdlib/forcerec.h"
+#include "gromacs/mdlib/freeenergyparameters.h"
#include "gromacs/mdlib/md_support.h"
#include "gromacs/mdlib/mdatoms.h"
#include "gromacs/mdlib/mdoutf.h"
#include "gromacs/mdtypes/commrec.h"
#include "gromacs/mdtypes/df_history.h"
#include "gromacs/mdtypes/energyhistory.h"
-#include "gromacs/mdtypes/fcdata.h"
+#include "gromacs/mdtypes/forcebuffers.h"
#include "gromacs/mdtypes/forcerec.h"
#include "gromacs/mdtypes/group.h"
#include "gromacs/mdtypes/inputrec.h"
#include "gromacs/mdtypes/mdatom.h"
#include "gromacs/mdtypes/mdrunoptions.h"
#include "gromacs/mdtypes/observableshistory.h"
+#include "gromacs/mdtypes/observablesreducer.h"
+#include "gromacs/mdtypes/simulation_workload.h"
#include "gromacs/mdtypes/state.h"
#include "gromacs/mimic/utilities.h"
-#include "gromacs/pbcutil/mshift.h"
#include "gromacs/pbcutil/pbc.h"
+#include "gromacs/pulling/output.h"
#include "gromacs/pulling/pull.h"
#include "gromacs/swap/swapcoords.h"
#include "gromacs/timing/wallcycle.h"
#include "gromacs/utility/fatalerror.h"
#include "gromacs/utility/logger.h"
#include "gromacs/utility/real.h"
-#include "gromacs/utility/smalloc.h"
#include "legacysimulator.h"
#include "replicaexchange.h"
#include "shellfc.h"
using gmx::SimulationSignaller;
+using gmx::VirtualSitesHandler;
/*! \brief Copy the state from \p rerunFrame to \p globalState and, if requested, construct vsites
*
* \param[in,out] globalState The global state container
* \param[in] constructVsites When true, vsite coordinates are constructed
* \param[in] vsite Vsite setup, can be nullptr when \p constructVsites = false
- * \param[in] idef Topology parameters, used for constructing vsites
- * \param[in] timeStep Time step, used for constructing vsites
- * \param[in] forceRec Force record, used for constructing vsites
- * \param[in,out] graph The molecular graph, used for constructing vsites when != nullptr
*/
-static void prepareRerunState(const t_trxframe& rerunFrame,
- t_state* globalState,
- bool constructVsites,
- const gmx_vsite_t* vsite,
- const t_idef& idef,
- double timeStep,
- const t_forcerec& forceRec,
- t_graph* graph)
+static void prepareRerunState(const t_trxframe& rerunFrame,
+ t_state* globalState,
+ bool constructVsites,
+ const VirtualSitesHandler* vsite)
{
auto x = makeArrayRef(globalState->x);
auto rerunX = arrayRefFromArray(reinterpret_cast<gmx::RVec*>(rerunFrame.x), globalState->natoms);
{
GMX_ASSERT(vsite, "Need valid vsite for constructing vsites");
- if (graph)
- {
- /* Following is necessary because the graph may get out of sync
- * with the coordinates if we only have every N'th coordinate set
- */
- mk_mshift(nullptr, graph, forceRec.pbcType, globalState->box, globalState->x.rvec_array());
- shift_self(graph, globalState->box, as_rvec_array(globalState->x.data()));
- }
- construct_vsites(vsite, globalState->x.rvec_array(), timeStep, globalState->v.rvec_array(),
- idef.iparams, idef.il, forceRec.pbcType, forceRec.bMolPBC, nullptr,
- globalState->box);
- if (graph)
- {
- unshift_self(graph, globalState->box, globalState->x.rvec_array());
- }
+ vsite->construct(globalState->x, globalState->v, globalState->box, gmx::VSiteOperation::PositionsAndVelocities);
}
}
// alias to avoid a large ripple of nearly useless changes.
// t_inputrec is being replaced by IMdpOptionsProvider, so this
// will go away eventually.
- t_inputrec* ir = inputrec;
- int64_t step, step_rel;
- double t, lam0[efptNR];
- bool isLastStep = false;
- bool doFreeEnergyPerturbation = false;
- unsigned int force_flags;
- tensor force_vir, shake_vir, total_vir, pres;
- t_trxstatus* status = nullptr;
- rvec mu_tot;
- t_trxframe rerun_fr;
- gmx_localtop_t top;
- PaddedHostVector<gmx::RVec> f{};
- gmx_global_stat_t gstat;
- t_graph* graph = nullptr;
- gmx_shellfc_t* shellfc;
+ const t_inputrec* ir = inputrec;
+ double t;
+ bool isLastStep = false;
+ bool doFreeEnergyPerturbation = false;
+ unsigned int force_flags;
+ tensor force_vir, shake_vir, total_vir, pres;
+ t_trxstatus* status = nullptr;
+ rvec mu_tot;
+ t_trxframe rerun_fr;
+ ForceBuffers f;
+ gmx_global_stat_t gstat;
+ gmx_shellfc_t* shellfc;
double cycles;
- /* Domain decomposition could incorrectly miss a bonded
- interaction, but checking for that requires a global
- communication stage, which does not otherwise happen in DD
- code. So we do that alongside the first global energy reduction
- after a new DD is made. These variables handle whether the
- check happens, and the result it returns. */
- bool shouldCheckNumberOfBondedInteractions = false;
- int totalNumberOfBondedInteractions = -1;
-
SimulationSignals signals;
// Most global communnication stages don't propagate mdrun
// signals, and will use this object to achieve that.
"be available in a different form in a future version of GROMACS, "
"e.g. gmx rerun -f.");
- if (ir->efep != efepNO
+ if (ir->efep != FreeEnergyPerturbationType::No
&& (mdAtoms->mdatoms()->nMassPerturbed > 0 || (constr && constr->havePerturbedConstraints())))
{
gmx_fatal(FARGS,
{
gmx_fatal(FARGS, "Multiple simulations not supported by rerun.");
}
- if (std::any_of(ir->opts.annealing, ir->opts.annealing + ir->opts.ngtc,
- [](int i) { return i != eannNO; }))
+ if (std::any_of(ir->opts.annealing, ir->opts.annealing + ir->opts.ngtc, [](SimulatedAnnealing i) {
+ return i != SimulatedAnnealing::No;
+ }))
{
gmx_fatal(FARGS, "Simulated annealing not supported by rerun.");
}
}
/* Settings for rerun */
- ir->nstlist = 1;
- ir->nstcalcenergy = 1;
+ {
+ // TODO: Avoid changing inputrec (#3854)
+ auto* nonConstInputrec = const_cast<t_inputrec*>(inputrec);
+ nonConstInputrec->nstlist = 1;
+ nonConstInputrec->nstcalcenergy = 1;
+ nonConstInputrec->nstxout_compressed = 0;
+ }
int nstglobalcomm = 1;
const bool bNS = true;
- ir->nstxout_compressed = 0;
- SimulationGroups* groups = &top_global->groups;
- if (ir->eI == eiMimic)
+ ObservablesReducer observablesReducer = observablesReducerBuilder->build();
+
+ const SimulationGroups* groups = &top_global.groups;
+ if (ir->eI == IntegrationAlgorithm::Mimic)
{
- top_global->intermolecularExclusionGroup = genQmmmIndices(*top_global);
+ auto* nonConstGlobalTopology = const_cast<gmx_mtop_t*>(&top_global);
+ nonConstGlobalTopology->intermolecularExclusionGroup = genQmmmIndices(top_global);
}
-
- initialize_lambdas(fplog, *ir, MASTER(cr), &state_global->fep_state, state_global->lambda, lam0);
+ int* fep_state = MASTER(cr) ? &state_global->fep_state : nullptr;
+ gmx::ArrayRef<real> lambda = MASTER(cr) ? state_global->lambda : gmx::ArrayRef<real>();
+ initialize_lambdas(fplog,
+ ir->efep,
+ ir->bSimTemp,
+ *ir->fepvals,
+ ir->simtempvals->temperatures,
+ gmx::arrayRefFromArray(ir->opts.ref_t, ir->opts.ngtc),
+ MASTER(cr),
+ fep_state,
+ lambda);
const bool simulationsShareState = false;
- gmx_mdoutf* outf = init_mdoutf(fplog, nfile, fnm, mdrunOptions, cr, outputProvider,
- mdModulesNotifier, ir, top_global, oenv, wcycle,
- StartingBehavior::NewSimulation, simulationsShareState, ms);
- gmx::EnergyOutput energyOutput(mdoutf_get_fp_ene(outf), top_global, ir, pull_work,
- mdoutf_get_fp_dhdl(outf), true, StartingBehavior::NewSimulation,
- mdModulesNotifier);
+ gmx_mdoutf* outf = init_mdoutf(fplog,
+ nfile,
+ fnm,
+ mdrunOptions,
+ cr,
+ outputProvider,
+ mdModulesNotifiers,
+ ir,
+ top_global,
+ oenv,
+ wcycle,
+ StartingBehavior::NewSimulation,
+ simulationsShareState,
+ ms);
+ gmx::EnergyOutput energyOutput(mdoutf_get_fp_ene(outf),
+ top_global,
+ *ir,
+ pull_work,
+ mdoutf_get_fp_dhdl(outf),
+ true,
+ StartingBehavior::NewSimulation,
+ simulationsShareState,
+ mdModulesNotifiers);
gstat = global_stat_init(ir);
/* Check for polarizable models and flexible constraints */
- shellfc = init_shell_flexcon(fplog, top_global, constr ? constr->numFlexibleConstraints() : 0,
- ir->nstcalcenergy, DOMAINDECOMP(cr));
+ shellfc = init_shell_flexcon(fplog,
+ top_global,
+ constr ? constr->numFlexibleConstraints() : 0,
+ ir->nstcalcenergy,
+ haveDDAtomOrdering(*cr),
+ runScheduleWork->simulationWork.useGpuPme);
{
- double io = compute_io(ir, top_global->natoms, *groups, energyOutput.numEnergyTerms(), 1);
+ double io = compute_io(ir, top_global.natoms, *groups, energyOutput.numEnergyTerms(), 1);
if ((io > 2000) && MASTER(cr))
{
fprintf(stderr, "\nWARNING: This run will generate roughly %.0f Mb of data\n\n", io);
}
}
- // Local state only becomes valid now.
- std::unique_ptr<t_state> stateInstance;
- t_state* state;
-
- if (DOMAINDECOMP(cr))
+ if (haveDDAtomOrdering(*cr))
{
- dd_init_local_top(*top_global, &top);
-
- stateInstance = std::make_unique<t_state>();
- state = stateInstance.get();
- dd_init_local_state(cr->dd, state_global, state);
+ // Local state only becomes valid now.
+ dd_init_local_state(*cr->dd, state_global, state);
/* Distribute the charge groups over the nodes from the master node */
- dd_partition_system(fplog, mdlog, ir->init_step, cr, TRUE, 1, state_global, *top_global, ir,
- imdSession, pull_work, state, &f, mdAtoms, &top, fr, vsite, constr,
- nrnb, nullptr, FALSE);
- shouldCheckNumberOfBondedInteractions = true;
+ dd_partition_system(fplog,
+ mdlog,
+ ir->init_step,
+ cr,
+ TRUE,
+ 1,
+ state_global,
+ top_global,
+ *ir,
+ imdSession,
+ pull_work,
+ state,
+ &f,
+ mdAtoms,
+ top,
+ fr,
+ vsite,
+ constr,
+ nrnb,
+ nullptr,
+ FALSE);
}
else
{
state_change_natoms(state_global, state_global->natoms);
- /* We need to allocate one element extra, since we might use
- * (unaligned) 4-wide SIMD loads to access rvec entries.
- */
- f.resizeWithPadding(state_global->natoms);
/* Copy the pointer to the global state */
state = state_global;
- mdAlgorithmsSetupAtomData(cr, ir, *top_global, &top, fr, &graph, mdAtoms, constr, vsite, shellfc);
+ mdAlgorithmsSetupAtomData(cr, *ir, top_global, top, fr, &f, mdAtoms, constr, vsite, shellfc);
}
- auto mdatoms = mdAtoms->mdatoms();
+ auto* mdatoms = mdAtoms->mdatoms();
+ fr->longRangeNonbondeds->updateAfterPartition(*mdatoms);
// NOTE: The global state is no longer used at this point.
// But state_global is still used as temporary storage space for writing
// the global state to file and potentially for replica exchange.
// (Global topology should persist.)
- update_mdatoms(mdatoms, state->lambda[efptMASS]);
+ update_mdatoms(mdatoms, state->lambda[FreeEnergyPerturbationCouplingType::Mass]);
- if (ir->efep != efepNO && ir->fepvals->nstdhdl != 0)
+ if (ir->efep != FreeEnergyPerturbationType::No && ir->fepvals->nstdhdl != 0)
{
doFreeEnergyPerturbation = true;
}
+ int64_t step = ir->init_step;
+ int64_t step_rel = 0;
+
{
- int cglo_flags =
- (CGLO_GSTAT
- | (shouldCheckNumberOfBondedInteractions ? CGLO_CHECK_NUMBER_OF_BONDED_INTERACTIONS : 0));
+ int cglo_flags = CGLO_GSTAT;
bool bSumEkinhOld = false;
t_vcm* vcm = nullptr;
- compute_globals(gstat, cr, ir, fr, ekind, makeConstArrayRef(state->x),
- makeConstArrayRef(state->v), state->box, state->lambda[efptVDW], mdatoms, nrnb,
- vcm, nullptr, enerd, force_vir, shake_vir, total_vir, pres, constr, &nullSignaller,
- state->box, &totalNumberOfBondedInteractions, &bSumEkinhOld, cglo_flags);
+ compute_globals(gstat,
+ cr,
+ ir,
+ fr,
+ ekind,
+ makeConstArrayRef(state->x),
+ makeConstArrayRef(state->v),
+ state->box,
+ mdatoms,
+ nrnb,
+ vcm,
+ nullptr,
+ enerd,
+ force_vir,
+ shake_vir,
+ total_vir,
+ pres,
+ &nullSignaller,
+ state->box,
+ &bSumEkinhOld,
+ cglo_flags,
+ step,
+ &observablesReducer);
+ // Clean up after pre-step use of compute_globals()
+ observablesReducer.markAsReadyToReduce();
}
- checkNumberOfBondedInteractions(mdlog, cr, totalNumberOfBondedInteractions, top_global, &top,
- makeConstArrayRef(state->x), state->box,
- &shouldCheckNumberOfBondedInteractions);
if (MASTER(cr))
{
fprintf(stderr,
"starting md rerun '%s', reading coordinates from"
" input trajectory '%s'\n\n",
- *(top_global->name), opt2fn("-rerun", nfile, fnm));
+ *(top_global.name),
+ opt2fn("-rerun", nfile, fnm));
if (mdrunOptions.verbose)
{
fprintf(stderr,
}
walltime_accounting_start_time(walltime_accounting);
- wallcycle_start(wcycle, ewcRUN);
+ wallcycle_start(wcycle, WallCycleCounter::Run);
print_start(fplog, cr, walltime_accounting, "mdrun");
/***********************************************************
if (MASTER(cr))
{
isLastStep = !read_first_frame(oenv, &status, opt2fn("-rerun", nfile, fnm), &rerun_fr, TRX_NEED_X);
- if (rerun_fr.natoms != top_global->natoms)
+ if (rerun_fr.natoms != top_global.natoms)
{
gmx_fatal(FARGS,
"Number of atoms in trajectory (%d) does not match the "
"run input file (%d)\n",
- rerun_fr.natoms, top_global->natoms);
+ rerun_fr.natoms,
+ top_global.natoms);
}
if (ir->pbcType != PbcType::No)
"Rerun trajectory frame step %" PRId64
" time %f "
"does not contain a box, while pbc is used",
- rerun_fr.step, rerun_fr.time);
+ rerun_fr.step,
+ rerun_fr.time);
}
if (max_cutoff2(ir->pbcType, rerun_fr.box) < gmx::square(fr->rlist))
{
"Rerun trajectory frame step %" PRId64
" time %f "
"has too small box dimensions",
- rerun_fr.step, rerun_fr.time);
+ rerun_fr.step,
+ rerun_fr.time);
}
}
}
}
auto stopHandler = stopHandlerBuilder->getStopHandlerMD(
- compat::not_null<SimulationSignal*>(&signals[eglsSTOPCOND]), false, MASTER(cr),
- ir->nstlist, mdrunOptions.reproducible, nstglobalcomm, mdrunOptions.maximumHoursToRun,
- ir->nstlist == 0, fplog, step, bNS, walltime_accounting);
+ compat::not_null<SimulationSignal*>(&signals[eglsSTOPCOND]),
+ false,
+ MASTER(cr),
+ ir->nstlist,
+ mdrunOptions.reproducible,
+ nstglobalcomm,
+ mdrunOptions.maximumHoursToRun,
+ ir->nstlist == 0,
+ fplog,
+ step,
+ bNS,
+ walltime_accounting);
// we don't do counter resetting in rerun - finish will always be valid
walltime_accounting_set_valid_finish(walltime_accounting);
const DDBalanceRegionHandler ddBalanceRegionHandler(cr);
- step = ir->init_step;
- step_rel = 0;
-
/* and stop now if we should */
isLastStep = (isLastStep || (ir->nsteps >= 0 && step_rel > ir->nsteps));
while (!isLastStep)
{
- wallcycle_start(wcycle, ewcSTEP);
+ wallcycle_start(wcycle, WallCycleCounter::Step);
if (rerun_fr.bStep)
{
t = step;
}
- if (ir->efep != efepNO && MASTER(cr))
+ if (ir->efep != FreeEnergyPerturbationType::No && MASTER(cr))
{
- setCurrentLambdasRerun(step, ir->fepvals, &rerun_fr, lam0, state_global);
+ if (rerun_fr.bLambda)
+ {
+ ir->fepvals->init_lambda = rerun_fr.lambda;
+ }
+ else
+ {
+ if (rerun_fr.bFepState)
+ {
+ state->fep_state = rerun_fr.fep_state;
+ }
+ }
+
+ state_global->lambda = currentLambdas(step, *(ir->fepvals), state->fep_state);
}
if (MASTER(cr))
{
const bool constructVsites = ((vsite != nullptr) && mdrunOptions.rerunConstructVsites);
- if (constructVsites && DOMAINDECOMP(cr))
+ if (constructVsites && haveDDAtomOrdering(*cr))
{
gmx_fatal(FARGS,
"Vsite recalculation with -rerun is not implemented with domain "
"decomposition, "
"use a single rank");
}
- prepareRerunState(rerun_fr, state_global, constructVsites, vsite, top.idef, ir->delta_t,
- *fr, graph);
+ prepareRerunState(rerun_fr, state_global, constructVsites, vsite);
}
isLastStep = isLastStep || stopHandler->stoppingAfterCurrentStep(bNS);
- if (DOMAINDECOMP(cr))
+ if (haveDDAtomOrdering(*cr))
{
/* Repartition the domain decomposition */
const bool bMasterState = true;
- dd_partition_system(fplog, mdlog, step, cr, bMasterState, nstglobalcomm, state_global,
- *top_global, ir, imdSession, pull_work, state, &f, mdAtoms, &top,
- fr, vsite, constr, nrnb, wcycle, mdrunOptions.verbose);
- shouldCheckNumberOfBondedInteractions = true;
+ dd_partition_system(fplog,
+ mdlog,
+ step,
+ cr,
+ bMasterState,
+ nstglobalcomm,
+ state_global,
+ top_global,
+ *ir,
+ imdSession,
+ pull_work,
+ state,
+ &f,
+ mdAtoms,
+ top,
+ fr,
+ vsite,
+ constr,
+ nrnb,
+ wcycle,
+ mdrunOptions.verbose);
}
if (MASTER(cr))
{
- energyOutput.printHeader(fplog, step, t); /* can we improve the information printed here? */
+ EnergyOutput::printHeader(fplog, step, t); /* can we improve the information printed here? */
}
- if (ir->efep != efepNO)
+ if (ir->efep != FreeEnergyPerturbationType::No)
{
- update_mdatoms(mdatoms, state->lambda[efptMASS]);
+ update_mdatoms(mdatoms, state->lambda[FreeEnergyPerturbationCouplingType::Mass]);
}
+ fr->longRangeNonbondeds->updateAfterPartition(*mdatoms);
+
force_flags = (GMX_FORCE_STATECHANGED | GMX_FORCE_DYNAMICBOX | GMX_FORCE_ALLFORCES
| GMX_FORCE_VIRIAL | // TODO: Get rid of this once #2649 and #3400 are solved
GMX_FORCE_ENERGY | (doFreeEnergyPerturbation ? GMX_FORCE_DHDL : 0));
if (shellfc)
{
/* Now is the time to relax the shells */
- relax_shell_flexcon(fplog, cr, ms, mdrunOptions.verbose, enforcedRotation, step, ir,
- imdSession, pull_work, bNS, force_flags, &top, constr, enerd, fcd,
- state->natoms, state->x.arrayRefWithPadding(),
- state->v.arrayRefWithPadding(), state->box, state->lambda, &state->hist,
- f.arrayRefWithPadding(), force_vir, mdatoms, nrnb, wcycle, graph,
- shellfc, fr, runScheduleWork, t, mu_tot, vsite, ddBalanceRegionHandler);
+ relax_shell_flexcon(fplog,
+ cr,
+ ms,
+ mdrunOptions.verbose,
+ enforcedRotation,
+ step,
+ ir,
+ imdSession,
+ pull_work,
+ bNS,
+ force_flags,
+ top,
+ constr,
+ enerd,
+ state->natoms,
+ state->x.arrayRefWithPadding(),
+ state->v.arrayRefWithPadding(),
+ state->box,
+ state->lambda,
+ &state->hist,
+ &f.view(),
+ force_vir,
+ *mdatoms,
+ fr->longRangeNonbondeds.get(),
+ nrnb,
+ wcycle,
+ shellfc,
+ fr,
+ runScheduleWork,
+ t,
+ mu_tot,
+ vsite,
+ ddBalanceRegionHandler);
}
else
{
*/
Awh* awh = nullptr;
gmx_edsam* ed = nullptr;
- do_force(fplog, cr, ms, ir, awh, enforcedRotation, imdSession, pull_work, step, nrnb,
- wcycle, &top, state->box, state->x.arrayRefWithPadding(), &state->hist,
- f.arrayRefWithPadding(), force_vir, mdatoms, enerd, fcd, state->lambda, graph,
- fr, runScheduleWork, vsite, mu_tot, t, ed, GMX_FORCE_NS | force_flags,
+ do_force(fplog,
+ cr,
+ ms,
+ *ir,
+ awh,
+ enforcedRotation,
+ imdSession,
+ pull_work,
+ step,
+ nrnb,
+ wcycle,
+ top,
+ state->box,
+ state->x.arrayRefWithPadding(),
+ &state->hist,
+ &f.view(),
+ force_vir,
+ mdatoms,
+ enerd,
+ state->lambda,
+ fr,
+ runScheduleWork,
+ vsite,
+ mu_tot,
+ t,
+ ed,
+ fr->longRangeNonbondeds.get(),
+ GMX_FORCE_NS | force_flags,
ddBalanceRegionHandler);
}
const bool isCheckpointingStep = false;
const bool doRerun = true;
const bool bSumEkinhOld = false;
- do_md_trajectory_writing(fplog, cr, nfile, fnm, step, step_rel, t, ir, state,
- state_global, observablesHistory, top_global, fr, outf,
- energyOutput, ekind, f, isCheckpointingStep, doRerun,
- isLastStep, mdrunOptions.writeConfout, bSumEkinhOld);
+ do_md_trajectory_writing(fplog,
+ cr,
+ nfile,
+ fnm,
+ step,
+ step_rel,
+ t,
+ ir,
+ state,
+ state_global,
+ observablesHistory,
+ top_global,
+ fr,
+ outf,
+ energyOutput,
+ ekind,
+ f.view().force(),
+ isCheckpointingStep,
+ doRerun,
+ isLastStep,
+ mdrunOptions.writeConfout,
+ bSumEkinhOld);
}
stopHandler->setSignal();
- if (graph)
- {
- /* Need to unshift here */
- unshift_self(graph, state->box, as_rvec_array(state->x.data()));
- }
-
- if (vsite != nullptr)
- {
- wallcycle_start(wcycle, ewcVSITECONSTR);
- if (graph != nullptr)
- {
- shift_self(graph, state->box, as_rvec_array(state->x.data()));
- }
- construct_vsites(vsite, as_rvec_array(state->x.data()), ir->delta_t,
- as_rvec_array(state->v.data()), top.idef.iparams, top.idef.il,
- fr->pbcType, fr->bMolPBC, cr, state->box);
-
- if (graph != nullptr)
- {
- unshift_self(graph, state->box, as_rvec_array(state->x.data()));
- }
- wallcycle_stop(wcycle, ewcVSITECONSTR);
- }
-
{
const bool doInterSimSignal = false;
const bool doIntraSimSignal = true;
t_vcm* vcm = nullptr;
SimulationSignaller signaller(&signals, cr, ms, doInterSimSignal, doIntraSimSignal);
- compute_globals(gstat, cr, ir, fr, ekind, makeConstArrayRef(state->x),
- makeConstArrayRef(state->v), state->box, state->lambda[efptVDW], mdatoms,
- nrnb, vcm, wcycle, enerd, force_vir, shake_vir, total_vir, pres, constr,
- &signaller, state->box, &totalNumberOfBondedInteractions, &bSumEkinhOld,
- CGLO_GSTAT | CGLO_ENERGY
- | (shouldCheckNumberOfBondedInteractions ? CGLO_CHECK_NUMBER_OF_BONDED_INTERACTIONS
- : 0));
- checkNumberOfBondedInteractions(mdlog, cr, totalNumberOfBondedInteractions, top_global,
- &top, makeConstArrayRef(state->x), state->box,
- &shouldCheckNumberOfBondedInteractions);
+ int cglo_flags = CGLO_GSTAT | CGLO_ENERGY;
+ compute_globals(gstat,
+ cr,
+ ir,
+ fr,
+ ekind,
+ makeConstArrayRef(state->x),
+ makeConstArrayRef(state->v),
+ state->box,
+ mdatoms,
+ nrnb,
+ vcm,
+ wcycle,
+ enerd,
+ force_vir,
+ shake_vir,
+ total_vir,
+ pres,
+ &signaller,
+ state->box,
+ &bSumEkinhOld,
+ cglo_flags,
+ step,
+ &observablesReducer);
+ // Clean up after pre-step use of compute_globals()
+ observablesReducer.markAsReadyToReduce();
}
/* Note: this is OK, but there are some numerical precision issues with using the convergence of
but what we actually need entering the new cycle is the new shake_vir value. Ideally, we could
generate the new shake_vir, but test the veta value for convergence. This will take some thought. */
- if (ir->efep != efepNO)
- {
- /* Sum up the foreign energy and dhdl terms for md and sd.
- Currently done every step so that dhdl is correct in the .edr */
- sum_dhdl(enerd, state->lambda, *ir->fepvals);
- }
-
/* Output stuff */
if (MASTER(cr))
{
const bool bCalcEnerStep = true;
- energyOutput.addDataAtEnergyStep(doFreeEnergyPerturbation, bCalcEnerStep, t,
- mdatoms->tmass, enerd, state, ir->fepvals,
- ir->expandedvals, state->box, shake_vir, force_vir,
- total_vir, pres, ekind, mu_tot, constr);
+ energyOutput.addDataAtEnergyStep(doFreeEnergyPerturbation,
+ bCalcEnerStep,
+ t,
+ mdatoms->tmass,
+ enerd,
+ ir->fepvals.get(),
+ state->box,
+ PTCouplingArrays({ state->boxv,
+ state->nosehoover_xi,
+ state->nosehoover_vxi,
+ state->nhpres_xi,
+ state->nhpres_vxi }),
+ state->fep_state,
+ total_vir,
+ pres,
+ ekind,
+ mu_tot,
+ constr);
const bool do_ene = true;
const bool do_log = true;
const bool do_dr = ir->nstdisreout != 0;
const bool do_or = ir->nstorireout != 0;
- energyOutput.printAnnealingTemperatures(do_log ? fplog : nullptr, groups, &(ir->opts));
- energyOutput.printStepToEnergyFile(mdoutf_get_fp_ene(outf), do_ene, do_dr, do_or,
- do_log ? fplog : nullptr, step, t, fcd, awh);
+ EnergyOutput::printAnnealingTemperatures(do_log ? fplog : nullptr, groups, &(ir->opts));
+ energyOutput.printStepToEnergyFile(mdoutf_get_fp_ene(outf),
+ do_ene,
+ do_dr,
+ do_or,
+ do_log ? fplog : nullptr,
+ step,
+ t,
+ fr->fcdata.get(),
+ awh);
+
+ if (ir->bPull)
+ {
+ pull_print_output(pull_work, step, t);
+ }
if (do_per_step(step, ir->nstlog))
{
/* Ion/water position swapping.
* Not done in last step since trajectory writing happens before this call
* in the MD loop and exchanges would be lost anyway. */
- if ((ir->eSwapCoords != eswapNO) && (step > 0) && !isLastStep && do_per_step(step, ir->swap->nstswap))
+ if ((ir->eSwapCoords != SwapType::No) && (step > 0) && !isLastStep
+ && do_per_step(step, ir->swap->nstswap))
{
const bool doRerun = true;
- do_swapcoords(cr, step, t, ir, swap, wcycle, rerun_fr.x, rerun_fr.box,
- MASTER(cr) && mdrunOptions.verbose, doRerun);
+ do_swapcoords(cr,
+ step,
+ t,
+ ir,
+ swap,
+ wcycle,
+ rerun_fr.x,
+ rerun_fr.box,
+ MASTER(cr) && mdrunOptions.verbose,
+ doRerun);
}
if (MASTER(cr))
rerun_parallel_comm(cr, &rerun_fr, &isLastStep);
}
- cycles = wallcycle_stop(wcycle, ewcSTEP);
- if (DOMAINDECOMP(cr) && wcycle)
+ cycles = wallcycle_stop(wcycle, WallCycleCounter::Step);
+ if (haveDDAtomOrdering(*cr) && wcycle)
{
dd_cycles_add(cr->dd, cycles, ddCyclStep);
}
step++;
step_rel++;
}
+ observablesReducer.markAsReadyToReduce();
}
/* End of main MD loop */