VNCTF 2022 Writeup

前言

难得在短暂的假期结束前还有能参加的CTF比赛,趁机打一打,题目质量也很合适。这次出乎意料的排在了前面一些的位置,明明没有写出几道题,属于是运气问题。

13

Blockchain

VNloan

1

这题出乎意料地拿到了一血,我在工作量证明上就卡了47分钟,连题都看不到- -

这题我也不知道是不是预期解,感觉我的解法太过简单,可能和出题人最初的想法不一致。根据题目信息我猜测是考察闪电贷攻击,但根据flag的内容又发现考的好像是重入攻击,但我自己写的时候,完全就没有用到任何的攻击类型,就达成条件了,也有可能是出题人在编写合约代码时出现了一些纰漏,总之既然题目已经公开,也只能按当时题目的样子去解了。

按比赛时情况,我们先分析一下题目中的两个合约代码。

//Setup.sol

pragma solidity 0.4.26;

import "./VNETH.sol";

contract Setup {
    VNETH public vneth;
    bool public Solved = false;

    constructor() public payable {
        vneth = new VNETH();
    }

    function checksuccess() public {
        if (vneth.balanceOf(msg.sender) >= 5000) Solved = true;
    }

    function isSolved() public view returns (bool) {
        if (Solved == true) {
            return true;
        }
        return false;
    }
}
//VNETH.sol

pragma solidity 0.4.26;

contract VNETH {
    address public owner;
    string public name     = "VN ETHER";
    string public symbol   = "VNeth";
    uint8  public decimals = 18;
    bool  public isLoan=false;
    event  Approval(address indexed src, address indexed guy, uint wad);
    event  Transfer(address indexed src, address indexed dst, uint wad);
    event  Deposit(address indexed dst, uint wad);
    event  Withdrawal(address indexed src, uint wad);

    mapping (address => uint)                       public  balanceOf;
    mapping (address => mapping (address => uint))  public  allowance;
    constructor()public{
        owner=msg.sender;
        balanceOf[owner]=1e18 ether;
        balanceOf[address(this)]=1e18 ether;
    }
    function() external payable {
        deposit();
    }
    function deposit() public payable {
        balanceOf[msg.sender] += msg.value;
        emit Deposit(msg.sender, msg.value);
    }
    function withdraw(uint wad) public {
        require(balanceOf[msg.sender] >= wad);
        balanceOf[msg.sender] -= wad;
        (msg.sender).transfer(wad);
        emit Withdrawal(msg.sender, wad);
    }

    function totalSupply() public view returns (uint) {
        return address(this).balance;
    }

    function approve(address guy, uint wad) public returns (bool) {
        allowance[msg.sender][guy] = wad;
        emit Approval(msg.sender, guy, wad);
        return true;
    }

    function transfer(address dst, uint wad) public returns (bool) {
        return transferFrom(msg.sender, dst, wad);
    }

    function fakeflashloan(uint256 value,address target,bytes memory data) public{
        require(isLoan==false&&value>=0&&value<=1000);
        balanceOf[address(this)]-=value;
        balanceOf[target]+=value;
        
        address(target).call(data);
        
        isLoan=true;
        require(balanceOf[target]>=value);
        balanceOf[address(this)]+=value;
        balanceOf[target]-=value;
        isLoan=false;
    }

    function transferFrom(address src, address dst, uint wad)
        public
        returns (bool)
    {
        require(balanceOf[src] >= wad);

        if (src != msg.sender && allowance[src][msg.sender] != 2**256-1) {
            require(allowance[src][msg.sender] >= wad);
            allowance[src][msg.sender] -= wad;
        }

        balanceOf[src] -= wad;
        balanceOf[dst] += wad;

        emit Transfer(src, dst, wad);

        return true;
    }
}

2

可以发现当我们的代币余额大于等于5000 wei时,即可达成解出条件,且vneth的属性是public的,可以直接读取到合约地址

3

当时代码审计到这里我就不往下看了,因为已经可以快速达成解出条件,只需要往vneth合约转账5000 weitest ETH,我们的代币余额就已经达成要求,所以当时我是一脸懵,这道题考察的是什么呢,也许是面向新手的链上交互操作吧,只要懂得如何与链交互就能解出题目。

下面是我的半自动脚本,事先需要请求水龙头向Option 1得到的deployer地址转账一些test ETH作为手续费,然后部署题目合约。

