LDMX Software
HcalRawDecoder.cxx
1
2
3#include "Hcal/HcalRawDecoder.h"
4// un comment for HcalRawDecoder-specific debug printouts to std::cout
5//#define DEBUG
6
7namespace hcal {
8
9namespace utility {
10
14class Reader {
15 const std::vector<uint8_t>& buffer_;
16 std::size_t i_word_;
17 uint32_t next() {
18 uint32_t w = buffer_.at(i_word_) | (buffer_.at(i_word_ + 1) << 8) |
19 (buffer_.at(i_word_ + 2) << 16) |
20 (buffer_.at(i_word_ + 3) << 24);
21 i_word_ += 4;
22 return w;
23 }
24
25 public:
26 Reader(const std::vector<uint8_t>& b) : buffer_{b}, i_word_{0} {}
27 operator bool() { return (i_word_ < buffer_.size()); }
28 Reader& operator>>(uint32_t& w) {
29 if (*this) w = next();
30 return *this;
31 }
32}; // Reader
33
34} // namespace utility
35
36namespace debug {
37
38struct hex {
39 uint32_t word_;
40 hex(uint32_t w) : word_{w} {}
41};
42
43} // namespace debug
44
45inline std::ostream& operator<<(std::ostream& os, const debug::hex& h) {
46 os << "0x" << std::setfill('0') << std::setw(8) << std::hex << h.word_
47 << std::dec;
48 return os;
49}
50
56 const std::string& prefix) {
57 {
58 event.add(prefix + "Version", version);
59 event.add(prefix + "FPGA", fpga);
60 event.add(prefix + "NSamples", nsamples);
61 event.add(prefix + "Spill", spill);
62 event.add(prefix + "Ticks", ticks);
63 event.add(prefix + "Bunch", bunch);
64 event.add(prefix + "Number", number);
65 event.add(prefix + "Run", run);
66 event.add(prefix + "DD", DD);
67 event.add(prefix + "MM", MM);
68 event.add(prefix + "hh", hh);
69 event.add(prefix + "mm", mm);
70 event.add(prefix + "GoodLinkHeader", good_bxheader);
71 event.add(prefix + "GoodLinkTrailer", good_trailer);
72 }
73}
74
76 input_file_ = ps.getParameter<std::string>("input_file");
77 input_names_ = ps.getParameter<std::vector<std::string>>("input_names", {});
78 input_pass_ = ps.getParameter<std::string>("input_pass");
79 output_name_ = ps.getParameter<std::string>("output_name");
80 roc_version_ = ps.getParameter<int>("roc_version");
81 translate_eid_ = ps.getParameter<bool>("translate_eid");
82 read_from_file_ = ps.getParameter<bool>("read_from_file");
83 detector_name_ = ps.getParameter<std::string>("detector_name");
84 if (read_from_file_) {
86 }
87}
88
90 // if we are reading from a file, we need to provide the detector name
91 if (read_from_file_) {
93 }
94}
95
98 std::vector<ldmx::HgcrocDigiCollection::Sample>>
99 eid_to_samples;
101 if (read_from_file_) {
102 if (!file_reader_ or file_reader_.eof()) return;
103 eid_to_samples = this->read(file_reader_, eh);
104 } else {
105 for (const auto& name : input_names_) {
106 hcal::utility::Reader bus_reader(
107 event.getCollection<uint8_t>(name, input_pass_));
108 auto single_pf_samples = this->read(bus_reader, eh);
109 for (const auto& [id, samples] : single_pf_samples) {
110 eid_to_samples[id] = samples;
111 }
112 }
113 }
114
115 eh.board(event, output_name_);
116
118 // assume all channels have same number of samples
119 digis.setNumSamplesPerDigi(eid_to_samples.begin()->second.size());
120 digis.setSampleOfInterestIndex(0); // TODO configurable
122 if (translate_eid_) {
130#ifdef DEBUG
131 std::cout << "Translating EIDs into DetIDs. Printing skipped EIDs..."
132 << std::endl;
133#endif
134 auto detmap{
135 getCondition<HcalDetectorMap>(HcalDetectorMap::CONDITIONS_OBJECT_NAME)};
136 for (auto const& [eid, digi] : eid_to_samples) {
137 // The electronics map returns an empty ID of the correct
138 // type when the electronics ID is not found.
139 // need to check if the electronics ID exists
140 // TODO: do we want to end processing if this happens?
141 if (detmap.exists(eid)) {
142 uint32_t did_raw = detmap.get(eid).raw();
143 digis.addDigi(did_raw, digi);
144 } else {
151#ifdef DEBUG
152 std::cout << "EID(" << eid.fiber() << "," << eid.elink() << ","
153 << eid.channel() << ") ";
154 for (auto& s : digi) std::cout << debug::hex(s.raw()) << " ";
155 std::cout << std::endl;
156#endif
157 }
158 }
159 } else {
167 for (auto const& [eid, digi] : eid_to_samples) {
168 digis.addDigi(eid.raw(), digi);
169 }
170 }
171
172#ifdef DEBUG
173 std::cout << "adding " << digis.getNumDigis() << " digis each with "
174 << digis.getNumSamplesPerDigi() << " samples to event bus"
175 << std::endl;
176#endif
177 event.add(output_name_, digis);
178 return;
179} // produce
180
181} // namespace hcal
182DECLARE_PRODUCER_NS(hcal, HcalRawDecoder);
#define DECLARE_PRODUCER_NS(NS, CLASS)
Macro which allows the framework to construct a producer given its name during configuration.
Implements an event buffer system for storing event data.
Definition Event.h:41
const std::vector< ContentType > & getCollection(const std::string &collectionName, const std::string &passName="") const
Get a collection (std::vector) of objects from the event bus.
Definition Event.h:386
Class encapsulating parameters for configuring a processor.
Definition Parameters.h:27
T getParameter(const std::string &name) const
Retrieve the parameter of the given name.
Definition Parameters.h:89
static constexpr const char * CONDITIONS_OBJECT_NAME
The name of the EID <-> DetID map for the ECal.
std::string detector_name_
the detector name if we are reading from a file
bool read_from_file_
is the input_name a file or an event object
std::string output_name_
output object to put onto event bus
std::string input_file_
input file of encoded data
void beforeNewRun(ldmx::RunHeader &rh) override
add detector name if we are reading from file
packing::utility::Reader file_reader_
the file reader (if we are doing that)
void configure(framework::config::Parameters &) override
Callback for the EventProcessor to configure itself from the given set of parameters.
std::vector< std::string > input_names_
input object of encoded data
std::map< ldmx::HcalElectronicsID, std::vector< ldmx::HgcrocDigiCollection::Sample > > read(ReaderType &reader, PolarfireEventHeader &eh)
Assume input reader behaves like a binary data input stream where we can "pop" individual 32-bit word...
bool translate_eid_
are get translating electronic IDs?
int roc_version_
version of HGC ROC we are decoding
std::string input_pass_
input pass of creating encoded data
void produce(framework::Event &event) override
use read function to decode data, then translate EIDs into DetIDs
Read out 32-bit words from a 8-bit buffer.
Identifies a location in the Hcal readout chain.
Represents a collection of the digi hits readout by an HGCROC.
unsigned int getNumSamplesPerDigi() const
Get number of samples per digi.
void setNumSamplesPerDigi(unsigned int n)
Set number of samples for each digi.
void setSampleOfInterestIndex(unsigned int n)
Set index of sample of interest.
void setVersion(int v)
Set the version of the ROC we have read.
void addDigi(unsigned int id, const std::vector< Sample > &digi)
Add samples to collection.
unsigned int getNumDigis() const
Get total number of digis.
Run-specific configuration and data stored in its own output TTree alongside the event TTree in the o...
Definition RunHeader.h:54
void setDetectorName(const std::string &det)
Set the name of the detector that was used in this run.
Definition RunHeader.h:80
void open(const std::string &file_name)
Open a file with this reader.
Definition Reader.h:35
bool eof()
check if file is done
Definition Reader.h:214
int hh
hour run started
int version
version of daq format
std::vector< bool > good_bxheader
quality of link headers
int mm
minute run started
int number
event number according to this polarfire
void board(framework::Event &event, const std::string &prefix)
board us onto the bus with the input prefix
int ticks
number of 5MHz ticks since spill
int DD
day of month run started
std::vector< bool > good_trailer
quality of link trailers
int fpga
id for polarfire
int nsamples
number of samples
int run
run number according to this polarfire
int MM
month run started
int bunch
bunch number according to this polarfire