CMS 3D CMS Logo

RPCAMCRawToDigi.cc
Go to the documentation of this file.
2 
3 #include <memory>
4 
12 
19 
21  : calculate_crc_(config.getParameter<bool>("calculateCRC")),
22  fill_counters_(config.getParameter<bool>("fillCounters")),
23  rpc_unpacker_(
24  RPCAMCUnpackerFactory::get()->create(config.getParameter<std::string>("RPCAMCUnpacker"),
25  config.getParameter<edm::ParameterSet>("RPCAMCUnpackerSettings"),
26  consumesCollector(),
27  producesCollector())) {
28  if (fill_counters_) {
29  produces<RPCAMCLinkCounters>();
30  }
31 
32  raw_token_ = consumes<FEDRawDataCollection>(config.getParameter<edm::InputTag>("inputTag"));
33 }
34 
36 
39  desc.add<edm::InputTag>("inputTag", edm::InputTag("rawDataCollector", ""));
40  desc.add<bool>("calculateCRC", true);
41  desc.add<bool>("fillCounters", true);
42  desc.add<std::string>("RPCAMCUnpacker", "RPCAMCUnpacker");
44  descs.add("RPCAMCRawToDigi", desc);
45 }
46 
48  rpc_unpacker_->beginRun(run, setup);
49 }
50 
52  // Get RAW Data
53  edm::Handle<FEDRawDataCollection> raw_data_collection;
54  event.getByToken(raw_token_, raw_data_collection);
55 
56  std::unique_ptr<RPCAMCLinkCounters> counters(new RPCAMCLinkCounters());
57 
58  std::map<RPCAMCLink, rpcamc13::AMCPayload> amc_payload;
59 
60  // Loop over the FEDs
61  for (int fed : rpc_unpacker_->getFeds()) {
62  if (fill_counters_) {
64  }
65 
66  std::uint16_t crc(0xffff);
67 
68  FEDRawData const &raw_data = raw_data_collection->FEDData(fed);
69  unsigned int nwords(raw_data.size() / sizeof(std::uint64_t));
70  if (!nwords) {
71  continue;
72  }
73 
74  std::uint64_t const *word(reinterpret_cast<std::uint64_t const *>(raw_data.data()));
75  std::uint64_t const *word_end = word + nwords;
76 
77  LogDebug("RPCAMCRawToDigi") << "Handling FED " << fed << " with length " << nwords;
78 
79  // Handle the CDF Headers
80  if (!processCDFHeaders(fed, word, word_end, crc, *counters)) {
81  continue;
82  }
83 
84  // Handle the CDF Trailers
85  if (!processCDFTrailers(fed, nwords, word, word_end, crc, *counters)) {
86  continue;
87  }
88 
89  // Loop over the Blocks
90  if (!processBlocks(fed, word, word_end, crc, *counters, amc_payload)) {
91  continue;
92  }
93 
94  // Complete CRC check with trailer
95  if (calculate_crc_) {
96  word = word_end;
97  word_end = reinterpret_cast<std::uint64_t const *>(raw_data.data()) + nwords - 1;
98  for (; word < word_end; ++word) {
100  }
101  compute_crc16_64bit(crc, (*word & 0xffffffff0000ffff)); // trailer excluding crc
102  FEDTrailer trailer(reinterpret_cast<unsigned char const *>(word_end));
103  if ((unsigned int)(trailer.crc()) != crc) {
104  if (fill_counters_) {
106  }
107  edm::LogWarning("RPCAMCRawToDigi") << "FED Trailer CRC doesn't match for FED id " << fed;
108  continue;
109  }
110  }
111  }
112 
113  rpc_unpacker_->produce(event, setup, amc_payload);
114 
115  if (fill_counters_) {
116  event.put(std::move(counters));
117  }
118 }
119 
121  std::uint64_t const *&word,
122  std::uint64_t const *&word_end,
123  std::uint16_t &crc,
124  RPCAMCLinkCounters &counters) const {
125  bool more_headers(true);
126  for (; word < word_end && more_headers; ++word) {
127  if (calculate_crc_) {
128  compute_crc16_64bit(crc, *word);
129  }
130 
131  LogDebug("RPCAMCRawToDigi") << "CDF Header " << std::hex << *word << std::dec;
132  FEDHeader header(reinterpret_cast<unsigned char const *>(word));
133  if (!header.check()) {
134  if (fill_counters_) {
136  }
137  edm::LogWarning("RPCAMCRawToDigi") << "FED Header check failed for FED id " << fed;
138  ++word;
139  return false;
140  }
141  if (header.sourceID() != fed) {
142  if (fill_counters_) {
144  }
145  edm::LogWarning("RPCAMCRawToDigi") << "FED Header Source ID " << header.sourceID()
146  << " does not match requested FED id " << fed;
147  ++word;
148  return false;
149  }
150 
151  // moreHeaders() not used
152  // more_headers = header.moreHeaders();
153  more_headers = false;
154  }
155 
156  return !more_headers;
157 }
158 
160  unsigned int nwords,
161  std::uint64_t const *&word,
162  std::uint64_t const *&word_end,
163  std::uint16_t &crc,
164  RPCAMCLinkCounters &counters) const {
165  bool more_trailers(true);
166  for (--word_end; word_end > word && more_trailers; --word_end) {
167  FEDTrailer trailer(reinterpret_cast<unsigned char const *>(word_end));
168  LogDebug("RPCAMCRawToDigi") << "CDF Trailer " << std::hex << *word_end << std::dec << ", length "
169  << trailer.fragmentLength();
170  if (!trailer.check()) {
171  if (fill_counters_) {
173  }
174  edm::LogWarning("RPCAMCRawToDigi") << "FED Trailer check failed for FED id " << fed;
175  return false;
176  }
177  if (trailer.fragmentLength() != nwords) {
178  if (fill_counters_) {
180  }
181  edm::LogWarning("RPCAMCRawToDigi") << "FED Trailer length " << trailer.fragmentLength()
182  << " does not match actual data size " << nwords << " for FED id " << fed;
183  return false;
184  }
185 
186  // moreTrailers() not used
187  // more_trailers = trailer.moreTrailers();
188  more_trailers = false;
189  }
190 
191  ++word_end;
192 
193  return !more_trailers;
194 }
195 
197  std::uint64_t const *&word,
198  std::uint64_t const *word_end,
199  std::uint16_t &crc,
201  std::map<RPCAMCLink, rpcamc13::AMCPayload> &amc_payload) const {
202  while (word < word_end) {
204  if (calculate_crc_) {
205  compute_crc16_64bit(crc, *word);
206  }
207  ++word;
208 
209  unsigned int n_amc(header.getNAMC());
210  if (word + n_amc + 1 >= word_end) { // AMC Headers and AMC13 Trailer
211  if (fill_counters_) {
213  }
214  edm::LogWarning("RPCAMCRawToDigi") << "AMC13 Block can not be complete for FED " << fed;
215  word = word_end;
216  return false;
217  }
218 
219  std::uint64_t const *payload_word(word + n_amc);
220  std::uint64_t const *payload_word_end(payload_word);
221  for (unsigned int amc = 0; amc < n_amc; ++amc) {
222  rpcamc13::AMCHeader amc13_amc_header(*word);
223  if (calculate_crc_) {
224  compute_crc16_64bit(crc, *word);
225  }
226  ++word;
227 
228  unsigned int size_in_block(amc13_amc_header.getSizeInBlock());
229  if (size_in_block == 0) {
230  continue;
231  }
232  payload_word = payload_word_end;
233  payload_word_end += size_in_block;
234 
235  unsigned int amc_number(amc13_amc_header.getAMCNumber());
236  if (amc_number > (unsigned int)RPCAMCLink::max_amcnumber_) {
237  if (fill_counters_) {
239  }
240  edm::LogWarning("RPCAMCRawToDigi") << "Invalid AMC Number " << amc_number << " for FED " << fed;
241  continue;
242  }
243 
244  if (payload_word_end > word_end) {
245  if (fill_counters_) {
247  }
248  edm::LogWarning("RPCAMCRawToDigi")
249  << "AMC Block can not be complete for FED " << fed << " at AMC " << amc_number;
250  return false;
251  }
252 
253  rpcamc13::AMCPayload &payload(amc_payload[RPCAMCLink(fed, amc_number)]);
254 
255  if (amc13_amc_header.isFirstBlock()) {
256  payload.setAMCHeader(amc13_amc_header);
257  if (fill_counters_) {
258  counters.add(RPCAMCLinkEvents::amc_event_, RPCAMCLink(fed, amc_number));
259  }
260 
261  if (!amc13_amc_header.isValid()) {
262  if (fill_counters_) {
264  }
265  edm::LogWarning("RPCAMCRawToDigi")
266  << "AMC13 AMC Header is reporting an invalid "
267  << "Event Counter or Bunch Counter for FED " << fed << ", AMC " << amc_number;
268  payload.setValid(false);
269  }
270 
271  rpcamc::Header amc_amc_header(payload_word);
272  if (amc_number != amc_amc_header.getAMCNumber()) {
273  if (fill_counters_) {
275  }
276  edm::LogWarning("RPCAMCRawToDigi")
277  << "AMC Number inconsistent in AMC13 AMC Header vs AMC Header: " << amc_number << " vs "
278  << amc_amc_header.getAMCNumber();
279  payload.setValid(false);
280  }
281 
282  if (amc_amc_header.hasDataLength() && amc13_amc_header.hasTotalSize() &&
283  amc13_amc_header.getSize() != amc_amc_header.getDataLength()) {
284  if (fill_counters_) {
286  }
287  edm::LogWarning("RPCAMCRawToDigi")
288  << "AMC size inconsistent in AMC13 AMC Header vs AMC Header: " << amc13_amc_header.getSize() << " vs "
289  << amc_amc_header.getDataLength();
290  payload.setValid(false);
291  }
292  }
293 
294  if (amc13_amc_header.isLastBlock()) {
295  if (!amc13_amc_header.isFirstBlock()) {
296  edm::LogWarning("RPCAMCRawToDigi") << "Multiple blocks";
297  }
298  payload.getAMCHeader().setCRCOk(amc13_amc_header.isCRCOk());
299  payload.getAMCHeader().setLengthCorrect(amc13_amc_header.isLengthCorrect());
300 
301  if (!amc13_amc_header.isCRCOk()) {
302  if (fill_counters_) {
304  }
305  edm::LogWarning("RPCAMCRawToDigi")
306  << "AMC13 AMC Header is reporting a mismatched "
307  << "Event Counter or Bunch Counter for FED " << fed << ", AMC " << amc_number;
308  payload.setValid(false);
309  }
310 
311  if (!amc13_amc_header.isLengthCorrect()) {
312  if (fill_counters_) {
314  }
315  edm::LogWarning("RPCAMCRawToDigi") << "AMC13 AMC Header is reporting an incorrect length "
316  << "for FED " << fed << ", AMC " << amc_number;
317  payload.setValid(false);
318  }
319 
320  if (amc13_amc_header.hasTotalSize() &&
321  amc13_amc_header.getSize() != (payload.getData().size() + size_in_block)) {
322  if (fill_counters_) {
324  }
325  edm::LogWarning("RPCAMCRawToDigi") << "Size in AMC13 AMC Header doesn't match payload size "
326  << "for FED " << fed << ", AMC " << amc_number;
327  payload.setValid(false);
328  }
329 
330  if (!payload.getData().empty() && (payload.getData().size() + size_in_block) < 3) {
331  if (fill_counters_) {
333  }
334  edm::LogWarning("RPCAMCRawToDigi") << "Size in AMC13 AMC Header doesn't match payload size "
335  << "for FED " << fed << ", AMC " << amc_number;
336  payload.setValid(false);
337  }
338  }
339 
340  if (size_in_block > 0) {
341  payload.insert(payload_word, size_in_block);
342  }
343  }
344 
345  if (calculate_crc_) {
346  for (; word < payload_word_end; ++word) {
347  compute_crc16_64bit(crc, *word);
348  }
349  } else {
350  word = payload_word_end;
351  }
352 
353  if (calculate_crc_) {
354  compute_crc16_64bit(crc, *word);
355  }
356  ++word;
357  }
358  return true;
359 }
360 
static unsigned int const fed_amc13_amc_number_invalid_
static unsigned int const fed_trailer_crc_mismatch_
bool hasTotalSize() const
static unsigned int const amc_payload_incomplete_
static unsigned int const amc_size_mismatch_
static void compute_crc16_64bit(std::uint16_t &crc, std::uint64_t const &word)
static unsigned int const amc_event_
def create(alignables, pedeDump, additionalData, outputFile, config)
unsigned int getSizeInBlock() const
unsigned int getDataLength() const
bool isValid() const
static unsigned int const fed_header_check_fail_
RPCAMCRawToDigi(edm::ParameterSet const &config)
edm::EDGetTokenT< FEDRawDataCollection > raw_token_
size_t size() const
Lenght of the data buffer in bytes.
Definition: FEDRawData.h:45
Definition: config.py:1
unsigned int getAMCNumber() const
static unsigned int const amc_amc13_evc_bc_invalid_
void produce(edm::Event &event, edm::EventSetup const &setup) override
static unsigned int const fed_trailer_length_mismatch_
bool isLastBlock() const
bool processCDFTrailers(int fed, unsigned int nwords, std::uint64_t const *&word, std::uint64_t const *&word_end, std::uint16_t &crc, RPCAMCLinkCounters &counters) const
uint32_t fragmentLength() const
The length of the event fragment counted in 64-bit words including header and trailer.
Definition: FEDTrailer.cc:13
uint64_t word
unsigned int getSize() const
static void fillDescription(edm::ParameterSetDescription &desc)
TupleMultiplicity< TrackerTraits > const HitToTuple< TrackerTraits > const cms::cuda::AtomicPairCounter GPUCACellT< TrackerTraits > const *__restrict__ uint32_t const *__restrict__ CellNeighborsVector< TrackerTraits > const CellTracksVector< TrackerTraits > const OuterHitOfCell< TrackerTraits > const int32_t uint32_t Counters * counters
double amc
Definition: hdecay.h:20
static unsigned int const amc_amc13_length_incorrect_
bool isLengthCorrect() const
uint16_t crc() const
Cyclic Redundancy Code of the event fragment including header and trailer.
Definition: FEDTrailer.cc:15
bool hasDataLength() const
#define DEFINE_FWK_MODULE(type)
Definition: MakerMacros.h:16
static void fillDescriptions(edm::ConfigurationDescriptions &descs)
static unsigned int const amc_amc13_size_inconsistent_
bool processBlocks(int fed, std::uint64_t const *&word, std::uint64_t const *word_end, std::uint16_t &crc, RPCAMCLinkCounters &counters, std::map< RPCAMCLink, rpcamc13::AMCPayload > &amc_payload) const
~RPCAMCRawToDigi() override
static unsigned int const fed_header_id_mismatch_
static unsigned int const amc_number_mismatch_
const FEDRawData & FEDData(int fedid) const
retrieve data for fed
static unsigned int const fed_amc13_block_incomplete_
static unsigned int const fed_event_
bool isFirstBlock() const
unsigned long long uint64_t
Definition: Time.h:13
bool isCRCOk() const
void add(std::string const &label, ParameterSetDescription const &psetDescription)
static unsigned int const amc_amc13_block_incomplete_
static unsigned int const amc_amc13_crc_mismatch_
HLT enums.
const unsigned char * data() const
Return a const pointer to the beginning of the data buffer.
Definition: FEDRawData.cc:24
#define get
Log< level::Warning, false > LogWarning
Definition: AMCSpec.h:8
bool check() const
Check that the trailer is OK.
Definition: FEDTrailer.cc:45
bool processCDFHeaders(int fed, std::uint64_t const *&word, std::uint64_t const *&word_end, std::uint16_t &crc, RPCAMCLinkCounters &counters) const
void beginRun(edm::Run const &run, edm::EventSetup const &setup) override
std::unique_ptr< RPCAMCUnpacker > rpc_unpacker_
static unsigned int const fed_trailer_check_fail_
def move(src, dest)
Definition: eostools.py:511
Definition: event.py:1
Definition: Run.h:45
unsigned int getAMCNumber() const
#define LogDebug(id)