1// Licensed to the .NET Foundation under one or more agreements.
2// The .NET Foundation licenses this file to you under the MIT license.
3// See the LICENSE file in the project root for more information.
4
5//
6
7// --------------------------------------------------------------------------------
8// BitMask.h
9// --------------------------------------------------------------------------------
10
11// --------------------------------------------------------------------------------
12// BitMask is an arbitrarily large sized bitfield which has optimal storage
13// for 32 bits or less.
14// Storage is proportional to the highest index which is set.
15// --------------------------------------------------------------------------------
16
17
18#include <clrtypes.h>
19
20#ifndef _BITMASK_H_
21#define _BITMASK_H_
22
23class BitMask
24{
25 public:
26
27 BitMask();
28 ~BitMask();
29
30 BOOL TestBit(int bit);
31 void SetBit(int bit);
32 void ClearBit(int bit);
33
34 // returns true if any bit is set
35 BOOL TestAnyBit();
36
37 void ClearAllBits();
38
39 // Allocation exposed for ngen save/fixup
40 size_t GetAllocatedBlockOffset();
41 void *GetAllocatedBlock();
42 COUNT_T GetAllocatedBlockSize();
43
44 private:
45
46 static const int BIT_SIZE_SHIFT = 5;
47 static const int BIT_SIZE = (1<<BIT_SIZE_SHIFT);
48 static const int BIT_SIZE_MASK = BIT_SIZE-1;
49
50 static const COUNT_T MIN_ARRAY_ALLOCATION = 3;
51
52 // The first bit is used to indicate whether we've got a flat mask or
53 // an array of mask elements
54 BOOL IsArray();
55
56 // Indexing computations
57 COUNT_T BitToIndex(int bit);
58 COUNT_T BitToShift(int bit);
59
60 // Generic mask array access. Works for either case (array or non-array).
61 COUNT_T *GetMaskArray();
62 COUNT_T GetMaskArraySize();
63
64 // Need more bits...
65 void GrowArray(COUNT_T newSize);
66
67 union
68 {
69 COUNT_T m_mask;
70 COUNT_T *m_maskArray; // first array element is size of rest of array
71 };
72};
73
74// provides a wrapper around the BitMask class providing synchronized reads/writes safe for multithreaded access.
75// I've only added the public methods that were required by Module which needs a thread-safe BitMask. add others as required.
76class SynchronizedBitMask
77{
78 public:
79 // Allow Module access so we can use Offsetof on this class's private members during native image creation (determinism)
80 friend class Module;
81 SynchronizedBitMask();
82 ~SynchronizedBitMask() {}
83
84 BOOL TestBit(int bit);
85 void SetBit(int bit);
86 void ClearBit(int bit);
87
88 BOOL TestAnyBit();
89
90 void ClearAllBits();
91
92 private:
93
94 BitMask m_bitMask;
95
96 // note that this lock (at present) doesn't support promotion from reader->writer so be very careful
97 // when taking this lock else you might deadlock your own thread!
98 SimpleRWLock m_bitMaskLock;
99};
100
101#include <bitmask.inl>
102
103#endif // _BITMASK_H_
104