Пример #1
0
int main(int argc,char *argv[])
{
  FILE      *fp;
  int       nnn[] = { 8, 10, 12, 15, 16, 18, 20, 24, 25, 27, 30, 32, 36, 40,
		      45, 48, 50, 54, 60, 64, 72, 75, 80, 81, 90, 100 };
#define NNN asize(nnn)
  int       *niter;
  int       i,j,n,nit,ntot,n3;
  double    t,nflop;
  double    *rt,*ct;
  t_complex ***g;
  real      ***h;
  
  snew(rt,NNN);
  snew(ct,NNN);
  snew(niter,NNN);
  
  for(i=0; (i<NNN); i++) {
    n = nnn[i];
    fprintf(stderr,"\rReal %d     ",n);
    if (n < 16)
      niter[i] = 100;
    else if (n < 26)
      niter[i] = 50;
    else if (n < 51)
      niter[i] = 10;
    else
      niter[i] = 5;
    nit = niter[i];
      
    h   = mk_rgrid(n+2,n,n);
    start_time();
    for(j=0; (j<nit); j++) {
      testrft(stdout,h,n,n,n,(j==0));
    }
    update_time();
    rt[i] = node_time();
    free_rgrid(h,n,n);
    
    fprintf(stderr,"\rComplex %d     ",n);
    g   = mk_cgrid(n,n,n);
    start_time();
    for(j=0; (j<nit); j++) {
      testfft(stdout,g,n,n,n,(j==0));
    }
    update_time();
    ct[i] = node_time();
    free_cgrid(g,n,n);
  }
  fprintf(stderr,"\n");
  fp=xvgropen("timing.xvg","FFT timings per grid point","n","t (s)");
  for(i=0; (i<NNN); i++) {
    n3 = 2*niter[i]*nnn[i]*nnn[i]*nnn[i];
    fprintf(fp,"%10d  %10g  %10g\n",nnn[i],rt[i]/n3,ct[i]/n3);
  }
  gmx_fio_fclose(fp);
  
  return 0;
}
Пример #2
0
real do_opt_pppm(FILE *log,       bool bVerbose,
		 t_inputrec *ir,  int natoms,
		 rvec x[],        rvec f[],
		 real charge[],   rvec box,
		 real phi[],      t_commrec *cr,
		 t_nrnb *nrnb,    rvec beta,
		 t_fftgrid *grid, bool bOld)
{
  real      ***ghat;
  int       nx,ny,nz;
  real      ener;
  
  ener = 0.0;
    
  fprintf(log,"Generating Ghat function\n");
  nx     = ir->nkx;
  ny     = ir->nky;
  nz     = ir->nkz;
  ghat   = mk_rgrid(nx,ny,nz);
  mk_ghat(NULL,nx,ny,nz,ghat,box,ir->rcoulomb_switch,ir->rcoulomb,TRUE,bOld);
  
  /* pr_scalar_gk("generghat.xvg",nx,ny,nz,box,ghat); */
  
  /* Now start the actual PPPM procedure.
   * First step: spreading the charges over the grid.
   */
  /* Make the grid empty */
  clear_fftgrid(grid);
  
  spread_q(log,bVerbose,0,natoms,x,charge,box,grid,nrnb);
  
  /* Second step: solving the poisson equation in Fourier space */
  solve_pppm(log,cr,grid,ghat,box,bVerbose,nrnb);
  
  /* Third and last step: gather the forces, energies and potential
   * from the grid.
   */
  ener=gather_f(log,bVerbose,0,natoms,x,f,charge,box,phi,grid,beta,nrnb);

  free_rgrid(ghat,nx,ny);
    
  return ener;
}
Пример #3
0
void init_pppm(FILE *log,t_commrec *cr,t_nsborder *nsb,
	       bool bVerbose,bool bOld,rvec box,char *ghatfn,t_inputrec *ir)
{
  int   nx,ny,nz,m,porder;
  ivec  grids;
  real  r1,rc;
  const real tol = 1e-5;
  rvec  spacing;

#ifdef WITHOUT_FFTW
  fatal_error(0,"PPPM used, but GROMACS was compiled without FFTW support!\n");
#endif

  if (cr != NULL) {
    if (cr->nnodes > 1)
	fprintf(log,"Initializing parallel PPPM.\n");
  }
  fprintf(log,"Will use the PPPM algorithm for long-range electrostatics\n");
 
  if (!fexist(ghatfn)) {    
    beta[XX]=beta[YY]=beta[ZZ]= 1.85;
    nx     = ir->nkx;
    ny     = ir->nky;
    nz     = ir->nkz;
    
    fprintf(log,"Generating Ghat function\n");
    fprintf(log,"Grid size is %d x %d x %d\n",nx,ny,nz);

    if ((nx < 4) || (ny < 4) || (nz < 4)) 
      fatal_error(0,"Grid must be at least 4 points in all directions");
      
    ghat   = mk_rgrid(nx,ny,nz);
    mk_ghat(NULL,nx,ny,nz,ghat,box,ir->rcoulomb_switch,ir->rcoulomb,TRUE,bOld);
    
    if (bVerbose)
      pr_scalar_gk("generghat.xvg",nx,ny,nz,box,ghat);
  }
  else {
    fprintf(stderr,"Reading Ghat function from %s\n",ghatfn);
    ghat = rd_ghat(log,ghatfn,grids,spacing,beta,&porder,&r1,&rc);
    
    /* Check whether cut-offs correspond */
    if ((fabs(r1-ir->rcoulomb_switch)>tol) || (fabs(rc-ir->rcoulomb)>tol)) {
      fprintf(log,"rcoulomb_switch = %10.3e  rcoulomb = %10.3e"
	          "  r1 = %10.3e  rc = %10.3e\n",
	      ir->rcoulomb_switch,ir->rcoulomb,r1,rc);
      fflush(log);
      fatal_error(0,"Cut-off lengths in tpb file and Ghat file %s "
		  "do not match\nCheck your log file!",ghatfn);
    }
      
    /* Check whether boxes correspond */
    for(m=0; (m<DIM); m++)
      if (fabs(box[m]-grids[m]*spacing[m]) > tol) {
	pr_rvec(log,0,"box",box,DIM);
	pr_rvec(log,0,"grid-spacing",spacing,DIM);
	pr_ivec(log,0,"grid size",grids,DIM);
	fflush(log);
	fatal_error(0,"Box sizes in tpb file and Ghat file %s do not match\n"
		    "Check your log file!",ghatfn);
      }

    if (porder != 2)
      fatal_error(0,"porder = %d, should be 2 in %s",porder,ghatfn);
      
    nx = grids[XX];
    ny = grids[YY];
    nz = grids[ZZ];
    
    if (bVerbose)
      pr_scalar_gk("optimghat.xvg",nx,ny,nz,box,ghat);
  }
  /* Now setup the FFT things */
  grid = mk_fftgrid(log,PAR(cr),nx,ny,nz,ir->bOptFFT);
}
Пример #4
0
int gmx_pppm_init(FILE *log,      t_commrec *cr,
                  const output_env_t oenv, gmx_bool bVerbose,
                  gmx_bool bOld,      matrix box,
                  char *ghatfn,   t_inputrec *ir,
                  gmx_bool bReproducible)
{
  int   nx,ny,nz,m,porder;
  ivec  grids;
  real  r1,rc;
  const real tol = 1e-5;
  rvec  box_diag,spacing;

#ifdef DISABLE_PPPM
    gmx_fatal(FARGS,"PPPM is not functional in the current version, we plan to implement PPPM through a small modification of the PME code.");
    return -1;
#else
    
#ifdef GMX_WITHOUT_FFTW
  gmx_fatal(FARGS,"PPPM used, but GROMACS was compiled without FFTW support!\n");
#endif

  if (log) {
    if (cr != NULL) {
      if (cr->nnodes > 1)
	fprintf(log,"Initializing parallel PPPM.\n");
    }
    fprintf(log,
	    "Will use the PPPM algorithm for long-range electrostatics\n");
  }
 
  for(m=0; m<DIM; m++)
    box_diag[m] = box[m][m];

  if (!gmx_fexist(ghatfn)) {    
    beta[XX]=beta[YY]=beta[ZZ]= 1.85;
    nx     = ir->nkx;
    ny     = ir->nky;
    nz     = ir->nkz;
   
    if (log) {
      fprintf(log,"Generating Ghat function\n");
      fprintf(log,"Grid size is %d x %d x %d\n",nx,ny,nz);
    }

    if ((nx < 4) || (ny < 4) || (nz < 4)) 
      gmx_fatal(FARGS,"Grid must be at least 4 points in all directions");
      
    ghat   = mk_rgrid(nx,ny,nz);
    mk_ghat(NULL,nx,ny,nz,ghat,box_diag,
	    ir->rcoulomb_switch,ir->rcoulomb,TRUE,bOld);
    
    if (bVerbose)
      pr_scalar_gk("generghat.xvg",oenv,nx,ny,nz,box_diag,ghat);
  }
  else {
    fprintf(stderr,"Reading Ghat function from %s\n",ghatfn);
    ghat = rd_ghat(log,oenv,ghatfn,grids,spacing,beta,&porder,&r1,&rc);
    
    /* Check whether cut-offs correspond */
    if ((fabs(r1-ir->rcoulomb_switch)>tol) || (fabs(rc-ir->rcoulomb)>tol)) {
      if (log) {
	fprintf(log,"rcoulomb_switch = %10.3e  rcoulomb = %10.3e"
		"  r1 = %10.3e  rc = %10.3e\n",
		ir->rcoulomb_switch,ir->rcoulomb,r1,rc);
	fflush(log);
      }
      gmx_fatal(FARGS,"Cut-off lengths in tpb file and Ghat file %s "
		  "do not match\nCheck your log file!",ghatfn);
    }
      
    /* Check whether boxes correspond */
    for(m=0; (m<DIM); m++)
      if (fabs(box_diag[m]-grids[m]*spacing[m]) > tol) {
	if (log) {
	  pr_rvec(log,0,"box",box_diag,DIM,TRUE);
	  pr_rvec(log,0,"grid-spacing",spacing,DIM,TRUE);
	  pr_ivec(log,0,"grid size",grids,DIM,TRUE);
	  fflush(log);
	}
	gmx_fatal(FARGS,"Box sizes in tpb file and Ghat file %s do not match\n"
		    "Check your log file!",ghatfn);
      }

    if (porder != 2)
      gmx_fatal(FARGS,"porder = %d, should be 2 in %s",porder,ghatfn);
      
    nx = grids[XX];
    ny = grids[YY];
    nz = grids[ZZ];
    
    if (bVerbose)
      pr_scalar_gk("optimghat.xvg",oenv,nx,ny,nz,box_diag,ghat);
  }
  /* Now setup the FFT things */
#ifdef GMX_MPI
  cr->mpi_comm_mygroup=cr->mpi_comm_mysim;
#endif
  grid = mk_fftgrid(nx,ny,nz,NULL,NULL,cr,bReproducible);
  
  return 0;
#endif
}