Geant4  10.03.p03
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
G4AttCheck.cc
Go to the documentation of this file.
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 //
27 // $Id: G4AttCheck.cc 78955 2014-02-05 09:45:46Z gcosmo $
28 
29 #include "G4AttCheck.hh"
30 
31 #include "globals.hh"
32 
33 #include "G4AttDef.hh"
34 #include "G4AttDefStore.hh"
35 #include "G4AttValue.hh"
36 #include "G4UnitsTable.hh"
37 #include "G4UIcommand.hh"
38 
39 G4ThreadLocal G4bool G4AttCheck::fFirst = true;
40 
41 G4ThreadLocal std::set<G4String> *G4AttCheck::fUnitCategories = 0;
42 
43 G4ThreadLocal std::map<G4String,G4String> *G4AttCheck::fStandardUnits = 0;
44 
45 G4ThreadLocal std::set<G4String> *G4AttCheck::fCategories = 0;
46 
47 G4ThreadLocal std::set<G4String> *G4AttCheck::fUnits = 0;
48 
49 G4ThreadLocal std::set<G4String> *G4AttCheck::fValueTypes = 0;
50 
52 (const std::vector<G4AttValue>* values,
53  const std::map<G4String,G4AttDef>* definitions):
54  fpValues(values),
55  fpDefinitions(definitions)
56 {
57  Init();
58 
59  if (fFirst) { // Initialise static containers.
60  fFirst = false;
61 
62  // Legal Unit Category Types...
63  fUnitCategories->insert("Length");
64  fUnitCategories->insert("Energy");
65  fUnitCategories->insert("Time");
66  fUnitCategories->insert("Electric charge");
67  fUnitCategories->insert("Volumic Mass"); // (Density)
68 
69  // Corresponding Standard Units...
70  (*fStandardUnits)["Length"] = "m";
71  (*fStandardUnits)["Energy"] = "MeV";
72  (*fStandardUnits)["Time"] = "ns";
73  (*fStandardUnits)["Electric charge"] = "e+";
74  (*fStandardUnits)["Volumic Mass"] = "kg/m3";
75 
76  // Legal Categories...
77  fCategories->insert("Bookkeeping");
78  fCategories->insert("Draw");
79  fCategories->insert("Physics");
80  fCategories->insert("PickAction");
81  fCategories->insert("Association");
82 
83  // Legal units...
84  fUnits->insert("");
85  fUnits->insert("G4BestUnit");
86  // ...plus any legal unit symbol ("MeV", "km", etc.)...
88  for (size_t i = 0; i < units.size(); ++i) {
89  if (fUnitCategories->find(units[i]->GetName()) !=
90  fUnitCategories->end()) {
91  //G4cout << units[i]->GetName() << G4endl;
92  G4UnitsContainer& container = units[i]->GetUnitsList();
93  for (size_t j = 0; j < container.size(); ++j) {
94  //G4cout << container[j]->GetName() << ' '
95  // << container[j]->GetSymbol() << G4endl;
96  fUnits->insert(container[j]->GetSymbol());
97  }
98  }
99  }
100 
101  // Legal Value Types...
102  fValueTypes->insert("G4String");
103  fValueTypes->insert("G4int");
104  fValueTypes->insert("G4double");
105  fValueTypes->insert("G4ThreeVector");
106  fValueTypes->insert("G4bool");
107  }
108 }
109 
111 {
112 }
113 
114 void G4AttCheck::Init()
115 {
116  if (!fValueTypes) fValueTypes = new std::set<G4String>;
117  if (!fUnits) fUnits = new std::set<G4String>;
118  if (!fCategories) fCategories = new std::set<G4String>;
119  if (!fStandardUnits) fStandardUnits = new std::map<G4String,G4String>;
120  if (!fUnitCategories) fUnitCategories = new std::set<G4String>;
121 }
122 
123 G4bool G4AttCheck::Check(const G4String& leader) const
124 {
125  // Check only. Silent unless error - then G4cerr. Returns error.
126  G4bool error = false;
127  static G4ThreadLocal G4int iError = 0;
128  G4bool print = false;
129  if (iError < 10 || iError%100 == 0) {
130  print = true;
131  }
132  using namespace std;
133  if (!fpValues) return error; // A null values vector is a valid situation.
134  if (!fpDefinitions) {
135  ++iError;
136  error = true;
137  if (print) {
138  G4cerr <<
139  "\n*******************************************************";
140  if (leader != "") {
141  G4cerr << '\n' << leader;
142  }
143  G4cerr <<
144  "\nG4AttCheck: ERROR " << iError << ": Null definitions pointer"
145  "\n*******************************************************"
146  << G4endl;
147  }
148  return error;
149  }
150  vector<G4AttValue>::const_iterator iValue;
151  for (iValue = fpValues->begin(); iValue != fpValues->end(); ++iValue) {
152  const G4String& valueName = iValue->GetName();
153  const G4String& value = iValue->GetValue();
154  map<G4String,G4AttDef>::const_iterator iDef =
155  fpDefinitions->find(valueName);
156  if (iDef == fpDefinitions->end()) {
157  ++iError;
158  error = true;
159  if (print) {
160  G4cerr <<
161  "\n*******************************************************";
162  if (leader != "") {
163  G4cerr << '\n' << leader;
164  }
165  G4cerr <<
166  "\nG4AttCheck: ERROR " << iError << ": No G4AttDef for G4AttValue \""
167  << valueName << "\": " << value <<
168  "\n*******************************************************"
169  << G4endl;
170  }
171  } else {
172  const G4String& category = iDef->second.GetCategory();
173  const G4String& extra = iDef->second.GetExtra();
174  const G4String& valueType = iDef->second.GetValueType();
175  if (fCategories->find(category) == fCategories->end()) {
176  ++iError;
177  error = true;
178  if (print) {
179  G4cerr <<
180  "\n*******************************************************";
181  if (leader != "") {
182  G4cerr << '\n' << leader;
183  }
184  G4cerr <<
185  "\nG4AttCheck: ERROR " << iError << ": Illegal Category Field \""
186  << category << "\" for G4AttValue \""
187  << valueName << "\": " << value <<
188  "\n Possible Categories:";
189  set<G4String>::iterator i;
190  for (i = fCategories->begin(); i != fCategories->end(); ++i) {
191  G4cerr << ' ' << *i;
192  }
193  G4cerr <<
194  "\n*******************************************************"
195  << G4endl;
196  }
197  }
198  if(category == "Physics" && fUnits->find(extra) == fUnits->end()) {
199  ++iError;
200  error = true;
201  if (print) {
202  G4cerr <<
203  "\n*******************************************************";
204  if (leader != "") {
205  G4cerr << '\n' << leader;
206  }
207  G4cerr <<
208  "\nG4AttCheck: ERROR " << iError << ": Illegal Extra field \""
209  << extra << "\" for G4AttValue \""
210  << valueName << "\": " << value <<
211  "\n Possible Extra fields if Category==\"Physics\":\n ";
212  set<G4String>::iterator i;
213  for (i = fUnits->begin(); i != fUnits->end(); ++i) {
214  G4cerr << ' ' << *i;
215  }
216  G4cerr <<
217  "\n*******************************************************"
218  << G4endl;
219  }
220  }
221  if (fValueTypes->find(valueType) == fValueTypes->end()) {
222  ++iError;
223  error = true;
224  if (print) {
225  G4cerr <<
226  "\n*******************************************************";
227  if (leader != "") {
228  G4cerr << '\n' << leader;
229  }
230  G4cerr <<
231  "\nG4AttCheck: ERROR " << iError << ": Illegal Value Type field \""
232  << valueType << "\" for G4AttValue \""
233  << valueName << "\": " << value <<
234  "\n Possible Value Types:";
235  set<G4String>::iterator i;
236  for (i = fValueTypes->begin(); i != fValueTypes->end(); ++i) {
237  G4cerr << ' ' << *i;
238  }
239  G4cerr <<
240  "\n*******************************************************"
241  << G4endl;
242  }
243  }
244  }
245  }
246  return error;
247 }
248 
249 std::ostream& operator<< (std::ostream& os, const G4AttCheck& ac)
250 {
251  using namespace std;
252  if (!ac.fpDefinitions) {
253  os << "G4AttCheck: ERROR: zero definitions pointer." << endl;
254  return os;
255  }
256  G4String storeKey;
257  if (G4AttDefStore::GetStoreKey(ac.fpDefinitions, storeKey)) {
258  os << storeKey << ':' << endl;
259  }
260  if (!ac.fpValues) {
261  // A null values vector is a valid situation.
262  os << "G4AttCheck: zero values pointer." << endl;
263  return os;
264  }
265  vector<G4AttValue>::const_iterator iValue;
266  for (iValue = ac.fpValues->begin(); iValue != ac.fpValues->end(); ++iValue) {
267  const G4String& valueName = iValue->GetName();
268  const G4String& value = iValue->GetValue();
269  map<G4String,G4AttDef>::const_iterator iDef =
270  ac.fpDefinitions->find(valueName);
271  G4bool error = false;
272  if (iDef == ac.fpDefinitions->end()) {
273  error = true;
274  os << "G4AttCheck: ERROR: No G4AttDef for G4AttValue \""
275  << valueName << "\": " << value << endl;
276  } else {
277  const G4String& category = iDef->second.GetCategory();
278  const G4String& extra = iDef->second.GetExtra();
279  const G4String& valueType = iDef->second.GetValueType();
280  if (ac.fCategories->find(category) == ac.fCategories->end()) {
281  error = true;
282  os <<
283  "G4AttCheck: ERROR: Illegal Category Field \"" << category
284  << "\" for G4AttValue \"" << valueName << "\": " << value <<
285  "\n Possible Categories:";
286  set<G4String>::iterator i;
287  for (i = ac.fCategories->begin(); i != ac.fCategories->end(); ++i) {
288  os << ' ' << *i;
289  }
290  os << endl;
291  }
292  if(category == "Physics" && ac.fUnits->find(extra) == ac.fUnits->end()) {
293  error = true;
294  os <<
295  "G4AttCheck: ERROR: Illegal Extra field \""<< extra
296  << "\" for G4AttValue \"" << valueName << "\": " << value <<
297  "\n Possible Extra fields if Category==\"Physics\":\n ";
298  set<G4String>::iterator i;
299  for (i = ac.fUnits->begin(); i != ac.fUnits->end(); ++i) {
300  os << ' ' << *i;
301  }
302  os << endl;
303  }
304  if (ac.fValueTypes->find(valueType) == ac.fValueTypes->end()) {
305  error = true;
306  os <<
307  "G4AttCheck: ERROR: Illegal Value Type field \"" << valueType
308  << "\" for G4AttValue \"" << valueName << "\": " << value <<
309  "\n Possible Value Types:";
310  set<G4String>::iterator i;
311  for (i = ac.fValueTypes->begin(); i != ac.fValueTypes->end(); ++i) {
312  os << ' ' << *i;
313  }
314  os << endl;
315  }
316  }
317  if (!error) {
318  os << iDef->second.GetDesc()
319  << " (" << valueName
320  << "): " << value;
321  if (iDef->second.GetCategory() == "Physics" &&
322  !iDef->second.GetExtra().empty()) {
323  os << " (" << iDef->second.GetExtra() << ")";
324  }
325  os << endl;
326  }
327  }
328  return os;
329 }
330 
331 void G4AttCheck::AddValuesAndDefs
332 (std::vector<G4AttValue>* standardValues,
333  std::map<G4String,G4AttDef>* standardDefinitions,
334  const G4String& oldName,
335  const G4String& name,
336  const G4String& value,
337  const G4String& extra,
338  const G4String& description) const
339 {
340  // Add new G4AttDeff...
341  standardValues->push_back(G4AttValue(name,value,""));
342  // Copy original G4AttDef...
343  (*standardDefinitions)[name] = fpDefinitions->find(oldName)->second;
344  // ...and make appropriate changes...
345  (*standardDefinitions)[name].SetName(name);
346  (*standardDefinitions)[name].SetExtra(extra);
347  if (description != "") (*standardDefinitions)[name].SetDesc(description);
348 }
349 
351 (std::vector<G4AttValue>* standardValues,
352  std::map<G4String,G4AttDef>* standardDefinitions) const
353 {
354  // Places standard versions in provided vector and map and returns error.
355  // Assumes valid input. Use Check to check.
356  using namespace std;
357  G4bool error = false;
358  vector<G4AttValue>::const_iterator iValue;
359  for (iValue = fpValues->begin(); iValue != fpValues->end(); ++iValue) {
360  const G4String& valueName = iValue->GetName();
361  const G4String& value = iValue->GetValue();
362  map<G4String,G4AttDef>::const_iterator iDef =
363  fpDefinitions->find(valueName);
364  if (iDef == fpDefinitions->end()) {
365  error = true;
366  } else {
367  const G4String& category = iDef->second.GetCategory();
368  const G4String& extra = iDef->second.GetExtra();
369  const G4String& valueType = iDef->second.GetValueType();
370  if (fCategories->find(category) == fCategories->end() ||
371  (category == "Physics" && fUnits->find(extra) == fUnits->end()) ||
372  fValueTypes->find(valueType) == fValueTypes->end()) {
373  error = true;
374  } else {
375  if (category != "Physics") { // Simply copy...
376  standardValues->push_back(*iValue);
377  (*standardDefinitions)[valueName] =
378  fpDefinitions->find(valueName)->second;
379  } else { // "Physics"...
380  if (extra.empty()) { // Dimensionless...
381  if (valueType == "G4ThreeVector") { // Split vector into 3...
382  G4ThreeVector internalValue =
384  AddValuesAndDefs
385  (standardValues,standardDefinitions,
386  valueName,valueName+"-X",
387  G4UIcommand::ConvertToString(internalValue.x()),"",
388  fpDefinitions->find(valueName)->second.GetDesc()+"-X");
389  AddValuesAndDefs
390  (standardValues,standardDefinitions,
391  valueName,valueName+"-Y",
392  G4UIcommand::ConvertToString(internalValue.y()),"",
393  fpDefinitions->find(valueName)->second.GetDesc()+"-Y");
394  AddValuesAndDefs
395  (standardValues,standardDefinitions,
396  valueName,valueName+"-Z",
397  G4UIcommand::ConvertToString(internalValue.z()),"",
398  fpDefinitions->find(valueName)->second.GetDesc()+"-Z");
399  } else { // Simply copy...
400  standardValues->push_back(*iValue);
401  (*standardDefinitions)[valueName] =
402  fpDefinitions->find(valueName)->second;
403  }
404  } else { // Dimensioned...
405  G4String valueAndUnit;
406  G4String unit;
407  if (extra == "G4BestUnit") {
408  valueAndUnit = value;
409  valueAndUnit = valueAndUnit.strip();
410  unit = valueAndUnit.substr(valueAndUnit.rfind(' ')+1);
411  } else {
412  valueAndUnit = value + ' ' + extra;
413  valueAndUnit = valueAndUnit.strip();
414  unit = extra;
415  }
416  G4String unitCategory = G4UnitDefinition::GetCategory(unit);
417  if (fUnitCategories->find(unitCategory) != fUnitCategories->end()) {
418  G4String standardUnit = (*fStandardUnits)[unitCategory];
419  G4double valueOfStandardUnit =
420  G4UnitDefinition::GetValueOf(standardUnit);
421 // G4String exstr = iDef->second.GetExtra();
422  if (valueType == "G4ThreeVector") { // Split vector into 3...
423  G4ThreeVector internalValue =
425  AddValuesAndDefs
426  (standardValues,standardDefinitions,
427  valueName,valueName+"-X",
429  (internalValue.x()/valueOfStandardUnit),
430  standardUnit,
431  fpDefinitions->find(valueName)->second.GetDesc()+"-X");
432  AddValuesAndDefs
433  (standardValues,standardDefinitions,
434  valueName,valueName+"-Y",
436  (internalValue.y()/valueOfStandardUnit),
437  standardUnit,
438  fpDefinitions->find(valueName)->second.GetDesc()+"-Y");
439  AddValuesAndDefs
440  (standardValues,standardDefinitions,
441  valueName,valueName+"-Z",
443  (internalValue.z()/valueOfStandardUnit),
444  standardUnit,
445  fpDefinitions->find(valueName)->second.GetDesc()+"-Z");
446  } else {
447  G4double internalValue =
449  AddValuesAndDefs
450  (standardValues,standardDefinitions,
451  valueName,valueName,
453  (internalValue/valueOfStandardUnit),
454  standardUnit);
455  }
456  }
457  }
458  }
459  }
460  }
461  }
462  if (error) {
463  G4cerr << "G4AttCheck::Standard: Conversion error." << G4endl;
464  }
465  return error;
466 }
const XML_Char * name
Definition: expat.h:151
void Init()
Definition: G4IonTable.cc:90
G4AttCheck(const std::vector< G4AttValue > *values, const std::map< G4String, G4AttDef > *definitions)
Definition: G4AttCheck.cc:52
G4bool GetStoreKey(const std::map< G4String, G4AttDef > *definitions, G4String &key)
double x() const
G4String strip(G4int strip_Type=trailing, char c=' ')
std::vector< G4UnitsCategory * > G4UnitsTable
Definition: G4UnitsTable.hh:60
friend std::ostream & operator<<(std::ostream &, const G4AttCheck &)
Definition: G4AttCheck.cc:249
static G4String ConvertToString(G4bool boolVal)
Definition: G4UIcommand.cc:372
G4bool Standard(std::vector< G4AttValue > *standardValues, std::map< G4String, G4AttDef > *standardDefinitions) const
Definition: G4AttCheck.cc:351
#define G4ThreadLocal
Definition: tls.hh:89
int G4int
Definition: G4Types.hh:78
static G4ThreeVector ConvertTo3Vector(const char *st)
Definition: G4UIcommand.cc:475
double z() const
static G4double ConvertToDimensionedDouble(const char *st)
Definition: G4UIcommand.cc:463
static G4double GetValueOf(const G4String &)
const XML_Char int const XML_Char * value
Definition: expat.h:331
bool G4bool
Definition: G4Types.hh:79
void print(G4double elem)
static G4UnitsTable & GetUnitsTable()
static G4String GetCategory(const G4String &)
G4bool Check(const G4String &leader="") const
Definition: G4AttCheck.cc:123
double y() const
#define G4endl
Definition: G4ios.hh:61
static PROLOG_HANDLER error
Definition: xmlrole.cc:112
double G4double
Definition: G4Types.hh:76
std::vector< G4UnitDefinition * > G4UnitsContainer
G4GLOB_DLL std::ostream G4cerr
static G4ThreeVector ConvertToDimensioned3Vector(const char *st)
Definition: G4UIcommand.cc:485