1 ////////////////////////////////////////////////////////////////////////////////
2 //
3 // Copyright (c) 2008-2012 The Regents of the University of California
4 //
5 // This file is part of Qbox
6 //
7 // Qbox is distributed under the terms of the GNU General Public License
8 // as published by the Free Software Foundation, either version 2 of
9 // the License, or (at your option) any later version.
10 // See the file COPYING in the root directory of this distribution
11 // or <http://www.gnu.org/licenses/>.
12 //
13 ////////////////////////////////////////////////////////////////////////////////
14 //
15 // SpeciesHandler.cpp
16 //
17 ////////////////////////////////////////////////////////////////////////////////
18
19 #include "SpeciesHandler.h"
20 #include "Species.h"
21 #include "StrX.h"
22 using namespace xercesc;
23 #include <iostream>
24 #include <sstream>
25 #include <cassert>
26 using namespace std;
27
28 ////////////////////////////////////////////////////////////////////////////////
SpeciesHandler(Species & sp)29 SpeciesHandler::SpeciesHandler(Species& sp) :
30 sp_(sp), d_ij_alloc(false) {}
31
32 ////////////////////////////////////////////////////////////////////////////////
~SpeciesHandler()33 SpeciesHandler::~SpeciesHandler() {}
34
35 ////////////////////////////////////////////////////////////////////////////////
36 // read attributes
read(const Attributes & attributes)37 void SpeciesHandler::read(const Attributes& attributes)
38 {
39 unsigned int len = attributes.getLength();
40 for ( unsigned int index = 0; index < len; index++ )
41 {
42 string attrname = StrX(attributes.getLocalName(index)).localForm();
43 if ( attrname == "l" )
44 {
45 current_l = atoi(StrX(attributes.getValue(index)).localForm());
46 }
47 else if ( attrname == "size" )
48 {
49 current_size = atoi(StrX(attributes.getValue(index)).localForm());
50 }
51 else if ( attrname == "i" )
52 {
53 current_i = atoi(StrX(attributes.getValue(index)).localForm()) - 1;
54 }
55 else if ( attrname == "j" )
56 {
57 current_j = atoi(StrX(attributes.getValue(index)).localForm()) - 1;
58 }
59 }
60 }
61
62 ////////////////////////////////////////////////////////////////////////////////
63 // allocate array for d_ij matrix
alloc_d_ij()64 void SpeciesHandler::alloc_d_ij()
65 {
66 // allocate for every l
67 sp_.d_.resize(sp_.proj_.size());
68 for ( int l = 0; l < sp_.d_.size(); l++ )
69 {
70 const int size = sp_.proj_[l].size();
71 sp_.d_[l].resize(size);
72 for ( int i = 0; i < size; i++ )
73 {
74 sp_.d_[l][i].resize(size);
75 }
76 }
77 d_ij_alloc = true;
78 }
79
80 ////////////////////////////////////////////////////////////////////////////////
startElement(const XMLCh * const uri,const XMLCh * const localname,const XMLCh * const qname,const Attributes & attributes)81 void SpeciesHandler::startElement(const XMLCh* const uri,
82 const XMLCh* const localname, const XMLCh* const qname,
83 const Attributes& attributes)
84 {
85 // cout << " SpeciesHandler::startElement " << StrX(qname) << endl;
86
87 string locname = StrX(localname).localForm();
88
89 if ( locname == "species" )
90 {
91 // check for the case where the species is a link to another uri
92 unsigned int len = attributes.getLength();
93 for ( unsigned int index = 0; index < len; index++ )
94 {
95 string attrname = StrX(attributes.getLocalName(index)).localForm();
96 if ( attrname == "name" )
97 {
98 current_name = StrX(attributes.getValue(index)).localForm();
99 sp_.name_ = current_name;
100 }
101 else if ( attrname == "href" )
102 {
103 current_href = StrX(attributes.getValue(index)).localForm();
104 sp_.uri_ = current_href;
105 }
106 }
107 }
108 else if ( locname == "norm_conserving_pseudopotential" )
109 {
110 sp_.type_ = Species::NCPP;
111 }
112 else if ( locname == "norm_conserving_semilocal_pseudopotential" )
113 {
114 sp_.type_ = Species::SLPP;
115 }
116 else if ( locname == "core_density" )
117 {
118 read(attributes);
119 }
120 else if ( locname == "local_potential" )
121 {
122 read(attributes);
123 }
124 else if ( locname == "projector" )
125 {
126 read(attributes);
127 }
128 else if ( locname == "d_ij" )
129 {
130 read(attributes);
131 }
132 }
133
134 ////////////////////////////////////////////////////////////////////////////////
endElement(const XMLCh * const uri,const XMLCh * const localname,const XMLCh * const qname,string & content)135 void SpeciesHandler::endElement(const XMLCh* const uri,
136 const XMLCh* const localname, const XMLCh* const qname, string& content)
137 {
138 string locname = StrX(localname).localForm();
139 istringstream stst(content);
140
141 if ( locname == "description" )
142 {
143 // reject ambiguous case where both the href and the definition are given
144 if ( current_href != "" )
145 {
146 cout << " SpeciesHandler: ambiguous definition: uri=" << StrX(uri)
147 << endl << " using local definition (href: " << current_href
148 << " ignored)" << endl;
149 }
150 sp_.description_ = content;
151 }
152 else if ( locname == "atomic_number" )
153 {
154 stst >> sp_.atomic_number_;
155 }
156 else if ( locname == "mass" )
157 {
158 stst >> sp_.mass_;
159 }
160 else if ( locname == "symbol" )
161 {
162 stst >> skipws >> sp_.symbol_;
163 }
164 else if ( locname == "valence_charge" )
165 {
166 stst >> sp_.zval_;
167 }
168 else if ( locname == "lmax" )
169 {
170 stst >> sp_.lmax_;
171 }
172 else if ( locname == "llocal" )
173 {
174 stst >> sp_.llocal_;
175 }
176 else if ( locname == "nquad" )
177 {
178 stst >> sp_.nquad_;
179 }
180 else if ( locname == "rquad" )
181 {
182 stst >> sp_.rquad_;
183 }
184 else if ( locname == "mesh_spacing" )
185 {
186 stst >> sp_.deltar_;
187 }
188 else if ( locname == "radial_potential" )
189 {
190 assert(sp_.type_ == Species::NCPP);
191 if ( current_l + 1 > sp_.vps_.size() )
192 {
193 sp_.vps_.resize(current_l + 1);
194 sp_.phi_.resize(current_l + 1);
195 }
196 sp_.vps_[current_l].resize(current_size);
197 for ( int i = 0; i < current_size; i++ )
198 stst >> sp_.vps_[current_l][i];
199 }
200 else if ( locname == "local_potential" )
201 {
202 assert(sp_.type_ == Species::SLPP);
203 sp_.vlocal_.resize(current_size);
204 for ( int i = 0; i < current_size; i++ )
205 stst >> sp_.vlocal_[i];
206 }
207 else if ( locname == "radial_function" )
208 {
209 assert(sp_.type_ == Species::NCPP);
210 sp_.phi_[current_l].resize(current_size);
211 for ( int i = 0; i < current_size; i++ )
212 stst >> sp_.phi_[current_l][i];
213 }
214 else if ( locname == "core_density" )
215 {
216 // read charge for nonlinear core correction
217 sp_.nlcc_.resize(current_size);
218 for ( int i = 0; i < current_size; i++ )
219 stst >> sp_.nlcc_[i];
220 }
221 else if ( locname == "projector" and sp_.type_ == Species::SLPP )
222 {
223 // read one of the projector with this angular momentum
224 // resize vector if necessary
225 if ( current_l >= sp_.proj_.size() ) sp_.proj_.resize(current_l + 1);
226 if ( current_i >= sp_.proj_[current_l].size() )
227 sp_.proj_[current_l].resize(current_i + 1);
228 sp_.proj_[current_l][current_i].resize(current_size);
229 // read the projector
230 for ( int i = 0; i < current_size; i++ )
231 stst >> sp_.proj_[current_l][current_i][i];
232 }
233 else if ( locname == "d_ij" )
234 {
235 assert(sp_.type_ == Species::SLPP);
236 if ( not d_ij_alloc ) alloc_d_ij();
237 assert(current_l < sp_.d_.size());
238 assert(current_i < sp_.d_[current_l].size());
239 assert(current_j < sp_.d_[current_l][current_i].size());
240 stst >> sp_.d_[current_l][current_i][current_j];
241 }
242 }
243
244 ////////////////////////////////////////////////////////////////////////////////
startSubHandler(const XMLCh * const uri,const XMLCh * const localname,const XMLCh * const qname,const Attributes & attributes)245 StructureHandler* SpeciesHandler::startSubHandler(const XMLCh* const uri,
246 const XMLCh* const localname, const XMLCh* const qname,
247 const Attributes& attributes)
248 {
249 // check if element qname can be processed by another StructureHandler
250 // If it can, return a pointer to the StructureHandler, otherwise return 0
251 // cout << " SpeciesHandler::startSubHandler " << StrX(qname) << endl;
252 return 0;
253 }
254
255 ////////////////////////////////////////////////////////////////////////////////
endSubHandler(const XMLCh * const uri,const XMLCh * const localname,const XMLCh * const qname,const StructureHandler * const subHandler)256 void SpeciesHandler::endSubHandler(const XMLCh* const uri,
257 const XMLCh* const localname, const XMLCh* const qname,
258 const StructureHandler* const subHandler)
259 {
260 // cout << " SpeciesHandler::endSubHandler " << StrX(qname) << endl;
261 // if any StructureHandler was created by startSubHandler, delete it
262 // delete subHandler;
263 }
264