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

Support for native-meta transaction in contract3.X standard #2242

Closed
sanchaymittal opened this issue May 22, 2020 · 4 comments
Closed

Support for native-meta transaction in contract3.X standard #2242

sanchaymittal opened this issue May 22, 2020 · 4 comments

Comments

@sanchaymittal
Copy link

sanchaymittal commented May 22, 2020

🧐 Motivation
Contracts3.X doesn't support Native Meta-Transaction support. It's not compatible with any of the meta-transaction out there in the market.

📝 Details
As contract 3.X uses v0.6.6 standard of solidity, And function _msgSender in Context contract is virtual so it can only be overridden in parent contract which inherits the ERC20 standard. That means, the existing solutions for meta transaction are not compatible anymore. To give some context, Meta-Transaction relayers uses _msgSender, For instance Gas station network uses this implementation.

    function _msgSender() internal view returns (address payable) {
        if (msg.sender == address(this)) {
            bytes20 userAddress;
            uint256 dataLength = msg.data.length;
            assembly {
                calldatacopy(0x0, sub(dataLength, 40), sub(dataLength, 20))
                userAddress := mload(0x0)
            }
            return address(uint160(userAddress));
        } else {
            return msg.sender;
        }
    }

I propose that we should include this change in Context contract itself or make changes so _msgSender() can be overridden by the other contracts too.

@frangio
Copy link
Contributor

frangio commented May 22, 2020

Thank you for reaching out @sanchaymittal.

I wasn't able to understand the problem that you point out.

Context._msgSender was specifically built for the GSN. The inheritance changes in Solidity 0.6 made it a bit more cumbersome to use, but everything should work. GSNRecipient defines the override for _msgSender.

Unfortunately in Solidity 0.6 inheriting from GSNRecipient will likely result in a contract that doesn't compile because the compiler doesn't know if it should use Context._msgSender or GSNRecipient._msgSender, but this is fixed by adding the following lines to your contract:

function _msgSender() internal view override(Context, GSNRecipient) returns (address payable) {
    return super._msgSender();
}

function _msgData() internal view override(Context, GSNRecipient) returns (bytes memory) {
    return super._msgData();
}

By using super we specify that we want to use the "most specific" implementation of _msgData according to the Solidity linearization, and that will be GSNRecipient's.

We definitely should have specifically this bit of code in the docs, but I couldn't find it. cc @nventuro

@abcoathup
Copy link
Contributor

We have notes on the required overrides for GSN in the release notes for v3: https://github.com/OpenZeppelin/openzeppelin-contracts/releases/tag/v3.0.0

@sanchaymittal
Copy link
Author

Thanks a lot guys!!! @frangio @abcoathup.
Got it resolved...

pragma solidity "0.6.6";

import { ERC20 } from "@openzeppelin/contracts/token/ERC20/ERC20.sol";
import "@opengsn/gsn/contracts/BaseRelayRecipient.sol";

contract TestToken is ERC20, BaseRelayRecipient {
  constructor() 
    ERC20("Test Token", "TST")
    public 
  {
    uint256 value = 10**10 * (10**18);
    _mint(_msgSender(), value);
  }

function _msgSender() internal view override(Context, BaseRelayRecipient) returns (address payable) {
    return BaseRelayRecipient._msgSender();
}
}

@frangio
Copy link
Contributor

frangio commented May 26, 2020

Awesome!

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

No branches or pull requests

3 participants