Merge release-4-6 into master
[alexxy/gromacs.git] / src / programs / mdrun / runner.c
1 /* -*- mode: c; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; c-file-style: "stroustrup"; -*-
2  *
3  * 
4  *                This source code is part of
5  * 
6  *                 G   R   O   M   A   C   S
7  * 
8  *          GROningen MAchine for Chemical Simulations
9  * 
10  *                        VERSION 3.2.0
11  * Written by David van der Spoel, Erik Lindahl, Berk Hess, and others.
12  * Copyright (c) 1991-2000, University of Groningen, The Netherlands.
13  * Copyright (c) 2001-2004, The GROMACS development team,
14  * check out http://www.gromacs.org for more information.
15
16  * This program is free software; you can redistribute it and/or
17  * modify it under the terms of the GNU General Public License
18  * as published by the Free Software Foundation; either version 2
19  * of the License, or (at your option) any later version.
20  * 
21  * If you want to redistribute modifications, please consider that
22  * scientific software is very special. Version control is crucial -
23  * bugs must be traceable. We will be happy to consider code for
24  * inclusion in the official distribution, but derived work must not
25  * be called official GROMACS. Details are found in the README & COPYING
26  * files - if they are missing, get the official version at www.gromacs.org.
27  * 
28  * To help us fund GROMACS development, we humbly ask that you cite
29  * the papers on the package - you can find them in the top README file.
30  * 
31  * For more info, check our website at http://www.gromacs.org
32  * 
33  * And Hey:
34  * Gallium Rubidium Oxygen Manganese Argon Carbon Silicon
35  */
36 #ifdef HAVE_CONFIG_H
37 #include <config.h>
38 #endif
39 #if defined(HAVE_SCHED_H) && defined(HAVE_SCHED_GETAFFINITY)
40 #define _GNU_SOURCE
41 #include <sched.h>
42 #include <sys/syscall.h>
43 #endif
44 #include <signal.h>
45 #include <stdlib.h>
46 #ifdef HAVE_UNISTD_H
47 #include <unistd.h>
48 #endif
49 #include <string.h>
50 #include <assert.h>
51
52 #include "typedefs.h"
53 #include "smalloc.h"
54 #include "sysstuff.h"
55 #include "statutil.h"
56 #include "mdrun.h"
57 #include "md_logging.h"
58 #include "md_support.h"
59 #include "network.h"
60 #include "pull.h"
61 #include "pull_rotation.h"
62 #include "names.h"
63 #include "disre.h"
64 #include "orires.h"
65 #include "pme.h"
66 #include "mdatoms.h"
67 #include "repl_ex.h"
68 #include "qmmm.h"
69 #include "domdec.h"
70 #include "partdec.h"
71 #include "coulomb.h"
72 #include "constr.h"
73 #include "mvdata.h"
74 #include "checkpoint.h"
75 #include "mtop_util.h"
76 #include "sighandler.h"
77 #include "tpxio.h"
78 #include "txtdump.h"
79 #include "gmx_detect_hardware.h"
80 #include "gmx_omp_nthreads.h"
81 #include "pull_rotation.h"
82 #include "calc_verletbuf.h"
83 #include "../mdlib/nbnxn_search.h"
84 #include "../mdlib/nbnxn_consts.h"
85 #include "gmx_fatal_collective.h"
86 #include "membed.h"
87 #include "macros.h"
88 #include "gmx_omp.h"
89
90 #include "thread_mpi/threads.h"
91
92 #ifdef GMX_LIB_MPI
93 #include <mpi.h>
94 #endif
95 #ifdef GMX_THREAD_MPI
96 #include "tmpi.h"
97 #endif
98
99 #ifdef GMX_FAHCORE
100 #include "corewrap.h"
101 #endif
102
103 #include "gpu_utils.h"
104 #include "nbnxn_cuda_data_mgmt.h"
105
106 typedef struct { 
107     gmx_integrator_t *func;
108 } gmx_intp_t;
109
110 /* The array should match the eI array in include/types/enums.h */
111 const gmx_intp_t integrator[eiNR] = { {do_md}, {do_steep}, {do_cg}, {do_md}, {do_md}, {do_nm}, {do_lbfgs}, {do_tpi}, {do_tpi}, {do_md}, {do_md},{do_md}};
112
113 gmx_large_int_t     deform_init_init_step_tpx;
114 matrix              deform_init_box_tpx;
115 #ifdef GMX_THREAD_MPI
116 tMPI_Thread_mutex_t deform_init_box_mutex=TMPI_THREAD_MUTEX_INITIALIZER;
117 #endif
118
119
120 #ifdef GMX_THREAD_MPI
121 struct mdrunner_arglist
122 {
123     gmx_hw_opt_t *hw_opt;
124     FILE *fplog;
125     t_commrec *cr;
126     int nfile;
127     const t_filenm *fnm;
128     output_env_t oenv;
129     gmx_bool bVerbose;
130     gmx_bool bCompact;
131     int nstglobalcomm;
132     ivec ddxyz;
133     int dd_node_order;
134     real rdd;
135     real rconstr;
136     const char *dddlb_opt;
137     real dlb_scale;
138     const char *ddcsx;
139     const char *ddcsy;
140     const char *ddcsz;
141     const char *nbpu_opt;
142     int nsteps_cmdline;
143     int nstepout;
144     int resetstep;
145     int nmultisim;
146     int repl_ex_nst;
147     int repl_ex_nex;
148     int repl_ex_seed;
149     real pforce;
150     real cpt_period;
151     real max_hours;
152     const char *deviceOptions;
153     unsigned long Flags;
154     int ret; /* return value */
155 };
156
157
158 /* The function used for spawning threads. Extracts the mdrunner() 
159    arguments from its one argument and calls mdrunner(), after making
160    a commrec. */
161 static void mdrunner_start_fn(void *arg)
162 {
163     struct mdrunner_arglist *mda=(struct mdrunner_arglist*)arg;
164     struct mdrunner_arglist mc=*mda; /* copy the arg list to make sure 
165                                         that it's thread-local. This doesn't
166                                         copy pointed-to items, of course,
167                                         but those are all const. */
168     t_commrec *cr;  /* we need a local version of this */
169     FILE *fplog=NULL;
170     t_filenm *fnm;
171
172     fnm = dup_tfn(mc.nfile, mc.fnm);
173
174     cr = init_par_threads(mc.cr);
175
176     if (MASTER(cr))
177     {
178         fplog=mc.fplog;
179     }
180
181     mda->ret=mdrunner(mc.hw_opt, fplog, cr, mc.nfile, fnm, mc.oenv, 
182                       mc.bVerbose, mc.bCompact, mc.nstglobalcomm, 
183                       mc.ddxyz, mc.dd_node_order, mc.rdd,
184                       mc.rconstr, mc.dddlb_opt, mc.dlb_scale, 
185                       mc.ddcsx, mc.ddcsy, mc.ddcsz,
186                       mc.nbpu_opt,
187                       mc.nsteps_cmdline, mc.nstepout, mc.resetstep,
188                       mc.nmultisim, mc.repl_ex_nst, mc.repl_ex_nex, mc.repl_ex_seed, mc.pforce, 
189                       mc.cpt_period, mc.max_hours, mc.deviceOptions, mc.Flags);
190 }
191
192 /* called by mdrunner() to start a specific number of threads (including 
193    the main thread) for thread-parallel runs. This in turn calls mdrunner()
194    for each thread. 
195    All options besides nthreads are the same as for mdrunner(). */
196 static t_commrec *mdrunner_start_threads(gmx_hw_opt_t *hw_opt, 
197               FILE *fplog,t_commrec *cr,int nfile, 
198               const t_filenm fnm[], const output_env_t oenv, gmx_bool bVerbose,
199               gmx_bool bCompact, int nstglobalcomm,
200               ivec ddxyz,int dd_node_order,real rdd,real rconstr,
201               const char *dddlb_opt,real dlb_scale,
202               const char *ddcsx,const char *ddcsy,const char *ddcsz,
203               const char *nbpu_opt,
204               int nsteps_cmdline, int nstepout,int resetstep,
205               int nmultisim,int repl_ex_nst,int repl_ex_nex, int repl_ex_seed,
206               real pforce,real cpt_period, real max_hours, 
207               const char *deviceOptions, unsigned long Flags)
208 {
209     int ret;
210     struct mdrunner_arglist *mda;
211     t_commrec *crn; /* the new commrec */
212     t_filenm *fnmn;
213
214     /* first check whether we even need to start tMPI */
215     if (hw_opt->nthreads_tmpi < 2)
216     {
217         return cr;
218     }
219
220     /* a few small, one-time, almost unavoidable memory leaks: */
221     snew(mda,1);
222     fnmn=dup_tfn(nfile, fnm);
223
224     /* fill the data structure to pass as void pointer to thread start fn */
225     mda->hw_opt=hw_opt;
226     mda->fplog=fplog;
227     mda->cr=cr;
228     mda->nfile=nfile;
229     mda->fnm=fnmn;
230     mda->oenv=oenv;
231     mda->bVerbose=bVerbose;
232     mda->bCompact=bCompact;
233     mda->nstglobalcomm=nstglobalcomm;
234     mda->ddxyz[XX]=ddxyz[XX];
235     mda->ddxyz[YY]=ddxyz[YY];
236     mda->ddxyz[ZZ]=ddxyz[ZZ];
237     mda->dd_node_order=dd_node_order;
238     mda->rdd=rdd;
239     mda->rconstr=rconstr;
240     mda->dddlb_opt=dddlb_opt;
241     mda->dlb_scale=dlb_scale;
242     mda->ddcsx=ddcsx;
243     mda->ddcsy=ddcsy;
244     mda->ddcsz=ddcsz;
245     mda->nbpu_opt=nbpu_opt;
246     mda->nsteps_cmdline=nsteps_cmdline;
247     mda->nstepout=nstepout;
248     mda->resetstep=resetstep;
249     mda->nmultisim=nmultisim;
250     mda->repl_ex_nst=repl_ex_nst;
251     mda->repl_ex_nex=repl_ex_nex;
252     mda->repl_ex_seed=repl_ex_seed;
253     mda->pforce=pforce;
254     mda->cpt_period=cpt_period;
255     mda->max_hours=max_hours;
256     mda->deviceOptions=deviceOptions;
257     mda->Flags=Flags;
258
259     /* now spawn new threads that start mdrunner_start_fn(), while 
260        the main thread returns */
261     ret=tMPI_Init_fn(TRUE, hw_opt->nthreads_tmpi,
262                      (hw_opt->bThreadPinning ? TMPI_AFFINITY_ALL_CORES : TMPI_AFFINITY_NONE),
263                      mdrunner_start_fn, (void*)(mda) );
264     if (ret!=TMPI_SUCCESS)
265         return NULL;
266
267     /* make a new comm_rec to reflect the new situation */
268     crn=init_par_threads(cr);
269     return crn;
270 }
271
272
273 static int get_tmpi_omp_thread_division(const gmx_hw_info_t *hwinfo,
274                                         const gmx_hw_opt_t *hw_opt,
275                                         int nthreads_tot,
276                                         int ngpu)
277 {
278     int nthreads_tmpi;
279
280     /* There are no separate PME nodes here, as we ensured in
281      * check_and_update_hw_opt that nthreads_tmpi>0 with PME nodes
282      * and a conditional ensures we would not have ended up here.
283      * Note that separate PME nodes might be switched on later.
284      */
285     if (ngpu > 0)
286     {
287         nthreads_tmpi = ngpu;
288         if (nthreads_tot > 0 && nthreads_tot < nthreads_tmpi)
289         {
290             nthreads_tmpi = nthreads_tot;
291         }
292     }
293     else if (hw_opt->nthreads_omp > 0)
294     {
295         /* Here we could oversubscribe, when we do, we issue a warning later */
296         nthreads_tmpi = max(1,nthreads_tot/hw_opt->nthreads_omp);
297     }
298     else
299     {
300         /* TODO choose nthreads_omp based on hardware topology
301            when we have a hardware topology detection library */
302         /* In general, when running up to 4 threads, OpenMP should be faster.
303          * Note: on AMD Bulldozer we should avoid running OpenMP over two dies.
304          * On Intel>=Nehalem running OpenMP on a single CPU is always faster,
305          * even on two CPUs it's usually faster (but with many OpenMP threads
306          * it could be faster not to use HT, currently we always use HT).
307          * On Nehalem/Westmere we want to avoid running 16 threads over
308          * two CPUs with HT, so we need a limit<16; thus we use 12.
309          * A reasonable limit for Intel Sandy and Ivy bridge,
310          * not knowing the topology, is 16 threads.
311          */
312         const int nthreads_omp_always_faster             =  4;
313         const int nthreads_omp_always_faster_Nehalem     = 12;
314         const int nthreads_omp_always_faster_SandyBridge = 16;
315         const int first_model_Nehalem     = 0x1A;
316         const int first_model_SandyBridge = 0x2A;
317         gmx_bool bIntel_Family6;
318
319         bIntel_Family6 =
320             (gmx_cpuid_vendor(hwinfo->cpuid_info) == GMX_CPUID_VENDOR_INTEL &&
321              gmx_cpuid_family(hwinfo->cpuid_info) == 6);
322
323         if (nthreads_tot <= nthreads_omp_always_faster ||
324             (bIntel_Family6 &&
325              ((gmx_cpuid_model(hwinfo->cpuid_info) >= nthreads_omp_always_faster_Nehalem && nthreads_tot <= nthreads_omp_always_faster_Nehalem) ||
326               (gmx_cpuid_model(hwinfo->cpuid_info) >= nthreads_omp_always_faster_SandyBridge && nthreads_tot <= nthreads_omp_always_faster_SandyBridge))))
327         {
328             /* Use pure OpenMP parallelization */
329             nthreads_tmpi = 1;
330         }
331         else
332         {
333             /* Don't use OpenMP parallelization */
334             nthreads_tmpi = nthreads_tot;
335         }
336     }
337
338     return nthreads_tmpi;
339 }
340
341
342 /* Get the number of threads to use for thread-MPI based on how many
343  * were requested, which algorithms we're using,
344  * and how many particles there are.
345  * At the point we have already called check_and_update_hw_opt.
346  * Thus all options should be internally consistent and consistent
347  * with the hardware, except that ntmpi could be larger than #GPU.
348  */
349 static int get_nthreads_mpi(gmx_hw_info_t *hwinfo,
350                             gmx_hw_opt_t *hw_opt,
351                             t_inputrec *inputrec, gmx_mtop_t *mtop,
352                             const t_commrec *cr,
353                             FILE *fplog)
354 {
355     int nthreads_hw,nthreads_tot_max,nthreads_tmpi,nthreads_new,ngpu;
356     int min_atoms_per_mpi_thread;
357     char *env;
358     char sbuf[STRLEN];
359     gmx_bool bCanUseGPU;
360
361     if (hw_opt->nthreads_tmpi > 0)
362     {
363         /* Trivial, return right away */
364         return hw_opt->nthreads_tmpi;
365     }
366
367     nthreads_hw = hwinfo->nthreads_hw_avail;
368
369     /* How many total (#tMPI*#OpenMP) threads can we start? */ 
370     if (hw_opt->nthreads_tot > 0)
371     {
372         nthreads_tot_max = hw_opt->nthreads_tot;
373     }
374     else
375     {
376         nthreads_tot_max = nthreads_hw;
377     }
378
379     bCanUseGPU = (inputrec->cutoff_scheme == ecutsVERLET && hwinfo->bCanUseGPU);
380     if (bCanUseGPU)
381     {
382         ngpu = hwinfo->gpu_info.ncuda_dev_use;
383     }
384     else
385     {
386         ngpu = 0;
387     }
388
389     nthreads_tmpi =
390         get_tmpi_omp_thread_division(hwinfo,hw_opt,nthreads_tot_max,ngpu);
391
392     if (inputrec->eI == eiNM || EI_TPI(inputrec->eI))
393     {
394         /* Steps are divided over the nodes iso splitting the atoms */
395         min_atoms_per_mpi_thread = 0;
396     }
397     else
398     {
399         if (bCanUseGPU)
400         {
401             min_atoms_per_mpi_thread = MIN_ATOMS_PER_GPU;
402         }
403         else
404         {
405             min_atoms_per_mpi_thread = MIN_ATOMS_PER_MPI_THREAD;
406         }
407     }
408
409     /* Check if an algorithm does not support parallel simulation.  */
410     if (nthreads_tmpi != 1 &&
411         ( inputrec->eI == eiLBFGS ||
412           inputrec->coulombtype == eelEWALD ) )
413     {
414         nthreads_tmpi = 1;
415
416         md_print_warn(cr,fplog,"The integration or electrostatics algorithm doesn't support parallel runs. Using a single thread-MPI thread.\n");
417         if (hw_opt->nthreads_tmpi > nthreads_tmpi)
418         {
419             gmx_fatal(FARGS,"You asked for more than 1 thread-MPI thread, but an algorithm doesn't support that");
420         }
421     }
422     else if (mtop->natoms/nthreads_tmpi < min_atoms_per_mpi_thread)
423     {
424         /* the thread number was chosen automatically, but there are too many
425            threads (too few atoms per thread) */
426         nthreads_new = max(1,mtop->natoms/min_atoms_per_mpi_thread);
427
428         /* Avoid partial use of Hyper-Threading */
429         if (gmx_cpuid_x86_smt(hwinfo->cpuid_info) == GMX_CPUID_X86_SMT_ENABLED &&
430             nthreads_new > nthreads_hw/2 && nthreads_new < nthreads_hw)
431         {
432             nthreads_new = nthreads_hw/2;
433         }
434
435         /* Avoid large prime numbers in the thread count */
436         if (nthreads_new >= 6)
437         {
438             /* Use only 6,8,10 with additional factors of 2 */
439             int fac;
440
441             fac = 2;
442             while (3*fac*2 <= nthreads_new)
443             {
444                 fac *= 2;
445             }
446
447             nthreads_new = (nthreads_new/fac)*fac;
448         }
449         else
450         {
451             /* Avoid 5 */
452             if (nthreads_new == 5)
453             {
454                 nthreads_new = 4;
455             }
456         }
457
458         nthreads_tmpi = nthreads_new;
459
460         fprintf(stderr,"\n");
461         fprintf(stderr,"NOTE: Parallelization is limited by the small number of atoms,\n");
462         fprintf(stderr,"      only starting %d thread-MPI threads.\n",nthreads_tmpi);
463         fprintf(stderr,"      You can use the -nt and/or -ntmpi option to optimize the number of threads.\n\n");
464     }
465
466     return nthreads_tmpi;
467 }
468 #endif /* GMX_THREAD_MPI */
469
470
471 /* Environment variable for setting nstlist */
472 static const char*  NSTLIST_ENVVAR          =  "GMX_NSTLIST";
473 /* Try to increase nstlist when using a GPU with nstlist less than this */
474 static const int    NSTLIST_GPU_ENOUGH      = 20;
475 /* Increase nstlist until the non-bonded cost increases more than this factor */
476 static const float  NBNXN_GPU_LIST_OK_FAC   = 1.25;
477 /* Don't increase nstlist beyond a non-bonded cost increases of this factor */
478 static const float  NBNXN_GPU_LIST_MAX_FAC  = 1.40;
479
480 /* Try to increase nstlist when running on a GPU */
481 static void increase_nstlist(FILE *fp,t_commrec *cr,
482                              t_inputrec *ir,const gmx_mtop_t *mtop,matrix box)
483 {
484     char *env;
485     int  nstlist_orig,nstlist_prev;
486     verletbuf_list_setup_t ls;
487     real rlist_inc,rlist_ok,rlist_max,rlist_new,rlist_prev;
488     int  i;
489     t_state state_tmp;
490     gmx_bool bBox,bDD,bCont;
491     const char *nstl_fmt="\nFor optimal performance with a GPU nstlist (now %d) should be larger.\nThe optimum depends on your CPU and GPU resources.\nYou might want to try several nstlist values.\n";
492     const char *vbd_err="Can not increase nstlist for GPU run because verlet-buffer-drift is not set or used";
493     const char *box_err="Can not increase nstlist for GPU run because the box is too small";
494     const char *dd_err ="Can not increase nstlist for GPU run because of domain decomposition limitations";
495     char buf[STRLEN];
496
497     /* Number of + nstlist alternative values to try when switching  */
498     const int nstl[]={ 20, 25, 40, 50 };
499 #define NNSTL  sizeof(nstl)/sizeof(nstl[0])
500
501     env = getenv(NSTLIST_ENVVAR);
502     if (env == NULL)
503     {
504         if (fp != NULL)
505         {
506             fprintf(fp,nstl_fmt,ir->nstlist);
507         }
508     }
509
510     if (ir->verletbuf_drift == 0)
511     {
512         gmx_fatal(FARGS,"You are using an old tpr file with a GPU, please generate a new tpr file with an up to date version of grompp");
513     }
514
515     if (ir->verletbuf_drift < 0)
516     {
517         if (MASTER(cr))
518         {
519             fprintf(stderr,"%s\n",vbd_err);
520         }
521         if (fp != NULL)
522         {
523             fprintf(fp,"%s\n",vbd_err);
524         }
525
526         return;
527     }
528
529     nstlist_orig = ir->nstlist;
530     if (env != NULL)
531     {
532         sprintf(buf,"Getting nstlist from environment variable GMX_NSTLIST=%s",env);
533         if (MASTER(cr))
534         {
535             fprintf(stderr,"%s\n",buf);
536         }
537         if (fp != NULL)
538         {
539             fprintf(fp,"%s\n",buf);
540         }
541         sscanf(env,"%d",&ir->nstlist);
542     }
543
544     verletbuf_get_list_setup(TRUE,&ls);
545
546     /* Allow rlist to make the list double the size of the cut-off sphere */
547     rlist_inc = nbnxn_get_rlist_effective_inc(NBNXN_GPU_CLUSTER_SIZE,mtop->natoms/det(box));
548     rlist_ok  = (max(ir->rvdw,ir->rcoulomb) + rlist_inc)*pow(NBNXN_GPU_LIST_OK_FAC,1.0/3.0) - rlist_inc;
549     rlist_max = (max(ir->rvdw,ir->rcoulomb) + rlist_inc)*pow(NBNXN_GPU_LIST_MAX_FAC,1.0/3.0) - rlist_inc;
550     if (debug)
551     {
552         fprintf(debug,"GPU nstlist tuning: rlist_inc %.3f rlist_max %.3f\n",
553                 rlist_inc,rlist_max);
554     }
555
556     i = 0;
557     nstlist_prev = nstlist_orig;
558     rlist_prev   = ir->rlist;
559     do
560     {
561         if (env == NULL)
562         {
563             ir->nstlist = nstl[i];
564         }
565
566         /* Set the pair-list buffer size in ir */
567         calc_verlet_buffer_size(mtop,det(box),ir,ir->verletbuf_drift,&ls,
568                                 NULL,&rlist_new);
569
570         /* Does rlist fit in the box? */
571         bBox = (sqr(rlist_new) < max_cutoff2(ir->ePBC,box));
572         bDD  = TRUE;
573         if (bBox && DOMAINDECOMP(cr))
574         {
575             /* Check if rlist fits in the domain decomposition */
576             if (inputrec2nboundeddim(ir) < DIM)
577             {
578                 gmx_incons("Changing nstlist with domain decomposition and unbounded dimensions is not implemented yet");
579             }
580             copy_mat(box,state_tmp.box);
581             bDD = change_dd_cutoff(cr,&state_tmp,ir,rlist_new);
582         }
583
584         bCont = FALSE;
585
586         if (env == NULL)
587         {
588             if (bBox && bDD && rlist_new <= rlist_max)
589             {
590                 /* Increase nstlist */
591                 nstlist_prev = ir->nstlist;
592                 rlist_prev   = rlist_new;
593                 bCont = (i+1 < NNSTL && rlist_new < rlist_ok);
594             }
595             else
596             {
597                 /* Stick with the previous nstlist */
598                 ir->nstlist = nstlist_prev;
599                 rlist_new   = rlist_prev;
600                 bBox = TRUE;
601                 bDD  = TRUE;
602             }
603         }
604
605         i++;
606     }
607     while (bCont);
608
609     if (!bBox || !bDD)
610     {
611         gmx_warning(!bBox ? box_err : dd_err);
612         if (fp != NULL)
613         {
614             fprintf(fp,"\n%s\n",bBox ? box_err : dd_err);
615         }
616         ir->nstlist = nstlist_orig;
617     }
618     else if (ir->nstlist != nstlist_orig || rlist_new != ir->rlist)
619     {
620         sprintf(buf,"Changing nstlist from %d to %d, rlist from %g to %g",
621                 nstlist_orig,ir->nstlist,
622                 ir->rlist,rlist_new);
623         if (MASTER(cr))
624         {
625             fprintf(stderr,"%s\n\n",buf);
626         }
627         if (fp != NULL)
628         {
629             fprintf(fp,"%s\n\n",buf);
630         }
631         ir->rlist     = rlist_new;
632         ir->rlistlong = rlist_new;
633     }
634 }
635
636 static void prepare_verlet_scheme(FILE *fplog,
637                                   gmx_hw_info_t *hwinfo,
638                                   t_commrec *cr,
639                                   gmx_hw_opt_t *hw_opt,
640                                   const char *nbpu_opt,
641                                   t_inputrec *ir,
642                                   const gmx_mtop_t *mtop,
643                                   matrix box,
644                                   gmx_bool *bUseGPU)
645 {
646     /* Here we only check for GPU usage on the MPI master process,
647      * as here we don't know how many GPUs we will use yet.
648      * We check for a GPU on all processes later.
649      */
650     *bUseGPU = hwinfo->bCanUseGPU || (getenv("GMX_EMULATE_GPU") != NULL);
651
652     if (ir->verletbuf_drift > 0)
653     {
654         /* Update the Verlet buffer size for the current run setup */
655         verletbuf_list_setup_t ls;
656         real rlist_new;
657
658         /* Here we assume CPU acceleration is on. But as currently
659          * calc_verlet_buffer_size gives the same results for 4x8 and 4x4
660          * and 4x2 gives a larger buffer than 4x4, this is ok.
661          */
662         verletbuf_get_list_setup(*bUseGPU,&ls);
663
664         calc_verlet_buffer_size(mtop,det(box),ir,
665                                 ir->verletbuf_drift,&ls,
666                                 NULL,&rlist_new);
667         if (rlist_new != ir->rlist)
668         {
669             if (fplog != NULL)
670             {
671                 fprintf(fplog,"\nChanging rlist from %g to %g for non-bonded %dx%d atom kernels\n\n",
672                         ir->rlist,rlist_new,
673                         ls.cluster_size_i,ls.cluster_size_j);
674             }
675             ir->rlist     = rlist_new;
676             ir->rlistlong = rlist_new;
677         }
678     }
679
680     /* With GPU or emulation we should check nstlist for performance */
681     if ((EI_DYNAMICS(ir->eI) &&
682          *bUseGPU &&
683          ir->nstlist < NSTLIST_GPU_ENOUGH) ||
684         getenv(NSTLIST_ENVVAR) != NULL)
685     {
686         /* Choose a better nstlist */
687         increase_nstlist(fplog,cr,ir,mtop,box);
688     }
689 }
690
691 static void convert_to_verlet_scheme(FILE *fplog,
692                                      t_inputrec *ir,
693                                      gmx_mtop_t *mtop,real box_vol)
694 {
695     char *conv_mesg="Converting input file with group cut-off scheme to the Verlet cut-off scheme";
696
697     md_print_warn(NULL,fplog,"%s\n",conv_mesg);
698
699     ir->cutoff_scheme   = ecutsVERLET;
700     ir->verletbuf_drift = 0.005;
701
702     if (ir->rcoulomb != ir->rvdw)
703     {
704         gmx_fatal(FARGS,"The VdW and Coulomb cut-offs are different, whereas the Verlet scheme only supports equal cut-offs");
705     }
706
707     if (ir->vdwtype == evdwUSER || EEL_USER(ir->coulombtype))
708     {
709         gmx_fatal(FARGS,"User non-bonded potentials are not (yet) supported with the Verlet scheme");
710     }
711     else if (EVDW_SWITCHED(ir->vdwtype) || EEL_SWITCHED(ir->coulombtype))
712     {
713         md_print_warn(NULL,fplog,"Converting switched or shifted interactions to a shifted potential (without force shift), this will lead to slightly different interaction potentials");
714
715         if (EVDW_SWITCHED(ir->vdwtype))
716         {
717             ir->vdwtype = evdwCUT;
718         }
719         if (EEL_SWITCHED(ir->coulombtype))
720         {
721             if (EEL_FULL(ir->coulombtype))
722             {
723                 /* With full electrostatic only PME can be switched */
724                 ir->coulombtype = eelPME;
725             }
726             else
727             {
728                 md_print_warn(NULL,fplog,"NOTE: Replacing %s electrostatics with reaction-field with epsilon-rf=inf\n",eel_names[ir->coulombtype]);
729                 ir->coulombtype = eelRF;
730                 ir->epsilon_rf  = 0.0;
731             }
732         }
733
734         /* We set the target energy drift to a small number.
735          * Note that this is only for testing. For production the user
736          * should think about this and set the mdp options.
737          */
738         ir->verletbuf_drift = 1e-4;
739     }
740
741     if (inputrec2nboundeddim(ir) != 3)
742     {
743         gmx_fatal(FARGS,"Can only convert old tpr files to the Verlet cut-off scheme with 3D pbc");
744     }
745
746     if (ir->efep != efepNO || ir->implicit_solvent != eisNO)
747     {
748         gmx_fatal(FARGS,"Will not convert old tpr files to the Verlet cut-off scheme with free-energy calculations or implicit solvent");
749     }
750
751     if (EI_DYNAMICS(ir->eI) && !(EI_MD(ir->eI) && ir->etc == etcNO))
752     {
753         verletbuf_list_setup_t ls;
754
755         verletbuf_get_list_setup(FALSE,&ls);
756         calc_verlet_buffer_size(mtop,box_vol,ir,ir->verletbuf_drift,&ls,
757                                 NULL,&ir->rlist);
758     }
759     else
760     {
761         ir->verletbuf_drift = -1;
762         ir->rlist           = 1.05*max(ir->rvdw,ir->rcoulomb);
763     }
764
765     gmx_mtop_remove_chargegroups(mtop);
766 }
767
768 /* Check the process affinity mask. If it is non-zero, something
769  * else has set the affinity, and mdrun should honor that and
770  * not attempt to do its own thread pinning.
771  *
772  * This function should be called twice. Once before the OpenMP
773  * library gets initialized with bAfterOpenMPInit=FALSE (which will
774  * detect affinity set by external tools like taskset), and again
775  * later, after the OpenMP initialization, with bAfterOpenMPInit=TRUE
776  * (which will detect affinity changes made by the OpenMP library).
777  *
778  * Note that this will only work on Linux, because we use a GNU
779  * feature. */
780 static void check_cpu_affinity_set(FILE *fplog, const t_commrec *cr,
781                                    gmx_hw_opt_t *hw_opt, int ncpus,
782                                    gmx_bool bAfterOpenmpInit)
783 {
784 #ifdef HAVE_SCHED_GETAFFINITY
785     cpu_set_t mask_current;
786     int       i, ret, cpu_count, cpu_set;
787     gmx_bool  bAllSet;
788
789     assert(hw_opt);
790     if (!hw_opt->bThreadPinning)
791     {
792         /* internal affinity setting is off, don't bother checking process affinity */
793         return;
794     }
795
796     CPU_ZERO(&mask_current);
797     if ((ret = sched_getaffinity(0, sizeof(cpu_set_t), &mask_current)) != 0)
798     {
799         /* failed to query affinity mask, will just return */
800         if (debug)
801         {
802             fprintf(debug, "Failed to query affinity mask (error %d)", ret);
803         }
804         return;
805     }
806
807     /* Before proceeding with the actual check, make sure that the number of
808      * detected CPUs is >= the CPUs in the current set.
809      * We need to check for CPU_COUNT as it was added only in glibc 2.6. */
810 #ifdef CPU_COUNT
811     if (ncpus < CPU_COUNT(&mask_current))
812     {
813         if (debug)
814         {
815             fprintf(debug, "%d CPUs detected, but %d was returned by CPU_COUNT",
816                     ncpus, CPU_COUNT(&mask_current));
817         }
818         return;
819     }
820 #endif /* CPU_COUNT */
821
822     bAllSet = TRUE;
823     for (i = 0; (i < ncpus && i < CPU_SETSIZE); i++)
824     {
825         bAllSet = bAllSet && (CPU_ISSET(i, &mask_current) != 0);
826     }
827
828     if (!bAllSet)
829     {
830         if (!bAfterOpenmpInit)
831         {
832             md_print_warn(cr, fplog,
833                           "%s detected a non-default process affinity, "
834                           "so it will not attempt to pin its threads", ShortProgram());
835         }
836         else
837         {
838             md_print_warn(cr, fplog,
839                           "%s detected a non-default process affinity, "
840                           "probably set by the OpenMP library, "
841                           "so it will not attempt to pin its threads", ShortProgram());
842         }
843         hw_opt->bThreadPinning = FALSE;
844
845         if (debug)
846         {
847             fprintf(debug, "Non-default affinity mask found, mdrun will not pin threads\n");
848         }
849     }
850     else
851     {
852         if (debug)
853         {
854             fprintf(debug, "Default affinity mask found\n");
855         }
856     }
857 #endif /* HAVE_SCHED_GETAFFINITY */
858 }
859
860 /* Set CPU affinity. Can be important for performance.
861    On some systems (e.g. Cray) CPU Affinity is set by default.
862    But default assigning doesn't work (well) with only some ranks
863    having threads. This causes very low performance.
864    External tools have cumbersome syntax for setting affinity
865    in the case that only some ranks have threads.
866    Thus it is important that GROMACS sets the affinity internally
867    if only PME is using threads.
868 */
869 static void set_cpu_affinity(FILE *fplog,
870                              const t_commrec *cr,
871                              gmx_hw_opt_t *hw_opt,
872                              int nthreads_pme,
873                              const gmx_hw_info_t *hwinfo,
874                              const t_inputrec *inputrec)
875 {
876 #if defined GMX_THREAD_MPI
877     /* With the number of TMPI threads equal to the number of cores
878      * we already pinned in thread-MPI, so don't pin again here.
879      */
880     if (hw_opt->nthreads_tmpi == tMPI_Thread_get_hw_number())
881     {
882         return;
883     }
884 #endif
885
886 #ifndef __APPLE__
887     /* If the tMPI thread affinity setting is not supported encourage the user
888      * to report it as it's either a bug or an exotic platform which we might
889      * want to support. */
890     if (tMPI_Thread_setaffinity_support() != TMPI_SETAFFINITY_SUPPORT_YES)
891     {
892         md_print_warn(NULL, fplog,
893                       "Can not set thread affinities on the current plarform. On NUMA systems this\n"
894                       "can cause performance degradation. If you think your platform should support\n"
895                       "setting affinities, contact the GROMACS developers.");
896         return;
897     }
898 #endif /* __APPLE__ */
899
900     if (hw_opt->bThreadPinning)
901     {
902         int nth_affinity_set, thread_id_node, thread_id,
903             nthread_local, nthread_node, nthread_hw_max, nphyscore;
904         int offset;
905         char *env;
906
907         /* threads on this MPI process or TMPI thread */
908         if (cr->duty & DUTY_PP)
909         {
910             nthread_local = gmx_omp_nthreads_get(emntNonbonded);
911         }
912         else
913         {
914             nthread_local = gmx_omp_nthreads_get(emntPME);
915         }
916
917         /* map the current process to cores */
918         thread_id_node = 0;
919         nthread_node = nthread_local;
920 #ifdef GMX_MPI
921         if (PAR(cr) || MULTISIM(cr))
922         {
923             /* We need to determine a scan of the thread counts in this
924              * compute node.
925              */
926             MPI_Comm comm_intra;
927
928             MPI_Comm_split(MPI_COMM_WORLD,gmx_hostname_num(),cr->rank_intranode,
929                            &comm_intra);
930             MPI_Scan(&nthread_local,&thread_id_node,1,MPI_INT,MPI_SUM,comm_intra);
931             /* MPI_Scan is inclusive, but here we need exclusive */
932             thread_id_node -= nthread_local;
933             /* Get the total number of threads on this physical node */
934             MPI_Allreduce(&nthread_local,&nthread_node,1,MPI_INT,MPI_SUM,comm_intra);
935             MPI_Comm_free(&comm_intra);
936         }
937 #endif
938
939         offset = 0;
940         if (hw_opt->core_pinning_offset > 0)
941         {
942             offset = hw_opt->core_pinning_offset;
943             if (SIMMASTER(cr))
944             {
945                 fprintf(stderr, "Applying core pinning offset %d\n", offset);
946             }
947             if (fplog)
948             {
949                 fprintf(fplog, "Applying core pinning offset %d\n", offset);
950             }
951         }
952
953         /* With Intel Hyper-Threading enabled, we want to pin consecutive
954          * threads to physical cores when using more threads than physical
955          * cores or when the user requests so.
956          */
957         nthread_hw_max = hwinfo->nthreads_hw_avail;
958         nphyscore = -1;
959         if (hw_opt->bPinHyperthreading ||
960             (gmx_cpuid_x86_smt(hwinfo->cpuid_info) == GMX_CPUID_X86_SMT_ENABLED &&
961              nthread_node > nthread_hw_max/2 && getenv("GMX_DISABLE_PINHT") == NULL))
962         {
963             if (gmx_cpuid_x86_smt(hwinfo->cpuid_info) != GMX_CPUID_X86_SMT_ENABLED)
964             {
965                 /* We print to stderr on all processes, as we might have
966                  * different settings on different physical nodes.
967                  */
968                 if (gmx_cpuid_vendor(hwinfo->cpuid_info) != GMX_CPUID_VENDOR_INTEL)
969                 {
970                     md_print_warn(NULL, fplog, "Pinning for Hyper-Threading layout requested, "
971                                   "but non-Intel CPU detected (vendor: %s)\n",
972                                   gmx_cpuid_vendor_string[gmx_cpuid_vendor(hwinfo->cpuid_info)]);
973                 }
974                 else
975                 {
976                     md_print_warn(NULL, fplog, "Pinning for Hyper-Threading layout requested, "
977                                   "but the CPU detected does not have Intel Hyper-Threading support "
978                                   "(or it is turned off)\n");
979                 }
980             }
981             nphyscore = nthread_hw_max/2;
982
983             if (SIMMASTER(cr))
984             {
985                 fprintf(stderr, "Pinning to Hyper-Threading cores with %d physical cores in a compute node\n",
986                         nphyscore);
987             }
988             if (fplog)
989             {
990                 fprintf(fplog, "Pinning to Hyper-Threading cores with %d physical cores in a compute node\n",
991                         nphyscore);
992             }
993         }
994
995         /* Set the per-thread affinity. In order to be able to check the success
996          * of affinity settings, we will set nth_affinity_set to 1 on threads
997          * where the affinity setting succeded and to 0 where it failed.
998          * Reducing these 0/1 values over the threads will give the total number
999          * of threads on which we succeeded.
1000          */
1001          nth_affinity_set = 0;
1002 #pragma omp parallel firstprivate(thread_id_node) num_threads(nthread_local) \
1003                      reduction(+:nth_affinity_set)
1004         {
1005             int      core;
1006             gmx_bool setaffinity_ret;
1007
1008             thread_id       = gmx_omp_get_thread_num();
1009             thread_id_node += thread_id;
1010             if (nphyscore <= 0)
1011             {
1012                 core = offset + thread_id_node;
1013             }
1014             else
1015             {
1016                 /* Lock pairs of threads to the same hyperthreaded core */
1017                 core = offset + thread_id_node/2 + (thread_id_node % 2)*nphyscore;
1018             }
1019
1020             setaffinity_ret = tMPI_Thread_setaffinity_single(tMPI_Thread_self(), core);
1021
1022             /* store the per-thread success-values of the setaffinity */
1023             nth_affinity_set = (setaffinity_ret == 0);
1024
1025             if (debug)
1026             {
1027                 fprintf(debug, "On rank %2d, thread %2d, core %2d the affinity setting returned %d\n",
1028                         cr->nodeid, gmx_omp_get_thread_num(), core, setaffinity_ret);
1029             }
1030         }
1031
1032         if (nth_affinity_set > nthread_local)
1033         {
1034             char msg[STRLEN];
1035
1036             sprintf(msg, "Looks like we have set affinity for more threads than "
1037                     "we have (%d > %d)!\n", nth_affinity_set, nthread_local);
1038             gmx_incons(msg);
1039         }
1040         else
1041         {
1042             /* check & warn if some threads failed to set their affinities */
1043             if (nth_affinity_set != nthread_local)
1044             {
1045                 char sbuf1[STRLEN], sbuf2[STRLEN];
1046
1047                 /* sbuf1 contains rank info, while sbuf2 OpenMP thread info */
1048                 sbuf1[0] = sbuf2[0] = '\0';
1049 #ifdef GMX_MPI
1050 #ifdef GMX_THREAD_MPI
1051                 sprintf(sbuf1, "In thread-MPI thread #%d: ", cr->nodeid);
1052 #else /* GMX_LIB_MPI */
1053                 sprintf(sbuf1, "In MPI process #%d: ", cr->nodeid);
1054 #endif
1055 #endif /* GMX_MPI */
1056
1057                 if (nthread_local > 1)
1058                 {
1059                     sprintf(sbuf2, "of %d/%d thread%s ",
1060                             nthread_local - nth_affinity_set, nthread_local,
1061                             (nthread_local - nth_affinity_set) > 1 ? "s" : "");
1062                 }
1063
1064                 md_print_warn(NULL, fplog,
1065                               "NOTE: %sAffinity setting %sfailed.\n"
1066                               "      This can cause performance degradation!",
1067                               sbuf1, sbuf2);
1068             }
1069         }
1070     }
1071 }
1072
1073
1074 static void check_and_update_hw_opt(gmx_hw_opt_t *hw_opt,
1075                                     int cutoff_scheme,
1076                                     gmx_bool bIsSimMaster)
1077 {
1078     gmx_omp_nthreads_read_env(&hw_opt->nthreads_omp, bIsSimMaster);
1079
1080 #ifndef GMX_THREAD_MPI
1081     if (hw_opt->nthreads_tot > 0)
1082     {
1083         gmx_fatal(FARGS,"Setting the total number of threads is only supported with thread-MPI and Gromacs was compiled without thread-MPI");
1084     }
1085     if (hw_opt->nthreads_tmpi > 0)
1086     {
1087         gmx_fatal(FARGS,"Setting the number of thread-MPI threads is only supported with thread-MPI and Gromacs was compiled without thread-MPI");
1088     }
1089 #endif
1090
1091     if (hw_opt->nthreads_tot > 0 && hw_opt->nthreads_omp_pme <= 0)
1092     {
1093         /* We have the same number of OpenMP threads for PP and PME processes,
1094          * thus we can perform several consistency checks.
1095          */
1096         if (hw_opt->nthreads_tmpi > 0 &&
1097             hw_opt->nthreads_omp > 0 &&
1098             hw_opt->nthreads_tot != hw_opt->nthreads_tmpi*hw_opt->nthreads_omp)
1099         {
1100             gmx_fatal(FARGS,"The total number of threads requested (%d) does not match the thread-MPI threads (%d) times the OpenMP threads (%d) requested",
1101                       hw_opt->nthreads_tot,hw_opt->nthreads_tmpi,hw_opt->nthreads_omp);
1102         }
1103
1104         if (hw_opt->nthreads_tmpi > 0 &&
1105             hw_opt->nthreads_tot % hw_opt->nthreads_tmpi != 0)
1106         {
1107             gmx_fatal(FARGS,"The total number of threads requested (%d) is not divisible by the number of thread-MPI threads requested (%d)",
1108                       hw_opt->nthreads_tot,hw_opt->nthreads_tmpi);
1109         }
1110
1111         if (hw_opt->nthreads_omp > 0 &&
1112             hw_opt->nthreads_tot % hw_opt->nthreads_omp != 0)
1113         {
1114             gmx_fatal(FARGS,"The total number of threads requested (%d) is not divisible by the number of OpenMP threads requested (%d)",
1115                       hw_opt->nthreads_tot,hw_opt->nthreads_omp);
1116         }
1117
1118         if (hw_opt->nthreads_tmpi > 0 &&
1119             hw_opt->nthreads_omp <= 0)
1120         {
1121             hw_opt->nthreads_omp = hw_opt->nthreads_tot/hw_opt->nthreads_tmpi;
1122         }
1123     }
1124
1125 #ifndef GMX_OPENMP
1126     if (hw_opt->nthreads_omp > 1)
1127     {
1128         gmx_fatal(FARGS,"OpenMP threads are requested, but Gromacs was compiled without OpenMP support");
1129     }
1130 #endif
1131
1132     if (cutoff_scheme == ecutsGROUP)
1133     {
1134         /* We only have OpenMP support for PME only nodes */
1135         if (hw_opt->nthreads_omp > 1)
1136         {
1137             gmx_fatal(FARGS,"OpenMP threads have been requested with cut-off scheme %s, but these are only supported with cut-off scheme %s",
1138                       ecutscheme_names[cutoff_scheme],
1139                       ecutscheme_names[ecutsVERLET]);
1140         }
1141         hw_opt->nthreads_omp = 1;
1142     }
1143
1144     if (hw_opt->nthreads_omp_pme > 0 && hw_opt->nthreads_omp <= 0)
1145     {
1146         gmx_fatal(FARGS,"You need to specify -ntomp in addition to -ntomp_pme");
1147     }
1148
1149     if (hw_opt->nthreads_tot == 1)
1150     {
1151         hw_opt->nthreads_tmpi = 1;
1152
1153         if (hw_opt->nthreads_omp > 1)
1154         {
1155             gmx_fatal(FARGS,"You requested %d OpenMP threads with %d total threads",
1156                       hw_opt->nthreads_tmpi,hw_opt->nthreads_tot);
1157         }
1158         hw_opt->nthreads_omp = 1;
1159     }
1160
1161     if (hw_opt->nthreads_omp_pme <= 0 && hw_opt->nthreads_omp > 0)
1162     {
1163         hw_opt->nthreads_omp_pme = hw_opt->nthreads_omp;
1164     }
1165
1166     if (debug)
1167     {
1168         fprintf(debug,"hw_opt: nt %d ntmpi %d ntomp %d ntomp_pme %d gpu_id '%s'\n",
1169                 hw_opt->nthreads_tot,
1170                 hw_opt->nthreads_tmpi,
1171                 hw_opt->nthreads_omp,
1172                 hw_opt->nthreads_omp_pme,
1173                 hw_opt->gpu_id!=NULL ? hw_opt->gpu_id : "");
1174                 
1175     }
1176 }
1177
1178
1179 /* Override the value in inputrec with value passed on the command line (if any) */
1180 static void override_nsteps_cmdline(FILE *fplog,
1181                                     int nsteps_cmdline,
1182                                     t_inputrec *ir,
1183                                     const t_commrec *cr)
1184 {
1185     assert(ir);
1186     assert(cr);
1187
1188     /* override with anything else than the default -2 */
1189     if (nsteps_cmdline > -2)
1190     {
1191         char stmp[STRLEN];
1192
1193         ir->nsteps = nsteps_cmdline;
1194         if (EI_DYNAMICS(ir->eI))
1195         {
1196             sprintf(stmp, "Overriding nsteps with value passed on the command line: %d steps, %.3f ps",
1197                     nsteps_cmdline, nsteps_cmdline*ir->delta_t);
1198         }
1199         else
1200         {
1201             sprintf(stmp, "Overriding nsteps with value passed on the command line: %d steps",
1202                     nsteps_cmdline);
1203         }
1204
1205         md_print_warn(cr, fplog, "%s\n", stmp);
1206     }
1207 }
1208
1209 /* Data structure set by SIMMASTER which needs to be passed to all nodes
1210  * before the other nodes have read the tpx file and called gmx_detect_hardware.
1211  */
1212 typedef struct {
1213     int cutoff_scheme; /* The cutoff scheme from inputrec_t */
1214     gmx_bool bUseGPU;       /* Use GPU or GPU emulation          */
1215 } master_inf_t;
1216
1217 int mdrunner(gmx_hw_opt_t *hw_opt,
1218              FILE *fplog,t_commrec *cr,int nfile,
1219              const t_filenm fnm[], const output_env_t oenv, gmx_bool bVerbose,
1220              gmx_bool bCompact, int nstglobalcomm,
1221              ivec ddxyz,int dd_node_order,real rdd,real rconstr,
1222              const char *dddlb_opt,real dlb_scale,
1223              const char *ddcsx,const char *ddcsy,const char *ddcsz,
1224              const char *nbpu_opt,
1225              int nsteps_cmdline, int nstepout,int resetstep,
1226              int nmultisim,int repl_ex_nst,int repl_ex_nex,
1227              int repl_ex_seed, real pforce,real cpt_period,real max_hours,
1228              const char *deviceOptions, unsigned long Flags)
1229 {
1230     gmx_bool   bForceUseGPU,bTryUseGPU;
1231     double     nodetime=0,realtime;
1232     t_inputrec *inputrec;
1233     t_state    *state=NULL;
1234     matrix     box;
1235     gmx_ddbox_t ddbox={0};
1236     int        npme_major,npme_minor;
1237     real       tmpr1,tmpr2;
1238     t_nrnb     *nrnb;
1239     gmx_mtop_t *mtop=NULL;
1240     t_mdatoms  *mdatoms=NULL;
1241     t_forcerec *fr=NULL;
1242     t_fcdata   *fcd=NULL;
1243     real       ewaldcoeff=0;
1244     gmx_pme_t  *pmedata=NULL;
1245     gmx_vsite_t *vsite=NULL;
1246     gmx_constr_t constr;
1247     int        i,m,nChargePerturbed=-1,status,nalloc;
1248     char       *gro;
1249     gmx_wallcycle_t wcycle;
1250     gmx_bool       bReadRNG,bReadEkin;
1251     int        list;
1252     gmx_runtime_t runtime;
1253     int        rc;
1254     gmx_large_int_t reset_counters;
1255     gmx_edsam_t ed=NULL;
1256     t_commrec   *cr_old=cr; 
1257     int         nthreads_pme=1;
1258     int         nthreads_pp=1;
1259     gmx_membed_t membed=NULL;
1260     gmx_hw_info_t *hwinfo=NULL;
1261     master_inf_t minf={-1,FALSE};
1262
1263     /* CAUTION: threads may be started later on in this function, so
1264        cr doesn't reflect the final parallel state right now */
1265     snew(inputrec,1);
1266     snew(mtop,1);
1267     
1268     if (Flags & MD_APPENDFILES) 
1269     {
1270         fplog = NULL;
1271     }
1272
1273     bForceUseGPU = (strncmp(nbpu_opt, "gpu", 3) == 0);
1274     bTryUseGPU   = (strncmp(nbpu_opt, "auto", 4) == 0) || bForceUseGPU;
1275
1276     snew(state,1);
1277     if (SIMMASTER(cr)) 
1278     {
1279         /* Read (nearly) all data required for the simulation */
1280         read_tpx_state(ftp2fn(efTPX,nfile,fnm),inputrec,state,NULL,mtop);
1281
1282         if (inputrec->cutoff_scheme != ecutsVERLET &&
1283             ((Flags & MD_TESTVERLET) || getenv("GMX_VERLET_SCHEME") != NULL))
1284         {
1285             convert_to_verlet_scheme(fplog,inputrec,mtop,det(state->box));
1286         }
1287
1288         /* Detect hardware, gather information. With tMPI only thread 0 does it
1289          * and after threads are started broadcasts hwinfo around. */
1290         snew(hwinfo, 1);
1291         gmx_detect_hardware(fplog, hwinfo, cr,
1292                             bForceUseGPU, bTryUseGPU, hw_opt->gpu_id);
1293
1294         minf.cutoff_scheme = inputrec->cutoff_scheme;
1295         minf.bUseGPU       = FALSE;
1296
1297         if (inputrec->cutoff_scheme == ecutsVERLET)
1298         {
1299             prepare_verlet_scheme(fplog,hwinfo,cr,hw_opt,nbpu_opt,
1300                                   inputrec,mtop,state->box,
1301                                   &minf.bUseGPU);
1302         }
1303         else if (hwinfo->bCanUseGPU)
1304         {
1305             md_print_warn(cr,fplog,
1306                           "NOTE: GPU(s) found, but the current simulation can not use GPUs\n"
1307                           "      To use a GPU, set the mdp option: cutoff-scheme = Verlet\n"
1308                           "      (for quick performance testing you can use the -testverlet option)\n");
1309
1310             if (bForceUseGPU)
1311             {
1312                 gmx_fatal(FARGS,"GPU requested, but can't be used without cutoff-scheme=Verlet");
1313             }
1314         }
1315     }
1316 #ifndef GMX_THREAD_MPI
1317     if (PAR(cr))
1318     {
1319         gmx_bcast_sim(sizeof(minf),&minf,cr);
1320     }
1321 #endif
1322     if (minf.bUseGPU && cr->npmenodes == -1)
1323     {
1324         /* Don't automatically use PME-only nodes with GPUs */
1325         cr->npmenodes = 0;
1326     }
1327
1328     /* Check for externally set OpenMP affinity and turn off internal
1329      * pinning if any is found. We need to do this check early to tell
1330      * thread-MPI whether it should do pinning when spawning threads.
1331      */
1332     gmx_omp_check_thread_affinity(fplog, cr, hw_opt);
1333
1334 #ifdef GMX_THREAD_MPI
1335     /* With thread-MPI inputrec is only set here on the master thread */
1336     if (SIMMASTER(cr))
1337 #endif
1338     {
1339         check_and_update_hw_opt(hw_opt,minf.cutoff_scheme,SIMMASTER(cr));
1340
1341 #ifdef GMX_THREAD_MPI
1342         /* Early check for externally set process affinity. Can't do over all
1343          * MPI processes because hwinfo is not available everywhere, but with
1344          * thread-MPI it's needed as pinning might get turned off which needs
1345          * to be known before starting thread-MPI. */
1346         check_cpu_affinity_set(fplog,
1347                                NULL,
1348                                hw_opt, hwinfo->nthreads_hw_avail, FALSE);
1349 #endif
1350
1351 #ifdef GMX_THREAD_MPI
1352         if (cr->npmenodes > 0 && hw_opt->nthreads_tmpi <= 0)
1353         {
1354             gmx_fatal(FARGS,"You need to explicitly specify the number of MPI threads (-ntmpi) when using separate PME nodes");
1355         }
1356 #endif
1357
1358         if (hw_opt->nthreads_omp_pme != hw_opt->nthreads_omp &&
1359             cr->npmenodes <= 0)
1360         {
1361             gmx_fatal(FARGS,"You need to explicitly specify the number of PME nodes (-npme) when using different number of OpenMP threads for PP and PME nodes");
1362         }
1363     }
1364
1365 #ifdef GMX_THREAD_MPI
1366     if (SIMMASTER(cr))
1367     {
1368         /* NOW the threads will be started: */
1369         hw_opt->nthreads_tmpi = get_nthreads_mpi(hwinfo,
1370                                                  hw_opt,
1371                                                  inputrec, mtop,
1372                                                  cr, fplog);
1373         if (hw_opt->nthreads_tot > 0 && hw_opt->nthreads_omp <= 0)
1374         {
1375             hw_opt->nthreads_omp = hw_opt->nthreads_tot/hw_opt->nthreads_tmpi;
1376         }
1377
1378         if (hw_opt->nthreads_tmpi > 1)
1379         {
1380             /* now start the threads. */
1381             cr=mdrunner_start_threads(hw_opt, fplog, cr_old, nfile, fnm, 
1382                                       oenv, bVerbose, bCompact, nstglobalcomm, 
1383                                       ddxyz, dd_node_order, rdd, rconstr, 
1384                                       dddlb_opt, dlb_scale, ddcsx, ddcsy, ddcsz,
1385                                       nbpu_opt,
1386                                       nsteps_cmdline, nstepout, resetstep, nmultisim, 
1387                                       repl_ex_nst, repl_ex_nex, repl_ex_seed, pforce,
1388                                       cpt_period, max_hours, deviceOptions, 
1389                                       Flags);
1390             /* the main thread continues here with a new cr. We don't deallocate
1391                the old cr because other threads may still be reading it. */
1392             if (cr == NULL)
1393             {
1394                 gmx_comm("Failed to spawn threads");
1395             }
1396         }
1397     }
1398 #endif
1399     /* END OF CAUTION: cr is now reliable */
1400
1401     /* g_membed initialisation *
1402      * Because we change the mtop, init_membed is called before the init_parallel *
1403      * (in case we ever want to make it run in parallel) */
1404     if (opt2bSet("-membed",nfile,fnm))
1405     {
1406         if (MASTER(cr))
1407         {
1408             fprintf(stderr,"Initializing membed");
1409         }
1410         membed = init_membed(fplog,nfile,fnm,mtop,inputrec,state,cr,&cpt_period);
1411     }
1412
1413     if (PAR(cr))
1414     {
1415         /* now broadcast everything to the non-master nodes/threads: */
1416         init_parallel(fplog, cr, inputrec, mtop);
1417
1418         /* This check needs to happen after get_nthreads_mpi() */
1419         if (inputrec->cutoff_scheme == ecutsVERLET && (Flags & MD_PARTDEC))
1420         {
1421             gmx_fatal_collective(FARGS,cr,NULL,
1422                                  "The Verlet cut-off scheme is not supported with particle decomposition.\n"
1423                                  "You can achieve the same effect as particle decomposition by running in parallel using only OpenMP threads.");
1424         }
1425     }
1426     if (fplog != NULL)
1427     {
1428         pr_inputrec(fplog,0,"Input Parameters",inputrec,FALSE);
1429     }
1430
1431 #if defined GMX_THREAD_MPI
1432     /* With tMPI we detected on thread 0 and we'll just pass the hwinfo pointer
1433      * to the other threads  -- slightly uncool, but works fine, just need to
1434      * make sure that the data doesn't get freed twice. */
1435     if (cr->nnodes > 1)
1436     {
1437         if (!SIMMASTER(cr))
1438         {
1439             snew(hwinfo, 1);
1440         }
1441         gmx_bcast(sizeof(&hwinfo), &hwinfo, cr);
1442     }
1443 #else
1444     if (PAR(cr) && !SIMMASTER(cr))
1445     {
1446         /* now we have inputrec on all nodes, can run the detection */
1447         /* TODO: perhaps it's better to propagate within a node instead? */
1448         snew(hwinfo, 1);
1449         gmx_detect_hardware(fplog, hwinfo, cr,
1450                                  bForceUseGPU, bTryUseGPU, hw_opt->gpu_id);
1451     }
1452
1453     /* Now do the affinity check with MPI/no-MPI (done earlier with thread-MPI). */
1454     check_cpu_affinity_set(fplog, cr,
1455                            hw_opt, hwinfo->nthreads_hw_avail, FALSE);
1456 #endif
1457
1458     /* now make sure the state is initialized and propagated */
1459     set_state_entries(state,inputrec,cr->nnodes);
1460
1461     /* A parallel command line option consistency check that we can
1462        only do after any threads have started. */
1463     if (!PAR(cr) &&
1464         (ddxyz[XX] > 1 || ddxyz[YY] > 1 || ddxyz[ZZ] > 1 || cr->npmenodes > 0))
1465     {
1466         gmx_fatal(FARGS,
1467                   "The -dd or -npme option request a parallel simulation, "
1468 #ifndef GMX_MPI
1469                   "but %s was compiled without threads or MPI enabled"
1470 #else
1471 #ifdef GMX_THREAD_MPI
1472                   "but the number of threads (option -nt) is 1"
1473 #else
1474                   "but %s was not started through mpirun/mpiexec or only one process was requested through mpirun/mpiexec"
1475 #endif
1476 #endif
1477                   , ShortProgram()
1478             );
1479     }
1480
1481     if ((Flags & MD_RERUN) &&
1482         (EI_ENERGY_MINIMIZATION(inputrec->eI) || eiNM == inputrec->eI))
1483     {
1484         gmx_fatal(FARGS, "The .mdp file specified an energy mininization or normal mode algorithm, and these are not compatible with mdrun -rerun");
1485     }
1486
1487     if (can_use_allvsall(inputrec,mtop,TRUE,cr,fplog) && PAR(cr))
1488     {
1489         /* All-vs-all loops do not work with domain decomposition */
1490         Flags |= MD_PARTDEC;
1491     }
1492
1493     if (!EEL_PME(inputrec->coulombtype) || (Flags & MD_PARTDEC))
1494     {
1495         if (cr->npmenodes > 0)
1496         {
1497             if (!EEL_PME(inputrec->coulombtype))
1498             {
1499                 gmx_fatal_collective(FARGS,cr,NULL,
1500                                      "PME nodes are requested, but the system does not use PME electrostatics");
1501             }
1502             if (Flags & MD_PARTDEC)
1503             {
1504                 gmx_fatal_collective(FARGS,cr,NULL,
1505                                      "PME nodes are requested, but particle decomposition does not support separate PME nodes");
1506             }
1507         }
1508
1509         cr->npmenodes = 0;
1510     }
1511
1512 #ifdef GMX_FAHCORE
1513     fcRegisterSteps(inputrec->nsteps,inputrec->init_step);
1514 #endif
1515
1516     /* NMR restraints must be initialized before load_checkpoint,
1517      * since with time averaging the history is added to t_state.
1518      * For proper consistency check we therefore need to extend
1519      * t_state here.
1520      * So the PME-only nodes (if present) will also initialize
1521      * the distance restraints.
1522      */
1523     snew(fcd,1);
1524
1525     /* This needs to be called before read_checkpoint to extend the state */
1526     init_disres(fplog,mtop,inputrec,cr,Flags & MD_PARTDEC,fcd,state, repl_ex_nst > 0);
1527
1528     if (gmx_mtop_ftype_count(mtop,F_ORIRES) > 0)
1529     {
1530         if (PAR(cr) && !(Flags & MD_PARTDEC))
1531         {
1532             gmx_fatal(FARGS,"Orientation restraints do not work (yet) with domain decomposition, use particle decomposition (mdrun option -pd)");
1533         }
1534         /* Orientation restraints */
1535         if (MASTER(cr))
1536         {
1537             init_orires(fplog,mtop,state->x,inputrec,cr->ms,&(fcd->orires),
1538                         state);
1539         }
1540     }
1541
1542     if (DEFORM(*inputrec))
1543     {
1544         /* Store the deform reference box before reading the checkpoint */
1545         if (SIMMASTER(cr))
1546         {
1547             copy_mat(state->box,box);
1548         }
1549         if (PAR(cr))
1550         {
1551             gmx_bcast(sizeof(box),box,cr);
1552         }
1553         /* Because we do not have the update struct available yet
1554          * in which the reference values should be stored,
1555          * we store them temporarily in static variables.
1556          * This should be thread safe, since they are only written once
1557          * and with identical values.
1558          */
1559 #ifdef GMX_THREAD_MPI
1560         tMPI_Thread_mutex_lock(&deform_init_box_mutex);
1561 #endif
1562         deform_init_init_step_tpx = inputrec->init_step;
1563         copy_mat(box,deform_init_box_tpx);
1564 #ifdef GMX_THREAD_MPI
1565         tMPI_Thread_mutex_unlock(&deform_init_box_mutex);
1566 #endif
1567     }
1568
1569     if (opt2bSet("-cpi",nfile,fnm)) 
1570     {
1571         /* Check if checkpoint file exists before doing continuation.
1572          * This way we can use identical input options for the first and subsequent runs...
1573          */
1574         if( gmx_fexist_master(opt2fn_master("-cpi",nfile,fnm,cr),cr) )
1575         {
1576             load_checkpoint(opt2fn_master("-cpi",nfile,fnm,cr),&fplog,
1577                             cr,Flags & MD_PARTDEC,ddxyz,
1578                             inputrec,state,&bReadRNG,&bReadEkin,
1579                             (Flags & MD_APPENDFILES),
1580                             (Flags & MD_APPENDFILESSET));
1581             
1582             if (bReadRNG)
1583             {
1584                 Flags |= MD_READ_RNG;
1585             }
1586             if (bReadEkin)
1587             {
1588                 Flags |= MD_READ_EKIN;
1589             }
1590         }
1591     }
1592
1593     if (((MASTER(cr) || (Flags & MD_SEPPOT)) && (Flags & MD_APPENDFILES))
1594 #ifdef GMX_THREAD_MPI
1595         /* With thread MPI only the master node/thread exists in mdrun.c,
1596          * therefore non-master nodes need to open the "seppot" log file here.
1597          */
1598         || (!MASTER(cr) && (Flags & MD_SEPPOT))
1599 #endif
1600         )
1601     {
1602         gmx_log_open(ftp2fn(efLOG,nfile,fnm),cr,!(Flags & MD_SEPPOT),
1603                              Flags,&fplog);
1604     }
1605
1606     /* override nsteps with value from cmdline */
1607     override_nsteps_cmdline(fplog, nsteps_cmdline, inputrec, cr);
1608
1609     if (SIMMASTER(cr)) 
1610     {
1611         copy_mat(state->box,box);
1612     }
1613
1614     if (PAR(cr)) 
1615     {
1616         gmx_bcast(sizeof(box),box,cr);
1617     }
1618
1619     /* Essential dynamics */
1620     if (opt2bSet("-ei",nfile,fnm))
1621     {
1622         /* Open input and output files, allocate space for ED data structure */
1623         ed = ed_open(mtop->natoms,&state->edsamstate,nfile,fnm,Flags,oenv,cr);
1624     }
1625
1626     if (PAR(cr) && !((Flags & MD_PARTDEC) ||
1627                      EI_TPI(inputrec->eI) ||
1628                      inputrec->eI == eiNM))
1629     {
1630         cr->dd = init_domain_decomposition(fplog,cr,Flags,ddxyz,rdd,rconstr,
1631                                            dddlb_opt,dlb_scale,
1632                                            ddcsx,ddcsy,ddcsz,
1633                                            mtop,inputrec,
1634                                            box,state->x,
1635                                            &ddbox,&npme_major,&npme_minor);
1636
1637         make_dd_communicators(fplog,cr,dd_node_order);
1638
1639         /* Set overallocation to avoid frequent reallocation of arrays */
1640         set_over_alloc_dd(TRUE);
1641     }
1642     else
1643     {
1644         /* PME, if used, is done on all nodes with 1D decomposition */
1645         cr->npmenodes = 0;
1646         cr->duty = (DUTY_PP | DUTY_PME);
1647         npme_major = 1;
1648         npme_minor = 1;
1649         if (!EI_TPI(inputrec->eI))
1650         {
1651             npme_major = cr->nnodes;
1652         }
1653         
1654         if (inputrec->ePBC == epbcSCREW)
1655         {
1656             gmx_fatal(FARGS,
1657                       "pbc=%s is only implemented with domain decomposition",
1658                       epbc_names[inputrec->ePBC]);
1659         }
1660     }
1661
1662     if (PAR(cr))
1663     {
1664         /* After possible communicator splitting in make_dd_communicators.
1665          * we can set up the intra/inter node communication.
1666          */
1667         gmx_setup_nodecomm(fplog,cr);
1668     }
1669
1670     /* Initialize per-physical-node MPI process/thread ID and counters. */
1671     gmx_init_intranode_counters(cr);
1672
1673 #ifdef GMX_MPI
1674     md_print_info(cr,fplog,"Using %d MPI %s\n",
1675                   cr->nnodes,
1676 #ifdef GMX_THREAD_MPI
1677                   cr->nnodes==1 ? "thread" : "threads"
1678 #else
1679                   cr->nnodes==1 ? "process" : "processes"
1680 #endif
1681                   );
1682     fflush(stderr);
1683 #endif
1684
1685     gmx_omp_nthreads_init(fplog, cr,
1686                           hwinfo->nthreads_hw_avail,
1687                           hw_opt->nthreads_omp,
1688                           hw_opt->nthreads_omp_pme,
1689                           (cr->duty & DUTY_PP) == 0,
1690                           inputrec->cutoff_scheme == ecutsVERLET);
1691
1692     gmx_check_hw_runconf_consistency(fplog, hwinfo, cr, hw_opt->nthreads_tmpi, minf.bUseGPU);
1693
1694     /* getting number of PP/PME threads
1695        PME: env variable should be read only on one node to make sure it is 
1696        identical everywhere;
1697      */
1698     /* TODO nthreads_pp is only used for pinning threads.
1699      * This is a temporary solution until we have a hw topology library.
1700      */
1701     nthreads_pp  = gmx_omp_nthreads_get(emntNonbonded);
1702     nthreads_pme = gmx_omp_nthreads_get(emntPME);
1703
1704     wcycle = wallcycle_init(fplog,resetstep,cr,nthreads_pp,nthreads_pme);
1705
1706     if (PAR(cr))
1707     {
1708         /* Master synchronizes its value of reset_counters with all nodes 
1709          * including PME only nodes */
1710         reset_counters = wcycle_get_reset_counters(wcycle);
1711         gmx_bcast_sim(sizeof(reset_counters),&reset_counters,cr);
1712         wcycle_set_reset_counters(wcycle, reset_counters);
1713     }
1714
1715     snew(nrnb,1);
1716     if (cr->duty & DUTY_PP)
1717     {
1718         /* For domain decomposition we allocate dynamically
1719          * in dd_partition_system.
1720          */
1721         if (DOMAINDECOMP(cr))
1722         {
1723             bcast_state_setup(cr,state);
1724         }
1725         else
1726         {
1727             if (PAR(cr))
1728             {
1729                 bcast_state(cr,state,TRUE);
1730             }
1731         }
1732
1733         /* Initiate forcerecord */
1734         fr = mk_forcerec();
1735         fr->hwinfo = hwinfo;
1736         init_forcerec(fplog,oenv,fr,fcd,inputrec,mtop,cr,box,FALSE,
1737                       opt2fn("-table",nfile,fnm),
1738                       opt2fn("-tabletf",nfile,fnm),
1739                       opt2fn("-tablep",nfile,fnm),
1740                       opt2fn("-tableb",nfile,fnm),
1741                       nbpu_opt,
1742                       FALSE,pforce);
1743
1744         /* version for PCA_NOT_READ_NODE (see md.c) */
1745         /*init_forcerec(fplog,fr,fcd,inputrec,mtop,cr,box,FALSE,
1746           "nofile","nofile","nofile","nofile",FALSE,pforce);
1747           */        
1748         fr->bSepDVDL = ((Flags & MD_SEPPOT) == MD_SEPPOT);
1749
1750         /* Initialize QM-MM */
1751         if(fr->bQMMM)
1752         {
1753             init_QMMMrec(cr,box,mtop,inputrec,fr);
1754         }
1755
1756         /* Initialize the mdatoms structure.
1757          * mdatoms is not filled with atom data,
1758          * as this can not be done now with domain decomposition.
1759          */
1760         mdatoms = init_mdatoms(fplog,mtop,inputrec->efep!=efepNO);
1761
1762         /* Initialize the virtual site communication */
1763         vsite = init_vsite(mtop,cr,FALSE);
1764
1765         calc_shifts(box,fr->shift_vec);
1766
1767         /* With periodic molecules the charge groups should be whole at start up
1768          * and the virtual sites should not be far from their proper positions.
1769          */
1770         if (!inputrec->bContinuation && MASTER(cr) &&
1771             !(inputrec->ePBC != epbcNONE && inputrec->bPeriodicMols))
1772         {
1773             /* Make molecules whole at start of run */
1774             if (fr->ePBC != epbcNONE)
1775             {
1776                 do_pbc_first_mtop(fplog,inputrec->ePBC,box,mtop,state->x);
1777             }
1778             if (vsite)
1779             {
1780                 /* Correct initial vsite positions are required
1781                  * for the initial distribution in the domain decomposition
1782                  * and for the initial shell prediction.
1783                  */
1784                 construct_vsites_mtop(fplog,vsite,mtop,state->x);
1785             }
1786         }
1787
1788         if (EEL_PME(fr->eeltype))
1789         {
1790             ewaldcoeff = fr->ewaldcoeff;
1791             pmedata = &fr->pmedata;
1792         }
1793         else
1794         {
1795             pmedata = NULL;
1796         }
1797     }
1798     else
1799     {
1800         /* This is a PME only node */
1801
1802         /* We don't need the state */
1803         done_state(state);
1804
1805         ewaldcoeff = calc_ewaldcoeff(inputrec->rcoulomb, inputrec->ewald_rtol);
1806         snew(pmedata,1);
1807     }
1808
1809     /* Before setting affinity, check whether the affinity has changed
1810      * - which indicates that probably the OpenMP library has changed it since
1811      * we first checked). */
1812     check_cpu_affinity_set(fplog, cr, hw_opt, hwinfo->nthreads_hw_avail, TRUE);
1813
1814     /* Set the CPU affinity */
1815     set_cpu_affinity(fplog,cr,hw_opt,nthreads_pme,hwinfo,inputrec);
1816
1817     /* Initiate PME if necessary,
1818      * either on all nodes or on dedicated PME nodes only. */
1819     if (EEL_PME(inputrec->coulombtype))
1820     {
1821         if (mdatoms)
1822         {
1823             nChargePerturbed = mdatoms->nChargePerturbed;
1824         }
1825         if (cr->npmenodes > 0)
1826         {
1827             /* The PME only nodes need to know nChargePerturbed */
1828             gmx_bcast_sim(sizeof(nChargePerturbed),&nChargePerturbed,cr);
1829         }
1830
1831         if (cr->duty & DUTY_PME)
1832         {
1833             status = gmx_pme_init(pmedata,cr,npme_major,npme_minor,inputrec,
1834                                   mtop ? mtop->natoms : 0,nChargePerturbed,
1835                                   (Flags & MD_REPRODUCIBLE),nthreads_pme);
1836             if (status != 0) 
1837             {
1838                 gmx_fatal(FARGS,"Error %d initializing PME",status);
1839             }
1840         }
1841     }
1842
1843
1844     if (integrator[inputrec->eI].func == do_md)
1845     {
1846         /* Turn on signal handling on all nodes */
1847         /*
1848          * (A user signal from the PME nodes (if any)
1849          * is communicated to the PP nodes.
1850          */
1851         signal_handler_install();
1852     }
1853
1854     if (cr->duty & DUTY_PP)
1855     {
1856         if (inputrec->ePull != epullNO)
1857         {
1858             /* Initialize pull code */
1859             init_pull(fplog,inputrec,nfile,fnm,mtop,cr,oenv, inputrec->fepvals->init_lambda,
1860                       EI_DYNAMICS(inputrec->eI) && MASTER(cr),Flags);
1861         }
1862         
1863         if (inputrec->bRot)
1864         {
1865            /* Initialize enforced rotation code */
1866            init_rot(fplog,inputrec,nfile,fnm,cr,state->x,box,mtop,oenv,
1867                     bVerbose,Flags);
1868         }
1869
1870         constr = init_constraints(fplog,mtop,inputrec,ed,state,cr);
1871
1872         if (DOMAINDECOMP(cr))
1873         {
1874             dd_init_bondeds(fplog,cr->dd,mtop,vsite,constr,inputrec,
1875                             Flags & MD_DDBONDCHECK,fr->cginfo_mb);
1876
1877             set_dd_parameters(fplog,cr->dd,dlb_scale,inputrec,fr,&ddbox);
1878
1879             setup_dd_grid(fplog,cr->dd);
1880         }
1881
1882         /* Now do whatever the user wants us to do (how flexible...) */
1883         integrator[inputrec->eI].func(fplog,cr,nfile,fnm,
1884                                       oenv,bVerbose,bCompact,
1885                                       nstglobalcomm,
1886                                       vsite,constr,
1887                                       nstepout,inputrec,mtop,
1888                                       fcd,state,
1889                                       mdatoms,nrnb,wcycle,ed,fr,
1890                                       repl_ex_nst,repl_ex_nex,repl_ex_seed,
1891                                       membed,
1892                                       cpt_period,max_hours,
1893                                       deviceOptions,
1894                                       Flags,
1895                                       &runtime);
1896
1897         if (inputrec->ePull != epullNO)
1898         {
1899             finish_pull(fplog,inputrec->pull);
1900         }
1901         
1902         if (inputrec->bRot)
1903         {
1904             finish_rot(fplog,inputrec->rot);
1905         }
1906
1907     } 
1908     else 
1909     {
1910         /* do PME only */
1911         gmx_pmeonly(*pmedata,cr,nrnb,wcycle,ewaldcoeff,FALSE,inputrec);
1912     }
1913
1914     if (EI_DYNAMICS(inputrec->eI) || EI_TPI(inputrec->eI))
1915     {
1916         /* Some timing stats */  
1917         if (SIMMASTER(cr))
1918         {
1919             if (runtime.proc == 0)
1920             {
1921                 runtime.proc = runtime.real;
1922             }
1923         }
1924         else
1925         {
1926             runtime.real = 0;
1927         }
1928     }
1929
1930     wallcycle_stop(wcycle,ewcRUN);
1931
1932     /* Finish up, write some stuff
1933      * if rerunMD, don't write last frame again 
1934      */
1935     finish_run(fplog,cr,ftp2fn(efSTO,nfile,fnm),
1936                inputrec,nrnb,wcycle,&runtime,
1937                fr != NULL && fr->nbv != NULL && fr->nbv->bUseGPU ?
1938                  nbnxn_cuda_get_timings(fr->nbv->cu_nbv) : NULL,
1939                nthreads_pp, 
1940                EI_DYNAMICS(inputrec->eI) && !MULTISIM(cr));
1941
1942     if ((cr->duty & DUTY_PP) && fr->nbv != NULL && fr->nbv->bUseGPU)
1943     {
1944         char gpu_err_str[STRLEN];
1945
1946         /* free GPU memory and uninitialize GPU (by destroying the context) */
1947         nbnxn_cuda_free(fplog, fr->nbv->cu_nbv);
1948
1949         if (!free_gpu(gpu_err_str))
1950         {
1951             gmx_warning("On node %d failed to free GPU #%d: %s",
1952                         cr->nodeid, get_current_gpu_device_id(), gpu_err_str);
1953         }
1954     }
1955
1956     if (opt2bSet("-membed",nfile,fnm))
1957     {
1958         sfree(membed);
1959     }
1960
1961 #ifdef GMX_THREAD_MPI
1962     if (PAR(cr) && SIMMASTER(cr))
1963 #endif
1964     {
1965         gmx_hardware_info_free(hwinfo);
1966     }
1967
1968     /* Does what it says */  
1969     print_date_and_time(fplog,cr->nodeid,"Finished mdrun",&runtime);
1970
1971     /* Close logfile already here if we were appending to it */
1972     if (MASTER(cr) && (Flags & MD_APPENDFILES))
1973     {
1974         gmx_log_close(fplog);
1975     }   
1976
1977     rc=(int)gmx_get_stop_condition();
1978
1979 #ifdef GMX_THREAD_MPI
1980     /* we need to join all threads. The sub-threads join when they
1981        exit this function, but the master thread needs to be told to 
1982        wait for that. */
1983     if (PAR(cr) && MASTER(cr))
1984     {
1985         tMPI_Finalize();
1986     }
1987 #endif
1988
1989     return rc;
1990 }