如果你没遇到过这个问题,你会觉得很奇怪,Solidity的关键字require,根据用法解释:https://ethfans.org/posts/when-to-use-revert-assert-and-require-in-solidity 如果括号内条件为false,不是应该返还未消耗的gas吗?
而个人遇到的是,遇到require(false) 反而消耗完了我的gas。
一、我按照网上的一般版本在geth上搭建私有链,创世区块配置文件genesis.json如下:
{
"config":{
"chainId":9,
"homesteadBlock":0,
"eip155Block":0,
"eip158Block":0
},
"nonce":"0x0000000000000042",
"timestamp":"0x0",
"parentHash":"0x0000000000000000000000000000000000000000000000000000000000000000",
"extraData":"0x00000000",
"gasLimit":"0x80000000",
"difficulty":"0x100",
"mixhash":"0x0000000000000000000000000000000000000000000000000000000000000000",
"coinbase":"0x3333333333333333333333333333333333333333",
"alloc": {}
}
二、在remix-ide编写合约如下:
pragma solidity ^0.4.22;
contract aPlusb{
function aPlusb(){}
uint a=1;
event happen(uint input,uint output);
function plus(uint a,uint b) returns (uint){
require(a==2);
happen(a,a+1);
return a+1;
}
}
三、在remix-ide的虚拟机测试合约,调用plus()方法,require正常返还gas
四、利用remix-ide连接我在geth搭建的私有链后,部署合约到私有链,再调用plus()方法,则会消耗完我所有的gas,如下:
五、国内查阅相关情况:无果。
六、google查阅相关资料:
七、无奈之下,个人在 ethereum.stackexchange.com 提交问题,幸好有大神回复如下:
https://ethereum.stackexchange.com/questions/63348/solidity-keyword-require-false-will-run-out-of-my-gas-why
八、解决方案
1、修改创世区块文件,在config选项中加入拜占庭版本的起始区块,如果不设置,大概要挖到 4,370,000区块,require才能正常使用。
新的创世区块配置文件如下:
{
"config":{
"chainId":9,
"homesteadBlock":0,
"eip155Block":0,
"eip158Block":0,
"byzantiumBlock":0
},
"nonce":"0x0000000000000042",
"timestamp":"0x0",
"parentHash":"0x0000000000000000000000000000000000000000000000000000000000000000",
"extraData":"0x00000000",
"gasLimit":"0x80000000",
"difficulty":"0x100",
"mixhash":"0x0000000000000000000000000000000000000000000000000000000000000000",
"coinbase":"0x3333333333333333333333333333333333333333",
"alloc": {}
}
2、重新部署
3、启动节点
geth --datadir "./" --networkid 9541 -rpc console --port 30304 --rpcport 8545 --rpccorsdomain "*" --ws --wsorigins="*" --wsaddr 0.0.0.0 --nodiscover --syncmode=full
4、测试,require正确返回未消耗的gas。问题解决。