Warning! Contract bytecode has been changed and doesn't match the verified one. Therefore, interaction with this smart contract may be risky.
- Contract name:
- ConsumerWrapperMock
- Optimization enabled
- false
- Compiler version
- v0.8.20+commit.a1b79de6
- EVM Version
- paris
- Verified at
- 2024-09-14T07:51:03.895883Z
Constructor Arguments
000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c
Arg [0] (address) : 0xc5d2637d24379d6371a5059d34718b70aecc2d7c
contracts/Mocks/ConsumerWrapperMock.sol
pragma solidity ^0.8.6;import "../vrf/VRFV2WrapperConsumerBase.sol";import "../vrf/ErinaceusVRFWrapper.sol";import "hardhat/console.sol";contract ConsumerWrapperMock is VRFV2WrapperConsumerBase {ErinaceusVRFWrapper public erinaceus;uint256[] public random;mapping(uint256 => uint256) public randomWord;uint256 public currentId;constructor(address erinaceusVRFWrapper)VRFV2WrapperConsumerBase(erinaceusVRFWrapper){erinaceus = ErinaceusVRFWrapper(erinaceusVRFWrapper);}function getRandom(uint256 id) public view returns (uint256){return randomWord[id];}function getRandom1() public view returns (uint256[] memory){return random;}function generateRandomWords(uint16 requestConfirmations,uint32 callbackGasLimit,uint32 numWords) external payable {requestRandomness(callbackGasLimit,requestConfirmations,numWords,msg.value);}function fulfillRandomWords(uint256 requestId, uint256[] memory randomWords) internal virtual override {// random = randomWords;randomWord[currentId] = randomWords[0];currentId++;}}
@openzeppelin/contracts/access/Ownable.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.0) (access/Ownable.sol)pragma solidity ^0.8.0;import "../utils/Context.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 Ownable is Context {address private _owner;event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);/*** @dev Initializes the contract setting the deployer as the initial owner.*/constructor() {_transferOwnership(_msgSender());}/*** @dev Throws if called by any account other than the owner.*/modifier onlyOwner() {_checkOwner();_;}/*** @dev Returns the address of the current owner.
@openzeppelin/contracts/utils/Context.sol
// SPDX-License-Identifier: MIT// OpenZeppelin Contracts (last updated v4.9.4) (utils/Context.sol)pragma solidity ^0.8.0;/*** @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 Context {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;}}
contracts/vrf/ErinaceusVRFWrapper.sol
// SPDX-License-Identifier: MIT// solhint-disable-next-line one-contract-per-filepragma solidity ^0.8.6;import {ErinaceusVRFWrapperInterface} from "./interfaces/ErinaceusVRFWrapperInterface.sol";import {ErinaceusVRFInterface} from "./interfaces/ErinaceusVRFInterface.sol";import {VRFV2WrapperConsumerBase} from "./VRFV2WrapperConsumerBase.sol";import {Ownable} from "@openzeppelin/contracts/access/Ownable.sol";import {VRFConsumerBaseV2} from "./VRFConsumerBaseV2.sol";/*** @notice A wrapper for VRFCoordinatorV2 that provides an interface better suited to one-off* @notice requests for randomness.*/contract ErinaceusVRFWrapper is Ownable, VRFConsumerBaseV2, ErinaceusVRFWrapperInterface {event WrapperFulfillmentFailed(uint256 indexed requestId, address indexed consumer);ExtendedErinaceusVRFInterface public immutable COORDINATOR;uint64 public immutable SUBSCRIPTION_ID;/// @dev this is the size of a VRF v2 fulfillment's calldata abi-encoded in bytes./// @dev proofSize = 13 words = 13 * 256 = 3328 bits/// @dev commitmentSize = 5 words = 5 * 256 = 1280 bits/// @dev dataSize = proofSize + commitmentSize = 4608 bits/// @dev selector = 32 bits/// @dev total data size = 4608 bits + 32 bits = 4640 bits = 580 bytesuint32 public s_fulfillmentTxSizeBytes = 580;// 5k is plenty for an EXTCODESIZE call (2600) + warm CALL (100)// and some arithmetic operations.uint256 private constant GAS_FOR_CALL_EXACT_CHECK = 5_000;// lastRequestId is the request ID of the most recent VRF V2 request made by this wrapper. This// should only be relied on within the same transaction the request was made.uint256 public override lastRequestId;// Configuration fetched from VRFCoordinatorV2// s_configured tracks whether this contract has been configured. If not configured, randomness// requests cannot be made.bool public s_configured;
contracts/vrf/VRFConsumerBaseV2.sol
// SPDX-License-Identifier: MITpragma solidity ^0.8.4;/** ***************************************************************************** @notice Interface for contracts using VRF randomness* ****************************************************************************** @dev PURPOSE** @dev Reggie the Random Oracle (not his real job) wants to provide randomness* @dev to Vera the verifier in such a way that Vera can be sure he's not* @dev making his output up to suit himself. Reggie provides Vera a public key* @dev to which he knows the secret key. Each time Vera provides a seed to* @dev Reggie, he gives back a value which is computed completely* @dev deterministically from the seed and the secret key.** @dev Reggie provides a proof by which Vera can verify that the output was* @dev correctly computed once Reggie tells it to her, but without that proof,* @dev the output is indistinguishable to her from a uniform random sample* @dev from the output space.** @dev The purpose of this contract is to make it easy for unrelated contracts* @dev to talk to Vera the verifier about the work Reggie is doing, to provide* @dev simple access to a verifiable source of randomness. It ensures 2 things:* @dev 1. The fulfillment came from the ErinaceusVRF* @dev 2. The consumer contract implements fulfillRandomWords.* ****************************************************************************** @dev USAGE** @dev Calling contracts must inherit from VRFConsumerBase, and can* @dev initialize VRFConsumerBase's attributes in their constructor as* @dev shown:** @dev contract VRFConsumer {* @dev constructor(<other arguments>, address _erinaceusVRF, address _link)* @dev VRFConsumerBase(_erinaceusVRF) public {* @dev <initialization with other arguments goes here>* @dev }* @dev }** @dev The oracle will have given you an ID for the VRF keypair they have* @dev committed to (let's call it keyHash). Create subscription, fund it
contracts/vrf/VRFV2WrapperConsumerBase.sol
// SPDX-License-Identifier: MITpragma solidity ^0.8.0;// import {LinkTokenInterface} from "../shared/interfaces/LinkTokenInterface.sol";import {ErinaceusVRFWrapperInterface} from "./interfaces/ErinaceusVRFWrapperInterface.sol";/** ******************************************************************************** @notice Interface for contracts using VRF randomness through the VRF V2 wrapper* ********************************************************************************* @dev PURPOSE** @dev Create VRF V2 requests without the need for subscription management. Rather than creating* @dev and funding a VRF V2 subscription, a user can use this wrapper to create one off requests,* @dev paying up front rather than at fulfillment.** @dev Since the price is determined using the gas price of the request transaction rather than* @dev the fulfillment transaction, the wrapper charges an additional premium on callback gas* @dev usage, in addition to some extra overhead costs associated with the VRFV2Wrapper contract.* ****************************************************************************** @dev USAGE** @dev Calling contracts must inherit from VRFV2WrapperConsumerBase. The consumer must be funded* @dev with enough LINK to make the request, otherwise requests will revert. To request randomness,* @dev call the 'requestRandomness' function with the desired VRF parameters. This function handles* @dev paying for the request based on the current pricing.** @dev Consumers must implement the fullfillRandomWords function, which will be called during* @dev fulfillment with the randomness result.*/abstract contract VRFV2WrapperConsumerBase {ErinaceusVRFWrapperInterface internal immutable ERINACEUS_VRF_WRAPPER;/*** @param _vrfV2Wrapper is the address of the VRFV2Wrapper contract*/constructor(address _vrfV2Wrapper) {ERINACEUS_VRF_WRAPPER = ErinaceusVRFWrapperInterface(_vrfV2Wrapper);}/*** @dev Requests randomness from the VRF V2 wrapper.
contracts/vrf/interfaces/ErinaceusVRFInterface.sol
// SPDX-License-Identifier: MITpragma solidity ^0.8.0;interface ErinaceusVRFInterface {/*** @notice Get configuration relevant for making requests* @return minimumRequestConfirmations global min for request confirmations* @return maxGasLimit global max for request gas limit* @return s_provingKeyHashes list of registered key hashes*/function getRequestConfig() external view returns (uint16, uint32, bytes32[] memory);/*** @notice Request a set of random words.* @param keyHash - Corresponds to a particular oracle job which uses* that key for generating the VRF proof. Different keyHash's have different gas price* ceilings, so you can select a specific one to bound your maximum per request cost.* @param subId - The ID of the VRF subscription. Must be funded* with the minimum subscription balance required for the selected keyHash.* @param minimumRequestConfirmations - How many blocks you'd like the* oracle to wait before responding to the request. See SECURITY CONSIDERATIONS* for why you may want to request more. The acceptable range is* [minimumRequestBlockConfirmations, 200].* @param callbackGasLimit - How much gas you'd like to receive in your* fulfillRandomWords callback. Note that gasleft() inside fulfillRandomWords* may be slightly less than this amount because of gas used calling the function* (argument decoding etc.), so you may need to request slightly more than you expect* to have inside fulfillRandomWords. The acceptable range is* [0, maxGasLimit]* @param numWords - The number of uint256 random values you'd like to receive* in your fulfillRandomWords callback. Note these numbers are expanded in a* secure way by the ErinaceusVRF from a single random value supplied by the oracle.* @return requestId - A unique identifier of the request. Can be used to match* a request to a response in fulfillRandomWords.*/function requestRandomWords(bytes32 keyHash,uint64 subId,uint16 minimumRequestConfirmations,uint32 callbackGasLimit,uint32 numWords
contracts/vrf/interfaces/ErinaceusVRFWrapperInterface.sol
// SPDX-License-Identifier: MITpragma solidity ^0.8.6;interface ErinaceusVRFWrapperInterface {/*** @return the request ID of the most recent VRF V2 request made by this wrapper. This should only* be relied option within the same transaction that the request was made.*/function lastRequestId() external view returns (uint256);function requestRandomWords(uint32 callbackGasLimit, uint16 requestConfirmations, uint32 numWords) external payable;/*** @notice Calculates the price of a VRF request with the given callbackGasLimit at the current* @notice block.** @dev This function relies on the transaction gas price which is not automatically set during* @dev simulation. To estimate the price at a specific gas price, use the estimatePrice function.** @param _callbackGasLimit is the gas limit used to estimate the price.*/function calculateRequestPrice(uint32 _callbackGasLimit) external view returns (uint256);/*** @notice Estimates the price of a VRF request with a specific gas limit and gas price.** @dev This is a convenience function that can be called in simulation to better understand* @dev pricing.** @param _callbackGasLimit is the gas limit used to estimate the price.* @param _requestGasPriceWei is the gas price in wei used for the estimation.*/function estimateRequestPrice(uint32 _callbackGasLimit, uint256 _requestGasPriceWei) external view returns (uint256);}
hardhat/console.sol
// SPDX-License-Identifier: MITpragma solidity >=0.4.22 <0.9.0;library console {address constant CONSOLE_ADDRESS =0x000000000000000000636F6e736F6c652e6c6f67;function _sendLogPayloadImplementation(bytes memory payload) internal view {address consoleAddress = CONSOLE_ADDRESS;/// @solidity memory-safe-assemblyassembly {pop(staticcall(gas(),consoleAddress,add(payload, 32),mload(payload),0,0))}}function _castToPure(function(bytes memory) internal view fnIn) internal pure returns (function(bytes memory) pure fnOut) {assembly {fnOut := fnIn}}function _sendLogPayload(bytes memory payload) internal pure {_castToPure(_sendLogPayloadImplementation)(payload);}function log() internal pure {_sendLogPayload(abi.encodeWithSignature("log()"));}function logInt(int256 p0) internal pure {_sendLogPayload(abi.encodeWithSignature("log(int256)", p0));
Compiler Settings
{"outputSelection":{"*":{"*":["*"],"":["*"]}},"optimizer":{"runs":200,"enabled":false},"metadata":{"useLiteralContent":true},"libraries":{},"evmVersion":"paris"}
Contract ABI
[{"type":"constructor","stateMutability":"nonpayable","inputs":[{"type":"address","name":"erinaceusVRFWrapper","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"currentId","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"contract ErinaceusVRFWrapper"}],"name":"erinaceus","inputs":[]},{"type":"function","stateMutability":"payable","outputs":[],"name":"generateRandomWords","inputs":[{"type":"uint16","name":"requestConfirmations","internalType":"uint16"},{"type":"uint32","name":"callbackGasLimit","internalType":"uint32"},{"type":"uint32","name":"numWords","internalType":"uint32"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"getRandom","inputs":[{"type":"uint256","name":"id","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256[]","name":"","internalType":"uint256[]"}],"name":"getRandom1","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"random","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"randomWord","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"rawFulfillRandomWords","inputs":[{"type":"uint256","name":"_requestId","internalType":"uint256"},{"type":"uint256[]","name":"_randomWords","internalType":"uint256[]"}]}]
Contract Creation Code
0x60a06040523480156200001157600080fd5b50604051620011623803806200116283398181016040528101906200003791906200011e565b808073ffffffffffffffffffffffffffffffffffffffff1660808173ffffffffffffffffffffffffffffffffffffffff168152505050806000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055505062000150565b600080fd5b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000620000e682620000b9565b9050919050565b620000f881620000d9565b81146200010457600080fd5b50565b6000815190506200011881620000ed565b92915050565b600060208284031215620001375762000136620000b4565b5b6000620001478482850162000107565b91505092915050565b608051610fcc62000196600039600081816101ff015281816103db015281816104b7015281816104f3015281816105e00152818161068501526107300152610fcc6000f3fe60806040526004361061007b5760003560e01c8063d29f1a3b1161004e578063d29f1a3b1461014e578063d64ddd891461016a578063e00dd161146101a7578063fe1d45b0146101d25761007b565b80631fe543e31461008057806395d430f2146100a9578063b863bd37146100d4578063cd4b691414610111575b600080fd5b34801561008c57600080fd5b506100a760048036038101906100a291906109e5565b6101fd565b005b3480156100b557600080fd5b506100be610299565b6040516100cb9190610aff565b60405180910390f35b3480156100e057600080fd5b506100fb60048036038101906100f69190610b21565b6102f1565b6040516101089190610b5d565b60405180910390f35b34801561011d57600080fd5b5061013860048036038101906101339190610b21565b610315565b6040516101459190610b5d565b60405180910390f35b61016860048036038101906101639190610bee565b610332565b005b34801561017657600080fd5b50610191600480360381019061018c9190610b21565b610344565b60405161019e9190610b5d565b60405180910390f35b3480156101b357600080fd5b506101bc61035c565b6040516101c99190610b5d565b60405180910390f35b3480156101de57600080fd5b506101e7610362565b6040516101f49190610cc0565b60405180910390f35b7f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff161461028b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161028290610d38565b60405180910390fd5b6102958282610386565b5050565b606060018054806020026020016040519081016040528092919081815260200182805480156102e757602002820191906000526020600020905b8154815260200190600101908083116102d3575b5050505050905090565b6001818154811061030157600080fd5b906000526020600020016000915090505481565b600060026000838152602001908152602001600020549050919050565b61033e828483346103d7565b50505050565b60026020528060005260406000206000915090505481565b60035481565b60008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b8060008151811061039a57610399610d58565b5b602002602001015160026000600354815260200190815260200160002081905550600360008154809291906103ce90610db6565b91905055505050565b60007f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff16634306d354866040518263ffffffff1660e01b81526004016104329190610e0d565b602060405180830381865afa15801561044f573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104739190610e3d565b8210156104b5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016104ac90610eb6565b60405180910390fd5b7f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff16634b494dc07f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff16634306d354886040518263ffffffff1660e01b815260040161054a9190610e0d565b602060405180830381865afa158015610567573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061058b9190610e3d565b8787876040518563ffffffff1660e01b81526004016105ac93929190610ee5565b6000604051808303818588803b1580156105c557600080fd5b505af11580156105d9573d6000803e3d6000fd5b50505050507f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff16634306d354866040518263ffffffff1660e01b81526004016106379190610e0d565b602060405180830381865afa158015610654573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106789190610e3d565b82111561072e5761072d337f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff16634306d354886040518263ffffffff1660e01b81526004016106dc9190610e0d565b602060405180830381865afa1580156106f9573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061071d9190610e3d565b846107289190610f1c565b6107c7565b5b7f000000000000000000000000000000000000000000000000000000000000000073ffffffffffffffffffffffffffffffffffffffff1663fc2a88c36040518163ffffffff1660e01b8152600401602060405180830381865afa158015610799573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107bd9190610e3d565b9050949350505050565b60008273ffffffffffffffffffffffffffffffffffffffff16826040516107ed90610f81565b60006040518083038185875af1925050503d806000811461082a576040519150601f19603f3d011682016040523d82523d6000602084013e61082f565b606091505b505090508061083d57600080fd5b505050565b6000604051905090565b600080fd5b600080fd5b6000819050919050565b61086981610856565b811461087457600080fd5b50565b60008135905061088681610860565b92915050565b600080fd5b6000601f19601f8301169050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6108da82610891565b810181811067ffffffffffffffff821117156108f9576108f86108a2565b5b80604052505050565b600061090c610842565b905061091882826108d1565b919050565b600067ffffffffffffffff821115610938576109376108a2565b5b602082029050602081019050919050565b600080fd5b600061096161095c8461091d565b610902565b9050808382526020820190506020840283018581111561098457610983610949565b5b835b818110156109ad57806109998882610877565b845260208401935050602081019050610986565b5050509392505050565b600082601f8301126109cc576109cb61088c565b5b81356109dc84826020860161094e565b91505092915050565b600080604083850312156109fc576109fb61084c565b5b6000610a0a85828601610877565b925050602083013567ffffffffffffffff811115610a2b57610a2a610851565b5b610a37858286016109b7565b9150509250929050565b600081519050919050565b600082825260208201905092915050565b6000819050602082019050919050565b610a7681610856565b82525050565b6000610a888383610a6d565b60208301905092915050565b6000602082019050919050565b6000610aac82610a41565b610ab68185610a4c565b9350610ac183610a5d565b8060005b83811015610af2578151610ad98882610a7c565b9750610ae483610a94565b925050600181019050610ac5565b5085935050505092915050565b60006020820190508181036000830152610b198184610aa1565b905092915050565b600060208284031215610b3757610b3661084c565b5b6000610b4584828501610877565b91505092915050565b610b5781610856565b82525050565b6000602082019050610b726000830184610b4e565b92915050565b600061ffff82169050919050565b610b8f81610b78565b8114610b9a57600080fd5b50565b600081359050610bac81610b86565b92915050565b600063ffffffff82169050919050565b610bcb81610bb2565b8114610bd657600080fd5b50565b600081359050610be881610bc2565b92915050565b600080600060608486031215610c0757610c0661084c565b5b6000610c1586828701610b9d565b9350506020610c2686828701610bd9565b9250506040610c3786828701610bd9565b9150509250925092565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b6000610c86610c81610c7c84610c41565b610c61565b610c41565b9050919050565b6000610c9882610c6b565b9050919050565b6000610caa82610c8d565b9050919050565b610cba81610c9f565b82525050565b6000602082019050610cd56000830184610cb1565b92915050565b600082825260208201905092915050565b7f6f6e6c792056524620563220777261707065722063616e2066756c66696c6c00600082015250565b6000610d22601f83610cdb565b9150610d2d82610cec565b602082019050919050565b60006020820190508181036000830152610d5181610d15565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b6000610dc182610856565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8203610df357610df2610d87565b5b600182019050919050565b610e0781610bb2565b82525050565b6000602082019050610e226000830184610dfe565b92915050565b600081519050610e3781610860565b92915050565b600060208284031215610e5357610e5261084c565b5b6000610e6184828501610e28565b91505092915050565b7f496e73756666696369656e74207061796d656e7420616d6f756e740000000000600082015250565b6000610ea0601b83610cdb565b9150610eab82610e6a565b602082019050919050565b60006020820190508181036000830152610ecf81610e93565b9050919050565b610edf81610b78565b82525050565b6000606082019050610efa6000830186610dfe565b610f076020830185610ed6565b610f146040830184610dfe565b949350505050565b6000610f2782610856565b9150610f3283610856565b9250828203905081811115610f4a57610f49610d87565b5b92915050565b600081905092915050565b50565b6000610f6b600083610f50565b9150610f7682610f5b565b600082019050919050565b6000610f8c82610f5e565b915081905091905056fea26469706673582212206a124e63531ba842dd70849ed882f4e54a467a068311dd9bc064eb56b01714bc64736f6c63430008140033000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c
Deployed ByteCode
0x60806040526004361061007b5760003560e01c8063d29f1a3b1161004e578063d29f1a3b1461014e578063d64ddd891461016a578063e00dd161146101a7578063fe1d45b0146101d25761007b565b80631fe543e31461008057806395d430f2146100a9578063b863bd37146100d4578063cd4b691414610111575b600080fd5b34801561008c57600080fd5b506100a760048036038101906100a291906109e5565b6101fd565b005b3480156100b557600080fd5b506100be610299565b6040516100cb9190610aff565b60405180910390f35b3480156100e057600080fd5b506100fb60048036038101906100f69190610b21565b6102f1565b6040516101089190610b5d565b60405180910390f35b34801561011d57600080fd5b5061013860048036038101906101339190610b21565b610315565b6040516101459190610b5d565b60405180910390f35b61016860048036038101906101639190610bee565b610332565b005b34801561017657600080fd5b50610191600480360381019061018c9190610b21565b610344565b60405161019e9190610b5d565b60405180910390f35b3480156101b357600080fd5b506101bc61035c565b6040516101c99190610b5d565b60405180910390f35b3480156101de57600080fd5b506101e7610362565b6040516101f49190610cc0565b60405180910390f35b7f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff161461028b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161028290610d38565b60405180910390fd5b6102958282610386565b5050565b606060018054806020026020016040519081016040528092919081815260200182805480156102e757602002820191906000526020600020905b8154815260200190600101908083116102d3575b5050505050905090565b6001818154811061030157600080fd5b906000526020600020016000915090505481565b600060026000838152602001908152602001600020549050919050565b61033e828483346103d7565b50505050565b60026020528060005260406000206000915090505481565b60035481565b60008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b8060008151811061039a57610399610d58565b5b602002602001015160026000600354815260200190815260200160002081905550600360008154809291906103ce90610db6565b91905055505050565b60007f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff16634306d354866040518263ffffffff1660e01b81526004016104329190610e0d565b602060405180830381865afa15801561044f573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906104739190610e3d565b8210156104b5576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016104ac90610eb6565b60405180910390fd5b7f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff16634b494dc07f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff16634306d354886040518263ffffffff1660e01b815260040161054a9190610e0d565b602060405180830381865afa158015610567573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061058b9190610e3d565b8787876040518563ffffffff1660e01b81526004016105ac93929190610ee5565b6000604051808303818588803b1580156105c557600080fd5b505af11580156105d9573d6000803e3d6000fd5b50505050507f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff16634306d354866040518263ffffffff1660e01b81526004016106379190610e0d565b602060405180830381865afa158015610654573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106789190610e3d565b82111561072e5761072d337f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff16634306d354886040518263ffffffff1660e01b81526004016106dc9190610e0d565b602060405180830381865afa1580156106f9573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061071d9190610e3d565b846107289190610f1c565b6107c7565b5b7f000000000000000000000000c5d2637d24379d6371a5059d34718b70aecc2d7c73ffffffffffffffffffffffffffffffffffffffff1663fc2a88c36040518163ffffffff1660e01b8152600401602060405180830381865afa158015610799573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107bd9190610e3d565b9050949350505050565b60008273ffffffffffffffffffffffffffffffffffffffff16826040516107ed90610f81565b60006040518083038185875af1925050503d806000811461082a576040519150601f19603f3d011682016040523d82523d6000602084013e61082f565b606091505b505090508061083d57600080fd5b505050565b6000604051905090565b600080fd5b600080fd5b6000819050919050565b61086981610856565b811461087457600080fd5b50565b60008135905061088681610860565b92915050565b600080fd5b6000601f19601f8301169050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b6108da82610891565b810181811067ffffffffffffffff821117156108f9576108f86108a2565b5b80604052505050565b600061090c610842565b905061091882826108d1565b919050565b600067ffffffffffffffff821115610938576109376108a2565b5b602082029050602081019050919050565b600080fd5b600061096161095c8461091d565b610902565b9050808382526020820190506020840283018581111561098457610983610949565b5b835b818110156109ad57806109998882610877565b845260208401935050602081019050610986565b5050509392505050565b600082601f8301126109cc576109cb61088c565b5b81356109dc84826020860161094e565b91505092915050565b600080604083850312156109fc576109fb61084c565b5b6000610a0a85828601610877565b925050602083013567ffffffffffffffff811115610a2b57610a2a610851565b5b610a37858286016109b7565b9150509250929050565b600081519050919050565b600082825260208201905092915050565b6000819050602082019050919050565b610a7681610856565b82525050565b6000610a888383610a6d565b60208301905092915050565b6000602082019050919050565b6000610aac82610a41565b610ab68185610a4c565b9350610ac183610a5d565b8060005b83811015610af2578151610ad98882610a7c565b9750610ae483610a94565b925050600181019050610ac5565b5085935050505092915050565b60006020820190508181036000830152610b198184610aa1565b905092915050565b600060208284031215610b3757610b3661084c565b5b6000610b4584828501610877565b91505092915050565b610b5781610856565b82525050565b6000602082019050610b726000830184610b4e565b92915050565b600061ffff82169050919050565b610b8f81610b78565b8114610b9a57600080fd5b50565b600081359050610bac81610b86565b92915050565b600063ffffffff82169050919050565b610bcb81610bb2565b8114610bd657600080fd5b50565b600081359050610be881610bc2565b92915050565b600080600060608486031215610c0757610c0661084c565b5b6000610c1586828701610b9d565b9350506020610c2686828701610bd9565b9250506040610c3786828701610bd9565b9150509250925092565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b6000610c86610c81610c7c84610c41565b610c61565b610c41565b9050919050565b6000610c9882610c6b565b9050919050565b6000610caa82610c8d565b9050919050565b610cba81610c9f565b82525050565b6000602082019050610cd56000830184610cb1565b92915050565b600082825260208201905092915050565b7f6f6e6c792056524620563220777261707065722063616e2066756c66696c6c00600082015250565b6000610d22601f83610cdb565b9150610d2d82610cec565b602082019050919050565b60006020820190508181036000830152610d5181610d15565b9050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b6000610dc182610856565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8203610df357610df2610d87565b5b600182019050919050565b610e0781610bb2565b82525050565b6000602082019050610e226000830184610dfe565b92915050565b600081519050610e3781610860565b92915050565b600060208284031215610e5357610e5261084c565b5b6000610e6184828501610e28565b91505092915050565b7f496e73756666696369656e74207061796d656e7420616d6f756e740000000000600082015250565b6000610ea0601b83610cdb565b9150610eab82610e6a565b602082019050919050565b60006020820190508181036000830152610ecf81610e93565b9050919050565b610edf81610b78565b82525050565b6000606082019050610efa6000830186610dfe565b610f076020830185610ed6565b610f146040830184610dfe565b949350505050565b6000610f2782610856565b9150610f3283610856565b9250828203905081811115610f4a57610f49610d87565b5b92915050565b600081905092915050565b50565b6000610f6b600083610f50565b9150610f7682610f5b565b600082019050919050565b6000610f8c82610f5e565b915081905091905056fea26469706673582212206a124e63531ba842dd70849ed882f4e54a467a068311dd9bc064eb56b01714bc64736f6c63430008140033