22
33use crate :: fmt;
44use crate :: hash:: { Hash , Hasher } ;
5- use crate :: ptr:: NonNull ;
65
76/// FIXME docs
87#[ lang = "pointee_trait" ]
@@ -62,17 +61,48 @@ impl<T: ?Sized> Clone for PtrComponents<T> {
6261/// The metadata for a `dyn SomeTrait` trait object type.
6362#[ lang = "dyn_metadata" ]
6463pub struct DynMetadata < Dyn : ?Sized > {
65- #[ allow( unused) ]
66- vtable_ptr : NonNull < ( ) > ,
64+ vtable_ptr : & ' static VTable ,
6765 phantom : crate :: marker:: PhantomData < Dyn > ,
6866}
6967
68+ /// The common prefix of all vtables. It is followed by function pointers for trait methods.
69+ ///
70+ /// Private implementation detail of `DynMetadata::size_of` etc.
71+ #[ repr( C ) ]
72+ struct VTable {
73+ drop_in_place : fn ( * mut ( ) ) ,
74+ size_of : usize ,
75+ align_of : usize ,
76+ }
77+
78+ impl < Dyn : ?Sized > DynMetadata < Dyn > {
79+ /// Returns the size of the type associated with this vtable.
80+ #[ inline]
81+ pub fn size_of ( self ) -> usize {
82+ self . vtable_ptr . size_of
83+ }
84+
85+ /// Returns the alignment of the type associated with this vtable.
86+ #[ inline]
87+ pub fn align_of ( self ) -> usize {
88+ self . vtable_ptr . align_of
89+ }
90+
91+ /// Returns the size and alignment together as a `Layout`
92+ #[ inline]
93+ pub fn layout ( self ) -> crate :: alloc:: Layout {
94+ // SAFETY: the compiler emitted this vtable for a concrete Rust type which
95+ // is known to have a valid layout. Same rationale as in `Layout::for_value`.
96+ unsafe { crate :: alloc:: Layout :: from_size_align_unchecked ( self . size_of ( ) , self . align_of ( ) ) }
97+ }
98+ }
99+
70100unsafe impl < Dyn : ?Sized > Send for DynMetadata < Dyn > { }
71101unsafe impl < Dyn : ?Sized > Sync for DynMetadata < Dyn > { }
72102
73103impl < Dyn : ?Sized > fmt:: Debug for DynMetadata < Dyn > {
74104 fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
75- f. write_str ( "DynMetadata { … }" )
105+ f. debug_tuple ( "DynMetadata" ) . field ( & ( self . vtable_ptr as * const VTable ) ) . finish ( )
76106 }
77107}
78108
@@ -94,27 +124,27 @@ impl<Dyn: ?Sized> Eq for DynMetadata<Dyn> {}
94124impl < Dyn : ?Sized > PartialEq for DynMetadata < Dyn > {
95125 #[ inline]
96126 fn eq ( & self , other : & Self ) -> bool {
97- self . vtable_ptr == other. vtable_ptr
127+ crate :: ptr :: eq :: < VTable > ( self . vtable_ptr , other. vtable_ptr )
98128 }
99129}
100130
101131impl < Dyn : ?Sized > Ord for DynMetadata < Dyn > {
102132 #[ inline]
103133 fn cmp ( & self , other : & Self ) -> crate :: cmp:: Ordering {
104- self . vtable_ptr . cmp ( & other. vtable_ptr )
134+ ( self . vtable_ptr as * const VTable ) . cmp ( & ( other. vtable_ptr as * const VTable ) )
105135 }
106136}
107137
108138impl < Dyn : ?Sized > PartialOrd for DynMetadata < Dyn > {
109139 #[ inline]
110140 fn partial_cmp ( & self , other : & Self ) -> Option < crate :: cmp:: Ordering > {
111- Some ( self . vtable_ptr . cmp ( & other. vtable_ptr ) )
141+ Some ( self . cmp ( other) )
112142 }
113143}
114144
115145impl < Dyn : ?Sized > Hash for DynMetadata < Dyn > {
116146 #[ inline]
117147 fn hash < H : Hasher > ( & self , hasher : & mut H ) {
118- self . vtable_ptr . hash ( hasher)
148+ crate :: ptr :: hash :: < VTable , _ > ( self . vtable_ptr , hasher)
119149 }
120150}
0 commit comments