11cfg_if:: cfg_if! { 
22    if  #[ cfg( target_os = "linux" ) ]  { 
3+         /// pthread_t is a pointer on some platforms, 
4+          /// so we wrap it in this to impl Send + Sync. 
5+          #[ derive( Clone ,  Copy ) ] 
6+         #[ repr( transparent) ] 
7+         struct  PThread ( libc:: pthread_t) ; 
8+         // Safety: pthread_t is safe to send between threads 
9+         unsafe  impl  Send  for  PThread  { } 
10+         // Safety: pthread_t is safe to share between threads 
11+         unsafe  impl  Sync  for  PThread  { } 
312        /// Mitigation for <https://github.com/rust-lang/rust/issues/126600> 
413         /// 
514         /// On glibc, `libc::exit` has been observed to not always be thread-safe. 
@@ -23,17 +32,17 @@ cfg_if::cfg_if! {
2332        pub ( crate )  fn  unique_thread_exit( )  { 
2433            let  this_thread_id = unsafe  {  libc:: pthread_self( )  } ; 
2534            use  crate :: sync:: { Mutex ,  PoisonError } ; 
26-             static  EXITING_THREAD_ID :  Mutex <Option <libc :: pthread_t >> = Mutex :: new( None ) ; 
35+             static  EXITING_THREAD_ID :  Mutex <Option <PThread >> = Mutex :: new( None ) ; 
2736            let  mut  exiting_thread_id =
2837                EXITING_THREAD_ID . lock( ) . unwrap_or_else( PoisonError :: into_inner) ; 
2938            match  * exiting_thread_id { 
3039                None  => { 
3140                    // This is the first thread to call `unique_thread_exit`, 
3241                    // and this is the first time it is called. 
3342                    // Set EXITING_THREAD_ID to this thread's ID and return. 
34-                     * exiting_thread_id = Some ( this_thread_id) ; 
43+                     * exiting_thread_id = Some ( PThread ( this_thread_id) ) ; 
3544                } , 
36-                 Some ( exiting_thread_id)  if  exiting_thread_id == this_thread_id => { 
45+                 Some ( exiting_thread_id)  if  exiting_thread_id. 0  == this_thread_id => { 
3746                    // This is the first thread to call `unique_thread_exit`, 
3847                    // but this is the second time it is called. 
3948                    // Abort the process. 
0 commit comments