@@ -161,7 +161,7 @@ mod tests;
161161use crate :: any:: Any ;
162162use crate :: cell:: { OnceCell , UnsafeCell } ;
163163use crate :: env;
164- use crate :: ffi:: { CStr , CString } ;
164+ use crate :: ffi:: CStr ;
165165use crate :: fmt;
166166use crate :: io;
167167use crate :: marker:: PhantomData ;
@@ -487,11 +487,7 @@ impl Builder {
487487 amt
488488 } ) ;
489489
490- let my_thread = name. map_or_else ( Thread :: new_unnamed, |name| unsafe {
491- Thread :: new (
492- CString :: new ( name) . expect ( "thread name may not contain interior null bytes" ) ,
493- )
494- } ) ;
490+ let my_thread = name. map_or_else ( Thread :: new_unnamed, |name| Thread :: new ( name. into ( ) ) ) ;
495491 let their_thread = my_thread. clone ( ) ;
496492
497493 let my_packet: Arc < Packet < ' scope , T > > = Arc :: new ( Packet {
@@ -1273,10 +1269,34 @@ impl ThreadId {
12731269/// The internal representation of a `Thread`'s name.
12741270enum ThreadName {
12751271 Main ,
1276- Other ( CString ) ,
1272+ Other ( ThreadNameString ) ,
12771273 Unnamed ,
12781274}
12791275
1276+ // This module ensures private fields are kept private, which is necessary to enforce the safety requirements.
1277+ mod thread_name_string {
1278+ use crate :: ffi:: { CStr , CString } ;
1279+
1280+ /// Like a `String` it's guaranteed UTF-8 and like a `CString` it's null terminated.
1281+ pub ( crate ) struct ThreadNameString {
1282+ inner : CString ,
1283+ }
1284+ impl core:: ops:: Deref for ThreadNameString {
1285+ type Target = CStr ;
1286+ fn deref ( & self ) -> & CStr {
1287+ & self . inner
1288+ }
1289+ }
1290+ impl From < String > for ThreadNameString {
1291+ fn from ( s : String ) -> Self {
1292+ Self {
1293+ inner : CString :: new ( s) . expect ( "thread name may not contain interior null bytes" ) ,
1294+ }
1295+ }
1296+ }
1297+ }
1298+ pub ( crate ) use thread_name_string:: ThreadNameString ;
1299+
12801300/// The internal representation of a `Thread` handle
12811301struct Inner {
12821302 name : ThreadName , // Guaranteed to be UTF-8
@@ -1316,10 +1336,7 @@ pub struct Thread {
13161336
13171337impl Thread {
13181338 /// Used only internally to construct a thread object without spawning.
1319- ///
1320- /// # Safety
1321- /// `name` must be valid UTF-8.
1322- pub ( crate ) unsafe fn new ( name : CString ) -> Thread {
1339+ pub ( crate ) fn new ( name : ThreadNameString ) -> Thread {
13231340 unsafe { Self :: new_inner ( ThreadName :: Other ( name) ) }
13241341 }
13251342
0 commit comments