FairRoot/PandaRoot
MvdTestBeam/Tools/mrfdata_8b.cxx
Go to the documentation of this file.
1 /*============================================================*/
2 /* mrfdata.cpp */
3 /* MVD Readout Framework Data Storage */
4 /* M.C. Mertens */
5 /*============================================================*/
6 
7 
8 #include "mrfdata_8b.h"
9 #include "mrftools.h"
10 #include <string>
11 #include <sstream>
12 
15 using mrftools::shiftBy;
16 
17 const UInt_t TMrfData_8b::zeroval;
18 const UInt_t TMrfData_8b::bitsinablock;
19 
21 : reglengthbits(0), reglengthwords(0), lastreglengthbits(0), errcode(0) //, bitsinablock(sizeof(mrf::registertype) * CHAR_BIT)
22 {
23 }
24 
25 TMrfData_8b::TMrfData_8b(UInt_t _reglengthbits, UInt_t _reglengthwords, UInt_t _lastreglengthbits, std::vector<u_int8_t> _regdata)
26 {
27  reglengthbits = _reglengthbits;
28  reglengthwords = _reglengthwords;
29  lastreglengthbits = _lastreglengthbits;
30  regdata =_regdata;
31 
32 }
33 
34 void TMrfData_8b::setNumBits(const UInt_t& length)
35 {
36  reglengthbits = length;
37  reglengthwords = (length + bitsinablock - 1) / bitsinablock;
38  regdata.resize(reglengthwords);
40  if (lastreglengthbits) {
41  regdata.at(reglengthwords-1) &= (~((~0) << lastreglengthbits));
42  }
43 }
44 
45 const UInt_t& TMrfData_8b::getNumBits() const
46 {
47  return reglengthbits;
48 }
49 
50 void TMrfData_8b::setNumWords(const UInt_t& length)
51 {
52  reglengthwords = length;
53  reglengthbits = length * bitsinablock;
54  regdata.resize(reglengthwords);
55 }
56 
57 const UInt_t& TMrfData_8b::getNumWords() const
58 {
59  return reglengthwords;
60 }
61 
62 void TMrfData_8b::setBit(const UInt_t& position, const bool& state)
63 {
64  if ((position < reglengthbits) && (reglengthbits > 0)) {
65  /*
66  if (state) {
67  regdata.at(position / bitsinablock) |= ((mrf::registertype) 1<<(position % bitsinablock));
68  } else {
69  regdata.at(position / bitsinablock) &= (~((mrf::registertype) 1<<(position % bitsinablock))) ;
70  }
71  */
72  setIntBit(position % bitsinablock,(UInt_t&)regdata.at(position / bitsinablock), state);
73  errcode = 0;
74  } else {
76  }
77 }
78 
79 bool TMrfData_8b::getBit(const UInt_t& position) const
80 {
81  if (position < reglengthbits) {
82  errcode = 0;
83  return bool (regdata.at(position / bitsinablock) & ((u_int8_t) 1<<(position % bitsinablock)));
84  } else {
86  return false;
87  }
88 }
89 
90 const UInt_t& TMrfData_8b::appendBit(const bool& state)
91 {
93  setBit(reglengthbits - 1, state);
94  return reglengthbits;
95 }
96 
97 void TMrfData_8b::setWord(const UInt_t& position, const u_int8_t &dataword, const bool& truncate_ok)
98 {
99  // Noch aendern, um stattdessen die masked funktion mit konstanter einsmaske zu benutzen
100  if (((position < (reglengthwords - 1)) || ((position < reglengthwords) && ((reglengthbits % bitsinablock) == 0))) && (reglengthbits > 0)) {
101  regdata.at(position) = dataword;
102  errcode = 0;
103  } else if (position < reglengthwords) {
104  mrf::registertype bitmask = 1;
105  for (u_int i = 0; i < ((reglengthbits % bitsinablock) - 1); ++i) {
106  bitmask |= bitmask << 1;
107  }
108  regdata.at(position) = (dataword & bitmask);
109  if (!(dataword & (~bitmask)) || truncate_ok) {
110  //regdata.at(position) = (dataword & bitmask);
111  errcode = 0;
112  } else {
114  }
115  } else {
117  }
118 }
119 
120 void TMrfData_8b::setWordMasked(const UInt_t& position, const u_int8_t &dataword, const u_int8_t &mask, const bool& truncate_ok)
121 {
122  if (((position < (reglengthwords - 1)) || ((position < reglengthwords) && ((reglengthbits % bitsinablock) == 0))) && (reglengthbits > 0)) {
123  regdata.at(position) = dataword;
124  errcode = 0;
125  } else if (position < reglengthwords) {
126  u_int8_t bitmask = 1;
127  for (u_int i = 0; i < ((reglengthbits % bitsinablock) - 1); ++i) {
128  bitmask |= bitmask << 1;
129  }
130  //regdata.at(position) = (((dataword & mask) | (regdata.at(position) & (~ mask))) & bitmask);
131  regdata.at(position) &= (~ mask);
132  regdata.at(position) |= (dataword & mask);
133  regdata.at(position) &= bitmask;
134  if (!((dataword & mask) & (~bitmask)) || truncate_ok) {
135  //regdata.at(position) = (dataword & bitmask);
136  errcode = 0;
137  } else {
139  }
140  } else {
142  }
143 }
144 
145 const u_int8_t &TMrfData_8b::getWord(const UInt_t& position) const
146 {
147  if (position < reglengthwords) {
148  errcode = 0;
149  return regdata.at(position);
150  } else {
152  return zeroval;
153  }
154 }
155 
156 const u_int8_t &TMrfData_8b::appendWord(const u_int8_t& dataword)
157 {
158  setNumWords(getNumWords() + 1);
159  setWord(getNumWords()-1, dataword);
160  return getNumWords();
161 }
162 
163 
164 void TMrfData_8b::setBitBlock(const UInt_t& position, const UInt_t& length, const u_int8_t& value, const UInt_t& offset, const bool& reverse)
165 {
166  UInt_t i;
167  if (reverse) {
168  for (i = 0; i < length; ++i) {
169  setBit(position + length - 1 - i, getIntBit(offset + i, value));
170  }
171  } else {
172  for (i = 0; i < length; ++i) {
173  setBit(position + i, getIntBit(offset + i, value));
174  }
175  }
176 }
177 
178 const UInt_t& TMrfData_8b::getBitBlock(const UInt_t& position, const UInt_t& length, const UInt_t& offset, const bool& reverse) const
179 {
180  UInt_t i;
181  _bitblock = 0;
182  if (reverse) {
183  for (i = 0; i < length; ++i) {
184  //setBit(position + length - 1 - i, getIntBit(value, offset + i));
185  setIntBit(offset + i, _bitblock, getBit(position + length - 1 - i));
186  }
187  } else {
188  for (i = 0; i < length; ++i) {
189  //setBit(position + i, getIntBit(value, offset + i));
190  setIntBit(offset + i, _bitblock, getBit(position + i));
191  }
192  }
193  return _bitblock;
194 }
195 
196 /*
197 void TMrfData_8b::copyFragment(const UInt_t sourcestart, const UInt_t destposition, const UInt_t size, const mrf::registertype value)
198 {
199  if (destposition + size < reglengthbits) {
200  UInt_t mask;
201  mrf::registertype pattern;
202  // Data fits in one block.
203  if ((destposition % bitsinablock) + size < bitsinablock) {
204  pattern = shiftBy(sourcestart - (destposition % bitsinablock), value);
205  mask = 0;
206  for (UInt_t i = (destposition % bitsinablock); i < ((destposition % bitsinablock) + size); ++i) {
207  setIntBit(mask, i, true);
208  }
209  setWordMasked(bitInBlock(destposition), pattern, mask, false);
210  } else {
211  // Data goes to two adjacent blocks.
212  // Left pattern
213 
214  //linkes pattern:
215  //Nach rechts shiften: destpos % bitsinablock - sourcestart
216  //Soviel Nullen links: destpos % bitsinablock
217 
218  pattern = shiftBy((destposition % bitsinablock) - sourcestart, value);
219  mask = (~ 0);
220  for (UInt_t i = 0; i < (destposition % bitsinablock); ++i) {
221  setIntBit(mask, i, false);
222  }
223  setWordMasked(bitInBlock(destposition), pattern, mask, false);
224  // Right Pattern
225  pattern = shiftBy(-(bitsinablock + sourcestart - (destposition % bitsinablock)), value);
226  mask = 0;
227  for (UInt_t i = 0; i < (size + (destposition % bitsinablock) - bitsinablock); ++i) {
228  setIntBit(mask, i, true);
229  }
230  setWordMasked(bitInBlock(destposition) + 1, pattern, mask, false);
231  //linkes pattern:
232  //Nach rechts shiften: destpos % bitsinablock - sourcestart
233  //Soviel Nullen links: destpos % bitsinablock
234  //rechtes pattern:
235  //Nach links shiften: bitsinablock - leftshifts
236  // = bitsinablock + sourcestart - destpos % bitsinablock
237  //Soviel Einsen links: size - linkebits
238  // = size - (bitsinablock - destpos % bitsinablock)
239  // = size + destpos % bitsinablock - bitsinablock
240  }
241  } else {
242  errcode |= mrfdata_8b_error::out_of_bounds;
243  }
244 }
245 */
246 
247 UInt_t TMrfData_8b::bitInBlock(const UInt_t& position) const
248 {
249  return (position / bitsinablock);
250 }
251 
253 {
254  //setNumBits(0);
255  setNumWords(0);
256 }
257 
258 bool TMrfData_8b::sameDataStream(const TMrfData_8b& other) const
259 {
260  return (regdata == other.regdata);
261 }
262 
263 void TMrfData_8b::importBinString(const std::string& data, const UInt_t& offset)
264 {
265  UInt_t i;
266  UInt_t reglength = data.length();
267  if (getNumBits() < (offset + reglength)) {
268  setNumBits(offset + reglength);
269  }
270  for (i = 0; i < reglength; ++i) {
271  setBit(offset + i, (data.compare(i, 1, "1") == 0));
272  }
273 }
274 
275 //void TMrfData_8b::importHexString(const std::string data, const UInt_t offset)
276 //{
277 // //setBitBlock(position + offset);
278 //}
279 
280 const std::string& TMrfData_8b::exportBinString() const
281 {
282  u_int8_t i;
283  _data.clear();
284  for (i = 0; i < getNumBits(); ++i) {
285  if (getBit(i)) {
286  _data.append("1");
287  } else {
288  _data.append("0");
289  }
290  }
291  return _data;
292 }
293 
294 
295 //const std::string TMrfData_8b::exportHexString() const
296 //{
297 // // throw "Not implemented yet.";
298 // return "nix";
299 //}
300 
301 void TMrfData_8b::resample(const UInt_t& offset, const UInt_t& factor, const bool& reverse, const UInt_t& cutoff)
302 {
303  std::vector<u_int8_t> tmp = regdata;
304  UInt_t newlength = 0;
305  if (reverse) {
306  for (UInt_t i = offset; i < getNumBits(); i += factor) {
307  setBit((i - offset) / factor, getIntBit(bitsinablock - 1 - (i % bitsinablock), tmp.at(i / bitsinablock)));
308  ++newlength;
309  }
310  } else {
311  for (UInt_t i = offset; i < getNumBits(); i += factor) {
312  setBit((i - offset) / factor, getIntBit(i % bitsinablock, tmp.at(i / bitsinablock)));
313  ++newlength;
314  }
315  }
316  if (cutoff == 0) {
317  setNumBits(newlength);
318  } else {
319  setNumBits(cutoff);
320  }
321 }
322 
323 const UInt_t& TMrfData_8b::getLastError() const
324 {
325  return errcode;
326 }
327 
329 {
330  return !(errcode);
331 }
332 
333 
334 
335 
336 
337 
338 
339 
Int_t i
Definition: run_full.C:25
void setNumWords(const UInt_t &length)
Sets the length of the register to lengths words.
void setWordMasked(const UInt_t &position, const UChar_t &dataword, const UChar_t &mask=~0, const bool &truncate_ok=false)
Sets a subset of bits in a word based on a mask.
void setBit(const UInt_t &position, const bool &state)
Sets or resets the bit at position.
TVector3 offset(2, 0, 0)
const UInt_t & appendBit(const bool &state)
Appends a bit to the data stream.
UInt_t shiftBy(const int &positions, const UInt_t &value)
Shifts the bits in an integer value.
bool lastActionSuccessful() const
Returns True if the last action completed successfullly, False otherwise.
static const UInt_t bitsinablock
Number of bits stored in each data word.
const std::string & exportBinString() const
Exports a data stream to a string representing binary digits.
void resample(const UInt_t &offset, const UInt_t &factor, const bool &reverse=false, const UInt_t &cutoff=0)
Extracts binary data from returned oversampled data.
const UInt_t & getNumBits() const
Retrieves the length of the register in bits.
void setBitBlock(const UInt_t &position, const UInt_t &length, const UChar_t &value, const UInt_t &offset=0, const bool &reverse=false)
Sets a bit block of given length to the least significant bits of value.
Base interface class for data storage and manipulation. Compatible with IO classes from MRF Suite...
std::vector< UChar_t > regdata
Internal storage for data structure.
UInt_t registertype
Register content data type.
void setWord(const UInt_t &position, const UChar_t &dataword, const bool &truncate_ok=false)
Sets a complete data word at position to value.
void clearDataStream()
Sets a bitfield within the data storage based on the configuration stored in the map parameter bitmap...
const UInt_t & getBitBlock(const UInt_t &position, const UInt_t &length, const UInt_t &offset=0, const bool &reverse=false) const
UInt_t bitInBlock(const UInt_t &position) const
Returns the word index which holds bit position.
const UChar_t & getWord(const UInt_t &position) const
Retrieves the word found at position.
void setNumBits(const UInt_t &length)
Sets the length of the binary data stream.
void importBinString(const std::string &data, const UInt_t &offset=0)
Imports a data stream from a string representing binary digits.
UInt_t errcode
Internal error code.
const UInt_t & getLastError() const
Returns an integer with errorflags of all errors occured after last successful command.
const UChar_t & appendWord(const UChar_t &dataword)
bool getIntBit(const UInt_t &position, const UInt_t &value)
Retrieves a single bit from an integer value.
bool getBit(const UInt_t &position) const
Determines if bit at position is set.
void setIntBit(const UInt_t &position, UInt_t &value, const bool &state)
Sets a single bit in an integer value.
const UInt_t & getNumWords() const
Retrieves the length of the register in words.
bool sameDataStream(const TMrfData_8b &other) const
Checks data streams for equality.