-
Notifications
You must be signed in to change notification settings - Fork 16
Fix RLP decoding for MorphTx #299
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -190,6 +190,39 @@ func (tx *MorphTx) EncodeRLP(w io.Writer) error { | |
| return err | ||
| } | ||
|
|
||
| // DecodeRLP implements rlp.Decoder so that direct rlp.Decode calls use the | ||
| // version-aware decode logic instead of reflection-based struct decoding. | ||
| // Without this, the field order mismatch between MorphTx (which has Version | ||
| // before FeeTokenID) and the v0 wire format (which lacks Version) causes | ||
| // decode failures. | ||
| func (tx *MorphTx) DecodeRLP(s *rlp.Stream) error { | ||
| kind, _, err := s.Kind() | ||
| if err != nil { | ||
| return err | ||
| } | ||
| if kind == rlp.List { | ||
| // V0 format: data is a single RLP list | ||
| raw, err := s.Raw() | ||
| if err != nil { | ||
| return err | ||
| } | ||
| return decodeV0MorphTxRLP(tx, raw) | ||
| } | ||
| // V1+ format: version byte followed by RLP list | ||
| versionByte, err := s.Uint8() | ||
| if err != nil { | ||
| return err | ||
| } | ||
| if versionByte != MorphTxVersion1 { | ||
| return errors.New("unsupported morph tx version: " + strconv.Itoa(int(versionByte))) | ||
| } | ||
| raw, err := s.Raw() | ||
| if err != nil { | ||
| return err | ||
| } | ||
| return decodeV1MorphTxRLP(tx, raw) | ||
|
Comment on lines
+209
to
+223
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Reset version-specific fields before decoding into a reused receiver.
Suggested fixfunc decodeV1MorphTxRLP(tx *MorphTx, blob []byte) error {
var v1 v1MorphTxRLP
if err := rlp.DecodeBytes(blob, &v1); err != nil {
return err
}
+ tx.Reference = nil
+ tx.Memo = nil
tx.ChainID = v1.ChainID
tx.Nonce = v1.Nonce
tx.GasTipCap = v1.GasTipCap
tx.GasFeeCap = v1.GasFeeCap
tx.Gas = v1.Gas
tx.To = v1.To
tx.Value = v1.Value
tx.Data = v1.Data
tx.AccessList = v1.AccessList
tx.Version = MorphTxVersion1
tx.FeeTokenID = v1.FeeTokenID
tx.FeeLimit = v1.FeeLimit
// Convert []byte to *common.Reference
if len(v1.Reference) != 0 && len(v1.Reference) != common.ReferenceLength {
return errors.New("invalid reference length: expected 0 or " + strconv.Itoa(common.ReferenceLength) + ", got " + strconv.Itoa(len(v1.Reference)))
}
if len(v1.Reference) == common.ReferenceLength {
ref := common.BytesToReference(v1.Reference)
tx.Reference = &ref
}
// Convert []byte to *[]byte and validate memo length
if len(v1.Memo) > common.MaxMemoLength {
return errors.New("memo exceeds maximum length of " + strconv.Itoa(common.MaxMemoLength) + " bytes, got " + strconv.Itoa(len(v1.Memo)))
}
if len(v1.Memo) > 0 {
tx.Memo = &v1.Memo
}
tx.V = v1.V
tx.R = v1.R
tx.S = v1.S
return nil
}
func decodeV0MorphTxRLP(tx *MorphTx, blob []byte) error {
var v0 v0MorphTxRLP
if err := rlp.DecodeBytes(blob, &v0); err != nil {
return err
}
if v0.FeeTokenID == 0 {
return errors.New("invalid fee token id, expected non-zero")
}
+ tx.Version = MorphTxVersion0
+ tx.Reference = nil
+ tx.Memo = nil
tx.ChainID = v0.ChainID
tx.Nonce = v0.Nonce
tx.GasTipCap = v0.GasTipCap
tx.GasFeeCap = v0.GasFeeCap
tx.Gas = v0.Gas
tx.To = v0.To
tx.Value = v0.Value
tx.Data = v0.Data
tx.AccessList = v0.AccessList
tx.FeeTokenID = v0.FeeTokenID
tx.FeeLimit = v0.FeeLimit
tx.V = v0.V
tx.R = v0.R
tx.S = v0.S
return nil
}Also applies to: 314-340, 348-373 🤖 Prompt for AI Agents |
||
| } | ||
|
|
||
| func (tx *MorphTx) encode(b *bytes.Buffer) error { | ||
| switch tx.Version { | ||
| case MorphTxVersion0: | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Keep
DecodeRLPaligned withdecode()for the0x00V0 form.Line 296 still routes a leading
0x00to the V0 decoder, but Lines 216-218 reject the same input as an unsupported version. Right nowrlp.DecodeBytesanddecode()do not accept the same byte streams.Also applies to: 292-305
🤖 Prompt for AI Agents