ATLAS Offline Software
Loading...
Searching...
No Matches
MuonPhaseII/MuonDetDescr/MuonReadoutGeometryR4/src/MuonDetectorManager.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
5
13#include <limits>
14#include <cassert>
15
16#ifndef SIMULATIONBASE
17#include "Acts/Utilities/Helpers.hpp"
18#endif
19namespace {
21 template <class T>
25 template <class ReadOutEleStoreType,
26 class ReadoutEleReturnType>
27 void insert(const ElementStorage_t<ReadOutEleStoreType>& eleStore,
28 std::vector<ReadoutEleReturnType>& returnVec) {
29 returnVec.reserve(returnVec.capacity() + eleStore.size());
30 for (const auto& ele : eleStore) {
31 if (ele) returnVec.push_back(ele.get());
32 }
33 }
34 template <class ReadOutEleType,
35 class ReadOutEleReturnType>
36 void insert(std::vector<ReadOutEleType*>&& eleStore,
37 std::vector<ReadOutEleReturnType*>& returnVec) {
38 returnVec.insert(returnVec.end(),
39 std::make_move_iterator(eleStore.begin()),
40 std::make_move_iterator(eleStore.end()));
41 }
42#ifndef SIMULATIONBASE
43 inline unsigned msSectorIdHash(const ChIndex chIndex, const int sector, const int side) {
44 using namespace Muon::MuonStationIndex;
45 constexpr unsigned chIdxMax = Acts::toUnderlying(StIndex::StIndexMax);
46 constexpr unsigned secMax = Muon::MuonStationIndex::numberOfSectors();
47 return sector + secMax* Acts::toUnderlying(toStationIndex(chIndex))* secMax +
48 (Acts::copySign(1,side) == 1) * chIdxMax * secMax;
49 }
50#endif
51}
52
53#define WRITE_SETTER(ELE_TYPE, SETTER, STORAGE_VEC) \
54 StatusCode MuonDetectorManager::SETTER(ElementPtr_t<ELE_TYPE> element) { \
55 if (!element) { \
56 ATH_MSG_FATAL(__func__ << " -- nullptr is given."); \
57 return StatusCode::FAILURE; \
58 } \
59 ATH_CHECK(element->initElement()); \
60 element->releaseUnAlignedTrfs(); \
61 size_t idx = static_cast<size_t>(element->identHash()); \
62 if (idx >= STORAGE_VEC.size()) { \
63 STORAGE_VEC.resize(idx + 1); \
64 } \
65 std::unique_ptr<ELE_TYPE>& new_element = STORAGE_VEC[idx]; \
66 if (new_element) { \
67 ATH_MSG_FATAL("The detector element " \
68 << m_idHelperSvc->toStringDetEl(element->identify()) \
69 << " has already been added before " \
70 <<m_idHelperSvc->toStringDetEl(new_element->identify())); \
71 return StatusCode::FAILURE; \
72 } \
73 linkElements(STORAGE_VEC, element.get()); \
74 new_element = std::move(element); \
75 return StatusCode::SUCCESS; \
76 }
77#define ADD_DETECTOR(ELE_TYPE, STORAGE_VEC) \
78 WRITE_SETTER(ELE_TYPE, add##ELE_TYPE, STORAGE_VEC) \
79 \
80 std::vector<const ELE_TYPE*> MuonDetectorManager::getAll##ELE_TYPE##s() const { \
81 std::vector<const ELE_TYPE*> allElements{}; \
82 insert(STORAGE_VEC, allElements); \
83 return allElements; \
84 } \
85 \
86 std::vector<ELE_TYPE*> MuonDetectorManager::getAll##ELE_TYPE##s() { \
87 std::vector<ELE_TYPE*> allElements{}; \
88 insert(STORAGE_VEC, allElements); \
89 return allElements; \
90 }
91#define WRITE_ALLGETTER(CONSTNESS) \
92 std::vector<CONSTNESS MuonReadoutElement*> \
93 MuonDetectorManager::getAllReadoutElements(const ActsTrk::DetectorType type) CONSTNESS { \
94 std::vector<CONSTNESS MuonReadoutElement*> allEles{}; \
95 using enum ActsTrk::DetectorType; \
96 if (type == UnDefined || type == Mdt) { \
97 insert(getAllMdtReadoutElements(), allEles); \
98 } \
99 if (type == UnDefined || type == Rpc) { \
100 insert(getAllRpcReadoutElements(), allEles); \
101 } \
102 if (type == UnDefined || type == Tgc) { \
103 insert(getAllTgcReadoutElements(), allEles); \
104 } \
105 if (type == UnDefined || type == Mm) { \
106 insert(getAllMmReadoutElements(), allEles); \
107 } \
108 if (type == UnDefined || type == sTgc) { \
109 insert(getAllsTgcReadoutElements(), allEles); \
110 } \
111 return allEles; \
112 } \
113 \
114 CONSTNESS MuonReadoutElement* \
115 MuonDetectorManager::getReadoutElement(const Identifier& id) CONSTNESS { \
116 switch(m_idHelperSvc->technologyIndex(id)) { \
117 using enum Muon::MuonStationIndex::TechnologyIndex; \
118 case MDT: \
119 return getMdtReadoutElement(id); \
120 case RPC: \
121 return getRpcReadoutElement(id); \
122 case TGC: \
123 return getTgcReadoutElement(id); \
124 case STGC: \
125 return getsTgcReadoutElement(id); \
126 case MM: \
127 return getMmReadoutElement(id); \
128 default: \
129 ATH_MSG_WARNING(__FILE__<<":"<<__LINE__<<" Not a muon detector element " \
130 <<m_idHelperSvc->toString(id)); \
131 } \
132 return nullptr; \
133 }
134
135
136namespace MuonGMR4 {
137
138#ifndef SIMULATIONBASE
141
143 return (*a) < (*b);
144 }
146 return (*a) < (*b);
147 }
148#endif
150#ifndef SIMULATIONBASE
151 m_secEnvelopes.clear();
152#endif
153}
155 : AthMessaging{"MuonDetectorManagerR4"} {
156 if (!m_idHelperSvc.retrieve().isSuccess()) {
157 THROW_EXCEPTION(__func__<< "() -- Failed to retrieve the Identifier service");
158 }
159 setName("MuonR4");
160}
161
162WRITE_ALLGETTER(const)
169
170unsigned int MuonDetectorManager::getNumTreeTops() const {
171 return m_treeTopVector.size();
172}
173PVConstLink MuonDetectorManager::getTreeTop(unsigned int i) const {
174 assert(i < m_treeTopVector.size());
175 return m_treeTopVector[i];
176}
178
180 m_treeTopVector.push_back(pv);
181}
185std::vector<ActsTrk::DetectorType> MuonDetectorManager::getDetectorTypes() const {
186 std::vector<ActsTrk::DetectorType> types{};
187 if (!m_mdtEles.empty()) types.push_back(ActsTrk::DetectorType::Mdt);
188 if (!m_tgcEles.empty()) types.push_back(ActsTrk::DetectorType::Tgc);
189 if (!m_rpcEles.empty()) types.push_back(ActsTrk::DetectorType::Rpc);
190 if (!m_sTgcEles.empty()) types.push_back(ActsTrk::DetectorType::sTgc);
191 if (!m_mmEles.empty()) types.push_back(ActsTrk::DetectorType::Mm);
192 return types;
193}
194
195#ifndef SIMULATIONBASE
197 const unsigned hash = msSectorIdHash(chSector->chamberIndex(), chSector->sector(), chSector->side());
198 ATH_MSG_DEBUG("Add new sector "<<(*chSector)<<", hash: "<<hash);
199 const auto [element, isNew] = m_envelopesById.insert(std::make_pair(hash, chSector.get()));
200 if (!isNew) {
201 THROW_EXCEPTION("Conflicting hash: "<<hash<<", inserted: \n"<<(*element->second)
202 <<",\n tried to insert:\n "<<(*chSector));
203 }
204 m_secEnvelopes.push_back(std::move(chSector));
205 }
207 const unsigned sector,
208 const int side) const {
209 const unsigned hash = msSectorIdHash(chIdx, sector, side);
210 EnvelopeMap_t::const_iterator itr = m_envelopesById.find(hash);
211 if (itr != m_envelopesById.end()) {
212 return itr->second;
213 }
214 ATH_MSG_WARNING("Failed to fetch valid envelope for "<<Muon::MuonStationIndex::chName(chIdx)
215 <<", sector: "<<sector<<", side: "<<side);
216 return nullptr;
217 }
219 return getReadoutElement(channelId)->msSector();
220 }
221
223 const Chamber* MuonDetectorManager::getChamber(const Identifier& channelId) const {
224 return getReadoutElement(channelId)->chamber();
225 }
226
228 return Acts::unpackConstSmartPointers(m_secEnvelopes);
229 }
231 MuonChamberSet chambers{};
232 std::ranges::for_each(m_secEnvelopes,
233 [&chambers](const ElementPtr_t<SpectrometerSector>& ms){
234 std::ranges::transform(ms->chambers(), std::back_inserter(chambers),
235 [](const SpectrometerSector::ChamberPtr& ch){
236 return ch.get();
237 });
238 });
239 return chambers;
240 }
241#endif
242
243template <class MuonDetectorType> void MuonDetectorManager::linkElements(ElementStorage_t<MuonDetectorType>& detStore,
244 MuonDetectorType* reEle) {
245 ATH_MSG_VERBOSE("No inter-linking for "<<ActsTrk::to_string(reEle->detectorType())<<" "<<detStore.size());
246}
248 MdtReadoutElement* refEle) {
249 const MdtIdHelper& idHelper{m_idHelperSvc->mdtIdHelper()};
250 const int complMl = refEle->multilayer() == 2 ? 1 : idHelper.multilayerMax(refEle->identify());
251 const Identifier complMlId = idHelper.multilayerID(refEle->identify(), complMl);
252 const unsigned mlHash =static_cast<unsigned>(m_idHelperSvc->detElementHash(complMlId));
254 if (mlHash >= detStore.size() || !detStore[mlHash]) {
255 return;
256 }
257 detStore[mlHash]->setComplementaryReadoutEle(refEle);
258 refEle->setComplementaryReadoutEle(detStore[mlHash].get());
259
260}
261
262
263} // namespace MuonGMR4
264#undef WRITE_SETTER
265#undef ADD_DETECTOR
266#undef WRITE_ALLGETTER
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
static Double_t a
static const std::vector< std::string > types
AthMessaging(IMessageSvc *msgSvc, const std::string &name)
Constructor.
Identifier multilayerID(const Identifier &channeldID) const
static int multilayerMax()
Chamber represent the volume enclosing a muon station.
Definition Chamber.h:28
Readout element to describe the Monitored Drift Tube (Mdt) chambers Mdt chambers usually comrpise out...
void setComplementaryReadoutEle(const MdtReadoutElement *other)
Set the link to the second readout element inside the muon station.
unsigned multilayer() const
Returns the multi layer of the readout element [1;\2].
const Muon::IMuonIdHelperSvc * idHelperSvc() const
Returns a pointer to the central MuonIdHelperSvc.
std::vector< ActsTrk::DetectorType > getDetectorTypes() const
Returns a list of all detector types.
std::vector< ElementPtr_t< MuonDetectorType > > ElementStorage_t
: Abbrivation of the container holding all readout elements of a technology.
void addSpectrometerSector(ElementPtr_t< SpectrometerSector > &&chSector)
Add a spectrometer enevelope object to the manager.
const Chamber * getChamber(const Identifier &channelId) const
Retrieves the chamber enclosing the channel's readout element.
PVConstLink getTreeTop(unsigned int i) const override final
Returns the i-the tree top GeoModel volume.
MuonSectorSet getAllSectors() const
: Returns all MuonChambers associated with the readout geometry
std::unique_ptr< MuonDetectorType > ElementPtr_t
: Abrivation of the smart pointer holding the readout element
const MuonReadoutElement * getReadoutElement(const Identifier &id) const
Returns a generic Muon readout element.
unsigned int getNumTreeTops() const override final
Declaration of the readout element getters & setter function as described above.
const SpectrometerSector * getSectorEnvelope(const Identifier &channelId) const
Retrieves the spectrometer envelope enclosing the channel's readout element.
void linkElements(ElementStorage_t< MuonDetectorType > &allStore, MuonDetectorType *readOutEle)
Method that connects the same elements from the station with the parsed readout Element and vice vers...
void addTreeTop(PVConstLink pv)
Adds a new GeoModelVolume with its children as a new top node of the muon system.
const SpectrometerSector * msSector() const
Returns the pointer to the envelope volume enclosing all chambers in the sector.
Identifier identify() const override final
Return the ATLAS identifier.
const Chamber * chamber() const
Returns the pointer to the chamber enclosing this readout element.
A spectrometer sector forms the envelope of all chambers that are placed in the same MS sector & laye...
GeoModel::TransientConstSharedPtr< Chamber > ChamberPtr
Interface for Helper service that creates muon Identifiers and can be used to print Identifiers.
T * get(TKey *tobj)
get a TObject* from a TKey* (why can't a TObject be a TKey?)
Definition hcg.cxx:130
std::string to_string(const DetectorType &type)
@ Mm
Maybe not needed in the migration.
@ Tgc
Resitive Plate Chambers.
@ sTgc
Micromegas (NSW)
@ Rpc
Monitored Drift Tubes.
@ Mdt
MuonSpectrometer.
The ReadoutGeomCnvAlg converts the Run4 Readout geometry build from the GeoModelXML into the legacy M...
ADD_DETECTOR(MdtReadoutElement, m_mdtEles)
ChIndex chIndex(const std::string &index)
convert ChIndex name string to enum
StIndex toStationIndex(ChIndex index)
convert ChIndex into StIndex
constexpr unsigned numberOfSectors()
return total number of sectors
const std::string & chName(ChIndex index)
convert ChIndex into a string
ChIndex
enum to classify the different chamber layers in the muon spectrometer
constexpr int chIdxMax
#define THROW_EXCEPTION(MESSAGE)
Definition throwExcept.h:10