umbracle/ethgo

Incorrect implementation of RecoverSender

Closed this issue · 1 comments

bynil commented

Current version RecoverSender:

ethgo/wallet/signer.go

Lines 26 to 41 in c54938f

func (e *EIP1155Signer) RecoverSender(tx *ethgo.Transaction) (ethgo.Address, error) {
v := new(big.Int).SetBytes(tx.V).Uint64()
v -= e.chainID * 2
v -= 8
v -= 27
sig, err := encodeSignature(tx.R, tx.S, byte(v))
if err != nil {
return ethgo.Address{}, err
}
addr, err := Ecrecover(signHash(tx, e.chainID), sig)
if err != nil {
return ethgo.Address{}, err
}
return addr, nil
}

After EIP-2930 tx.V is 0 or 1. v should not be calculated this way, or it will sometimes get the wrong sender address.

How about to fix with compatibility:

v := new(big.Int).SetBytes(tx.V).Uint64()
if v > 1 {
	v -= 27
	if v > 1 {
		v -= e.chainID * 2
		v -= 8
	}
}

Thank you! I added your fix and include also more test coverage for the sign/recover workflow.