Jpp  17.3.1
the software that should make you happy
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
JEditTuneHV.cc
Go to the documentation of this file.
1 #include <iostream>
2 #include <iomanip>
3 #include <fstream>
4 #include <sstream>
5 #include <set>
6 
8 
9 #include "JSystem/JDate.hh"
10 
11 #include "JLang/JUUID.hh"
12 
13 #include "Jeep/JPrint.hh"
14 #include "Jeep/JParser.hh"
15 #include "Jeep/JMessage.hh"
16 #include "Jeep/JProperties.hh"
17 
18 #include "JLang/JPredicate.hh"
19 
20 #include "JSupport/JMeta.hh"
22 
24 
25 #include "JDB/JUPI_t.hh"
26 #include "JDB/JVendorHV.hh"
27 #include "JDB/JDBSupportkit.hh"
28 #include "JDB/JPMTHVRunSettings.hh"
29 
30 #include "JSon/JSon.hh"
31 
32 namespace {
33 
34  /**
35  * Auxiliary class for creating PMT high-voltage look-up table from ASCII DB file.
36  */
37  struct JHVTable
38  {
39  /**
40  * HV-table types.
41  */
42  enum JHVTableTypes {
43  VENDOR_HV = 1, //!< Vendor high-voltages
44  RUN_HV = 2 //!< Run-specific high-voltages
45  };
46 
47  /**
48  * Initialise
49  *
50  * \param filename file name
51  * \param type HV-table type
52  */
53  JHVTable(const char* const filename,
54  const JHVTableTypes type)
55  {
56  using namespace std;
57  using namespace JPP;
58 
59  ifstream in(filename);
60 
61  switch (type) {
62  case VENDOR_HV: {
63 
64  for (string buffer; getline(in, buffer); ) {
65 
66  istringstream is(buffer);
67 
68  JVendorHV entry;
69 
70  if (is >> entry.DETID >> entry.DUID >> entry.FLOORID >> entry.CABLEPOS >> entry.PMTSERIAL >> entry.PMT_SUPPLY_VOLTAGE) {
71 
72  if (entry.PMTSERIAL > 0 &&
73  entry.PMT_SUPPLY_VOLTAGE < 0) {
74 
75  HVmap[entry.PMTSERIAL] = entry.PMT_SUPPLY_VOLTAGE;
76  }
77  }
78  }
79 
80  break;
81  }
82 
83  case RUN_HV: {
84 
85  for (string buffer; getline(in, buffer); ) {
86 
87  istringstream is(buffer);
88 
89  JPMTHVRunSettings entry;
90 
91  if (is >> entry.DETOID >> entry.DETID >>
92  entry.RUN >> entry.RUNSETUPID >>
93  entry.DUID >> entry.FLOORID >> entry.PMTINTID >> entry.CABLEPOS >> entry.PMTSERIAL >>
94  entry.CG_OID >> entry.HV_INDEX >> entry.HV_VALUE) {
95 
96  if (entry.PMTSERIAL > 0 &&
97  entry.HV_VALUE < 0) {
98 
99  HVmap[entry.PMTSERIAL] = entry.HV_VALUE;
100  }
101  }
102  }
103 
104  break;
105  }
106 
107  default:
108  THROW(JValueOutOfRange, "JHVTable::JHVTable(): Invalid HV-table type: " << type);
109  }
110 
111  in.close();
112  }
113 
114 
115  /**
116  * Get high-voltage.
117  *
118  * \param serialID PMT serial number
119  * \return high-voltage [V]
120  */
121  double operator()(const int serialID)
122  {
123  using namespace std;
124  using namespace JPP;
125 
126  map<int, double>::const_iterator p = HVmap.find(serialID);
127 
128  if (p != HVmap.end()) {
129  return p->second;
130  } else {
131  THROW(JValueOutOfRange, "Serial number " << serialID << " not found.");
132  }
133  }
134 
135  protected:
136  std::map<int, double> HVmap;
137  };
138 
139 
140  /**
141  * Read PMT HV-table type from input.
142  *
143  * \param in input stream
144  * \param object PMT HV-table type
145  * \return input stream
146  */
147  inline std::istream& operator>>(std::istream& in,
148  JHVTable::JHVTableTypes& object) {
149 
151 
152  int type;
153 
154  in >> type;
155 
156  switch (type) {
157  case int(JHVTable::VENDOR_HV):
158  object = JHVTable::VENDOR_HV;
159  return in;
160  case int(JHVTable::RUN_HV):
161  object = JHVTable::RUN_HV;
162  return in;
163  default:
164  THROW(JValueOutOfRange, "operator>>(): Invalid HV-table type: " << type);
165  }
166  }
167 
168 
169  /**
170  * Write PMT HV-table type to output.
171  *
172  * \param out output stream
173  * \param object PMT HV-table type
174  * \return output stream
175  */
176  inline std::ostream& operator<<(std::ostream& out,
177  JHVTable::JHVTableTypes object) {
178  return out << int(object);
179  }
180 }
181 
182 
183 /**
184  * \file
185  *
186  * Auxiliary program to treat failed HV-tuning calibrations.
187  * \author bjung
188  */
189 int main(int argc, char **argv)
190 {
191  using namespace std;
192  using namespace JPP;
193 
194  typedef JHVTable::JHVTableTypes JHVTableType_t;
195  typedef pair<JHVTableType_t, string> JHVTable_t;
196 
197  string inputFile;
198  string outputFile;
199  JHVTable_t HVtable;
200 
201  set<JUPI_t> pmtSet;
202 
203  string login;
204  string locationID;
205  int elapsedTime = 0;
206 
207  double minHV = -1500;
208  double maxHV = - 800;
209 
210  int debug;
211 
212  try {
213 
214  JProperties properties;
215 
216  properties.insert(gmake_property(login));
217  properties.insert(gmake_property(locationID));
218  properties.insert(gmake_property(elapsedTime));
219 
220  JProperties settings;
221 
222  settings.insert(gmake_property(minHV));
223  settings.insert(gmake_property(maxHV));
224 
225  JParser<> zap("Auxiliary program to treat failed high-voltage tuning results.");
226 
227  zap['f'] = make_field(inputFile, "input file");
228  zap['o'] = make_field(outputFile, "output file");
229  zap['b'] = make_field(HVtable, "ASCII HV table") = JPARSER::initialised();
230  zap['P'] = make_field(pmtSet, "Set of PMT UPIs") = JPARSER::initialised();
231  zap['#'] = make_field(properties, "database information") = JPARSER::initialised();
232  zap['@'] = make_field(settings, "HV limits") = JPARSER::initialised();
233  zap['d'] = make_field(debug, "debug") = 2;
234 
235  zap(argc, argv);
236 
237  } catch(const exception &error) {
238 
239  FATAL(error.what() << endl);
240  }
241 
242  if (login.empty() || locationID.empty()) {
243  FATAL("Missing user information (please specify via -#login and -#locationID).");
244  }
245 
246 
247  const JUUID& UUID = JUUID::rndm();
248 
249  JDateAndTime timer;
250 
251  timer.sub(elapsedTime);
252 
253 
254  // Edit high-voltage calibrations
255 
256  JDBAPIVersion DBAPIVersion;
257  string DBTestType;
258  string metaInfoStr = MAKE_STRING(JMeta(argc, argv));
259 
260  JHVCalibration toEdit;
261 
262  if (isJSONFile(inputFile.c_str())) {
263 
264  json js;
265 
266  ifstream ifs(inputFile.c_str());
267 
268  ifs >> js;
269  ifs.close();
270 
271  // Extract data
272 
273  json::const_iterator i0 = js.find(APIVersion_t);
274 
275  if (i0 != js.cend()) {
276 
277  istringstream iss(i0->get<string>());
278 
279  iss >> DBAPIVersion;
280  }
281 
282  JHVCalibration HVcals;
283 
284  json::const_iterator i1 = js.find(Data_t);
285 
286  if ((DBAPIVersion.getMajorVersion() == 2) &&
287  (i1 != js.cend() && i1->size() > 0)) {
288 
289  DBTestType = (*i1)[0].at(Test_t + Type_t).get<string>();
290 
291  JHVCalibration_t::setVersion(getDBVersionTuneHV(DBTestType));
292 
293  HVcals = (*i1)[0].at(Tests_t).get<JHVCalibration>();
294  metaInfoStr += (*i1)[0].at(Provenance_t + Info_t).at(Configuration_t).get<string>();
295 
296  } else {
297 
298  DBTestType = js.at(Test_t + Type_t).get<string>();
299 
300  JHVCalibration_t::setVersion(getDBVersionTuneHV(DBTestType));
301 
302  HVcals = js.at(Tests_t).get<JHVCalibration>();
303  }
304 
305  // Collect PMTs which need to be edited
306 
307  if (pmtSet.empty()) {
308 
309  for (JHVCalibration::iterator it = HVcals.begin(); it != HVcals.end(); ++it) {
310 
311  if (it->result != OK_t) {
312  toEdit.push_back(*it);
313  }
314  }
315 
316  } else {
317 
318  for (set<JUPI_t>::const_iterator it = pmtSet.cbegin(); it != pmtSet.cend(); ++it) {
319 
320  JHVCalibration::iterator pmt = find_if(HVcals.begin(), HVcals.end(),
321  make_predicate(&JHVCalibration_t::getNumber, it->getNumber()));
322  if (pmt != HVcals.end()) {
323 
324  if (pmt->result == OK_t) {
325  WARNING("Editing " << OK_t << " result for " << pmt->getUPI() << endl);
326  }
327 
328  toEdit.push_back(*pmt);
329  }
330  }
331  }
332 
333  } else {
334 
335  ERROR(inputFile << " is not a JSON file." << endl);
336  }
337 
338 
339  if (!HVtable.second.empty()) {
340 
341  NOTICE("Setting " << (HVtable.first == JHVTableType_t::VENDOR_HV ? "vendor " : "run-specific ") <<
342  "PMT high-voltages from file " << HVtable.second << "..." << endl);
343 
344  JHVTable getHV(HVtable.second.c_str(), HVtable.first);
345 
346  for (JHVCalibration::iterator i = toEdit.begin(); i != toEdit.end(); ++i) {
347 
348  const JUPI_t& upi = i->getUPI();
349  const double HV = getHV(upi.getNumber());
350 
351  if (HV > minHV && HV < maxHV) {
352 
353  i->supplyVoltage = getHV(upi.getNumber());
354  i->result = OK_t;
355 
356  } else {
357 
358  WARNING("Invalid high-voltage for PMT " << upi << " (" << FIXED(7,1) << HV <<
359  " not within [ " << FIXED(7,1) << minHV << ", " << FIXED(7,1) << maxHV << "]); skip." << endl);
360  }
361  }
362 
363  } else {
364 
365  NOTICE("Setting high-voltages manually..." << endl);
366 
367  for (JHVCalibration::iterator i = toEdit.begin(); i != toEdit.end(); ++i) {
368 
369  NOTICE("Please specify high-voltage for " << RIGHT(30) << i->getUPI() << ":" << endl);
370 
371  double manualHV;
372  cin >> manualHV;
373 
374  while (manualHV < minHV || manualHV > maxHV) {
375 
376  WARNING("Specified high-voltage is not within range [" <<
377  FIXED(7,1) << minHV << ", " << FIXED(7,1) << maxHV <<
378  "]; Please specify again." << endl);
379 
380  cin >> manualHV;
381  }
382 
383  i->supplyVoltage = manualHV;
384  i->result = OK_t;
385  }
386  }
387 
388 
389  json js;
390 
391  if (DBAPIVersion.getMajorVersion() == 2) {
392 
393  json error = { {Message_t, "" },
394  {Code_t, OK_t },
395  {Arguments_t, json::array() } };
396 
397  json metaData = { {Configuration_t, metaInfoStr },
398  {UUID_t, MAKE_STRING(UUID) } };
399 
400  json data = { {Provenance_t + Info_t, json(metaData) },
401  {User_t, login },
402  {Location_t, locationID },
403  {Start_t + Time_t, timer.toString() },
404  {End_t + Time_t, timer().toString() },
405  {Test_t + Type_t, DBTestType },
406  {Tests_t, json(toEdit) } };
407 
408  js[APIVersion_t] = MAKE_STRING(DBAPIVersion);
409  js[Data_t + Type_t] = MAKE_STRING("ProductTestSession");
410  js[Encoding_t] = MAKE_STRING("NativeJSON");
411  js[Error_t] = json(error);
412  js[Start_t] = timer.toString();
413  js[End_t] = timer().toString();
414  js[Data_t][0] = json(data);
415 
416  } else {
417 
418  js[User_t] = login;
419  js[Location_t] = locationID;
420  js[Test_t + Type_t] = DBTestType;
421  js[Start_t + Time_t] = timer.toString();
422  js[End_t + Time_t] = timer().toString();
423  js[Tests_t] = json(toEdit);
424  }
425 
426 
427  ofstream ofs(outputFile.c_str());
428 
429  ofs << setw(2) << setprecision(8);
430  ofs << js;
431 
432  ofs.close();
433 
434  return 0;
435 }
static JDBTestTypesTuneHV & getDBVersionTuneHV
Function object for looking up the HV-tuning database version number corresponding to a specific test...
static const std::string Arguments_t
Utility class to parse command line options.
Definition: JParser.hh:1517
static const std::string Start_t
JPredicate< JResult_t T::*, JComparison::eq > make_predicate(JResult_t T::*member, const JResult_t value)
Helper method to create predicate for data member.
Definition: JPredicate.hh:128
static const std::string Location_t
int main(int argc, char *argv[])
Definition: Main.cc:15
static const std::string Code_t
static const std::string Encoding_t
#define gmake_property(A)
macro to convert (template) parameter to JPropertiesElement object
#define THROW(JException_t, A)
Marco for throwing exception with std::ostream compatible message.
Definition: JException.hh:696
static const std::string Error_t
Utility class to parse parameter values.
Definition: JProperties.hh:496
Empty structure for specification of parser element that is initialised (i.e. does not require input)...
Definition: JParser.hh:83
Auxiliary data structure for floating point format specification.
Definition: JManip.hh:446
string outputFile
is
Definition: JDAQCHSM.chsm:167
Utility class to parse parameter values.
#define MAKE_STRING(A)
Make string.
Definition: JPrint.hh:127
static const std::string Time_t
Date and time functions.
static const std::string APIVersion_t
I/O formatting auxiliaries.
static const std::string Configuration_t
static const std::string Test_t
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
Definition: JParser.hh:1993
std::vector< JHVCalibration_t > JHVCalibration
PMT high voltage calibration.
ROOT I/O of application specific meta data.
#define NOTICE(A)
Definition: JMessage.hh:64
#define ERROR(A)
Definition: JMessage.hh:66
std::istream & getline(std::istream &in, JString &object)
Read string from input stream until end of line.
Definition: JString.hh:478
static const std::string End_t
static const std::string Info_t
General purpose messaging.
static const std::string Message_t
#define FATAL(A)
Definition: JMessage.hh:67
std::istream & operator>>(std::istream &in, JAANET::JHead &header)
Read header from input.
Definition: JHead.hh:1756
static const std::string Data_t
Utility class to parse command line options.
nlohmann::json json
std::ostream & operator<<(std::ostream &stream, const CLBCommonHeader &header)
static const std::string Type_t
Exception for accessing a value in a collection that is outside of its range.
Definition: JException.hh:162
static const std::string Provenance_t
KM3NeT DAQ constants, bit handling, etc.
then fatal Wrong number of arguments fi set_variable DETECTOR $argv[1] set_variable INPUT_FILE $argv[2] eval JPrintDetector a $DETECTOR O IDENTIFIER eval JPrintDetector a $DETECTOR O SUMMARY JAcoustics sh $DETECTOR_ID source JAcousticsToolkit sh CHECK_EXIT_CODE typeset A EMITTERS get_tripods $WORKDIR tripod txt EMITTERS get_transmitters $WORKDIR transmitter txt EMITTERS for EMITTER in
Definition: JCanberra.sh:46
then echo WARNING
Definition: JTuneHV.sh:91
static const std::string UUID_t
Specifications of file name extensions.
static const std::string Tests_t
bool isJSONFile(const char *file_name)
Check file format.
int debug
debug level
static const std::string OK_t
static const std::string User_t