ATLAS Offline Software
Loading...
Searching...
No Matches
CTP_Decoder.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2024 CERN for the benefit of the ATLAS collaboration
3*/
4
5
6// this header file
8
9// tdaq-common includes for format definition
10#include "CTPfragment/CTPdataformat.h"
11
12#include "GaudiKernel/MsgStream.h"
14
16 AthMessaging(Athena::getMessageSvc(), "CTP_Decoder")
17{
18}
19
21{
22 m_rdo = rdo;
23 unsigned int ctpVersionNumber = m_rdo->getCTPVersionNumber();
24 CTPdataformatVersion ctpVersion(ctpVersionNumber);
25
26 unsigned int nBunches = rdo->getNumberOfBunches();
27 ATH_MSG_DEBUG("setRDO> #bunches: " << nBunches << ", ctp version (found in RDO): " << ctpVersionNumber);
28 ATH_MSG_VERBOSE(ctpVersion.dump());
29
30 m_BCs.clear();
31 m_BCs.resize(nBunches);
32 for (CTP_BC& bc : m_BCs) {
33 bc.setCTPVersion(ctpVersionNumber);
34 }
35
36 //std::vector<uint32_t> PITs = rdo->getPITWords();
37 //std::vector<uint32_t> FPIs = rdo->getFPIWords();
38 const std::vector<uint32_t> & TIPs = rdo->getTIPWords();
39 const std::vector<uint32_t> & TBPs = rdo->getTBPWords();
40 const std::vector<uint32_t> & TAPs = rdo->getTAPWords();
41 const std::vector<uint32_t> & TAVs = rdo->getTAVWords();
42
43 if( nBunches * ctpVersion.getTIPwords() != TIPs.size() ) {
44 ATH_MSG_FATAL("Expected " << nBunches * ctpVersion.getTIPwords() << " TIP words, but TIP vector has size " << TIPs.size());
45 } else {
46 ATH_MSG_DEBUG(TIPs.size() << " TIP words as expected");
47 }
48 if( nBunches * ctpVersion.getTBPwords() != TBPs.size() ) {
49 ATH_MSG_FATAL(nBunches * ctpVersion.getTBPwords() << " TBP words, but TBP vector has size " << TBPs.size());
50 } else {
51 ATH_MSG_DEBUG(TBPs.size() << " TBP words as expected");
52 }
53 if( nBunches * ctpVersion.getTAPwords() != TAPs.size() ) {
54 ATH_MSG_FATAL(nBunches * ctpVersion.getTAPwords() << " TAP words, but TAP vector has size " << TAPs.size());
55 } else {
56 ATH_MSG_DEBUG(TAPs.size() << " TAP words as expected");
57 }
58 if( nBunches * ctpVersion.getTAVwords() != TAVs.size() ) {
59 ATH_MSG_FATAL(nBunches * ctpVersion.getTAVwords() << " TAV words, but TAV vector has size " << TAVs.size());
60 } else {
61 ATH_MSG_DEBUG(TAVs.size() << " TAV words as expected");
62 }
63
64
65 for(unsigned int i = 0 ; i < nBunches ; ++i) {
66
67 ATH_MSG_DEBUG(i << " from CTP_RDO to internal bitsets");
68
69 for(unsigned int tip = 0; tip < ctpVersion.getTIPwords(); ++tip) {
70 unsigned int index = i*ctpVersion.getTIPwords() + tip;
71 if(index >= TIPs.size()) {
72 ATH_MSG_FATAL("Invalid TIP position " << index);
73 return;
74 }
75 m_BCs[i].setTIPWord(TIPs[index],tip); //sets m_tip
76 }
77
78 for(unsigned int tbp = 0; tbp < ctpVersion.getTBPwords(); ++tbp) {
79 unsigned int index = i * ctpVersion.getTBPwords() + tbp;
80 if(index >= TBPs.size()) {
81 ATH_MSG_FATAL("Invalid TBP position " << index);
82 return;
83 }
84 m_BCs[i].setTBPWord(TBPs[index],tbp); //sets m_tbp
85 }
86
87 for(unsigned int tap = 0; tap < ctpVersion.getTAPwords(); ++tap) {
88 unsigned int index = i * ctpVersion.getTAPwords() + tap;
89 if(index >= TAPs.size()) {
90 ATH_MSG_FATAL("Invalid TAP position " << index);
91 return;
92 }
93 m_BCs[i].setTAPWord(TAPs[index],tap); //sets m_tap
94 }
95
96 for(unsigned int tav = 0; tav < ctpVersion.getTAVwords(); ++tav) {
97 unsigned int index = i * ctpVersion.getTAVwords() + tav;
98 if(index >= TAVs.size()) {
99 ATH_MSG_FATAL("Invalid TAV position " << index);
100 return;
101 }
102 m_BCs[i].setTAVWord(TAVs[index],tav); //set m_tav
103 }
104 }
105}
106
108{
109 unsigned int nBunches = m_rdo->getNumberOfBunches();
110 unsigned int vecSize = m_BCs.size();
111
112 if(nBunches == 0) {
113 ATH_MSG_DEBUG("CTP_RDO empty");
114 return;
115 }
116
117 if(nBunches != vecSize) {
118 ATH_MSG_ERROR("mismatch: " << nBunches << " bunches, but vector size is " << vecSize);
119 }
120
121 if( msgLvl(MSG::DEBUG) ){
122 msg() << MSG::DEBUG << "=================================================" << endmsg;
123 msg() << MSG::DEBUG << "Event dump" << endmsg;
124 msg() << MSG::DEBUG << "Time " << m_rdo->getTimeSec() << "s "
125 << std::setw(10) << std::setiosflags(std::ios_base::right) << std::setfill(' ')
126 << m_rdo->getTimeNanoSec() << std::resetiosflags(std::ios_base::right)
127 << "ns" << endmsg;
128 msg() << MSG::DEBUG << "Number of bunches: " << nBunches
129 << " (BC vector size " << vecSize << ")" << endmsg;
130 msg() << MSG::DEBUG << "L1A position: " << m_rdo->getL1AcceptBunchPosition() << endmsg;
131 }
132
133 for(unsigned int i = 0; i<vecSize; ++i) {
134 ATH_MSG_DEBUG("Now dumping BC " << i);
135 m_BCs[i].dumpData(msg());
136 }
137
138 ATH_MSG_DEBUG("=================================================");
139}
140
141
142
143bool CTP_Decoder::checkTrigger(unsigned int itemNo,unsigned int pos)
144{
145 if(pos >= m_BCs.size()) {
146 ATH_MSG_WARNING("Trying to access bunch crossing no "
147 << pos << ", but in the event are only " << m_BCs.size());
148 return false;
149 }
150 if(itemNo >= getBunchCrossing(pos).getTAV().size()) {
151 ATH_MSG_WARNING("Checking item no " << itemNo
152 << ", which is more than the maximum : "
153 << getBunchCrossing(pos).getTAV().size());
154 }
155 return getBunchCrossing(pos).getTAV().test(itemNo);
156}
157
158bool CTP_Decoder::checkTriggerAfterPrescale(unsigned int itemNo,unsigned int pos) {
159 if(pos >= m_BCs.size()) {
160 ATH_MSG_WARNING("Trying to access bunch crossing no "
161 << pos << ", but in the event are only " << m_BCs.size());
162 return false;
163 }
164 if(itemNo >= getBunchCrossing(pos).getTAP().size()) {
165 ATH_MSG_WARNING("Checking item no " << itemNo
166 << ", which is more than the maximum : "
167 << getBunchCrossing(pos).getTAP().size());
168 }
169 return getBunchCrossing(pos).getTAP().test(itemNo);
170}
171
172
173
174std::vector<unsigned int> CTP_Decoder::getAllTriggers(unsigned int pos) {
175 if(pos >= m_BCs.size()) {
176 ATH_MSG_WARNING("Trying to access bunch crossing no "
177 << pos << ", but in the event are only " << m_BCs.size());
178 return std::vector<unsigned int>();
179 }
180 std::vector<unsigned int> triggers;
181 const CTP_BC& bc = getBunchCrossing(pos);
182 if(bc.getTAV().any()) {
183 for(unsigned int i = 0; i < bc.getTAV().size() ; ++i) {
184 if(bc.getTAV().test(i)) {
185 triggers.push_back(i+1);
186 }
187 }
188 }
189 return triggers;
190}
191
192
193
194
200
201void CTP_BC::dumpData(MsgStream& msglog) const
202{
203 if( msglog.level() > MSG::DEBUG )
204 return;
205
206 msglog << MSG::DEBUG << "-------------- BC dump for " << getBCID() << " ------------------------------------" << endmsg;
207 msglog << MSG::DEBUG << "PITWordAux : " << printPITWordAux() << endmsg;
208 msglog << MSG::DEBUG << "BCID : " << getBCID() << endmsg;
209 msglog << MSG::DEBUG << "Random trig : " << getRandomTrig() << " (binary: " << printRandomTrig() << ")" << endmsg;
210 msglog << MSG::DEBUG << "Prescaled clock : " << getPrescaledClock() << " (binary: " << printPrescaledClock() << ")" << endmsg;
211
212 if(m_tip.any()) {
213 int count(0);
214 std::ostringstream outstream;
215 for(unsigned int i = 0; i<m_tip.size() ; ++i) {
216 if(m_tip.test(i)) {
217 outstream << std::setw(3) << std::setfill('0') << (i+1) << " ";
218 ++count;
219 }
220 }
221 msglog << MSG::DEBUG << "TIP with input (" << count << " items): " << outstream.str() << endmsg;
222 } else {
223 msglog << MSG::DEBUG << "No TIP!" << endmsg;
224 }
225
226
227 if(m_tbp.any()) {
228 int count(0);
229 std::ostringstream outstream;
230 for(unsigned int i = 0; i<m_tbp.size() ; ++i) {
231 if(m_tbp.test(i)) {
232 outstream << i << " ";
233 ++count;
234 }
235 }
236 msglog << MSG::DEBUG << "Fired TBP (" << count << " items): " << outstream.str() << endmsg;
237 } else {
238 msglog << MSG::DEBUG << "No TBP fired!" << endmsg;
239 }
240
241
242 if(m_tap.any()) {
243 int count(0);
244 std::ostringstream outstream;
245 for(unsigned int i = 0; i<m_tap.size() ; ++i) {
246 if(m_tap.test(i)) {
247 outstream << i << " ";
248 ++count;
249 }
250 }
251 msglog << MSG::DEBUG << "Fired TAP (" << count << " items): " << outstream.str() << endmsg;
252 } else {
253 msglog << MSG::DEBUG << "No TAP fired!" << endmsg;
254 }
255
256
257 if(m_tav.any()) {
258 int count(0);
259 std::ostringstream outstream;
260 for(unsigned int i = 0; i<m_tav.size() ; ++i) {
261 if(m_tav.test(i)) {
262 outstream << i << " ";
263 ++count;
264 }
265 }
266 msglog << MSG::DEBUG << "Fired TAV (" << count << " items): " << outstream.str() << endmsg;
267 } else {
268 msglog << MSG::DEBUG << "No TAV fired!" << endmsg;
269 }
270
271 msglog << MSG::VERBOSE << "TIP - total size: " << m_tip.size() << ", with input: "
272 << m_tip.count() << ", pattern:" << std::endl << printTIP() << endmsg;
273 msglog << MSG::VERBOSE << "TBP " << std::endl << printTBP() << endmsg;
274 msglog << MSG::VERBOSE << "TAP " << std::endl << printTAP() << endmsg;
275 msglog << MSG::VERBOSE << "TAV " << std::endl << printTAV() << endmsg;
276}
277
278
279std::bitset<32> CTP_BC::getBCIDBitSet() const
280{
281 std::bitset<32> bcid = (m_pitAux >> m_ctpVersion.getBcidShift());
282
283 // the bcid mask is wrong in CTPfragment/CTPdataformatVersion.h (0xF000)
284 // so we set it here
285 uint32_t bcidMask = 0xFFF;
286 if(m_ctpVersion.getVersionNumber()>=1 && m_ctpVersion.getVersionNumber()<=3) {
287 bcidMask = 0xF;
288 }
289 //bcid &= m_ctpVersion.getBcidMask();
290 bcid &= bcidMask;
291 return bcid;
292}
293
294uint32_t CTP_BC::getBCID() const
295{
296 return getBCIDBitSet().to_ulong();
297}
298
299std::string CTP_BC::printBCID() const
300{
301 std::bitset<32> bcid = getBCIDBitSet();
302 return bcid.to_string<char,
303 std::char_traits<char>, std::allocator<char> >();
304}
305
306std::bitset<32> CTP_BC::getRandomTrigBitSet() const
307{
308 std::bitset<32> rnd = (m_pitAux >> m_ctpVersion.getRandomTrigShift());
309 rnd &= m_ctpVersion.getRandomTrigMask();
310 return rnd;
311}
312
313uint32_t CTP_BC::getRandomTrig() const
314{
315 return getRandomTrigBitSet().to_ulong();
316}
317
318std::string CTP_BC::printRandomTrig() const
319{
320 std::bitset<32> rnd = getRandomTrigBitSet();
321 return rnd.to_string<char,
322 std::char_traits<char>, std::allocator<char> >();
323}
324
325std::bitset<32> CTP_BC::getPrescaledClockBitSet() const
326{
327 std::bitset<32> prcl;
328
329 if (!m_ctpVersion.getNumPrescaledClocks()) {
330 return prcl;
331 }
332
333 prcl = (m_pitAux >> m_ctpVersion.getPrescaledClockShift());
334 prcl &= m_ctpVersion.getPrescaledClockMask();
335 return prcl;
336}
337
339{
340 return getPrescaledClockBitSet().to_ulong();
341}
342
344{
345 std::bitset<32> prcl = getPrescaledClockBitSet();
346 return prcl.to_string<char,
347 std::char_traits<char>, std::allocator<char> >();
348}
349
350std::string CTP_BC::printPITWordAux() const
351{
352 return m_pitAux.to_string<char,
353 std::char_traits<char>, std::allocator<char> >();
354}
355
356void CTP_BC::setTIPWord( uint32_t word, uint32_t pos)
357{
358 if(pos >= m_ctpVersion.getTIPwords()) {
359 MsgStream log(Athena::getMessageSvc(), "CTP_Decoder");
360 log << MSG::ERROR <<"Invalid TIP position " << pos <<endmsg;
361 return;
362 }
363
364 std::bitset<512> bs = word;
365
366 bs <<= (pos * CTP_RDO::SIZEOF_WORDS);
367
368 if( pos < (m_ctpVersion.getTIPwords()-1) ) m_tip |= bs;
369 else setPITWordAux(word);
370}
371
372void CTP_BC::setTIP(const std::vector<uint32_t>& words)
373{
374 for(uint32_t i = 0; i<words.size();++i) setTIPWord(words[i],i);
375}
376
377std::string CTP_BC::printTIP() const
378{
379 return m_tip.to_string<char,
380 std::char_traits<char>, std::allocator<char> >();
381}
382
383
384
385void CTP_BC::setTBPWord( uint32_t word, uint32_t pos)
386{
387 if(pos >= m_ctpVersion.getTBPwords()) {
388 MsgStream log(Athena::getMessageSvc(), "CTP_Decoder");
389 log << MSG::ERROR <<"Invalid TBP position " << pos <<endmsg;
390 return;
391 }
392
393 std::bitset<512> bs = word;
394 bs <<= (pos * CTP_RDO::SIZEOF_WORDS);
395 m_tbp |= bs;
396}
397
398void CTP_BC::setTBP(const std::vector<uint32_t>& words)
399{
400 for(uint32_t i = 0; i<words.size();++i) setTBPWord(words[i],i);
401}
402
403std::string CTP_BC::printTBP() const
404{
405 return m_tbp.to_string<char,
406 std::char_traits<char>, std::allocator<char> >();
407}
408
409void CTP_BC::setTAPWord( uint32_t word, uint32_t pos)
410{
411 if(pos >= m_ctpVersion.getTAPwords()) {
412 MsgStream log(Athena::getMessageSvc(), "CTP_Decoder");
413 log << MSG::ERROR <<"Invalid TAP position " << pos <<endmsg;
414 return;
415 }
416 std::bitset<512> bs = word;
417 bs <<= (pos * CTP_RDO::SIZEOF_WORDS);
418 m_tap |= bs;
419}
420
421void CTP_BC::setTAP(const std::vector<uint32_t>& words)
422{
423 for(uint32_t i = 0; i<words.size();++i)
424 setTAPWord(words[i],i);
425}
426
427std::string CTP_BC::printTAP() const
428{
429 return m_tap.to_string<char,
430 std::char_traits<char>, std::allocator<char> >();
431}
432
433void CTP_BC::setTAVWord( uint32_t word, uint32_t pos)
434{
435 if(pos >= m_ctpVersion.getTAVwords()) {
436 MsgStream log(Athena::getMessageSvc(), "CTP_Decoder");
437 log << MSG::ERROR <<"Invalid TAV position " << pos <<endmsg;
438 return;
439 }
440 std::bitset<512> bs = word;
441 bs <<= (pos * CTP_RDO::SIZEOF_WORDS);
442 m_tav |= bs;
443}
444
445void CTP_BC::setTAV(const std::vector<uint32_t>& words)
446{
447 for(uint32_t i = 0; i<words.size();++i)
448 setTAVWord(words[i],i);
449}
450
451std::string CTP_BC::printTAV() const
452{
453 return m_tav.to_string<char,
454 std::char_traits<char>, std::allocator<char> >();
455}
#define endmsg
#define ATH_MSG_ERROR(x)
#define ATH_MSG_FATAL(x)
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
static TRandom * rnd
MsgStream & msg() const
The standard message stream.
bool msgLvl(const MSG::Level lvl) const
Test the output level.
AthMessaging(IMessageSvc *msgSvc, const std::string &name)
Constructor.
void setTIPWord(uint32_t word, uint32_t pos=0)
Set TIP word number 'pos'.
std::string printTBP() const
Obtain TBP bitpattern string (binary format)
void setTAP(const std::vector< uint32_t > &words)
Set TAP (Trigger After Prescales) words.
void setTBPWord(uint32_t word, uint32_t pos=0)
Set TBP word number 'pos'.
uint32_t getBCID() const
Get BCID as unsigned integer.
void dumpData(MsgStream &) const
Helper class to decode the CTP data for one bunch-crossing.
std::string printBCID() const
Return string with BCID in binary format.
std::bitset< 32 > getPrescaledClockBitSet() const
Accessor to obtain prescaled-clock input bits.
void setTAVWord(uint32_t word, uint32_t pos=0)
Set TAV word number 'pos'.
void setTAV(const std::vector< uint32_t > &words)
Set TAV (Trigger After Veto) words.
std::bitset< 512 > m_tip
Bitsets containing bit-patterns of trigger inputs and trigger.
void setTIP(const std::vector< uint32_t > &words)
Set TIP words.
const std::bitset< 512 > & getTAV() const
get bitset of TAV words
std::bitset< 512 > m_tav
std::bitset< 512 > m_tbp
void setTAPWord(uint32_t word, uint32_t pos=0)
Set TAP word number 'pos'.
std::bitset< 32 > getBCIDBitSet() const
Accessor to obtain std::bitset containing the bunch-crossing.
std::string printPITWordAux() const
Get auxiliary PIT word as string in binary format.
std::string printTIP() const
Obtain TIP bitpattern string (binary format)
void setPITWordAux(uint32_t word)
Set auxiliary PIT word, which is the one containing the 12-bit BCID (bit.
Definition CTP_Decoder.h:69
std::string printTAP() const
Obtain TAP bitpattern string (binary format)
std::string printRandomTrig() const
Return string with random trigger in binary format.
std::bitset< 32 > getRandomTrigBitSet() const
Accessor to obtain random-trigger input bits.
std::string printTAV() const
Obtain TAV bitpattern string (binary format)
uint32_t getPrescaledClock() const
Prescaled-clock inputs as uint32_t.
const std::bitset< 512 > & getTAP() const
get bitset of TAP words
CTPdataformatVersion m_ctpVersion
std::bitset< 512 > m_tap
void setTBP(const std::vector< uint32_t > &words)
Set TBP (Trigger Before Prescales) words.
uint32_t getRandomTrig() const
Random-trigger inputs as uint32_t.
std::bitset< 32 > m_pitAux
Contains BCID, random trigger and prescaled clock.
std::string printPrescaledClock() const
Return string with prescaled clock in binary format.
CTP_Decoder()
Helper class to decode the CTP data fragment.
void dumpData() const
Helper to dump data for debugging.
bool checkTrigger(unsigned int itemNo, unsigned int bcPos)
Test the LVL1 trigger result for a certain trigger item.
bool checkTriggerAfterPrescale(unsigned int itemNo, unsigned int bcPos)
Test the LVL1 trigger result after pre-scale factors are applied, before the final trigger decision,...
std::vector< unsigned int > getAllTriggers(unsigned int bcPos)
Function to obtain a vector with the numbers of the trigger items that fired for the current event.
void setRDO(const CTP_RDO *rdo)
Set RDO and fill internal variables from the data object.
const CTP_RDO * m_rdo
The RDO member.
std::vector< CTP_BC > m_BCs
Vector of BCs for the current event.
const CTP_BC & getBunchCrossing(unsigned int pos)
Get data of a single bunch-crossing.
std::vector< uint32_t > getTBPWords() const
Definition CTP_RDO.cxx:206
std::vector< uint32_t > getTAPWords() const
Definition CTP_RDO.cxx:211
uint32_t getNumberOfBunches() const
Definition CTP_RDO.cxx:89
static constexpr unsigned int SIZEOF_WORDS
number of bits in one data word (32)
Definition CTP_RDO.h:90
std::vector< uint32_t > getTIPWords() const
Definition CTP_RDO.cxx:201
std::vector< uint32_t > getTAVWords() const
Definition CTP_RDO.cxx:216
singleton-like access to IMessageSvc via open function and helper
int count(std::string s, const std::string &regx)
count how many occurances of a regx are in a string
Definition hcg.cxx:146
Some weak symbol referencing magic... These are declared in AthenaKernel/getMessageSvc....
IMessageSvc * getMessageSvc(bool quiet=false)
Definition index.py:1