@@ -56,6 +56,14 @@ impl AtomicBitmap {
5656 /// is for the page corresponding to `start_addr`, and the last bit that we set corresponds
5757 /// to address `start_addr + len - 1`.
5858 pub fn set_addr_range ( & self , start_addr : usize , len : usize ) {
59+ self . set_reset_addr_range ( start_addr, len, true ) ;
60+ }
61+
62+ // Set/Reset a range of `len` bytes starting at `start_addr`
63+ // reset parameter determines whether bit will be set/reset
64+ // if set is true then the range of bits will be set to one,
65+ // otherwise zero
66+ fn set_reset_addr_range ( & self , start_addr : usize , len : usize , set : bool ) {
5967 // Return early in the unlikely event that `len == 0` so the `len - 1` computation
6068 // below does not underflow.
6169 if len == 0 {
@@ -71,8 +79,37 @@ impl AtomicBitmap {
7179 // Attempts to set bits beyond the end of the bitmap are simply ignored.
7280 break ;
7381 }
74- self . map [ n >> 6 ] . fetch_or ( 1 << ( n & 63 ) , Ordering :: SeqCst ) ;
82+ if set {
83+ self . map [ n >> 6 ] . fetch_or ( 1 << ( n & 63 ) , Ordering :: SeqCst ) ;
84+ } else {
85+ self . map [ n >> 6 ] . fetch_and ( !( 1 << ( n & 63 ) ) , Ordering :: SeqCst ) ;
86+ }
87+ }
88+ }
89+
90+ /// Reset a range of `len` bytes starting at `start_addr`. The first bit set in the bitmap
91+ /// is for the page corresponding to `start_addr`, and the last bit that we set corresponds
92+ /// to address `start_addr + len - 1`.
93+ pub fn reset_addr_range ( & self , start_addr : usize , len : usize ) {
94+ self . set_reset_addr_range ( start_addr, len, false ) ;
95+ }
96+
97+ /// Set bit to corresponding index
98+ pub fn set_bit ( & self , index : usize ) {
99+ if index >= self . size {
100+ // Attempts to set bits beyond the end of the bitmap are simply ignored.
101+ return ;
102+ }
103+ self . map [ index >> 6 ] . fetch_or ( 1 << ( index & 63 ) , Ordering :: SeqCst ) ;
104+ }
105+
106+ /// Reset bit to corresponding index
107+ pub fn reset_bit ( & self , index : usize ) {
108+ if index >= self . size {
109+ // Attempts to reset bits beyond the end of the bitmap are simply ignored.
110+ return ;
75111 }
112+ self . map [ index >> 6 ] . fetch_and ( !( 1 << ( index & 63 ) ) , Ordering :: SeqCst ) ;
76113 }
77114
78115 /// Get the length of the bitmap in bits (i.e. in how many pages it can represent).
@@ -208,6 +245,23 @@ mod tests {
208245 assert_eq ! ( v[ 0 ] , 0b110 ) ;
209246 }
210247
248+ #[ test]
249+ fn test_bitmap_reset ( ) {
250+ let b = AtomicBitmap :: new ( 1024 , DEFAULT_PAGE_SIZE ) ;
251+ assert_eq ! ( b. len( ) , 8 ) ;
252+ b. set_addr_range ( 128 , 129 ) ;
253+ assert ! ( !b. is_addr_set( 0 ) ) ;
254+ assert ! ( b. is_addr_set( 128 ) ) ;
255+ assert ! ( b. is_addr_set( 256 ) ) ;
256+ assert ! ( !b. is_addr_set( 384 ) ) ;
257+
258+ b. reset_addr_range ( 128 , 129 ) ;
259+ assert ! ( !b. is_addr_set( 0 ) ) ;
260+ assert ! ( !b. is_addr_set( 128 ) ) ;
261+ assert ! ( !b. is_addr_set( 256 ) ) ;
262+ assert ! ( !b. is_addr_set( 384 ) ) ;
263+ }
264+
211265 #[ test]
212266 fn test_bitmap_out_of_range ( ) {
213267 let b = AtomicBitmap :: new ( 1024 , NonZeroUsize :: MIN ) ;
0 commit comments