@@ -346,11 +346,20 @@ unsafe fn enqueue<T>(
346346mod tests {
347347 use static_assertions:: assert_not_impl_any;
348348
349- use super :: Queue ;
349+ use super :: { Queue , QueueView } ;
350350
351351 // Ensure a `Queue` containing `!Send` values stays `!Send` itself.
352352 assert_not_impl_any ! ( Queue <* const ( ) , 4 >: Send ) ;
353353
354+ fn to_vec < T > ( q : & QueueView < T > ) -> Vec < T > {
355+ // inaccurate
356+ let mut ret = vec ! [ ] ;
357+ while let Some ( v) = q. dequeue ( ) {
358+ ret. push ( v) ;
359+ }
360+ ret
361+ }
362+
354363 #[ test]
355364 fn memory_leak ( ) {
356365 droppable ! ( ) ;
@@ -419,4 +428,83 @@ mod tests {
419428 // Queue is full, this should not block forever.
420429 q. enqueue ( 0x55 ) . unwrap_err ( ) ;
421430 }
431+
432+ #[ test]
433+ fn issue_583_enqueue ( ) {
434+ const N : usize = 4 ;
435+
436+ let q0 = Queue :: < u8 , N > :: new ( ) ;
437+ for i in 0 ..N {
438+ q0. enqueue ( i as u8 ) . expect ( "new enqueue" ) ;
439+ }
440+ eprintln ! ( "start!" ) ;
441+
442+ std:: thread:: scope ( |sc| {
443+ for _ in 0 ..2 {
444+ sc. spawn ( || {
445+ for k in 0 ..1000_000 {
446+ if let Some ( v) = q0. dequeue ( ) {
447+ q0. enqueue ( v) . unwrap_or_else ( |v| {
448+ panic ! ( "{k}: q0 -> q0: {v}, {:?}" , to_vec( & q0) )
449+ } ) ;
450+ }
451+ }
452+ } ) ;
453+ }
454+ } ) ;
455+ }
456+
457+ #[ test]
458+ fn issue_583_dequeue ( ) {
459+ const N : usize = 4 ;
460+
461+ let q0 = Queue :: < u8 , N > :: new ( ) ;
462+ eprintln ! ( "start!" ) ;
463+ std:: thread:: scope ( |sc| {
464+ for _ in 0 ..2 {
465+ sc. spawn ( || {
466+ for k in 0 ..1000_000 {
467+ q0. enqueue ( k as u8 ) . unwrap ( ) ;
468+ if q0. dequeue ( ) . is_none ( ) {
469+ panic ! ( "{k}" ) ;
470+ }
471+ }
472+ } ) ;
473+ }
474+ } ) ;
475+ }
476+
477+ #[ test]
478+ fn issue_583_enqueue_loom ( ) {
479+ const N : usize = 4 ;
480+
481+ loom:: model ( || {
482+ let q0 = loom:: sync:: Arc :: new ( Queue :: < u8 , N > :: new ( ) ) ;
483+ for i in 0 ..N {
484+ q0. enqueue ( i as u8 ) . expect ( "new enqueue" ) ;
485+ }
486+ eprintln ! ( "start!" ) ;
487+
488+ let q1 = q0. clone ( ) ;
489+ loom:: thread:: spawn ( move || {
490+ for k in 0 ..1000_000 {
491+ if let Some ( v) = q0. dequeue ( ) {
492+ q0. enqueue ( v) . unwrap_or_else ( |v| {
493+ panic ! ( "{k}: q0 -> q0: {v}, {:?}" , to_vec( & * q0) )
494+ } ) ;
495+ }
496+ }
497+ } ) ;
498+
499+ loom:: thread:: spawn ( move || {
500+ for k in 0 ..1000_000 {
501+ if let Some ( v) = q1. dequeue ( ) {
502+ q1. enqueue ( v) . unwrap_or_else ( |v| {
503+ panic ! ( "{k}: q0 -> q0: {v}, {:?}" , to_vec( & * q1) )
504+ } ) ;
505+ }
506+ }
507+ } ) ;
508+ } ) ;
509+ }
422510}
0 commit comments