diff --git a/Cargo.lock b/Cargo.lock index 5dca433823..48657e08ad 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2193,8 +2193,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c85e1d9ab2eadba7e5040d4e09cbd6d072b76a557ad64e797c2cb9d4da21d7e4" dependencies = [ "cfg-if 1.0.0", + "js-sys", "libc", "wasi", + "wasm-bindgen", ] [[package]] diff --git a/Makefile b/Makefile index a651f2de65..f141d387ed 100644 --- a/Makefile +++ b/Makefile @@ -101,6 +101,10 @@ test-contracts-as: build-contracts-rs build-contracts-as .PHONY: test-contracts test-contracts: test-contracts-rs +.PHONY: check-no-default-features +check-no-default-features: + cd types && $(CARGO) check --all-targets --no-default-features + .PHONY: check-std-features check-std-features: cd types && $(CARGO) check --all-targets --no-default-features --features=std @@ -158,6 +162,7 @@ check-rs: \ lint \ audit \ check-std-features \ + check-no-default-features \ test-rs \ test-rs-no-default-features \ test-contracts-rs diff --git a/hashing/Cargo.toml b/hashing/Cargo.toml index 10b9bbd682..ad8e3e801e 100644 --- a/hashing/Cargo.toml +++ b/hashing/Cargo.toml @@ -12,7 +12,7 @@ license = "Apache-2.0" [dependencies] blake2 = "0.9.0" base16 = "0.2.1" -casper-types = { version = "4.0.1", path = "../types", features = ["datasize", "std"] } +casper-types = { version = "4.0.1", path = "../types", default-features = false, features = ["datasize", "std"] } datasize = "0.2.9" hex = { version = "0.4.2", default-features = false, features = ["serde"] } hex-buffer-serde = "0.3.0" diff --git a/types/CHANGELOG.md b/types/CHANGELOG.md index 08b78b254f..e8ebab7053 100644 --- a/types/CHANGELOG.md +++ b/types/CHANGELOG.md @@ -9,7 +9,11 @@ All notable changes to this project will be documented in this file. The format [comment]: <> (Fixed: any bug fixes) [comment]: <> (Security: in case of vulnerabilities) +## Unreleased +### Added + +- Add "std-fs-io" feature and config checks to compile to wasm ## 4.0.1 @@ -197,4 +201,4 @@ No changes. [1.1.1]: https://github.com/casper-network/casper-node/compare/v1.0.1...v1.1.1 [1.1.0]: https://github.com/casper-network/casper-node/compare/v1.0.1...v1.1.1 [1.0.1]: https://github.com/casper-network/casper-node/compare/v1.0.0...v1.0.1 -[1.0.0]: https://github.com/casper-network/casper-node/releases/tag/v1.0.0 +[1.0.0]: https://github.com/casper-network/casper-node/releases/tag/v1.0.0 \ No newline at end of file diff --git a/types/Cargo.toml b/types/Cargo.toml index 98c2eedcb1..fdd9ff2993 100644 --- a/types/Cargo.toml +++ b/types/Cargo.toml @@ -18,7 +18,7 @@ blake2 = { version = "0.9.0", default-features = false } datasize = { version = "0.2.4", optional = true } derp = { version = "0.0.14", optional = true } ed25519-dalek = { version = "2.0.0", default-features = false, features = ["alloc", "zeroize"] } -getrandom = { version = "0.2.0", features = ["rdrand"], optional = true } +getrandom = { version = "0.2.0", features = ["rdrand", "js"], optional = true } hex = { version = "0.4.2", default-features = false, features = ["alloc"] } hex_fmt = "0.3.0" humantime = { version = "2", optional = true } @@ -39,7 +39,7 @@ serde = { version = "1", default-features = false, features = ["alloc", "derive" serde_bytes = { version = "0.11.5", default-features = false, features = ["alloc"] } serde_json = { version = "1.0.59", default-features = false, features = ["alloc"] } strum = { version = "0.24", features = ["derive"], optional = true } -thiserror = {version = "1", optional = true } +thiserror = { version = "1", optional = true } uint = { version = "0.9.0", default-features = false } untrusted = { version = "0.7.1", optional = true } version-sync = { version = "0.9", optional = true } @@ -66,6 +66,8 @@ thiserror = "1" untrusted = "0.7.1" [features] +default = ["std-fs-io"] +std-fs-io = [] json-schema = ["once_cell", "schemars"] std = ["derp", "getrandom/std", "humantime", "once_cell", "pem", "serde_json/preserve_order", "thiserror", "untrusted"] testing = ["proptest", "proptest-derive", "rand_pcg", "strum"] @@ -74,4 +76,4 @@ gens = ["testing"] [[bench]] name = "bytesrepr_bench" -harness = false +harness = false \ No newline at end of file diff --git a/types/src/cl_value.rs b/types/src/cl_value.rs index 1dc1bee5b7..e39ec46a12 100644 --- a/types/src/cl_value.rs +++ b/types/src/cl_value.rs @@ -1,3 +1,4 @@ +//! CLvalue type // TODO - remove once schemars stops causing warning. #![allow(clippy::field_reassign_with_default)] @@ -17,6 +18,8 @@ use crate::{ }; mod jsonrepr; +#[cfg(not(feature = "std-fs-io"))] +pub use jsonrepr::cl_value_to_json; /// Error while converting a [`CLValue`] into a given type. #[derive(PartialEq, Eq, Clone, Debug, Serialize, Deserialize)] diff --git a/types/src/crypto/asymmetric_key.rs b/types/src/crypto/asymmetric_key.rs index 5c82289f02..90fa27d683 100644 --- a/types/src/crypto/asymmetric_key.rs +++ b/types/src/crypto/asymmetric_key.rs @@ -55,11 +55,12 @@ use crate::{ crypto::Error, CLType, CLTyped, Tagged, }; + #[cfg(any(feature = "std", test))] -use crate::{ - crypto::ErrorExt, - file_utils::{read_file, write_file, write_private_file}, -}; +use crate::crypto::ErrorExt; + +#[cfg(all(feature = "std", feature = "std-fs-io"))] +use crate::file_utils::{read_file, write_file, write_private_file}; #[cfg(any(feature = "testing", test))] pub mod gens; @@ -247,16 +248,33 @@ impl SecretKey { } /// Attempts to write the key bytes to the configured file path. + #[cfg(feature = "std-fs-io")] pub fn to_file>(&self, file: P) -> Result<(), ErrorExt> { write_private_file(file, self.to_pem()?).map_err(ErrorExt::SecretKeySave) } + /// No operation without std-fs-io + #[cfg(not(feature = "std-fs-io"))] + #[allow(unused_variables)] + pub fn to_file>(&self, file: P) -> Result<(), ErrorExt> { + Ok(()) + } + /// Attempts to read the key bytes from configured file path. + #[cfg(feature = "std-fs-io")] pub fn from_file>(file: P) -> Result { let data = read_file(file).map_err(ErrorExt::SecretKeyLoad)?; Self::from_pem(data) } + /// No operation without std-fs-io, use SecretKey::from_pem + #[cfg(not(feature = "std-fs-io"))] + #[allow(unused_variables)] + pub fn from_file>(file: P) -> Result { + let data = vec![]; + Self::from_pem(data) + } + /// DER encodes a key. pub fn to_der(&self) -> Result, ErrorExt> { match self { @@ -528,16 +546,33 @@ impl PublicKey { } /// Attempts to write the key bytes to the configured file path. + #[cfg(feature = "std-fs-io")] pub fn to_file>(&self, file: P) -> Result<(), ErrorExt> { write_file(file, self.to_pem()?).map_err(ErrorExt::PublicKeySave) } + /// No operation without std-fs-io + #[cfg(not(feature = "std-fs-io"))] + #[allow(unused_variables)] + pub fn to_file>(&self, file: P) -> Result<(), ErrorExt> { + Ok(()) + } + /// Attempts to read the key bytes from configured file path. + #[cfg(feature = "std-fs-io")] pub fn from_file>(file: P) -> Result { let data = read_file(file).map_err(ErrorExt::PublicKeyLoad)?; Self::from_pem(data) } + /// No operation without std-fs-io, use SecretKey::from_pem + #[cfg(not(feature = "std-fs-io"))] + #[allow(unused_variables)] + pub fn from_file>(file: P) -> Result { + let data = vec![]; + Self::from_pem(data) + } + /// DER encodes a key. pub fn to_der(&self) -> Result, ErrorExt> { match self { diff --git a/types/src/crypto/error.rs b/types/src/crypto/error.rs index 6750e61f01..e749897cdc 100644 --- a/types/src/crypto/error.rs +++ b/types/src/crypto/error.rs @@ -11,7 +11,7 @@ use pem::PemError; #[cfg(any(feature = "std", test))] use thiserror::Error; -#[cfg(any(feature = "std", test))] +#[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] use crate::file_utils::{ReadFileError, WriteFileError}; /// Cryptographic errors. @@ -75,18 +75,22 @@ pub enum ErrorExt { CryptoError(#[from] Error), /// Error trying to read a secret key. + #[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[error("secret key load failed: {0}")] SecretKeyLoad(ReadFileError), /// Error trying to read a public key. + #[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[error("public key load failed: {0}")] PublicKeyLoad(ReadFileError), /// Error trying to write a secret key. + #[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[error("secret key save failed: {0}")] SecretKeySave(WriteFileError), /// Error trying to write a public key. + #[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[error("public key save failed: {0}")] PublicKeySave(WriteFileError), diff --git a/types/src/file_utils.rs b/types/src/file_utils.rs index 775a7315fa..814063aad6 100644 --- a/types/src/file_utils.rs +++ b/types/src/file_utils.rs @@ -1,15 +1,14 @@ //! Utilities for handling reading from and writing to files. -use std::{ - fs, - io::{self, Write}, - os::unix::fs::OpenOptionsExt, - path::{Path, PathBuf}, -}; - +#[cfg(all(feature = "std", feature = "std-fs-io"))] +use std::{fs, io::Write, os::unix::fs::OpenOptionsExt, path::Path}; +#[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] +use std::{io, path::PathBuf}; +#[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] use thiserror::Error; /// Error reading a file. +#[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[derive(Debug, Error)] #[error("could not read '{0}': {error}", .path.display())] pub struct ReadFileError { @@ -21,6 +20,7 @@ pub struct ReadFileError { } /// Error writing a file +#[cfg(any(all(feature = "std", feature = "std-fs-io"), test))] #[derive(Debug, Error)] #[error("could not write to '{0}': {error}", .path.display())] pub struct WriteFileError { @@ -34,6 +34,7 @@ pub struct WriteFileError { /// Read complete at `path` into memory. /// /// Wraps `fs::read`, but preserves the filename for better error printing. +#[cfg(all(feature = "std", feature = "std-fs-io"))] pub fn read_file>(filename: P) -> Result, ReadFileError> { let path = filename.as_ref(); fs::read(path).map_err(|error| ReadFileError { @@ -45,6 +46,7 @@ pub fn read_file>(filename: P) -> Result, ReadFileError> /// Write data to `path`. /// /// Wraps `fs::write`, but preserves the filename for better error printing. +#[cfg(all(feature = "std", feature = "std-fs-io"))] pub(crate) fn write_file, B: AsRef<[u8]>>( filename: P, data: B, @@ -59,6 +61,7 @@ pub(crate) fn write_file, B: AsRef<[u8]>>( /// Writes data to `path`, ensuring only the owner can read or write it. /// /// Otherwise functions like [`write_file`]. +#[cfg(all(feature = "std", feature = "std-fs-io"))] pub(crate) fn write_private_file, B: AsRef<[u8]>>( filename: P, data: B, diff --git a/types/src/lib.rs b/types/src/lib.rs index c2aeac55d0..7b1227ab37 100644 --- a/types/src/lib.rs +++ b/types/src/lib.rs @@ -28,14 +28,17 @@ mod block_time; pub mod bytesrepr; pub mod checksummed_hex; mod cl_type; +#[cfg(feature = "std-fs-io")] mod cl_value; +#[cfg(not(feature = "std-fs-io"))] +pub mod cl_value; mod contract_wasm; pub mod contracts; pub mod crypto; mod deploy_info; mod era_id; mod execution_result; -#[cfg(any(feature = "std", test))] +#[cfg(any(feature = "std", feature = "std-fs-io", test))] pub mod file_utils; mod gas; #[cfg(any(feature = "testing", feature = "gens", test))] @@ -66,6 +69,8 @@ pub use access_rights::{ pub use api_error::ApiError; pub use block_time::{BlockTime, BLOCKTIME_SERIALIZED_LENGTH}; pub use cl_type::{named_key_type, CLType, CLTyped}; +#[cfg(not(feature = "std-fs-io"))] +pub use cl_value::cl_value_to_json; pub use cl_value::{CLTypeMismatch, CLValue, CLValueError}; pub use contract_wasm::{ContractWasm, ContractWasmHash}; #[doc(inline)] diff --git a/types/src/transfer.rs b/types/src/transfer.rs index 23f51df809..c751736dcb 100644 --- a/types/src/transfer.rs +++ b/types/src/transfer.rs @@ -53,6 +53,12 @@ impl DeployHash { } } +impl AsRef<[u8]> for DeployHash { + fn as_ref(&self) -> &[u8] { + self.0.as_ref() + } +} + #[cfg(feature = "json-schema")] impl JsonSchema for DeployHash { fn schema_name() -> String {