artdaq_core  v3_05_10
Fragment_t.cc
1 #include "artdaq-core/Data/Fragment.hh"
2 #include "artdaq-core/Data/detail/RawFragmentHeader.hh"
3 
4 #define BOOST_TEST_MODULE(Fragment_t)
5 #include "cetlib/quiet_unit_test.hpp"
6 
11 {
12  uint64_t field1;
13  uint32_t field2;
14  uint32_t field3;
15 };
16 
21 {
22  uint64_t field1;
23  uint32_t field2;
24  uint32_t field3;
25  uint64_t field4;
26  uint16_t field5;
27 };
28 
33 {
34  uint64_t fields[300];
35 };
36 
37 BOOST_AUTO_TEST_SUITE(Fragment_test)
38 
39 BOOST_AUTO_TEST_CASE(Construct)
40 {
41  // 01-Mar-2013, KAB - I'm constructing these tests based on the
42  // constructors that I already see in the class, but I have to
43  // wonder if these truly correspond to the behavior that we want.
45  BOOST_REQUIRE_EQUAL(f1.dataSize(), (size_t)0);
46  BOOST_REQUIRE_EQUAL(f1.size(), (size_t)artdaq::detail::RawFragmentHeader::num_words());
51  BOOST_REQUIRE_EQUAL(f1.hasMetadata(), false);
52 
53  artdaq::Fragment f2(7);
54  BOOST_REQUIRE_EQUAL(f2.dataSize(), (size_t)7);
55  BOOST_REQUIRE_EQUAL(f2.size(), (size_t)artdaq::detail::RawFragmentHeader::num_words() + 7);
57  BOOST_REQUIRE(f2.type() == artdaq::Fragment::InvalidFragmentType);
58  BOOST_REQUIRE(f2.sequenceID() == artdaq::Fragment::InvalidSequenceID);
59  BOOST_REQUIRE(f2.fragmentID() == artdaq::Fragment::InvalidFragmentID);
60  BOOST_REQUIRE_EQUAL(f2.hasMetadata(), false);
61 
62  artdaq::Fragment f3(101, 202);
63  BOOST_REQUIRE_EQUAL(f3.dataSize(), (size_t)0);
64  BOOST_REQUIRE_EQUAL(f3.size(), (size_t)artdaq::detail::RawFragmentHeader::num_words());
66  BOOST_REQUIRE(f3.type() == artdaq::Fragment::DataFragmentType);
67  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (artdaq::Fragment::sequence_id_t)101);
68  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (artdaq::Fragment::fragment_id_t)202);
69  BOOST_REQUIRE_EQUAL(f3.hasMetadata(), false);
70 
71  // Verify that only "user" fragment types may be specified
72  // in the constructor
73  try
74  {
75  artdaq::Fragment frag(101, 202, 0);
76  BOOST_REQUIRE(0 && "Should have thrown exception");
77  }
78  catch (cet::exception const& excpt)
79  {}
80  catch (...)
81  {
82  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
83  }
84 
85  try
86  {
87  artdaq::Fragment frag(101, 202, 225);
88  BOOST_REQUIRE(0 && "Should have thrown exception");
89  }
90  catch (cet::exception const& excpt)
91  {}
92  catch (...)
93  {
94  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
95  }
96 
97  try
98  {
99  artdaq::Fragment frag(101, 202, 255);
100  BOOST_REQUIRE(0 && "Should have thrown exception");
101  }
102  catch (cet::exception const& excpt)
103  {}
104  catch (...)
105  {
106  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
107  }
108 
109  try
110  {
112  BOOST_REQUIRE(0 && "Should have thrown exception");
113  }
114  catch (cet::exception const& excpt)
115  {}
116  catch (...)
117  {
118  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
119  }
120 
121  try
122  {
125  BOOST_REQUIRE(0 && "Should have thrown exception");
126  }
127  catch (cet::exception const& excpt)
128  {}
129  catch (...)
130  {
131  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
132  }
133 
134  try
135  {
138  BOOST_REQUIRE(0 && "Should have thrown exception");
139  }
140  catch (cet::exception const& excpt)
141  {}
142  catch (...)
143  {
144  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
145  }
146 
147  try
148  {
153  artdaq::Fragment fragC(101, 202, 1);
154  artdaq::Fragment fragD(101, 202, 2);
155  artdaq::Fragment fragE(101, 202, 3);
156  artdaq::Fragment fragF(101, 202, 100);
157  artdaq::Fragment fragG(101, 202, 200);
158  artdaq::Fragment fragH(101, 202, 224);
159  }
160  catch (...)
161  {
162  BOOST_REQUIRE(0 && "Should not have thrown exception");
163  }
164 }
165 
166 BOOST_AUTO_TEST_CASE(FragmentType)
167 {
168  artdaq::Fragment frag(15);
169 
170  // test "user" fragment types
171  try
172  {
173  frag.setUserType(0);
174  BOOST_REQUIRE(0 && "Should have thrown exception");
175  }
176  catch (cet::exception const& excpt)
177  {}
178  catch (...)
179  {
180  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
181  }
182 
183  try
184  {
185  frag.setUserType(225);
186  BOOST_REQUIRE(0 && "Should have thrown exception");
187  }
188  catch (cet::exception const& excpt)
189  {}
190  catch (...)
191  {
192  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
193  }
194 
195  try
196  {
197  frag.setUserType(255);
198  BOOST_REQUIRE(0 && "Should have thrown exception");
199  }
200  catch (cet::exception const& excpt)
201  {}
202  catch (...)
203  {
204  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
205  }
206 
207  try
208  {
209  frag.setUserType(artdaq::Fragment::InvalidFragmentType);
210  BOOST_REQUIRE(0 && "Should have thrown exception");
211  }
212  catch (cet::exception const& excpt)
213  {}
214  catch (...)
215  {
216  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
217  }
218 
219  try
220  {
222  BOOST_REQUIRE(0 && "Should have thrown exception");
223  }
224  catch (cet::exception const& excpt)
225  {}
226  catch (...)
227  {
228  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
229  }
230 
231  try
232  {
234  BOOST_REQUIRE(0 && "Should have thrown exception");
235  }
236  catch (cet::exception const& excpt)
237  {}
238  catch (...)
239  {
240  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
241  }
242 
243  try
244  {
247  frag.setUserType(1);
248  frag.setUserType(2);
249  frag.setUserType(3);
250  frag.setUserType(100);
251  frag.setUserType(200);
252  frag.setUserType(224);
253  }
254  catch (...)
255  {
256  BOOST_REQUIRE(0 && "Should not have thrown exception");
257  }
258 
259  // test "system" fragment types
260  try
261  {
262  frag.setSystemType(0);
263  BOOST_REQUIRE(0 && "Should have thrown exception");
264  }
265  catch (cet::exception const& excpt)
266  {}
267  catch (...)
268  {
269  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
270  }
271 
272  try
273  {
274  frag.setSystemType(1);
275  BOOST_REQUIRE(0 && "Should have thrown exception");
276  }
277  catch (cet::exception const& excpt)
278  {}
279  catch (...)
280  {
281  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
282  }
283 
284  try
285  {
286  frag.setSystemType(224);
287  BOOST_REQUIRE(0 && "Should have thrown exception");
288  }
289  catch (cet::exception const& excpt)
290  {}
291  catch (...)
292  {
293  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
294  }
295 
296  try
297  {
298  frag.setSystemType(artdaq::Fragment::InvalidFragmentType);
299  BOOST_REQUIRE(0 && "Should have thrown exception");
300  }
301  catch (cet::exception const& excpt)
302  {}
303  catch (...)
304  {
305  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
306  }
307 
308  try
309  {
311  BOOST_REQUIRE(0 && "Should have thrown exception");
312  }
313  catch (cet::exception const& excpt)
314  {}
315  catch (...)
316  {
317  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
318  }
319 
320  try
321  {
323  BOOST_REQUIRE(0 && "Should have thrown exception");
324  }
325  catch (cet::exception const& excpt)
326  {}
327  catch (...)
328  {
329  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
330  }
331 
332  try
333  {
336  frag.setSystemType(225);
337  frag.setSystemType(230);
338  frag.setSystemType(240);
339  frag.setSystemType(250);
340  frag.setSystemType(255);
341  }
342  catch (...)
343  {
344  BOOST_REQUIRE(0 && "Should not have thrown exception");
345  }
346 }
347 
348 BOOST_AUTO_TEST_CASE(SequenceID)
349 {
350  artdaq::Fragment f1;
351  f1.setSequenceID(0);
352  BOOST_REQUIRE_EQUAL(f1.sequenceID(), (uint64_t)0);
353  f1.setSequenceID(1);
354  BOOST_REQUIRE_EQUAL(f1.sequenceID(), (uint64_t)1);
355  f1.setSequenceID(0xffff);
356  BOOST_REQUIRE_EQUAL(f1.sequenceID(), (uint64_t)0xffff);
357  f1.setSequenceID(0x0000ffffffffffff);
358  BOOST_REQUIRE_EQUAL(f1.sequenceID(), (uint64_t)0x0000ffffffffffff);
359 
360  artdaq::Fragment f2(0x12345, 0xab);
361  BOOST_REQUIRE_EQUAL(f2.sequenceID(), (uint64_t)0x12345);
362 
363  artdaq::Fragment f3(0x0000567812345678, 0xab);
364  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (uint64_t)0x0000567812345678);
365 }
366 
367 BOOST_AUTO_TEST_CASE(FragmentID)
368 {
369  artdaq::Fragment f1;
370  f1.setFragmentID(0);
371  BOOST_REQUIRE_EQUAL(f1.fragmentID(), (uint16_t)0);
372  f1.setFragmentID(1);
373  BOOST_REQUIRE_EQUAL(f1.fragmentID(), (uint16_t)1);
374  f1.setFragmentID(0xffff);
375  BOOST_REQUIRE_EQUAL(f1.fragmentID(), (uint16_t)0xffff);
376 
377  artdaq::Fragment f2(0x12345, 0xab);
378  BOOST_REQUIRE_EQUAL(f2.fragmentID(), (uint16_t)0xab);
379 
380  artdaq::Fragment f3(0x0000567812345678, 0xffff);
381  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (uint16_t)0xffff);
382 }
383 
384 BOOST_AUTO_TEST_CASE(Resize)
385 {
386  // basic fragment
387  artdaq::Fragment f1;
388  f1.resize(1234);
389  BOOST_REQUIRE_EQUAL(f1.dataSize(), (size_t)1234);
390  BOOST_REQUIRE_EQUAL(f1.size(), (size_t)1234 +
392 
393  // fragment with metadata
394  MetadataTypeOne mdOneA;
395  artdaq::Fragment f2(1, 123, 3, 5, mdOneA);
396  f2.resize(129);
397  BOOST_REQUIRE_EQUAL(f2.dataSize(), (size_t)129);
398  BOOST_REQUIRE_EQUAL(f2.size(), (size_t)129 + 2 +
400 }
401 
402 BOOST_AUTO_TEST_CASE(Empty)
403 {
404  artdaq::Fragment f1;
405  BOOST_REQUIRE_EQUAL(f1.empty(), true);
406  f1.resize(1234);
407  BOOST_REQUIRE_EQUAL(f1.empty(), false);
408 
409  MetadataTypeOne mdOneA;
410  artdaq::Fragment f2(1, 123, 3, 5, mdOneA);
411  BOOST_REQUIRE_EQUAL(f2.empty(), false);
412  f2.resize(129);
413  BOOST_REQUIRE_EQUAL(f2.empty(), false);
414  f2.resize(0);
415  BOOST_REQUIRE_EQUAL(f2.empty(), true);
416  BOOST_REQUIRE_EQUAL(f2.dataSize(), (size_t)0);
417  BOOST_REQUIRE_EQUAL(f2.size(), (size_t)2 +
419 
420  artdaq::Fragment f3;
421  BOOST_REQUIRE_EQUAL(f3.empty(), true);
422  f3.setMetadata(mdOneA);
423  BOOST_REQUIRE_EQUAL(f3.empty(), true);
424 
425  artdaq::Fragment f4(14);
426  BOOST_REQUIRE_EQUAL(f4.empty(), false);
427  f4.setMetadata(mdOneA);
428  BOOST_REQUIRE_EQUAL(f4.empty(), false);
429 }
430 
431 BOOST_AUTO_TEST_CASE(Clear)
432 {
433  artdaq::Fragment f1;
434  BOOST_REQUIRE_EQUAL(f1.empty(), true);
435  f1.resize(1234);
436  BOOST_REQUIRE_EQUAL(f1.empty(), false);
437  f1.clear();
438  BOOST_REQUIRE_EQUAL(f1.empty(), true);
439 
440  MetadataTypeOne mdOneA;
441  artdaq::Fragment f2(1, 123, 3, 5, mdOneA);
442  BOOST_REQUIRE_EQUAL(f2.empty(), false);
443  f2.resize(129);
444  BOOST_REQUIRE_EQUAL(f2.empty(), false);
445  f2.clear();
446  BOOST_REQUIRE_EQUAL(f2.empty(), true);
447  BOOST_REQUIRE_EQUAL(f2.dataSize(), (size_t)0);
448  BOOST_REQUIRE_EQUAL(f2.size(), (size_t)2 +
450 
451  artdaq::Fragment f3;
452  BOOST_REQUIRE_EQUAL(f3.empty(), true);
453  BOOST_REQUIRE_EQUAL(f3.hasMetadata(), false);
454  f3.setMetadata(mdOneA);
455  BOOST_REQUIRE_EQUAL(f3.empty(), true);
456  BOOST_REQUIRE_EQUAL(f3.hasMetadata(), true);
457  f3.clear();
458  BOOST_REQUIRE_EQUAL(f3.empty(), true);
459  BOOST_REQUIRE_EQUAL(f3.hasMetadata(), true);
460 
461  artdaq::Fragment f4(14);
462  BOOST_REQUIRE_EQUAL(f4.empty(), false);
463  BOOST_REQUIRE_EQUAL(f4.hasMetadata(), false);
464  f4.setMetadata(mdOneA);
465  BOOST_REQUIRE_EQUAL(f4.empty(), false);
466  BOOST_REQUIRE_EQUAL(f4.hasMetadata(), true);
467  f4.clear();
468  BOOST_REQUIRE_EQUAL(f4.empty(), true);
469  BOOST_REQUIRE_EQUAL(f4.hasMetadata(), true);
470 }
471 
472 BOOST_AUTO_TEST_CASE(Addresses)
473 {
474  // no metadata
475  artdaq::Fragment f1(200);
476  BOOST_REQUIRE_EQUAL(f1.dataSize(), (size_t)200);
477  BOOST_REQUIRE_EQUAL(f1.size(), (size_t)200 +
479  artdaq::RawDataType* haddr = f1.headerAddress();
480  artdaq::RawDataType* daddr = f1.dataAddress();
481  BOOST_REQUIRE_EQUAL(daddr,
483  try
484  {
485  f1.metadataAddress();
486  BOOST_REQUIRE(0 && "Should have thrown exception");
487  }
488  catch (cet::exception const& excpt)
489  {}
490  catch (...)
491  {
492  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
493  }
494  BOOST_REQUIRE_EQUAL(haddr, &(*(f1.headerBegin())));
495  BOOST_REQUIRE_EQUAL(daddr, &(*(f1.dataBegin())));
496  BOOST_REQUIRE_EQUAL(daddr + 200, &(*(f1.dataEnd())));
497 
498  // metadata with integer number of longwords
499  MetadataTypeOne mdOneA;
500  artdaq::Fragment f2(135, 101, 0, 3, mdOneA);
501  BOOST_REQUIRE_EQUAL(f2.dataSize(), (size_t)135);
502  BOOST_REQUIRE_EQUAL(f2.size(), (size_t)135 + 2 +
504  haddr = f2.headerAddress();
505  daddr = f2.dataAddress();
506  artdaq::RawDataType* maddr = f2.metadataAddress();
507  BOOST_REQUIRE_EQUAL(maddr, haddr +
509  BOOST_REQUIRE_EQUAL(daddr, maddr + 2);
510  BOOST_REQUIRE_EQUAL(haddr, &(*(f2.headerBegin())));
511  BOOST_REQUIRE_EQUAL(daddr, &(*(f2.dataBegin())));
512  BOOST_REQUIRE_EQUAL(daddr + 135, &(*(f2.dataEnd())));
513 
514  // metadata with fractional number of longwords
515  MetadataTypeTwo mdTwoA;
516  artdaq::Fragment f3(77, 101, 0, 3, mdTwoA);
517  BOOST_REQUIRE_EQUAL(f3.dataSize(), (size_t)77);
518  BOOST_REQUIRE_EQUAL(f3.size(), (size_t)77 + 4 +
520  haddr = f3.headerAddress();
521  daddr = f3.dataAddress();
522  maddr = f3.metadataAddress();
523  BOOST_REQUIRE_EQUAL(maddr, haddr +
525  BOOST_REQUIRE_EQUAL(daddr, maddr + 4);
526  BOOST_REQUIRE_EQUAL(haddr, &(*(f3.headerBegin())));
527  BOOST_REQUIRE_EQUAL(daddr, &(*(f3.dataBegin())));
528  BOOST_REQUIRE_EQUAL(daddr + 77, &(*(f3.dataEnd())));
529 }
530 
531 BOOST_AUTO_TEST_CASE(Metadata)
532 {
533  artdaq::Fragment f1(42);
534  BOOST_REQUIRE_EQUAL(f1.hasMetadata(), false);
535  try
536  {
538  BOOST_REQUIRE(0 && "Should have thrown exception");
539  }
540  catch (cet::exception const& excpt)
541  {}
542  catch (...)
543  {
544  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
545  }
546 
547  MetadataTypeOne mdOneA;
548  mdOneA.field1 = 5;
549  mdOneA.field2 = 10;
550  mdOneA.field3 = 15;
551 
552  try
553  {
554  f1.updateMetadata(mdOneA);
555  BOOST_REQUIRE(0 && "Should have thrown exception");
556  }
557  catch (cet::exception const& excpt)
558  {}
559  catch (...)
560  {
561  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
562  }
563 
564  f1.setMetadata(mdOneA);
565  MetadataTypeOne* mdOnePtr = f1.metadata<MetadataTypeOne>();
566  BOOST_REQUIRE_EQUAL(mdOnePtr->field1, (uint64_t)5);
567  BOOST_REQUIRE_EQUAL(mdOnePtr->field2, (uint32_t)10);
568  BOOST_REQUIRE_EQUAL(mdOnePtr->field3, (uint32_t)15);
569 
570  try
571  {
572  MetadataTypeOne mdOneB;
573  f1.setMetadata(mdOneB);
574  BOOST_REQUIRE(0 && "Should have thrown exception");
575  }
576  catch (cet::exception const& excpt)
577  {}
578  catch (...)
579  {
580  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
581  }
582 
583  f1.updateMetadata(*mdOnePtr);
584 
585  MetadataTypeTwo mdTwoA;
586  mdTwoA.field1 = 10;
587  mdTwoA.field2 = 20;
588  mdTwoA.field3 = 30;
589  mdTwoA.field4 = 40;
590  mdTwoA.field5 = 50;
591 
592  try
593  {
594  f1.updateMetadata(mdTwoA);
595  BOOST_REQUIRE(0 && "Should have thrown exception");
596  }
597  catch (cet::exception const& excpt)
598  {}
599  catch (...)
600  {
601  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
602  }
603 
604  artdaq::Fragment f2(10, 1, 2, 3, mdTwoA);
605  MetadataTypeTwo* mdTwoPtr = f2.metadata<MetadataTypeTwo>();
606  BOOST_REQUIRE_EQUAL(mdTwoPtr->field1, (uint64_t)10);
607  BOOST_REQUIRE_EQUAL(mdTwoPtr->field2, (uint32_t)20);
608  BOOST_REQUIRE_EQUAL(mdTwoPtr->field3, (uint32_t)30);
609  BOOST_REQUIRE_EQUAL(mdTwoPtr->field4, (uint32_t)40);
610  BOOST_REQUIRE_EQUAL(mdTwoPtr->field5, (uint32_t)50);
611 
612  artdaq::Fragment f3(0xabcdef, 0xc3a5, 123);
613  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (uint32_t)0xabcdef);
614  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (uint16_t)0xc3a5);
615  BOOST_REQUIRE_EQUAL(f3.type(), (uint16_t)123);
616  f3.resize(5);
617  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (uint32_t)0xabcdef);
618  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (uint16_t)0xc3a5);
619  BOOST_REQUIRE_EQUAL(f3.type(), (uint8_t)123);
620  artdaq::RawDataType* dataPtr = f3.dataAddress();
621  dataPtr[0] = 0x12345678;
622  dataPtr[1] = 0xabcd;
623  dataPtr[2] = 0x456789ab;
624  dataPtr[3] = 0x3c3c3c3c;
625  dataPtr[4] = 0x5a5a5a5a;
626  BOOST_REQUIRE_EQUAL(dataPtr[0], (uint64_t)0x12345678);
627  BOOST_REQUIRE_EQUAL(dataPtr[1], (uint64_t)0xabcd);
628  BOOST_REQUIRE_EQUAL(dataPtr[2], (uint64_t)0x456789ab);
629  BOOST_REQUIRE_EQUAL(dataPtr[3], (uint64_t)0x3c3c3c3c);
630  BOOST_REQUIRE_EQUAL(dataPtr[4], (uint64_t)0x5a5a5a5a);
631  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (uint32_t)0xabcdef);
632  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (uint16_t)0xc3a5);
633  BOOST_REQUIRE_EQUAL(f3.type(), (uint8_t)123);
634  MetadataTypeOne mdOneC;
635  mdOneC.field1 = 505;
636  mdOneC.field2 = 510;
637  mdOneC.field3 = 515;
638  f3.setMetadata(mdOneC);
639  mdOnePtr = f3.metadata<MetadataTypeOne>();
640  BOOST_REQUIRE_EQUAL(mdOnePtr->field1, (uint64_t)505);
641  BOOST_REQUIRE_EQUAL(mdOnePtr->field2, (uint32_t)510);
642  BOOST_REQUIRE_EQUAL(mdOnePtr->field3, (uint32_t)515);
643  BOOST_REQUIRE_EQUAL(f3.sequenceID(), (uint32_t)0xabcdef);
644  BOOST_REQUIRE_EQUAL(f3.fragmentID(), (uint16_t)0xc3a5);
645  BOOST_REQUIRE_EQUAL(f3.type(), (uint8_t)123);
646  dataPtr = f3.dataAddress();
647  dataPtr[0] = 0x12345678;
648  dataPtr[1] = 0xabcd;
649  dataPtr[2] = 0x456789ab;
650  dataPtr[3] = 0x3c3c3c3c;
651  dataPtr[4] = 0x5a5a5a5a;
652  BOOST_REQUIRE_EQUAL(dataPtr[0], (uint64_t)0x12345678);
653  BOOST_REQUIRE_EQUAL(dataPtr[1], (uint64_t)0xabcd);
654  BOOST_REQUIRE_EQUAL(dataPtr[2], (uint64_t)0x456789ab);
655  BOOST_REQUIRE_EQUAL(dataPtr[3], (uint64_t)0x3c3c3c3c);
656  BOOST_REQUIRE_EQUAL(dataPtr[4], (uint64_t)0x5a5a5a5a);
657 
658  MetadataTypeHuge mdHuge;
659  artdaq::Fragment f4(19);
660  BOOST_REQUIRE_EQUAL(f4.hasMetadata(), false);
661  try
662  {
663  f4.setMetadata(mdHuge);
664  BOOST_REQUIRE(0 && "Should have thrown exception");
665  }
666  catch (cet::exception const& excpt)
667  {}
668  catch (...)
669  {
670  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
671  }
672 
673  try
674  {
675  artdaq::Fragment f5(127, 1, 2, 3, mdHuge);
676  BOOST_REQUIRE(0 && "Should have thrown exception");
677  }
678  catch (cet::exception const& excpt)
679  {}
680  catch (...)
681  {
682  BOOST_REQUIRE(0 && "Should have thrown cet::exception");
683  }
684 }
685 
686 // JCF, 4/15/14 -- perform a set of tests concerning the new
687 // byte-by-byte interface functions added to artdaq::Fragment
688 
689 BOOST_AUTO_TEST_CASE(Bytes)
690 {
691  std::size_t payload_size = 5;
692 
693  // seqID, fragID, type are all random
696  artdaq::Fragment::type_t type = 3;
697 
698  // No explicit constructor necessary for Metadata -- all we care
699  // about is its size in the artdaq::Fragment, not its values
700 
701  struct Metadata
702  {
703  uint8_t byteOne;
704  uint8_t byteTwo;
705  uint8_t byteThree;
706  };
707 
708  Metadata theMetadata;
709 
710  BOOST_REQUIRE(sizeof(artdaq::Fragment::byte_t) == 1);
711 
712  // Assumption in some of the arithmetic below is that RawDataType is 8 bytes
713  BOOST_REQUIRE(sizeof(artdaq::RawDataType) == 8);
714 
715  // Check that the factory function and the explicit constructor
716  // methods of creating a fragment yield identical results IF the
717  // number of bytes passed to FragmentBytes() is a multiple of the
718  // size of the RawDataType
719 
720  std::unique_ptr<artdaq::Fragment> f1(new artdaq::Fragment(payload_size));
721  std::unique_ptr<artdaq::Fragment> f1_factory(artdaq::Fragment::FragmentBytes(
722  payload_size * sizeof(artdaq::RawDataType)));
723 
724  BOOST_REQUIRE(f1->size() == f1_factory->size());
725  BOOST_REQUIRE(f1->sizeBytes() == f1_factory->sizeBytes());
726 
727  std::unique_ptr<artdaq::Fragment> f2(new artdaq::Fragment(payload_size, seqID, fragID, type, theMetadata));
728  std::unique_ptr<artdaq::Fragment> f2_factory(artdaq::Fragment::FragmentBytes(
729  payload_size * sizeof(artdaq::RawDataType),
730  seqID, fragID,
731  type, theMetadata));
732 
733  BOOST_REQUIRE(f2->size() == f2_factory->size());
734  BOOST_REQUIRE(f2->sizeBytes() == f2_factory->sizeBytes());
735 
736  // Now let's make sure that data gets aligned as expected (i.e.,
737  // along boundaries separated by sizeof(RawDataType) bytes)
738 
739  std::size_t offset = 3;
740  std::unique_ptr<artdaq::Fragment> f3_factory(artdaq::Fragment::FragmentBytes(
741  payload_size * sizeof(artdaq::RawDataType) - offset,
742  seqID, fragID,
743  type, theMetadata));
744 
745  BOOST_REQUIRE(f3_factory->size() == f2->size());
746  BOOST_REQUIRE(f3_factory->sizeBytes() == f2->sizeBytes());
747 
748  // Make certain dataBegin(), dataBeginBytes() and the
749  // (now-deprecated, but still in legacy code) dataAddress() point to
750  // the same region in memory, i.e., the start of the payload
751 
752  artdaq::Fragment::byte_t* ptr1 = reinterpret_cast<artdaq::Fragment::byte_t*>(
753  &*f3_factory->dataBegin());
754 
755  artdaq::Fragment::byte_t* ptr2 = f3_factory->dataBeginBytes();
756 
757  artdaq::Fragment::byte_t* ptr3 = reinterpret_cast<artdaq::Fragment::byte_t*>(f3_factory->dataAddress());
758 
759  BOOST_REQUIRE_EQUAL(ptr1, ptr2);
760  BOOST_REQUIRE_EQUAL(ptr2, ptr3);
761 
762  // Make sure metadata struct gets aligned
763  // header == 3 RawDataTypes, metadata is 3 bytes (rounds up to 1 RawDataType)
764  BOOST_REQUIRE(f3_factory->dataBeginBytes() -
765  reinterpret_cast<artdaq::Fragment::byte_t*>(
766  &*f3_factory->headerBegin()) ==
768 
769  // Sanity check for the payload size
770  BOOST_REQUIRE(static_cast<std::size_t>(f3_factory->dataEndBytes() - f3_factory->dataBeginBytes()) == f3_factory->dataSizeBytes());
771 
772  // Check resizing
773  artdaq::Fragment f4(payload_size);
774  BOOST_REQUIRE_EQUAL(f4.dataSize(), payload_size);
775  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), (payload_size * sizeof(artdaq::RawDataType)));
776  f4.resize(payload_size + 1);
777  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 1));
778  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 1) * sizeof(artdaq::RawDataType)));
779  f4.resizeBytes(f4.dataSizeBytes() + 2);
780  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 2));
781  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 2) * sizeof(artdaq::RawDataType)));
782  f4.resizeBytes(f4.dataSizeBytes() + 1);
783  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 3));
784  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 3) * sizeof(artdaq::RawDataType)));
785  f4.resizeBytes(f4.dataSizeBytes() + 1);
786  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 4));
787  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 4) * sizeof(artdaq::RawDataType)));
788 
789  size_t targetSize = (payload_size + 4) * sizeof(artdaq::RawDataType);
790  ++targetSize;
791  f4.resizeBytes(targetSize);
792  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
793  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
794  ++targetSize;
795  f4.resizeBytes(targetSize);
796  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
797  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
798  ++targetSize;
799  f4.resizeBytes(targetSize);
800  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
801  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
802  ++targetSize;
803  f4.resizeBytes(targetSize);
804  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
805  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
806  ++targetSize;
807  f4.resizeBytes(targetSize);
808  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
809  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
810  ++targetSize;
811  f4.resizeBytes(targetSize);
812  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
813  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
814  ++targetSize;
815  f4.resizeBytes(targetSize);
816  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
817  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
818  ++targetSize;
819  f4.resizeBytes(targetSize);
820  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 5));
821  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 5) * sizeof(artdaq::RawDataType)));
822  ++targetSize;
823  f4.resizeBytes(targetSize);
824  BOOST_REQUIRE_EQUAL(f4.dataSize(), (payload_size + 6));
825  BOOST_REQUIRE_EQUAL(f4.dataSizeBytes(), ((payload_size + 6) * sizeof(artdaq::RawDataType)));
826 
827  // Check adding metadata after construction
828  artdaq::Fragment f5(payload_size);
829  BOOST_REQUIRE_EQUAL(f5.size(), (payload_size + artdaq::detail::RawFragmentHeader::num_words()));
830  BOOST_REQUIRE_EQUAL(f5.sizeBytes(), ((payload_size + artdaq::detail::RawFragmentHeader::num_words()) * sizeof(artdaq::RawDataType)));
831  f5.setMetadata(theMetadata);
832  BOOST_REQUIRE_EQUAL(f5.dataSize(), payload_size);
833  BOOST_REQUIRE_EQUAL(f5.dataSizeBytes(), (payload_size * sizeof(artdaq::RawDataType)));
834  BOOST_REQUIRE_EQUAL(f5.size(), (payload_size + 1 + artdaq::detail::RawFragmentHeader::num_words()));
835  BOOST_REQUIRE_EQUAL(f5.sizeBytes(), ((payload_size + 1 + artdaq::detail::RawFragmentHeader::num_words()) * sizeof(artdaq::RawDataType)));
836 }
837 
838 BOOST_AUTO_TEST_CASE(Upgrade_V0)
839 {
840  artdaq::Fragment f(7);
842 
844  hdr0.version = 0;
845  hdr0.type = 0xFE;
846  hdr0.metadata_word_count = 0;
847 
848  hdr0.sequence_id = 0xFEEDDEADBEEF;
849  hdr0.fragment_id = 0xBEE7;
850  hdr0.timestamp = 0xCAFEFECA;
851 
852  hdr0.unused1 = 0xF0F0;
853  hdr0.unused2 = 0xC5C5;
854 
855  memcpy(f.headerBeginBytes(), &hdr0, sizeof(hdr0));
856 
859  {
860  memcpy(f.headerBegin() + ii, &(++counter), sizeof(counter));
861  }
862 
863  BOOST_REQUIRE_EQUAL(f.version(), 0);
864  BOOST_REQUIRE_EQUAL(f.type(), 0xFE);
865  BOOST_REQUIRE_EQUAL(f.hasMetadata(), false);
866 
867  BOOST_REQUIRE_EQUAL(f.sequenceID(), 0xFEEDDEADBEEF);
868  BOOST_REQUIRE_EQUAL(f.fragmentID(), 0xBEE7);
869  BOOST_REQUIRE_EQUAL(f.timestamp(), 0xCAFEFECA);
870 
871  for (size_t jj = 0; jj < f.dataSize(); ++jj)
872  {
873  BOOST_REQUIRE_EQUAL(*(f.dataBegin() + jj), jj + 1);
874  }
875 }
876 
877 BOOST_AUTO_TEST_CASE(Upgrade_V1)
878 {
879  artdaq::Fragment f(7);
881 
883  hdr1.version = 1;
884  hdr1.type = 0xFE;
885  hdr1.metadata_word_count = 0;
886 
887  hdr1.sequence_id = 0xFEEDDEADBEEF;
888  hdr1.fragment_id = 0xBEE7;
889  hdr1.timestamp = 0xCAFEFECAAAAABBBB;
890 
891  memcpy(f.headerBeginBytes(), &hdr1, sizeof(hdr1));
892 
895  {
896  memcpy(f.headerBegin() + ii, &(++counter), sizeof(counter));
897  }
898 
899  BOOST_REQUIRE_EQUAL(f.version(), 1);
900  BOOST_REQUIRE_EQUAL(f.type(), 0xFE);
901  BOOST_REQUIRE_EQUAL(f.hasMetadata(), false);
902 
903  BOOST_REQUIRE_EQUAL(f.sequenceID(), 0xFEEDDEADBEEF);
904  BOOST_REQUIRE_EQUAL(f.fragmentID(), 0xBEE7);
905  BOOST_REQUIRE_EQUAL(f.timestamp(), 0xCAFEFECAAAAABBBB);
906 
907  for (size_t jj = 0; jj < f.dataSize(); ++jj)
908  {
909  BOOST_REQUIRE_EQUAL(*(f.dataBegin() + jj), jj + 1);
910  }
911 }
912 
913 BOOST_AUTO_TEST_SUITE_END()
RawDataType metadata_word_count
The number of RawDataType words in the user-defined metadata.
uint32_t field2
Definition: Fragment_t.cc:23
static constexpr type_t FIRST_SYSTEM_TYPE
The first system type.
static constexpr type_t InvalidFragmentType
Copy InvalidFragmentType from RawFragmentHeader.
Definition: Fragment.hh:147
uint32_t field2
Definition: Fragment_t.cc:13
void setSequenceID(sequence_id_t sequence_id)
Sets the Sequence ID of the Fragment.
Definition: Fragment.hh:890
uint16_t field5
Definition: Fragment_t.cc:26
Test Metadata with three fields in two long words.
Definition: Fragment_t.cc:10
The RawFragmentHeaderV0 class contains the basic fields used by artdaq for routing Fragment objects t...
RawDataType timestamp
The 64-bit timestamp field is the output of a user-defined clock used for building time-correlated ev...
std::size_t size() const
Gets the size of the Fragment, from the Fragment header.
Definition: Fragment.hh:835
static constexpr std::size_t num_words()
Returns the number of RawDataType words present in the header.
void updateMetadata(const T &md)
Updates existing metadata with a new metadata object.
Definition: Fragment.hh:987
Test Metadata that is very large.
Definition: Fragment_t.cc:32
detail::RawFragmentHeader::fragment_id_t fragment_id_t
typedef for fragment_id_t from RawFragmentHeader
Definition: Fragment.hh:139
std::size_t sizeBytes() const
Size of vals_ vector ( header + (optional) metadata + payload) in bytes.
Definition: Fragment.hh:360
static constexpr std::size_t num_words()
Returns the number of RawDataType words present in the header.
RawDataType type
The type of the fragment, either system or user-defined.
detail::RawFragmentHeader::type_t type_t
typedef for type_t from RawFragmentHeader
Definition: Fragment.hh:137
RawDataType timestamp
The 64-bit timestamp field is the output of a user-defined clock used for building time-correlated ev...
sequence_id_t sequenceID() const
Sequence ID of the Fragment, from the Fragment header.
Definition: Fragment.hh:860
static constexpr type_t DataFragmentType
Copy DataFragmentType from RawFragmentHeader.
Definition: Fragment.hh:149
uint8_t byte_t
For byte representation.
Definition: Fragment.hh:100
void resize(std::size_t sz)
Resize the data payload to hold sz RawDataType words.
Definition: Fragment.hh:1007
uint64_t field1
Definition: Fragment_t.cc:22
uint32_t field3
Definition: Fragment_t.cc:24
static constexpr fragment_id_t InvalidFragmentID
Copy InvalidFragmentID from RawFragmentHeader.
Definition: Fragment.hh:144
static constexpr type_t LAST_USER_TYPE
The last user-accessible type (types above this number are system types.
static constexpr std::size_t num_words()
Returns the number of RawDataType words present in the header.
uint32_t field3
Definition: Fragment_t.cc:14
RawDataType fragment_id
The fragment_id uniquely identifies a particular piece of hardware within the artdaq system...
detail::RawFragmentHeader::version_t version_t
typedef for version_t from RawFragmentHeader
Definition: Fragment.hh:136
iterator headerBegin()
Return an iterator to the beginning of the header (should be used for serialization only: use setters...
Definition: Fragment.hh:1078
RawDataType sequence_id
The 48-bit sequence_id uniquely identifies events within the artdaq system.
iterator dataBegin()
Return an iterator to the beginning of the data payload (after header and metadata) ...
Definition: Fragment.hh:1065
bool empty()
Determines if the Fragment contains no data.
Definition: Fragment.hh:1110
static constexpr sequence_id_t InvalidSequenceID
Copy InvalidSequenceID from RawFragmentHeader.
Definition: Fragment.hh:143
uint64_t field1
Definition: Fragment_t.cc:12
RawDataType type
The type of the fragment, either system or user-defined.
void setMetadata(const T &md)
Set the metadata in the Fragment to the contents of the specified structure. This throws an exception...
Definition: Fragment.hh:971
static constexpr type_t FIRST_USER_TYPE
The first user-accessible type.
type_t type() const
Type of the Fragment, from the Fragment header.
Definition: Fragment.hh:848
RawDataType word_count
number of RawDataType words in this Fragment
RawDataType * dataAddress()
Returns a RawDataType pointer to the beginning of the payload.
Definition: Fragment.hh:1130
unsigned long long RawDataType
The RawDataType (currently a 64-bit integer) is the basic unit of data representation within artdaq ...
T * metadata()
Return a pointer to the metadata. This throws an exception if the Fragment contains no metadata...
Definition: Fragment.hh:947
iterator dataEnd()
Return an iterator to the end of the data payload.
Definition: Fragment.hh:1072
static FragmentPtr FragmentBytes(std::size_t nbytes)
Create a Fragment using a static factory function rather than a constructor to allow for the function...
Definition: Fragment.hh:202
RawDataType fragment_id
The fragment_id uniquely identifies a particular piece of hardware within the artdaq system...
detail::RawFragmentHeader::RawDataType RawDataType
The RawDataType (currently a 64-bit integer) is the basic unit of data representation within artdaq ...
Definition: Fragment.hh:40
RawDataType * metadataAddress()
Get the address of the metadata. For internal use only, use metadata() instead.
Definition: Fragment.hh:1137
void clear()
Removes all elements from the payload section of the Fragment.
Definition: Fragment.hh:1103
static const version_t CurrentVersion
The CurrentVersion field should be incremented whenever the RawFragmentHeader changes.
uint64_t field4
Definition: Fragment_t.cc:25
bool hasMetadata() const
Test whether this Fragment has metadata.
Definition: Fragment.hh:941
void setFragmentID(fragment_id_t fragment_id)
Sets the Fragment ID of the Fragment.
Definition: Fragment.hh:897
A Fragment contains the data from one piece of the DAQ system for one event The artdaq::Fragment is t...
Definition: Fragment.hh:85
static constexpr type_t LAST_SYSTEM_TYPE
The last system type.
RawDataType version
The version of the fragment. Currently always InvalidVersion.
Test Metadata with five fields, mixing field sizes.
Definition: Fragment_t.cc:20
RawDataType metadata_word_count
The number of RawDataType words in the user-defined metadata.
uint64_t fields[300]
300 long words
Definition: Fragment_t.cc:34
std::size_t dataSize() const
Return the number of RawDataType words in the data payload. This does not include the number of words...
Definition: Fragment.hh:934
The RawFragmentHeaderV1 class contains the basic fields used by artdaq for routing Fragment objects t...
RawDataType word_count
number of RawDataType words in this Fragment
detail::RawFragmentHeader::sequence_id_t sequence_id_t
typedef for sequence_id_t from RawFragmentHeader
Definition: Fragment.hh:138
RawDataType sequence_id
The 48-bit sequence_id uniquely identifies events within the artdaq system.
fragment_id_t fragmentID() const
Fragment ID of the Fragment, from the Fragment header.
Definition: Fragment.hh:866
RawDataType * headerAddress()
Gets the address of the header.
Definition: Fragment.hh:1148
version_t version() const
Version of the Fragment, from the Fragment header.
Definition: Fragment.hh:841
RawDataType version
The version of the fragment.