CHROMA
unprec_nef_linop_array_w.cc
Go to the documentation of this file.
1 /*! \file
2  * \brief Unpreconditioned NEF domain-wall linear operator
3  */
4 
5 #include "chromabase.h"
7 
8 using namespace QDP::Hints;
9 
10 namespace Chroma
11 {
12  //! Creation routine
13  /*! \ingroup linop
14  *
15  * \param u_ gauge field (Read)
16  * \param WilsonMass_ DWF height (Read)
17  * \param b5_ NEF parameter (Read)
18  * \param c5_ NEF parameter (Read)
19  * \param m_q_ quark mass (Read)
20  */
21  void UnprecNEFDWLinOpArray::create(Handle< FermState<T,P,Q> > state,
22  const Real& WilsonMass_,
23  const multi1d<Real>& b5_, const multi1d<Real>& c5_,
24  const Real& m_q_, int N5_)
25  {
26  WilsonMass = WilsonMass_;
27  b5 = b5_ ;
28  c5 = c5_ ;
29  m_q = m_q_ ;
30  N5 = N5_ ;
31 
32  fb5.resize(N5);
33  fc5.resize(N5);
34  Real ff = Nd - WilsonMass;
35  for(int s=0; s < N5; ++s)
36  {
37  fb5[s] = b5[s]*ff + 1;
38  fc5[s] = c5[s]*ff - 1;
39  }
40 
41  D.create(state);
42  fbc = state->getFermBC();
43  }
44 
45 
46 
47  //! Apply unpreconditioned domain-wall fermion linear operator
48  /*!
49  * \ingroup linop
50  *
51  * The operator acts on the entire lattice
52  *
53  * \param psi Pseudofermion field (Read)
54  * \param isign Flag ( PLUS | MINUS ) (Read)
55  */
56  void UnprecNEFDWLinOpArray::operator() (multi1d<LatticeFermion>& chi,
57  const multi1d<LatticeFermion>& psi,
58  enum PlusMinus isign) const
59  {
60  START_CODE();
61 
62  if( chi.size() != N5 ) chi.resize(N5);
63 
64  //
65  // Chi = D' Psi
66  //
67  LatticeFermion tmp,c_tmp,cmb ;
68  moveToFastMemoryHint(tmp);
69  moveToFastMemoryHint(c_tmp);
70  moveToFastMemoryHint(cmb);
71 
72  switch (isign)
73  {
74  case PLUS:
75  {
76  for(int n=0; n < N5; ++n)
77  {
78  if (n == 0)
79  //c_tmp=0.5*(psi[1]-
80  // m_q*psi[N5-1] - GammaConst<Ns,Ns*Ns-1>()*(m_q*psi[N5-1]+psi[1])) ;
81  c_tmp = chiralProjectMinus(psi[1]) -m_q*chiralProjectPlus(psi[N5-1]);
82  else if (n == N5-1)
83  //c_tmp = 0.5*(psi[N5-2] -
84  // m_q*psi[0] + GammaConst<Ns,Ns*Ns-1>()*(psi[N5-2] + m_q*psi[0])) ;
85  c_tmp = chiralProjectPlus(psi[N5-2]) - m_q*chiralProjectMinus(psi[0]) ;
86  else
87  //c_tmp=0.5*(psi[n+1]+
88  // psi[n-1]+GammaConst<Ns,Ns*Ns-1>()*(psi[n-1]-psi[n+1]));
89  c_tmp = chiralProjectPlus(psi[n-1]) + chiralProjectMinus(psi[n+1]);
90 
91  cmb = b5[n]*psi[n] + c5[n]*c_tmp;
92  D(tmp, cmb, isign);
93  chi[n] = fb5[n]*psi[n] + fc5[n]*c_tmp;
94  chi[n] -= 0.5*tmp;
95  }
96  }
97  break;
98 
99  case MINUS:
100  {
101  multi1d<LatticeFermion> Dpsi(N5), c5Dpsi(N5);
102  for(int n=0; n < N5; ++n)
103  {
104  D(Dpsi[n], psi[n], isign);
105 
106  Real cc5 = -0.5*c5[n];
107  c5Dpsi[n] = fc5[n]*psi[n] + cc5*Dpsi[n];
108  }
109 
110  for(int n=0; n < N5; ++n)
111  {
112  if (n == 0){
113  c_tmp = chiralProjectPlus(c5Dpsi[1]) - m_q*chiralProjectMinus(c5Dpsi[N5-1]);
114  }
115  else if (n == N5-1)
116  c_tmp = chiralProjectMinus(c5Dpsi[N5-2]) - m_q*chiralProjectPlus(c5Dpsi[0]);
117  else
118  c_tmp = chiralProjectMinus(c5Dpsi[n-1]) + chiralProjectPlus(c5Dpsi[n+1]);
119 
120  Real bb5 = -0.5*b5[n];
121  chi[n] = fb5[n]*psi[n] + bb5*Dpsi[n];
122  chi[n] += c_tmp;
123  }
124  }
125  break;
126  }
127 
128  getFermBC().modifyF(chi);
129 
130  END_CODE();
131  }
132 
133  //! Apply the Dminus operator on a lattice fermion. See my notes ;-)
134  void UnprecNEFDWLinOpArray::Dminus(LatticeFermion& chi,
135  const LatticeFermion& psi,
136  enum PlusMinus isign,
137  int s5) const
138  {
139  LatticeFermion tt ;
140  D.apply(tt,psi,isign,0);
141  D.apply(tt,psi,isign,1);
142 
143  chi = fc5[s5]*psi + Real(-0.5*c5[s5])*tt;
144  chi *= -1;
145  }
146 
147 
148  //! Derivative
149  void
150  UnprecNEFDWLinOpArray::deriv(multi1d<LatticeColorMatrix>& ds_u,
151  const multi1d<LatticeFermion>& chi, const multi1d<LatticeFermion>& psi,
152  enum PlusMinus isign) const
153  {
154  START_CODE();
155 
156  // THIS IS A VERY INEFFICIENT IMPLEMENTATION - JUST WANT IT FOR DEBUGGING
157 
158  ds_u.resize(Nd);
159  ds_u = zero;
160 
161  multi1d<LatticeColorMatrix> ds_tmp(Nd);
162 
163  LatticeFermion tmp,c_tmp,cmb;
164 
165  switch (isign)
166  {
167  case PLUS:
168  {
169  for(int n=0; n < N5; ++n)
170  {
171  if (n == 0)
172  {
173  tmp = b5[0]*psi[0];
174  D.deriv(ds_tmp, chi[0], tmp, isign);
175  ds_u += ds_tmp;
176 
177  tmp = chiralProjectMinus(psi[1]);
178  tmp *= c5[0];
179  D.deriv(ds_tmp, chi[0], tmp, isign);
180  ds_u += ds_tmp;
181 
182  tmp = chiralProjectPlus(psi[N5-1]);
183  tmp *= -m_q*c5[0];
184  D.deriv(ds_tmp, chi[0], tmp, isign);
185  ds_u += ds_tmp;
186  }
187  else if (n == N5-1)
188  {
189  tmp = b5[n]*psi[n];
190  D.deriv(ds_tmp, chi[n], tmp, isign);
191  ds_u += ds_tmp;
192 
193  tmp = chiralProjectPlus(psi[n-1]);
194  tmp *= c5[n];
195  D.deriv(ds_tmp, chi[n], tmp, isign);
196  ds_u += ds_tmp;
197 
198  tmp = chiralProjectMinus(psi[0]);
199  tmp *= -m_q*c5[n];
200  D.deriv(ds_tmp, chi[n], tmp, isign);
201  ds_u += ds_tmp;
202  }
203  else
204  {
205  tmp = b5[n]*psi[n];
206  D.deriv(ds_tmp, chi[n], tmp, isign);
207  ds_u += ds_tmp;
208 
209  tmp = chiralProjectPlus(psi[n-1]);
210  tmp *= c5[n];
211  D.deriv(ds_tmp, chi[n], tmp, isign);
212  ds_u += ds_tmp;
213 
214  tmp = chiralProjectMinus(psi[n+1]);
215  tmp *= c5[n];
216  D.deriv(ds_tmp, chi[n], tmp, isign);
217  ds_u += ds_tmp;
218  }
219  }
220  }
221  break;
222 
223  case MINUS:
224  {
225  for(int n=0; n < N5; ++n)
226  {
227  if (n == 0)
228  {
229  tmp = b5[0]*chi[0];
230  D.deriv(ds_tmp, tmp, psi[0], isign);
231  ds_u += ds_tmp;
232 
233  tmp = chiralProjectPlus(chi[0]);
234  tmp *= c5[1];
235  D.deriv(ds_tmp, tmp, psi[1], isign);
236  ds_u += ds_tmp;
237 
238  tmp = chiralProjectMinus(chi[0]);
239  tmp *= -m_q*c5[N5-1];
240  D.deriv(ds_tmp, tmp, psi[N5-1], isign);
241  ds_u += ds_tmp;
242  }
243  else if (n == N5-1)
244  {
245  tmp = b5[n]*chi[n];
246  D.deriv(ds_tmp, tmp, psi[n], isign);
247  ds_u += ds_tmp;
248 
249  tmp = chiralProjectMinus(chi[n]);
250  tmp *= c5[n-1];
251  D.deriv(ds_tmp, tmp, psi[n-1], isign);
252  ds_u += ds_tmp;
253 
254  tmp = chiralProjectPlus(chi[n]);
255  tmp *= -m_q*c5[0];
256  D.deriv(ds_tmp, tmp, psi[0], isign);
257  ds_u += ds_tmp;
258  }
259  else
260  {
261  tmp = b5[n]*chi[n];
262  D.deriv(ds_tmp, tmp, psi[n], isign);
263  ds_u += ds_tmp;
264 
265  tmp = chiralProjectMinus(chi[n]);
266  tmp *= c5[n-1];
267  D.deriv(ds_tmp, tmp, psi[n-1], isign);
268  ds_u += ds_tmp;
269 
270  tmp = chiralProjectPlus(chi[n]);
271  tmp *= c5[n+1];
272  D.deriv(ds_tmp, tmp, psi[n+1], isign);
273  ds_u += ds_tmp;
274  }
275  }
276  }
277  break;
278  }
279 
280  for(int m=0; m < Nd; ++m)
281  ds_u[m] *= Real(-0.5);
282 
283  getFermBC().zero(ds_u);
284 
285  END_CODE();
286  }
287 
288 } // End Namespace Chroma
289 
Primary include file for CHROMA library code.
#define END_CODE()
Definition: chromabase.h:65
#define START_CODE()
Definition: chromabase.h:64
Support class for fermion actions and linear operators.
Definition: state.h:94
Class for counted reference semantics.
Definition: handle.h:33
unsigned s
Definition: ldumul_w.cc:37
unsigned n
Definition: ldumul_w.cc:36
static int m[4]
Definition: make_seeds.cc:16
Double tmp
Definition: meslate.cc:60
Nd
Definition: meslate.cc:74
multi1d< Hadron2PtContraction_t > operator()(const multi1d< LatticeColorMatrix > &u)
Asqtad Staggered-Dirac operator.
Definition: klein_gord.cc:10
@ MINUS
Definition: chromabase.h:45
@ PLUS
Definition: chromabase.h:45
const WilsonTypeFermAct< multi1d< LatticeFermion > > Handle< const ConnectState > state
Definition: pbg5p_w.cc:28
Double zero
Definition: invbicg.cc:106
chi
Definition: pade_trln_w.cc:24
psi
Definition: pade_trln_w.cc:191
multi1d< LatticeColorMatrix > deriv(const EvenOddPrecLinearOperator< LatticeFermion, multi1d< LatticeColorMatrix >, multi1d< LatticeColorMatrix > > &AP, const LatticeFermion &chi, const LatticeFermion &psi, enum PlusMinus isign)
Apply the operator onto a source std::vector.
Unpreconditioned NEF domain-wall fermion linear operator.