ATLAS Offline Software
IdDictDictionary.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3  */
4 
6 
7 #include "IdDict/IdDictField.h"
8 #include "IdDict/IdDictLabel.h"
9 #include "IdDict/IdDictRegion.h"
10 #include "IdDict/IdDictGroup.h"
11 #include "IdDict/IdDictSubRegion.h"
13 #include "IdDict/IdDictMgr.h"
14 #include "IdDict/IdDictRange.h"
15 #include "src/Debugger.h"
16 #include "src/get_bits.h"
17 #include "Identifier/MultiRange.h"
18 #include <iostream>
19 
20 using IdDict::get_bits;
21 
22 static bool isNumber(const std::string& str) {
23  bool result = true;
24 
25  for (unsigned int i = 0; i < str.size(); ++i) {
26  if (!isdigit(str[i])) return(false);
27  }
28  if (0 == str.size()) return(false);
29 
30  return(result);
31 }
32 
35 
36 IdDictField* IdDictDictionary::find_field(const std::string& name) const {
37  std::map <std::string, IdDictField*>::const_iterator it;
38 
39  it = m_fields.find(name);
40 
41  if (it == m_fields.end()) {
42  // If parent exists, look for field there
43  if (m_parent_dict) {
44  it = m_parent_dict->m_fields.find(name);
45  if (it == m_parent_dict->m_fields.end()) {
46  return(0);
47  }
48  } else {
49  return(0);
50  }
51  }
52 
53  return((*it).second);
54 }
55 
56 IdDictLabel* IdDictDictionary::find_label(const std::string& field, const std::string& label) const {
57  IdDictField* idField = find_field(field);
58 
59  if (!idField) return nullptr;
60 
61  return(idField->find_label(label));
62 }
63 
64 int IdDictDictionary::get_label_value(const std::string& field, const std::string& label, int& value) const {
65  IdDictLabel* idLabel = find_label(field, label);
66 
67  if (!idLabel || !idLabel->m_valued) return(1);
68 
69  value = idLabel->m_value;
70  return(0);
71 }
72 
74  if (field == 0) return;
75 
76  std::string& name = field->m_name;
77 
78  m_fields[name] = field;
79 }
80 
82 IdDictDictionary::find_subregion(const std::string& name) const {
83  std::map <std::string, IdDictSubRegion*>::const_iterator it;
84 
85  it = m_subregions.find(name);
86 
87  if (it == m_subregions.end()) return(0);
88 
89  return((*it).second);
90 }
91 
92 IdDictRegion* IdDictDictionary::find_region(const std::string& region_name) const {
93  return find_region(region_name, "");
94 }
95 
96 IdDictRegion* IdDictDictionary::find_region(const std::string& region_name, const std::string& group_name) const {
97  for (size_t i = 0; i < m_regions.size(); ++i) {
98  IdDictRegion* region = m_regions[i];
99  if ((group_name != "") && (region->group_name() != group_name)) continue;
100  if ((region != 0) && (region_name == region->m_name)) return(region);
101  }
102 
103  return(0);
104 }
105 
107  for (size_t i = 0; i < m_groups.size(); ++i) {
109  if ((group != 0) && (group->name() == group_name)) return(group);
110  }
111 
112  return(0);
113 }
114 
116  if (subregion == 0) return;
117 
118  std::string& name = subregion->m_name;
119 
120  m_subregions[name] = subregion;
121 }
122 
124  m_subdictionary_names.push_back(name);
125 }
126 
128  // Add region to corresponding group
129  IdDictGroup* group = find_group(region->group_name());
130 
131  if (0 == group) {
132  group = new IdDictGroup(region->group_name());
133  m_groups.push_back(group);
134  }
135  group->add_dictentry(region);
136 }
137 
139  {
141 
142  for (it = m_fields.begin(); it != m_fields.end(); ++it) {
143  IdDictField* field = (*it).second;
144  field->resolve_references(idd);
145  }
146  }
147  {
149 
150  for (it = m_subregions.begin(); it != m_subregions.end(); ++it) {
151  IdDictSubRegion* subregion = (*it).second;
152  subregion->resolve_references(idd, *this);
153  }
154  }
155  {
156  size_t index = 0;
157 
159  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
160  (*it)->resolve_references(idd, *this, index);
161  }
162  }
163 }
164 
166  const std::string& tag) {
167  if (Debugger::debug()) {
168  std::cout << "IdDictDictionary::generate_implementation>" << std::endl;
169  }
170 
172  // Propagate to each region and copy their generation into the
173  // dict's vector.
175  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
176  (*it)->generate_implementation(idd, *this, tag);
177  // Get regions from group and save in m_regions
178  const regions_type& regions = (*it)->regions();
180  for (it1 = regions.begin(); it1 != regions.end(); ++it1) {
181  m_regions.push_back(*it1);
182  }
183  }
184 
185  // Loop again over groups and set the bit-packing - starting at
186  // level 0
187  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
188  // Copy to temporary vector all regions in the group. And
189  // look for regions in local m_regions vector for any
190  // regions "dummy", which come from reference
191  // dictionaries.
192  // Skip special group
193  if ("dummy" == (*it)->name()) continue;
194 
195  get_bits(m_regions, 0, (*it)->name());
196 // get_bits (regions, 0, (*it)->name());
197  }
198 
199  // Set integral over the number of bits
200  integrate_bits();
201 
202  // Set neighbours for regions
204  for (itr = m_regions.begin(); itr != m_regions.end(); ++itr) {
205  (*itr)->find_neighbours(*this);
206  }
207 
209  }
210 }
211 
214  m_regions.clear();
216  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
217  (*it)->reset_implementation();
218  }
220  }
221 }
222 
223 int
225  // Find first region that matches id
226 
228 
229  size_type i = 0;
230  for (it = m_regions.begin(); it != m_regions.end(); ++it, ++i) {
231  const IdDictRegion& region = *(*it);
232 
233  Range range = region.build_range();
234 
235  if (range.match(id) && range.fields() >= id.fields()) {
236  index = i;
237  return(0);
238  }
239  }
240 
241  return(1);
242 }
243 
245  return find_region(id, "");
246 }
247 
249  // Find first region that matches id
250 
251  IdDictRegion* pRegion = 0;
252 
254 
255  for (it = m_regions.begin(); it != m_regions.end(); ++it) {
256  IdDictRegion& region = *(*it);
257  if ((group_name != "") && (region.group_name() != group_name)) continue;
258 
259  Range range = region.build_range();
260 
261  if (range.match(id) && range.fields() >= id.fields()) {
262  pRegion = &region;
263  }
264  }
265 
266  return(pRegion);
267 }
268 
269 void
271  // For each region, loop over its levels and set the bit offset
272  // for each FieldImplementation
273 
274  for (IdDictRegion* region : m_regions) {
275  size_t bits_offset = 0;
276  for (IdDictFieldImplementation& impl : region->m_implementation) {
277  impl.optimize(); // optimize for decoding
278  impl.set_bits_offset(bits_offset);
279  bits_offset += impl.bits();
280 
281  // Set whether or not to decode index
282  Range::field field = impl.ored_field();
283  if ((not field.isBounded()) || (0 != field.get_minimum())) {
284  impl.set_decode_index(true);
285  }
286  }
287  }
288 }
289 
292 
294 
295  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
296  const IdDictGroup& group = *(*it);
297 
298  MultiRange group_mr = group.build_multirange();
299 
300  for (unsigned int i = 0; i < group_mr.size(); ++i) {
301  const Range& range = group_mr[i];
302  result.add(range);
303  }
304  }
305 
306  return(result);
307 }
308 
310  const Range& prefix,
311  const std::string& last_field) const {
313 
315  if ("" == last_field) {
316  // Take all fields
317  for (it = m_regions.begin(); it != m_regions.end(); ++it) {
318  const IdDictRegion& region = *(*it);
319 
320  // skip regions created from parents
321  if ("dummy" == region.m_name) continue;
322 
323  // skip empty regions - may arise from alternate_regions
324  // where a tag selects an empty region
325  if (region.m_is_empty) continue;
326 
327  Range range(region.build_range());
328  // Check region selection
329  if (range.match(region_id)) result.add(std::move(range));
330  }
331  } else {
332  // Not all fields required
333  for (it = m_regions.begin(); it != m_regions.end(); ++it) {
334  const IdDictRegion& region = *(*it);
335 
336  // skip regions created from parents
337  if ("dummy" == region.m_name) continue;
338 
339  // skip empty regions - may arise from alternate_regions
340  // where a tag selects an empty region
341  if (region.m_is_empty) continue;
342 
343  Range range(region.build_range());
344  // Check region selection
345  if (range.match(region_id)) {
346  // Build new range up to last_field and add it to result -
347  // remove duplicate ranges with addRangeToMR
348  Range new_range(prefix); // Prepend with prefix
349 
350  std::vector <IdDictFieldImplementation>::const_iterator fit;
351  for (fit = region.m_implementation.begin();
352  fit != region.m_implementation.end();
353  ++fit) {
355 
356 // new_range.add(impl.m_field);
357  new_range.add(impl.range()->build_range());
358 
359  if (last_field == impl.range()->m_field->m_name) {
360  break;
361  }
362  }
363  result.add(std::move(new_range));
364  }
365  }
366  }
367 
368  return(result);
369 }
370 
372  const std::string& group_name,
373  const Range& prefix,
374  const std::string& last_field) const {
376 
378  if ("" == last_field) {
379  // Take all fields
380  for (it = m_regions.begin(); it != m_regions.end(); ++it) {
381  const IdDictRegion& region = *(*it);
382 
383  // skip regions created from parents
384  if ("dummy" == region.m_name) continue;
385 
386  // skip empty regions - may arise from alternate_regions
387  // where a tag selects an empty region
388  if (region.m_is_empty) continue;
389 
390  Range range(region.build_range());
391  // Check region selection
392  if (range.match(region_id) && region.group_name() == group_name) result.add(std::move(range));
393  }
394  } else {
395  // Not all fields required
396  for (it = m_regions.begin(); it != m_regions.end(); ++it) {
397  const IdDictRegion& region = *(*it);
398 
399  // skip regions created from parents
400  if ("dummy" == region.m_name) continue;
401 
402  // skip empty regions - may arise from alternate_regions
403  // where a tag selects an empty region
404  if (region.m_is_empty) continue;
405 
406  Range range(region.build_range());
407  // Check region selection
408  if (range.match(region_id) && region.group_name() == group_name) {
409  // Build new range up to last_field and add it to result -
410  // remove duplicate ranges with addRangeToMR
411  Range new_range(prefix); // Prepend with prefix
412 
413  std::vector <IdDictFieldImplementation>::const_iterator fit;
414  for (fit = region.m_implementation.begin();
415  fit != region.m_implementation.end();
416  ++fit) {
418 
419 // new_range.add(impl.m_field);
420  new_range.add(impl.range()->build_range());
421 
422  if (last_field == impl.range()->m_field->m_name) {
423  break;
424  }
425  }
426  result.add(std::move(new_range));
427  }
428  }
429  }
430 
431  return(result);
432 }
433 
447 int
449  size_t index1,
450  size_t index2,
451  Identifier& packedId) const {
452  packedId = 0;
453 
454 
455  // Preconditions...
456 
457  if (index2 < index1) {
458  // bad parameters.
459  return(1);
460  }
461 
462  if (index1 >= id.fields()) {
463  // nothing very useful !!
464  return(1);
465  }
466 
467  if (index2 >= id.fields()) {
468  // bad parameter...
469  return(1);
470  }
471 
481  for (size_t k = 0; k < m_regions.size(); ++k) {
482  bool selected = true;
483 
484  const IdDictRegion& region = *m_regions[k];
485 
486  // Must skip empty regions - can arise when a tag selects an
487  // empty region
488  if (region.m_is_empty) continue;
489 
490  for (size_t i = 0; i < region.m_implementation.size(); ++i) {
491  if (i >= id.fields()) break;
492 
494 
495  if (!impl.field().match(id[i])) {
496  selected = false;
497  break;
498  }
499  }
500 
501  if (selected) {
502  size_t position = Identifier::NBITS;
503  // We have the proper region.
504  for (size_t i = index1; i <= index2; ++i) {
506 
507  Identifier::value_type index = impl.ored_field().get_value_index(id[i]);
508 
509  if (0 == position && impl.bits() > 0) {
510  return(1);
511  }
512 
513  position -= impl.bits();
514  packedId |= (index << position);
515  }
516  break;
517  }
518  }
519 
520 
521  return(0);
522 }
523 
524 int
526  size_t index1,
527  size_t index2,
528  size_t region_index,
529  Identifier& packedId,
530  size_t first_field_index) const {
531  // Preconditions...
532 
533  if (m_do_checks) {
534  if (index2 < index1) {
535  // bad parameters.
536  std::cout << "IdDictDictionary::pack32 - index2 < index1 - 1,2"
537  << index1 << " " << index2 << std::endl;
538  return(1);
539  }
540 
541  if (region_index >= m_regions.size()) {
542  // bad parameters.
543  std::cout << "IdDictDictionary::pack32 - region index incorrect - index,size"
544  << region_index << " " << m_regions.size() << std::endl;
545  return(1);
546  }
547  }
548 
549 
550  // Get the region
551  const IdDictRegion& region = *m_regions[region_index];
552 
553  if (m_do_checks) {
554  if (region.m_is_empty) {
555  std::cout << "IdDictDictionary::pack32 - region id empty" << std::endl;
556  // bad parameters.
557  return(1);
558  }
559  if (index1 < first_field_index) {
560  std::cout << "IdDictDictionary::pack32 - first_field_index > index1 "
561  << first_field_index << " " << index1 << std::endl;
562  return(1);
563  }
564  }
565 
566  // Set the starting position
567  size_t position = Identifier::NBITS;
568  if (!first_field_index) {
570  position -= impl.bits_offset();
571  }
572 
573  size_t field_index = 0;
574  for (size_t i = index1; i <= index2; ++i, ++field_index) {
576 
577  if (m_do_checks) {
578  // Field should be within allowed range
579  if (!impl.ored_field().match(fields[field_index])) {
580  std::cout << "IdDictDictionary::pack32 - field does NOT match: value, allowed values "
581  << fields[field_index] << " " << (std::string) impl.ored_field()
582  << std::endl;
583  // bad parameters.
584  return(1);
585  }
586 
587  // Check that we don't try to go below 0
588  if (0 == position && impl.bits() > 0) {
589  std::cout << "IdDictDictionary::pack32 - going past 0" << std::endl;
590  return(1);
591  }
592  }
593 
595  if (impl.decode_index()) {
596  index = impl.ored_field().get_value_index(fields[field_index]);
597  } else {
598  index = (Identifier::value_type) fields[field_index];
599  }
600 
601  position -= impl.bits();
602  packedId |= (index << position);
603  }
604 
605 
606  return(0);
607 }
608 
613  size_t index2,
614  size_t region_index,
615  Identifier& packedId) const {
616  // Preconditions...
617 
618  if (m_do_checks) {
619  if (index2 < index1) {
620  // bad parameters.
621  std::cout << "IdDictDictionary::pack32 - index2 < index1 - 1,2"
622  << index1 << " " << index2 << std::endl;
623  return(1);
624  }
625 
626  if (region_index >= m_regions.size()) {
627  // bad parameters.
628  std::cout << "IdDictDictionary::pack32 - region index incorrect - index,size"
629  << region_index << " " << m_regions.size() << std::endl;
630  return(1);
631  }
632  }
633 
634 
635  // Get the region
636  const IdDictRegion& region = *m_regions[region_index];
637 
638  if (m_do_checks) {
639  if (region.m_is_empty) {
640  std::cout << "IdDictDictionary::pack32 - region id empty" << std::endl;
641  // bad parameters.
642  return(1);
643  }
644  }
645 
646  size_t field_index = 0;
647  for (size_t i = index1; i <= index2; ++i, ++field_index) {
649 
650  size_t position = Identifier::NBITS - impl.bits_offset() - impl.bits();
651 
652  Identifier::value_type mask = (((Identifier::value_type) 1 << impl.bits()) - 1) << position;
653 
655 
656  packedId &= (mask);
657  }
658  return(0);
659 }
660 
665 #if defined(FLATTEN) && defined(__GNUC__)
666 // We compile this package with optimization, even in debug builds; otherwise,
667 // the heavy use of Eigen makes it too slow. However, from here we may call
668 // to out-of-line Eigen code that is linked from other DSOs; in that case,
669 // it would not be optimized. Avoid this by forcing all Eigen code
670 // to be inlined here if possible.
671 __attribute__ ((flatten))
672 #endif
673 int
675  const ExpandedIdentifier& prefix,
676  size_t index2,
677  ExpandedIdentifier& unpackedId) const {
678  ExpandedIdentifier localPrefix(prefix);
679 
680  unpackedId.clear();
681  if (localPrefix.isValid()) unpackedId = localPrefix;
682 
688  size_t index1 = 0; // field index
689  size_t position = Identifier::NBITS; // overall bit position - used for debugging only
690 
691  for (size_t k = 0; k < m_regions.size(); ++k) {
692  bool selected = false;
693 
694  const IdDictRegion& region = *m_regions[k];
695 
696  // Must skip empty regions - can arise when a tag selects an
697  // empty region
698  if (region.m_is_empty) continue;
699 
700  for (size_t i = 0; i < region.m_implementation.size(); ++i) {
701  if (i >= localPrefix.fields()) {
706  selected = true;
707  index1 = i;
708  break;
709  }
710 
712 
713  if (!impl.field().match(localPrefix[i])) {
714  break;
715  }
716  }
717  if (!selected) {
718  continue;
719  }
720 
726  for (size_t i = index1; i < region.m_implementation.size(); ++i) {
728 
729  if (impl.bits() == 0) continue;
730  Identifier::value_type mask = (static_cast<Identifier::value_type>(1) << impl.bits()) - 1;
731  if (position < impl.bits()) break; // Nothing more to get
732  size_t index = id.extract(position - impl.bits(), mask);
733 
734  if (index >= impl.ored_field().get_indices()) {
741  selected = false;
742  break;
743  }
744 
745  ExpandedIdentifier::element_type value = impl.ored_field().get_value_at(index);
746 
753  if (!impl.field().match(value)) {
754  selected = false;
755  break;
756  }
757 
758 
759 
760  // Found value
761 
762  unpackedId.add(value);
763  localPrefix.add(value);
764 
765  position -= impl.bits(); // overall bit position
766 
767 
768 
769  index1++; // next field
770 
771  if (index1 > index2) break; // quit at index2
772  }
773 
774  if (selected) break;
775  }
776 
777  return(0);
778 }
779 
785 int
787  const ExpandedIdentifier& prefix,
788  size_t index2,
789  const std::string& sep,
790  std::string& unpackedId) const {
791  ExpandedIdentifier localPrefix(prefix);
792 
793 
799  size_t index1 = 0; // field index
800  size_t position = Identifier::NBITS; // overall bit position - used for debugging only
801 
802  for (size_t k = 0; k < m_regions.size(); ++k) {
803  bool selected = false;
804 
805  const IdDictRegion& region = *m_regions[k];
806 
807  // Must skip empty regions - can arise when a tag selects an
808  // empty region
809  if (region.m_is_empty) continue;
810 
811 // for (size_t i = index1; i < region.m_implementation.size (); ++i)
812  for (size_t i = 0; i < region.m_implementation.size(); ++i) {
813  if (i >= localPrefix.fields()) {
818  selected = true;
819  index1 = i;
820  break;
821  }
822 
824 
825  if (!impl.field().match(localPrefix[i])) {
826  break;
827  }
828  }
829 
830  if (selected) {
837 // bits32 temp = id;
838 
839 // std::cout << "Region #" << region.m_index << " selected" << std::endl;
840 
841  for (size_t i = index1; i < region.m_implementation.size(); ++i) {
843 
844  if (impl.bits() == 0) continue;
845 
846  Identifier::value_type mask = (static_cast<Identifier::value_type>(1) << impl.bits()) - 1;
847 
848  if (position < impl.bits()) break; // Nothing more to get
849  size_t index = id.extract(position - impl.bits(), mask);
850 
851  if (index >= impl.ored_field().get_indices()) {
852  selected = false;
853  break;
854  }
855 
856  ExpandedIdentifier::element_type value = impl.ored_field().get_value_at(index);
857 
864  if (!impl.field().match(value)) {
865  selected = false;
866  break;
867  }
868 
869 
870  // Add value to string
871 
872  std::string str_value("nil");
873  char temp[20];
874 
875  // The policy below is:
876  // - if a value is a character string or name, just add this name
877  // - if a value is a number, then prefix it with the
878  // name of the field
879  //
880  // NOTE: min/max is a number, but for value/label we
881  // distinguish between number and name by looking for an IdDictLabel
882  const IdDictRange* range = impl.range();
883  IdDictLabel* label = range->m_field->find_label(range->m_label);
884  switch (range->m_specification) {
886  // For a range of values (numbers), add in the field name
887  str_value = range->m_field->m_name + ' ';
888  sprintf(temp, "%d", value);
889  str_value += temp;
890  break;
891 
894  str_value = "";
895  if (!label) {
896  // Is a number, add in field name
897  str_value += range->m_field->m_name + ' ';
898  }
899  str_value += range->m_label;
900  break;
901 
904  str_value = "";
905  // Is a name
906  if (label) {
907  // Found label with "find_label" on the field
908  if (label->m_valued) {
909  str_value += range->m_label;
910  }
911  } else {
912  // If not found with the "find" above, we must
913  // get the value and name from the range
914  // itself.
915 
916  unsigned int index1 = 0;
917  for (; index1 < range->m_values.size(); ++index1) {
918  if (value == range->m_values[index1]) {
919  break;
920  }
921  }
922 
923  // In some cases we
924  if (index1 < range->m_labels.size()) {
925  if (isNumber(range->m_labels[index1])) {
926  str_value += range->m_field->m_name + ' ';
927  }
928  str_value += range->m_labels[index1];
929  } else {
930  std::cout << "IdDictDictionary::unpack - Could not find value." << std::endl;
931  std::cout << "value " << value << std::endl;
932  std::cout << "field values " << std::endl;
933  for (unsigned int i = 0; i < range->m_values.size(); ++i) {
934  std::cout << range->m_values[i] << " ";
935  }
936  std::cout << std::endl;
937  }
938  }
939  break;
940 
942 
943  std::cout << "unknown" << std::endl;
944 
945  break;
946  }
947 
948 
949  if (index1) unpackedId += sep;
950  unpackedId += str_value;
951  localPrefix.add(value);
952 
953  position -= impl.bits(); // overall bit position
954 
955 
956 
957  index1++; // next field
958 
959  if (index1 > index2) break; // quit at index2
960  }
961  if (selected) break;
962  }
963  }
964 
965  return(0);
966 }
967 
976 int
978  size_t first_field_index,
979  size_t field_index,
980  size_t region_index,
981  int& field) const {
982  field = 0;
983 
984  if (m_do_checks) {
985  // Check regions
986  if (region_index >= m_regions.size()) {
987  std::cout << "IdDictDictionary::unpack - region index too large. Index, nregions "
988  << region_index << " " << m_regions.size() << std::endl;
989  return(1);
990  }
991  }
992 
993  const IdDictRegion& region = *m_regions.at(region_index);
994 
995  if (m_do_checks) {
996  // check number of fields
997  if (field_index >= region.m_implementation.size()) {
998  std::cout << "IdDictDictionary::unpack - field index too large. Index, nfields "
999  << field_index << " " << region.m_implementation.size()
1000  << std::endl;
1001  return(1);
1002  }
1003  }
1004 
1005  const IdDictFieldImplementation& impl = region.m_implementation.at(field_index);
1006  size_t prefix_offset = 0;
1007 
1008  size_t position = Identifier::NBITS; // overall bit position
1009 
1010  // One or more fields missing from prefix, get the offset
1011  if (first_field_index) {
1012  if (m_do_checks) {
1013  if (first_field_index >= region.m_implementation.size()) {
1014  std::cout << "IdDictDictionary::unpack - first_field_index too large. Index, nfields "
1015  << first_field_index << " " << region.m_implementation.size()
1016  << std::endl;
1017  return(1);
1018  }
1019  }
1020 
1021  // One or more fields missing from prefix, get the offset
1022  prefix_offset = region.m_implementation[first_field_index].bits_offset();
1023 
1024  if (m_do_checks) {
1025  // Should have a non-zero number of bits
1026  if (impl.bits() == 0) {
1027  std::cout << "IdDictDictionary::unpack - no bits for this field. Region, field indexes "
1028  << region_index << " " << field_index << std::endl;
1029  return(1);
1030  }
1031 
1032  // Check the shift value
1033  if (impl.bits() + impl.bits_offset() - prefix_offset > position) {
1034  std::cout << "IdDictDictionary::unpack - bits + offset too large. Region, field indexes, bits, offset "
1035  << region_index << " " << field_index << " "
1036  << impl.bits() << " " << impl.bits_offset() << " " << prefix_offset
1037  << std::endl;
1038  return(1);
1039  }
1040  }
1041  }
1042 
1043  Identifier::value_type mask = (static_cast<Identifier::value_type>(1) << impl.bits()) - 1;
1044 
1045  size_t index = id.extract(position -= impl.bits() + impl.bits_offset() - prefix_offset, mask);
1046 
1047  field = index;
1048  if (impl.decode_index()) field = impl.ored_field().get_value_at(index);
1049 
1050 
1051  return(0);
1052 }
1053 
1063 int
1065  size_t first_field_index,
1066  size_t begin_field_index,
1067  size_t end_field_index,
1068  size_t region_index,
1069  Identifier& idout) const {
1070  idout = Identifier();
1071  if (region_index >= m_regions.size()) {
1072  std::cout << "IdDictDictionary::copy - region index too large. Index, nregions "
1073  << region_index << " " << m_regions.size() << std::endl;
1074  return(1);
1075  }
1076 
1077  const IdDictRegion& region = *m_regions[region_index];
1078 
1079  if (first_field_index >= region.m_implementation.size() ||
1080  begin_field_index >= region.m_implementation.size() ||
1081  end_field_index >= region.m_implementation.size()) {
1082  std::cout << "IdDictDictionary::copy - field index too large. Indexes first, begin, end, nfields "
1083  << first_field_index << " "
1084  << begin_field_index << " "
1085  << end_field_index << " "
1086  << region.m_implementation.size()
1087  << std::endl;
1088  return(1);
1089  }
1090 
1091  size_t missing_offset = 0;
1092  if (first_field_index) {
1093  if (first_field_index > begin_field_index) {
1094  std::cout << "IdDictDictionary::copy - first_field_index > begin_field_index. Indexes "
1095  << first_field_index << " " << begin_field_index << std::endl;
1096  return(1);
1097  }
1098  // One or more fields missing from prefix, get the offset
1099  missing_offset = region.m_implementation[first_field_index].bits_offset();
1100  }
1101 
1102  size_t prefix_offset = 0;
1103  if (begin_field_index) {
1104  if (begin_field_index > end_field_index) {
1105  std::cout << "IdDictDictionary::copy - begin_field_index > end_field_index. Indexes "
1106  << begin_field_index << " " << end_field_index << std::endl;
1107  return(1);
1108  }
1109  // One or more fields missing from prefix, get the offset
1110  prefix_offset = region.m_implementation[begin_field_index].bits_offset();
1111  }
1112 
1113  const IdDictFieldImplementation& impl = region.m_implementation[end_field_index];
1114  size_t suffix_offset = impl.bits() + impl.bits_offset();
1115 
1116  size_t position = Identifier::NBITS; // overall bit position
1117 
1118  if (position < prefix_offset - missing_offset) {
1119  std::cout << "IdDictDictionary::copy - position < prefix + missing. "
1120  << prefix_offset << " " << missing_offset << std::endl;
1121  return(1);
1122  }
1123 
1124 
1125  if (position < suffix_offset + missing_offset) {
1126  std::cout << "IdDictDictionary::copy - position < suffix + missing. "
1127  << suffix_offset << " " << missing_offset << std::endl;
1128  return(1);
1129  }
1130 
1131 
1132  // prepare the mask for copying
1133 
1135 
1136  Identifier::value_type prefix_mask =
1137  prefix_offset ? (static_cast<Identifier::value_type>(1) << (position - prefix_offset + missing_offset)) - 1 : 0;
1138 
1139  Identifier::value_type suffix_mask =
1140  (static_cast<Identifier::value_type>(1) << (position - suffix_offset + missing_offset)) - 1;
1141 
1142  mask -= prefix_mask + suffix_mask;
1143 
1144  idout = idin.mask_shift(mask, missing_offset);
1145 
1146 
1147  return(0);
1148 }
1149 
1150 bool
1152  return(m_do_checks);
1153 }
1154 
1155 void
1158 }
1159 
1160 bool
1162  return(m_do_neighbours);
1163 }
1164 
1165 void
1168 }
1169 
1195  // check #1
1196 
1198 
1199  if (mr.has_overlap()) return(false);
1200 
1201 
1202  return(true);
1203 }
1204 
1216  // verify
1217  if (verify()) {
1218  std::map< ExpandedIdentifier, IdDictDictEntry* > regions;
1219 
1221 
1222  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
1223  (*it)->sort();
1224  }
1225  } else {
1226  std::cout << "IdDictDictionary::sort - WARNING verify is FALSE - cannot sort "
1227  << std::endl;
1228  }
1229 }
1230 
1232  {
1234 
1235  for (it = m_subregions.begin(); it != m_subregions.end(); ++it) {
1236  IdDictSubRegion* subregion = (*it).second;
1237  subregion->clear();
1238  delete subregion;
1239  }
1240 
1241  m_subregions.clear();
1242  }
1243 
1244  {
1246 
1247  for (it = m_fields.begin(); it != m_fields.end(); ++it) {
1248  IdDictField* field = (*it).second;
1249  field->clear();
1250  delete field;
1251  }
1252 
1253  m_fields.clear();
1254  }
1255 
1256  {
1258 
1259  for (it = m_groups.begin(); it != m_groups.end(); ++it) {
1260  IdDictGroup* group = *it;
1261  group->clear();
1262  delete group;
1263  }
1264 
1265  m_groups.clear();
1266  }
1267 }
xAOD::iterator
JetConstituentVector::iterator iterator
Definition: JetConstituentVector.cxx:68
IdDictDictionary::find_region
IdDictRegion * find_region(const std::string &region_name) const
Definition: IdDictDictionary.cxx:92
IdDictRange.h
IdDictMgr.h
IdDictDictionary::build_multirange
MultiRange build_multirange() const
Get MultiRange for full dictionary.
Definition: IdDictDictionary.cxx:290
IdDictDictionary::unpack
int unpack(const Identifier &id, const ExpandedIdentifier &prefix, size_t index2, ExpandedIdentifier &unpackedId) const
Unpack the value_type id to an expanded Identifier, considering the provided prefix (result will incl...
Definition: IdDictDictionary.cxx:674
IdDictRegion::resolve_references
void resolve_references(const IdDictMgr &idd, IdDictDictionary &dictionary)
Definition: IdDictRegion.cxx:28
IdDictDictionary::reset
int reset(size_t index1, size_t index2, size_t region_index, Identifier &packedId) const
Reset fields from index1 to index2.
Definition: IdDictDictionary.cxx:612
get_generator_info.result
result
Definition: get_generator_info.py:21
IdDictGroup
Definition: IdDictGroup.h:19
IdDictDictionary::do_neighbours
bool do_neighbours(void) const
Neighbour initialization is performed by default One can switch or query this mode for any idHelper w...
Definition: IdDictDictionary.cxx:1161
IdDictLabel.h
IdDictDictionary::generate_implementation
void generate_implementation(const IdDictMgr &idd, const std::string &tag="")
Definition: IdDictDictionary.cxx:165
IdDictRange::by_minmax
@ by_minmax
Definition: IdDictRange.h:40
IdDictLabel::m_value
int m_value
Definition: IdDictLabel.h:13
IdDictDictionary::m_groups
std::vector< IdDictGroup * > m_groups
Definition: IdDictDictionary.h:237
IdDictDictionary::do_checks
bool do_checks(void) const
Checks are performed by default in debug compilation and NOT in optimized compilation.
Definition: IdDictDictionary.cxx:1151
IdDict::get_bits
void get_bits(const RV &regions, size_t level, const std::string &group)
Definition: get_bits.cxx:45
index
Definition: index.py:1
IdDictRange::by_label
@ by_label
Definition: IdDictRange.h:38
IdDictDictionary::find_label
IdDictLabel * find_label(const std::string &field, const std::string &label) const
Definition: IdDictDictionary.cxx:56
Identifier::mask_shift
value_type mask_shift(value_type mask, size_type shift) const
extract field(s) by masking first, then shifting
IdDictDictionary.h
IdDictDictionary::groups_const_it
groups_type::const_iterator groups_const_it
Definition: IdDictDictionary.h:231
ExpandedIdentifier::add
void add(element_type value)
Append a value into a new field.
skel.it
it
Definition: skel.GENtoEVGEN.py:407
IdDictRange::by_labels
@ by_labels
Definition: IdDictRange.h:39
IdDictDictionary::regions_type
std::vector< IdDictRegion * > regions_type
Definition: IdDictDictionary.h:225
ExpandedIdentifier
Definition: DetectorDescription/Identifier/Identifier/ExpandedIdentifier.h:102
IdDictDictionary::m_do_checks
bool m_do_checks
Definition: IdDictDictionary.h:245
IdDictField::find_label
IdDictLabel * find_label(const std::string &name) const
Definition: IdDictField.cxx:26
athena.value
value
Definition: athena.py:124
ExpandedIdentifier::fields
size_type fields() const
IdDictSubRegion.h
IdDictDictionary::~IdDictDictionary
~IdDictDictionary()
Debugger.h
ReadOfcFromCool.field
field
Definition: ReadOfcFromCool.py:48
IdDictRegion::clear
void clear()
Definition: IdDictRegion.cxx:126
IdDictDictEntry
Definition: IdDictDictEntry.h:13
IdDictDictionary::pack32
int pack32(const ExpandedIdentifier &id, size_t index1, size_t index2, Identifier &packedId) const
Pack to 32bits the subset of id between (inclusive) index1 and index2 - this is generic,...
Definition: IdDictDictionary.cxx:448
IdDictGroup.h
IdDictDictionary::find_field
IdDictField * find_field(const std::string &name) const
Definition: IdDictDictionary.cxx:36
CalibDbCompareRT.region_id
region_id
Definition: CalibDbCompareRT.py:68
IdDictRegion
Definition: IdDictRegion.h:20
IdDictDictionary::resolve_references
void resolve_references(const IdDictMgr &idd)
Definition: IdDictDictionary.cxx:138
python.utils.AtlRunQueryLookup.mask
string mask
Definition: AtlRunQueryLookup.py:460
IdDictRegion::m_name
std::string m_name
Definition: IdDictRegion.h:44
IdDictDictionary::verify
bool verify() const
Here, we verify global constraints : (this must only be applied after the resolve_references and gene...
Definition: IdDictDictionary.cxx:1194
IdDictLabel::m_valued
bool m_valued
Definition: IdDictLabel.h:12
IdDictDictionary::reset_implementation
void reset_implementation()
Definition: IdDictDictionary.cxx:212
IdDictDictionary::m_parent_dict
IdDictDictionary * m_parent_dict
Definition: IdDictDictionary.h:239
get_bits.h
IdDictDictionary::size_type
Identifier::size_type size_type
Definition: IdDictDictionary.h:33
IdDictMgr
Definition: IdDictMgr.h:14
IdDictDictionary::groups_it
groups_type::iterator groups_it
Definition: IdDictDictionary.h:230
IdDictDictionary::m_fields
std::map< std::string, IdDictField * > m_fields
Definition: IdDictDictionary.h:233
IdDictDictionary::IdDictDictionary
IdDictDictionary()
IdDictDictionary::find_group
IdDictGroup * find_group(const std::string &group_name) const
Definition: IdDictDictionary.cxx:106
Identifier::ALL_BITS
static constexpr value_type ALL_BITS
Definition: DetectorDescription/Identifier/Identifier/Identifier.h:33
IdDictRegion::build_range
Range build_range() const
Definition: IdDictRegion.cxx:147
Trk::index1
@ index1
Definition: BoundarySurfaceFace.h:48
Identifier::NBITS
static constexpr unsigned int NBITS
Definition: DetectorDescription/Identifier/Identifier/Identifier.h:31
lumiFormat.i
int i
Definition: lumiFormat.py:85
DetDescrDictionaryDict::it1
std::vector< HWIdentifier >::iterator it1
Definition: DetDescrDictionaryDict.h:17
IdDictDictionary::m_generated_implementation
bool m_generated_implementation
Definition: IdDictDictionary.h:244
IdDictRegion::m_is_empty
bool m_is_empty
Definition: IdDictRegion.h:47
add-xsec-uncert-quadrature-N.label
label
Definition: add-xsec-uncert-quadrature-N.py:104
IdDictDictionary::m_regions
std::vector< IdDictRegion * > m_regions
Definition: IdDictDictionary.h:235
plotBeamSpotVxVal.range
range
Definition: plotBeamSpotVxVal.py:195
checkCorrelInHIST.prefix
dictionary prefix
Definition: checkCorrelInHIST.py:391
mc.group_name
group_name
Definition: mc.PhPy8EG_A14NNPDF23_NNLOPS_example.py:33
IdDictRegion::group_name
std::string group_name() const
Definition: IdDictRegion.cxx:13
IdDictRange::unknown
@ unknown
Definition: IdDictRange.h:35
IdDictDictionary::add_subdictionary_name
void add_subdictionary_name(const std::string &name)
Definition: IdDictDictionary.cxx:123
IdDictDictionary::regions_it
regions_type::iterator regions_it
Definition: IdDictDictionary.h:226
IdDictLabel
Definition: IdDictLabel.h:10
Debugger::debug
static bool debug()
Definition: Debugger.h:18
MuonValidation_CreateResolutionProfiles.fit
def fit(h, emin, emax)
Definition: MuonValidation_CreateResolutionProfiles.py:69
IdDictDictionary::regions_const_it
regions_type::const_iterator regions_const_it
Definition: IdDictDictionary.h:227
IdDictDictionary::get_label_value
int get_label_value(const std::string &field, const std::string &label, int &value) const
Definition: IdDictDictionary.cxx:64
python.update_ci_reference_files.mr
mr
Definition: update_ci_reference_files.py:415
grepfile.sep
sep
Definition: grepfile.py:38
IdDictDictionary::sort
void sort()
Sort:
Definition: IdDictDictionary.cxx:1215
MultiRange
A MultiRange combines several Ranges.
Definition: MultiRange.h:17
Trk::index2
@ index2
Definition: BoundarySurfaceFace.h:49
IdDictDictionary::clear
void clear()
Definition: IdDictDictionary.cxx:1231
name
std::string name
Definition: Control/AthContainers/Root/debug.cxx:240
IdDictDictionary::add_field
void add_field(IdDictField *field)
Definition: IdDictDictionary.cxx:73
ExpandedIdentifier::isValid
bool isValid() const
Returns whether the expanded Identifier contains any information.
IdDictDictionary::m_do_neighbours
bool m_do_neighbours
Definition: IdDictDictionary.h:246
IdDictDictEntry::group_name
virtual std::string group_name() const =0
Range
A Range describes the possible ranges for the field values of an ExpandedIdentifier.
Definition: DetectorDescription/Identifier/Identifier/Range.h:29
MultiRange.h
Range::add
void add()
Add a wild card field.
Definition: DetectorDescription/Identifier/src/Range.cxx:75
IdDictFieldImplementation.h
IdDictDictionary::find_subregion
IdDictSubRegion * find_subregion(const std::string &subregion_name) const
Definition: IdDictDictionary.cxx:82
IdDictRange
Definition: IdDictRange.h:18
impl
Definition: CaloGPUClusterAndCellDataMonitorOptions.h:46
DeMoScan.index
string index
Definition: DeMoScan.py:364
__attribute__
__attribute__((always_inline)) inline uint16_t TileCalibDrawerBase
Definition: TileCalibDrawerBase.h:190
IdDictDictionary::m_subdictionary_names
std::vector< std::string > m_subdictionary_names
Definition: IdDictDictionary.h:238
IdDictField.h
CaloLCW_tf.group
group
Definition: CaloLCW_tf.py:28
IdDictDictionary::m_subregions
std::map< std::string, IdDictSubRegion * > m_subregions
Definition: IdDictDictionary.h:234
IdDictDictionary::add_dictentry
void add_dictentry(IdDictDictEntry *entry)
Definition: IdDictDictionary.cxx:127
MultiRange::size
size_type size() const
Definition: MultiRange.cxx:70
IdentifierField
This is the individual specification for the range of one ExpandedIdentifier IdentifierField.
Definition: IdentifierField.h:21
IdDictRange::by_values
@ by_values
Definition: IdDictRange.h:37
ExpandedIdentifier::clear
void clear()
Erase all fields.
Identifier::value_type
unsigned long long value_type
Definition: DetectorDescription/Identifier/Identifier/Identifier.h:27
isNumber
bool isNumber(const std::string &s)
Definition: PoolSvc.cxx:52
str
Definition: BTagTrackIpAccessor.cxx:11
IdDictRegion.h
IdDictSubRegion
Definition: IdDictSubRegion.h:13
IdDictRange::by_value
@ by_value
Definition: IdDictRange.h:36
CaloCondBlobAlgs_fillNoiseFromASCII.tag
string tag
Definition: CaloCondBlobAlgs_fillNoiseFromASCII.py:24
IdDictDictionary::set_do_neighbours
void set_do_neighbours(bool do_neighbours)
Definition: IdDictDictionary.cxx:1166
CaloCondBlobAlgs_fillNoiseFromASCII.fields
fields
Definition: CaloCondBlobAlgs_fillNoiseFromASCII.py:106
IdDictField
Definition: IdDictField.h:15
IdDictFieldImplementation
IdDictFieldImplementation is used to capture the specification of a single field of an Identifier.
Definition: IdDictFieldImplementation.h:58
IdDictDictionary::integrate_bits
void integrate_bits()
Set up integral of bits for efficient unpacking.
Definition: IdDictDictionary.cxx:270
ExpandedIdentifier::element_type
int element_type
Definition: DetectorDescription/Identifier/Identifier/ExpandedIdentifier.h:106
IdDictRegion::m_implementation
std::vector< IdDictFieldImplementation > m_implementation
Definition: IdDictRegion.h:42
IdDictDictionary::copy
int copy(const Identifier &idin, size_t first_field_index, size_t begin_field_index, size_t end_field_index, size_t region_index, Identifier &idout) const
Copy a number of fields of the value_type id into another value_type id.
Definition: IdDictDictionary.cxx:1064
IdDictDictionary::add_subregion
void add_subregion(IdDictSubRegion *subregion)
Definition: IdDictDictionary.cxx:115
fitman.k
k
Definition: fitman.py:528
Identifier
Definition: IdentifierFieldParser.cxx:14
IdDictDictionary::set_do_checks
void set_do_checks(bool do_checks)
Definition: IdDictDictionary.cxx:1156