同时欢迎使用我的 Poseidon 库,Poseidon_Blockchain可以让你轻松地与链上交互(主流的区块链题目大都与以太坊有关),即使你刚刚入门。

出题人环境部署得很好,禁用了大部分链上函数,使得没有办法扫链获得其他人的交易信息,也因此Poseidon_Blockchain需要进行一些代码行的注释暂停使用后才能运行。注释掉第68、69行,将第158、178行的gasPrice修改为5*10**9(即5 Gwei)。

from Poseidon_Blockchain import *
from loguru import logger
import requests
import solcx

# deployer:0x4c7A8Fbffe8585aCB736FBc1a885Df2083f48F79
# token:v4.local.YLxt2XkscX0zOuSjwGprwVy2k_kKhTq-EJIRolVu-kMjr7khCqejWz9raWvWKrp15YyP4_o5yuVYw5iKq7deMsjZxlQxoj1BgbGu1Ut-UOj1HCuywiEBa0UjXuBHyeCGgB2Ub-nY5zjdkwA2fNgiCUwdXy0Qcf5UYmRPx-TQ-CHhqA
# contract:0x3d8fB1A9aaBFEfd8cf5910202d05E664CcBd02D5
# VNCTF{I_will_us3_th3_R3ENtracyGu4rd-nexT_t1m3}

logger.add('log/VNloan_{time}.log', rotation='00:00')

# 安装并切换到对应的solidity版本
SolidityVersion = solcx.install_solc('0.4.26')
solcx.set_solc_version(SolidityVersion)
logger.success(f"Solidity Version:{SolidityVersion}")

# 连接至链 生成新账户 调用水龙头获取test ETH
chain = Chain("http://81.68.163.153:8545")
account = Account(chain, Account.CreateNewAccount()[1])
faucetHash = requests.post("http://81.68.163.153:8080/api/claim", data={"address": account.Address}).text
chain.Net.eth.wait_for_transaction_receipt(faucetHash, timeout=180)
chain.GetBalanceByAddress(account.Address)

# 实例化合约 获取vneth合约地址 向其转账5000wei
contractAddress = Web3.toChecksumAddress("0x3d8fB1A9aaBFEfd8cf5910202d05E664CcBd02D5")
abi, bytecode = SolidityToAbiAndBytecode("Setup.sol", "Setup")
contract = chain.Net.eth.contract(address=contractAddress, abi=abi)
vnethAddress = contract.functions.vneth().call()
account.SendTransactionToChain(vnethAddress, "0x", 5000)
abi, bytecode = SolidityToAbiAndBytecode("VNETH.sol", "VNETH")
vneth = chain.Net.eth.contract(address=vnethAddress, abi=abi)
logger.info(f"{vneth.functions.balanceOf(account.Address).call()}")

# 调用checksuccess修改状态变量 达成解出条件
transactionData = contract.functions.checksuccess().buildTransaction()
account.SendTransactionToChain(transactionData["to"], transactionData["data"])
logger.info(f"{contract.functions.Solved().call()}")
logger.info(f"{contract.functions.isSolved().call()}")

logger.success("Execution completed.")


运行日志如下:

