LCOV - code coverage report
Current view: top level - detdataformats/unittest - DAQEthHeader_test.cxx (source / functions) Coverage Total Hit
Test: code.result Lines: 100.0 % 121 121
Test Date: 2026-05-24 15:29:04 Functions: 100.0 % 16 16

            Line data    Source code
       1              : /**
       2              :  * @file DAQEthHeader_test.cxx DAQEthHeader class Unit Tests
       3              :  *
       4              :  * This is part of the DUNE DAQ Application Framework, copyright 2022.
       5              :  * Licensing/copyright details are in the COPYING file that you should have
       6              :  * received with this code.
       7              :  */
       8              : 
       9              : #include "detdataformats/DAQEthHeader.hpp"
      10              : 
      11              : #define BOOST_TEST_MODULE DAQEthHeader_test // NOLINT
      12              : 
      13              : #include "boost/test/unit_test.hpp"
      14              : 
      15              : #include <cstring>
      16              : #include <limits>
      17              : #include <sstream>
      18              : #include <string>
      19              : #include <vector>
      20              : 
      21              : #pragma GCC diagnostic ignored "-Woverflow" // intentional overflows are performed as part of testing
      22              : 
      23              : using namespace dunedaq::detdataformats;
      24              : 
      25              : // Unit tests for a data formats library can expect to work with a lot of unsigned integers
      26              : // NOLINTBEGIN(build/unsigned)
      27              : 
      28              : namespace {
      29              : using word_t = DAQEthHeader::word_t;
      30              : 
      31              : DAQEthHeader
      32           11 : make_header(word_t version,
      33              :             word_t det_id,
      34              :             word_t crate_id,
      35              :             word_t slot_id,
      36              :             word_t stream_id,
      37              :             word_t reserved,
      38              :             word_t seq_id,
      39              :             word_t block_length,
      40              :             word_t timestamp)
      41              : {
      42           11 :   DAQEthHeader header;
      43           11 :   header.version = version;
      44           11 :   header.det_id = det_id;
      45           11 :   header.crate_id = crate_id;
      46           11 :   header.slot_id = slot_id;
      47           11 :   header.stream_id = stream_id;
      48           11 :   header.reserved = reserved;
      49           11 :   header.seq_id = seq_id;
      50           11 :   header.block_length = block_length;
      51           11 :   header.timestamp = timestamp;
      52           11 :   return header;
      53              : }
      54              : 
      55              : DAQEthHeader
      56            1 : header_from_stream_output(const std::string& output)
      57              : {
      58            1 :   std::istringstream iss(output);
      59              : 
      60            1 :   std::string version_token;
      61            1 :   std::string det_id_token;
      62            1 :   std::string crate_id_token;
      63            1 :   std::string slot_id_token;
      64            1 :   std::string stream_id_token;
      65            1 :   std::string sequence_label;
      66            1 :   unsigned int sequence_value{};
      67            1 :   std::string block_label;
      68            1 :   std::string block_length_label;
      69            1 :   unsigned int block_length_value{};
      70            1 :   std::string timestamp_label;
      71            1 :   uint64_t timestamp_value{};
      72              : 
      73            1 :   iss >> version_token >> det_id_token >> crate_id_token >> slot_id_token >> stream_id_token >> sequence_label >>
      74            1 :     sequence_value >> block_label >> block_length_label >> block_length_value >> timestamp_label >> timestamp_value;
      75              : 
      76            1 :   BOOST_REQUIRE_EQUAL(sequence_label, "SequenceID:");
      77            1 :   BOOST_REQUIRE_EQUAL(block_label, "Block");
      78            1 :   BOOST_REQUIRE_EQUAL(block_length_label, "length:");
      79            1 :   BOOST_REQUIRE_EQUAL(timestamp_label, "Timestamp:");
      80              : 
      81            2 :   return make_header(static_cast<word_t>(std::stoull(version_token.substr(std::string("Version:").size()))),
      82            2 :                      static_cast<word_t>(std::stoull(det_id_token.substr(std::string("DetID:").size()))),
      83            2 :                      static_cast<word_t>(std::stoull(crate_id_token.substr(std::string("CrateID:").size()))),
      84            2 :                      static_cast<word_t>(std::stoull(slot_id_token.substr(std::string("SlotID:").size()))),
      85            2 :                      static_cast<word_t>(std::stoull(stream_id_token.substr(std::string("StreamID:").size()))),
      86              :                      0,
      87              :                      static_cast<word_t>(sequence_value),
      88              :                      static_cast<word_t>(block_length_value),
      89            1 :                      static_cast<word_t>(timestamp_value));
      90            1 : }
      91              : } // namespace ""
      92              : 
      93              : BOOST_AUTO_TEST_SUITE(DAQEthHeader_test)
      94              : 
      95            2 : BOOST_AUTO_TEST_CASE(DefaultConstruction)
      96              : {
      97            1 :   DAQEthHeader header;
      98              : 
      99            1 :   BOOST_REQUIRE_EQUAL(header.timestamp, std::numeric_limits<word_t>::max());
     100            1 :   BOOST_REQUIRE_EQUAL(header.get_timestamp(), std::numeric_limits<uint64_t>::max());
     101            1 : }
     102              : 
     103            2 : BOOST_AUTO_TEST_CASE(TimestampAccess)
     104              : {
     105            1 :   const DAQEthHeader header = make_header(0, 0, 0, 0, 0, 0, 0, 0, 0x0123456789ABCDEFULL);
     106              : 
     107            1 :   BOOST_REQUIRE_EQUAL(header.get_timestamp(), 0x0123456789ABCDEFULL);
     108            1 : }
     109              : 
     110            2 : BOOST_AUTO_TEST_CASE(TimestampRoundTripFromGetTimestamp)
     111              : {
     112            1 :   const std::vector<word_t> values = {
     113              :     0x0000000000000000ULL, 0x0000000000000001ULL, 0x0123456789ABCDEFULL, 0xFEDCBA9876543210ULL, 0xFFFFFFFFFFFFFFFFULL
     114            1 :   };
     115              : 
     116            6 :   for (const auto& value : values) {
     117            5 :     const DAQEthHeader original = make_header(0, 0, 0, 0, 0, 0, 0, 0, value);
     118            5 :     const uint64_t timestamp = original.get_timestamp();
     119              : 
     120            5 :     BOOST_REQUIRE_EQUAL(static_cast<word_t>(timestamp), original.timestamp);
     121              :   }
     122            1 : }
     123              : 
     124            2 : BOOST_AUTO_TEST_CASE(BitfieldUpperBounds)
     125              : {
     126            1 :   const DAQEthHeader header = make_header(63, 63, 1023, 15, 255, 63, 4095, 4095, 0);
     127              : 
     128            1 :   BOOST_REQUIRE_EQUAL(header.version, 63);
     129            1 :   BOOST_REQUIRE_EQUAL(header.det_id, 63);
     130            1 :   BOOST_REQUIRE_EQUAL(header.crate_id, 1023);
     131            1 :   BOOST_REQUIRE_EQUAL(header.slot_id, 15);
     132            1 :   BOOST_REQUIRE_EQUAL(header.stream_id, 255);
     133            1 :   BOOST_REQUIRE_EQUAL(header.reserved, 63);
     134            1 :   BOOST_REQUIRE_EQUAL(header.seq_id, 4095);
     135            1 :   BOOST_REQUIRE_EQUAL(header.block_length, 4095);
     136            1 : }
     137              : 
     138            2 : BOOST_AUTO_TEST_CASE(BitfieldMasking)
     139              : {
     140            1 :   DAQEthHeader header = make_header(0, 0, 0, 0, 0, 0, 0, 0, 0);
     141              : 
     142            1 :   header.version = 99;        // NOLINT 99 & 0x3F = 35
     143            1 :   header.det_id = 127;        // NOLINT 127 & 0x3F = 63
     144            1 :   header.crate_id = 2048;     // NOLINT 2048 & 0x3FF = 0
     145            1 :   header.slot_id = 31;        // NOLINT 31 & 0x0F = 15
     146            1 :   header.stream_id = 511;     // NOLINT 511 & 0xFF = 255
     147            1 :   header.reserved = 127;      // NOLINT 127 & 0x3F = 63
     148            1 :   header.seq_id = 5000;       // NOLINT 5000 & 0xFFF = 904
     149            1 :   header.block_length = 5000; // NOLINT 5000 & 0xFFF = 904
     150              : 
     151            1 :   BOOST_REQUIRE_EQUAL(header.version, 35);
     152            1 :   BOOST_REQUIRE_EQUAL(header.det_id, 63);
     153            1 :   BOOST_REQUIRE_EQUAL(header.crate_id, 0);
     154            1 :   BOOST_REQUIRE_EQUAL(header.slot_id, 15);
     155            1 :   BOOST_REQUIRE_EQUAL(header.stream_id, 255);
     156            1 :   BOOST_REQUIRE_EQUAL(header.reserved, 63);
     157            1 :   BOOST_REQUIRE_EQUAL(header.seq_id, 904);
     158            1 :   BOOST_REQUIRE_EQUAL(header.block_length, 904);
     159            1 : }
     160              : 
     161            2 : BOOST_AUTO_TEST_CASE(StreamOperatorRoundTrip)
     162              : {
     163            1 :   const DAQEthHeader original = make_header(7, 3, 22, 4, 9, 0, 1234, 88, 0x0123456789ABCDEFULL);
     164              : 
     165            1 :   std::ostringstream oss;
     166            1 :   oss << original;
     167            1 :   const std::string output = oss.str();
     168            1 :   const DAQEthHeader recovered = header_from_stream_output(output);
     169              : 
     170            1 :   BOOST_REQUIRE(!output.empty());
     171            1 :   BOOST_REQUIRE(output.back() == '\n');
     172              : 
     173            1 :   BOOST_REQUIRE_EQUAL(recovered.version, original.version);
     174            1 :   BOOST_REQUIRE_EQUAL(recovered.det_id, original.det_id);
     175            1 :   BOOST_REQUIRE_EQUAL(recovered.crate_id, original.crate_id);
     176            1 :   BOOST_REQUIRE_EQUAL(recovered.slot_id, original.slot_id);
     177            1 :   BOOST_REQUIRE_EQUAL(recovered.stream_id, original.stream_id);
     178            1 :   BOOST_REQUIRE_EQUAL(recovered.reserved, original.reserved);
     179            1 :   BOOST_REQUIRE_EQUAL(recovered.seq_id, original.seq_id);
     180            1 :   BOOST_REQUIRE_EQUAL(recovered.block_length, original.block_length);
     181            1 :   BOOST_REQUIRE_EQUAL(recovered.timestamp, original.timestamp);
     182            1 : }
     183              : 
     184            2 : BOOST_AUTO_TEST_CASE(ByteRoundTrip)
     185              : {
     186            1 :   const DAQEthHeader original = make_header(13, 21, 777, 10, 55, 6, 2048, 1024, 0x1122334455667788ULL);
     187              : 
     188            1 :   uint8_t buffer[sizeof(DAQEthHeader)]; // NOLINT(modernize-avoid-c-arrays)
     189            1 :   std::memcpy(buffer, &original, sizeof(DAQEthHeader));
     190              : 
     191            1 :   DAQEthHeader recovered;
     192            1 :   std::memcpy(&recovered, buffer, sizeof(DAQEthHeader));
     193              : 
     194            1 :   BOOST_REQUIRE_EQUAL(recovered.version, original.version);
     195            1 :   BOOST_REQUIRE_EQUAL(recovered.det_id, original.det_id);
     196            1 :   BOOST_REQUIRE_EQUAL(recovered.crate_id, original.crate_id);
     197            1 :   BOOST_REQUIRE_EQUAL(recovered.slot_id, original.slot_id);
     198            1 :   BOOST_REQUIRE_EQUAL(recovered.stream_id, original.stream_id);
     199            1 :   BOOST_REQUIRE_EQUAL(recovered.reserved, original.reserved);
     200            1 :   BOOST_REQUIRE_EQUAL(recovered.seq_id, original.seq_id);
     201            1 :   BOOST_REQUIRE_EQUAL(recovered.block_length, original.block_length);
     202            1 :   BOOST_REQUIRE_EQUAL(recovered.timestamp, original.timestamp);
     203            1 :   BOOST_REQUIRE_EQUAL(recovered.get_timestamp(), original.get_timestamp());
     204            1 : }
     205              : 
     206              : BOOST_AUTO_TEST_SUITE_END()
     207              : 
     208              : // NOLINTEND(build/unsigned)
        

Generated by: LCOV version 2.0-1