Belle II Software development
PXDReadRawONSEN.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8
9#include <pxd/modules/pxdUnpacking/PXDReadRawONSEN.h>
10#include <framework/dataobjects/EventMetaData.h>
11#include <rawdata/dataobjects/RawPXD.h>
12#include <pxd/unpacking/PXDRawDataDefinitions.h>
13
14#include <framework/datastore/StoreArray.h>
15
16#include <boost/endian/arithmetic.hpp>
17
18using namespace std;
19using namespace Belle2;
20using namespace PXD;
21
22using ulittle16_t = boost::endian::little_uint16_t;
23using ulittle32_t = boost::endian::little_uint32_t;
24using ubig16_t = boost::endian::big_uint16_t;
25using ubig32_t = boost::endian::big_uint32_t;
26
27//-----------------------------------------------------------------
28// Register the Module
29//-----------------------------------------------------------------
30REG_MODULE(PXDReadRawONSEN);
31
32//-----------------------------------------------------------------
33// Implementation
34//-----------------------------------------------------------------
35
37{
38 fh = 0;
39 m_msghandler = 0;
40 //Set module properties
41 setDescription("Read a Raw PXD-Data Dump from ONSEN (or a simulator) and stores it as RawPXD in Data Store");
42 //setPropertyFlags(c_Input | c_ParallelProcessingCertified);
43 //setPropertyFlags(c_Input);
44
45 addParam("FileName", m_filename, "file name");
46 addParam("SetEvtMeta", m_setEvtMeta, "Set Event MEta Info from DHE", true);
47
48 m_nread = 0;
50 m_buffer = new int[MAXEVTSIZE];
51
52 B2DEBUG(29, "PXDReadRawONSENModule: Constructor done.");
53}
54
55
60
62{
63 // Open receiver sockets
64// m_recv = new EvtSocketSend(m_host, m_port);
65 fh = fopen(m_filename.c_str(), "rb");
66 if (fh) {
67 B2INFO("Read Raw ONSEN Data from " << m_filename);
68 } else {
69 B2ERROR("Could not open Raw ONSEN Data: " << m_filename);
70 }
71
72 // Open message handler
74
75 // Initialize EvtMetaData
76 m_eventMetaDataPtr.registerInDataStore();
77
78 // Initialize Array of RawCOPPER
79 StoreArray<RawPXD> storeRawPIDs;
80 storeRawPIDs.registerInDataStore();
81
82 B2DEBUG(29, "PXDReadRawONSENModule: initialized.");
83}
84
85int PXDReadRawONSENModule::read_data(char* data, size_t len)
86{
87 size_t l = 0;
88 if (fh) l = fread(data, 1, len, fh);
89 if (l != len) return 0;
90 return l;
91}
92
94{
95 char* data = (char*)m_buffer;
96 int len = MAXEVTSIZE * sizeof(int);
97
98#define MAX_PXD_FRAMES 256
99 const int headerlen = 8;
100 ubig32_t* pxdheader = (ubig32_t*) data;
101 ubig32_t* pxdheadertable = (ubig32_t*) &data[headerlen];
102 int framenr = 0, tablelen = 0, datalen = 0;
103 int br = read_data(data, headerlen);
104 if (br <= 0) return br;
105 if (pxdheader[0] != 0xCAFEBABEu) {
106 B2FATAL(Form("pxdheader wrong : Magic %X , Frames %X \n", (unsigned int) pxdheader[0], (unsigned int) pxdheader[1]));
107 exit(0);
108 }
109 framenr = pxdheader[1];
110 if (framenr > MAX_PXD_FRAMES) {
111 B2FATAL(Form("MAX_PXD_FRAMES too small : %d(%d) \n", framenr, MAX_PXD_FRAMES));
112 exit(0);
113 }
114 tablelen = 4 * framenr;
115 br = read_data((char*)&data[headerlen], tablelen);
116 if (br <= 0) return br;
117 for (int i = 0; i < framenr; i++) {
118 datalen += (pxdheadertable[i] + 3) & 0xFFFFFFFC;
119 }
120
121 if (datalen + headerlen + tablelen > len) {
122 B2FATAL(Form("buffer too small : %d %d %d(%d) \n", headerlen, tablelen, datalen, len));
123 exit(0);
124 }
125 br = read_data(data + headerlen + tablelen, datalen);
126 if (br <= 0) return br;
127 return (headerlen + tablelen + br);
128}
129
131{
132 if (fh == 0) {
133 B2ERROR("Unexpected close of dump file.");
134 terminate();
135 return;
136 }
137 // DataStore interface
138 StoreArray<RawPXD> rawpxdary;
139
140 // Get a record from socket
141 int stat;
142 do {
143 stat = readOneEvent();
144 if (stat <= 0) {
146 terminate();
147 return;
148 };
149 } while (stat == 0);
150
151 // Fill RawPXD in DataStore, stat=lenght_in_Bytes
152 rawpxdary.appendNew(m_buffer, stat);
153
154
155 if (m_setEvtMeta) {
156 // Update EventMetaData
157 m_eventMetaDataPtr.create();
158 for (auto& it : rawpxdary) {
159 if (getTrigNr(it)) break; // only first (valid) one
160 }
161 }
162
163 m_nread++;
164
165 return;
166}
167
169{
170 if (fh) fclose(fh);
171 fh = 0;
172}
173
174
176{
177 int Frames_in_event;
178 int fullsize;
179 int datafullsize;
180
181 if (px.size() <= 0 || px.size() > 16 * 1024 * 1024) {
182 B2ERROR("PXD Trigger Shifter --> invalid packet size (32bit words) " << hex << px.size());
183 return false;
184 }
185 std::vector<unsigned int> data(px.size());
186 fullsize = px.size() * 4;
187 std::copy_n(px.data(), px.size(), data.begin());
188
189
190 if (fullsize < 8) {
191 B2ERROR("Data is to small to hold a valid Header! Will not unpack anything. Size:" << fullsize);
192 return false;
193 }
194
195 if (data[0] != 0xCAFEBABE && data[0] != 0xBEBAFECA) {
196 B2ERROR("Magic invalid: Will not unpack anything. Header corrupted! " << hex << data[0]);
197 return false;
198 }
199
200 Frames_in_event = ((ubig32_t*)data.data())[1];
201 if (Frames_in_event < 1 || Frames_in_event > 250) {
202 B2ERROR("Number of Frames invalid: Will not unpack anything. Header corrupted! Frames in event: " << Frames_in_event);
203 return false;
204 }
205
206 unsigned int* tableptr;
207 tableptr = &data[2]; // skip header!!!
208
209 unsigned int* dataptr;
210 dataptr = &tableptr[Frames_in_event];
211 datafullsize = fullsize - 2 * 4 - Frames_in_event * 4; // minus header, minus table
212
213 int ll = 0; // Offset in dataptr in bytes
214 for (int j = 0; j < Frames_in_event; j++) {
215 int lo;
216 lo = ((ubig32_t*)tableptr)[j];
217 if (lo <= 0) {
218 B2ERROR("size of frame invalid: " << j << "size " << lo << " at byte offset in dataptr " << ll);
219 return false;
220 }
221 if (ll + lo > datafullsize) {
222 B2ERROR("frames exceed packet size: " << j << " size " << lo << " at byte offset in dataptr " << ll << " of datafullsize " <<
223 datafullsize << " of fullsize " << fullsize);
224 return false;
225 }
226 if (lo & 0x3) {
227 B2ERROR("SKIP Frame with Data with not MOD 4 length " << " ( $" << hex << lo << " ) ");
228 ll += (lo + 3) & 0xFFFFFFFC;
229 } else {
230 if (unpack_dhc_frame(ll + (char*)dataptr)) return true;
231 ll += lo;
232 }
233 }
234 return false;
235}
236
238{
239 switch (((*(ubig16_t*)data) & 0x7800) >> 11) {
240 case EDHCFrameHeaderDataType::c_ONSEN_TRG: {
241 unsigned int trignr = ((ubig32_t*)data)[2];
242 unsigned int tag = ((ubig32_t*)data)[3];
243
244 B2INFO("Set event and exp/run from ONSEN: $" << hex << trignr << ", $" << hex << tag);
245 m_eventMetaDataPtr->setEvent(trignr);
246 m_eventMetaDataPtr->setRun((tag & 0x003FFF00) >> 8);
247 m_eventMetaDataPtr->setSubrun(tag & 0xFF);
248 m_eventMetaDataPtr->setExperiment((tag & 0xFFC00000) >> 22);
249 m_eventMetaDataPtr->setTime(0);// will overwrite in next frame (below)
250 break;
251 }
252 case EDHCFrameHeaderDataType::c_DHC_START: {
253 unsigned int time_tag_lo_and_type = ((ubig16_t*)data)[3];
254 unsigned int time_tag_mid = ((ubig16_t*)data)[4];
255 unsigned int time_tag_hi = ((ubig16_t*)data)[5];
256 B2INFO("Set time tag from DHC: $" << hex << time_tag_mid << ", $" << hex << time_tag_lo_and_type);
257 uint32_t tt = ((time_tag_mid & 0x7FFF) << 12) | (time_tag_lo_and_type >> 4);
258 // we cannot recover full time tag from DHH header, but we do as much as possible to
259 // allow for check against a second PXD packet. Again: The time recovered here is WRONG, as we only have the lowest 17 bit of the second since epoch
260 m_eventMetaDataPtr->setTime((unsigned long long int)((time_tag_hi << 1) + ((time_tag_mid & 0x8000) ? 1 : 0)) * 1000000000 +
261 (int)std::round(tt / 0.127216));
262 return true;// assumes that DHC start is behind ONSEN_TRG
263 }
264 default:
265 break;
266
267 }
268 return false;
269}
void setDescription(const std::string &description)
Sets the description of the module.
Definition Module.cc:214
Module()
Constructor.
Definition Module.cc:30
A class to encode/decode an EvtMessage.
Definition MsgHandler.h:103
void initialize() override final
Initialize.
bool getTrigNr(RawPXD &px)
get the trigger number
int read_data(char *data, size_t len)
Read amount of data (len bytes) from file to ptr data.
PXDReadRawONSENModule()
Constructor / Destructor.
bool m_setEvtMeta
Set Event Meta Info.
void terminate() override final
Terminate.
void event() override final
Event.
MsgHandler * m_msghandler
Message handler.
bool unpack_dhc_frame(void *data)
unpack the dhc frame
int m_compressionLevel
Compression Level.
int readOneEvent(void)
Read data of one Event from File.
StoreObjPtr< EventMetaData > m_eventMetaDataPtr
Event Meta Data.
The Raw PXD class.
Definition RawPXD.h:27
virtual int * data(void)
get pointer to data
Definition RawPXD.cc:81
virtual int size() const
get size of buffer in 32 Bit words
Definition RawPXD.cc:76
bool registerInDataStore(DataStore::EStoreFlags storeFlags=DataStore::c_WriteOut)
Register the object/array in the DataStore.
Accessor to arrays stored in the data store.
Definition StoreArray.h:113
T * appendNew()
Construct a new T object at the end of the array.
Definition StoreArray.h:246
void addParam(const std::string &name, T &paramVariable, const std::string &description, const T &defaultValue)
Adds a new parameter to the module.
Definition Module.h:559
#define REG_MODULE(moduleName)
Register the given module (without 'Module' suffix) with the framework.
Definition Module.h:649
Namespace to encapsulate code needed for simulation and reconstrucion of the PXD.
boost::endian::big_uint16_t ubig16_t
define alias ubig16_t
boost::endian::big_uint32_t ubig32_t
define alias ubig32_t
Abstract base class for different kinds of events.
STL namespace.