From 317c57628440d9d9e9c2b38543d4ca922edb885d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 13:24:27 +0300 Subject: [PATCH 01/19] add store/restore functions to context --- Cargo.toml | 4 +-- bench/Cargo.toml | 2 +- cavp/Cargo.toml | 2 +- src/digest.rs | 91 ++++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 95 insertions(+), 4 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index d53062249b..a8ed0af1d4 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,7 +6,7 @@ description = "Safe, fast, small crypto using Rust." edition = "2021" keywords = ["crypto", "cryptography", "rand", "ECC", "RSA"] license-file = "LICENSE" -name = "ring" +name = "ringpcx" repository = "https://github.com/briansmith/ring" # Keep in sync with .github/workflows/ci.yml ("MSRV") and see the MSRV note @@ -21,7 +21,7 @@ version = "0.17.8" # build.rs verifies that this equals "ring_core_{major}_{minor}_{patch}_{pre}" # as keeping this in sync with the symbol prefixing is crucial for ensuring # the safety of multiple versions of *ring* being used in a program. -links = "ring_core_0_17_8_" +links = "ringpcx_core_0_17_8_" include = [ "LICENSE", diff --git a/bench/Cargo.toml b/bench/Cargo.toml index c93b09b364..3f9e6977bd 100644 --- a/bench/Cargo.toml +++ b/bench/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dependencies] -ring = { path = "../" } +ring = { path = "../", package = "ringpcx" } [dev-dependencies] criterion = { version = "0.5.1", default-features = false } diff --git a/cavp/Cargo.toml b/cavp/Cargo.toml index effe09c63f..264e373ce3 100644 --- a/cavp/Cargo.toml +++ b/cavp/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dev-dependencies] -ring = { path = ".." } +ring = { path = "..", package = "ringpcx" } [target.'cfg(all(target_arch = "wasm32", target_os = "unknown"))'.dev-dependencies] wasm-bindgen-test = { version = "0.3.37", default-features = false } diff --git a/src/digest.rs b/src/digest.rs index 85a91a71a2..7afbc02265 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -24,6 +24,8 @@ // The goal for this implementation is to drive the overhead as close to zero // as possible. +use alloc::string::{String, ToString}; +use alloc::vec::Vec; use self::{ dynstate::DynState, sha2::{SHA256_BLOCK_LEN, SHA512_BLOCK_LEN}, @@ -33,6 +35,7 @@ use crate::{ cpu, debug, polyfill, }; use core::num::Wrapping; +use crate::digest::sha2::{State32, State64}; mod dynstate; mod sha1; @@ -149,7 +152,95 @@ pub struct Context { num_pending: usize, } +/// Structure to store and restore BlockContext state +#[derive(Clone)] +pub struct ContextState { + pub name: String, + pub data: Vec, +} + +/// Structure to store and restore Context +#[derive(Clone)] +pub struct ContextData { + pub state: ContextState, + pub completed_bytes: u64, + pub algorithm: String, + pub num_pending: usize, + pub pending: Vec, +} impl Context { + /// Retrieves context data from current context states + pub fn serialize(&self) -> ContextData { + let (state_name, state_data) = match self.block.state { + DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), + DynState::As32(as32) => ("as32", as32.iter().map(|w| w.0 as u64).collect::>()), + }; + + let algo = match self.block.algorithm.id { + AlgorithmID::SHA1 => "SHA1", + AlgorithmID::SHA256 => "SHA256", + AlgorithmID::SHA384 => "SHA384", + AlgorithmID::SHA512 => "SHA512", + AlgorithmID::SHA512_256 => "SHA512_256", + }; + + ContextData { + completed_bytes: self.block.completed_bytes, + state: ContextState { + name: state_name.to_string(), + data: state_data, + }, + algorithm: algo.to_string(), + num_pending: self.num_pending, + pending: self.pending.to_vec(), + } + } + + /// Create context from stored context data + pub fn deserialize(data: ContextData) -> Self { + let algo = match data.algorithm.as_str() { + "SHA1" => &SHA1_FOR_LEGACY_USE_ONLY, + "SHA256" => &SHA256, + "SHA384" => &SHA384, + "SHA512" => &SHA512, + "SHA512_256" => &SHA512_256, + _ => &SHA256, + }; + + let mut block = BlockContext::new(algo); + block.completed_bytes = data.completed_bytes; + block.state = match data.state.name.as_str() { + "as64" => { + let state: State64 = data + .state + .data + .iter() + .map(|b| Wrapping(*b)) + .collect::>() + .try_into() + .unwrap(); + DynState::As64(state) + } + _ => { + let state: State32 = data + .state + .data + .iter() + .map(|b| Wrapping(*b as u32)) + .collect::>() + .try_into() + .unwrap(); + DynState::As32(state) + } + }; + + Self { + block, + pending: data.pending.try_into().unwrap(), + num_pending: data.num_pending, + } + } + /// Constructs a new context. pub fn new(algorithm: &'static Algorithm) -> Self { Self { From a036c6dfc36ca3e9529a7f9f82272c9cde34f759 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 13:41:04 +0300 Subject: [PATCH 02/19] fix format and clippy --- src/digest.rs | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/digest.rs b/src/digest.rs index 7afbc02265..1c8d9b31df 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -24,18 +24,18 @@ // The goal for this implementation is to drive the overhead as close to zero // as possible. -use alloc::string::{String, ToString}; -use alloc::vec::Vec; use self::{ dynstate::DynState, sha2::{SHA256_BLOCK_LEN, SHA512_BLOCK_LEN}, }; +use crate::digest::sha2::{State32, State64}; use crate::{ bits::{BitLength, FromByteLen as _}, cpu, debug, polyfill, }; +use alloc::string::{String, ToString}; +use alloc::vec::Vec; use core::num::Wrapping; -use crate::digest::sha2::{State32, State64}; mod dynstate; mod sha1; @@ -155,17 +155,24 @@ pub struct Context { /// Structure to store and restore BlockContext state #[derive(Clone)] pub struct ContextState { + /// Field used to determine state enum name pub name: String, + /// State data pub data: Vec, } /// Structure to store and restore Context #[derive(Clone)] pub struct ContextData { + /// Context state pub state: ContextState, + /// Completed bytes pub completed_bytes: u64, + /// Digest algorithm name = AlgorithmID pub algorithm: String, + /// Number of pending bytes pub num_pending: usize, + /// Pending bytes pub pending: Vec, } impl Context { From fb45fe4d0ff3f5ec9d209a013cab3ababbbc273a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 13:43:52 +0300 Subject: [PATCH 03/19] fix package names --- mk/package.sh | 4 ++-- mk/publish.sh | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/mk/package.sh b/mk/package.sh index 18cda44325..92bbb5e3a0 100644 --- a/mk/package.sh +++ b/mk/package.sh @@ -11,9 +11,9 @@ fi cargo clean --target-dir=target/pregenerate_asm RING_PREGENERATE_ASM=1 CC_AARCH64_PC_WINDOWS_MSVC=clang \ - cargo build -p ring --target-dir=target/pregenerate_asm + cargo build -p ringpcx --target-dir=target/pregenerate_asm if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo package -p ring --allow-dirty +cargo package -p ringpcx --allow-dirty diff --git a/mk/publish.sh b/mk/publish.sh index 194ef1361e..67ae6febd3 100644 --- a/mk/publish.sh +++ b/mk/publish.sh @@ -6,4 +6,4 @@ if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo publish -p ring --allow-dirty +cargo publish -p ringpcx --allow-dirty From 59a2ce47bf883c2209a0ef7867fe7042b0e2c510 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 13:51:39 +0300 Subject: [PATCH 04/19] fix clippy deny --- deny.toml | 4 ++-- src/digest.rs | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/deny.toml b/deny.toml index c26aa860a2..34af48116f 100644 --- a/deny.toml +++ b/deny.toml @@ -6,13 +6,13 @@ version = 2 allow = [ "Apache-2.0", "ISC", - "LicenseRef-ring", + "LicenseRef-ringpcx", "MIT", ] confidence-threshold = 1.0 [[licenses.clarify]] -name = "ring" +name = "ringpcx" expression = "LicenseRef-ring" license-files = [ { path = "LICENSE", hash = 0xbd0eed23 }, diff --git a/src/digest.rs b/src/digest.rs index 1c8d9b31df..0b9211afb8 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -180,7 +180,7 @@ impl Context { pub fn serialize(&self) -> ContextData { let (state_name, state_data) = match self.block.state { DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), - DynState::As32(as32) => ("as32", as32.iter().map(|w| w.0 as u64).collect::>()), + DynState::As32(as32) => ("as32", as32.iter().map(|w| u64::from(w.0)).collect::>()), }; let algo = match self.block.algorithm.id { @@ -233,7 +233,7 @@ impl Context { .state .data .iter() - .map(|b| Wrapping(*b as u32)) + .map(|b| Wrapping(u32::try_from(*b).unwrap())) .collect::>() .try_into() .unwrap(); From db27a4b0748d2030bfeb0817396b72c1ef53d33d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 14:10:17 +0300 Subject: [PATCH 05/19] fix packahe sh --- mk/package.sh | 0 1 file changed, 0 insertions(+), 0 deletions(-) mode change 100644 => 100755 mk/package.sh diff --git a/mk/package.sh b/mk/package.sh old mode 100644 new mode 100755 From aa1f505b1e00cf93c3c5cfabbe34984e32a810a2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Thu, 9 May 2024 14:16:55 +0300 Subject: [PATCH 06/19] fix dirty --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index b625d1f7ab..760ce95a11 100644 --- a/.gitignore +++ b/.gitignore @@ -41,3 +41,4 @@ target/ .idea *.iml CMakeLists.txt +/pregenerated/ From 486b48dc5e8ed7ce48736ee1ebe71b7bd6567ebd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 11:03:04 +0300 Subject: [PATCH 07/19] rollback crate renaming --- Cargo.toml | 4 ++-- bench/Cargo.toml | 2 +- cavp/Cargo.toml | 2 +- deny.toml | 4 ++-- mk/package.sh | 4 ++-- mk/publish.sh | 2 +- 6 files changed, 9 insertions(+), 9 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 3ef6df1f48..0898ddd1af 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,7 +6,7 @@ description = "Safe, fast, small crypto using Rust." edition = "2021" keywords = ["crypto", "cryptography", "rand", "ECC", "RSA"] license-file = "LICENSE" -name = "ringpcx" +name = "ring" repository = "https://github.com/briansmith/ring" # Keep in sync with .github/workflows/ci.yml ("MSRV") and see the MSRV note @@ -21,7 +21,7 @@ version = "0.17.8" # build.rs verifies that this equals "ring_core_{major}_{minor}_{patch}_{pre}" # as keeping this in sync with the symbol prefixing is crucial for ensuring # the safety of multiple versions of *ring* being used in a program. -links = "ringpcx_core_0_17_8_" +links = "ring_core_0_17_8_" include = [ "LICENSE", diff --git a/bench/Cargo.toml b/bench/Cargo.toml index 3f9e6977bd..cead52f6ab 100644 --- a/bench/Cargo.toml +++ b/bench/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dependencies] -ring = { path = "../", package = "ringpcx" } +ring = { path = "../", package = "ring" } [dev-dependencies] criterion = { version = "0.5.1", default-features = false } diff --git a/cavp/Cargo.toml b/cavp/Cargo.toml index 264e373ce3..5c551d38a6 100644 --- a/cavp/Cargo.toml +++ b/cavp/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dev-dependencies] -ring = { path = "..", package = "ringpcx" } +ring = { path = "..", package = "ring" } [target.'cfg(all(target_arch = "wasm32", target_os = "unknown"))'.dev-dependencies] wasm-bindgen-test = { version = "0.3.37", default-features = false } diff --git a/deny.toml b/deny.toml index 34af48116f..c26aa860a2 100644 --- a/deny.toml +++ b/deny.toml @@ -6,13 +6,13 @@ version = 2 allow = [ "Apache-2.0", "ISC", - "LicenseRef-ringpcx", + "LicenseRef-ring", "MIT", ] confidence-threshold = 1.0 [[licenses.clarify]] -name = "ringpcx" +name = "ring" expression = "LicenseRef-ring" license-files = [ { path = "LICENSE", hash = 0xbd0eed23 }, diff --git a/mk/package.sh b/mk/package.sh index 92bbb5e3a0..18cda44325 100755 --- a/mk/package.sh +++ b/mk/package.sh @@ -11,9 +11,9 @@ fi cargo clean --target-dir=target/pregenerate_asm RING_PREGENERATE_ASM=1 CC_AARCH64_PC_WINDOWS_MSVC=clang \ - cargo build -p ringpcx --target-dir=target/pregenerate_asm + cargo build -p ring --target-dir=target/pregenerate_asm if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo package -p ringpcx --allow-dirty +cargo package -p ring --allow-dirty diff --git a/mk/publish.sh b/mk/publish.sh index 67ae6febd3..194ef1361e 100644 --- a/mk/publish.sh +++ b/mk/publish.sh @@ -6,4 +6,4 @@ if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo publish -p ringpcx --allow-dirty +cargo publish -p ring --allow-dirty From 07dead874be5abd37ac83cb0f1841e72f9d21817 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 11:43:17 +0300 Subject: [PATCH 08/19] formatting --- src/digest.rs | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/digest.rs b/src/digest.rs index 7e792678ef..15b441322b 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -186,7 +186,10 @@ impl Context { pub fn serialize(&self) -> ContextData { let (state_name, state_data) = match self.block.state { DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), - DynState::As32(as32) => ("as32", as32.iter().map(|w| u64::from(w.0)).collect::>()), + DynState::As32(as32) => ( + "as32", + as32.iter().map(|w| u64::from(w.0)).collect::>(), + ), }; let algo = match self.block.algorithm.id { @@ -656,6 +659,8 @@ impl OutputLen { #[cfg(test)] mod tests { + mod store_restore_context {} + mod max_input { extern crate alloc; use super::super::super::digest; From b78367bbf62416e52c5ab0248d2f29003e93f764 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 11:55:37 +0300 Subject: [PATCH 09/19] formatting --- src/digest.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/digest.rs b/src/digest.rs index 15b441322b..ecf7ae2582 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -659,7 +659,9 @@ impl OutputLen { #[cfg(test)] mod tests { - mod store_restore_context {} + mod store_restore_context { + + } mod max_input { extern crate alloc; From 964f2088d798a7dc369621560314a56eba62b362 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 14:23:23 +0300 Subject: [PATCH 10/19] Add serde and tests --- Cargo.toml | 6 ++ src/digest.rs | 251 ++++++++++++++++++++++++++++++++------------------ 2 files changed, 166 insertions(+), 91 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 0898ddd1af..109c321e8d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -157,6 +157,7 @@ name = "ring" cfg-if = { version = "1.0.0", default-features = false } getrandom = { version = "0.2.10" } untrusted = { version = "0.9" } +serde = { version = "1.0.203", optional = true, features = ["derive"] } [target.'cfg(any(target_arch = "aarch64", target_arch = "arm", target_arch = "x86",target_arch = "x86_64"))'.dependencies] spin = { version = "0.9.8", default-features = false, features = ["once"] } @@ -176,6 +177,9 @@ libc = { version = "0.2.148", default-features = false } [build-dependencies] cc = { version = "1.0.83", default-features = false } +[dev-dependencies] +serde_json = "1.0.117" + [features] # These features are documented in the top-level module's documentation. default = ["alloc", "dev_urandom_fallback"] @@ -183,6 +187,8 @@ alloc = [] dev_urandom_fallback = [] less-safe-getrandom-custom-or-rdrand = [] less-safe-getrandom-espidf = [] +serde = ["dep:serde", "serialize"] +serialize = [] slow_tests = [] std = ["alloc"] unstable-testing-arm-no-hw = [] diff --git a/src/digest.rs b/src/digest.rs index ecf7ae2582..99ae07e4e0 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -28,16 +28,17 @@ use self::{ dynstate::DynState, sha2::{SHA256_BLOCK_LEN, SHA512_BLOCK_LEN}, }; -use crate::digest::sha2::{State32, State64}; + use crate::{ bits::{BitLength, FromByteLen as _}, cpu, debug, polyfill::{self, slice, sliceutil}, }; -use alloc::string::{String, ToString}; -use alloc::vec::Vec; use core::num::Wrapping; +#[cfg(any(feature = "serde", feature = "serialize"))] +pub use ctx_serialize::ContextData; + mod dynstate; mod sha1; mod sha2; @@ -158,105 +159,125 @@ pub struct Context { num_pending: usize, } -/// Structure to store and restore BlockContext state -#[derive(Clone)] -pub struct ContextState { - /// Field used to determine state enum name - pub name: String, - /// State data - pub data: Vec, -} - -/// Structure to store and restore Context -#[derive(Clone)] -pub struct ContextData { - /// Context state - pub state: ContextState, - /// Completed bytes - pub completed_bytes: u64, - /// Digest algorithm name = AlgorithmID - pub algorithm: String, - /// Number of pending bytes - pub num_pending: usize, - /// Pending bytes - pub pending: Vec, -} -impl Context { - /// Retrieves context data from current context states - pub fn serialize(&self) -> ContextData { - let (state_name, state_data) = match self.block.state { - DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), - DynState::As32(as32) => ( - "as32", - as32.iter().map(|w| u64::from(w.0)).collect::>(), - ), - }; +#[cfg(any(feature = "serde", feature = "serialize"))] +mod ctx_serialize { + use alloc::string::{String, ToString}; + use alloc::vec::Vec; + use core::num::Wrapping; + #[cfg(feature = "serde")] + use serde::{Deserialize, Deserializer, Serialize, Serializer}; + use crate::digest::{AlgorithmID, BlockContext, Context, SHA1_FOR_LEGACY_USE_ONLY, SHA256, SHA384, SHA512, SHA512_256}; + use crate::digest::dynstate::DynState; + use crate::digest::sha2::{State32, State64}; + + /// Structure used to store and restore Context + #[derive(Clone)] + #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))] + pub struct ContextData { + /// Context state name + pub state_name: String, + /// Context state data + pub state_data: Vec, + /// Completed bytes + pub completed_bytes: u64, + /// Digest algorithm name = AlgorithmID + pub algorithm: String, + /// Number of pending bytes + pub num_pending: usize, + /// Pending bytes + pub pending: Vec, + } - let algo = match self.block.algorithm.id { - AlgorithmID::SHA1 => "SHA1", - AlgorithmID::SHA256 => "SHA256", - AlgorithmID::SHA384 => "SHA384", - AlgorithmID::SHA512 => "SHA512", - AlgorithmID::SHA512_256 => "SHA512_256", - }; + #[cfg(feature = "serde")] + impl Serialize for Context { + fn serialize(&self, serializer: S) -> Result where S: Serializer { + self.serialize().serialize(serializer) + } + } - ContextData { - completed_bytes: self.block.completed_bytes, - state: ContextState { - name: state_name.to_string(), - data: state_data, - }, - algorithm: algo.to_string(), - num_pending: self.num_pending, - pending: self.pending.to_vec(), + #[cfg(feature = "serde")] + impl<'de> Deserialize<'de> for Context { + fn deserialize(deserializer: D) -> Result where D: Deserializer<'de> { + let c_data = ContextData::deserialize(deserializer)?; + Ok(Context::deserialize(c_data)) } } - /// Create context from stored context data - pub fn deserialize(data: ContextData) -> Self { - let algo = match data.algorithm.as_str() { - "SHA1" => &SHA1_FOR_LEGACY_USE_ONLY, - "SHA256" => &SHA256, - "SHA384" => &SHA384, - "SHA512" => &SHA512, - "SHA512_256" => &SHA512_256, - _ => &SHA256, - }; + impl Context { + /// Retrieves context data from current context states + pub fn serialize(&self) -> ContextData { + let (state_name, state_data) = match self.block.state { + DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), + DynState::As32(as32) => ( + "as32", + as32.iter().map(|w| u64::from(w.0)).collect::>(), + ), + }; - let mut block = BlockContext::new(algo); - block.completed_bytes = data.completed_bytes; - block.state = match data.state.name.as_str() { - "as64" => { - let state: State64 = data - .state - .data - .iter() - .map(|b| Wrapping(*b)) - .collect::>() - .try_into() - .unwrap(); - DynState::As64(state) - } - _ => { - let state: State32 = data - .state - .data - .iter() - .map(|b| Wrapping(u32::try_from(*b).unwrap())) - .collect::>() - .try_into() - .unwrap(); - DynState::As32(state) + let algo = match self.block.algorithm.id { + AlgorithmID::SHA1 => "SHA1", + AlgorithmID::SHA256 => "SHA256", + AlgorithmID::SHA384 => "SHA384", + AlgorithmID::SHA512 => "SHA512", + AlgorithmID::SHA512_256 => "SHA512_256", + }; + + ContextData { + completed_bytes: self.block.completed_bytes, + state_name: state_name.to_string(), + state_data, + algorithm: algo.to_string(), + num_pending: self.num_pending, + pending: self.pending.to_vec(), } - }; + } - Self { - block, - pending: data.pending.try_into().unwrap(), - num_pending: data.num_pending, + /// Create context from stored context data + pub fn deserialize(data: ContextData) -> Self { + let algo = match data.algorithm.as_str() { + "SHA1" => &SHA1_FOR_LEGACY_USE_ONLY, + "SHA256" => &SHA256, + "SHA384" => &SHA384, + "SHA512" => &SHA512, + "SHA512_256" => &SHA512_256, + _ => &SHA256, + }; + + let mut block = BlockContext::new(algo); + block.completed_bytes = data.completed_bytes; + block.state = match data.state_name.as_str() { + "as64" => { + let state: State64 = data + .state_data + .iter() + .map(|b| Wrapping(*b)) + .collect::>() + .try_into() + .unwrap(); + DynState::As64(state) + } + _ => { + let state: State32 = data + .state_data + .iter() + .map(|b| Wrapping(u32::try_from(*b).unwrap())) + .collect::>() + .try_into() + .unwrap(); + DynState::As32(state) + } + }; + + Self { + block, + pending: data.pending.try_into().unwrap(), + num_pending: data.num_pending, + } } } +} +impl Context { /// Constructs a new context. pub fn new(algorithm: &'static Algorithm) -> Self { Self { @@ -659,8 +680,56 @@ impl OutputLen { #[cfg(test)] mod tests { + #[cfg(any(feature = "serde", feature = "serialize"))] mod store_restore_context { + use crate::digest; + use crate::digest::{Context, Digest, SHA256}; + + fn compute_full_digest(alg: &'static digest::Algorithm, data: &[u8]) -> Digest { + let mut context = Context::new(alg); + context.update(data); + context.finish() + } + + #[cfg(feature = "serde")] + #[test] + fn test_context_serde() { + let algo = &SHA256; + let license = include_str!("../LICENSE"); + let expected_digest = compute_full_digest(algo, license.as_bytes()); + + let len = license.len(); + let mut context = Context::new(algo); + + // Compute and store half file context + context.update(&license.as_bytes()[..len/2]); + let stored_context = serde_json::to_string(&context).expect("Error serializing context"); + + context = serde_json::from_str(&stored_context).expect("Error deserialize context"); + context.update(&license.as_bytes()[len/2..]); + let digest = context.finish(); + assert_eq!(expected_digest.value.0, digest.value.0); + } + + #[cfg(feature = "serialize")] + #[test] + fn test_context_serialization() { + let algo = &SHA256; + let license = include_str!("../LICENSE"); + let expected_digest = compute_full_digest(algo, license.as_bytes()); + + let len = license.len(); + let mut context = Context::new(algo); + // Compute and store half file context + context.update(&license.as_bytes()[..len/2]); + let stored_context = context.serialize(); + + context = Context::deserialize(stored_context); + context.update(&license.as_bytes()[len/2..]); + let digest = context.finish(); + assert_eq!(expected_digest.value.0, digest.value.0); + } } mod max_input { From f9e6f5b1361129fa2376e7cbc00b4f59933623ff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 14:35:03 +0300 Subject: [PATCH 11/19] format & remove redundant package --- bench/Cargo.toml | 2 +- cavp/Cargo.toml | 2 +- src/digest.rs | 30 ++++++++++++++++++++---------- 3 files changed, 22 insertions(+), 12 deletions(-) diff --git a/bench/Cargo.toml b/bench/Cargo.toml index cead52f6ab..c93b09b364 100644 --- a/bench/Cargo.toml +++ b/bench/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dependencies] -ring = { path = "../", package = "ring" } +ring = { path = "../" } [dev-dependencies] criterion = { version = "0.5.1", default-features = false } diff --git a/cavp/Cargo.toml b/cavp/Cargo.toml index 5c551d38a6..effe09c63f 100644 --- a/cavp/Cargo.toml +++ b/cavp/Cargo.toml @@ -5,7 +5,7 @@ publish = false version = "0.1.0" [dev-dependencies] -ring = { path = "..", package = "ring" } +ring = { path = ".." } [target.'cfg(all(target_arch = "wasm32", target_os = "unknown"))'.dev-dependencies] wasm-bindgen-test = { version = "0.3.37", default-features = false } diff --git a/src/digest.rs b/src/digest.rs index 99ae07e4e0..3fcea147c8 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -161,14 +161,17 @@ pub struct Context { #[cfg(any(feature = "serde", feature = "serialize"))] mod ctx_serialize { + use crate::digest::dynstate::DynState; + use crate::digest::sha2::{State32, State64}; + use crate::digest::{ + AlgorithmID, BlockContext, Context, SHA1_FOR_LEGACY_USE_ONLY, SHA256, SHA384, SHA512, + SHA512_256, + }; use alloc::string::{String, ToString}; use alloc::vec::Vec; use core::num::Wrapping; #[cfg(feature = "serde")] use serde::{Deserialize, Deserializer, Serialize, Serializer}; - use crate::digest::{AlgorithmID, BlockContext, Context, SHA1_FOR_LEGACY_USE_ONLY, SHA256, SHA384, SHA512, SHA512_256}; - use crate::digest::dynstate::DynState; - use crate::digest::sha2::{State32, State64}; /// Structure used to store and restore Context #[derive(Clone)] @@ -190,14 +193,20 @@ mod ctx_serialize { #[cfg(feature = "serde")] impl Serialize for Context { - fn serialize(&self, serializer: S) -> Result where S: Serializer { + fn serialize(&self, serializer: S) -> Result + where + S: Serializer, + { self.serialize().serialize(serializer) } } #[cfg(feature = "serde")] impl<'de> Deserialize<'de> for Context { - fn deserialize(deserializer: D) -> Result where D: Deserializer<'de> { + fn deserialize(deserializer: D) -> Result + where + D: Deserializer<'de>, + { let c_data = ContextData::deserialize(deserializer)?; Ok(Context::deserialize(c_data)) } @@ -702,11 +711,12 @@ mod tests { let mut context = Context::new(algo); // Compute and store half file context - context.update(&license.as_bytes()[..len/2]); - let stored_context = serde_json::to_string(&context).expect("Error serializing context"); + context.update(&license.as_bytes()[..len / 2]); + let stored_context = + serde_json::to_string(&context).expect("Error serializing context"); context = serde_json::from_str(&stored_context).expect("Error deserialize context"); - context.update(&license.as_bytes()[len/2..]); + context.update(&license.as_bytes()[len / 2..]); let digest = context.finish(); assert_eq!(expected_digest.value.0, digest.value.0); } @@ -722,11 +732,11 @@ mod tests { let mut context = Context::new(algo); // Compute and store half file context - context.update(&license.as_bytes()[..len/2]); + context.update(&license.as_bytes()[..len / 2]); let stored_context = context.serialize(); context = Context::deserialize(stored_context); - context.update(&license.as_bytes()[len/2..]); + context.update(&license.as_bytes()[len / 2..]); let digest = context.finish(); assert_eq!(expected_digest.value.0, digest.value.0); } From 8869b72a98ff35546dff58f63bbddb43532fdd3f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 15:04:52 +0300 Subject: [PATCH 12/19] remove serialize/deserialize function from context add from/to conversion to/from ContextData --- src/digest.rs | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/src/digest.rs b/src/digest.rs index 3fcea147c8..39c5559743 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -197,7 +197,7 @@ mod ctx_serialize { where S: Serializer, { - self.serialize().serialize(serializer) + ContextData::from(self).serialize(serializer) } } @@ -208,14 +208,13 @@ mod ctx_serialize { D: Deserializer<'de>, { let c_data = ContextData::deserialize(deserializer)?; - Ok(Context::deserialize(c_data)) + Ok(Context::from(c_data)) } } - impl Context { - /// Retrieves context data from current context states - pub fn serialize(&self) -> ContextData { - let (state_name, state_data) = match self.block.state { + impl From<&Context> for ContextData { + fn from(value: &Context) -> Self { + let (state_name, state_data) = match value.block.state { DynState::As64(as64) => ("as64", as64.iter().map(|w| w.0).collect::>()), DynState::As32(as32) => ( "as32", @@ -223,7 +222,7 @@ mod ctx_serialize { ), }; - let algo = match self.block.algorithm.id { + let algo = match value.block.algorithm.id { AlgorithmID::SHA1 => "SHA1", AlgorithmID::SHA256 => "SHA256", AlgorithmID::SHA384 => "SHA384", @@ -232,17 +231,18 @@ mod ctx_serialize { }; ContextData { - completed_bytes: self.block.completed_bytes, + completed_bytes: value.block.completed_bytes, state_name: state_name.to_string(), state_data, algorithm: algo.to_string(), - num_pending: self.num_pending, - pending: self.pending.to_vec(), + num_pending: value.num_pending, + pending: value.pending.to_vec(), } } + } - /// Create context from stored context data - pub fn deserialize(data: ContextData) -> Self { + impl From for Context { + fn from(data: ContextData) -> Self { let algo = match data.algorithm.as_str() { "SHA1" => &SHA1_FOR_LEGACY_USE_ONLY, "SHA256" => &SHA256, @@ -692,7 +692,7 @@ mod tests { #[cfg(any(feature = "serde", feature = "serialize"))] mod store_restore_context { use crate::digest; - use crate::digest::{Context, Digest, SHA256}; + use crate::digest::{Context, ContextData, Digest, SHA256}; fn compute_full_digest(alg: &'static digest::Algorithm, data: &[u8]) -> Digest { let mut context = Context::new(alg); @@ -733,9 +733,9 @@ mod tests { // Compute and store half file context context.update(&license.as_bytes()[..len / 2]); - let stored_context = context.serialize(); + let stored_context = ContextData::from(&context); - context = Context::deserialize(stored_context); + context = Context::from(stored_context); context.update(&license.as_bytes()[len / 2..]); let digest = context.finish(); assert_eq!(expected_digest.value.0, digest.value.0); From bbe4471175d6c3b08f8baf12becfbf4b75d97e7d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 15:21:37 +0300 Subject: [PATCH 13/19] revert gitignore --- .gitignore | 1 - 1 file changed, 1 deletion(-) diff --git a/.gitignore b/.gitignore index 760ce95a11..b625d1f7ab 100644 --- a/.gitignore +++ b/.gitignore @@ -41,4 +41,3 @@ target/ .idea *.iml CMakeLists.txt -/pregenerated/ From ffce7c49f9d1944a8b9a215344f880fdcf510ed3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 15:22:46 +0300 Subject: [PATCH 14/19] revert package.sh --- mk/package.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mk/package.sh b/mk/package.sh index 18cda44325..330b961a3a 100755 --- a/mk/package.sh +++ b/mk/package.sh @@ -16,4 +16,4 @@ if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo package -p ring --allow-dirty +cargo package -p ring --allow-dirty \ No newline at end of file From 032dc6e38707d9dc985d856b5c4a7e09dba53879 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Mon, 27 May 2024 15:23:38 +0300 Subject: [PATCH 15/19] revert package.sh --- mk/package.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mk/package.sh b/mk/package.sh index 330b961a3a..18cda44325 100755 --- a/mk/package.sh +++ b/mk/package.sh @@ -16,4 +16,4 @@ if [[ -n "$(git status --porcelain -- ':(exclude)pregenerated/')" ]]; then echo Repository is dirty. exit 1 fi -cargo package -p ring --allow-dirty \ No newline at end of file +cargo package -p ring --allow-dirty From 678ea0169f9b19a1994a17b8076e00078b4265c3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Tue, 28 May 2024 11:32:05 +0300 Subject: [PATCH 16/19] remove serde --- Cargo.toml | 2 -- src/digest.rs | 47 +---------------------------------------------- 2 files changed, 1 insertion(+), 48 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 109c321e8d..c99e6f3083 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -157,7 +157,6 @@ name = "ring" cfg-if = { version = "1.0.0", default-features = false } getrandom = { version = "0.2.10" } untrusted = { version = "0.9" } -serde = { version = "1.0.203", optional = true, features = ["derive"] } [target.'cfg(any(target_arch = "aarch64", target_arch = "arm", target_arch = "x86",target_arch = "x86_64"))'.dependencies] spin = { version = "0.9.8", default-features = false, features = ["once"] } @@ -187,7 +186,6 @@ alloc = [] dev_urandom_fallback = [] less-safe-getrandom-custom-or-rdrand = [] less-safe-getrandom-espidf = [] -serde = ["dep:serde", "serialize"] serialize = [] slow_tests = [] std = ["alloc"] diff --git a/src/digest.rs b/src/digest.rs index 39c5559743..9450660e61 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -36,7 +36,7 @@ use crate::{ }; use core::num::Wrapping; -#[cfg(any(feature = "serde", feature = "serialize"))] +#[cfg(feature = "serialize")] pub use ctx_serialize::ContextData; mod dynstate; @@ -170,12 +170,9 @@ mod ctx_serialize { use alloc::string::{String, ToString}; use alloc::vec::Vec; use core::num::Wrapping; - #[cfg(feature = "serde")] - use serde::{Deserialize, Deserializer, Serialize, Serializer}; /// Structure used to store and restore Context #[derive(Clone)] - #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))] pub struct ContextData { /// Context state name pub state_name: String, @@ -191,27 +188,6 @@ mod ctx_serialize { pub pending: Vec, } - #[cfg(feature = "serde")] - impl Serialize for Context { - fn serialize(&self, serializer: S) -> Result - where - S: Serializer, - { - ContextData::from(self).serialize(serializer) - } - } - - #[cfg(feature = "serde")] - impl<'de> Deserialize<'de> for Context { - fn deserialize(deserializer: D) -> Result - where - D: Deserializer<'de>, - { - let c_data = ContextData::deserialize(deserializer)?; - Ok(Context::from(c_data)) - } - } - impl From<&Context> for ContextData { fn from(value: &Context) -> Self { let (state_name, state_data) = match value.block.state { @@ -700,27 +676,6 @@ mod tests { context.finish() } - #[cfg(feature = "serde")] - #[test] - fn test_context_serde() { - let algo = &SHA256; - let license = include_str!("../LICENSE"); - let expected_digest = compute_full_digest(algo, license.as_bytes()); - - let len = license.len(); - let mut context = Context::new(algo); - - // Compute and store half file context - context.update(&license.as_bytes()[..len / 2]); - let stored_context = - serde_json::to_string(&context).expect("Error serializing context"); - - context = serde_json::from_str(&stored_context).expect("Error deserialize context"); - context.update(&license.as_bytes()[len / 2..]); - let digest = context.finish(); - assert_eq!(expected_digest.value.0, digest.value.0); - } - #[cfg(feature = "serialize")] #[test] fn test_context_serialization() { From c63ea712976da82072bcbff9d9fcc8b09788e04b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Tue, 28 May 2024 11:34:34 +0300 Subject: [PATCH 17/19] remove serde_json --- Cargo.toml | 3 --- 1 file changed, 3 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index c99e6f3083..d414433fd9 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -176,9 +176,6 @@ libc = { version = "0.2.148", default-features = false } [build-dependencies] cc = { version = "1.0.83", default-features = false } -[dev-dependencies] -serde_json = "1.0.117" - [features] # These features are documented in the top-level module's documentation. default = ["alloc", "dev_urandom_fallback"] From 5482e919cc514258c3c8720a3293d98881a6ea9a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Tue, 28 May 2024 11:35:18 +0300 Subject: [PATCH 18/19] fix tests --- src/digest.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/digest.rs b/src/digest.rs index 9450660e61..e2c6d07a0e 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -665,7 +665,7 @@ impl OutputLen { #[cfg(test)] mod tests { - #[cfg(any(feature = "serde", feature = "serialize"))] + #[cfg(feature = "serialize")] mod store_restore_context { use crate::digest; use crate::digest::{Context, ContextData, Digest, SHA256}; @@ -676,7 +676,6 @@ mod tests { context.finish() } - #[cfg(feature = "serialize")] #[test] fn test_context_serialization() { let algo = &SHA256; From 6b1587afbef70a6ce2fd8fadfda54b72ba93be18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BD=D0=B0=D1=82=D0=BE=D0=BB=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B5=D0=BC=D0=B5=D0=BD=D1=86=D0=BE=D0=B2?= Date: Tue, 28 May 2024 11:35:50 +0300 Subject: [PATCH 19/19] reformat --- src/digest.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/digest.rs b/src/digest.rs index e2c6d07a0e..d583d59e42 100644 --- a/src/digest.rs +++ b/src/digest.rs @@ -159,7 +159,7 @@ pub struct Context { num_pending: usize, } -#[cfg(any(feature = "serde", feature = "serialize"))] +#[cfg(feature = "serialize")] mod ctx_serialize { use crate::digest::dynstate::DynState; use crate::digest::sha2::{State32, State64};