Belle II Software  release-06-02-00
EventBuffer.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 #include "daq/storage/EventBuffer.h"
9 
10 #include <cstdio>
11 #include <cstdlib>
12 #include <cstring>
13 
14 using namespace Belle2;
15 
16 unsigned int EventBuffer::size() throw()
17 {
18  return sizeof(int) * (m_nword);
19 }
20 
21 EventBuffer::EventBuffer(unsigned int nword)
22 {
23  m_nword = nword;
24  char* buf = (char*) malloc(size());
25  if (buf == NULL) {
26  return;
27  }
28  m_buf = (int*)buf;
29  memset(&m_header, 0, sizeof(Header));
30  for (unsigned long long i = 0; i < m_nword; i++) {
31  m_buf[i] = 0;
32  }
33 }
34 
35 void EventBuffer::clear()
36 {
37  if (m_buf == NULL) return;
38  memset(&m_header, 0, sizeof(Header));
39  for (unsigned long long i = 0; i < m_nword; i++) {
40  m_buf[i] = 0;
41  }
42 }
43 
44 EventBuffer::~EventBuffer()
45 {
46  free(m_buf);
47 }
48 
49 bool EventBuffer::isWritable(int nword) throw()
50 {
51  if (m_buf == NULL) return false;
52  bool writable = m_header.nword_in - m_header.nword_out < m_nword - (nword + 1);
53  return writable;
54 }
55 
56 bool EventBuffer::isReadable() throw()
57 {
58  if (m_buf == NULL) return false;
59  bool readable = m_header.nword_in - m_header.nword_out > 0;
60  return readable;
61 }
62 
63 unsigned int EventBuffer::write(const int* buf, unsigned int nword,
64  unsigned int serial)
65 {
66  if (m_buf == NULL) return 0;
67  if (nword == 0) return 0;
68  if (nword > m_nword) return -1;
69  unsigned int i_w = 0;
70  unsigned int i_r = 0;
71  while (true) {
72  i_w = m_header.nword_in % m_nword;
73  i_r = m_header.nword_out % m_nword;
74  if ((serial == 0 || serial - 1 == m_header.count_in) &&
75  m_header.nword_in - m_header.nword_out < m_nword - (nword + 1)) {
76  if (i_w >= i_r) {
77  unsigned int count = m_nword - i_w;
78  if (nword + 1 < count) {
79  m_buf[i_w] = nword;
80  memcpy((m_buf + i_w + 1), buf, sizeof(int) * nword);
81  } else {
82  m_buf[i_w] = nword;
83  memcpy((m_buf + i_w + 1), buf, sizeof(int) * count);
84  if (nword >= count)
85  memcpy(m_buf, buf + count, sizeof(int) * (nword - count));
86  }
87  } else {
88  m_buf[i_w] = nword;
89  memcpy((m_buf + i_w + 1), buf, sizeof(int) * nword);
90  }
91  break;
92  }
93  }
94  m_header.nword_in += nword + 1;
95  unsigned int count = ++m_header.count_in;
96  return count;
97 }
98 
99 unsigned int EventBuffer::read(int* buf, EventBuffer::Header* hdr)
100 {
101  if (m_buf == NULL) return 0;
102  m_header.nreader++;
103  unsigned int i_w = 0;
104  unsigned int i_r = 0;
105  unsigned int nword = 0;
106  while (true) {
107  i_w = m_header.nword_in % m_nword;
108  i_r = m_header.nword_out % m_nword;
109  nword = m_buf[i_r];
110  if (nword > 0) {
111  if (m_header.nword_in - m_header.nword_out >= (nword + 1)) {
112  if (i_w > i_r) {
113  memcpy(buf, (m_buf + i_r + 1), sizeof(int) * nword);
114  break;
115  } else if (i_w < i_r) {
116  if (m_nword - i_r > nword) {
117  memcpy(buf, (m_buf + i_r + 1), sizeof(int) * nword);
118  break;
119  } else {
120  unsigned int count = m_nword - i_r;
121  memcpy(buf, (m_buf + i_r + 1), sizeof(int) * count);
122  if (nword > count) {
123  memcpy(buf + count, m_buf, sizeof(int) * (nword - count));
124  }
125  break;
126  }
127  }
128  }
129  }
130  }
131  m_header.nword_out += nword + 1;
132  unsigned int count = ++m_header.count_out;
133  m_header.nreader--;
134  if (hdr != NULL) {
135  memcpy(hdr, &m_header, sizeof(EventBuffer::Header));
136  }
137  return count;
138 }
Abstract base class for different kinds of events.