+134
| // This file is part of ICU4X. For terms of use, please see the file | ||
| // called LICENSE at the top level of the ICU4X source tree | ||
| // (online at: https://github.com/unicode-org/icu4x/blob/main/LICENSE ). | ||
| use crate::{ | ||
| map::ZeroMapKV, | ||
| ule::{AsULE, VarULE}, | ||
| vecs::VarZeroVecFormat, | ||
| VarZeroVec, ZeroMap, ZeroSlice, ZeroVec, | ||
| }; | ||
| use alloc::{borrow::Cow, format}; | ||
| use schemars::JsonSchema; | ||
| impl<T: VarULE + JsonSchema + ?Sized, F: VarZeroVecFormat> JsonSchema for VarZeroVec<'_, T, F> { | ||
| fn inline_schema() -> bool { | ||
| true | ||
| } | ||
| fn schema_name() -> Cow<'static, str> { | ||
| format!("VarZeroVec<{}>", T::schema_name()).into() | ||
| } | ||
| fn json_schema(generator: &mut schemars::SchemaGenerator) -> schemars::Schema { | ||
| schemars::json_schema!({ | ||
| "type": "array", | ||
| "items": generator.subschema_for::<T>(), | ||
| }) | ||
| } | ||
| } | ||
| impl<'a, T: AsULE + JsonSchema> JsonSchema for ZeroVec<'a, T> { | ||
| fn inline_schema() -> bool { | ||
| true | ||
| } | ||
| fn schema_name() -> Cow<'static, str> { | ||
| alloc::format!("ZeroVec<{}>", T::schema_name()).into() | ||
| } | ||
| fn json_schema(generator: &mut schemars::SchemaGenerator) -> schemars::Schema { | ||
| schemars::json_schema!({ | ||
| "type": "array", | ||
| "items": generator.subschema_for::<T>(), | ||
| }) | ||
| } | ||
| } | ||
| impl<T: AsULE + JsonSchema> JsonSchema for ZeroSlice<T> { | ||
| fn inline_schema() -> bool { | ||
| true | ||
| } | ||
| fn schema_name() -> Cow<'static, str> { | ||
| format!("ZeroSlice<{}>", T::schema_name()).into() | ||
| } | ||
| fn json_schema(generator: &mut schemars::SchemaGenerator) -> schemars::Schema { | ||
| schemars::json_schema!({ | ||
| "type": "array", | ||
| "items": generator.subschema_for::<T>(), | ||
| }) | ||
| } | ||
| } | ||
| impl<'a, K, V> JsonSchema for ZeroMap<'a, K, V> | ||
| where | ||
| K: ZeroMapKV<'a> + ?Sized + JsonSchema, | ||
| V: ZeroMapKV<'a> + ?Sized + JsonSchema, | ||
| { | ||
| fn inline_schema() -> bool { | ||
| true | ||
| } | ||
| fn schema_name() -> Cow<'static, str> { | ||
| format!("ZeroMap<{}, {}>", K::schema_name(), V::schema_name()).into() | ||
| } | ||
| fn json_schema(generator: &mut schemars::SchemaGenerator) -> schemars::Schema { | ||
| // forward to the BTreeMap impl, as the impl is quite complex | ||
| // | ||
| // as the impl for the BTreeMap requires its arguments to be Sized, i cannot forward | ||
| // K and V directly, but since schemars simply forwards &T impls to T, this is fine | ||
| <alloc::collections::BTreeMap<&K, &V> as JsonSchema>::json_schema(generator) | ||
| } | ||
| } | ||
| #[cfg(test)] | ||
| mod tests { | ||
| use crate::{VarZeroVec, ZeroMap, ZeroSlice, ZeroVec}; | ||
| #[test] | ||
| #[cfg(feature = "schemars")] | ||
| fn schema_zerovec_u32() { | ||
| let generator = schemars::SchemaGenerator::default(); | ||
| let schema = generator.into_root_schema_for::<ZeroVec<u32>>(); | ||
| insta::assert_json_snapshot!(schema); | ||
| } | ||
| #[test] | ||
| #[cfg(feature = "schemars")] | ||
| fn schema_zerovec_char() { | ||
| let generator = schemars::SchemaGenerator::default(); | ||
| let schema = generator.into_root_schema_for::<ZeroVec<char>>(); | ||
| insta::assert_json_snapshot!(schema); | ||
| } | ||
| #[test] | ||
| #[cfg(feature = "schemars")] | ||
| fn schema_varzerovec_str() { | ||
| let generator = schemars::SchemaGenerator::default(); | ||
| let schema = generator.into_root_schema_for::<VarZeroVec<str>>(); | ||
| insta::assert_json_snapshot!(schema); | ||
| } | ||
| #[test] | ||
| #[cfg(feature = "schemars")] | ||
| fn schema_varzerovec_zeroslice() { | ||
| let generator = schemars::SchemaGenerator::default(); | ||
| let schema = generator.into_root_schema_for::<VarZeroVec<ZeroSlice<u32>>>(); | ||
| insta::assert_json_snapshot!(schema); | ||
| } | ||
| #[test] | ||
| fn schema_zeromap_u32_str() { | ||
| let generator = schemars::SchemaGenerator::default(); | ||
| let schema = generator.into_root_schema_for::<ZeroMap<u32, str>>(); | ||
| insta::assert_json_snapshot!(schema); | ||
| } | ||
| } |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
| { | ||
| "git": { | ||
| "sha1": "29dfe2790b6cfdab94ca6a6b69f58ce54802dbf7", | ||
| "dirty": true | ||
| "sha1": "c9fac4e625ccb2c6a7aa35079fff9709db4385ac" | ||
| }, | ||
| "path_in_vcs": "utils/zerovec" | ||
| } |
@@ -356,11 +356,11 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// This type lets us use a u32-index-format VarZeroVec with the ZeroMap. | ||
| /// This type lets us use a u32-index-format `VarZeroVec` with the `ZeroMap`. | ||
| /// | ||
| /// Eventually we will have a FormatSelector type that lets us do `ZeroMap<FormatSelector<K, Index32>, V>` | ||
| /// (https://github.com/unicode-org/icu4x/issues/2312) | ||
| /// Eventually we will have a `FormatSelector` type that lets us do `ZeroMap<FormatSelector<K, Index32>, V>` | ||
| /// (<https://github.com/unicode-org/icu4x/issues/2312>) | ||
| /// | ||
| /// , isn't actually important; it's just more convenient to use make_varule to get the | ||
| /// , isn't actually important; it's just more convenient to use `make_varule` to get the | ||
| /// full suite of traits instead of `#[derive(VarULE)]`. (With `#[derive(VarULE)]` we would have to manually | ||
| /// define a Serialize implementation, and that would be gnarly) | ||
| /// https://github.com/unicode-org/icu4x/issues/2310 tracks being able to do this with derive(ULE) | ||
| /// <https://github.com/unicode-org/icu4x/issues/2310> tracks being able to do this with derive(ULE) | ||
| #[zerovec::make_varule(Index32Str)] | ||
@@ -367,0 +367,0 @@ #[zerovec::skip_derive(ZeroMapKV)] |
+948
-19
@@ -6,6 +6,212 @@ # This file is automatically @generated by Cargo. | ||
| [[package]] | ||
| name = "aho-corasick" | ||
| version = "1.1.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ddd31a130427c27518df266943a5308ed92d4b226cc639f5a8f1002816174301" | ||
| dependencies = [ | ||
| "memchr", | ||
| ] | ||
| [[package]] | ||
| name = "anes" | ||
| version = "0.1.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "4b46cbb362ab8752921c97e041f5e366ee6297bd428a31275b9fcf1e380f7299" | ||
| [[package]] | ||
| name = "anstyle" | ||
| version = "1.0.14" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "940b3a0ca603d1eade50a4846a2afffd5ef57a9feac2c0e2ec2e14f9ead76000" | ||
| [[package]] | ||
| name = "autocfg" | ||
| version = "1.5.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8" | ||
| [[package]] | ||
| name = "bincode" | ||
| version = "1.3.3" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b1f45e9417d87227c7a56d22e471c6206462cba514c7590c09aff4cf6d1ddcad" | ||
| dependencies = [ | ||
| "serde", | ||
| ] | ||
| [[package]] | ||
| name = "bitflags" | ||
| version = "2.11.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "843867be96c8daad0d758b57df9392b6d8d271134fce549de6ce169ff98a92af" | ||
| [[package]] | ||
| name = "bumpalo" | ||
| version = "3.20.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "5d20789868f4b01b2f2caec9f5c4e0213b41e3e5702a50157d699ae31ced2fcb" | ||
| [[package]] | ||
| name = "byteorder" | ||
| version = "1.5.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" | ||
| [[package]] | ||
| name = "cast" | ||
| version = "0.3.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "37b2a672a2cb129a2e41c10b1224bb368f9f37a2b16b612598138befd7b37eb5" | ||
| [[package]] | ||
| name = "cfg-if" | ||
| version = "1.0.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "9330f8b2ff13f34540b44e946ef35111825727b38d33286ef986142615121801" | ||
| [[package]] | ||
| name = "ciborium" | ||
| version = "0.2.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "42e69ffd6f0917f5c029256a24d0161db17cea3997d185db0d35926308770f0e" | ||
| dependencies = [ | ||
| "ciborium-io", | ||
| "ciborium-ll", | ||
| "serde", | ||
| ] | ||
| [[package]] | ||
| name = "ciborium-io" | ||
| version = "0.2.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "05afea1e0a06c9be33d539b876f1ce3692f4afea2cb41f740e7743225ed1c757" | ||
| [[package]] | ||
| name = "ciborium-ll" | ||
| version = "0.2.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "57663b653d948a338bfb3eeba9bb2fd5fcfaecb9e199e87e1eda4d9e8b240fd9" | ||
| dependencies = [ | ||
| "ciborium-io", | ||
| "half", | ||
| ] | ||
| [[package]] | ||
| name = "clap" | ||
| version = "4.4.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "1e578d6ec4194633722ccf9544794b71b1385c3c027efe0c55db226fc880865c" | ||
| dependencies = [ | ||
| "clap_builder", | ||
| ] | ||
| [[package]] | ||
| name = "clap_builder" | ||
| version = "4.4.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "4df4df40ec50c46000231c914968278b1eb05098cf8f1b3a518a95030e71d1c7" | ||
| dependencies = [ | ||
| "anstyle", | ||
| "clap_lex", | ||
| ] | ||
| [[package]] | ||
| name = "clap_lex" | ||
| version = "0.6.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "702fc72eb24e5a1e48ce58027a675bc24edd52096d5397d4aea7c6dd9eca0bd1" | ||
| [[package]] | ||
| name = "cobs" | ||
| version = "0.3.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "0fa961b519f0b462e3a3b4a34b64d119eeaca1d59af726fe450bbba07a9fc0a1" | ||
| dependencies = [ | ||
| "thiserror", | ||
| ] | ||
| [[package]] | ||
| name = "console" | ||
| version = "0.15.11" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "054ccb5b10f9f2cbf51eb355ca1d05c2d279ce1804688d0db74b4733a5aeafd8" | ||
| dependencies = [ | ||
| "encode_unicode", | ||
| "libc", | ||
| "once_cell", | ||
| "windows-sys 0.59.0", | ||
| ] | ||
| [[package]] | ||
| name = "criterion" | ||
| version = "0.5.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "f2b12d017a929603d80db1831cd3a24082f8137ce19c69e6447f54f5fc8d692f" | ||
| dependencies = [ | ||
| "anes", | ||
| "cast", | ||
| "ciborium", | ||
| "clap", | ||
| "criterion-plot", | ||
| "is-terminal", | ||
| "itertools", | ||
| "num-traits", | ||
| "once_cell", | ||
| "oorandom", | ||
| "plotters", | ||
| "rayon", | ||
| "regex", | ||
| "serde", | ||
| "serde_derive", | ||
| "serde_json", | ||
| "tinytemplate", | ||
| "walkdir", | ||
| ] | ||
| [[package]] | ||
| name = "criterion-plot" | ||
| version = "0.5.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6b50826342786a51a89e2da3a28f1c32b06e387201bc2d19791f622c673706b1" | ||
| dependencies = [ | ||
| "cast", | ||
| "itertools", | ||
| ] | ||
| [[package]] | ||
| name = "crossbeam-deque" | ||
| version = "0.8.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "9dd111b7b7f7d55b72c0a6ae361660ee5853c9af73f70c3c2ef6858b950e2e51" | ||
| dependencies = [ | ||
| "crossbeam-epoch", | ||
| "crossbeam-utils", | ||
| ] | ||
| [[package]] | ||
| name = "crossbeam-epoch" | ||
| version = "0.9.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "5b82ac4a3c2ca9c3460964f020e1402edd5753411d7737aa39c3714ad1b5420e" | ||
| dependencies = [ | ||
| "crossbeam-utils", | ||
| ] | ||
| [[package]] | ||
| name = "crossbeam-utils" | ||
| version = "0.8.21" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "d0a5c400df2834b80a4c3327b3aad3a4c4cd4de0629063962b03235697506a28" | ||
| [[package]] | ||
| name = "crunchy" | ||
| version = "0.2.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "460fbee9c2c2f33933d720630a6a0bac33ba7053db5344fac858d4b8952d77d5" | ||
| [[package]] | ||
| name = "databake" | ||
| version = "0.2.0" | ||
| version = "0.2.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ff6ee9e2d2afb173bcdeee45934c89ec341ab26f91c9933774fc15c2b58f83ef" | ||
| checksum = "74d4b1db5ca40636726f1f73daff0d626accbd49bcd8136fcade87d7cf1e6bbb" | ||
| dependencies = [ | ||
@@ -19,5 +225,5 @@ "databake-derive", | ||
| name = "databake-derive" | ||
| version = "0.2.0" | ||
| version = "0.2.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6834770958c7b84223607e49758ec0dde273c4df915e734aad50f62968a4c134" | ||
| checksum = "72b537745234cbf0e296a3bd836d70a614dff4cb522b14e2680ef006bb1ed5ff" | ||
| dependencies = [ | ||
@@ -31,6 +237,238 @@ "proc-macro2", | ||
| [[package]] | ||
| name = "dyn-clone" | ||
| version = "1.0.20" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "d0881ea181b1df73ff77ffaaf9c7544ecc11e82fba9b5f27b262a3c73a332555" | ||
| [[package]] | ||
| name = "either" | ||
| version = "1.15.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "48c757948c5ede0e46177b7add2e67155f70e33c07fea8284df6576da70b3719" | ||
| [[package]] | ||
| name = "embedded-io" | ||
| version = "0.4.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ef1a6892d9eef45c8fa6b9e0086428a2cca8491aca8f787c534a3d6d0bcb3ced" | ||
| [[package]] | ||
| name = "embedded-io" | ||
| version = "0.6.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "edd0f118536f44f5ccd48bcb8b111bdc3de888b58c74639dfb034a357d0f206d" | ||
| [[package]] | ||
| name = "encode_unicode" | ||
| version = "1.0.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "34aa73646ffb006b8f5147f3dc182bd4bcb190227ce861fc4a4844bf8e3cb2c0" | ||
| [[package]] | ||
| name = "errno" | ||
| version = "0.3.14" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "39cab71617ae0d63f51a36d69f866391735b51691dbda63cf6f96d042b63efeb" | ||
| dependencies = [ | ||
| "libc", | ||
| "windows-sys 0.61.2", | ||
| ] | ||
| [[package]] | ||
| name = "fastrand" | ||
| version = "2.3.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "37909eebbb50d72f9059c3b6d82c0463f2ff062c9e95845c43a6c9c0355411be" | ||
| [[package]] | ||
| name = "getrandom" | ||
| version = "0.3.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "899def5c37c4fd7b2664648c28120ecec138e4d395b459e5ca34f9cce2dd77fd" | ||
| dependencies = [ | ||
| "cfg-if", | ||
| "js-sys", | ||
| "libc", | ||
| "r-efi", | ||
| "wasip2", | ||
| "wasm-bindgen", | ||
| ] | ||
| [[package]] | ||
| name = "half" | ||
| version = "2.4.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6dd08c532ae367adf81c312a4580bc67f1d0fe8bc9c460520283f4c0ff277888" | ||
| dependencies = [ | ||
| "cfg-if", | ||
| "crunchy", | ||
| ] | ||
| [[package]] | ||
| name = "hermit-abi" | ||
| version = "0.5.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "fc0fef456e4baa96da950455cd02c081ca953b141298e41db3fc7e36b1da849c" | ||
| [[package]] | ||
| name = "iai" | ||
| version = "0.1.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "71a816c97c42258aa5834d07590b718b4c9a598944cd39a52dc25b351185d678" | ||
| [[package]] | ||
| name = "insta" | ||
| version = "1.46.3" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "e82db8c87c7f1ccecb34ce0c24399b8a73081427f3c7c50a5d597925356115e4" | ||
| dependencies = [ | ||
| "console", | ||
| "once_cell", | ||
| "serde", | ||
| "similar", | ||
| "tempfile", | ||
| ] | ||
| [[package]] | ||
| name = "is-terminal" | ||
| version = "0.4.17" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "3640c1c38b8e4e43584d8df18be5fc6b0aa314ce6ebf51b53313d4306cca8e46" | ||
| dependencies = [ | ||
| "hermit-abi", | ||
| "libc", | ||
| "windows-sys 0.61.2", | ||
| ] | ||
| [[package]] | ||
| name = "itertools" | ||
| version = "0.10.5" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" | ||
| dependencies = [ | ||
| "either", | ||
| ] | ||
| [[package]] | ||
| name = "itoa" | ||
| version = "1.0.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "8f42a60cbdf9a97f5d2305f08a87dc4e09308d1276d28c869c684d7777685682" | ||
| [[package]] | ||
| name = "js-sys" | ||
| version = "0.3.91" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b49715b7073f385ba4bc528e5747d02e66cb39c6146efb66b781f131f0fb399c" | ||
| dependencies = [ | ||
| "once_cell", | ||
| "wasm-bindgen", | ||
| ] | ||
| [[package]] | ||
| name = "libc" | ||
| version = "0.2.183" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b5b646652bf6661599e1da8901b3b9522896f01e736bad5f723fe7a3a27f899d" | ||
| [[package]] | ||
| name = "libm" | ||
| version = "0.2.16" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b6d2cec3eae94f9f509c767b45932f1ada8350c4bdb85af2fcab4a3c14807981" | ||
| [[package]] | ||
| name = "linux-raw-sys" | ||
| version = "0.12.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "32a66949e030da00e8c7d4434b251670a91556f4144941d37452769c25d58a53" | ||
| [[package]] | ||
| name = "memchr" | ||
| version = "2.8.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "f8ca58f447f06ed17d5fc4043ce1b10dd205e060fb3ce5b979b8ed8e59ff3f79" | ||
| [[package]] | ||
| name = "num-traits" | ||
| version = "0.2.19" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841" | ||
| dependencies = [ | ||
| "autocfg", | ||
| "libm", | ||
| ] | ||
| [[package]] | ||
| name = "once_cell" | ||
| version = "1.21.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "9f7c3e4beb33f85d45ae3e3a1792185706c8e16d043238c593331cc7cd313b50" | ||
| [[package]] | ||
| name = "oorandom" | ||
| version = "11.1.5" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "d6790f58c7ff633d8771f42965289203411a5e5c68388703c06e14f24770b41e" | ||
| [[package]] | ||
| name = "paste" | ||
| version = "1.0.15" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a" | ||
| [[package]] | ||
| name = "plotters" | ||
| version = "0.3.7" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "5aeb6f403d7a4911efb1e33402027fc44f29b5bf6def3effcc22d7bb75f2b747" | ||
| dependencies = [ | ||
| "num-traits", | ||
| "plotters-backend", | ||
| "plotters-svg", | ||
| "wasm-bindgen", | ||
| "web-sys", | ||
| ] | ||
| [[package]] | ||
| name = "plotters-backend" | ||
| version = "0.3.7" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "df42e13c12958a16b3f7f4386b9ab1f3e7933914ecea48da7139435263a4172a" | ||
| [[package]] | ||
| name = "plotters-svg" | ||
| version = "0.3.7" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "51bae2ac328883f7acdfea3d66a7c35751187f870bc81f94563733a154d7a670" | ||
| dependencies = [ | ||
| "plotters-backend", | ||
| ] | ||
| [[package]] | ||
| name = "postcard" | ||
| version = "1.1.3" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6764c3b5dd454e283a30e6dfe78e9b31096d9e32036b5d1eaac7a6119ccb9a24" | ||
| dependencies = [ | ||
| "cobs", | ||
| "embedded-io 0.4.0", | ||
| "embedded-io 0.6.1", | ||
| "serde", | ||
| ] | ||
| [[package]] | ||
| name = "ppv-lite86" | ||
| version = "0.2.21" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9" | ||
| dependencies = [ | ||
| "zerocopy", | ||
| ] | ||
| [[package]] | ||
| name = "proc-macro2" | ||
| version = "1.0.103" | ||
| version = "1.0.106" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "5ee95bc4ef87b8d5ba32e8b7714ccc834865276eab0aed5c9958d00ec45f49e8" | ||
| checksum = "8fd00f0bb2e90d81d1044c2b32617f68fcb9fa3bb7640c23e9c748e53fb30934" | ||
| dependencies = [ | ||
@@ -42,5 +480,5 @@ "unicode-ident", | ||
| name = "quote" | ||
| version = "1.0.41" | ||
| version = "1.0.45" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ce25767e7b499d1b604768e7cde645d14cc8584231ea6b295e9c9eb22c02e1d1" | ||
| checksum = "41f2619966050689382d2b44f664f4bc593e129785a36d6ee376ddf37259b924" | ||
| dependencies = [ | ||
@@ -51,2 +489,187 @@ "proc-macro2", | ||
| [[package]] | ||
| name = "r-efi" | ||
| version = "5.3.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f" | ||
| [[package]] | ||
| name = "rand" | ||
| version = "0.9.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6db2770f06117d490610c7488547d543617b21bfa07796d7a12f6f1bd53850d1" | ||
| dependencies = [ | ||
| "rand_chacha", | ||
| "rand_core", | ||
| ] | ||
| [[package]] | ||
| name = "rand_chacha" | ||
| version = "0.9.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb" | ||
| dependencies = [ | ||
| "ppv-lite86", | ||
| "rand_core", | ||
| ] | ||
| [[package]] | ||
| name = "rand_core" | ||
| version = "0.9.5" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "76afc826de14238e6e8c374ddcc1fa19e374fd8dd986b0d2af0d02377261d83c" | ||
| dependencies = [ | ||
| "getrandom", | ||
| ] | ||
| [[package]] | ||
| name = "rand_distr" | ||
| version = "0.5.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6a8615d50dcf34fa31f7ab52692afec947c4dd0ab803cc87cb3b0b4570ff7463" | ||
| dependencies = [ | ||
| "num-traits", | ||
| "rand", | ||
| ] | ||
| [[package]] | ||
| name = "rand_pcg" | ||
| version = "0.9.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b48ac3f7ffaab7fac4d2376632268aa5f89abdb55f7ebf8f4d11fffccb2320f7" | ||
| dependencies = [ | ||
| "rand_core", | ||
| ] | ||
| [[package]] | ||
| name = "rayon" | ||
| version = "1.10.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b418a60154510ca1a002a752ca9714984e21e4241e804d32555251faf8b78ffa" | ||
| dependencies = [ | ||
| "either", | ||
| "rayon-core", | ||
| ] | ||
| [[package]] | ||
| name = "rayon-core" | ||
| version = "1.12.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "1465873a3dfdaa8ae7cb14b4383657caab0b3e8a0aa9ae8e04b044854c8dfce2" | ||
| dependencies = [ | ||
| "crossbeam-deque", | ||
| "crossbeam-utils", | ||
| ] | ||
| [[package]] | ||
| name = "ref-cast" | ||
| version = "1.0.25" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "f354300ae66f76f1c85c5f84693f0ce81d747e2c3f21a45fef496d89c960bf7d" | ||
| dependencies = [ | ||
| "ref-cast-impl", | ||
| ] | ||
| [[package]] | ||
| name = "ref-cast-impl" | ||
| version = "1.0.25" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b7186006dcb21920990093f30e3dea63b7d6e977bf1256be20c3563a5db070da" | ||
| dependencies = [ | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| ] | ||
| [[package]] | ||
| name = "regex" | ||
| version = "1.12.3" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "e10754a14b9137dd7b1e3e5b0493cc9171fdd105e0ab477f51b72e7f3ac0e276" | ||
| dependencies = [ | ||
| "aho-corasick", | ||
| "memchr", | ||
| "regex-automata", | ||
| "regex-syntax", | ||
| ] | ||
| [[package]] | ||
| name = "regex-automata" | ||
| version = "0.4.14" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6e1dd4122fc1595e8162618945476892eefca7b88c52820e74af6262213cae8f" | ||
| dependencies = [ | ||
| "aho-corasick", | ||
| "memchr", | ||
| "regex-syntax", | ||
| ] | ||
| [[package]] | ||
| name = "regex-syntax" | ||
| version = "0.8.10" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "dc897dd8d9e8bd1ed8cdad82b5966c3e0ecae09fb1907d58efaa013543185d0a" | ||
| [[package]] | ||
| name = "rmp" | ||
| version = "0.8.14" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "228ed7c16fa39782c3b3468e974aec2795e9089153cd08ee2e9aefb3613334c4" | ||
| dependencies = [ | ||
| "byteorder", | ||
| "num-traits", | ||
| "paste", | ||
| ] | ||
| [[package]] | ||
| name = "rmp-serde" | ||
| version = "1.3.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "52e599a477cf9840e92f2cde9a7189e67b42c57532749bf90aea6ec10facd4db" | ||
| dependencies = [ | ||
| "byteorder", | ||
| "rmp", | ||
| "serde", | ||
| ] | ||
| [[package]] | ||
| name = "rustix" | ||
| version = "1.1.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b6fe4565b9518b83ef4f91bb47ce29620ca828bd32cb7e408f0062e9930ba190" | ||
| dependencies = [ | ||
| "bitflags", | ||
| "errno", | ||
| "libc", | ||
| "linux-raw-sys", | ||
| "windows-sys 0.61.2", | ||
| ] | ||
| [[package]] | ||
| name = "rustversion" | ||
| version = "1.0.22" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b39cdef0fa800fc44525c84ccb54a029961a8215f9619753635a9c0d2538d46d" | ||
| [[package]] | ||
| name = "same-file" | ||
| version = "1.0.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" | ||
| dependencies = [ | ||
| "winapi-util", | ||
| ] | ||
| [[package]] | ||
| name = "schemars" | ||
| version = "1.2.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "a2b42f36aa1cd011945615b92222f6bf73c599a102a300334cd7f8dbeec726cc" | ||
| dependencies = [ | ||
| "dyn-clone", | ||
| "ref-cast", | ||
| "serde", | ||
| "serde_json", | ||
| ] | ||
| [[package]] | ||
| name = "serde" | ||
@@ -82,2 +705,21 @@ version = "1.0.228" | ||
| [[package]] | ||
| name = "serde_json" | ||
| version = "1.0.149" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "83fc039473c5595ace860d8c4fafa220ff474b3fc6bfdb4293327f1a37e94d86" | ||
| dependencies = [ | ||
| "itoa", | ||
| "memchr", | ||
| "serde", | ||
| "serde_core", | ||
| "zmij", | ||
| ] | ||
| [[package]] | ||
| name = "similar" | ||
| version = "2.7.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "bbbb5d9659141646ae647b42fe094daf6c6192d1620870b449d9557f748b2daa" | ||
| [[package]] | ||
| name = "stable_deref_trait" | ||
@@ -90,5 +732,5 @@ version = "1.2.1" | ||
| name = "syn" | ||
| version = "2.0.108" | ||
| version = "2.0.117" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "da58917d35242480a05c2897064da0a80589a2a0476c9a3f2fdc83b53502e917" | ||
| checksum = "e665b8803e7b1d2a727f4023456bbbbe74da67099c585258af0ad9c5013b9b99" | ||
| dependencies = [ | ||
@@ -112,2 +754,45 @@ "proc-macro2", | ||
| [[package]] | ||
| name = "tempfile" | ||
| version = "3.27.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "32497e9a4c7b38532efcdebeef879707aa9f794296a4f0244f6f69e9bc8574bd" | ||
| dependencies = [ | ||
| "fastrand", | ||
| "getrandom", | ||
| "once_cell", | ||
| "rustix", | ||
| "windows-sys 0.61.2", | ||
| ] | ||
| [[package]] | ||
| name = "thiserror" | ||
| version = "2.0.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "4288b5bcbc7920c07a1149a35cf9590a2aa808e0bc1eafaade0b80947865fbc4" | ||
| dependencies = [ | ||
| "thiserror-impl", | ||
| ] | ||
| [[package]] | ||
| name = "thiserror-impl" | ||
| version = "2.0.18" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ebc4ee7f67670e9b64d05fa4253e753e016c6c95ff35b89b7941d6b856dec1d5" | ||
| dependencies = [ | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| ] | ||
| [[package]] | ||
| name = "tinytemplate" | ||
| version = "1.2.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "be4d6b5f19ff7664e8c98d03e2139cb510db9b0a60b55f8e8709b689d939b6bc" | ||
| dependencies = [ | ||
| "serde", | ||
| "serde_json", | ||
| ] | ||
| [[package]] | ||
| name = "twox-hash" | ||
@@ -120,27 +805,265 @@ version = "2.1.2" | ||
| name = "unicode-ident" | ||
| version = "1.0.20" | ||
| version = "1.0.24" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "462eeb75aeb73aea900253ce739c8e18a67423fadf006037cd3ff27e82748a06" | ||
| checksum = "e6e4313cd5fcd3dad5cafa179702e2b244f760991f45397d14d4ebf38247da75" | ||
| [[package]] | ||
| name = "walkdir" | ||
| version = "2.5.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "29790946404f91d9c5d06f9874efddea1dc06c5efe94541a7d6863108e3a5e4b" | ||
| dependencies = [ | ||
| "same-file", | ||
| "winapi-util", | ||
| ] | ||
| [[package]] | ||
| name = "wasip2" | ||
| version = "1.0.1+wasi-0.2.4" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "0562428422c63773dad2c345a1882263bbf4d65cf3f42e90921f787ef5ad58e7" | ||
| dependencies = [ | ||
| "wit-bindgen", | ||
| ] | ||
| [[package]] | ||
| name = "wasm-bindgen" | ||
| version = "0.2.114" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "6532f9a5c1ece3798cb1c2cfdba640b9b3ba884f5db45973a6f442510a87d38e" | ||
| dependencies = [ | ||
| "cfg-if", | ||
| "once_cell", | ||
| "rustversion", | ||
| "wasm-bindgen-macro", | ||
| "wasm-bindgen-shared", | ||
| ] | ||
| [[package]] | ||
| name = "wasm-bindgen-macro" | ||
| version = "0.2.114" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "18a2d50fcf105fb33bb15f00e7a77b772945a2ee45dcf454961fd843e74c18e6" | ||
| dependencies = [ | ||
| "quote", | ||
| "wasm-bindgen-macro-support", | ||
| ] | ||
| [[package]] | ||
| name = "wasm-bindgen-macro-support" | ||
| version = "0.2.114" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "03ce4caeaac547cdf713d280eda22a730824dd11e6b8c3ca9e42247b25c631e3" | ||
| dependencies = [ | ||
| "bumpalo", | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| "wasm-bindgen-shared", | ||
| ] | ||
| [[package]] | ||
| name = "wasm-bindgen-shared" | ||
| version = "0.2.114" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "75a326b8c223ee17883a4251907455a2431acc2791c98c26279376490c378c16" | ||
| dependencies = [ | ||
| "unicode-ident", | ||
| ] | ||
| [[package]] | ||
| name = "web-sys" | ||
| version = "0.3.91" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "854ba17bb104abfb26ba36da9729addc7ce7f06f5c0f90f3c391f8461cca21f9" | ||
| dependencies = [ | ||
| "js-sys", | ||
| "wasm-bindgen", | ||
| ] | ||
| [[package]] | ||
| name = "winapi-util" | ||
| version = "0.1.11" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22" | ||
| dependencies = [ | ||
| "windows-sys 0.61.2", | ||
| ] | ||
| [[package]] | ||
| name = "windows-link" | ||
| version = "0.2.1" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "f0805222e57f7521d6a62e36fa9163bc891acd422f971defe97d64e70d0a4fe5" | ||
| [[package]] | ||
| name = "windows-sys" | ||
| version = "0.59.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "1e38bc4d79ed67fd075bcc251a1c39b32a1776bbe92e5bef1f0bf1f8c531853b" | ||
| dependencies = [ | ||
| "windows-targets", | ||
| ] | ||
| [[package]] | ||
| name = "windows-sys" | ||
| version = "0.61.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "ae137229bcbd6cdf0f7b80a31df61766145077ddf49416a728b02cb3921ff3fc" | ||
| dependencies = [ | ||
| "windows-link", | ||
| ] | ||
| [[package]] | ||
| name = "windows-targets" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973" | ||
| dependencies = [ | ||
| "windows_aarch64_gnullvm", | ||
| "windows_aarch64_msvc", | ||
| "windows_i686_gnu", | ||
| "windows_i686_gnullvm", | ||
| "windows_i686_msvc", | ||
| "windows_x86_64_gnu", | ||
| "windows_x86_64_gnullvm", | ||
| "windows_x86_64_msvc", | ||
| ] | ||
| [[package]] | ||
| name = "windows_aarch64_gnullvm" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" | ||
| [[package]] | ||
| name = "windows_aarch64_msvc" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" | ||
| [[package]] | ||
| name = "windows_i686_gnu" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b" | ||
| [[package]] | ||
| name = "windows_i686_gnullvm" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" | ||
| [[package]] | ||
| name = "windows_i686_msvc" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" | ||
| [[package]] | ||
| name = "windows_x86_64_gnu" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" | ||
| [[package]] | ||
| name = "windows_x86_64_gnullvm" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" | ||
| [[package]] | ||
| name = "windows_x86_64_msvc" | ||
| version = "0.52.6" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" | ||
| [[package]] | ||
| name = "wit-bindgen" | ||
| version = "0.46.0" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "f17a85883d4e6d00e8a97c586de764dabcc06133f7f1d55dce5cdc070ad7fe59" | ||
| [[package]] | ||
| name = "yoke" | ||
| version = "0.8.1" | ||
| version = "0.8.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "72d6e5c6afb84d73944e5cedb052c4680d5657337201555f9f2a16b7406d4954" | ||
| checksum = "abe8c5fda708d9ca3df187cae8bfb9ceda00dd96231bed36e445a1a48e66f9ca" | ||
| dependencies = [ | ||
| "stable_deref_trait", | ||
| "yoke-derive", | ||
| "zerofrom", | ||
| ] | ||
| [[package]] | ||
| name = "yoke-derive" | ||
| version = "0.8.2" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "de844c262c8848816172cef550288e7dc6c7b7814b4ee56b3e1553f275f1858e" | ||
| dependencies = [ | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| "synstructure", | ||
| ] | ||
| [[package]] | ||
| name = "zerocopy" | ||
| version = "0.8.47" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "efbb2a062be311f2ba113ce66f697a4dc589f85e78a4aea276200804cea0ed87" | ||
| dependencies = [ | ||
| "zerocopy-derive", | ||
| ] | ||
| [[package]] | ||
| name = "zerocopy-derive" | ||
| version = "0.8.47" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "0e8bc7269b54418e7aeeef514aa68f8690b8c0489a06b0136e5f57c4c5ccab89" | ||
| dependencies = [ | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| ] | ||
| [[package]] | ||
| name = "zerofrom" | ||
| version = "0.1.6" | ||
| version = "0.1.7" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "50cc42e0333e05660c3587f3bf9d0478688e15d870fab3346451ce7f8c9fbea5" | ||
| checksum = "69faa1f2a1ea75661980b013019ed6687ed0e83d069bc1114e2cc74c6c04c4df" | ||
| dependencies = [ | ||
| "zerofrom-derive", | ||
| ] | ||
| [[package]] | ||
| name = "zerofrom-derive" | ||
| version = "0.1.7" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "11532158c46691caf0f2593ea8358fed6bbf68a0315e80aae9bd41fbade684a1" | ||
| dependencies = [ | ||
| "proc-macro2", | ||
| "quote", | ||
| "syn", | ||
| "synstructure", | ||
| ] | ||
| [[package]] | ||
| name = "zerovec" | ||
| version = "0.11.5" | ||
| version = "0.11.6" | ||
| dependencies = [ | ||
| "bincode", | ||
| "criterion", | ||
| "databake", | ||
| "getrandom", | ||
| "iai", | ||
| "insta", | ||
| "postcard", | ||
| "rand", | ||
| "rand_distr", | ||
| "rand_pcg", | ||
| "rmp-serde", | ||
| "schemars", | ||
| "serde", | ||
| "serde_json", | ||
| "twox-hash", | ||
@@ -154,5 +1077,5 @@ "yoke", | ||
| name = "zerovec-derive" | ||
| version = "0.11.2" | ||
| version = "0.11.3" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "eadce39539ca5cb3985590102671f2567e659fca9666581ad3411d59207951f3" | ||
| checksum = "625dc425cab0dca6dc3c3319506e6593dcb08a9f387ea3b284dbd52a92c40555" | ||
| dependencies = [ | ||
@@ -163,1 +1086,7 @@ "proc-macro2", | ||
| ] | ||
| [[package]] | ||
| name = "zmij" | ||
| version = "1.0.21" | ||
| source = "registry+https://github.com/rust-lang/crates.io-index" | ||
| checksum = "b8848ee67ecc8aedbaf3e4122217aff892639231befc6a1b58d29fff4c2cabaa" |
+112
-7
@@ -14,5 +14,5 @@ # THIS FILE IS AUTOMATICALLY GENERATED BY CARGO | ||
| edition = "2021" | ||
| rust-version = "1.82" | ||
| rust-version = "1.83" | ||
| name = "zerovec" | ||
| version = "0.11.5" | ||
| version = "0.11.6" | ||
| authors = ["The ICU4X Project Developers"] | ||
@@ -39,5 +39,5 @@ build = false | ||
| keywords = [ | ||
| "zerocopy", | ||
| "zero-copy", | ||
| "serialization", | ||
| "zero-copy", | ||
| "memory-efficiency", | ||
| "serde", | ||
@@ -72,2 +72,6 @@ ] | ||
| ] | ||
| schemars = [ | ||
| "dep:schemars", | ||
| "alloc", | ||
| ] | ||
| serde = ["dep:serde"] | ||
@@ -124,2 +128,7 @@ std = [] | ||
| [dependencies.schemars] | ||
| version = "1.0.4" | ||
| optional = true | ||
| default-features = false | ||
| [dependencies.serde] | ||
@@ -138,3 +147,3 @@ version = "1.0.220" | ||
| [dependencies.yoke] | ||
| version = "0.8.0" | ||
| version = "0.8.2" | ||
| optional = true | ||
@@ -144,8 +153,104 @@ default-features = false | ||
| [dependencies.zerofrom] | ||
| version = "0.1.3" | ||
| version = "0.1.6" | ||
| default-features = false | ||
| [dependencies.zerovec-derive] | ||
| version = "0.11.1" | ||
| version = "0.11.3" | ||
| optional = true | ||
| default-features = false | ||
| [dev-dependencies.bincode] | ||
| version = "1.3.1" | ||
| [dev-dependencies.getrandom] | ||
| version = "0.3" | ||
| features = ["wasm_js"] | ||
| [dev-dependencies.iai] | ||
| version = "0.1.1" | ||
| [dev-dependencies.insta] | ||
| version = "1.43.2" | ||
| features = ["json"] | ||
| [dev-dependencies.postcard] | ||
| version = "1.0.3" | ||
| features = ["use-std"] | ||
| default-features = false | ||
| [dev-dependencies.rand] | ||
| version = "0.9" | ||
| [dev-dependencies.rand_distr] | ||
| version = "0.5" | ||
| [dev-dependencies.rand_pcg] | ||
| version = "0.9" | ||
| [dev-dependencies.rmp-serde] | ||
| version = "1.2.0" | ||
| [dev-dependencies.serde] | ||
| version = "1.0.220" | ||
| features = ["derive"] | ||
| default-features = false | ||
| [dev-dependencies.serde_json] | ||
| version = "1.0.45" | ||
| [dev-dependencies.yoke] | ||
| version = "0.8.2" | ||
| features = ["derive"] | ||
| default-features = false | ||
| [target.'cfg(not(target_arch = "wasm32"))'.dev-dependencies.criterion] | ||
| version = "0.5.0" | ||
| [lints.clippy] | ||
| alloc-instead-of-core = "warn" | ||
| branches-sharing-code = "warn" | ||
| collection_is_never_read = "warn" | ||
| crosspointer_transmute = "warn" | ||
| dbg_macro = "warn" | ||
| debug_assert_with_mut_call = "warn" | ||
| doc_markdown = "warn" | ||
| exhaustive_enums = "deny" | ||
| exhaustive_structs = "deny" | ||
| fn_to_numeric_cast_any = "warn" | ||
| infinite_loop = "warn" | ||
| large_stack_arrays = "warn" | ||
| mismatching_type_param_order = "warn" | ||
| missing_fields_in_debug = "warn" | ||
| missing_transmute_annotations = "warn" | ||
| negative_feature_names = "warn" | ||
| or-fun-call = "warn" | ||
| same_functions_in_if_condition = "warn" | ||
| todo = "warn" | ||
| transmute_bytes_to_str = "warn" | ||
| transmute_int_to_bool = "warn" | ||
| transmute_int_to_non_zero = "warn" | ||
| transmute_ptr_to_ptr = "warn" | ||
| transmute_ptr_to_ref = "warn" | ||
| transmute_undefined_repr = "warn" | ||
| transmutes_expressible_as_ptr_casts = "warn" | ||
| trivially_copy_pass_by_ref = "deny" | ||
| unnecessary-wraps = "warn" | ||
| useless_transmute = "warn" | ||
| wildcard_dependencies = "warn" | ||
| [lints.rust] | ||
| missing_debug_implementations = "deny" | ||
| trivial_numeric_casts = "deny" | ||
| unused_lifetimes = "warn" | ||
| unused_macro_rules = "warn" | ||
| unused_qualifications = "warn" | ||
| [lints.rust.unexpected_cfgs] | ||
| level = "warn" | ||
| priority = 0 | ||
| check-cfg = [ | ||
| "cfg(icu4c_enable_renaming)", | ||
| "cfg(needs_alloc_error_handler)", | ||
| "cfg(icu4x_run_size_tests)", | ||
| "cfg(icu4x_unstable_fast_trie_only)", | ||
| ] |
+3
-3
@@ -54,3 +54,3 @@ # zerovec [](https://crates.io/crates/zerovec) | ||
| Serialize and deserialize a struct with ZeroVec and VarZeroVec with Bincode: | ||
| Serialize and deserialize a struct with [`ZeroVec`] and [`VarZeroVec`] with Bincode: | ||
@@ -89,3 +89,3 @@ ```rust | ||
| Use custom types inside of ZeroVec: | ||
| Use custom types inside of [`ZeroVec`]: | ||
@@ -169,3 +169,3 @@ ```rust | ||
| Benchmark results on x86_64: | ||
| Benchmark results on `x86_64`: | ||
@@ -172,0 +172,0 @@ | Operation | `Vec<T>` | `zerovec` | |
+2
-2
@@ -42,3 +42,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// VarZeroCow without the `V` to simulate a dropck eyepatch | ||
| /// [`VarZeroCow`] without the `V` to simulate a dropck eyepatch | ||
| /// (i.e., prove to rustc that the dtor is not able to observe V or 'a) | ||
@@ -54,3 +54,3 @@ /// | ||
| /// 2. If `owned` is true, this slice can be freed. | ||
| /// 3. VarZeroCow, the only user of this type, will impose an additional invariant that the buffer is a valid V | ||
| /// 3. [`VarZeroCow`], the only user of this type, will impose an additional invariant that the buffer is a valid V | ||
| buf: NonNull<[u8]>, | ||
@@ -57,0 +57,0 @@ /// The buffer is `Box<[u8]>` if true |
+19
-20
@@ -5,2 +5,15 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| // https://github.com/unicode-org/icu4x/blob/main/documents/process/boilerplate.md#library-annotations | ||
| #![cfg_attr(not(any(test, doc)), no_std)] | ||
| #![cfg_attr( | ||
| not(test), | ||
| deny( | ||
| clippy::indexing_slicing, | ||
| clippy::unwrap_used, | ||
| clippy::expect_used, | ||
| clippy::panic, | ||
| ) | ||
| )] | ||
| // #![warn(missing_docs)] | ||
| //! Zero-copy vector abstractions for arbitrary types, backed by byte slices. | ||
@@ -55,3 +68,3 @@ //! | ||
| //! | ||
| //! Serialize and deserialize a struct with ZeroVec and VarZeroVec with Bincode: | ||
| //! Serialize and deserialize a struct with [`ZeroVec`] and [`VarZeroVec`] with Bincode: | ||
| //! | ||
@@ -92,3 +105,3 @@ //! ``` | ||
| //! | ||
| //! Use custom types inside of ZeroVec: | ||
| //! Use custom types inside of [`ZeroVec`]: | ||
| //! | ||
@@ -173,3 +186,3 @@ //! ```rust | ||
| //! | ||
| //! Benchmark results on x86_64: | ||
| //! Benchmark results on `x86_64`: | ||
| //! | ||
@@ -200,17 +213,2 @@ //! | Operation | `Vec<T>` | `zerovec` | | ||
| // https://github.com/unicode-org/icu4x/blob/main/documents/process/boilerplate.md#library-annotations | ||
| #![cfg_attr(not(any(test, doc)), no_std)] | ||
| #![cfg_attr( | ||
| not(test), | ||
| deny( | ||
| clippy::indexing_slicing, | ||
| clippy::unwrap_used, | ||
| clippy::expect_used, | ||
| clippy::panic, | ||
| clippy::exhaustive_structs, | ||
| clippy::exhaustive_enums, | ||
| clippy::trivially_copy_pass_by_ref, | ||
| missing_debug_implementations, | ||
| ) | ||
| )] | ||
| // this crate does a lot of nuanced lifetime manipulation, being explicit | ||
@@ -232,2 +230,4 @@ // is better here. | ||
| pub mod samples; | ||
| #[cfg(feature = "schemars")] | ||
| mod schemars; | ||
| mod varzerovec; | ||
@@ -425,3 +425,3 @@ mod zerovec; | ||
| /// [`Cow<'a, str>`](alloc::borrow::Cow), [`ZeroSlice`], or [`VarZeroSlice`]. If there is more than one such field, it will be represented | ||
| /// using [`MultiFieldsULE`](crate::ule::MultiFieldsULE) and getters will be generated. Other VarULE fields will be detected if they are | ||
| /// using [`MultiFieldsULE`](crate::ule::MultiFieldsULE) and getters will be generated. Other [`VarULE`] fields will be detected if they are | ||
| /// tagged with `#[zerovec::varule(NameOfVarULETy)]`. | ||
@@ -552,3 +552,2 @@ /// | ||
| use super::*; | ||
| use core::mem::size_of; | ||
@@ -555,0 +554,0 @@ /// Checks that the size of the type is one of the given sizes. |
+2
-2
@@ -8,4 +8,4 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use crate::{VarZeroVec, ZeroSlice, ZeroVec}; | ||
| use alloc::borrow::Borrow; | ||
| use alloc::boxed::Box; | ||
| use core::borrow::Borrow; | ||
| use core::cmp::Ordering; | ||
@@ -415,3 +415,3 @@ use core::fmt; | ||
| { | ||
| /// Same as `insert()`, but allows using [EncodeAsVarULE](crate::ule::EncodeAsVarULE) | ||
| /// Same as `insert()`, but allows using [`EncodeAsVarULE`](crate::ule::EncodeAsVarULE) | ||
| /// types with the value to avoid an extra allocation when dealing with custom ULE types. | ||
@@ -418,0 +418,0 @@ /// |
+1
-1
@@ -69,3 +69,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Modified example from https://serde.rs/deserialize-map.html | ||
| /// Modified example from <https://serde.rs/deserialize-map.html> | ||
| struct ZeroMapMapVisitor<'a, K, V> | ||
@@ -72,0 +72,0 @@ where |
@@ -138,3 +138,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Given key0_index, returns the corresponding range of keys1, which will be valid | ||
| /// Given `key0_index`, returns the corresponding range of keys1, which will be valid | ||
| pub(super) fn get_range(&self) -> Range<usize> { | ||
@@ -291,3 +291,3 @@ debug_assert!(self.key0_index < self.joiner.len()); | ||
| /// Given key0_index and predicate, returns the index into the values array | ||
| /// Given `key0_index` and `predicate`, returns the index into the values array | ||
| fn get_key1_index_by(&self, predicate: impl FnMut(&K1) -> Ordering) -> Option<usize> { | ||
@@ -306,3 +306,3 @@ let range = self.get_range(); | ||
| /// Given key0_index and key1, returns the index into the values array | ||
| /// Given `key0_index` and `key1`, returns the index into the values array | ||
| fn get_key1_index(&self, key1: &K1) -> Option<usize> { | ||
@@ -309,0 +309,0 @@ let range = self.get_range(); |
+5
-5
@@ -7,3 +7,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use crate::ZeroVec; | ||
| use alloc::borrow::Borrow; | ||
| use core::borrow::Borrow; | ||
| use core::cmp::Ordering; | ||
@@ -204,3 +204,3 @@ use core::convert::TryFrom; | ||
| /// | ||
| /// Loop over all elements of a ZeroMap2d: | ||
| /// Loop over all elements of a [`ZeroMap2d`]: | ||
| /// | ||
@@ -239,3 +239,3 @@ /// ``` | ||
| /// Removes key0_index from the keys0 array and the joiner array | ||
| /// Removes `key0_index` from the keys0 array and the joiner array | ||
| fn remove_key0_index(&mut self, key0_index: usize) { | ||
@@ -246,3 +246,3 @@ self.keys0.zvl_remove(key0_index); | ||
| /// Shifts all joiner ranges from key0_index onward one index up | ||
| /// Shifts all joiner ranges from `key0_index` onward one index up | ||
| fn joiner_expand(&mut self, key0_index: usize) { | ||
@@ -264,3 +264,3 @@ #[expect(clippy::expect_used)] // slice overflow | ||
| /// Shifts all joiner ranges from key0_index onward one index down | ||
| /// Shifts all joiner ranges from `key0_index` onward one index down | ||
| fn joiner_shrink(&mut self, key0_index: usize) { | ||
@@ -267,0 +267,0 @@ self.joiner |
@@ -44,3 +44,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Helper struct for human-serializing the inner map of a ZeroMap2d | ||
| /// Helper struct for human-serializing the inner map of a [`ZeroMap2d`] | ||
| #[cfg(feature = "serde")] | ||
@@ -98,3 +98,3 @@ struct ZeroMap2dInnerMapSerialize<'a, 'l, K0, K1, V> | ||
| /// Modified example from https://serde.rs/deserialize-map.html | ||
| /// Modified example from <https://serde.rs/deserialize-map.html> | ||
| struct ZeroMap2dMapVisitor<'a, K0, K1, V> | ||
@@ -171,3 +171,3 @@ where | ||
| /// Helper struct for human-deserializing the inner map of a ZeroMap2d | ||
| /// Helper struct for human-deserializing the inner map of a [`ZeroMap2d`] | ||
| struct TupleVecMap<K1, V> { | ||
@@ -174,0 +174,0 @@ pub entries: Vec<(K1, V)>, |
+5
-5
@@ -5,3 +5,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| //! Example data useful for testing ZeroVec. | ||
| //! Example data useful for testing [`ZeroVec`]. | ||
@@ -34,9 +34,9 @@ // This module is included directly in tests and can trigger the dead_code | ||
| /// The sum of the numbers in TEST_SLICE. | ||
| /// The sum of the numbers in `TEST_SLICE`. | ||
| pub const TEST_SUM: u32 = 52629240; | ||
| /// Representation of TEST_SLICE in JSON. | ||
| /// Representation of `TEST_SLICE` in JSON. | ||
| pub const JSON_STR: &str = "[131328,394500,657672,920844,1184016,1447188,1710360,1973532,2236704,2499876,2763048,3026220,3289392,3552564,3815736,4078908,4342080,4605252,4868424,5131596]"; | ||
| /// Representation of TEST_SLICE in Bincode. | ||
| /// Representation of `TEST_SLICE` in Bincode. | ||
| pub const BINCODE_BUF: &[u8] = &[ | ||
@@ -49,3 +49,3 @@ 80, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 0, 4, 5, 6, 0, 8, 9, 10, 0, 12, 13, 14, 0, 16, 17, 18, 0, 20, | ||
| /// Representation of a VarZeroVec<str> with contents ["w", "ω", "文", "𑄃"] | ||
| /// Representation of a `VarZeroVec<str>` with contents `["w", "ω", "文", "𑄃"]` | ||
| pub const TEST_VARZEROSLICE_BYTES: &[u8] = &[ | ||
@@ -52,0 +52,0 @@ 4, 0, 0, 0, 0, 0, 1, 0, 3, 0, 6, 0, 119, 207, 137, 230, 150, 135, 240, 145, 132, 131, |
+11
-13
@@ -16,13 +16,11 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use alloc::{vec, vec::Vec}; | ||
| #[cfg(feature = "alloc")] | ||
| use core::mem; | ||
| /// Allows types to be encoded as VarULEs. This is highly useful for implementing VarULE on | ||
| /// Allows types to be encoded as [`VarULE`]s. This is highly useful for implementing [`VarULE`] on | ||
| /// custom DSTs where the type cannot be obtained as a reference to some other type. | ||
| /// | ||
| /// [`Self::encode_var_ule_as_slices()`] should be implemented by providing an encoded slice for each field | ||
| /// of the VarULE type to the callback, in order. For an implementation to be safe, the slices | ||
| /// to the callback must, when concatenated, be a valid instance of the VarULE type. | ||
| /// of the [`VarULE`] type to the callback, in order. For an implementation to be safe, the slices | ||
| /// to the callback must, when concatenated, be a valid instance of the [`VarULE`] type. | ||
| /// | ||
| /// See the [custom VarULEdocumentation](crate::ule::custom) for examples. | ||
| /// See the [custom `VarULEdocumentation`](crate::ule::custom) for examples. | ||
| /// | ||
@@ -43,3 +41,3 @@ /// [`Self::encode_var_ule_as_slices()`] is only used to provide default implementations for [`Self::encode_var_ule_write()`] | ||
| /// | ||
| /// # Reverse-encoding VarULE | ||
| /// # Reverse-encoding [`VarULE`] | ||
| /// | ||
@@ -63,3 +61,3 @@ /// This trait maps a struct to its bytes representation ("serialization"), and | ||
| /// The safety invariants of [`Self::encode_var_ule_len()`] are: | ||
| /// - It must return the length of the corresponding VarULE type | ||
| /// - It must return the length of the corresponding [`VarULE`] type | ||
| /// | ||
@@ -97,3 +95,3 @@ /// The safety invariants of [`Self::encode_var_ule_write()`] are: | ||
| /// | ||
| /// This is primarily useful for generating `Deserialize` impls for VarULE types | ||
| /// This is primarily useful for generating `Deserialize` impls for [`VarULE`] types | ||
| #[cfg(feature = "alloc")] | ||
@@ -104,3 +102,3 @@ pub fn encode_varule_to_box<S: EncodeAsVarULE<T> + ?Sized, T: VarULE + ?Sized>(x: &S) -> Box<T> { | ||
| x.encode_var_ule_write(&mut vec); | ||
| let boxed = mem::ManuallyDrop::new(vec.into_boxed_slice()); | ||
| let boxed = core::mem::ManuallyDrop::new(vec.into_boxed_slice()); | ||
| unsafe { | ||
@@ -195,3 +193,3 @@ // Safety: `ptr` is a box, and `T` is a VarULE which guarantees it has the same memory layout as `[u8]` | ||
| fn encode_var_ule_len(&self) -> usize { | ||
| self.len() * core::mem::size_of::<T::ULE>() | ||
| self.len() * size_of::<T::ULE>() | ||
| } | ||
@@ -201,7 +199,7 @@ | ||
| #[allow(non_snake_case)] | ||
| let S = core::mem::size_of::<T::ULE>(); | ||
| let S = size_of::<T::ULE>(); | ||
| debug_assert_eq!(self.len() * S, dst.len()); | ||
| for (item, ref mut chunk) in self.iter().zip(dst.chunks_mut(S)) { | ||
| let ule = item.to_unaligned(); | ||
| chunk.copy_from_slice(ULE::slice_as_bytes(core::slice::from_ref(&ule))); | ||
| chunk.copy_from_slice(ULE::slice_as_bytes(slice::from_ref(&ule))); | ||
| } | ||
@@ -208,0 +206,0 @@ } |
+14
-14
@@ -38,4 +38,7 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::{any, fmt, mem, slice}; | ||
| use core::{any, fmt, slice}; | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::boxed::Box; | ||
| /// Fixed-width, byte-aligned data that can be cast to and from a little-endian byte slice. | ||
@@ -104,3 +107,3 @@ /// | ||
| Self::validate_bytes(bytes)?; | ||
| debug_assert_eq!(bytes.len() % mem::size_of::<Self>(), 0); | ||
| debug_assert_eq!(bytes.len() % size_of::<Self>(), 0); | ||
| Ok(unsafe { Self::slice_from_bytes_unchecked(bytes) }) | ||
@@ -136,5 +139,5 @@ } | ||
| let data = bytes.as_ptr(); | ||
| let len = bytes.len() / mem::size_of::<Self>(); | ||
| debug_assert_eq!(bytes.len() % mem::size_of::<Self>(), 0); | ||
| core::slice::from_raw_parts(data as *const Self, len) | ||
| let len = bytes.len() / size_of::<Self>(); | ||
| debug_assert_eq!(bytes.len() % size_of::<Self>(), 0); | ||
| slice::from_raw_parts(data as *const Self, len) | ||
| } | ||
@@ -154,5 +157,3 @@ | ||
| fn slice_as_bytes(slice: &[Self]) -> &[u8] { | ||
| unsafe { | ||
| slice::from_raw_parts(slice as *const [Self] as *const u8, mem::size_of_val(slice)) | ||
| } | ||
| unsafe { slice::from_raw_parts(slice as *const [Self] as *const u8, size_of_val(slice)) } | ||
| } | ||
@@ -231,3 +232,3 @@ } | ||
| let ule_slice = | ||
| unsafe { core::slice::from_raw_parts(slice.as_ptr() as *const Self::ULE, slice.len()) }; | ||
| unsafe { slice::from_raw_parts(slice.as_ptr() as *const Self::ULE, slice.len()) }; | ||
| Some(ule_slice) | ||
@@ -323,3 +324,3 @@ } | ||
| let result = unsafe { Self::from_bytes_unchecked(bytes) }; | ||
| debug_assert_eq!(mem::size_of_val(result), mem::size_of_val(bytes)); | ||
| debug_assert_eq!(size_of_val(result), size_of_val(bytes)); | ||
| Ok(result) | ||
@@ -360,3 +361,3 @@ } | ||
| fn as_bytes(&self) -> &[u8] { | ||
| unsafe { slice::from_raw_parts(self as *const Self as *const u8, mem::size_of_val(self)) } | ||
| unsafe { slice::from_raw_parts(self as *const Self as *const u8, size_of_val(self)) } | ||
| } | ||
@@ -369,8 +370,7 @@ | ||
| #[cfg(feature = "alloc")] | ||
| fn to_boxed(&self) -> alloc::boxed::Box<Self> { | ||
| fn to_boxed(&self) -> Box<Self> { | ||
| use alloc::borrow::ToOwned; | ||
| use alloc::boxed::Box; | ||
| use core::alloc::Layout; | ||
| let bytesvec = self.as_bytes().to_owned().into_boxed_slice(); | ||
| let bytesvec = mem::ManuallyDrop::new(bytesvec); | ||
| let bytesvec = core::mem::ManuallyDrop::new(bytesvec); | ||
| unsafe { | ||
@@ -377,0 +377,0 @@ // Get the pointer representation |
+23
-16
@@ -8,3 +8,5 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use crate::vecs::VarZeroVecFormat; | ||
| use core::{fmt, mem}; | ||
| #[cfg(doc)] | ||
| use crate::VarZeroSlice; | ||
| use core::fmt; | ||
@@ -16,5 +18,5 @@ /// This type is used by the custom derive to represent multiple [`VarULE`] | ||
| /// Logically, consider it to be `(, , , ..)` | ||
| /// where `` etc are potentially different [`VarULE`] types. | ||
| /// where ` ` etc are potentially different [`VarULE`] types. | ||
| /// | ||
| /// Internally, it is represented by a VarZeroSlice without the length part. | ||
| /// Internally, it is represented by a [`VarZeroSlice`] without the length part. | ||
| #[derive(PartialEq, Eq)] | ||
@@ -38,3 +40,3 @@ #[repr(transparent)] | ||
| /// Construct a partially initialized MultiFieldsULE backed by a mutable byte buffer | ||
| /// Construct a partially initialized `MultiFieldsULE` backed by a mutable byte buffer | ||
| pub fn new_from_lengths_partially_initialized<'a>( | ||
@@ -54,5 +56,6 @@ lengths: [usize; LEN], | ||
| // Safe since write_serializable_bytes produces a valid VarZeroLengthlessSlice buffer with the right format | ||
| let slice = <VarZeroLengthlessSlice<[u8], Format>>::from_bytes_unchecked_mut(output); | ||
| let slice = VarZeroLengthlessSlice::<[u8], Format>::from_bytes_unchecked_mut(output); | ||
| // safe since `Self` is transparent over VarZeroLengthlessSlice<[u8], Format> | ||
| mem::transmute::<&mut VarZeroLengthlessSlice<[u8], Format>, &mut Self>(slice) | ||
| &mut *(slice as *mut VarZeroLengthlessSlice<[u8], Format> | ||
| as *mut MultiFieldsULE<LEN, Format>) | ||
| } | ||
@@ -75,3 +78,3 @@ } | ||
| /// Validate field at `index` to see if it is a valid `T` VarULE type | ||
| /// Validate field at `index` to see if it is a valid `T` [`VarULE`] type | ||
| /// | ||
@@ -91,3 +94,3 @@ /// # Safety | ||
| /// - `index` must be in range | ||
| /// - Element at `index` must have been created with the VarULE type T | ||
| /// - Element at `index` must have been created with the [`VarULE`] type T | ||
| #[inline] | ||
@@ -101,7 +104,9 @@ pub unsafe fn get_field<T: VarULE + ?Sized>(&self, index: usize) -> &T { | ||
| /// # Safety | ||
| /// - byte slice must be a valid VarZeroLengthlessSlice<[u8], Format> with length LEN | ||
| /// - byte slice must be a valid `VarZeroLengthlessSlice<[u8], Format>` with length `LEN` | ||
| #[inline] | ||
| pub unsafe fn from_bytes_unchecked(bytes: &[u8]) -> &Self { | ||
| // &Self is transparent over &VZS<..> with the right format | ||
| mem::transmute(<VarZeroLengthlessSlice<[u8], Format>>::from_bytes_unchecked(bytes)) | ||
| let slice = VarZeroLengthlessSlice::<[u8], Format>::from_bytes_unchecked(bytes); | ||
| &*(slice as *const VarZeroLengthlessSlice<[u8], Format> | ||
| as *const MultiFieldsULE<LEN, Format>) | ||
| } | ||
@@ -120,3 +125,3 @@ | ||
| } | ||
| /// This lets us conveniently use the EncodeAsVarULE functionality to create | ||
| /// This lets us conveniently use the `EncodeAsVarULE` functionality to create | ||
| /// `VarZeroVec<[u8]>`s that have the right amount of space for elements | ||
@@ -153,9 +158,9 @@ /// without having to duplicate any unsafe code | ||
| unsafe impl<const LEN: usize, Format: VarZeroVecFormat> VarULE for MultiFieldsULE<LEN, Format> { | ||
| /// Note: MultiFieldsULE is usually used in cases where one should be calling .validate_field() directly for | ||
| /// each field, rather than using the regular VarULE impl. | ||
| /// Note: `MultiFieldsULE` is usually used in cases where one should be calling .`validate_field()` directly for | ||
| /// each field, rather than using the regular `VarULE` impl. | ||
| /// | ||
| /// This impl exists so that EncodeAsVarULE can work. | ||
| /// This impl exists so that `EncodeAsVarULE` can work. | ||
| #[inline] | ||
| fn validate_bytes(slice: &[u8]) -> Result<(), UleError> { | ||
| <VarZeroLengthlessSlice<[u8], Format>>::parse_bytes(LEN as u32, slice).map(|_| ()) | ||
| VarZeroLengthlessSlice::<[u8], Format>::parse_bytes(LEN as u32, slice).map(|_| ()) | ||
| } | ||
@@ -166,4 +171,6 @@ | ||
| // &Self is transparent over &VZS<..> | ||
| mem::transmute(<VarZeroLengthlessSlice<[u8], Format>>::from_bytes_unchecked(bytes)) | ||
| let slice = VarZeroLengthlessSlice::<[u8], Format>::from_bytes_unchecked(bytes); | ||
| &*(slice as *const VarZeroLengthlessSlice<[u8], Format> | ||
| as *const MultiFieldsULE<LEN, Format>) | ||
| } | ||
| } |
+12
-12
@@ -5,3 +5,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::{marker::Copy, mem::size_of}; | ||
| use core::marker::Copy; | ||
@@ -56,5 +56,5 @@ #[cfg(feature = "alloc")] | ||
| pub union NichedOptionULE<U: NicheBytes<N> + ULE, const N: usize> { | ||
| /// Invariant: The value is `niche` only if the bytes equal NICHE_BIT_PATTERN. | ||
| /// Invariant: The value is `niche` only if the bytes equal `NICHE_BIT_PATTERN`. | ||
| niche: [u8; N], | ||
| /// Invariant: The value is `valid` if the `niche` field does not match NICHE_BIT_PATTERN. | ||
| /// Invariant: The value is `valid` if the `niche` field does not match `NICHE_BIT_PATTERN`. | ||
| valid: U, | ||
@@ -74,3 +74,3 @@ } | ||
| pub fn new(opt: Option<U>) -> Self { | ||
| assert!(N == core::mem::size_of::<U>()); | ||
| assert!(N == size_of::<U>()); | ||
| match opt { | ||
@@ -126,12 +126,12 @@ Some(u) => Self { valid: u }, | ||
| /// Safety for ULE trait | ||
| /// 1. NichedOptionULE does not have any padding bytes due to `#[repr(C)]` on a struct | ||
| /// 1. `NichedOptionULE` does not have any padding bytes due to `#[repr(C)]` on a struct | ||
| /// containing only ULE fields. | ||
| /// NichedOptionULE either contains NICHE_BIT_PATTERN or valid U byte sequences. | ||
| /// `NichedOptionULE` either contains `NICHE_BIT_PATTERN` or valid U byte sequences. | ||
| /// In both cases the data is initialized. | ||
| /// 2. NichedOptionULE is aligned to 1 byte due to `#[repr(C, packed)]` on a struct containing only | ||
| /// 2. `NichedOptionULE` is aligned to 1 byte due to `#[repr(C, packed)]` on a struct containing only | ||
| /// ULE fields. | ||
| /// 3. validate_bytes impl returns an error if invalid bytes are encountered. | ||
| /// 4. validate_bytes impl returns an error there are extra bytes. | ||
| /// 3. `validate_bytes` impl returns an error if invalid bytes are encountered. | ||
| /// 4. `validate_bytes` impl returns an error there are extra bytes. | ||
| /// 5. The other ULE methods are left to their default impl. | ||
| /// 6. NichedOptionULE equality is based on ULE equality of the subfield, assuming that NicheBytes | ||
| /// 6. `NichedOptionULE` equality is based on ULE equality of the subfield, assuming that `NicheBytes` | ||
| /// has been implemented correctly (this is a correctness but not a safety guarantee). | ||
@@ -143,3 +143,3 @@ unsafe impl<U: NicheBytes<N> + ULE, const N: usize> ULE for NichedOptionULE<U, N> { | ||
| // type. | ||
| debug_assert!(N == core::mem::size_of::<U>()); | ||
| debug_assert!(N == size_of::<U>()); | ||
@@ -164,3 +164,3 @@ // The bytes should fully transmute to a collection of Self | ||
| /// | ||
| /// The implementors guarantee that `N == core::mem::size_of::<Self>()` | ||
| /// The implementors guarantee that `N == size_of::<Self>()` | ||
| /// `#[repr(transparent)]` guarantees that the layout is same as [`Option<U>`] | ||
@@ -167,0 +167,0 @@ #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)] |
@@ -8,3 +8,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::marker::PhantomData; | ||
| use core::mem::{self, MaybeUninit}; | ||
| use core::mem::MaybeUninit; | ||
@@ -58,4 +58,4 @@ /// This type is the [`ULE`] type for `Option<U>` where `U` is a [`ULE`] type | ||
| impl<U: Copy + core::fmt::Debug> core::fmt::Debug for OptionULE<U> { | ||
| fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result { | ||
| impl<U: Copy + fmt::Debug> fmt::Debug for OptionULE<U> { | ||
| fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
| self.get().fmt(f) | ||
@@ -79,3 +79,3 @@ } | ||
| fn validate_bytes(bytes: &[u8]) -> Result<(), UleError> { | ||
| let size = mem::size_of::<Self>(); | ||
| let size = size_of::<Self>(); | ||
| if bytes.len() % size != 0 { | ||
@@ -164,4 +164,4 @@ return Err(UleError::length::<Self>(bytes.len())); | ||
| impl<U: VarULE + ?Sized + core::fmt::Debug> core::fmt::Debug for OptionVarULE<U> { | ||
| fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result { | ||
| impl<U: VarULE + ?Sized + fmt::Debug> fmt::Debug for OptionVarULE<U> { | ||
| fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
| self.as_ref().fmt(f) | ||
@@ -168,0 +168,0 @@ } |
+74
-98
@@ -30,3 +30,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| // Safe because Self is transparent over [u8; N] | ||
| unsafe { core::slice::from_raw_parts_mut(data as *mut Self, len) } | ||
| unsafe { slice::from_raw_parts_mut(data as *mut Self, len) } | ||
| } | ||
@@ -63,13 +63,29 @@ } | ||
| macro_rules! impl_byte_slice_size { | ||
| ($unsigned:ty, $size:literal) => { | ||
| impl RawBytesULE<$size> { | ||
| #[doc = concat!("Gets this `RawBytesULE` as a `", stringify!($unsigned), "`. This is equivalent to calling [`AsULE::from_unaligned()`] on the appropriately sized type.")] | ||
| macro_rules! impl_numbers_with_raw_bytes_ule { | ||
| ($unsigned:ty, $signed:ty $(, $float:ty)?) => { | ||
| const _: () = assert!(size_of::<$unsigned>() == size_of::<$signed>() $(&& size_of::<$unsigned>() == size_of::<$float>())?); | ||
| impl RawBytesULE<{ size_of::<$unsigned>() }> { | ||
| #[doc = concat!("Gets this `RawBytesULE` as a `", stringify!($unsigned), "`. This is equivalent to calling [`AsULE::from_unaligned()`] on [`", stringify!($unsigned), "`].")] | ||
| #[inline] | ||
| pub fn as_unsigned_int(&self) -> $unsigned { | ||
| <$unsigned as $crate::ule::AsULE>::from_unaligned(*self) | ||
| pub const fn as_unsigned_int(&self) -> $unsigned { | ||
| <$unsigned>::from_le_bytes(self.0) | ||
| } | ||
| #[doc = concat!("Converts a `", stringify!($unsigned), "` to a `RawBytesULE`. This is equivalent to calling [`AsULE::to_unaligned()`] on the appropriately sized type.")] | ||
| #[doc = concat!("Gets this `RawBytesULE` as a `", stringify!($unsigned), "`. This is equivalent to calling [`AsULE::from_unaligned()`] on [`", stringify!($signed), "`].")] | ||
| #[inline] | ||
| pub const fn as_signed_int(&self) -> $signed { | ||
| <$signed>::from_le_bytes(self.0) | ||
| } | ||
| $( | ||
| #[doc = concat!("Gets this `RawBytesULE` as a `", stringify!($float), "`. This is equivalent to calling [`AsULE::from_unaligned()`] on [`", stringify!($float), "`].")] | ||
| #[inline] | ||
| pub const fn as_float(&self) -> $float { | ||
| <$float>::from_le_bytes(self.0) | ||
| } | ||
| )? | ||
| #[doc = concat!("Converts a `", stringify!($unsigned), "` to a `RawBytesULE`. This is equivalent to calling [`AsULE::to_unaligned()`] on [`", stringify!($unsigned), "`].")] | ||
| #[inline] | ||
| pub const fn from_aligned(value: $unsigned) -> Self { | ||
@@ -81,17 +97,36 @@ Self(value.to_le_bytes()) | ||
| $unsigned, | ||
| RawBytesULE<$size>, | ||
| RawBytesULE([0; $size]) | ||
| RawBytesULE<{ size_of::<$unsigned>() }>, | ||
| RawBytesULE([0; { size_of::<$unsigned>() }]) | ||
| ); | ||
| } | ||
| }; | ||
| impl_byte_slice_type!(from_unsigned, $unsigned); | ||
| impl_const_constructors!($unsigned); | ||
| impl_byte_slice_type!(from_signed, $signed); | ||
| impl_const_constructors!($signed); | ||
| $( | ||
| // These impls are actually safe and portable due to Rust always using IEEE 754, see the documentation | ||
| // on f32::from_le_bytes: https://doc.rust-lang.org/stable/std/primitive.f32.html#method.from_le_bytes | ||
| // | ||
| // The only potential problem is that some older platforms treat signaling NaNs differently. This is | ||
| // still quite portable, signalingness is not typically super important. | ||
| // The from_bits documentation mentions that they have identical byte representations to integers | ||
| // and EqULE only cares about LE systems | ||
| impl_byte_slice_type!(from_float, $float); | ||
| impl_const_constructors!($float); | ||
| )? | ||
| }; | ||
| } | ||
| macro_rules! impl_const_constructors { | ||
| ($base:ty, $size:literal) => { | ||
| ($base:ty) => { | ||
| impl ZeroSlice<$base> { | ||
| /// This function can be used for constructing ZeroVecs in a const context, avoiding | ||
| /// This function can be used for constructing [`ZeroVec`](crate::ZeroVec)s in a `const` context, avoiding | ||
| /// parsing checks. | ||
| /// | ||
| /// This cannot be generic over T because of current limitations in `const`, but if | ||
| /// this method is needed in a non-const context, check out [`ZeroSlice::parse_bytes()`] | ||
| /// This cannot be generic over `T` because of current limitations in `const`, but if | ||
| /// this method is needed in a non-`const` context, check out [`ZeroSlice::parse_bytes()`] | ||
| /// instead. | ||
@@ -102,8 +137,9 @@ /// | ||
| let len = bytes.len(); | ||
| const STRIDE: usize = size_of::<$base>(); | ||
| #[allow(clippy::modulo_one)] | ||
| if len % $size == 0 { | ||
| if (if STRIDE <= 1 { len } else { len % STRIDE }) == 0 { | ||
| Ok(unsafe { Self::from_bytes_unchecked(bytes) }) | ||
| } else { | ||
| Err(UleError::InvalidLength { | ||
| ty: concat!("<const construct: ", $size, ">"), | ||
| ty: concat!("<const construct: ", stringify!($base), ">"), | ||
| len, | ||
@@ -118,4 +154,4 @@ }) | ||
| macro_rules! impl_byte_slice_type { | ||
| ($single_fn:ident, $type:ty, $size:literal) => { | ||
| impl From<$type> for RawBytesULE<$size> { | ||
| ($single_fn:ident, $type:ty) => { | ||
| impl From<$type> for RawBytesULE<{ size_of::<$type>() }> { | ||
| #[inline] | ||
@@ -127,3 +163,3 @@ fn from(value: $type) -> Self { | ||
| impl AsULE for $type { | ||
| type ULE = RawBytesULE<$size>; | ||
| type ULE = RawBytesULE<{ size_of::<$type>() }>; | ||
| #[inline] | ||
@@ -138,7 +174,7 @@ fn to_unaligned(self) -> Self::ULE { | ||
| } | ||
| // EqULE is true because $type and RawBytesULE<$size> | ||
| // EqULE is true because $type and RawBytesULE<{ size_of::<$type> }> | ||
| // have the same byte sequence on little-endian | ||
| unsafe impl EqULE for $type {} | ||
| impl RawBytesULE<$size> { | ||
| impl RawBytesULE<{ size_of::<$type>() }> { | ||
| pub const fn $single_fn(v: $type) -> Self { | ||
@@ -151,40 +187,7 @@ RawBytesULE(v.to_le_bytes()) | ||
| macro_rules! impl_byte_slice_unsigned_type { | ||
| ($type:ty, $size:literal) => { | ||
| impl_byte_slice_type!(from_unsigned, $type, $size); | ||
| }; | ||
| } | ||
| impl_numbers_with_raw_bytes_ule!(u16, i16); | ||
| impl_numbers_with_raw_bytes_ule!(u32, i32, f32); | ||
| impl_numbers_with_raw_bytes_ule!(u64, i64, f64); | ||
| impl_numbers_with_raw_bytes_ule!(u128, i128); | ||
| macro_rules! impl_byte_slice_signed_type { | ||
| ($type:ty, $size:literal) => { | ||
| impl_byte_slice_type!(from_signed, $type, $size); | ||
| }; | ||
| } | ||
| impl_byte_slice_size!(u16, 2); | ||
| impl_byte_slice_size!(u32, 4); | ||
| impl_byte_slice_size!(u64, 8); | ||
| impl_byte_slice_size!(u128, 16); | ||
| impl_byte_slice_unsigned_type!(u16, 2); | ||
| impl_byte_slice_unsigned_type!(u32, 4); | ||
| impl_byte_slice_unsigned_type!(u64, 8); | ||
| impl_byte_slice_unsigned_type!(u128, 16); | ||
| impl_byte_slice_signed_type!(i16, 2); | ||
| impl_byte_slice_signed_type!(i32, 4); | ||
| impl_byte_slice_signed_type!(i64, 8); | ||
| impl_byte_slice_signed_type!(i128, 16); | ||
| impl_const_constructors!(u8, 1); | ||
| impl_const_constructors!(u16, 2); | ||
| impl_const_constructors!(u32, 4); | ||
| impl_const_constructors!(u64, 8); | ||
| impl_const_constructors!(u128, 16); | ||
| // Note: The f32 and f64 const constructors currently have limited use because | ||
| // `f32::to_le_bytes` is not yet const. | ||
| impl_const_constructors!(bool, 1); | ||
| // Safety (based on the safety checklist on the ULE trait): | ||
@@ -219,2 +222,4 @@ // 1. u8 does not include any uninitialized or padding bytes. | ||
| impl_const_constructors!(u8); | ||
| // Safety (based on the safety checklist on the ULE trait): | ||
@@ -291,4 +296,5 @@ // 1. NonZeroU8 does not include any uninitialized or padding bytes. | ||
| fn to_unaligned(self) -> Self::ULE { | ||
| // Safety: NonZeroU8 and NonZeroI8 have same size | ||
| unsafe { core::mem::transmute(self) } | ||
| // TODO: use cast_signed at 1.87 MSRV | ||
| // Safety: .get() is non-zero | ||
| unsafe { NonZeroU8::new_unchecked(self.get() as u8) } | ||
| } | ||
@@ -298,42 +304,8 @@ | ||
| fn from_unaligned(unaligned: Self::ULE) -> Self { | ||
| // Safety: NonZeroU8 and NonZeroI8 have same size | ||
| unsafe { core::mem::transmute(unaligned) } | ||
| // TODO: use cast_unsigned at 1.87 MSRV | ||
| // Safety: .get() is non-zero | ||
| unsafe { NonZeroI8::new_unchecked(unaligned.get() as i8) } | ||
| } | ||
| } | ||
| // These impls are actually safe and portable due to Rust always using IEEE 754, see the documentation | ||
| // on f32::from_bits: https://doc.rust-lang.org/stable/std/primitive.f32.html#method.from_bits | ||
| // | ||
| // The only potential problem is that some older platforms treat signaling NaNs differently. This is | ||
| // still quite portable, signalingness is not typically super important. | ||
| impl AsULE for f32 { | ||
| type ULE = RawBytesULE<4>; | ||
| #[inline] | ||
| fn to_unaligned(self) -> Self::ULE { | ||
| self.to_bits().to_unaligned() | ||
| } | ||
| #[inline] | ||
| fn from_unaligned(unaligned: Self::ULE) -> Self { | ||
| Self::from_bits(u32::from_unaligned(unaligned)) | ||
| } | ||
| } | ||
| impl AsULE for f64 { | ||
| type ULE = RawBytesULE<8>; | ||
| #[inline] | ||
| fn to_unaligned(self) -> Self::ULE { | ||
| self.to_bits().to_unaligned() | ||
| } | ||
| #[inline] | ||
| fn from_unaligned(unaligned: Self::ULE) -> Self { | ||
| Self::from_bits(u64::from_unaligned(unaligned)) | ||
| } | ||
| } | ||
| // The from_bits documentation mentions that they have identical byte representations to integers | ||
| // and EqULE only cares about LE systems | ||
| unsafe impl EqULE for f32 {} | ||
| unsafe impl EqULE for f64 {} | ||
| // The bool impl is not as efficient as it could be | ||
@@ -379,2 +351,4 @@ // We can, in the future, have https://github.com/unicode-org/icu4x/blob/main/utils/zerovec/design_doc.md#bitpacking | ||
| impl_const_constructors!(bool); | ||
| // Safety (based on the safety checklist on the ULE trait): | ||
@@ -412,1 +386,3 @@ // 1. () does not include any uninitialized or padding bytes (it has no bytes) | ||
| unsafe impl EqULE for () {} | ||
| impl_const_constructors!(()); |
@@ -63,3 +63,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Note: VarULE is well-defined for all `[T]` where `T: ULE`, but [`ZeroSlice`] is more ergonomic | ||
| /// Note: [`VarULE`] is well-defined for all `[T] where T: ULE`, but [`ZeroSlice`] is more ergonomic | ||
| /// when `T` is a low-level ULE type. For example: | ||
@@ -66,0 +66,0 @@ /// |
@@ -5,7 +5,7 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Take a VarULE type and serialize it both in human and machine readable contexts, | ||
| /// Take a `VarULE` type and serialize it both in human and machine readable contexts, | ||
| /// and ensure it roundtrips correctly | ||
| /// | ||
| /// Note that the concrete type may need to be explicitly specified to prevent issues with | ||
| /// https://github.com/rust-lang/rust/issues/130180 | ||
| /// <https://github.com/rust-lang/rust/issues/130180> | ||
| #[cfg(feature = "serde")] | ||
@@ -12,0 +12,0 @@ pub(crate) fn assert_serde_roundtrips<T>(var: &T) |
+4
-5
@@ -7,3 +7,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| //! | ||
| //! Rust does not guarantee the layout of tuples, so ZeroVec defines its own tuple ULE types. | ||
| //! Rust does not guarantee the layout of tuples, so [`ZeroVec`](crate::ZeroVec) defines its own tuple ULE types. | ||
| //! | ||
@@ -29,3 +29,2 @@ //! Impls are defined for tuples of up to 6 elements. For longer tuples, use a custom struct | ||
| use core::fmt; | ||
| use core::mem; | ||
@@ -51,4 +50,4 @@ macro_rules! tuple_ule { | ||
| fn validate_bytes(bytes: &[u8]) -> Result<(), UleError> { | ||
| // expands to: 0size + mem::size_of::<A>() + mem::size_of::<B>(); | ||
| let ule_bytes = 0usize $(+ mem::size_of::<$t>())+; | ||
| // expands to: 0size + size_of::<A>() + size_of::<B>(); | ||
| let ule_bytes = 0usize $(+ size_of::<$t>())+; | ||
| if bytes.len() % ule_bytes != 0 { | ||
@@ -61,3 +60,3 @@ return Err(UleError::length::<Self>(bytes.len())); | ||
| let j = i; | ||
| i += mem::size_of::<$t>(); | ||
| i += size_of::<$t>(); | ||
| #[expect(clippy::indexing_slicing)] // length checked | ||
@@ -64,0 +63,0 @@ <$t>::validate_bytes(&chunk[j..i])?; |
@@ -18,3 +18,2 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::marker::PhantomData; | ||
| use core::mem; | ||
| use zerofrom::ZeroFrom; | ||
@@ -93,3 +92,3 @@ | ||
| // Field invariant upheld here: validate_bytes above validates every field for being the right type | ||
| mem::transmute::<&MultiFieldsULE<$len, Format>, &Self>(multi) | ||
| &*(multi as *const MultiFieldsULE<$len, Format> as *const $name<$($T,)+ Format>) | ||
| } | ||
@@ -271,3 +270,3 @@ } | ||
| // Can't use inference due to https://github.com/rust-lang/rust/issues/130180 | ||
| crate::ule::test_utils::assert_serde_roundtrips::<Tuple2VarULE<str, [u8]>>(val); | ||
| test_utils::assert_serde_roundtrips::<Tuple2VarULE<str, [u8]>>(val); | ||
| } | ||
@@ -298,5 +297,5 @@ } | ||
| // Can't use inference due to https://github.com/rust-lang/rust/issues/130180 | ||
| crate::ule::test_utils::assert_serde_roundtrips::< | ||
| Tuple3VarULE<str, [u8], VarZeroSlice<str>, Format>, | ||
| >(val); | ||
| test_utils::assert_serde_roundtrips::<Tuple3VarULE<str, [u8], VarZeroSlice<str>, Format>>( | ||
| val, | ||
| ); | ||
| } | ||
@@ -303,0 +302,0 @@ } |
@@ -55,2 +55,5 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::{borrow::ToOwned, boxed::Box}; | ||
| use super::{AsULE, EncodeAsVarULE, UleError, VarULE, ULE}; | ||
@@ -115,3 +118,3 @@ | ||
| .split_at_checked(size_of::<A::ULE>()) | ||
| .ok_or(UleError::length::<Self>(bytes.len()))?; | ||
| .ok_or_else(|| UleError::length::<Self>(bytes.len()))?; | ||
| A::ULE::validate_bytes(sized_chunk)?; | ||
@@ -182,3 +185,3 @@ V::validate_bytes(variable_chunk)?; | ||
| #[cfg(feature = "alloc")] | ||
| impl<A, V> alloc::borrow::ToOwned for VarTupleULE<A, V> | ||
| impl<A, V> ToOwned for VarTupleULE<A, V> | ||
| where | ||
@@ -188,3 +191,3 @@ A: AsULE + 'static, | ||
| { | ||
| type Owned = alloc::boxed::Box<Self>; | ||
| type Owned = Box<Self>; | ||
| fn to_owned(&self) -> Self::Owned { | ||
@@ -256,3 +259,3 @@ crate::ule::encode_varule_to_box(self) | ||
| #[cfg(all(feature = "serde", feature = "alloc"))] | ||
| impl<'de, A, V> serde::Deserialize<'de> for alloc::boxed::Box<VarTupleULE<A, V>> | ||
| impl<'de, A, V> serde::Deserialize<'de> for Box<VarTupleULE<A, V>> | ||
| where | ||
@@ -262,3 +265,3 @@ A: AsULE + 'static, | ||
| A: serde::Deserialize<'de>, | ||
| alloc::boxed::Box<V>: serde::Deserialize<'de>, | ||
| Box<V>: serde::Deserialize<'de>, | ||
| { | ||
@@ -270,3 +273,3 @@ fn deserialize<Des>(deserializer: Des) -> Result<Self, Des::Error> | ||
| if deserializer.is_human_readable() { | ||
| let this = VarTuple::<A, alloc::boxed::Box<V>>::deserialize(deserializer)?; | ||
| let this = VarTuple::<A, Box<V>>::deserialize(deserializer)?; | ||
| Ok(crate::ule::encode_varule_to_box(&this)) | ||
@@ -273,0 +276,0 @@ } else { |
@@ -5,2 +5,4 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| #![allow(unused_qualifications)] | ||
| use super::VarZeroVecFormatError; | ||
@@ -11,7 +13,6 @@ use crate::ule::*; | ||
| use core::marker::PhantomData; | ||
| use core::mem; | ||
| use core::ops::Range; | ||
| /// This trait allows switching between different possible internal | ||
| /// representations of VarZeroVec. | ||
| /// representations of [`VarZeroVec`](super::VarZeroVec). | ||
| /// | ||
@@ -113,3 +114,3 @@ /// Currently this crate supports three formats: [`Index8`], [`Index16`] and [`Index32`], | ||
| cumulatively are larger than a u8 in size"; | ||
| const SIZE: usize = mem::size_of::<Self>(); | ||
| const SIZE: usize = size_of::<Self>(); | ||
| const MAX_VALUE: u32 = u8::MAX as u32; | ||
@@ -134,3 +135,3 @@ #[inline] | ||
| cumulatively are larger than a u16 in size"; | ||
| const SIZE: usize = mem::size_of::<Self>(); | ||
| const SIZE: usize = size_of::<Self>(); | ||
| const MAX_VALUE: u32 = u16::MAX as u32; | ||
@@ -155,3 +156,3 @@ #[inline] | ||
| cumulatively are larger than a u32 in size"; | ||
| const SIZE: usize = mem::size_of::<Self>(); | ||
| const SIZE: usize = size_of::<Self>(); | ||
| const MAX_VALUE: u32 = u32::MAX; | ||
@@ -173,3 +174,3 @@ #[inline] | ||
| /// A more parsed version of `VarZeroSlice`. This type is where most of the VarZeroVec | ||
| /// A more parsed version of [`VarZeroSlice`](super::VarZeroSlice). This type is where most of the[ `VarZeroVec`](super::VarZeroVec) | ||
| /// internal representation code lies. | ||
@@ -223,3 +224,3 @@ /// | ||
| impl<'a, T: VarULE + ?Sized, F: VarZeroVecFormat> VarZeroVecComponents<'a, T, F> { | ||
| /// Construct a new VarZeroVecComponents, checking invariants about the overall buffer size: | ||
| /// Construct a new [`VarZeroVecComponents`], checking invariants about the overall buffer size: | ||
| /// | ||
@@ -264,3 +265,3 @@ /// - There must be either zero or at least four bytes (if four, this is the "length" parsed as a usize) | ||
| /// Construct a new VarZeroVecComponents, checking invariants about the overall buffer size: | ||
| /// Construct a new [`VarZeroVecComponents`], checking invariants about the overall buffer size: | ||
| /// | ||
@@ -431,3 +432,3 @@ /// - There must be at least `4*len` bytes total, to form the array `indices` of indices. | ||
| /// Check the internal invariants of VarZeroVecComponents: | ||
| /// Check the internal invariants of [`VarZeroVecComponents`]: | ||
| /// | ||
@@ -440,4 +441,4 @@ /// - `indices[i]..indices[i+1]` must index into a valid section of | ||
| /// | ||
| /// This method is NOT allowed to call any other methods on VarZeroVecComponents since all other methods | ||
| /// assume that the slice has been passed through check_indices_and_things | ||
| /// This method is NOT allowed to call any other methods on [`VarZeroVecComponents`] since all other methods | ||
| /// assume that the slice has been passed through [`Self::check_indices_and_things`] | ||
| #[inline] | ||
@@ -484,3 +485,3 @@ #[expect(clippy::len_zero)] // more explicit to enforce safety invariants | ||
| /// Create an iterator over the Ts contained in VarZeroVecComponents | ||
| /// Create an iterator over the Ts contained in [`VarZeroVecComponents`] | ||
| #[inline] | ||
@@ -515,3 +516,3 @@ pub fn iter(self) -> VarZeroSliceIter<'a, T, F> { | ||
| /// An iterator over VarZeroSlice | ||
| /// An iterator over [`VarZeroSlice`](super::VarZeroSlice) | ||
| #[derive(Debug)] | ||
@@ -528,2 +529,12 @@ pub struct VarZeroSliceIter<'a, T: ?Sized, F = Index16> { | ||
| impl<'a, T: VarULE + ?Sized, F: VarZeroVecFormat> Clone for VarZeroSliceIter<'a, T, F> { | ||
| fn clone(&self) -> Self { | ||
| Self { | ||
| components: self.components, | ||
| index: self.index, | ||
| start_index: self.start_index, | ||
| } | ||
| } | ||
| } | ||
| impl<'a, T: VarULE + ?Sized, F: VarZeroVecFormat> VarZeroSliceIter<'a, T, F> { | ||
@@ -693,3 +704,3 @@ fn new(c: VarZeroVecComponents<'a, T, F>) -> Self { | ||
| /// Collects the bytes for a VarZeroSlice into a Vec. | ||
| /// Collects the bytes for a [`VarZeroSlice`](super::VarZeroSlice) into a [`Vec`]. | ||
| #[cfg(feature = "alloc")] | ||
@@ -713,4 +724,4 @@ pub fn get_serializable_bytes_non_empty<T, A, F>(elements: &[A]) -> Option<alloc::vec::Vec<u8>> | ||
| /// Writes the bytes for a VarZeroLengthlessSlice into an output buffer. | ||
| /// Usable for a VarZeroSlice if you first write the length bytes. | ||
| /// Writes the bytes for a [`VarZeroLengthlessSlice`](super::lenghtless::VarZeroLengthlessSlice) into an output buffer. | ||
| /// Usable for a [`VarZeroSlice`](super::VarZeroSlice) if you first write the length bytes. | ||
| /// | ||
@@ -770,3 +781,3 @@ /// Every byte in the buffer will be initialized after calling this function. | ||
| /// Writes the bytes for a VarZeroSlice into an output buffer. | ||
| /// Writes the bytes for a [`VarZeroSlice`](super::VarZeroSlice) into an output buffer. | ||
| /// | ||
@@ -773,0 +784,0 @@ /// Every byte in the buffer will be initialized after calling this function. |
@@ -15,3 +15,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a VarZeroVec via as_bytes() above, | ||
@@ -30,3 +30,3 @@ // and thus is valid for unchecked construction. | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a VarZeroVec via as_bytes() above, | ||
@@ -57,3 +57,3 @@ // and thus is valid for unchecked construction. | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a VarZeroSlice via as_bytes() above, | ||
@@ -72,3 +72,3 @@ // and thus is valid for unchecked construction. | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a VarZeroSlice via as_bytes() above, | ||
@@ -75,0 +75,0 @@ // and thus is valid for unchecked construction. |
@@ -9,3 +9,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| pub enum VarZeroVecFormatError { | ||
| /// The byte buffer was not in the appropriate format for VarZeroVec. | ||
| /// The byte buffer was not in the appropriate format for [`VarZeroVec`](crate::VarZeroVec). | ||
| Metadata, | ||
@@ -12,0 +12,0 @@ /// One of the values could not be decoded. |
@@ -9,5 +9,4 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::marker::PhantomData; | ||
| use core::mem; | ||
| /// A slice representing the index and data tables of a VarZeroVec, | ||
| /// A slice representing the index and data tables of a [`VarZeroVec`], | ||
| /// *without* any length fields. The length field is expected to be stored elsewhere. | ||
@@ -39,3 +38,3 @@ /// | ||
| /// Parse a VarZeroLengthlessSlice from a slice of the appropriate format | ||
| /// Parse a [`VarZeroLengthlessSlice`] from a slice of the appropriate format | ||
| /// | ||
@@ -62,3 +61,3 @@ /// Slices of the right format can be obtained via [`VarZeroSlice::as_bytes()`] | ||
| // self is really just a wrapper around a byte slice | ||
| mem::transmute(bytes) | ||
| &*(bytes as *const [u8] as *const Self) | ||
| } | ||
@@ -76,3 +75,3 @@ | ||
| // self is really just a wrapper around a byte slice | ||
| mem::transmute(bytes) | ||
| &mut *(bytes as *mut [u8] as *mut VarZeroLengthlessSlice<T, F>) | ||
| } | ||
@@ -85,3 +84,3 @@ | ||
| /// `index` must be in range, and `len` must be the length associated with this | ||
| /// instance of VarZeroLengthlessSlice. | ||
| /// instance of [`VarZeroLengthlessSlice`]. | ||
| pub(crate) unsafe fn get_unchecked(&self, len: u32, idx: usize) -> &T { | ||
@@ -105,3 +104,3 @@ self.as_components(len).get_unchecked(idx) | ||
| /// | ||
| /// - `len` is the length associated with this VarZeroLengthlessSlice | ||
| /// - `len` is the length associated with this [`VarZeroLengthlessSlice`] | ||
| /// - The resultant slice is only mutated in a way such that it remains a valid `T` | ||
@@ -108,0 +107,0 @@ /// |
@@ -64,3 +64,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| impl<T: VarULE + ?Sized, F> VarZeroVecOwned<T, F> { | ||
| /// Construct an empty VarZeroVecOwned | ||
| /// Construct an empty [`VarZeroVecOwned`] | ||
| pub fn new() -> Self { | ||
@@ -76,3 +76,3 @@ Self { | ||
| impl<T: VarULE + ?Sized, F: VarZeroVecFormat> VarZeroVecOwned<T, F> { | ||
| /// Construct a VarZeroVecOwned from a [`VarZeroSlice`] by cloning the internal data | ||
| /// Construct a [`VarZeroVecOwned`] from a [`VarZeroSlice`] by cloning the internal data | ||
| pub fn from_slice(slice: &VarZeroSlice<T, F>) -> Self { | ||
@@ -86,3 +86,3 @@ Self { | ||
| /// Construct a VarZeroVecOwned from a list of elements | ||
| /// Construct a [`VarZeroVecOwned`] from a list of elements | ||
| pub fn try_from_elements<A>(elements: &[A]) -> Result<Self, &'static str> | ||
@@ -155,3 +155,3 @@ where | ||
| /// `idx < self.len()` and `self.as_encoded_bytes()` is well-formed. | ||
| unsafe fn element_range_unchecked(&self, idx: usize) -> core::ops::Range<usize> { | ||
| unsafe fn element_range_unchecked(&self, idx: usize) -> Range<usize> { | ||
| let start = self.element_position_unchecked(idx); | ||
@@ -187,3 +187,3 @@ let end = self.element_position_unchecked(idx + 1); | ||
| /// ## Safety | ||
| /// The index must be valid, and self.as_encoded_bytes() must be well-formed | ||
| /// The index must be valid, and `self.as_encoded_bytes()` must be well-formed | ||
| unsafe fn index_data(&self, index: usize) -> Option<&F::Index> { | ||
@@ -197,3 +197,3 @@ let index_range = Self::index_range(index)?; | ||
| /// ## Safety | ||
| /// The index must be valid. self.as_encoded_bytes() must have allocated space | ||
| /// The index must be valid. `self.as_encoded_bytes()` must have allocated space | ||
| /// for this index, but need not have its length appropriately set. | ||
@@ -200,0 +200,0 @@ unsafe fn index_data_mut(&mut self, index: usize) -> Option<&mut F::Index> { |
+12
-10
@@ -12,3 +12,2 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use core::marker::PhantomData; | ||
| use core::mem; | ||
@@ -18,2 +17,5 @@ use core::ops::Index; | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::{boxed::Box, vec::Vec}; | ||
| /// A zero-copy "slice", that works for unsized types, i.e. the zero-copy version of `[T]` | ||
@@ -83,3 +85,3 @@ /// where `T` is not `Sized`. | ||
| /// Although [`VarZeroSlice`] does not itself have a `.windows` iterator like | ||
| /// [core::slice::Windows], this behavior can be easily modeled using an iterator: | ||
| /// [`core::slice::Windows`], this behavior can be easily modeled using an iterator: | ||
| /// | ||
@@ -110,6 +112,6 @@ /// ``` | ||
| impl<T: VarULE + ?Sized, F: VarZeroVecFormat> VarZeroSlice<T, F> { | ||
| /// Construct a new empty VarZeroSlice | ||
| /// Construct a new empty [`VarZeroSlice`] | ||
| pub const fn new_empty() -> &'static Self { | ||
| // The empty VZV is special-cased to the empty slice | ||
| unsafe { mem::transmute(&[] as &[u8]) } | ||
| unsafe { &*(&[] as *const [u8] as *const Self) } | ||
| } | ||
@@ -133,3 +135,3 @@ | ||
| // self is really just a wrapper around a byte slice | ||
| mem::transmute(bytes) | ||
| &*(bytes as *const [u8] as *const Self) | ||
| } | ||
@@ -240,3 +242,3 @@ | ||
| #[cfg(feature = "alloc")] | ||
| pub fn to_vec(&self) -> alloc::vec::Vec<alloc::boxed::Box<T>> { | ||
| pub fn to_vec(&self) -> Vec<Box<T>> { | ||
| self.as_components().to_vec() | ||
@@ -274,3 +276,3 @@ } | ||
| /// Parse a VarZeroSlice from a slice of the appropriate format | ||
| /// Parse a [`VarZeroSlice`] from a slice of the appropriate format | ||
| /// | ||
@@ -453,4 +455,4 @@ /// Slices of the right format can be obtained via [`VarZeroSlice::as_bytes()`] | ||
| fn validate_bytes(bytes: &[u8]) -> Result<(), UleError> { | ||
| let _: VarZeroVecComponents<T, F> = | ||
| VarZeroVecComponents::parse_bytes(bytes).map_err(|_| UleError::parse::<Self>())?; | ||
| let _ = VarZeroVecComponents::<T, F>::parse_bytes(bytes) | ||
| .map_err(|_| UleError::parse::<Self>())?; | ||
| Ok(()) | ||
@@ -461,3 +463,3 @@ } | ||
| // self is really just a wrapper around a byte slice | ||
| mem::transmute(bytes) | ||
| &*(bytes as *const [u8] as *const Self) | ||
| } | ||
@@ -464,0 +466,0 @@ |
@@ -12,2 +12,4 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use super::*; | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::vec::Vec; | ||
@@ -226,3 +228,3 @@ /// A zero-copy, byte-aligned vector for variable-width types. | ||
| /// Parse a VarZeroVec from a slice of the appropriate format | ||
| /// Parse a [`VarZeroVec`] from a slice of the appropriate format | ||
| /// | ||
@@ -299,3 +301,3 @@ /// Slices of the right format can be obtained via [`VarZeroSlice::as_bytes()`]. | ||
| /// Converts a borrowed ZeroVec to an owned ZeroVec. No-op if already owned. | ||
| /// Converts a borrowed [`VarZeroVec`] to an owned [`VarZeroVec`]. No-op if already owned. | ||
| /// | ||
@@ -325,3 +327,3 @@ /// ✨ *Enabled with the `alloc` Cargo feature.* | ||
| /// Obtain this `VarZeroVec` as a [`VarZeroSlice`] | ||
| /// Obtain this [`VarZeroVec`] as a [`VarZeroSlice`] | ||
| pub fn as_slice(&self) -> &VarZeroSlice<T, F> { | ||
@@ -335,3 +337,3 @@ match self.0 { | ||
| /// Takes the byte vector representing the encoded data of this VarZeroVec. If borrowed, | ||
| /// Takes the byte vector representing the encoded data of this [`VarZeroVec`]. If borrowed, | ||
| /// this function allocates a byte vector and copies the borrowed bytes into it. | ||
@@ -358,3 +360,3 @@ /// | ||
| #[cfg(feature = "alloc")] | ||
| pub fn into_bytes(self) -> alloc::vec::Vec<u8> { | ||
| pub fn into_bytes(self) -> Vec<u8> { | ||
| match self.0 { | ||
@@ -384,3 +386,3 @@ VarZeroVecInner::Owned(vec) => vec.into_bytes(), | ||
| #[cfg(feature = "alloc")] | ||
| impl<A, T, F> From<&alloc::vec::Vec<A>> for VarZeroVec<'static, T, F> | ||
| impl<A, T, F> From<&Vec<A>> for VarZeroVec<'static, T, F> | ||
| where | ||
@@ -392,3 +394,3 @@ T: VarULE + ?Sized, | ||
| #[inline] | ||
| fn from(elements: &alloc::vec::Vec<A>) -> Self { | ||
| fn from(elements: &Vec<A>) -> Self { | ||
| Self::from(elements.as_slice()) | ||
@@ -395,0 +397,0 @@ } |
+11
-11
@@ -39,3 +39,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -68,3 +68,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -97,3 +97,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -133,3 +133,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| fn transform_owned(self) -> Self::Output { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| unsafe { | ||
@@ -145,3 +145,3 @@ // Similar problem as transform(), but we need to use ptr::read since | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -181,3 +181,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| fn transform_owned(self) -> Self::Output { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| unsafe { | ||
@@ -193,3 +193,3 @@ // Similar problem as transform(), but we need to use ptr::read since | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -231,3 +231,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| fn transform_owned(self) -> Self::Output { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| unsafe { | ||
@@ -243,3 +243,3 @@ // Similar problem as transform(), but we need to use ptr::read since | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -281,3 +281,3 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); | ||
| fn transform_owned(self) -> Self::Output { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| unsafe { | ||
@@ -293,3 +293,3 @@ // Similar problem as transform(), but we need to use ptr::read since | ||
| unsafe fn make(from: Self::Output) -> Self { | ||
| debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>()); | ||
| debug_assert!(size_of::<Self::Output>() == size_of::<Self>()); | ||
| let from = mem::ManuallyDrop::new(from); | ||
@@ -296,0 +296,0 @@ let ptr: *const Self = (&*from as *const Self::Output).cast(); |
@@ -15,3 +15,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a ZeroVec via as_bytes() above, | ||
@@ -36,3 +36,3 @@ // and thus is valid for unchecked construction. | ||
| } else { | ||
| let bytes = databake::Bake::bake(&self.as_bytes(), env); | ||
| let bytes = Bake::bake(&self.as_bytes(), env); | ||
| // Safety: bytes was obtained from a ZeroSlice via as_bytes() above, | ||
@@ -39,0 +39,0 @@ // and thus is valid for unchecked construction. |
+27
-27
@@ -332,3 +332,3 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| /// Creates a new owned `ZeroVec` using an existing | ||
| /// Creates a new owned [`ZeroVec`] using an existing | ||
| /// allocated backing buffer | ||
@@ -361,3 +361,3 @@ /// | ||
| /// Creates a new borrowed `ZeroVec` using an existing | ||
| /// Creates a new borrowed [`ZeroVec`] using an existing | ||
| /// backing buffer | ||
@@ -395,3 +395,3 @@ /// | ||
| /// | ||
| /// The bytes within the byte buffer must remain constant for the life of the ZeroVec. | ||
| /// The bytes within the byte buffer must remain constant for the life of the [`ZeroVec`]. | ||
| /// | ||
@@ -429,3 +429,3 @@ /// # Endianness | ||
| bytes.as_ptr() as *const T::ULE, | ||
| bytes.len() / core::mem::size_of::<T::ULE>(), | ||
| bytes.len() / size_of::<T::ULE>(), | ||
| )) | ||
@@ -436,3 +436,3 @@ } | ||
| /// | ||
| /// Note that the length of the ZeroVec may change. | ||
| /// Note that the length of the [`ZeroVec`] may change. | ||
| /// | ||
@@ -443,3 +443,3 @@ /// ✨ *Enabled with the `alloc` Cargo feature.* | ||
| /// | ||
| /// Convert a borrowed `ZeroVec`: | ||
| /// Convert a borrowed [`ZeroVec`]: | ||
| /// | ||
@@ -458,3 +458,3 @@ /// ``` | ||
| /// | ||
| /// Convert an owned `ZeroVec`: | ||
| /// Convert an owned [`ZeroVec`]: | ||
| /// | ||
@@ -542,3 +542,3 @@ /// ``` | ||
| /// | ||
| /// Convert a borrowed `ZeroVec`: | ||
| /// Convert a borrowed [`ZeroVec`]: | ||
| /// | ||
@@ -558,3 +558,3 @@ /// ``` | ||
| /// | ||
| /// Convert an owned `ZeroVec`: | ||
| /// Convert an owned [`ZeroVec`]: | ||
| /// | ||
@@ -582,3 +582,3 @@ /// ``` | ||
| /// | ||
| /// // Panics! core::mem::size_of::<char::ULE> != core::mem::size_of::<u16::ULE> | ||
| /// // Panics! size_of::<char::ULE> != size_of::<u16::ULE> | ||
| /// zv_char.try_into_converted::<u16>(); | ||
@@ -604,4 +604,4 @@ /// ``` | ||
| assert_eq!( | ||
| core::mem::size_of::<<T as AsULE>::ULE>(), | ||
| core::mem::size_of::<<P as AsULE>::ULE>() | ||
| size_of::<<T as AsULE>::ULE>(), | ||
| size_of::<<P as AsULE>::ULE>() | ||
| ); | ||
@@ -664,5 +664,5 @@ match self.into_cow() { | ||
| /// If the ZeroVec is owned, returns the capacity of the vector. | ||
| /// If the [`ZeroVec`] is owned, returns the capacity of the vector. | ||
| /// | ||
| /// Otherwise, if the ZeroVec is borrowed, returns `None`. | ||
| /// Otherwise, if the [`ZeroVec`] is borrowed, returns `None`. | ||
| /// | ||
@@ -700,3 +700,3 @@ /// # Examples | ||
| /// | ||
| /// Note that the length of the ZeroVec may change. | ||
| /// Note that the length of the [`ZeroVec`] may change. | ||
| /// | ||
@@ -707,3 +707,3 @@ /// ✨ *Enabled with the `alloc` Cargo feature.* | ||
| /// | ||
| /// Convert a borrowed `ZeroVec`: | ||
| /// Convert a borrowed [`ZeroVec`]: | ||
| /// | ||
@@ -721,3 +721,3 @@ /// ``` | ||
| /// | ||
| /// Convert an owned `ZeroVec`: | ||
| /// Convert an owned [`ZeroVec`]: | ||
| /// | ||
@@ -864,3 +864,3 @@ /// ``` | ||
| /// | ||
| /// This will convert the ZeroVec into an owned ZeroVec if not already the case. | ||
| /// This will convert the [`ZeroVec`] into an owned [`ZeroVec`] if not already the case. | ||
| /// | ||
@@ -929,3 +929,3 @@ /// ✨ *Enabled with the `alloc` Cargo feature.* | ||
| /// Converts a borrowed ZeroVec to an owned ZeroVec. No-op if already owned. | ||
| /// Converts a borrowed [`ZeroVec`] to an owned [`ZeroVec`]. No-op if already owned. | ||
| /// | ||
@@ -956,3 +956,3 @@ /// ✨ *Enabled with the `alloc` Cargo feature.* | ||
| /// Allows the ZeroVec to be mutated by converting it to an owned variant, and producing | ||
| /// Allows the [`ZeroVec`] to be mutated by converting it to an owned variant, and producing | ||
| /// a mutable vector of ULEs. If you only need a mutable slice, consider using [`Self::to_mut_slice()`] | ||
@@ -978,3 +978,3 @@ /// instead. | ||
| #[cfg(feature = "alloc")] | ||
| pub fn with_mut<R>(&mut self, f: impl FnOnce(&mut alloc::vec::Vec<T::ULE>) -> R) -> R { | ||
| pub fn with_mut<R>(&mut self, f: impl FnOnce(&mut Vec<T::ULE>) -> R) -> R { | ||
| use alloc::borrow::Cow; | ||
@@ -993,3 +993,3 @@ // We're in danger if f() panics whilst we've moved a vector out of self; | ||
| /// Allows the ZeroVec to be mutated by converting it to an owned variant (if necessary) | ||
| /// Allows the [`ZeroVec`] to be mutated by converting it to an owned variant (if necessary) | ||
| /// and returning a slice to its backing buffer. [`Self::with_mut()`] allows for mutation | ||
@@ -1024,3 +1024,3 @@ /// of the vector itself. | ||
| } | ||
| /// Remove all elements from this ZeroVec and reset it to an empty borrowed state. | ||
| /// Remove all elements from this [`ZeroVec`] and reset it to an empty borrowed state. | ||
| pub fn clear(&mut self) { | ||
@@ -1030,3 +1030,3 @@ *self = Self::new_borrowed(&[]) | ||
| /// Removes the first element of the ZeroVec. The ZeroVec remains in the same | ||
| /// Removes the first element of the [`ZeroVec`]. The [`ZeroVec`] remains in the same | ||
| /// borrowed or owned state. | ||
@@ -1078,3 +1078,3 @@ /// | ||
| /// Removes the last element of the ZeroVec. The ZeroVec remains in the same | ||
| /// Removes the last element of the [`ZeroVec`]. The [`ZeroVec`] remains in the same | ||
| /// borrowed or owned state. | ||
@@ -1172,3 +1172,3 @@ /// | ||
| /// * `$convert` - A const function that converts an `$aligned` into its unaligned equivalent, e.g., | ||
| /// const fn from_aligned(a: CanonicalType) -> CanonicalType::ULE`. | ||
| /// `const fn from_aligned(a: CanonicalType) -> CanonicalType::ULE`. | ||
| /// * `$x` - The elements that the `ZeroSlice` will hold. | ||
@@ -1213,3 +1213,3 @@ /// | ||
| /// Creates a borrowed `ZeroVec`. Convenience wrapper for `zeroslice!(...).as_zerovec()`. The value | ||
| /// Creates a borrowed [`ZeroVec`]. Convenience wrapper for `zeroslice!(...).as_zerovec()`. The value | ||
| /// will be created at compile-time, meaning that all arguments must also be constant. | ||
@@ -1216,0 +1216,0 @@ /// |
+14
-10
@@ -7,5 +7,9 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use crate::ule::*; | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::{boxed::Box, vec::Vec}; | ||
| use core::fmt; | ||
| use core::marker::PhantomData; | ||
| use serde::de::{self, Deserialize, Deserializer, Visitor}; | ||
| #[cfg(feature = "alloc")] | ||
| use serde::de::SeqAccess; | ||
| use serde::de::{Deserialize, Deserializer, Error, Visitor}; | ||
| #[cfg(feature = "serde")] | ||
@@ -38,5 +42,5 @@ use serde::ser::{Serialize, SerializeSeq, Serializer}; | ||
| where | ||
| E: de::Error, | ||
| E: Error, | ||
| { | ||
| ZeroVec::parse_bytes(bytes).map_err(de::Error::custom) | ||
| ZeroVec::parse_bytes(bytes).map_err(Error::custom) | ||
| } | ||
@@ -47,8 +51,8 @@ | ||
| where | ||
| A: serde::de::SeqAccess<'de>, | ||
| A: SeqAccess<'de>, | ||
| { | ||
| let mut vec: alloc::vec::Vec<T::ULE> = if let Some(capacity) = seq.size_hint() { | ||
| alloc::vec::Vec::with_capacity(capacity) | ||
| let mut vec: Vec<T::ULE> = if let Some(capacity) = seq.size_hint() { | ||
| Vec::with_capacity(capacity) | ||
| } else { | ||
| alloc::vec::Vec::new() | ||
| Vec::new() | ||
| }; | ||
@@ -104,3 +108,3 @@ while let Some(value) = seq.next_element::<T>()? { | ||
| #[cfg(feature = "alloc")] | ||
| impl<'de, T> Deserialize<'de> for alloc::boxed::Box<ZeroSlice<T>> | ||
| impl<'de, T> Deserialize<'de> for Box<ZeroSlice<T>> | ||
| where | ||
@@ -130,3 +134,3 @@ T: Deserialize<'de> + AsULE + 'static, | ||
| if deserializer.is_human_readable() { | ||
| Err(de::Error::custom( | ||
| Err(Error::custom( | ||
| "&ZeroSlice cannot be deserialized from human-readable formats", | ||
@@ -139,3 +143,3 @@ )) | ||
| } else { | ||
| return Err(de::Error::custom( | ||
| return Err(Error::custom( | ||
| "&ZeroSlice can only deserialize in zero-copy ways", | ||
@@ -142,0 +146,0 @@ )); |
+11
-9
@@ -6,2 +6,4 @@ // This file is part of ICU4X. For terms of use, please see the file | ||
| use super::*; | ||
| #[cfg(feature = "alloc")] | ||
| use alloc::boxed::Box; | ||
| use core::cmp::Ordering; | ||
@@ -23,3 +25,3 @@ use core::ops::Range; | ||
| /// | ||
| /// Const-construct a ZeroSlice of u16: | ||
| /// Const-construct a [`ZeroSlice`] of u16: | ||
| /// | ||
@@ -73,3 +75,3 @@ /// ``` | ||
| bytes.as_ptr() as *const T::ULE, | ||
| bytes.len() / core::mem::size_of::<T::ULE>(), | ||
| bytes.len() / size_of::<T::ULE>(), | ||
| )) | ||
@@ -80,3 +82,3 @@ } | ||
| /// | ||
| /// This function can be used for constructing ZeroVecs in a const context, avoiding | ||
| /// This function can be used for constructing [`ZeroVec`]s in a const context, avoiding | ||
| /// parsing checks. | ||
@@ -97,6 +99,6 @@ /// | ||
| #[cfg(feature = "alloc")] | ||
| pub fn from_boxed_slice(slice: alloc::boxed::Box<[T::ULE]>) -> alloc::boxed::Box<Self> { | ||
| pub fn from_boxed_slice(slice: Box<[T::ULE]>) -> Box<Self> { | ||
| // This is safe because ZeroSlice is transparent over [T::ULE] | ||
| // so Box<ZeroSlice<T>> can be safely cast from Box<[T::ULE]> | ||
| unsafe { alloc::boxed::Box::from_raw(alloc::boxed::Box::into_raw(slice) as *mut Self) } | ||
| unsafe { Box::from_raw(Box::into_raw(slice) as *mut Self) } | ||
| } | ||
@@ -147,3 +149,3 @@ | ||
| /// bytes.len(), | ||
| /// zerovec.len() * std::mem::size_of::<<u16 as AsULE>::ULE>() | ||
| /// zerovec.len() * size_of::<<u16 as AsULE>::ULE>() | ||
| /// ); | ||
@@ -225,3 +227,3 @@ /// ``` | ||
| /// Gets a subslice of elements within a certain range. Returns `None` if the range | ||
| /// is out of bounds of this `ZeroSlice`. | ||
| /// is out of bounds of this [`ZeroSlice`]. | ||
| /// | ||
@@ -413,3 +415,3 @@ /// # Example | ||
| /// An iterator over elements in a VarZeroVec | ||
| /// An iterator over elements in a [`ZeroSlice`] | ||
| #[derive(Debug)] | ||
@@ -585,3 +587,3 @@ pub struct ZeroSliceIter<'a, T: AsULE>(core::slice::Iter<'a, T::ULE>); | ||
| #[cfg(feature = "alloc")] | ||
| impl<T: AsULE> AsRef<ZeroSlice<T>> for alloc::vec::Vec<T::ULE> { | ||
| impl<T: AsULE> AsRef<ZeroSlice<T>> for Vec<T::ULE> { | ||
| fn as_ref(&self) -> &ZeroSlice<T> { | ||
@@ -588,0 +590,0 @@ ZeroSlice::<T>::from_ule_slice(self) |
Sorry, the diff of this file is not supported yet