LCOV - code coverage report
Current view: top level - mu2e-pcie-utils/dtcInterfaceLib - DTC_Data_Verifier.h (source / functions) Coverage Total Hit
Test: mu2edaq.info.cleaned Lines: 0.0 % 265 0
Test Date: 2026-07-30 01:56:44 Functions: 0.0 % 45 0

            Line data    Source code
       1              : 
       2              : #include <bitset>
       3              : #include <fstream>
       4              : #include <unordered_map>
       5              : #include <vector>
       6              : 
       7              : // #include "artdaq-core-mu2e/Overlays/DTC_Packets.h"
       8              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DCSReplyPacket.h"
       9              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DCSRequestPacket.h"
      10              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DMAPacket.h"
      11              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DataBlock.h"
      12              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DataHeaderPacket.h"
      13              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DataPacket.h"
      14              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DataRequestPacket.h"
      15              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_DataStatus.h"
      16              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_Event.h"
      17              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_EventHeader.h"
      18              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_HeartbeatPacket.h"
      19              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_PacketType.h"
      20              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_SubEvent.h"
      21              : #include "artdaq-core-mu2e/Overlays/DTC_Packets/DTC_SubEventHeader.h"
      22              : 
      23              : // #include "artdaq-core-mu2e/Overlays/DTC_Types.h"
      24              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_CharacterNotInTableError.h"
      25              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_DCSOperationType.h"
      26              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_DDRFlags.h"
      27              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_DebugType.h"
      28              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_EVBStatus.h"
      29              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_EventMode.h"
      30              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_EventWindowTag.h"
      31              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_FIFOFullErrorFlags.h"
      32              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_IICDDRBusAddress.h"
      33              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_IICSERDESBusAddress.h"
      34              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_LinkEnableMode.h"
      35              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_LinkStatus.h"
      36              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_Link_ID.h"
      37              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_OscillatorType.h"
      38              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_PLL_ID.h"
      39              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_PRBSMode.h"
      40              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_ROC_Emulation_Type.h"
      41              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_RXBufferStatus.h"
      42              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_RXStatus.h"
      43              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_SERDESLoopbackMode.h"
      44              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_SERDESRXDisparityError.h"
      45              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_SerdesClockSpeed.h"
      46              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_SimMode.h"
      47              : #include "artdaq-core-mu2e/Overlays/DTC_Types/DTC_Subsystem.h"
      48              : #include "artdaq-core-mu2e/Overlays/DTC_Types/Exceptions.h"
      49              : #include "artdaq-core-mu2e/Overlays/DTC_Types/Utilities.h"
      50              : 
      51              : #include "mu2e_driver/mu2e_mmap_ioctl.h"
      52              : 
      53              : namespace DTCLib
      54              : {
      55              : class DTC_Data_Verifier
      56              : {
      57              :   public:
      58            0 :         bool VerifyTrackerDataBlock(DTCLib::DTC_DataBlock /*block*/)
      59              :         {
      60            0 :                 return true;
      61              :         }
      62              : 
      63            0 :         bool VerifyCalorimeterDataBlock(DTCLib::DTC_DataBlock block)
      64              :         {
      65            0 :                 auto blockByteSize = block.GetHeader()->GetByteCount();
      66              : 
      67            0 :                 if(blockByteSize == 0x10)
      68              :                 {
      69              :                         // TLOG(TLVL_WARNING) << "VerifyCalorimeterDataBlock: Empty block encountered!";
      70            0 :                         return true;
      71              :                 }
      72              : 
      73            0 :                 auto dataPtr       = reinterpret_cast<const uint16_t*>(block.GetData());
      74            0 :                 auto hitCount      = *dataPtr;
      75            0 :                 auto currentOffset = 0;
      76              : 
      77            0 :                 std::vector<uint16_t> hitOffsets;
      78            0 :                 for(int ii = 0; ii < hitCount; ++ii)
      79              :                 {
      80            0 :                         hitOffsets.push_back(*(++dataPtr));
      81            0 :                         currentOffset += 2;
      82            0 :                         if(currentOffset > blockByteSize)
      83              :                         {
      84            0 :                                 TLOG(TLVL_ERROR) << "VerifyCalorimeterDataBlock: Calorimeter data extends past declared block size! (0x" << std::hex << currentOffset << " > 0x" << std::hex << blockByteSize << ")";
      85            0 :                                 return false;
      86              :                         }
      87              :                 }
      88              : 
      89            0 :                 ++dataPtr;
      90            0 :                 currentOffset += 2;
      91              : 
      92            0 :                 auto channelStatusA = (*dataPtr & 0xFC00) >> 10;
      93              : 
      94            0 :                 ++dataPtr;
      95            0 :                 currentOffset += 2;
      96              : 
      97            0 :                 auto channelStatusB = (*dataPtr & 0x3FFF);
      98            0 :                 if((*dataPtr & 0xC000) != 0)
      99              :                 {
     100            0 :                         TLOG(TLVL_ERROR) << "VerifyCalorimeterDataBlock: Data present in BoardID Reserved field!";
     101            0 :                         return false;
     102              :                 }
     103              : 
     104            0 :                 if(channelStatusA == 0x0 && channelStatusB != 0x0)
     105              :                 {
     106            0 :                         TLOG(TLVL_WARNING) << "VerifyCalorimeterDataBlock: None of the 20 channels are enabled! StsA: 0x" << std::hex << channelStatusA << ", stsB: 0x" << std::hex << channelStatusB;
     107              :                         // Not sure if this is a fatal error or not, leaving it for now
     108              :                         // return false;
     109              :                 }
     110              : 
     111            0 :                 if(hitCount == 0)
     112              :                 {
     113            0 :                         TLOG(TLVL_WARNING) << "VerifyCalorimeterDataBlock: There are zero hits in this block!";
     114              :                 }
     115              : 
     116            0 :                 for(int ii = 0; ii < hitCount; ++ii)
     117              :                 {
     118            0 :                         ++dataPtr;
     119            0 :                         currentOffset += 2;
     120            0 :                         if(currentOffset != hitOffsets[ii])
     121              :                         {
     122            0 :                                 TLOG(TLVL_ERROR) << "VerifyCalorimeterDataBlock: Hit " << ii << " index value " << hitOffsets[ii] << " does not agree with current offset " << currentOffset;
     123            0 :                                 return false;
     124              :                         }
     125              : 
     126              :                         // auto channelNumber = *dataPtr & 0x3F;
     127              :                         // auto diracA = (*dataPtr >> 6) & 0x3FF;
     128            0 :                         ++dataPtr;
     129            0 :                         auto diracB = *dataPtr;
     130              : 
     131            0 :                         auto sipmID    = diracB >> 12;
     132            0 :                         auto crystalID = diracB & 0xFFF;
     133              : 
     134            0 :                         if(sipmID != 0 && sipmID != 1)
     135              :                         {
     136            0 :                                 TLOG(TLVL_WARNING) << "Invalid sipmID " << sipmID << " detected!";
     137              :                         }
     138            0 :                         if(crystalID > 674 * 2)
     139              :                         {
     140            0 :                                 TLOG(TLVL_WARNING) << "Invalid crystalID " << crystalID << " detected!";
     141              :                         }
     142              : 
     143            0 :                         dataPtr += 2;
     144              : 
     145            0 :                         auto time = *dataPtr;
     146            0 :                         if(time < 500)
     147              :                         {
     148            0 :                                 TLOG(TLVL_WARNING) << "VerifyCalorimeterBlock: Suspicious time " << time << " detected!";
     149              :                         }
     150              : 
     151            0 :                         ++dataPtr;
     152            0 :                         currentOffset += 8;
     153              : 
     154            0 :                         auto numSamples          = *dataPtr & 0xFF;
     155            0 :                         auto maxSample           = (*dataPtr & 0xFF00) >> 8;
     156            0 :                         auto currentMaximumValue = 0;
     157            0 :                         auto currentMaximumIndex = 0;
     158              : 
     159            0 :                         if(numSamples == 0)
     160              :                         {
     161            0 :                                 TLOG(TLVL_WARNING) << "VerifyCalorimeterBlock: This hit has zero samples!";
     162              :                         }
     163              : 
     164            0 :                         for(int jj = 0; jj < numSamples; ++jj)
     165              :                         {
     166            0 :                                 ++dataPtr;
     167            0 :                                 currentOffset += 2;
     168              : 
     169            0 :                                 if(*dataPtr > currentMaximumValue)
     170              :                                 {
     171            0 :                                         currentMaximumValue = *dataPtr;
     172            0 :                                         currentMaximumIndex = jj;
     173              :                                 }
     174              :                         }
     175              : 
     176            0 :                         if(maxSample != currentMaximumIndex)
     177              :                         {
     178            0 :                                 TLOG(TLVL_ERROR) << "VerifyCalorimeterDataBlock: Hit " << ii << " has mismatched maximum sample; expected " << maxSample << ", actual maximum " << currentMaximumIndex;
     179            0 :                                 return false;
     180              :                         }
     181              :                 }
     182              : 
     183            0 :                 ++dataPtr;
     184            0 :                 currentOffset += 2;
     185            0 :                 while(currentOffset % 16 != 0)
     186              :                 {
     187            0 :                         if(*dataPtr != 0)
     188              :                         {
     189            0 :                                 TLOG(TLVL_ERROR) << "VerifyCalorimeterDataBlock: Data detected in end padding: 0x" << std::hex << *dataPtr;
     190            0 :                                 return false;
     191              :                         }
     192            0 :                         ++dataPtr;
     193            0 :                         currentOffset += 2;
     194              :                 }
     195              : 
     196            0 :                 return true;
     197            0 :         }
     198              : 
     199            0 :         bool VerifyCRVDataBlock(DTCLib::DTC_DataBlock /*block*/)
     200              :         {
     201            0 :                 return true;
     202              :         }
     203              : 
     204            0 :         bool VerifyROCEmulatorBlock(DTCLib::DTC_DataBlock block)
     205              :         {
     206            0 :                 auto headerDP = block.GetHeader()->ConvertToDataPacket();
     207              : 
     208            0 :                 bool success = true;
     209            0 :                 success      = headerDP.GetByte(12) == 0xEF;
     210            0 :                 success &= headerDP.GetByte(13) == 0xBE;
     211            0 :                 success &= headerDP.GetByte(15) == 0xBE;
     212            0 :                 if(!success)
     213              :                 {
     214            0 :                         TLOG(TLVL_ERROR) << "VerifyROCEmulatorBlock: Header format is incorrect (check bytes)";
     215            0 :                         return false;
     216              :                 }
     217              : 
     218            0 :                 auto packetCount = block.GetHeader()->GetPacketCount();
     219            0 :                 auto roc         = block.GetHeader()->GetLinkID();
     220            0 :                 auto dataPtr     = reinterpret_cast<uint16_t const*>(block.GetData());
     221              : 
     222            0 :                 for(int ii = 0; ii < packetCount; ++ii)
     223              :                 {
     224            0 :                         success = *dataPtr == 0x1111;
     225            0 :                         ++dataPtr;
     226            0 :                         success &= *dataPtr == 0x2222;
     227            0 :                         ++dataPtr;
     228              : 
     229            0 :                         uint32_t roc_packet_counter_test = (*dataPtr << 16);
     230            0 :                         ++dataPtr;
     231            0 :                         roc_packet_counter_test += *dataPtr;
     232            0 :                         ++dataPtr;
     233              : 
     234            0 :                         if(roc_emulator_packet_counters_.count(roc) == 0)
     235              :                         {
     236            0 :                                 roc_emulator_packet_counters_[roc] = roc_packet_counter_test;
     237              :                         }
     238              : 
     239            0 :                         if(roc_packet_counter_test != roc_emulator_packet_counters_[roc])
     240              :                         {
     241            0 :                                 TLOG(TLVL_INFO) << "VerifyROCEmulatorBlock: ROC Emulator packet counter for roc " << static_cast<int>(roc) << " unexpected, shifting from " << roc_emulator_packet_counters_[roc] << " (expected) to " << roc_packet_counter_test << " (received) ";
     242            0 :                                 roc_emulator_packet_counters_[roc] = roc_packet_counter_test;
     243              :                         }
     244              : 
     245            0 :                         success &= *dataPtr == 0x3333;
     246            0 :                         ++dataPtr;
     247            0 :                         success &= *dataPtr == 0x4444;
     248            0 :                         ++dataPtr;
     249              : 
     250            0 :                         roc_packet_counter_test = (*dataPtr << 16);
     251            0 :                         ++dataPtr;
     252            0 :                         roc_packet_counter_test += *dataPtr;
     253            0 :                         success &= (roc_packet_counter_test == roc_emulator_packet_counters_[roc]);
     254            0 :                         ++dataPtr;
     255              : 
     256            0 :                         roc_emulator_packet_counters_[roc]++;
     257              : 
     258            0 :                         if(!success)
     259              :                         {
     260            0 :                                 TLOG(TLVL_ERROR) << "VerifyROCEmulatorBlock: Data packet " << ii << " has format error";
     261            0 :                                 dataPtr -= 8;
     262            0 :                                 std::vector<uint16_t> pktData(8);
     263            0 :                                 for(size_t jj = 0; jj < 8; ++jj)
     264              :                                 {
     265            0 :                                         pktData[jj] = *dataPtr;
     266            0 :                                         ++dataPtr;
     267              :                                 }
     268            0 :                                 TLOG(TLVL_ERROR) << "Packet data: " << std::hex << pktData[0] << " " << pktData[1]
     269            0 :                                                  << " " << pktData[2] << " " << pktData[3]
     270            0 :                                                  << " " << pktData[4] << " " << pktData[5]
     271            0 :                                                  << " " << pktData[6] << " " << pktData[7];
     272            0 :                                 return false;
     273            0 :                         }
     274              :                 }
     275              : 
     276            0 :                 return true;
     277            0 :         }
     278              : 
     279            0 :         bool VerifyBlock(DTCLib::DTC_DataBlock block)
     280              :         {
     281            0 :                 auto header        = block.GetHeader();
     282            0 :                 auto blockByteSize = header->GetByteCount();
     283              : 
     284              :                 // Check that this is indeed a DataHeader packet
     285            0 :                 auto     dataHeaderMask = 0x80F0;
     286            0 :                 uint16_t dataHeaderTest = static_cast<uint16_t>(header->ConvertToDataPacket().GetByte(2)) + (static_cast<uint16_t>(header->ConvertToDataPacket().GetByte(3)) << 8);
     287            0 :                 TLOG(TLVL_DEBUG + 5) << "Block size: 0x" << std::hex << blockByteSize << ", Test word: " << std::hex << dataHeaderTest << ", masked: " << (dataHeaderTest & dataHeaderMask) << " =?= 0x8050";
     288            0 :                 if((dataHeaderTest & dataHeaderMask) != 0x8050)
     289              :                 {
     290            0 :                         auto offset = file_mode_ ? (current_buffer_offset_ + current_buffer_pos_) : current_buffer_pos_;
     291            0 :                         TLOG(TLVL_ERROR) << "Encountered bad data at 0x" << std::hex << offset << ": expected DataHeader, got 0x" << std::hex << *reinterpret_cast<const uint64_t*>(block.blockPointer);
     292              : 
     293            0 :                         Utilities::PrintBuffer(block.blockPointer, 16);
     294              : 
     295              :                         // go to next file
     296            0 :                         continueFile_ = false;
     297            0 :                         return false;
     298              :                 }
     299              : 
     300            0 :                 auto packetCountTest = header->GetPacketCount();
     301            0 :                 if((packetCountTest + 1) * 16 != blockByteSize)
     302              :                 {
     303            0 :                         TLOG(TLVL_ERROR) << "Block data packet count and byte count disagree! packetCount: " << packetCountTest << ", which implies block size of 0x" << std::hex << ((packetCountTest + 1) * 16) << ", blockSize: 0x" << std::hex << blockByteSize;
     304              : 
     305            0 :                         Utilities::PrintBuffer(block.blockPointer, 16);
     306              :                         // We don't have to skip to the next file, because we already know the data block integrity is fine.
     307            0 :                         current_buffer_pos_ += blockByteSize;
     308            0 :                         return false;
     309              :                 }
     310              : 
     311            0 :                 auto subsystemID    = header->GetSubsystemID();
     312            0 :                 bool subsystemCheck = true;
     313            0 :                 switch(subsystemID)
     314              :                 {
     315            0 :                 case 0:  // Tracker
     316            0 :                         subsystemCheck = VerifyTrackerDataBlock(block);
     317            0 :                         break;
     318            0 :                 case 1:  // Calorimeter
     319            0 :                         subsystemCheck = VerifyCalorimeterDataBlock(block);
     320            0 :                         break;
     321            0 :                 case 2:  // CRV
     322            0 :                         subsystemCheck = VerifyCRVDataBlock(block);
     323            0 :                         break;
     324            0 :                 case 3:  // ROC Emulator
     325            0 :                         subsystemCheck = VerifyROCEmulatorBlock(block);
     326            0 :                         break;
     327            0 :                 default:
     328            0 :                         TLOG(TLVL_INFO) << "Data-level verification not implemented for subsystem ID " << subsystemID;
     329            0 :                         break;
     330              :                 }
     331            0 :                 if(!subsystemCheck)
     332              :                 {
     333            0 :                         auto offset = file_mode_ ? (current_buffer_offset_ + current_buffer_pos_) : current_buffer_pos_;
     334            0 :                         TLOG(TLVL_ERROR) << "Data block at 0x" << std::hex << offset << " is not a valid data block for subsystem ID " << static_cast<int>(subsystemID);
     335              : 
     336            0 :                         current_buffer_pos_ += blockByteSize;
     337              : 
     338            0 :                         return false;
     339              :                         // We don't have to skip to the next file, because we already know the data block integrity is fine.
     340              :                 }
     341              : 
     342            0 :                 current_buffer_pos_ += blockByteSize;
     343            0 :                 return true;
     344            0 :         }
     345              : 
     346            0 :         bool VerifySubEvent(DTCLib::DTC_SubEvent subevt, DTCLib::DTC_EventWindowTag eventTag)
     347              :         {
     348            0 :                 if(subevt.GetEventWindowTag() != eventTag)
     349              :                 {
     350            0 :                         TLOG(TLVL_WARNING) << "Event Window Tag from Event does not agree with EWT from SubEvent! (" << eventTag.GetEventWindowTag(true) << " != " << subevt.GetEventWindowTag().GetEventWindowTag(true) << ")";
     351              :                 }
     352            0 :                 if(subevt.GetHeader()->num_rocs != subevt.GetDataBlockCount())
     353              :                 {
     354            0 :                         TLOG(TLVL_WARNING) << "SubEvent Header num_rocs field disagrees with number of DataBlocks! (" << subevt.GetHeader()->num_rocs << " != " << subevt.GetDataBlockCount() << ")";
     355              :                 }
     356            0 :                 TLOG(TLVL_DEBUG + 4) << subevt.GetHeader()->toJson();
     357            0 :                 current_buffer_pos_ += sizeof(DTCLib::DTC_SubEventHeader);
     358              : 
     359            0 :                 bool success = true;
     360            0 :                 for(auto& block : subevt.GetDataBlocks())
     361              :                 {
     362            0 :                         auto blockSuccess = VerifyBlock(block);
     363            0 :                         success &= blockSuccess;
     364            0 :                         if(file_mode_ && !continueFile_)
     365            0 :                                 return false;
     366              :                 }
     367            0 :                 return success;
     368              :         }
     369              : 
     370            0 :         bool VerifyEvent(DTCLib::DTC_Event evt)
     371              :         {
     372            0 :                 bool success        = true;
     373            0 :                 current_buffer_pos_ = 0;
     374              : 
     375            0 :                 auto eventTag = evt.GetEventWindowTag();
     376              : 
     377            0 :                 if(evt.GetHeader()->num_dtcs != evt.GetSubEventCount())
     378              :                 {
     379            0 :                         TLOG(TLVL_WARNING) << "Event Header num_dtcs field (" << evt.GetHeader()->num_dtcs << ") disagrees with number of SubEvents! (" << evt.GetSubEventCount() << ")";
     380              :                 }
     381              : 
     382            0 :                 TLOG(TLVL_DEBUG + 3) << evt.GetHeader()->toJson();
     383              : 
     384            0 :                 current_buffer_pos_ += sizeof(DTCLib::DTC_EventHeader);
     385              : 
     386            0 :                 for(auto& subevt : evt.GetSubEvents())
     387              :                 {
     388            0 :                         auto subevtSuccess = VerifySubEvent(subevt, eventTag);
     389            0 :                         success &= subevtSuccess;
     390            0 :                         if(file_mode_ && !continueFile_)
     391            0 :                                 return false;
     392              :                 }
     393            0 :                 return success;
     394            0 :         }
     395              : 
     396            0 :         bool VerifyFile(std::string file)
     397              :         {
     398            0 :                 std::ifstream is(file);
     399            0 :                 if(is.bad() || !is)
     400              :                 {
     401            0 :                         TLOG(TLVL_ERROR) << "Cannot read file " << file;
     402            0 :                         return false;
     403              :                 }
     404            0 :                 TLOG(TLVL_INFO) << "Reading binary file " << file;
     405            0 :                 size_t total_size_read = 0;
     406            0 :                 file_mode_             = true;
     407              : 
     408              :                 mu2e_databuff_t buf;
     409              : 
     410            0 :                 bool success  = true;
     411            0 :                 continueFile_ = true;
     412            0 :                 while(is && continueFile_)
     413              :                 {
     414              :                         uint64_t dmaWriteSize;  // DMA Write buffer size
     415            0 :                         is.read((char*)&dmaWriteSize, sizeof(dmaWriteSize));
     416            0 :                         if(!is || is.eof())
     417            0 :                                 break;
     418              : 
     419            0 :                         total_size_read += sizeof(dmaWriteSize);
     420              : 
     421              :                         uint64_t dmaSize;
     422            0 :                         is.read((char*)&dmaSize, sizeof(dmaSize));
     423              : 
     424              :                         // Check that DMA Write Buffer Size = DMA Buffer Size + 8
     425            0 :                         if(dmaSize + 8 != dmaWriteSize)
     426              :                         {
     427            0 :                                 TLOG(TLVL_ERROR) << "Buffer error detected: DMA Size mismatch at " << std::showbase << std::hex << total_size_read << ". Write size: " << static_cast<size_t>(dmaWriteSize) << ", DMA Size: " << static_cast<size_t>(dmaSize);
     428            0 :                                 success = false;
     429            0 :                                 break;
     430              :                         }
     431              : 
     432            0 :                         if(dmaSize > SET_DTC_MAX_DMA_SIZE)
     433              :                         {
     434            0 :                                 TLOG(TLVL_WARNING) << "Over-size block detected! DTC has a limit of " << SET_DTC_MAX_DMA_SIZE << ", dma size is " << std::showbase << std::hex << dmaSize << "!";
     435              :                         }
     436              : 
     437              :                         // Check that size of all DataBlocks = DMA Buffer Size
     438            0 :                         is.read((char*)buf, dmaSize - 8);
     439            0 :                         total_size_read += dmaSize;
     440            0 :                         current_buffer_offset_ = total_size_read;
     441              : 
     442            0 :                         TLOG(TLVL_DEBUG + 1) << "Verifying event at offset " << std::showbase << std::hex << current_buffer_offset_;
     443            0 :                         DTCLib::DTC_Event thisEvent(buf);
     444              : 
     445            0 :                         TLOG(TLVL_DEBUG + 2) << "Getting Size of Event...";
     446            0 :                         size_t eventByteCount = thisEvent.GetEventByteCount();
     447            0 :                         if(eventByteCount > dmaSize - 8U)
     448              :                         {
     449            0 :                                 TLOG(TLVL_DEBUG + 1) << "Event is continued in next DMA! (Event size " << std::showbase << std::hex << eventByteCount << ", first DMA size " << dmaSize - 8U << ")";
     450            0 :                                 DTC_Event newEvt(eventByteCount);
     451            0 :                                 memcpy(const_cast<void*>(newEvt.GetRawBufferPointer()), thisEvent.GetRawBufferPointer(), dmaSize - 8);
     452            0 :                                 size_t newEvtSize = dmaSize - 8;
     453            0 :                                 while(newEvtSize < eventByteCount)
     454              :                                 {
     455            0 :                                         is.read((char*)&dmaWriteSize, sizeof(dmaWriteSize));
     456            0 :                                         if(!is || is.eof())
     457              :                                         {
     458            0 :                                                 TLOG(TLVL_ERROR) << "File ended while reading continued DMA!";
     459            0 :                                                 break;
     460              :                                         }
     461              : 
     462            0 :                                         total_size_read += sizeof(dmaWriteSize);
     463              : 
     464            0 :                                         is.read((char*)&dmaSize, sizeof(dmaSize));
     465              : 
     466              :                                         // Check that DMA Write Buffer Size = DMA Buffer Size + 8
     467            0 :                                         if(dmaSize + 8 != dmaWriteSize)
     468              :                                         {
     469            0 :                                                 TLOG(TLVL_ERROR) << "Buffer error detected: DMA Size mismatch at " << std::showbase << std::hex << total_size_read << ". Write size: " << static_cast<size_t>(dmaWriteSize) << ", DMA Size: " << static_cast<size_t>(dmaSize);
     470            0 :                                                 success = false;
     471            0 :                                                 break;
     472              :                                         }
     473              : 
     474              :                                         // Check that size of all DataBlocks = DMA Buffer Size
     475            0 :                                         TLOG(TLVL_DEBUG + 1) << "Reading continued DMA at offset " << std::showbase << std::hex << total_size_read << " of size " << dmaSize - 8 << " into event";
     476            0 :                                         is.read((char*)buf, dmaSize - 8);
     477            0 :                                         current_buffer_offset_ = total_size_read;
     478            0 :                                         total_size_read += dmaSize;
     479              : 
     480            0 :                                         size_t bytes_to_read = dmaSize - 8;
     481            0 :                                         if(newEvtSize + dmaSize - 8 > eventByteCount)
     482              :                                         {
     483            0 :                                                 bytes_to_read = eventByteCount - newEvtSize;
     484              :                                         }
     485              : 
     486            0 :                                         memcpy(const_cast<uint8_t*>(static_cast<const uint8_t*>(newEvt.GetRawBufferPointer()) + newEvtSize), buf, bytes_to_read);
     487            0 :                                         newEvtSize += dmaSize - 8;
     488              :                                 }
     489              : 
     490            0 :                                 newEvt.SetupEvent();
     491            0 :                                 success = VerifyEvent(newEvt);
     492            0 :                         }
     493              :                         else
     494              :                         {
     495            0 :                                 thisEvent.SetupEvent();
     496            0 :                                 success = VerifyEvent(thisEvent);
     497              :                         }
     498            0 :                 }
     499              : 
     500            0 :                 if(success)
     501              :                 {
     502            0 :                         TLOG(TLVL_INFO) << "File " << file << " verified successfully!";
     503              :                 }
     504              :                 else
     505              :                 {
     506            0 :                         TLOG(TLVL_WARNING) << "File " << file << " had verification errors, see TRACE output for details";
     507              :                 }
     508              : 
     509            0 :                 return success;
     510            0 :         }
     511              : 
     512              :   private:
     513              :         bool                                              continueFile_{true};
     514              :         bool                                              file_mode_{false};
     515              :         uint64_t                                          current_buffer_offset_{0};
     516              :         uint64_t                                          current_buffer_pos_{0};
     517              :         std::unordered_map<DTCLib::DTC_Link_ID, uint32_t> roc_emulator_packet_counters_;
     518              : };
     519              : }  // namespace DTCLib
        

Generated by: LCOV version 2.0-1