#include namespace Grid { namespace QCD { template void ContinuedFractionFermion5D::SetCoefficientsTanh(Approx::zolotarev_data *zdata,RealD scale) { SetCoefficientsZolotarev(1.0/scale,zdata); } template void ContinuedFractionFermion5D::SetCoefficientsZolotarev(RealD zolo_hi,Approx::zolotarev_data *zdata) { // How to check Ls matches?? // std::cout<n << " - n"<da << " -da "<db << " -db"<dn << " -dn"<dd << " -dd"<Ls; assert(zdata->db==Ls);// Beta has Ls coeffs R=(1+this->mass)/(1-this->mass); Beta.resize(Ls); cc.resize(Ls); cc_d.resize(Ls); sqrt_cc.resize(Ls); for(int i=0; i < Ls ; i++){ Beta[i] = zdata -> beta[i]; cc[i] = 1.0/Beta[i]; cc_d[i]=sqrt(cc[i]); } cc_d[Ls-1]=1.0; for(int i=0; i < Ls-1 ; i++){ sqrt_cc[i]= sqrt(cc[i]*cc[i+1]); } sqrt_cc[Ls-2]=sqrt(cc[Ls-2]); ZoloHiInv =1.0/zolo_hi; dw_diag = (4.0-this->M5)*ZoloHiInv; See.resize(Ls); Aee.resize(Ls); int sign=1; for(int s=0;s RealD ContinuedFractionFermion5D::M (const FermionField &psi, FermionField &chi) { int Ls = this->Ls; FermionField D(psi._grid); this->DW(psi,D,DaggerNo); int sign=1; for(int s=0;s RealD ContinuedFractionFermion5D::Mdag (const FermionField &psi, FermionField &chi) { // This matrix is already hermitian. (g5 Dw) = Dw dag g5 = (g5 Dw)dag // The rest of matrix is symmetric. // Can ignore "dag" return M(psi,chi); } template void ContinuedFractionFermion5D::Mdir (const FermionField &psi, FermionField &chi,int dir,int disp){ int Ls = this->Ls; this->DhopDir(psi,chi,dir,disp); // Dslash on diagonal. g5 Dslash is hermitian int sign=1; for(int s=0;s void ContinuedFractionFermion5D::Meooe (const FermionField &psi, FermionField &chi) { int Ls = this->Ls; // Apply 4d dslash if ( psi.checkerboard == Odd ) { this->DhopEO(psi,chi,DaggerNo); // Dslash on diagonal. g5 Dslash is hermitian } else { this->DhopOE(psi,chi,DaggerNo); // Dslash on diagonal. g5 Dslash is hermitian } int sign=1; for(int s=0;s void ContinuedFractionFermion5D::MeooeDag (const FermionField &psi, FermionField &chi) { this->Meooe(psi,chi); } template void ContinuedFractionFermion5D::Mooee (const FermionField &psi, FermionField &chi) { int Ls = this->Ls; int sign=1; for(int s=0;s void ContinuedFractionFermion5D::MooeeDag (const FermionField &psi, FermionField &chi) { this->Mooee(psi,chi); } template void ContinuedFractionFermion5D::MooeeInv (const FermionField &psi, FermionField &chi) { int Ls = this->Ls; // Apply Linv axpby_ssp(chi,1.0/cc_d[0],psi,0.0,psi,0,0); for(int s=1;s=0;s--){ axpbg5y_ssp(chi,1.0/cc_d[s],chi,-1.0*cc_d[s+1]/See[s]/cc_d[s],chi,s,s+1); } } template void ContinuedFractionFermion5D::MooeeInvDag (const FermionField &psi, FermionField &chi) { this->MooeeInv(psi,chi); } // force terms; five routines; default to Dhop on diagonal template void ContinuedFractionFermion5D::MDeriv (GaugeField &mat,const FermionField &U,const FermionField &V,int dag) { int Ls = this->Ls; FermionField D(V._grid); int sign=1; for(int s=0;sDhopDeriv(mat,D,V,DaggerNo); }; template void ContinuedFractionFermion5D::MoeDeriv(GaugeField &mat,const FermionField &U,const FermionField &V,int dag) { int Ls = this->Ls; FermionField D(V._grid); int sign=1; for(int s=0;sDhopDerivOE(mat,D,V,DaggerNo); }; template void ContinuedFractionFermion5D::MeoDeriv(GaugeField &mat,const FermionField &U,const FermionField &V,int dag) { int Ls = this->Ls; FermionField D(V._grid); int sign=1; for(int s=0;sDhopDerivEO(mat,D,V,DaggerNo); }; // Constructors template ContinuedFractionFermion5D::ContinuedFractionFermion5D( GaugeField &_Umu, GridCartesian &FiveDimGrid, GridRedBlackCartesian &FiveDimRedBlackGrid, GridCartesian &FourDimGrid, GridRedBlackCartesian &FourDimRedBlackGrid, RealD _mass,RealD M5) : WilsonFermion5D(_Umu, FiveDimGrid, FiveDimRedBlackGrid, FourDimGrid, FourDimRedBlackGrid,M5), mass(_mass) { int Ls = this->Ls; assert((Ls&0x1)==1); // Odd Ls required } FermOpTemplateInstantiate(ContinuedFractionFermion5D); } }