Add support for 128-bit integers.#63
Merged
Merged
Conversation
Adds `u128` and `i128` encoding and decoding, including `Encode`, `Decode`, `CborLen`, `NonZeroU128`, and `NonZeroI128` impls. Values within the CBOR integer range are encoded as native unsigned/signed ints; values outside are encoded as positive or negative bignums (tags 2 and 3) per RFC 8949 §3.4.3. Signed-off-by: Stan Bondi <sdbondi@users.noreply.github.com>
Wires `Serializer::serialize_u128`/`serialize_i128` and the matching `Deserializer::deserialize_u128`/`deserialize_i128` through to the new `Encoder`/`Decoder` methods. Extends `deserialize_any` to recognise the positive (tag 2) and negative (tag 3) bignum encodings and route them to `visit_u128`/`visit_i128`; CBOR integers wider than `i64` (`Type::Int`) are likewise routed to `visit_i128`. Note that serde's `Content` buffer used by untagged enums only stores values up to 64 bits, so bignum dispatch through `deserialize_any` is only observable to visitors that implement `visit_u128`/`visit_i128` themselves. Signed-off-by: Stan Bondi <sdbondi@users.noreply.github.com>
sdbondi
added a commit
to sdbondi/tari-ootle
that referenced
this pull request
May 19, 2026
…nicbor-serde minicbor-serde 0.6.2 doesn't implement serialize_u128/serialize_i128 (upstream PR twittner/minicbor#63 is in flight), which left foreign types like tari_sidechain::ShardGroupAccumulatedData::total_exhaust_burn unencodable through serde_bridge. Vendor a fork into tari_bor::serde_codec that adds: - serialize_u128 / serialize_i128 via RFC 8949 §3.4.3 bignum tags (2 / 3) + bstr of positive-magnitude bytes with leading zeros stripped, plus matching decoder paths that also accept the plain integer encoding for values that fit in u64. - deserialize_seq fallback that surfaces a CBOR byte string as a Vec<u8>-shaped sequence (single-byte SeqAccess), so foreign types using `#[serde(with = "hex_or_bytes")]` like tari_sidechain::SidechainBlockHeader round-trip via Vec<u8> / Cow<'_, [u8]> without re-implementing their serde impls. - collect_indef_bytes helper that pre-sizes the destination buffer for indefinite-length CBOR byte strings. All 58 consensus_tests now run (they were previously hanging in a "u128 is not supported" loop on the foreign sidechain proof). Companion changes: - tari_bor::adapters::u128_codec: a dedicated tag-2 positive-bignum adapter for direct u128 fields we control. consensus_types::ShardGroupAccumulatedData switched off serde_bridge to use it. - tari_bor::cbor! macro: $v:expr arms now route through a new helper that calls tari_bor::to_value, so any Encode<()> type drops in directly without callers having to wrap it. Primitive behaviour preserved via encode/decode round-trip identity. - engine/benches/common/mod.rs: bench component body uses the positional [FAUCET_VAULT_ID] shape matching the template struct's minicbor array encoding (not the old string-keyed map). - Two clippy fixes in tari_bor / engine_types (drop &Box<[T]> in the boxed_slice adapter and 14 redundant .map_err(BorError::from) calls in indexed_value where Value::decoded() already returns BorError). Workspace cleanup: - All direct minicbor-serde callers — state_store_rocksdb::SerdeBridgeCodec, p2p::conversions::rpc, ootle_serde tests, applications/tari_indexer storage_sqlite serialization, ootle_address tests — routed through tari_bor::serde_codec. - minicbor-serde dropped from workspace dependencies. Version bumps (workspace + 16 self-versioned crates): - workspace.package.version 0.30.12 → 0.31.0 - tari_bor 0.13 → 0.14, ootle_byte_type 0.7 → 0.8, ootle_serde 0.2 → 0.3, ootle-network 0.1 → 0.2, tari_ootle_address 0.5 → 0.6, tari_template_abi 0.16 → 0.17, tari_template_macros 0.19 → 0.20, tari_template_lib 0.26 → 0.27, tari_template_lib_types 0.26 → 0.27, tari_ootle_template_build 0.6 → 0.7, tari_ootle_template_metadata 0.6 → 0.7, tari_template_builtin 0.30 → 0.31, ootle-rs 0.6 → 0.7, tari_ootle_wallet_sdk_services 0.1 → 0.2, tari_indexer_client 0.30 → 0.31, tari_ootle_walletd_client 0.30 → 0.31. Matching workspace dependency version constraints updated.
sdbondi
added a commit
to sdbondi/tari-ootle
that referenced
this pull request
May 19, 2026
…nicbor-serde minicbor-serde 0.6.2 doesn't implement serialize_u128/serialize_i128 (upstream PR twittner/minicbor#63 is in flight), which left foreign types like tari_sidechain::ShardGroupAccumulatedData::total_exhaust_burn unencodable through serde_bridge. Vendor a fork into tari_bor::serde_codec that adds: - serialize_u128 / serialize_i128 via RFC 8949 §3.4.3 bignum tags (2 / 3) + bstr of positive-magnitude bytes with leading zeros stripped, plus matching decoder paths that also accept the plain integer encoding for values that fit in u64. - deserialize_seq fallback that surfaces a CBOR byte string as a Vec<u8>-shaped sequence (single-byte SeqAccess), so foreign types using `#[serde(with = "hex_or_bytes")]` like tari_sidechain::SidechainBlockHeader round-trip via Vec<u8> / Cow<'_, [u8]> without re-implementing their serde impls. - collect_indef_bytes helper that pre-sizes the destination buffer for indefinite-length CBOR byte strings. All 58 consensus_tests now run (they were previously hanging in a "u128 is not supported" loop on the foreign sidechain proof). Companion changes: - tari_bor::adapters::u128_codec: a dedicated tag-2 positive-bignum adapter for direct u128 fields we control. consensus_types::ShardGroupAccumulatedData switched off serde_bridge to use it. - tari_bor::cbor! macro: $v:expr arms now route through a new helper that calls tari_bor::to_value, so any Encode<()> type drops in directly without callers having to wrap it. Primitive behaviour preserved via encode/decode round-trip identity. - engine/benches/common/mod.rs: bench component body uses the positional [FAUCET_VAULT_ID] shape matching the template struct's minicbor array encoding (not the old string-keyed map). - Two clippy fixes in tari_bor / engine_types (drop &Box<[T]> in the boxed_slice adapter and 14 redundant .map_err(BorError::from) calls in indexed_value where Value::decoded() already returns BorError). Workspace cleanup: - All direct minicbor-serde callers — state_store_rocksdb::SerdeBridgeCodec, p2p::conversions::rpc, ootle_serde tests, applications/tari_indexer storage_sqlite serialization, ootle_address tests — routed through tari_bor::serde_codec. - minicbor-serde dropped from workspace dependencies. Version bumps (workspace + 16 self-versioned crates): - workspace.package.version 0.30.12 → 0.31.0 - tari_bor 0.13 → 0.14, ootle_byte_type 0.7 → 0.8, ootle_serde 0.2 → 0.3, ootle-network 0.1 → 0.2, tari_ootle_address 0.5 → 0.6, tari_template_abi 0.16 → 0.17, tari_template_macros 0.19 → 0.20, tari_template_lib 0.26 → 0.27, tari_template_lib_types 0.26 → 0.27, tari_ootle_template_build 0.6 → 0.7, tari_ootle_template_metadata 0.6 → 0.7, tari_template_builtin 0.30 → 0.31, ootle-rs 0.6 → 0.7, tari_ootle_wallet_sdk_services 0.1 → 0.2, tari_indexer_client 0.30 → 0.31, tari_ootle_walletd_client 0.30 → 0.31. Matching workspace dependency version constraints updated.
sdbondi
added a commit
to sdbondi/tari-ootle
that referenced
this pull request
May 19, 2026
…nicbor-serde minicbor-serde 0.6.2 doesn't implement serialize_u128/serialize_i128 (upstream PR twittner/minicbor#63 is in flight), which left foreign types like tari_sidechain::ShardGroupAccumulatedData::total_exhaust_burn unencodable through serde_bridge. Vendor a fork into tari_bor::serde_codec that adds: - serialize_u128 / serialize_i128 via RFC 8949 §3.4.3 bignum tags (2 / 3) + bstr of positive-magnitude bytes with leading zeros stripped, plus matching decoder paths that also accept the plain integer encoding for values that fit in u64. - deserialize_seq fallback that surfaces a CBOR byte string as a Vec<u8>-shaped sequence (single-byte SeqAccess), so foreign types using `#[serde(with = "hex_or_bytes")]` like tari_sidechain::SidechainBlockHeader round-trip via Vec<u8> / Cow<'_, [u8]> without re-implementing their serde impls. - collect_indef_bytes helper that pre-sizes the destination buffer for indefinite-length CBOR byte strings. All 58 consensus_tests now run (they were previously hanging in a "u128 is not supported" loop on the foreign sidechain proof). Companion changes: - tari_bor::adapters::u128_codec: a dedicated tag-2 positive-bignum adapter for direct u128 fields we control. consensus_types::ShardGroupAccumulatedData switched off serde_bridge to use it. - tari_bor::cbor! macro: $v:expr arms now route through a new helper that calls tari_bor::to_value, so any Encode<()> type drops in directly without callers having to wrap it. Primitive behaviour preserved via encode/decode round-trip identity. - engine/benches/common/mod.rs: bench component body uses the positional [FAUCET_VAULT_ID] shape matching the template struct's minicbor array encoding (not the old string-keyed map). - Two clippy fixes in tari_bor / engine_types (drop &Box<[T]> in the boxed_slice adapter and 14 redundant .map_err(BorError::from) calls in indexed_value where Value::decoded() already returns BorError). Workspace cleanup: - All direct minicbor-serde callers — state_store_rocksdb::SerdeBridgeCodec, p2p::conversions::rpc, ootle_serde tests, applications/tari_indexer storage_sqlite serialization, ootle_address tests — routed through tari_bor::serde_codec. - minicbor-serde dropped from workspace dependencies. Version bumps (workspace + 16 self-versioned crates): - workspace.package.version 0.30.12 → 0.31.0 - tari_bor 0.13 → 0.14, ootle_byte_type 0.7 → 0.8, ootle_serde 0.2 → 0.3, ootle-network 0.1 → 0.2, tari_ootle_address 0.5 → 0.6, tari_template_abi 0.16 → 0.17, tari_template_macros 0.19 → 0.20, tari_template_lib 0.26 → 0.27, tari_template_lib_types 0.26 → 0.27, tari_ootle_template_build 0.6 → 0.7, tari_ootle_template_metadata 0.6 → 0.7, tari_template_builtin 0.30 → 0.31, ootle-rs 0.6 → 0.7, tari_ootle_wallet_sdk_services 0.1 → 0.2, tari_indexer_client 0.30 → 0.31, tari_ootle_walletd_client 0.30 → 0.31. Matching workspace dependency version constraints updated.
twittner
reviewed
Jul 20, 2026
Refer to `IanaTag::PosBignum`/`IanaTag::NegBignum` instead of matching raw tag numbers in `Decoder::u128`, `Decoder::i128` and the serde `Deserializer`. Comparing a `Tag` against an `IanaTag` requires new `PartialEq` impls, which are added in both directions. Compute the number of leading zero bytes in `Encoder::u128`/`i128` via `leading_zeros() / 8`, matching the existing `CborLen` impls, and let the non-negative branch of `Encoder::i128` delegate to `Encoder::u128` rather than duplicating the bignum encoding. Handle the empty byte string explicitly in `decode_bignum_u128`. Also drop an inaccurate remark about overflow: `-1 - x` does not overflow for any negative `x: i128`, so that is not the reason to prefer `!x`. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Signed-off-by: Stan Bondi <sdbondi@users.noreply.github.com>
* develop: Import `wrap_in_crate_alias`. Update CHANGELOG and increment versions. Style Use IP and socket address types from `core`. Add `#[cbor(crate = "...")]` to override the minicbor crate path Update CHANGELOG and increment version. Minor changes. Add buffer getters on io Readers and Writers add interop unit tests for tags ser: add support to serialize tag wrappers de: add support to deserialize into tag wrappers introduce tag module
Contributor
Author
|
Thanks for the review and suggestions - applied them :) |
Owner
|
Thank you! |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Adds
u128andi128encoding and decoding, includingEncode,Decode,CborLen,NonZeroU128, andNonZeroI128impls. Values within the CBOR integer range are encoded as native unsigned/signed ints; values outside are encoded as positive or negative bignums (tags 2 and 3) per RFC 8949 §3.4.3.