fermion_links_t * create_fermion_links(int precision, int phases_in, su3_matrix *links) { fermion_links_t *fl; ks_action_paths *ap, *ap_du0; info_t info = INFO_ZERO; char myname[] = "create_fermion_links"; /* Precision for MILC is ignored: use the prevailing precision */ if(precision != PRECISION) if(mynode() == 0)printf("%s: Warning. Precision request replaced by %d\n", myname, PRECISION); if( phases_in != 1) { if(mynode() == 0)printf("BOTCH: %s needs phases in\n",myname); terminate(1); } fl = create_fermion_links_t(); /* Create the path tables */ /* (We copy the pointers into the fm_ap_links_t objects and the responsibility for freeing space is handed over to "destroy_fm_ap_links_t") */ ap = create_path_table(); if(fl->options.want_du0) ap_du0 = create_path_table(); else ap_du0 = NULL; make_path_table(ap, ap_du0); /* Complete the structure */ fl->flg = create_milc_fm_links_t(&info, ap, ap_du0, links, &fl->options); #ifdef FLTIME if(mynode()==0)printf("FLTIME: time = %e (asqtad %s) mflops = %e\n", info.final_sec,milc_prec[PRECISION-1], info.final_flop/(1e6*info.final_sec) ); #endif return fl; }
int main( int argc, char **argv ){ register site *s; int i,si; int prompt; double dtime; su3_vector **eigVec ; su3_vector *tmp ; double *eigVal ; int total_R_iters ; double chirality ; initialize_machine(&argc,&argv); #ifdef HAVE_QDP QDP_initialize(&argc, &argv); #ifndef QDP_PROFILE QDP_profcontrol(0); #endif #endif /* Remap standard I/O */ if(remap_stdio_from_args(argc, argv) == 1)terminate(1); g_sync(); /* set up */ prompt = setup(); /* loop over input sets */ while( readin(prompt) == 0){ dtime = -dclock(); invalidate_all_ferm_links(&fn_links); make_path_table(&ks_act_paths, &ks_act_paths_dmdu0); /* Load fat and long links for fermion measurements if needed */ load_ferm_links(&fn_links, &ks_act_paths); /* call fermion_variable measuring routines */ /* results are printed in output file */ f_meas_imp( F_OFFSET(phi), F_OFFSET(xxx), mass, &fn_links, &fn_links_dmdu0); eigVal = (double *)malloc(Nvecs*sizeof(double)); eigVec = (su3_vector **)malloc(Nvecs*sizeof(su3_vector*)); for(i=0;i<Nvecs;i++) eigVec[i]= (su3_vector*)malloc(sites_on_node*sizeof(su3_vector)); total_R_iters=Kalkreuter(eigVec, eigVal, eigenval_tol, error_decr, Nvecs, MaxIter, Restart, Kiters, EVEN, &fn_links) ; tmp = (su3_vector*)malloc(sites_on_node*sizeof(su3_vector)); for(i=0;i<Nvecs;i++) { /* Construct to odd part of the vector. * * Note that the true odd part of the eigenvector is * * i/sqrt(eigVal) Dslash Psi. But since I only compute * * the chirality the i factor is irrelevant (-i)*i=1!! */ dslash_fn_field(eigVec[i], tmp, ODD, &fn_links) ; FORSOMEPARITY(si,s,ODD){ scalar_mult_su3_vector( &(tmp[si]), 1.0/sqrt(eigVal[i]), &(eigVec[i][si]) ) ; } measure_chirality(eigVec[i], &chirality, EVENANDODD); /* Here I divide by 2 since the EVEN vector is normalized to * 1. The EVENANDODD vector is normalized to 2. I could have * normalized the EVENANDODD vector to 1 and then not devide * by to. The measure_chirality routine assumes vectors * normalized to 1. */ node0_printf("Chirality(%i): %g\n",i,chirality/2) ; } free(tmp); /** for(i=0;i<Nvecs;i++) { sprintf(label,"DENSITY(%i)",i) ; print_densities(eigVec[i], label, ny/2,nz/2,nt/2, EVEN) ; } **/ for(i=0;i<Nvecs;i++) free(eigVec[i]) ; free(eigVec) ; free(eigVal) ; #ifdef FN invalidate_all_ferm_links(&fn_links); #endif fflush(stdout); node0_printf("RUNNING COMPLETED\n"); fflush(stdout); dtime += dclock(); if(this_node==0){ printf("Time = %e seconds\n",dtime); printf("total_iters = %d\n",total_iters); printf("total Rayleigh iters = %d\n",total_R_iters); } fflush(stdout); }
/* read in parameters and coupling constants */ int readin(int prompt) { /* read in parameters for U1 monte carlo */ /* argument "prompt" is 1 if prompts are to be given for input */ complex *temp_field; complex *temp_link; register int dir, j; register site *s; int status; Real x; /* On node zero, read parameters and send to all other nodes */ if(this_node==0){ printf("\n\n"); status=0; /* get couplings and broadcast to nodes */ /* beta, mass */ IF_OK status += get_f(stdin, prompt,"mass", &par_buf.mass ); IF_OK status += get_f(stdin, prompt,"u0_s", &par_buf.u0_s ); IF_OK status += get_f(stdin, prompt,"u0_t", &par_buf.u0_t ); IF_OK status += get_f(stdin, prompt,"v_Fermi", &par_buf.v_Fermi); printf("par_buf.v_Fermi = %f\n", par_buf.v_Fermi); /* maximum no. of conjugate gradient iterations */ IF_OK status += get_i(stdin, prompt,"max_cg_iterations", &par_buf.niter ); /* maximum no. of conjugate gradient restarts */ IF_OK status += get_i(stdin, prompt,"max_cg_restarts", &par_buf.nrestart ); /* error per site for conjugate gradient */ IF_OK status += get_f(stdin, prompt,"error_per_site", &x ); IF_OK par_buf.rsqmin = x*x; /* rsqmin is r**2 in conjugate gradient */ /* New conjugate gradient normalizes rsqmin by norm of source */ /* error for propagator conjugate gradient */ IF_OK status += get_f(stdin, prompt,"error_for_propagator", &x ); IF_OK par_buf.rsqprop = x*x; IF_OK status += get_i(stdin, prompt,"Number_of_eigenvals", &par_buf.Nvecs ); IF_OK status += get_i(stdin, prompt,"Max_Rayleigh_iters", &par_buf.MaxIter ); IF_OK status += get_i(stdin, prompt,"Restart_Rayleigh", &par_buf.Restart ); IF_OK status += get_i(stdin, prompt,"Kalkreuter_iters", &par_buf.Kiters ); IF_OK status += get_f(stdin, prompt,"eigenval_tolerance", &par_buf.eigenval_tol ); IF_OK status += get_f(stdin, prompt,"error_decrease", &par_buf.error_decr); /* find out what kind of starting lattice to use */ IF_OK status += ask_starting_lattice(stdin, prompt, &(par_buf.startflag), par_buf.startfile ); if( status > 0)par_buf.stopflag=1; else par_buf.stopflag=0; } /* end if(this_node==0) */ /* Node 0 broadcasts parameter buffer to all other nodes */ broadcast_bytes((char *)&par_buf,sizeof(par_buf)); if( par_buf.stopflag != 0 )return par_buf.stopflag; niter = par_buf.niter; nrestart = par_buf.nrestart; rsqmin = par_buf.rsqmin; rsqprop = par_buf.rsqprop; mass = par_buf.mass; u0_s = par_buf.u0_s; u0_t = par_buf.u0_t; v_Fermi = par_buf.v_Fermi; Nvecs = par_buf.Nvecs ; MaxIter = par_buf.MaxIter ; Restart = par_buf.Restart ; Kiters = par_buf.Kiters ; eigenval_tol = par_buf.eigenval_tol ; error_decr = par_buf.error_decr ; startflag = par_buf.startflag; strcpy(startfile,par_buf.startfile); /* Do whatever is needed to get lattice */ if( startflag == CONTINUE ){ rephase( OFF ); } if( startflag != CONTINUE ) { if(startflag == FRESH ) { coldlat_u1(); //funnylat_u1(); /*testing SciDAC routines and eigenvalues*/ } else { temp_field = (complex *)malloc(sites_on_node*4*sizeof(complex)); if(temp_field == NULL) { printf("Malloc failed to create temp_field in setup\n"); exit(1); } restore_complex_scidac_to_field( startfile, QIO_SERIAL, temp_field, 4); //put back into site structure FORALLSITES(j,s) { for(dir=XUP;dir<=TUP;dir++){ temp_link = temp_field + 4*j + dir; s->link[dir].real = temp_link->real; s->link[dir].imag = temp_link->imag; } } free(temp_field); }//else } //if /* if a lattice was read in, put in KS phases and AP boundary condition */ phases_in = OFF; rephase( ON ); node0_printf("Calling for path table\n");fflush(stdout); /* make table of coefficients and permutations of paths in quark action */ init_path_table(&ks_act_paths); make_path_table(&ks_act_paths, NULL); node0_printf("Done with path table\n");fflush(stdout); return(0); }