编译器
0.8.21+commit.d9974bed
文件 1 的 6:BurnEngine.sol
pragma solidity =0.8.21;
import "./OwnableMaster.sol";
import "./InterfaceHub/IVerseToken.sol";
import "./TransferHub/TransferHelper.sol";
error NoTokens();
error InvalidValue();
contract BurnEngine is OwnableMaster, TransferHelper {
uint256 public burnCost;
IVerseToken public immutable VERSE_TOKEN;
event TokensBurned(
address indexed burner,
uint256 amount
);
event BurnCostUpdated(
address indexed manager,
uint256 newBurnCost
);
constructor(
uint256 _burnCost,
IVerseToken _verseToken
)
OwnableMaster(
msg.sender
)
{
burnCost = _burnCost;
VERSE_TOKEN = _verseToken;
}
function adminBurn()
external
onlyMaster
{
_burn();
}
function userBurn()
external
{
_safeTransferFrom(
address(VERSE_TOKEN),
msg.sender,
address(this),
burnCost
);
_burn();
}
function _burn()
private
{
uint256 balance = VERSE_TOKEN.balanceOf(
address(this)
);
if (balance == 0) {
revert NoTokens();
}
VERSE_TOKEN.burn(
balance
);
emit TokensBurned(
msg.sender,
balance
);
}
function setBurnCost(
uint256 _newBurnCost
)
external
onlyMaster
{
if (_newBurnCost == 0) {
revert InvalidValue();
}
burnCost = _newBurnCost;
emit BurnCostUpdated(
msg.sender,
_newBurnCost
);
}
}
文件 2 的 6:CallOptionalReturn.sol
pragma solidity =0.8.21;
import "../InterfaceHub/IERC20.sol";
error CallFailed();
contract CallOptionalReturn {
function _callOptionalReturn(
address token,
bytes memory data
)
internal
returns (bool call)
{
(
bool success,
bytes memory returndata
) = token.call(
data
);
bool results = returndata.length == 0 || abi.decode(
returndata,
(bool)
);
call = success
&& results
&& token.code.length > 0;
}
}
文件 3 的 6:IERC20.sol
pragma solidity =0.8.21;
interface IERC20 {
function totalSupply()
external
view
returns (uint256);
function balanceOf(
address _account
)
external
view
returns (uint256);
function transferFrom(
address _sender,
address _recipient,
uint256 _amount
)
external
returns (bool);
function transfer(
address _recipient,
uint256 _amount
)
external
returns (bool);
function allowance(
address owner,
address spender
)
external
view
returns (uint256);
function approve(
address _spender,
uint256 _amount
)
external
returns (bool);
function decimals()
external
view
returns (uint8);
event Transfer(
address indexed from,
address indexed to,
uint256 value
);
event Approval(
address indexed owner,
address indexed spender,
uint256 value
);
event Deposit(
address indexed dst,
uint wad
);
event Withdrawal(
address indexed src,
uint wad
);
}
文件 4 的 6:IVerseToken.sol
pragma solidity =0.8.21;
import "./IERC20.sol";
interface IVerseToken is IERC20 {
function burn(
uint256 _value
)
external;
}
文件 5 的 6:OwnableMaster.sol
pragma solidity =0.8.21;
error NoValue();
error NotMaster();
error NotProposed();
contract OwnableMaster {
address public master;
address public proposedMaster;
address internal constant ZERO_ADDRESS = address(0x0);
modifier onlyProposed() {
_onlyProposed();
_;
}
function _onlyMaster()
private
view
{
if (msg.sender == master) {
return;
}
revert NotMaster();
}
modifier onlyMaster() {
_onlyMaster();
_;
}
function _onlyProposed()
private
view
{
if (msg.sender == proposedMaster) {
return;
}
revert NotProposed();
}
event MasterProposed(
address indexed proposer,
address indexed proposedMaster
);
event ClaimedOwnership(
address indexed newMaster,
address indexed previousMaster
);
event RenouncedOwnership(
address indexed previousMaster
);
constructor(
address _master
) {
if (_master == ZERO_ADDRESS) {
revert NoValue();
}
master = _master;
}
function proposeOwner(
address _proposedOwner
)
external
onlyMaster
{
if (_proposedOwner == ZERO_ADDRESS) {
revert NoValue();
}
proposedMaster = _proposedOwner;
emit MasterProposed(
msg.sender,
_proposedOwner
);
}
function claimOwnership()
external
onlyProposed
{
master = proposedMaster;
emit ClaimedOwnership(
master,
msg.sender
);
}
function renounceOwnership()
external
onlyMaster
{
master = ZERO_ADDRESS;
proposedMaster = ZERO_ADDRESS;
emit RenouncedOwnership(
msg.sender
);
}
}
文件 6 的 6:TransferHelper.sol
pragma solidity =0.8.21;
import "./CallOptionalReturn.sol";
contract TransferHelper is CallOptionalReturn {
bytes4 private constant transferSelector = IERC20
.transfer
.selector;
bytes4 private constant transferFromSelector = IERC20
.transferFrom
.selector;
function _safeTransfer(
address _token,
address _to,
uint256 _value
)
internal
{
_callOptionalReturn(
_token,
abi.encodeWithSelector(
transferSelector,
_to,
_value
)
);
}
function _safeTransferFrom(
address _token,
address _from,
address _to,
uint256 _value
)
internal
{
_callOptionalReturn(
_token,
abi.encodeWithSelector(
transferFromSelector,
_from,
_to,
_value
)
);
}
}
{
"compilationTarget": {
"contracts/BurnEngine.sol": "BurnEngine"
},
"evmVersion": "shanghai",
"libraries": {},
"metadata": {
"bytecodeHash": "ipfs"
},
"optimizer": {
"enabled": true,
"runs": 200
},
"remappings": []
}
[{"inputs":[{"internalType":"uint256","name":"_burnCost","type":"uint256"},{"internalType":"contract IVerseToken","name":"_verseToken","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"InvalidValue","type":"error"},{"inputs":[],"name":"NoTokens","type":"error"},{"inputs":[],"name":"NoValue","type":"error"},{"inputs":[],"name":"NotMaster","type":"error"},{"inputs":[],"name":"NotProposed","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"manager","type":"address"},{"indexed":false,"internalType":"uint256","name":"newBurnCost","type":"uint256"}],"name":"BurnCostUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"newMaster","type":"address"},{"indexed":true,"internalType":"address","name":"previousMaster","type":"address"}],"name":"ClaimedOwnership","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"proposer","type":"address"},{"indexed":true,"internalType":"address","name":"proposedMaster","type":"address"}],"name":"MasterProposed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousMaster","type":"address"}],"name":"RenouncedOwnership","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"burner","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"TokensBurned","type":"event"},{"inputs":[],"name":"VERSE_TOKEN","outputs":[{"internalType":"contract IVerseToken","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"adminBurn","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"burnCost","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"claimOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"master","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_proposedOwner","type":"address"}],"name":"proposeOwner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"proposedMaster","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_newBurnCost","type":"uint256"}],"name":"setBurnCost","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"userBurn","outputs":[],"stateMutability":"nonpayable","type":"function"}]