Skip to content

fix!: remove LengthPrefix deref fallback that could silently drop length encoding - #48

Merged
Altair-Bueno merged 8 commits into
masterfrom
copilot/fix-length-prefix-encoding
Sep 7, 2026
Merged

fix!: remove LengthPrefix deref fallback that could silently drop length encoding#48
Altair-Bueno merged 8 commits into
masterfrom
copilot/fix-length-prefix-encoding

Conversation

Copilot AI commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

LengthPrefix could compile and run without writing a prefix when Length was not Encodable (e.g. u32), because method resolution fell through Deref to the wrapped value’s encode. This change removes that fallback so invalid LengthPrefix usage is rejected at compile time.

  • API behavior change: remove Deref on LengthPrefix

    • Deleted impl Deref for LengthPrefix<...> to prevent .encode() from auto-forwarding to the inner encodable when LengthPrefix itself does not satisfy Encodable bounds.
    • This makes mis-specified length types fail loudly instead of producing truncated output.
  • Regression guard: compile-fail coverage

    • Added trybuild-based UI test asserting LengthPrefix::<_, u32, _>::new("hello").encode(...) does not compile.
    • Added expected compiler output snapshot to lock the behavior.
  • Test cleanup aligned with API change

    • Removed LengthPrefix unit tests that relied on deref semantics (*lp style assertions), preserving only behavior that remains part of the type’s API.
use core::num::TryFromIntError;
use encode::combinators::LengthPrefix;
use encode::Encodable;

fn main() {
    let mut buf = Vec::new();
    LengthPrefix::<_, u32, TryFromIntError>::new("hello")
        .encode(&mut buf) // now compile error: `u32` does not satisfy `Encodable`
        .unwrap();
}

Co-authored-by: Altair-Bueno <67512202+Altair-Bueno@users.noreply.github.com>
Copilot AI changed the title [WIP] Fix LengthPrefix to ensure length encoding fails correctly fix!: remove LengthPrefix deref fallback that could silently drop length encoding Sep 3, 2026
Copilot AI requested a review from Altair-Bueno September 3, 2026 21:21
@Altair-Bueno

Copy link
Copy Markdown
Owner

@copilot is there any combinator that has this issue too? We should fix any other deref that leads to the same bug

Co-authored-by: Altair-Bueno <67512202+Altair-Bueno@users.noreply.github.com>

Copilot AI commented Sep 3, 2026

Copy link
Copy Markdown
Contributor Author

@copilot is there any combinator that has this issue too? We should fix any other deref that leads to the same bug

Yes—I audited all combinators with Deref and removed the ones that could silently bypass combinator behavior: BE, LE, Iter, and FromError. I also added compile-fail regressions for each misuse pattern. Fixed in 19b6a9d. Cond still has Deref, but it doesn’t have the same fallback hazard in practice because its constructor and Encodable bounds line up.

@Altair-Bueno

Copy link
Copy Markdown
Owner

Cond still has Deref, but it doesn’t have the same fallback hazard in practice because its constructor and Encodable bounds line up.

@copilot I would rather have it gone to avoid potential issues in the future. Are there any more Deref uses I missed?

Co-authored-by: Altair-Bueno <67512202+Altair-Bueno@users.noreply.github.com>

Copilot AI commented Sep 3, 2026

Copy link
Copy Markdown
Contributor Author

Cond still has Deref, but it doesn’t have the same fallback hazard in practice because its constructor and Encodable bounds line up.

@copilot I would rather have it gone to avoid potential issu...

Done in 9e88b34: I removed Deref from Cond and added a compile-fail regression for invalid Cond encode usage. I also re-audited the repo—there are no remaining combinator Deref impls; the only Deref left is IoEncoder in src/encoders/std_io.rs.

@Altair-Bueno
Altair-Bueno marked this pull request as ready for review September 7, 2026 19:50
Copilot AI lite review requested due to automatic review settings September 7, 2026 19:50

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@codecov

codecov Bot commented Sep 7, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 100.00%. Comparing base (0f73ad7) to head (6d0279c).

Additional details and impacted files
@@             Coverage Diff             @@
##           master       #48      +/-   ##
===========================================
+ Coverage   99.43%   100.00%   +0.56%     
===========================================
  Files          25        25              
  Lines        1067      1025      -42     
===========================================
- Hits         1061      1025      -36     
+ Misses          6         0       -6     
Files with missing lines Coverage Δ
src/combinators/be.rs 100.00% <ø> (ø)
src/combinators/cond.rs 100.00% <ø> (ø)
src/combinators/from_error.rs 100.00% <100.00%> (+3.44%) ⬆️
src/combinators/iter.rs 100.00% <ø> (ø)
src/combinators/le.rs 100.00% <ø> (ø)
src/combinators/length_prefix.rs 100.00% <100.00%> (+2.88%) ⬆️
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

Altair-Bueno and others added 2 commits September 7, 2026 21:54
Removing the `Deref` impls also removed the `clone`/`default`/`from`
tests, since they asserted through `*value`. Restore them using
`as_ref()`/`into_inner()` and additionally cover `partial_cmp`, which
was already uncovered before this branch.

Fixes the codecov/project regression (99.43% -> 96.70%).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@Altair-Bueno
Altair-Bueno merged commit 7fe1c1f into master Sep 7, 2026
32 checks passed
@github-actions github-actions Bot mentioned this pull request Sep 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

LengthPrefix silently drops the prefix when Length is not Encodable (Deref shadows the failed impl)

3 participants