CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
AMCSpec.cc
Go to the documentation of this file.
1 #include <iomanip>
2 
5 
7 
8 #define EDM_ML_DEBUG 1
9 
10 namespace amc {
11  BlockHeader::BlockHeader(unsigned int amc_no, unsigned int board_id, unsigned int size, unsigned int block)
12  {
13  // Determine size
14  unsigned int max_block_no = 0;
15  if (size >= 0x13ff)
16  max_block_no = (size - 1023) / 4096;
17 
18  if (block != max_block_no)
19  size = split_block_size;
20  else if (block != 0)
21  size -= split_block_size * max_block_no;
22 
23  data_ =
24  (static_cast<uint64_t>(size & Size_mask) << Size_shift) |
25  (static_cast<uint64_t>(block & BlkNo_mask) << BlkNo_shift) |
26  (static_cast<uint64_t>(amc_no & AmcNo_mask) << AmcNo_shift) |
27  (static_cast<uint64_t>(board_id & BoardID_mask) << BoardID_shift) |
28  (1llu << Enabled_bit_shift) |
29  (1llu << Present_bit_shift);
30 
31  if (block == getBlocks() - 1) {
32  // Last block
33  data_ |=
34  (1llu << CRC_bit_shift) |
35  (1llu << Valid_bit_shift) |
36  (1llu << Length_bit_shift);
37  }
38 
39  if (block == 0 && getBlocks() == 1) {
40  // Bits already zeroed - only one block
41  } else if (block == 0) {
42  // First of many blocks
43  data_ |= 1llu << More_bit_shift;
44  } else if (block == getBlocks() - 1) {
45  // Last of many blocks
46  data_ |= 1llu << Segmented_bit_shift;
47  } else {
48  // Intermediate of many blocks
49  data_ |= (1llu << More_bit_shift) | (1llu << Segmented_bit_shift);
50  }
51  }
52 
53  unsigned int
55  {
56  // The first block of a segmented event has a size of 1023, all
57  // following have a max size of 4096. Segmentation only happens
58  // for AMC payloads >= 0x13ff 64 bit words.
59  unsigned int size = getSize();
60  if (size >= 0x13ff)
61  return (size - 1023) / 4096 + 1;
62  return 1;
63  }
64 
65  unsigned int
67  {
68  // More and not Segmented means the first of multiple blocks. For
69  // these, getSize() returns the total size of the AMC packet, not the
70  // size of the first block.
71  if (getMore() && !getSegmented())
72  return split_block_size;
73  return getSize();
74  }
75 
76  Header::Header(unsigned int amc_no, unsigned int lv1_id, unsigned int bx_id, unsigned int size,
77  unsigned int or_n, unsigned int board_id, unsigned int user) :
78  data0_(
79  (uint64_t(amc_no & AmcNo_mask) << AmcNo_shift) |
80  (uint64_t(lv1_id & LV1ID_mask) << LV1ID_shift) |
81  (uint64_t(bx_id & BX_mask) << BX_shift) |
82  (uint64_t(size & Size_mask) << Size_shift)
83  ),
84  data1_(
85  (uint64_t(or_n & OrN_mask) << OrN_shift) |
86  (uint64_t(board_id & BoardID_mask) << BoardID_shift) |
87  (uint64_t(user & User_mask) << User_shift)
88  )
89  {
90  }
91 
92  Trailer::Trailer(unsigned int crc, unsigned int lv1_id, unsigned int size) :
93  data_(
94  (uint64_t(crc & CRC_mask) << CRC_shift) |
95  (uint64_t(lv1_id & LV1ID_mask) << LV1ID_shift) |
96  (uint64_t(size & Size_mask) << Size_shift)
97  )
98  {
99  }
100 
101  bool
102  Trailer::check(unsigned int crc, unsigned int lv1_id, unsigned int size) const
103  {
104  if (crc != getCRC() || size != getSize() || (lv1_id & LV1ID_mask) != getLV1ID()) {
105  edm::LogWarning("L1T")
106  << "Found AMC trailer with:"
107  << "\n\tLV1 ID " << getLV1ID() << ", size " << getSize()
108  << ", CRC " << std::hex << std::setw(8) << std::setfill('0') << getCRC() << std::dec
109  << "\nBut expected:"
110  << "\n\tLV1 ID " << (lv1_id & LV1ID_mask) << ", size " << size
111  << ", CRC " << std::hex << std::setw(8) << std::setfill('0') << crc;
112  return false;
113  }
114  return true;
115  }
116 
117  void
119  {
120  std::string dstring(reinterpret_cast<const char*>(start), reinterpret_cast<const char*>(end) + 4);
121  auto crc = cms::CRC32Calculator(dstring).checksum();
122 
123  *end = ((*end) & ~(uint64_t(CRC_mask) << CRC_shift)) | (static_cast<uint64_t>(crc & CRC_mask) << CRC_shift);
124  }
125 
126  Packet::Packet(unsigned int amc, unsigned int board, unsigned int lv1id, unsigned int orbit, unsigned int bx, const std::vector<uint64_t>& load) :
127  block_header_(amc, board, load.size() + 3), // add 3 words for header (2) and trailer (1)
128  header_(amc, lv1id, bx, load.size() + 3, orbit, board, 0),
129  trailer_(0, lv1id, load.size() + 3)
130  {
131  auto hdata = header_.raw();
132  payload_.reserve(load.size() + 3);
133  payload_.insert(payload_.end(), hdata.begin(), hdata.end());
134  payload_.insert(payload_.end(), load.begin(), load.end());
135  payload_.insert(payload_.end(), trailer_.raw());
136 
137  auto ptr = payload_.data();
138  Trailer::writeCRC(ptr, ptr + payload_.size() - 1);
139  }
140 
141  void
142  Packet::addPayload(const uint64_t * data, unsigned int size)
143  {
144  payload_.insert(payload_.end(), data, data + size);
145  }
146 
147  void
148  Packet::finalize(unsigned int lv1, unsigned int bx, bool legacy_mc)
149  {
150  if (legacy_mc) {
152 
153  payload_.insert(payload_.begin(), {0, 0});
154  payload_.insert(payload_.end(), {0});
155  } else {
156  header_ = Header(payload_.data());
157  trailer_ = Trailer(&payload_.back());
158 
159  std::string check(reinterpret_cast<const char*>(payload_.data()), payload_.size() * 8 - 4);
160  auto crc = cms::CRC32Calculator(check).checksum();
161 
162  trailer_.check(crc, lv1, header_.getSize());
163  }
164  }
165 
166  std::vector<uint64_t>
167  Packet::block(unsigned int id) const
168  {
169  if (id == 0 and id == block_header_.getBlocks() - 1) {
170  return payload_;
171  } else if (id == block_header_.getBlocks() - 1) {
172  return std::vector<uint64_t>(payload_.begin() + id * split_block_size, payload_.end());
173  } else {
174  return std::vector<uint64_t>(payload_.begin() + id * split_block_size, payload_.begin() + (id + 1) * split_block_size);
175  }
176  }
177 
178  std::unique_ptr<uint64_t[]>
180  {
181  // Remove 3 words: 2 for the header, 1 for the trailer
182  std::unique_ptr<uint64_t[]> res(new uint64_t[payload_.size() - 3]);
183  for (unsigned int i = 0; i < payload_.size() - 3; ++i)
184  res.get()[i] = payload_[i + 2];
185  return res;
186  }
187 }
unsigned int getLV1ID() const
Definition: AMCSpec.h:104
int i
Definition: DBlmapReader.cc:9
static const unsigned int CRC_mask
Definition: AMCSpec.h:118
static const unsigned int BoardID_mask
Definition: AMCSpec.h:44
tuple start
Check for commandline option errors.
Definition: dqm_diff.py:58
static const unsigned int Size_shift
Definition: AMCSpec.h:37
static const unsigned int CRC_bit_shift
Definition: AMCSpec.h:52
unsigned int getSize() const
Definition: AMCSpec.h:105
static void writeCRC(const uint64_t *start, uint64_t *end)
Definition: AMCSpec.cc:118
unsigned int getCRC() const
Definition: AMCSpec.h:103
BlockHeader block_header_
Definition: AMCSpec.h:143
uint64_t raw() const
Definition: AMCSpec.h:107
unsigned int getMore() const
Definition: AMCSpec.h:31
std::vector< uint64_t > block(unsigned int id) const
Definition: AMCSpec.cc:167
unsigned int getAMCNumber() const
Definition: AMCSpec.h:28
static const unsigned int CRC_shift
Definition: AMCSpec.h:117
static const unsigned int Segmented_bit_shift
Definition: AMCSpec.h:48
static const unsigned int Present_bit_shift
Definition: AMCSpec.h:50
static const unsigned int AmcNo_shift
Definition: AMCSpec.h:41
static const unsigned int BlkNo_shift
Definition: AMCSpec.h:39
void addPayload(const uint64_t *, unsigned int)
Definition: AMCSpec.cc:142
static const unsigned int Valid_bit_shift
Definition: AMCSpec.h:51
bool check(const std::string &)
double amc
Definition: hdecay.h:20
std::vector< uint64_t > raw() const
Definition: AMCSpec.h:74
static const unsigned int BlkNo_mask
Definition: AMCSpec.h:40
unsigned int getBlocks() const
Definition: AMCSpec.cc:54
static const unsigned int Size_mask
Definition: AMCSpec.h:38
static const unsigned int split_block_size
Definition: AMCSpec.h:9
#define end
Definition: vmac.h:37
static const unsigned int More_bit_shift
Definition: AMCSpec.h:47
Trailer trailer_
Definition: AMCSpec.h:148
unsigned int getBlockSize() const
Definition: AMCSpec.cc:66
uint64_t data_
Definition: AMCSpec.h:54
static const unsigned int AmcNo_mask
Definition: AMCSpec.h:42
unsigned int size() const
Definition: AMCSpec.h:143
static const unsigned int LV1ID_mask
Definition: AMCSpec.h:116
static const unsigned int BoardID_shift
Definition: AMCSpec.h:43
unsigned long long uint64_t
Definition: Time.h:15
unsigned int getSize() const
Definition: AMCSpec.h:30
unsigned int getSize() const
Definition: AMCSpec.h:71
unsigned int getBoardID() const
Definition: AMCSpec.h:29
Header header_
Definition: AMCSpec.h:147
static const unsigned int Length_bit_shift
Definition: AMCSpec.h:46
void load(int perCUT=90)
Definition: getMaxPt.h:59
char data[epos_bytes_allocation]
Definition: EPOS_Wrapper.h:82
std::unique_ptr< uint64_t[]> data()
Definition: AMCSpec.cc:179
unsigned int getSegmented() const
Definition: AMCSpec.h:32
static const unsigned int Enabled_bit_shift
Definition: AMCSpec.h:49
std::uint32_t checksum()
void finalize(unsigned int lv1, unsigned int bx, bool legacy_mc=false)
Definition: AMCSpec.cc:148
Packet(const uint64_t *d)
Definition: AMCSpec.h:125
tuple size
Write out results.
bool check(unsigned int crc, unsigned int lv1_id, unsigned int size) const
Definition: AMCSpec.cc:102
std::vector< uint64_t > payload_
Definition: AMCSpec.h:150