Fix use of inline in IMD
[alexxy/gromacs.git] / src / gromacs / imd / imd.c
1 /*
2  * This file is part of the GROMACS molecular simulation package.
3  *
4  * Copyright (c) 2014, by the GROMACS development team, led by
5  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
6  * and including many others, as listed in the AUTHORS file in the
7  * top-level source directory and at http://www.gromacs.org.
8  *
9  * GROMACS is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public License
11  * as published by the Free Software Foundation; either version 2.1
12  * of the License, or (at your option) any later version.
13  *
14  * GROMACS is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with GROMACS; if not, see
21  * http://www.gnu.org/licenses, or write to the Free Software Foundation,
22  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA.
23  *
24  * If you want to redistribute modifications to GROMACS, please
25  * consider that scientific software is very special. Version
26  * control is crucial - bugs must be traceable. We will be happy to
27  * consider code for inclusion in the official distribution, but
28  * derived work must not be called official GROMACS. Details are found
29  * in the README & COPYING files - if they are missing, get the
30  * official version at http://www.gromacs.org.
31  *
32  * To help us fund GROMACS development, we humbly ask that you cite
33  * the research papers on the package. Check out http://www.gromacs.org.
34  */
35
36 /*! \libinternal \file
37  *
38  * \brief
39  * Implements functions of imd.h.
40  *
41  * Re-implementation of basic IMD functions from NAMD/VMD from scratch,
42  * see imdsocket.h for references to the IMD API.
43  *
44  * \author Martin Hoefling, Carsten Kutzner <ckutzne@gwdg.de>
45  *
46  * \inlibraryapi
47  * \ingroup module_imd
48  */
49
50 #ifdef HAVE_CONFIG_H
51 #include <config.h>
52 #endif
53
54
55 #include "imd.h"
56 #include "imdsocket.h"
57 #include "smalloc.h"
58 #include "network.h"
59 #include "mdrun.h"
60 #include "sighandler.h"
61 #include "gmx_ga2la.h"
62 #include "xvgr.h"
63 #include "gromacs/mdlib/groupcoord.h"
64 #include "gromacs/fileio/confio.h"
65 #include "mtop_util.h"
66 #include "names.h"
67 #include "gromacs/timing/wallcycle.h"
68
69 #include <string.h>
70
71 #ifdef GMX_NATIVE_WINDOWS
72 #include <Windows.h>
73 #else
74 #include <unistd.h>
75 #endif
76
77 /*! \brief How long shall we wait in seconds until we check for a connection again? */
78 #define IMDLOOPWAIT 1
79
80 /*! \brief How long shall we check for the IMD_GO? */
81 #define IMDCONNECTWAIT 2
82
83 /*! \brief IMD Header Size. */
84 #define HEADERSIZE 8
85 /*! \brief IMD Protocol Version. */
86 #define IMDVERSION 2
87
88 /*! \brief Broadcast d to all nodes */
89 #define  block_bc(cr,   d) gmx_bcast(     sizeof(d),     &(d), (cr))
90
91 /*! \brief Broadcast nr elements of d to all nodes */
92 #define  nblock_bc(cr, nr, d) gmx_bcast((nr)*sizeof((d)[0]), (d), (cr))
93
94
95 /*! \libinternal
96  * \brief
97  * IMD (interactive molecular dynamics) energy record.
98  *
99  * As in the original IMD implementation. Energies in kcal/mol.
100  * NOTE: We return the energies in GROMACS / SI units,
101  * so they also show up as SI in VMD.
102  *
103  */
104 typedef struct
105 {
106     gmx_int32_t tstep;     /**< time step                                     */
107     float       T_abs;     /**< absolute temperature                          */
108     float       E_tot;     /**< total energy                                  */
109     float       E_pot;     /**< potential energy                              */
110     float       E_vdw;     /**< van der Waals energy                          */
111     float       E_coul;    /**< Coulomb interaction energy                    */
112     float       E_bond;    /**< bonds energy                                  */
113     float       E_angle;   /**< angles energy                                 */
114     float       E_dihe;    /**< dihedrals energy                              */
115     float       E_impr;    /**< improper dihedrals energy                     */
116 } IMDEnergyBlock;
117
118
119 /*! \libinternal
120  * \brief IMD (interactive molecular dynamics) communication structure.
121  *
122  * This structure defines the IMD communication message header & protocol version.
123  */
124 typedef struct
125 {
126     gmx_int32_t type;      /**< Type of IMD message, see IMDType_t above      */
127     gmx_int32_t length;    /**< Length                                        */
128 } IMDHeader;
129
130
131 /*! \libinternal
132  * \brief IMD (interactive molecular dynamics) main data structure.
133  *
134  * Contains private IMD data
135  */
136 typedef struct gmx_IMD
137 {
138     FILE      *outf;                 /**< Output file for IMD data, mainly forces.    */
139
140     int        nat;                  /**< Number of atoms that can be pulled via IMD. */
141     int        nat_loc;              /**< Part of the atoms that are local.           */
142     atom_id   *ind;                  /**< Global indices of the IMD atoms.            */
143     atom_id   *ind_loc;              /**< Local indices of the IMD atoms.             */
144     int        nalloc_loc;           /**< Allocation size for ind_loc.                */
145     rvec      *xa;                   /**< Positions for all IMD atoms assembled on
146                                           the master node.                            */
147     ivec      *xa_shifts;            /**< Shifts for all IMD atoms, to make
148                                           molecule(s) whole.                          */
149     ivec      *xa_eshifts;           /**< Extra shifts since last DD step.            */
150     rvec      *xa_old;               /**< Old positions for all IMD atoms on master.  */
151     int       *xa_ind;               /**< Position of each local atom in the
152                                           collective array.                           */
153
154     int             nstimd;          /**< Global IMD frequency, known to all nodes.   */
155     int             nstimd_new;      /**< New frequency from IMD client, master only. */
156     int             nstimd_def;      /**< Default IMD frequency when disconnected.    */
157
158     int             port;            /**< Port to use for network socket.             */
159     IMDSocket      *socket;          /**< The IMD socket on the master node.          */
160     IMDSocket      *clientsocket;    /**< The IMD socket on the client.               */
161     int             length;          /**< Length we got with last header.             */
162
163     gmx_bool        bWConnect;       /**< Shall we block and wait for connection?     */
164     gmx_bool        bTerminated;     /**< Set if MD is terminated.                    */
165     gmx_bool        bTerminatable;   /**< Set if MD can be terminated.                */
166     gmx_bool        bConnected;      /**< Set if connection is present.               */
167     gmx_bool        bNewForces;      /**< Set if we received new forces.              */
168     gmx_bool        bForceActivated; /**< Set if pulling from VMD is allowed.         */
169
170     IMDEnergyBlock *energies;        /**< Pointer to energies we send back.           */
171
172     gmx_int32_t     vmd_nforces;     /**< Number of VMD forces.                       */
173     gmx_int32_t    *vmd_f_ind;       /**< VMD forces indices.                         */
174     float          *vmd_forces;      /**< The VMD forces flat in memory.              */
175     int             nforces;         /**< Number of actual MD forces;
176                                           this gets communicated to the clients.      */
177     atom_id        *f_ind;           /**< Force indices.                              */
178     rvec           *f;               /**< The IMD pulling forces.                     */
179
180     char           *forcesendbuf;    /**< Buffer for force sending.                   */
181     char           *coordsendbuf;    /**< Buffer for coordinate sending.              */
182     char           *energysendbuf;   /**< Send buffer for energies.                   */
183     rvec           *sendxbuf;        /**< Buffer to make molecules whole before
184                                           sending.                                    */
185
186     t_block         mols;            /**< Molecules block in IMD group.               */
187
188     /* The next block is used on the master node only to reduce the output
189      * without sacrificing information. If any of these values changes,
190      * we need to write output */
191     int       old_nforces;           /**< Old value for nforces.                      */
192     atom_id  *old_f_ind;             /**< Old values for force indices.               */
193     rvec     *old_forces;            /**< Old values for IMD pulling forces.          */
194
195 } t_gmx_IMD_setup;
196
197
198 /*! \libinternal
199  * \brief Enum for types of IMD messages.
200  *
201  * We use the same records as the NAMD/VMD IMD implementation.
202  */
203 typedef enum IMDType_t
204 {
205     IMD_DISCONNECT,      /**< client disconnect                               */
206     IMD_ENERGIES,        /**< energy data                                     */
207     IMD_FCOORDS,         /**< atomic coordinates                              */
208     IMD_GO,              /**< start command for the simulation                */
209     IMD_HANDSHAKE,       /**< handshake to determine little/big endianness    */
210     IMD_KILL,            /**< terminates the simulation                       */
211     IMD_MDCOMM,          /**< force data                                      */
212     IMD_PAUSE,           /**< pauses the simulation                           */
213     IMD_TRATE,           /**< sets the IMD transmission and processing rate   */
214     IMD_IOERROR,         /**< I/O error                                       */
215     IMD_NR               /**< number of entries                               */
216 } IMDMessageType;
217
218
219 /*! \libinternal
220  * \brief Names of the IMDType for error messages.
221  */
222 const char *eIMDType_names[IMD_NR + 1] = {
223     "IMD_DISCONNECT",
224     "IMD_ENERGIES",
225     "IMD_FCOORDS",
226     "IMD_GO",
227     "IMD_HANDSHAKE",
228     "IMD_KILL",
229     "IMD_MDCOMM",
230     "IMD_PAUSE",
231     "IMD_TRATE",
232     "IMD_IOERROR",
233     NULL
234 };
235
236
237 #ifdef GMX_IMD
238
239 /*! \brief Fills the header with message and the length argument. */
240 static void fill_header(IMDHeader *header, IMDMessageType type, gmx_int32_t length)
241 {
242     /* We (ab-)use htonl network function for the correct endianness */
243     header->type   = htonl((gmx_int32_t) type);
244     header->length = htonl(length);
245 }
246
247
248 /*! \brief Swaps the endianess of the header. */
249 static void swap_header(IMDHeader *header)
250 {
251     /* and vice versa... */
252     header->type   = ntohl(header->type);
253     header->length = ntohl(header->length);
254 }
255
256
257 /*! \brief Reads multiple bytes from socket. */
258 static gmx_int32_t imd_read_multiple(IMDSocket *socket, char *datptr, gmx_int32_t toread)
259 {
260     gmx_int32_t leftcount, countread;
261
262
263     leftcount = toread;
264     /* Try to read while we haven't reached toread */
265     while (leftcount != 0)
266     {
267         if ((countread = imdsock_read(socket, datptr, leftcount)) < 0)
268         {
269             /* interrupted function call, try again... */
270             if (errno == EINTR)
271             {
272                 countread = 0;
273             }
274             /* this is an unexpected error, return what we got */
275             else
276             {
277                 return toread - leftcount;
278             }
279
280             /* nothing read, finished */
281         }
282         else if (countread == 0)
283         {
284             break;
285         }
286         leftcount -= countread;
287         datptr    += countread;
288     } /* end while */
289
290     /* return nr of bytes read */
291     return toread - leftcount;
292 }
293
294
295 /*! \brief Writes multiple bytes to socket in analogy to imd_read_multiple. */
296 static gmx_int32_t imd_write_multiple(IMDSocket *socket, const char *datptr, gmx_int32_t towrite)
297 {
298     gmx_int32_t leftcount, countwritten;
299
300
301     leftcount = towrite;
302     while (leftcount != 0)
303     {
304         if ((countwritten = imdsock_write(socket, datptr, leftcount)) <= 0)
305         {
306             if (errno == EINTR)
307             {
308                 countwritten = 0;
309             }
310             else
311             {
312                 return towrite - leftcount;
313             }
314         }
315         leftcount -= countwritten;
316         datptr    += countwritten;
317     } /* end while */
318
319     return towrite - leftcount;
320 }
321
322
323 /*! \brief Handshake with IMD client. */
324 static int imd_handshake(IMDSocket *socket)
325 {
326     IMDHeader header;
327
328
329     fill_header(&header, IMD_HANDSHAKE, 1);
330     header.length = IMDVERSION; /* client wants unswapped version */
331
332     return (imd_write_multiple(socket, (char *) &header, HEADERSIZE) != HEADERSIZE);
333 }
334
335
336 /*! \brief Send energies using the energy block and the send buffer. */
337 static int imd_send_energies(IMDSocket *socket, const IMDEnergyBlock *energies, char *buffer)
338 {
339     gmx_int32_t recsize;
340
341
342     recsize = HEADERSIZE + sizeof(IMDEnergyBlock);
343     fill_header((IMDHeader *) buffer, IMD_ENERGIES, 1);
344     memcpy(buffer + HEADERSIZE, energies, sizeof(IMDEnergyBlock));
345
346     return (imd_write_multiple(socket, buffer, recsize) != recsize);
347 }
348
349
350 /*! \brief Receive IMD header from socket, sets the length and returns the IMD message. */
351 static IMDMessageType imd_recv_header(IMDSocket *socket, gmx_int32_t *length)
352 {
353     IMDHeader header;
354
355
356     if (imd_read_multiple(socket, (char *) &header, HEADERSIZE) != HEADERSIZE)
357     {
358         return IMD_IOERROR;
359     }
360     swap_header(&header);
361     *length = header.length;
362
363     return (IMDMessageType) header.type;
364 }
365
366
367 /*! \brief Receive force indices and forces.
368  *
369  * The number of forces was previously communicated via the header.
370  */
371 static int imd_recv_mdcomm(IMDSocket *socket, gmx_int32_t nforces, gmx_int32_t *forcendx, float *forces)
372 {
373     int retsize, retbytes;
374
375
376     /* reading indices */
377     retsize  = sizeof(gmx_int32_t) * nforces;
378     retbytes = imd_read_multiple(socket, (char *) forcendx, retsize);
379     if (retbytes != retsize)
380     {
381         return FALSE;
382     }
383
384     /* reading forces as float array */
385     retsize  = 3 * sizeof(float) * nforces;
386     retbytes = imd_read_multiple(socket, (char *) forces, retsize);
387     if (retbytes != retsize)
388     {
389         return FALSE;
390     }
391
392     return TRUE;
393 }
394
395 #endif
396
397 /* GROMACS specific functions for the IMD implementation */
398
399 extern void write_IMDgroup_to_file(gmx_bool bIMD, t_inputrec *ir, t_state *state,
400                                    gmx_mtop_t *sys, int nfile, const t_filenm fnm[])
401 {
402     t_atoms IMDatoms;
403
404
405     if (bIMD)
406     {
407         IMDatoms = gmx_mtop_global_atoms(sys);
408         write_sto_conf_indexed(opt2fn("-imd", nfile, fnm), "IMDgroup", &IMDatoms,
409                                state->x, state->v, ir->ePBC, state->box, ir->imd->nat, ir->imd->ind);
410     }
411 }
412
413
414 extern void dd_make_local_IMD_atoms(gmx_bool bIMD, gmx_domdec_t *dd, t_IMD *imd)
415 {
416     gmx_ga2la_t         ga2la;
417     t_gmx_IMD_setup    *IMDsetup;
418
419
420     if (bIMD)
421     {
422         IMDsetup = imd->setup;
423         ga2la    = dd->ga2la;
424
425         dd_make_local_group_indices(
426                 ga2la, IMDsetup->nat, IMDsetup->ind, &IMDsetup->nat_loc,
427                 &IMDsetup->ind_loc, &IMDsetup->nalloc_loc, IMDsetup->xa_ind);
428     }
429 }
430
431
432 #ifdef GMX_IMD
433 /*! \brief Send positions from rvec.
434  *
435  * We need a separate send buffer and conversion to Angstrom.
436  */
437 static int imd_send_rvecs(IMDSocket *socket, int nat, rvec *x, char *buffer)
438 {
439     gmx_int32_t size;
440     int         i;
441     float       sendx[3];
442     int         tuplesize = 3 * sizeof(float);
443
444
445     /* Required size for the send buffer */
446     size = HEADERSIZE + 3 * sizeof(float) * nat;
447
448     /* Prepare header */
449     fill_header((IMDHeader *) buffer, IMD_FCOORDS, (gmx_int32_t) nat);
450     for (i = 0; i < nat; i++)
451     {
452         sendx[0] = (float) x[i][0] * NM2A;
453         sendx[1] = (float) x[i][1] * NM2A;
454         sendx[2] = (float) x[i][2] * NM2A;
455         memcpy(buffer + HEADERSIZE + i * tuplesize, sendx, tuplesize);
456     }
457
458     return (imd_write_multiple(socket, buffer, size) != size);
459 }
460
461
462 /*! \brief Initializes the IMD private data. */
463 static t_gmx_IMD_setup* imd_create(int imdatoms, int nstimddef, int imdport)
464 {
465     t_gmx_IMD_setup *IMDsetup = NULL;
466
467
468     snew(IMDsetup, 1);
469     IMDsetup->nat             = imdatoms;
470     IMDsetup->bTerminated     = FALSE;
471     IMDsetup->bTerminatable   = FALSE;
472     IMDsetup->bWConnect       = FALSE;
473     IMDsetup->bConnected      = FALSE;
474     IMDsetup->bForceActivated = FALSE;
475     IMDsetup->bNewForces      = FALSE;
476     IMDsetup->bForceActivated = FALSE;
477     IMDsetup->nstimd          = 1;
478     IMDsetup->nstimd_new      = 1;
479     IMDsetup->nstimd_def      = nstimddef;
480     if (imdport < 1)
481     {
482         IMDsetup->port        = 0;
483         fprintf(stderr, "%s You chose a port number < 1. Will automatically assign a free port.\n", IMDstr);
484     }
485     else
486     {
487         IMDsetup->port        = imdport;
488     }
489
490     return IMDsetup;
491 }
492
493
494 /*! \brief Prepare the socket on the MASTER. */
495 static void imd_prepare_master_socket(t_gmx_IMD_setup *IMDsetup)
496 {
497     int ret;
498
499
500 #ifdef GMX_NATIVE_WINDOWS
501     /* Winsock requires separate initialization */
502     fprintf(stderr, "%s Initializing winsock.\n", IMDstr);
503 #ifdef GMX_HAVE_WINSOCK
504     if (imdsock_winsockinit())
505     {
506         gmx_fatal(FARGS, "%s Failed to initialize winsock.\n", IMDstr);
507     }
508 #endif
509 #endif
510
511     /* The rest is identical, first create and bind a socket and set to listen then. */
512     fprintf(stderr, "%s Setting up incoming socket.\n", IMDstr);
513     IMDsetup->socket = imdsock_create();
514     if (!IMDsetup->socket)
515     {
516         gmx_fatal(FARGS, "%s Failed to create socket.", IMDstr);
517     }
518
519     /* Bind to port */
520     ret = imdsock_bind(IMDsetup->socket, IMDsetup->port);
521     if (ret)
522     {
523         gmx_fatal(FARGS, "%s binding socket to port %d failed with error %d.\n", IMDstr, IMDsetup->port, ret);
524     }
525
526     if (imd_sock_listen(IMDsetup->socket))
527     {
528         gmx_fatal(FARGS, "%s socket listen failed with error %d.\n", IMDstr, ret);
529     }
530
531     if (imdsock_getport(IMDsetup->socket, &IMDsetup->port))
532     {
533         gmx_fatal(FARGS, "%s Could not determine port number.\n", IMDstr, ret);
534     }
535
536     fprintf(stderr, "%s Listening for IMD connection on port %d.\n", IMDstr, IMDsetup->port);
537 }
538
539
540 /*! \brief Disconnect the client. */
541 static void imd_disconnect(t_gmx_IMD_setup *IMDsetup)
542 {
543     /* Write out any buffered pulling data */
544     fflush(IMDsetup->outf);
545
546     /* we first try to shut down the clientsocket */
547     imdsock_shutdown(IMDsetup->clientsocket);
548     if (!imdsock_destroy(IMDsetup->clientsocket))
549     {
550         fprintf(stderr, "%s Failed to destroy socket.\n", IMDstr);
551     }
552
553     /* then we reset the IMD step to its default, and reset the connection boolean */
554     IMDsetup->nstimd_new   = IMDsetup->nstimd_def;
555     IMDsetup->clientsocket = NULL;
556     IMDsetup->bConnected   = FALSE;
557 }
558
559
560 /*! \brief Prints an error message and disconnects the client.
561  *
562  *  Does not terminate mdrun!
563  */
564 static void imd_fatal(t_gmx_IMD_setup *IMDsetup, const char *msg)
565 {
566     fprintf(stderr, "%s %s", IMDstr, msg);
567     imd_disconnect(IMDsetup);
568     fprintf(stderr, "%s disconnected.\n", IMDstr);
569 }
570
571
572 /*! \brief Check whether we got an incoming connection. */
573 static gmx_bool imd_tryconnect(t_gmx_IMD_setup *IMDsetup)
574 {
575     if (imdsock_tryread(IMDsetup->socket, 0, 0) > 0)
576     {
577         /* yes, we got something, accept on clientsocket */
578         IMDsetup->clientsocket = imdsock_accept(IMDsetup->socket);
579         if (!IMDsetup->clientsocket)
580         {
581             fprintf(stderr, "%s Accepting the connection on the socket failed.\n", IMDstr);
582             return FALSE;
583         }
584
585         /* handshake with client */
586         if (imd_handshake(IMDsetup->clientsocket))
587         {
588             imd_fatal(IMDsetup, "Connection failed.\n");
589             return FALSE;
590         }
591
592         fprintf(stderr, "%s Connection established, checking if I got IMD_GO orders.\n", IMDstr);
593
594         /* Check if we get the proper "GO" command from client. */
595         if (imdsock_tryread(IMDsetup->clientsocket, IMDCONNECTWAIT, 0) != 1 || imd_recv_header(IMDsetup->clientsocket, &(IMDsetup->length)) != IMD_GO)
596         {
597             imd_fatal(IMDsetup, "No IMD_GO order received. IMD connection failed.\n");
598         }
599
600         /* IMD connected */
601         IMDsetup->bConnected = TRUE;
602
603         return TRUE;
604     }
605
606     return FALSE;
607 }
608
609
610 /*! \brief Wrap imd_tryconnect in order to make it blocking.
611  *
612  * Used when the simulation should wait for an incoming connection.
613  */
614 static void imd_blockconnect(t_gmx_IMD_setup *IMDsetup)
615 {
616     /* do not wait for connection, when e.g. ctrl+c is pressed and we will terminate anyways. */
617     if (!(int) gmx_get_stop_condition() == gmx_stop_cond_none)
618     {
619         return;
620     }
621
622     fprintf(stderr, "%s Will wait until I have a connection and IMD_GO orders.\n", IMDstr);
623
624     /* while we have no clientsocket... 2nd part: we should still react on ctrl+c */
625     while ((!IMDsetup->clientsocket) && ((int) gmx_get_stop_condition() == gmx_stop_cond_none))
626     {
627         imd_tryconnect(IMDsetup);
628 #ifdef GMX_NATIVE_WINDOWS
629         /* for whatever reason, it is called Sleep on windows */
630         Sleep(IMDLOOPWAIT);
631 #else
632         sleep(IMDLOOPWAIT);
633 #endif
634     }
635 }
636
637
638 /*! \brief Make sure that our array holding the forces received via IMD is large enough. */
639 static void imd_prepare_vmd_Forces(t_gmx_IMD_setup *IMDsetup)
640 {
641     srenew((IMDsetup->vmd_f_ind), IMDsetup->vmd_nforces);
642     srenew((IMDsetup->vmd_forces), 3*IMDsetup->vmd_nforces);
643 }
644
645
646 /*! \brief Reads forces received via IMD. */
647 static void imd_read_vmd_Forces(t_gmx_IMD_setup *IMDsetup)
648 {
649     /* the length of the previously received header tells us the nr of forces we will receive */
650     IMDsetup->vmd_nforces = IMDsetup->length;
651     /* prepare the arrays */
652     imd_prepare_vmd_Forces(IMDsetup);
653     /* Now we read the forces... */
654     if (!(imd_recv_mdcomm(IMDsetup->clientsocket, IMDsetup->vmd_nforces, IMDsetup->vmd_f_ind, IMDsetup->vmd_forces)))
655     {
656         imd_fatal(IMDsetup, "Error while reading forces from remote. Disconnecting\n");
657     }
658 }
659
660
661 /*! \brief Prepares the MD force arrays. */
662 static void imd_prepare_MD_Forces(t_gmx_IMD_setup *IMDsetup)
663 {
664     srenew((IMDsetup->f_ind), IMDsetup->nforces);
665     srenew((IMDsetup->f    ), IMDsetup->nforces);
666 }
667
668
669 /*! \brief Copy IMD forces to MD forces.
670  *
671  * Do conversion from Cal->Joule and from
672  * Angstrom -> nm and from a pointer array to arrays to 3*N array.
673  */
674 static void imd_copyto_MD_Forces(t_gmx_IMD_setup *IMDsetup)
675 {
676     int  i;
677     real conversion = CAL2JOULE * NM2A;
678
679
680     for (i = 0; i < IMDsetup->nforces; i++)
681     {
682         /* Copy the indices, a copy is important because we may update the incoming forces
683          * whenever we receive new forces while the MD forces are only communicated upon
684          * IMD communication.*/
685         IMDsetup->f_ind[i] = IMDsetup->vmd_f_ind[i];
686
687         /* Convert to rvecs and do a proper unit conversion */
688         IMDsetup->f[i][0] = IMDsetup->vmd_forces[3*i    ] * conversion;
689         IMDsetup->f[i][1] = IMDsetup->vmd_forces[3*i + 1] * conversion;
690         IMDsetup->f[i][2] = IMDsetup->vmd_forces[3*i + 2] * conversion;
691     }
692 }
693
694
695 /*! \brief Return TRUE if any of the forces or indices changed. */
696 static gmx_bool bForcesChanged(t_gmx_IMD_setup *IMDsetup)
697 {
698     int i;
699
700
701     /* First, check whether the number of pulled atoms changed */
702     if (IMDsetup->nforces != IMDsetup->old_nforces)
703     {
704         return TRUE;
705     }
706
707     /* Second, check whether any of the involved atoms changed */
708     for (i = 0; i < IMDsetup->nforces; i++)
709     {
710         if (IMDsetup->f_ind[i] != IMDsetup->old_f_ind[i])
711         {
712             return TRUE;
713         }
714     }
715
716     /* Third, check whether all forces are the same */
717     for (i = 0; i < IMDsetup->nforces; i++)
718     {
719         if (IMDsetup->f[i][XX] != IMDsetup->old_forces[i][XX])
720         {
721             return TRUE;
722         }
723         if (IMDsetup->f[i][YY] != IMDsetup->old_forces[i][YY])
724         {
725             return TRUE;
726         }
727         if (IMDsetup->f[i][ZZ] != IMDsetup->old_forces[i][ZZ])
728         {
729             return TRUE;
730         }
731     }
732
733     /* All old and new forces are identical! */
734     return FALSE;
735 }
736
737
738 /*! \brief Fill the old_f_ind and old_forces arrays with the new, old values. */
739 static void keep_old_values(t_gmx_IMD_setup *IMDsetup)
740 {
741     int i;
742
743
744     IMDsetup->old_nforces = IMDsetup->nforces;
745
746     for (i = 0; i < IMDsetup->nforces; i++)
747     {
748         IMDsetup->old_f_ind[i] = IMDsetup->f_ind[i];
749         copy_rvec(IMDsetup->f[i], IMDsetup->old_forces[i]);
750     }
751 }
752
753
754 /*! \brief Returns TRUE if any component of the two rvecs differs. */
755 static gmx_inline gmx_bool rvecs_differ(const rvec v1, const rvec v2)
756 {
757     int i;
758
759
760     for (i = 0; i < DIM; i++)
761     {
762         if (v1[i] != v2[i])
763         {
764             return TRUE;
765         }
766     }
767
768     return FALSE;
769 }
770
771
772 /*! \brief Write the applied pull forces to logfile.
773  *
774  * Call on master only!
775  */
776 static void output_imd_forces(t_inputrec *ir, double time)
777 {
778     t_gmx_IMD_setup *IMDsetup;
779     int              i;
780
781
782     IMDsetup = ir->imd->setup;
783
784     if (bForcesChanged(IMDsetup))
785     {
786         /* Write time and total number of applied IMD forces */
787         fprintf(IMDsetup->outf, "%14.6e%6d", time, IMDsetup->nforces);
788
789         /* Write out the global atom indices of the pulled atoms and the forces itself,
790          * write out a force only if it has changed since the last output */
791         for (i = 0; i < IMDsetup->nforces; i++)
792         {
793             if (rvecs_differ(IMDsetup->f[i], IMDsetup->old_forces[i]))
794             {
795                 fprintf(IMDsetup->outf, "%9d", IMDsetup->ind[IMDsetup->f_ind[i]] + 1);
796                 fprintf(IMDsetup->outf, "%12.4e%12.4e%12.4e", IMDsetup->f[i][0], IMDsetup->f[i][1], IMDsetup->f[i][2]);
797             }
798         }
799         fprintf(IMDsetup->outf, "\n");
800
801         keep_old_values(IMDsetup);
802     }
803 }
804
805
806 /*! \brief Synchronize the nodes. */
807 static void imd_sync_nodes(t_inputrec *ir, t_commrec *cr, double t)
808 {
809     int              new_nforces = 0;
810     t_gmx_IMD_setup *IMDsetup;
811     int              start, end, i;
812
813
814     IMDsetup = ir->imd->setup;
815
816     /* Notify the other nodes whether we are still connected. */
817     if (PAR(cr))
818     {
819         block_bc(cr, IMDsetup->bConnected);
820     }
821
822     /* ...if not connected, the job is done here. */
823     if (!IMDsetup->bConnected)
824     {
825         return;
826     }
827
828     /* Let the other nodes know whether we got a new IMD synchronization frequency. */
829     if (PAR(cr))
830     {
831         block_bc(cr, IMDsetup->nstimd_new);
832     }
833
834     /* Now we all set the (new) nstimd communication time step */
835     IMDsetup->nstimd = IMDsetup->nstimd_new;
836
837     /* We're done if we don't allow pulling at all */
838     if (!(IMDsetup->bForceActivated))
839     {
840         return;
841     }
842
843     /* OK, let's check if we have received forces which we need to communicate
844      * to the other nodes */
845     if (MASTER(cr))
846     {
847         if (IMDsetup->bNewForces)
848         {
849             new_nforces = IMDsetup->vmd_nforces;
850         }
851         /* make the "new_forces" negative, when we did not receive new ones */
852         else
853         {
854             new_nforces = IMDsetup->vmd_nforces * -1;
855         }
856     }
857
858     /* make new_forces known to the clients */
859     if (PAR(cr))
860     {
861         block_bc(cr, new_nforces);
862     }
863
864     /* When new_natoms < 0 then we know that these are still the same forces
865      * so we don't communicate them, otherwise... */
866     if (new_nforces >= 0)
867     {
868         /* set local VMD and nforces */
869         IMDsetup->vmd_nforces = new_nforces;
870         IMDsetup->nforces     = IMDsetup->vmd_nforces;
871
872         /* now everybody knows the number of forces in f_ind, so we can prepare
873          * the target arrays for indices and forces */
874         imd_prepare_MD_Forces(IMDsetup);
875
876         /* we first update the MD forces on the master by converting the VMD forces */
877         if (MASTER(cr))
878         {
879             imd_copyto_MD_Forces(IMDsetup);
880             /* We also write out forces on every update, so that we know which
881              * forces are applied for every step */
882             if (IMDsetup->outf)
883             {
884                 output_imd_forces(ir, t);
885             }
886         }
887
888         /* In parallel mode we communicate the to-be-applied forces to the other nodes */
889         if (PAR(cr))
890         {
891             nblock_bc(cr, IMDsetup->nforces, IMDsetup->f_ind);
892             nblock_bc(cr, IMDsetup->nforces, IMDsetup->f    );
893         }
894
895         /* done communicating the forces, reset bNewForces */
896         IMDsetup->bNewForces = FALSE;
897     }
898 }
899
900
901 /*! \brief Reads header from the client and decides what to do. */
902 static void imd_readcommand(t_gmx_IMD_setup *IMDsetup)
903 {
904     gmx_bool       IMDpaused = FALSE;
905     IMDMessageType itype;
906
907
908     while (IMDsetup->clientsocket && (imdsock_tryread(IMDsetup->clientsocket, 0, 0) > 0 || IMDpaused))
909     {
910         itype = imd_recv_header(IMDsetup->clientsocket, &(IMDsetup->length));
911         /* let's see what we got: */
912         switch (itype)
913         {
914             /* IMD asks us to terminate the simulation, check if the user allowed this */
915             case IMD_KILL:
916                 if (IMDsetup->bTerminatable)
917                 {
918                     fprintf(stderr, " %s Terminating connection and running simulation (if supported by integrator).\n", IMDstr);
919                     IMDsetup->bTerminated = TRUE;
920                     IMDsetup->bWConnect   = FALSE;
921                     gmx_set_stop_condition(gmx_stop_cond_next);
922                 }
923                 else
924                 {
925                     fprintf(stderr, " %s Set -imdterm command line switch to allow mdrun termination from within IMD.\n", IMDstr);
926                 }
927
928                 break;
929
930             /* the client doen't want to talk to us anymore */
931             case IMD_DISCONNECT:
932                 fprintf(stderr, " %s Disconnecting client.\n", IMDstr);
933                 imd_disconnect(IMDsetup);
934                 break;
935
936             /* we got new forces, read them and set bNewForces flag */
937             case IMD_MDCOMM:
938                 imd_read_vmd_Forces(IMDsetup);
939                 IMDsetup->bNewForces = TRUE;
940                 break;
941
942             /* the client asks us to (un)pause the simulation. So we toggle the IMDpaused state */
943             case IMD_PAUSE:
944                 if (IMDpaused)
945                 {
946                     fprintf(stderr, " %s Un-pause command received.\n", IMDstr);
947                     IMDpaused = FALSE;
948                 }
949                 else
950                 {
951                     fprintf(stderr, " %s Pause command received.\n", IMDstr);
952                     IMDpaused = TRUE;
953                 }
954
955                 break;
956
957             /* the client sets a new transfer rate, if we get 0, we reset the rate
958              * to the default. VMD filters 0 however */
959             case IMD_TRATE:
960                 IMDsetup->nstimd_new = (IMDsetup->length > 0) ? IMDsetup->length : IMDsetup->nstimd_def;
961                 fprintf(stderr, " %s Update frequency will be set to %d.\n", IMDstr, IMDsetup->nstimd_new);
962                 break;
963
964             /* Catch all rule for the remaining IMD types which we don't expect */
965             default:
966                 fprintf(stderr, " %s Received unexpected %s.\n", IMDstr, ENUM_NAME((int)itype, IMD_NR, eIMDType_names));
967                 imd_fatal(IMDsetup, "Terminating connection\n");
968                 break;
969         } /* end switch */
970     }     /* end while  */
971 }
972
973
974 /*! \brief Open IMD output file and write header information.
975  *
976  * Call on master only.
977  */
978 static FILE *open_imd_out(
979         const char           *fn,
980         t_gmx_IMD_setup      *IMDsetup,
981         int                   nat_total,
982         output_env_t          oenv,
983         unsigned long         Flags)
984 {
985     FILE       *fp;
986
987
988     /* Open log file of applied IMD forces if requested */
989     if (fn && oenv)
990     {
991         /* If we append to an existing file, all the header information is already there */
992         if (Flags & MD_APPENDFILES)
993         {
994             fp = gmx_fio_fopen(fn, "a+");
995         }
996         else
997         {
998             fp = gmx_fio_fopen(fn, "w+");
999             if (IMDsetup->nat == nat_total)
1000             {
1001                 fprintf(fp, "# Note that you can select an IMD index group in the .mdp file if a subset of the atoms suffices.\n");
1002             }
1003
1004             xvgr_header(fp, "IMD Pull Forces", "Time (ps)", "# of Forces / Atom IDs / Forces (kJ/mol)", exvggtNONE, oenv);
1005
1006             fprintf(fp, "# Can display and manipulate %d (of a total of %d) atoms via IMD.\n", IMDsetup->nat, nat_total);
1007             fprintf(fp, "# column 1    : time (ps)\n");
1008             fprintf(fp, "# column 2    : total number of atoms feeling an IMD pulling force at that time\n");
1009             fprintf(fp, "# cols. 3.-6  : global atom number of pulled atom, x-force, y-force, z-force (kJ/mol)\n");
1010             fprintf(fp, "# then follow : atom-ID, f[x], f[y], f[z] for more atoms in case the force on multiple atoms is changed simultaneously.\n");
1011             fprintf(fp, "# Note that the force on any atom is always equal to the last value for that atom-ID found in the data.\n");
1012             fflush(fp);
1013         }
1014
1015         /* To reduce the output file size we remember the old values and output only
1016          * when something changed */
1017         snew(IMDsetup->old_f_ind, IMDsetup->nat);  /* One can never pull on more atoms */
1018         snew(IMDsetup->old_forces, IMDsetup->nat);
1019
1020         return fp;
1021     }
1022
1023     fprintf(stdout, "%s For a log of the IMD pull forces explicitly specify '-if' on the command line.\n"
1024             "%s (Not possible with energy minimization.)\n", IMDstr, IMDstr);
1025
1026     return NULL;
1027 }
1028 #endif
1029
1030
1031 extern void IMD_finalize(gmx_bool bIMD, t_IMD *imd)
1032 {
1033     if (bIMD)
1034     {
1035         if (imd->setup->outf)
1036         {
1037             gmx_fio_fclose(imd->setup->outf);
1038         }
1039     }
1040 }
1041
1042
1043 #ifdef GMX_IMD
1044 /*! \brief Creates the molecule start-end position array of molecules in the IMD group. */
1045 static void init_imd_prepare_mols_in_imdgroup(t_gmx_IMD_setup *IMDsetup, gmx_mtop_t *top_global)
1046 {
1047     int      i, ii;
1048     int      gstart, gend, count;
1049     t_block  gmols, lmols;
1050     int      nat;
1051     atom_id *ind;
1052
1053     gmols = top_global->mols;
1054     nat   = IMDsetup->nat;
1055     ind   = IMDsetup->ind;
1056
1057     lmols.nr = 0;
1058
1059     /* check whether index is sorted */
1060     for (i = 0; i < nat-1; i++)
1061     {
1062         if (ind[i] > ind[i+1])
1063         {
1064             gmx_fatal(FARGS, "%s IMD index is not sorted. This is currently not supported.\n", IMDstr);
1065         }
1066     }
1067
1068     snew(lmols.index, gmols.nr+1);
1069     lmols.index[0] = 0;
1070
1071     for (i = 0; i < gmols.nr; i++)
1072     {
1073         gstart = gmols.index[i];
1074         gend   = gmols.index[i+1];
1075         count  = 0;
1076         for (ii = 0; ii < nat; ii++)
1077         {
1078             if ((ind[ii] >= gstart) && (ind[ii] < gend))
1079             {
1080                 count += 1;
1081             }
1082         }
1083         if (count > 0)
1084         {
1085             lmols.index[lmols.nr+1] = lmols.index[lmols.nr]+count;
1086             lmols.nr               += 1;
1087         }
1088     }
1089     srenew(lmols.index, lmols.nr+1);
1090     lmols.nalloc_index = lmols.nr+1;
1091     IMDsetup->mols     = lmols;
1092 }
1093
1094
1095 /*! \brief Copied and modified from groupcoord.c shift_positions_group(). */
1096 static void shift_positions(
1097         matrix box,
1098         rvec   x[],      /* The positions [0..nr] */
1099         ivec   is,       /* The shift [0..nr] */
1100         int    nr)       /* The number of positions */
1101 {
1102     int      i, tx, ty, tz;
1103
1104     /* Loop over the group's atoms */
1105     if (TRICLINIC(box))
1106     {
1107         for (i = 0; i < nr; i++)
1108         {
1109             tx = is[XX];
1110             ty = is[YY];
1111             tz = is[ZZ];
1112
1113             x[i][XX] = x[i][XX]-tx*box[XX][XX]-ty*box[YY][XX]-tz*box[ZZ][XX];
1114             x[i][YY] = x[i][YY]-ty*box[YY][YY]-tz*box[ZZ][YY];
1115             x[i][ZZ] = x[i][ZZ]-tz*box[ZZ][ZZ];
1116         }
1117     }
1118     else
1119     {
1120         for (i = 0; i < nr; i++)
1121         {
1122             tx = is[XX];
1123             ty = is[YY];
1124             tz = is[ZZ];
1125
1126             x[i][XX] = x[i][XX]-tx*box[XX][XX];
1127             x[i][YY] = x[i][YY]-ty*box[YY][YY];
1128             x[i][ZZ] = x[i][ZZ]-tz*box[ZZ][ZZ];
1129         }
1130     }
1131 }
1132
1133
1134 /*! \brief Removes shifts of molecules diffused outside of the box. */
1135 static void imd_remove_molshifts(t_gmx_IMD_setup *IMDsetup, matrix box)
1136 {
1137     int     i, ii, molsize;
1138     ivec    largest, smallest, shift;
1139     t_block mols;
1140
1141
1142     mols = IMDsetup->mols;
1143
1144     /* for each molecule also present in IMD group */
1145     for (i = 0; i < mols.nr; i++)
1146     {
1147         /* first we determine the minimum and maximum shifts for each molecule */
1148
1149         clear_ivec(largest);
1150         clear_ivec(smallest);
1151         clear_ivec(shift);
1152
1153         copy_ivec(IMDsetup->xa_shifts[mols.index[i]], largest);
1154         copy_ivec(IMDsetup->xa_shifts[mols.index[i]], smallest);
1155
1156         for (ii = mols.index[i]+1; ii < mols.index[i+1]; ii++)
1157         {
1158             if (IMDsetup->xa_shifts[ii][XX] > largest[XX])
1159             {
1160                 largest[XX]  = IMDsetup->xa_shifts[ii][XX];
1161             }
1162             if (IMDsetup->xa_shifts[ii][XX] < smallest[XX])
1163             {
1164                 smallest[XX] = IMDsetup->xa_shifts[ii][XX];
1165             }
1166
1167             if (IMDsetup->xa_shifts[ii][YY] > largest[YY])
1168             {
1169                 largest[YY]  = IMDsetup->xa_shifts[ii][YY];
1170             }
1171             if (IMDsetup->xa_shifts[ii][YY] < smallest[YY])
1172             {
1173                 smallest[YY] = IMDsetup->xa_shifts[ii][YY];
1174             }
1175
1176             if (IMDsetup->xa_shifts[ii][ZZ] > largest[ZZ])
1177             {
1178                 largest[ZZ]  = IMDsetup->xa_shifts[ii][ZZ];
1179             }
1180             if (IMDsetup->xa_shifts[ii][ZZ] < smallest[ZZ])
1181             {
1182                 smallest[ZZ] = IMDsetup->xa_shifts[ii][ZZ];
1183             }
1184
1185         }
1186
1187         /* check if we what we can subtract/add to the positions
1188          * to put them back into the central box */
1189         if (smallest[XX] > 0)
1190         {
1191             shift[XX] = smallest[XX];
1192         }
1193         if (smallest[YY] > 0)
1194         {
1195             shift[YY] = smallest[YY];
1196         }
1197         if (smallest[ZZ] > 0)
1198         {
1199             shift[ZZ] = smallest[ZZ];
1200         }
1201
1202         if (largest[XX] < 0)
1203         {
1204             shift[XX] = largest[XX];
1205         }
1206         if (largest[YY] < 0)
1207         {
1208             shift[YY] = largest[YY];
1209         }
1210         if (largest[ZZ] < 0)
1211         {
1212             shift[ZZ] = largest[ZZ];
1213         }
1214
1215         /* is there a shift at all? */
1216         if ((shift[XX]) || (shift[YY]) || (shift[ZZ]))
1217         {
1218             molsize = mols.index[i+1]-mols.index[i];
1219             /* shift the positions */
1220             shift_positions(box, &(IMDsetup->xa[mols.index[i]]), shift, molsize);
1221         }
1222
1223     }
1224 }
1225
1226
1227 /*! \brief Initialize arrays used to assemble the positions from the other nodes. */
1228 static void init_imd_prepare_for_x_assembly(t_commrec *cr, rvec x[], t_gmx_IMD_setup *IMDsetup)
1229 {
1230     int i, ii;
1231
1232
1233     snew(IMDsetup->xa,         IMDsetup->nat);
1234     snew(IMDsetup->xa_ind,     IMDsetup->nat);
1235     snew(IMDsetup->xa_shifts,  IMDsetup->nat);
1236     snew(IMDsetup->xa_eshifts, IMDsetup->nat);
1237     snew(IMDsetup->xa_old,     IMDsetup->nat);
1238
1239     /* Save the original (whole) set of positions such that later the
1240      * molecule can always be made whole again */
1241     if (MASTER(cr))
1242     {
1243         for (i = 0; i < IMDsetup->nat; i++)
1244         {
1245             ii = IMDsetup->ind[i];
1246             copy_rvec(x[ii], IMDsetup->xa_old[i]);
1247         }
1248     }
1249
1250     if (!PAR(cr))
1251     {
1252         IMDsetup->nat_loc = IMDsetup->nat;
1253         IMDsetup->ind_loc = IMDsetup->ind;
1254
1255         /* xa_ind[i] needs to be set to i for serial runs */
1256         for (i = 0; i < IMDsetup->nat; i++)
1257         {
1258             IMDsetup->xa_ind[i] = i;
1259         }
1260     }
1261
1262     /* Communicate initial coordinates xa_old to all processes */
1263 #ifdef GMX_MPI
1264     if (PAR(cr))
1265     {
1266         gmx_bcast(IMDsetup->nat * sizeof(IMDsetup->xa_old[0]), IMDsetup->xa_old, cr);
1267     }
1268 #endif
1269 }
1270 #endif
1271
1272
1273 /*! \brief Check for non-working integrator / parallel options. */
1274 static void imd_check_integrator_parallel(t_inputrec *ir, t_commrec *cr)
1275 {
1276     if (PAR(cr))
1277     {
1278         if (((ir->eI) == eiSteep) || ((ir->eI) == eiCG) || ((ir->eI) == eiLBFGS) || ((ir->eI) == eiNM))
1279         {
1280             gmx_fatal(FARGS, "%s Energy minimization via steep, CG, lbfgs and nm in parallel is currently not supported by IMD.\n", IMDstr);
1281             return;
1282         }
1283     }
1284 }
1285
1286
1287 extern void init_IMD(
1288         t_inputrec    *ir,
1289         t_commrec     *cr,
1290         gmx_mtop_t    *top_global,
1291         FILE          *fplog,
1292         int            defnstimd,
1293         rvec           x[],
1294         int            nfile,
1295         const t_filenm fnm[],
1296         output_env_t   oenv,
1297         int            imdport,
1298         unsigned long  Flags)
1299 {
1300     int              i;
1301     int              nat_total;
1302     t_gmx_IMD_setup *IMDsetup;
1303     gmx_int32_t      bufxsize;
1304     gmx_bool         bIMD = FALSE;
1305
1306
1307     /* We will allow IMD sessions only if explicitly enabled in the .tpr file */
1308     if (FALSE == ir->bIMD)
1309     {
1310         return;
1311     }
1312
1313     /* It seems we have a .tpr file that defines an IMD group and thus allows IMD sessions.
1314      * Check whether we can actually provide the IMD functionality for this setting: */
1315     if (MASTER(cr))
1316     {
1317         /* Check whether IMD was enabled by one of the command line switches: */
1318         if ((Flags & MD_IMDWAIT) || (Flags & MD_IMDTERM) || (Flags & MD_IMDPULL))
1319         {
1320             /* Multiple simulations or replica exchange */
1321             if (MULTISIM(cr))
1322             {
1323                 fprintf(stderr, "%s Cannot use IMD for multiple simulations or replica exchange.\n", IMDstr);
1324             }
1325             /* OK, IMD seems to be allowed and turned on... */
1326             else
1327             {
1328                 fprintf(stderr, "%s Enabled. This simulation will accept incoming IMD connections.\n", IMDstr);
1329                 bIMD = TRUE;
1330             }
1331         }
1332         else
1333         {
1334             fprintf(stderr, "%s None of the -imd switches was used.\n"
1335                     "%s This run will not accept incoming IMD connections\n", IMDstr, IMDstr);
1336         }
1337     } /* end master only */
1338
1339     /* Disable IMD if not all the needed functionality is there! */
1340 #if defined(GMX_NATIVE_WINDOWS) && !defined(GMX_HAVE_WINSOCK)
1341     bIMD = FALSE;
1342     fprintf(stderr, "Disabling IMD because the winsock library was not found at compile time.\n");
1343 #endif
1344
1345     /* Let the other nodes know whether we want IMD */
1346     if (PAR(cr))
1347     {
1348         block_bc(cr, bIMD);
1349     }
1350     /* ... and update our local inputrec accordingly. */
1351     ir->bIMD = bIMD;
1352
1353     /*... if not we are done.*/
1354     if (!ir->bIMD)
1355     {
1356         return;
1357     }
1358
1359
1360     /* check if we're using a sane integrator / parallel combination */
1361     imd_check_integrator_parallel(ir, cr);
1362
1363
1364     /*******************************************************/
1365     /** From here on we assume that IMD is turned on      **/
1366     /*******************************************************/
1367
1368 #ifdef GMX_IMD
1369     nat_total = top_global->natoms;
1370
1371     /* Initialize IMD setup structure. If we read in a pre-IMD .tpr file, imd->nat
1372      * will be zero. For those cases we transfer _all_ atomic positions */
1373     ir->imd->setup = imd_create(ir->imd->nat > 0 ? ir->imd->nat : nat_total,
1374                                 defnstimd, imdport);
1375     IMDsetup       = ir->imd->setup;
1376
1377     /* We might need to open an output file for IMD forces data */
1378     if (MASTER(cr))
1379     {
1380         IMDsetup->outf = open_imd_out(opt2fn("-if", nfile, fnm), ir->imd->setup, nat_total, oenv, Flags);
1381     }
1382
1383     /* Make sure that we operate with a valid atom index array for the IMD atoms */
1384     if (ir->imd->nat > 0)
1385     {
1386         /* Point to the user-supplied array of atom numbers */
1387         IMDsetup->ind = ir->imd->ind;
1388     }
1389     else
1390     {
1391         /* Make a dummy (ind[i] = i) array of all atoms */
1392         snew(IMDsetup->ind, nat_total);
1393         for (i = 0; i < nat_total; i++)
1394         {
1395             IMDsetup->ind[i] = i;
1396         }
1397     }
1398
1399     /* read environment on master and prepare socket for incoming connections */
1400     if (MASTER(cr))
1401     {
1402         /* we allocate memory for our IMD energy structure */
1403         gmx_int32_t recsize = HEADERSIZE + sizeof(IMDEnergyBlock);
1404         snew(IMDsetup->energysendbuf, recsize);
1405
1406         /* Shall we wait for a connection? */
1407         if (Flags & MD_IMDWAIT)
1408         {
1409             IMDsetup->bWConnect = TRUE;
1410             fprintf(stderr, "%s Pausing simulation while no IMD connection present (-imdwait).\n", IMDstr);
1411         }
1412
1413         /* Will the IMD clients be able to terminate the simulation? */
1414         if (Flags & MD_IMDTERM)
1415         {
1416             IMDsetup->bTerminatable = TRUE;
1417             fprintf(stderr, "%s Allow termination of the simulation from IMD client (-imdterm).\n", IMDstr);
1418         }
1419
1420         /* Is pulling from IMD client allowed? */
1421         if (Flags & MD_IMDPULL)
1422         {
1423             IMDsetup->bForceActivated = TRUE;
1424             fprintf(stderr, "%s Pulling from IMD remote is enabled (-imdpull).\n", IMDstr);
1425         }
1426
1427         /* Initialize send buffers with constant size */
1428         snew(IMDsetup->sendxbuf, IMDsetup->nat);
1429         snew(IMDsetup->energies, 1);
1430         bufxsize = HEADERSIZE + 3 * sizeof(float) * IMDsetup->nat;
1431         snew(IMDsetup->coordsendbuf, bufxsize);
1432     }
1433
1434     /* do we allow interactive pulling? If so let the other nodes know. */
1435     if (PAR(cr))
1436     {
1437         block_bc(cr, IMDsetup->bForceActivated);
1438     }
1439
1440     /* setup the listening socket on master process */
1441     if (MASTER(cr))
1442     {
1443         fprintf(fplog, "%s Setting port for connection requests to %d.\n", IMDstr, IMDsetup->port);
1444         fprintf(stderr, "%s Turning on IMD - port for incoming requests is %d.\n", IMDstr, IMDsetup->port);
1445         imd_prepare_master_socket(IMDsetup);
1446         /* Wait until we have a connection if specified before */
1447         if (IMDsetup->bWConnect)
1448         {
1449             imd_blockconnect(IMDsetup);
1450         }
1451         else
1452         {
1453             fprintf(stderr, "%s -imdwait not set, starting simulation.\n", IMDstr);
1454         }
1455     }
1456     /* Let the other nodes know whether we are connected */
1457     imd_sync_nodes(ir, cr, 0);
1458
1459     /* Initialize arrays used to assemble the positions from the other nodes */
1460     init_imd_prepare_for_x_assembly(cr, x, IMDsetup);
1461
1462     /* Initialize molecule blocks to make them whole later...*/
1463     if (MASTER(cr))
1464     {
1465         init_imd_prepare_mols_in_imdgroup(IMDsetup, top_global);
1466     }
1467 #else
1468     gmx_incons("init_IMD: this GROMACS version was not compiled with IMD support!");
1469 #endif
1470 }
1471
1472
1473 extern gmx_bool do_IMD(
1474         gmx_bool        bIMD,
1475         gmx_int64_t     step,
1476         t_commrec      *cr,
1477         gmx_bool        bNS,
1478         matrix          box,
1479         rvec            x[],
1480         t_inputrec     *ir,
1481         double          t,
1482         gmx_wallcycle_t wcycle)
1483 {
1484     gmx_bool         imdstep = FALSE;
1485     t_gmx_IMD_setup *IMDsetup;
1486
1487
1488     /* IMD at all? */
1489     if (!bIMD)
1490     {
1491         return FALSE;
1492     }
1493
1494 #ifdef GMX_IMD
1495     wallcycle_start(wcycle, ewcIMD);
1496
1497     IMDsetup = ir->imd->setup;
1498
1499     /* read command from client and check if new incoming connection */
1500     if (MASTER(cr))
1501     {
1502         /* If not already connected, check for new connections */
1503         if (!IMDsetup->clientsocket)
1504         {
1505             if (IMDsetup->bWConnect)
1506             {
1507                 imd_blockconnect(IMDsetup);
1508             }
1509             else
1510             {
1511                 imd_tryconnect(IMDsetup);
1512             }
1513         }
1514
1515         /* Let's see if we have new IMD messages for us */
1516         if (IMDsetup->clientsocket)
1517         {
1518             imd_readcommand(IMDsetup);
1519         }
1520     }
1521
1522     /* is this an IMD communication step? */
1523     imdstep = do_per_step(step, IMDsetup->nstimd);
1524
1525     /* OK so this is an IMD step ... */
1526     if (imdstep)
1527     {
1528         /* First we sync all nodes to let everybody know whether we are connected to VMD */
1529         imd_sync_nodes(ir, cr, t);
1530     }
1531
1532     /* If a client is connected, we collect the positions
1533      * and put molecules back into the box before transfer */
1534     if ((imdstep && IMDsetup->bConnected)
1535         || bNS)            /* independent of imdstep, we communicate positions at each NS step */
1536     {
1537         /* Transfer the IMD positions to the master node. Every node contributes
1538          * its local positions x and stores them in the assembled xa array. */
1539         communicate_group_positions(cr, IMDsetup->xa, IMDsetup->xa_shifts, IMDsetup->xa_eshifts,
1540                                     TRUE, x, IMDsetup->nat, IMDsetup->nat_loc,
1541                                     IMDsetup->ind_loc, IMDsetup->xa_ind, IMDsetup->xa_old, box);
1542
1543         /* If connected and master -> remove shifts */
1544         if ((imdstep && IMDsetup->bConnected) && MASTER(cr))
1545         {
1546             imd_remove_molshifts(IMDsetup, box);
1547         }
1548     }
1549
1550     wallcycle_stop(wcycle, ewcIMD);
1551 #else
1552     gmx_incons("do_IMD called without IMD support!");
1553 #endif
1554
1555     return imdstep;
1556 }
1557
1558
1559 extern void IMD_fill_energy_record(gmx_bool bIMD, t_IMD *imd, gmx_enerdata_t *enerd,
1560                                    gmx_int64_t step, gmx_bool bHaveNewEnergies)
1561 {
1562     IMDEnergyBlock *ene;
1563     t_gmx_IMD       IMDsetup;
1564
1565
1566     if (bIMD)
1567     {
1568 #ifdef GMX_IMD
1569         IMDsetup = imd->setup;
1570
1571         if (IMDsetup->clientsocket)
1572         {
1573             ene = IMDsetup->energies;
1574
1575             ene->tstep = step;
1576
1577             /* In MPI-parallel simulations the energies are not accessible a at every time step.
1578              * We update them if we have new values, otherwise, the energy values from the
1579              * last global communication step are still on display in the viewer. */
1580             if (bHaveNewEnergies)
1581             {
1582                 ene->T_abs   = (float)  enerd->term[F_TEMP   ];
1583                 ene->E_pot   = (float)  enerd->term[F_EPOT   ];
1584                 ene->E_tot   = (float)  enerd->term[F_ETOT   ];
1585                 ene->E_bond  = (float)  enerd->term[F_BONDS  ];
1586                 ene->E_angle = (float)  enerd->term[F_ANGLES ];
1587                 ene->E_dihe  = (float)  enerd->term[F_PDIHS  ];
1588                 ene->E_impr  = (float)  enerd->term[F_IDIHS  ];
1589                 ene->E_vdw   = (float)  enerd->term[F_LJ     ];
1590                 ene->E_coul  = (float) (enerd->term[F_COUL_SR] + enerd->term[F_COUL_LR]);
1591             }
1592         }
1593 #else
1594         gmx_incons("IMD_fill_energy_record called without IMD support.");
1595 #endif
1596     }
1597 }
1598
1599
1600 extern void IMD_send_positions(t_IMD *imd)
1601 {
1602 #ifdef GMX_IMD
1603     t_gmx_IMD IMDsetup;
1604
1605
1606     IMDsetup = imd->setup;
1607
1608     if (IMDsetup->clientsocket)
1609     {
1610
1611         if (imd_send_energies(IMDsetup->clientsocket, IMDsetup->energies, IMDsetup->energysendbuf))
1612         {
1613             imd_fatal(IMDsetup, "Error sending updated energies. Disconnecting client.\n");
1614         }
1615
1616         if (imd_send_rvecs(IMDsetup->clientsocket, IMDsetup->nat, IMDsetup->xa, IMDsetup->coordsendbuf))
1617         {
1618             imd_fatal(IMDsetup, "Error sending updated positions. Disconnecting client.\n");
1619         }
1620     }
1621 #else
1622     gmx_incons("IMD_send_positions called without IMD support.");
1623 #endif
1624 }
1625
1626
1627 extern void IMD_prep_energies_send_positions(gmx_bool bIMD, gmx_bool bIMDstep,
1628                                              t_IMD *imd, gmx_enerdata_t *enerd,
1629                                              gmx_int64_t step, gmx_bool bHaveNewEnergies,
1630                                              gmx_wallcycle_t wcycle)
1631 {
1632     if (bIMD)
1633     {
1634 #ifdef GMX_IMD
1635         wallcycle_start(wcycle, ewcIMD);
1636
1637         /* Update time step for IMD and prepare IMD energy record if we have new energies. */
1638         IMD_fill_energy_record(TRUE, imd, enerd, step, bHaveNewEnergies);
1639
1640         if (bIMDstep)
1641         {
1642             /* Send positions and energies to VMD client via IMD */
1643             IMD_send_positions(imd);
1644         }
1645
1646         wallcycle_stop(wcycle, ewcIMD);
1647 #else
1648         gmx_incons("IMD_prep_energies_send_positions called without IMD support.");
1649 #endif
1650     }
1651 }
1652
1653
1654 extern int IMD_get_step(t_gmx_IMD IMDsetup)
1655 {
1656     return IMDsetup->nstimd;
1657 }
1658
1659
1660 extern void IMD_apply_forces(gmx_bool bIMD, t_IMD *imd, t_commrec *cr, rvec *f,
1661                              gmx_wallcycle_t wcycle)
1662 {
1663     int              i, j;
1664     int              locndx;
1665     t_gmx_IMD_setup *IMDsetup;
1666
1667
1668     if (bIMD)
1669     {
1670 #ifdef GMX_IMD
1671         wallcycle_start(wcycle, ewcIMD);
1672
1673         IMDsetup = imd->setup;
1674
1675         /* Are forces allowed at all? If not we're done */
1676         if (!IMDsetup->bForceActivated)
1677         {
1678             return;
1679         }
1680
1681         for (i = 0; i < IMDsetup->nforces; i++)
1682         {
1683             /* j are the indices in the "System group".*/
1684             j = IMDsetup->ind[IMDsetup->f_ind[i]];
1685
1686             /* check if this is a local atom and find out locndx */
1687             if (PAR(cr) && ga2la_get_home(cr->dd->ga2la, j, &locndx))
1688             {
1689                 j = locndx;
1690             }
1691
1692             rvec_inc(f[j], IMDsetup->f[i]);
1693         }
1694
1695         wallcycle_start(wcycle, ewcIMD);
1696 #else
1697         gmx_incons("IMD_apply_forces called without IMD support.");
1698 #endif
1699     }
1700 }