@@ -7,6 +7,21 @@ use Secp256k1;
7
7
#[ cfg( feature = "std" ) ]
8
8
pub use self :: std_only:: * ;
9
9
10
+
11
+
12
+ /// A type that represents the type with the biggest alignment we can get in rust.
13
+ /// Trying to match what `malloc` does in C, this should be aligned enough to contain pointers too.
14
+ /// This type can have different size/alignment depending on the architecture.
15
+ #[ cfg( any( target_pointer_width = "32" , target_pointer_width = "16" , target_pointer_wid = "8" ) ) ]
16
+ pub type AlignType = u64 ;
17
+
18
+ /// A type that represents the type with the biggest alignment we can get in rust.
19
+ /// Trying to match what `malloc` does in C, this should be aligned enough to contain pointers too.
20
+ /// This type can have different size/alignment depending on the architecture.
21
+ #[ cfg( not( any( target_pointer_width = "32" , target_pointer_width = "16" , target_pointer_wid = "8" ) ) ) ]
22
+ pub type AlignType = usize ;
23
+
24
+
10
25
/// A trait for all kinds of Context's that Lets you define the exact flags and a function to deallocate memory.
11
26
/// * DO NOT * implement it for your own types.
12
27
pub unsafe trait Context {
@@ -15,7 +30,7 @@ pub unsafe trait Context {
15
30
/// A constant description of the context.
16
31
const DESCRIPTION : & ' static str ;
17
32
/// A function to deallocate the memory when the context is dropped.
18
- fn deallocate ( ptr : * mut [ u8 ] ) ;
33
+ fn deallocate ( ptr : * mut [ AlignType ] ) ;
19
34
}
20
35
21
36
/// Marker trait for indicating that an instance of `Secp256k1` can be used for signing.
@@ -62,7 +77,7 @@ mod std_only {
62
77
const FLAGS : c_uint = ffi:: SECP256K1_START_SIGN ;
63
78
const DESCRIPTION : & ' static str = "signing only" ;
64
79
65
- fn deallocate ( ptr : * mut [ u8 ] ) {
80
+ fn deallocate ( ptr : * mut [ AlignType ] ) {
66
81
let _ = unsafe { Box :: from_raw ( ptr) } ;
67
82
}
68
83
}
@@ -71,7 +86,7 @@ mod std_only {
71
86
const FLAGS : c_uint = ffi:: SECP256K1_START_VERIFY ;
72
87
const DESCRIPTION : & ' static str = "verification only" ;
73
88
74
- fn deallocate ( ptr : * mut [ u8 ] ) {
89
+ fn deallocate ( ptr : * mut [ AlignType ] ) {
75
90
let _ = unsafe { Box :: from_raw ( ptr) } ;
76
91
}
77
92
}
@@ -80,15 +95,15 @@ mod std_only {
80
95
const FLAGS : c_uint = VerifyOnly :: FLAGS | SignOnly :: FLAGS ;
81
96
const DESCRIPTION : & ' static str = "all capabilities" ;
82
97
83
- fn deallocate ( ptr : * mut [ u8 ] ) {
98
+ fn deallocate ( ptr : * mut [ AlignType ] ) {
84
99
let _ = unsafe { Box :: from_raw ( ptr) } ;
85
100
}
86
101
}
87
102
88
103
impl < C : Context > Secp256k1 < C > {
89
104
/// Lets you create a context in a generic manner(sign/verify/all)
90
105
pub fn gen_new ( ) -> Secp256k1 < C > {
91
- let buf = vec ! [ 0u8 ; Self :: preallocate_size_gen( ) ] . into_boxed_slice ( ) ;
106
+ let buf = vec ! [ 0 as AlignType ; Self :: preallocate_size_gen( ) ] . into_boxed_slice ( ) ;
92
107
let ptr = Box :: into_raw ( buf) ;
93
108
Secp256k1 {
94
109
ctx : unsafe { ffi:: secp256k1_context_preallocated_create ( ptr as * mut c_void , C :: FLAGS ) } ,
@@ -128,7 +143,7 @@ mod std_only {
128
143
impl < C : Context > Clone for Secp256k1 < C > {
129
144
fn clone ( & self ) -> Secp256k1 < C > {
130
145
let clone_size = unsafe { ffi:: secp256k1_context_preallocated_clone_size ( self . ctx ) } ;
131
- let ptr_buf = Box :: into_raw ( vec ! [ 0u8 ; clone_size] . into_boxed_slice ( ) ) ;
146
+ let ptr_buf = Box :: into_raw ( vec ! [ 0 as AlignType ; clone_size] . into_boxed_slice ( ) ) ;
132
147
Secp256k1 {
133
148
ctx : unsafe { ffi:: secp256k1_context_preallocated_clone ( self . ctx , ptr_buf as * mut c_void ) } ,
134
149
phantom : PhantomData ,
@@ -149,7 +164,7 @@ unsafe impl<'buf> Context for SignOnlyPreallocated<'buf> {
149
164
const FLAGS : c_uint = ffi:: SECP256K1_START_SIGN ;
150
165
const DESCRIPTION : & ' static str = "signing only" ;
151
166
152
- fn deallocate ( _ptr : * mut [ u8 ] ) {
167
+ fn deallocate ( _ptr : * mut [ AlignType ] ) {
153
168
// Allocated by the user
154
169
}
155
170
}
@@ -158,7 +173,7 @@ unsafe impl<'buf> Context for VerifyOnlyPreallocated<'buf> {
158
173
const FLAGS : c_uint = ffi:: SECP256K1_START_VERIFY ;
159
174
const DESCRIPTION : & ' static str = "verification only" ;
160
175
161
- fn deallocate ( _ptr : * mut [ u8 ] ) {
176
+ fn deallocate ( _ptr : * mut [ AlignType ] ) {
162
177
// Allocated by the user
163
178
}
164
179
}
@@ -167,14 +182,14 @@ unsafe impl<'buf> Context for AllPreallocated<'buf> {
167
182
const FLAGS : c_uint = SignOnlyPreallocated :: FLAGS | VerifyOnlyPreallocated :: FLAGS ;
168
183
const DESCRIPTION : & ' static str = "all capabilities" ;
169
184
170
- fn deallocate ( _ptr : * mut [ u8 ] ) {
185
+ fn deallocate ( _ptr : * mut [ AlignType ] ) {
171
186
// Allocated by the user
172
187
}
173
188
}
174
189
175
190
impl < ' buf , C : Context + ' buf > Secp256k1 < C > {
176
191
/// Lets you create a context with preallocated buffer in a generic manner(sign/verify/all)
177
- pub fn preallocated_gen_new ( buf : & ' buf mut [ u8 ] ) -> Result < Secp256k1 < C > , Error > {
192
+ pub fn preallocated_gen_new ( buf : & ' buf mut [ AlignType ] ) -> Result < Secp256k1 < C > , Error > {
178
193
if buf. len ( ) < Self :: preallocate_size_gen ( ) {
179
194
return Err ( Error :: NotEnoughMemory ) ;
180
195
}
@@ -185,29 +200,51 @@ impl<'buf, C: Context + 'buf> Secp256k1<C> {
185
200
C :: FLAGS )
186
201
} ,
187
202
phantom : PhantomData ,
188
- buf : buf as * mut [ u8 ] ,
203
+ buf : buf as * mut [ AlignType ] ,
189
204
} )
190
205
}
191
206
}
192
207
193
208
impl < ' buf > Secp256k1 < AllPreallocated < ' buf > > {
194
209
/// Creates a new Secp256k1 context with all capabilities
195
- pub fn preallocated_new ( buf : & ' buf mut [ u8 ] ) -> Result < Secp256k1 < AllPreallocated < ' buf > > , Error > {
210
+ pub fn preallocated_new ( buf : & ' buf mut [ AlignType ] ) -> Result < Secp256k1 < AllPreallocated < ' buf > > , Error > {
196
211
Secp256k1 :: preallocated_gen_new ( buf)
197
212
}
198
- /// Uses the ffi `secp256k1_context_preallocated_size` to check the memory size needed for a context
213
+ /// Returns the required memory for a preallocated context buffer in a generic manner(sign/verify/all)
214
+ ///
215
+ /// Notice that the memory returned is in [AlignedType](type.AlignType.html)
216
+ ///
217
+ /// ## Examples
218
+ /// ```rust
219
+ /// # use secp256k1::*;
220
+ /// let buf_size = Secp256k1::preallocate_size();
221
+ /// let mut buf = vec![0; buf_size];
222
+ /// let secp = Secp256k1::preallocated_new(&mut buf).unwrap();
223
+ ///
224
+ /// ```
199
225
pub fn preallocate_size ( ) -> usize {
200
226
Self :: preallocate_size_gen ( )
201
227
}
202
228
}
203
229
204
230
impl < ' buf > Secp256k1 < SignOnlyPreallocated < ' buf > > {
205
231
/// Creates a new Secp256k1 context that can only be used for signing
206
- pub fn preallocated_signing_only ( buf : & ' buf mut [ u8 ] ) -> Result < Secp256k1 < SignOnlyPreallocated < ' buf > > , Error > {
232
+ pub fn preallocated_signing_only ( buf : & ' buf mut [ AlignType ] ) -> Result < Secp256k1 < SignOnlyPreallocated < ' buf > > , Error > {
207
233
Secp256k1 :: preallocated_gen_new ( buf)
208
234
}
209
235
210
- /// Uses the ffi `secp256k1_context_preallocated_size` to check the memory size needed for the context
236
+ /// Returns the required memory for a preallocated context buffer in a generic manner(sign/verify/all)
237
+ ///
238
+ /// Notice that the memory returned is in [AlignedType](type.AlignType.html)
239
+ ///
240
+ /// ## Examples
241
+ /// ```rust
242
+ /// # use secp256k1::*;
243
+ /// let buf_size = Secp256k1::preallocate_signing_size();
244
+ /// let mut buf = vec![0; buf_size];
245
+ /// let secp = Secp256k1::preallocated_signing_only(&mut buf).unwrap();
246
+ ///
247
+ /// ```
211
248
#[ inline]
212
249
pub fn preallocate_signing_size ( ) -> usize {
213
250
Self :: preallocate_size_gen ( )
@@ -216,11 +253,22 @@ impl<'buf> Secp256k1<SignOnlyPreallocated<'buf>> {
216
253
217
254
impl < ' buf > Secp256k1 < VerifyOnlyPreallocated < ' buf > > {
218
255
/// Creates a new Secp256k1 context that can only be used for verification
219
- pub fn preallocated_verification_only ( buf : & ' buf mut [ u8 ] ) -> Result < Secp256k1 < VerifyOnlyPreallocated < ' buf > > , Error > {
256
+ pub fn preallocated_verification_only ( buf : & ' buf mut [ AlignType ] ) -> Result < Secp256k1 < VerifyOnlyPreallocated < ' buf > > , Error > {
220
257
Secp256k1 :: preallocated_gen_new ( buf)
221
258
}
222
259
223
- /// Uses the ffi `secp256k1_context_preallocated_size` to check the memory size needed for the context
260
+ /// Returns the required memory for a preallocated context buffer in a generic manner(sign/verify/all)
261
+ ///
262
+ /// Notice that the memory returned is in [AlignedType](type.AlignType.html)
263
+ ///
264
+ /// ## Examples
265
+ /// ```rust
266
+ /// # use secp256k1::*;
267
+ /// let buf_size = Secp256k1::preallocate_verification_size();
268
+ /// let mut buf = vec![0; buf_size];
269
+ /// let secp = Secp256k1::preallocated_verification_only(&mut buf).unwrap();
270
+ ///
271
+ /// ```
224
272
#[ inline]
225
273
pub fn preallocate_verification_size ( ) -> usize {
226
274
Self :: preallocate_size_gen ( )
0 commit comments