23aa493db585568c5808b5a6bcd952e3759bdaf9
[alexxy/gromacs.git] / src / gromacs / gmxlib / checkpoint.c
1 /* -*- mode: c; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; c-file-style: "stroustrup"; -*-
2  *
3  *
4  * This file is part of Gromacs        Copyright (c) 1991-2008
5  * David van der Spoel, Erik Lindahl, Berk Hess, University of Groningen.
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * To help us fund GROMACS development, we humbly ask that you cite
13  * the research papers on the package. Check out http://www.gromacs.org
14  *
15  * And Hey:
16  * Gnomes, ROck Monsters And Chili Sauce
17  */
18
19 /* The source code in this file should be thread-safe.
20    Please keep it that way. */
21
22
23 #ifdef HAVE_CONFIG_H
24 #include <config.h>
25 #endif
26
27 #include <string.h>
28 #include <time.h>
29
30 #ifdef HAVE_SYS_TIME_H
31 #include <sys/time.h>
32 #endif
33
34 #ifdef HAVE_UNISTD_H
35 #include <unistd.h>
36 #endif
37
38 #ifdef GMX_NATIVE_WINDOWS
39 /* _chsize_s */
40 #include <io.h>
41 #include <sys/locking.h>
42 #endif
43
44
45 #include "filenm.h"
46 #include "names.h"
47 #include "typedefs.h"
48 #include "smalloc.h"
49 #include "gmxfio.h"
50 #include "xdrf.h"
51 #include "statutil.h"
52 #include "txtdump.h"
53 #include "vec.h"
54 #include "network.h"
55 #include "gmx_random.h"
56 #include "checkpoint.h"
57 #include "futil.h"
58 #include "string2.h"
59 #include <fcntl.h>
60
61 #include "buildinfo.h"
62
63 #ifdef GMX_FAHCORE
64 #include "corewrap.h"
65 #endif
66
67
68 /* Portable version of ctime_r implemented in src/gmxlib/string2.c, but we do not want it declared in public installed headers */
69 char *
70 gmx_ctime_r(const time_t *clock, char *buf, int n);
71
72
73 #define CPT_MAGIC1 171817
74 #define CPT_MAGIC2 171819
75 #define CPTSTRLEN 1024
76
77 #ifdef GMX_DOUBLE
78 #define GMX_CPT_BUILD_DP 1
79 #else
80 #define GMX_CPT_BUILD_DP 0
81 #endif
82
83 /* cpt_version should normally only be changed
84  * when the header of footer format changes.
85  * The state data format itself is backward and forward compatible.
86  * But old code can not read a new entry that is present in the file
87  * (but can read a new format when new entries are not present).
88  */
89 static const int cpt_version = 15;
90
91
92 const char *est_names[estNR] =
93 {
94     "FE-lambda",
95     "box", "box-rel", "box-v", "pres_prev",
96     "nosehoover-xi", "thermostat-integral",
97     "x", "v", "SDx", "CGp", "LD-rng", "LD-rng-i",
98     "disre_initf", "disre_rm3tav",
99     "orire_initf", "orire_Dtav",
100     "svir_prev", "nosehoover-vxi", "v_eta", "vol0", "nhpres_xi", "nhpres_vxi", "fvir_prev", "fep_state", "MC-rng", "MC-rng-i"
101 };
102
103 enum {
104     eeksEKIN_N, eeksEKINH, eeksDEKINDL, eeksMVCOS, eeksEKINF, eeksEKINO, eeksEKINSCALEF, eeksEKINSCALEH, eeksVSCALE, eeksEKINTOTAL, eeksNR
105 };
106
107 const char *eeks_names[eeksNR] =
108 {
109     "Ekin_n", "Ekinh", "dEkindlambda", "mv_cos",
110     "Ekinf", "Ekinh_old", "EkinScaleF_NHC", "EkinScaleH_NHC", "Vscale_NHC", "Ekin_Total"
111 };
112
113 enum {
114     eenhENERGY_N, eenhENERGY_AVER, eenhENERGY_SUM, eenhENERGY_NSUM,
115     eenhENERGY_SUM_SIM, eenhENERGY_NSUM_SIM,
116     eenhENERGY_NSTEPS, eenhENERGY_NSTEPS_SIM,
117     eenhENERGY_DELTA_H_NN,
118     eenhENERGY_DELTA_H_LIST,
119     eenhENERGY_DELTA_H_STARTTIME,
120     eenhENERGY_DELTA_H_STARTLAMBDA,
121     eenhNR
122 };
123
124 const char *eenh_names[eenhNR] =
125 {
126     "energy_n", "energy_aver", "energy_sum", "energy_nsum",
127     "energy_sum_sim", "energy_nsum_sim",
128     "energy_nsteps", "energy_nsteps_sim",
129     "energy_delta_h_nn",
130     "energy_delta_h_list",
131     "energy_delta_h_start_time",
132     "energy_delta_h_start_lambda"
133 };
134
135 /* free energy history variables -- need to be preserved over checkpoint */
136 enum {
137     edfhBEQUIL, edfhNATLAMBDA, edfhWLHISTO, edfhWLDELTA, edfhSUMWEIGHTS, edfhSUMDG, edfhSUMMINVAR, edfhSUMVAR,
138     edfhACCUMP, edfhACCUMM, edfhACCUMP2, edfhACCUMM2, edfhTIJ, edfhTIJEMP, edfhNR
139 };
140 /* free energy history variable names  */
141 const char *edfh_names[edfhNR] =
142 {
143     "bEquilibrated", "N_at_state", "Wang-Landau_Histogram", "Wang-Landau-delta", "Weights", "Free Energies", "minvar", "variance",
144     "accumulated_plus", "accumulated_minus", "accumulated_plus_2",  "accumulated_minus_2", "Tij", "Tij_empirical"
145 };
146
147 #ifdef GMX_NATIVE_WINDOWS
148 static int
149 gmx_wintruncate(const char *filename, __int64 size)
150 {
151 #ifdef GMX_FAHCORE
152     /*we do this elsewhere*/
153     return 0;
154 #else
155     FILE *fp;
156     int   rc;
157
158     fp = fopen(filename, "rb+");
159
160     if (fp == NULL)
161     {
162         return -1;
163     }
164
165     return _chsize_s( fileno(fp), size);
166 #endif
167 }
168 #endif
169
170
171 enum {
172     ecprREAL, ecprRVEC, ecprMATRIX
173 };
174
175 enum {
176     cptpEST, cptpEEKS, cptpEENH, cptpEDFH
177 };
178 /* enums for the different components of checkpoint variables, replacing the hard coded ones.
179    cptpEST - state variables.
180    cptpEEKS - Kinetic energy state variables.
181    cptpEENH - Energy history state variables.
182    cptpEDFH - free energy history variables.
183  */
184
185
186 static const char *st_names(int cptp, int ecpt)
187 {
188     switch (cptp)
189     {
190         case cptpEST: return est_names [ecpt]; break;
191         case cptpEEKS: return eeks_names[ecpt]; break;
192         case cptpEENH: return eenh_names[ecpt]; break;
193         case cptpEDFH: return edfh_names[ecpt]; break;
194     }
195
196     return NULL;
197 }
198
199 static void cp_warning(FILE *fp)
200 {
201     fprintf(fp, "\nWARNING: Checkpoint file is corrupted or truncated\n\n");
202 }
203
204 static void cp_error()
205 {
206     gmx_fatal(FARGS, "Checkpoint file corrupted/truncated, or maybe you are out of disk space?");
207 }
208
209 static void do_cpt_string_err(XDR *xd, gmx_bool bRead, const char *desc, char **s, FILE *list)
210 {
211     bool_t res = 0;
212
213     if (bRead)
214     {
215         snew(*s, CPTSTRLEN);
216     }
217     res = xdr_string(xd, s, CPTSTRLEN);
218     if (res == 0)
219     {
220         cp_error();
221     }
222     if (list)
223     {
224         fprintf(list, "%s = %s\n", desc, *s);
225         sfree(*s);
226     }
227 }
228
229 static int do_cpt_int(XDR *xd, const char *desc, int *i, FILE *list)
230 {
231     bool_t res = 0;
232
233     res = xdr_int(xd, i);
234     if (res == 0)
235     {
236         return -1;
237     }
238     if (list)
239     {
240         fprintf(list, "%s = %d\n", desc, *i);
241     }
242     return 0;
243 }
244
245 static int do_cpt_u_chars(XDR *xd, const char *desc, int n, unsigned char *i, FILE *list)
246 {
247     bool_t res = 1;
248     int    j;
249     if (list)
250     {
251         fprintf(list, "%s = ", desc);
252     }
253     for (j = 0; j < n && res; j++)
254     {
255         res &= xdr_u_char(xd, &i[j]);
256         if (list)
257         {
258             fprintf(list, "%02x", i[j]);
259         }
260     }
261     if (list)
262     {
263         fprintf(list, "\n");
264     }
265     if (res == 0)
266     {
267         return -1;
268     }
269
270     return 0;
271 }
272
273 static void do_cpt_int_err(XDR *xd, const char *desc, int *i, FILE *list)
274 {
275     if (do_cpt_int(xd, desc, i, list) < 0)
276     {
277         cp_error();
278     }
279 }
280
281 static void do_cpt_step_err(XDR *xd, const char *desc, gmx_large_int_t *i, FILE *list)
282 {
283     bool_t res = 0;
284     char   buf[STEPSTRSIZE];
285
286     res = xdr_gmx_large_int(xd, i);
287     if (res == 0)
288     {
289         cp_error();
290     }
291     if (list)
292     {
293         fprintf(list, "%s = %s\n", desc, gmx_step_str(*i, buf));
294     }
295 }
296
297 static void do_cpt_double_err(XDR *xd, const char *desc, double *f, FILE *list)
298 {
299     bool_t res = 0;
300
301     res = xdr_double(xd, f);
302     if (res == 0)
303     {
304         cp_error();
305     }
306     if (list)
307     {
308         fprintf(list, "%s = %f\n", desc, *f);
309     }
310 }
311
312 static void do_cpt_real_err(XDR *xd, real *f)
313 {
314     bool_t res = 0;
315
316 #ifdef GMX_DOUBLE
317     res = xdr_double(xd, f);
318 #else
319     res = xdr_float(xd, f);
320 #endif
321     if (res == 0)
322     {
323         cp_error();
324     }
325 }
326
327 static void do_cpt_n_rvecs_err(XDR *xd, const char *desc, int n, rvec f[], FILE *list)
328 {
329     int i, j;
330
331     for (i = 0; i < n; i++)
332     {
333         for (j = 0; j < DIM; j++)
334         {
335             do_cpt_real_err(xd, &f[i][j]);
336         }
337     }
338
339     if (list)
340     {
341         pr_rvecs(list, 0, desc, f, n);
342     }
343 }
344
345 /* If nval >= 0, nval is used; on read this should match the passed value.
346  * If nval n<0, *nptr is used; on read the value is stored in nptr
347  */
348 static int do_cpte_reals_low(XDR *xd, int cptp, int ecpt, int sflags,
349                              int nval, int *nptr, real **v,
350                              FILE *list, int erealtype)
351 {
352     bool_t  res = 0;
353 #ifndef GMX_DOUBLE
354     int     dtc = xdr_datatype_float;
355 #else
356     int     dtc = xdr_datatype_double;
357 #endif
358     real   *vp, *va = NULL;
359     float  *vf;
360     double *vd;
361     int     nf, dt, i;
362
363     if (list == NULL)
364     {
365         if (nval >= 0)
366         {
367             nf = nval;
368         }
369         else
370         {
371             if (nptr == NULL)
372             {
373                 gmx_incons("*ntpr=NULL in do_cpte_reals_low");
374             }
375             nf = *nptr;
376         }
377     }
378     res = xdr_int(xd, &nf);
379     if (res == 0)
380     {
381         return -1;
382     }
383     if (list == NULL)
384     {
385         if (nval >= 0)
386         {
387             if (nf != nval)
388             {
389                 gmx_fatal(FARGS, "Count mismatch for state entry %s, code count is %d, file count is %d\n", st_names(cptp, ecpt), nval, nf);
390             }
391         }
392         else
393         {
394             *nptr = nf;
395         }
396     }
397     dt  = dtc;
398     res = xdr_int(xd, &dt);
399     if (res == 0)
400     {
401         return -1;
402     }
403     if (dt != dtc)
404     {
405         fprintf(stderr, "Precision mismatch for state entry %s, code precision is %s, file precision is %s\n",
406                 st_names(cptp, ecpt), xdr_datatype_names[dtc],
407                 xdr_datatype_names[dt]);
408     }
409     if (list || !(sflags & (1<<ecpt)))
410     {
411         snew(va, nf);
412         vp = va;
413     }
414     else
415     {
416         if (*v == NULL)
417         {
418             snew(*v, nf);
419         }
420         vp = *v;
421     }
422     if (dt == xdr_datatype_float)
423     {
424         if (dtc == xdr_datatype_float)
425         {
426             vf = (float *)vp;
427         }
428         else
429         {
430             snew(vf, nf);
431         }
432         res = xdr_vector(xd, (char *)vf, nf,
433                          (unsigned int)sizeof(float), (xdrproc_t)xdr_float);
434         if (res == 0)
435         {
436             return -1;
437         }
438         if (dtc != xdr_datatype_float)
439         {
440             for (i = 0; i < nf; i++)
441             {
442                 vp[i] = vf[i];
443             }
444             sfree(vf);
445         }
446     }
447     else
448     {
449         if (dtc == xdr_datatype_double)
450         {
451             vd = (double *)vp;
452         }
453         else
454         {
455             snew(vd, nf);
456         }
457         res = xdr_vector(xd, (char *)vd, nf,
458                          (unsigned int)sizeof(double), (xdrproc_t)xdr_double);
459         if (res == 0)
460         {
461             return -1;
462         }
463         if (dtc != xdr_datatype_double)
464         {
465             for (i = 0; i < nf; i++)
466             {
467                 vp[i] = vd[i];
468             }
469             sfree(vd);
470         }
471     }
472
473     if (list)
474     {
475         switch (erealtype)
476         {
477             case ecprREAL:
478                 pr_reals(list, 0, st_names(cptp, ecpt), vp, nf);
479                 break;
480             case ecprRVEC:
481                 pr_rvecs(list, 0, st_names(cptp, ecpt), (rvec *)vp, nf/3);
482                 break;
483             default:
484                 gmx_incons("Unknown checkpoint real type");
485         }
486     }
487     if (va)
488     {
489         sfree(va);
490     }
491
492     return 0;
493 }
494
495
496 /* This function stores n along with the reals for reading,
497  * but on reading it assumes that n matches the value in the checkpoint file,
498  * a fatal error is generated when this is not the case.
499  */
500 static int do_cpte_reals(XDR *xd, int cptp, int ecpt, int sflags,
501                          int n, real **v, FILE *list)
502 {
503     return do_cpte_reals_low(xd, cptp, ecpt, sflags, n, NULL, v, list, ecprREAL);
504 }
505
506 /* This function does the same as do_cpte_reals,
507  * except that on reading it ignores the passed value of *n
508  * and stored the value read from the checkpoint file in *n.
509  */
510 static int do_cpte_n_reals(XDR *xd, int cptp, int ecpt, int sflags,
511                            int *n, real **v, FILE *list)
512 {
513     return do_cpte_reals_low(xd, cptp, ecpt, sflags, -1, n, v, list, ecprREAL);
514 }
515
516 static int do_cpte_real(XDR *xd, int cptp, int ecpt, int sflags,
517                         real *r, FILE *list)
518 {
519     int n;
520
521     return do_cpte_reals_low(xd, cptp, ecpt, sflags, 1, NULL, &r, list, ecprREAL);
522 }
523
524 static int do_cpte_ints(XDR *xd, int cptp, int ecpt, int sflags,
525                         int n, int **v, FILE *list)
526 {
527     bool_t res = 0;
528     int    dtc = xdr_datatype_int;
529     int   *vp, *va = NULL;
530     int    nf, dt, i;
531
532     nf  = n;
533     res = xdr_int(xd, &nf);
534     if (res == 0)
535     {
536         return -1;
537     }
538     if (list == NULL && v != NULL && nf != n)
539     {
540         gmx_fatal(FARGS, "Count mismatch for state entry %s, code count is %d, file count is %d\n", st_names(cptp, ecpt), n, nf);
541     }
542     dt  = dtc;
543     res = xdr_int(xd, &dt);
544     if (res == 0)
545     {
546         return -1;
547     }
548     if (dt != dtc)
549     {
550         gmx_fatal(FARGS, "Type mismatch for state entry %s, code type is %s, file type is %s\n",
551                   st_names(cptp, ecpt), xdr_datatype_names[dtc],
552                   xdr_datatype_names[dt]);
553     }
554     if (list || !(sflags & (1<<ecpt)) || v == NULL)
555     {
556         snew(va, nf);
557         vp = va;
558     }
559     else
560     {
561         if (*v == NULL)
562         {
563             snew(*v, nf);
564         }
565         vp = *v;
566     }
567     res = xdr_vector(xd, (char *)vp, nf,
568                      (unsigned int)sizeof(int), (xdrproc_t)xdr_int);
569     if (res == 0)
570     {
571         return -1;
572     }
573     if (list)
574     {
575         pr_ivec(list, 0, st_names(cptp, ecpt), vp, nf, TRUE);
576     }
577     if (va)
578     {
579         sfree(va);
580     }
581
582     return 0;
583 }
584
585 static int do_cpte_int(XDR *xd, int cptp, int ecpt, int sflags,
586                        int *i, FILE *list)
587 {
588     return do_cpte_ints(xd, cptp, ecpt, sflags, 1, &i, list);
589 }
590
591 static int do_cpte_doubles(XDR *xd, int cptp, int ecpt, int sflags,
592                            int n, double **v, FILE *list)
593 {
594     bool_t  res = 0;
595     int     dtc = xdr_datatype_double;
596     double *vp, *va = NULL;
597     int     nf, dt, i;
598
599     nf  = n;
600     res = xdr_int(xd, &nf);
601     if (res == 0)
602     {
603         return -1;
604     }
605     if (list == NULL && nf != n)
606     {
607         gmx_fatal(FARGS, "Count mismatch for state entry %s, code count is %d, file count is %d\n", st_names(cptp, ecpt), n, nf);
608     }
609     dt  = dtc;
610     res = xdr_int(xd, &dt);
611     if (res == 0)
612     {
613         return -1;
614     }
615     if (dt != dtc)
616     {
617         gmx_fatal(FARGS, "Precision mismatch for state entry %s, code precision is %s, file precision is %s\n",
618                   st_names(cptp, ecpt), xdr_datatype_names[dtc],
619                   xdr_datatype_names[dt]);
620     }
621     if (list || !(sflags & (1<<ecpt)))
622     {
623         snew(va, nf);
624         vp = va;
625     }
626     else
627     {
628         if (*v == NULL)
629         {
630             snew(*v, nf);
631         }
632         vp = *v;
633     }
634     res = xdr_vector(xd, (char *)vp, nf,
635                      (unsigned int)sizeof(double), (xdrproc_t)xdr_double);
636     if (res == 0)
637     {
638         return -1;
639     }
640     if (list)
641     {
642         pr_doubles(list, 0, st_names(cptp, ecpt), vp, nf);
643     }
644     if (va)
645     {
646         sfree(va);
647     }
648
649     return 0;
650 }
651
652 static int do_cpte_double(XDR *xd, int cptp, int ecpt, int sflags,
653                           double *r, FILE *list)
654 {
655     return do_cpte_doubles(xd, cptp, ecpt, sflags, 1, &r, list);
656 }
657
658
659 static int do_cpte_rvecs(XDR *xd, int cptp, int ecpt, int sflags,
660                          int n, rvec **v, FILE *list)
661 {
662     int n3;
663
664     return do_cpte_reals_low(xd, cptp, ecpt, sflags,
665                              n*DIM, NULL, (real **)v, list, ecprRVEC);
666 }
667
668 static int do_cpte_matrix(XDR *xd, int cptp, int ecpt, int sflags,
669                           matrix v, FILE *list)
670 {
671     real *vr;
672     real  ret;
673
674     vr  = (real *)&(v[0][0]);
675     ret = do_cpte_reals_low(xd, cptp, ecpt, sflags,
676                             DIM*DIM, NULL, &vr, NULL, ecprMATRIX);
677
678     if (list && ret == 0)
679     {
680         pr_rvecs(list, 0, st_names(cptp, ecpt), v, DIM);
681     }
682
683     return ret;
684 }
685
686
687 static int do_cpte_nmatrix(XDR *xd, int cptp, int ecpt, int sflags,
688                            int n, real **v, FILE *list)
689 {
690     int   i;
691     real *vr;
692     real  ret, reti;
693     char  name[CPTSTRLEN];
694
695     ret = 0;
696     if (v == NULL)
697     {
698         snew(v, n);
699     }
700     for (i = 0; i < n; i++)
701     {
702         reti = 0;
703         vr   = v[i];
704         reti = do_cpte_reals_low(xd, cptp, ecpt, sflags, n, NULL, &(v[i]), NULL, ecprREAL);
705         if (list && reti == 0)
706         {
707             sprintf(name, "%s[%d]", st_names(cptp, ecpt), i);
708             pr_reals(list, 0, name, v[i], n);
709         }
710         if (reti == 0)
711         {
712             ret = 0;
713         }
714     }
715     return ret;
716 }
717
718 static int do_cpte_matrices(XDR *xd, int cptp, int ecpt, int sflags,
719                             int n, matrix **v, FILE *list)
720 {
721     bool_t  res = 0;
722     matrix *vp, *va = NULL;
723     real   *vr;
724     int     nf, i, j, k;
725     int     ret;
726
727     nf  = n;
728     res = xdr_int(xd, &nf);
729     if (res == 0)
730     {
731         return -1;
732     }
733     if (list == NULL && nf != n)
734     {
735         gmx_fatal(FARGS, "Count mismatch for state entry %s, code count is %d, file count is %d\n", st_names(cptp, ecpt), n, nf);
736     }
737     if (list || !(sflags & (1<<ecpt)))
738     {
739         snew(va, nf);
740         vp = va;
741     }
742     else
743     {
744         if (*v == NULL)
745         {
746             snew(*v, nf);
747         }
748         vp = *v;
749     }
750     snew(vr, nf*DIM*DIM);
751     for (i = 0; i < nf; i++)
752     {
753         for (j = 0; j < DIM; j++)
754         {
755             for (k = 0; k < DIM; k++)
756             {
757                 vr[(i*DIM+j)*DIM+k] = vp[i][j][k];
758             }
759         }
760     }
761     ret = do_cpte_reals_low(xd, cptp, ecpt, sflags,
762                             nf*DIM*DIM, NULL, &vr, NULL, ecprMATRIX);
763     for (i = 0; i < nf; i++)
764     {
765         for (j = 0; j < DIM; j++)
766         {
767             for (k = 0; k < DIM; k++)
768             {
769                 vp[i][j][k] = vr[(i*DIM+j)*DIM+k];
770             }
771         }
772     }
773     sfree(vr);
774
775     if (list && ret == 0)
776     {
777         for (i = 0; i < nf; i++)
778         {
779             pr_rvecs(list, 0, st_names(cptp, ecpt), vp[i], DIM);
780         }
781     }
782     if (va)
783     {
784         sfree(va);
785     }
786
787     return ret;
788 }
789
790 static void do_cpt_header(XDR *xd, gmx_bool bRead, int *file_version,
791                           char **version, char **btime, char **buser, char **bhost,
792                           int *double_prec,
793                           char **fprog, char **ftime,
794                           int *eIntegrator, int *simulation_part,
795                           gmx_large_int_t *step, double *t,
796                           int *nnodes, int *dd_nc, int *npme,
797                           int *natoms, int *ngtc, int *nnhpres, int *nhchainlength,
798                           int *nlambda, int *flags_state,
799                           int *flags_eks, int *flags_enh, int *flags_dfh,
800                           int *nED,
801                           FILE *list)
802 {
803     bool_t res = 0;
804     int    magic;
805     int    idum = 0;
806     int    i;
807     char  *fhost;
808
809     if (bRead)
810     {
811         magic = -1;
812     }
813     else
814     {
815         magic = CPT_MAGIC1;
816     }
817     res = xdr_int(xd, &magic);
818     if (res == 0)
819     {
820         gmx_fatal(FARGS, "The checkpoint file is empty/corrupted, or maybe you are out of disk space?");
821     }
822     if (magic != CPT_MAGIC1)
823     {
824         gmx_fatal(FARGS, "Start of file magic number mismatch, checkpoint file has %d, should be %d\n"
825                   "The checkpoint file is corrupted or not a checkpoint file",
826                   magic, CPT_MAGIC1);
827     }
828     if (!bRead)
829     {
830         snew(fhost, 255);
831 #ifdef HAVE_UNISTD_H
832         if (gethostname(fhost, 255) != 0)
833         {
834             sprintf(fhost, "unknown");
835         }
836 #else
837         sprintf(fhost, "unknown");
838 #endif
839     }
840     do_cpt_string_err(xd, bRead, "GROMACS version", version, list);
841     do_cpt_string_err(xd, bRead, "GROMACS build time", btime, list);
842     do_cpt_string_err(xd, bRead, "GROMACS build user", buser, list);
843     do_cpt_string_err(xd, bRead, "GROMACS build host", bhost, list);
844     do_cpt_string_err(xd, bRead, "generating program", fprog, list);
845     do_cpt_string_err(xd, bRead, "generation time", ftime, list);
846     *file_version = cpt_version;
847     do_cpt_int_err(xd, "checkpoint file version", file_version, list);
848     if (*file_version > cpt_version)
849     {
850         gmx_fatal(FARGS, "Attempting to read a checkpoint file of version %d with code of version %d\n", *file_version, cpt_version);
851     }
852     if (*file_version >= 13)
853     {
854         do_cpt_int_err(xd, "GROMACS double precision", double_prec, list);
855     }
856     else
857     {
858         *double_prec = -1;
859     }
860     if (*file_version >= 12)
861     {
862         do_cpt_string_err(xd, bRead, "generating host", &fhost, list);
863         if (list == NULL)
864         {
865             sfree(fhost);
866         }
867     }
868     do_cpt_int_err(xd, "#atoms", natoms, list);
869     do_cpt_int_err(xd, "#T-coupling groups", ngtc, list);
870     if (*file_version >= 10)
871     {
872         do_cpt_int_err(xd, "#Nose-Hoover T-chains", nhchainlength, list);
873     }
874     else
875     {
876         *nhchainlength = 1;
877     }
878     if (*file_version >= 11)
879     {
880         do_cpt_int_err(xd, "#Nose-Hoover T-chains for barostat ", nnhpres, list);
881     }
882     else
883     {
884         *nnhpres = 0;
885     }
886     if (*file_version >= 14)
887     {
888         do_cpt_int_err(xd, "# of total lambda states ", nlambda, list);
889     }
890     else
891     {
892         *nlambda = 0;
893     }
894     do_cpt_int_err(xd, "integrator", eIntegrator, list);
895     if (*file_version >= 3)
896     {
897         do_cpt_int_err(xd, "simulation part #", simulation_part, list);
898     }
899     else
900     {
901         *simulation_part = 1;
902     }
903     if (*file_version >= 5)
904     {
905         do_cpt_step_err(xd, "step", step, list);
906     }
907     else
908     {
909         do_cpt_int_err(xd, "step", &idum, list);
910         *step = idum;
911     }
912     do_cpt_double_err(xd, "t", t, list);
913     do_cpt_int_err(xd, "#PP-nodes", nnodes, list);
914     idum = 1;
915     do_cpt_int_err(xd, "dd_nc[x]", dd_nc ? &(dd_nc[0]) : &idum, list);
916     do_cpt_int_err(xd, "dd_nc[y]", dd_nc ? &(dd_nc[1]) : &idum, list);
917     do_cpt_int_err(xd, "dd_nc[z]", dd_nc ? &(dd_nc[2]) : &idum, list);
918     do_cpt_int_err(xd, "#PME-only nodes", npme, list);
919     do_cpt_int_err(xd, "state flags", flags_state, list);
920     if (*file_version >= 4)
921     {
922         do_cpt_int_err(xd, "ekin data flags", flags_eks, list);
923         do_cpt_int_err(xd, "energy history flags", flags_enh, list);
924     }
925     else
926     {
927         *flags_eks   = 0;
928         *flags_enh   = (*flags_state >> (estORIRE_DTAV+1));
929         *flags_state = (*flags_state & ~((1<<(estORIRE_DTAV+1)) |
930                                          (1<<(estORIRE_DTAV+2)) |
931                                          (1<<(estORIRE_DTAV+3))));
932     }
933     if (*file_version >= 14)
934     {
935         do_cpt_int_err(xd, "df history flags", flags_dfh, list);
936     }
937     else
938     {
939         *flags_dfh = 0;
940     }
941
942     if (*file_version >= 15)
943     {
944         do_cpt_int_err(xd, "ED data sets", nED, list);
945     }
946     else
947     {
948         *nED = 0;
949     }
950 }
951
952 static int do_cpt_footer(XDR *xd, int file_version)
953 {
954     bool_t res = 0;
955     int    magic;
956
957     if (file_version >= 2)
958     {
959         magic = CPT_MAGIC2;
960         res   = xdr_int(xd, &magic);
961         if (res == 0)
962         {
963             cp_error();
964         }
965         if (magic != CPT_MAGIC2)
966         {
967             return -1;
968         }
969     }
970
971     return 0;
972 }
973
974 static int do_cpt_state(XDR *xd, int fflags, t_state *state,
975                         gmx_bool bReadRNG, FILE *list)
976 {
977     int    sflags;
978     int  **rng_p, **rngi_p;
979     int    i;
980     int    ret;
981     int    nnht, nnhtp;
982
983     ret = 0;
984
985     nnht  = state->nhchainlength*state->ngtc;
986     nnhtp = state->nhchainlength*state->nnhpres;
987
988     if (bReadRNG)
989     {
990         rng_p  = (int **)&state->ld_rng;
991         rngi_p = &state->ld_rngi;
992     }
993     else
994     {
995         /* Do not read the RNG data */
996         rng_p  = NULL;
997         rngi_p = NULL;
998     }
999     /* We want the MC_RNG the same across all the notes for now -- lambda MC is global */
1000
1001     sflags = state->flags;
1002     for (i = 0; (i < estNR && ret == 0); i++)
1003     {
1004         if (fflags & (1<<i))
1005         {
1006             switch (i)
1007             {
1008                 case estLAMBDA:  ret      = do_cpte_reals(xd, cptpEST, i, sflags, efptNR, &(state->lambda), list); break;
1009                 case estFEPSTATE: ret     = do_cpte_int (xd, cptpEST, i, sflags, &state->fep_state, list); break;
1010                 case estBOX:     ret      = do_cpte_matrix(xd, cptpEST, i, sflags, state->box, list); break;
1011                 case estBOX_REL: ret      = do_cpte_matrix(xd, cptpEST, i, sflags, state->box_rel, list); break;
1012                 case estBOXV:    ret      = do_cpte_matrix(xd, cptpEST, i, sflags, state->boxv, list); break;
1013                 case estPRES_PREV: ret    = do_cpte_matrix(xd, cptpEST, i, sflags, state->pres_prev, list); break;
1014                 case estSVIR_PREV:  ret   = do_cpte_matrix(xd, cptpEST, i, sflags, state->svir_prev, list); break;
1015                 case estFVIR_PREV:  ret   = do_cpte_matrix(xd, cptpEST, i, sflags, state->fvir_prev, list); break;
1016                 case estNH_XI:   ret      = do_cpte_doubles(xd, cptpEST, i, sflags, nnht, &state->nosehoover_xi, list); break;
1017                 case estNH_VXI:  ret      = do_cpte_doubles(xd, cptpEST, i, sflags, nnht, &state->nosehoover_vxi, list); break;
1018                 case estNHPRES_XI:   ret  = do_cpte_doubles(xd, cptpEST, i, sflags, nnhtp, &state->nhpres_xi, list); break;
1019                 case estNHPRES_VXI:  ret  = do_cpte_doubles(xd, cptpEST, i, sflags, nnhtp, &state->nhpres_vxi, list); break;
1020                 case estTC_INT:  ret      = do_cpte_doubles(xd, cptpEST, i, sflags, state->ngtc, &state->therm_integral, list); break;
1021                 case estVETA:    ret      = do_cpte_real(xd, cptpEST, i, sflags, &state->veta, list); break;
1022                 case estVOL0:    ret      = do_cpte_real(xd, cptpEST, i, sflags, &state->vol0, list); break;
1023                 case estX:       ret      = do_cpte_rvecs(xd, cptpEST, i, sflags, state->natoms, &state->x, list); break;
1024                 case estV:       ret      = do_cpte_rvecs(xd, cptpEST, i, sflags, state->natoms, &state->v, list); break;
1025                 case estSDX:     ret      = do_cpte_rvecs(xd, cptpEST, i, sflags, state->natoms, &state->sd_X, list); break;
1026                 case estLD_RNG:  ret      = do_cpte_ints(xd, cptpEST, i, sflags, state->nrng, rng_p, list); break;
1027                 case estLD_RNGI: ret      = do_cpte_ints(xd, cptpEST, i, sflags, state->nrngi, rngi_p, list); break;
1028                 case estMC_RNG:  ret      = do_cpte_ints(xd, cptpEST, i, sflags, state->nmcrng, (int **)&state->mc_rng, list); break;
1029                 case estMC_RNGI: ret      = do_cpte_ints(xd, cptpEST, i, sflags, 1, &state->mc_rngi, list); break;
1030                 case estDISRE_INITF:  ret = do_cpte_real (xd, cptpEST, i, sflags, &state->hist.disre_initf, list); break;
1031                 case estDISRE_RM3TAV: ret = do_cpte_reals(xd, cptpEST, i, sflags, state->hist.ndisrepairs, &state->hist.disre_rm3tav, list); break;
1032                 case estORIRE_INITF:  ret = do_cpte_real (xd, cptpEST, i, sflags, &state->hist.orire_initf, list); break;
1033                 case estORIRE_DTAV:   ret = do_cpte_reals(xd, cptpEST, i, sflags, state->hist.norire_Dtav, &state->hist.orire_Dtav, list); break;
1034                 default:
1035                     gmx_fatal(FARGS, "Unknown state entry %d\n"
1036                               "You are probably reading a new checkpoint file with old code", i);
1037             }
1038         }
1039     }
1040
1041     return ret;
1042 }
1043
1044 static int do_cpt_ekinstate(XDR *xd, int fflags, ekinstate_t *ekins,
1045                             FILE *list)
1046 {
1047     int  i;
1048     int  ret;
1049
1050     ret = 0;
1051
1052     for (i = 0; (i < eeksNR && ret == 0); i++)
1053     {
1054         if (fflags & (1<<i))
1055         {
1056             switch (i)
1057             {
1058
1059                 case eeksEKIN_N:     ret = do_cpte_int(xd, cptpEEKS, i, fflags, &ekins->ekin_n, list); break;
1060                 case eeksEKINH:     ret  = do_cpte_matrices(xd, cptpEEKS, i, fflags, ekins->ekin_n, &ekins->ekinh, list); break;
1061                 case eeksEKINF:      ret = do_cpte_matrices(xd, cptpEEKS, i, fflags, ekins->ekin_n, &ekins->ekinf, list); break;
1062                 case eeksEKINO:      ret = do_cpte_matrices(xd, cptpEEKS, i, fflags, ekins->ekin_n, &ekins->ekinh_old, list); break;
1063                 case eeksEKINTOTAL:  ret = do_cpte_matrix(xd, cptpEEKS, i, fflags, ekins->ekin_total, list); break;
1064                 case eeksEKINSCALEF: ret = do_cpte_doubles(xd, cptpEEKS, i, fflags, ekins->ekin_n, &ekins->ekinscalef_nhc, list); break;
1065                 case eeksVSCALE:     ret = do_cpte_doubles(xd, 1, cptpEEKS, fflags, ekins->ekin_n, &ekins->vscale_nhc, list); break;
1066                 case eeksEKINSCALEH: ret = do_cpte_doubles(xd, 1, cptpEEKS, fflags, ekins->ekin_n, &ekins->ekinscaleh_nhc, list); break;
1067                 case eeksDEKINDL:   ret  = do_cpte_real(xd, 1, cptpEEKS, fflags, &ekins->dekindl, list); break;
1068                 case eeksMVCOS:      ret = do_cpte_real(xd, 1, cptpEEKS, fflags, &ekins->mvcos, list); break;
1069                 default:
1070                     gmx_fatal(FARGS, "Unknown ekin data state entry %d\n"
1071                               "You are probably reading a new checkpoint file with old code", i);
1072             }
1073         }
1074     }
1075
1076     return ret;
1077 }
1078
1079
1080 static int do_cpt_enerhist(XDR *xd, gmx_bool bRead,
1081                            int fflags, energyhistory_t *enerhist,
1082                            FILE *list)
1083 {
1084     int  i;
1085     int  j;
1086     int  ret;
1087
1088     ret = 0;
1089
1090     if (bRead)
1091     {
1092         enerhist->nsteps     = 0;
1093         enerhist->nsum       = 0;
1094         enerhist->nsteps_sim = 0;
1095         enerhist->nsum_sim   = 0;
1096         enerhist->dht        = NULL;
1097
1098         if (fflags & (1<< eenhENERGY_DELTA_H_NN) )
1099         {
1100             snew(enerhist->dht, 1);
1101             enerhist->dht->ndh              = NULL;
1102             enerhist->dht->dh               = NULL;
1103             enerhist->dht->start_lambda_set = FALSE;
1104         }
1105     }
1106
1107     for (i = 0; (i < eenhNR && ret == 0); i++)
1108     {
1109         if (fflags & (1<<i))
1110         {
1111             switch (i)
1112             {
1113                 case eenhENERGY_N:     ret = do_cpte_int(xd, cptpEENH, i, fflags, &enerhist->nener, list); break;
1114                 case eenhENERGY_AVER:  ret = do_cpte_doubles(xd, cptpEENH, i, fflags, enerhist->nener, &enerhist->ener_ave, list); break;
1115                 case eenhENERGY_SUM:   ret = do_cpte_doubles(xd, cptpEENH, i, fflags, enerhist->nener, &enerhist->ener_sum, list); break;
1116                 case eenhENERGY_NSUM:  do_cpt_step_err(xd, eenh_names[i], &enerhist->nsum, list); break;
1117                 case eenhENERGY_SUM_SIM: ret = do_cpte_doubles(xd, cptpEENH, i, fflags, enerhist->nener, &enerhist->ener_sum_sim, list); break;
1118                 case eenhENERGY_NSUM_SIM:   do_cpt_step_err(xd, eenh_names[i], &enerhist->nsum_sim, list); break;
1119                 case eenhENERGY_NSTEPS:     do_cpt_step_err(xd, eenh_names[i], &enerhist->nsteps, list); break;
1120                 case eenhENERGY_NSTEPS_SIM: do_cpt_step_err(xd, eenh_names[i], &enerhist->nsteps_sim, list); break;
1121                 case eenhENERGY_DELTA_H_NN: do_cpt_int_err(xd, eenh_names[i], &(enerhist->dht->nndh), list);
1122                     if (bRead) /* now allocate memory for it */
1123                     {
1124                         snew(enerhist->dht->dh, enerhist->dht->nndh);
1125                         snew(enerhist->dht->ndh, enerhist->dht->nndh);
1126                         for (j = 0; j < enerhist->dht->nndh; j++)
1127                         {
1128                             enerhist->dht->ndh[j] = 0;
1129                             enerhist->dht->dh[j]  = NULL;
1130                         }
1131                     }
1132                     break;
1133                 case eenhENERGY_DELTA_H_LIST:
1134                     for (j = 0; j < enerhist->dht->nndh; j++)
1135                     {
1136                         ret = do_cpte_n_reals(xd, cptpEENH, i, fflags, &enerhist->dht->ndh[j], &(enerhist->dht->dh[j]), list);
1137                     }
1138                     break;
1139                 case eenhENERGY_DELTA_H_STARTTIME:
1140                     ret = do_cpte_double(xd, cptpEENH, i, fflags, &(enerhist->dht->start_time), list); break;
1141                 case eenhENERGY_DELTA_H_STARTLAMBDA:
1142                     ret = do_cpte_double(xd, cptpEENH, i, fflags, &(enerhist->dht->start_lambda), list); break;
1143                 default:
1144                     gmx_fatal(FARGS, "Unknown energy history entry %d\n"
1145                               "You are probably reading a new checkpoint file with old code", i);
1146             }
1147         }
1148     }
1149
1150     if ((fflags & (1<<eenhENERGY_SUM)) && !(fflags & (1<<eenhENERGY_SUM_SIM)))
1151     {
1152         /* Assume we have an old file format and copy sum to sum_sim */
1153         srenew(enerhist->ener_sum_sim, enerhist->nener);
1154         for (i = 0; i < enerhist->nener; i++)
1155         {
1156             enerhist->ener_sum_sim[i] = enerhist->ener_sum[i];
1157         }
1158         fflags |= (1<<eenhENERGY_SUM_SIM);
1159     }
1160
1161     if ( (fflags & (1<<eenhENERGY_NSUM)) &&
1162          !(fflags & (1<<eenhENERGY_NSTEPS)))
1163     {
1164         /* Assume we have an old file format and copy nsum to nsteps */
1165         enerhist->nsteps = enerhist->nsum;
1166         fflags          |= (1<<eenhENERGY_NSTEPS);
1167     }
1168     if ( (fflags & (1<<eenhENERGY_NSUM_SIM)) &&
1169          !(fflags & (1<<eenhENERGY_NSTEPS_SIM)))
1170     {
1171         /* Assume we have an old file format and copy nsum to nsteps */
1172         enerhist->nsteps_sim = enerhist->nsum_sim;
1173         fflags              |= (1<<eenhENERGY_NSTEPS_SIM);
1174     }
1175
1176     return ret;
1177 }
1178
1179 static int do_cpt_df_hist(XDR *xd, int fflags, df_history_t *dfhist, FILE *list)
1180 {
1181     int  i, nlambda;
1182     int  ret;
1183
1184     nlambda = dfhist->nlambda;
1185     ret     = 0;
1186
1187     for (i = 0; (i < edfhNR && ret == 0); i++)
1188     {
1189         if (fflags & (1<<i))
1190         {
1191             switch (i)
1192             {
1193                 case edfhBEQUIL:       ret = do_cpte_int(xd, cptpEDFH, i, fflags, &dfhist->bEquil, list); break;
1194                 case edfhNATLAMBDA:    ret = do_cpte_ints(xd, cptpEDFH, i, fflags, nlambda, &dfhist->n_at_lam, list); break;
1195                 case edfhWLHISTO:      ret = do_cpte_reals(xd, cptpEDFH, i, fflags, nlambda, &dfhist->wl_histo, list); break;
1196                 case edfhWLDELTA:      ret = do_cpte_real(xd, cptpEDFH, i, fflags, &dfhist->wl_delta, list); break;
1197                 case edfhSUMWEIGHTS:   ret = do_cpte_reals(xd, cptpEDFH, i, fflags, nlambda, &dfhist->sum_weights, list); break;
1198                 case edfhSUMDG:        ret = do_cpte_reals(xd, cptpEDFH, i, fflags, nlambda, &dfhist->sum_dg, list); break;
1199                 case edfhSUMMINVAR:    ret = do_cpte_reals(xd, cptpEDFH, i, fflags, nlambda, &dfhist->sum_minvar, list); break;
1200                 case edfhSUMVAR:       ret = do_cpte_reals(xd, cptpEDFH, i, fflags, nlambda, &dfhist->sum_variance, list); break;
1201                 case edfhACCUMP:       ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->accum_p, list); break;
1202                 case edfhACCUMM:       ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->accum_m, list); break;
1203                 case edfhACCUMP2:      ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->accum_p2, list); break;
1204                 case edfhACCUMM2:      ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->accum_m2, list); break;
1205                 case edfhTIJ:          ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->Tij, list); break;
1206                 case edfhTIJEMP:       ret = do_cpte_nmatrix(xd, cptpEDFH, i, fflags, nlambda, dfhist->Tij_empirical, list); break;
1207
1208                 default:
1209                     gmx_fatal(FARGS, "Unknown df history entry %d\n"
1210                               "You are probably reading a new checkpoint file with old code", i);
1211             }
1212         }
1213     }
1214
1215     return ret;
1216 }
1217
1218
1219 /* This function stores the last whole configuration of the reference and
1220  * average structure in the .cpt file
1221  */
1222 static int do_cpt_EDstate(XDR *xd, gmx_bool bRead,
1223                           edsamstate_t *EDstate, FILE *list)
1224 {
1225     int  i, j;
1226     int  ret = 0;
1227     char buf[STRLEN];
1228
1229
1230     EDstate->bFromCpt = bRead;
1231
1232     if (EDstate->nED <= 0)
1233     {
1234         return ret;
1235     }
1236
1237     /* When reading, init_edsam has not been called yet,
1238      * so we have to allocate memory first. */
1239     if (bRead)
1240     {
1241         snew(EDstate->nref, EDstate->nED);
1242         snew(EDstate->old_sref, EDstate->nED);
1243         snew(EDstate->nav, EDstate->nED);
1244         snew(EDstate->old_sav, EDstate->nED);
1245     }
1246
1247     /* Read/write the last whole conformation of SREF and SAV for each ED dataset (usually only one) */
1248     for (i = 0; i < EDstate->nED; i++)
1249     {
1250         /* Reference structure SREF */
1251         sprintf(buf, "ED%d # of atoms in reference structure", i+1);
1252         do_cpt_int_err(xd, buf, &EDstate->nref[i], list);
1253         sprintf(buf, "ED%d x_ref", i+1);
1254         if (bRead)
1255         {
1256             snew(EDstate->old_sref[i], EDstate->nref[i]);
1257             do_cpt_n_rvecs_err(xd, buf, EDstate->nref[i], EDstate->old_sref[i], list);
1258         }
1259         else
1260         {
1261             do_cpt_n_rvecs_err(xd, buf, EDstate->nref[i], EDstate->old_sref_p[i], list);
1262         }
1263
1264         /* Average structure SAV */
1265         sprintf(buf, "ED%d # of atoms in average structure", i+1);
1266         do_cpt_int_err(xd, buf, &EDstate->nav[i], list);
1267         sprintf(buf, "ED%d x_av", i+1);
1268         if (bRead)
1269         {
1270             snew(EDstate->old_sav[i], EDstate->nav[i]);
1271             do_cpt_n_rvecs_err(xd, buf, EDstate->nav[i], EDstate->old_sav[i], list);
1272         }
1273         else
1274         {
1275             do_cpt_n_rvecs_err(xd, buf, EDstate->nav[i], EDstate->old_sav_p[i], list);
1276         }
1277     }
1278
1279     return ret;
1280 }
1281
1282
1283 static int do_cpt_files(XDR *xd, gmx_bool bRead,
1284                         gmx_file_position_t **p_outputfiles, int *nfiles,
1285                         FILE *list, int file_version)
1286 {
1287     int                  i, j;
1288     gmx_off_t            offset;
1289     gmx_off_t            mask = 0xFFFFFFFFL;
1290     int                  offset_high, offset_low;
1291     char                *buf;
1292     gmx_file_position_t *outputfiles;
1293
1294     if (do_cpt_int(xd, "number of output files", nfiles, list) != 0)
1295     {
1296         return -1;
1297     }
1298
1299     if (bRead)
1300     {
1301         snew(*p_outputfiles, *nfiles);
1302     }
1303
1304     outputfiles = *p_outputfiles;
1305
1306     for (i = 0; i < *nfiles; i++)
1307     {
1308         /* 64-bit XDR numbers are not portable, so it is stored as separate high/low fractions */
1309         if (bRead)
1310         {
1311             do_cpt_string_err(xd, bRead, "output filename", &buf, list);
1312             strncpy(outputfiles[i].filename, buf, CPTSTRLEN-1);
1313             if (list == NULL)
1314             {
1315                 sfree(buf);
1316             }
1317
1318             if (do_cpt_int(xd, "file_offset_high", &offset_high, list) != 0)
1319             {
1320                 return -1;
1321             }
1322             if (do_cpt_int(xd, "file_offset_low", &offset_low, list) != 0)
1323             {
1324                 return -1;
1325             }
1326 #if (SIZEOF_GMX_OFF_T > 4)
1327             outputfiles[i].offset = ( ((gmx_off_t) offset_high) << 32 ) | ( (gmx_off_t) offset_low & mask );
1328 #else
1329             outputfiles[i].offset = offset_low;
1330 #endif
1331         }
1332         else
1333         {
1334             buf = outputfiles[i].filename;
1335             do_cpt_string_err(xd, bRead, "output filename", &buf, list);
1336             /* writing */
1337             offset      = outputfiles[i].offset;
1338             if (offset == -1)
1339             {
1340                 offset_low  = -1;
1341                 offset_high = -1;
1342             }
1343             else
1344             {
1345 #if (SIZEOF_GMX_OFF_T > 4)
1346                 offset_low  = (int) (offset & mask);
1347                 offset_high = (int) ((offset >> 32) & mask);
1348 #else
1349                 offset_low  = offset;
1350                 offset_high = 0;
1351 #endif
1352             }
1353             if (do_cpt_int(xd, "file_offset_high", &offset_high, list) != 0)
1354             {
1355                 return -1;
1356             }
1357             if (do_cpt_int(xd, "file_offset_low", &offset_low, list) != 0)
1358             {
1359                 return -1;
1360             }
1361         }
1362         if (file_version >= 8)
1363         {
1364             if (do_cpt_int(xd, "file_checksum_size", &(outputfiles[i].chksum_size),
1365                            list) != 0)
1366             {
1367                 return -1;
1368             }
1369             if (do_cpt_u_chars(xd, "file_checksum", 16, outputfiles[i].chksum, list) != 0)
1370             {
1371                 return -1;
1372             }
1373         }
1374         else
1375         {
1376             outputfiles[i].chksum_size = -1;
1377         }
1378     }
1379     return 0;
1380 }
1381
1382
1383 void write_checkpoint(const char *fn, gmx_bool bNumberAndKeep,
1384                       FILE *fplog, t_commrec *cr,
1385                       int eIntegrator, int simulation_part,
1386                       gmx_bool bExpanded, int elamstats,
1387                       gmx_large_int_t step, double t, t_state *state)
1388 {
1389     t_fileio            *fp;
1390     int                  file_version;
1391     char                *version;
1392     char                *btime;
1393     char                *buser;
1394     char                *bhost;
1395     int                  double_prec;
1396     char                *fprog;
1397     char                *fntemp; /* the temporary checkpoint file name */
1398     time_t               now;
1399     char                 timebuf[STRLEN];
1400     int                  nppnodes, npmenodes, flag_64bit;
1401     char                 buf[1024], suffix[5+STEPSTRSIZE], sbuf[STEPSTRSIZE];
1402     gmx_file_position_t *outputfiles;
1403     int                  noutputfiles;
1404     char                *ftime;
1405     int                  flags_eks, flags_enh, flags_dfh, i;
1406     t_fileio            *ret;
1407
1408     if (PAR(cr))
1409     {
1410         if (DOMAINDECOMP(cr))
1411         {
1412             nppnodes  = cr->dd->nnodes;
1413             npmenodes = cr->npmenodes;
1414         }
1415         else
1416         {
1417             nppnodes  = cr->nnodes;
1418             npmenodes = 0;
1419         }
1420     }
1421     else
1422     {
1423         nppnodes  = 1;
1424         npmenodes = 0;
1425     }
1426
1427     /* make the new temporary filename */
1428     snew(fntemp, strlen(fn)+5+STEPSTRSIZE);
1429     strcpy(fntemp, fn);
1430     fntemp[strlen(fn) - strlen(ftp2ext(fn2ftp(fn))) - 1] = '\0';
1431     sprintf(suffix, "_%s%s", "step", gmx_step_str(step, sbuf));
1432     strcat(fntemp, suffix);
1433     strcat(fntemp, fn+strlen(fn) - strlen(ftp2ext(fn2ftp(fn))) - 1);
1434
1435     time(&now);
1436     gmx_ctime_r(&now, timebuf, STRLEN);
1437
1438     if (fplog)
1439     {
1440         fprintf(fplog, "Writing checkpoint, step %s at %s\n\n",
1441                 gmx_step_str(step, buf), timebuf);
1442     }
1443
1444     /* Get offsets for open files */
1445     gmx_fio_get_output_file_positions(&outputfiles, &noutputfiles);
1446
1447     fp = gmx_fio_open(fntemp, "w");
1448
1449     if (state->ekinstate.bUpToDate)
1450     {
1451         flags_eks =
1452             ((1<<eeksEKIN_N) | (1<<eeksEKINH) | (1<<eeksEKINF) |
1453              (1<<eeksEKINO) | (1<<eeksEKINSCALEF) | (1<<eeksEKINSCALEH) |
1454              (1<<eeksVSCALE) | (1<<eeksDEKINDL) | (1<<eeksMVCOS));
1455     }
1456     else
1457     {
1458         flags_eks = 0;
1459     }
1460
1461     flags_enh = 0;
1462     if (state->enerhist.nsum > 0 || state->enerhist.nsum_sim > 0)
1463     {
1464         flags_enh |= (1<<eenhENERGY_N);
1465         if (state->enerhist.nsum > 0)
1466         {
1467             flags_enh |= ((1<<eenhENERGY_AVER) | (1<<eenhENERGY_SUM) |
1468                           (1<<eenhENERGY_NSTEPS) | (1<<eenhENERGY_NSUM));
1469         }
1470         if (state->enerhist.nsum_sim > 0)
1471         {
1472             flags_enh |= ((1<<eenhENERGY_SUM_SIM) | (1<<eenhENERGY_NSTEPS_SIM) |
1473                           (1<<eenhENERGY_NSUM_SIM));
1474         }
1475         if (state->enerhist.dht)
1476         {
1477             flags_enh |= ( (1<< eenhENERGY_DELTA_H_NN) |
1478                            (1<< eenhENERGY_DELTA_H_LIST) |
1479                            (1<< eenhENERGY_DELTA_H_STARTTIME) |
1480                            (1<< eenhENERGY_DELTA_H_STARTLAMBDA) );
1481         }
1482     }
1483
1484     if (bExpanded)
1485     {
1486         flags_dfh = ((1<<edfhBEQUIL) | (1<<edfhNATLAMBDA) | (1<<edfhSUMWEIGHTS) |  (1<<edfhSUMDG)  |
1487                      (1<<edfhTIJ) | (1<<edfhTIJEMP));
1488         if (EWL(elamstats))
1489         {
1490             flags_dfh |= ((1<<edfhWLDELTA) | (1<<edfhWLHISTO));
1491         }
1492         if ((elamstats == elamstatsMINVAR) || (elamstats == elamstatsBARKER) || (elamstats == elamstatsMETROPOLIS))
1493         {
1494             flags_dfh |= ((1<<edfhACCUMP) | (1<<edfhACCUMM) | (1<<edfhACCUMP2) | (1<<edfhACCUMM2)
1495                           | (1<<edfhSUMMINVAR) | (1<<edfhSUMVAR));
1496         }
1497     }
1498     else
1499     {
1500         flags_dfh = 0;
1501     }
1502
1503     /* We can check many more things now (CPU, acceleration, etc), but
1504      * it is highly unlikely to have two separate builds with exactly
1505      * the same version, user, time, and build host!
1506      */
1507
1508     version = gmx_strdup(VERSION);
1509     btime   = gmx_strdup(BUILD_TIME);
1510     buser   = gmx_strdup(BUILD_USER);
1511     bhost   = gmx_strdup(BUILD_HOST);
1512
1513     double_prec = GMX_CPT_BUILD_DP;
1514     fprog       = gmx_strdup(Program());
1515
1516     ftime   = &(timebuf[0]);
1517
1518     do_cpt_header(gmx_fio_getxdr(fp), FALSE, &file_version,
1519                   &version, &btime, &buser, &bhost, &double_prec, &fprog, &ftime,
1520                   &eIntegrator, &simulation_part, &step, &t, &nppnodes,
1521                   DOMAINDECOMP(cr) ? cr->dd->nc : NULL, &npmenodes,
1522                   &state->natoms, &state->ngtc, &state->nnhpres,
1523                   &state->nhchainlength, &(state->dfhist.nlambda), &state->flags, &flags_eks, &flags_enh, &flags_dfh,
1524                   &state->edsamstate.nED,
1525                   NULL);
1526
1527     sfree(version);
1528     sfree(btime);
1529     sfree(buser);
1530     sfree(bhost);
1531     sfree(fprog);
1532
1533     if ((do_cpt_state(gmx_fio_getxdr(fp), state->flags, state, TRUE, NULL) < 0)        ||
1534         (do_cpt_ekinstate(gmx_fio_getxdr(fp), flags_eks, &state->ekinstate, NULL) < 0) ||
1535         (do_cpt_enerhist(gmx_fio_getxdr(fp), FALSE, flags_enh, &state->enerhist, NULL) < 0)  ||
1536         (do_cpt_df_hist(gmx_fio_getxdr(fp), flags_dfh, &state->dfhist, NULL) < 0)  ||
1537         (do_cpt_EDstate(gmx_fio_getxdr(fp), FALSE, &state->edsamstate, NULL) < 0)      ||
1538         (do_cpt_files(gmx_fio_getxdr(fp), FALSE, &outputfiles, &noutputfiles, NULL,
1539                       file_version) < 0))
1540     {
1541         gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
1542     }
1543
1544     do_cpt_footer(gmx_fio_getxdr(fp), file_version);
1545
1546     /* we really, REALLY, want to make sure to physically write the checkpoint,
1547        and all the files it depends on, out to disk. Because we've
1548        opened the checkpoint with gmx_fio_open(), it's in our list
1549        of open files.  */
1550     ret = gmx_fio_all_output_fsync();
1551
1552     if (ret)
1553     {
1554         char buf[STRLEN];
1555         sprintf(buf,
1556                 "Cannot fsync '%s'; maybe you are out of disk space?",
1557                 gmx_fio_getname(ret));
1558
1559         if (getenv(GMX_IGNORE_FSYNC_FAILURE_ENV) == NULL)
1560         {
1561             gmx_file(buf);
1562         }
1563         else
1564         {
1565             gmx_warning(buf);
1566         }
1567     }
1568
1569     if (gmx_fio_close(fp) != 0)
1570     {
1571         gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
1572     }
1573
1574     /* we don't move the checkpoint if the user specified they didn't want it,
1575        or if the fsyncs failed */
1576     if (!bNumberAndKeep && !ret)
1577     {
1578         if (gmx_fexist(fn))
1579         {
1580             /* Rename the previous checkpoint file */
1581             strcpy(buf, fn);
1582             buf[strlen(fn) - strlen(ftp2ext(fn2ftp(fn))) - 1] = '\0';
1583             strcat(buf, "_prev");
1584             strcat(buf, fn+strlen(fn) - strlen(ftp2ext(fn2ftp(fn))) - 1);
1585 #ifndef GMX_FAHCORE
1586             /* we copy here so that if something goes wrong between now and
1587              * the rename below, there's always a state.cpt.
1588              * If renames are atomic (such as in POSIX systems),
1589              * this copying should be unneccesary.
1590              */
1591             gmx_file_copy(fn, buf, FALSE);
1592             /* We don't really care if this fails:
1593              * there's already a new checkpoint.
1594              */
1595 #else
1596             gmx_file_rename(fn, buf);
1597 #endif
1598         }
1599         if (gmx_file_rename(fntemp, fn) != 0)
1600         {
1601             gmx_file("Cannot rename checkpoint file; maybe you are out of disk space?");
1602         }
1603     }
1604
1605     sfree(outputfiles);
1606     sfree(fntemp);
1607
1608 #ifdef GMX_FAHCORE
1609     /*code for alternate checkpointing scheme.  moved from top of loop over
1610        steps */
1611     fcRequestCheckPoint();
1612     if (fcCheckPointParallel( cr->nodeid, NULL, 0) == 0)
1613     {
1614         gmx_fatal( 3, __FILE__, __LINE__, "Checkpoint error on step %d\n", step );
1615     }
1616 #endif /* end GMX_FAHCORE block */
1617 }
1618
1619 static void print_flag_mismatch(FILE *fplog, int sflags, int fflags)
1620 {
1621     int i;
1622
1623     fprintf(fplog, "\nState entry mismatch between the simulation and the checkpoint file\n");
1624     fprintf(fplog, "Entries which are not present in the checkpoint file will not be updated\n");
1625     fprintf(fplog, "  %24s    %11s    %11s\n", "", "simulation", "checkpoint");
1626     for (i = 0; i < estNR; i++)
1627     {
1628         if ((sflags & (1<<i)) || (fflags & (1<<i)))
1629         {
1630             fprintf(fplog, "  %24s    %11s    %11s\n",
1631                     est_names[i],
1632                     (sflags & (1<<i)) ? "  present  " : "not present",
1633                     (fflags & (1<<i)) ? "  present  " : "not present");
1634         }
1635     }
1636 }
1637
1638 static void check_int(FILE *fplog, const char *type, int p, int f, gmx_bool *mm)
1639 {
1640     FILE *fp = fplog ? fplog : stderr;
1641
1642     if (p != f)
1643     {
1644         fprintf(fp, "  %s mismatch,\n", type);
1645         fprintf(fp, "    current program: %d\n", p);
1646         fprintf(fp, "    checkpoint file: %d\n", f);
1647         fprintf(fp, "\n");
1648         *mm = TRUE;
1649     }
1650 }
1651
1652 static void check_string(FILE *fplog, const char *type, const char *p,
1653                          const char *f, gmx_bool *mm)
1654 {
1655     FILE *fp = fplog ? fplog : stderr;
1656
1657     if (strcmp(p, f) != 0)
1658     {
1659         fprintf(fp, "  %s mismatch,\n", type);
1660         fprintf(fp, "    current program: %s\n", p);
1661         fprintf(fp, "    checkpoint file: %s\n", f);
1662         fprintf(fp, "\n");
1663         *mm = TRUE;
1664     }
1665 }
1666
1667 static void check_match(FILE *fplog,
1668                         char *version,
1669                         char *btime, char *buser, char *bhost, int double_prec,
1670                         char *fprog,
1671                         t_commrec *cr, gmx_bool bPartDecomp, int npp_f, int npme_f,
1672                         ivec dd_nc, ivec dd_nc_f)
1673 {
1674     int      npp;
1675     gmx_bool mm;
1676
1677     mm = FALSE;
1678
1679     check_string(fplog, "Version", VERSION, version, &mm);
1680     check_string(fplog, "Build time", BUILD_TIME, btime, &mm);
1681     check_string(fplog, "Build user", BUILD_USER, buser, &mm);
1682     check_string(fplog, "Build host", BUILD_HOST, bhost, &mm);
1683     check_int   (fplog, "Double prec.", GMX_CPT_BUILD_DP, double_prec, &mm);
1684     check_string(fplog, "Program name", Program(), fprog, &mm);
1685
1686     check_int   (fplog, "#nodes", cr->nnodes, npp_f+npme_f, &mm);
1687     if (bPartDecomp)
1688     {
1689         dd_nc[XX] = 1;
1690         dd_nc[YY] = 1;
1691         dd_nc[ZZ] = 1;
1692     }
1693     if (cr->nnodes > 1)
1694     {
1695         check_int (fplog, "#PME-nodes", cr->npmenodes, npme_f, &mm);
1696
1697         npp = cr->nnodes;
1698         if (cr->npmenodes >= 0)
1699         {
1700             npp -= cr->npmenodes;
1701         }
1702         if (npp == npp_f)
1703         {
1704             check_int (fplog, "#DD-cells[x]", dd_nc[XX], dd_nc_f[XX], &mm);
1705             check_int (fplog, "#DD-cells[y]", dd_nc[YY], dd_nc_f[YY], &mm);
1706             check_int (fplog, "#DD-cells[z]", dd_nc[ZZ], dd_nc_f[ZZ], &mm);
1707         }
1708     }
1709
1710     if (mm)
1711     {
1712         fprintf(stderr,
1713                 "Gromacs binary or parallel settings not identical to previous run.\n"
1714                 "Continuation is exact, but is not guaranteed to be binary identical%s.\n\n",
1715                 fplog ? ",\n see the log file for details" : "");
1716
1717         if (fplog)
1718         {
1719             fprintf(fplog,
1720                     "Gromacs binary or parallel settings not identical to previous run.\n"
1721                     "Continuation is exact, but is not guaranteed to be binary identical.\n\n");
1722         }
1723     }
1724 }
1725
1726 static void read_checkpoint(const char *fn, FILE **pfplog,
1727                             t_commrec *cr, gmx_bool bPartDecomp, ivec dd_nc,
1728                             int eIntegrator, int *init_fep_state, gmx_large_int_t *step, double *t,
1729                             t_state *state, gmx_bool *bReadRNG, gmx_bool *bReadEkin,
1730                             int *simulation_part,
1731                             gmx_bool bAppendOutputFiles, gmx_bool bForceAppend)
1732 {
1733     t_fileio            *fp;
1734     int                  i, j, rc;
1735     int                  file_version;
1736     char                *version, *btime, *buser, *bhost, *fprog, *ftime;
1737     int                  double_prec;
1738     char                 filename[STRLEN], buf[STEPSTRSIZE];
1739     int                  nppnodes, eIntegrator_f, nppnodes_f, npmenodes_f;
1740     ivec                 dd_nc_f;
1741     int                  natoms, ngtc, nnhpres, nhchainlength, nlambda, fflags, flags_eks, flags_enh, flags_dfh;
1742     int                  d;
1743     int                  ret;
1744     gmx_file_position_t *outputfiles;
1745     int                  nfiles;
1746     t_fileio            *chksum_file;
1747     FILE               * fplog = *pfplog;
1748     unsigned char        digest[16];
1749 #ifndef GMX_NATIVE_WINDOWS
1750     struct flock         fl; /* don't initialize here: the struct order is OS
1751                                 dependent! */
1752 #endif
1753
1754     const char *int_warn =
1755         "WARNING: The checkpoint file was generated with integrator %s,\n"
1756         "         while the simulation uses integrator %s\n\n";
1757     const char *sd_note =
1758         "NOTE: The checkpoint file was for %d nodes doing SD or BD,\n"
1759         "      while the simulation uses %d SD or BD nodes,\n"
1760         "      continuation will be exact, except for the random state\n\n";
1761
1762 #ifndef GMX_NATIVE_WINDOWS
1763     fl.l_type   = F_WRLCK;
1764     fl.l_whence = SEEK_SET;
1765     fl.l_start  = 0;
1766     fl.l_len    = 0;
1767     fl.l_pid    = 0;
1768 #endif
1769
1770     if (PARTDECOMP(cr))
1771     {
1772         gmx_fatal(FARGS,
1773                   "read_checkpoint not (yet) supported with particle decomposition");
1774     }
1775
1776     fp = gmx_fio_open(fn, "r");
1777     do_cpt_header(gmx_fio_getxdr(fp), TRUE, &file_version,
1778                   &version, &btime, &buser, &bhost, &double_prec, &fprog, &ftime,
1779                   &eIntegrator_f, simulation_part, step, t,
1780                   &nppnodes_f, dd_nc_f, &npmenodes_f,
1781                   &natoms, &ngtc, &nnhpres, &nhchainlength, &nlambda,
1782                   &fflags, &flags_eks, &flags_enh, &flags_dfh,
1783                   &state->edsamstate.nED, NULL);
1784
1785     if (bAppendOutputFiles &&
1786         file_version >= 13 && double_prec != GMX_CPT_BUILD_DP)
1787     {
1788         gmx_fatal(FARGS, "Output file appending requested, but the code and checkpoint file precision (single/double) don't match");
1789     }
1790
1791     if (cr == NULL || MASTER(cr))
1792     {
1793         fprintf(stderr, "\nReading checkpoint file %s generated: %s\n\n",
1794                 fn, ftime);
1795     }
1796
1797     /* This will not be written if we do appending, since fplog is still NULL then */
1798     if (fplog)
1799     {
1800         fprintf(fplog, "\n");
1801         fprintf(fplog, "Reading checkpoint file %s\n", fn);
1802         fprintf(fplog, "  file generated by:     %s\n", fprog);
1803         fprintf(fplog, "  file generated at:     %s\n", ftime);
1804         fprintf(fplog, "  GROMACS build time:    %s\n", btime);
1805         fprintf(fplog, "  GROMACS build user:    %s\n", buser);
1806         fprintf(fplog, "  GROMACS build host:    %s\n", bhost);
1807         fprintf(fplog, "  GROMACS double prec.:  %d\n", double_prec);
1808         fprintf(fplog, "  simulation part #:     %d\n", *simulation_part);
1809         fprintf(fplog, "  step:                  %s\n", gmx_step_str(*step, buf));
1810         fprintf(fplog, "  time:                  %f\n", *t);
1811         fprintf(fplog, "\n");
1812     }
1813
1814     if (natoms != state->natoms)
1815     {
1816         gmx_fatal(FARGS, "Checkpoint file is for a system of %d atoms, while the current system consists of %d atoms", natoms, state->natoms);
1817     }
1818     if (ngtc != state->ngtc)
1819     {
1820         gmx_fatal(FARGS, "Checkpoint file is for a system of %d T-coupling groups, while the current system consists of %d T-coupling groups", ngtc, state->ngtc);
1821     }
1822     if (nnhpres != state->nnhpres)
1823     {
1824         gmx_fatal(FARGS, "Checkpoint file is for a system of %d NH-pressure-coupling variables, while the current system consists of %d NH-pressure-coupling variables", nnhpres, state->nnhpres);
1825     }
1826
1827     if (nlambda != state->dfhist.nlambda)
1828     {
1829         gmx_fatal(FARGS, "Checkpoint file is for a system with %d lambda states, while the current system consists of %d lambda states", nlambda, state->dfhist.nlambda);
1830     }
1831
1832     init_gtc_state(state, state->ngtc, state->nnhpres, nhchainlength); /* need to keep this here to keep the tpr format working */
1833     /* write over whatever was read; we use the number of Nose-Hoover chains from the checkpoint */
1834
1835     if (eIntegrator_f != eIntegrator)
1836     {
1837         if (MASTER(cr))
1838         {
1839             fprintf(stderr, int_warn, EI(eIntegrator_f), EI(eIntegrator));
1840         }
1841         if (bAppendOutputFiles)
1842         {
1843             gmx_fatal(FARGS,
1844                       "Output file appending requested, but input/checkpoint integrators do not match.\n"
1845                       "Stopping the run to prevent you from ruining all your data...\n"
1846                       "If you _really_ know what you are doing, try with the -noappend option.\n");
1847         }
1848         if (fplog)
1849         {
1850             fprintf(fplog, int_warn, EI(eIntegrator_f), EI(eIntegrator));
1851         }
1852     }
1853
1854     if (!PAR(cr))
1855     {
1856         nppnodes      = 1;
1857         cr->npmenodes = 0;
1858     }
1859     else if (bPartDecomp)
1860     {
1861         nppnodes      = cr->nnodes;
1862         cr->npmenodes = 0;
1863     }
1864     else if (cr->nnodes == nppnodes_f + npmenodes_f)
1865     {
1866         if (cr->npmenodes < 0)
1867         {
1868             cr->npmenodes = npmenodes_f;
1869         }
1870         nppnodes = cr->nnodes - cr->npmenodes;
1871         if (nppnodes == nppnodes_f)
1872         {
1873             for (d = 0; d < DIM; d++)
1874             {
1875                 if (dd_nc[d] == 0)
1876                 {
1877                     dd_nc[d] = dd_nc_f[d];
1878                 }
1879             }
1880         }
1881     }
1882     else
1883     {
1884         /* The number of PP nodes has not been set yet */
1885         nppnodes = -1;
1886     }
1887
1888     if ((EI_SD(eIntegrator) || eIntegrator == eiBD) && nppnodes > 0)
1889     {
1890         /* Correct the RNG state size for the number of PP nodes.
1891          * Such assignments should all be moved to one central function.
1892          */
1893         state->nrng  = nppnodes*gmx_rng_n();
1894         state->nrngi = nppnodes;
1895     }
1896
1897     *bReadRNG = TRUE;
1898     if (fflags != state->flags)
1899     {
1900
1901         if (MASTER(cr))
1902         {
1903             if (bAppendOutputFiles)
1904             {
1905                 gmx_fatal(FARGS,
1906                           "Output file appending requested, but input and checkpoint states are not identical.\n"
1907                           "Stopping the run to prevent you from ruining all your data...\n"
1908                           "You can try with the -noappend option, and get more info in the log file.\n");
1909             }
1910
1911             if (getenv("GMX_ALLOW_CPT_MISMATCH") == NULL)
1912             {
1913                 gmx_fatal(FARGS, "You seem to have switched ensemble, integrator, T and/or P-coupling algorithm between the cpt and tpr file. The recommended way of doing this is passing the cpt file to grompp (with option -t) instead of to mdrun. If you know what you are doing, you can override this error by setting the env.var. GMX_ALLOW_CPT_MISMATCH");
1914             }
1915             else
1916             {
1917                 fprintf(stderr,
1918                         "WARNING: The checkpoint state entries do not match the simulation,\n"
1919                         "         see the log file for details\n\n");
1920             }
1921         }
1922
1923         if (fplog)
1924         {
1925             print_flag_mismatch(fplog, state->flags, fflags);
1926         }
1927     }
1928     else
1929     {
1930         if ((EI_SD(eIntegrator) || eIntegrator == eiBD) &&
1931             nppnodes != nppnodes_f)
1932         {
1933             *bReadRNG = FALSE;
1934             if (MASTER(cr))
1935             {
1936                 fprintf(stderr, sd_note, nppnodes_f, nppnodes);
1937             }
1938             if (fplog)
1939             {
1940                 fprintf(fplog, sd_note, nppnodes_f, nppnodes);
1941             }
1942         }
1943         if (MASTER(cr))
1944         {
1945             check_match(fplog, version, btime, buser, bhost, double_prec, fprog,
1946                         cr, bPartDecomp, nppnodes_f, npmenodes_f, dd_nc, dd_nc_f);
1947         }
1948     }
1949     ret             = do_cpt_state(gmx_fio_getxdr(fp), fflags, state, *bReadRNG, NULL);
1950     *init_fep_state = state->fep_state;  /* there should be a better way to do this than setting it here.
1951                                             Investigate for 5.0. */
1952     if (ret)
1953     {
1954         cp_error();
1955     }
1956     ret = do_cpt_ekinstate(gmx_fio_getxdr(fp), flags_eks, &state->ekinstate, NULL);
1957     if (ret)
1958     {
1959         cp_error();
1960     }
1961     *bReadEkin = ((flags_eks & (1<<eeksEKINH)) || (flags_eks & (1<<eeksEKINF)) || (flags_eks & (1<<eeksEKINO)) ||
1962                   ((flags_eks & (1<<eeksEKINSCALEF)) | (flags_eks & (1<<eeksEKINSCALEH)) | (flags_eks & (1<<eeksVSCALE))));
1963
1964     ret = do_cpt_enerhist(gmx_fio_getxdr(fp), TRUE,
1965                           flags_enh, &state->enerhist, NULL);
1966     if (ret)
1967     {
1968         cp_error();
1969     }
1970
1971     ret = do_cpt_EDstate(gmx_fio_getxdr(fp), TRUE, &state->edsamstate, NULL);
1972     if (ret)
1973     {
1974         cp_error();
1975     }
1976
1977     if (file_version < 6)
1978     {
1979         const char *warn = "Reading checkpoint file in old format, assuming that the run that generated this file started at step 0, if this is not the case the averages stored in the energy file will be incorrect.";
1980
1981         fprintf(stderr, "\nWARNING: %s\n\n", warn);
1982         if (fplog)
1983         {
1984             fprintf(fplog, "\nWARNING: %s\n\n", warn);
1985         }
1986         state->enerhist.nsum     = *step;
1987         state->enerhist.nsum_sim = *step;
1988     }
1989
1990     ret = do_cpt_df_hist(gmx_fio_getxdr(fp), flags_dfh, &state->dfhist, NULL);
1991     if (ret)
1992     {
1993         cp_error();
1994     }
1995
1996     ret = do_cpt_files(gmx_fio_getxdr(fp), TRUE, &outputfiles, &nfiles, NULL, file_version);
1997     if (ret)
1998     {
1999         cp_error();
2000     }
2001
2002     ret = do_cpt_footer(gmx_fio_getxdr(fp), file_version);
2003     if (ret)
2004     {
2005         cp_error();
2006     }
2007     if (gmx_fio_close(fp) != 0)
2008     {
2009         gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
2010     }
2011
2012     sfree(fprog);
2013     sfree(ftime);
2014     sfree(btime);
2015     sfree(buser);
2016     sfree(bhost);
2017
2018     /* If the user wants to append to output files,
2019      * we use the file pointer positions of the output files stored
2020      * in the checkpoint file and truncate the files such that any frames
2021      * written after the checkpoint time are removed.
2022      * All files are md5sum checked such that we can be sure that
2023      * we do not truncate other (maybe imprortant) files.
2024      */
2025     if (bAppendOutputFiles)
2026     {
2027         if (fn2ftp(outputfiles[0].filename) != efLOG)
2028         {
2029             /* make sure first file is log file so that it is OK to use it for
2030              * locking
2031              */
2032             gmx_fatal(FARGS, "The first output file should always be the log "
2033                       "file but instead is: %s. Cannot do appending because of this condition.", outputfiles[0].filename);
2034         }
2035         for (i = 0; i < nfiles; i++)
2036         {
2037             if (outputfiles[i].offset < 0)
2038             {
2039                 gmx_fatal(FARGS, "The original run wrote a file called '%s' which "
2040                           "is larger than 2 GB, but mdrun did not support large file"
2041                           " offsets. Can not append. Run mdrun with -noappend",
2042                           outputfiles[i].filename);
2043             }
2044 #ifdef GMX_FAHCORE
2045             chksum_file = gmx_fio_open(outputfiles[i].filename, "a");
2046
2047 #else
2048             chksum_file = gmx_fio_open(outputfiles[i].filename, "r+");
2049
2050             /* lock log file */
2051             if (i == 0)
2052             {
2053                 /* Note that there are systems where the lock operation
2054                  * will succeed, but a second process can also lock the file.
2055                  * We should probably try to detect this.
2056                  */
2057 #ifndef GMX_NATIVE_WINDOWS
2058                 if (fcntl(fileno(gmx_fio_getfp(chksum_file)), F_SETLK, &fl)
2059                     == -1)
2060 #else
2061                 if (_locking(fileno(gmx_fio_getfp(chksum_file)), _LK_NBLCK, LONG_MAX) == -1)
2062 #endif
2063                 {
2064                     if (errno == ENOSYS)
2065                     {
2066                         if (!bForceAppend)
2067                         {
2068                             gmx_fatal(FARGS, "File locking is not supported on this system. Use -noappend or specify -append explicitly to append anyhow.");
2069                         }
2070                         else
2071                         {
2072                             fprintf(stderr, "\nNOTE: File locking is not supported on this system, will not lock %s\n\n", outputfiles[i].filename);
2073                             if (fplog)
2074                             {
2075                                 fprintf(fplog, "\nNOTE: File locking not supported on this system, will not lock %s\n\n", outputfiles[i].filename);
2076                             }
2077                         }
2078                     }
2079                     else if (errno == EACCES || errno == EAGAIN)
2080                     {
2081                         gmx_fatal(FARGS, "Failed to lock: %s. Already running "
2082                                   "simulation?", outputfiles[i].filename);
2083                     }
2084                     else
2085                     {
2086                         gmx_fatal(FARGS, "Failed to lock: %s. %s.",
2087                                   outputfiles[i].filename, strerror(errno));
2088                     }
2089                 }
2090             }
2091
2092             /* compute md5 chksum */
2093             if (outputfiles[i].chksum_size != -1)
2094             {
2095                 if (gmx_fio_get_file_md5(chksum_file, outputfiles[i].offset,
2096                                          digest) != outputfiles[i].chksum_size) /*at the end of the call the file position is at the end of the file*/
2097                 {
2098                     gmx_fatal(FARGS, "Can't read %d bytes of '%s' to compute checksum. The file has been replaced or its contents have been modified. Cannot do appending because of this condition.",
2099                               outputfiles[i].chksum_size,
2100                               outputfiles[i].filename);
2101                 }
2102             }
2103             if (i == 0)  /*log file needs to be seeked in case we need to truncate (other files are truncated below)*/
2104             {
2105                 if (gmx_fio_seek(chksum_file, outputfiles[i].offset))
2106                 {
2107                     gmx_fatal(FARGS, "Seek error! Failed to truncate log-file: %s.", strerror(errno));
2108                 }
2109             }
2110 #endif
2111
2112             if (i == 0) /*open log file here - so that lock is never lifted
2113                            after chksum is calculated */
2114             {
2115                 *pfplog = gmx_fio_getfp(chksum_file);
2116             }
2117             else
2118             {
2119                 gmx_fio_close(chksum_file);
2120             }
2121 #ifndef GMX_FAHCORE
2122             /* compare md5 chksum */
2123             if (outputfiles[i].chksum_size != -1 &&
2124                 memcmp(digest, outputfiles[i].chksum, 16) != 0)
2125             {
2126                 if (debug)
2127                 {
2128                     fprintf(debug, "chksum for %s: ", outputfiles[i].filename);
2129                     for (j = 0; j < 16; j++)
2130                     {
2131                         fprintf(debug, "%02x", digest[j]);
2132                     }
2133                     fprintf(debug, "\n");
2134                 }
2135                 gmx_fatal(FARGS, "Checksum wrong for '%s'. The file has been replaced or its contents have been modified. Cannot do appending because of this condition.",
2136                           outputfiles[i].filename);
2137             }
2138 #endif
2139
2140
2141             if (i != 0) /*log file is already seeked to correct position */
2142             {
2143 #ifdef GMX_NATIVE_WINDOWS
2144                 rc = gmx_wintruncate(outputfiles[i].filename, outputfiles[i].offset);
2145 #else
2146                 rc = truncate(outputfiles[i].filename, outputfiles[i].offset);
2147 #endif
2148                 if (rc != 0)
2149                 {
2150                     gmx_fatal(FARGS, "Truncation of file %s failed. Cannot do appending because of this failure.", outputfiles[i].filename);
2151                 }
2152             }
2153         }
2154     }
2155
2156     sfree(outputfiles);
2157 }
2158
2159
2160 void load_checkpoint(const char *fn, FILE **fplog,
2161                      t_commrec *cr, gmx_bool bPartDecomp, ivec dd_nc,
2162                      t_inputrec *ir, t_state *state,
2163                      gmx_bool *bReadRNG, gmx_bool *bReadEkin,
2164                      gmx_bool bAppend, gmx_bool bForceAppend)
2165 {
2166     gmx_large_int_t step;
2167     double          t;
2168
2169     if (SIMMASTER(cr))
2170     {
2171         /* Read the state from the checkpoint file */
2172         read_checkpoint(fn, fplog,
2173                         cr, bPartDecomp, dd_nc,
2174                         ir->eI, &(ir->fepvals->init_fep_state), &step, &t, state, bReadRNG, bReadEkin,
2175                         &ir->simulation_part, bAppend, bForceAppend);
2176     }
2177     if (PAR(cr))
2178     {
2179         gmx_bcast(sizeof(cr->npmenodes), &cr->npmenodes, cr);
2180         gmx_bcast(DIM*sizeof(dd_nc[0]), dd_nc, cr);
2181         gmx_bcast(sizeof(step), &step, cr);
2182         gmx_bcast(sizeof(*bReadRNG), bReadRNG, cr);
2183         gmx_bcast(sizeof(*bReadEkin), bReadEkin, cr);
2184     }
2185     ir->bContinuation    = TRUE;
2186     if (ir->nsteps >= 0)
2187     {
2188         ir->nsteps          += ir->init_step - step;
2189     }
2190     ir->init_step        = step;
2191     ir->simulation_part += 1;
2192 }
2193
2194 static void read_checkpoint_data(t_fileio *fp, int *simulation_part,
2195                                  gmx_large_int_t *step, double *t, t_state *state,
2196                                  gmx_bool bReadRNG,
2197                                  int *nfiles, gmx_file_position_t **outputfiles)
2198 {
2199     int                  file_version;
2200     char                *version, *btime, *buser, *bhost, *fprog, *ftime;
2201     int                  double_prec;
2202     int                  eIntegrator;
2203     int                  nppnodes, npme;
2204     ivec                 dd_nc;
2205     int                  flags_eks, flags_enh, flags_dfh;
2206     int                  nfiles_loc;
2207     gmx_file_position_t *files_loc = NULL;
2208     int                  ret;
2209
2210     do_cpt_header(gmx_fio_getxdr(fp), TRUE, &file_version,
2211                   &version, &btime, &buser, &bhost, &double_prec, &fprog, &ftime,
2212                   &eIntegrator, simulation_part, step, t, &nppnodes, dd_nc, &npme,
2213                   &state->natoms, &state->ngtc, &state->nnhpres, &state->nhchainlength,
2214                   &(state->dfhist.nlambda), &state->flags, &flags_eks, &flags_enh, &flags_dfh,
2215                   &state->edsamstate.nED, NULL);
2216     ret =
2217         do_cpt_state(gmx_fio_getxdr(fp), state->flags, state, bReadRNG, NULL);
2218     if (ret)
2219     {
2220         cp_error();
2221     }
2222     ret = do_cpt_ekinstate(gmx_fio_getxdr(fp), flags_eks, &state->ekinstate, NULL);
2223     if (ret)
2224     {
2225         cp_error();
2226     }
2227     ret = do_cpt_enerhist(gmx_fio_getxdr(fp), TRUE,
2228                           flags_enh, &state->enerhist, NULL);
2229     if (ret)
2230     {
2231         cp_error();
2232     }
2233     ret = do_cpt_df_hist(gmx_fio_getxdr(fp), flags_dfh, &state->dfhist, NULL);
2234     if (ret)
2235     {
2236         cp_error();
2237     }
2238
2239     ret = do_cpt_EDstate(gmx_fio_getxdr(fp), TRUE, &state->edsamstate, NULL);
2240     if (ret)
2241     {
2242         cp_error();
2243     }
2244
2245     ret = do_cpt_files(gmx_fio_getxdr(fp), TRUE,
2246                        outputfiles != NULL ? outputfiles : &files_loc,
2247                        outputfiles != NULL ? nfiles : &nfiles_loc,
2248                        NULL, file_version);
2249     if (files_loc != NULL)
2250     {
2251         sfree(files_loc);
2252     }
2253
2254     if (ret)
2255     {
2256         cp_error();
2257     }
2258
2259     ret = do_cpt_footer(gmx_fio_getxdr(fp), file_version);
2260     if (ret)
2261     {
2262         cp_error();
2263     }
2264
2265     sfree(fprog);
2266     sfree(ftime);
2267     sfree(btime);
2268     sfree(buser);
2269     sfree(bhost);
2270 }
2271
2272 void
2273 read_checkpoint_state(const char *fn, int *simulation_part,
2274                       gmx_large_int_t *step, double *t, t_state *state)
2275 {
2276     t_fileio *fp;
2277
2278     fp = gmx_fio_open(fn, "r");
2279     read_checkpoint_data(fp, simulation_part, step, t, state, FALSE, NULL, NULL);
2280     if (gmx_fio_close(fp) != 0)
2281     {
2282         gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
2283     }
2284 }
2285
2286 void read_checkpoint_trxframe(t_fileio *fp, t_trxframe *fr)
2287 {
2288     t_state         state;
2289     int             simulation_part;
2290     gmx_large_int_t step;
2291     double          t;
2292
2293     init_state(&state, 0, 0, 0, 0, 0);
2294
2295     read_checkpoint_data(fp, &simulation_part, &step, &t, &state, FALSE, NULL, NULL);
2296
2297     fr->natoms  = state.natoms;
2298     fr->bTitle  = FALSE;
2299     fr->bStep   = TRUE;
2300     fr->step    = gmx_large_int_to_int(step,
2301                                        "conversion of checkpoint to trajectory");
2302     fr->bTime      = TRUE;
2303     fr->time       = t;
2304     fr->bLambda    = TRUE;
2305     fr->lambda     = state.lambda[efptFEP];
2306     fr->fep_state  = state.fep_state;
2307     fr->bAtoms     = FALSE;
2308     fr->bX         = (state.flags & (1<<estX));
2309     if (fr->bX)
2310     {
2311         fr->x     = state.x;
2312         state.x   = NULL;
2313     }
2314     fr->bV      = (state.flags & (1<<estV));
2315     if (fr->bV)
2316     {
2317         fr->v     = state.v;
2318         state.v   = NULL;
2319     }
2320     fr->bF      = FALSE;
2321     fr->bBox    = (state.flags & (1<<estBOX));
2322     if (fr->bBox)
2323     {
2324         copy_mat(state.box, fr->box);
2325     }
2326     done_state(&state);
2327 }
2328
2329 void list_checkpoint(const char *fn, FILE *out)
2330 {
2331     t_fileio            *fp;
2332     int                  file_version;
2333     char                *version, *btime, *buser, *bhost, *fprog, *ftime;
2334     int                  double_prec;
2335     int                  eIntegrator, simulation_part, nppnodes, npme;
2336     gmx_large_int_t      step;
2337     double               t;
2338     ivec                 dd_nc;
2339     t_state              state;
2340     int                  flags_eks, flags_enh, flags_dfh;
2341     int                  indent;
2342     int                  i, j;
2343     int                  ret;
2344     gmx_file_position_t *outputfiles;
2345     int                  nfiles;
2346
2347     init_state(&state, -1, -1, -1, -1, 0);
2348
2349     fp = gmx_fio_open(fn, "r");
2350     do_cpt_header(gmx_fio_getxdr(fp), TRUE, &file_version,
2351                   &version, &btime, &buser, &bhost, &double_prec, &fprog, &ftime,
2352                   &eIntegrator, &simulation_part, &step, &t, &nppnodes, dd_nc, &npme,
2353                   &state.natoms, &state.ngtc, &state.nnhpres, &state.nhchainlength,
2354                   &(state.dfhist.nlambda), &state.flags,
2355                   &flags_eks, &flags_enh, &flags_dfh, &state.edsamstate.nED, out);
2356     ret = do_cpt_state(gmx_fio_getxdr(fp), state.flags, &state, TRUE, out);
2357     if (ret)
2358     {
2359         cp_error();
2360     }
2361     ret = do_cpt_ekinstate(gmx_fio_getxdr(fp), flags_eks, &state.ekinstate, out);
2362     if (ret)
2363     {
2364         cp_error();
2365     }
2366     ret = do_cpt_enerhist(gmx_fio_getxdr(fp), TRUE,
2367                           flags_enh, &state.enerhist, out);
2368
2369     if (ret == 0)
2370     {
2371         init_df_history(&state.dfhist, state.dfhist.nlambda, 0); /* reinitialize state with correct sizes */
2372         ret = do_cpt_df_hist(gmx_fio_getxdr(fp), flags_dfh, &state.dfhist, out);
2373     }
2374
2375     if (ret == 0)
2376     {
2377         ret = do_cpt_EDstate(gmx_fio_getxdr(fp), TRUE, &state.edsamstate, out);
2378     }
2379
2380     if (ret == 0)
2381     {
2382         do_cpt_files(gmx_fio_getxdr(fp), TRUE, &outputfiles, &nfiles, out, file_version);
2383     }
2384
2385     if (ret == 0)
2386     {
2387         ret = do_cpt_footer(gmx_fio_getxdr(fp), file_version);
2388     }
2389
2390     if (ret)
2391     {
2392         cp_warning(out);
2393     }
2394     if (gmx_fio_close(fp) != 0)
2395     {
2396         gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
2397     }
2398
2399     done_state(&state);
2400 }
2401
2402
2403 static gmx_bool exist_output_file(const char *fnm_cp, int nfile, const t_filenm fnm[])
2404 {
2405     int i;
2406
2407     /* Check if the output file name stored in the checkpoint file
2408      * is one of the output file names of mdrun.
2409      */
2410     i = 0;
2411     while (i < nfile &&
2412            !(is_output(&fnm[i]) && strcmp(fnm_cp, fnm[i].fns[0]) == 0))
2413     {
2414         i++;
2415     }
2416
2417     return (i < nfile && gmx_fexist(fnm_cp));
2418 }
2419
2420 /* This routine cannot print tons of data, since it is called before the log file is opened. */
2421 gmx_bool read_checkpoint_simulation_part(const char *filename, int *simulation_part,
2422                                          gmx_large_int_t *cpt_step, t_commrec *cr,
2423                                          gmx_bool bAppendReq,
2424                                          int nfile, const t_filenm fnm[],
2425                                          const char *part_suffix, gmx_bool *bAddPart)
2426 {
2427     t_fileio            *fp;
2428     gmx_large_int_t      step = 0;
2429     double               t;
2430     t_state              state;
2431     int                  nfiles;
2432     gmx_file_position_t *outputfiles;
2433     int                  nexist, f;
2434     gmx_bool             bAppend;
2435     char                *fn, suf_up[STRLEN];
2436
2437     bAppend = FALSE;
2438
2439     if (SIMMASTER(cr))
2440     {
2441         if (!gmx_fexist(filename) || (!(fp = gmx_fio_open(filename, "r")) ))
2442         {
2443             *simulation_part = 0;
2444         }
2445         else
2446         {
2447             init_state(&state, 0, 0, 0, 0, 0);
2448
2449             read_checkpoint_data(fp, simulation_part, &step, &t, &state, FALSE,
2450                                  &nfiles, &outputfiles);
2451             if (gmx_fio_close(fp) != 0)
2452             {
2453                 gmx_file("Cannot read/write checkpoint; corrupt file, or maybe you are out of disk space?");
2454             }
2455             done_state(&state);
2456
2457             if (bAppendReq)
2458             {
2459                 nexist = 0;
2460                 for (f = 0; f < nfiles; f++)
2461                 {
2462                     if (exist_output_file(outputfiles[f].filename, nfile, fnm))
2463                     {
2464                         nexist++;
2465                     }
2466                 }
2467                 if (nexist == nfiles)
2468                 {
2469                     bAppend = bAppendReq;
2470                 }
2471                 else if (nexist > 0)
2472                 {
2473                     fprintf(stderr,
2474                             "Output file appending has been requested,\n"
2475                             "but some output files listed in the checkpoint file %s\n"
2476                             "are not present or are named differently by the current program:\n",
2477                             filename);
2478                     fprintf(stderr, "output files present:");
2479                     for (f = 0; f < nfiles; f++)
2480                     {
2481                         if (exist_output_file(outputfiles[f].filename,
2482                                               nfile, fnm))
2483                         {
2484                             fprintf(stderr, " %s", outputfiles[f].filename);
2485                         }
2486                     }
2487                     fprintf(stderr, "\n");
2488                     fprintf(stderr, "output files not present or named differently:");
2489                     for (f = 0; f < nfiles; f++)
2490                     {
2491                         if (!exist_output_file(outputfiles[f].filename,
2492                                                nfile, fnm))
2493                         {
2494                             fprintf(stderr, " %s", outputfiles[f].filename);
2495                         }
2496                     }
2497                     fprintf(stderr, "\n");
2498
2499                     gmx_fatal(FARGS, "File appending requested, but only %d of the %d output files are present", nexist, nfiles);
2500                 }
2501             }
2502
2503             if (bAppend)
2504             {
2505                 if (nfiles == 0)
2506                 {
2507                     gmx_fatal(FARGS, "File appending requested, but no output file information is stored in the checkpoint file");
2508                 }
2509                 fn = outputfiles[0].filename;
2510                 if (strlen(fn) < 4 ||
2511                     gmx_strcasecmp(fn+strlen(fn)-4, ftp2ext(efLOG)) == 0)
2512                 {
2513                     gmx_fatal(FARGS, "File appending requested, but the log file is not the first file listed in the checkpoint file");
2514                 }
2515                 /* Set bAddPart to whether the suffix string '.part' is present
2516                  * in the log file name.
2517                  */
2518                 strcpy(suf_up, part_suffix);
2519                 upstring(suf_up);
2520                 *bAddPart = (strstr(fn, part_suffix) != NULL ||
2521                              strstr(fn, suf_up) != NULL);
2522             }
2523
2524             sfree(outputfiles);
2525         }
2526     }
2527     if (PAR(cr))
2528     {
2529         gmx_bcast(sizeof(*simulation_part), simulation_part, cr);
2530
2531         if (*simulation_part > 0 && bAppendReq)
2532         {
2533             gmx_bcast(sizeof(bAppend), &bAppend, cr);
2534             gmx_bcast(sizeof(*bAddPart), bAddPart, cr);
2535         }
2536     }
2537     if (NULL != cpt_step)
2538     {
2539         *cpt_step = step;
2540     }
2541
2542     return bAppend;
2543 }