Merge pull request #179 from elichai/2019-11-raw-context
Creating context from raw pointer
This commit is contained in:
commit
02f66177f0
|
@ -1,4 +1,5 @@
|
||||||
use core::marker::PhantomData;
|
use core::marker::PhantomData;
|
||||||
|
use ptr;
|
||||||
use ffi::{self, CPtr};
|
use ffi::{self, CPtr};
|
||||||
use types::{c_uint, c_void};
|
use types::{c_uint, c_void};
|
||||||
use Error;
|
use Error;
|
||||||
|
@ -214,6 +215,25 @@ impl<'buf> Secp256k1<AllPreallocated<'buf>> {
|
||||||
pub fn preallocate_size() -> usize {
|
pub fn preallocate_size() -> usize {
|
||||||
Self::preallocate_size_gen()
|
Self::preallocate_size_gen()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Create a context from a raw context.
|
||||||
|
///
|
||||||
|
/// # Safety
|
||||||
|
/// This is highly unsafe, due to the number of conditions that aren't checked.
|
||||||
|
/// * `raw_ctx` needs to be a valid Secp256k1 context pointer.
|
||||||
|
/// that was generated by *exactly* the same code/version of the libsecp256k1 used here.
|
||||||
|
/// * The capabilities (All/SignOnly/VerifyOnly) of the context *must* match the flags passed to libsecp256k1
|
||||||
|
/// when generating the context.
|
||||||
|
/// * The user must handle the freeing of the context(using the correct functions) by himself.
|
||||||
|
/// * Violating these may lead to Undefined Behavior.
|
||||||
|
///
|
||||||
|
pub unsafe fn from_raw_all(raw_ctx: *mut ffi::Context) -> Secp256k1<AllPreallocated<'buf>> {
|
||||||
|
Secp256k1 {
|
||||||
|
ctx: raw_ctx,
|
||||||
|
phantom: PhantomData,
|
||||||
|
buf: ptr::null_mut::<[u8;0]>() as *mut [u8] ,
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'buf> Secp256k1<SignOnlyPreallocated<'buf>> {
|
impl<'buf> Secp256k1<SignOnlyPreallocated<'buf>> {
|
||||||
|
@ -227,6 +247,25 @@ impl<'buf> Secp256k1<SignOnlyPreallocated<'buf>> {
|
||||||
pub fn preallocate_signing_size() -> usize {
|
pub fn preallocate_signing_size() -> usize {
|
||||||
Self::preallocate_size_gen()
|
Self::preallocate_size_gen()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Create a context from a raw context.
|
||||||
|
///
|
||||||
|
/// # Safety
|
||||||
|
/// This is highly unsafe, due to the number of conditions that aren't checked.
|
||||||
|
/// * `raw_ctx` needs to be a valid Secp256k1 context pointer.
|
||||||
|
/// that was generated by *exactly* the same code/version of the libsecp256k1 used here.
|
||||||
|
/// * The capabilities (All/SignOnly/VerifyOnly) of the context *must* match the flags passed to libsecp256k1
|
||||||
|
/// when generating the context.
|
||||||
|
/// * The user must handle the freeing of the context(using the correct functions) by himself.
|
||||||
|
/// * This list *is not* exhaustive, and any violation may lead to Undefined Behavior.,
|
||||||
|
///
|
||||||
|
pub unsafe fn from_raw_signining_only(raw_ctx: *mut ffi::Context) -> Secp256k1<SignOnlyPreallocated<'buf>> {
|
||||||
|
Secp256k1 {
|
||||||
|
ctx: raw_ctx,
|
||||||
|
phantom: PhantomData,
|
||||||
|
buf: ptr::null_mut::<[u8;0]>() as *mut [u8] ,
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'buf> Secp256k1<VerifyOnlyPreallocated<'buf>> {
|
impl<'buf> Secp256k1<VerifyOnlyPreallocated<'buf>> {
|
||||||
|
@ -240,4 +279,23 @@ impl<'buf> Secp256k1<VerifyOnlyPreallocated<'buf>> {
|
||||||
pub fn preallocate_verification_size() -> usize {
|
pub fn preallocate_verification_size() -> usize {
|
||||||
Self::preallocate_size_gen()
|
Self::preallocate_size_gen()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Create a context from a raw context.
|
||||||
|
///
|
||||||
|
/// # Safety
|
||||||
|
/// This is highly unsafe, due to the number of conditions that aren't checked.
|
||||||
|
/// * `raw_ctx` needs to be a valid Secp256k1 context pointer.
|
||||||
|
/// that was generated by *exactly* the same code/version of the libsecp256k1 used here.
|
||||||
|
/// * The capabilities (All/SignOnly/VerifyOnly) of the context *must* match the flags passed to libsecp256k1
|
||||||
|
/// when generating the context.
|
||||||
|
/// * The user must handle the freeing of the context(using the correct functions) by himself.
|
||||||
|
/// * This list *is not* exhaustive, and any violation may lead to Undefined Behavior.,
|
||||||
|
///
|
||||||
|
pub unsafe fn from_raw_verification_only(raw_ctx: *mut ffi::Context) -> Secp256k1<VerifyOnlyPreallocated<'buf>> {
|
||||||
|
Secp256k1 {
|
||||||
|
ctx: raw_ctx,
|
||||||
|
phantom: PhantomData,
|
||||||
|
buf: ptr::null_mut::<[u8;0]>() as *mut [u8] ,
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
35
src/lib.rs
35
src/lib.rs
|
@ -756,6 +756,41 @@ mod tests {
|
||||||
unsafe { ffi::secp256k1_context_destroy(ctx_full) };
|
unsafe { ffi::secp256k1_context_destroy(ctx_full) };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_raw_ctx() {
|
||||||
|
let ctx_full = Secp256k1::new();
|
||||||
|
let ctx_sign = Secp256k1::signing_only();
|
||||||
|
let ctx_vrfy = Secp256k1::verification_only();
|
||||||
|
|
||||||
|
let full = unsafe {Secp256k1::from_raw_all(ctx_full.ctx)};
|
||||||
|
let sign = unsafe {Secp256k1::from_raw_signining_only(ctx_sign.ctx)};
|
||||||
|
let vrfy = unsafe {Secp256k1::from_raw_verification_only(ctx_vrfy.ctx)};
|
||||||
|
|
||||||
|
let (sk, pk) = full.generate_keypair(&mut thread_rng());
|
||||||
|
let msg = Message::from_slice(&[2u8; 32]).unwrap();
|
||||||
|
// Try signing
|
||||||
|
assert_eq!(sign.sign(&msg, &sk), full.sign(&msg, &sk));
|
||||||
|
let sig = full.sign(&msg, &sk);
|
||||||
|
|
||||||
|
// Try verifying
|
||||||
|
assert!(vrfy.verify(&msg, &sig, &pk).is_ok());
|
||||||
|
assert!(full.verify(&msg, &sig, &pk).is_ok());
|
||||||
|
|
||||||
|
drop(full);drop(sign);drop(vrfy);
|
||||||
|
drop(ctx_full);drop(ctx_sign);drop(ctx_vrfy);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[should_panic]
|
||||||
|
fn test_panic_raw_ctx() {
|
||||||
|
let ctx_vrfy = Secp256k1::verification_only();
|
||||||
|
let raw_ctx_verify_as_full = unsafe {Secp256k1::from_raw_all(ctx_vrfy.ctx)};
|
||||||
|
let (sk, _) = raw_ctx_verify_as_full.generate_keypair(&mut thread_rng());
|
||||||
|
let msg = Message::from_slice(&[2u8; 32]).unwrap();
|
||||||
|
// Try signing
|
||||||
|
raw_ctx_verify_as_full.sign(&msg, &sk);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_preallocation() {
|
fn test_preallocation() {
|
||||||
let mut buf_ful = vec![0u8; Secp256k1::preallocate_size()];
|
let mut buf_ful = vec![0u8; Secp256k1::preallocate_size()];
|
||||||
|
|
Loading…
Reference in New Issue