Fix Parrinello-Rahman with nstpcouple>1
[alexxy/gromacs.git] / src / gromacs / mdlib / update.cpp
1 /*
2  * This file is part of the GROMACS molecular simulation package.
3  *
4  * Copyright (c) 1991-2000, University of Groningen, The Netherlands.
5  * Copyright (c) 2001-2004, The GROMACS development team.
6  * Copyright (c) 2013,2014,2015,2016, by the GROMACS development team, led by
7  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
8  * and including many others, as listed in the AUTHORS file in the
9  * top-level source directory and at http://www.gromacs.org.
10  *
11  * GROMACS is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Lesser General Public License
13  * as published by the Free Software Foundation; either version 2.1
14  * of the License, or (at your option) any later version.
15  *
16  * GROMACS is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  * Lesser General Public License for more details.
20  *
21  * You should have received a copy of the GNU Lesser General Public
22  * License along with GROMACS; if not, see
23  * http://www.gnu.org/licenses, or write to the Free Software Foundation,
24  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA.
25  *
26  * If you want to redistribute modifications to GROMACS, please
27  * consider that scientific software is very special. Version
28  * control is crucial - bugs must be traceable. We will be happy to
29  * consider code for inclusion in the official distribution, but
30  * derived work must not be called official GROMACS. Details are found
31  * in the README & COPYING files - if they are missing, get the
32  * official version at http://www.gromacs.org.
33  *
34  * To help us fund GROMACS development, we humbly ask that you cite
35  * the research papers on the package. Check out http://www.gromacs.org.
36  */
37 #include "gmxpre.h"
38
39 #include "gromacs/legacyheaders/update.h"
40
41 #include <math.h>
42 #include <stdio.h>
43
44 #include <algorithm>
45
46 #include "gromacs/fileio/confio.h"
47 #include "gromacs/legacyheaders/constr.h"
48 #include "gromacs/legacyheaders/disre.h"
49 #include "gromacs/legacyheaders/force.h"
50 #include "gromacs/legacyheaders/gmx_omp_nthreads.h"
51 #include "gromacs/legacyheaders/macros.h"
52 #include "gromacs/legacyheaders/mdrun.h"
53 #include "gromacs/legacyheaders/names.h"
54 #include "gromacs/legacyheaders/nrnb.h"
55 #include "gromacs/legacyheaders/orires.h"
56 #include "gromacs/legacyheaders/tgroup.h"
57 #include "gromacs/legacyheaders/txtdump.h"
58 #include "gromacs/legacyheaders/typedefs.h"
59 #include "gromacs/legacyheaders/types/commrec.h"
60 #include "gromacs/math/units.h"
61 #include "gromacs/math/vec.h"
62 #include "gromacs/pbcutil/mshift.h"
63 #include "gromacs/pbcutil/pbc.h"
64 #include "gromacs/pulling/pull.h"
65 #include "gromacs/random/random.h"
66 #include "gromacs/timing/wallcycle.h"
67 #include "gromacs/utility/futil.h"
68 #include "gromacs/utility/gmxomp.h"
69 #include "gromacs/utility/smalloc.h"
70
71 /*For debugging, start at v(-dt/2) for velolcity verlet -- uncomment next line */
72 /*#define STARTFROMDT2*/
73
74 typedef struct {
75     double gdt;
76     double eph;
77     double emh;
78     double em;
79     double b;
80     double c;
81     double d;
82 } gmx_sd_const_t;
83
84 typedef struct {
85     real V;
86     real X;
87     real Yv;
88     real Yx;
89 } gmx_sd_sigma_t;
90
91 typedef struct {
92     /* BD stuff */
93     real           *bd_rf;
94     /* SD stuff */
95     gmx_sd_const_t *sdc;
96     gmx_sd_sigma_t *sdsig;
97     rvec           *sd_V;
98     int             sd_V_nalloc;
99     /* andersen temperature control stuff */
100     gmx_bool       *randomize_group;
101     real           *boltzfac;
102 } gmx_stochd_t;
103
104 typedef struct gmx_update
105 {
106     gmx_stochd_t *sd;
107     /* xprime for constraint algorithms */
108     rvec         *xp;
109     int           xp_nalloc;
110
111     /* Variables for the deform algorithm */
112     gmx_int64_t     deformref_step;
113     matrix          deformref_box;
114 } t_gmx_update;
115
116
117 static void do_update_md(int start, int nrend,
118                          double dt, int nstpcouple,
119                          t_grp_tcstat *tcstat,
120                          double nh_vxi[],
121                          gmx_bool bNEMD, t_grp_acc *gstat, rvec accel[],
122                          ivec nFreeze[],
123                          real invmass[],
124                          unsigned short ptype[], unsigned short cFREEZE[],
125                          unsigned short cACC[], unsigned short cTC[],
126                          rvec x[], rvec xprime[], rvec v[],
127                          rvec f[], matrix M,
128                          gmx_bool bNH, gmx_bool bPR)
129 {
130     double imass, w_dt;
131     int    gf = 0, ga = 0, gt = 0;
132     rvec   vrel;
133     real   vn, vv, va, vb, vnrel;
134     real   lg, vxi = 0, u;
135     int    n, d;
136
137     if (bNH || bPR)
138     {
139         /* Update with coupling to extended ensembles, used for
140          * Nose-Hoover and Parrinello-Rahman coupling
141          * Nose-Hoover uses the reversible leap-frog integrator from
142          * Holian et al. Phys Rev E 52(3) : 2338, 1995
143          */
144         for (n = start; n < nrend; n++)
145         {
146             imass = invmass[n];
147             if (cFREEZE)
148             {
149                 gf   = cFREEZE[n];
150             }
151             if (cACC)
152             {
153                 ga   = cACC[n];
154             }
155             if (cTC)
156             {
157                 gt   = cTC[n];
158             }
159             lg   = tcstat[gt].lambda;
160             if (bNH)
161             {
162                 vxi   = nh_vxi[gt];
163             }
164             rvec_sub(v[n], gstat[ga].u, vrel);
165
166             for (d = 0; d < DIM; d++)
167             {
168                 if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
169                 {
170                     vnrel = (lg*vrel[d] + dt*(imass*f[n][d] - 0.5*vxi*vrel[d]
171                                               - nstpcouple*iprod(M[d], vrel)))/(1 + 0.5*vxi*dt);
172                     /* do not scale the mean velocities u */
173                     vn             = gstat[ga].u[d] + accel[ga][d]*dt + vnrel;
174                     v[n][d]        = vn;
175                     xprime[n][d]   = x[n][d]+vn*dt;
176                 }
177                 else
178                 {
179                     v[n][d]        = 0.0;
180                     xprime[n][d]   = x[n][d];
181                 }
182             }
183         }
184     }
185     else if (cFREEZE != NULL ||
186              nFreeze[0][XX] || nFreeze[0][YY] || nFreeze[0][ZZ] ||
187              bNEMD)
188     {
189         /* Update with Berendsen/v-rescale coupling and freeze or NEMD */
190         for (n = start; n < nrend; n++)
191         {
192             w_dt = invmass[n]*dt;
193             if (cFREEZE)
194             {
195                 gf   = cFREEZE[n];
196             }
197             if (cACC)
198             {
199                 ga   = cACC[n];
200             }
201             if (cTC)
202             {
203                 gt   = cTC[n];
204             }
205             lg   = tcstat[gt].lambda;
206
207             for (d = 0; d < DIM; d++)
208             {
209                 vn             = v[n][d];
210                 if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
211                 {
212                     vv             = lg*vn + f[n][d]*w_dt;
213
214                     /* do not scale the mean velocities u */
215                     u              = gstat[ga].u[d];
216                     va             = vv + accel[ga][d]*dt;
217                     vb             = va + (1.0-lg)*u;
218                     v[n][d]        = vb;
219                     xprime[n][d]   = x[n][d]+vb*dt;
220                 }
221                 else
222                 {
223                     v[n][d]        = 0.0;
224                     xprime[n][d]   = x[n][d];
225                 }
226             }
227         }
228     }
229     else
230     {
231         /* Plain update with Berendsen/v-rescale coupling */
232         for (n = start; n < nrend; n++)
233         {
234             if ((ptype[n] != eptVSite) && (ptype[n] != eptShell))
235             {
236                 w_dt = invmass[n]*dt;
237                 if (cTC)
238                 {
239                     gt = cTC[n];
240                 }
241                 lg = tcstat[gt].lambda;
242
243                 for (d = 0; d < DIM; d++)
244                 {
245                     vn           = lg*v[n][d] + f[n][d]*w_dt;
246                     v[n][d]      = vn;
247                     xprime[n][d] = x[n][d] + vn*dt;
248                 }
249             }
250             else
251             {
252                 for (d = 0; d < DIM; d++)
253                 {
254                     v[n][d]        = 0.0;
255                     xprime[n][d]   = x[n][d];
256                 }
257             }
258         }
259     }
260 }
261
262 static void do_update_vv_vel(int start, int nrend, double dt,
263                              rvec accel[], ivec nFreeze[], real invmass[],
264                              unsigned short ptype[], unsigned short cFREEZE[],
265                              unsigned short cACC[], rvec v[], rvec f[],
266                              gmx_bool bExtended, real veta, real alpha)
267 {
268     double w_dt;
269     int    gf = 0, ga = 0;
270     int    n, d;
271     double g, mv1, mv2;
272
273     if (bExtended)
274     {
275         g        = 0.25*dt*veta*alpha;
276         mv1      = exp(-g);
277         mv2      = series_sinhx(g);
278     }
279     else
280     {
281         mv1      = 1.0;
282         mv2      = 1.0;
283     }
284     for (n = start; n < nrend; n++)
285     {
286         w_dt = invmass[n]*dt;
287         if (cFREEZE)
288         {
289             gf   = cFREEZE[n];
290         }
291         if (cACC)
292         {
293             ga   = cACC[n];
294         }
295
296         for (d = 0; d < DIM; d++)
297         {
298             if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
299             {
300                 v[n][d]             = mv1*(mv1*v[n][d] + 0.5*(w_dt*mv2*f[n][d]))+0.5*accel[ga][d]*dt;
301             }
302             else
303             {
304                 v[n][d]        = 0.0;
305             }
306         }
307     }
308 } /* do_update_vv_vel */
309
310 static void do_update_vv_pos(int start, int nrend, double dt,
311                              ivec nFreeze[],
312                              unsigned short ptype[], unsigned short cFREEZE[],
313                              rvec x[], rvec xprime[], rvec v[],
314                              gmx_bool bExtended, real veta)
315 {
316     int    gf = 0;
317     int    n, d;
318     double g, mr1, mr2;
319
320     /* Would it make more sense if Parrinello-Rahman was put here? */
321     if (bExtended)
322     {
323         g        = 0.5*dt*veta;
324         mr1      = exp(g);
325         mr2      = series_sinhx(g);
326     }
327     else
328     {
329         mr1      = 1.0;
330         mr2      = 1.0;
331     }
332
333     for (n = start; n < nrend; n++)
334     {
335
336         if (cFREEZE)
337         {
338             gf   = cFREEZE[n];
339         }
340
341         for (d = 0; d < DIM; d++)
342         {
343             if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
344             {
345                 xprime[n][d]   = mr1*(mr1*x[n][d]+mr2*dt*v[n][d]);
346             }
347             else
348             {
349                 xprime[n][d]   = x[n][d];
350             }
351         }
352     }
353 } /* do_update_vv_pos */
354
355 static void do_update_visc(int start, int nrend,
356                            double dt, int nstpcouple,
357                            t_grp_tcstat *tcstat,
358                            double nh_vxi[],
359                            real invmass[],
360                            unsigned short ptype[], unsigned short cTC[],
361                            rvec x[], rvec xprime[], rvec v[],
362                            rvec f[], matrix M, matrix box, real
363                            cos_accel, real vcos,
364                            gmx_bool bNH, gmx_bool bPR)
365 {
366     double imass, w_dt;
367     int    gt = 0;
368     real   vn, vc;
369     real   lg, vxi = 0, vv;
370     real   fac, cosz;
371     rvec   vrel;
372     int    n, d;
373
374     fac = 2*M_PI/(box[ZZ][ZZ]);
375
376     if (bNH || bPR)
377     {
378         /* Update with coupling to extended ensembles, used for
379          * Nose-Hoover and Parrinello-Rahman coupling
380          */
381         for (n = start; n < nrend; n++)
382         {
383             imass = invmass[n];
384             if (cTC)
385             {
386                 gt   = cTC[n];
387             }
388             lg   = tcstat[gt].lambda;
389             cosz = cos(fac*x[n][ZZ]);
390
391             copy_rvec(v[n], vrel);
392
393             vc            = cosz*vcos;
394             vrel[XX]     -= vc;
395             if (bNH)
396             {
397                 vxi        = nh_vxi[gt];
398             }
399             for (d = 0; d < DIM; d++)
400             {
401                 if ((ptype[n] != eptVSite) && (ptype[n] != eptShell))
402                 {
403                     vn  = (lg*vrel[d] + dt*(imass*f[n][d] - 0.5*vxi*vrel[d]
404                                             - nstpcouple*iprod(M[d], vrel)))/(1 + 0.5*vxi*dt);
405                     if (d == XX)
406                     {
407                         vn += vc + dt*cosz*cos_accel;
408                     }
409                     v[n][d]        = vn;
410                     xprime[n][d]   = x[n][d]+vn*dt;
411                 }
412                 else
413                 {
414                     xprime[n][d]   = x[n][d];
415                 }
416             }
417         }
418     }
419     else
420     {
421         /* Classic version of update, used with berendsen coupling */
422         for (n = start; n < nrend; n++)
423         {
424             w_dt = invmass[n]*dt;
425             if (cTC)
426             {
427                 gt   = cTC[n];
428             }
429             lg   = tcstat[gt].lambda;
430             cosz = cos(fac*x[n][ZZ]);
431
432             for (d = 0; d < DIM; d++)
433             {
434                 vn             = v[n][d];
435
436                 if ((ptype[n] != eptVSite) && (ptype[n] != eptShell))
437                 {
438                     if (d == XX)
439                     {
440                         vc           = cosz*vcos;
441                         /* Do not scale the cosine velocity profile */
442                         vv           = vc + lg*(vn - vc + f[n][d]*w_dt);
443                         /* Add the cosine accelaration profile */
444                         vv          += dt*cosz*cos_accel;
445                     }
446                     else
447                     {
448                         vv           = lg*(vn + f[n][d]*w_dt);
449                     }
450                     v[n][d]        = vv;
451                     xprime[n][d]   = x[n][d]+vv*dt;
452                 }
453                 else
454                 {
455                     v[n][d]        = 0.0;
456                     xprime[n][d]   = x[n][d];
457                 }
458             }
459         }
460     }
461 }
462
463 static gmx_stochd_t *init_stochd(t_inputrec *ir)
464 {
465     gmx_stochd_t   *sd;
466     gmx_sd_const_t *sdc;
467     int             ngtc, n;
468     real            y;
469
470     snew(sd, 1);
471
472     ngtc = ir->opts.ngtc;
473
474     if (ir->eI == eiBD)
475     {
476         snew(sd->bd_rf, ngtc);
477     }
478     else if (EI_SD(ir->eI))
479     {
480         snew(sd->sdc, ngtc);
481         snew(sd->sdsig, ngtc);
482
483         sdc = sd->sdc;
484         for (n = 0; n < ngtc; n++)
485         {
486             if (ir->opts.tau_t[n] > 0)
487             {
488                 sdc[n].gdt = ir->delta_t/ir->opts.tau_t[n];
489                 sdc[n].eph = exp(sdc[n].gdt/2);
490                 sdc[n].emh = exp(-sdc[n].gdt/2);
491                 sdc[n].em  = exp(-sdc[n].gdt);
492             }
493             else
494             {
495                 /* No friction and noise on this group */
496                 sdc[n].gdt = 0;
497                 sdc[n].eph = 1;
498                 sdc[n].emh = 1;
499                 sdc[n].em  = 1;
500             }
501             if (sdc[n].gdt >= 0.05)
502             {
503                 sdc[n].b = sdc[n].gdt*(sdc[n].eph*sdc[n].eph - 1)
504                     - 4*(sdc[n].eph - 1)*(sdc[n].eph - 1);
505                 sdc[n].c = sdc[n].gdt - 3 + 4*sdc[n].emh - sdc[n].em;
506                 sdc[n].d = 2 - sdc[n].eph - sdc[n].emh;
507             }
508             else
509             {
510                 y = sdc[n].gdt/2;
511                 /* Seventh order expansions for small y */
512                 sdc[n].b = y*y*y*y*(1/3.0+y*(1/3.0+y*(17/90.0+y*7/9.0)));
513                 sdc[n].c = y*y*y*(2/3.0+y*(-1/2.0+y*(7/30.0+y*(-1/12.0+y*31/1260.0))));
514                 sdc[n].d = y*y*(-1+y*y*(-1/12.0-y*y/360.0));
515             }
516             if (debug)
517             {
518                 fprintf(debug, "SD const tc-grp %d: b %g  c %g  d %g\n",
519                         n, sdc[n].b, sdc[n].c, sdc[n].d);
520             }
521         }
522     }
523     else if (ETC_ANDERSEN(ir->etc))
524     {
525         int        ngtc;
526         t_grpopts *opts;
527         real       reft;
528
529         opts = &ir->opts;
530         ngtc = opts->ngtc;
531
532         snew(sd->randomize_group, ngtc);
533         snew(sd->boltzfac, ngtc);
534
535         /* for now, assume that all groups, if randomized, are randomized at the same rate, i.e. tau_t is the same. */
536         /* since constraint groups don't necessarily match up with temperature groups! This is checked in readir.c */
537
538         for (n = 0; n < ngtc; n++)
539         {
540             reft = std::max<real>(0, opts->ref_t[n]);
541             if ((opts->tau_t[n] > 0) && (reft > 0))  /* tau_t or ref_t = 0 means that no randomization is done */
542             {
543                 sd->randomize_group[n] = TRUE;
544                 sd->boltzfac[n]        = BOLTZ*opts->ref_t[n];
545             }
546             else
547             {
548                 sd->randomize_group[n] = FALSE;
549             }
550         }
551     }
552     return sd;
553 }
554
555 gmx_update_t init_update(t_inputrec *ir)
556 {
557     t_gmx_update *upd;
558
559     snew(upd, 1);
560
561     if (ir->eI == eiBD || EI_SD(ir->eI) || ir->etc == etcVRESCALE || ETC_ANDERSEN(ir->etc))
562     {
563         upd->sd    = init_stochd(ir);
564     }
565
566     upd->xp        = NULL;
567     upd->xp_nalloc = 0;
568
569     return upd;
570 }
571
572 static void do_update_sd1(gmx_stochd_t *sd,
573                           int start, int nrend, double dt,
574                           rvec accel[], ivec nFreeze[],
575                           real invmass[], unsigned short ptype[],
576                           unsigned short cFREEZE[], unsigned short cACC[],
577                           unsigned short cTC[],
578                           rvec x[], rvec xprime[], rvec v[], rvec f[],
579                           int ngtc, real ref_t[],
580                           gmx_bool bDoConstr,
581                           gmx_bool bFirstHalfConstr,
582                           gmx_int64_t step, int seed, int* gatindex)
583 {
584     gmx_sd_const_t *sdc;
585     gmx_sd_sigma_t *sig;
586     real            kT;
587     int             gf = 0, ga = 0, gt = 0;
588     real            ism;
589     int             n, d;
590
591     sdc = sd->sdc;
592     sig = sd->sdsig;
593
594     for (n = 0; n < ngtc; n++)
595     {
596         kT = BOLTZ*ref_t[n];
597         /* The mass is encounted for later, since this differs per atom */
598         sig[n].V  = sqrt(kT*(1 - sdc[n].em*sdc[n].em));
599     }
600
601     if (!bDoConstr)
602     {
603         for (n = start; n < nrend; n++)
604         {
605             real rnd[3];
606             int  ng = gatindex ? gatindex[n] : n;
607
608             ism = sqrt(invmass[n]);
609             if (cFREEZE)
610             {
611                 gf  = cFREEZE[n];
612             }
613             if (cACC)
614             {
615                 ga  = cACC[n];
616             }
617             if (cTC)
618             {
619                 gt  = cTC[n];
620             }
621
622             gmx_rng_cycle_3gaussian_table(step, ng, seed, RND_SEED_UPDATE, rnd);
623
624             for (d = 0; d < DIM; d++)
625             {
626                 if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
627                 {
628                     real sd_V, vn;
629
630                     sd_V         = ism*sig[gt].V*rnd[d];
631                     vn           = v[n][d] + (invmass[n]*f[n][d] + accel[ga][d])*dt;
632                     v[n][d]      = vn*sdc[gt].em + sd_V;
633                     /* Here we include half of the friction+noise
634                      * update of v into the integration of x.
635                      */
636                     xprime[n][d] = x[n][d] + 0.5*(vn + v[n][d])*dt;
637                 }
638                 else
639                 {
640                     v[n][d]      = 0.0;
641                     xprime[n][d] = x[n][d];
642                 }
643             }
644         }
645     }
646     else
647     {
648         /* We do have constraints */
649         if (bFirstHalfConstr)
650         {
651             /* First update without friction and noise */
652             real im;
653
654             for (n = start; n < nrend; n++)
655             {
656                 im = invmass[n];
657
658                 if (cFREEZE)
659                 {
660                     gf  = cFREEZE[n];
661                 }
662                 if (cACC)
663                 {
664                     ga  = cACC[n];
665                 }
666
667                 for (d = 0; d < DIM; d++)
668                 {
669                     if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
670                     {
671                         v[n][d]      = v[n][d] + (im*f[n][d] + accel[ga][d])*dt;
672                         xprime[n][d] = x[n][d] +  v[n][d]*dt;
673                     }
674                     else
675                     {
676                         v[n][d]      = 0.0;
677                         xprime[n][d] = x[n][d];
678                     }
679                 }
680             }
681         }
682         else
683         {
684             /* Update friction and noise only */
685             for (n = start; n < nrend; n++)
686             {
687                 real rnd[3];
688                 int  ng = gatindex ? gatindex[n] : n;
689
690                 ism = sqrt(invmass[n]);
691                 if (cFREEZE)
692                 {
693                     gf  = cFREEZE[n];
694                 }
695                 if (cTC)
696                 {
697                     gt  = cTC[n];
698                 }
699
700                 gmx_rng_cycle_3gaussian_table(step, ng, seed, RND_SEED_UPDATE, rnd);
701
702                 for (d = 0; d < DIM; d++)
703                 {
704                     if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
705                     {
706                         real sd_V, vn;
707
708                         sd_V         = ism*sig[gt].V*rnd[d];
709                         vn           = v[n][d];
710                         v[n][d]      = vn*sdc[gt].em + sd_V;
711                         /* Add the friction and noise contribution only */
712                         xprime[n][d] = xprime[n][d] + 0.5*(v[n][d] - vn)*dt;
713                     }
714                 }
715             }
716         }
717     }
718 }
719
720 static void check_sd2_work_data_allocation(gmx_stochd_t *sd, int nrend)
721 {
722     if (nrend > sd->sd_V_nalloc)
723     {
724         sd->sd_V_nalloc = over_alloc_dd(nrend);
725         srenew(sd->sd_V, sd->sd_V_nalloc);
726     }
727 }
728
729 static void do_update_sd2_Tconsts(gmx_stochd_t *sd,
730                                   int           ngtc,
731                                   const real    tau_t[],
732                                   const real    ref_t[])
733 {
734     /* This is separated from the update below, because it is single threaded */
735     gmx_sd_const_t *sdc;
736     gmx_sd_sigma_t *sig;
737     int             gt;
738     real            kT;
739
740     sdc = sd->sdc;
741     sig = sd->sdsig;
742
743     for (gt = 0; gt < ngtc; gt++)
744     {
745         kT = BOLTZ*ref_t[gt];
746         /* The mass is encounted for later, since this differs per atom */
747         sig[gt].V  = sqrt(kT*(1-sdc[gt].em));
748         sig[gt].X  = sqrt(kT*sqr(tau_t[gt])*sdc[gt].c);
749         sig[gt].Yv = sqrt(kT*sdc[gt].b/sdc[gt].c);
750         sig[gt].Yx = sqrt(kT*sqr(tau_t[gt])*sdc[gt].b/(1-sdc[gt].em));
751     }
752 }
753
754 static void do_update_sd2(gmx_stochd_t *sd,
755                           gmx_bool bInitStep,
756                           int start, int nrend,
757                           rvec accel[], ivec nFreeze[],
758                           real invmass[], unsigned short ptype[],
759                           unsigned short cFREEZE[], unsigned short cACC[],
760                           unsigned short cTC[],
761                           rvec x[], rvec xprime[], rvec v[], rvec f[],
762                           rvec sd_X[],
763                           const real tau_t[],
764                           gmx_bool bFirstHalf, gmx_int64_t step, int seed,
765                           int* gatindex)
766 {
767     gmx_sd_const_t *sdc;
768     gmx_sd_sigma_t *sig;
769     /* The random part of the velocity update, generated in the first
770      * half of the update, needs to be remembered for the second half.
771      */
772     rvec  *sd_V;
773     int    gf = 0, ga = 0, gt = 0;
774     real   vn = 0, Vmh, Xmh;
775     real   ism;
776     int    n, d, ng;
777
778     sdc  = sd->sdc;
779     sig  = sd->sdsig;
780     sd_V = sd->sd_V;
781
782     for (n = start; n < nrend; n++)
783     {
784         real rnd[6], rndi[3];
785         ng  = gatindex ? gatindex[n] : n;
786         ism = sqrt(invmass[n]);
787         if (cFREEZE)
788         {
789             gf  = cFREEZE[n];
790         }
791         if (cACC)
792         {
793             ga  = cACC[n];
794         }
795         if (cTC)
796         {
797             gt  = cTC[n];
798         }
799
800         gmx_rng_cycle_6gaussian_table(step*2+(bFirstHalf ? 1 : 2), ng, seed, RND_SEED_UPDATE, rnd);
801         if (bInitStep)
802         {
803             gmx_rng_cycle_3gaussian_table(step*2, ng, seed, RND_SEED_UPDATE, rndi);
804         }
805         for (d = 0; d < DIM; d++)
806         {
807             if (bFirstHalf)
808             {
809                 vn             = v[n][d];
810             }
811             if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
812             {
813                 if (bFirstHalf)
814                 {
815                     if (bInitStep)
816                     {
817                         sd_X[n][d] = ism*sig[gt].X*rndi[d];
818                     }
819                     Vmh = sd_X[n][d]*sdc[gt].d/(tau_t[gt]*sdc[gt].c)
820                         + ism*sig[gt].Yv*rnd[d*2];
821                     sd_V[n][d] = ism*sig[gt].V*rnd[d*2+1];
822
823                     v[n][d] = vn*sdc[gt].em
824                         + (invmass[n]*f[n][d] + accel[ga][d])*tau_t[gt]*(1 - sdc[gt].em)
825                         + sd_V[n][d] - sdc[gt].em*Vmh;
826
827                     xprime[n][d] = x[n][d] + v[n][d]*tau_t[gt]*(sdc[gt].eph - sdc[gt].emh);
828                 }
829                 else
830                 {
831                     /* Correct the velocities for the constraints.
832                      * This operation introduces some inaccuracy,
833                      * since the velocity is determined from differences in coordinates.
834                      */
835                     v[n][d] =
836                         (xprime[n][d] - x[n][d])/(tau_t[gt]*(sdc[gt].eph - sdc[gt].emh));
837
838                     Xmh = sd_V[n][d]*tau_t[gt]*sdc[gt].d/(sdc[gt].em-1)
839                         + ism*sig[gt].Yx*rnd[d*2];
840                     sd_X[n][d] = ism*sig[gt].X*rnd[d*2+1];
841
842                     xprime[n][d] += sd_X[n][d] - Xmh;
843
844                 }
845             }
846             else
847             {
848                 if (bFirstHalf)
849                 {
850                     v[n][d]        = 0.0;
851                     xprime[n][d]   = x[n][d];
852                 }
853             }
854         }
855     }
856 }
857
858 static void do_update_bd_Tconsts(double dt, real friction_coefficient,
859                                  int ngtc, const real ref_t[],
860                                  real *rf)
861 {
862     /* This is separated from the update below, because it is single threaded */
863     int gt;
864
865     if (friction_coefficient != 0)
866     {
867         for (gt = 0; gt < ngtc; gt++)
868         {
869             rf[gt] = sqrt(2.0*BOLTZ*ref_t[gt]/(friction_coefficient*dt));
870         }
871     }
872     else
873     {
874         for (gt = 0; gt < ngtc; gt++)
875         {
876             rf[gt] = sqrt(2.0*BOLTZ*ref_t[gt]);
877         }
878     }
879 }
880
881 static void do_update_bd(int start, int nrend, double dt,
882                          ivec nFreeze[],
883                          real invmass[], unsigned short ptype[],
884                          unsigned short cFREEZE[], unsigned short cTC[],
885                          rvec x[], rvec xprime[], rvec v[],
886                          rvec f[], real friction_coefficient,
887                          real *rf, gmx_int64_t step, int seed,
888                          int* gatindex)
889 {
890     /* note -- these appear to be full step velocities . . .  */
891     int    gf = 0, gt = 0;
892     real   vn;
893     real   invfr = 0;
894     int    n, d;
895
896     if (friction_coefficient != 0)
897     {
898         invfr = 1.0/friction_coefficient;
899     }
900
901     for (n = start; (n < nrend); n++)
902     {
903         real rnd[3];
904         int  ng  = gatindex ? gatindex[n] : n;
905
906         if (cFREEZE)
907         {
908             gf = cFREEZE[n];
909         }
910         if (cTC)
911         {
912             gt = cTC[n];
913         }
914         gmx_rng_cycle_3gaussian_table(step, ng, seed, RND_SEED_UPDATE, rnd);
915         for (d = 0; (d < DIM); d++)
916         {
917             if ((ptype[n] != eptVSite) && (ptype[n] != eptShell) && !nFreeze[gf][d])
918             {
919                 if (friction_coefficient != 0)
920                 {
921                     vn = invfr*f[n][d] + rf[gt]*rnd[d];
922                 }
923                 else
924                 {
925                     /* NOTE: invmass = 2/(mass*friction_constant*dt) */
926                     vn = 0.5*invmass[n]*f[n][d]*dt
927                         + sqrt(0.5*invmass[n])*rf[gt]*rnd[d];
928                 }
929
930                 v[n][d]      = vn;
931                 xprime[n][d] = x[n][d]+vn*dt;
932             }
933             else
934             {
935                 v[n][d]      = 0.0;
936                 xprime[n][d] = x[n][d];
937             }
938         }
939     }
940 }
941
942 static void dump_it_all(FILE gmx_unused *fp, const char gmx_unused *title,
943                         int gmx_unused natoms, rvec gmx_unused x[], rvec gmx_unused xp[],
944                         rvec gmx_unused v[], rvec gmx_unused f[])
945 {
946 #ifdef DEBUG
947     if (fp)
948     {
949         fprintf(fp, "%s\n", title);
950         pr_rvecs(fp, 0, "x", x, natoms);
951         pr_rvecs(fp, 0, "xp", xp, natoms);
952         pr_rvecs(fp, 0, "v", v, natoms);
953         pr_rvecs(fp, 0, "f", f, natoms);
954     }
955 #endif
956 }
957
958 static void calc_ke_part_normal(rvec v[], t_grpopts *opts, t_mdatoms *md,
959                                 gmx_ekindata_t *ekind, t_nrnb *nrnb, gmx_bool bEkinAveVel)
960 {
961     int           g;
962     t_grp_tcstat *tcstat  = ekind->tcstat;
963     t_grp_acc    *grpstat = ekind->grpstat;
964     int           nthread, thread;
965
966     /* three main: VV with AveVel, vv with AveEkin, leap with AveEkin.  Leap with AveVel is also
967        an option, but not supported now.
968        bEkinAveVel: If TRUE, we sum into ekin, if FALSE, into ekinh.
969      */
970
971     /* group velocities are calculated in update_ekindata and
972      * accumulated in acumulate_groups.
973      * Now the partial global and groups ekin.
974      */
975     for (g = 0; (g < opts->ngtc); g++)
976     {
977         copy_mat(tcstat[g].ekinh, tcstat[g].ekinh_old);
978         if (bEkinAveVel)
979         {
980             clear_mat(tcstat[g].ekinf);
981             tcstat[g].ekinscalef_nhc = 1.0;   /* need to clear this -- logic is complicated! */
982         }
983         else
984         {
985             clear_mat(tcstat[g].ekinh);
986         }
987     }
988     ekind->dekindl_old = ekind->dekindl;
989     nthread            = gmx_omp_nthreads_get(emntUpdate);
990
991 #pragma omp parallel for num_threads(nthread) schedule(static)
992     for (thread = 0; thread < nthread; thread++)
993     {
994         int     start_t, end_t, n;
995         int     ga, gt;
996         rvec    v_corrt;
997         real    hm;
998         int     d, m;
999         matrix *ekin_sum;
1000         real   *dekindl_sum;
1001
1002         start_t = ((thread+0)*md->homenr)/nthread;
1003         end_t   = ((thread+1)*md->homenr)/nthread;
1004
1005         ekin_sum    = ekind->ekin_work[thread];
1006         dekindl_sum = ekind->dekindl_work[thread];
1007
1008         for (gt = 0; gt < opts->ngtc; gt++)
1009         {
1010             clear_mat(ekin_sum[gt]);
1011         }
1012         *dekindl_sum = 0.0;
1013
1014         ga = 0;
1015         gt = 0;
1016         for (n = start_t; n < end_t; n++)
1017         {
1018             if (md->cACC)
1019             {
1020                 ga = md->cACC[n];
1021             }
1022             if (md->cTC)
1023             {
1024                 gt = md->cTC[n];
1025             }
1026             hm   = 0.5*md->massT[n];
1027
1028             for (d = 0; (d < DIM); d++)
1029             {
1030                 v_corrt[d]  = v[n][d]  - grpstat[ga].u[d];
1031             }
1032             for (d = 0; (d < DIM); d++)
1033             {
1034                 for (m = 0; (m < DIM); m++)
1035                 {
1036                     /* if we're computing a full step velocity, v_corrt[d] has v(t).  Otherwise, v(t+dt/2) */
1037                     ekin_sum[gt][m][d] += hm*v_corrt[m]*v_corrt[d];
1038                 }
1039             }
1040             if (md->nMassPerturbed && md->bPerturbed[n])
1041             {
1042                 *dekindl_sum +=
1043                     0.5*(md->massB[n] - md->massA[n])*iprod(v_corrt, v_corrt);
1044             }
1045         }
1046     }
1047
1048     ekind->dekindl = 0;
1049     for (thread = 0; thread < nthread; thread++)
1050     {
1051         for (g = 0; g < opts->ngtc; g++)
1052         {
1053             if (bEkinAveVel)
1054             {
1055                 m_add(tcstat[g].ekinf, ekind->ekin_work[thread][g],
1056                       tcstat[g].ekinf);
1057             }
1058             else
1059             {
1060                 m_add(tcstat[g].ekinh, ekind->ekin_work[thread][g],
1061                       tcstat[g].ekinh);
1062             }
1063         }
1064
1065         ekind->dekindl += *ekind->dekindl_work[thread];
1066     }
1067
1068     inc_nrnb(nrnb, eNR_EKIN, md->homenr);
1069 }
1070
1071 static void calc_ke_part_visc(matrix box, rvec x[], rvec v[],
1072                               t_grpopts *opts, t_mdatoms *md,
1073                               gmx_ekindata_t *ekind,
1074                               t_nrnb *nrnb, gmx_bool bEkinAveVel)
1075 {
1076     int           start = 0, homenr = md->homenr;
1077     int           g, d, n, m, gt = 0;
1078     rvec          v_corrt;
1079     real          hm;
1080     t_grp_tcstat *tcstat = ekind->tcstat;
1081     t_cos_acc    *cosacc = &(ekind->cosacc);
1082     real          dekindl;
1083     real          fac, cosz;
1084     double        mvcos;
1085
1086     for (g = 0; g < opts->ngtc; g++)
1087     {
1088         copy_mat(ekind->tcstat[g].ekinh, ekind->tcstat[g].ekinh_old);
1089         clear_mat(ekind->tcstat[g].ekinh);
1090     }
1091     ekind->dekindl_old = ekind->dekindl;
1092
1093     fac     = 2*M_PI/box[ZZ][ZZ];
1094     mvcos   = 0;
1095     dekindl = 0;
1096     for (n = start; n < start+homenr; n++)
1097     {
1098         if (md->cTC)
1099         {
1100             gt = md->cTC[n];
1101         }
1102         hm   = 0.5*md->massT[n];
1103
1104         /* Note that the times of x and v differ by half a step */
1105         /* MRS -- would have to be changed for VV */
1106         cosz         = cos(fac*x[n][ZZ]);
1107         /* Calculate the amplitude of the new velocity profile */
1108         mvcos       += 2*cosz*md->massT[n]*v[n][XX];
1109
1110         copy_rvec(v[n], v_corrt);
1111         /* Subtract the profile for the kinetic energy */
1112         v_corrt[XX] -= cosz*cosacc->vcos;
1113         for (d = 0; (d < DIM); d++)
1114         {
1115             for (m = 0; (m < DIM); m++)
1116             {
1117                 /* if we're computing a full step velocity, v_corrt[d] has v(t).  Otherwise, v(t+dt/2) */
1118                 if (bEkinAveVel)
1119                 {
1120                     tcstat[gt].ekinf[m][d] += hm*v_corrt[m]*v_corrt[d];
1121                 }
1122                 else
1123                 {
1124                     tcstat[gt].ekinh[m][d] += hm*v_corrt[m]*v_corrt[d];
1125                 }
1126             }
1127         }
1128         if (md->nPerturbed && md->bPerturbed[n])
1129         {
1130             /* The minus sign here might be confusing.
1131              * The kinetic contribution from dH/dl doesn't come from
1132              * d m(l)/2 v^2 / dl, but rather from d p^2/2m(l) / dl,
1133              * where p are the momenta. The difference is only a minus sign.
1134              */
1135             dekindl -= 0.5*(md->massB[n] - md->massA[n])*iprod(v_corrt, v_corrt);
1136         }
1137     }
1138     ekind->dekindl = dekindl;
1139     cosacc->mvcos  = mvcos;
1140
1141     inc_nrnb(nrnb, eNR_EKIN, homenr);
1142 }
1143
1144 void calc_ke_part(t_state *state, t_grpopts *opts, t_mdatoms *md,
1145                   gmx_ekindata_t *ekind, t_nrnb *nrnb, gmx_bool bEkinAveVel)
1146 {
1147     if (ekind->cosacc.cos_accel == 0)
1148     {
1149         calc_ke_part_normal(state->v, opts, md, ekind, nrnb, bEkinAveVel);
1150     }
1151     else
1152     {
1153         calc_ke_part_visc(state->box, state->x, state->v, opts, md, ekind, nrnb, bEkinAveVel);
1154     }
1155 }
1156
1157 extern void init_ekinstate(ekinstate_t *ekinstate, const t_inputrec *ir)
1158 {
1159     ekinstate->ekin_n = ir->opts.ngtc;
1160     snew(ekinstate->ekinh, ekinstate->ekin_n);
1161     snew(ekinstate->ekinf, ekinstate->ekin_n);
1162     snew(ekinstate->ekinh_old, ekinstate->ekin_n);
1163     snew(ekinstate->ekinscalef_nhc, ekinstate->ekin_n);
1164     snew(ekinstate->ekinscaleh_nhc, ekinstate->ekin_n);
1165     snew(ekinstate->vscale_nhc, ekinstate->ekin_n);
1166     ekinstate->dekindl = 0;
1167     ekinstate->mvcos   = 0;
1168 }
1169
1170 void update_ekinstate(ekinstate_t *ekinstate, gmx_ekindata_t *ekind)
1171 {
1172     int i;
1173
1174     for (i = 0; i < ekinstate->ekin_n; i++)
1175     {
1176         copy_mat(ekind->tcstat[i].ekinh, ekinstate->ekinh[i]);
1177         copy_mat(ekind->tcstat[i].ekinf, ekinstate->ekinf[i]);
1178         copy_mat(ekind->tcstat[i].ekinh_old, ekinstate->ekinh_old[i]);
1179         ekinstate->ekinscalef_nhc[i] = ekind->tcstat[i].ekinscalef_nhc;
1180         ekinstate->ekinscaleh_nhc[i] = ekind->tcstat[i].ekinscaleh_nhc;
1181         ekinstate->vscale_nhc[i]     = ekind->tcstat[i].vscale_nhc;
1182     }
1183
1184     copy_mat(ekind->ekin, ekinstate->ekin_total);
1185     ekinstate->dekindl = ekind->dekindl;
1186     ekinstate->mvcos   = ekind->cosacc.mvcos;
1187
1188 }
1189
1190 void restore_ekinstate_from_state(t_commrec *cr,
1191                                   gmx_ekindata_t *ekind, ekinstate_t *ekinstate)
1192 {
1193     int i, n;
1194
1195     if (MASTER(cr))
1196     {
1197         for (i = 0; i < ekinstate->ekin_n; i++)
1198         {
1199             copy_mat(ekinstate->ekinh[i], ekind->tcstat[i].ekinh);
1200             copy_mat(ekinstate->ekinf[i], ekind->tcstat[i].ekinf);
1201             copy_mat(ekinstate->ekinh_old[i], ekind->tcstat[i].ekinh_old);
1202             ekind->tcstat[i].ekinscalef_nhc = ekinstate->ekinscalef_nhc[i];
1203             ekind->tcstat[i].ekinscaleh_nhc = ekinstate->ekinscaleh_nhc[i];
1204             ekind->tcstat[i].vscale_nhc     = ekinstate->vscale_nhc[i];
1205         }
1206
1207         copy_mat(ekinstate->ekin_total, ekind->ekin);
1208
1209         ekind->dekindl      = ekinstate->dekindl;
1210         ekind->cosacc.mvcos = ekinstate->mvcos;
1211         n                   = ekinstate->ekin_n;
1212     }
1213
1214     if (PAR(cr))
1215     {
1216         gmx_bcast(sizeof(n), &n, cr);
1217         for (i = 0; i < n; i++)
1218         {
1219             gmx_bcast(DIM*DIM*sizeof(ekind->tcstat[i].ekinh[0][0]),
1220                       ekind->tcstat[i].ekinh[0], cr);
1221             gmx_bcast(DIM*DIM*sizeof(ekind->tcstat[i].ekinf[0][0]),
1222                       ekind->tcstat[i].ekinf[0], cr);
1223             gmx_bcast(DIM*DIM*sizeof(ekind->tcstat[i].ekinh_old[0][0]),
1224                       ekind->tcstat[i].ekinh_old[0], cr);
1225
1226             gmx_bcast(sizeof(ekind->tcstat[i].ekinscalef_nhc),
1227                       &(ekind->tcstat[i].ekinscalef_nhc), cr);
1228             gmx_bcast(sizeof(ekind->tcstat[i].ekinscaleh_nhc),
1229                       &(ekind->tcstat[i].ekinscaleh_nhc), cr);
1230             gmx_bcast(sizeof(ekind->tcstat[i].vscale_nhc),
1231                       &(ekind->tcstat[i].vscale_nhc), cr);
1232         }
1233         gmx_bcast(DIM*DIM*sizeof(ekind->ekin[0][0]),
1234                   ekind->ekin[0], cr);
1235
1236         gmx_bcast(sizeof(ekind->dekindl), &ekind->dekindl, cr);
1237         gmx_bcast(sizeof(ekind->cosacc.mvcos), &ekind->cosacc.mvcos, cr);
1238     }
1239 }
1240
1241 void set_deform_reference_box(gmx_update_t upd, gmx_int64_t step, matrix box)
1242 {
1243     upd->deformref_step = step;
1244     copy_mat(box, upd->deformref_box);
1245 }
1246
1247 static void deform(gmx_update_t upd,
1248                    int start, int homenr, rvec x[], matrix box,
1249                    const t_inputrec *ir, gmx_int64_t step)
1250 {
1251     matrix bnew, invbox, mu;
1252     real   elapsed_time;
1253     int    i, j;
1254
1255     elapsed_time = (step + 1 - upd->deformref_step)*ir->delta_t;
1256     copy_mat(box, bnew);
1257     for (i = 0; i < DIM; i++)
1258     {
1259         for (j = 0; j < DIM; j++)
1260         {
1261             if (ir->deform[i][j] != 0)
1262             {
1263                 bnew[i][j] =
1264                     upd->deformref_box[i][j] + elapsed_time*ir->deform[i][j];
1265             }
1266         }
1267     }
1268     /* We correct the off-diagonal elements,
1269      * which can grow indefinitely during shearing,
1270      * so the shifts do not get messed up.
1271      */
1272     for (i = 1; i < DIM; i++)
1273     {
1274         for (j = i-1; j >= 0; j--)
1275         {
1276             while (bnew[i][j] - box[i][j] > 0.5*bnew[j][j])
1277             {
1278                 rvec_dec(bnew[i], bnew[j]);
1279             }
1280             while (bnew[i][j] - box[i][j] < -0.5*bnew[j][j])
1281             {
1282                 rvec_inc(bnew[i], bnew[j]);
1283             }
1284         }
1285     }
1286     m_inv_ur0(box, invbox);
1287     copy_mat(bnew, box);
1288     mmul_ur0(box, invbox, mu);
1289
1290     for (i = start; i < start+homenr; i++)
1291     {
1292         x[i][XX] = mu[XX][XX]*x[i][XX]+mu[YY][XX]*x[i][YY]+mu[ZZ][XX]*x[i][ZZ];
1293         x[i][YY] = mu[YY][YY]*x[i][YY]+mu[ZZ][YY]*x[i][ZZ];
1294         x[i][ZZ] = mu[ZZ][ZZ]*x[i][ZZ];
1295     }
1296 }
1297
1298 void update_tcouple(gmx_int64_t       step,
1299                     t_inputrec       *inputrec,
1300                     t_state          *state,
1301                     gmx_ekindata_t   *ekind,
1302                     t_extmass        *MassQ,
1303                     t_mdatoms        *md)
1304
1305 {
1306     gmx_bool   bTCouple = FALSE;
1307     real       dttc;
1308     int        i, offset;
1309
1310     /* if using vv with trotter decomposition methods, we do this elsewhere in the code */
1311     if (inputrec->etc != etcNO &&
1312         !(IR_NVT_TROTTER(inputrec) || IR_NPT_TROTTER(inputrec) || IR_NPH_TROTTER(inputrec)))
1313     {
1314         /* We should only couple after a step where energies were determined (for leapfrog versions)
1315            or the step energies are determined, for velocity verlet versions */
1316
1317         if (EI_VV(inputrec->eI))
1318         {
1319             offset = 0;
1320         }
1321         else
1322         {
1323             offset = 1;
1324         }
1325         bTCouple = (inputrec->nsttcouple == 1 ||
1326                     do_per_step(step+inputrec->nsttcouple-offset,
1327                                 inputrec->nsttcouple));
1328     }
1329
1330     if (bTCouple)
1331     {
1332         dttc = inputrec->nsttcouple*inputrec->delta_t;
1333
1334         switch (inputrec->etc)
1335         {
1336             case etcNO:
1337                 break;
1338             case etcBERENDSEN:
1339                 berendsen_tcoupl(inputrec, ekind, dttc);
1340                 break;
1341             case etcNOSEHOOVER:
1342                 nosehoover_tcoupl(&(inputrec->opts), ekind, dttc,
1343                                   state->nosehoover_xi, state->nosehoover_vxi, MassQ);
1344                 break;
1345             case etcVRESCALE:
1346                 vrescale_tcoupl(inputrec, step, ekind, dttc,
1347                                 state->therm_integral);
1348                 break;
1349         }
1350         /* rescale in place here */
1351         if (EI_VV(inputrec->eI))
1352         {
1353             rescale_velocities(ekind, md, 0, md->homenr, state->v);
1354         }
1355     }
1356     else
1357     {
1358         /* Set the T scaling lambda to 1 to have no scaling */
1359         for (i = 0; (i < inputrec->opts.ngtc); i++)
1360         {
1361             ekind->tcstat[i].lambda = 1.0;
1362         }
1363     }
1364 }
1365
1366 void update_pcouple(FILE             *fplog,
1367                     gmx_int64_t       step,
1368                     t_inputrec       *inputrec,
1369                     t_state          *state,
1370                     matrix            pcoupl_mu,
1371                     matrix            M,
1372                     gmx_bool          bInitStep)
1373 {
1374     gmx_bool   bPCouple = FALSE;
1375     real       dtpc     = 0;
1376     int        i;
1377
1378     /* if using Trotter pressure, we do this in coupling.c, so we leave it false. */
1379     if (inputrec->epc != epcNO && (!(IR_NPT_TROTTER(inputrec) || IR_NPH_TROTTER(inputrec))))
1380     {
1381         /* We should only couple after a step where energies were determined */
1382         bPCouple = (inputrec->nstpcouple == 1 ||
1383                     do_per_step(step+inputrec->nstpcouple-1,
1384                                 inputrec->nstpcouple));
1385     }
1386
1387     clear_mat(pcoupl_mu);
1388     for (i = 0; i < DIM; i++)
1389     {
1390         pcoupl_mu[i][i] = 1.0;
1391     }
1392
1393     clear_mat(M);
1394
1395     if (bPCouple)
1396     {
1397         dtpc = inputrec->nstpcouple*inputrec->delta_t;
1398
1399         switch (inputrec->epc)
1400         {
1401             /* We can always pcoupl, even if we did not sum the energies
1402              * the previous step, since state->pres_prev is only updated
1403              * when the energies have been summed.
1404              */
1405             case (epcNO):
1406                 break;
1407             case (epcBERENDSEN):
1408                 if (!bInitStep)
1409                 {
1410                     berendsen_pcoupl(fplog, step, inputrec, dtpc, state->pres_prev, state->box,
1411                                      pcoupl_mu);
1412                 }
1413                 break;
1414             case (epcPARRINELLORAHMAN):
1415                 parrinellorahman_pcoupl(fplog, step, inputrec, dtpc, state->pres_prev,
1416                                         state->box, state->box_rel, state->boxv,
1417                                         M, pcoupl_mu, bInitStep);
1418                 break;
1419             default:
1420                 break;
1421         }
1422     }
1423 }
1424
1425 static rvec *get_xprime(const t_state *state, gmx_update_t upd)
1426 {
1427     if (state->nalloc > upd->xp_nalloc)
1428     {
1429         upd->xp_nalloc = state->nalloc;
1430         srenew(upd->xp, upd->xp_nalloc);
1431     }
1432
1433     return upd->xp;
1434 }
1435
1436 static void combine_forces(gmx_update_t upd,
1437                            int nstcalclr,
1438                            gmx_constr_t constr,
1439                            t_inputrec *ir, t_mdatoms *md, t_idef *idef,
1440                            t_commrec *cr,
1441                            gmx_int64_t step,
1442                            t_state *state, gmx_bool bMolPBC,
1443                            int start, int nrend,
1444                            rvec f[], rvec f_lr[],
1445                            tensor *vir_lr_constr,
1446                            t_nrnb *nrnb)
1447 {
1448     int  i, d;
1449
1450     /* f contains the short-range forces + the long range forces
1451      * which are stored separately in f_lr.
1452      */
1453
1454     if (constr != NULL && vir_lr_constr != NULL &&
1455         !(ir->eConstrAlg == econtSHAKE && ir->epc == epcNO))
1456     {
1457         /* We need to constrain the LR forces separately,
1458          * because due to the different pre-factor for the SR and LR
1459          * forces in the update algorithm, we have to correct
1460          * the constraint virial for the nstcalclr-1 extra f_lr.
1461          * Constrain only the additional LR part of the force.
1462          */
1463         /* MRS -- need to make sure this works with trotter integration -- the constraint calls may not be right.*/
1464         rvec *xp;
1465         real  fac;
1466         int   gf = 0;
1467
1468         xp  = get_xprime(state, upd);
1469
1470         fac = (nstcalclr - 1)*ir->delta_t*ir->delta_t;
1471
1472         for (i = 0; i < md->homenr; i++)
1473         {
1474             if (md->cFREEZE != NULL)
1475             {
1476                 gf = md->cFREEZE[i];
1477             }
1478             for (d = 0; d < DIM; d++)
1479             {
1480                 if ((md->ptype[i] != eptVSite) &&
1481                     (md->ptype[i] != eptShell) &&
1482                     !ir->opts.nFreeze[gf][d])
1483                 {
1484                     xp[i][d] = state->x[i][d] + fac*f_lr[i][d]*md->invmass[i];
1485                 }
1486                 else
1487                 {
1488                     xp[i][d] = state->x[i][d];
1489                 }
1490             }
1491         }
1492         constrain(NULL, FALSE, FALSE, constr, idef, ir, cr, step, 0, 1.0, md,
1493                   state->x, xp, xp, bMolPBC, state->box, state->lambda[efptBONDED], NULL,
1494                   NULL, vir_lr_constr, nrnb, econqForce);
1495     }
1496
1497     /* Add nstcalclr-1 times the LR force to the sum of both forces
1498      * and store the result in forces_lr.
1499      */
1500     for (i = start; i < nrend; i++)
1501     {
1502         for (d = 0; d < DIM; d++)
1503         {
1504             f_lr[i][d] = f[i][d] + (nstcalclr - 1)*f_lr[i][d];
1505         }
1506     }
1507 }
1508
1509 void update_constraints(FILE             *fplog,
1510                         gmx_int64_t       step,
1511                         real             *dvdlambda, /* the contribution to be added to the bonded interactions */
1512                         t_inputrec       *inputrec,  /* input record and box stuff      */
1513                         t_mdatoms        *md,
1514                         t_state          *state,
1515                         gmx_bool          bMolPBC,
1516                         t_graph          *graph,
1517                         rvec              force[],   /* forces on home particles */
1518                         t_idef           *idef,
1519                         tensor            vir_part,
1520                         t_commrec        *cr,
1521                         t_nrnb           *nrnb,
1522                         gmx_wallcycle_t   wcycle,
1523                         gmx_update_t      upd,
1524                         gmx_constr_t      constr,
1525                         gmx_bool          bFirstHalf,
1526                         gmx_bool          bCalcVir)
1527 {
1528     gmx_bool             bLastStep, bLog = FALSE, bEner = FALSE, bDoConstr = FALSE;
1529     double               dt;
1530     int                  start, homenr, nrend, i, m;
1531     tensor               vir_con;
1532     rvec                *xprime = NULL;
1533     int                  nth, th;
1534
1535     if (constr)
1536     {
1537         bDoConstr = TRUE;
1538     }
1539     if (bFirstHalf && !EI_VV(inputrec->eI))
1540     {
1541         bDoConstr = FALSE;
1542     }
1543
1544     /* for now, SD update is here -- though it really seems like it
1545        should be reformulated as a velocity verlet method, since it has two parts */
1546
1547     start  = 0;
1548     homenr = md->homenr;
1549     nrend  = start+homenr;
1550
1551     dt   = inputrec->delta_t;
1552
1553     /*
1554      *  Steps (7C, 8C)
1555      *  APPLY CONSTRAINTS:
1556      *  BLOCK SHAKE
1557
1558      * When doing PR pressure coupling we have to constrain the
1559      * bonds in each iteration. If we are only using Nose-Hoover tcoupling
1560      * it is enough to do this once though, since the relative velocities
1561      * after this will be normal to the bond vector
1562      */
1563
1564     if (bDoConstr)
1565     {
1566         /* clear out constraints before applying */
1567         clear_mat(vir_part);
1568
1569         xprime = get_xprime(state, upd);
1570
1571         bLastStep = (step == inputrec->init_step+inputrec->nsteps);
1572         bLog      = (do_per_step(step, inputrec->nstlog) || bLastStep || (step < 0));
1573         bEner     = (do_per_step(step, inputrec->nstenergy) || bLastStep);
1574         /* Constrain the coordinates xprime */
1575         wallcycle_start(wcycle, ewcCONSTR);
1576         if (EI_VV(inputrec->eI) && bFirstHalf)
1577         {
1578             constrain(NULL, bLog, bEner, constr, idef,
1579                       inputrec, cr, step, 1, 1.0, md,
1580                       state->x, state->v, state->v,
1581                       bMolPBC, state->box,
1582                       state->lambda[efptBONDED], dvdlambda,
1583                       NULL, bCalcVir ? &vir_con : NULL, nrnb, econqVeloc);
1584         }
1585         else
1586         {
1587             constrain(NULL, bLog, bEner, constr, idef,
1588                       inputrec, cr, step, 1, 1.0, md,
1589                       state->x, xprime, NULL,
1590                       bMolPBC, state->box,
1591                       state->lambda[efptBONDED], dvdlambda,
1592                       state->v, bCalcVir ? &vir_con : NULL, nrnb, econqCoord);
1593         }
1594         wallcycle_stop(wcycle, ewcCONSTR);
1595
1596         where();
1597
1598         dump_it_all(fplog, "After Shake",
1599                     state->natoms, state->x, xprime, state->v, force);
1600
1601         if (bCalcVir)
1602         {
1603             if (inputrec->eI == eiSD2)
1604             {
1605                 /* A correction factor eph is needed for the SD constraint force */
1606                 /* Here we can, unfortunately, not have proper corrections
1607                  * for different friction constants, so we use the first one.
1608                  */
1609                 for (i = 0; i < DIM; i++)
1610                 {
1611                     for (m = 0; m < DIM; m++)
1612                     {
1613                         vir_part[i][m] += upd->sd->sdc[0].eph*vir_con[i][m];
1614                     }
1615                 }
1616             }
1617             else
1618             {
1619                 m_add(vir_part, vir_con, vir_part);
1620             }
1621             if (debug)
1622             {
1623                 pr_rvecs(debug, 0, "constraint virial", vir_part, DIM);
1624             }
1625         }
1626     }
1627
1628     where();
1629
1630     if (inputrec->eI == eiSD1 && bDoConstr && !bFirstHalf)
1631     {
1632         wallcycle_start(wcycle, ewcUPDATE);
1633         xprime = get_xprime(state, upd);
1634
1635         nth = gmx_omp_nthreads_get(emntUpdate);
1636
1637 #pragma omp parallel for num_threads(nth) schedule(static)
1638
1639         for (th = 0; th < nth; th++)
1640         {
1641             int start_th, end_th;
1642
1643             start_th = start + ((nrend-start)* th   )/nth;
1644             end_th   = start + ((nrend-start)*(th+1))/nth;
1645
1646             /* The second part of the SD integration */
1647             do_update_sd1(upd->sd,
1648                           start_th, end_th, dt,
1649                           inputrec->opts.acc, inputrec->opts.nFreeze,
1650                           md->invmass, md->ptype,
1651                           md->cFREEZE, md->cACC, md->cTC,
1652                           state->x, xprime, state->v, force,
1653                           inputrec->opts.ngtc, inputrec->opts.ref_t,
1654                           bDoConstr, FALSE,
1655                           step, inputrec->ld_seed,
1656                           DOMAINDECOMP(cr) ? cr->dd->gatindex : NULL);
1657         }
1658         inc_nrnb(nrnb, eNR_UPDATE, homenr);
1659         wallcycle_stop(wcycle, ewcUPDATE);
1660
1661         if (bDoConstr)
1662         {
1663             /* Constrain the coordinates xprime for half a time step */
1664             wallcycle_start(wcycle, ewcCONSTR);
1665
1666             constrain(NULL, bLog, bEner, constr, idef,
1667                       inputrec, cr, step, 1, 0.5, md,
1668                       state->x, xprime, NULL,
1669                       bMolPBC, state->box,
1670                       state->lambda[efptBONDED], dvdlambda,
1671                       state->v, NULL, nrnb, econqCoord);
1672
1673             wallcycle_stop(wcycle, ewcCONSTR);
1674         }
1675     }
1676
1677     if ((inputrec->eI == eiSD2) && !(bFirstHalf))
1678     {
1679         wallcycle_start(wcycle, ewcUPDATE);
1680         xprime = get_xprime(state, upd);
1681
1682         nth = gmx_omp_nthreads_get(emntUpdate);
1683
1684 #pragma omp parallel for num_threads(nth) schedule(static)
1685         for (th = 0; th < nth; th++)
1686         {
1687             int start_th, end_th;
1688
1689             start_th = start + ((nrend-start)* th   )/nth;
1690             end_th   = start + ((nrend-start)*(th+1))/nth;
1691
1692             /* The second part of the SD integration */
1693             do_update_sd2(upd->sd,
1694                           FALSE, start_th, end_th,
1695                           inputrec->opts.acc, inputrec->opts.nFreeze,
1696                           md->invmass, md->ptype,
1697                           md->cFREEZE, md->cACC, md->cTC,
1698                           state->x, xprime, state->v, force, state->sd_X,
1699                           inputrec->opts.tau_t,
1700                           FALSE, step, inputrec->ld_seed,
1701                           DOMAINDECOMP(cr) ? cr->dd->gatindex : NULL);
1702         }
1703         inc_nrnb(nrnb, eNR_UPDATE, homenr);
1704         wallcycle_stop(wcycle, ewcUPDATE);
1705
1706         if (bDoConstr)
1707         {
1708             /* Constrain the coordinates xprime */
1709             wallcycle_start(wcycle, ewcCONSTR);
1710             constrain(NULL, bLog, bEner, constr, idef,
1711                       inputrec, cr, step, 1, 1.0, md,
1712                       state->x, xprime, NULL,
1713                       bMolPBC, state->box,
1714                       state->lambda[efptBONDED], dvdlambda,
1715                       NULL, NULL, nrnb, econqCoord);
1716             wallcycle_stop(wcycle, ewcCONSTR);
1717         }
1718     }
1719
1720
1721     /* We must always unshift after updating coordinates; if we did not shake
1722        x was shifted in do_force */
1723
1724     if (!(bFirstHalf)) /* in the first half of vv, no shift. */
1725     {
1726         /* NOTE This part of the update actually does not belong with
1727          * the constraints, since we also call it without constraints.
1728          * But currently we always integrate to a temporary buffer and
1729          * then copy the results back here.
1730          */
1731         wallcycle_start_nocount(wcycle, ewcUPDATE);
1732
1733         if (md->cFREEZE != NULL && constr != NULL)
1734         {
1735             /* If we have atoms that are frozen along some, but not all
1736              * dimensions, the constraints will have moved them also along
1737              * the frozen dimensions. To freeze such degrees of freedom
1738              * we copy them back here to later copy them forward. It would
1739              * be more elegant and slightly more efficient to copies zero
1740              * times instead of twice, but the graph case below prevents this.
1741              */
1742             const ivec *nFreeze                     = inputrec->opts.nFreeze;
1743             bool        partialFreezeAndConstraints = false;
1744             for (int g = 0; g < inputrec->opts.ngfrz; g++)
1745             {
1746                 int numFreezeDim = nFreeze[g][XX] + nFreeze[g][YY] + nFreeze[g][ZZ];
1747                 if (numFreezeDim > 0 && numFreezeDim < 3)
1748                 {
1749                     partialFreezeAndConstraints = true;
1750                 }
1751             }
1752             if (partialFreezeAndConstraints)
1753             {
1754                 for (int i = start; i < nrend; i++)
1755                 {
1756                     int g = md->cFREEZE[i];
1757
1758                     for (int d = 0; d < DIM; d++)
1759                     {
1760                         if (nFreeze[g][d])
1761                         {
1762                             upd->xp[i][d] = state->x[i][d];
1763                         }
1764                     }
1765                 }
1766             }
1767         }
1768
1769         if (graph && (graph->nnodes > 0))
1770         {
1771             unshift_x(graph, state->box, state->x, upd->xp);
1772             if (TRICLINIC(state->box))
1773             {
1774                 inc_nrnb(nrnb, eNR_SHIFTX, 2*graph->nnodes);
1775             }
1776             else
1777             {
1778                 inc_nrnb(nrnb, eNR_SHIFTX, graph->nnodes);
1779             }
1780         }
1781         else
1782         {
1783 #ifndef __clang_analyzer__
1784             // cppcheck-suppress unreadVariable
1785             nth = gmx_omp_nthreads_get(emntUpdate);
1786 #endif
1787 #pragma omp parallel for num_threads(nth) schedule(static)
1788             for (i = start; i < nrend; i++)
1789             {
1790                 copy_rvec(upd->xp[i], state->x[i]);
1791             }
1792         }
1793         wallcycle_stop(wcycle, ewcUPDATE);
1794
1795         dump_it_all(fplog, "After unshift",
1796                     state->natoms, state->x, upd->xp, state->v, force);
1797     }
1798 /* ############# END the update of velocities and positions ######### */
1799 }
1800
1801 void update_box(FILE             *fplog,
1802                 gmx_int64_t       step,
1803                 t_inputrec       *inputrec,  /* input record and box stuff      */
1804                 t_mdatoms        *md,
1805                 t_state          *state,
1806                 rvec              force[],   /* forces on home particles */
1807                 matrix            pcoupl_mu,
1808                 t_nrnb           *nrnb,
1809                 gmx_update_t      upd)
1810 {
1811     double               dt;
1812     int                  start, homenr, i, n, m;
1813
1814     start  = 0;
1815     homenr = md->homenr;
1816
1817     dt = inputrec->delta_t;
1818
1819     where();
1820
1821     /* now update boxes */
1822     switch (inputrec->epc)
1823     {
1824         case (epcNO):
1825             break;
1826         case (epcBERENDSEN):
1827             /* We should only scale after a step where the pressure (kinetic
1828              * energy and virial) was calculated. This happens after the
1829              * coordinate update, whereas the current routine is called before
1830              * that, so we scale when step % nstpcouple = 1 instead of 0.
1831              */
1832             if (inputrec->nstpcouple == 1 || (step % inputrec->nstpcouple == 1))
1833             {
1834                 berendsen_pscale(inputrec, pcoupl_mu, state->box, state->box_rel,
1835                                  start, homenr, state->x, md->cFREEZE, nrnb);
1836             }
1837             break;
1838         case (epcPARRINELLORAHMAN):
1839             /* The box velocities were updated in do_pr_pcoupl in the update
1840              * iteration, but we dont change the box vectors until we get here
1841              * since we need to be able to shift/unshift above.
1842              */
1843             for (i = 0; i < DIM; i++)
1844             {
1845                 for (m = 0; m <= i; m++)
1846                 {
1847                     state->box[i][m] += dt*state->boxv[i][m];
1848                 }
1849             }
1850             preserve_box_shape(inputrec, state->box_rel, state->box);
1851
1852             /* Scale the coordinates */
1853             for (n = start; (n < start+homenr); n++)
1854             {
1855                 tmvmul_ur0(pcoupl_mu, state->x[n], state->x[n]);
1856             }
1857             break;
1858         case (epcMTTK):
1859             switch (inputrec->epct)
1860             {
1861                 case (epctISOTROPIC):
1862                     /* DIM * eta = ln V.  so DIM*eta_new = DIM*eta_old + DIM*dt*veta =>
1863                        ln V_new = ln V_old + 3*dt*veta => V_new = V_old*exp(3*dt*veta) =>
1864                        Side length scales as exp(veta*dt) */
1865
1866                     msmul(state->box, exp(state->veta*dt), state->box);
1867
1868                     /* Relate veta to boxv.  veta = d(eta)/dT = (1/DIM)*1/V dV/dT.
1869                        o               If we assume isotropic scaling, and box length scaling
1870                        factor L, then V = L^DIM (det(M)).  So dV/dt = DIM
1871                        L^(DIM-1) dL/dt det(M), and veta = (1/L) dL/dt.  The
1872                        determinant of B is L^DIM det(M), and the determinant
1873                        of dB/dt is (dL/dT)^DIM det (M).  veta will be
1874                        (det(dB/dT)/det(B))^(1/3).  Then since M =
1875                        B_new*(vol_new)^(1/3), dB/dT_new = (veta_new)*B(new). */
1876
1877                     msmul(state->box, state->veta, state->boxv);
1878                     break;
1879                 default:
1880                     break;
1881             }
1882             break;
1883         default:
1884             break;
1885     }
1886
1887     if (DEFORM(*inputrec))
1888     {
1889         deform(upd, start, homenr, state->x, state->box, inputrec, step);
1890     }
1891     where();
1892     dump_it_all(fplog, "After update",
1893                 state->natoms, state->x, upd->xp, state->v, force);
1894 }
1895
1896 void update_coords(FILE             *fplog,
1897                    gmx_int64_t       step,
1898                    t_inputrec       *inputrec,  /* input record and box stuff   */
1899                    t_mdatoms        *md,
1900                    t_state          *state,
1901                    gmx_bool          bMolPBC,
1902                    rvec             *f,    /* forces on home particles */
1903                    gmx_bool          bDoLR,
1904                    rvec             *f_lr,
1905                    tensor           *vir_lr_constr,
1906                    t_fcdata         *fcd,
1907                    gmx_ekindata_t   *ekind,
1908                    matrix            M,
1909                    gmx_update_t      upd,
1910                    gmx_bool          bInitStep,
1911                    int               UpdatePart,
1912                    t_commrec        *cr, /* these shouldn't be here -- need to think about it */
1913                    t_nrnb           *nrnb,
1914                    gmx_constr_t      constr,
1915                    t_idef           *idef)
1916 {
1917     gmx_bool          bNH, bPR, bDoConstr = FALSE;
1918     double            dt, alpha;
1919     rvec             *force;
1920     int               start, homenr, nrend;
1921     rvec             *xprime;
1922     int               nth, th;
1923
1924     bDoConstr = (NULL != constr);
1925
1926     /* Running the velocity half does nothing except for velocity verlet */
1927     if ((UpdatePart == etrtVELOCITY1 || UpdatePart == etrtVELOCITY2) &&
1928         !EI_VV(inputrec->eI))
1929     {
1930         gmx_incons("update_coords called for velocity without VV integrator");
1931     }
1932
1933     start  = 0;
1934     homenr = md->homenr;
1935     nrend  = start+homenr;
1936
1937     xprime = get_xprime(state, upd);
1938
1939     dt   = inputrec->delta_t;
1940
1941     /* We need to update the NMR restraint history when time averaging is used */
1942     if (state->flags & (1<<estDISRE_RM3TAV))
1943     {
1944         update_disres_history(fcd, &state->hist);
1945     }
1946     if (state->flags & (1<<estORIRE_DTAV))
1947     {
1948         update_orires_history(fcd, &state->hist);
1949     }
1950
1951
1952     bNH = inputrec->etc == etcNOSEHOOVER;
1953     bPR = ((inputrec->epc == epcPARRINELLORAHMAN) || (inputrec->epc == epcMTTK));
1954
1955     if (bDoLR && inputrec->nstcalclr > 1 && !EI_VV(inputrec->eI))  /* get this working with VV? */
1956     {
1957         /* Store the total force + nstcalclr-1 times the LR force
1958          * in forces_lr, so it can be used in a normal update algorithm
1959          * to produce twin time stepping.
1960          */
1961         /* is this correct in the new construction? MRS */
1962         combine_forces(upd,
1963                        inputrec->nstcalclr, constr, inputrec, md, idef, cr,
1964                        step, state, bMolPBC,
1965                        start, nrend, f, f_lr, vir_lr_constr, nrnb);
1966         force = f_lr;
1967     }
1968     else
1969     {
1970         force = f;
1971     }
1972
1973     /* ############# START The update of velocities and positions ######### */
1974     where();
1975     dump_it_all(fplog, "Before update",
1976                 state->natoms, state->x, xprime, state->v, force);
1977
1978     if (inputrec->eI == eiSD2)
1979     {
1980         check_sd2_work_data_allocation(upd->sd, nrend);
1981
1982         do_update_sd2_Tconsts(upd->sd,
1983                               inputrec->opts.ngtc,
1984                               inputrec->opts.tau_t,
1985                               inputrec->opts.ref_t);
1986     }
1987     if (inputrec->eI == eiBD)
1988     {
1989         do_update_bd_Tconsts(dt, inputrec->bd_fric,
1990                              inputrec->opts.ngtc, inputrec->opts.ref_t,
1991                              upd->sd->bd_rf);
1992     }
1993
1994     nth = gmx_omp_nthreads_get(emntUpdate);
1995
1996 #pragma omp parallel for num_threads(nth) schedule(static) private(alpha)
1997     for (th = 0; th < nth; th++)
1998     {
1999         int start_th, end_th;
2000
2001         start_th = start + ((nrend-start)* th   )/nth;
2002         end_th   = start + ((nrend-start)*(th+1))/nth;
2003
2004         switch (inputrec->eI)
2005         {
2006             case (eiMD):
2007                 if (ekind->cosacc.cos_accel == 0)
2008                 {
2009                     do_update_md(start_th, end_th,
2010                                  dt, inputrec->nstpcouple,
2011                                  ekind->tcstat, state->nosehoover_vxi,
2012                                  ekind->bNEMD, ekind->grpstat, inputrec->opts.acc,
2013                                  inputrec->opts.nFreeze,
2014                                  md->invmass, md->ptype,
2015                                  md->cFREEZE, md->cACC, md->cTC,
2016                                  state->x, xprime, state->v, force, M,
2017                                  bNH, bPR);
2018                 }
2019                 else
2020                 {
2021                     do_update_visc(start_th, end_th,
2022                                    dt, inputrec->nstpcouple,
2023                                    ekind->tcstat, state->nosehoover_vxi,
2024                                    md->invmass, md->ptype,
2025                                    md->cTC, state->x, xprime, state->v, force, M,
2026                                    state->box,
2027                                    ekind->cosacc.cos_accel,
2028                                    ekind->cosacc.vcos,
2029                                    bNH, bPR);
2030                 }
2031                 break;
2032             case (eiSD1):
2033                 /* With constraints, the SD1 update is done in 2 parts */
2034                 do_update_sd1(upd->sd,
2035                               start_th, end_th, dt,
2036                               inputrec->opts.acc, inputrec->opts.nFreeze,
2037                               md->invmass, md->ptype,
2038                               md->cFREEZE, md->cACC, md->cTC,
2039                               state->x, xprime, state->v, force,
2040                               inputrec->opts.ngtc, inputrec->opts.ref_t,
2041                               bDoConstr, TRUE,
2042                               step, inputrec->ld_seed, DOMAINDECOMP(cr) ? cr->dd->gatindex : NULL);
2043                 break;
2044             case (eiSD2):
2045                 /* The SD2 update is always done in 2 parts,
2046                  * because an extra constraint step is needed
2047                  */
2048                 do_update_sd2(upd->sd,
2049                               bInitStep, start_th, end_th,
2050                               inputrec->opts.acc, inputrec->opts.nFreeze,
2051                               md->invmass, md->ptype,
2052                               md->cFREEZE, md->cACC, md->cTC,
2053                               state->x, xprime, state->v, force, state->sd_X,
2054                               inputrec->opts.tau_t,
2055                               TRUE, step, inputrec->ld_seed,
2056                               DOMAINDECOMP(cr) ? cr->dd->gatindex : NULL);
2057                 break;
2058             case (eiBD):
2059                 do_update_bd(start_th, end_th, dt,
2060                              inputrec->opts.nFreeze, md->invmass, md->ptype,
2061                              md->cFREEZE, md->cTC,
2062                              state->x, xprime, state->v, force,
2063                              inputrec->bd_fric,
2064                              upd->sd->bd_rf,
2065                              step, inputrec->ld_seed, DOMAINDECOMP(cr) ? cr->dd->gatindex : NULL);
2066                 break;
2067             case (eiVV):
2068             case (eiVVAK):
2069                 alpha = 1.0 + DIM/((double)inputrec->opts.nrdf[0]); /* assuming barostat coupled to group 0. */
2070                 switch (UpdatePart)
2071                 {
2072                     case etrtVELOCITY1:
2073                     case etrtVELOCITY2:
2074                         do_update_vv_vel(start_th, end_th, dt,
2075                                          inputrec->opts.acc, inputrec->opts.nFreeze,
2076                                          md->invmass, md->ptype,
2077                                          md->cFREEZE, md->cACC,
2078                                          state->v, force,
2079                                          (bNH || bPR), state->veta, alpha);
2080                         break;
2081                     case etrtPOSITION:
2082                         do_update_vv_pos(start_th, end_th, dt,
2083                                          inputrec->opts.nFreeze,
2084                                          md->ptype, md->cFREEZE,
2085                                          state->x, xprime, state->v,
2086                                          (bNH || bPR), state->veta);
2087                         break;
2088                 }
2089                 break;
2090             default:
2091                 gmx_fatal(FARGS, "Don't know how to update coordinates");
2092                 break;
2093         }
2094     }
2095
2096 }
2097
2098
2099 void correct_ekin(FILE *log, int start, int end, rvec v[], rvec vcm, real mass[],
2100                   real tmass, tensor ekin)
2101 {
2102     /*
2103      * This is a debugging routine. It should not be called for production code
2104      *
2105      * The kinetic energy should calculated according to:
2106      *   Ekin = 1/2 m (v-vcm)^2
2107      * However the correction is not always applied, since vcm may not be
2108      * known in time and we compute
2109      *   Ekin' = 1/2 m v^2 instead
2110      * This can be corrected afterwards by computing
2111      *   Ekin = Ekin' + 1/2 m ( -2 v vcm + vcm^2)
2112      * or in hsorthand:
2113      *   Ekin = Ekin' - m v vcm + 1/2 m vcm^2
2114      */
2115     int    i, j, k;
2116     real   m, tm;
2117     rvec   hvcm, mv;
2118     tensor dekin;
2119
2120     /* Local particles */
2121     clear_rvec(mv);
2122
2123     /* Processor dependent part. */
2124     tm = 0;
2125     for (i = start; (i < end); i++)
2126     {
2127         m      = mass[i];
2128         tm    += m;
2129         for (j = 0; (j < DIM); j++)
2130         {
2131             mv[j] += m*v[i][j];
2132         }
2133     }
2134     /* Shortcut */
2135     svmul(1/tmass, vcm, vcm);
2136     svmul(0.5, vcm, hvcm);
2137     clear_mat(dekin);
2138     for (j = 0; (j < DIM); j++)
2139     {
2140         for (k = 0; (k < DIM); k++)
2141         {
2142             dekin[j][k] += vcm[k]*(tm*hvcm[j]-mv[j]);
2143         }
2144     }
2145     pr_rvecs(log, 0, "dekin", dekin, DIM);
2146     pr_rvecs(log, 0, " ekin", ekin, DIM);
2147     fprintf(log, "dekin = %g, ekin = %g  vcm = (%8.4f %8.4f %8.4f)\n",
2148             trace(dekin), trace(ekin), vcm[XX], vcm[YY], vcm[ZZ]);
2149     fprintf(log, "mv = (%8.4f %8.4f %8.4f)\n",
2150             mv[XX], mv[YY], mv[ZZ]);
2151 }
2152
2153 extern gmx_bool update_randomize_velocities(t_inputrec *ir, gmx_int64_t step, const t_commrec *cr,
2154                                             t_mdatoms *md, t_state *state, gmx_update_t upd, gmx_constr_t constr)
2155 {
2156
2157     real rate = (ir->delta_t)/ir->opts.tau_t[0];
2158
2159     if (ir->etc == etcANDERSEN && constr != NULL)
2160     {
2161         /* Currently, Andersen thermostat does not support constrained
2162            systems. Functionality exists in the andersen_tcoupl
2163            function in GROMACS 4.5.7 to allow this combination. That
2164            code could be ported to the current random-number
2165            generation approach, but has not yet been done because of
2166            lack of time and resources. */
2167         gmx_fatal(FARGS, "Normal Andersen is currently not supported with constraints, use massive Andersen instead");
2168     }
2169
2170     /* proceed with andersen if 1) it's fixed probability per
2171        particle andersen or 2) it's massive andersen and it's tau_t/dt */
2172     if ((ir->etc == etcANDERSEN) || do_per_step(step, (int)(1.0/rate)))
2173     {
2174         andersen_tcoupl(ir, step, cr, md, state, rate,
2175                         upd->sd->randomize_group, upd->sd->boltzfac);
2176         return TRUE;
2177     }
2178     return FALSE;
2179 }