@@ -67,17 +67,24 @@ struct LeafNode<K, V> {
67
67
}
68
68
69
69
impl < K , V > LeafNode < K , V > {
70
- /// Creates a new `LeafNode`. Unsafe because all nodes should really be hidden behind
70
+ /// Initializes a new `LeafNode` in-place.
71
+ unsafe fn init ( this : * mut Self ) {
72
+ // As a general policy, we leave fields uninitialized if they can be, as this should
73
+ // be both slightly faster and easier to track in Valgrind.
74
+ unsafe {
75
+ // parent_idx, keys, and vals are all MaybeUninit
76
+ ptr:: addr_of_mut!( ( * this) . parent) . write ( None ) ;
77
+ ptr:: addr_of_mut!( ( * this) . len) . write ( 0 ) ;
78
+ }
79
+ }
80
+
81
+ /// Creates a new boxed `LeafNode`. Unsafe because all nodes should really be hidden behind
71
82
/// `BoxedNode`, preventing accidental dropping of uninitialized keys and values.
72
- unsafe fn new ( ) -> Self {
73
- LeafNode {
74
- // As a general policy, we leave fields uninitialized if they can be, as this should
75
- // be both slightly faster and easier to track in Valgrind.
76
- keys : MaybeUninit :: uninit_array ( ) ,
77
- vals : MaybeUninit :: uninit_array ( ) ,
78
- parent : None ,
79
- parent_idx : MaybeUninit :: uninit ( ) ,
80
- len : 0 ,
83
+ unsafe fn new ( ) -> Box < Self > {
84
+ unsafe {
85
+ let mut leaf = Box :: new_uninit ( ) ;
86
+ LeafNode :: init ( leaf. as_mut_ptr ( ) ) ;
87
+ leaf. assume_init ( )
81
88
}
82
89
}
83
90
}
@@ -99,15 +106,20 @@ struct InternalNode<K, V> {
99
106
}
100
107
101
108
impl < K , V > InternalNode < K , V > {
102
- /// Creates a new `InternalNode`.
109
+ /// Creates a new boxed `InternalNode`.
103
110
///
104
- /// This is unsafe for two reasons. First, it returns an `InternalNode` by value , risking
111
+ /// This is unsafe for two reasons. First, it returns an owned `InternalNode` in a box , risking
105
112
/// dropping of uninitialized fields. Second, an invariant of internal nodes is that `len + 1`
106
113
/// edges are initialized and valid, meaning that even when the node is empty (having a
107
114
/// `len` of 0), there must be one initialized and valid edge. This function does not set up
108
115
/// such an edge.
109
- unsafe fn new ( ) -> Self {
110
- InternalNode { data : unsafe { LeafNode :: new ( ) } , edges : MaybeUninit :: uninit_array ( ) }
116
+ unsafe fn new ( ) -> Box < Self > {
117
+ unsafe {
118
+ let mut node = Box :: < Self > :: new_uninit ( ) ;
119
+ // We only need to initialize the data; the edges are MaybeUninit.
120
+ LeafNode :: init ( ptr:: addr_of_mut!( ( * node. as_mut_ptr( ) ) . data) ) ;
121
+ node. assume_init ( )
122
+ }
111
123
}
112
124
}
113
125
@@ -133,7 +145,7 @@ impl<K, V> Root<K, V> {
133
145
134
146
impl < K , V > NodeRef < marker:: Owned , K , V , marker:: Leaf > {
135
147
fn new_leaf ( ) -> Self {
136
- Self :: from_new_leaf ( Box :: new ( unsafe { LeafNode :: new ( ) } ) )
148
+ Self :: from_new_leaf ( unsafe { LeafNode :: new ( ) } )
137
149
}
138
150
139
151
fn from_new_leaf ( leaf : Box < LeafNode < K , V > > ) -> Self {
@@ -143,7 +155,7 @@ impl<K, V> NodeRef<marker::Owned, K, V, marker::Leaf> {
143
155
144
156
impl < K , V > NodeRef < marker:: Owned , K , V , marker:: Internal > {
145
157
fn new_internal ( child : Root < K , V > ) -> Self {
146
- let mut new_node = Box :: new ( unsafe { InternalNode :: new ( ) } ) ;
158
+ let mut new_node = unsafe { InternalNode :: new ( ) } ;
147
159
new_node. edges [ 0 ] . write ( child. node ) ;
148
160
NodeRef :: from_new_internal ( new_node, child. height + 1 )
149
161
}
@@ -1075,7 +1087,7 @@ impl<'a, K: 'a, V: 'a> Handle<NodeRef<marker::Mut<'a>, K, V, marker::Leaf>, mark
1075
1087
/// allocated node.
1076
1088
pub fn split ( mut self ) -> SplitResult < ' a , K , V , marker:: Leaf > {
1077
1089
unsafe {
1078
- let mut new_node = Box :: new ( LeafNode :: new ( ) ) ;
1090
+ let mut new_node = LeafNode :: new ( ) ;
1079
1091
1080
1092
let kv = self . split_leaf_data ( & mut new_node) ;
1081
1093
@@ -1110,7 +1122,7 @@ impl<'a, K: 'a, V: 'a> Handle<NodeRef<marker::Mut<'a>, K, V, marker::Internal>,
1110
1122
pub fn split ( mut self ) -> SplitResult < ' a , K , V , marker:: Internal > {
1111
1123
let old_len = self . node . len ( ) ;
1112
1124
unsafe {
1113
- let mut new_node = Box :: new ( InternalNode :: new ( ) ) ;
1125
+ let mut new_node = InternalNode :: new ( ) ;
1114
1126
let kv = self . split_leaf_data ( & mut new_node. data ) ;
1115
1127
let new_len = usize:: from ( new_node. data . len ) ;
1116
1128
move_to_slice (
0 commit comments