Skip to content

Commit

Permalink
Move secp256k1_recover to its own crate (#1656)
Browse files Browse the repository at this point in the history
* move secp256k1_recover to its own crate

* move syscall definition

* remove libsecp256k1 dep from solana-program

* update sbf lock file

* update doc links

* fix doc tests and dev deps

* update deps in programs/sbf

* fmt

* add frozen-abi support

* update lock files

* use borsh directly in solana-secp256k1-recover dev deps

* re-export solana_secp256k1_recover with deprecation

* re-export in solana-program too

* use define_syscall macro now that it's available as a standalone crate

* fix macro import

* only require solana-define-syscall when target_os = "solana"

* re-export sol_secp256k1_recover with deprecation warning

* add docs.rs metadata

* don't compile doc examples to get around false positive in order-crates-for-publishing.py

* fmt

* fix AbiExample duplication

* Revert "fix AbiExample duplication"

This reverts commit 86e8671.

* fix frozen-abi usage
  • Loading branch information
kevinheavey committed Jul 17, 2024
1 parent 4f228f4 commit d809bd9
Show file tree
Hide file tree
Showing 14 changed files with 104 additions and 20 deletions.
16 changes: 16 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -397,6 +397,7 @@ solana-runtime = { path = "runtime", version = "=2.1.0" }
solana-runtime-transaction = { path = "runtime-transaction", version = "=2.1.0" }
solana-sdk = { path = "sdk", version = "=2.1.0" }
solana-sdk-macro = { path = "sdk/macro", version = "=2.1.0" }
solana-secp256k1-recover = { path = "curves/secp256k1-recover", version = "=2.1.0", default-features = false }
solana-send-transaction-service = { path = "send-transaction-service", version = "=2.1.0" }
solana-stake-program = { path = "programs/stake", version = "=2.1.0" }
solana-storage-bigtable = { path = "storage-bigtable", version = "=2.1.0" }
Expand Down
39 changes: 39 additions & 0 deletions curves/secp256k1-recover/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
[package]
name = "solana-secp256k1-recover"
description = "Solana SECP256K1 Recover"
documentation = "https://docs.rs/solana-secp256k1-recover"
version = { workspace = true }
authors = { workspace = true }
repository = { workspace = true }
homepage = { workspace = true }
license = { workspace = true }
edition = { workspace = true }

[dependencies]
borsh = { workspace = true, optional = true }
solana-frozen-abi = { workspace = true, optional = true }
solana-frozen-abi-macro = { workspace = true, optional = true }
thiserror = { workspace = true }

[target.'cfg(target_os = "solana")'.dependencies]
solana-define-syscall = { workspace = true }

[target.'cfg(not(target_os = "solana"))'.dependencies]
libsecp256k1 = { workspace = true }

[dev-dependencies]
anyhow = { workspace = true }
borsh = { workspace = true }

[target.'cfg(not(target_os = "solana"))'.dev-dependencies]
libsecp256k1 = { workspace = true, features = ["hmac"] }

[build-dependencies]
rustc_version = { workspace = true }

[features]
borsh = ["dep:borsh"]
frozen-abi = ["dep:solana-frozen-abi", "dep:solana-frozen-abi-macro"]

[package.metadata.docs.rs]
targets = ["x86_64-unknown-linux-gnu"]
1 change: 1 addition & 0 deletions curves/secp256k1-recover/build.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
#![cfg_attr(RUSTC_WITH_SPECIALIZATION, feature(min_specialization))]
//! Public key recovery from [secp256k1] ECDSA signatures.
//!
//! [secp256k1]: https://en.bitcoin.it/wiki/Secp256k1
Expand All @@ -21,7 +22,7 @@
//! also provides the [secp256k1 program][sp], which is more flexible, has lower CPU
//! cost, and can validate many signatures at once.
//!
//! [sp]: crate::secp256k1_program
//! [sp]: https://docs.rs/solana-program/latest/solana_program/secp256k1_program/
//! [`ecrecover`]: https://docs.soliditylang.org/en/v0.8.14/units-and-global-variables.html?highlight=ecrecover#mathematical-and-cryptographic-functions

#[cfg(feature = "borsh")]
Expand Down Expand Up @@ -63,7 +64,7 @@ pub const SECP256K1_SIGNATURE_LENGTH: usize = 64;
pub const SECP256K1_PUBLIC_KEY_LENGTH: usize = 64;

#[repr(transparent)]
#[cfg_attr(feature = "frozen-abi", derive(AbiExample))]
#[cfg_attr(feature = "frozen-abi", derive(solana_frozen_abi_macro::AbiExample))]
#[cfg_attr(
feature = "borsh",
derive(BorshSerialize, BorshDeserialize, BorshSchema),
Expand All @@ -85,6 +86,9 @@ impl Secp256k1Pubkey {
}
}

#[cfg(target_os = "solana")]
solana_define_syscall::define_syscall!(fn sol_secp256k1_recover(hash: *const u8, recovery_id: u64, signature: *const u8, result: *mut u8) -> u64);

