Warning! Contract bytecode has been changed and doesn't match the verified one. Therefore, interaction with this smart contract may be risky.
- Contract name:
- TaikoL2
- Optimization enabled
- true
- Compiler version
- v0.8.24+commit.e11b9ed9
- Optimization runs
- 200
- EVM Version
- cancun
- Verified at
- 2024-05-26T02:14:00.202253Z
contracts/L2/TaikoL2.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;import "@openzeppelin/contracts/token/ERC20/IERC20.sol";import "@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol";import "../common/EssentialContract.sol";import "../common/LibStrings.sol";import "../libs/LibAddress.sol";import "../signal/ISignalService.sol";import "./Lib1559Math.sol";import "./LibL2Config.sol";/// @title TaikoL2/// @notice Taiko L2 is a smart contract that handles cross-layer message/// verification and manages EIP-1559 gas pricing for Layer 2 (L2) operations./// It is used to anchor the latest L1 block details to L2 for cross-layer/// communication, manage EIP-1559 parameters for gas pricing, and store/// verified L1 block information./// @custom:security-contact security@taiko.xyzcontract TaikoL2 is EssentialContract {using LibAddress for address;using SafeERC20 for IERC20;/// @notice Golden touch address is the only address that can do the anchor transaction.address public constant GOLDEN_TOUCH_ADDRESS = 0x0000777735367b36bC9B61C50022d9D0700dB4Ec;/// @notice Mapping from L2 block numbers to their block hashes. All L2 block hashes will/// be saved in this mapping.mapping(uint256 blockId => bytes32 blockHash) public l2Hashes;/// @notice A hash to check the integrity of public inputs./// @dev Slot 2.bytes32 public publicInputHash;/// @notice The gas excess value used to calculate the base fee./// @dev Slot 3.uint64 public gasExcess;/// @notice The last synced L1 block height.uint64 public lastSyncedBlock;
contracts/L2/Lib1559Math.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;import "../thirdparty/solmate/LibFixedPointMath.sol";import "../libs/LibMath.sol";/// @title Lib1559Math/// @notice Implements e^(x) based bonding curve for EIP-1559/// @dev See https://ethresear.ch/t/make-eip-1559-more-like-an-amm-curve/9082 but some minor/// difference as stated in docs/eip1559_on_l2.md./// @custom:security-contact security@taiko.xyzlibrary Lib1559Math {using LibMath for uint256;error EIP1559_INVALID_PARAMS();function calc1559BaseFee(uint32 _gasTargetPerL1Block,uint8 _adjustmentQuotient,uint64 _gasExcess,uint64 _gasIssuance,uint32 _parentGasUsed)internalpurereturns (uint256 basefee_, uint64 gasExcess_){// We always add the gas used by parent block to the gas excess// value as this has already happeneduint256 excess = uint256(_gasExcess) + _parentGasUsed;excess = excess > _gasIssuance ? excess - _gasIssuance : 1;gasExcess_ = uint64(excess.min(type(uint64).max));// The base fee per gas used by this block is the spot price at the// bonding curve, regardless the actual amount of gas used by this// block, however, this block's gas used will affect the next// block's base fee.basefee_ = basefee(gasExcess_, uint256(_adjustmentQuotient) * _gasTargetPerL1Block);// Always make sure basefee is nonzero, this is required by the node.if (basefee_ == 0) basefee_ = 1;
contracts/L2/LibL2Config.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title LibL2Configlibrary LibL2Config {struct Config {uint32 gasTargetPerL1Block;uint8 basefeeAdjustmentQuotient;}/// @notice Returns EIP1559 related configurations./// @return config_ struct containing configuration parameters.function get() internal pure returns (Config memory config_) {// Assuming we sell 3x more blockspace than Ethereum: 15_000_000 * 4// Note that Brecht's concern is that this value may be too large.// We need to monitor L2 state growth and lower this value when necessary.config_.gasTargetPerL1Block = 60_000_000;config_.basefeeAdjustmentQuotient = 8;}}
contracts/common/AddressResolver.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";import "./IAddressManager.sol";import "./IAddressResolver.sol";/// @title AddressResolver/// @notice See the documentation in {IAddressResolver}./// @custom:security-contact security@taiko.xyzabstract contract AddressResolver is IAddressResolver, Initializable {/// @notice Address of the AddressManager.address public addressManager;uint256[49] private __gap;error RESOLVER_DENIED();error RESOLVER_INVALID_MANAGER();error RESOLVER_UNEXPECTED_CHAINID();error RESOLVER_ZERO_ADDR(uint64 chainId, bytes32 name);/// @dev Modifier that ensures the caller is the resolved address of a given/// name./// @param _name The name to check against.modifier onlyFromNamed(bytes32 _name) {if (msg.sender != resolve(_name, true)) revert RESOLVER_DENIED();_;}/// @dev Modifier that ensures the caller is a resolved address to either _name1 or _name2/// name./// @param _name1 The first name to check against./// @param _name2 The second name to check against.modifier onlyFromNamedEither(bytes32 _name1, bytes32 _name2) {if (msg.sender != resolve(_name1, true) && msg.sender != resolve(_name2, true)) {revert RESOLVER_DENIED();}_;}/// @custom:oz-upgrades-unsafe-allow constructorconstructor() {
contracts/common/EssentialContract.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;import "@openzeppelin/contracts/proxy/utils/UUPSUpgradeable.sol";import "@openzeppelin/contracts-upgradeable/access/Ownable2StepUpgradeable.sol";import "./AddressResolver.sol";import "../libs/LibNetwork.sol";/// @title EssentialContract/// @custom:security-contact security@taiko.xyzabstract contract EssentialContract is UUPSUpgradeable, Ownable2StepUpgradeable, AddressResolver {uint8 private constant _FALSE = 1;uint8 private constant _TRUE = 2;/// @dev The slot in transient storage of the reentry lock./// This is the result of keccak256("ownerUUPS.reentry_slot") plus 1. The addition aims to/// prevent hash collisions with slots defined in EIP-1967, where slots are derived by/// keccak256("something") - 1, and with slots in SignalService, calculated directly with/// keccak256("something").bytes32 private constant _REENTRY_SLOT =0xa5054f728453d3dbe953bdc43e4d0cb97e662ea32d7958190f3dc2da31d9721b;/// @dev Slot 1.uint8 private __reentry;uint8 private __paused;uint64 public lastUnpausedAt;uint256[49] private __gap;/// @notice Emitted when the contract is paused./// @param account The account that paused the contract.event Paused(address account);/// @notice Emitted when the contract is unpaused./// @param account The account that unpaused the contract.event Unpaused(address account);error INVALID_PAUSE_STATUS();error FUNC_NOT_IMPLEMENTED();error REENTRANT_CALL();
contracts/common/IAddressManager.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title IAddressManager/// @notice Manages a mapping of (chainId, name) pairs to Ethereum addresses./// @custom:security-contact security@taiko.xyzinterface IAddressManager {/// @notice Gets the address mapped to a specific chainId-name pair./// @dev Note that in production, this method shall be a pure function/// without any storage access./// @param _chainId The chainId for which the address needs to be fetched./// @param _name The name for which the address needs to be fetched./// @return Address associated with the chainId-name pair.function getAddress(uint64 _chainId, bytes32 _name) external view returns (address);}
contracts/common/IAddressResolver.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title IAddressResolver/// @notice This contract acts as a bridge for name-to-address resolution./// It delegates the resolution to the AddressManager. By separating the logic,/// we can maintain flexibility in address management without affecting the/// resolving process./// @dev Note that the address manager should be changed using upgradability, there/// is no setAddressManager() function to guarantee atomicity across all/// contracts that are resolvers./// @custom:security-contact security@taiko.xyzinterface IAddressResolver {/// @notice Resolves a name to its address deployed on this chain./// @param _name Name whose address is to be resolved./// @param _allowZeroAddress If set to true, does not throw if the resolved/// address is `address(0)`./// @return Address associated with the given name.function resolve(bytes32 _name,bool _allowZeroAddress)externalviewreturns (address payable);/// @notice Resolves a name to its address deployed on a specified chain./// @param _chainId The chainId of interest./// @param _name Name whose address is to be resolved./// @param _allowZeroAddress If set to true, does not throw if the resolved/// address is `address(0)`./// @return Address associated with the given name on the specified/// chain.function resolve(uint64 _chainId,bytes32 _name,bool _allowZeroAddress)externalviewreturns (address payable);
contracts/common/LibStrings.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title LibStrings/// @custom:security-contact security@taiko.xyzlibrary LibStrings {bytes32 internal constant B_ASSIGNMENT_HOOK = bytes32("assignment_hook");bytes32 internal constant B_AUTOMATA_DCAP_ATTESTATION = bytes32("automata_dcap_attestation");bytes32 internal constant B_BRIDGE = bytes32("bridge");bytes32 internal constant B_BRIDGE_WATCHDOG = bytes32("bridge_watchdog");bytes32 internal constant B_BRIDGED_ERC1155 = bytes32("bridged_erc1155");bytes32 internal constant B_BRIDGED_ERC20 = bytes32("bridged_erc20");bytes32 internal constant B_BRIDGED_ERC721 = bytes32("bridged_erc721");bytes32 internal constant B_CHAIN_WATCHDOG = bytes32("chain_watchdog");bytes32 internal constant B_ERC1155_VAULT = bytes32("erc1155_vault");bytes32 internal constant B_ERC20_VAULT = bytes32("erc20_vault");bytes32 internal constant B_ERC721_VAULT = bytes32("erc721_vault");bytes32 internal constant B_PROPOSER = bytes32("proposer");bytes32 internal constant B_PROPOSER_ONE = bytes32("proposer_one");bytes32 internal constant B_PROVER_ASSIGNMENT = bytes32("PROVER_ASSIGNMENT");bytes32 internal constant B_PROVER_SET = bytes32("prover_set");bytes32 internal constant B_QUOTA_MANAGER = bytes32("quota_manager");bytes32 internal constant B_SGX_WATCHDOG = bytes32("sgx_watchdog");bytes32 internal constant B_SIGNAL_SERVICE = bytes32("signal_service");bytes32 internal constant B_TAIKO = bytes32("taiko");bytes32 internal constant B_TAIKO_TOKEN = bytes32("taiko_token");bytes32 internal constant B_TIER_GUARDIAN = bytes32("tier_guardian");bytes32 internal constant B_TIER_GUARDIAN_MINORITY = bytes32("tier_guardian_minority");bytes32 internal constant B_TIER_PROVIDER = bytes32("tier_provider");bytes32 internal constant B_TIER_SGX = bytes32("tier_sgx");bytes32 internal constant B_TIER_SGX_ZKVM = bytes32("tier_sgx_zkvm");bytes32 internal constant B_WITHDRAWER = bytes32("withdrawer");bytes32 internal constant H_RETURN_LIVENESS_BOND = keccak256("RETURN_LIVENESS_BOND");bytes32 internal constant H_SIGNAL_ROOT = keccak256("SIGNAL_ROOT");bytes32 internal constant H_STATE_ROOT = keccak256("STATE_ROOT");}
contracts/libs/LibAddress.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;import "@openzeppelin/contracts/utils/Address.sol";import "@openzeppelin/contracts/utils/introspection/IERC165.sol";import "@openzeppelin/contracts/interfaces/IERC1271.sol";/// @title LibAddress/// @dev Provides utilities for address-related operations./// @custom:security-contact security@taiko.xyzlibrary LibAddress {error ETH_TRANSFER_FAILED();/// @dev Sends Ether to the specified address. This method will not revert even if sending ether/// fails./// This function is inspired by/// https://github.com/nomad-xyz/ExcessivelySafeCall/blob/main/src/ExcessivelySafeCall.sol/// @param _to The recipient address./// @param _amount The amount of Ether to send in wei./// @param _gasLimit The max amount gas to pay for this transaction./// @return success_ true if the call is successful, false otherwise.function sendEther(address _to,uint256 _amount,uint256 _gasLimit,bytes memory _calldata)internalreturns (bool success_){// Check for zero-address transactionsif (_to == address(0)) revert ETH_TRANSFER_FAILED();// dispatch message to recipient// by assembly calling "handle" function// we call via assembly to avoid memcopying a very large returndata// returned by a malicious contractassembly {success_ :=call(_gasLimit, // gas_to, // recipient
contracts/libs/LibMath.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title LibMath/// @dev This library offers additional math functions for uint256./// @custom:security-contact security@taiko.xyzlibrary LibMath {/// @dev Returns the smaller of the two given values./// @param _a The first number to compare./// @param _b The second number to compare./// @return The smaller of the two numbers.function min(uint256 _a, uint256 _b) internal pure returns (uint256) {return _a > _b ? _b : _a;}/// @dev Returns the larger of the two given values./// @param _a The first number to compare./// @param _b The second number to compare./// @return The larger of the two numbers.function max(uint256 _a, uint256 _b) internal pure returns (uint256) {return _a > _b ? _a : _b;}}
contracts/libs/LibNetwork.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title LibNetworklibrary LibNetwork {uint256 internal constant MAINNET = 1;uint256 internal constant ROPSTEN = 2;uint256 internal constant RINKEBY = 4;uint256 internal constant GOERLI = 5;uint256 internal constant KOVAN = 42;uint256 internal constant HOLESKY = 17_000;uint256 internal constant SEPOLIA = 11_155_111;uint64 internal constant TAIKO = 167_000;/// @dev Checks if the chain ID represents an Ethereum testnet./// @param _chainId The chain ID./// @return true if the chain ID represents an Ethereum testnet, false otherwise.function isEthereumTestnet(uint256 _chainId) internal pure returns (bool) {return _chainId == LibNetwork.ROPSTEN || _chainId == LibNetwork.RINKEBY|| _chainId == LibNetwork.GOERLI || _chainId == LibNetwork.KOVAN|| _chainId == LibNetwork.HOLESKY || _chainId == LibNetwork.SEPOLIA;}/// @dev Checks if the chain ID represents an Ethereum testnet or the Etheruem mainnet./// @param _chainId The chain ID./// @return true if the chain ID represents an Ethereum testnet or the Etheruem mainnet, false/// otherwise.function isEthereumMainnetOrTestnet(uint256 _chainId) internal pure returns (bool) {return _chainId == LibNetwork.MAINNET || isEthereumTestnet(_chainId);}/// @dev Checks if the chain ID represents the Taiko L2 mainnet./// @param _chainId The chain ID./// @return true if the chain ID represents the Taiko L2 mainnet.function isTaikoMainnet(uint256 _chainId) internal pure returns (bool) {return _chainId == TAIKO;}/// @dev Checks if the chain ID represents an internal Taiko devnet's base layer./// @param _chainId The chain ID.
contracts/signal/ISignalService.sol
// SPDX-License-Identifier: MITpragma solidity 0.8.24;/// @title ISignalService/// @notice The SignalService contract serves as a secure cross-chain message/// passing system. It defines methods for sending and verifying signals with/// merkle proofs. The trust assumption is that the target chain has secure/// access to the merkle root (such as Taiko injects it in the anchor/// transaction). With this, verifying a signal is reduced to simply verifying/// a merkle proof./// @custom:security-contact security@taiko.xyzinterface ISignalService {enum CacheOption {CACHE_NOTHING,CACHE_SIGNAL_ROOT,CACHE_STATE_ROOT,CACHE_BOTH}struct HopProof {/// @notice This hop's destination chain ID. If there is a next hop, this ID is the next/// hop's source chain ID.uint64 chainId;/// @notice The ID of a source chain block whose state root has been synced to the hop's/// destination chain./// Note that this block ID must be greater than or equal to the block ID where the signal/// was sent on the source chain.uint64 blockId;/// @notice The state root or signal root of the source chain at the above blockId. This/// value has been synced to the destination chain./// @dev To get both the blockId and the rootHash, apps should subscribe to the/// ChainDataSynced event or query `topBlockId` first using the source chain's ID and/// LibStrings.H_STATE_ROOT to get the most recent block ID synced, then call/// `getSyncedChainData` to read the synchronized data.bytes32 rootHash;/// @notice Options to cache either the state roots or signal roots of middle-hops to the/// current chain.CacheOption cacheOption;/// @notice The signal service's account proof. If this value is empty, then `rootHash` will/// be used as the signal root, otherwise, `rootHash` will be used as the state root.bytes[] accountProof;
contracts/thirdparty/solmate/LibFixedPointMath.sol
// SPDX-License-Identifier: MIT// Taken from the contract below, expWad() function tailored to Taiko's need// https://github.com/transmissions11/solmate/blob/v7/src/utils/FixedPointMathLib.solpragma solidity 0.8.24;library LibFixedPointMath {uint128 public constant MAX_EXP_INPUT = 135_305_999_368_893_231_588;uint256 public constant SCALING_FACTOR = 1e18; // For fixed point representation factorerror Overflow();// Computes e^x in 1e18 fixed point.function exp(int256 x) internal pure returns (int256 r) {unchecked {// Input x is in fixed point format, with scale factor 1/1e18.// When the result is < 0.5 we return zero. This happens when// x <= floor(log(0.5e18) * 1e18) ~ -42e18if (x <= -42_139_678_854_452_767_551) {return 0;}// When the result is > (2**255 - 1) / 1e18 we can not represent it// as an int256. This happens when x >= floor(log((2**255 -1) /// 1e18) * 1e18) ~ 135.if (x >= 135_305_999_368_893_231_589) revert Overflow();// x is now in the range (-42, 136) * 1e18. Convert to (-42, 136) *// 2**96// for more intermediate precision and a binary basis. This base// conversion// is a multiplication by 1e18 / 2**96 = 5**18 / 2**78.x = (x << 78) / 5 ** 18;// Reduce range of x to (-½ ln 2, ½ ln 2) * 2**96 by factoring out// powers of two// such that exp(x) = exp(x') * 2**k, where k is an integer.// Solving this gives k = round(x / log(2)) and x' = x - k * log(2).int256 k = ((x << 96) / 54_916_777_467_707_473_351_141_471_128 + 2 ** 95) >> 96;x = x - k * 54_916_777_467_707_473_351_141_471_128;// k is in the range [-61, 195].
node_modules/@openzeppelin/contracts-upgradeable/access/Ownable2StepUpgradeable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (access/Ownable2Step.sol)pragma solidity ^0.8.0;import "./OwnableUpgradeable.sol";import {Initializable} from "../proxy/utils/Initializable.sol";/*** @dev Contract module which provides access control mechanism, where* there is an account (an owner) that can be granted exclusive access to* specific functions.** By default, the owner account will be the one that deploys the contract. This* can later be changed with {transferOwnership} and {acceptOwnership}.** This module is used through inheritance. It will make available all functions* from parent (Ownable).*/abstract contract Ownable2StepUpgradeable is Initializable, OwnableUpgradeable {address private _pendingOwner;event OwnershipTransferStarted(address indexed previousOwner, address indexed newOwner);function __Ownable2Step_init() internal onlyInitializing {__Ownable_init_unchained();}function __Ownable2Step_init_unchained() internal onlyInitializing {}/*** @dev Returns the address of the pending owner.*/function pendingOwner() public view virtual returns (address) {return _pendingOwner;}/*** @dev Starts the ownership transfer of the contract to a new account. Replaces the pending transfer if there is one.* Can only be called by the current owner.*/
node_modules/@openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (access/Ownable.sol)pragma solidity ^0.8.0;import "../utils/ContextUpgradeable.sol";import {Initializable} from "../proxy/utils/Initializable.sol";/*** @dev Contract module which provides a basic access control mechanism, where* there is an account (an owner) that can be granted exclusive access to* specific functions.** By default, the owner account will be the one that deploys the contract. This* can later be changed with {transferOwnership}.** This module is used through inheritance. It will make available the modifier* `onlyOwner`, which can be applied to your functions to restrict their use to* the owner.*/abstract contract OwnableUpgradeable is Initializable, ContextUpgradeable {address private _owner;event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);/*** @dev Initializes the contract setting the deployer as the initial owner.*/function __Ownable_init() internal onlyInitializing {__Ownable_init_unchained();}function __Ownable_init_unchained() internal onlyInitializing {_transferOwnership(_msgSender());}/*** @dev Throws if called by any account other than the owner.*/modifier onlyOwner() {_checkOwner();
node_modules/@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (proxy/utils/Initializable.sol)pragma solidity ^0.8.2;import "../../utils/AddressUpgradeable.sol";/*** @dev This is a base contract to aid in writing upgradeable contracts, or any kind of contract that will be deployed* behind a proxy. Since proxied contracts do not make use of a constructor, it's common to move constructor logic to an* external initializer function, usually called `initialize`. It then becomes necessary to protect this initializer* function so it can only be called once. The {initializer} modifier provided by this contract will have this effect.** The initialization functions use a version number. Once a version number is used, it is consumed and cannot be* reused. This mechanism prevents re-execution of each "step" but allows the creation of new initialization steps in* case an upgrade adds a module that needs to be initialized.** For example:** [.hljs-theme-light.nopadding]* ```solidity* contract MyToken is ERC20Upgradeable {* function initialize() initializer public {* __ERC20_init("MyToken", "MTK");* }* }** contract MyTokenV2 is MyToken, ERC20PermitUpgradeable {* function initializeV2() reinitializer(2) public {* __ERC20Permit_init("MyToken");* }* }* ```** TIP: To avoid leaving the proxy in an uninitialized state, the initializer function should be called as early as* possible by providing the encoded function call as the `_data` argument to {ERC1967Proxy-constructor}.** CAUTION: When used with inheritance, manual care must be taken to not invoke a parent initializer twice, or to ensure* that all initializers are idempotent. This is not verified automatically as constructors are by Solidity.** [CAUTION]
node_modules/@openzeppelin/contracts-upgradeable/utils/AddressUpgradeable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (utils/Address.sol)pragma solidity ^0.8.1;/*** @dev Collection of functions related to the address type*/library AddressUpgradeable {/*** @dev Returns true if `account` is a contract.** [IMPORTANT]* ====* It is unsafe to assume that an address for which this function returns* false is an externally-owned account (EOA) and not a contract.** Among others, `isContract` will return false for the following* types of addresses:** - an externally-owned account* - a contract in construction* - an address where a contract will be created* - an address where a contract lived, but was destroyed** Furthermore, `isContract` will also return true if the target contract within* the same transaction is already scheduled for destruction by `SELFDESTRUCT`,* which only has an effect at the end of a transaction.* ====** [IMPORTANT]* ====* You shouldn't rely on `isContract` to protect against flash loan attacks!** Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract* constructor.* ====*/function isContract(address account) internal view returns (bool) {// This method relies on extcodesize/address.code.length, which returns 0
node_modules/@openzeppelin/contracts-upgradeable/utils/ContextUpgradeable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.4) (utils/Context.sol)pragma solidity ^0.8.0;import {Initializable} from "../proxy/utils/Initializable.sol";/*** @dev Provides information about the current execution context, including the* sender of the transaction and its data. While these are generally available* via msg.sender and msg.data, they should not be accessed in such a direct* manner, since when dealing with meta-transactions the account sending and* paying for execution may not be the actual sender (as far as an application* is concerned).** This contract is only required for intermediate, library-like contracts.*/abstract contract ContextUpgradeable is Initializable {function __Context_init() internal onlyInitializing {}function __Context_init_unchained() internal onlyInitializing {}function _msgSender() internal view virtual returns (address) {return msg.sender;}function _msgData() internal view virtual returns (bytes calldata) {return msg.data;}function _contextSuffixLength() internal view virtual returns (uint256) {return 0;}/*** @dev This empty reserved space is put in place to allow future versions to add new* variables without shifting down storage in the inheritance chain.* See https://docs.openzeppelin.com/contracts/4.x/upgradeable#storage_gaps*/uint256[50] private __gap;}
node_modules/@openzeppelin/contracts/interfaces/IERC1271.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts v4.4.1 (interfaces/IERC1271.sol)pragma solidity ^0.8.0;/*** @dev Interface of the ERC1271 standard signature validation method for* contracts as defined in https://eips.ethereum.org/EIPS/eip-1271[ERC-1271].** _Available since v4.1._*/interface IERC1271 {/*** @dev Should return whether the signature provided is valid for the provided data* @param hash Hash of the data to be signed* @param signature Signature byte array associated with _data*/function isValidSignature(bytes32 hash, bytes memory signature) external view returns (bytes4 magicValue);}
node_modules/@openzeppelin/contracts/interfaces/IERC1967.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (interfaces/IERC1967.sol)pragma solidity ^0.8.0;/*** @dev ERC-1967: Proxy Storage Slots. This interface contains the events defined in the ERC.** _Available since v4.8.3._*/interface IERC1967 {/*** @dev Emitted when the implementation is upgraded.*/event Upgraded(address indexed implementation);/*** @dev Emitted when the admin account has changed.*/event AdminChanged(address previousAdmin, address newAdmin);/*** @dev Emitted when the beacon is changed.*/event BeaconUpgraded(address indexed beacon);}
node_modules/@openzeppelin/contracts/interfaces/draft-IERC1822.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.5.0) (interfaces/draft-IERC1822.sol)pragma solidity ^0.8.0;/*** @dev ERC1822: Universal Upgradeable Proxy Standard (UUPS) documents a method for upgradeability through a simplified* proxy whose upgrades are fully controlled by the current implementation.*/interface IERC1822Proxiable {/*** @dev Returns the storage slot that the proxiable contract assumes is being used to store the implementation* address.** IMPORTANT: A proxy pointing at a proxiable contract should not be considered proxiable itself, because this risks* bricking a proxy that upgrades to it, by delegating to itself until out of gas. Thus it is critical that this* function revert if invoked through a proxy.*/function proxiableUUID() external view returns (bytes32);}
node_modules/@openzeppelin/contracts/proxy/ERC1967/ERC1967Upgrade.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (proxy/ERC1967/ERC1967Upgrade.sol)pragma solidity ^0.8.2;import "../beacon/IBeacon.sol";import "../../interfaces/IERC1967.sol";import "../../interfaces/draft-IERC1822.sol";import "../../utils/Address.sol";import "../../utils/StorageSlot.sol";/*** @dev This abstract contract provides getters and event emitting update functions for* https://eips.ethereum.org/EIPS/eip-1967[EIP1967] slots.** _Available since v4.1._*/abstract contract ERC1967Upgrade is IERC1967 {// This is the keccak-256 hash of "eip1967.proxy.rollback" subtracted by 1bytes32 private constant _ROLLBACK_SLOT = 0x4910fdfa16fed3260ed0e7147f7cc6da11a60208b5b9406d12a635614ffd9143;/*** @dev Storage slot with the address of the current implementation.* This is the keccak-256 hash of "eip1967.proxy.implementation" subtracted by 1, and is* validated in the constructor.*/bytes32 internal constant _IMPLEMENTATION_SLOT = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc;/*** @dev Returns the current implementation address.*/function _getImplementation() internal view returns (address) {return StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value;}/*** @dev Stores a new address in the EIP1967 implementation slot.*/function _setImplementation(address newImplementation) private {require(Address.isContract(newImplementation), "ERC1967: new implementation is not a contract");StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value = newImplementation;
node_modules/@openzeppelin/contracts/proxy/beacon/IBeacon.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts v4.4.1 (proxy/beacon/IBeacon.sol)pragma solidity ^0.8.0;/*** @dev This is the interface that {BeaconProxy} expects of its beacon.*/interface IBeacon {/*** @dev Must return an address that can be used as a delegate call target.** {BeaconProxy} will check that this address is a contract.*/function implementation() external view returns (address);}
node_modules/@openzeppelin/contracts/proxy/utils/UUPSUpgradeable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (proxy/utils/UUPSUpgradeable.sol)pragma solidity ^0.8.0;import "../../interfaces/draft-IERC1822.sol";import "../ERC1967/ERC1967Upgrade.sol";/*** @dev An upgradeability mechanism designed for UUPS proxies. The functions included here can perform an upgrade of an* {ERC1967Proxy}, when this contract is set as the implementation behind such a proxy.** A security mechanism ensures that an upgrade does not turn off upgradeability accidentally, although this risk is* reinstated if the upgrade retains upgradeability but removes the security mechanism, e.g. by replacing* `UUPSUpgradeable` with a custom implementation of upgrades.** The {_authorizeUpgrade} function must be overridden to include access restriction to the upgrade mechanism.** _Available since v4.1._*/abstract contract UUPSUpgradeable is IERC1822Proxiable, ERC1967Upgrade {/// @custom:oz-upgrades-unsafe-allow state-variable-immutable state-variable-assignmentaddress private immutable __self = address(this);/*** @dev Check that the execution is being performed through a delegatecall call and that the execution context is* a proxy contract with an implementation (as defined in ERC1967) pointing to self. This should only be the case* for UUPS and transparent proxies that are using the current contract as their implementation. Execution of a* function through ERC1167 minimal proxies (clones) would not normally pass this test, but is not guaranteed to* fail.*/modifier onlyProxy() {require(address(this) != __self, "Function must be called through delegatecall");require(_getImplementation() == __self, "Function must be called through active proxy");_;}/*** @dev Check that the execution is not being performed through a delegate call. This allows a function to be* callable on the implementing contract but not through proxies.*/
node_modules/@openzeppelin/contracts/token/ERC20/IERC20.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (token/ERC20/IERC20.sol)pragma solidity ^0.8.0;/*** @dev Interface of the ERC20 standard as defined in the EIP.*/interface IERC20 {/*** @dev Emitted when `value` tokens are moved from one account (`from`) to* another (`to`).** Note that `value` may be zero.*/event Transfer(address indexed from, address indexed to, uint256 value);/*** @dev Emitted when the allowance of a `spender` for an `owner` is set by* a call to {approve}. `value` is the new allowance.*/event Approval(address indexed owner, address indexed spender, uint256 value);/*** @dev Returns the amount of tokens in existence.*/function totalSupply() external view returns (uint256);/*** @dev Returns the amount of tokens owned by `account`.*/function balanceOf(address account) external view returns (uint256);/*** @dev Moves `amount` tokens from the caller's account to `to`.** Returns a boolean value indicating whether the operation succeeded.** Emits a {Transfer} event.*/function transfer(address to, uint256 amount) external returns (bool);
node_modules/@openzeppelin/contracts/token/ERC20/extensions/IERC20Permit.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.4) (token/ERC20/extensions/IERC20Permit.sol)pragma solidity ^0.8.0;/*** @dev Interface of the ERC20 Permit extension allowing approvals to be made via signatures, as defined in* https://eips.ethereum.org/EIPS/eip-2612[EIP-2612].** Adds the {permit} method, which can be used to change an account's ERC20 allowance (see {IERC20-allowance}) by* presenting a message signed by the account. By not relying on {IERC20-approve}, the token holder account doesn't* need to send a transaction, and thus is not required to hold Ether at all.** ==== Security Considerations** There are two important considerations concerning the use of `permit`. The first is that a valid permit signature* expresses an allowance, and it should not be assumed to convey additional meaning. In particular, it should not be* considered as an intention to spend the allowance in any specific way. The second is that because permits have* built-in replay protection and can be submitted by anyone, they can be frontrun. A protocol that uses permits should* take this into consideration and allow a `permit` call to fail. Combining these two aspects, a pattern that may be* generally recommended is:** ```solidity* function doThingWithPermit(..., uint256 value, uint256 deadline, uint8 v, bytes32 r, bytes32 s) public {* try token.permit(msg.sender, address(this), value, deadline, v, r, s) {} catch {}* doThing(..., value);* }** function doThing(..., uint256 value) public {* token.safeTransferFrom(msg.sender, address(this), value);* ...* }* ```** Observe that: 1) `msg.sender` is used as the owner, leaving no ambiguity as to the signer intent, and 2) the use of* `try/catch` allows the permit to fail and makes the code tolerant to frontrunning. (See also* {SafeERC20-safeTransferFrom}).** Additionally, note that smart contract wallets (such as Argent or Safe) are not able to produce permit signatures, so* contracts should have entry points that don't rely on permit.*/
node_modules/@openzeppelin/contracts/token/ERC20/utils/SafeERC20.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.3) (token/ERC20/utils/SafeERC20.sol)pragma solidity ^0.8.0;import "../IERC20.sol";import "../extensions/IERC20Permit.sol";import "../../../utils/Address.sol";/*** @title SafeERC20* @dev Wrappers around ERC20 operations that throw on failure (when the token* contract returns false). Tokens that return no value (and instead revert or* throw on failure) are also supported, non-reverting calls are assumed to be* successful.* To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,* which allows you to call the safe operations as `token.safeTransfer(...)`, etc.*/library SafeERC20 {using Address for address;/*** @dev Transfer `value` amount of `token` from the calling contract to `to`. If `token` returns no value,* non-reverting calls are assumed to be successful.*/function safeTransfer(IERC20 token, address to, uint256 value) internal {_callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));}/*** @dev Transfer `value` amount of `token` from `from` to `to`, spending the approval given by `from` to the* calling contract. If `token` returns no value, non-reverting calls are assumed to be successful.*/function safeTransferFrom(IERC20 token, address from, address to, uint256 value) internal {_callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));}/*** @dev Deprecated. This function has issues similar to the ones found in* {IERC20-approve}, and its usage is discouraged.*
node_modules/@openzeppelin/contracts/utils/Address.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (utils/Address.sol)pragma solidity ^0.8.1;/*** @dev Collection of functions related to the address type*/library Address {/*** @dev Returns true if `account` is a contract.** [IMPORTANT]* ====* It is unsafe to assume that an address for which this function returns* false is an externally-owned account (EOA) and not a contract.** Among others, `isContract` will return false for the following* types of addresses:** - an externally-owned account* - a contract in construction* - an address where a contract will be created* - an address where a contract lived, but was destroyed** Furthermore, `isContract` will also return true if the target contract within* the same transaction is already scheduled for destruction by `SELFDESTRUCT`,* which only has an effect at the end of a transaction.* ====** [IMPORTANT]* ====* You shouldn't rely on `isContract` to protect against flash loan attacks!** Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets* like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract* constructor.* ====*/function isContract(address account) internal view returns (bool) {// This method relies on extcodesize/address.code.length, which returns 0
node_modules/@openzeppelin/contracts/utils/StorageSlot.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (utils/StorageSlot.sol)// This file was procedurally generated from scripts/generate/templates/StorageSlot.js.pragma solidity ^0.8.0;/*** @dev Library for reading and writing primitive types to specific storage slots.** Storage slots are often used to avoid storage conflict when dealing with upgradeable contracts.* This library helps with reading and writing to such slots without the need for inline assembly.** The functions in this library return Slot structs that contain a `value` member that can be used to read or write.** Example usage to set ERC1967 implementation slot:* ```solidity* contract ERC1967 {* bytes32 internal constant _IMPLEMENTATION_SLOT = 0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc;** function _getImplementation() internal view returns (address) {* return StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value;* }** function _setImplementation(address newImplementation) internal {* require(Address.isContract(newImplementation), "ERC1967: new implementation is not a contract");* StorageSlot.getAddressSlot(_IMPLEMENTATION_SLOT).value = newImplementation;* }* }* ```** _Available since v4.1 for `address`, `bool`, `bytes32`, `uint256`._* _Available since v4.9 for `string`, `bytes`._*/library StorageSlot {struct AddressSlot {address value;}struct BooleanSlot {bool value;}
node_modules/@openzeppelin/contracts/utils/introspection/IERC165.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol)pragma solidity ^0.8.0;/*** @dev Interface of the ERC165 standard, as defined in the* https://eips.ethereum.org/EIPS/eip-165[EIP].** Implementers can declare support of contract interfaces, which can then be* queried by others ({ERC165Checker}).** For an implementation, see {ERC165}.*/interface IERC165 {/*** @dev Returns true if this contract implements the interface defined by* `interfaceId`. See the corresponding* https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]* to learn more about how these ids are created.** This function call must use less than 30 000 gas.*/function supportsInterface(bytes4 interfaceId) external view returns (bool);}
Compiler Settings
{"viaIR":false,"remappings":["@openzeppelin/contracts-upgradeable/=node_modules/@openzeppelin/contracts-upgradeable/","@openzeppelin/contracts/=node_modules/@openzeppelin/contracts/","solady/=node_modules/solady/","forge-std/=node_modules/forge-std/","ds-test/=node_modules/ds-test/src/","p256-verifier/=node_modules/p256-verifier/","forge-safe/=node_modules/forge-safe/"],"outputSelection":{"*":{"*":["*"],"":["*"]}},"optimizer":{"runs":200,"enabled":true},"metadata":{"useLiteralContent":false,"bytecodeHash":"ipfs","appendCBOR":true},"libraries":{},"evmVersion":"cancun"}
Contract ABI
[{"type":"error","name":"EIP1559_INVALID_PARAMS","inputs":[]},{"type":"error","name":"ETH_TRANSFER_FAILED","inputs":[]},{"type":"error","name":"FUNC_NOT_IMPLEMENTED","inputs":[]},{"type":"error","name":"INVALID_PAUSE_STATUS","inputs":[]},{"type":"error","name":"L2_BASEFEE_MISMATCH","inputs":[]},{"type":"error","name":"L2_INVALID_L1_CHAIN_ID","inputs":[]},{"type":"error","name":"L2_INVALID_L2_CHAIN_ID","inputs":[]},{"type":"error","name":"L2_INVALID_PARAM","inputs":[]},{"type":"error","name":"L2_INVALID_SENDER","inputs":[]},{"type":"error","name":"L2_PUBLIC_INPUT_HASH_MISMATCH","inputs":[]},{"type":"error","name":"L2_TOO_LATE","inputs":[]},{"type":"error","name":"Overflow","inputs":[]},{"type":"error","name":"REENTRANT_CALL","inputs":[]},{"type":"error","name":"RESOLVER_DENIED","inputs":[]},{"type":"error","name":"RESOLVER_INVALID_MANAGER","inputs":[]},{"type":"error","name":"RESOLVER_UNEXPECTED_CHAINID","inputs":[]},{"type":"error","name":"RESOLVER_ZERO_ADDR","inputs":[{"type":"uint64","name":"chainId","internalType":"uint64"},{"type":"bytes32","name":"name","internalType":"bytes32"}]},{"type":"error","name":"ZERO_ADDRESS","inputs":[]},{"type":"error","name":"ZERO_VALUE","inputs":[]},{"type":"event","name":"AdminChanged","inputs":[{"type":"address","name":"previousAdmin","internalType":"address","indexed":false},{"type":"address","name":"newAdmin","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"Anchored","inputs":[{"type":"bytes32","name":"parentHash","internalType":"bytes32","indexed":false},{"type":"uint64","name":"gasExcess","internalType":"uint64","indexed":false}],"anonymous":false},{"type":"event","name":"BeaconUpgraded","inputs":[{"type":"address","name":"beacon","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"Initialized","inputs":[{"type":"uint8","name":"version","internalType":"uint8","indexed":false}],"anonymous":false},{"type":"event","name":"OwnershipTransferStarted","inputs":[{"type":"address","name":"previousOwner","internalType":"address","indexed":true},{"type":"address","name":"newOwner","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"OwnershipTransferred","inputs":[{"type":"address","name":"previousOwner","internalType":"address","indexed":true},{"type":"address","name":"newOwner","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"Paused","inputs":[{"type":"address","name":"account","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"Unpaused","inputs":[{"type":"address","name":"account","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"Upgraded","inputs":[{"type":"address","name":"implementation","internalType":"address","indexed":true}],"anonymous":false},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"GOLDEN_TOUCH_ADDRESS","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"acceptOwnership","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"addressManager","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"anchor","inputs":[{"type":"bytes32","name":"_l1BlockHash","internalType":"bytes32"},{"type":"bytes32","name":"_l1StateRoot","internalType":"bytes32"},{"type":"uint64","name":"_l1BlockId","internalType":"uint64"},{"type":"uint32","name":"_parentGasUsed","internalType":"uint32"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint64","name":"","internalType":"uint64"}],"name":"gasExcess","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"basefee_","internalType":"uint256"},{"type":"uint64","name":"gasExcess_","internalType":"uint64"}],"name":"getBasefee","inputs":[{"type":"uint64","name":"_l1BlockId","internalType":"uint64"},{"type":"uint32","name":"_parentGasUsed","internalType":"uint32"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bytes32","name":"","internalType":"bytes32"}],"name":"getBlockHash","inputs":[{"type":"uint64","name":"_blockId","internalType":"uint64"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"tuple","name":"","internalType":"struct LibL2Config.Config","components":[{"type":"uint32","name":"gasTargetPerL1Block","internalType":"uint32"},{"type":"uint8","name":"basefeeAdjustmentQuotient","internalType":"uint8"}]}],"name":"getConfig","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"impl","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"inNonReentrant","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"init","inputs":[{"type":"address","name":"_owner","internalType":"address"},{"type":"address","name":"_addressManager","internalType":"address"},{"type":"uint64","name":"_l1ChainId","internalType":"uint64"},{"type":"uint64","name":"_gasExcess","internalType":"uint64"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint64","name":"","internalType":"uint64"}],"name":"l1ChainId","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bytes32","name":"blockHash","internalType":"bytes32"}],"name":"l2Hashes","inputs":[{"type":"uint256","name":"blockId","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint64","name":"","internalType":"uint64"}],"name":"lastSyncedBlock","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint64","name":"","internalType":"uint64"}],"name":"lastUnpausedAt","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"owner","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"pause","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"paused","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"pendingOwner","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bytes32","name":"","internalType":"bytes32"}],"name":"proxiableUUID","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bytes32","name":"","internalType":"bytes32"}],"name":"publicInputHash","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"renounceOwnership","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address payable"}],"name":"resolve","inputs":[{"type":"uint64","name":"_chainId","internalType":"uint64"},{"type":"bytes32","name":"_name","internalType":"bytes32"},{"type":"bool","name":"_allowZeroAddress","internalType":"bool"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address payable"}],"name":"resolve","inputs":[{"type":"bytes32","name":"_name","internalType":"bytes32"},{"type":"bool","name":"_allowZeroAddress","internalType":"bool"}]},{"type":"function","stateMutability":"pure","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"skipFeeCheck","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferOwnership","inputs":[{"type":"address","name":"newOwner","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"unpause","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"upgradeTo","inputs":[{"type":"address","name":"newImplementation","internalType":"address"}]},{"type":"function","stateMutability":"payable","outputs":[],"name":"upgradeToAndCall","inputs":[{"type":"address","name":"newImplementation","internalType":"address"},{"type":"bytes","name":"data","internalType":"bytes"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"withdraw","inputs":[{"type":"address","name":"_token","internalType":"address"},{"type":"address","name":"_to","internalType":"address"}]}]
Deployed ByteCode
0x6080604052600436106101c5575f3560e01c80638456cb59116100f2578063c3f909d411610092578063e30c397811610062578063e30c397814610524578063f2fde38b14610541578063f535bd5614610560578063f940e3851461057f575f80fd5b8063c3f909d414610493578063da69d3db146104cb578063dac5df78146104ea578063e07baba6146104ff575f80fd5b80638da5cb5b116100cd5780638da5cb5b146103f65780639ee512f214610413578063a7e022d114610438578063a86f9d9e14610474575f80fd5b80638456cb59146103a35780638551f41e146103b75780638abf6077146103e2575f80fd5b80633eb6b8cf116101685780635950f9f1116101385780635950f9f11461033c5780635c975abb1461035b578063715018a61461037b57806379ba50971461038f575f80fd5b80633eb6b8cf146102e25780633f4ba83a146103015780634f1ef2861461031557806352d1902d14610328575f80fd5b80633075db56116101a35780633075db561461025057806333d5ac9b146102645780633659cfe61461028a5780633ab76e9f146102ab575f80fd5b806312622e5b146101c957806323ac7136146102055780632f98047314610232575b5f80fd5b3480156101d4575f80fd5b5060fe546101e8906001600160401b031681565b6040516001600160401b0390911681526020015b60405180910390f35b348015610210575f80fd5b5061022461021f366004611f62565b61059e565b6040519081526020016101fc565b34801561023d575f80fd5b505f5b60405190151581526020016101fc565b34801561025b575f80fd5b506102406105fa565b34801561026f575f80fd5b5060fd546101e890600160401b90046001600160401b031681565b348015610295575f80fd5b506102a96102a4366004611f8f565b61060e565b005b3480156102b6575f80fd5b506097546102ca906001600160a01b031681565b6040516001600160a01b0390911681526020016101fc565b3480156102ed575f80fd5b506102ca6102fc366004611fbe565b6106de565b34801561030c575f80fd5b506102a96106f2565b6102a961032336600461200f565b610706565b348015610333575f80fd5b506102246107bf565b348015610347575f80fd5b506102a96103563660046120cc565b610870565b348015610366575f80fd5b5061024060c954610100900460ff1660021490565b348015610386575f80fd5b506102a9610a79565b34801561039a575f80fd5b506102a9610a8a565b3480156103ae575f80fd5b506102a9610b01565b3480156103c2575f80fd5b506102246103d1366004612121565b60fb6020525f908152604090205481565b3480156103ed575f80fd5b506102ca610b14565b348015610401575f80fd5b506033546001600160a01b03166102ca565b34801561041e575f80fd5b506102ca71777735367b36bc9b61c50022d9d0700db4ec81565b348015610443575f80fd5b5061045761045236600461214b565b610b22565b604080519283526001600160401b039091166020830152016101fc565b34801561047f575f80fd5b506102ca61048e36600461217c565b610b92565b34801561049e575f80fd5b506104a7610ba7565b60408051825163ffffffff16815260209283015160ff1692810192909252016101fc565b3480156104d6575f80fd5b506102a96104e53660046121aa565b610bd8565b3480156104f5575f80fd5b5061022460fc5481565b34801561050a575f80fd5b5060c9546101e8906201000090046001600160401b031681565b34801561052f575f80fd5b506065546001600160a01b03166102ca565b34801561054c575f80fd5b506102a961055b366004611f8f565b610ea2565b34801561056b575f80fd5b5060fd546101e8906001600160401b031681565b34801561058a575f80fd5b506102a96105993660046121e2565b610f13565b5f43826001600160401b0316106105b657505f919050565b436105c383610100612222565b6001600160401b0316106105df57506001600160401b03164090565b506001600160401b03165f90815260fb602052604090205490565b5f60026106056110ce565b60ff1614905090565b6001600160a01b037f000000000000000000000000016700000000000000000000000000000001000116300361065f5760405162461bcd60e51b815260040161065690612249565b60405180910390fd5b7f00000000000000000000000001670000000000000000000000000000000100016001600160a01b031661069161110d565b6001600160a01b0316146106b75760405162461bcd60e51b815260040161065690612295565b6106c081611128565b604080515f808252602082019092526106db91839190611130565b50565b5f6106ea84848461129a565b949350505050565b6106fa61138b565b610704335f61141b565b565b6001600160a01b037f000000000000000000000000016700000000000000000000000000000001000116300361074e5760405162461bcd60e51b815260040161065690612249565b7f00000000000000000000000001670000000000000000000000000000000100016001600160a01b031661078061110d565b6001600160a01b0316146107a65760405162461bcd60e51b815260040161065690612295565b6107af82611128565b6107bb82826001611130565b5050565b5f306001600160a01b037f0000000000000000000000000167000000000000000000000000000000010001161461085e5760405162461bcd60e51b815260206004820152603860248201527f555550535570677261646561626c653a206d757374206e6f742062652063616c60448201527f6c6564207468726f7567682064656c656761746563616c6c00000000000000006064820152608401610656565b505f805160206124bf83398151915290565b5f54610100900460ff161580801561088e57505f54600160ff909116105b806108a75750303b1580156108a757505f5460ff166001145b61090a5760405162461bcd60e51b815260206004820152602e60248201527f496e697469616c697a61626c653a20636f6e747261637420697320616c72656160448201526d191e481a5b9a5d1a585b1a5e995960921b6064820152608401610656565b5f805460ff19166001179055801561092b575f805461ff0019166101001790555b6109358585611423565b6001600160401b0383161580610953575046836001600160401b0316145b15610971576040516308279a2560e31b815260040160405180910390fd5b60014611158061098757506001600160401b0346115b156109a557604051638f972ecb60e01b815260040160405180910390fd5b43156109ef57436001036109d6575f6109bf6001436122e1565b5f81815260fb6020526040902090409055506109ef565b604051635a0f9e4160e11b815260040160405180910390fd5b60fe80546001600160401b0380861667ffffffffffffffff199283161790925560fd805492851692909116919091179055610a294361145d565b5060fc558015610a72575f805461ff0019169055604051600181527f7f26b83ff96e1f2b6a682f133852f6798a09c465da95921460cefb38474024989060200160405180910390a15b5050505050565b610a816114ed565b6107045f611547565b60655433906001600160a01b03168114610af85760405162461bcd60e51b815260206004820152602960248201527f4f776e61626c6532537465703a2063616c6c6572206973206e6f7420746865206044820152683732bb9037bbb732b960b91b6064820152608401610656565b6106db81611547565b610b09611560565b61070433600161141b565b5f610b1d61110d565b905090565b5f805f610b2d610ba7565b805160fd549192505f9163ffffffff90911690610b5a90600160401b90046001600160401b0316886122f4565b610b649190612314565b8251602084015160fd54929350610b85926001600160401b031684896115d1565b9097909650945050505050565b5f610b9e46848461129a565b90505b92915050565b604080518082019091525f8082526020820152610b1d60408051808201909152630393870081526008602082015290565b6002610be26110ce565b60ff1603610c035760405163dfc60d8560e01b815260040160405180910390fd5b610c0d600261166c565b831580610c18575082155b80610c2a57506001600160401b038216155b80610c45575043600114158015610c45575063ffffffff8116155b15610c635760405163053fd54760e01b815260040160405180910390fd5b3371777735367b36bc9b61c50022d9d0700db4ec14610c9557604051636494e9f760e01b815260040160405180910390fd5b5f1943015f80610ca48361145d565b915091508160fc5414610cca5760405163d719258d60e01b815260040160405180910390fd5b5f80610cd68787610b22565b91509150610ce15f90565b158015610cee5750814814155b15610d0c576040516336d54d4f60e11b815260040160405180910390fd5b60fd546001600160401b03600160401b90910481169088161115610e1c57610d456d7369676e616c5f7365727669636560901b5f610b92565b60fe546040516313e4299d60e21b81526001600160401b0391821660048201527f73e6d340850343cc6f001515dc593377337c95a6ffe034fe1e844d4dab5da16960248201529089166044820152606481018a90526001600160a01b039190911690634f90a674906084016020604051808303815f875af1158015610dcc573d5f803e3d5ffd5b505050506040513d601f19601f82011682018060405250810190610df0919061233f565b5060fd80546fffffffffffffffff00000000000000001916600160401b6001600160401b038a16021790555b5f85815260fb602090815260409182902087409081905560fc86905560fd805467ffffffffffffffff19166001600160401b038616908117909155835182815292830152917f41c3f410f5c8ac36bb46b1dccef0de0f964087c9e688795fa02ecfa2c20b3fe4910160405180910390a1505050505050610e9c600161166c565b50505050565b610eaa6114ed565b606580546001600160a01b0383166001600160a01b03199091168117909155610edb6033546001600160a01b031690565b6001600160a01b03167f38d16b8cac22d99fc7c124b9cd0de2d3fa1faef420bfe791d8c362d765e2270060405160405180910390a350565b610f2760c954610100900460ff1660021490565b15610f455760405163bae6e2a960e01b815260040160405180910390fd5b693bb4ba34323930bbb2b960b11b610f656033546001600160a01b031690565b6001600160a01b0316336001600160a01b031614158015610fa25750610f8c816001610b92565b6001600160a01b0316336001600160a01b031614155b15610fc057604051630d85cccf60e11b815260040160405180910390fd5b6002610fca6110ce565b60ff1603610feb5760405163dfc60d8560e01b815260040160405180910390fd5b610ff5600261166c565b6001600160a01b03821661101c5760405163053fd54760e01b815260040160405180910390fd5b6001600160a01b0383166110425761103d6001600160a01b038316476116b4565b6110bf565b6040516370a0823160e01b81523060048201526110bf9083906001600160a01b038616906370a0823190602401602060405180830381865afa15801561108a573d5f803e3d5ffd5b505050506040513d601f19601f820116820180604052508101906110ae919061233f565b6001600160a01b03861691906116bf565b6110c9600161166c565b505050565b5f6110d846611711565b1561110357507fa5054f728453d3dbe953bdc43e4d0cb97e662ea32d7958190f3dc2da31d9721b5c90565b5060c95460ff1690565b5f805160206124bf833981519152546001600160a01b031690565b6106db6114ed565b7f4910fdfa16fed3260ed0e7147f7cc6da11a60208b5b9406d12a635614ffd91435460ff1615611163576110c98361173e565b826001600160a01b03166352d1902d6040518163ffffffff1660e01b8152600401602060405180830381865afa9250505080156111bd575060408051601f3d908101601f191682019092526111ba9181019061233f565b60015b6112205760405162461bcd60e51b815260206004820152602e60248201527f45524331393637557067726164653a206e657720696d706c656d656e7461746960448201526d6f6e206973206e6f74205555505360901b6064820152608401610656565b5f805160206124bf833981519152811461128e5760405162461bcd60e51b815260206004820152602960248201527f45524331393637557067726164653a20756e737570706f727465642070726f786044820152681a58589b195555525160ba1b6064820152608401610656565b506110c98383836117d9565b6097545f906001600160a01b0316806112c657604051638ed88b2560e01b815260040160405180910390fd5b604051630a3dc4f360e21b81526001600160401b0386166004820152602481018590526001600160a01b038216906328f713cc90604401602060405180830381865afa158015611318573d5f803e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061133c9190612356565b91508215801561135357506001600160a01b038216155b1561138357604051632b0d65db60e01b81526001600160401b038616600482015260248101859052604401610656565b509392505050565b61139f60c954610100900460ff1660021490565b6113bc5760405163bae6e2a960e01b815260040160405180910390fd5b60c9805461010069ffffffffffffffffff001990911662010000426001600160401b031602171790556040513381527f5db9ee0a495bf2e6ff9c91a7834c1ba4fdd244a5e8aa4e537bd38aeae4b073aa906020015b60405180910390a1565b6107bb6114ed565b806001600160a01b03811661144b5760405163538ba4f960e01b815260040160405180910390fd5b611454836117fd565b6110c98261185b565b5f80611467611f27565b5f5b60ff8110801561147c5750806001018510155b156114ad575f198186030180408360ff8306610100811061149f5761149f612385565b602002015250600101611469565b5046611fe0820152612000812092508340816114ca60ff87612399565b61010081106114db576114db612385565b60200201526120009020919391925050565b6033546001600160a01b031633146107045760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610656565b606580546001600160a01b03191690556106db816118cb565b61157460c954610100900460ff1660021490565b156115925760405163bae6e2a960e01b815260040160405180910390fd5b60c9805461ff0019166102001790556040513381527f62e78cea01bee320cd4e420270b5ea74000d11b0c9f74754ebdbfc544b05a25890602001611411565b5f80806115ed63ffffffff85166001600160401b0388166123ac565b9050846001600160401b03168111611606576001611619565b6116196001600160401b038616826122e1565b905061162c816001600160401b0361191c565b91506116536001600160401b03831661164e63ffffffff8b1660ff8b166123bf565b611930565b9250825f0361166157600192505b509550959350505050565b61167546611711565b156116a057807fa5054f728453d3dbe953bdc43e4d0cb97e662ea32d7958190f3dc2da31d9721b5d50565b60c9805460ff831660ff1990911617905550565b6107bb82825a61196e565b604080516001600160a01b038416602482015260448082018490528251808303909101815260649091019091526020810180516001600160e01b031663a9059cbb60e01b1790526110c99084906119b1565b5f6001821480611722575061426882145b8061172f575062aa36a782145b80610ba15750610ba182611a84565b6001600160a01b0381163b6117ab5760405162461bcd60e51b815260206004820152602d60248201527f455243313936373a206e657720696d706c656d656e746174696f6e206973206e60448201526c1bdd08184818dbdb9d1c9858dd609a1b6064820152608401610656565b5f805160206124bf83398151915280546001600160a01b0319166001600160a01b0392909216919091179055565b6117e283611a9b565b5f825111806117ee5750805b156110c957610e9c8383611ada565b5f54610100900460ff166118235760405162461bcd60e51b8152600401610656906123d6565b61182b611aff565b6118496001600160a01b038216156118435781611547565b33611547565b5060c9805461ff001916610100179055565b5f54610100900460ff166118815760405162461bcd60e51b8152600401610656906123d6565b6001600160401b034611156118a95760405163a12e8fa960e01b815260040160405180910390fd5b609780546001600160a01b0319166001600160a01b0392909216919091179055565b603380546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0905f90a35050565b5f81831161192a5782610b9e565b50919050565b5f815f0361195157604051636296f1b960e11b815260040160405180910390fd5b670de0b6b3a76400006119648484611b25565b610b9e9190612421565b815f0361197a57505050565b61199483838360405180602001604052805f815250611b6c565b6110c957604051634c67134d60e11b815260040160405180910390fd5b5f611a05826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316611ba99092919063ffffffff16565b905080515f1480611a25575080806020019051810190611a259190612434565b6110c95760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610656565b5f617e2c8210158015610ba1575050617e90101590565b611aa48161173e565b6040516001600160a01b038216907fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b905f90a250565b6060610b9e83836040518060600160405280602781526020016124df60279139611bb7565b5f54610100900460ff166107045760405162461bcd60e51b8152600401610656906123d6565b5f8082611b3a670de0b6b3a7640000866123bf565b611b449190612421565b9050680755bf798b4a1bf1e4811115611b635750680755bf798b4a1bf1e45b6106ea81611c2b565b5f6001600160a01b038516611b9457604051634c67134d60e11b815260040160405180910390fd5b5f80835160208501878988f195945050505050565b60606106ea84845f85611db3565b60605f80856001600160a01b031685604051611bd39190612471565b5f60405180830381855af49150503d805f8114611c0b576040519150601f19603f3d011682016040523d82523d5f602084013e611c10565b606091505b5091509150611c2186838387611e8a565b9695505050505050565b5f680248ce36a70cb26b3e198213611c4457505f919050565b680755bf798b4a1bf1e58212611c6d57604051631a93c68960e11b815260040160405180910390fd5b6503782dace9d9604e83901b0591505f60606bb17217f7d1cf79abc9e3b39884821b056001605f1b01901d6bb17217f7d1cf79abc9e3b39881029093036c240c330e9fb2d9cbaf0fd5aafb1981018102606090811d6d0277594991cfc85f6e2461837cd9018202811d6d1a521255e34f6a5061b25ef1c9c319018202811d6db1bbb201f443cf962f1a1d3db4a5018202811d6e02c72388d9f74f51a9331fed693f1419018202811d6e05180bb14799ab47a8a8cb2a527d57016d02d16720577bd19bf614176fe9ea6c10fe68e7fd37d0007b713f765084018402831d9081019084016d01d3967ed30fc4f89c02bab5708119010290911d6e0587f503bb6ea29d25fcb740196450019091026d360d7aeea093263ecc6e0ecb291760621b010574029d9dc38563c32e5c2f6dc192ee70ef65f9978af30260c3939093039290921c92915050565b606082471015611e145760405162461bcd60e51b815260206004820152602660248201527f416464726573733a20696e73756666696369656e742062616c616e636520666f6044820152651c8818d85b1b60d21b6064820152608401610656565b5f80866001600160a01b03168587604051611e2f9190612471565b5f6040518083038185875af1925050503d805f8114611e69576040519150601f19603f3d011682016040523d82523d5f602084013e611e6e565b606091505b5091509150611e7f87838387611e8a565b979650505050505050565b60608315611ef85782515f03611ef1576001600160a01b0385163b611ef15760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610656565b50816106ea565b6106ea8383815115611f0d5781518083602001fd5b8060405162461bcd60e51b8152600401610656919061248c565b604051806120000160405280610100906020820280368337509192915050565b80356001600160401b0381168114611f5d575f80fd5b919050565b5f60208284031215611f72575f80fd5b610b9e82611f47565b6001600160a01b03811681146106db575f80fd5b5f60208284031215611f9f575f80fd5b8135611faa81611f7b565b9392505050565b80151581146106db575f80fd5b5f805f60608486031215611fd0575f80fd5b611fd984611f47565b9250602084013591506040840135611ff081611fb1565b809150509250925092565b634e487b7160e01b5f52604160045260245ffd5b5f8060408385031215612020575f80fd5b823561202b81611f7b565b915060208301356001600160401b0380821115612046575f80fd5b818501915085601f830112612059575f80fd5b81358181111561206b5761206b611ffb565b604051601f8201601f19908116603f0116810190838211818310171561209357612093611ffb565b816040528281528860208487010111156120ab575f80fd5b826020860160208301375f6020848301015280955050505050509250929050565b5f805f80608085870312156120df575f80fd5b84356120ea81611f7b565b935060208501356120fa81611f7b565b925061210860408601611f47565b915061211660608601611f47565b905092959194509250565b5f60208284031215612131575f80fd5b5035919050565b803563ffffffff81168114611f5d575f80fd5b5f806040838503121561215c575f80fd5b61216583611f47565b915061217360208401612138565b90509250929050565b5f806040838503121561218d575f80fd5b82359150602083013561219f81611fb1565b809150509250929050565b5f805f80608085870312156121bd575f80fd5b84359350602085013592506121d460408601611f47565b915061211660608601612138565b5f80604083850312156121f3575f80fd5b82356121fe81611f7b565b9150602083013561219f81611f7b565b634e487b7160e01b5f52601160045260245ffd5b6001600160401b038181168382160190808211156122425761224261220e565b5092915050565b6020808252602c908201527f46756e6374696f6e206d7573742062652063616c6c6564207468726f7567682060408201526b19195b1959d85d1958d85b1b60a21b606082015260800190565b6020808252602c908201527f46756e6374696f6e206d7573742062652063616c6c6564207468726f7567682060408201526b6163746976652070726f787960a01b606082015260800190565b81810381811115610ba157610ba161220e565b6001600160401b038281168282160390808211156122425761224261220e565b6001600160401b038181168382160280821691908281146123375761233761220e565b505092915050565b5f6020828403121561234f575f80fd5b5051919050565b5f60208284031215612366575f80fd5b8151611faa81611f7b565b634e487b7160e01b5f52601260045260245ffd5b634e487b7160e01b5f52603260045260245ffd5b5f826123a7576123a7612371565b500690565b80820180821115610ba157610ba161220e565b8082028115828204841417610ba157610ba161220e565b6020808252602b908201527f496e697469616c697a61626c653a20636f6e7472616374206973206e6f74206960408201526a6e697469616c697a696e6760a81b606082015260800190565b5f8261242f5761242f612371565b500490565b5f60208284031215612444575f80fd5b8151611faa81611fb1565b5f5b83811015612469578181015183820152602001612451565b50505f910152565b5f825161248281846020870161244f565b9190910192915050565b602081525f82518060208401526124aa81604085016020870161244f565b601f01601f1916919091016040019291505056fe360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc416464726573733a206c6f772d6c6576656c2064656c65676174652063616c6c206661696c6564a2646970667358221220dd805646fbd402e3dd00f2e2ed2bf34ee8b6c44c1aee4f0ee9aaf88caab4582f64736f6c63430008180033