File tree Expand file tree Collapse file tree 4 files changed +68
-0
lines changed Expand file tree Collapse file tree 4 files changed +68
-0
lines changed Original file line number Diff line number Diff line change @@ -11,6 +11,7 @@ async-lock = "2.5.0"
11
11
async-oneshot = " 0.5.0"
12
12
async-weighted-semaphore = " 0.2.1"
13
13
async_singleflight = " 0.5.0"
14
+ atomic-waker = " 1.1.2"
14
15
atomic_float = " 0.1.0"
15
16
atomicbox = " 0.4.0"
16
17
atomig = " 0.4.0"
Original file line number Diff line number Diff line change @@ -61,6 +61,7 @@ fn main() {
61
61
sync_cow_example ( ) . unwrap ( ) ;
62
62
arc_swap_example ( ) ;
63
63
64
+ atomic_waker_example ( ) ;
64
65
}
65
66
66
67
Original file line number Diff line number Diff line change
1
+ use futures:: future:: Future ;
2
+ use futures:: task:: { Context , Poll , AtomicWaker } ;
3
+ use std:: sync:: Arc ;
4
+ use std:: sync:: atomic:: AtomicBool ;
5
+ use std:: sync:: atomic:: Ordering :: Relaxed ;
6
+ use std:: pin:: Pin ;
7
+
8
+ struct Inner {
9
+ waker : AtomicWaker ,
10
+ set : AtomicBool ,
11
+ }
12
+
13
+ #[ derive( Clone ) ]
14
+ struct Flag ( Arc < Inner > ) ;
15
+
16
+ impl Flag {
17
+ pub fn new ( ) -> Self {
18
+ Flag ( Arc :: new ( Inner {
19
+ waker : AtomicWaker :: new ( ) ,
20
+ set : AtomicBool :: new ( false ) ,
21
+ } ) )
22
+ }
23
+
24
+ pub fn signal ( & self ) {
25
+ self . 0 . set . store ( true , Relaxed ) ;
26
+ self . 0 . waker . wake ( ) ;
27
+ }
28
+ }
29
+
30
+ impl Future for Flag {
31
+ type Output = bool ;
32
+
33
+ fn poll ( self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < bool > {
34
+ // quick check to avoid registration if already done.
35
+ if self . 0 . set . load ( Relaxed ) {
36
+ return Poll :: Ready ( true ) ;
37
+ }
38
+
39
+ self . 0 . waker . register ( cx. waker ( ) ) ;
40
+
41
+ // Need to check condition **after** `register` to avoid a race
42
+ // condition that would result in lost notifications.
43
+ if self . 0 . set . load ( Relaxed ) {
44
+ Poll :: Ready ( true )
45
+ } else {
46
+ Poll :: Pending
47
+ }
48
+ }
49
+ }
50
+
51
+ pub fn atomic_waker_example ( ) {
52
+ smol:: block_on ( async {
53
+ let flag = Flag :: new ( ) ;
54
+ let flag2 = flag. clone ( ) ;
55
+
56
+ smol:: spawn ( async move {
57
+ smol:: Timer :: after ( std:: time:: Duration :: from_secs ( 1 ) ) . await ;
58
+ flag2. signal ( ) ;
59
+ } )
60
+ . detach ( ) ;
61
+
62
+ println ! ( "Waiting for flag: {}" , flag. await ) ;
63
+ } ) ;
64
+ }
Original file line number Diff line number Diff line change @@ -12,11 +12,13 @@ mod async_lock_examples;
12
12
mod atomic_examples;
13
13
mod simple_mutex_examples;
14
14
mod waitgroup_examples;
15
+ mod atomic_waker_examples;
15
16
16
17
pub use try_lock_examples:: * ;
17
18
pub use sharded_slab_example:: * ;
18
19
pub use async_lock_examples:: * ;
19
20
pub use atomic_examples:: * ;
20
21
pub use simple_mutex_examples:: * ;
21
22
pub use waitgroup_examples:: * ;
23
+ pub use atomic_waker_examples:: * ;
22
24
You can’t perform that action at this time.
0 commit comments