From 880565cb819e8b52883151d3b109713975561078 Mon Sep 17 00:00:00 2001 From: Luke Parker Date: Fri, 26 Jul 2024 19:20:04 -0400 Subject: [PATCH] Rust 1.80 Preserves the fn accessors within the Monero crates so that we can use statics in some cfgs yet not all (in order to provide support for more low-memory devices) with the exception of `H` (which truly should be cached). --- common/std-shims/Cargo.toml | 2 +- common/std-shims/src/sync.rs | 25 +--------- networks/bitcoin/Cargo.toml | 2 +- networks/bitcoin/tests/runner.rs | 11 ++-- networks/monero/Cargo.toml | 2 +- networks/monero/generators/src/lib.rs | 33 ++++++------ networks/monero/io/Cargo.toml | 1 + networks/monero/primitives/Cargo.toml | 2 +- networks/monero/primitives/src/lib.rs | 17 ++++--- .../monero/primitives/src/unreduced_scalar.rs | 26 ++++------ networks/monero/ringct/borromean/Cargo.toml | 2 +- .../monero/ringct/bulletproofs/Cargo.toml | 2 +- networks/monero/ringct/bulletproofs/build.rs | 28 ++++------- .../ringct/bulletproofs/src/batch_verifier.rs | 6 +-- .../src/original/inner_product.rs | 6 +-- .../ringct/bulletproofs/src/original/mod.rs | 10 ++-- .../ringct/bulletproofs/src/plus/mod.rs | 6 +-- .../bulletproofs/src/plus/transcript.rs | 13 ++--- .../src/tests/original/inner_product.rs | 4 +- networks/monero/ringct/clsag/Cargo.toml | 2 +- networks/monero/ringct/mlsag/Cargo.toml | 2 +- networks/monero/ringct/mlsag/src/lib.rs | 2 +- networks/monero/rpc/Cargo.toml | 2 +- networks/monero/rpc/simple-request/Cargo.toml | 2 +- .../monero/rpc/simple-request/tests/tests.rs | 10 ++-- networks/monero/verify-chain/Cargo.toml | 2 +- networks/monero/wallet/Cargo.toml | 2 +- networks/monero/wallet/address/Cargo.toml | 2 +- networks/monero/wallet/polyseed/Cargo.toml | 2 +- networks/monero/wallet/polyseed/src/lib.rs | 50 +++++++++---------- networks/monero/wallet/seed/Cargo.toml | 2 +- networks/monero/wallet/seed/src/lib.rs | 46 ++++++++--------- networks/monero/wallet/seed/src/tests.rs | 2 +- networks/monero/wallet/tests/runner/mod.rs | 6 +-- networks/monero/wallet/util/Cargo.toml | 2 +- orchestration/runtime/Dockerfile | 4 +- orchestration/src/main.rs | 2 +- rust-toolchain.toml | 2 +- 38 files changed, 147 insertions(+), 195 deletions(-) diff --git a/common/std-shims/Cargo.toml b/common/std-shims/Cargo.toml index 4861e00a..534a4216 100644 --- a/common/std-shims/Cargo.toml +++ b/common/std-shims/Cargo.toml @@ -17,7 +17,7 @@ rustdoc-args = ["--cfg", "docsrs"] workspace = true [dependencies] -spin = { version = "0.9", default-features = false, features = ["use_ticket_mutex", "once"] } +spin = { version = "0.9", default-features = false, features = ["use_ticket_mutex", "lazy"] } hashbrown = { version = "0.14", default-features = false, features = ["ahash", "inline-more"] } [features] diff --git a/common/std-shims/src/sync.rs b/common/std-shims/src/sync.rs index 6b8070bc..8193bcfb 100644 --- a/common/std-shims/src/sync.rs +++ b/common/std-shims/src/sync.rs @@ -26,27 +26,6 @@ mod mutex_shim { pub use mutex_shim::{ShimMutex as Mutex, MutexGuard}; #[cfg(feature = "std")] -pub use std::sync::OnceLock; +pub use std::sync::LazyLock; #[cfg(not(feature = "std"))] -mod oncelock_shim { - use spin::Once; - - pub struct OnceLock(Once); - impl OnceLock { - pub const fn new() -> OnceLock { - OnceLock(Once::new()) - } - pub fn get(&self) -> Option<&T> { - self.0.poll() - } - pub fn get_mut(&mut self) -> Option<&mut T> { - self.0.get_mut() - } - - pub fn get_or_init T>(&self, f: F) -> &T { - self.0.call_once(f) - } - } -} -#[cfg(not(feature = "std"))] -pub use oncelock_shim::*; +pub use spin::Lazy as LazyLock; diff --git a/networks/bitcoin/Cargo.toml b/networks/bitcoin/Cargo.toml index 7d6c9412..6fc33da1 100644 --- a/networks/bitcoin/Cargo.toml +++ b/networks/bitcoin/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/bitcoin" authors = ["Luke Parker ", "Vrx "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/bitcoin/tests/runner.rs b/networks/bitcoin/tests/runner.rs index bc471279..4cd6f0cf 100644 --- a/networks/bitcoin/tests/runner.rs +++ b/networks/bitcoin/tests/runner.rs @@ -1,14 +1,11 @@ -use std::sync::OnceLock; +use std::sync::LazyLock; use bitcoin_serai::rpc::Rpc; use tokio::sync::Mutex; -static SEQUENTIAL_CELL: OnceLock> = OnceLock::new(); -#[allow(non_snake_case)] -pub fn SEQUENTIAL() -> &'static Mutex<()> { - SEQUENTIAL_CELL.get_or_init(|| Mutex::new(())) -} +#[allow(dead_code)] +pub(crate) static SEQUENTIAL: LazyLock> = LazyLock::new(|| Mutex::new(())); #[allow(dead_code)] pub(crate) async fn rpc() -> Rpc { @@ -34,7 +31,7 @@ macro_rules! async_sequential { $( #[tokio::test] async fn $name() { - let guard = runner::SEQUENTIAL().lock().await; + let guard = runner::SEQUENTIAL.lock().await; let local = tokio::task::LocalSet::new(); local.run_until(async move { if let Err(err) = tokio::task::spawn_local(async move { $body }).await { diff --git a/networks/monero/Cargo.toml b/networks/monero/Cargo.toml index 73ce850c..c6bb14fd 100644 --- a/networks/monero/Cargo.toml +++ b/networks/monero/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/generators/src/lib.rs b/networks/monero/generators/src/lib.rs index 1fc7c099..bc78a1e5 100644 --- a/networks/monero/generators/src/lib.rs +++ b/networks/monero/generators/src/lib.rs @@ -3,7 +3,7 @@ #![deny(missing_docs)] #![cfg_attr(not(feature = "std"), no_std)] -use std_shims::{sync::OnceLock, vec::Vec}; +use std_shims::{sync::LazyLock, vec::Vec}; use sha3::{Digest, Keccak256}; @@ -21,33 +21,30 @@ fn keccak256(data: &[u8]) -> [u8; 32] { Keccak256::digest(data).into() } -static H_CELL: OnceLock = OnceLock::new(); /// Monero's `H` generator. /// /// Contrary to convention (`G` for values, `H` for randomness), `H` is used by Monero for amounts /// within Pedersen commitments. #[allow(non_snake_case)] -pub fn H() -> EdwardsPoint { - *H_CELL.get_or_init(|| { - decompress_point(keccak256(&ED25519_BASEPOINT_POINT.compress().to_bytes())) - .unwrap() - .mul_by_cofactor() - }) -} +pub static H: LazyLock = LazyLock::new(|| { + decompress_point(keccak256(&ED25519_BASEPOINT_POINT.compress().to_bytes())) + .unwrap() + .mul_by_cofactor() +}); -static H_POW_2_CELL: OnceLock<[EdwardsPoint; 64]> = OnceLock::new(); +static H_POW_2_CELL: LazyLock<[EdwardsPoint; 64]> = LazyLock::new(|| { + let mut res = [*H; 64]; + for i in 1 .. 64 { + res[i] = res[i - 1] + res[i - 1]; + } + res +}); /// Monero's `H` generator, multiplied by 2**i for i in 1 ..= 64. /// /// This table is useful when working with amounts, which are u64s. #[allow(non_snake_case)] pub fn H_pow_2() -> &'static [EdwardsPoint; 64] { - H_POW_2_CELL.get_or_init(|| { - let mut res = [H(); 64]; - for i in 1 .. 64 { - res[i] = res[i - 1] + res[i - 1]; - } - res - }) + &H_POW_2_CELL } /// The maximum amount of commitments provable for within a single range proof. @@ -74,7 +71,7 @@ pub fn bulletproofs_generators(dst: &'static [u8]) -> Generators { // The maximum amount of bits used within a single range proof. const MAX_MN: usize = MAX_COMMITMENTS * COMMITMENT_BITS; - let mut preimage = H().compress().to_bytes().to_vec(); + let mut preimage = H.compress().to_bytes().to_vec(); preimage.extend(dst); let mut res = Generators { G: Vec::with_capacity(MAX_MN), H: Vec::with_capacity(MAX_MN) }; diff --git a/networks/monero/io/Cargo.toml b/networks/monero/io/Cargo.toml index a4270738..887df8b2 100644 --- a/networks/monero/io/Cargo.toml +++ b/networks/monero/io/Cargo.toml @@ -6,6 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/io" authors = ["Luke Parker "] edition = "2021" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/primitives/Cargo.toml b/networks/monero/primitives/Cargo.toml index 2e0bb5cd..1aef394e 100644 --- a/networks/monero/primitives/Cargo.toml +++ b/networks/monero/primitives/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/primitives" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/primitives/src/lib.rs b/networks/monero/primitives/src/lib.rs index 5d8a2336..543f385e 100644 --- a/networks/monero/primitives/src/lib.rs +++ b/networks/monero/primitives/src/lib.rs @@ -5,7 +5,7 @@ use std_shims::{io, vec::Vec}; #[cfg(feature = "std")] -use std_shims::sync::OnceLock; +use std_shims::sync::LazyLock; use zeroize::{Zeroize, ZeroizeOnDrop}; @@ -28,15 +28,15 @@ mod tests; // On std, we cache some variables in statics. #[cfg(feature = "std")] -static INV_EIGHT_CELL: OnceLock = OnceLock::new(); -/// The inverse of 8 over l. +static INV_EIGHT_CELL: LazyLock = LazyLock::new(|| Scalar::from(8u8).invert()); +/// The inverse of 8 over l, the prime factor of the order of Ed25519. #[cfg(feature = "std")] #[allow(non_snake_case)] pub fn INV_EIGHT() -> Scalar { - *INV_EIGHT_CELL.get_or_init(|| Scalar::from(8u8).invert()) + *INV_EIGHT_CELL } // In no-std environments, we prefer the reduced memory use and calculate it ad-hoc. -/// The inverse of 8 over l. +/// The inverse of 8 over l, the prime factor of the order of Ed25519. #[cfg(not(feature = "std"))] #[allow(non_snake_case)] pub fn INV_EIGHT() -> Scalar { @@ -44,12 +44,13 @@ pub fn INV_EIGHT() -> Scalar { } #[cfg(feature = "std")] -static G_PRECOMP_CELL: OnceLock = OnceLock::new(); +static G_PRECOMP_CELL: LazyLock = + LazyLock::new(|| VartimeEdwardsPrecomputation::new([ED25519_BASEPOINT_POINT])); /// A cached (if std) pre-computation of the Ed25519 generator, G. #[cfg(feature = "std")] #[allow(non_snake_case)] pub fn G_PRECOMP() -> &'static VartimeEdwardsPrecomputation { - G_PRECOMP_CELL.get_or_init(|| VartimeEdwardsPrecomputation::new([ED25519_BASEPOINT_POINT])) + &G_PRECOMP_CELL } /// A cached (if std) pre-computation of the Ed25519 generator, G. #[cfg(not(feature = "std"))] @@ -105,7 +106,7 @@ impl Commitment { /// Calculate the Pedersen commitment, as a point, from this transparent structure. pub fn calculate(&self) -> EdwardsPoint { - EdwardsPoint::vartime_double_scalar_mul_basepoint(&Scalar::from(self.amount), &H(), &self.mask) + EdwardsPoint::vartime_double_scalar_mul_basepoint(&Scalar::from(self.amount), &H, &self.mask) } /// Write the Commitment. diff --git a/networks/monero/primitives/src/unreduced_scalar.rs b/networks/monero/primitives/src/unreduced_scalar.rs index 8b75a4f7..90331cd7 100644 --- a/networks/monero/primitives/src/unreduced_scalar.rs +++ b/networks/monero/primitives/src/unreduced_scalar.rs @@ -1,6 +1,6 @@ use core::cmp::Ordering; use std_shims::{ - sync::OnceLock, + sync::LazyLock, io::{self, *}, }; @@ -10,18 +10,14 @@ use curve25519_dalek::scalar::Scalar; use monero_io::*; -static PRECOMPUTED_SCALARS_CELL: OnceLock<[Scalar; 8]> = OnceLock::new(); // Precomputed scalars used to recover an incorrectly reduced scalar. -#[allow(non_snake_case)] -fn PRECOMPUTED_SCALARS() -> [Scalar; 8] { - *PRECOMPUTED_SCALARS_CELL.get_or_init(|| { - let mut precomputed_scalars = [Scalar::ONE; 8]; - for (i, scalar) in precomputed_scalars.iter_mut().enumerate().skip(1) { - *scalar = Scalar::from(u8::try_from((i * 2) + 1).unwrap()); - } - precomputed_scalars - }) -} +static PRECOMPUTED_SCALARS: LazyLock<[Scalar; 8]> = LazyLock::new(|| { + let mut precomputed_scalars = [Scalar::ONE; 8]; + for (i, scalar) in precomputed_scalars.iter_mut().enumerate().skip(1) { + *scalar = Scalar::from(u8::try_from((i * 2) + 1).unwrap()); + } + precomputed_scalars +}); /// An unreduced scalar. /// @@ -127,14 +123,12 @@ impl UnreducedScalar { return Scalar::from_bytes_mod_order(self.0); } - let precomputed_scalars = PRECOMPUTED_SCALARS(); - let mut recovered = Scalar::ZERO; for &numb in self.non_adjacent_form().iter().rev() { recovered += recovered; match numb.cmp(&0) { - Ordering::Greater => recovered += precomputed_scalars[usize::try_from(numb).unwrap() / 2], - Ordering::Less => recovered -= precomputed_scalars[usize::try_from(-numb).unwrap() / 2], + Ordering::Greater => recovered += PRECOMPUTED_SCALARS[usize::try_from(numb).unwrap() / 2], + Ordering::Less => recovered -= PRECOMPUTED_SCALARS[usize::try_from(-numb).unwrap() / 2], Ordering::Equal => (), } } diff --git a/networks/monero/ringct/borromean/Cargo.toml b/networks/monero/ringct/borromean/Cargo.toml index b720c0e2..f5fdd34a 100644 --- a/networks/monero/ringct/borromean/Cargo.toml +++ b/networks/monero/ringct/borromean/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/ringct/borromean" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/ringct/bulletproofs/Cargo.toml b/networks/monero/ringct/bulletproofs/Cargo.toml index a4d395e0..9c807193 100644 --- a/networks/monero/ringct/bulletproofs/Cargo.toml +++ b/networks/monero/ringct/bulletproofs/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/ringct/bulletproofs" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/ringct/bulletproofs/build.rs b/networks/monero/ringct/bulletproofs/build.rs index 6ef1bb54..8eb21eaf 100644 --- a/networks/monero/ringct/bulletproofs/build.rs +++ b/networks/monero/ringct/bulletproofs/build.rs @@ -40,17 +40,14 @@ fn generators(prefix: &'static str, path: &str) { .write_all( format!( " - static GENERATORS_CELL: OnceLock = OnceLock::new(); - pub(crate) fn GENERATORS() -> &'static Generators {{ - GENERATORS_CELL.get_or_init(|| Generators {{ - G: std_shims::vec![ - {G_str} - ], - H: std_shims::vec![ - {H_str} - ], - }}) - }} + pub(crate) static GENERATORS: LazyLock = LazyLock::new(|| Generators {{ + G: std_shims::vec![ + {G_str} + ], + H: std_shims::vec![ + {H_str} + ], + }}); ", ) .as_bytes(), @@ -67,12 +64,9 @@ fn generators(prefix: &'static str, path: &str) { .write_all( format!( r#" - static GENERATORS_CELL: OnceLock = OnceLock::new(); - pub(crate) fn GENERATORS() -> &'static Generators {{ - GENERATORS_CELL.get_or_init(|| {{ - monero_generators::bulletproofs_generators(b"{prefix}") - }}) - }} + pub(crate) static GENERATORS: LazyLock = LazyLock::new(|| {{ + monero_generators::bulletproofs_generators(b"{prefix}") + }}); "#, ) .as_bytes(), diff --git a/networks/monero/ringct/bulletproofs/src/batch_verifier.rs b/networks/monero/ringct/bulletproofs/src/batch_verifier.rs index 1bf9fb8d..3898801c 100644 --- a/networks/monero/ringct/bulletproofs/src/batch_verifier.rs +++ b/networks/monero/ringct/bulletproofs/src/batch_verifier.rs @@ -7,7 +7,7 @@ use curve25519_dalek::{ edwards::EdwardsPoint, }; -use monero_generators::{H, Generators}; +use monero_generators::{H as MONERO_H, Generators}; use crate::{original, plus}; @@ -57,7 +57,7 @@ pub(crate) struct BulletproofsBatchVerifier(pub(crate) InternalBatchVerifier); impl BulletproofsBatchVerifier { #[must_use] pub(crate) fn verify(self) -> bool { - self.0.verify(ED25519_BASEPOINT_POINT, H(), original::GENERATORS()) + self.0.verify(ED25519_BASEPOINT_POINT, *MONERO_H, &original::GENERATORS) } } @@ -68,7 +68,7 @@ impl BulletproofsPlusBatchVerifier { pub(crate) fn verify(self) -> bool { // Bulletproofs+ is written as per the paper, with G for the value and H for the mask // Monero uses H for the value and G for the mask - self.0.verify(H(), ED25519_BASEPOINT_POINT, plus::GENERATORS()) + self.0.verify(*MONERO_H, ED25519_BASEPOINT_POINT, &plus::GENERATORS) } } diff --git a/networks/monero/ringct/bulletproofs/src/original/inner_product.rs b/networks/monero/ringct/bulletproofs/src/original/inner_product.rs index be8f3a83..a72ddf81 100644 --- a/networks/monero/ringct/bulletproofs/src/original/inner_product.rs +++ b/networks/monero/ringct/bulletproofs/src/original/inner_product.rs @@ -96,13 +96,13 @@ impl IpStatement { mut transcript: Scalar, witness: IpWitness, ) -> Result { - let generators = crate::original::GENERATORS(); + let generators = &crate::original::GENERATORS; let g_bold_slice = &generators.G[.. witness.a.len()]; let h_bold_slice = &generators.H[.. witness.a.len()]; let (mut g_bold, mut h_bold, u, mut a, mut b) = { let IpStatement { h_bold_weights, u } = self; - let u = H() * u; + let u = *H * u; // Ensure we have the exact amount of weights if h_bold_weights.len() != g_bold_slice.len() { @@ -218,7 +218,7 @@ impl IpStatement { verifier_weight: Scalar, proof: IpProof, ) -> Result<(), IpError> { - let generators = crate::original::GENERATORS(); + let generators = &crate::original::GENERATORS; let g_bold_slice = &generators.G[.. ip_rows]; let h_bold_slice = &generators.H[.. ip_rows]; diff --git a/networks/monero/ringct/bulletproofs/src/original/mod.rs b/networks/monero/ringct/bulletproofs/src/original/mod.rs index 18fac4d6..f001bc9b 100644 --- a/networks/monero/ringct/bulletproofs/src/original/mod.rs +++ b/networks/monero/ringct/bulletproofs/src/original/mod.rs @@ -1,4 +1,4 @@ -use std_shims::{sync::OnceLock, vec::Vec}; +use std_shims::{sync::LazyLock, vec::Vec}; use rand_core::{RngCore, CryptoRng}; @@ -6,7 +6,7 @@ use zeroize::Zeroize; use curve25519_dalek::{constants::ED25519_BASEPOINT_POINT, Scalar, EdwardsPoint}; -use monero_generators::{H, Generators, MAX_COMMITMENTS, COMMITMENT_BITS}; +use monero_generators::{H as MONERO_H, Generators, MAX_COMMITMENTS, COMMITMENT_BITS}; use monero_primitives::{Commitment, INV_EIGHT, keccak256_to_scalar}; use crate::{core::multiexp, scalar_vector::ScalarVector, BulletproofsBatchVerifier}; @@ -107,7 +107,7 @@ impl<'a> AggregateRangeStatement<'a> { None? }; - let generators = GENERATORS(); + let generators = &GENERATORS; let (mut transcript, _) = self.initial_transcript(); @@ -186,7 +186,7 @@ impl<'a> AggregateRangeStatement<'a> { let tau_1 = Scalar::random(&mut *rng); let T1 = { - let mut T1_terms = [(t1, H()), (tau_1, ED25519_BASEPOINT_POINT)]; + let mut T1_terms = [(t1, *MONERO_H), (tau_1, ED25519_BASEPOINT_POINT)]; for term in &mut T1_terms { term.0 *= INV_EIGHT(); } @@ -196,7 +196,7 @@ impl<'a> AggregateRangeStatement<'a> { }; let tau_2 = Scalar::random(&mut *rng); let T2 = { - let mut T2_terms = [(t2, H()), (tau_2, ED25519_BASEPOINT_POINT)]; + let mut T2_terms = [(t2, *MONERO_H), (tau_2, ED25519_BASEPOINT_POINT)]; for term in &mut T2_terms { term.0 *= INV_EIGHT(); } diff --git a/networks/monero/ringct/bulletproofs/src/plus/mod.rs b/networks/monero/ringct/bulletproofs/src/plus/mod.rs index 92bff236..6b7eb820 100644 --- a/networks/monero/ringct/bulletproofs/src/plus/mod.rs +++ b/networks/monero/ringct/bulletproofs/src/plus/mod.rs @@ -1,6 +1,6 @@ #![allow(non_snake_case)] -use std_shims::sync::OnceLock; +use std_shims::sync::LazyLock; use curve25519_dalek::{constants::ED25519_BASEPOINT_POINT, scalar::Scalar, edwards::EdwardsPoint}; @@ -39,7 +39,7 @@ include!(concat!(env!("OUT_DIR"), "/generators_plus.rs")); impl BpPlusGenerators { #[allow(clippy::new_without_default)] pub(crate) fn new() -> Self { - let gens = GENERATORS(); + let gens = &GENERATORS; BpPlusGenerators { g_bold: &gens.G, h_bold: &gens.H } } @@ -48,7 +48,7 @@ impl BpPlusGenerators { } pub(crate) fn g() -> EdwardsPoint { - H() + *H } pub(crate) fn h() -> EdwardsPoint { diff --git a/networks/monero/ringct/bulletproofs/src/plus/transcript.rs b/networks/monero/ringct/bulletproofs/src/plus/transcript.rs index 3e43a239..e42f1ade 100644 --- a/networks/monero/ringct/bulletproofs/src/plus/transcript.rs +++ b/networks/monero/ringct/bulletproofs/src/plus/transcript.rs @@ -1,4 +1,4 @@ -use std_shims::{sync::OnceLock, vec::Vec}; +use std_shims::{sync::LazyLock, vec::Vec}; use curve25519_dalek::{scalar::Scalar, edwards::EdwardsPoint}; @@ -6,15 +6,12 @@ use monero_generators::hash_to_point; use monero_primitives::{keccak256, keccak256_to_scalar}; // Monero starts BP+ transcripts with the following constant. -static TRANSCRIPT_CELL: OnceLock<[u8; 32]> = OnceLock::new(); -pub(crate) fn TRANSCRIPT() -> [u8; 32] { - // Why this uses a hash_to_point is completely unknown. - *TRANSCRIPT_CELL - .get_or_init(|| hash_to_point(keccak256(b"bulletproof_plus_transcript")).compress().to_bytes()) -} +// Why this uses a hash_to_point is completely unknown. +pub(crate) static TRANSCRIPT: LazyLock<[u8; 32]> = + LazyLock::new(|| hash_to_point(keccak256(b"bulletproof_plus_transcript")).compress().to_bytes()); pub(crate) fn initial_transcript(commitments: core::slice::Iter<'_, EdwardsPoint>) -> Scalar { let commitments_hash = keccak256_to_scalar(commitments.flat_map(|V| V.compress().to_bytes()).collect::>()); - keccak256_to_scalar([TRANSCRIPT().as_ref(), &commitments_hash.to_bytes()].concat()) + keccak256_to_scalar([TRANSCRIPT.as_ref(), &commitments_hash.to_bytes()].concat()) } diff --git a/networks/monero/ringct/bulletproofs/src/tests/original/inner_product.rs b/networks/monero/ringct/bulletproofs/src/tests/original/inner_product.rs index 98aa842f..ce026e65 100644 --- a/networks/monero/ringct/bulletproofs/src/tests/original/inner_product.rs +++ b/networks/monero/ringct/bulletproofs/src/tests/original/inner_product.rs @@ -35,12 +35,12 @@ fn test_zero_inner_product() { #[test] fn test_inner_product() { // P = sum(g_bold * a, h_bold * b, g * u * ) - let generators = GENERATORS(); + let generators = &GENERATORS; let mut verifier = BulletproofsBatchVerifier::default(); verifier.0.g_bold = vec![Scalar::ZERO; 32]; verifier.0.h_bold = vec![Scalar::ZERO; 32]; for i in [1, 2, 4, 8, 16, 32] { - let g = H(); + let g = *H; let mut g_bold = vec![]; let mut h_bold = vec![]; for i in 0 .. i { diff --git a/networks/monero/ringct/clsag/Cargo.toml b/networks/monero/ringct/clsag/Cargo.toml index 27e100ee..801717c7 100644 --- a/networks/monero/ringct/clsag/Cargo.toml +++ b/networks/monero/ringct/clsag/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/ringct/clsag" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/ringct/mlsag/Cargo.toml b/networks/monero/ringct/mlsag/Cargo.toml index 718b2e7c..d666ebfa 100644 --- a/networks/monero/ringct/mlsag/Cargo.toml +++ b/networks/monero/ringct/mlsag/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/ringct/mlsag" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/ringct/mlsag/src/lib.rs b/networks/monero/ringct/mlsag/src/lib.rs index d9f15ead..f5164b88 100644 --- a/networks/monero/ringct/mlsag/src/lib.rs +++ b/networks/monero/ringct/mlsag/src/lib.rs @@ -203,7 +203,7 @@ impl AggregateRingMatrixBuilder { AggregateRingMatrixBuilder { key_ring: vec![], amounts_ring: vec![], - sum_out: commitments.iter().sum::() + (H() * Scalar::from(fee)), + sum_out: commitments.iter().sum::() + (*H * Scalar::from(fee)), } } diff --git a/networks/monero/rpc/Cargo.toml b/networks/monero/rpc/Cargo.toml index e6e65284..0eb92baa 100644 --- a/networks/monero/rpc/Cargo.toml +++ b/networks/monero/rpc/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/rpc" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/rpc/simple-request/Cargo.toml b/networks/monero/rpc/simple-request/Cargo.toml index 71f7cbfb..cba8bdbd 100644 --- a/networks/monero/rpc/simple-request/Cargo.toml +++ b/networks/monero/rpc/simple-request/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/rpc/simple-request" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/rpc/simple-request/tests/tests.rs b/networks/monero/rpc/simple-request/tests/tests.rs index 7b28f9a7..2f7964d6 100644 --- a/networks/monero/rpc/simple-request/tests/tests.rs +++ b/networks/monero/rpc/simple-request/tests/tests.rs @@ -1,4 +1,4 @@ -use std::sync::OnceLock; +use std::sync::LazyLock; use tokio::sync::Mutex; use monero_address::{Network, MoneroAddress}; @@ -8,7 +8,7 @@ use monero_address::{Network, MoneroAddress}; // Accordingly, we test monero-rpc here (implicitly testing the simple-request transport) use monero_simple_request_rpc::*; -static SEQUENTIAL: OnceLock> = OnceLock::new(); +static SEQUENTIAL: LazyLock> = LazyLock::new(|| Mutex::new(())); const ADDRESS: &str = "4B33mFPMq6mKi7Eiyd5XuyKRVMGVZz1Rqb9ZTyGApXW5d1aT7UBDZ89ewmnWFkzJ5wPd2SFbn313vCT8a4E2Qf4KQH4pNey"; @@ -17,7 +17,7 @@ const ADDRESS: &str = async fn test_rpc() { use monero_rpc::Rpc; - let guard = SEQUENTIAL.get_or_init(|| Mutex::new(())).lock().await; + let guard = SEQUENTIAL.lock().await; let rpc = SimpleRequestRpc::new("http://serai:seraidex@127.0.0.1:18081".to_string()).await.unwrap(); @@ -68,7 +68,7 @@ async fn test_rpc() { async fn test_decoy_rpc() { use monero_rpc::{Rpc, DecoyRpc}; - let guard = SEQUENTIAL.get_or_init(|| Mutex::new(())).lock().await; + let guard = SEQUENTIAL.lock().await; let rpc = SimpleRequestRpc::new("http://serai:seraidex@127.0.0.1:18081".to_string()).await.unwrap(); @@ -122,7 +122,7 @@ async fn test_decoy_rpc() { async fn test_zero_out_tx_o_indexes() { use monero_rpc::Rpc; - let guard = SEQUENTIAL.get_or_init(|| Mutex::new(())).lock().await; + let guard = SEQUENTIAL.lock().await; let rpc = SimpleRequestRpc::new("https://node.sethforprivacy.com".to_string()).await.unwrap(); diff --git a/networks/monero/verify-chain/Cargo.toml b/networks/monero/verify-chain/Cargo.toml index 82b2182e..e1aba16e 100644 --- a/networks/monero/verify-chain/Cargo.toml +++ b/networks/monero/verify-chain/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/verify-chain" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" publish = false [package.metadata.docs.rs] diff --git a/networks/monero/wallet/Cargo.toml b/networks/monero/wallet/Cargo.toml index 0a2f9c55..3515c0ed 100644 --- a/networks/monero/wallet/Cargo.toml +++ b/networks/monero/wallet/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/wallet" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/wallet/address/Cargo.toml b/networks/monero/wallet/address/Cargo.toml index f6f90b16..a86ff73c 100644 --- a/networks/monero/wallet/address/Cargo.toml +++ b/networks/monero/wallet/address/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/wallet/address" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/wallet/polyseed/Cargo.toml b/networks/monero/wallet/polyseed/Cargo.toml index 4d17e58b..38861481 100644 --- a/networks/monero/wallet/polyseed/Cargo.toml +++ b/networks/monero/wallet/polyseed/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/wallet/polyseed" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/wallet/polyseed/src/lib.rs b/networks/monero/wallet/polyseed/src/lib.rs index 7cd19ac7..8163d3c4 100644 --- a/networks/monero/wallet/polyseed/src/lib.rs +++ b/networks/monero/wallet/polyseed/src/lib.rs @@ -4,7 +4,7 @@ #![cfg_attr(not(feature = "std"), no_std)] use core::fmt; -use std_shims::{sync::OnceLock, string::String, collections::HashMap}; +use std_shims::{sync::LazyLock, string::String, collections::HashMap}; #[cfg(feature = "std")] use std::time::{SystemTime, UNIX_EPOCH}; @@ -163,30 +163,26 @@ impl WordList { } } -static LANGUAGES_CELL: OnceLock> = OnceLock::new(); -#[allow(non_snake_case)] -fn LANGUAGES() -> &'static HashMap { - LANGUAGES_CELL.get_or_init(|| { - HashMap::from([ - (Language::Czech, WordList::new(include!("./words/cs.rs"), true, false)), - (Language::French, WordList::new(include!("./words/fr.rs"), true, true)), - (Language::Korean, WordList::new(include!("./words/ko.rs"), false, false)), - (Language::English, WordList::new(include!("./words/en.rs"), true, false)), - (Language::Italian, WordList::new(include!("./words/it.rs"), true, false)), - (Language::Spanish, WordList::new(include!("./words/es.rs"), true, true)), - (Language::Japanese, WordList::new(include!("./words/ja.rs"), false, false)), - (Language::Portuguese, WordList::new(include!("./words/pt.rs"), true, false)), - ( - Language::ChineseSimplified, - WordList::new(include!("./words/zh_simplified.rs"), false, false), - ), - ( - Language::ChineseTraditional, - WordList::new(include!("./words/zh_traditional.rs"), false, false), - ), - ]) - }) -} +static LANGUAGES: LazyLock> = LazyLock::new(|| { + HashMap::from([ + (Language::Czech, WordList::new(include!("./words/cs.rs"), true, false)), + (Language::French, WordList::new(include!("./words/fr.rs"), true, true)), + (Language::Korean, WordList::new(include!("./words/ko.rs"), false, false)), + (Language::English, WordList::new(include!("./words/en.rs"), true, false)), + (Language::Italian, WordList::new(include!("./words/it.rs"), true, false)), + (Language::Spanish, WordList::new(include!("./words/es.rs"), true, true)), + (Language::Japanese, WordList::new(include!("./words/ja.rs"), false, false)), + (Language::Portuguese, WordList::new(include!("./words/pt.rs"), true, false)), + ( + Language::ChineseSimplified, + WordList::new(include!("./words/zh_simplified.rs"), false, false), + ), + ( + Language::ChineseTraditional, + WordList::new(include!("./words/zh_traditional.rs"), false, false), + ), + ]) +}); /// A Polyseed. #[derive(Clone, PartialEq, Eq, Zeroize, ZeroizeOnDrop)] @@ -317,7 +313,7 @@ impl Polyseed { let mut poly = [0; POLYSEED_LENGTH]; // Validate words are in the lang word list - let lang_word_list: &WordList = &LANGUAGES()[&lang]; + let lang_word_list: &WordList = &LANGUAGES[&lang]; for (i, word) in seed.split_whitespace().enumerate() { // Find the word's index fn check_if_matches, I: Iterator>( @@ -464,7 +460,7 @@ impl Polyseed { // Output words let mut seed = Zeroizing::new(String::new()); - let words = &LANGUAGES()[&self.language].words; + let words = &LANGUAGES[&self.language].words; for i in 0 .. poly.len() { seed.push_str(words[usize::from(poly[i])]); if i < poly.len() - 1 { diff --git a/networks/monero/wallet/seed/Cargo.toml b/networks/monero/wallet/seed/Cargo.toml index d66f4334..ba28ed0c 100644 --- a/networks/monero/wallet/seed/Cargo.toml +++ b/networks/monero/wallet/seed/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/wallet/seed" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/networks/monero/wallet/seed/src/lib.rs b/networks/monero/wallet/seed/src/lib.rs index 5c8cbe34..1cbdffa8 100644 --- a/networks/monero/wallet/seed/src/lib.rs +++ b/networks/monero/wallet/seed/src/lib.rs @@ -5,7 +5,7 @@ use core::{ops::Deref, fmt}; use std_shims::{ - sync::OnceLock, + sync::LazyLock, vec, vec::Vec, string::{String, ToString}, @@ -102,27 +102,23 @@ impl WordList { } } -static LANGUAGES_CELL: OnceLock> = OnceLock::new(); -#[allow(non_snake_case)] -fn LANGUAGES() -> &'static HashMap { - LANGUAGES_CELL.get_or_init(|| { - HashMap::from([ - (Language::Chinese, WordList::new(include!("./words/zh.rs"), 1)), - (Language::English, WordList::new(include!("./words/en.rs"), 3)), - (Language::Dutch, WordList::new(include!("./words/nl.rs"), 4)), - (Language::French, WordList::new(include!("./words/fr.rs"), 4)), - (Language::Spanish, WordList::new(include!("./words/es.rs"), 4)), - (Language::German, WordList::new(include!("./words/de.rs"), 4)), - (Language::Italian, WordList::new(include!("./words/it.rs"), 4)), - (Language::Portuguese, WordList::new(include!("./words/pt.rs"), 4)), - (Language::Japanese, WordList::new(include!("./words/ja.rs"), 3)), - (Language::Russian, WordList::new(include!("./words/ru.rs"), 4)), - (Language::Esperanto, WordList::new(include!("./words/eo.rs"), 4)), - (Language::Lojban, WordList::new(include!("./words/jbo.rs"), 4)), - (Language::DeprecatedEnglish, WordList::new(include!("./words/ang.rs"), 4)), - ]) - }) -} +static LANGUAGES: LazyLock> = LazyLock::new(|| { + HashMap::from([ + (Language::Chinese, WordList::new(include!("./words/zh.rs"), 1)), + (Language::English, WordList::new(include!("./words/en.rs"), 3)), + (Language::Dutch, WordList::new(include!("./words/nl.rs"), 4)), + (Language::French, WordList::new(include!("./words/fr.rs"), 4)), + (Language::Spanish, WordList::new(include!("./words/es.rs"), 4)), + (Language::German, WordList::new(include!("./words/de.rs"), 4)), + (Language::Italian, WordList::new(include!("./words/it.rs"), 4)), + (Language::Portuguese, WordList::new(include!("./words/pt.rs"), 4)), + (Language::Japanese, WordList::new(include!("./words/ja.rs"), 3)), + (Language::Russian, WordList::new(include!("./words/ru.rs"), 4)), + (Language::Esperanto, WordList::new(include!("./words/eo.rs"), 4)), + (Language::Lojban, WordList::new(include!("./words/jbo.rs"), 4)), + (Language::DeprecatedEnglish, WordList::new(include!("./words/ang.rs"), 4)), + ]) +}); fn checksum_index(words: &[Zeroizing], lang: &WordList) -> usize { let mut trimmed_words = Zeroizing::new(String::new()); @@ -170,7 +166,7 @@ fn key_to_seed(lang: Language, key: Zeroizing) -> Seed { let bytes = Zeroizing::new(key.to_bytes()); // get the language words - let words = &LANGUAGES()[&lang].word_list; + let words = &LANGUAGES[&lang].word_list; let list_len = u64::try_from(words.len()).unwrap(); // To store the found words & add the checksum word later. @@ -204,7 +200,7 @@ fn key_to_seed(lang: Language, key: Zeroizing) -> Seed { // create a checksum word for all languages except old english if lang != Language::DeprecatedEnglish { - let checksum = seed[checksum_index(&seed, &LANGUAGES()[&lang])].clone(); + let checksum = seed[checksum_index(&seed, &LANGUAGES[&lang])].clone(); seed.push(checksum); } @@ -232,7 +228,7 @@ fn seed_to_bytes(lang: Language, words: &str) -> Result, See } // Validate words are in the language word list - let lang_word_list: &WordList = &LANGUAGES()[&lang]; + let lang_word_list: &WordList = &LANGUAGES[&lang]; let matched_indices = (|| { let has_checksum = words.len() == SEED_LENGTH_WITH_CHECKSUM; let mut matched_indices = Zeroizing::new(vec![]); diff --git a/networks/monero/wallet/seed/src/tests.rs b/networks/monero/wallet/seed/src/tests.rs index c477a00d..59d6ea00 100644 --- a/networks/monero/wallet/seed/src/tests.rs +++ b/networks/monero/wallet/seed/src/tests.rs @@ -183,7 +183,7 @@ fn test_original_seed() { for vector in vectors { fn trim_by_lang(word: &str, lang: Language) -> String { if lang != Language::DeprecatedEnglish { - word.chars().take(LANGUAGES()[&lang].unique_prefix_length).collect() + word.chars().take(LANGUAGES[&lang].unique_prefix_length).collect() } else { word.to_string() } diff --git a/networks/monero/wallet/tests/runner/mod.rs b/networks/monero/wallet/tests/runner/mod.rs index 7fe6ac53..4d042b53 100644 --- a/networks/monero/wallet/tests/runner/mod.rs +++ b/networks/monero/wallet/tests/runner/mod.rs @@ -1,5 +1,5 @@ use core::ops::Deref; -use std_shims::sync::OnceLock; +use std_shims::sync::LazyLock; use zeroize::Zeroizing; use rand_core::OsRng; @@ -145,7 +145,7 @@ pub async fn rpc() -> SimpleRequestRpc { rpc } -pub static SEQUENTIAL: OnceLock> = OnceLock::new(); +pub(crate) static SEQUENTIAL: LazyLock> = LazyLock::new(|| Mutex::new(())); #[macro_export] macro_rules! async_sequential { @@ -153,7 +153,7 @@ macro_rules! async_sequential { $( #[tokio::test] async fn $name() { - let guard = runner::SEQUENTIAL.get_or_init(|| tokio::sync::Mutex::new(())).lock().await; + let guard = runner::SEQUENTIAL.lock().await; let local = tokio::task::LocalSet::new(); local.run_until(async move { if let Err(err) = tokio::task::spawn_local(async move { $body }).await { diff --git a/networks/monero/wallet/util/Cargo.toml b/networks/monero/wallet/util/Cargo.toml index a72f09bf..39dfe3a6 100644 --- a/networks/monero/wallet/util/Cargo.toml +++ b/networks/monero/wallet/util/Cargo.toml @@ -6,7 +6,7 @@ license = "MIT" repository = "https://github.com/serai-dex/serai/tree/develop/networks/monero/wallet/util" authors = ["Luke Parker "] edition = "2021" -rust-version = "1.79" +rust-version = "1.80" [package.metadata.docs.rs] all-features = true diff --git a/orchestration/runtime/Dockerfile b/orchestration/runtime/Dockerfile index f3120758..b09c5949 100644 --- a/orchestration/runtime/Dockerfile +++ b/orchestration/runtime/Dockerfile @@ -1,5 +1,5 @@ -# rust:1.79.0-slim-bookworm as of June 14th, 2024 (GMT) -FROM --platform=linux/amd64 rust@sha256:fa189cd885739dd17fc6bb4e132687fce43f2bf42983c0ac39b60e4943201e9c as deterministic +# rust:1.80.0-slim-bookworm as of July 27th, 2024 (GMT) +FROM --platform=linux/amd64 rust@sha256:37e6f90f98b3afd15c2526d7abb257a1f4cb7d49808fe3729d9d62020b07b544 as deterministic # Move to a Debian package snapshot RUN rm -rf /etc/apt/sources.list.d/debian.sources && \ diff --git a/orchestration/src/main.rs b/orchestration/src/main.rs index 3185c107..4655be01 100644 --- a/orchestration/src/main.rs +++ b/orchestration/src/main.rs @@ -146,7 +146,7 @@ fn build_serai_service(prelude: &str, release: bool, features: &str, package: &s format!( r#" -FROM rust:1.79-slim-bookworm as builder +FROM rust:1.80-slim-bookworm as builder COPY --from=mimalloc-debian libmimalloc.so /usr/lib RUN echo "/usr/lib/libmimalloc.so" >> /etc/ld.so.preload diff --git a/rust-toolchain.toml b/rust-toolchain.toml index fe982784..73cb338c 100644 --- a/rust-toolchain.toml +++ b/rust-toolchain.toml @@ -1,5 +1,5 @@ [toolchain] -channel = "1.79" +channel = "1.80" targets = ["wasm32-unknown-unknown"] profile = "minimal" components = ["rust-src", "rustfmt", "clippy"]