Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
RawTowerDigitizer.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file RawTowerDigitizer.cc
1 #include "RawTowerDigitizer.h"
2 
3 #include <calobase/RawTower.h> // for RawTower
4 #include <calobase/RawTowerContainer.h>
5 #include <calobase/RawTowerDeadMap.h>
6 #include <calobase/RawTowerDefs.h> // for keytype
7 #include <calobase/RawTowerGeom.h>
8 #include <calobase/RawTowerGeomContainer.h>
9 #include <calobase/RawTowerv2.h>
10 
11 #include <calobase/TowerInfoContainer.h>
12 #include <calobase/TowerInfoContainerv1.h>
13 #include <calobase/TowerInfo.h>
14 #include <calobase/TowerInfov1.h>
15 
16 #include <phparameter/PHParameters.h>
17 
18 #include <cdbobjects/CDBTTree.h>
19 
21 
22 #include <fun4all/Fun4AllBase.h> // for Fun4AllBase::VERBOSITY_MORE
24 #include <fun4all/SubsysReco.h> // for SubsysReco
25 
26 
27 #include <phool/PHCompositeNode.h>
28 #include <phool/PHIODataNode.h>
29 #include <phool/PHNode.h> // for PHNode
30 #include <phool/PHNodeIterator.h>
31 #include <phool/PHObject.h> // for PHObject
32 #include <phool/PHRandomSeed.h>
33 #include <phool/getClass.h>
34 #include <phool/phool.h> // for PHWHERE
35 
36 #include <TSystem.h>
37 
38 #include <gsl/gsl_cdf.h>
39 #include <gsl/gsl_randist.h>
40 #include <gsl/gsl_rng.h>
41 
42 #include <cmath>
43 #include <cstdlib> // for exit
44 #include <exception> // for exception
45 #include <iostream>
46 #include <map>
47 #include <stdexcept>
48 #include <string>
49 #include <utility> // for pair
50 
52  : SubsysReco(name)
53  , _tower_params(name)
54 {
55  m_RandomGenerator = gsl_rng_alloc(gsl_rng_mt19937);
56  m_Seed = PHRandomSeed(); // fixed seed handled in PHRandomSeed()
57  // std::cout << Name() << " Random Seed: " << m_Seed << std::endl;
59 }
60 
62 {
63  gsl_rng_free(m_RandomGenerator);
64  delete m_CDBTTree;
65 }
66 
67 void RawTowerDigitizer::set_seed(const unsigned int iseed)
68 {
69  m_Seed = iseed;
71 }
72 
74 {
75  PHNodeIterator iter(topNode);
76 
77  // Looking for the DST node
78  PHCompositeNode *dstNode;
79  dstNode = dynamic_cast<PHCompositeNode *>(iter.findFirst("PHCompositeNode", "DST"));
80  if (!dstNode)
81  {
82  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
83  << "DST Node missing, doing nothing." << std::endl;
84  exit(1);
85  }
86 
87  try
88  {
89  CreateNodes(topNode);
90  }
91  catch (std::exception &e)
92  {
93  std::cout << e.what() << std::endl;
95  }
96 
97  if (m_DoDecal)
98  {
99  if (m_Detector.c_str()[0] == 'H')
100  {
101  std::string url = CDBInterface::instance()->getUrl("HCALGAINSCORR");
102  if (url.empty())
103  {
104  std::cout << PHWHERE << " Could not get Hcal Calibration for domain HCALGAINSCORR" << std::endl;
105  gSystem->Exit(1);
106  exit(1);
107  }
108 
109  m_CDBTTree = new CDBTTree(url);
110  }
111  else if (m_Detector.c_str()[0] == 'C')
112  {
113  std::string url = CDBInterface::instance()->getUrl("CEMCGAINSCORR");
114  if (url.empty())
115  {
116  std::cout << PHWHERE << " Could not get Cemc Calibration for domain CEMCGAINSCORR" << std::endl;
117  gSystem->Exit(1);
118  exit(1);
119  }
120 
121  m_CDBTTree = new CDBTTree(url);
122  }
123  else
124  {
125  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
126  << "Calo Decal requested but Detector Name not HCALOUT/IN or CEMC"
127  << std::endl;
128  gSystem->Exit(1);
129  }
130  //warnings for bad file names handled inside Open
131  }
132 
134 }
135 
137 {
138  if (Verbosity())
139  {
140  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
141  << "Process event entered. "
142  << "Digitalization method: ";
143 
145  {
146  std::cout << "directly pass the energy of sim tower to digitalized tower";
147  }
149  {
150  std::cout << "simple digitization with photon statistics, ADC conversion and pedstal";
151  }
152  std::cout << std::endl;
153  }
154  // loop over all possible towers, even empty ones. The digitization can add towers containing
155  // pedestals
157 
158  double deadChanEnergy = 0;
159 
160  for (RawTowerGeomContainer::ConstIterator it = all_towers.first;
161  it != all_towers.second; ++it)
162  {
163  const RawTowerDefs::keytype key = it->second->get_id();
165  const int eta = it->second->get_bineta();
166  const int phi = it->second->get_binphi();
167 
168  if (caloid == RawTowerDefs::LFHCAL)
169  {
170  const int l = it->second->get_binl();
171  if (m_ZeroSuppressionFile == true)
172  {
173  const std::string zsName = "ZS_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi) + "_l" + std::to_string(l);
176  }
177 
178  if (m_pedestalFile == true)
179  {
180  const std::string pedCentralName = "PedCentral_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi) + "_l" + std::to_string(l);
182  _tower_params.get_double_param(pedCentralName);
183  const std::string pedWidthName = "PedWidth_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi) + "_l" + std::to_string(l);
185  _tower_params.get_double_param(pedWidthName);
186  }
187  }
188  else
189  {
190  if (m_ZeroSuppressionFile == true)
191  {
192  const std::string zsName = "ZS_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi);
194  }
195 
196  if (m_pedestalFile == true)
197  {
198  const std::string pedCentralName = "PedCentral_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi);
200  const std::string pedWidthName = "PedWidth_ADC_eta" + std::to_string(eta) + "_phi" + std::to_string(phi);
202  }
203  }
204 
205  if (m_TowerType >= 0)
206  {
207  // Skip towers that don't match the type we are supposed to digitize
208  if (m_TowerType != it->second->get_tower_type())
209  {
210  continue;
211  }
212  }
213 
214  RawTower *digi_tower = nullptr;
215  TowerInfo *digi_towerinfo = nullptr;
216 
217  if(m_UseTowerInfo != 1)
218  {
219 
220  RawTower *sim_tower = m_SimTowers->getTower(key);
221  if (m_DeadMap)
222  {
223  if (m_DeadMap->isDeadTower(key))
224  {
225  if (sim_tower) deadChanEnergy += sim_tower->get_energy();
226 
227  sim_tower = nullptr;
228 
229  if (Verbosity() >= VERBOSITY_MORE)
230  {
231  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
232  << " apply dead tower " << key << std::endl;
233  }
234  }
235  }
237  {
238  // for no digitization just copy existing towers
239  if (sim_tower)
240  {
241  digi_tower = new RawTowerv2(*sim_tower);
242  }
243  }
245  {
246  // for photon digitization towers can be created if sim_tower is null pointer
247  digi_tower = simple_photon_digitization(sim_tower);
248  }
250  {
251  // for photon digitization towers can be created if sim_tower is null pointer
252  digi_tower = sipm_photon_digitization(sim_tower);
253  }
254  else
255  {
256  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
257  << " invalid digitization algorithm #" << m_DigiAlgorithm
258  << std::endl;
259 
261  }
262 
263  if (digi_tower)
264  {
265  if (m_DoDecal && m_Decal)
266  {
267  unsigned int etaphikey = phi;
268  etaphikey = (etaphikey << 16U) + eta;
269  float decal_fctr = m_CDBTTree->GetFloatValue(etaphikey,"etaphi");
270 
271  if (m_DecalInverse)
272  {
273  decal_fctr = 1.0 / decal_fctr;
274  }
275  float e_dec = digi_tower->get_energy();
276  digi_tower->set_energy(e_dec * decal_fctr);
277  }
278  m_RawTowers->AddTower(key, digi_tower);
279  if (Verbosity() >= VERBOSITY_MORE)
280  {
281  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
282  << " output tower:"
283  << std::endl;
284  digi_tower->identify();
285  }
286  }
287  }
288 
289 
290  if (m_UseTowerInfo > 0)
291  {
292  unsigned int towerkey = (eta << 16U) + phi;
293  // unsigned int towerindex = m_SimTowerInfos->decode_key(towerkey);
294  TowerInfo *sim_tower = m_SimTowerInfos->get_tower_at_key(towerkey);
295  if (m_DeadMap)
296  {
297  if (m_DeadMap->isDeadTower(key))
298  {
299  if (sim_tower) deadChanEnergy += sim_tower->get_energy();
300  sim_tower = nullptr;
301  if (Verbosity() >= VERBOSITY_MORE)
302  {
303  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
304  << " apply dead tower " << key << std::endl;
305  }
306  }
307  }
309  {
310  // for no digitization just copy existing towers
311  if (sim_tower)
312  {
313  digi_towerinfo = new TowerInfov1(*sim_tower);
314  }
315  }
317  {
318  // for photon digitization towers can be created if sim_tower is null pointer
319  digi_towerinfo = simple_photon_digitization(sim_tower);
320  }
322  {
323  // for photon digitization towers can be created if sim_tower is null pointer
324  digi_towerinfo = sipm_photon_digitization(sim_tower);
325  }
326  else
327  {
328  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
329  << " invalid digitization algorithm #" << m_DigiAlgorithm
330  << std::endl;
331 
333  }
334 
335  if (digi_towerinfo)
336  {
337  if (m_DoDecal && m_Decal)
338  {
339  unsigned int etaphikey = phi;
340  etaphikey = (etaphikey << 16U) + eta;
341  float decal_fctr = m_CDBTTree->GetFloatValue(etaphikey,"etaphi");
342  if (m_DecalInverse)
343  {
344  decal_fctr = 1.0 / decal_fctr;
345  }
346  float e_dec = digi_towerinfo->get_energy();
347  digi_towerinfo->set_energy(e_dec * decal_fctr);
348  }
349  TowerInfo *digitized_towerinfo = m_RawTowerInfos->get_tower_at_key(towerkey);
350  if (m_UseTowerInfo == 2 ) //if reconstructing both RawTowers and towerinfo objects force them to be the same
351  {
352  if (digi_tower)
353  {
354  digitized_towerinfo->set_energy(digi_tower->get_energy());
355  }
356  else
357  {
358  digitized_towerinfo->set_energy(0);
359  }
360  }
361  else
362  {
363  digitized_towerinfo->set_energy(digi_towerinfo->get_energy());
364  }
365  }
366  delete digi_towerinfo;
367  }
368  }
369 
370  if (Verbosity())
371  {
372  if (m_UseTowerInfo !=1)
373  {
374  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
375  << "input sum energy = " << m_SimTowers->getTotalEdep() << " GeV"
376  << ", dead channel masked energy = " << deadChanEnergy << " GeV"
377  << ", output sum digitalized value = " << m_RawTowers->getTotalEdep() << " ADC"
378  << std::endl;
379  }
380  }
382 }
383 
384 RawTower *
386 {
387  RawTower *digi_tower = nullptr;
388 
389  double energy = 0.;
390  if (sim_tower)
391  {
392  energy = sim_tower->get_energy();
393  }
394  const double photon_count_mean = energy * m_PhotonElecYieldVisibleGeV;
395  const int photon_count = gsl_ran_poisson(m_RandomGenerator, photon_count_mean);
396 
397  const int signal_ADC = floor(photon_count / m_PhotonElecADC);
398  const double pedestal = m_PedstalCentralADC + ((m_PedstalWidthADC > 0) ? gsl_ran_gaussian(m_RandomGenerator, m_PedstalWidthADC) : 0);
399 
400  const int sum_ADC = signal_ADC + (int) pedestal;
401 
402  double sum_ADC_d = (double) sum_ADC;
403 
404  // temporary fix to remove digitization
405  // for decalibration tests
406  // to be replaced permanently for all cases
407  // with sim of pulse extraction/fitting
408  if (m_DoDecal)
409  {
410  double signal_ADC_d = 1. * photon_count;
411  signal_ADC_d /= m_PhotonElecADC;
412 
413  sum_ADC_d = signal_ADC_d + pedestal;
414  }
415 
416  if (sum_ADC > m_ZeroSuppressionADC)
417  {
418  // create new digitalizaed tower
419  if (sim_tower)
420  {
421  digi_tower = new RawTowerv2(*sim_tower);
422  }
423  else
424  {
425  digi_tower = new RawTowerv2();
426  }
427  digi_tower->set_energy(sum_ADC_d);
428  }
429 
430  if (Verbosity() >= 2)
431  {
432  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
433  << std::endl;
434 
435  std::cout << "input: ";
436  if (sim_tower)
437  {
438  sim_tower->identify();
439  }
440  else
441  {
442  std::cout << "None" << std::endl;
443  }
444  std::cout << "output based on "
445  << "sum_ADC = " << sum_ADC << ", zero_sup = "
446  << m_ZeroSuppressionADC << " : ";
447  if (digi_tower)
448  {
449  digi_tower->identify();
450  }
451  else
452  {
453  std::cout << "None" << std::endl;
454  }
455  }
456  return digi_tower;
457 }
458 
459 
460 
461 TowerInfo *
463 {
464  TowerInfo* digi_tower = nullptr;
465  if (sim_tower)
466  {
467  digi_tower = new TowerInfov1(*sim_tower);
468  }
469  else
470  {
471  digi_tower = new TowerInfov1();
472  }
473  double energy = 0.;
474  if (sim_tower)
475  {
476  energy = sim_tower->get_energy();
477  }
478  const double photon_count_mean = energy * m_PhotonElecYieldVisibleGeV;
479  const int photon_count = gsl_ran_poisson(m_RandomGenerator, photon_count_mean);
480 
481  const int signal_ADC = floor(photon_count / m_PhotonElecADC);
482  const double pedestal = m_PedstalCentralADC + ((m_PedstalWidthADC > 0) ? gsl_ran_gaussian(m_RandomGenerator, m_PedstalWidthADC) : 0);
483 
484  const int sum_ADC = signal_ADC + (int) pedestal;
485 
486  double sum_ADC_d = (double) sum_ADC;
487 
488  // temporary fix to remove digitization
489  // for decalibration tests
490  // to be replaced permanently for all cases
491  // with sim of pulse extraction/fitting
492  if (m_DoDecal)
493  {
494  double signal_ADC_d = 1. * photon_count;
495  signal_ADC_d /= m_PhotonElecADC;
496 
497  sum_ADC_d = signal_ADC_d + pedestal;
498  }
499 
500  if (sum_ADC > m_ZeroSuppressionADC)
501  {
502  digi_tower->set_energy(sum_ADC_d);
503  }
504 
505  if (Verbosity() >= 2)
506  {
507  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
508  << std::endl;
509 
510  std::cout << "input: ";
511  if (sim_tower)
512  {
513  sim_tower->identify();
514  }
515  else
516  {
517  std::cout << "None" << std::endl;
518  }
519  std::cout << "output based on "
520  << "sum_ADC = " << sum_ADC << ", zero_sup = "
521  << m_ZeroSuppressionADC << " : ";
522  if (digi_tower)
523  {
524  digi_tower->identify();
525  }
526  else
527  {
528  std::cout << "None" << std::endl;
529  }
530  }
531  return digi_tower;
532 }
533 
534 
535 
536 RawTower *
538 {
539  RawTower *digi_tower = nullptr;
540 
541  double energy = 0;
542  if (sim_tower)
543  {
544  energy = sim_tower->get_energy();
545  }
546 
547  int signal_ADC = 0;
548 
549  if (energy > 0)
550  {
551  const double photon_count_mean = energy * m_PhotonElecYieldVisibleGeV;
552  const double poission_param_per_pixel = photon_count_mean / m_SiPMEffectivePixel;
553  const double prob_activated_per_pixel = gsl_cdf_poisson_Q(0, poission_param_per_pixel);
554  const double active_pixel = gsl_ran_binomial(m_RandomGenerator, prob_activated_per_pixel, m_SiPMEffectivePixel);
555  signal_ADC = floor(active_pixel / m_PhotonElecADC);
556  }
557 
558  const double pedstal = m_PedstalCentralADC + ((m_PedstalWidthADC > 0) ? gsl_ran_gaussian(m_RandomGenerator, m_PedstalWidthADC) : 0);
559  const int sum_ADC = signal_ADC + (int) pedstal;
560 
561  if (sum_ADC > m_ZeroSuppressionADC)
562  {
563  // create new digitalizaed tower
564  if (sim_tower)
565  {
566  digi_tower = new RawTowerv2(*sim_tower);
567  }
568  else
569  {
570  digi_tower = new RawTowerv2();
571  }
572  digi_tower->set_energy((double) sum_ADC);
573  }
574 
575  if (Verbosity() >= 2)
576  {
577  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
578  << std::endl;
579 
580  std::cout << "input: ";
581  if (sim_tower)
582  {
583  sim_tower->identify();
584  }
585  else
586  {
587  std::cout << "None" << std::endl;
588  }
589  std::cout << "output based on "
590  << "sum_ADC = " << sum_ADC << ", zero_sup = "
591  << m_ZeroSuppressionADC << " : ";
592  if (digi_tower)
593  {
594  digi_tower->identify();
595  }
596  else
597  {
598  std::cout << "None" << std::endl;
599  }
600  }
601 
602  return digi_tower;
603 }
604 
605 
606 
607 
608 
609 TowerInfo *
611 {
612  TowerInfo *digi_tower = nullptr;
613 
614  double energy = 0;
615  if (sim_tower)
616  {
617  energy = sim_tower->get_energy();
618  }
619 
620  int signal_ADC = 0;
621 
622  if (energy > 0)
623  {
624  const double photon_count_mean = energy * m_PhotonElecYieldVisibleGeV;
625  const double poission_param_per_pixel = photon_count_mean / m_SiPMEffectivePixel;
626  const double prob_activated_per_pixel = gsl_cdf_poisson_Q(0, poission_param_per_pixel);
627  const double active_pixel = gsl_ran_binomial(m_RandomGenerator, prob_activated_per_pixel, m_SiPMEffectivePixel);
628  signal_ADC = floor(active_pixel / m_PhotonElecADC);
629  }
630 
631  const double pedstal = m_PedstalCentralADC + ((m_PedstalWidthADC > 0) ? gsl_ran_gaussian(m_RandomGenerator, m_PedstalWidthADC) : 0);
632  const int sum_ADC = signal_ADC + (int) pedstal;
633 
634  if (sum_ADC > m_ZeroSuppressionADC)
635  {
636  // create new digitalizaed tower
637  if (sim_tower)
638  {
639  digi_tower = new TowerInfov1(*sim_tower);
640  }
641  else
642  {
643  digi_tower = new TowerInfov1();
644  }
645  digi_tower->set_energy((double) sum_ADC);
646  }
647 
648  if (Verbosity() >= 2)
649  {
650  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
651  << std::endl;
652 
653  std::cout << "input: ";
654  if (sim_tower)
655  {
656  sim_tower->identify();
657  }
658  else
659  {
660  std::cout << "None" << std::endl;
661  }
662  std::cout << "output based on "
663  << "sum_ADC = " << sum_ADC << ", zero_sup = "
664  << m_ZeroSuppressionADC << " : ";
665  if (digi_tower)
666  {
667  digi_tower->identify();
668  }
669  else
670  {
671  std::cout << "None" << std::endl;
672  }
673  }
674  return digi_tower;
675 }
676 
677 
678 
679 
680 
681 
682 
683 
684 
685 
686 
687 
689 {
690  PHNodeIterator iter(topNode);
691  PHCompositeNode *runNode = static_cast<PHCompositeNode *>(iter.findFirst("PHCompositeNode", "RUN"));
692  if (!runNode)
693  {
694  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
695  << "Run Node missing, doing nothing." << std::endl;
696  throw std::runtime_error("Failed to find Run node in RawTowerDigitizer::CreateNodes");
697  }
698 
699  std::string TowerGeomNodeName = "TOWERGEOM_" + m_Detector;
700  m_RawTowerGeom = findNode::getClass<RawTowerGeomContainer>(topNode, TowerGeomNodeName);
701  if (!m_RawTowerGeom)
702  {
703  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
704  << " " << TowerGeomNodeName << " Node missing, doing bail out!"
705  << std::endl;
706  throw std::runtime_error("Failed to find " + TowerGeomNodeName + " node in RawTowerDigitizer::CreateNodes");
707  }
708 
709  if (Verbosity() >= 1)
710  {
712  }
713 
714  const std::string deadMapName = "DEADMAP_" + m_Detector;
715  m_DeadMap = findNode::getClass<RawTowerDeadMap>(topNode, deadMapName);
716  if (m_DeadMap)
717  {
718  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
719  << " use dead map: ";
720  m_DeadMap->identify();
721  }
722 
723  PHCompositeNode *dstNode = dynamic_cast<PHCompositeNode *>(iter.findFirst("PHCompositeNode", "DST"));
724  if (!dstNode)
725  {
726  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
727  << "DST Node missing, doing nothing." << std::endl;
728  throw std::runtime_error("Failed to find DST node in RawTowerDigitizer::CreateNodes");
729  }
730 
731 
732  if (m_UseTowerInfo != 1)
733  {
734  std::string SimTowerNodeName = "TOWER_" + m_SimTowerNodePrefix + "_" + m_Detector;
735  m_SimTowers = findNode::getClass<RawTowerContainer>(dstNode, SimTowerNodeName);
736  if (!m_SimTowers)
737  {
738  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
739  << " " << SimTowerNodeName << " Node missing, doing bail out!"
740  << std::endl;
741  throw std::runtime_error("Failed to find " + SimTowerNodeName + " node in RawTowerDigitizer::CreateNodes");
742  }
743  }
744  if (m_UseTowerInfo > 0 )
745  {
746  std::string SimTowerInfoNodeName = "TOWERINFO_" + m_SimTowerNodePrefix + "_" + m_Detector;
747  m_SimTowerInfos = findNode::getClass<TowerInfoContainer>(dstNode, SimTowerInfoNodeName);
748  if (!m_SimTowerInfos)
749  {
750  std::cout << Name() << "::" << m_Detector << "::" << __PRETTY_FUNCTION__
751  << " " << SimTowerInfoNodeName << " Node missing, doing bail out!"
752  << std::endl;
753  throw std::runtime_error("Failed to find " + SimTowerInfoNodeName + " node in RawTowerDigitizer::CreateNodes");
754  }
755  }
756 
757 
758 
759 
760 
761 
762 
763 
764  // Create the tower nodes on the tree
765  PHNodeIterator dstiter(dstNode);
766  PHCompositeNode *DetNode = dynamic_cast<PHCompositeNode *>(dstiter.findFirst("PHCompositeNode", m_Detector));
767  if (!DetNode)
768  {
769  DetNode = new PHCompositeNode(m_Detector);
770  dstNode->addNode(DetNode);
771  }
772 
773  // Be careful as a previous digitizer may have been registered for this detector
774 
775  if (m_UseTowerInfo != 1)
776  {
777  std::string RawTowerNodeName = "TOWER_" + m_RawTowerNodePrefix + "_" + m_Detector;
778  m_RawTowers = findNode::getClass<RawTowerContainer>(DetNode, RawTowerNodeName);
779  if (!m_RawTowers)
780  {
783  RawTowerNodeName, "PHObject");
784  DetNode->addNode(towerNode);
785  }
786  }
787  if (m_UseTowerInfo > 0 )
788  {
789  std::string TowerInfoNodeName = "TOWERINFO_" + m_RawTowerNodePrefix + "_" + m_Detector;
790  m_RawTowerInfos = findNode::getClass<TowerInfoContainer>(DetNode,TowerInfoNodeName);
791  if (m_RawTowerInfos == nullptr)
792  {
794  if (m_Detector == "CEMC")
795  {
796  detec = TowerInfoContainer::DETECTOR::EMCAL;
797  }
798  else if (m_Detector == "HCALIN" || m_Detector == "HCALOUT")
799  {
800  detec = TowerInfoContainer::DETECTOR::HCAL;
801  }
802  else
803  {
804  std::cout << PHWHERE << "Detector not implemented into the TowerInfoContainer object, defaulting to HCal implementation." << std::endl;
805  detec = TowerInfoContainer::DETECTOR::HCAL;
806  }
808  PHIODataNode<PHObject> *towerinfoNode = new PHIODataNode<PHObject>(m_RawTowerInfos, TowerInfoNodeName, "PHObject");
809  DetNode->addNode(towerinfoNode);
810  }
811  }
812 
813 
814  return;
815 }