izelnakri / eth

Ethereum utilities for Elixir
MIT License
119 stars 44 forks source link

trim leading zero for signature r and s #18

Closed seamon closed 3 years ago

seamon commented 4 years ago

hey there, thanks for your good work.

after signing transaction using %{data: xxx, nonce: xxx, ...} |> ETH.parse() |> ETH.sign_transaction(pkey), if the generated signature r or s has a leading zero <<0>>, the transaction sending call will get an error from the ethereum endpoint:

rlp: non-canonical integer (leading zero bytes) for *big.Int, decoding into (types.Transaction)(types.txdata).R

it has been mentioned years ago:

https://ethereum.stackexchange.com/questions/71616/ethereum-boardcast-shows-error-non-canonical-integer-leading-zero-bytes-for

it's not a mistake, neither a bug, it looks like a, hmm..., specification conflict?

after digging it for hours, i reproduced it successfully, got an s like this:

<<0, 107, 148, 141, 178, 99, 64, 168, 233, 83, 227, 146, 181, 23, 67, 73, 156, 25, 30, 221, 168, 80, 241, 88, 51, 232, 102, 213, 157, 18, 130, 225>>

i tried and tested, found that the most convenient way to solve this problem is to trim the leading zero from signature r or s directly.

hope it helps, thank you so much.

izelnakri commented 4 years ago

I just saw this PR, and wow, thanks for your contribution @seamon!

All ethereum nodes should follow the same spec, do you know which clients(parity, geth etc) needed this change? Ideally we shouldn't cater to a specific client in order to trim 0s.

seamon commented 4 years ago

i just reproduced and tested on infura.io, seems that it's following the geth specification. but according to the topics about this problem in the last several years, it's likely client independency. thank you