18namespace fs = std::filesystem;
22getFilename(
const char * filenameArg);
25decodeEventWord(uint16_t currWord,
int errorType,
bool &linkCondensed,
26 std::string &type, std::vector<std::pair<std::string, int> > &arguments,
27 std::vector<std::string> &errors);
29std::vector<std::string>
30decodeEventFlags(uint32_t flags);
33findNextEvent(uint32_t* &start, uint32_t* &finish, uint32_t *end, uint32_t startWord);
36decodeEvent(uint32_t *buffer,
int length);
39decodeSubFragment(uint32_t *buffer,
int length);
43str(
const char * word){
44 return word ? word :
"";
49 std::cout<<
"'DecodeSCT' takes exactly one argument, the bytestream filename." <<std::endl;
53int main(
int argc,
char **argv) {
58 fs::path input_file = getFilename(argv[1]);
59 if (input_file.empty()) {
60 std::cerr << argv[1] <<
" does not exist."<<std::endl;
63 auto length = fs::file_size(input_file);
64 printf(
"Length: %lu\n",
length);
65 auto fd = open(input_file.c_str(), O_RDONLY);
67 perror(
"File open failed");
70 uint32_t *buffer = (uint32_t *) mmap(0,
length, PROT_READ, MAP_PRIVATE, fd, 0);
71 if(buffer == MAP_FAILED) {
73 perror(
"mmap failed");
76 uint32_t *endBuffer = &buffer[
length/4];
77 uint32_t *begin = buffer;
79 while(findNextEvent(begin, end, endBuffer, 0xee1234ee)) {
81 printf(
"Event from %li to %li\n", begin-buffer, end-buffer);
82 int length =
static_cast<int>(end - 1l - begin);
83 decodeEvent(begin,
length);
91 bool findNextEvent(uint32_t* &start, uint32_t* &finish, uint32_t *end, uint32_t startWord) {
93 if(start >= end)
return false;
94 while(*start != startWord) {
96 if(start >= end)
return false;
100 while((!( ((*finish & 0x00ffff00) == 0x00123400) || ((*finish & 0xffff0000) == 0x12340000))) || ((*finish) == 0xff1234ff)) {
102 if(finish >= end)
break;
108 bool findNextSubFragment(uint32_t* &start, uint32_t* &finish, uint32_t *end) {
110 if(start >= end)
return false;
111 while(*start != 0xff1234ff) {
113 if(start >= end)
return false;
116 while((!( ((*finish & 0x00ffff00) == 0x00123400) || ((*finish & 0xffff0000) == 0x12340000))) ) {
118 if(finish >= end)
break;
125 eventWord(
const uint32_t *
const buffer,
const int index,
const int length) {
127 std::cout <<
"Attempt to read from the end of the buffer " <<
index <<
" " <<
length << std::endl;
134 void decodeEvent(uint32_t *frameBuffer,
int length) {
135 if(frameBuffer[0] == 0xee1234ee) {
136 std::cout <<
"Valid header\n";
138 std::cout <<
"Bad check 0x" << std::hex << frameBuffer[0] << std::dec <<
"\n";
139 std::cout <<
"Skipping decode as SCT ROD fragment\n";
147 int eventLength =
length - headerLength - trailerLength + 2;
149 if(frameBuffer[1] != headerLength) {
150 std::cout <<
"Unknown header length (" << frameBuffer[1] <<
")\n";
152 std::cout <<
"New formatter version:\n";
153 std::cout <<
"Version: 0x" << std::hex << eventWord(frameBuffer, 3,
length) << std::dec
154 <<
" ID: 0x" <<std::hex << eventWord(frameBuffer, 4,
length) <<std::dec
155 <<
" Run number = " << eventWord(frameBuffer, 5,
length) <<
"\n";
156 std::cout <<
"L1ID = 0x" << std::hex << eventWord(frameBuffer, 6,
length) << std::dec
157 <<
" BCID = 0x" << std::hex << eventWord(frameBuffer, 7,
length) << std::dec
158 <<
" TType = " << eventWord(frameBuffer, 8,
length)
159 <<
" det type = " << eventWord(frameBuffer, 9,
length) <<
"\n";
161 std::cout <<
"SubDetID = " << std::hex <<
SubDetID <<std::dec;
169 std::cout <<
" Found SCT fragment [" <<
SubDetID <<
"]. Decoding...\n";
172 uint16_t lastWord = 1 + ((eventWord(frameBuffer, rawOffset,
length) & 0xffff0000) >> 16);
175 bool linkCondensed =
true;
177 for(
int i=0;
i<eventLength * 2;
i++) {
180 uint32_t rawWord = eventWord(frameBuffer, rawOffset + i/2,
length);
182 currWord = rawWord & 0x00ffff;
184 currWord = (rawWord & 0xffff0000) >> 16;
188 if(currWord == lastWord) {
192 std::cout <<
" Repeated " << repeats <<
" times\n";
198 std::cout << std::hex << currWord << std::dec;
201 std::vector<std::pair<std::string, int> >
arguments;
202 std::vector<std::string>
errors;
203 decodeEventWord(currWord, 0, linkCondensed,
type, arguments, errors);
204 std::cout <<
" " <<
type <<
" ";
206 std::cout <<
" " <<
iter->first <<
": " <<
iter->second;
209 std::cout <<
" ERRORS: ";
211 for(
auto iter =
errors.begin();iter !=
errors.end();++iter) {
212 std::cout <<
" " << *
iter;
214 std::cout << std::endl;
217 std::cout <<
" Repeated " << repeats <<
" times\n";
220 std::cout <<
"Error count = 0x" << std::hex << eventWord(frameBuffer,
length-trailerLength + 2,
length) << std::dec <<
"\n";
221 std::cout <<
"Error flags = 0x" << std::hex << eventWord(frameBuffer,
length-trailerLength + 3,
length) << std::dec <<
"\n";
223 std::vector<std::string> flagStrings = decodeEventFlags(flags);
224 for(
auto iter = flagStrings.begin();iter != flagStrings.end();++iter) {
225 std::cout << *
iter <<
" ";
227 if(flagStrings.size() > 0)
228 std::cout << std::endl;
229 std::cout <<
"nData = " << eventWord(frameBuffer,
length-trailerLength + 5,
length) <<
" words found = " << (
length - (headerLength + trailerLength) + 2) << std::endl;
233 std::cout <<
" TDAQ [" <<
SubDetID <<
"] beam crate fragment: " << std::endl;
237 bool found = findNextSubFragment(begin, end, endBuffer);
239 printf(
"SubFragment from %ld to %ld\n", begin-frameBuffer, end-frameBuffer);
241 const int extent =
static_cast<int>(
end-
begin);
242 decodeSubFragment(begin, extent);
243 found = findNextSubFragment(begin, end, endBuffer);
245 if (found) printf(
"SubFragment from %ld to %ld\n", begin-frameBuffer, end-frameBuffer);
254 std::cout <<
" TRT fragment [" <<
SubDetID <<
"] ... skipping" << std::endl;
258 std::cout <<
" Not an known fragment [" <<
SubDetID <<
"] ... skipping" << std::endl;
265 decodeSubFragment(uint32_t *frameBuffer,
int length) {
267 std::cout <<
"SubFragmentID = " << SubFragID ;
268 std::cout <<
" Length = " <<
length;
269 std::string
Type[8]={
"data",
"res ",
"head",
"res ",
"eob ",
"res ",
"inv ",
"res "};
272 std::cout <<
" Found TDC fragment. Decoding..."<< std::endl;
275 std::cout <<
"data[" <<
i <<
"]=0x" << std::hex <<(
data&0xFFF) << std::dec <<
" ";
276 std::cout <<
"type=" <<
Type[(
data>>24)&0x07] <<
" ";
277 std::cout <<
"chan=" << ((
data>>16)&0x001f) <<
" ";
278 std::cout <<
"un=" << ((
data>>13)&1) <<
" ";
279 std::cout <<
"ov=" << ((
data>>12)&1) <<
" ";
280 std::cout <<
"value=" << ((
data&0x0fff)) <<
" ";
281 std::cout << std::endl;
286 std::cout <<
" Found ADC fragment. Decoding..." << std::endl;
289 std::cout <<
"data[" <<
i <<
"]=0x" << std::hex <<
data << std::dec <<
" ";
290 std::cout <<
"type=" <<
Type[(
data>>24)&0x07] <<
" ";
291 std::cout <<
"chan=" << ((
data>>16)&0x001f) <<
" ";
292 std::cout <<
"un=" << ((
data>>13)&1) <<
" ";
293 std::cout <<
"ov=" << ((
data>>12)&1) <<
" ";
294 std::cout <<
"value=" << ((
data&0x0fff)) <<
" ";
295 std::cout << std::endl;
300 std::cout <<
" Not an known SubFragment [" << SubFragID <<
"] ... skipping" << std::endl;
307 decodeEventWord(uint16_t currWord,
int errorType,
bool &linkCondensed,
308 std::string &
type, std::vector<std::pair<std::string, int> > &arguments,
309 std::vector<std::string> &errors) {
314 switch((currWord & 0xe000) >> 13) {
317 if(currWord & 0x1f80)
321 type =
"Flagged error";
322 errors.push_back(
"FLAGGED");
323 arguments.push_back(std::make_pair(
"chip", (currWord & 0x78) >> 3));
324 arguments.push_back(std::make_pair(
"value", currWord & 0x7));
334 arguments.push_back(std::make_pair(
"L1", ((currWord & 0x0f00) >> 8)));
335 arguments.push_back(std::make_pair(
"BCID", ((currWord & 0xff))));
336 if(currWord & 0x1000) {
337 errors.push_back(
"Preamble err");
340 int link = (currWord & 0x7f);
341 arguments.push_back(std::make_pair(
"Link", link));
342 if(currWord & 0x100) {
343 arguments.push_back(std::make_pair(
"Condensed mode", 1));
344 linkCondensed =
true;
346 linkCondensed =
false;
349 errors.push_back(
"BC err");
351 errors.push_back(
"L1 err");
353 errors.push_back(
"Time out err");
354 if(currWord & 0x1000)
355 errors.push_back(
"Preamble err");
367 errors.push_back(
"Data overflow err");
369 errors.push_back(
"H/T limit err");
370 if(currWord & 0x1000)
371 errors.push_back(
"Trailer bit err");
382 int bits = ((currWord & 0x1c00) >> 10) + 1;
383 arguments.push_back(std::make_pair(
"bits", bits));
384 int value = ((currWord<<(8-bits)) & 0xff) >> (8-bits);
385 arguments.push_back(std::make_pair(
"value", value));
388 for(
int b=8-bits;
b<8;
b++) {
389 binValue = binValue * 10 + ((
value>>(7-
b)) & 1);
392 arguments.push_back(std::make_pair(
"binValue", binValue));
399 if((currWord & 0x2) == 0) {
401 if(linkCondensed || errorType) {
402 arguments.push_back(std::make_pair(
"Chip", ((currWord & 0x7800) >> 11)));
403 arguments.push_back(std::make_pair(
"Channel", ((currWord & 0x7f0) >> 4)));
405 type =
"Condensed double hit";
406 if(currWord & 0x4)
errors.push_back(
"Error in hit1");
407 if(currWord & 0x8)
errors.push_back(
"Error in hit2");
409 type =
"Condensed hit";
410 if(currWord & 0x4)
errors.push_back(
"Error in hit");
416 if(!linkCondensed || errorType) {
417 if((currWord & 0x8) == 0) {
418 type =
"1st hit clust exp";
419 arguments.push_back(std::make_pair(
"Chip", ((currWord & 0x7800) >> 11)));
420 arguments.push_back(std::make_pair(
"Channel", ((currWord & 0x7f0) >> 4)));
421 arguments.push_back(std::make_pair(
"hits", currWord & 0x7));
423 if((currWord & 0x7f00) == 0) {
425 arguments.push_back(std::make_pair(
"hits", currWord & 0x7));
426 if(currWord & 0x80) {
427 arguments.push_back(std::make_pair(
"hits2", (currWord & 0x70) >> 4));
436 std::vector<std::string>
437 decodeEventFlags(uint32_t flags) {
438 std::vector<std::string>
result;
439 if(flags & 0x1)
result.push_back(
"HEADER");
440 if(flags & 0x2)
result.push_back(
"TRAILER");
441 if(flags & 0x4)
result.push_back(
"FLAGGED");
442 if(flags & 0x8)
result.push_back(
"\"HIT PATTERN\"");
443 if(flags & 0x10)
result.push_back(
"SYNC");
444 if(flags & 0x20)
result.push_back(
"L1ID");
445 if(flags & 0x40)
result.push_back(
"BCID");
446 if(flags & 0x80)
result.push_back(
"TIMEOUT");
447 if(flags & 0x100)
result.push_back(
"\"ALMOST FULL\"");
448 if(flags & 0x200)
result.push_back(
"OVERFLOW");
449 if(flags & 0x400)
result.push_back(
"\"CHIP SEQ\"");
450 if(flags & 0x800)
result.push_back(
"\"BAD CHIP\"");
455 getFilename(
const char * filenameArg){
457 const fs::path
file(filenameArg);
char data[hepevt_bytes_allocation_ATLAS]