Repository navigation
Conversation
947bd2a to
0aabb73
Compare
Signed-off-by: Hendrik Amler <hendrik@perun.network>
0aabb73 to
bd33a90
Compare
There was a problem hiding this comment.
Pull request overview
This PR fixes restore-time signature decoding failures in multi-backend setups by making signature decoding backend-aware whenever participant backend information is available, avoiding unsafe “try all backends on the same reader” behavior during restore.
Changes:
- Add backend-specific signature decoding support (
SigDecbackend selection,DecodeSparseSigsForParts, andTransactionDec). - Update keyvalue restore path to decode transactions/signatures with participant backend context and add stricter restorer guards.
- Add focused unit tests covering backend-aware decoding and restore-time decoding invariants (unexpected keys, trailing bytes).
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
wallet/sig.go |
Adds backend-aware decoding in SigDec and introduces DecodeSparseSigsForParts with fallback behavior. |
wallet/backend.go |
Adds decodeSigForBackend helper to decode signatures using a specific backend. |
wallet/address.go |
Adds SingleBackendID helper to extract a single backend ID from a participant map. |
channel/transaction.go |
Introduces TransactionDec to decode transactions using participant backend IDs for signature decoding. |
channel/persistence/keyvalue/restorer.go |
Uses participant backend IDs when decoding persisted transactions/signatures; adds key-suffix guard and trailing-bytes detection. |
wallet/sig_test.go |
Adds tests for backend-specific SigDec and sparse signature decoding with participant backend context/fallback. |
channel/transaction_dec_test.go |
Adds test ensuring TransactionDec decodes correctly using participant backend IDs. |
channel/persistence/keyvalue/persistrestorer_internal_test.go |
Adds tests ensuring restore rejects unexpected keys and trailing bytes in persisted values. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| if actual := i.its[0].Key(); !strings.HasSuffix(actual, key) { | ||
| i.err = errors.Errorf("unexpected iterator key %q, expected suffix %q", actual, key) |
There was a problem hiding this comment.
readNextValue uses strings.HasSuffix(actual, key) to validate the iterator key. This can incorrectly accept unexpected keys that merely end with the expected key (e.g., ...:mycurrent would pass for key="current"), weakening the new guard.
Consider additionally checking that the byte immediately preceding the suffix is the channel DB separator (":"), or otherwise validating the exact key format produced by channelDB(...)+":"+key.
| if actual := i.its[0].Key(); !strings.HasSuffix(actual, key) { | |
| i.err = errors.Errorf("unexpected iterator key %q, expected suffix %q", actual, key) | |
| expectedSuffix := ":" + key | |
| if actual := i.its[0].Key(); !strings.HasSuffix(actual, expectedSuffix) { | |
| i.err = errors.Errorf("unexpected iterator key %q, expected suffix %q", actual, expectedSuffix) |
| type SigDec struct { | ||
| Sig *Sig | ||
| BackendID int | ||
| Sig *Sig | ||
| // BackendID optionally selects the backend-specific signature decoder. If it | ||
| // is nil, decoding falls back to the global multi-backend decoder. | ||
| BackendID *BackendID | ||
| } |
There was a problem hiding this comment.
SigDec is an exported type, and changing BackendID from an int/value field to a *BackendID is a breaking API change for downstream users constructing wallet.SigDec{...}.
If preserving backwards compatibility matters, consider keeping the old field (deprecated) or adding a new field (e.g., BackendIDPtr *BackendID) / constructor helper, and translating internally.
Summary
This PR fixes channel restore failures in multi-backend use cases.
Previously, persisted channel data could decode signatures via the global
wallet.DecodeSig(...)path, which tries all registered backends sequentially on the same reader. In multi-backend setups, that can consume signature bytes with the wrong backend decoder before the correct backend gets a chance, causing restore failures.This change makes restore-time signature decoding backend-aware wherever participant backend information is already available.
Changes
SigDecTransactionDecwith participant backend contextWhy
The core issue is that the generic multi-backend decode path is unsafe on a shared reader:
the first backend decoder may consume bytes even when it ultimately fails.
This PR avoids that ambiguity in restore and persistence paths by decoding with the correct backend whenever the participant metadata already identifies it.
Result
sim + ethValidation
go test