All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
FlagSet_test.cc
Go to the documentation of this file.
1 /**
2  * @file FlagSet_test.cc
3  * @brief Test for the util::flags::FlagSet class
4  * @author Gianluca Petrillo (petrillo@fnal.gov)
5  * @date January 25, 2017
6  *
7  *
8  */
9 
10 // Boost libraries
11 /*
12  * Boost: define the name of the module;
13  * and do that before the inclusion of Boost unit test headers
14  * because it will change what they provide.
15  * Among the those, there is a main() function and some wrapping catching
16  * unhandled exceptions and considering them test failures, and probably more.
17  * This also makes fairly complicate to receive parameters from the command line
18  * (for example, a random seed).
19  */
20 #define BOOST_TEST_MODULE ( trajectorypointflags_test )
21 #include "boost/test/unit_test.hpp"
22 
23 // LArSoft libraries
25 
26 // C/C++ standard library
27 #include <set>
28 #include <array>
29 #include <algorithm> // std::copy()
30 #include <iostream> // std::cout
31 
32 //------------------------------------------------------------------------------
33 
34 namespace MyFlags {
35 
36  using Storage_t = unsigned short;
38 
39  constexpr MyFlag_t F0 { 0 };
40  constexpr MyFlag_t F1 { 1 };
41  constexpr MyFlag_t F2 { 2 };
42  constexpr MyFlag_t F3 { 3 };
43  constexpr MyFlag_t F4 { 4 };
44  constexpr MyFlag_t F5 { 5 };
45  constexpr MyFlag_t F6 { 6 };
46  constexpr MyFlag_t F7 { 7 };
47  constexpr MyFlag_t F8 [[gnu::unused]] { 8 };
48 
49 } // namespace MyFlags
50 
51 
52 template <typename FlagSet>
54  FlagSet const& flags,
55  std::set<typename FlagSet::Flag_t> const& defined,
56  std::set<typename FlagSet::Flag_t> const& set
57 ) {
58 
59  using FlagIndex_t = typename FlagSet::FlagIndex_t;
60  using Flag_t = typename FlagSet::Flag_t;
61 
62  for (FlagIndex_t i = 0; i <= flags.capacity(); ++i) {
63 
64  Flag_t flag { i };
65 
66  BOOST_TEST_MESSAGE(" flag #" << i);
67 
68  bool const isFlag = (i < flags.size());
69  bool const isDefined = (defined.count(i) > 0);
70  bool const isSet = (set.count(i) > 0);
71 
72  BOOST_TEST(flags.isFlag(i) == isFlag);
73  BOOST_TEST(flags.isFlag(flag) == isFlag);
74 
75  // In fact, the fact that the flag is not supported does not mean it can't
76  // be used. But not with test().
77  if (!isFlag) {
78  BOOST_CHECK_THROW(flags.test(i), typename FlagSet::OutOfRangeError);
79  BOOST_CHECK_THROW(flags.test(flag), typename FlagSet::OutOfRangeError);
80  continue;
81  }
82  else if (!isDefined) {
83  BOOST_CHECK_THROW(flags.test(i), typename FlagSet::FlagNotDefinedError);
84  BOOST_CHECK_THROW
85  (flags.test(flag), typename FlagSet::FlagNotDefinedError);
86  }
87  else {
88  BOOST_TEST(flags.test(i) == isSet);
89  BOOST_TEST(flags.test(flag) == isSet);
90  }
91 
92  BOOST_TEST(flags.isUndefined(i) == !isDefined);
93  BOOST_TEST(flags.isDefined(i) == isDefined);
94  BOOST_TEST(flags.isUndefined(flag) == !isDefined);
95  BOOST_TEST(flags.isDefined(flag) == isDefined);
96 
97  if (isDefined) {
98  // if the flag is undefined, so it the result of get()
99  BOOST_TEST(flags.get(i) == isSet);
100  BOOST_TEST(flags.get(flag) == isSet);
101 
102  BOOST_TEST(flags.isSet(i) == isSet);
103  BOOST_TEST(flags.isUnset(i) == !isSet);
104  BOOST_TEST(flags.isSet(flag) == isSet);
105  BOOST_TEST(flags.isUnset(flag) == !isSet);
106  }
107  else {
108  BOOST_TEST(!flags.isSet(i));
109  BOOST_TEST(!flags.isUnset(i));
110  BOOST_TEST(!flags.isSet(flag));
111  BOOST_TEST(!flags.isUnset(flag));
112  }
113  } // for
114 
115 } // CheckFlags()
116 
117 
118 //------------------------------------------------------------------------------
119 //--- Test code
120 //
121 
123 
124  // make sure the object is aware of having allocated flags enough
125  static_assert(util::flags::FlagSet<4U>::capacity() >= 4,
126  "Capacity mismatch for util::flags::FlagSet<4U>");
127  static_assert(util::flags::FlagSet<8U>::capacity() >= 8,
128  "Capacity mismatch for util::flags::FlagSet<8U>");
129  static_assert(util::flags::FlagSet<12U>::capacity() >= 12,
130  "Capacity mismatch for util::flags::FlagSet<12U>");
131  static_assert(util::flags::FlagSet<16U>::capacity() >= 16,
132  "Capacity mismatch for util::flags::FlagSet<16U>");
133  static_assert(util::flags::FlagSet<32U>::capacity() >= 32,
134  "Capacity mismatch for util::flags::FlagSet<32U>");
135 
136  // make sure the object is as small as possible
137  static_assert(sizeof(util::flags::FlagSet<4U>) == 2, // ideally it would be 1
138  "Capacity mismatch for util::flags::FlagSet<4U>");
139  static_assert(sizeof(util::flags::FlagSet<8U>) == 2,
140  "Capacity mismatch for util::flags::FlagSet<8U>");
141  static_assert(sizeof(util::flags::FlagSet<12U>) == 4, // ideally it would be 3
142  "Capacity mismatch for util::flags::FlagSet<12U>");
143  static_assert(sizeof(util::flags::FlagSet<16U>) == 4,
144  "Capacity mismatch for util::flags::FlagSet<16U>");
145  static_assert(sizeof(util::flags::FlagSet<32U>) == 8,
146  "Capacity mismatch for util::flags::FlagSet<32U>");
147 
148 
150 
151  constexpr FlagSet_t flags0;
152  static_assert(flags0.size() == 7U, "Invalid size.");
153 
154  static_assert(!flags0.isDefined(MyFlags::F0), "Unexpected flag #0 definition.");
155  static_assert(!flags0.isDefined(MyFlags::F1), "Unexpected flag #1 definition.");
156  static_assert(!flags0.isDefined(MyFlags::F2), "Unexpected flag #2 definition.");
157  static_assert(!flags0.isDefined(MyFlags::F3), "Unexpected flag #3 definition.");
158  static_assert(!flags0.isDefined(MyFlags::F4), "Unexpected flag #4 definition.");
159  static_assert(!flags0.isDefined(MyFlags::F5), "Unexpected flag #5 definition.");
160  static_assert(!flags0.isDefined(MyFlags::F6), "Unexpected flag #6 definition.");
161  static_assert(!flags0.isDefined(MyFlags::F7), "Unexpected flag #7 definition.");
162  static_assert(!flags0.isSet(MyFlags::F0), "Unexpected flag #0 value.");
163  static_assert(!flags0.isSet(MyFlags::F1), "Unexpected flag #1 value.");
164  static_assert(!flags0.isSet(MyFlags::F2), "Unexpected flag #2 value.");
165  static_assert(!flags0.isSet(MyFlags::F3), "Unexpected flag #3 value.");
166  static_assert(!flags0.isSet(MyFlags::F4), "Unexpected flag #4 value.");
167  static_assert(!flags0.isSet(MyFlags::F5), "Unexpected flag #5 value.");
168  static_assert(!flags0.isSet(MyFlags::F6), "Unexpected flag #6 value.");
169  static_assert(!flags0.isSet(MyFlags::F7), "Unexpected flag #7 value.");
170  static_assert(!flags0.isUnset(MyFlags::F0), "Unexpected flag #0 value.");
171  static_assert(!flags0.isUnset(MyFlags::F1), "Unexpected flag #1 value.");
172  static_assert(!flags0.isUnset(MyFlags::F2), "Unexpected flag #2 value.");
173  static_assert(!flags0.isUnset(MyFlags::F3), "Unexpected flag #3 value.");
174  static_assert(!flags0.isUnset(MyFlags::F4), "Unexpected flag #4 value.");
175  static_assert(!flags0.isUnset(MyFlags::F5), "Unexpected flag #5 value.");
176  static_assert(!flags0.isUnset(MyFlags::F6), "Unexpected flag #6 value.");
177  static_assert(!flags0.isUnset(MyFlags::F7), "Unexpected flag #7 value.");
178 
179  constexpr FlagSet_t flags1(MyFlags::F7, MyFlags::F6);
180  static_assert(flags1.size() == 7U, "Invalid size.");
181 
182  static_assert(!flags1.isDefined(MyFlags::F0), "Unexpected flag #0 definition.");
183  static_assert(!flags1.isDefined(MyFlags::F1), "Unexpected flag #1 definition.");
184  static_assert(!flags1.isDefined(MyFlags::F2), "Unexpected flag #2 definition.");
185  static_assert(!flags1.isDefined(MyFlags::F3), "Unexpected flag #3 definition.");
186  static_assert(!flags1.isDefined(MyFlags::F4), "Unexpected flag #4 definition.");
187  static_assert(!flags1.isDefined(MyFlags::F5), "Unexpected flag #5 definition.");
188  static_assert( flags1.isDefined(MyFlags::F6), "Unexpected flag #6 definition.");
189  static_assert( flags1.isDefined(MyFlags::F7), "Unexpected flag #7 definition.");
190  static_assert(!flags1.isSet(MyFlags::F0), "Unexpected flag #0 value.");
191  static_assert(!flags1.isSet(MyFlags::F1), "Unexpected flag #1 value.");
192  static_assert(!flags1.isSet(MyFlags::F2), "Unexpected flag #2 value.");
193  static_assert(!flags1.isSet(MyFlags::F3), "Unexpected flag #3 value.");
194  static_assert(!flags1.isSet(MyFlags::F4), "Unexpected flag #4 value.");
195  static_assert(!flags1.isSet(MyFlags::F5), "Unexpected flag #5 value.");
196  static_assert( flags1.isSet(MyFlags::F6), "Unexpected flag #6 value.");
197  static_assert( flags1.isSet(MyFlags::F7), "Unexpected flag #7 value.");
198  static_assert(!flags1.isUnset(MyFlags::F0), "Unexpected flag #0 value.");
199  static_assert(!flags1.isUnset(MyFlags::F1), "Unexpected flag #1 value.");
200  static_assert(!flags1.isUnset(MyFlags::F2), "Unexpected flag #2 value.");
201  static_assert(!flags1.isUnset(MyFlags::F3), "Unexpected flag #3 value.");
202  static_assert(!flags1.isUnset(MyFlags::F4), "Unexpected flag #4 value.");
203  static_assert(!flags1.isUnset(MyFlags::F5), "Unexpected flag #5 value.");
204  static_assert(!flags1.isUnset(MyFlags::F6), "Unexpected flag #6 value.");
205  static_assert(!flags1.isUnset(MyFlags::F7), "Unexpected flag #7 value.");
206 
207 
208 
209 } // FlagSetStaticTest()
210 
211 
212 void FlagSetTest() {
213 
215  using Flag_t = FlagSet_t::Flag_t;
216 
217 
218  // the last flag is "unsupported"
219  // BUG the double brace syntax is required to work around clang bug 21629
220  // (https://bugs.llvm.org/show_bug.cgi?id=21629)
221 // std::array<Flag_t, 3> const indices = { 4, MyFlags::F6, 7 };
222  std::array<Flag_t, 3> const indices = {{ 4, MyFlags::F6, 7 }};
223 
224  std::set<Flag_t> defined, set;
225 
226  BOOST_TEST_MESSAGE("Default construction");
227  FlagSet_t flags;
228  std::cout << " => " << flags << std::endl;
229  CheckFlags(flags, defined, set);
230 
231  BOOST_TEST_MESSAGE("Single bit set");
232  flags.set(1);
233  defined.insert(1);
234  set.insert(1);
235  std::cout << " => " << flags << std::endl;
236  CheckFlags(flags, defined, set);
237 
238  BOOST_TEST_MESSAGE("Two more bits set (one set again)");
239  flags.set(5, MyFlags::F7, MyFlags::F3, 1);
240  defined.insert(3);
241  defined.insert(5);
242  defined.insert(7);
243  set.insert(3);
244  set.insert(5);
245  set.insert(7);
246  std::cout << " => " << flags << std::endl;
247  CheckFlags(flags, defined, set);
248 
249  BOOST_TEST_MESSAGE("Bits set from a list of bits to set");
250  flags.rangeSet(indices.begin(), indices.end());
251  std::for_each(indices.begin(), indices.end(),
252  [&defined](auto flag){ defined.insert(flag); }
253  );
254  std::for_each
255  (indices.begin(), indices.end(), [&set](auto flag){ set.insert(flag); });
256  std::cout << " => " << flags << std::endl;
257  CheckFlags(flags, defined, set);
258 
259  BOOST_TEST_MESSAGE("Undefine bits");
260  flags.remove(2, 3, MyFlags::F4); // flag 2 was already not defined
261  defined.erase(3);
262  defined.erase(4);
263  set.erase(4);
264  std::cout << " => " << flags << std::endl;
265  CheckFlags(flags, defined, set);
266 
267  BOOST_TEST_MESSAGE("Unset bits");
268  flags.unset(MyFlags::F7, 5);
269  set.erase(7);
270  set.erase(5);
271  std::cout << " => " << flags << std::endl;
272  CheckFlags(flags, defined, set);
273 
274  BOOST_TEST_MESSAGE("Unset bit range");
275  flags.rangeUnset(indices.begin(), indices.end());
276  std::for_each(indices.begin(), indices.end(),
277  [&defined](auto flag){ defined.insert(flag); }
278  );
279  std::for_each(indices.begin(), indices.end(),
280  [&set](auto flag){ set.erase(flag); }
281  );
282  std::cout << " => " << flags << std::endl;
283  CheckFlags(flags, defined, set);
284 
285  flags.clear();
286  CheckFlags(flags, {}, {});
287  flags.set (MyFlags::F1);
288  flags.unset(MyFlags::F4);
289  flags.unset(MyFlags::F5);
290 
291  /*
292  * constexpr bool all(Bits_t bits) const
293  * constexpr bool any(Bits_t bits) const
294  * constexpr bool none(Bits_t bits) const
295  */
296 
297  // Reminder: undefined flags will always contribute a "false".
298  // flag 1 is set
299  BOOST_TEST( flags.all (MyFlags::F1));
300  BOOST_TEST( flags.any (MyFlags::F1));
301  BOOST_TEST(!flags.none(MyFlags::F1));
302 
303  // flag 1 is set, flag 4 is unset
304  BOOST_TEST(!flags.all (MyFlags::F1 + MyFlags::F4));
305  BOOST_TEST( flags.any (MyFlags::F1 + MyFlags::F4));
306  BOOST_TEST(!flags.none(MyFlags::F1 + MyFlags::F4));
307 
308  // flag 1 is set, flag 3 is undefined (had been defined and set though)
309  BOOST_TEST(!flags.all (MyFlags::F1 + MyFlags::F3));
310  BOOST_TEST( flags.any (MyFlags::F1 + MyFlags::F3));
311  BOOST_TEST(!flags.none(MyFlags::F1 + MyFlags::F3));
312 
313  // flag 4 is unset, flag 3 is undefined (had been defined though)
314  BOOST_TEST(!flags.all (MyFlags::F3 + MyFlags::F4));
315  BOOST_TEST(!flags.any (MyFlags::F3 + MyFlags::F4));
316  BOOST_TEST(!flags.none(MyFlags::F3 + MyFlags::F4));
317 
318  // flag 3 is undefined (had been defined though)
319  BOOST_TEST(!flags.all (MyFlags::F3));
320  BOOST_TEST(!flags.any (MyFlags::F3));
321  BOOST_TEST(!flags.none(MyFlags::F3));
322 
323  // flag 4 is unset
324  BOOST_TEST(!flags.all (MyFlags::F4));
325  BOOST_TEST(!flags.any (MyFlags::F4));
326  BOOST_TEST( flags.none(MyFlags::F4));
327 
328  /*
329  * constexpr bool anySet(Mask_t const& mask) const
330  * constexpr bool match(Mask_t const& mask) const
331  */
332  BOOST_TEST( flags.match (flags.mask()));
333  BOOST_TEST(!flags.match (flags.mask() - MyFlags::F6)); // also unset F6
334  BOOST_TEST(!flags.match (flags.mask() + MyFlags::F5)); // set F5
335  BOOST_TEST(!flags.match (flags.mask() + MyFlags::F6)); // also set F6
336  BOOST_TEST(!flags.match (flags.mask() - MyFlags::F1 + MyFlags::F6));
337  BOOST_TEST( flags.anySet (flags.mask()));
338  BOOST_TEST( flags.anySet (flags.mask() - MyFlags::F6));
339  BOOST_TEST( flags.anySet (flags.mask() + MyFlags::F5));
340  BOOST_TEST( flags.anySet (flags.mask() + MyFlags::F6));
341  BOOST_TEST(!flags.anySet (flags.mask() - MyFlags::F1 + MyFlags::F6));
342  BOOST_TEST(!flags.noneSet(flags.mask()));
343  BOOST_TEST(!flags.noneSet(flags.mask() - MyFlags::F6));
344  BOOST_TEST(!flags.noneSet(flags.mask() + MyFlags::F5));
345  BOOST_TEST(!flags.noneSet(flags.mask() + MyFlags::F6));
346  BOOST_TEST( flags.noneSet(flags.mask() - MyFlags::F1 + MyFlags::F6));
347 
348 } // FlagSetTest()
349 
350 
351 //------------------------------------------------------------------------------
353 
354  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
355  using MyMask_t = util::flags::BitMask<unsigned int>;
356  constexpr MyMask_t DefaultMask [[maybe_unused]] (MyMask_t::fromValues, 0x0300U);
357  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
358 
359 } // BitMaskDocTest_ConstructorFromValues1()
360 
361 
363 
364  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
365  using MyMask_t = util::flags::BitMask<unsigned int>;
366  constexpr MyMask_t DefaultMask [[maybe_unused]] (MyMask_t::fromValues, 0x0300U, 0x0200U);
367  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
368 
369 } // BitMaskDocTest_ConstructorFromValues2()
370 
371 
373 
376 
377 } // BitMaskDocTest()
378 
379 
380 //------------------------------------------------------------------------------
381 
383 
385 
386  constexpr Mask_t maskA(Mask_t::fromValues, 0b011'011'011, 0b001'001'001);
387  constexpr Mask_t maskB(Mask_t::fromValues, 0b000'111'111, 0b000'000'111);
388  constexpr Mask_t::Bits_t bitsB (0b000'000'111);
389 
390  /*
391  * constexpr mergeIntoMask(Mask_t baseMask, Mask_t mask)
392  */
393  constexpr Mask_t maskMAB(Mask_t::fromValues, 0b011'111'111, 0b001'000'111);
394  static_assert(Mask_t::mergeIntoMask(maskA, maskB) == maskMAB,
395  "mergeIntoMask(Mask_t, Mask_t) failure");
396  static_assert
397  (maskA + maskB == maskMAB, "maskA + maskB failure");
398 
399  constexpr Mask_t maskMBA(Mask_t::fromValues, 0b011'111'111, 0b001'001'101);
400  static_assert(Mask_t::mergeIntoMask(maskB, maskA) == maskMBA,
401  "mergeIntoMask(Mask_t, Mask_t) failure");
402  static_assert
403  (maskB + maskA == maskMBA, "maskB + maskA failure");
404 
405  /*
406  * mergeIntoMask(Mask_t baseMask, Bits_t bits)
407  */
408  constexpr Mask_t maskMAbB(Mask_t::fromValues, 0b011'011'111, 0b001'001'111);
409  static_assert(Mask_t::mergeIntoMask(maskA, bitsB) == maskMAbB,
410  "mergeIntoMask(Mask_t, Bits_t) failure");
411  static_assert
412  (maskA + bitsB == maskMAbB, "maskA + bitsB failure");
413 
414  constexpr Mask_t maskMbBA(Mask_t::fromValues, 0b011'011'111, 0b001'001'101);
415  static_assert(bitsB + maskA == maskMbBA, "bitsB + maskA failure");
416 
417  /*
418  * combineWithMask(Mask_t A, Mask_t B)
419  */
420  constexpr Mask_t maskCAB(Mask_t::fromValues, 0b011'111'111, 0b001'001'111);
421  static_assert(Mask_t::combineWithMask(maskA, maskB) == maskCAB,
422  "combineWithMask(Mask_t, Mask_t) failure");
423  static_assert
424  ((maskA | maskB) == maskCAB, "maskA | maskB failure");
425 
426  constexpr Mask_t maskCBA(Mask_t::fromValues, 0b011'111'111, 0b001'001'111);
427  static_assert(Mask_t::combineWithMask(maskB, maskA) == maskCBA,
428  "combineWithMask(Mask_t, Mask_t) failure");
429  static_assert
430  ((maskB | maskA) == maskCBA, "maskB | maskA failure");
431 
432  /*
433  * combineWithMask(Mask_t mask, Bits_t bits)
434  */
435  constexpr Mask_t maskCAbB(Mask_t::fromValues, 0b011'011'111, 0b001'001'111);
436  static_assert(Mask_t::combineWithMask(maskA, bitsB) == maskCAbB,
437  "combineWithMask(Mask_t, Bits_t) failure");
438  static_assert
439  ((maskA | bitsB) == maskCAbB, "maskA | bitsB failure");
440 
441  constexpr Mask_t maskCbBA(Mask_t::fromValues, 0b011'011'111, 0b001'001'111);
442  static_assert
443  ((bitsB | maskA) == maskCbBA, "bitsB | maskA failure");
444 
445  /*
446  * intersectWithMask(Mask_t A, Mask_t B)
447  */
448  constexpr Mask_t maskIAB(Mask_t::fromValues, 0b011'111'111, 0b001'000'101);
449  static_assert(Mask_t::intersectWithMask(maskA, maskB) == maskIAB,
450  "intersectWithMask(Mask_t, Mask_t) failure");
451  static_assert((maskA & maskB) == maskIAB, "maskA & maskB failure");
452 
453  constexpr Mask_t maskIBA(Mask_t::fromValues, 0b011'111'111, 0b001'000'101);
454  static_assert(Mask_t::intersectWithMask(maskB, maskA) == maskIBA,
455  "intersectWithMask(Mask_t, Mask_t) failure");
456  static_assert((maskB & maskA) == maskIBA, "maskB & maskA failure");
457 
458  /*
459  * intersectWithMask(Mask_t mask, Bits_t bits)
460  */
461  constexpr Mask_t maskIAbB(Mask_t::fromValues, 0b011'011'111, 0b001'001'101);
462  static_assert(Mask_t::intersectWithMask(maskA, bitsB) == maskIAbB,
463  "intersectWithMask(Mask_t, Bits_t) failure");
464  static_assert
465  ((maskA & bitsB) == maskIAbB, "maskA & bitsB failure");
466 
467  constexpr Mask_t maskIbBA(Mask_t::fromValues, 0b011'011'111, 0b001'001'101);
468  static_assert((bitsB & maskA) == maskIbBA, "bitsB & maskA failure");
469 
470  /*
471  * unsetMask(Mask_t A, Mask_t B)
472  */
473  constexpr Mask_t maskUAB(Mask_t::fromValues, 0b011'111'111, 0b001'001'000);
474  static_assert(Mask_t::unsetMask(maskA, maskB) == maskUAB,
475  "unsetMask(Mask_t, Mask_t) failure");
476  static_assert((maskA - maskB) == maskUAB, "maskA - maskB failure");
477 
478  constexpr Mask_t maskUBA(Mask_t::fromValues, 0b011'111'111, 0b000'000'110);
479  static_assert(Mask_t::unsetMask(maskB, maskA) == maskUBA,
480  "unsetMask(Mask_t, Mask_t) failure");
481  static_assert((maskB - maskA) == maskUBA, "maskB - maskA failure");
482 
483  /*
484  * unsetMask(Mask_t mask, Bits_t bits)
485  */
486  constexpr Mask_t maskUAbB(Mask_t::fromValues, 0b011'011'111, 0b001'001'000);
487  static_assert(Mask_t::unsetMask(maskA, bitsB) == maskUAbB,
488  "unsetMask(Mask_t, Bits_t) failure");
489  static_assert((maskA - bitsB) == maskUAbB, "maskA - bitsB failure");
490 
491  constexpr Mask_t maskUbBA(Mask_t::fromValues, 0b011'011'111, 0b000'000'110);
492  static_assert((bitsB - maskA) == maskUbBA, "bitsB - maskA failure");
493 
494  /*
495  * negateMask(Mask_t mask)
496  */
497  constexpr Mask_t maskNA(Mask_t::fromValues, 0b011'011'011, 0b010'010'010);
498  static_assert
499  (Mask_t::negateMask(maskA) == maskNA, "negateMask(Mask_t) failure");
500  static_assert(~maskA == maskNA, "~mask failure");
501 
502  /*
503  * negateMask(Bits_t bits)
504  */
505  constexpr Mask_t maskNbB(Mask_t::fromValues, 0b000'000'111, 0b000'000'000);
506  static_assert
507  (Mask_t::negateMask(bitsB) == maskNbB, "negateMask(Bits_t) failure");
508 // static_assert(~bitsB == maskNbB, "~bits failure");
509 
510  /*
511  * unary operator+
512  */
513  constexpr Mask_t maskbB(Mask_t::fromValues, 0b000'000'111, 0b000'000'111);
514  static_assert(+maskA == maskA, "+mask failure");
515  static_assert(+bitsB == maskbB, "+bits failure");
516 
517  /*
518  * unary operator-
519  */
520  static_assert(maskA + (-bitsB) == maskA - bitsB, "-bits failure");
521 
522 
523 } // BitMaskCombineTests()
524 
525 
526 
527 //------------------------------------------------------------------------------
528 void SetUnsetTest() {
529 
531 
533 
534  std::cout << "Testing Set()/Unset() on " << mask << std::endl;
535 
536  BOOST_TEST(!mask.isDefined(0));
537  BOOST_TEST( mask.isDefined(1));
538  BOOST_TEST( mask.isDefined(2));
539  BOOST_TEST(!mask.isDefined(3));
540 
541  BOOST_TEST(!mask.isSet(0));
542  BOOST_TEST( mask.isSet(1));
543  BOOST_TEST(!mask.isSet(2));
544  BOOST_TEST(!mask.isSet(3));
545 
546  BOOST_TEST(!mask.isUnset(0));
547  BOOST_TEST(!mask.isUnset(1));
548  BOOST_TEST( mask.isUnset(2));
549  BOOST_TEST(!mask.isUnset(3));
550 
551 
552 } // SetUnsetTest()
553 
554 
555 //------------------------------------------------------------------------------
556 //--- registration of tests
557 
558 BOOST_AUTO_TEST_CASE(BitMaskTestCase) {
559 
561  BitMaskDocTest();
562 
563 } // BOOST_AUTO_TEST_CASE(FlagSetTestCase)
564 
565 
566 BOOST_AUTO_TEST_CASE(FlagSetTestCase) {
567 
569  FlagSetTest();
570  SetUnsetTest();
571 
572 } // BOOST_AUTO_TEST_CASE(FlagSetTestCase)
BOOST_AUTO_TEST_CASE(AllTests)
void BitMaskDocTest_ConstructorFromValues1()
constexpr MyFlag_t F8[[gnu::unused]]
Definition: FlagSet_test.cc:47
then echo unknown compiler flag
Type identifying a flag. Operations are implemented as free functions.
Definition: BitMask.h:89
constexpr MyFlag_t F0
Definition: FlagSet_test.cc:39
constexpr MyFlag_t F4
Definition: FlagSet_test.cc:43
A class containing a set of flags.
Definition: FlagSet.h:41
void BitMaskDocTest_ConstructorFromValues2()
constexpr MyFlag_t F2
Definition: FlagSet_test.cc:41
Class holding flags.
A class containing a set of flags.
Definition: BitMask.h:420
constexpr mask_t< EnumType > mask(EnumType bit, OtherBits...otherBits)
Returns a mask with all specified bits set.
constexpr BitMask< Storage > Set(Flag_t< Storage > flag)
Returns a bit mask which sets the specified flag.
void FlagSetStaticTest()
void BitMaskCombineTests()
constexpr std::array< std::size_t, geo::vect::dimension< Vector >)> indices()
Returns a sequence of indices valid for a vector of the specified type.
void SetUnsetTest()
constexpr MyFlag_t F5
Definition: FlagSet_test.cc:44
unsigned short Storage_t
Definition: FlagSet_test.cc:36
then echo echo For and will not be changed by echo further linking echo echo B echo The symbol is in the uninitialized data multiple common symbols may appear with the echo same name If the symbol is defined the common echo symbols are treated as undefined references For more echo details on common see the discussion of warn common echo in *Note Linker see the discussion of warn common echo in *Note Linker such as a global int variable echo as opposed to a large global array echo echo I echo The symbol is an indirect reference to another symbol This echo is a GNU extension to the a out object file format which is echo rarely used echo echo N echo The symbol is a debugging symbol echo echo R echo The symbol is in a read only data section echo echo S echo The symbol is in an uninitialized data section for small echo objects echo echo T echo The symbol is in the the normal defined echo symbol is used with no error When a weak undefined symbol echo is linked and the symbol is not defined
constexpr MyFlag_t F1
Definition: FlagSet_test.cc:40
constexpr MyFlag_t F6
Definition: FlagSet_test.cc:45
constexpr MyFlag_t F3
Definition: FlagSet_test.cc:42
constexpr MyFlag_t F7
Definition: FlagSet_test.cc:46
void CheckFlags(FlagSet const &flags, std::set< typename FlagSet::Flag_t > const &defined, std::set< typename FlagSet::Flag_t > const &set)
Definition: FlagSet_test.cc:53
void BitMaskDocTest()
constexpr BitMask< Storage > Unset(Flag_t< Storage > flag)
Returns a bit mask which unsets the specified flag.
BEGIN_PROLOG could also be cout
void FlagSetTest()