Alamo
Disconnection.H
Go to the documentation of this file.
1//
2// This simulates the creation of "disconnection pairs" at a GB
3// by perturbing the order parameter :math:`\eta` with a gaussian.
4//
5// Disconnections can be nucleated randomly, or they can be added
6// in a controlled way through the "fixed" option.
7//
8// See the following reference for further details
9//
10// .. bibliography::
11// :list: none
12// :filter: False
13//
14// gokuli2021multiphase
15//
16//
17
18#ifndef MODEL_DEFECT_DISCONNECTION
19#define MODEL_DEFECT_DISCONNECTION
20
21#include <random>
22
23#include "AMReX_SPACE.H"
24#include "IO/ParmParse.H"
25#include "Set/Base.H"
26#include "Util/MPI.H"
27
28namespace Model
29{
30namespace Defect
31{
33{
34public:
35
38
39 static void
41 {
42 Util::Assert(INFO,TEST(AMREX_SPACEDIM==2),"2D only");
43 // time to start applying disconnections
44 pp_query_default ("tstart", value.tstart,0.0);
45 // nucleation energy
46 pp_query_default ("nucleation_energy", value.nucleation_energy,0.0);
47 // characteristic time
48 pp_query_default("tau_vol", value.tau_vol, 1.0);
49 // temperature
50 pp_query_default("temp", value.temp, 0.0);
51 // characteristic size
52 pp_query_default("box_size", value.box_size, 0.0);
53 // interval between generation events
54 pp_query_required("interval", value.interval);
55 // regularization epsilon
56 pp_query_default ("epsilon",value.epsilon,1E-20);
57 // whether to manually specify disconnection nucleation points
58 pp.query("disconnection.fixed.on",value.fixed.on);
59 if (value.fixed.on)
60 {
61 // array of x locations
62 pp.queryarr("fixed.sitex",value.fixed.sitex);
63 // array of y locations
64 pp.queryarr("fixed.sitey",value.fixed.sitey);
65 // array of order parameter number
66 pp.queryarr("fixed.phases",value.fixed.phases);
67 // time to appear
68 pp.queryarr("fixed.time",value.fixed.time);
69 Util::Assert(INFO,TEST(value.fixed.sitex.size() == value.fixed.sitey.size()));
70 Util::Assert(INFO,TEST(value.fixed.sitex.size() == value.fixed.phases.size()));
71 Util::Assert(INFO,TEST(value.fixed.sitex.size() == value.fixed.time.size()));
72 value.fixed.done.resize(value.fixed.sitex.size(),false);
73 }
74 else
75 {
76 value.unif_dist = std::uniform_real_distribution<double>(0.0,1.0);
77 value.int_dist = std::uniform_int_distribution<int>(0,1);
78 value.rand_num_gen.seed(amrex::ParallelDescriptor::MyProc());
79 }
80
81 // verbosity
82 pp_query_default("verbose",value.verbose,false);
83 }
84
85
86 /// This operates on an entire field, and manages all of the MPI
87 /// communication necessary for consistent nucleation.
88 void
90 std::vector<amrex::Geometry> &geom,
91 Set::Scalar timestep,
93 int iter
94 )
95 {
96 Util::Assert(INFO,TEST(eta_mf[0]->nComp() == 2), "This only works for 2 component phase fields");
97
98 if (time < tstart) // wait until it's time to go
99 return;
100 if (iter % interval) // skip every [interval] timesteps
101 return;
102
103 sitex.clear();
104 sitey.clear();
105 phases.clear();
106
107 int max_lev = eta_mf.finest_level;
108
109 const Set::Scalar *DX = geom[max_lev].CellSize();
110 Set::Scalar exponent = DX[0] * DX[0] * (timestep * interval) / tau_vol;
111
112 // Determine the nucleation sites in the finest grid only
113 for (amrex::MFIter mfi(*eta_mf[max_lev], amrex::TilingIfNotGPU()); mfi.isValid(); ++mfi)
114 {
115 const amrex::Box &bx = mfi.tilebox();
116 amrex::Array4<amrex::Real> const &eta = (*eta_mf[max_lev]).array(mfi);
117 amrex::ParallelFor(bx, [=] AMREX_GPU_DEVICE(int i, int j, int k)
118 {
120 E0 /= epsilon + 256.0*eta(i,j,k,0)*eta(i,j,k,0)*eta(i,j,k,0)*eta(i,j,k,0)*eta(i,j,k,1)*eta(i,j,k,1)*eta(i,j,k,1)*eta(i,j,k,1);
121 Set::Scalar p = std::exp(-E0/(K_b*temp));
122 Set::Scalar P = 1.0 - std::pow(1.0 - p,exponent);
123 if (eta(i,j,k,0) < 0 || eta(i,j,k,0) > 1.0 || eta(i,j,k,1) < 0 || eta(i,j,k,1) > 1.0) P = 0.0;
124 Set::Scalar q = 0.0;
126 if (q < P)
127 {
128 sitex.push_back(geom[max_lev].ProbLo()[0] + ((amrex::Real)(i)) * DX[0]);
129 sitey.push_back(geom[max_lev].ProbLo()[1] + ((amrex::Real)(j)) * DX[1]);
130 int phase = int_dist(rand_num_gen);
131 phases.push_back(phase);
132 } });
133 }
134
135 // Sync up all the nucleation sites among processors
139
140 if (verbose)
141 {
142 Util::Message(INFO, "Nucleating ", phases.size(), " disconnections");
143 }
144
145 if (sitex.size() > 0)
146 {
147 // Now that we all know the nucleation locations, perform the nucleation
148 for (int lev = 0; lev <= max_lev; lev++)
149 {
150 amrex::Box domain = geom[lev].Domain();
151 domain.convert(amrex::IntVect::TheNodeVector());
152 const amrex::Real *DX = geom[lev].CellSize();
153 for (amrex::MFIter mfi(*eta_mf[lev], amrex::TilingIfNotGPU()); mfi.isValid(); ++mfi)
154 {
155 const amrex::Box bx = mfi.grownnodaltilebox() & domain;
156 amrex::Array4<Set::Scalar> const &eta = (*eta_mf[lev]).array(mfi);
157 amrex::ParallelFor(bx, [=] AMREX_GPU_DEVICE(int i, int j, int k)
158 {
159 Set::Vector x;
160 AMREX_D_TERM(
161 x(0) = geom[lev].ProbLo()[0] + ((amrex::Real)(i)) * DX[0];,
162 x(1) = geom[lev].ProbLo()[1] + ((amrex::Real)(j)) * DX[1];,
163 x(2) = geom[lev].ProbLo()[2] + ((amrex::Real)(k)) * DX[2];);
164 for (unsigned int m = 0; m < phases.size(); m++)
165 {
166 amrex::Real r_squared = 0;
167 Set::Vector nucleation_site(AMREX_D_DECL(sitex[m], sitey[m], 0.0));
168 for (int n = 0; n < AMREX_SPACEDIM; n++)
169 {
170 amrex::Real dist = nucleation_site(n) - x(n);
171 r_squared += dist * dist;
172 }
173 amrex::Real bump = exp(-r_squared / box_size);
174 eta(i, j, k, phases[m]) = bump * (1 - eta(i, j, k, phases[m])) + eta(i, j, k, phases[m]);
175 eta(i, j, k, 1 - phases[m]) = (1. - bump) * eta(i, j, k, 1 - phases[m]);
176 }
177 });
178 }
179 }
180 }
181 }
182
183
184
185private:
186
187 bool verbose = false;
188
195
196 int interval = -1;
197
198 std::uniform_real_distribution<double> unif_dist; /// random number distribution for spatial location
199 std::uniform_int_distribution<int> int_dist; /// random number generator for phase
200 std::default_random_engine rand_num_gen; /// generator object
201
202 struct {
203 int on = 0;
204 std::vector<Set::Scalar> sitex;
205 std::vector<Set::Scalar> sitey;
206 std::vector<int> phases;
207 std::vector<Set::Scalar> time;
208 std::vector<bool> done;
210
211
212 std::vector<Set::Scalar> sitex; /// list of nucleation site x coordinates
213 std::vector<Set::Scalar> sitey; /// list of nucleation stie y coordinates
214 std::vector<int> phases; /// list of nucleation site phases (up or down)
215
216 const Set::Scalar K_b = 8.617333262145e-5; // eV/K
217};
218}
219}
220
221#endif
#define pp_query_required(...)
Definition ParmParse.H:99
#define pp_query_default(...)
Definition ParmParse.H:100
#define TEST(x)
Definition Util.H:21
#define INFO
Definition Util.H:20
int queryarr(std::string name, std::vector< T > &value, std::string, std::string, int)
Definition ParmParse.H:336
std::vector< int > phases
list of nucleation stie y coordinates
void Nucleate(Set::Field< Set::Scalar > &eta_mf, std::vector< amrex::Geometry > &geom, Set::Scalar timestep, Set::Scalar time, int iter)
This operates on an entire field, and manages all of the MPI communication necessary for consistent n...
std::vector< Set::Scalar > sitex
struct Model::Defect::Disconnection::@31 fixed
generator object
const Set::Scalar K_b
list of nucleation site phases (up or down)
std::uniform_int_distribution< int > int_dist
random number distribution for spatial location
std::vector< Set::Scalar > sitey
list of nucleation site x coordinates
std::default_random_engine rand_num_gen
random number generator for phase
std::uniform_real_distribution< double > unif_dist
static void Parse(Disconnection &value, IO::ParmParse &pp)
std::vector< Set::Scalar > time
int finest_level
Definition Set.H:67
amrex::Real Scalar
Definition Base.H:19
Eigen::Matrix< amrex::Real, AMREX_SPACEDIM, 1 > Vector
Definition Base.H:20
int Allgather(std::vector< T > &a_data)
Definition MPI.H:12
AMREX_FORCE_INLINE void Assert(std::string file, std::string func, int line, std::string smt, bool pass, Args const &... args)
Definition Util.H:70
void Message(std::string file, std::string func, int line, Args const &... args)
Definition Util.H:141