首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >状态变量在DelegateCall之后未更新

状态变量在DelegateCall之后未更新
EN

Ethereum用户
提问于 2022-01-19 09:31:37
回答 1查看 294关注 0票数 1

我部署了两个契约“WalletLibrary”和“Wallet”:Wallet delegateCall()中的大多数函数--来自WalletLibrary的函数。我想重新创建一个攻击,通过触发Wallet的回退函数,从WalletLibrary调用WalletLibrary()函数。然而,当我这样做时,钱包的所有者会被更新到我的地址,但是WalletLibrary中的那个不会。此外,WalletLibrary的所有者在部署时是0000000000000000 (我可能在部署时做错了什么吗?),我希望所有者应该是我部署它的地址。

根据我的理解,当我在Wallet中更新一些变量时,它也应该在WalletLibrary中被更新,因为delegateCall()保留了上下文,对吗?我的问题是,为什么它不起作用。如果我出了什么问题请告诉我。希望有人能帮上忙。

下面,两份合同的代码..。

WalletLibrary.sol:

代码语言:javascript
复制
    pragma solidity ^0.5.4;
    
    contract WalletLibrary {
        address walletLibrary; 
        address payable owner;
        address payable student;
    
        event LogValue(uint256 exitcode,uint256 amount);
    
        function initWallet(address payable _owner) public payable {
        owner = _owner;
        }
    
        function getOwner() public view returns (address payable) {
        return owner;
        }
    
        function changeOwner(address payable new_owner) public returns (bool success) {
        if (msg.sender == owner) {
            owner = new_owner;
            return true;
        } else {
            return false;
        }
        }
    
        function withdraw(uint256 amount) public returns (bool success) {
            if (msg.sender == owner) {
                return owner.send(amount);
            } else {
                return false;
            }
        }
    
        function () external payable {
            emit LogValue(200,msg.value);
        }
    }

Wallet.sol:

代码语言:javascript
复制
    pragma solidity ^0.5.4;
    
    contract Wallet {
        address walletLibrary;
        address payable owner;
        address payable student;
    
        event LogValue(uint256 exitcode,uint256 amount);
    
        // constructor, called once when this contract is created 
        constructor(address payable _student, address lib) public payable {
            student = _student;  
            walletLibrary = lib; // hardcode lib address at deploy time
            // init the owner with the respective lib contract
            walletLibrary.delegatecall(abi.encodeWithSignature("initWallet(address)", msg.sender));
        }
    
        function getOwner() public view returns (address payable) {
            return owner;
        } 
    
        function getWalletLibrary() public view returns (address) {
            return walletLibrary;
        }
    
        function withdraw(uint256 amount) public returns (bool) {
            (bool success, bytes memory data) = walletLibrary.delegatecall(abi.encodeWithSignature("withdraw(uint256)", amount));
            if ( success ) {
                emit LogValue(200,amount);
            } else {
                emit LogValue(401,amount);
            }
            return success;
        }
    
        function changeOwner(address payable new_owner) public returns (bool) {
            (bool success, bytes memory data) = walletLibrary.delegatecall(abi.encodeWithSignature("changeOwner(address)", new_owner));
            return success;
        }
    
        function getStudent() public view returns (address) {
            return student;
        }
    
        // fallback function gets called if no other function matches call
        function () external payable {
            emit LogValue(301,msg.value);
            require( tx.origin == student ); 
            walletLibrary.delegatecall(msg.data);
        }
    }
EN

回答 1

Ethereum用户

回答已采纳

发布于 2022-01-19 09:52:50

当您使用委托时,它将在调用者的上下文中执行目标的代码。这意味着当您的Wallet合同使用委托给您的WalletLibrary时,它将使用来自库的代码,而使用来自Wallet的状态(例如ownerstudent等)。

因此,要更改WalletLibrary的状态,您必须直接与该契约交互。

关于委托的详细介绍可以在这里找到:https://medium.com/coinmonks/delegatecall-calling-another-contract-function-in-solidity-b579f804178c

您的owner WalletLibrary0x0000...0000,因为您没有任何构造函数,因此所有者不是不正确的。在您的Wallet中,您可以调用initWallet函数来这样做,因此Wallet所有者被设置为msg.sender

票数 1
EN
页面原文内容由Ethereum提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://ethereum.stackexchange.com/questions/119319

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档