The Gaudi Framework  v36r1 (3e2fb5a8)
GaudiHive.precedence.CruncherSequence Class Reference
Inheritance diagram for GaudiHive.precedence.CruncherSequence:
Collaboration diagram for GaudiHive.precedence.CruncherSequence:

Public Member Functions

def __init__ (self, timeValue, BlockingBoolValue, sleepFraction, cfgPath, dfgPath, topSequencer, showStat=False, timeline=False, outputLevel=INFO, cardinality=1)
 
def get (self)
 

Public Attributes

 cardinality
 
 timeValue
 
 BlockingBoolValue
 
 sleepFraction
 
 cfg
 
 dfg
 
 enableTimeline
 
 outputLevel
 
 sequencer
 

Static Public Attributes

list unique_sequencers = []
 
dictionary dupl_seqs = {}
 
list OR_sequencers = []
 
list unique_algos = []
 
dictionary dupl_algos = {}
 
list unique_data_objects = []
 

Private Member Functions

def _declare_data_deps (self, algo_name, algo)
 
def _generate_sequence (self, name, seq=None)
 

Detailed Description

Constructs the sequence tree of CPUCrunchers with provided control flow and data flow precedence rules.

Definition at line 163 of file precedence.py.

Constructor & Destructor Documentation

◆ __init__()

def GaudiHive.precedence.CruncherSequence.__init__ (   self,
  timeValue,
  BlockingBoolValue,
  sleepFraction,
  cfgPath,
  dfgPath,
  topSequencer,
  showStat = False,
  timeline = False,
  outputLevel = INFO,
  cardinality = 1 
)
Keyword arguments:
timeValue -- timeValue object to set algorithm execution time
BlockingBoolValue -- *BooleanValue object to set whether an algorithm has to experience CPU-blocking execution
cfgPath -- relative to $ENV_CMAKE_SOURCE_DIR/GaudiHive/data path to GRAPHML file with control flow dependencies
dfgPath -- relative to $ENV_CMAKE_SOURCE_DIR/GaudiHive/data path to GRAPHML file with data flow dependencies
showStat -- print out statistics on precedence graph

Definition at line 174 of file precedence.py.

174  def __init__(self,
175  timeValue,
176  BlockingBoolValue,
177  sleepFraction,
178  cfgPath,
179  dfgPath,
180  topSequencer,
181  showStat=False,
182  timeline=False,
183  outputLevel=INFO,
184  cardinality=1):
185  """
186  Keyword arguments:
187  timeValue -- timeValue object to set algorithm execution time
188  BlockingBoolValue -- *BooleanValue object to set whether an algorithm has to experience CPU-blocking execution
189  cfgPath -- relative to $ENV_CMAKE_SOURCE_DIR/GaudiHive/data path to GRAPHML file with control flow dependencies
190  dfgPath -- relative to $ENV_CMAKE_SOURCE_DIR/GaudiHive/data path to GRAPHML file with data flow dependencies
191  showStat -- print out statistics on precedence graph
192  """
193 
194  self.cardinality = cardinality
195  self.timeValue = timeValue
196  self.BlockingBoolValue = BlockingBoolValue
197  self.sleepFraction = sleepFraction
198 
199  self.cfg = nx.read_graphml(_buildFilePath(cfgPath))
200  self.dfg = nx.read_graphml(_buildFilePath(dfgPath))
201 
202  self.enableTimeline = timeline
203 
204  self.outputLevel = outputLevel
205 
206  # Generate control flow part
207  self.sequencer = self._generate_sequence(topSequencer)
208 
209  if showStat:
210  import pprint
211 
212  print("\n===== Statistics on Algorithms =====")
213  print(
214  "Total number of algorithm nodes: ",
215  len(self.unique_algos) + sum(
216  [self.dupl_algos[i] - 1 for i in self.dupl_algos]))
217  print("Number of unique algorithms: ", len(self.unique_algos))
218  print(" -->", len(self.dupl_algos),
219  "of them being re-used with the following distribution: ",
220  [self.dupl_algos[i] for i in self.dupl_algos])
221  # pprint.pprint(dupl_algos)
222 
223  print("\n===== Statistics on Sequencers =====")
224  print(
225  "Total number of sequencers: ",
226  len(self.unique_sequencers) + sum(
227  [self.dupl_seqs[i] - 1 for i in self.dupl_seqs]))
228  print("Number of unique sequencers: ", len(self.unique_sequencers))
229  print(" -->", len(self.dupl_seqs),
230  "of them being re-used with the following distribution: ",
231  [self.dupl_seqs[i] for i in self.dupl_seqs])
232  # pprint.pprint(dupl_seqs)
233  print("Number of OR-sequencers: ", len(self.OR_sequencers))
234 
235  print("\n===== Statistics on DataObjects =====")
236  print("Number of unique DataObjects: ",
237  len(self.unique_data_objects))
238  # pprint.pprint(self.unique_data_objects)
239  print()
240 

