
前言
- 复现 
balsn2019 ctf中的Creativity区块链题目 - 这道题其实早就想复现了,只不过一直没有复现成功,是有关 
create2的骚操作,基本操作可参考另外一片文章https://hitcxy.com/2020/Create2/ - 具体分析及官方 
WP如下: https://x9453.github.io/2020/01/04/Balsn-CTF-2019-Creativity/ - 原谅我菜的抠脚…都 
2020了,还在做2019的题目 - 复现地址为: 
ropsten@0x3975c105e8D582A324F6093E7471fDf9d5b9Fa67 
Source
1  | pragma solidity ^0.5.10;  | 
Analyse
题目大概逻辑是:
- 让我们部署一个合约,合约代码大小不超过4字节
 - 调用 
check,参数是我们部署的合约地址 - 调用 
execute,执行delegatecall到我们部署的合约内 
但是,有个问题,我们没法在4个字节内
emit SendFlag- 其实题目考查知识点为 
Create2的骚操作: 在同一个地址上部署合约,合约的字节码可以不同,即在同一个地址上先后可部署不同的合约 - 通过调用下面 
Deployer.deploy函数,我们可以把不同合约先后部署在同一个地址上,deployedAddr即为部署的合约地址 
1  | pragma solidity ^0.5.10;  | 
- 所以题目的逻辑如下:
- 用 
create2的骚操作,部署一个合约0x33ff,即selfdestruct(msg.sender) - 调用 
check(),让target为我们部署的合约地址 - 给我们部署的合约发一笔空交易,让它自毁
 - 再次使用 
create2骚操作,在同一个地址部署合约,合约内容为emit SendFlag(0) - 调用 
execute(),就会执行我们第二次部署的合约的emit SendFlag事件,因为是delegatecall操作,所以还是相当于在原题目合约中进行的emit SendFlag操作,成功! 
 - 用 
 
Solution
- 先将 
Deployer部署,地址为0x307FdF03B1842A501F52221e4cF02D67BfeEc399, 然后使用Deployer.deploy部署0x33ff,得到部署的合约地址0x2b473f517088f6d08e82cA06dD5A5e6A68Eb4663 

- 调用 
check(),target已经变成了我们部署的合约地址 

- 给我们部署的合约发一笔空交易,让它自毁,目的是为了重新在这个地址部署合约触发 
SendFlag事件,可以看到部署的合约已经自毁 
1  | web3.eth.sendTransaction({ from: '0x785a8D0d84ad29c96f8e1F26BfDb3E6CB72cAe9b', to: "0x2b473f517088f6d08e82cA06dD5A5e6A68Eb4663", data: "" }, function(err,res){console.log(res)});  | 

- 使用 
create2骚操作,在同一个地址部署合约,合约内容为emit SendFlag(0),这里我是写了一个hack合约,然后使用Deployer.deploy部署 
1  | contract hack {  | 
- 这样就把内容为 
emit SendFlag的hack合约给部署到同一个地址0x2b473f517088f6d08e82cA06dD5A5e6A68Eb4663上了,如下图 

- 调用 
execute(),就会执行我们第二次部署的合约的emit SendFlag事件 

- 完结!!!🎉🎉🎉🎉🎉🎉
 
