File indexing completed on 2025-06-28 06:19:01
0001 #ifndef DataFormats_FEDRawData_SLinkRocketHeaders_h
0002 #define DataFormats_FEDRawData_SLinkRocketHeaders_h
0003
0004 #include "FWCore/Utilities/interface/Exception.h"
0005
0006
0007 #include <span>
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017 constexpr uint32_t SLR_MAX_EVENT_LEN = (1 << 20) - 1;
0018 constexpr uint32_t SLR_WORD_NUM_BYTES_SHIFT = 4;
0019
0020
0021
0022
0023 constexpr uint8_t SLR_BOE = 0x55;
0024 constexpr uint8_t SLR_EOE = 0xaa;
0025
0026
0027 class SLinkRocketHeader_version {
0028 public:
0029 SLinkRocketHeader_version() {}
0030 uint8_t version() const { return version_; }
0031 bool verifyMarker() const { return boe_ == SLR_BOE; }
0032
0033 private:
0034 uint32_t source_id_;
0035 uint16_t l1a_types_;
0036 uint8_t phys_type_;
0037 uint8_t emu_status_ : 2, res1_ : 6;
0038 uint64_t event_id_ : 44, res2_ : 8, version_ : 4, boe_ : 8;
0039 };
0040
0041 class SLinkRocketHeader_v3 {
0042 public:
0043 SLinkRocketHeader_v3(uint32_t source_id, uint16_t l1a_types, uint8_t l1a_phys, uint8_t emu_status, uint64_t event_id)
0044 : source_id_(source_id),
0045 l1a_types_(l1a_types),
0046 phys_type_(l1a_phys),
0047 emu_status_(emu_status),
0048 event_id_(event_id) {}
0049
0050 uint32_t sourceID() const { return source_id_; }
0051 uint16_t l1aTypes() const { return l1a_types_; }
0052 uint8_t l1aPhysType() const { return phys_type_; }
0053 uint8_t emuStatus() const { return emu_status_; }
0054 uint64_t globalEventID() const { return event_id_; }
0055 uint8_t version() const { return version_; }
0056 bool verifyMarker() const { return boe_ == SLR_BOE; }
0057
0058 private:
0059 uint32_t source_id_;
0060 uint16_t l1a_types_;
0061 uint8_t phys_type_;
0062 uint8_t emu_status_ : 2, res1_ : 6;
0063 uint64_t event_id_ : 44, res2_ : 8, version_ : 4 = 3, boe_ : 8 = SLR_BOE;
0064 };
0065
0066 class SLinkRocketTrailer_v3 {
0067 public:
0068 SLinkRocketTrailer_v3(
0069 uint16_t status, uint16_t crc, uint32_t orbit_id, uint16_t bx_id, uint32_t evtlen_word_count, uint16_t daq_crc)
0070 : crc_(crc), orbit_id_(orbit_id), bx_id_(bx_id), event_length_wcount_(evtlen_word_count), daq_crc_(daq_crc) {
0071 status_.all_ = status;
0072 }
0073
0074 uint16_t status() const { return status_.all_; }
0075 uint16_t crc() const { return crc_; }
0076 uint32_t orbitID() const { return orbit_id_; }
0077 uint16_t bxID() const { return bx_id_; }
0078 uint32_t eventLenBytes() const { return uint32_t(event_length_wcount_) << SLR_WORD_NUM_BYTES_SHIFT; }
0079 uint16_t daqCRC() const { return daq_crc_; }
0080 bool verifyMarker() const { return eoe_ == SLR_EOE; }
0081
0082 private:
0083 union {
0084 struct {
0085 uint16_t fed_crc_error_ : 1,
0086 slink_crc_error_ : 1,
0087 source_id_error_ : 1,
0088 sync_lost_error_ : 1,
0089 fragment_cut_ : 1,
0090 res_ : 11;
0091 } bits_;
0092 uint16_t all_;
0093 } status_;
0094 uint16_t crc_;
0095 uint32_t orbit_id_;
0096 uint32_t bx_id_ : 12,
0097 event_length_wcount_ : 20;
0098 uint32_t reserved_ : 8, daq_crc_ : 16,
0099 eoe_ : 8 = SLR_EOE;
0100 };
0101
0102
0103
0104
0105
0106 class SLinkRocketHeaderView {
0107 public:
0108 virtual ~SLinkRocketHeaderView() = default;
0109 virtual uint32_t sourceID() const = 0;
0110 virtual uint16_t l1aTypes() const = 0;
0111 virtual uint8_t l1aPhysType() const = 0;
0112 virtual uint8_t emuStatus() const = 0;
0113 virtual uint64_t globalEventID() const = 0;
0114 virtual uint8_t version() const = 0;
0115 virtual bool verifyMarker() const = 0;
0116 };
0117
0118
0119
0120
0121
0122 class SLinkRocketHeaderView_v3 : public SLinkRocketHeaderView {
0123 public:
0124 SLinkRocketHeaderView_v3(const void* header) : header_(static_cast<const SLinkRocketHeader_v3*>(header)) {}
0125
0126 uint32_t sourceID() const override { return header_->sourceID(); }
0127 uint16_t l1aTypes() const override { return header_->l1aTypes(); }
0128 uint8_t l1aPhysType() const override { return header_->l1aPhysType(); }
0129 uint8_t emuStatus() const override { return header_->emuStatus(); }
0130 uint64_t globalEventID() const override { return header_->globalEventID(); }
0131 uint8_t version() const override { return header_->version(); }
0132 bool verifyMarker() const override { return header_->verifyMarker(); }
0133
0134 private:
0135 const SLinkRocketHeader_v3* header_;
0136 };
0137
0138 static inline std::unique_ptr<SLinkRocketHeaderView> makeSLinkRocketHeaderView(const void* buf) {
0139 auto version = static_cast<const SLinkRocketHeader_version*>(buf)->version();
0140 if (version == 3)
0141 return std::unique_ptr<SLinkRocketHeaderView>(
0142 static_cast<SLinkRocketHeaderView*>(new SLinkRocketHeaderView_v3(buf)));
0143 throw cms::Exception("SLinkRocketHeaderView::makeView")
0144 << "unknown SLinkRocketHeader version: " << (unsigned int)version;
0145 }
0146
0147 static inline std::unique_ptr<SLinkRocketHeaderView> makeSLinkRocketHeaderView(std::span<const unsigned char> const& s) {
0148 if (s.size() < sizeof(SLinkRocketHeader_version))
0149 throw cms::Exception("SLinkRocketHeaderView::makeView")
0150 << "size is smaller than SLink header version fields: " << s.size();
0151 auto version = static_cast<const SLinkRocketHeader_version*>(static_cast<const void*>(&s[0]))->version();
0152 if (version == 3 && s.size() != sizeof(SLinkRocketHeader_v3))
0153 throw cms::Exception("SLinkRocketHeaderView::makeView") << "SLinkRocketHeader v3 size mismatch: got " << s.size()
0154 << " expected:" << sizeof(SLinkRocketHeader_v3) << " bytes";
0155
0156 return makeSLinkRocketHeaderView(static_cast<const void*>(&s[0]));
0157 }
0158
0159
0160
0161
0162
0163 class SLinkRocketTrailerView {
0164 public:
0165 virtual ~SLinkRocketTrailerView() = default;
0166 virtual uint16_t status() const = 0;
0167 virtual uint16_t crc() const = 0;
0168 virtual uint32_t orbitID() const = 0;
0169 virtual uint16_t bxID() const = 0;
0170 virtual uint32_t eventLenBytes() const = 0;
0171 virtual uint16_t daqCRC() const = 0;
0172 virtual bool verifyMarker() const = 0;
0173 };
0174
0175
0176
0177
0178
0179 class SLinkRocketTrailerView_v3 : public SLinkRocketTrailerView {
0180 public:
0181 SLinkRocketTrailerView_v3(const void* trailer) : trailer_(static_cast<const SLinkRocketTrailer_v3*>(trailer)) {}
0182 uint16_t status() const override { return trailer_->status(); }
0183 uint16_t crc() const override { return trailer_->crc(); }
0184 uint32_t orbitID() const override { return trailer_->orbitID(); }
0185 uint16_t bxID() const override { return trailer_->bxID(); }
0186 uint32_t eventLenBytes() const override { return trailer_->eventLenBytes(); }
0187 uint16_t daqCRC() const override { return trailer_->daqCRC(); }
0188 bool verifyMarker() const override { return trailer_->verifyMarker(); }
0189
0190 private:
0191 const SLinkRocketTrailer_v3* trailer_;
0192 };
0193
0194 static inline std::unique_ptr<SLinkRocketTrailerView> makeSLinkRocketTrailerView(const void* buf, uint8_t version) {
0195 if (version == 3)
0196 return std::unique_ptr<SLinkRocketTrailerView>(
0197 static_cast<SLinkRocketTrailerView*>(new SLinkRocketTrailerView_v3(buf)));
0198 throw cms::Exception("SLinkRocketTrailerView::makeView")
0199 << "unknown SLinkRocketHeader version: " << (unsigned int)version;
0200 }
0201
0202 static inline std::unique_ptr<SLinkRocketTrailerView> makeSLinkRocketTrailerView(
0203 std::span<const unsigned char> const& s, uint8_t version) {
0204 if (version == 3 && s.size() < sizeof(SLinkRocketTrailer_v3))
0205 throw cms::Exception("SLinkRocketTrailerView::makeView")
0206 << "SLinkRocketTrailer v3 size mismatch: got " << s.size() << " expected " << sizeof(SLinkRocketTrailer_v3)
0207 << " bytes";
0208 return makeSLinkRocketTrailerView(static_cast<const void*>(&s[0]), version);
0209 }
0210 #endif