Member Function Documentation

◆ _declare_data_deps()

def GaudiHive.precedence.CruncherSequence._declare_data_deps (   self,
  algo_name,
  algo 
)
private
Declare data inputs and outputs for a given algorithm. 

Definition at line 245 of file precedence.py.

245  def _declare_data_deps(self, algo_name, algo):
246  """ Declare data inputs and outputs for a given algorithm. """
247 
248  # Declare data inputs
249  for inNode, outNode in self.dfg.in_edges(algo_name):
250  dataName = inNode
251  if dataName not in self.unique_data_objects:
252  self.unique_data_objects.append(dataName)
253 
254  if dataName not in algo.inpKeys:
255  algo.inpKeys.append(dataName)
256 
257  # Declare data outputs
258  for inNode, outNode in self.dfg.out_edges(algo_name):
259  dataName = outNode
260  if dataName not in self.unique_data_objects:
261  self.unique_data_objects.append(dataName)
262 
263  if dataName not in algo.outKeys:
264  algo.outKeys.append(dataName)
265 

◆ _generate_sequence()

def GaudiHive.precedence.CruncherSequence._generate_sequence (   self,
  name,
  seq = None 
)
private
Assemble the tree of sequencers. 

Definition at line 266 of file precedence.py.

266  def _generate_sequence(self, name, seq=None):
267  """ Assemble the tree of sequencers. """
268 
269  if not seq:
270  seq = GaudiSequencer(name, ShortCircuit=False)
271 
272  for n in self.cfg[name]:
273  # extract entity name and type
274  algo_name = n.split('/')[1] if '/' in n else n
275 
276  if 'type' in self.cfg.node[n]:
277  # first rely on explicit type, if given
278  algo_type = self.cfg.node[n].get('type')
279  else:
280  # if the type is not given explicitly, try to extract it from entity name,
281  # and, if unsuccessful, assume it is an algorithm
282  algo_type = n.split('/')[0] if '/' in n else 'Algorithm'
283 
284  if algo_type in ['GaudiSequencer', 'AthSequencer', 'ProcessPhase']:
285  if algo_name in ['RecoITSeq', 'RecoOTSeq', 'RecoTTSeq']:
286  continue
287 
288  if n not in self.unique_sequencers:
289  self.unique_sequencers.append(n)
290  else:
291  if n not in self.dupl_seqs:
292  self.dupl_seqs[n] = 2
293  else:
294  self.dupl_seqs[n] += 1
295 
296  seq_daughter = GaudiSequencer(algo_name, OutputLevel=INFO)
297  if self.cfg.node[n].get('ModeOR') == 'True':
298  self.OR_sequencers.append(n)
299  seq_daughter.ModeOR = True
300  # if self.cfg.node[n].get('Lazy') == 'False':
301  # print "Non-Lazy - ", n
302  seq_daughter.ShortCircuit = False
303  if seq_daughter not in seq.Members:
304  seq.Members += [seq_daughter]
305  # iterate deeper
306  self._generate_sequence(n, seq_daughter)
307  else:
308  #rndname = ''.join(random.choice(string.lowercase) for i in range(5))
309  #if algo_name in unique_algos: algo_name = algo_name + "-" + rndname
310  if n not in self.unique_algos:
311  self.unique_algos.append(n)
312  else:
313  if n not in self.dupl_algos:
314  self.dupl_algos[n] = 2
315  else:
316  self.dupl_algos[n] += 1
317 
318  avgRuntime, varRuntime = self.timeValue.get(algo_name)
319 
320  algo_daughter = CPUCruncher(
321  algo_name,
322  Cardinality=self.cardinality,
323  OutputLevel=self.outputLevel,
324  varRuntime=varRuntime,
325  avgRuntime=avgRuntime,
326  SleepFraction=self.sleepFraction
327  if self.BlockingBoolValue.get() else 0.,
328  Timeline=self.enableTimeline)
329 
330  self._declare_data_deps(algo_name, algo_daughter)
331 
332  if algo_daughter not in seq.Members:
333  seq.Members += [algo_daughter]
334 
335  return seq

