@@ -63,7 +63,9 @@ impl<J: 'static + AsyncJob, T: Copy + Send + 'static>
6363 }
6464 }
6565
66- /// spawns `task` if nothing is running currently, otherwise schedules as `next` overwriting if `next` was set before
66+ /// spawns `task` if nothing is running currently,
67+ /// otherwise schedules as `next` overwriting if `next` was set before.
68+ /// return `true` if the new task gets started right away.
6769 pub fn spawn ( & mut self , task : J ) -> bool {
6870 self . schedule_next ( task) ;
6971 self . check_for_job ( )
@@ -129,23 +131,35 @@ mod test {
129131 use crossbeam_channel:: unbounded;
130132 use pretty_assertions:: assert_eq;
131133 use std:: {
132- sync:: atomic:: AtomicU32 , thread:: sleep, time:: Duration ,
134+ sync:: atomic:: { AtomicBool , AtomicU32 , Ordering } ,
135+ thread,
136+ time:: Duration ,
133137 } ;
134138
135139 #[ derive( Clone ) ]
136140 struct TestJob {
137141 v : Arc < AtomicU32 > ,
142+ finish : Arc < AtomicBool > ,
138143 value_to_add : u32 ,
139144 }
140145
141146 impl AsyncJob for TestJob {
142147 fn run ( & mut self ) {
143- sleep ( Duration :: from_millis ( 100 ) ) ;
148+ self . finish . store ( false , Ordering :: Relaxed ) ;
144149
145- self . v . fetch_add (
146- self . value_to_add ,
147- std:: sync:: atomic:: Ordering :: Relaxed ,
148- ) ;
150+ println ! ( "[job] wait" ) ;
151+
152+ while self . finish . load ( Ordering :: Relaxed ) {
153+ std:: thread:: yield_now ( ) ;
154+ }
155+
156+ println ! ( "[job] sleep" ) ;
157+
158+ thread:: sleep ( Duration :: from_millis ( 100 ) ) ;
159+
160+ println ! ( "[job] done sleeping" ) ;
161+
162+ self . v . fetch_add ( self . value_to_add , Ordering :: Relaxed ) ;
149163 }
150164 }
151165
@@ -160,15 +174,20 @@ mod test {
160174
161175 let task = TestJob {
162176 v : Arc :: new ( AtomicU32 :: new ( 1 ) ) ,
177+ finish : Arc :: new ( AtomicBool :: new ( false ) ) ,
163178 value_to_add : 1 ,
164179 } ;
165180
166181 assert ! ( job. spawn( task. clone( ) ) ) ;
167- sleep ( Duration :: from_millis ( 1 ) ) ;
182+ thread:: sleep ( Duration :: from_millis ( 10 ) ) ;
183+
168184 for _ in 0 ..5 {
185+ println ! ( "spawn" ) ;
169186 assert ! ( !job. spawn( task. clone( ) ) ) ;
170187 }
171188
189+ task. finish . store ( true , Ordering :: Relaxed ) ;
190+
172191 let _foo = receiver. recv ( ) . unwrap ( ) ;
173192 let _foo = receiver. recv ( ) . unwrap ( ) ;
174193 assert ! ( receiver. is_empty( ) ) ;
@@ -188,17 +207,26 @@ mod test {
188207
189208 let task = TestJob {
190209 v : Arc :: new ( AtomicU32 :: new ( 1 ) ) ,
210+ finish : Arc :: new ( AtomicBool :: new ( false ) ) ,
191211 value_to_add : 1 ,
192212 } ;
193213
194214 assert ! ( job. spawn( task. clone( ) ) ) ;
195- sleep ( Duration :: from_millis ( 1 ) ) ;
215+ task. finish . store ( true , Ordering :: Relaxed ) ;
216+ thread:: sleep ( Duration :: from_millis ( 10 ) ) ;
196217
197218 for _ in 0 ..5 {
219+ println ! ( "spawn" ) ;
198220 assert ! ( !job. spawn( task. clone( ) ) ) ;
199221 }
222+
223+ println ! ( "cancel" ) ;
200224 assert ! ( job. cancel( ) ) ;
201225
226+ task. finish . store ( true , Ordering :: Relaxed ) ;
227+ thread:: sleep ( Duration :: from_millis ( 100 ) ) ;
228+ assert ! ( !job. is_pending( ) ) ;
229+
202230 let _foo = receiver. recv ( ) . unwrap ( ) ;
203231
204232 assert_eq ! (
0 commit comments