1 /* Ergo, version 3.8, a program for linear scaling electronic structure
2  * calculations.
3  * Copyright (C) 2019 Elias Rudberg, Emanuel H. Rubensson, Pawel Salek,
4  * and Anastasia Kruchinina.
5  *
6  * This program is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
18  *
19  * Primary academic reference:
20  * Ergo: An open-source program for linear-scaling electronic structure
21  * calculations,
22  * Elias Rudberg, Emanuel H. Rubensson, Pawel Salek, and Anastasia
23  * Kruchinina,
24  * SoftwareX 7, 107 (2018),
25  * <http://dx.doi.org/10.1016/j.softx.2018.03.005>
26  *
27  * For further information about Ergo, see <http://www.ergoscf.org>.
28  */
29 
30 /** @file basisinfo.h
31 
32     \brief Code for setting up basis functions starting from shells.
33 
34     @author: Elias Rudberg <em>responsible</em>.
35 */
36 
37 #ifndef BASISINFO_HEADER
38 #define BASISINFO_HEADER
39 
40 /* for NULL */
41 #include <stdlib.h>
42 
43 #include "realtype.h"
44 #include "integral_info.h"
45 /* for Molecule */
46 #include "molecule.h"
47 
48 #include "basisset.h"
49 
50 struct DistributionSpecStruct {
51   ergo_real coeff;           /**< Coefficient A */
52   ergo_real exponent;        /**< exponent alfa */
53   ergo_real extent;          /* FIXME ELIAS: remove this here since the "extent" you want to use depends on what you are doing? */
54   ergo_real centerCoords[3]; /**< x0, y0, z0    */
55   char monomialInts[4];  /**< nx, ny, nz    */
56 };
57 
58 struct DistributionSpecStructLabeled {
59   int basisFuncIndex_1;
60   int basisFuncIndex_2;
61   int pairIndex;
62   int groupID;
63   ergo_real limitingFactor; // squareroot of repulsion integral of this distr with itself.
64   ergo_real dmatElement;
65   DistributionSpecStruct distr;
66 };
67 
68 
69 #define MAX_NO_OF_CONTR_GAUSSIANS 20
70 
71 struct ShellSpecStruct {
72   ergo_real coeffList[MAX_NO_OF_CONTR_GAUSSIANS];
73   ergo_real exponentList[MAX_NO_OF_CONTR_GAUSSIANS];
74   ergo_real sizeList[MAX_NO_OF_CONTR_GAUSSIANS];
75   ergo_real padding; /* We keep this for compatibility with old density files... */
76   ergo_real centerCoords[3]; /* x0, y0, z0 */
77   int noOfContr;
78   int shellType;
79   int shell_ID;
80   int noOfBasisFuncs;
81   int startIndexInMatrix; /* start index in density matrix  */
82   int dummy; /* padding to make sure the size of this structure is a multiple of 8 bytes */
83 };
84 
85 struct BasisFuncStruct {
86   int noOfContr;
87   ergo_real coeffList[MAX_NO_OF_CONTR_GAUSSIANS];
88   ergo_real exponentList[MAX_NO_OF_CONTR_GAUSSIANS];
89   ergo_real extent;
90   Vector3D centerCoords; /* x0, y0, z0 */
91   int shellType; /* 0 <-> 's', 1 <-> 'p', 2 <-> 'd' etc */
92   int functionNumber; /* -1,0,1 for 'p', -2,-1,0,1,2 for 'd', etc */
93   int noOfSimplePrimitives;
94   int simplePrimitiveIndex;
95   int noOfTermsInPolynomial;
96   basis_func_term_struct poly[MAX_NO_OF_TERMS_IN_BASIS_FUNC_POLY];
97 };
98 
99 
100 struct basis_set_range_struct {
101   int startAtomIndex;
102   int count;
103   basisset_info* basisset;
104 };
105 
106 struct BasissetNameRange {
107   int startAtomIndex;
108   int count;
109   char* basisSetFileName;
110 };
111 
112 struct BasisInfoStruct {
113   int use_6_d_funcs; /**< Whether to use 6 d-type basis functions
114 			instead of the usual 5 functions. This option
115 			exists to make it possible to get results
116 			compatible with other codes that have d-type
117 			functions defined in that way.  */
118   int noOfShells;
119   ShellSpecStruct* shellList;
120   int noOfBasisFuncs;
121   BasisFuncStruct* basisFuncList;
122   int noOfSimplePrimitives;
123   DistributionSpecStruct* simplePrimitiveList;
124 
125   /** Initializes all the fields to sane values. */
126   BasisInfoStruct(int use_6_d_funcs_ = 0);
127 
128   /** Copies values from another BasisInfoStruct. */
129   BasisInfoStruct(const BasisInfoStruct & b);
130 
131   ~BasisInfoStruct();
132 
133   void addBasisfuncsForPoint(ergo_real x,
134 			     ergo_real y,
135 			     ergo_real z,
136 			     int shellType,
137 			     ergo_real exponent,
138 			     const IntegralInfo & integralInfo,
139 			     int print_raw,
140 			     int do_normalization,
141 			     int skip_sort_shells);
142 
143   void addBasisfuncsForAtomList(const Atom* atomList,
144 				int noOfAtoms,
145 				const basisset_info & basissetDefault,
146 				int noOfRanges,
147 				const basis_set_range_struct* rangeList,
148 				const IntegralInfo & integralInfo,
149 				int print_raw,
150 				int do_normalization,
151 				int skip_sort_shells);
152 
153   int addBasisfuncsForMolecule(const Molecule& molecule,
154 				  const char* basisset_filename_default,
155 				  int noOfRanges,
156 				  const BasissetNameRange* rangeList,
157 				  const IntegralInfo& integralInfo,
158 				  int print_raw,
159 				  int do_normalization,
160 				  int skip_sort_shells);
161 
162   static int getNoOfBasisFuncsForAtomType(const basisset_info & basisset,
163 					  const IntegralInfo & integralInfo,
164 					  int atomCharge,
165 					  int use_6_d_funcs);
166 
167   BasisInfoStruct *permuteShells(const int *shellMap,
168                                  const IntegralInfo& ii) const;
169 
170   int normalizeShells(const IntegralInfo& integralInfo);
171 
172   int get_basis_funcs();
173 
174   int getSimplePrimitivesAll(const IntegralInfo& integralInfo);
175 
176   // Stuff needed for Chunks&Tasks usage
177   void write_to_buffer ( char * dataBuffer, size_t const bufferSize ) const;
178   size_t get_size() const;
179   void assign_from_buffer ( char const * dataBuffer, size_t const bufferSize);
180 };
181 
182 
183 
184 /** Provides temporary storage for
185     compute_integral_of_square_of_basis_func.  Stack used to be the
186     storage but many operating systems do not like to allocate so
187     much space for stack, particularly when many threads are
188     present. */
189 struct SquareFuncIntegrator {
190   const int MAX_NO_OF_PRIMS;
191   DistributionSpecStruct *list;
192   DistributionSpecStruct *productlist;
SquareFuncIntegratorSquareFuncIntegrator193 SquareFuncIntegrator() :  MAX_NO_OF_PRIMS(44444)
194   {
195     list = new DistributionSpecStruct[MAX_NO_OF_PRIMS];
196     productlist = new DistributionSpecStruct[MAX_NO_OF_PRIMS];
197   }
~SquareFuncIntegratorSquareFuncIntegrator198   ~SquareFuncIntegrator()
199   {
200     delete []list;
201     delete []productlist;
202   }
203   ergo_real computeIntegralOfSquareOfBasisFunc
204   (const IntegralInfo& integralInfo, BasisFuncStruct* basisFunc, int use_6_d_funcs);
205 
206   ergo_real getShellFactor(const IntegralInfo& integralInfo,
207 			   ergo_real exponent, int shellType, int use_6_d_funcs);
208 };
209 
210 
211 
212 
213 #ifdef ERGO_ENABLE_DEPRECATED
214 
215 int basisinfo_construct_multi_basis(BasisInfoStruct* result_basisInfo,
216 				    const Molecule* molecule,
217 				    const char* basisset_filename_default,
218 				    const Molecule* ghostMolecule,
219 				    const char* ghost_molecule_basisset_filename,
220 				    int noOfRanges,
221 				    const BasissetNameRange* rangeList,
222 				    IntegralInfo* integralInfo,
223 				    int print_raw,
224 				    int do_normalization,
225 				    int skip_sort_shells,
226 				    int skip_standard_basis);
227 struct AtomInfoStruct_{
228   int charge;
229   ergo_real coords[3];
230 };
231 typedef struct AtomInfoStruct_ AtomInfoStruct;
232 #endif
233 
234 int get_basis_funcs(BasisInfoStruct* basisInfo,
235 		    const IntegralInfo* integralInfo,
236 		    int do_normalization);
237 
238 int get_simple_primitives_all(BasisInfoStruct* basisInfo,
239 			      const IntegralInfo* integralInfo);
240 
241 int output_basisinfo(const BasisInfoStruct & basisInfo);
242 
243 ergo_real getSafeMaxDistance(const BasisInfoStruct & basisInfo);
244 
245 
246 #endif
247