Belle II Software  release-08-00-10
commondqm.py
1 #!/usr/bin/env python3
2 # -*- coding: utf-8 -*-
3 
4 
11 
12 import basf2 as b2
13 from svd import add_svd_create_recodigits
14 from svd.dqm_utils import add_svd_dqm_dose
15 from geometry import check_components
16 from analysisDQM import add_analysis_dqm, add_mirabelle_dqm
17 import neurotrigger
18 
19 
20 def add_common_dqm(path, components=None, dqm_environment="expressreco", dqm_mode="dont_care", create_hlt_unit_histograms=False):
21  """
22  This function adds DQMs which are common for Cosmic runs and Collion runs
23 
24  @param components: A list of the detector components which are available in this
25  run of basf2
26  @param dqm_environment: The environment the DQM modules are running in
27  "expressreco" (default) if running on the ExpressReco system
28  "hlt" if running on the HLT online reconstructon nodes
29  If running on the hlt, you may want to output less or other DQM plots
30  due to the limited bandwith of the HLT nodes.
31  @param dqm_mode: How to split up the path for online/HLT.
32  For dqm_mode == "dont_care" all the DQM modules should be added.
33  For dqm_mode == "all_events" only the DQM modules which should run on all events
34  (filtered and dismissed) should be added
35  For dqm_mode == "before_reco" only the DQM modules which should run before
36  all reconstruction
37  For dqm_mode == "filtered" only the DQM modules which should run on filtered
38  events should be added
39  @param create_hlt_unit_histograms: Parameter for SoftwareTiggerHLTDQMModule.
40  Should be True only when running on the HLT servers
41  """
42  assert dqm_mode in ["dont_care", "all_events", "filtered", "before_filter"]
43  # Check components.
44  check_components(components)
45 
46  if dqm_mode in ["dont_care", "filtered"]:
47  # TTD trigger and bunch injection monitoring
48  path.add_module('TTDDQM')
49 
50  if dqm_environment == "expressreco" and (dqm_mode in ["dont_care"]):
51  # PXD (not useful on HLT)
52  if components is None or 'PXD' in components:
53  path.add_module('PXDDAQDQM', histogramDirectoryName='PXDDAQ')
54  path.add_module('PXDROIDQM', histogramDirectoryName='PXDROI')
55  path.add_module('PXDDQMExpressReco', histogramDirectoryName='PXDER')
56  path.add_module('SetupGenfitExtrapolation')
57  path.add_module('PXDROIFinder',
58  recoTrackListName='RecoTracks',
59  PXDInterceptListName='PXDIntercepts')
60  # moved to cosmics/collision as we need different cuts
61  # path.add_module('PXDDQMEfficiency', histogramDirectoryName='PXDEFF')
62  path.add_module('PXDTrackClusterDQM', histogramDirectoryName='PXDER')
63  path.add_module('PXDInjectionDQM', histogramDirectoryName='PXDINJ', eachModule=True)
64  # SVD
65  if components is None or 'SVD' in components:
66  # reconstruct SVDRecoDigits first of all
67  add_svd_create_recodigits(path)
68 
69  # SVD DATA FORMAT
70  svdunpackerdqm = b2.register_module('SVDUnpackerDQM')
71  path.add_module(svdunpackerdqm)
72  # offline ZS emulator
73  path.add_module(
74  'SVDZeroSuppressionEmulator',
75  SNthreshold=5,
76  ShaperDigits='SVDShaperDigits',
77  ShaperDigitsIN='SVDShaperDigitsZS5',
78  FADCmode=True)
79  # SVD Occupancy after Injection
80  path.add_module('SVDDQMInjection', ShaperDigits='SVDShaperDigitsZS5')
81  # SVDDQMExpressReco General
82  path.add_module('SVDDQMExpressReco',
83  offlineZSShaperDigits='SVDShaperDigitsZS5')
84  # SVD HIT TIME
85  path.add_module('SVDDQMHitTime')
86  # SVD EFFICIENCY
87  path.add_module('SetupGenfitExtrapolation')
88  path.add_module('SVDROIFinder',
89  recoTrackListName='RecoTracks',
90  SVDInterceptListName='SVDIntercepts')
91  path.add_module('SVDDQMEfficiency')
92  # SVD CLUSTERS ON TRACK
93  path.add_module('SVDDQMClustersOnTrack')
94  # SVD DOSE
95  add_svd_dqm_dose(path, 'SVDShaperDigitsZS5')
96 
97  # Event time measuring detectors
98  if components is None or 'CDC' in components or 'ECL' in components or 'TOP' in components:
99  eventT0DQMmodule = b2.register_module('EventT0DQM')
100  path.add_module(eventT0DQMmodule)
101 
102  if dqm_environment == "hlt" and (dqm_mode in ["dont_care", "before_filter"]):
103  path.add_module(
104  "SoftwareTriggerHLTDQM",
105  createHLTUnitHistograms=create_hlt_unit_histograms,
106  createTotalResultHistograms=False,
107  createExpRunEventHistograms=False,
108  createErrorFlagHistograms=True,
109  cutResultIdentifiers={},
110  histogramDirectoryName="softwaretrigger_before_filter",
111  pathLocation="before filter",
112  ).set_name("SoftwareTriggerHLTDQM_before_filter")
113 
114  path.add_module("StatisticsTimingHLTDQM",
115  createHLTUnitHistograms=create_hlt_unit_histograms,
116  )
117 
118  if dqm_environment == "hlt" and (dqm_mode in ["dont_care", "filtered"]):
119  # HLT
120  hlt_trigger_lines_in_plot = []
121  hlt_skim_lines_in_plot = []
122 
123  hlt_trigger_lines_per_unit_in_plot = [
124  "ge3_loose_tracks_inc_1_tight_not_ee2leg",
125  "Elab_gt_0.5_plus_2_others_with_Elab_gt_0.18_plus_no_clust_with_Ecms_gt_2.0",
126  "selectee",
127  "Estargt2_GeV_cluster",
128  ]
129  cutResultIdentifiers = {}
130 
131  from softwaretrigger import filter_categories, skim_categories
132 
133  filter_cat = [method for method in dir(filter_categories) if method.startswith('__') is False if method != 'RESULTS']
134  skim_cat = [method for method in dir(skim_categories) if method.startswith('__') is False]
135 
136  def read_lines(category):
137  return [i.split(" ", 1)[1].replace(" ", "_") for i in category]
138 
139  for i in filter_cat:
140  cutResultIdentifiers[i] = {"filter": read_lines(getattr(filter_categories, i))}
141  hlt_trigger_lines_in_plot += read_lines(getattr(filter_categories, i))
142 
143  for i in skim_cat:
144  cutResultIdentifiers[i] = {"skim": read_lines(getattr(skim_categories, i))}
145  hlt_skim_lines_in_plot += read_lines(getattr(skim_categories, i))
146 
147  cutResultIdentifiers["skim"] = {"skim": hlt_skim_lines_in_plot}
148  cutResultIdentifiers["filter"] = {"filter": hlt_trigger_lines_in_plot}
149 
150  additionalL1Identifiers = [
151  'ffy',
152  'fyo',
153  'c4',
154  'hie',
155  'mu_b2b',
156  'mu_eb2b',
157  'beklm',
158  'eklm2',
159  'cdcklm1',
160  'seklm1',
161  'ieklm1',
162  'ecleklm1',
163  'fso',
164  'fioiecl1',
165  'ff30',
166  'stt',
167  'ioiecl1',
168  'ioiecl2',
169  'lml1',
170  'lml2',
171  'lml3',
172  'lml4',
173  'lml5',
174  'lml6',
175  'lml7',
176  'lml8',
177  'lml9',
178  'lml10',
179  'lml12',
180  'lml13',
181  'bhapur']
182 
183  # Default plot
184  path.add_module(
185  "SoftwareTriggerHLTDQM",
186  cutResultIdentifiers=cutResultIdentifiers,
187  l1Identifiers=["fff", "ffo", "lml0", "ffb", "fp"],
188  additionalL1Identifiers=additionalL1Identifiers,
189  createHLTUnitHistograms=create_hlt_unit_histograms,
190  cutResultIdentifiersPerUnit=hlt_trigger_lines_per_unit_in_plot,
191  pathLocation="after filter",
192  )
193  # Skim plots where bhabha contamination is removed
194  path.add_module(
195  "SoftwareTriggerHLTDQM",
196  cutResultIdentifiers={
197  "skim": {"skim": hlt_skim_lines_in_plot},
198  },
199  cutResultIdentifiersIgnored={
200  "skim": [
201  "accept_bhabha_all",
202  ]
203  },
204  createTotalResultHistograms=False,
205  createExpRunEventHistograms=False,
206  histogramDirectoryName="softwaretrigger_skim_nobhabha",
207  ).set_name("SoftwareTriggerHLTDQM_skim_nobhabha")
208 
209  if dqm_environment == "hlt" and (dqm_mode in ["dont_care", "filtered"]):
210  # SVD DATA FORMAT
211  if components is None or 'SVD' in components:
212  svdunpackerdqm = b2.register_module('SVDUnpackerDQM')
213  path.add_module(svdunpackerdqm)
214 
215  # CDC
216  if (components is None or 'CDC' in components) and (dqm_mode in ["dont_care", "filtered"]):
217  cdcdqm = b2.register_module('cdcDQM7')
218  path.add_module(cdcdqm)
219 
220  module_names = [m.name() for m in path.modules()]
221  if ('SoftwareTrigger' in module_names):
222  cdcdedxdqm = b2.register_module('CDCDedxDQM')
223  path.add_module(cdcdedxdqm)
224 
225  if dqm_environment == "expressreco":
226  path.add_module('CDCDQM')
227 
228  # ECL
229  if (components is None or 'ECL' in components) and (dqm_mode in ["dont_care", "filtered"]):
230  ecldqm = b2.register_module('ECLDQM')
231  path.add_module(ecldqm)
232  ecldqmext = b2.register_module('ECLDQMEXTENDED')
233  path.add_module(ecldqmext)
234  path.add_module('ECLDQMOutOfTimeDigits')
235  path.add_module('ECLDQMConnectedRegions')
236  # we dont want to create large histograms on HLT, thus ERECO only
237  if dqm_environment == "expressreco":
238  path.add_module('ECLDQMInjection', histogramDirectoryName='ECLINJ')
239 
240  # TOP
241  if (components is None or 'TOP' in components) and (dqm_mode in ["dont_care", "filtered"]):
242  topdqm = b2.register_module('TOPDQM')
243  path.add_module(topdqm)
244 
245  # KLM
246  if (components is None or 'KLM' in components) and (dqm_mode in ["dont_care", "filtered"]):
247  klmdqm = b2.register_module("KLMDQM")
248  path.add_module(klmdqm)
249 
250  # TRG before all reconstruction runs (so on all events with all unpacked information)
251  if (components is None or 'TRG' in components) and (dqm_mode in ["dont_care", "before_filter"]):
252  # TRGECL
253  trgecldqm = b2.register_module('TRGECLDQM')
254  path.add_module(trgecldqm)
255  # TRGGDL
256  trggdldqm = b2.register_module('TRGGDLDQM')
257  trggdldqm.param('skim', 0)
258  path.add_module(trggdldqm)
259  # TRGTOP
260  trgtopdqm = b2.register_module('TRGTOPDQM')
261  trgtopdqm.param('skim', 0)
262  path.add_module(trgtopdqm)
263  # TRGGRL
264  trggrldqm = b2.register_module('TRGGRLDQM')
265  path.add_module(trggrldqm)
266  # TRGCDCTSF
267  nmod_tsf = [0, 1, 2, 3, 4, 5, 6]
268  for mod_tsf in nmod_tsf:
269  path.add_module('TRGCDCTSFDQM', TSFMOD=mod_tsf)
270  # TRGCDC2D
271  trgcdct2ddqm = b2.register_module('TRGCDCT2DDQM')
272  path.add_module(trgcdct2ddqm)
273  # TRGCDC3D
274  nmod_t3d = [0, 1, 2, 3]
275  for mod_t3d in nmod_t3d:
276  path.add_module('TRGCDCT3DConverter',
277  hitCollectionName='FirmCDCTriggerSegmentHits' + str(mod_t3d),
278  addTSToDatastore=True,
279  EventTimeName='FirmBinnedEventT0' + str(mod_t3d),
280  addEventTimeToDatastore=True,
281  inputCollectionName='FirmTRGCDC2DFinderTracks' + str(mod_t3d),
282  add2DFinderToDatastore=True,
283  outputCollectionName='FirmTRGCDC3DFitterTracks' + str(mod_t3d),
284  add3DToDatastore=True,
285  fit3DWithTSIM=0,
286  firmwareResultCollectionName='TRGCDCT3DUnpackerStore' + str(mod_t3d),
287  isVerbose=0)
288  path.add_module('TRGCDCT3DDQM', T3DMOD=mod_t3d)
289  # CDCTriggerNeuro
290  if dqm_environment != "expressreco":
292  path.add_module('CDCTriggerNeuroDQMOnline', histogramDirectoryName="TRGCDCTNN2", useRecoTracks=False)
293  path.add_module('CDCTriggerNeuroDQM')
294 
295  # TRG for expressreco:
296  if dqm_environment == "expressreco" and (components is None or 'TRG' in components) and (dqm_mode in ["dont_care"]):
297  # TRGCDCTNN
299  path.add_module('CDCTriggerRecoMatcher', TrgTrackCollectionName=neurotrigger.hwneurotracks,
300  hitCollectionName=neurotrigger.hwneuroinputsegmenthits, axialOnly=True)
301  path.add_module('CDCTriggerRecoMatcher', TrgTrackCollectionName=neurotrigger.hwsimneurotracks,
302  hitCollectionName=neurotrigger.hwneuroinputsegmenthits, axialOnly=True)
303  path.add_module('CDCTriggerRecoMatcher', TrgTrackCollectionName=neurotrigger.hwneuroinput2dfindertracks,
304  hitCollectionName=neurotrigger.hwneuroinputsegmenthits, axialOnly=True)
305  path.add_module('CDCTriggerNeuroDQMOnline', histogramDirectoryName="TRGCDCTNN2", useRecoTracks=True)
306 
307  # TRG after skim
308  if (components is None or 'TRG' in components) and (dqm_mode in ["dont_care", "filtered"]):
309  # TRGGDL
310  trggdldqm_skim = b2.register_module('TRGGDLDQM')
311  trggdldqm_skim.param('skim', 1)
312  path.add_module(trggdldqm_skim)
313  # TRGTOP
314  trgtopdqm_skim = b2.register_module('TRGTOPDQM')
315  trgtopdqm_skim.param('skim', 1)
316  path.add_module(trgtopdqm_skim)
317 
318  # TrackDQM, needs at least one VXD components to be present or will crash otherwise
319  if (components is None or 'SVD' in components or 'PXD' in components) and (dqm_mode in ["dont_care", "filtered"]):
320  if (dqm_environment == "hlt"):
321  path.add_module('TrackingHLTDQM')
322  else:
323  path.add_module('ParallelTrackFilter', min_d0=-0.5, max_d0=0.5, min_z0=-1, max_z0=1,
324  inputArrayName="", outputINArrayName="TracksFromIP", outputOUTArrayName="TracksNotFromIP")
325  path.add_module('TrackingExpressRecoDQM', histogramDirectoryName="TrackingERDQM_FromIP",
326  tracksStoreArrayName="TracksFromIP", histogramTitleSuffix=" - Tracks from IP") \
327  .set_name("TrackingExpressRecoDQM_FromIP")
328  path.add_module('TrackingExpressRecoDQM', histogramDirectoryName="TrackingERDQM_NotFromIP",
329  tracksStoreArrayName="TracksNotFromIP", histogramTitleSuffix=" - Tracks not from IP") \
330  .set_name("TrackingExpressRecoDQM_NotFromIP")
331 
332  # ARICH
333  if (components is None or 'ARICH' in components) and (dqm_mode in ["dont_care", "filtered"]):
334  path.add_module('ARICHDQM')
335 
336  if dqm_mode in ["dont_care", "filtered"]:
337  # PhysicsObjectsDQM
338  add_analysis_dqm(path)
339  if dqm_environment == "expressreco" and (dqm_mode in ["dont_care"]):
340  add_mirabelle_dqm(path)
341 
342  # We want to see the datasize of all events after removing the raw data
343  if dqm_mode in ["dont_care", "all_events"]:
344  # DAQ Monitor
345  path.add_module('DAQMonitor')
def add_neurotrigger_hw(path, nntweightfile=None, debug_level=4, debugout=False, **kwargs)