EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
fileEventiterator.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file fileEventiterator.cc
1 //
2 // fileEventIterator mlp 4/19/1997
3 //
4 // this iterator reads events froma data file.
5 
6 
7 #include <stddef.h>
8 #include <string.h>
9 
10 #include <unistd.h>
11 #include <sys/types.h>
12 #include <sys/stat.h>
13 #include <fcntl.h>
14 
15 // there are two similar constructors, one with just the
16 // filename, the other with an additional status value
17 // which is non-zero on return if anything goes wrong.
18 #include "fileEventiterator.h"
19 
20 //#ifndef LVL2_WINNT
21 #include "lzobuffer.h"
22 //#endif
23 
24 
26 {
27  if (fd) close (fd);
28  if (thefilename != NULL) delete [] thefilename;
29  if (bp != NULL ) delete [] bp;
30  if (bptr != NULL ) delete bptr;
31 }
32 
33 
35 {
36  open_file ( filename);
37 }
38 
40 {
41  status = open_file ( filename);
42 }
43 
44 
46 {
47  fd = open (filename, O_RDONLY | O_LARGEFILE);
48  bptr = 0;
49  bp = 0;
50  allocatedsize = 0;
51  thefilename = NULL;
52  events_so_far = 0;
53  verbosity=0;
54  _defunct = 0;
55 
56  if (fd > 0)
57  {
58  thefilename = new char[strlen(filename)+1];
59  strcpy (thefilename, filename);
60  last_read_status = 0;
61  current_index = 0;
62  return 0;
63  }
64  else
65  {
66  last_read_status = 1;
67  _defunct = 1;
68  }
69  return 1;
70 
71 }
72 
73 
74 
76 {
77  os << "fileEventiterator reading from " << thefilename;
78  if ( _defunct ) os << " *** defunct";
79  os<< std::endl;
80 
81 };
82 
83 
85 {
86  static char namestr[512];
87  if ( thefilename == NULL)
88  {
89  return " ";
90  }
91  else
92  {
93  strcpy (namestr, thefilename);
94  return namestr;
95  }
96 };
97 
98 
99 
100 
101 const char * fileEventiterator::getIdTag () const
102 {
103  // sprintf (idline, " -- fileEventiterator reading from %s", thefilename);
104  return "fileEventiterator";
105 };
106 
107 
108 
109 // and, finally, the only non-constructor member function to
110 // retrieve events from the iterator.
111 
113 {
114  if ( _defunct ) return 0;
115  Event *evt = 0;
116 
117  // if we had a read error before, we just return
118  if (last_read_status) return NULL;
119 
120  // see if we have a buffer to read
121  if (bptr == 0)
122  {
123  if ( (last_read_status = read_next_buffer()) !=0 )
124  {
125  return NULL;
126  }
127  }
128 
129  while (last_read_status == 0)
130  {
131  if (bptr) evt = bptr->getEvent();
132  if (evt)
133  {
134  events_so_far++;
135  return evt;
136  }
138  }
139 
140  return NULL;
141 
142 }
143 
144 // -----------------------------------------------------
145 // this is a private function to read the next buffer
146 // if needed.
147 
149 {
150  PHDWORD initialbuffer[BUFFERBLOCKSIZE/4];
151 
152  unsigned int ip = 8192;
153 
154  buffer_size = 0;
155 
156  if (bptr)
157  {
158  delete bptr;
159  bptr = 0;
160  }
161  events_so_far = 0;
162 
163  // we are now reading the first block (8192 bytes) into
164  // initialbuffer. The buffer is at least that long. We
165  // look up the buffersize etc from that, and
166  // start filling the actual buffer. We do not read
167  // the data into the eventual destination since we may
168  // have to delete it to get more room (we might find that
169  // the buffer is larger than what we have allocated).
170 
171 
172  // set the pointer to char to the destination buffer
173  char *cp = (char *) initialbuffer;
174 
175  unsigned int xc;
176 
177 
178  // this while loop implements the skipping of 8k records until
179  // we find a valid buffer marker. (We usually find it right away).
180 
181  while (buffer_size == 0 )
182  {
183  // read the first record
184  xc = read ( fd, cp, BUFFERBLOCKSIZE);
185 
186  // error of EoF?
187  if ( xc < BUFFERBLOCKSIZE )
188  {
189  // COUT << "ferror" << std::endl;
190  return -1;
191  }
192 
193 
194  // get the buffer length into a dedicated variable
195  if (initialbuffer[1] == BUFFERMARKER || initialbuffer[1]== GZBUFFERMARKER
196  || initialbuffer[1]== LZO1XBUFFERMARKER || initialbuffer[1]== ONCSBUFFERMARKER)
197  {
198  buffer_size = initialbuffer[0];
199  }
200  else
201  {
202  unsigned int marker = buffer::u4swap(initialbuffer[1]);
203  if (marker == BUFFERMARKER || marker == GZBUFFERMARKER || marker == LZO1XBUFFERMARKER || marker == ONCSBUFFERMARKER)
204  {
205  buffer_size = buffer::u4swap(initialbuffer[0]);
206  }
207  }
208  }
209 
210 
211  int i;
212  if (bp)
213  {
214  // this tests if we have enough space in the existing buffer
215  if (buffer_size > allocatedsize*4) // no, we delete and make a bigger one
216  {
217  delete [] bp;
220  bp = new PHDWORD[allocatedsize];
221  // std::cout << __FILE__ << " " << __LINE__ << " new bp pointer is " << bp << " length value " << bp[-1]<< std::endl;
222  }
223  }
224  else
225  {
228  bp = new PHDWORD[allocatedsize];
229 
230  }
231 
232  // for (i = 0; i<BUFFERBLOCKSIZE/4; i++ ) bp[i] = initialbuffer[i];
233  memcpy ( bp, initialbuffer, BUFFERBLOCKSIZE);
234 
235  cp = (char *) bp;
236 
237  // and update the destination buffer pointer
238  cp += BUFFERBLOCKSIZE;
239 
240  PHDWORD read_so_far = BUFFERBLOCKSIZE;
241 
242  int errorinread=0;
243 
244  // now we read records until the whole buffer is read
245  while ( ip < buffer_size)
246  {
247  // COUT << "ip is " << ip << std::endl;
248  // read the next record
249  xc = read ( fd, cp, BUFFERBLOCKSIZE);
250  if ( xc < BUFFERBLOCKSIZE )
251  {
252  COUT << "error in buffer, salvaging" << std::endl;
253  bp[0] = read_so_far;
254  errorinread =1;
255  break;
256  }
257 
258  // update the pointer and byte count
259  cp += BUFFERBLOCKSIZE;
260  ip += BUFFERBLOCKSIZE;
261  read_so_far += BUFFERBLOCKSIZE;
262  }
263 
264  // and initialize the current_index to be the first event
265 
266  if ( ( initialbuffer[1]== GZBUFFERMARKER ||
267  buffer::u4swap(initialbuffer[1])== GZBUFFERMARKER ||
268  initialbuffer[1]== LZO1XBUFFERMARKER ||
269  buffer::u4swap(initialbuffer[1])== LZO1XBUFFERMARKER )
270  && errorinread )
271  {
272  bptr = 0;
273  return -3;
274  }
275 
277 
278 
279 }
280