$treeview $search $mathjax $extrastylesheet
otsdaq
v2_03_00
$projectbrief
|
$projectbrief
|
$searchbox |
00001 #ifndef artdaq_ots_Overlays_UDPFragmentWriter_hh 00002 #define artdaq_ots_Overlays_UDPFragmentWriter_hh 00003 00005 // UDPFragmentWriter 00006 // 00007 // Class derived from UDPFragment which allows writes to the data (for 00008 // simulation purposes). Note that for this reason it contains 00009 // non-const members which hide the const members in its parent class, 00010 // UDPFragment, including its reference to the artdaq::Fragment 00011 // object, artdaq_Fragment_, as well as its functions pointing to the 00012 // beginning and end of ADC values in the fragment, dataBegin() and 00013 // dataEnd() 00014 // 00016 00017 #include "artdaq-core/Data/Fragment.hh" 00018 #include "artdaq-ots/Overlays/UDPFragment.hh" 00019 00020 #include <iostream> 00021 00022 namespace ots 00023 { 00024 class UDPFragmentWriter; 00025 } 00026 00027 class ots::UDPFragmentWriter : public ots::UDPFragment 00028 { 00029 public: 00030 UDPFragmentWriter(artdaq::Fragment& f); 00031 00032 // These functions form overload sets with const functions from 00033 // ots::UDPFragment 00034 00035 uint8_t* dataBegin(); 00036 uint8_t* dataEnd(); 00037 00038 // We'll need to hide the const version of header in UDPFragment in 00039 // order to be able to perform writes 00040 00041 Header* header_() 00042 { 00043 assert(artdaq_Fragment_.dataSizeBytes() >= sizeof(Header)); 00044 return reinterpret_cast<Header*>(artdaq_Fragment_.dataBeginBytes()); 00045 } 00046 00047 void set_hdr_type(Header::data_type_t dataType) { header_()->type = dataType & 0xF; } 00048 00049 void resize(size_t nBytes); 00050 00051 private: 00052 size_t calc_event_size_words_(size_t nBytes); 00053 00054 static size_t bytes_to_words_(size_t nBytes); 00055 00056 // Note that this non-const reference hides the const reference in the base class 00057 artdaq::Fragment& artdaq_Fragment_; 00058 }; 00059 00060 // The constructor will expect the artdaq::Fragment object it's been 00061 // passed to contain the artdaq::Fragment header + the 00062 // UDPFragment::Metadata object, otherwise it throws 00063 00064 ots::UDPFragmentWriter::UDPFragmentWriter(artdaq::Fragment& f) 00065 : UDPFragment(f), artdaq_Fragment_(f) 00066 { 00067 if(!f.hasMetadata() || f.dataSizeBytes() > 0) 00068 { 00069 throw cet::exception( 00070 "Error in UDPFragmentWriter: Raw artdaq::Fragment object does not appear to " 00071 "consist of (and only of) its own header + the UDPFragment::Metadata object"); 00072 } 00073 00074 // Allocate space for the header 00075 artdaq_Fragment_.resizeBytes(sizeof(Header)); 00076 } 00077 00078 inline uint8_t* ots::UDPFragmentWriter::dataBegin() 00079 { 00080 // Make sure there's data past the UDPFragment header 00081 assert(artdaq_Fragment_.dataSizeBytes() >= 00082 sizeof(Header) + sizeof(artdaq::Fragment::value_type)); 00083 return reinterpret_cast<uint8_t*>(header_() + 1); 00084 } 00085 00086 inline uint8_t* ots::UDPFragmentWriter::dataEnd() 00087 { 00088 return dataBegin() + udp_data_words(); 00089 } 00090 00091 inline void ots::UDPFragmentWriter::resize(size_t nBytes) 00092 { 00093 artdaq_Fragment_.resizeBytes(sizeof(Header::data_t) * calc_event_size_words_(nBytes)); 00094 header_()->event_size = calc_event_size_words_(nBytes); 00095 } 00096 00097 inline size_t ots::UDPFragmentWriter::calc_event_size_words_(size_t nBytes) 00098 { 00099 return bytes_to_words_(nBytes) + hdr_size_words(); 00100 } 00101 00102 inline size_t ots::UDPFragmentWriter::bytes_to_words_(size_t nBytes) 00103 { 00104 auto mod(nBytes % bytes_per_word_()); 00105 return (mod == 0) ? nBytes / bytes_per_word_() : nBytes / bytes_per_word_() + 1; 00106 } 00107 00108 #endif /* artdaq_demo_Overlays_UDPFragmentWriter_hh */