Belle II Software  release-05-01-25
bklm-dst.py
1 #!/usr/bin/env python3
2 # -*- coding: utf-8 -*-
3 
4 # Purpose:
5 # Analyze a DST ROOT file or an SROOT file and write resulting histograms/scatterplots to
6 # ROOT and PDF files. This script cannot analyze MDST files because they don't contain RawKLMs.
7 #
8 # Prerequisite (on kekcc):
9 # Before running this script, type
10 # source /cvmfs/belle.cern.ch/tools/b2setup release-02-01-00 <or higher release>
11 # then verify that the corresponding proper global tag is used near the end of this script.
12 # (Global tags are tabulated at https://confluence.desy.de/display/BI/Global+Tag+%28GT%29+page)
13 # The external python script bklmDB.py must be in the same folder as this script.
14 #
15 # Usage:
16 # basf2 bklm-dst.py -- -e # -r # -i infilename -n # -d # -m # -t tagname
17 # You need the '--' before these options to tell basf2 that these are options to this script.
18 # Required arguments:
19 # either -i infilename or -e # -r # (can supply all three)
20 # -i infilename to specify the full pathname of the input ROOT DST file (no default)
21 # -e # to specify the experiment number (no default)
22 # -r # to specify the run number (no default)
23 # Optional arguments:
24 # -s # to select events with all (0) or exactly one (1) or two or more (2) entries/channel (default is 0)
25 # -n # to specify the maximum number of events to analyze (no default -> all events)
26 # --verbosity # to specify how many histograms to save in the PDF file (0=minimal, 1=all) [default is 0]
27 # -d # to specify the maximum number of event displays (default is 0)
28 # -m # to specify the minimum number of RPC BKLMHit2ds in any one sector (default is 4)
29 # -t tagName to specify the name of conditions-database global tag (no default)
30 # -l # to specify whether to use legacy time calculations (1) or not (0) (default is 0)
31 #
32 # Input:
33 # ROOT DST file written by basf2 (may include multiple folios for one expt/run). For example,
34 # /ghi/fs01/belle2/bdata/Data/Raw/e0003/r04794/sub00/physics.0003.r04794.HLT1.f*.root
35 # /ghi/fs01/belle2/bdata/Data/Raw/e0004/r06380/sub00/cosmic.0004.r06380.HLT1.f00000.root
36 # /ghi/fs01/belle2/bdata/Data/Raw/e0007/r01650/sub00/cosmic.0007.r01650.HLT1.f*.root
37 #
38 # Output:
39 # ROOT histogram file named bklmHists-e#r#.root, using the experiment number and run number
40 # PDF file named bklmHists-e#r#.pdf, using the experiment number and run number
41 #
42 
43 import basf2
44 from basf2 import *
45 import sys
46 import re
47 import EventInspector
48 from EventInspector import *
49 import simulation
50 import reconstruction
51 import rawdata
52 from optparse import Option, OptionValueError, OptionParser
53 import glob
54 
55 parser = OptionParser()
56 parser.add_option('-i', '--inputfile',
57  dest='infilename', default='',
58  help='Input [S]ROOT filename [no default]')
59 parser.add_option('-e', '--experiment',
60  dest='eNumber', default='',
61  help='Experiment number [no default]')
62 parser.add_option('-r', '--run',
63  dest='rNumber', default='',
64  help='Run number [no default]')
65 parser.add_option('-n', '--nEvents',
66  dest='nEvents', default='',
67  help='Max # of analyzed events [no default]')
68 parser.add_option('-s', '--singleEntry', type="int",
69  dest='singleEntry', default=0,
70  help='Select events with any (0) or exactly one (1) or more than one (2) entries/channel [0]')
71 parser.add_option('--verbosity', type="int",
72  dest='verbosity', default=0,
73  help='How many histograms to save (0=minimal, 1=all) [0]')
74 parser.add_option('-d', '--displays', type="int",
75  dest='displays', default=0,
76  help='Max # of displayed events [0]')
77 parser.add_option('-v', '--view', type="int",
78  dest='view', default=2,
79  help='View event displays using one-dimensional (1) or two-dimensional (2) hits [2]')
80 parser.add_option('-m', '--minRPCHits', type="int",
81  dest='minRPCHits', default=4,
82  help='Min # of RPC hits in any one sector to display the event [4]')
83 parser.add_option('-l', '--legacyTimes', type="int",
84  dest='legacyTimes', default=0,
85  help='Perform legacy time calculations (1) or not (0) for BKLMHit1ds,2ds [0]')
86 parser.add_option('-t', '--tagName',
87  dest='tagName', default='data_reprocessing_prompt',
88  help='Conditions-database global-tag name [data_reprocessing_prompt]')
89 (options, args) = parser.parse_args()
90 
91 singleEntry = options.singleEntry
92 if singleEntry < 0 or singleEntry > 2:
93  singleEntry = 0
94 
95 maxCount = -1
96 if options.nEvents != '':
97  maxCount = int(options.nEvents)
98  if maxCount <= 0:
99  print("Maximum number of events to analyze is", maxCount, " - nothing to do.")
100  sys.exit()
101 
102 verbosity = options.verbosity
103 
104 view = options.view
105 
106 maxDisplays = options.displays
107 
108 minRPCHits = options.minRPCHits
109 
110 legacyTimes = options.legacyTimes
111 
112 tagName = options.tagName
113 
114 inputName = ''
115 exp = ''
116 run = ''
117 if options.infilename != '':
118  inputName = re.sub("HLT.\.f0....", "HLT*.f*", options.infilename)
119  fileList = glob.glob(inputName)
120  if len(fileList) == 0:
121  print("No file(s) match {0}".format(inputName))
122  sys.exit()
123 if options.eNumber != '':
124  if not options.eNumber.isdecimal():
125  print("Experiment number ({0}) is not valid".format(options.eNumber))
126  sys.exit()
127  exp = '{0:04d}'.format(int(options.eNumber))
128 else:
129  eStart = inputName.find('/e') + 2
130  if eStart < 0:
131  print("Input filename does not contain the required experiment number")
132  sys.exit()
133  eEnd = inputName.find('/', eStart)
134  exp = inputName[eStart:eEnd]
135  if not exp.isdecimal():
136  print("Input filename's experiment number ({0}) is not valid".format(exp))
137  sys.exit()
138 if options.rNumber != '':
139  if not options.rNumber.isdecimal():
140  print("Run number ({0}) is not valid".format(options.rNumber))
141  sys.exit()
142  run = '{0:05d}'.format(int(options.rNumber))
143 else:
144  rStart = inputName.find('/r') + 2
145  if rStart < 0:
146  print("Input filename does not contain the required run number")
147  sys.exit()
148  rEnd = inputName.find('/', rStart)
149  run = inputName[rStart:rEnd]
150  if not run.isdecimal():
151  print("Input filename's run number ({0}) is not valid".format(run))
152  sys.exit()
153 if len(inputName) == 0:
154  inputName = '/ghi/fs01/belle2/bdata/Data/Raw/e{0}/r{1}/sub00/*.{0}.{1}.HLT*.f*.root'.format(exp, run)
155  fileList = glob.glob(inputName)
156  if len(fileList) == 0:
157  print("No file(s) found for experiment <{0}> run <{1}>".format(options.eNumber, options.rNumber))
158  sys.exit()
159 
160 suffix = '' if singleEntry == 0 else '-singleEntry' if singleEntry == 1 else '-multipleEntries'
161 histName = 'bklmHists-e{0}r{1}{2}.root'.format(exp, run, suffix)
162 pdfName = 'bklmPlots-e{0}r{1}{2}.pdf'.format(exp, run, suffix)
163 eventPdfName = 'bklmEvents{3}D-e{0}r{1}{2}.pdf'.format(exp, run, suffix, view)
164 
165 if maxCount >= 0:
166  print('bklm-dst: exp=' + exp + ' run=' + run + ' input=' + inputName + '. Analyze', maxCount, 'events using ' + tagName)
167 else:
168  print('bklm-dst: exp=' + exp + ' run=' + run + ' input=' + inputName + '. Analyze all events using ' + tagName)
169 
170 reset_database()
171 use_database_chain()
172 use_central_database(tagName)
173 
174 main = create_path()
175 if inputName.find(".sroot") >= 0:
176  main.add_module('SeqRootInput', inputFileNames=inputName)
177 else:
178  main.add_module('RootInput', inputFileName=inputName)
179 main.add_module('ProgressBar')
180 
181 eventInspector = EventInspector(exp, run, histName, pdfName, eventPdfName, verbosity,
182  maxDisplays, minRPCHits, legacyTimes, singleEntry, view)
183 rawdata.add_unpackers(main, components=['KLM'])
184 main.add_module('KLMReconstructor')
185 main.add_module(eventInspector)
186 
187 process(main, max_event=maxCount)
188 print(statistics)
EventInspector
Definition: EventInspector.py:1
rawdata.add_unpackers
def add_unpackers(path, components=None, writeKLMDigitRaws=False)
Definition: rawdata.py:62