2022-02-12 19:58:57.565 | SUCCESS  | __main__:<module>:15 - Solidity Version:0.4.26
2022-02-12 19:58:57.659 | SUCCESS  | Poseidon_Blockchain:__init__:65 - 
[ConnectToChain]Successfully connected to [http://81.68.163.153:8545].
2022-02-12 19:58:57.670 | SUCCESS  | Poseidon_Blockchain:CreateNewAccount:200 - 
[NewAccount]
[Address]0xCDD53a6422696fbc09dc8D1d480378A93f3d605e
[PrivateKey]
2022-02-12 19:58:57.674 | SUCCESS  | Poseidon_Blockchain:__init__:146 - 
[ImportAccount]Successfully import account.
[Address]0xCDD53a6422696fbc09dc8D1d480378A93f3d605e
2022-02-12 19:59:02.487 | INFO     | Poseidon_Blockchain:GetBalanceByAddress:116 - 
[Balance][0xCDD53a6422696fbc09dc8D1d480378A93f3d605e]
[1000000000000000000 Wei]<=>[1 Ether]
2022-02-12 19:59:02.638 | INFO     | Poseidon_Blockchain:SolidityToAbiAndBytecode:212 - 
[CompileContract]
[Abi][{'constant': False, 'inputs': [], 'name': 'checksuccess', 'outputs': [], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'isSolved', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'Solved', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'vneth', 'outputs': [{'name': '', 'type': 'address'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'inputs': [], 'payable': True, 'stateMutability': 'payable', 'type': 'constructor'}]
[Bytecode]608060405260008060146101000a81548160ff021916908315150217905550610026610087565b604051809103906000f080158015610042573d6000803e3d6000fd5b506000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550610097565b6040516113298061038b83390190565b6102e5806100a66000396000f300608060405260043610610062576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff168063094cc1131461006757806364d98f6e1461007e57806387272232146100ad578063c685bebe146100dc575b600080fd5b34801561007357600080fd5b5061007c610133565b005b34801561008a57600080fd5b50610093610252565b604051808215151515815260200191505060405180910390f35b3480156100b957600080fd5b506100c2610281565b604051808215151515815260200191505060405180910390f35b3480156100e857600080fd5b506100f1610294565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b6113886000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff166370a08231336040518263ffffffff167c0100000000000000000000000000000000000000000000000000000000028152600401808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001915050602060405180830381600087803b1580156101f257600080fd5b505af1158015610206573d6000803e3d6000fd5b505050506040513d602081101561021c57600080fd5b8101908080519060200190929190505050101515610250576001600060146101000a81548160ff0219169083151502179055505b565b600060011515600060149054906101000a900460ff1615151415610279576001905061027e565b600090505b90565b600060149054906101000a900460ff1681565b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff16815600a165627a7a723058201e54d7425b7eb19e876c7b80f57bc173a000b593b602bffa90e7625d79f95269002960806040526040805190810160405280600881526020017f564e2045544845520000000000000000000000000000000000000000000000008152506001908051906020019062000051929190620001f2565b506040805190810160405280600581526020017f564e657468000000000000000000000000000000000000000000000000000000815250600290805190602001906200009f929190620001f2565b506012600360006101000a81548160ff021916908360ff1602179055506000600360016101000a81548160ff021916908315150217905550348015620000e457600080fd5b50336000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506ec097ce7bc90715b34b9f1000000000600460008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506ec097ce7bc90715b34b9f1000000000600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550620002a1565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106200023557805160ff191683800117855562000266565b8280016001018555821562000266579182015b828111156200026557825182559160200191906001019062000248565b5b50905062000275919062000279565b5090565b6200029e91905b808211156200029a57600081600090555060010162000280565b5090565b90565b61107880620002b16000396000f3006080604052600436106100d0576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806306fdde03146100da578063095ea7b31461016a57806318160ddd146101cf57806323b872dd146101fa5780632e1a7d4d1461027f578063313ce567146102ac57806370a08231146102dd5780638da5cb5b146103345780639109149e1461038b57806395d89b41146103ba578063a9059cbb1461044a578063d0e30db0146104af578063dd62ed3e146104b9578063f6d5b8c414610530575b6100d86105c3565b005b3480156100e657600080fd5b506100ef610660565b6040518080602001828103825283818151815260200191508051906020019080838360005b8381101561012f578082015181840152602081019050610114565b50505050905090810190601f16801561015c5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b34801561017657600080fd5b506101b5600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291905050506106fe565b604051808215151515815260200191505060405180910390f35b3480156101db57600080fd5b506101e46107f0565b6040518082815260200191505060405180910390f35b34801561020657600080fd5b50610265600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919050505061080f565b604051808215151515815260200191505060405180910390f35b34801561028b57600080fd5b506102aa60048036038101908080359060200190929190505050610b5c565b005b3480156102b857600080fd5b506102c1610c8f565b604051808260ff1660ff16815260200191505060405180910390f35b3480156102e957600080fd5b5061031e600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050610ca2565b6040518082815260200191505060405180910390f35b34801561034057600080fd5b50610349610cba565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b34801561039757600080fd5b506103a0610cdf565b604051808215151515815260200191505060405180910390f35b3480156103c657600080fd5b506103cf610cf2565b6040518080602001828103825283818151815260200191508051906020019080838360005b8381101561040f5780820151818401526020810190506103f4565b50505050905090810190601f16801561043c5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b34801561045657600080fd5b50610495600480360381019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050610d90565b604051808215151515815260200191505060405180910390f35b6104b76105c3565b005b3480156104c557600080fd5b5061051a600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050610da5565b6040518082815260200191505060405180910390f35b34801561053c57600080fd5b506105c160048036038101908080359060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284378201915050505050509192919290505050610dca565b005b34600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055503373ffffffffffffffffffffffffffffffffffffffff167fe1fffcc4923d04b559f4d29a8bfc6cda04eb5b0d3c460751c2402c5c5cc9109c346040518082815260200191505060405180910390a2565b60018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156106f65780601f106106cb576101008083540402835291602001916106f6565b820191906000526020600020905b8154815290600101906020018083116106d957829003601f168201915b505050505081565b600081600560003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508273ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925846040518082815260200191505060405180910390a36001905092915050565b60003073ffffffffffffffffffffffffffffffffffffffff1631905090565b600081600460008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541015151561085f57600080fd5b3373ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415801561093757507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205414155b15610a525781600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054101515156109c757600080fd5b81600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055505b81600460008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254039250508190555081600460008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055508273ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef846040518082815260200191505060405180910390a3600190509392505050565b80600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205410151515610baa57600080fd5b80600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055503373ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015610c3d573d6000803e3d6000fd5b503373ffffffffffffffffffffffffffffffffffffffff167f7fcf532c15f0a6db0bd6d0e038bea71d30d808c7d98cb3bf7268a95bf5081b65826040518082815260200191505060405180910390a250565b600360009054906101000a900460ff1681565b60046020528060005260406000206000915090505481565b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600360019054906101000a900460ff1681565b60028054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015610d885780601f10610d5d57610100808354040283529160200191610d88565b820191906000526020600020905b815481529060010190602001808311610d6b57829003601f168201915b505050505081565b6000610d9d33848461080f565b905092915050565b6005602052816000526040600020602052806000526040600020600091509150505481565b60001515600360019054906101000a900460ff161515148015610dee575060008310155b8015610dfc57506103e88311155b1515610e0757600080fd5b82600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254039250508190555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055508173ffffffffffffffffffffffffffffffffffffffff168160405180828051906020019080838360005b83811015610ee6578082015181840152602081019050610ecb565b50505050905090810190601f168015610f135780820380516001836020036101000a031916815260200191505b509150506000604051808303816000865af1915050506001600360016101000a81548160ff02191690831515021790555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205410151515610f9257600080fd5b82600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254019250508190555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055506000600360016101000a81548160ff0219169083151502179055505050505600a165627a7a72305820fa508afafafb9b7b733483443682d333099e07b67364888b70dc901b290124410029
2022-02-12 19:59:02.846 | INFO     | Poseidon_Blockchain:SendTransactionToChain:167 - 
[SendTransaction]
[TransactionHash]0x354cb6b3307284ed4879c296bed69b45826aab9fb3641f0340ddc2ffbe4cd530
[Txn]{'from': '0xCDD53a6422696fbc09dc8D1d480378A93f3d605e', 'to': '0x7E7a74909Cab35a0885c9DC55062Ae27b8258297', 'gasPrice': 5000000000, 'gas': 3000000, 'nonce': 0, 'value': 5000, 'data': '0x', 'chainId': 1211}
2022-02-12 19:59:17.475 | SUCCESS  | Poseidon_Blockchain:SendTransactionToChain:169 - 
[ConfirmTransaction]
[TransactionHash]0x354cb6b3307284ed4879c296bed69b45826aab9fb3641f0340ddc2ffbe4cd530
[TransactionReceipt]AttributeDict({'blockHash': HexBytes('0x6db5d0683e2ec503e4379ec9e00af413831919375b79ff87097e68e29ddeee92'), 'blockNumber': 690658, 'contractAddress': None, 'cumulativeGasUsed': 44702, 'effectiveGasPrice': 5000000000, 'from': '0xCDD53a6422696fbc09dc8D1d480378A93f3d605e', 'gasUsed': 44702, 'logs': [AttributeDict({'address': '0x7E7a74909Cab35a0885c9DC55062Ae27b8258297', 'topics': [HexBytes('0xe1fffcc4923d04b559f4d29a8bfc6cda04eb5b0d3c460751c2402c5c5cc9109c'), HexBytes('0x000000000000000000000000cdd53a6422696fbc09dc8d1d480378a93f3d605e')], 'data': '0x0000000000000000000000000000000000000000000000000000000000001388', 'blockNumber': 690658, 'transactionHash': HexBytes('0x354cb6b3307284ed4879c296bed69b45826aab9fb3641f0340ddc2ffbe4cd530'), 'transactionIndex': 0, 'blockHash': HexBytes('0x6db5d0683e2ec503e4379ec9e00af413831919375b79ff87097e68e29ddeee92'), 'logIndex': 0, 'removed': False})], 'logsBloom': HexBytes('0x00000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000040000000000000000002000000000000000000000000000000000000000000000000000000000000000000000000000000000080000000000040000000000000000000000000000400000000000000000'), 'status': 1, 'to': '0x7E7a74909Cab35a0885c9DC55062Ae27b8258297', 'transactionHash': HexBytes('0x354cb6b3307284ed4879c296bed69b45826aab9fb3641f0340ddc2ffbe4cd530'), 'transactionIndex': 0, 'type': '0x0'})
2022-02-12 19:59:17.534 | INFO     | Poseidon_Blockchain:SolidityToAbiAndBytecode:212 - 
[CompileContract]
[Abi][{'constant': True, 'inputs': [], 'name': 'name', 'outputs': [{'name': '', 'type': 'string'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': False, 'inputs': [{'name': 'guy', 'type': 'address'}, {'name': 'wad', 'type': 'uint256'}], 'name': 'approve', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'totalSupply', 'outputs': [{'name': '', 'type': 'uint256'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': False, 'inputs': [{'name': 'src', 'type': 'address'}, {'name': 'dst', 'type': 'address'}, {'name': 'wad', 'type': 'uint256'}], 'name': 'transferFrom', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'constant': False, 'inputs': [{'name': 'wad', 'type': 'uint256'}], 'name': 'withdraw', 'outputs': [], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'decimals', 'outputs': [{'name': '', 'type': 'uint8'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [{'name': '', 'type': 'address'}], 'name': 'balanceOf', 'outputs': [{'name': '', 'type': 'uint256'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'owner', 'outputs': [{'name': '', 'type': 'address'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'isLoan', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': True, 'inputs': [], 'name': 'symbol', 'outputs': [{'name': '', 'type': 'string'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': False, 'inputs': [{'name': 'dst', 'type': 'address'}, {'name': 'wad', 'type': 'uint256'}], 'name': 'transfer', 'outputs': [{'name': '', 'type': 'bool'}], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'constant': False, 'inputs': [], 'name': 'deposit', 'outputs': [], 'payable': True, 'stateMutability': 'payable', 'type': 'function'}, {'constant': True, 'inputs': [{'name': '', 'type': 'address'}, {'name': '', 'type': 'address'}], 'name': 'allowance', 'outputs': [{'name': '', 'type': 'uint256'}], 'payable': False, 'stateMutability': 'view', 'type': 'function'}, {'constant': False, 'inputs': [{'name': 'value', 'type': 'uint256'}, {'name': 'target', 'type': 'address'}, {'name': 'data', 'type': 'bytes'}], 'name': 'fakeflashloan', 'outputs': [], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'function'}, {'inputs': [], 'payable': False, 'stateMutability': 'nonpayable', 'type': 'constructor'}, {'payable': True, 'stateMutability': 'payable', 'type': 'fallback'}, {'anonymous': False, 'inputs': [{'indexed': True, 'name': 'src', 'type': 'address'}, {'indexed': True, 'name': 'guy', 'type': 'address'}, {'indexed': False, 'name': 'wad', 'type': 'uint256'}], 'name': 'Approval', 'type': 'event'}, {'anonymous': False, 'inputs': [{'indexed': True, 'name': 'src', 'type': 'address'}, {'indexed': True, 'name': 'dst', 'type': 'address'}, {'indexed': False, 'name': 'wad', 'type': 'uint256'}], 'name': 'Transfer', 'type': 'event'}, {'anonymous': False, 'inputs': [{'indexed': True, 'name': 'dst', 'type': 'address'}, {'indexed': False, 'name': 'wad', 'type': 'uint256'}], 'name': 'Deposit', 'type': 'event'}, {'anonymous': False, 'inputs': [{'indexed': True, 'name': 'src', 'type': 'address'}, {'indexed': False, 'name': 'wad', 'type': 'uint256'}], 'name': 'Withdrawal', 'type': 'event'}]
[Bytecode]60806040526040805190810160405280600881526020017f564e2045544845520000000000000000000000000000000000000000000000008152506001908051906020019062000051929190620001f2565b506040805190810160405280600581526020017f564e657468000000000000000000000000000000000000000000000000000000815250600290805190602001906200009f929190620001f2565b506012600360006101000a81548160ff021916908360ff1602179055506000600360016101000a81548160ff021916908315150217905550348015620000e457600080fd5b50336000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506ec097ce7bc90715b34b9f1000000000600460008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506ec097ce7bc90715b34b9f1000000000600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550620002a1565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106200023557805160ff191683800117855562000266565b8280016001018555821562000266579182015b828111156200026557825182559160200191906001019062000248565b5b50905062000275919062000279565b5090565b6200029e91905b808211156200029a57600081600090555060010162000280565b5090565b90565b61107880620002b16000396000f3006080604052600436106100d0576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806306fdde03146100da578063095ea7b31461016a57806318160ddd146101cf57806323b872dd146101fa5780632e1a7d4d1461027f578063313ce567146102ac57806370a08231146102dd5780638da5cb5b146103345780639109149e1461038b57806395d89b41146103ba578063a9059cbb1461044a578063d0e30db0146104af578063dd62ed3e146104b9578063f6d5b8c414610530575b6100d86105c3565b005b3480156100e657600080fd5b506100ef610660565b6040518080602001828103825283818151815260200191508051906020019080838360005b8381101561012f578082015181840152602081019050610114565b50505050905090810190601f16801561015c5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b34801561017657600080fd5b506101b5600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001909291905050506106fe565b604051808215151515815260200191505060405180910390f35b3480156101db57600080fd5b506101e46107f0565b6040518082815260200191505060405180910390f35b34801561020657600080fd5b50610265600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff1690602001909291908035906020019092919050505061080f565b604051808215151515815260200191505060405180910390f35b34801561028b57600080fd5b506102aa60048036038101908080359060200190929190505050610b5c565b005b3480156102b857600080fd5b506102c1610c8f565b604051808260ff1660ff16815260200191505060405180910390f35b3480156102e957600080fd5b5061031e600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050610ca2565b6040518082815260200191505060405180910390f35b34801561034057600080fd5b50610349610cba565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b34801561039757600080fd5b506103a0610cdf565b604051808215151515815260200191505060405180910390f35b3480156103c657600080fd5b506103cf610cf2565b6040518080602001828103825283818151815260200191508051906020019080838360005b8381101561040f5780820151818401526020810190506103f4565b50505050905090810190601f16801561043c5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b34801561045657600080fd5b50610495600480360381019080803573ffffffffffffffffffffffffffffffffffffffff16906020019092919080359060200190929190505050610d90565b604051808215151515815260200191505060405180910390f35b6104b76105c3565b005b3480156104c557600080fd5b5061051a600480360381019080803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190505050610da5565b6040518082815260200191505060405180910390f35b34801561053c57600080fd5b506105c160048036038101908080359060200190929190803573ffffffffffffffffffffffffffffffffffffffff169060200190929190803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284378201915050505050509192919290505050610dca565b005b34600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055503373ffffffffffffffffffffffffffffffffffffffff167fe1fffcc4923d04b559f4d29a8bfc6cda04eb5b0d3c460751c2402c5c5cc9109c346040518082815260200191505060405180910390a2565b60018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156106f65780601f106106cb576101008083540402835291602001916106f6565b820191906000526020600020905b8154815290600101906020018083116106d957829003601f168201915b505050505081565b600081600560003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508273ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925846040518082815260200191505060405180910390a36001905092915050565b60003073ffffffffffffffffffffffffffffffffffffffff1631905090565b600081600460008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541015151561085f57600080fd5b3373ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff161415801561093757507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205414155b15610a525781600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054101515156109c757600080fd5b81600560008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055505b81600460008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254039250508190555081600460008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055508273ffffffffffffffffffffffffffffffffffffffff168473ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef846040518082815260200191505060405180910390a3600190509392505050565b80600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205410151515610baa57600080fd5b80600460003373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055503373ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015610c3d573d6000803e3d6000fd5b503373ffffffffffffffffffffffffffffffffffffffff167f7fcf532c15f0a6db0bd6d0e038bea71d30d808c7d98cb3bf7268a95bf5081b65826040518082815260200191505060405180910390a250565b600360009054906101000a900460ff1681565b60046020528060005260406000206000915090505481565b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b600360019054906101000a900460ff1681565b60028054600181600116156101000203166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615610100020316600290048015610d885780601f10610d5d57610100808354040283529160200191610d88565b820191906000526020600020905b815481529060010190602001808311610d6b57829003601f168201915b505050505081565b6000610d9d33848461080f565b905092915050565b6005602052816000526040600020602052806000526040600020600091509150505481565b60001515600360019054906101000a900460ff161515148015610dee575060008310155b8015610dfc57506103e88311155b1515610e0757600080fd5b82600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254039250508190555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825401925050819055508173ffffffffffffffffffffffffffffffffffffffff168160405180828051906020019080838360005b83811015610ee6578082015181840152602081019050610ecb565b50505050905090810190601f168015610f135780820380516001836020036101000a031916815260200191505b509150506000604051808303816000865af1915050506001600360016101000a81548160ff02191690831515021790555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205410151515610f9257600080fd5b82600460003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254019250508190555082600460008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020600082825403925050819055506000600360016101000a81548160ff0219169083151502179055505050505600a165627a7a7230582099b58a520b0d8b8e15b6b90828e34d0040bea564c48d68c46fa05b69f96ec3ee0029
2022-02-12 19:59:17.596 | INFO     | __main__:<module>:30 - 5000
2022-02-12 19:59:17.891 | INFO     | Poseidon_Blockchain:SendTransactionToChain:167 - 
[SendTransaction]
[TransactionHash]0xb00663cc2e9240c63aea8227046f4f508b1f1e5bdf406136ecc6ee5eead1170a
[Txn]{'from': '0xCDD53a6422696fbc09dc8D1d480378A93f3d605e', 'to': '0x3d8fB1A9aaBFEfd8cf5910202d05E664CcBd02D5', 'gasPrice': 5000000000, 'gas': 3000000, 'nonce': 1, 'value': 0, 'data': '0x094cc113', 'chainId': 1211}
2022-02-12 19:59:32.352 | SUCCESS  | Poseidon_Blockchain:SendTransactionToChain:169 - 
[ConfirmTransaction]
[TransactionHash]0xb00663cc2e9240c63aea8227046f4f508b1f1e5bdf406136ecc6ee5eead1170a
[TransactionReceipt]AttributeDict({'blockHash': HexBytes('0xa000e1f4ae1f8ce1ea493c12cf25a84946d9c4aa767b2cd02e17dad0b746679c'), 'blockNumber': 690659, 'contractAddress': None, 'cumulativeGasUsed': 29035, 'effectiveGasPrice': 5000000000, 'from': '0xCDD53a6422696fbc09dc8D1d480378A93f3d605e', 'gasUsed': 29035, 'logs': [], 'logsBloom': HexBytes('0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000'), 'status': 1, 'to': '0x3d8fB1A9aaBFEfd8cf5910202d05E664CcBd02D5', 'transactionHash': HexBytes('0xb00663cc2e9240c63aea8227046f4f508b1f1e5bdf406136ecc6ee5eead1170a'), 'transactionIndex': 0, 'type': '0x0'})
2022-02-12 19:59:32.402 | INFO     | __main__:<module>:34 - True
2022-02-12 19:59:32.452 | INFO     | __main__:<module>:35 - True
2022-02-12 19:59:32.452 | SUCCESS  | __main__:<module>:37 - Execution completed.

12

到服务器提交结果,获得flag。

11

(赛后向出题人询问了一下,确实是题目代码上写漏了,原本应该是代币余额大于5000 ether才满足条件,考察利用闪电贷内的重入攻击实现余额转换,但由于Setup合约代码第14行上少写了ether,导致合约使用了基本单位wei来计量,所以直接转账给VNETH合约5000 weitest ETH就达成了条件。当时也是急着做其他题,这题做出来后就没管了。)

14

如果按原考察意图解法的话我觉得应该是调用VNETH合约的fakeflashloan()进行闪电贷,并call自己的攻击合约,攻击合约内构造持续不断地再调用闪电贷,直到代币余额达到5000 ether(即5000*10**18 wei),之后攻击合约不再调用VNETHfakeflashloan,而是调用Setup合约的checksuccess(),达成解出条件,之后放出执行权,回到VNETH合约,完成闪电贷攻击流程。思路大概是这样,实现起来并不复杂,只需编写攻击合约代为操作即可,时间关系我就不复现正确解法了,理解具体流程即可。关于闪电贷攻击如果想了解更多可以浏览一下这篇文章

Crypto

ezmath

题目附件

首先浏览一遍server.py,寻找关键信息。

4

从此处代码得知,我们需要求出第x个满足条件(2^n-1)%15=0n,并成功提交777次至服务器,才可获得flag。

形式有点像数论领域的欧拉函数,使用简单的脚本寻找一下数学规律。

for i in range(1, 101):
    if (2**i - 1) % 15 == 0:
        print(i, end=" ")
# 4 8 12 16 20 24 28 32 36 40 44 48 52 56 60 64 68 72 76 80 84 88 92 96 100

可以发现,第x个满足条件的n等于4*x,还是比较容易求解的。

剩下的就是与服务器交互的问题了,使用下面的一把梭脚本直接获取flag。

import hashlib
from pwn import *
from pwnlib.util.iters import mbruteforce


def ProofOfWork_SHA256(Url, Port, Length, Begin, SendAfter):
    Connection = remote(Url, Port)
    Connection.recvuntil(Begin)
    s = Connection.recvuntil(") == ", drop=True).decode().strip()
    hash = Connection.recvuntil("\n", drop=True).decode().strip()
    Charset = string.printable
    Proof = mbruteforce(lambda x: hashlib.sha256((x + s).encode()).hexdigest() == hash, Charset, Length, method='fixed')
    Connection.sendlineafter(SendAfter, Proof)
    return Connection


Connection = ProofOfWork_SHA256("node4.buuoj.cn", 29570, 4, "sha256(XXXX+", "XXXX :")

for i in range(777):
    Connection.recvuntil("plz give me the ")
    num = Connection.recvuntil("th (n)", drop=True).decode().strip()
    answer = str(int(num) * 4)
    Connection.sendlineafter("is 15):", answer)

Connection.interactive()

5

Misc

仔细找找

6

题目附件

7

放大图片后发现明显的像素点,尝试将其提取出来合成图片。

在合成过程中发现特殊像素点的间距是不固定的,需要写一段测试脚本将其间距求出,之后再运行完整的图片合成脚本。

(这里使用到了Poseidon_Normal里的RGBToImage()函数)

from PIL import Image
from Poseidon_Normal import *

img = Image.open('flag.png')
img = img.convert('RGB')
xf = [24, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50,
      49, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 49, 50, 50, 49, 50, 50, 49, 50, 49, 50, 50]
yf = [15, 31, 31, 31, 31, 31, 31, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31,
      31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 31]
'''
for i in range(2205):
    if img.getpixel((i, 16)) == (255, 255, 255):
        xf.append(i)
xf.reverse()
for i in range(len(xf) - 1):
    xf[i] -= xf[i + 1]
xf.reverse()
print(xf)

for i in range(2205):
    if img.getpixel((25, i)) == (255, 255, 255):
        yf.append(i)
yf.reverse()
for i in range(len(yf) - 1):
    yf[i] -= yf[i + 1]
yf.reverse()
print(yf)
'''
data = []
x = 0
y = 0
xi = 0
yj = 0
for i in xf:
    xi += i
    x += 1
    yj = 0
    y = 0
    for j in yf:
        yj += j
        y += 1
        r, g, b = img.getpixel((xi, yj))
        data.append((r, g, b))
RGBToImage(data, x, y)

运行脚本后得到flag图片。

8

Web

GameV4.0

签到题,找到疑似flag的信息,Base64解码之后再Url解码,即可得到flag。当然想玩游戏的话也是可以的。

9

10


2 条留言

  1. crazy
    crazy · 2023-08-26 10:18

    这里使用到了Poseidon_Normal里的RGBToImage()函数

    大佬,这个好像不存在了啊

    1. B1ue1nWh1te
      B1ue1nWh1te · 2023-09-01 13:28 作者

      是的,新版已经删去了。

发表留言