CMS 3D CMS Logo

TotemDAQMappingESSourceXML.cc
Go to the documentation of this file.
1 /****************************************************************************
2 *
3 * This is a part of TOTEM offline software.
4 * Authors:
5 * Maciej Wróbel (wroblisko@gmail.com)
6 * Jan Kašpar (jan.kaspar@cern.ch)
7 * Marcin Borratynski (mborratynski@gmail.com)
8 * Seyed Mohsen Etesami (setesami@cern.ch)
9 * Laurent Forthomme
10 ****************************************************************************/
11 
24 
29 
36 
37 #include <xercesc/parsers/XercesDOMParser.hpp>
38 #include <xercesc/dom/DOM.hpp>
39 #include <xercesc/sax/HandlerBase.hpp>
40 #include <xercesc/util/XMLString.hpp>
41 #include <xercesc/util/PlatformUtils.hpp>
42 
43 #include <memory>
44 #include <sstream>
45 
46 //#define DEBUG 1
47 
48 //----------------------------------------------------------------------------------------------------
49 
50 using namespace std;
51 
56 public:
57  static const std::string tagVFAT;
58  static const std::string tagChannel;
60 
62  static const std::string tagArm;
63 
65  static const std::string tagRPStation;
66  static const std::string tagRPPot;
67  static const std::string tagRPPlane;
68 
70  static const std::string tagChip1;
71  static const std::string tagChip2;
72 
75  static const std::string tagDiamondCh;
76 
79  static const std::string tagSampicCh;
82 
86 
88  ~TotemDAQMappingESSourceXML() override;
89 
91 
92  edm::ESProducts<std::unique_ptr<TotemDAQMapping>, std::unique_ptr<TotemAnalysisMask>> produce(const TotemReadoutRcd &);
93 
94 private:
95  unsigned int verbosity;
96 
98  string subSystemName;
99 
100  //subdetector id for sampic
101  unsigned int sampicSubDetId;
102 
103  //Unpack multiple channels per payload for T2
105 
107  std::vector<std::string> mappingFileNames;
108 
109  struct ConfigBlock {
112 
114  std::vector<std::string> mappingFileNames;
115 
117  std::vector<std::string> maskFileNames;
118  };
119 
120  vector<ConfigBlock> configuration;
121 
123  unsigned int currentBlock;
124 
127 
129  enum NodeType {
146  nTotemT2Tile
147  };
148 
150  enum ParseType { pMapping, pMask };
151 
153  void ParseXML(ParseType,
154  const string &file,
155  const std::unique_ptr<TotemDAQMapping> &,
156  const std::unique_ptr<TotemAnalysisMask> &);
157 
159  void ParseTreeRP(ParseType,
160  xercesc::DOMNode *,
161  NodeType,
162  unsigned int parentID,
163  const std::unique_ptr<TotemDAQMapping> &,
164  const std::unique_ptr<TotemAnalysisMask> &);
165 
167  void ParseTreeDiamond(ParseType,
168  xercesc::DOMNode *,
169  NodeType,
170  unsigned int parentID,
171  const std::unique_ptr<TotemDAQMapping> &,
172  const std::unique_ptr<TotemAnalysisMask> &);
173 
175  void ParseTreeTotemTiming(ParseType,
176  xercesc::DOMNode *,
177  NodeType,
178  unsigned int parentID,
179  const std::unique_ptr<TotemDAQMapping> &,
180  const std::unique_ptr<TotemAnalysisMask> &);
181 
183  void ParseTreeTotemT2(ParseType,
184  xercesc::DOMNode *,
185  NodeType,
186  unsigned int parentID,
187  const std::unique_ptr<TotemDAQMapping> &,
188  const std::unique_ptr<TotemAnalysisMask> &);
189 
190 private:
192  string CompleteFileName(const string &fn);
193 
195  bool Test(xercesc::DOMNode *node, const std::string &name) {
196  return !(name.compare(cms::xerces::toString(node->getNodeName())));
197  }
198 
200  NodeType GetNodeType(xercesc::DOMNode *);
201 
203  string GetNodeContent(xercesc::DOMNode *parent) { return string(cms::xerces::toString(parent->getTextContent())); }
204 
206  string GetNodeValue(xercesc::DOMNode *node) { return cms::xerces::toString(node->getNodeValue()); }
207 
209  TotemFramePosition ChipFramePosition(xercesc::DOMNode *chipnode);
210 
212  TotemT2FramePosition ChipT2FramePosition(xercesc::DOMNode *chipnode);
213 
214  void GetChannels(xercesc::DOMNode *n, std::set<unsigned char> &channels);
215 
217  return ((type == nArm) || (type == nRPStation) || (type == nRPPot) || (type == nRPPlane) || (type == nChip));
218  }
219 
221  return ((type == nArm) || (type == nRPStation) || (type == nRPPot) || (type == nDiamondPlane) ||
222  (type == nDiamondCh));
223  }
224 
226  return ((type == nArm) || (type == nRPStation) || (type == nRPPot) || (type == nSampicBoard) ||
227  (type == nSampicChannel) || (type == nTotemTimingPlane) || (type == nTotemTimingCh));
228  }
229 
230  bool TotemT2Node(NodeType type) { return type == nArm || type == nTotemT2Plane || type == nTotemT2Tile; }
231 
232  bool CommonNode(NodeType type) { return ((type == nChip) || (type == nArm)); }
233 
234 protected:
236  void setIntervalFor(const edm::eventsetup::EventSetupRecordKey &,
237  const edm::IOVSyncValue &,
238  edm::ValidityInterval &) override;
239 };
240 
241 //----------------------------------------------------------------------------------------------------
242 
243 using namespace std;
244 using namespace edm;
245 using namespace xercesc;
246 
247 const string TotemDAQMappingESSourceXML::tagVFAT = "vfat";
248 const string TotemDAQMappingESSourceXML::tagChannel = "channel";
249 const string TotemDAQMappingESSourceXML::tagAnalysisMask = "analysisMask";
250 
251 // common XML position tags
252 const string TotemDAQMappingESSourceXML::tagArm = "arm";
253 
254 // common XML Chip tags
255 const string TotemDAQMappingESSourceXML::tagChip1 = "vfat";
256 const string TotemDAQMappingESSourceXML::tagChip2 = "test_vfat";
257 
258 // specific RP XML tags
259 const string TotemDAQMappingESSourceXML::tagRPStation = "station";
260 const string TotemDAQMappingESSourceXML::tagRPPot = "rp_detector_set";
261 const string TotemDAQMappingESSourceXML::tagRPPlane = "rp_plane";
262 
263 // specific tags for diamond
264 const string TotemDAQMappingESSourceXML::tagDiamondPlane = "rp_plane_diamond";
265 const string TotemDAQMappingESSourceXML::tagDiamondCh = "diamond_channel";
266 
267 // specific tags for totem timing
268 const string TotemDAQMappingESSourceXML::tagSampicBoard = "rp_sampic_board";
269 const string TotemDAQMappingESSourceXML::tagSampicCh = "rp_sampic_channel";
270 const string TotemDAQMappingESSourceXML::tagTotemTimingCh = "timing_channel";
271 const string TotemDAQMappingESSourceXML::tagTotemTimingPlane = "timing_plane";
272 
273 // specific tags for TOTEM nT2
274 const string TotemDAQMappingESSourceXML::tagTotemT2Plane = "nt2_plane";
275 const string TotemDAQMappingESSourceXML::tagTotemT2Tile = "nt2_tile";
276 
277 //----------------------------------------------------------------------------------------------------
278 
280  : verbosity(conf.getUntrackedParameter<unsigned int>("verbosity", 0)),
281  subSystemName(conf.getUntrackedParameter<string>("subSystem")),
282  sampicSubDetId(conf.getParameter<unsigned int>("sampicSubDetId")),
283  packedPayload(conf.getParameter<bool>("multipleChannelsPerPayload")),
284  currentBlock(0),
285  currentBlockValid(false) {
286  for (const auto &it : conf.getParameter<vector<ParameterSet>>("configuration")) {
287  ConfigBlock b;
288  b.validityRange = it.getParameter<EventRange>("validityRange");
289  b.mappingFileNames = it.getParameter<vector<string>>("mappingFileNames");
290  b.maskFileNames = it.getParameter<vector<string>>("maskFileNames");
291  configuration.push_back(b);
292  }
293 
295  findingRecord<TotemReadoutRcd>();
296 }
297 
298 //----------------------------------------------------------------------------------------------------
299 
301  const edm::IOVSyncValue &iosv,
302  edm::ValidityInterval &oValidity) {
303  LogVerbatim("TotemDAQMappingESSourceXML") << ">> TotemDAQMappingESSourceXML::setIntervalFor(" << key.name() << ")";
304 
305  LogVerbatim("TotemDAQMappingESSourceXML")
306  << " run=" << iosv.eventID().run() << ", event=" << iosv.eventID().event();
307 
308  currentBlockValid = false;
309  for (unsigned int idx = 0; idx < configuration.size(); ++idx) {
310  const auto &bl = configuration[idx];
311 
312  edm::EventRange range = bl.validityRange;
313 
314  // If "<run>:min" is specified in python config, it is translated into event <run>:0:1.
315  // However, the truly minimal event id often found in data is <run>:0:0. Therefore the
316  // adjustment below is needed.
317  if (range.startEventID().luminosityBlock() == 0 && range.startEventID().event() == 1)
318  range = edm::EventRange(edm::EventID(range.startEventID().run(), 0, 0), range.endEventID());
319 
320  if (edm::contains(range, iosv.eventID())) {
321  currentBlockValid = true;
322  currentBlock = idx;
323 
324  const IOVSyncValue begin(range.startEventID());
325  const IOVSyncValue end(range.endEventID());
326  oValidity = edm::ValidityInterval(begin, end);
327 
328  LogVerbatim("TotemDAQMappingESSourceXML") << " block found: index=" << currentBlock << ", interval=("
329  << range.startEventID() << " - " << range.endEventID() << ")";
330 
331  return;
332  }
333  }
334 
335  if (!currentBlockValid) {
336  throw cms::Exception("TotemDAQMappingESSourceXML::setIntervalFor")
337  << "No configuration for event " << iosv.eventID();
338  }
339 }
340 
341 //----------------------------------------------------------------------------------------------------
342 
344 
345 //----------------------------------------------------------------------------------------------------
346 
348  FileInPath fip(fn);
349  return fip.fullPath();
350 }
351 
352 //----------------------------------------------------------------------------------------------------
353 static inline std::string to_string(const XMLCh *ch) { return XERCES_CPP_NAMESPACE_QUALIFIER XMLString::transcode(ch); }
354 
355 edm::ESProducts<std::unique_ptr<TotemDAQMapping>, std::unique_ptr<TotemAnalysisMask>>
358 
359  auto mapping = std::make_unique<TotemDAQMapping>();
360  auto mask = std::make_unique<TotemAnalysisMask>();
361 
362  try {
363  // initialize Xerces
365 
366  // load mapping files
367  for (const auto &fn : configuration[currentBlock].mappingFileNames)
369 
370  // load mask files
371  for (const auto &fn : configuration[currentBlock].maskFileNames)
373 
374  // release Xerces
376  } catch (const XMLException &e) {
377  throw cms::Exception("XMLDocument") << "cms::concurrency::xercesInitialize failed because of "
378  << to_string(e.getMessage());
379  } catch (const SAXException &e) {
380  throw cms::Exception("XMLDocument") << "XML parser (SAX) reported: " << to_string(e.getMessage()) << ".";
381  } catch (const DOMException &e) {
382  throw cms::Exception("XMLDocument") << "XML parser (DOM) reported: " << to_string(e.getMessage()) << ".";
383  }
384 
385  // commit the products
387 }
388 
389 //----------------------------------------------------------------------------------------------------
390 
392  const string &file,
393  const std::unique_ptr<TotemDAQMapping> &mapping,
394  const std::unique_ptr<TotemAnalysisMask> &mask) {
395  unique_ptr<XercesDOMParser> parser(new XercesDOMParser());
396  parser->parse(file.c_str());
397 
398  DOMDocument *domDoc = parser->getDocument();
399 
400  if (!domDoc)
401  throw cms::Exception("TotemDAQMappingESSourceXML::ParseXML")
402  << "Cannot parse file `" << file << "' (domDoc = NULL).";
403 
404  DOMElement *elementRoot = domDoc->getDocumentElement();
405 
406  if (!elementRoot)
407  throw cms::Exception("TotemDAQMappingESSourceXML::ParseXML") << "File `" << file << "' is empty.";
408 
409  ParseTreeRP(pType, elementRoot, nTop, 0, mapping, mask);
410 
411  ParseTreeDiamond(pType, elementRoot, nTop, 0, mapping, mask);
412 
413  ParseTreeTotemTiming(pType, elementRoot, nTop, 0, mapping, mask);
414 
415  ParseTreeTotemT2(pType, elementRoot, nTop, 0, mapping, mask);
416 }
417 
418 //-----------------------------------------------------------------------------------------------------------
419 
421  xercesc::DOMNode *parent,
422  NodeType parentType,
423  unsigned int parentID,
424  const std::unique_ptr<TotemDAQMapping> &mapping,
425  const std::unique_ptr<TotemAnalysisMask> &mask) {
426 #ifdef DEBUG
427  printf(">> TotemDAQMappingESSourceXML::ParseTreeRP(%s, %u, %u)\n",
428  cms::xerces::toString(parent->getNodeName()),
429  parentType,
430  parentID);
431 #endif
432 
433  DOMNodeList *children = parent->getChildNodes();
434 
435  for (unsigned int i = 0; i < children->getLength(); i++) {
436  DOMNode *n = children->item(i);
437  if (n->getNodeType() != DOMNode::ELEMENT_NODE)
438  continue;
439 
441 
442 #ifdef DEBUG
443  printf("\tname = %s, type = %u\n", cms::xerces::toString(n->getNodeName()), type);
444 #endif
445 
446  // structure control
447  if (!RPNode(type))
448  continue;
449 
450  NodeType expectedParentType;
451  switch (type) {
452  case nArm:
453  expectedParentType = nTop;
454  break;
455  case nRPStation:
456  expectedParentType = nArm;
457  break;
458  case nRPPot:
459  expectedParentType = nRPStation;
460  break;
461  case nRPPlane:
462  expectedParentType = nRPPot;
463  break;
464  case nChip:
465  expectedParentType = nRPPlane;
466  break;
467  case nChannel:
468  expectedParentType = nChip;
469  break;
470  default:
471  expectedParentType = nUnknown;
472  break;
473  }
474 
475  if (expectedParentType != parentType) {
476  throw cms::Exception("TotemDAQMappingESSourceXML")
477  << "Node " << cms::xerces::toString(n->getNodeName()) << " not allowed within "
478  << cms::xerces::toString(parent->getNodeName()) << " block.\n";
479  }
480 
481  // parse tag attributes
482  unsigned int id = 0, hw_id = 0;
483  bool id_set = false, hw_id_set = false;
484  bool fullMask = false;
485  DOMNamedNodeMap *attr = n->getAttributes();
486 
487  for (unsigned int j = 0; j < attr->getLength(); j++) {
488  DOMNode *a = attr->item(j);
489 
490  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id")) {
491  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &id);
492  id_set = true;
493  }
494 
495  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "hw_id")) {
496  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%x", &hw_id);
497  hw_id_set = true;
498  }
499 
500  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "full_mask"))
501  fullMask = (strcmp(cms::xerces::toString(a->getNodeValue()).c_str(), "no") != 0);
502  }
503 
504  // content control
505  if (!id_set)
506  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeRP")
507  << "id not given for element `" << cms::xerces::toString(n->getNodeName()) << "'";
508 
509  if (!hw_id_set && type == nChip && pType == pMapping)
510  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeRP")
511  << "hw_id not given for element `" << cms::xerces::toString(n->getNodeName()) << "'";
512 
513  if (type == nRPPlane && id > 9)
514  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeRP")
515  << "Plane IDs range from 0 to 9. id = " << id << " is invalid.";
516 
517 #ifdef DEBUG
518  printf("\tID found: 0x%x\n", id);
519 #endif
520 
521  // store mapping data
522  if (pType == pMapping && type == nChip) {
523  const TotemFramePosition &framepos = ChipFramePosition(n);
524  TotemVFATInfo vfatInfo;
525  vfatInfo.hwID = hw_id;
526 
527  const unsigned int armIdx = (parentID / 1000) % 10;
528  const unsigned int stIdx = (parentID / 100) % 10;
529  const unsigned int rpIdx = (parentID / 10) % 10;
530  const unsigned int plIdx = parentID % 10;
531 
532  vfatInfo.symbolicID.symbolicID = TotemRPDetId(armIdx, stIdx, rpIdx, plIdx, id);
533 
534  mapping->insert(framepos, vfatInfo);
535 
536  continue;
537  }
538 
539  // store mask data
540  if (pType == pMask && type == nChip) {
541  const unsigned int armIdx = (parentID / 1000) % 10;
542  const unsigned int stIdx = (parentID / 100) % 10;
543  const unsigned int rpIdx = (parentID / 10) % 10;
544  const unsigned int plIdx = parentID % 10;
545 
546  TotemSymbID symbId;
547  symbId.symbolicID = TotemRPDetId(armIdx, stIdx, rpIdx, plIdx, id);
548 
550  am.fullMask = fullMask;
552 
553  mask->insert(symbId, am);
554 
555  continue;
556  }
557 
558  // recursion (deeper in the tree)
559  ParseTreeRP(pType, n, type, parentID * 10 + id, mapping, mask);
560  }
561 }
562 
563 //----------------------------------------------------------------------------------------------------
564 
566  xercesc::DOMNode *parent,
567  NodeType parentType,
568  unsigned int parentID,
569  const std::unique_ptr<TotemDAQMapping> &mapping,
570  const std::unique_ptr<TotemAnalysisMask> &mask) {
571 #ifdef DEBUG
572  printf(">> TotemDAQMappingESSourceXML::ParseTreeDiamond(%s, %u, %u)\n",
573  cms::xerces::toString(parent->getNodeName()),
574  parentType,
575  parentID);
576 #endif
577 
578  DOMNodeList *children = parent->getChildNodes();
579 
580  for (unsigned int i = 0; i < children->getLength(); i++) {
581  DOMNode *n = children->item(i);
582  if (n->getNodeType() != DOMNode::ELEMENT_NODE)
583  continue;
584 
586 #ifdef DEBUG
587  printf("\tname = %s, type = %u\n", cms::xerces::toString(n->getNodeName()), type);
588 #endif
589 
590  // structure control
591  if (!DiamondNode(type))
592  continue;
593 
594  NodeType expectedParentType;
595  switch (type) {
596  case nArm:
597  expectedParentType = nTop;
598  break;
599  case nRPStation:
600  expectedParentType = nArm;
601  break;
602  case nRPPot:
603  expectedParentType = nRPStation;
604  break;
605  case nDiamondPlane:
606  expectedParentType = nRPPot;
607  break;
608  case nDiamondCh:
609  expectedParentType = nDiamondPlane;
610  break;
611  default:
612  expectedParentType = nUnknown;
613  break;
614  }
615 
616  if (expectedParentType != parentType) {
617  throw cms::Exception("TotemDAQMappingESSourceXML")
618  << "Node " << cms::xerces::toString(n->getNodeName()) << " not allowed within "
619  << cms::xerces::toString(parent->getNodeName()) << " block.\n";
620  }
621 
622  // parse tag attributes
623  unsigned int id = 0, hw_id = 0;
624  bool id_set = false, hw_id_set = false;
625  DOMNamedNodeMap *attr = n->getAttributes();
626 
627  for (unsigned int j = 0; j < attr->getLength(); j++) {
628  DOMNode *a = attr->item(j);
629 
630  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id")) {
631  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &id);
632  id_set = true;
633  }
634 
635  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "hw_id")) {
636  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%x", &hw_id);
637  hw_id_set = true;
638  }
639  }
640 
641  // content control
642  if (!id_set)
643  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeDiamond")
644  << "id not given for element `" << cms::xerces::toString(n->getNodeName()) << "'";
645 
646  if (!hw_id_set && type == nDiamondCh && pType == pMapping)
647  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeDiamond")
648  << "hw_id not given for element `" << cms::xerces::toString(n->getNodeName()) << "'";
649 
650  if (type == nDiamondPlane && id > 3)
651  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeDiamond")
652  << "Plane IDs range from 0 to 3. id = " << id << " is invalid.";
653 
654 #ifdef DEBUG
655  printf("\tID found: 0x%x\n", id);
656 #endif
657 
658  // store mapping data
659  if (pType == pMapping && type == nDiamondCh) {
660  const TotemFramePosition &framepos = ChipFramePosition(n);
661 
662  TotemVFATInfo vfatInfo;
663  vfatInfo.hwID = hw_id;
664 
665  if (type == nDiamondCh) {
666  unsigned int ArmNum = (parentID / 10000) % 10;
667  unsigned int StationNum = (parentID / 1000) % 10;
668  unsigned int RpNum = (parentID / 100) % 10;
669  unsigned int PlaneNum = (parentID % 100);
670 
671  vfatInfo.symbolicID.symbolicID = CTPPSDiamondDetId(ArmNum, StationNum, RpNum, PlaneNum, id);
672  }
673 
674  mapping->insert(framepos, vfatInfo);
675 
676  continue;
677  }
678 
679  unsigned int childId;
680  if (pType == pMapping && type == nDiamondPlane)
681  childId = parentID * 100 + id;
682  else
683  childId = parentID * 10 + id;
684 
685  ParseTreeDiamond(pType, n, type, childId, mapping, mask);
686  }
687 }
688 
689 //----------------------------------------------------------------------------------------------------
690 
692  xercesc::DOMNode *parent,
693  NodeType parentType,
694  unsigned int parentID,
695  const std::unique_ptr<TotemDAQMapping> &mapping,
696  const std::unique_ptr<TotemAnalysisMask> &mask) {
697  DOMNodeList *children = parent->getChildNodes();
698 
699  // Fill map hwId -> TotemTimingPlaneChannelPair
700  for (unsigned int i = 0; i < children->getLength(); i++) {
701  DOMNode *child = children->item(i);
702  if ((child->getNodeType() != DOMNode::ELEMENT_NODE) || (GetNodeType(child) != nTotemTimingCh))
703  continue;
704 
705  int plane = -1;
706  DOMNamedNodeMap *attr = parent->getAttributes();
707  for (unsigned int j = 0; j < attr->getLength(); j++) {
708  DOMNode *a = attr->item(j);
709 
710  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id"))
711  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%d", &plane);
712  }
713 
714  int channel = -1;
715  unsigned int hwId = 0;
716  attr = child->getAttributes();
717  for (unsigned int j = 0; j < attr->getLength(); j++) {
718  DOMNode *a = attr->item(j);
719 
720  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id"))
721  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%d", &channel);
722  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "hwId"))
723  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%x", &hwId);
724  }
725 
726  mapping->totemTimingChannelMap[(uint8_t)hwId] = TotemDAQMapping::TotemTimingPlaneChannelPair(plane, channel);
727  }
728 
729  for (unsigned int i = 0; i < children->getLength(); i++) {
730  DOMNode *n = children->item(i);
731  if (n->getNodeType() != DOMNode::ELEMENT_NODE)
732  continue;
733 
735 
736  // structure control
737  if (!TotemTimingNode(type))
738  continue;
739 
740  NodeType expectedParentType;
741  switch (type) {
742  case nArm:
743  expectedParentType = nTop;
744  break;
745  case nRPStation:
746  expectedParentType = nArm;
747  break;
748  case nRPPot:
749  expectedParentType = nRPStation;
750  break;
751  case nSampicBoard:
752  expectedParentType = nRPPot;
753  break;
754  case nSampicChannel:
755  expectedParentType = nSampicBoard;
756  break;
757  case nTotemTimingPlane:
758  expectedParentType = nRPPot;
759  break;
760  case nTotemTimingCh:
761  expectedParentType = nTotemTimingPlane;
762  break;
763  default:
764  expectedParentType = nUnknown;
765  break;
766  }
767 
768  if (expectedParentType != parentType) {
769  throw cms::Exception("TotemDAQMappingESSourceXML")
770  << "Node " << cms::xerces::toString(n->getNodeName()) << " not allowed within "
771  << cms::xerces::toString(parent->getNodeName()) << " block.\n";
772  }
773 
774  // parse tag attributes
775  unsigned int id = 0;
776  bool id_set = false;
777  DOMNamedNodeMap *attr = n->getAttributes();
778 
779  for (unsigned int j = 0; j < attr->getLength(); j++) {
780  DOMNode *a = attr->item(j);
781 
782  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id")) {
783  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &id);
784  id_set = true;
785  }
786  }
787 
788  // content control
789  if (!id_set)
790  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeTotemTiming")
791  << "id not given for element `" << cms::xerces::toString(n->getNodeName()) << "'";
792  if (type == nSampicBoard && id > 5)
793  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeTotemTiming")
794  << "SampicBoard IDs range from 0 to 5. id = " << id << " is invalid.";
795 
796  // store mapping data
797  if (pType == pMapping && type == nSampicChannel) {
798  const TotemFramePosition &framepos = ChipFramePosition(n);
799 
800  TotemVFATInfo vfatInfo;
801  unsigned int ArmNum = (parentID / 10000) % 10;
802  unsigned int StationNum = (parentID / 1000) % 10;
803  unsigned int RpNum = (parentID / 100) % 10;
804 
805  vfatInfo.symbolicID.symbolicID = TotemTimingDetId(ArmNum,
806  StationNum,
807  RpNum,
808  0,
810  sampicSubDetId); //Dynamical: it is encoded in the frame
811 
812  mapping->insert(framepos, vfatInfo);
813 
814  continue;
815  }
816 
817  unsigned int childId;
818  if (pType == pMapping && type == nSampicBoard)
819  childId = parentID * 100 + id;
820  else
821  childId = parentID * 10 + id;
822 
823  ParseTreeTotemTiming(pType, n, type, childId, mapping, mask);
824  }
825 }
826 
827 //----------------------------------------------------------------------------------------------------
828 
830  xercesc::DOMNode *parent,
831  NodeType parentType,
832  unsigned int parentID,
833  const std::unique_ptr<TotemDAQMapping> &mapping,
834  const std::unique_ptr<TotemAnalysisMask> &mask) {
835  DOMNodeList *children = parent->getChildNodes();
836 
837  for (unsigned int i = 0; i < children->getLength(); i++) {
838  DOMNode *child = children->item(i);
839  if (child->getNodeType() != DOMNode::ELEMENT_NODE)
840  continue;
841 
843 
844  // structure control
845  if (!TotemT2Node(type))
846  continue;
847 
848  NodeType expectedParentType;
849  switch (type) {
850  case nArm:
851  expectedParentType = nTop;
852  break;
853  case nTotemT2Plane:
854  expectedParentType = nArm;
855  break;
856  case nTotemT2Tile:
857  expectedParentType = nTotemT2Plane;
858  break;
859  default:
860  expectedParentType = nUnknown;
861  break;
862  }
863 
864  if (expectedParentType != parentType) {
865  throw cms::Exception("TotemDAQMappingESSourceXML")
866  << "Node " << cms::xerces::toString(child->getNodeName()) << " not allowed within "
867  << cms::xerces::toString(parent->getNodeName()) << " block.\n";
868  }
869 
870  unsigned int id = 0;
871  bool id_set = false;
872  DOMNamedNodeMap *attr = child->getAttributes();
873 
874  for (unsigned int j = 0; j < attr->getLength(); j++) {
875  DOMNode *a = attr->item(j);
876  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id")) {
877  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &id);
878  id_set = true;
879  }
880  }
881  if (pType == pMapping && type == nTotemT2Tile) {
882  // parse tag attributes
883  unsigned int hw_id = 0;
884  bool hw_id_set = false;
885  unsigned int channel_in_payload = 0;
886  bool payload_set = false;
887  DOMNamedNodeMap *attr = child->getAttributes();
888 
889  for (unsigned int j = 0; j < attr->getLength(); j++) {
890  DOMNode *a = attr->item(j);
891  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "hwId")) {
892  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%x", &hw_id);
893  hw_id_set = true;
894  }
895  if (packedPayload && (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "pay"))) {
896  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &channel_in_payload);
897  payload_set = true;
898  }
899  }
900 
901  // content control
902  if (!id_set)
903  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeTotemT2")
904  << "id not given for element `" << cms::xerces::toString(child->getNodeName()) << "'";
905  if (!hw_id_set)
906  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeTotemT2")
907  << "hwId not given for element `" << cms::xerces::toString(child->getNodeName()) << "'";
908  if (packedPayload && (!payload_set))
909  throw cms::Exception("TotemDAQMappingESSourceXML::ParseTreeTotemT2")
910  << "Payload position in fibre not given for element `" << cms::xerces::toString(child->getNodeName())
911  << "'";
912 
913  // store mapping data
916  TotemVFATInfo vfatInfo;
917  vfatInfo.hwID = hw_id;
918  unsigned int arm = parentID / 10, plane = parentID % 10;
919  vfatInfo.symbolicID.symbolicID = TotemT2DetId(arm, plane, id);
920  if (verbosity > 2) {
921  edm::LogWarning("Totem") << "Print T2 frame pos (payload):" << framepos << " ("
922  << (packedPayload ? "true" : "false") << ") hw_id / T2 DetID" << hw_id << "/"
923  << TotemT2DetId(arm, plane, id) << endl;
924  }
925 
926  if (packedPayload)
927  mapping->insert(framepos, vfatInfo);
928  else
929  mapping->insert(frameposSingle, vfatInfo);
930 
931  continue;
932  }
933  // follow tree recursively
934  ParseTreeTotemT2(pType, child, type, parentID * 10 + id, mapping, mask);
935  }
936 }
937 
938 //----------------------------------------------------------------------------------------------------
939 
942  unsigned char attributeFlag = 0;
943 
944  DOMNamedNodeMap *attr = chipnode->getAttributes();
945  for (unsigned int j = 0; j < attr->getLength(); j++) {
946  DOMNode *a = attr->item(j);
947  if (fp.setXMLAttribute(
948  cms::xerces::toString(a->getNodeName()), cms::xerces::toString(a->getNodeValue()), attributeFlag) > 1) {
949  throw cms::Exception("TotemDAQMappingESSourceXML")
950  << "Unrecognized tag `" << cms::xerces::toString(a->getNodeName()) << "' or incompatible value `"
951  << cms::xerces::toString(a->getNodeValue()) << "'.";
952  }
953  }
954 
955  if (!fp.checkXMLAttributeFlag(attributeFlag)) {
956  throw cms::Exception("TotemDAQMappingESSourceXML")
957  << "Wrong/incomplete DAQ channel specification (attributeFlag = " << attributeFlag << ").";
958  }
959 
960  return fp;
961 }
962 
963 //----------------------------------------------------------------------------------------------------
964 
967  unsigned char attributeFlag = 0;
968 
969  DOMNamedNodeMap *attr = chipnode->getAttributes();
970  for (unsigned int j = 0; j < attr->getLength(); j++) {
971  DOMNode *a = attr->item(j);
972  if (fp.setXMLAttribute(
973  cms::xerces::toString(a->getNodeName()), cms::xerces::toString(a->getNodeValue()), attributeFlag) > 1) {
974  throw cms::Exception("TotemDAQMappingESSourceXML")
975  << "Unrecognized T2 tag `" << cms::xerces::toString(a->getNodeName()) << "' or incompatible value `"
976  << cms::xerces::toString(a->getNodeValue()) << "'.";
977  }
978  }
979 
980  if (!fp.checkXMLAttributeFlag(attributeFlag)) {
981  throw cms::Exception("TotemDAQMappingESSourceXML")
982  << "Wrong/incomplete T2 DAQ channel specification (attributeFlag = " << attributeFlag << ").";
983  }
984 
985  return fp;
986 }
987 //----------------------------------------------------------------------------------------------------
988 
990  // common node types
991  if (Test(n, tagArm))
992  return nArm;
993  if (Test(n, tagChip1))
994  return nChip;
995  if (Test(n, tagChip2))
996  return nChip;
997 
998  // RP node types
999  if (Test(n, tagRPStation))
1000  return nRPStation;
1001  if (Test(n, tagRPPot))
1002  return nRPPot;
1003  if (Test(n, tagRPPlane))
1004  return nRPPlane;
1005 
1006  //diamond specifics
1007  if (Test(n, tagDiamondCh))
1008  return nDiamondCh;
1009  if (Test(n, tagDiamondPlane))
1010  return nDiamondPlane;
1011 
1012  //totem timing specifics
1013  if (Test(n, tagSampicBoard))
1014  return nSampicBoard;
1015  if (Test(n, tagSampicCh))
1016  return nSampicChannel;
1017  if (Test(n, tagTotemTimingCh))
1018  return nTotemTimingCh;
1019  if (Test(n, tagTotemTimingPlane))
1020  return nTotemTimingPlane;
1021 
1022  // TOTEM nT2 specifics
1023  if (Test(n, tagTotemT2Plane))
1024  return nTotemT2Plane;
1025  if (Test(n, tagTotemT2Tile))
1026  return nTotemT2Tile;
1027 
1028  // for backward compatibility
1029  if (Test(n, "trigger_vfat"))
1030  return nSkip;
1031 
1032  throw cms::Exception("TotemDAQMappingESSourceXML::GetNodeType")
1033  << "Unknown tag `" << cms::xerces::toString(n->getNodeName()) << "'.\n";
1034 }
1035 
1036 //----------------------------------------------------------------------------------------------------
1037 
1038 void TotemDAQMappingESSourceXML::GetChannels(xercesc::DOMNode *n, set<unsigned char> &channels) {
1039  DOMNodeList *children = n->getChildNodes();
1040  for (unsigned int i = 0; i < children->getLength(); i++) {
1041  DOMNode *n = children->item(i);
1042  if (n->getNodeType() != DOMNode::ELEMENT_NODE || !Test(n, "channel"))
1043  continue;
1044 
1045  DOMNamedNodeMap *attr = n->getAttributes();
1046  bool idSet = false;
1047  for (unsigned int j = 0; j < attr->getLength(); j++) {
1048  DOMNode *a = attr->item(j);
1049 
1050  if (!strcmp(cms::xerces::toString(a->getNodeName()).c_str(), "id")) {
1051  unsigned int id = 0;
1052  sscanf(cms::xerces::toString(a->getNodeValue()).c_str(), "%u", &id);
1053  channels.insert(id);
1054  idSet = true;
1055  break;
1056  }
1057  }
1058 
1059  if (!idSet) {
1060  throw cms::Exception("TotemDAQMappingESSourceXML::GetChannels") << "Channel tags must have an `id' attribute.";
1061  }
1062  }
1063 }
1064 
1065 //----------------------------------------------------------------------------------------------------
1066 
1068  // totemDAQMappingESSourceXML
1070  desc.addUntracked<unsigned int>("verbosity", 0);
1071  desc.addUntracked<std::string>("subSystem", "")->setComment("set it to: TrackingStrip, ...");
1072  desc.add<unsigned int>("sampicSubDetId");
1073  desc.add<bool>("multipleChannelsPerPayload", false);
1074  {
1076  vpsd1.add<edm::EventRange>("validityRange", edm::EventRange(1, 0, 1, 1, 0, 0));
1077  vpsd1.add<std::vector<std::string>>("mappingFileNames", {});
1078  vpsd1.add<std::vector<std::string>>("maskFileNames", {});
1079  std::vector<edm::ParameterSet> temp1;
1080  temp1.reserve(1);
1081  {
1082  edm::ParameterSet temp2;
1083  temp2.addParameter<edm::EventRange>("validityRange", edm::EventRange(1, 0, 1, 1, 0, 0));
1084  temp2.addParameter<std::vector<std::string>>("mappingFileNames", {});
1085  temp2.addParameter<std::vector<std::string>>("maskFileNames", {});
1086  temp1.push_back(temp2);
1087  }
1088  desc.addVPSet("configuration", vpsd1, temp1)->setComment("validityRange, mappingFileNames and maskFileNames");
1089  }
1090  descriptions.add("totemDAQMappingESSourceXML", desc);
1091  // or use the following to generate the label from the module's C++ type
1092  //descriptions.addWithDefaultLabel(desc);
1093 }
1094 
1095 //----------------------------------------------------------------------------------------------------
1096 
Detector ID class for TOTEM Si strip detectors.
Definition: TotemRPDetId.h:30
Log< level::Info, true > LogVerbatim
auto setWhatProduced(T *iThis, const es::Label &iLabel={})
Definition: ESProducer.h:166
Contains data on masked channels of a VFAT.
static const std::string tagChannel
T getParameter(std::string const &) const
Definition: ParameterSet.h:307
string GetNodeContent(xercesc::DOMNode *parent)
returns the content of the node
bool contains(EventRange const &lh, EventID const &rh)
Definition: EventRange.cc:37
Loads TotemDAQMapping and TotemAnalysisMask from two XML files.
Detector ID class for Totem T2 detectors. Bits [19:31] : Base CTPPSDetId class attributes Bits [16:18...
Definition: TotemT2DetId.h:25
static const std::string tagDiamondPlane
diamond specific tags
edm::ESProducts< std::unique_ptr< TotemDAQMapping >, std::unique_ptr< TotemAnalysisMask > > produce(const TotemReadoutRcd &)
std::string fullPath() const
Definition: FileInPath.cc:161
ESProducts< std::remove_reference_t< TArgs >... > products(TArgs &&... args)
Definition: ESProducts.h:128
edm::EventRange validityRange
validity interval
void xercesTerminate()
Definition: Xerces.cc:23
static const std::string tagTotemT2Tile
EventSetup record for TOTEM readout-related information.
bool currentBlockValid
flag whether the &#39;currentBlock&#39; index is valid
NodeType
enumeration of XML node types
std::pair< Time_t, Time_t > ValidityInterval
Definition: Time.h:17
TotemSymbID symbolicID
the symbolic id
static const std::string tagSampicCh
#define XERCES_CPP_NAMESPACE_QUALIFIER
Definition: LHERunInfo.h:16
NodeType GetNodeType(xercesc::DOMNode *)
determines node type
void xercesInitialize()
Definition: Xerces.cc:18
assert(be >=bs)
std::vector< std::string > mappingFileNames
the mapping files
void ParseTreeTotemT2(ParseType, xercesc::DOMNode *, NodeType, unsigned int parentID, const std::unique_ptr< TotemDAQMapping > &, const std::unique_ptr< TotemAnalysisMask > &)
recursive method to extract nT2-related information from the DOM tree
static const std::string tagChip1
COMMON Chip XML tags.
string subSystemName
label of the CTPPS sub-system
constexpr uint32_t mask
Definition: gpuClustering.h:26
static std::string to_string(const XMLCh *ch)
void setIntervalFor(const edm::eventsetup::EventSetupRecordKey &, const edm::IOVSyncValue &, edm::ValidityInterval &) override
sets infinite validity of this data
std::string toString(XMLCh const *toTranscode)
static const std::string tagTotemT2Plane
TOTEM nT2 specific tags.
void ParseTreeTotemTiming(ParseType, xercesc::DOMNode *, NodeType, unsigned int parentID, const std::unique_ptr< TotemDAQMapping > &, const std::unique_ptr< TotemAnalysisMask > &)
recursive method to extract RP-related information from the DOM tree
Symbolic ID describing an entity of a TOTEM subdetector.
Definition: TotemSymbId.h:18
static const std::string tagTotemTimingPlane
static const std::string tagDiamondCh
void addParameter(std::string const &name, T const &value)
Definition: ParameterSet.h:136
static const std::string tagRPStation
RP XML tags.
TotemFramePosition ChipFramePosition(xercesc::DOMNode *chipnode)
extracts VFAT&#39;s DAQ channel from XML attributes
void ParseTreeDiamond(ParseType, xercesc::DOMNode *, NodeType, unsigned int parentID, const std::unique_ptr< TotemDAQMapping > &, const std::unique_ptr< TotemAnalysisMask > &)
recursive method to extract RP-related information from the DOM tree
std::vector< std::string > maskFileNames
the mask files
bool fullMask
whether all channels of the VFAT shall be masked
ParameterDescriptionBase * add(U const &iLabel, T const &value)
unsigned int symbolicID
chip ID, raw integer representation of DetId class
Definition: TotemSymbId.h:21
const int verbosity
Hw Id mapping for Totem Timing (dynamical mapping in Sampic)
RunNumber_t run() const
Definition: EventID.h:38
#define DEFINE_FWK_EVENTSETUP_SOURCE(type)
Definition: SourceFactory.h:92
static const std::string tagArm
Common position tags.
static void fillDescriptions(edm::ConfigurationDescriptions &descriptions)
unsigned int hwID
the hardware ID (16 bit)
void ParseXML(ParseType, const string &file, const std::unique_ptr< TotemDAQMapping > &, const std::unique_ptr< TotemAnalysisMask > &)
parses XML file
TotemDAQMappingESSourceXML(const edm::ParameterSet &)
double b
Definition: hdecay.h:120
void add(std::string const &label, ParameterSetDescription const &psetDescription)
string GetNodeValue(xercesc::DOMNode *node)
returns the value of the node
const EventID & eventID() const
Definition: IOVSyncValue.h:40
ParseType
whether to parse a mapping of a mask XML
bool Test(xercesc::DOMNode *node, const std::string &name)
returns true iff the node is of the given name
HLT enums.
static const std::string tagAnalysisMask
double a
Definition: hdecay.h:121
std::set< unsigned char > maskedChannels
list of channels to be masked
unsigned int currentBlock
index of the current block in &#39;configuration&#39; array
static const std::string tagSampicBoard
totem timing specific tags
Detector ID class for CTPPS Timing Diamond detectors. Bits [19:31] : Assigend in CTPPSDetId Calss Bit...
void ParseTreeRP(ParseType, xercesc::DOMNode *, NodeType, unsigned int parentID, const std::unique_ptr< TotemDAQMapping > &, const std::unique_ptr< TotemAnalysisMask > &)
recursive method to extract RP-related information from the DOM tree
static const std::string tagRPPlane
std::vector< std::string > mappingFileNames
the mapping files
static const std::string tagTotemTimingCh
Log< level::Warning, false > LogWarning
static void fillDescriptions(edm::ConfigurationDescriptions &)
void GetChannels(xercesc::DOMNode *n, std::set< unsigned char > &channels)
Contains mappind data related to a VFAT.
def move(src, dest)
Definition: eostools.py:511
EventNumber_t event() const
Definition: EventID.h:40
TotemT2FramePosition ChipT2FramePosition(xercesc::DOMNode *chipnode)
extracts VFAT&#39;s DAQ channel from XML attributes for packed T2 payload
string CompleteFileName(const string &fn)
adds the path prefix, if needed
Detector ID class for CTPPS Totem Timing detectors. Bits [19:31] : Assigend in CTPPSDetId Calss Bits ...