ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
FatrasAlgorithm.hpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file FatrasAlgorithm.hpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2017 CERN for the benefit of the Acts project
4 //
5 // This Source Code Form is subject to the terms of the Mozilla Public
6 // License, v. 2.0. If a copy of the MPL was not distributed with this
7 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 
9 #pragma once
10 
11 #include <memory>
12 #include <string>
13 
19 
20 namespace FW {
21 
25 template <typename simulator_t>
26 class FatrasAlgorithm final : public BareAlgorithm {
27  public:
28  struct Config {
30  std::string inputParticles;
34  std::string outputParticlesFinal;
36  std::string outputHits;
38  simulator_t simulator;
40  std::shared_ptr<const RandomNumbers> randomNumbers;
41 
43  Config(simulator_t&& simulator_) : simulator(std::move(simulator_)) {}
44  };
45 
51  : FW::BareAlgorithm("FatrasAlgorithm", lvl), m_cfg(std::move(cfg)) {
52  ACTS_DEBUG("hits on sensitive surfaces: "
53  << m_cfg.simulator.charged.selectHitSurface.sensitive);
54  ACTS_DEBUG("hits on material surfaces: "
55  << m_cfg.simulator.charged.selectHitSurface.material);
56  ACTS_DEBUG("hits on passive surfaces: "
57  << m_cfg.simulator.charged.selectHitSurface.passive);
58  }
59 
63  FW::ProcessCode execute(const AlgorithmContext& ctx) const final override {
64  // read input containers
65  const auto& inputParticles =
66  ctx.eventStore.get<SimParticleContainer>(m_cfg.inputParticles);
67  // prepare output containers
68  SimParticleContainer::sequence_type particlesInitialUnordered;
69  SimParticleContainer::sequence_type particlesFinalUnordered;
70  SimHitContainer::sequence_type hitsUnordered;
71  // reserve appropriate resources
72  constexpr auto meanHitsPerParticle = 16u;
73  particlesInitialUnordered.reserve(inputParticles.size());
74  particlesFinalUnordered.reserve(inputParticles.size());
75  hitsUnordered.reserve(meanHitsPerParticle * inputParticles.size());
76 
77  // run the simulation w/ a local random generator
78  auto rng = m_cfg.randomNumbers->spawnGenerator(ctx);
79  auto ret = m_cfg.simulator.simulate(
80  ctx.geoContext, ctx.magFieldContext, rng, inputParticles,
81  particlesInitialUnordered, particlesFinalUnordered, hitsUnordered);
82  // fatal error leads to panic
83  if (not ret.ok()) {
84  ACTS_FATAL("event " << ctx.eventNumber << " simulation failed with error "
85  << ret.error());
86  return ProcessCode::ABORT;
87  }
88  // failed particles are just logged. assumes that failed particles are due
89  // to edge-cases representing a tiny fraction of the event; not due to a
90  // fundamental issue.
91  for (const auto& failed : ret.value()) {
92  ACTS_ERROR("event " << ctx.eventNumber << " particle " << failed.particle
93  << " failed to simulate with error " << failed.error
94  << ": " << failed.error.message());
95  }
96  // TODO is there a point where too many failed particles or failed particles
97  // of a particular type (e.g. from hard interaction or any primary
98  // particle) should also lead to a panic?
99 
100  ACTS_DEBUG(inputParticles.size() << " input particles");
101  ACTS_DEBUG(particlesInitialUnordered.size()
102  << " simulated particles (initial state)");
103  ACTS_DEBUG(particlesFinalUnordered.size()
104  << " simulated particles (final state)");
105  ACTS_DEBUG(hitsUnordered.size() << " hits");
106 
107  // restore ordering for output containers
108  SimParticleContainer particlesInitial;
109  SimParticleContainer particlesFinal;
111  particlesInitial.adopt_sequence(std::move(particlesInitialUnordered));
112  particlesFinal.adopt_sequence(std::move(particlesFinalUnordered));
113  hits.adopt_sequence(std::move(hitsUnordered));
114 
115  // store ordered output containers
116  ctx.eventStore.add(m_cfg.outputParticlesInitial,
117  std::move(particlesInitial));
118  ctx.eventStore.add(m_cfg.outputParticlesFinal, std::move(particlesFinal));
119  ctx.eventStore.add(m_cfg.outputHits, std::move(hits));
120 
122  }
123 
124  private:
126 };
127 
128 } // namespace FW