【问题标题】:Making msg.sender available for external contract使 msg.sender 可用于外部合同
【发布时间】:2021-09-21 10:46:25
【问题描述】:

我正在尝试制作一个从 dAPP 中获取所有奖励的功能。

  • 收获合同:
function harvest(uint256 pid,address to)...{
     UserInfo storage user = userInfo[pid][msg.sender];
     .............
     token.safeTransfer(to, value)
}
  • MyContractToHarvestAll:
function myFunction(address _user) ...{
.....
for(i < maxPid){
   IMasterchef(masterchef).harvest(i, _user); 
}
....
}

正如你所看到的,每当我调用 .harvest() 函数时,它都会检查 msg.sender,在我的例子中是 MyContractToHarvestAll。这是一个错误,因为 Harvest() 函数永远不会找到关于真正的 msg.sender(MyContractToHarvestAll 的调用者)的任何信息。

如果我尝试:

 contract.delegateCall(abi...(harvest...))  

由于存储上下文,它不起作用


我的问题是:

  • 是否可以使用接口进行委托调用?类似的东西:
(bool success, bytes memory data) = IMasterchef(masterchef).delegatecall(abi.encodeWithSignature("harvest(uint256,address)",i,_user));
  • 您知道任何使 msg.sender = MyContractHarvestAll 的调用者的技巧吗?

【问题讨论】:

    标签: interface ethereum solidity


    【解决方案1】:

    可以使用接口进行delegateCall

    目前 (v0.8) 无法在接口上使用。您需要使用address 类型的(低级)delegatecall 成员

    (bool success, bytes memory data) =  masterchef.delegatecall(
        abi.encodeWithSignature("harvest(uint256,address)", i, _user)
    );
    

    你知道任何使 msg.sender = MyContractHarvestAll 的调用者的技巧吗?

    通过使用delegatecall。但随后 EVM 使用代理 (MyContractToHarvestAll) 的存储,而不是目标 (Contract to harvest) 的存储。

    设计上不可能让作为msg.sender 的原始调用者通过代理,并同时使用目标的存储。

    注意:原始调用者存储在已弃用的tx.origin 全局变量中。但除非您能够修改Contract to harvest(使用tx.origin 而不是msg.sender),否则无法绕过此逻辑。

    【讨论】:

    • 是的,我想。在这一点上,我将使用 web3 而不是一个可靠的合同 :( 谢谢,感谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-11
    • 1970-01-01
    • 1970-01-01
    • 2011-11-23
    • 1970-01-01
    • 2014-11-12
    相关资源
    最近更新 更多