Skip to content
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

Hevm abi encode #868

Open
wants to merge 8 commits into
base: master
Choose a base branch
from
Open

Hevm abi encode #868

wants to merge 8 commits into from

Conversation

rainbreak
Copy link
Member

@rainbreak rainbreak commented Nov 22, 2021

Nearly complete. Fixes #861.

  • tuple types are now supported in arguments, as (...) or tuple(...) or Whatever(...)
  • the --abi argument for hevm now accepts solidity fragments as well as json
  • hevm abi -> output json for a given solidity fragment (functions, events and errors)
  • hevm normalise -> canonical signature for a given abi
  • hevm selector -> signature hash for a given abi (cc @mds1)
  • hevm abidecode -> decode calldata and/or returndata given an abi

Note:

  • Strings output from hevm abidecode, and therefore the results of seth call, will be quoted with "...". Previously string results were unquoted
  • Similarly, Arrays output from hevm abidecode are now wrapped in [...]. Previously the output was just comma separated elements.
  • Multi-dimensional array output was broken before, e.g. uint[][] [[1, 2], [3, 4]] was output as 1, 2, 3, 4. This is now fixed.
  • The new seth abi-encode was renamed to seth --abi-encode for consistency with --abi-decode and now outputs the full calldata including signature.

Todo:

  • consider event encode / decode (kind of annoying because of indexed args), which would allow seth --decode-events to use hevm
  • maybe SolidityAbi.hs should be part of an existing file (created to speed up compile times)
  • changelog
  • there was an existing simple parser for AbiTypes in Solidity.hs, which uses MegaParsec. I didn't touch this to avoid breaking something. The parser here uses ReadP, but there is duplicated functionality. Potentially the two could be combined.

`hevm abiencode` now accepts solidity interface definitions:

    hevm abiencode --abi "f(bool b, uint x, Data(bytes[], string))"

New commands `hevm normalise` and `hevm selector` to give the canonical
signature and signature hash for a given --abi.
New command `hevm abidecode`, allowing for decoding of e.g. function
calldata or returndata, given an ABI.
New command `hevm abi` to generate ABI json from a Solidity fragment.
Works with functions, events and errors.

Examples:

    seth abi "f(bool)"
    seth abi "function hello()"
    seth abi "event SomeEvent(bool x, string indexed s)"
    seth abi "error SomeError(string)"
@rainbreak
Copy link
Member Author

rainbreak commented Nov 22, 2021

CI failing because I broke seth --abi-decode by parenthesising the output on a single line.

The current --abi-decode is broken though:

$ seth --abi-decode "f()(bool[][],uint)" 0x000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000
true,true,true,false
1

Here we should probably have instead:

[[true, true], [true, false]]
1

in
if (abiSelector == dataSelector) then
pack $ show values
pack $ intercalate "\n" (show <$> V.toList values)
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
pack $ intercalate "\n" (show <$> V.toList values)
pack $ unlines (show <$> V.toList values)

and sim

Right (Nothing, Just event, _) -> render (JSON.toJSON event)
Right (Nothing, Nothing, Just err) -> render (JSON.toJSON err)
where
render = decodeUtf8 . Lazy.toStrict . encoder
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
render = decodeUtf8 . Lazy.toStrict . encoder
render :: ToJSON a => a -> Text
render = decodeUtf8 . Lazy.toStrict . encoder

ish

src/hevm/shell.nix Outdated Show resolved Hide resolved
src/hevm/shell.nix Outdated Show resolved Hide resolved
makeArray t "" = AbiArrayDynamicType t
makeArray t s = AbiArrayType (read s) t

parseBasicType :: ReadP AbiType
Copy link
Member

Choose a reason for hiding this comment

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

this would be nice to have in ABI.hs next to the show instance for AbiType. We can also easily quickcheck the roundtrip

@MrChico
Copy link
Member

MrChico commented Dec 7, 2021

lgtm

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.

seth sig / seth calldata: handle tuple types
2 participants