imdclient 0.1.1__py3-none-any.whl → 0.1.3__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (32) hide show
  1. imdclient/{IMDREADER.py → IMD.py} +16 -15
  2. imdclient/IMDClient.py +146 -71
  3. imdclient/data/gromacs/md/gromacs_v3_nst8.mdp +58 -0
  4. imdclient/data/lammps/md/{lammps_v3.in → lammps_v3_nst_1.in} +3 -3
  5. imdclient/data/lammps/md/lammps_v3_nst_8.in +71 -0
  6. imdclient/data/namd/md/{namd_v3.namd → namd_v3_nst_1.namd} +17 -5
  7. imdclient/data/namd/md/namd_v3_nst_8.namd +59 -0
  8. imdclient/tests/base.py +133 -45
  9. imdclient/tests/conftest.py +14 -10
  10. imdclient/tests/datafiles.py +17 -9
  11. imdclient/tests/docker_testing/docker.md +25 -0
  12. imdclient/tests/test_gromacs.py +32 -10
  13. imdclient/tests/test_imdclient.py +51 -0
  14. imdclient/tests/test_imdreader.py +20 -6
  15. imdclient/tests/test_lammps.py +57 -12
  16. imdclient/tests/test_manual.py +52 -29
  17. imdclient/tests/test_namd.py +101 -14
  18. imdclient/tests/test_stream_analysis.py +2 -2
  19. imdclient/tests/utils.py +0 -1
  20. imdclient/utils.py +8 -8
  21. imdclient-0.1.3.dist-info/LICENSE +5 -0
  22. {imdclient-0.1.1.dist-info → imdclient-0.1.3.dist-info}/METADATA +21 -32
  23. imdclient-0.1.3.dist-info/RECORD +42 -0
  24. {imdclient-0.1.1.dist-info → imdclient-0.1.3.dist-info}/WHEEL +1 -1
  25. imdclient/data/gromacs/md/gromacs_v3_nst1.tpr +0 -0
  26. imdclient/data/gromacs/md/gromacs_v3_nst1.trr +0 -0
  27. imdclient/data/lammps/md/lammps_trj.h5md +0 -0
  28. imdclient/data/namd/md/alanin.dcd +0 -0
  29. imdclient-0.1.1.dist-info/LICENSE +0 -21
  30. imdclient-0.1.1.dist-info/RECORD +0 -42
  31. {imdclient-0.1.1.dist-info → imdclient-0.1.3.dist-info}/AUTHORS.md +0 -0
  32. {imdclient-0.1.1.dist-info → imdclient-0.1.3.dist-info}/top_level.txt +0 -0
@@ -24,6 +24,17 @@ logger = logging.getLogger("imdclient.IMDClient")
24
24
  class IMDReader(StreamReaderBase):
25
25
  """
26
26
  Reader for IMD protocol packets.
27
+
28
+ Parameters
29
+ ----------
30
+ filename : a string of the form "host:port" where host is the hostname
31
+ or IP address of the listening GROMACS server and port
32
+ is the port number.
33
+ n_atoms : int (optional)
34
+ number of atoms in the system. defaults to number of atoms
35
+ in the topology. don't set this unless you know what you're doing.
36
+ kwargs : dict (optional)
37
+ keyword arguments passed to the constructed :class:`IMDClient`
27
38
  """
28
39
 
29
40
  format = "IMD"
@@ -37,17 +48,6 @@ class IMDReader(StreamReaderBase):
37
48
  n_atoms=None,
38
49
  **kwargs,
39
50
  ):
40
- """
41
- Parameters
42
- ----------
43
- filename : a string of the form "host:port" where host is the hostname
44
- or IP address of the listening GROMACS server and port
45
- is the port number.
46
- n_atoms : int (optional)
47
- number of atoms in the system. defaults to number of atoms
48
- in the topology. don't set this unless you know what you're doing.
49
- """
50
-
51
51
  super(IMDReader, self).__init__(filename, **kwargs)
52
52
 
