Design ====== General principles ------------------ General purpose routines and computational algorithms are implemented as Fortran modules in `src/`. Parts of the code is tested with programs in `test/`. Actual simulations are found in `programs/`, where every program corresponds to a given setup. The programs read parameters from a text file and store trajectories in `H5MD `_ files. The aim of the code organization is that one can write a program that call trusted routines from the modules, giving a high-level view on the simulation. There is no global variable in the code so that a routine may only act on variables that are passed to it. Storage of cell and particle data --------------------------------- The storage of particle and cell data is defined in the module `particle_system` and `cell_system`, respectively. The derived type `particle_system_t` defines arrays for the position, velocity, etc of every particle. The derived type `cell_system_t` defines a cell list with a one-dimensional index that is mapped to a three-dimensional compact Hilbert index :cite:`hamilton_compact_hilbert_tr`. Particles are sorted according to this cell system, as in the nano-dimer software :cite:`colberg_nanodimer_web`. Operations on particles can proceed in two different ways: 1. Particle-wise: The loop goes over every particle, following the particle index of the particle data in memory. 2. Cell-wise: The loop runs over successive cells, where an inner loop runs over all particles. Thanks to the sorting of particles, the indices of the particles in a given cell are contiguous. Programming language -------------------- RMPCDMD is written in Fortran 2008 and uses derived types objects to store simulation data. RMPCDMD is built using `CMake `_, which facilitates the inclusion of external libraries (`fortran_h5md `_, `random_module `_, `ParseText `_ and `fortran_tester `_). The `HDF5 `_ library, with the Fortran 2003 interface, is also necessary to build RMPCDMD. Random numbers -------------- A C library implements the Threefry Random Number Generator (RNG) :cite:`random123`. This RNG can be used in separate independent threads, provided that the thread's numerical ID is part of the *key* of the RNG. The other part of the key, that is made of two 64-bit integers, is the seed that is provided by the user. The RNG is implemented in `random_module `_, that is fetched as a git submodule in RMPCDMD. A Fortran wrapper, using the ``bind(c)`` attribute, manages the Fortran/C interface.