271271// And now that you've seen all the races that I found and attempted to fix,
272272// here's the code for you to find some more!
273273
274- use cast;
275274use cell:: Cell ;
276275use clone:: Clone ;
277276use iter:: Iterator ;
@@ -284,6 +283,7 @@ use result::{Ok, Err, Result};
284283use rt:: local:: Local ;
285284use rt:: task:: { Task , BlockedTask } ;
286285use sync:: arc:: UnsafeArc ;
286+ use ty:: Unsafe ;
287287
288288pub use comm:: select:: { Select , Handle } ;
289289
@@ -325,7 +325,7 @@ static RESCHED_FREQ: int = 256;
325325/// The receiving-half of Rust's channel type. This half can only be owned by
326326/// one task
327327pub struct Receiver < T > {
328- inner : Flavor < T > ,
328+ inner : Unsafe < Flavor < T > > ,
329329 receives : Cell < uint > ,
330330 // can't share in an arc
331331 marker : marker:: NoShare ,
@@ -341,7 +341,7 @@ pub struct Messages<'a, T> {
341341/// The sending-half of Rust's asynchronous channel type. This half can only be
342342/// owned by one task, but it can be cloned to send to other tasks.
343343pub struct Sender < T > {
344- inner : Flavor < T > ,
344+ inner : Unsafe < Flavor < T > > ,
345345 sends : Cell < uint > ,
346346 // can't share in an arc
347347 marker : marker:: NoShare ,
@@ -390,6 +390,27 @@ enum Flavor<T> {
390390 Sync ( UnsafeArc < sync:: Packet < T > > ) ,
391391}
392392
393+ #[ doc( hidden) ]
394+ trait UnsafeFlavor < T > {
395+ fn inner_unsafe < ' a > ( & ' a self ) -> & ' a Unsafe < Flavor < T > > ;
396+ unsafe fn mut_inner < ' a > ( & ' a self ) -> & ' a mut Flavor < T > {
397+ & mut * self . inner_unsafe ( ) . get ( )
398+ }
399+ unsafe fn inner < ' a > ( & ' a self ) -> & ' a Flavor < T > {
400+ & * self . inner_unsafe ( ) . get ( )
401+ }
402+ }
403+ impl < T > UnsafeFlavor < T > for Sender < T > {
404+ fn inner_unsafe < ' a > ( & ' a self ) -> & ' a Unsafe < Flavor < T > > {
405+ & self . inner
406+ }
407+ }
408+ impl < T > UnsafeFlavor < T > for Receiver < T > {
409+ fn inner_unsafe < ' a > ( & ' a self ) -> & ' a Unsafe < Flavor < T > > {
410+ & self . inner
411+ }
412+ }
413+
393414/// Creates a new asynchronous channel, returning the sender/receiver halves.
394415///
395416/// All data sent on the sender will become available on the receiver, and no
@@ -458,7 +479,7 @@ pub fn sync_channel<T: Send>(bound: uint) -> (SyncSender<T>, Receiver<T>) {
458479
459480impl < T : Send > Sender < T > {
460481 fn new ( inner : Flavor < T > ) -> Sender < T > {
461- Sender { inner : inner, sends : Cell :: new ( 0 ) , marker : marker:: NoShare }
482+ Sender { inner : Unsafe :: new ( inner) , sends : Cell :: new ( 0 ) , marker : marker:: NoShare }
462483 }
463484
464485 /// Sends a value along this channel to be received by the corresponding
@@ -532,7 +553,7 @@ impl<T: Send> Sender<T> {
532553 task. map ( |t| t. maybe_yield ( ) ) ;
533554 }
534555
535- let ( new_inner, ret) = match self . inner {
556+ let ( new_inner, ret) = match * unsafe { self . inner ( ) } {
536557 Oneshot ( ref p) => {
537558 let p = p. get ( ) ;
538559 unsafe {
@@ -564,16 +585,16 @@ impl<T: Send> Sender<T> {
564585 } ;
565586
566587 unsafe {
567- let mut tmp = Sender :: new ( Stream ( new_inner) ) ;
568- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner , & mut tmp. inner ) ;
588+ let tmp = Sender :: new ( Stream ( new_inner) ) ;
589+ mem:: swap ( self . mut_inner ( ) , tmp. mut_inner ( ) ) ;
569590 }
570591 return ret;
571592 }
572593}
573594
574595impl < T : Send > Clone for Sender < T > {
575596 fn clone ( & self ) -> Sender < T > {
576- let ( packet, sleeper) = match self . inner {
597+ let ( packet, sleeper) = match * unsafe { self . inner ( ) } {
577598 Oneshot ( ref p) => {
578599 let ( a, b) = UnsafeArc :: new2 ( shared:: Packet :: new ( ) ) ;
579600 match unsafe { ( * p. get ( ) ) . upgrade ( Receiver :: new ( Shared ( a) ) ) } {
@@ -598,8 +619,8 @@ impl<T: Send> Clone for Sender<T> {
598619 unsafe {
599620 ( * packet. get ( ) ) . inherit_blocker ( sleeper) ;
600621
601- let mut tmp = Sender :: new ( Shared ( packet. clone ( ) ) ) ;
602- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner , & mut tmp. inner ) ;
622+ let tmp = Sender :: new ( Shared ( packet. clone ( ) ) ) ;
623+ mem:: swap ( self . mut_inner ( ) , tmp. mut_inner ( ) ) ;
603624 }
604625 Sender :: new ( Shared ( packet) )
605626 }
@@ -608,7 +629,7 @@ impl<T: Send> Clone for Sender<T> {
608629#[ unsafe_destructor]
609630impl < T : Send > Drop for Sender < T > {
610631 fn drop ( & mut self ) {
611- match self . inner {
632+ match * unsafe { self . mut_inner ( ) } {
612633 Oneshot ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_chan ( ) ; } ,
613634 Stream ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_chan ( ) ; } ,
614635 Shared ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_chan ( ) ; } ,
@@ -705,7 +726,7 @@ impl<T: Send> Drop for SyncSender<T> {
705726
706727impl < T : Send > Receiver < T > {
707728 fn new ( inner : Flavor < T > ) -> Receiver < T > {
708- Receiver { inner : inner, receives : Cell :: new ( 0 ) , marker : marker:: NoShare }
729+ Receiver { inner : Unsafe :: new ( inner) , receives : Cell :: new ( 0 ) , marker : marker:: NoShare }
709730 }
710731
711732 /// Blocks waiting for a value on this receiver
@@ -757,7 +778,7 @@ impl<T: Send> Receiver<T> {
757778 }
758779
759780 loop {
760- let mut new_port = match self . inner {
781+ let new_port = match * unsafe { self . inner ( ) } {
761782 Oneshot ( ref p) => {
762783 match unsafe { ( * p. get ( ) ) . try_recv ( ) } {
763784 Ok ( t) => return Ok ( t) ,
@@ -790,8 +811,8 @@ impl<T: Send> Receiver<T> {
790811 }
791812 } ;
792813 unsafe {
793- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner ,
794- & mut new_port. inner ) ;
814+ mem:: swap ( self . mut_inner ( ) ,
815+ new_port. mut_inner ( ) ) ;
795816 }
796817 }
797818 }
@@ -810,7 +831,7 @@ impl<T: Send> Receiver<T> {
810831 /// the value found on the receiver is returned.
811832 pub fn recv_opt ( & self ) -> Result < T , ( ) > {
812833 loop {
813- let mut new_port = match self . inner {
834+ let new_port = match * unsafe { self . inner ( ) } {
814835 Oneshot ( ref p) => {
815836 match unsafe { ( * p. get ( ) ) . recv ( ) } {
816837 Ok ( t) => return Ok ( t) ,
@@ -837,8 +858,7 @@ impl<T: Send> Receiver<T> {
837858 Sync ( ref p) => return unsafe { ( * p. get ( ) ) . recv ( ) }
838859 } ;
839860 unsafe {
840- mem:: swap ( & mut cast:: transmute_mut ( self ) . inner ,
841- & mut new_port. inner ) ;
861+ mem:: swap ( self . mut_inner ( ) , new_port. mut_inner ( ) ) ;
842862 }
843863 }
844864 }
@@ -853,7 +873,7 @@ impl<T: Send> Receiver<T> {
853873impl < T : Send > select:: Packet for Receiver < T > {
854874 fn can_recv ( & self ) -> bool {
855875 loop {
856- let mut new_port = match self . inner {
876+ let new_port = match * unsafe { self . inner ( ) } {
857877 Oneshot ( ref p) => {
858878 match unsafe { ( * p. get ( ) ) . can_recv ( ) } {
859879 Ok ( ret) => return ret,
@@ -874,15 +894,15 @@ impl<T: Send> select::Packet for Receiver<T> {
874894 }
875895 } ;
876896 unsafe {
877- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner ,
878- & mut new_port. inner ) ;
897+ mem:: swap ( self . mut_inner ( ) ,
898+ new_port. mut_inner ( ) ) ;
879899 }
880900 }
881901 }
882902
883903 fn start_selection ( & self , mut task : BlockedTask ) -> Result < ( ) , BlockedTask > {
884904 loop {
885- let ( t, mut new_port) = match self . inner {
905+ let ( t, new_port) = match * unsafe { self . inner ( ) } {
886906 Oneshot ( ref p) => {
887907 match unsafe { ( * p. get ( ) ) . start_selection ( task) } {
888908 oneshot:: SelSuccess => return Ok ( ( ) ) ,
@@ -906,16 +926,16 @@ impl<T: Send> select::Packet for Receiver<T> {
906926 } ;
907927 task = t;
908928 unsafe {
909- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner ,
910- & mut new_port. inner ) ;
929+ mem:: swap ( self . mut_inner ( ) ,
930+ new_port. mut_inner ( ) ) ;
911931 }
912932 }
913933 }
914934
915935 fn abort_selection ( & self ) -> bool {
916936 let mut was_upgrade = false ;
917937 loop {
918- let result = match self . inner {
938+ let result = match * unsafe { self . inner ( ) } {
919939 Oneshot ( ref p) => unsafe { ( * p. get ( ) ) . abort_selection ( ) } ,
920940 Stream ( ref p) => unsafe {
921941 ( * p. get ( ) ) . abort_selection ( was_upgrade)
@@ -927,11 +947,11 @@ impl<T: Send> select::Packet for Receiver<T> {
927947 ( * p. get ( ) ) . abort_selection ( )
928948 } ,
929949 } ;
930- let mut new_port = match result { Ok ( b) => return b, Err ( p) => p } ;
950+ let new_port = match result { Ok ( b) => return b, Err ( p) => p } ;
931951 was_upgrade = true ;
932952 unsafe {
933- mem:: swap ( & mut cast :: transmute_mut ( self ) . inner ,
934- & mut new_port. inner ) ;
953+ mem:: swap ( self . mut_inner ( ) ,
954+ new_port. mut_inner ( ) ) ;
935955 }
936956 }
937957 }
@@ -944,7 +964,7 @@ impl<'a, T: Send> Iterator<T> for Messages<'a, T> {
944964#[ unsafe_destructor]
945965impl < T : Send > Drop for Receiver < T > {
946966 fn drop ( & mut self ) {
947- match self . inner {
967+ match * unsafe { self . mut_inner ( ) } {
948968 Oneshot ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_port ( ) ; } ,
949969 Stream ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_port ( ) ; } ,
950970 Shared ( ref mut p) => unsafe { ( * p. get ( ) ) . drop_port ( ) ; } ,
0 commit comments