53
53
  logger.debug("IMDReader initializing")
@@ -83,9 +83,8 @@ class IMDReader(StreamReaderBase):
83
83
 
84
84
  try:
85
85
  imdf = self._imdclient.get_imdframe()
86
- except EOFError:
87
- # Not strictly necessary, but for clarity
88
- raise StopIteration
86
+ except EOFError as e:
87
+ raise e
89
88
 
90
89
  self._frame = frame
91
90
  self._load_imdframe_into_ts(imdf)
@@ -101,7 +100,9 @@ class IMDReader(StreamReaderBase):
101
100
  self.ts.data["dt"] = imdf.dt
102
101
  self.ts.data["step"] = imdf.step
103
102
  if imdf.energies is not None:
104
- self.ts.data.update(imdf.energies)
103
+ self.ts.data.update(
104
+ {k: v for k, v in imdf.energies.items() if k != "step"}
105
+ )
105
106
  if imdf.box is not None:
106
107
  self.ts.dimensions = core.triclinic_box(*imdf.box)
107
108
  if imdf.positions is not None:
imdclient/IMDClient.py CHANGED
@@ -25,11 +25,31 @@ import time
25
25
  import numpy as np
26
26
  from typing import Union, Dict
27
27
  import signal
28
+ import atexit
28
29
 
29
30
  logger = logging.getLogger(__name__)
30
31
 
31
32
 
32
33
  class IMDClient:
34
+ """
35
+ Parameters
36
+ ----------
37
+ host : str
38
+ Hostname of the server
39
+ port : int
40
+ Port number of the server
41
+ n_atoms : int
42
+ Number of atoms in the simulation
43
+ socket_bufsize : int, (optional)
44
+ Size of the socket buffer in bytes. Default is to use the system default
45
+ buffer_size : int (optional)
46
+ IMDFramebuffer will be filled with as many :class:`IMDFrame` fit in `buffer_size` bytes [``10MB``]
47
+ timeout : int, optional
48
+ Timeout for the socket in seconds [``5``]
49
+ **kwargs : dict (optional)
50
+ Additional keyword arguments to pass to the :class:`BaseIMDProducer` and :class:`IMDFrameBuffer`
51
+ """
52
+
33
53
  def __init__(
34
54
  self,
35
55
  host,
@@ -39,22 +59,7 @@ class IMDClient:
39
59
  multithreaded=True,
40
60
  **kwargs,
41
61
  ):
42
- """
43
- Parameters
44
- ----------
45
- host : str
46
- Hostname of the server
47
- port : int
48
- Port number of the server
49
- n_atoms : int
50
- Number of atoms in the simulation
51
- socket_bufsize : int, optional
52
- Size of the socket buffer in bytes. Default is to use the system default
53
- buffer_size : int, optional
54
- IMDFramebuffer will be filled with as many IMDFrames fit in `buffer_size` [``10MB``]
55
- **kwargs : optional
56
- Additional keyword arguments to pass to the IMDProducer and IMDFrameBuffer
57
- """
62
+
58
63
  self._stopped = False
59
64
  self._conn = self._connect_to_server(host, port, socket_bufsize)
60
65
  self._imdsinfo = self._await_IMD_handshake()
@@ -66,8 +71,10 @@ class IMDClient:
66
71
  n_atoms,
67
72
  **kwargs,
68
73
  )
74
+ self._error_queue = queue.Queue()
69
75
  else:
70
76
  self._buf = None
77
+ self._error_queue = None
71
78
  if self._imdsinfo.version == 2:
72
79
  self._producer = IMDProducerV2(
73
80
  self._conn,
@@ -75,6 +82,7 @@ class IMDClient:
75
82
  self._imdsinfo,
76
83
  n_atoms,
77
84
  multithreaded,
85
+ self._error_queue,
78
86
  **kwargs,
79
87
  )
80
88
  elif self._imdsinfo.version == 3:
@@ -84,23 +92,60 @@ class IMDClient:
84
92
  self._imdsinfo,
