CbmRoot
Loading...
Searching...
No Matches
CbmStsAddress.cxx
Go to the documentation of this file.
1/* Copyright (C) 2013-2020 GSI/JINR-LIT, Darmstadt/Dubna
2 SPDX-License-Identifier: GPL-3.0-only
3 Authors: Volker Friese, Andrey Lebedev [committer] */
4
10#include "CbmStsAddress.h"
11
12#include "CbmDefs.h" // for kSts
13
14#include <cassert> // for assert
15#include <sstream> // for operator<<, basic_ostream, stringstream
16
17#include "AlgoFairloggerCompat.h" // for Logger, LOG
18
19// ----- Construct address from element Ids ------------------------------
20int32_t CbmStsAddress::GetAddress(uint32_t unit, uint32_t ladder, uint32_t halfladder, uint32_t module, uint32_t sensor,
21 uint32_t side, uint32_t version)
22{
23 using namespace Detail;
24
25 assert(version <= kCurrentVersion);
26
27 // Catch overrun of allowed ranges
28 uint32_t maxUnit = (1 << kBits[version][kStsUnit]) - 1;
29 if (unit > maxUnit) {
30 LOG(error) << "Unit Id " << unit << " exceeds maximum " << maxUnit;
31 return 0;
32 }
33 uint32_t maxLadder = (1 << kBits[version][kStsLadder]) - 1;
34 if (ladder > maxLadder) {
35 LOG(error) << "Ladder Id " << ladder << " exceeds maximum " << maxLadder;
36 return 0;
37 }
38 uint32_t maxHalfLadder = (1 << kBits[version][kStsHalfLadder]) - 1;
39 if (halfladder > maxHalfLadder) {
40 LOG(error) << "HalfLadder Id " << halfladder << " exceeds maximum " << maxHalfLadder;
41 return 0;
42 }
43 uint32_t maxModule = (1 << kBits[version][kStsModule]) - 1;
44 if (module > maxModule) {
45 LOG(error) << "Module Id " << module << " exceeds maximum " << maxModule;
46 return 0;
47 }
48 uint32_t maxSensor = (1 << kBits[version][kStsSensor]) - 1;
49 if (sensor > maxSensor) {
50 LOG(error) << "Sensor Id " << sensor << " exceeds maximum " << maxSensor;
51 return 0;
52 }
53 uint32_t maxSide = (1 << kBits[version][kStsSide]) - 1;
54 if (side > maxSide) {
55 LOG(error) << "Side Id " << side << " exceeds maximum " << maxSide;
56 return 0;
57 }
58
59 return ToIntegralType(ECbmModuleId::kSts) << kShift[version][kStsSystem] | unit << kShift[version][kStsUnit]
60 | ladder << kShift[version][kStsLadder] | halfladder << kShift[version][kStsHalfLadder]
61 | module << kShift[version][kStsModule] | sensor << kShift[version][kStsSensor]
62 | side << kShift[version][kStsSide] | version << kVersionShift;
63}
64// ---------------------------------------------------------------------------
65
66
67// ----- Construct address from array of element Ids ----------------------
68int32_t CbmStsAddress::GetAddress(uint32_t* elementId, uint32_t version)
69{
70 using namespace Detail;
71
72 assert(version <= kCurrentVersion);
73
74 int32_t address = ToIntegralType(ECbmModuleId::kSts) << kShift[version][kStsSystem];
75 for (int32_t level = 1; level < kStsNofLevels; level++) {
76 uint32_t maxId = (1 << kBits[version][level]) - 1;
77 if (elementId[level] > maxId) {
78 LOG(error) << "Id " << elementId[level] << " for STS level " << level << " exceeds maximum " << maxId;
79 return 0;
80 }
81 address = address | (elementId[level] << kShift[version][level]);
82 }
83 address = address | (version << kVersionShift);
84
85 return address;
86}
87// ---------------------------------------------------------------------------
88
89
90// ----- Construct address from address of descendant element ------------
91int32_t CbmStsAddress::GetMotherAddress(int32_t address, int32_t level)
92{
93 using namespace Detail;
94 assert(level >= kStsSystem && level < kStsNofLevels);
95 if (level == kStsNofLevels - 1) return address;
96 uint32_t version = GetVersion(address);
97 int32_t motherAdd = (address & ((1 << kShift[version][level + 1]) - 1));
98 motherAdd = motherAdd | (version << kVersionShift);
99 return motherAdd;
100}
101// ---------------------------------------------------------------------------
102
103
104// ----- Get the index of an element -------------------------------------
105uint32_t CbmStsAddress::GetElementId(int32_t address, int32_t level)
106{
107 using namespace Detail;
108 assert(level >= kStsSystem && level < kStsNofLevels);
109 uint32_t version = GetVersion(address);
110 return (address & (kMask[version][level] << kShift[version][level])) >> kShift[version][level];
111}
112// ---------------------------------------------------------------------------
113
114
115// ----- Get System ID ---------------------------------------------------
117{
118 return static_cast<ECbmModuleId>(GetElementId(address, kStsSystem));
119 // return GetElementId(address, kStsSystem);
120}
121// ---------------------------------------------------------------------------
122
123
124// ----- Get the version number from the address -------------------------
125uint32_t CbmStsAddress::GetVersion(int32_t address)
126{
127 return uint32_t((address & (kVersionMask << kVersionShift)) >> kVersionShift);
128}
129// ---------------------------------------------------------------------------
130
131
132// ----- Construct address by changing the index of an element ------------
133int32_t CbmStsAddress::SetElementId(int32_t address, int32_t level, uint32_t newId)
134{
135 using namespace Detail;
136 assert(level >= kStsSystem && level < kStsNofLevels);
137 uint32_t version = GetVersion(address);
138 uint32_t maxId = (1 << kBits[version][level]) - 1;
139 if (newId > maxId) {
140 LOG(fatal) << "Id " << newId << " for STS level " << level << " exceeds maximum " << maxId;
141 return 0;
142 }
143 return (address & (~(kMask[version][level] << kShift[version][level]))) | (newId << kShift[version][level]);
144}
145// -------------------------------------------------------------------------
146
147// ----- String output -------------------------------------------------
148std::string CbmStsAddress::ToString(int32_t address)
149{
150 std::stringstream ss;
151
152 ss << "StsAddress: address " << address << " (version " << GetVersion(address) << ")"
153 << ": system " << GetElementId(address, kStsSystem) << ", unit " << GetElementId(address, kStsUnit) << ", ladder "
154 << GetElementId(address, kStsLadder) << ", half-ladder " << GetElementId(address, kStsHalfLadder) << ", module "
155 << GetElementId(address, kStsModule) << ", sensor " << GetElementId(address, kStsSensor) << ", side "
156 << GetElementId(address, kStsSide);
157 return ss.str();
158}
159// -------------------------------------------------------------------------
XPU_D constexpr auto ToIntegralType(T enumerator) -> typename std::underlying_type< T >::type
Definition CbmDefs.h:29
ECbmModuleId
Definition CbmDefs.h:39
@ kSts
Silicon Tracking System.
@ kStsModule
@ kStsLadder
@ kStsSystem
@ kStsSide
@ kStsNofLevels
@ kStsHalfLadder
@ kStsSensor
@ kStsUnit
uint32_t GetVersion(int32_t address)
Extract version number.
int32_t GetMotherAddress(int32_t address, int32_t level)
Construct the address of an element from the address of a descendant element.
int32_t SetElementId(int32_t address, int32_t level, uint32_t newId)
Set the index of an element, leaving the other element levels untouched.
int32_t GetAddress(uint32_t unit=0, uint32_t ladder=0, uint32_t halfladder=0, uint32_t module=0, uint32_t sensor=0, uint32_t side=0, uint32_t version=kCurrentVersion)
Construct address.
ECbmModuleId GetSystemId(int32_t address)
Get system Id (should be ECbmModuleId::kSts)
uint32_t GetElementId(int32_t address, int32_t level)
Get the index of an element.
std::string ToString(int32_t address)
String output.