CMS 3D CMS Logo

FileReaderDDU.cc
Go to the documentation of this file.
1 #include "FileReaderDDU.h"
2 #include <cerrno> // errno
3 #include <cstdlib> // exit
4 #include <cstring> // bzero, memcpy
5 #include <fcntl.h> // open
6 #include <iostream> // cerr
7 #include <sys/stat.h> // open
8 #include <sys/types.h> // open
9 #include <unistd.h> // read, close
10 
11 #ifndef O_LARGEFILE //for OSX
12 #define O_LARGEFILE 0
13 #endif
14 
16  if (sizeof(unsigned long long) != 8 || sizeof(unsigned short) != 2)
17  throw std::runtime_error(std::string("Wrong platform: sizeof(unsigned long long)!=8 || sizeof(unsigned short)!=2"));
18  end = (file_buffer_end = file_buffer + sizeof(file_buffer) / sizeof(unsigned long long));
19  bzero(raw_event, sizeof(raw_event));
20  bzero(file_buffer, sizeof(file_buffer));
21  word_0 = 0;
22  word_1 = 0;
23  word_2 = 0;
24  eventStatus = 0;
27  acceptCriteria = 0x3F; // Everything
28  fd = 0;
29 }
30 
32  if (fd)
33  close(fd);
34 }
35 
36 int FileReaderDDU::open(const char *filename) {
37  if (fd)
38  close(fd);
39  fd = ::open(filename, O_RDONLY | O_LARGEFILE);
40  if (fd == -1)
41  throw(std::runtime_error(std::string("Error opening ").append(filename).append(" data file.")));
42  return fd;
43 }
44 
45 size_t FileReaderDDU::read(const unsigned short *&buf) {
46  // Check for ubnormal situation
48  throw(std::runtime_error("Error of reading"));
49  if (!fd)
50  throw(std::runtime_error("Open some file first"));
51 
52  unsigned long long *start = end;
53  unsigned short *event = raw_event;
54 
55  eventStatus = 0;
56  size_t dduWordCount = 0;
57  end = nullptr;
58 
59  while (!end && dduWordCount < 50000) {
60  unsigned long long *dduWord = start;
61  unsigned long long preHeader = 0;
62 
63  // Did we reach end of current buffer and want to read next block?
64  // If it was first time and we don't have file buffer then we won't get inside
65  while (dduWord < file_buffer_end && dduWordCount < 50000) {
66  word_0 = word_1; // delay by 2 DDU words
67  word_1 = word_2; // delay by 1 DDU word
68  word_2 = *dduWord; // current DDU word
69  if ((word_2 & 0xFFFFFFFFFFFF0000LL) == 0x8000000180000000LL) {
70  if (eventStatus & Header) // Second header
71  {
72  word_2 = word_1; // Fall back to get rigth preHeader next time
73  end = dduWord; // Even if we end with preHeader of next evet put it to the end of this event too
74  break;
75  }
76  if (dduWordCount > 1) // Extra words between trailer and header
77  {
78  if ((word_0 & 0xFFFFFFFFFFFF0000LL) == 0xFFFFFFFFFFFF0000LL)
79  eventStatus |= FFFF;
80  word_2 = word_1; // Fall back to get rigth preHeader next time
81  end = dduWord;
82  break;
83  }
85  if (event == raw_event)
86  preHeader = word_1; // If preHeader not yet in event then put it there
87  start = dduWord;
88  }
89  if ((word_0 & 0xFFFFFFFFFFFF0000LL) == 0x8000FFFF80000000LL) {
91  end = ++dduWord;
92  break;
93  }
94  // Increase counters by one DDU word
95  dduWord++;
96  dduWordCount++;
97  }
98 
99  // If have DDU Header
100  if (preHeader) {
101  // Need to account first word of DDU Header
102  memcpy(event, &preHeader, sizeof(preHeader));
103  event += sizeof(preHeader) / sizeof(unsigned short);
104  }
105 
106  // Take care of the rest
107  memcpy(event, start, (dduWord - start) * sizeof(unsigned long long));
108  event += (dduWord - start) * sizeof(unsigned long long) / sizeof(unsigned short);
109 
110  // If reach max length
111  if (dduWordCount == 50000) {
112  end = dduWord;
113  break;
114  }
115 
116  if (!end) {
117  // Need to read next block for the rest of this event
118  ssize_t length = ::read(fd, file_buffer, sizeof(file_buffer));
119  if (length == -1)
120  throw(std::runtime_error("Error of reading"));
121  if (length == 0) {
123  end = (file_buffer_end = file_buffer + sizeof(file_buffer) / sizeof(unsigned long long));
124  break;
125  }
126  file_buffer_end = file_buffer + length / sizeof(unsigned long long);
127 
128  // Will start from the beginning of new buffer next time we read it
129  start = file_buffer;
130  }
131  }
132 
133  if (!end)
135  if (!(eventStatus & Header) && !(eventStatus & Trailer) && !(eventStatus & FFFF))
136  eventStatus |= Unknown;
137 
138  buf = (const unsigned short *)raw_event;
139  return (eventStatus & FFFF ? event - raw_event - 4 : event - raw_event);
140 }
141 
142 size_t FileReaderDDU::next(const unsigned short *&buf, int prescaling) {
143  size_t size = 0;
144  for (int i = 0; i < prescaling; i++) {
145  do {
146  if ((size = read(buf)) == 0)
147  break;
150  }
151  return size;
152 }
size
Write out results.
unsigned int rejectCriteria
Definition: FileReaderDDU.h:28
Definition: start.py:1
unsigned long long word_2
Definition: FileReaderDDU.h:11
size_t read(const unsigned short *&buf)
virtual ~FileReaderDDU(void)
unsigned short raw_event[200000]
Definition: FileReaderDDU.h:9
unsigned int acceptCriteria
Definition: FileReaderDDU.h:28
unsigned long long word_0
Definition: FileReaderDDU.h:11
unsigned long long * file_buffer_end
Definition: FileReaderDDU.h:14
#define O_LARGEFILE
unsigned int eventStatus
Definition: FileReaderDDU.h:28
unsigned long long file_buffer[4000]
Definition: FileReaderDDU.h:12
size_t next(const unsigned short *&buf, int prescaling=1)
unsigned int selectCriteria
Definition: FileReaderDDU.h:28
int open(const char *filename)
unsigned long long word_1
Definition: FileReaderDDU.h:11
unsigned long long * end
Definition: FileReaderDDU.h:14
Definition: event.py:1