85
93
  n_atoms,
86
94
  multithreaded,
95
+ self._error_queue,
87
96
  **kwargs,
88
97
  )
89
98
 
90
99
  self._go()
91
100
 
92
101
  if self._multithreaded:
102
+ # Disconnect MUST occur. This covers typical cases (Python, IPython interpreter)
93
103
  signal.signal(signal.SIGINT, self.signal_handler)
104
+ signal.signal(signal.SIGTERM, self.signal_handler)
105
+
106
+ # Disconnect and socket shutdown MUST occur. This covers Jupyter use
107
+ # since in jupyter, the signal handler is reset to the default
108
+ # by pre- and post- hooks
109
+ # https://stackoverflow.com/questions/70841648/jupyter-reverts-signal-handler-to-default-when-running-next-cell
110
+ try:
111
+ import IPython
112
+ except ImportError:
113
+ has_ipython = False
114
+ else:
115
+ has_ipython = True
116
+
117
+ if has_ipython:
118
+ try:
119
+ from IPython import get_ipython
120
+
121
+ if get_ipython() is not None:
122
+ kernel = get_ipython().kernel
123
+ kernel.pre_handler_hook = lambda: None
124
+ kernel.post_handler_hook = lambda: None
125
+ logger.debug("Running in Jupyter")
126
+ except NameError:
127
+ logger.debug("Running in non-jupyter IPython environment")
128
+
129
+ # Final case: error is raised outside of IMDClient code
130
+ logger.debug("Registering atexit")
131
+ atexit.register(self.stop)
132
+
94
133
  self._producer.start()
95
134
 
96
135
  def signal_handler(self, sig, frame):
97
136
  """Catch SIGINT to allow clean shutdown on CTRL+C
98
137
  This also ensures that main thread execution doesn't get stuck
99
138
  waiting in buf.pop_full_imdframe()"""
139
+ logger.debug("Intercepted signal")
100
140
  self.stop()
141
+ logger.debug("Shutdown success")
101
142
 
102
143
  def get_imdframe(self):
