/* DFT++ is a density functional package developed by the research group of Professor Tomas Arias Copyright 1996-2003 Sohrab Ismail-Beigi This file is part of DFT++. DFT++ is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. DFT++ is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with DFT++; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Please see the file CREDITS for a list of authors. For academic users, we request that publications using results obtained with this software reference "New algebraic formulation of density functional calculation," by Sohrab Ismail-Beigi and T.A. Arias, Computer Physics Communications 128:1-2, 1-45 (June 2000). and, if using the wavelet basis, further reference "Multiresolution analysis of electronic structure: semicardinal and wavelet bases," T.A. Arias, Reviews of Modern Physics 71:1, 267-311 (January 1999). and "Robust ab initio calculation of condensed matter: transparent convergence through semicardinal multiresolution analysis,'' I.P. Daykov, T.A. Arias, and Torkel D. Engeness, Physical Review Letters, 90:21, 216402 (May 2003). For your convenience, preprints of the above articles may be obtained from http://arXiv.org/abs/cond-mat/9909130, 9805262, and 0204411, respectively. */ #include "header.h" /////////// WL_BasisSpec ////////////////// // Default filename is "gridspec". WL_BasisSpec::WL_BasisSpec() { size_realgrid = 0; kpt_fold[0] = 0; kpt_fold[1] = 0; kpt_fold[2] = 0; basis_flag = 0; } // Setup function, called by the Everything class. void WL_BasisSpec::setup(Everything &e) { dft_log("\nSetting up wavelet BasisSpec.\n"); // Set lattice to point to the global lattice class. lattice = &(e.lattice); FILE *fp; // Read grid structure from file if ( (fp=fopen(e.basis_spec.filename,"r")) == NULL ) die("Can't open gridspec file %s for input! \n",e.basis_spec.filename); // Modified readgridspec to not read a top-level scale. This will be // specified by the DFT++ Lattice class. readgridspec(fp,gridspec); fclose(fp); // Now that we have the grid structure, get the scale ( L/#gridpts. ) // gridspec[0].scale.x = lattice->latvec.m[0][0]/gridspec[0].dim.x; // gridspec[0].scale.y = lattice->latvec.m[1][1]/gridspec[0].dim.y; // gridspec[0].scale.z = lattice->latvec.m[2][2]/gridspec[0].dim.z; // This needs to be more general. Lattice vectors are columns of latvec. vector3 a,b,c; a=lattice->latvec[0]; b=lattice->latvec[1]; c=lattice->latvec[2]; gridspec[0].scale.x = abs(a)/gridspec[0].dim.x; gridspec[0].scale.y = abs(b)/gridspec[0].dim.y; gridspec[0].scale.z = abs(c)/gridspec[0].dim.z; dft_log("\nTop level scale = [ %lf %lf %lf ] bohr\n", gridspec[0].scale.x, gridspec[0].scale.y, gridspec[0].scale.z); // compute the size of the grid int i=0; while ( gridspec[i].level >= 0 ) { size_realgrid+=(gridspec[i].dim.x*gridspec[i].dim.y*gridspec[i].dim.z); i++; } //now create the dense gridspec expandgridspec2x(gridspec,gridspec_dense); // if we are going to use dense grids - update the size if(use_dense) size_realgrid*=8; dft_log("Size of the realgrid %d\n", size_realgrid); } /////////// WL_Basis ////////////////////// WL_Basis::WL_Basis() { basis_spec = NULL; qnum=NULL; nbasis = 0; lwork = 0; } void WL_Basis::setup_template(WL_BasisSpec &bs) { // Set representation externally. // Default is realspace. // representation = REALSPACE; basis_spec = &bs; int i = 0; int max_x = 0, max_y = 0, max_z = 0; nbasis = 0; // Calculate the total number of basis elements, as well as the size // of the largest grid. while(bs.gridspec[i].level >= 0) { nbasis += (bs.gridspec[i].dim.x)*(bs.gridspec[i].dim.y)*\ (bs.gridspec[i].dim.z); if(bs.gridspec[i].dim.x > max_x) max_x = bs.gridspec[i].dim.x; if(bs.gridspec[i].dim.y > max_y) max_y = bs.gridspec[i].dim.y; if(bs.gridspec[i].dim.z > max_z) max_z = bs.gridspec[i].dim.z; i++; } dft_log("Maximum grid dimensions = [ %d %d %d ] \n",max_x,max_y,max_z); if(bs.use_dense) lwork = (2*max_x+3*HFL_O2)*(2*max_y+3*HFL_O2)*(2*max_z+3*HFL_O2); else lwork = (max_x+3*HFL_O2)*(max_y+3*HFL_O2)*(max_z+3*HFL_O2); return; } // ipd: Don't get confused here - the argument is just for namespace // compatibility with the casee of a k-point dependent basis // (planewaves) void WL_Basis::setup(const vector3 &kvec) { //qnum->kvec = kvec; return; }