HILA
Loading...
Searching...
No Matches
suN_gauge.cpp
Go to the documentation of this file.
1/**
2 * @file suN_gauge.cpp
3 * @brief Application to simulate \f$ SU(N) \f$ Gauge field.
4 * @details Simple application which Generates \f$ SU(N) \f$ GaugeField using \ref staplesum, \ref
5 * suN_overrelax and \ref suN_heatbath. Each evolution, the application measures the Wilson action
6 * using GaugeField::measure_plaq and Polyakov lines using \ref measure_polyakov.
7 *
8 */
9#include "hila.h"
10#include "gauge/staples.h"
11#include "gauge/polyakov.h"
12#include "gauge/stout_smear.h"
13#include "gauge/sun_heatbath.h"
14#include "gauge/sun_overrelax.h"
15#include "tools/checkpoint.h"
16
17
18#include <fftw3.h>
19
20// local includes
21#include "parameters.h"
22
23/**
24 * @brief Helper function to get valid z-coordinate index
25 *
26 * @param z
27 * @return int
28 */
29int z_ind(int z) {
30 return (z + lattice.size(e_z)) % lattice.size(e_z);
31}
32
33/**
34 * @brief Measures Polyakov lines and Wilson action
35 *
36 * @tparam group
37 * @param U GaugeField to measure
38 * @param p Parameter struct
39 */
40template <typename group>
41void measure_stuff(const GaugeField<group> &U, const parameters &p) {
42
43 static bool first = true;
44
45 if (first) {
46 hila::out0 << "Legend:";
47 hila::out0 << " plaq P.real P.imag\n";
48
49 first = false;
50 }
51
52 auto poly = measure_polyakov(U);
53
54 auto plaq = U.measure_plaq() / (lattice.volume() * NDIM * (NDIM - 1) / 2);
55
56 hila::out0 << "MEAS " << std::setprecision(8);
57
58 // write the -(polyakov potential) first, this is used as a weight factor in aa
59
60 hila::out0 << plaq << ' ' << poly << '\n';
61}
62
63/**
64 * @brief Wrapper update function
65 * @details Updates Gauge Field one direction at a time first EVEN then ODD parity
66 *
67 * @tparam group
68 * @param U GaugeField to update
69 * @param p Parameter struct
70 * @param relax If true evolves GaugeField with over relaxation if false then with heat bath
71 */
72template <typename group>
73void update(GaugeField<group> &U, const parameters &p, bool relax) {
74
75 // go through dirs in random order
76
77 for (auto &dp : hila::shuffle_directions_and_parities()) {
78
79 update_parity_dir(U, p, dp.parity, dp.direction, relax);
80 }
81
82 // for (Parity par : {EVEN, ODD}) foralldir(d) {
83 // update_parity_dir(U, p, par , d, relax);
84 // }
85}
86
87/**
88 * @brief Wrapper function to updated GaugeField per direction
89 * @details Computes first staplesum, then uses computed result to evolve GaugeField either with
90 * over relaxation or heat bath
91 *
92 * @tparam group
93 * @param U GaugeField to evolve
94 * @param p parameter struct
95 * @param par Parity
96 * @param d Direction to evolve
97 * @param relax If true evolves GaugeField with over relaxation if false then with heat bath
98 */
99template <typename group>
100void update_parity_dir(GaugeField<group> &U, const parameters &p, Parity par, Direction d,
101 bool relax) {
102
103 static hila::timer hb_timer("Heatbath");
104 static hila::timer or_timer("Overrelax");
105 static hila::timer staples_timer("Staplesum");
106
107 Field<group> staples;
108
109 staples_timer.start();
110
111 staplesum(U, staples, d, par);
112 staples_timer.stop();
113
114 if (relax) {
115
116 or_timer.start();
117
118 onsites(par) {
119#ifdef SUN_OVERRELAX_dFJ
120 suN_overrelax_dFJ(U[d][X], staples[X], p.beta);
121#else
122 suN_overrelax(U[d][X], staples[X]);
123#endif
124 }
125 or_timer.stop();
126
127 } else {
128
129 hb_timer.start();
130 onsites(par) {
131 suN_heatbath(U[d][X], staples[X], p.beta);
132 }
133 hb_timer.stop();
134 }
135}
136
137/**
138 * @brief Evolve gauge field
139 * @details Evolution happens by means of heat bath and over relaxation. For each heatbath update
140 * (p.n_update) we update p.n_overrelax times with over relaxation.
141 *
142 * @tparam group
143 * @param U
144 * @param p
145 */
146template <typename group>
147void do_trajectory(GaugeField<group> &U, const parameters &p) {
148
149 for (int n = 0; n < p.n_update; n++) {
150 for (int i = 0; i < p.n_overrelax; i++) {
151 update(U, p, true);
152 }
153 update(U, p, false);
154 }
156}
157
158
159int main(int argc, char **argv) {
160
161 // hila::initialize should be called as early as possible
162 hila::initialize(argc, argv);
163
164 // hila provides an input class hila::input, which is
165 // a convenient way to read in parameters from input files.
166 // parameters are presented as key - value pairs, as an example
167 // " lattice size 64, 64, 64, 64"
168 // is read below.
169 //
170 // Values are broadcast to all MPI nodes.
171 //
172 // .get() -method can read many different input types,
173 // see file "input.h" for documentation
174
175 parameters p;
176
177 hila::out0 << "SU(" << mygroup::size() << ") heat bath + overrelax update\n";
178
179 hila::input par("parameters");
180
181 CoordinateVector lsize;
182 lsize = par.get("lattice size"); // reads NDIM numbers
183
184 p.beta = par.get("beta");
185 // deltab sets system to different beta on different sides, by beta*(1 +- deltab)
186 // use for initial config generation only
187 p.deltab = par.get("delta beta fraction");
188 // trajectory length in steps
189 p.n_overrelax = par.get("overrelax steps");
190 p.n_update = par.get("updates in trajectory");
191 p.n_trajectories = par.get("trajectories");
192 p.n_thermal = par.get("thermalization");
193
194 // random seed = 0 -> get seed from time
195 uint64_t seed = par.get("random seed");
196 // save config and checkpoint
197 p.n_save = par.get("traj/saved");
198 // measure surface properties and print "profile"
199 p.config_file = par.get("config name");
200
201 par.close(); // file is closed also when par goes out of scope
202
203 // setting up the lattice is convenient to do after reading
204 // the parameter
205 lattice.setup(lsize);
206
207 // Alloc gauge field
209
210 U = 1;
211
212 // use negative trajectory for thermal
213 int start_traj = -p.n_thermal;
214
215 hila::timer update_timer("Updates");
216 hila::timer measure_timer("Measurements");
217
218 restore_checkpoint(U, p.config_file, p.n_trajectories, start_traj);
219
220 // We need random number here
221 if (!hila::is_rng_seeded())
222 hila::seed_random(seed);
223
224 for (int trajectory = start_traj; trajectory < p.n_trajectories; trajectory++) {
225
226 double ttime = hila::gettime();
227
228 update_timer.start();
229
230 double acc = 0;
231
232 do_trajectory(U, p);
233
234 // put sync here in order to get approx gpu timing
235 hila::synchronize_threads();
236 update_timer.stop();
237
238 // trajectory is negative during thermalization
239 if (trajectory >= 0) {
240 measure_timer.start();
241
242 hila::out0 << "Measure_start " << trajectory << '\n';
243
244 measure_stuff(U, p);
245
246 hila::out0 << "Measure_end " << trajectory << std::endl;
247
248 measure_timer.stop();
249 }
250
251 if (p.n_save > 0 && (trajectory + 1) % p.n_save == 0) {
252 checkpoint(U, p.config_file, p.n_trajectories, trajectory);
253 }
254 }
255
257}
The field class implements the standard methods for accessing Fields. Hilapp replaces the parity acce...
Definition field.h:61
Gauge field class.
Definition gaugefield.h:22
void reunitarize_gauge()
Reunitarize Gauge Field consisting of matrices.
Definition gaugefield.h:94
double measure_plaq() const
Computes Wilson action.
Definition gaugefield.h:108
static constexpr int size()
Returns size of Vector or square Matrix.
Definition matrix.h:248
hila::input - Class for parsing runtime parameter files.
Definition input.h:52
void setup(const CoordinateVector &siz)
General lattice setup.
Definition lattice.cpp:33
Parity
Parity enum with values EVEN, ODD, ALL; refers to parity of the site. Parity of site (x,...
Direction
Enumerator for direction that assigns integer to direction to be interpreted as unit vector.
Definition coordinates.h:34
auto shuffle_directions_and_parities()
Definition shuffle.h:49
std::ostream out0
This writes output only from main process (node 0)
void initialize(int argc, char **argv)
Read in command line arguments. Initialise default stream and MPI communication.
void seed_random(uint64_t seed, bool device_rng=true)
Seed random generators with 64-bit unsigned value. On MPI shuffles the seed so that different MPI ran...
Definition random.cpp:86
double gettime()
Definition timing.cpp:163
bool is_rng_seeded()
Check if RNG is seeded already.
Definition random.cpp:243
void finishrun()
Normal, controlled exit - all nodes must call this. Prints timing information and information about c...
Complex< double > measure_polyakov(const GaugeField< T > &U, Direction dir=Direction(NDIM - 1))
Measure Polyakov lines to direction dir.
Definition polyakov.h:17
void staplesum(const GaugeField< T > &U, Field< T > &staples, Direction d1, Parity par=ALL)
Sum the staples of link matrices to direction dir.
Definition staples.h:28
void update(GaugeField< group > &U, const parameters &p, bool relax)
Wrapper update function.
Definition suN_gauge.cpp:73
void update_parity_dir(GaugeField< group > &U, const parameters &p, Parity par, Direction d, bool relax)
Wrapper function to updated GaugeField per direction.
void do_trajectory(GaugeField< group > &U, const parameters &p)
Evolve gauge field.
int z_ind(int z)
Helper function to get valid z-coordinate index.
Definition suN_gauge.cpp:29
void measure_stuff(const GaugeField< group > &U, const parameters &p)
Measures Polyakov lines and Wilson action.
Definition suN_gauge.cpp:41
double suN_heatbath(SU< N, T > &U, const SU< N, T > &staple, double beta)
heatbath
void suN_overrelax(SU< N, T > &U, const SU< N, T > &staple)
Overrelaxation using SU(2) subgroups