103
144
  """
145
+ Returns
146
+ -------
147
+ IMDFrame
148
+ The next frame from the IMD server
104
149
  Raises
105
150
  ------
106
151
  EOFError
@@ -114,6 +159,9 @@ class IMDClient:
114
159
  # and doesn't need to be notified
115
160
  self._disconnect()
116
161
  self._stopped = True
162
+
163
+ if self._error_queue.qsize():
164
+ raise EOFError(f"{self._error_queue.get()}")
117
165
  raise EOFError
118
166
  else:
119
167
  try:
@@ -123,14 +171,23 @@ class IMDClient:
123
171
  raise EOFError
124
172
 
125
173
  def get_imdsessioninfo(self):
174
+ """
175
+ Returns
176
+ -------
177
+ IMDSessionInfo
178
+ Information about the IMD session
179
+ """
126
180
  return self._imdsinfo
127
181
 
128
182
  def stop(self):
183
+ """
184
+ Stop the client and close the connection
185
+ """
129
186
  if self._multithreaded:
130
187
  if not self._stopped:
131
- self._buf.notify_consumer_finished()
132
- self._disconnect()
133
188
  self._stopped = True
189
+ self._disconnect()
190
+ self._buf.notify_consumer_finished()
134
191
  else:
135
192
  self._disconnect()
136
193
 
@@ -144,9 +201,7 @@ class IMDClient:
144
201
  # /proc/sys/net/core/rmem_default
145
202
  # Max (linux):
146
203
  # /proc/sys/net/core/rmem_max
147
- conn.setsockopt(
148
- socket.SOL_SOCKET, socket.SO_RCVBUF, socket_bufsize
149
- )
204
+ conn.setsockopt(socket.SOL_SOCKET, socket.SO_RCVBUF, socket_bufsize)
150
205
  try:
151
206
  logger.debug(f"IMDClient: Connecting to {host}:{port}")
152
207
  conn.connect((host, port))
@@ -252,8 +307,37 @@ class IMDClient:
252
307
  finally:
253
308
  self._conn.close()
254
309
 
310
+ def __enter__(self):
311
+ return self
312
+
313
+ def __exit__(self, exc_type, exc_val, exc_tb):
314
+ self.stop()
315
+ return False
316
+
255
317
 
256
318
  class BaseIMDProducer(threading.Thread):
319
+ """
320
+
321
+ Parameters
322
+ ----------
323
+ conn : socket.socket
324
+ Connection object to the server
325
+ buffer : IMDFrameBuffer
326
+ Buffer object to hold IMD frames. If `multithreaded` is False, this
327
+ argument is ignored
328
+ sinfo : IMDSessionInfo
329
+ Information about the IMD session
330
+ n_atoms : int
331
+ Number of atoms in the simulation
332
+ multithreaded : bool
333
+ If True, socket interaction will occur in a separate thread &
334
+ frames will be buffered. Single-threaded, blocking IMDClient
335
+ should only be used in testing
336
+ error_queue: queue.Queue
337
+ Queue to hold errors produced by the producer thread
338
+ timeout : int, optional
339
+ Timeout for the socket in seconds [``5``]
340
+ """
257
341
 
258
342
  def __init__(
259
343
  self,
@@ -261,33 +345,17 @@ class BaseIMDProducer(threading.Thread):
261
345
  buffer,
262
346
  sinfo,
263
347
  n_atoms,
264
- multithreaded=True,
348
+ multithreaded,
349
+ error_queue,
265
350
  timeout=5,
266
351
  **kwargs,
267
352
  ):
268
- """
269
- Parameters
270
- ----------
271
- conn : socket.socket
272
- Connection object to the server
273
- buffer : IMDFrameBuffer
274
- Buffer object to hold IMD frames. If `multithreaded` is False, this
275
- argument is ignored
276
- sinfo : IMDSessionInfo
277
- Information about the IMD session
278
- n_atoms : int
279
- Number of atoms in the simulation
280
- multithreaded : bool, optional
281
- If True, socket interaction will occur in a separate thread &
282
- frames will be buffered. Single-threaded, blocking IMDClient
283
- should only be used in testing [[``True``]]
284
-
285
- """
286
353
  super(BaseIMDProducer, self).__init__(daemon=True)
287
354
  self._conn = conn
288
355
  self._imdsinfo = sinfo
289
356
  self._paused = False
290
357
 
358
+ self.error_queue = error_queue
291
359
  # Timeout for first frame should be longer
292
360
  # than rest of frames
293
361
  self._timeout = timeout
@@ -382,6 +450,7 @@ class BaseIMDProducer(threading.Thread):
382
450
  logger.debug("IMDProducer: Simulation ended normally, cleaning up")
383
451
  except Exception as e:
384
452
  logger.debug("IMDProducer: An unexpected error occurred: %s", e)
453
+ self.error_queue.put(e)
385
454
  finally:
386
455
  logger.debug("IMDProducer: Stopping run loop")
387
456
  # Tell consumer not to expect more frames to be added
@@ -397,9 +466,19 @@ class BaseIMDProducer(threading.Thread):
397
466
  )
398
467
  # Sometimes we do not care what the value is
399
468
  if expected_value is not None and header.length != expected_value:
400
- raise RuntimeError(
401
- f"IMDProducer: Expected header value {expected_value}, got {header.length}"
402
- )
469
+ if expected_type in [
470
+ IMDHeaderType.IMD_FCOORDS,
471
+ IMDHeaderType.IMD_VELOCITIES,
472
+ IMDHeaderType.IMD_FORCES,
473
+ ]:
474
+ raise RuntimeError(
475
+ f"IMDProducer: Expected n_atoms value {expected_value}, got {header.length}. "
476
+ + "Ensure you are using the correct topology file."
477
+ )
478
+ else:
479
+ raise RuntimeError(
480
+ f"IMDProducer: Expected header value {expected_value}, got {header.length}"
481
+ )
403
482
 
404
483
  def _get_header(self):
405
484
  self._read(self._header)
@@ -419,9 +498,11 @@ class BaseIMDProducer(threading.Thread):
419
498
 
420
499
 
421
500
  class IMDProducerV2(BaseIMDProducer):
422
- def __init__(self, conn, buffer, sinfo, n_atoms, multithreaded, **kwargs):
501
+ def __init__(
502
+ self, conn, buffer, sinfo, n_atoms, multithreaded, error_queue, **kwargs
503
+ ):
423
504
  super(IMDProducerV2, self).__init__(
424
- conn, buffer, sinfo, n_atoms, multithreaded, **kwargs
505
+ conn, buffer, sinfo, n_atoms, multithreaded, error_queue, **kwargs
425
506
  )
426
507
 
427
508
  self._energies = bytearray(IMDENERGYPACKETLENGTH)
@@ -514,6 +595,7 @@ class IMDProducerV3(BaseIMDProducer):
514
595
  sinfo,
515
596
  n_atoms,
516
597
  multithreaded,
598
+ error_queue,
517
599
  **kwargs,
518
600
  ):
519
601
  super(IMDProducerV3, self).__init__(
@@ -522,6 +604,7 @@ class IMDProducerV3(BaseIMDProducer):
522
604
  sinfo,
523
605
  n_atoms,
524
606
  multithreaded,
607
+ error_queue,
525
608
  **kwargs,
526
609
  )
527
610
  # The body of an x/v/f packet should contain
@@ -638,6 +721,21 @@ class IMDFrameBuffer:
638
721
  """