/// Recover the public key from a [secp256k1] ECDSA signature and
/// cryptographically-hashed message.
///
Expand All @@ -110,7 +114,7 @@ impl Secp256k1Pubkey {
/// "overflowing" signature, and this function returns an error when parsing
/// overflowing signatures.
///
/// [`keccak`]: crate::keccak
/// [`keccak`]: https://docs.rs/solana-program/latest/solana_program/keccak/
/// [`wrapping_sub`]: https://doc.rust-lang.org/std/primitive.u8.html#method.wrapping_sub
///
/// On success this function returns a [`Secp256k1Pubkey`], a wrapper around a
Expand All @@ -123,7 +127,7 @@ impl Secp256k1Pubkey {
/// the [secp256k1 program][sp], which is more flexible, has lower CPU cost, and
/// can validate many signatures at once.
///
/// [sp]: crate::secp256k1_program
/// [sp]: https://docs.rs/solana-program/latest/solana_program/secp256k1_program/
///
/// The `secp256k1_recover` syscall is implemented with the [`libsecp256k1`]
/// crate, which clients may also want to use.
Expand Down Expand Up @@ -161,7 +165,7 @@ impl Secp256k1Pubkey {
/// signatures with high-order `S` values. The following code will accomplish
/// this:
///
/// ```rust
/// ```rust,ignore
/// # use solana_program::program_error::ProgramError;
/// # let signature_bytes = [
/// # 0x83, 0x55, 0x81, 0xDF, 0xB1, 0x02, 0xA7, 0xD2,
Expand Down Expand Up @@ -257,13 +261,13 @@ impl Secp256k1Pubkey {
/// The Solana program. Note that it uses `libsecp256k1` version 0.7.0 to parse
/// the secp256k1 signature to prevent malleability.
///
/// ```no_run
/// ```rust,ignore
/// use solana_program::{
/// entrypoint::ProgramResult,
/// keccak, msg,
/// program_error::ProgramError,
/// secp256k1_recover::secp256k1_recover,
/// };
/// use solana_secp256k1_recover::secp256k1_recover;
///
/// /// The key we expect to sign secp256k1 messages,
/// /// as serialized by `libsecp256k1::PublicKey::serialize`.
Expand Down Expand Up @@ -327,7 +331,7 @@ impl Secp256k1Pubkey {
///
/// The RPC client program:
///
/// ```no_run
/// ```rust,ignore
/// # use solana_program::example_mocks::solana_rpc_client;
/// # use solana_program::example_mocks::solana_sdk;
/// use anyhow::Result;
Expand Down Expand Up @@ -399,7 +403,7 @@ pub fn secp256k1_recover(
{
let mut pubkey_buffer = [0u8; SECP256K1_PUBLIC_KEY_LENGTH];
let result = unsafe {
crate::syscalls::sol_secp256k1_recover(
sol_secp256k1_recover(
hash.as_ptr(),
recovery_id as u64,
signature.as_ptr(),
Expand Down
15 changes: 14 additions & 1 deletion programs/sbf/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions programs/sbf/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ solana-sbf-rust-param-passing-dep = { path = "rust/param_passing_dep", version =
solana-sbf-rust-realloc-dep = { path = "rust/realloc_dep", version = "=2.1.0" }
solana-sbf-rust-realloc-invoke-dep = { path = "rust/realloc_invoke_dep", version = "=2.1.0" }
solana-sdk = { path = "../../sdk", version = "=2.1.0" }
solana-secp256k1-recover = { path = "../../curves/secp256k1-recover", version = "=2.1.0" }
solana-svm = { path = "../../svm", version = "=2.1.0" }
solana-timings = { path = "../../timings", version = "=2.1.0" }
solana-transaction-status = { path = "../../transaction-status", version = "=2.1.0" }
Expand Down
1 change: 1 addition & 0 deletions programs/sbf/rust/secp256k1_recover/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ edition = { workspace = true }
[dependencies]
libsecp256k1 = { workspace = true }
solana-program = { workspace = true }
solana-secp256k1-recover = { workspace = true }

[lib]
crate-type = ["cdylib"]
5 changes: 3 additions & 2 deletions programs/sbf/rust/secp256k1_recover/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@
//! Secp256k1Recover Syscall test

extern crate solana_program;
use solana_program::{
custom_heap_default, custom_panic_default, msg, secp256k1_recover::secp256k1_recover,
use {
solana_program::{custom_heap_default, custom_panic_default, msg},
solana_secp256k1_recover::secp256k1_recover,
};

fn test_secp256k1_recover() {
Expand Down
3 changes: 2 additions & 1 deletion sdk/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ full = [
"sha3",
"digest",
]
borsh = ["dep:borsh", "solana-program/borsh"]
borsh = ["dep:borsh", "solana-program/borsh", "solana-secp256k1-recover/borsh"]
dev-context-only-utils = [
"qualifier_attr"
]
Expand Down Expand Up @@ -84,6 +84,7 @@ solana-frozen-abi-macro = { workspace = true, optional = true }
solana-program = { workspace = true }
solana-sanitize = { workspace = true }
solana-sdk-macro = { workspace = true }
solana-secp256k1-recover = { workspace = true }
thiserror = { workspace = true }
uriparse = { workspace = true }

Expand Down
2 changes: 1 addition & 1 deletion sdk/program/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ solana-frozen-abi = { workspace = true, optional = true }
solana-frozen-abi-macro = { workspace = true, optional = true }
solana-sanitize = { workspace = true }
solana-sdk-macro = { workspace = true }
solana-secp256k1-recover = { workspace = true }
thiserror = { workspace = true }

# This is currently needed to build on-chain programs reliably.
Expand All @@ -56,7 +57,6 @@ ark-serialize = { workspace = true }
base64 = { workspace = true, features = ["alloc", "std"] }
bitflags = { workspace = true }
curve25519-dalek = { workspace = true }
libsecp256k1 = { workspace = true }
num-bigint = { workspace = true }
rand = { workspace = true }

Expand Down
3 changes: 2 additions & 1 deletion sdk/program/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -519,7 +519,6 @@ pub mod program_utils;
pub mod pubkey;
pub mod rent;
pub mod secp256k1_program;
pub mod secp256k1_recover;
pub mod serde_varint;
pub mod serialize_utils;
pub mod short_vec;
Expand All @@ -537,6 +536,8 @@ pub mod wasm;

#[deprecated(since = "2.1.0", note = "Use `solana-sanitize` crate instead")]
pub use solana_sanitize as sanitize;
#[deprecated(since = "2.1.0", note = "Use `solana-secp256k1-recover` crate instead")]
pub use solana_secp256k1_recover as secp256k1_recover;
#[cfg(target_arch = "wasm32")]
pub use wasm_bindgen::prelude::wasm_bindgen;

Expand Down
6 changes: 5 additions & 1 deletion sdk/program/src/syscalls/definitions.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
#[cfg(target_feature = "static-syscalls")]
pub use solana_define_syscall::sys_hash;
#[deprecated(
since = "2.1.0",
note = "Use `solana_secp256k1_recover::sol_secp256k1_recover` instead"
)]
pub use solana_secp256k1_recover::sol_secp256k1_recover;
use {
crate::{
instruction::{AccountMeta, ProcessedSiblingInstruction},
Expand All @@ -16,7 +21,6 @@ define_syscall!(fn sol_create_program_address(seeds_addr: *const u8, seeds_len:
define_syscall!(fn sol_try_find_program_address(seeds_addr: *const u8, seeds_len: u64, program_id_addr: *const u8, address_bytes_addr: *const u8, bump_seed_addr: *const u8) -> u64);
define_syscall!(fn sol_sha256(vals: *const u8, val_len: u64, hash_result: *mut u8) -> u64);
define_syscall!(fn sol_keccak256(vals: *const u8, val_len: u64, hash_result: *mut u8) -> u64);
define_syscall!(fn sol_secp256k1_recover(hash: *const u8, recovery_id: u64, signature: *const u8, result: *mut u8) -> u64);
define_syscall!(fn sol_blake3(vals: *const u8, val_len: u64, hash_result: *mut u8) -> u64);
define_syscall!(fn sol_memcpy_(dst: *mut u8, src: *const u8, n: u64));
define_syscall!(fn sol_memmove_(dst: *mut u8, src: *const u8, n: u64));
Expand Down
9 changes: 5 additions & 4 deletions sdk/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,10 +52,9 @@ pub use solana_program::{
decode_error, ed25519_program, epoch_rewards, epoch_schedule, fee_calculator, impl_sysvar_get,
incinerator, instruction, keccak, lamports, loader_instruction, loader_upgradeable_instruction,
loader_v4, loader_v4_instruction, message, msg, native_token, nonce, program, program_error,
program_memory, program_option, program_pack, rent, secp256k1_program, secp256k1_recover,
serde_varint, serialize_utils, short_vec, slot_hashes, slot_history, stable_layout, stake,
stake_history, syscalls, system_instruction, system_program, sysvar, unchecked_div_by_const,
vote,
program_memory, program_option, program_pack, rent, secp256k1_program, serde_varint,
serialize_utils, short_vec, slot_hashes, slot_history, stable_layout, stake, stake_history,
syscalls, system_instruction, system_program, sysvar, unchecked_div_by_const, vote,
};
#[cfg(feature = "borsh")]
pub use solana_program::{borsh, borsh0_10, borsh1};
Expand Down Expand Up @@ -155,6 +154,8 @@ pub use solana_sdk_macro::declare_id;
pub use solana_sdk_macro::pubkey;
/// Convenience macro to define multiple static public keys.
pub use solana_sdk_macro::pubkeys;
#[deprecated(since = "2.1.0", note = "Use `solana-secp256k1-recover` crate instead")]
pub use solana_secp256k1_recover as secp256k1_recover;

/// Convenience macro for `AddAssign` with saturating arithmetic.
/// Replace by `std::num::Saturating` once stable
Expand Down

0 comments on commit d809bd9

Please sign in to comment.