◆ get()

def GaudiHive.precedence.CruncherSequence.get (   self)

Definition at line 241 of file precedence.py.

241  def get(self):
242 
243  return self.sequencer
244 

Member Data Documentation

◆ BlockingBoolValue

GaudiHive.precedence.CruncherSequence.BlockingBoolValue

Definition at line 186 of file precedence.py.

◆ cardinality

GaudiHive.precedence.CruncherSequence.cardinality

Definition at line 184 of file precedence.py.

◆ cfg

GaudiHive.precedence.CruncherSequence.cfg

Definition at line 189 of file precedence.py.

◆ dfg

GaudiHive.precedence.CruncherSequence.dfg

Definition at line 190 of file precedence.py.

◆ dupl_algos

dictionary GaudiHive.precedence.CruncherSequence.dupl_algos = {}
static

Definition at line 170 of file precedence.py.

◆ dupl_seqs

dictionary GaudiHive.precedence.CruncherSequence.dupl_seqs = {}
static

Definition at line 167 of file precedence.py.

◆ enableTimeline

GaudiHive.precedence.CruncherSequence.enableTimeline

Definition at line 192 of file precedence.py.

◆ OR_sequencers

list GaudiHive.precedence.CruncherSequence.OR_sequencers = []
static

Definition at line 168 of file precedence.py.

◆ outputLevel

GaudiHive.precedence.CruncherSequence.outputLevel

Definition at line 194 of file precedence.py.

◆ sequencer

GaudiHive.precedence.CruncherSequence.sequencer

Definition at line 197 of file precedence.py.

◆ sleepFraction

GaudiHive.precedence.CruncherSequence.sleepFraction

Definition at line 187 of file precedence.py.

◆ timeValue

GaudiHive.precedence.CruncherSequence.timeValue

Definition at line 185 of file precedence.py.

◆ unique_algos

list GaudiHive.precedence.CruncherSequence.unique_algos = []
static

Definition at line 169 of file precedence.py.

◆ unique_data_objects

list GaudiHive.precedence.CruncherSequence.unique_data_objects = []
static

Definition at line 172 of file precedence.py.

◆ unique_sequencers

list GaudiHive.precedence.CruncherSequence.unique_sequencers = []
static

Definition at line 166 of file precedence.py.


The documentation for this class was generated from the following file:
GaudiHive.precedence._buildFilePath
def _buildFilePath(filePath)
Definition: precedence.py:29
CPUCruncher
Definition: CPUCruncher.h:29
Gaudi::Functional::details::get
auto get(const Handle &handle, const Algo &, const EventContext &) -> decltype(details::deref(handle.get()))
Definition: FunctionalDetails.h:391
GaudiSequencer
Definition: GaudiSequencer.h:38