639
722
  Acts as interface between producer (IMDProducer) and consumer (IMDClient) threads
640
723
  when IMDClient runs in multithreaded mode
724
+
725
+ Parameters
726
+ ----------
727
+ imdsinfo : IMDSessionInfo
728
+ Information about the IMD session
729
+ n_atoms : int
730
+ Number of atoms in the simulation
731
+ buffer_size : int, optional
732
+ Size of the buffer in bytes [``10MB``]
733
+ pause_empty_proportion : float, optional
734
+ Lower threshold proportion of the buffer's IMDFrames that are empty
735
+ before the simulation is paused [``0.25``]
736
+ unpause_empty_proportion : float, optional
737
+ Proportion of the buffer's IMDFrames that must be empty
738
+ before the simulation is unpaused [``0.5``]
641
739
  """
642
740
 
643
741
  def __init__(
@@ -649,23 +747,6 @@ class IMDFrameBuffer:
649
747
  unpause_empty_proportion=0.5,
650
748
  **kwargs,
651
749
  ):
652
- """
653
- Parameters
654
- ----------
655
- imdsinfo : IMDSessionInfo
656
- Information about the IMD session
657
- n_atoms : int
658
- Number of atoms in the simulation
659
- buffer_size : int, optional
660
- Size of the buffer in bytes [``10MB``]
661
- pause_empty_proportion : float, optional
662
- Lower threshold proportion of the buffer's IMDFrames that are empty
663
- before the simulation is paused [``0.25``]
664
- unpause_empty_proportion : float, optional
665
- Proportion of the buffer's IMDFrames that must be empty
666
- before the simulation is unpaused [``0.5``]
667
- """
668
-
669
750
  # Syncing reader and producer
670
751
  self._producer_finished = False
671
752
  self._consumer_finished = False
@@ -681,9 +762,7 @@ class IMDFrameBuffer:
681
762
  raise ValueError("pause_empty_proportion must be between 0 and 1")
682
763
  self._pause_empty_proportion = pause_empty_proportion
683
764
  if unpause_empty_proportion < 0 or unpause_empty_proportion > 1:
684
- raise ValueError(
685
- "unpause_empty_proportion must be between 0 and 1"
686
- )
765
+ raise ValueError("unpause_empty_proportion must be between 0 and 1")
687
766
  self._unpause_empty_proportion = unpause_empty_proportion
688
767
 
689
768
  if buffer_size <= 0:
@@ -750,9 +829,7 @@ class IMDFrameBuffer:
750
829
  logger.debug("IMDProducer: Noticing consumer finished")
751
830
  raise EOFError
752
831
  except Exception as e:
753
- logger.debug(
754
- f"IMDProducer: Error waiting for space in buffer: {e}"
755
- )
832
+ logger.debug(f"IMDProducer: Error waiting for space in buffer: {e}")
756
833
 
757
834
  def pop_empty_imdframe(self):
758
835
  logger.debug("IMDProducer: Getting empty frame")
@@ -798,9 +875,7 @@ class IMDFrameBuffer:
798
875
  imdf = self._full_q.get()
799
876
  else:
800
877
  with self._full_imdf_avail:
801
- while (
802
- self._full_q.qsize() == 0 and not self._producer_finished
803
- ):
878
+ while self._full_q.qsize() == 0 and not self._producer_finished:
804
879
  self._full_imdf_avail.wait()
805
880
 
806
881
  if self._producer_finished and self._full_q.qsize() == 0:
@@ -0,0 +1,58 @@
1
+ title = PRODUCTION IN NPT
2
+ ld-seed = 1
3
+ ; Run parameters
4
+ integrator = md ; leap-frog integrator
5
+ nsteps = 100 ; 1 * 1000 = 1 ps
6
+ dt = 0.001 ; 1 fs
7
+ ; Output control
8
+ nstxout = 8 ; save coordinates every 1 fs
9
+ nstvout = 8 ; save velocities every 1 fs
10
+ nstfout = 8
11
+ nstenergy = 8 ; save energies every 1 fs
12
+ nstlog = 10 ; update log file every 1 ps
13
+ ; Center of mass (COM) motion
14
+ nstcomm = 10 ; remove COM motion every 10 steps
15
+ comm-mode = Linear ; remove only COM translation (liquids in PBC)
16
+ ; Bond parameters
17
+ continuation = yes ; first dynamics run
18
+ constraint_algorithm = lincs ; holonomic constraints
19
+ constraints = all-bonds ; all bonds lengths are constrained
20
+ lincs_iter = 1 ; accuracy of LINCS
21
+ lincs_order = 4 ; also related to accuracy
22
+ ; Nonbonded settings
23
+ cutoff-scheme = Verlet ; Buffered neighbor searching
24
+ ns_type = grid ; search neighboring grid cells
25
+ nstlist = 10 ; 10 fs, largely irrelevant with Verlet
26
+ rcoulomb = 1.0 ; short-range electrostatic cutoff (in nm)
27
+ rvdw = 1.0 ; short-range van der Waals cutoff (in nm)
28
+ DispCorr = EnerPres ; account for cut-off vdW scheme
29
+ ; Electrostatics
30
+ coulombtype = PME ; Particle Mesh Ewald for long-range electrostatics
31
+ pme_order = 4 ; cubic interpolation
32
+ fourierspacing = 0.12 ; grid spacing for FFT
33
+ ; Temperature coupling is on
34
+ tcoupl = Nose-Hoover ; good for production, after equilibration
35
+ ; we define separate thermostats for the solute and solvent (need to adapt)
36
+ ; see default groups defined by Gromacs for your system or define your own (make_ndx)
37
+ tc-grps = Protein SOL ; the separate groups for the thermostats
38
+ tau-t = 1.0 1.0 ; time constants for thermostats (ps)
39
+ ref-t = 300 300 ; reference temperature for thermostats (K)
40
+ ; Pressure coupling is off
41
+ pcoupl = Parrinello-Rahman ; good for production, after equilibration
42
+ tau-p = 2.0 ; time constant for barostat (ps)
43
+ compressibility = 4.5e-5 ; compressibility (1/bar) set to water at ~300K
44
+ ref-p = 1.0 ; reference pressure for barostat (bar)
45
+ ; Periodic boundary conditions
46
+ pbc = xyz ; 3-D PBC
47
+ ; Velocity generation
48
+ gen_vel = no
49
+ IMD-group = System
50
+ IMD-nst = 8
51
+ IMD-version = 3
52
+ IMD-time = yes
53
+ IMD-box = yes
54
+ IMD-coords = yes
55
+ IMD-unwrap = no
56
+ IMD-vels = yes
57
+ IMD-forces = yes
58
+ IMD-energies = no
@@ -52,8 +52,8 @@ velocity all create 300 102939 dist gaussian mom yes rot yes
52
52
  fix 1 all nve
53
53
 
54
54
  # Create source of truth trajectory
55
- # dump h5md1 all h5md 1 lammps_trj.h5md position velocity force box yes
56
- # dump_modify h5md1 unwrap no
55
+ dump h5md1 all h5md 1 lammps_trj.h5md position velocity force box yes
56
+ dump_modify h5md1 unwrap no
57
57
 
58
58
  ## IMD settings
59
59
  # https://docs.lammps.org/fix_imd.html
@@ -63,7 +63,7 @@ fix 2 all imd 8888 version 3 unwrap off nowait off
63
63
  run 100
64
64
 
65
65
  # Stop dumping information to the dump file.
66
- # undump h5md1
66
+ undump h5md1
67
67
 
68
68
  # Unfix the NVE. Additional lines if any will assume that this fix is off.
69
69
  unfix 1
@@ -0,0 +1,71 @@
1
+ ## Setup
2
+ units metal
3
+ boundary p p p #Specify periodic boundary condition are needed in all three faces
4
+ atom_style atomic #What style of atoms is to be used in the simulation
5
+ log logfile.txt #Write the log file to this text file. All thermodynamic information applicable to the entire system
6
+
7
+ ## Create Box
8
+ #Refers to an abstract geometric region of space. units box refers to the fact that the size of the box is specified in the units as given in the units command.
9
+ # The name "forbox" refers to the region ID so that you can refer to it somewhere else in this input script.
10
+ region forbox block 0 45.8 0 45.8 0 45.8 units box
11
+ create_box 1 forbox
12
+ # Since we have given fcc as lattice type no need to mention basis for this
13
+ lattice fcc 4.58
14
+
15
+ ## Create atoms & define interactions
16
+ # basis arg defines which atoms are created based on their lattice position (all are atom type 1)
17
+ create_atoms 1 region forbox basis 1 1 basis 2 1 basis 3 1 basis 4 1 units box
18
+ # Mass of atom type 1 is 39.48 [mass units grams/mole]
19
+ mass 1 39.948
20
+ # lj potential describes potential energy between two atoms as function of the dist between them
21
+ # don't apply lj interactions beyond cutoff dist
22
+ pair_style lj/cut 10
23
+ # The coefficient of the lj potential for the interactions of atom type 1 with atom type 1
24
+ pair_coeff 1 1 0.01006418 3.3952
25
+
26
+ ## Create atom group for argon atoms
27
+ group ar type 1 #Group all the argon types (argon type is of type 1). All atoms of type 1 are in group with the name 'ar'
28
+
29
+
30
+ ## Write initial configuration
31
+ dump dump_1 all custom 1 dump_initial_config.dump id type x y z ix iy iz vx vy vz
32
+
33
+
34
+ ## Perform energy minimization
35
+ run 1
36
+ # Stop dumping to this file
37
+ undump dump_1
38
+ # Minimize the energy using a conjugate gradient step.
39
+ minimize 1e-25 1e-19 10000 10000
40
+ print "Finished Minimizing"
41
+ variable ener equal pe
42
+
43
+ ## Output the topology after minimization
44
+ write_data topology_after_min.data
45
+
46
+ ## Prepare MD simulation
47
+ timestep 0.001
48
+ # Set the velocities of all the atoms so that the temperature of the system
49
+ # is 300K. Make the distribution Gaussian.
50
+ velocity all create 300 102939 dist gaussian mom yes rot yes
51
+ # this is equlibration process.
52
+ fix 1 all nve
53
+
54
+ # Create source of truth trajectory
55
+ dump h5md1 all h5md 8 lammps_trj.h5md position velocity force box yes
56
+ dump_modify h5md1 unwrap no
57
+
58
+ ## IMD settings
59
+ # https://docs.lammps.org/fix_imd.html
60
+ fix 2 all imd 8888 version 3 unwrap off nowait off trate 8
61
+
62
+ ## Run MD sim
63
+ run 100
64
+
65
+ # Stop dumping information to the dump file.
66
+ undump h5md1
67
+
68
+ # Unfix the NVE. Additional lines if any will assume that this fix is off.
69
+ unfix 1
70
+
71
+ #End
@@ -17,8 +17,20 @@ switchdist 7.0
17
17
  cutoff 8.0
18
18
  pairlistdist 9.0
19
19
 
20
- dcdfile alanin.dcd
21
- dcdfreq 1
20
+ # Add box dimensions
21
+ cellBasisVector1 32.76 0.0 0.0
22
+ cellBasisVector2 0.0 31.66 0.0
23
+ cellBasisVector3 0.0 0.0 32.89
24
+
25
+ DCDfile alanin.dcd
26
+ DCDfreq 1
27
+ DCDUnitCell yes
28
+ velDcdFile alanin.vel.dcd
29
+ velDcdFreq 1
30
+ forceDcdFile alanin.force.dcd
31
+ forceDcdFreq 1
32
+ XSTFile alanin.xst
33
+ xstFreq 1
22
34
 
23
35
  #restartname alanin.restart
24
36
  #restartfreq 10
@@ -40,8 +52,8 @@ IMDwait on
40
52
  IMDversion 3
41
53
  IMDsendPositions yes
42
54
  IMDsendEnergies yes
43
- #IMDsendTime yes
44
- #IMDsendBoxDimensions yes
55
+ IMDsendTime yes
56
+ IMDsendBoxDimensions yes
45
57
  IMDsendVelocities yes
46
- #IMDsendForces yes
58
+ IMDsendForces yes
47
59
  IMDwrapPositions yes
@@ -0,0 +1,59 @@
1
+ # This is a test namd configuration file
2
+
3
+ timestep 0.5
4
+ numsteps 100
5
+ structure alanin.psf
6
+ parameters alanin.params
7
+ coordinates alanin.pdb
8
+ exclude scaled1-4
9
+ 1-4scaling 0.4
10
+ outputname output[myReplica]
11
+ margin 1.0
12
+ stepspercycle 3
13
+ temperature 0
14
+
15
+ switching on
16
+ switchdist 7.0
17
+ cutoff 8.0
18
+ pairlistdist 9.0
19
+
20
+ # Add box dimensions
21
+ cellBasisVector1 32.76 0.0 0.0
22
+ cellBasisVector2 0.0 31.66 0.0
23
+ cellBasisVector3 0.0 0.0 32.89
24
+
25
+ DCDfile alanin.dcd
26
+ DCDfreq 8
27
+ DCDUnitCell yes
28
+ velDcdFile alanin.vel.dcd
29
+ velDcdFreq 8
30
+ forceDcdFile alanin.force.dcd
31
+ forceDcdFreq 8
32
+ XSTFile alanin.xst
33
+ xstFreq 8
34
+
35
+ #restartname alanin.restart
36
+ #restartfreq 10
37
+
38
+ #langevin on
39
+ #langevinTemp 300.0
40
+ #langevincol O
41
+
42
+ #constraints on
43
+
44
+ #fma on
45
+
46
+ seed 12345
47
+
48
+ IMDon yes
49
+ IMDport 8888
50
+ IMDfreq 8
51
+ IMDwait on
52
+ IMDversion 3
53
+ IMDsendPositions yes
54
+ IMDsendEnergies yes
55
+ IMDsendTime yes
56
+ IMDsendBoxDimensions yes
57
+ IMDsendVelocities yes
58
+ IMDsendForces yes
59
+ IMDwrapPositions yes