@@ -25,11 +25,10 @@ pub use sync::ReadLimiter;
2525#[ cfg( feature = "sync_reader" ) ]
2626mod sync {
2727 use crate :: { Error , Result } ;
28- use core:: sync:: atomic:: { AtomicUsize , AtomicBool , Ordering } ;
28+ use core:: sync:: atomic:: { AtomicUsize , Ordering } ;
2929
3030 pub struct ReadLimiter {
3131 pub limit : AtomicUsize ,
32- pub limit_reached : AtomicBool ,
3332 }
3433
3534 impl ReadLimiter {
@@ -40,22 +39,21 @@ mod sync {
4039
4140 ReadLimiter {
4241 limit : AtomicUsize :: new ( limit as usize ) ,
43- limit_reached : AtomicBool :: new ( false ) ,
4442 }
4543 }
4644
4745 #[ inline]
4846 pub fn can_read ( & self , amount : usize ) -> Result < ( ) > {
49- let limit_reached = self . limit_reached . load ( Ordering :: Relaxed ) ;
50- if limit_reached {
47+ let cur_limit = self . limit . load ( Ordering :: Relaxed ) ;
48+ if cur_limit < amount {
5149 return Err ( Error :: failed ( format ! ( "read limit exceeded" ) ) ) ;
5250 }
5351
5452 let prev_limit = self . limit . fetch_sub ( amount, Ordering :: Relaxed ) ;
55- if prev_limit == amount {
56- self . limit_reached . store ( true , Ordering :: Relaxed ) ;
57- } else if prev_limit < amount {
58- self . limit_reached . store ( true , Ordering :: Relaxed ) ;
53+ if prev_limit < amount {
54+ // if the previous limit was lower than the amount we read, the limit has underflowed
55+ // and wrapped around so we need to reset it to 0 for next reader to fail
56+ self . limit . store ( 0 , Ordering :: Relaxed ) ;
5957 return Err ( Error :: failed ( format ! ( "read limit exceeded" ) ) ) ;
6058 }
6159
0 commit comments