Latest Results
Optimize hashing by implementing `is_hash_trivial` (#7695)
## Description
This PR extends the `Hash` trait with the `is_hash_trivial() -> bool`
associated function. This function is supposed to return true if the
hash byte representation of the type is the same as its runtime memory
representation.
By using `is_hash_trivial`, `std::hash::sha256` and `keccak256` module
functions can skip expensive `Bytes` creation in the `Hasher` and
directly hash the value's memory content.
This optimization is similar to what `is_encode/decode_trivial()`
associated functions are providing for ABI encoding/decoding.
Similar to ABI encoding/decoding, implementation of hashing for a type
is in full control of the Sway package that owns the type. In practice,
and in `std` in particular, non-dynamic types are in general trivially
hashable if their packed memory representation is the same as their
runtime memory representation.
Because of this, when implementing `Hash` for tuples, we use the
`__runtime_mem_id` and the `__encoding_mem_id` intrinsics. While using
the `__encoding_mem_id` might look like coupling encoding and hashing,
it is not. What we are actually using is the notion of the "packed
memory representation" that the `__encoding_mem_id` provides.
Unfortunately, the intrinsic that provides this information was
originally created for ABI encoding and not for a more generic usage,
e.g., `__packed__mem_id`.
To make the distinction clear and remove what looks like coupling of
unrelated concepts, we will provide a follow-up PR that introduces
intrinsics for use case based memory layouts:
- `__mem_repr_id_runtime`
- `__mem_repr_id_encoding`
- `__mem_repr_id_hashing`
Currently, all enums in the `std` hash their descriminators as `u8`.
This makes them all being non-trivially hashable. For many of them,
hashing the descriminator as `u64` would make them trivially hashable.
This is however a breaking change that potentially affects the hashed
data we already have deployed, e.g., `StorageMap` keys.
In the future, we can provide this breaking change behind a feature
flag. Enums that can benefit from being trivially hashed are marked in
code with `TODO: (HASH-TRIVIAL-ENUMS)`.
## Checklist
- [ ] I have linked to any relevant issues.
- [x] I have commented my code, particularly in hard-to-understand
areas.
- [x] I have updated the documentation where relevant (API docs, the
reference, and the Sway book).
- [ ] If my change requires substantial documentation changes, I have
[requested support from the DevRel
team](https://github.com/FuelLabs/devrel-requests/issues/new/choose)
- [x] I have added tests that prove my fix is effective or that my
feature works.
- [x] I have added (or requested a maintainer to add) the necessary
`Breaking*` or `New Feature` labels where relevant.
- [x] I have done my best to ensure that my PR adheres to [the Fuel Labs
Code Review
Standards](https://github.com/FuelLabs/rfcs/blob/master/text/code-standards/external-contributors.md).
- [x] I have requested a review from the relevant team or maintainers. Fix `get_runtime_representation` and const-eval of `EnumInstantiation` (#7692)
## Description
This PR:
- fixes the runtime representations of `TypeContent::Array` and
`TypeContent::Union` calculated in `get_runtime_representation`:
- Arrays were padded to word boundary, which originally caused #7690.
- Unions were always having a size of minimum 8 bytes, even if all their
variants were zero-sized. Union variants were right-padded to word
boundary, instead of being left-padded.
- fixes the `const_eval` of `EnumInstantiation` to not add variant
payloads if the enum is compiled only to a tag.
The PR also improves compilation of enums whose all variants are
zero-sized. Up to now, it was required that all the variants must be
unit for the enum to be compiled only to a tag. This PR loosens this
requirement too all zero-sized types.
Additionally, the PR:
- adds IR verification that checks that a global's initializer fits to
the expected global type.
- in `MemoryRepresentation` adds padding in struct fields to a padded
field, and does not inserts them as additional elements. This accurately
reflects what gets padded and the underlying struct structure.
- makes `insta::assert_snapshot` fail if `logs` get changed in tests
that use them, like in the `type_layout` test.
- deletes redundant ABI JSON validation from `match` expressions tests.
Three tests extended or added in this PR use the same types and those
are currently copy-pasted across the tests. We had this situation
before. We will create a separate utility project that provides common
types and traits for tests as a part of #7693.
- Fixes #7690.
- Fixes #7691.
## Checklist
- [x] I have linked to any relevant issues.
- [x] I have commented my code, particularly in hard-to-understand
areas.
- [ ] I have updated the documentation where relevant (API docs, the
reference, and the Sway book).
- [ ] If my change requires substantial documentation changes, I have
[requested support from the DevRel
team](https://github.com/FuelLabs/devrel-requests/issues/new/choose)
- [x] I have added tests that prove my fix is effective or that my
feature works.
- [ ] I have added (or requested a maintainer to add) the necessary
`Breaking*` or `New Feature` labels where relevant.
- [x] I have done my best to ensure that my PR adheres to [the Fuel Labs
Code Review
Standards](https://github.com/FuelLabs/rfcs/blob/master/text/code-standards/external-contributors.md).
- [x] I have requested a review from the relevant team or maintainers. Latest Branches
0%
xunilrj/fix-sroa-load-multi-blocks -15%
ironcev/fix-get-runtime-representation +11%
© 2026 CodSpeed Technology