Feature Tip: Add private address tag to any address under My Name Tag !
ERC-721
NFT
Overview
Max Total Supply
963 CREAT
Holders
192
Market
Volume (24H)
N/A
Min Price (24H)
N/A
Max Price (24H)
N/A
Other Info
Token Contract
Balance
1 CREATLoading...
Loading
Loading...
Loading
Loading...
Loading
# | Exchange | Pair | Price | 24H Volume | % Volume |
---|
Contract Name:
Creatures
Compiler Version
v0.7.4+commit.3f05b770
Contract Source Code (Solidity Multiple files format)
// SPDX-License-Identifier: MIT // // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./ERC721URIStorage.sol"; contract Creatures is ERC721URIStorage { enum AnimalType { Cow, Horse, Rabbit, Chicken, Pig, Cat, Dog, Goose, Goat, Sheep, Snake, Fish, Frog, Worm, Lama, Mouse, Camel, Donkey, Bee, Duck, GenesisEgg // 20 } enum Rarity { Normie, // 0 Chad, // 1 Degen, // 2 Unique // 3 } struct Animal { AnimalType atype; // uint8 Rarity rarity; // uint8 uint32 index; uint64 birthday; string name; } mapping (uint256 => Animal) public animals; mapping(address => bool) public trusted_markets; event TrustedMarket(address indexed _market, bool _state); constructor(string memory name_, string memory symbol_) ERC721(name_, symbol_) { } function mint( address to, uint256 tokenId, uint8 _animalType, uint8 _rarity, uint32 index ) external onlyOwner { _mint(to, tokenId); animals[tokenId] = Animal(AnimalType(_animalType), Rarity(_rarity), index, uint64(block.timestamp), ""); } function setName(uint256 tokenId, string calldata _name) external { require(ownerOf(tokenId) == msg.sender, 'Only owner can change name'); require(bytes(animals[tokenId].name).length == 0, 'The name has already been given'); animals[tokenId].name = _name; } function setTrustedMarket(address _market, bool _state) external onlyOwner { trusted_markets[_market] = _state; emit TrustedMarket(_market, _state); } function getTypeAndRarity(uint256 _tokenId) external view returns(uint8, uint8) { return (uint8(animals[_tokenId].atype), uint8(animals[_tokenId].rarity)); } function getUsersTokens(address _owner) external view returns (uint256[] memory) { //We can return only uint256[] memory uint256 n = balanceOf(_owner); uint256[] memory result = new uint256[](n); for (uint16 i=0; i < n; i++) { result[i]=tokenOfOwnerByIndex(_owner, i); } return result; } function baseURI() public view override returns (string memory) { return 'http://degens.farm/meta/creatures/'; } /** * @dev Overriding standart function for gas safe traiding with trusted parts like DegenFarm * Requirements: * * - `from` and `to` cannot be the zero address. * - `caller` must be added to trustedMarkets. */ function transferFrom(address from, address to, uint256 tokenId) public override { if (trusted_markets[msg.sender]) { _transfer(from, to, tokenId); } else { super.transferFrom(from, to, tokenId); } } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.2 <0.8.0; /** * @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 * ==== */ function isContract(address account) internal view returns (bool) { // This method relies on extcodesize, which returns 0 for contracts in // construction, since the code is only stored at the end of the // constructor execution. uint256 size; // solhint-disable-next-line no-inline-assembly assembly { size := extcodesize(account) } return size > 0; } /** * @dev Replacement for Solidity's `transfer`: sends `amount` wei to * `recipient`, forwarding all available gas and reverting on errors. * * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost * of certain opcodes, possibly making contracts go over the 2300 gas limit * imposed by `transfer`, making them unable to receive funds via * `transfer`. {sendValue} removes this limitation. * * https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more]. * * IMPORTANT: because control is transferred to `recipient`, care must be * taken to not create reentrancy vulnerabilities. Consider using * {ReentrancyGuard} or the * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern]. */ function sendValue(address payable recipient, uint256 amount) internal { require(address(this).balance >= amount, "Address: insufficient balance"); // solhint-disable-next-line avoid-low-level-calls, avoid-call-value (bool success, ) = recipient.call{ value: amount }(""); require(success, "Address: unable to send value, recipient may have reverted"); } /** * @dev Performs a Solidity function call using a low level `call`. A * plain`call` is an unsafe replacement for a function call: use this * function instead. * * If `target` reverts with a revert reason, it is bubbled up by this * function (like regular Solidity function calls). * * Returns the raw returned data. To convert to the expected return value, * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`]. * * Requirements: * * - `target` must be a contract. * - calling `target` with `data` must not revert. * * _Available since v3.1._ */ function functionCall(address target, bytes memory data) internal returns (bytes memory) { return functionCall(target, data, "Address: low-level call failed"); } /** * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with * `errorMessage` as a fallback revert reason when `target` reverts. * * _Available since v3.1._ */ function functionCall(address target, bytes memory data, string memory errorMessage) internal returns (bytes memory) { return functionCallWithValue(target, data, 0, errorMessage); } /** * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], * but also transferring `value` wei to `target`. * * Requirements: * * - the calling contract must have an ETH balance of at least `value`. * - the called Solidity function must be `payable`. * * _Available since v3.1._ */ function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) { return functionCallWithValue(target, data, value, "Address: low-level call with value failed"); } /** * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but * with `errorMessage` as a fallback revert reason when `target` reverts. * * _Available since v3.1._ */ function functionCallWithValue(address target, bytes memory data, uint256 value, string memory errorMessage) internal returns (bytes memory) { require(address(this).balance >= value, "Address: insufficient balance for call"); require(isContract(target), "Address: call to non-contract"); // solhint-disable-next-line avoid-low-level-calls (bool success, bytes memory returndata) = target.call{ value: value }(data); return _verifyCallResult(success, returndata, errorMessage); } /** * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], * but performing a static call. * * _Available since v3.3._ */ function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) { return functionStaticCall(target, data, "Address: low-level static call failed"); } /** * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`], * but performing a static call. * * _Available since v3.3._ */ function functionStaticCall(address target, bytes memory data, string memory errorMessage) internal view returns (bytes memory) { require(isContract(target), "Address: static call to non-contract"); // solhint-disable-next-line avoid-low-level-calls (bool success, bytes memory returndata) = target.staticcall(data); return _verifyCallResult(success, returndata, errorMessage); } /** * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], * but performing a delegate call. * * _Available since v3.4._ */ function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) { return functionDelegateCall(target, data, "Address: low-level delegate call failed"); } /** * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`], * but performing a delegate call. * * _Available since v3.4._ */ function functionDelegateCall(address target, bytes memory data, string memory errorMessage) internal returns (bytes memory) { require(isContract(target), "Address: delegate call to non-contract"); // solhint-disable-next-line avoid-low-level-calls (bool success, bytes memory returndata) = target.delegatecall(data); return _verifyCallResult(success, returndata, errorMessage); } function _verifyCallResult(bool success, bytes memory returndata, string memory errorMessage) private pure returns(bytes memory) { if (success) { return returndata; } else { // Look for revert reason and bubble it up if present if (returndata.length > 0) { // The easiest way to bubble the revert reason is using memory via assembly // solhint-disable-next-line no-inline-assembly assembly { let returndata_size := mload(returndata) revert(add(32, returndata), returndata_size) } } else { revert(errorMessage); } } } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <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 GSN 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 payable) { return msg.sender; } function _msgData() internal view virtual returns (bytes memory) { this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691 return msg.data; } }
// SPDX-License-Identifier: MIT // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./DegensFarmBase.sol"; contract DegenFarm is DegenFarmBase { uint8 constant public CREATURE_TYPE_COUNT= 20; //how much creatures types may be used uint256 constant public FARMING_DURATION = 168 hours; //in seconds //uint256 constant public NEXT_FARMING_DELAY = 1 weeks; uint256 constant public TOOL_UNSTAKE_DELAY = 1 weeks; uint256 constant public REVEAL_THRESHOLD = 810e18; //90% from MAX_BAGS uint16 constant public NORMIE_COUNT_IN_TYPE = 100; uint16 constant public CHAD_COUNT_IN_TYPE = 20; uint16 constant public MAX_LANDS = 2500; constructor ( address _land, address _creatures, address _inventory, address _bagstoken, address _dungtoken, IEggs _eggs ) DegenFarmBase(_land, _creatures, _inventory, _bagstoken, _dungtoken, _eggs) { require(CREATURE_TYPE_COUNT <= CREATURE_TYPE_COUNT_MAX, "CREATURE_TYPE_COUNT is greater than CREATURE_TYPE_COUNT_MAX"); // Mainnet amulet addrresses amulets[0] = [0xD533a949740bb3306d119CC777fa900bA034cd52, 0x1F573D6Fb3F13d689FF844B4cE37794d79a7FF1C]; amulets[1] = [0x1f9840a85d5aF5bf1D1762F925BDADdC4201F984, 0x111111111117dC0aa78b770fA6A738034120C302]; amulets[2] = [0xE41d2489571d322189246DaFA5ebDe1F4699F498, 0xC011a73ee8576Fb46F5E1c5751cA3B9Fe0af2a6F, 0xfA5047c9c78B8877af97BDcb85Db743fD7313d4a ]; amulets[3] = [0x0000000000000000000000000000000000000000, 0x0000000000000000000000000000000000000000]; amulets[4] = [0xc00e94Cb662C3520282E6f5717214004A7f26888, 0x6B3595068778DD592e39A122f4f5a5cF09C90fE2, 0x9f8F72aA9304c8B593d555F12eF6589cC3A579A2 ]; amulets[5] = [0x0D8775F648430679A709E98d2b0Cb6250d2887EF, 0x584bC13c7D411c00c01A62e8019472dE68768430]; amulets[6] = [0x3472A5A71965499acd81997a54BBA8D852C6E53d, 0x0F5D2fB29fb7d3CFeE444a200298f468908cC942]; amulets[7] = [0x514910771AF9Ca656af840dff83E8264EcF986CA, 0xd7c49CEE7E9188cCa6AD8FF264C1DA2e69D4Cf3B]; amulets[8] = [0x0bc529c00C6401aEF6D220BE8C6Ea1667F6Ad93e, 0x3155BA85D5F96b2d030a4966AF206230e46849cb]; amulets[9] = [0xa1faa113cbE53436Df28FF0aEe54275c13B40975, 0x3F382DbD960E3a9bbCeaE22651E88158d2791550, 0x7Fc66500c84A76Ad7e9c93437bFc5Ac33E2DDaE9 ]; // TODO: add amulets for (uint i = 10; i < CREATURE_TYPE_COUNT; i++) { amulets[i] = [0xa1faa113cbE53436Df28FF0aEe54275c13B40975]; } } function getCreatureTypeCount() override internal view returns (uint16) { return CREATURE_TYPE_COUNT; } function getFarmingDuration() override internal view returns (uint) { return FARMING_DURATION; } function getNormieCountInType() override internal view returns (uint16) { return NORMIE_COUNT_IN_TYPE; } function getChadCountInType() override internal view returns (uint16) { return CHAD_COUNT_IN_TYPE; } function getMaxLands() override internal view returns (uint16) { return MAX_LANDS; } function getToolUnstakeDelay() override internal view returns (uint) { return TOOL_UNSTAKE_DELAY; } }
// SPDX-License-Identifier: MIT // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./IERC20.sol"; import "./IERC1155.sol"; import "./ERC1155Receiver.sol"; import "./IERC721.sol"; import "./Ownable.sol"; interface IEggs is IERC721 { function mint(address to, uint256 tokenId) external; function burn(uint256 tokenId) external; function getUsersTokens(address _owner) external view returns (uint256[] memory); } interface ICreatures is IERC721 { function mint( address to, uint256 tokenId, uint8 _animalType, uint8 _rarity, uint32 index ) external; function getTypeAndRarity(uint256 _tokenId) external view returns(uint8, uint8); } interface ILand is IERC721 { function mint( address to, uint256 tokenId ) external; function burn(uint256 tokenId) external; } interface IDung is IERC20 { function mint( address to, uint256 amount ) external; } interface IInventory is IERC1155 { function getToolBoost(uint8 _item) external view returns (uint16); } interface IAmuletPriceProvider { function getLastPrice(address _amulet) external view returns (uint256); } interface IOperatorManage { function addOperator(address _newOperator) external; function removeOperator(address _oldOperator) external; function withdrawERC20(IERC20 _tokenContract, address _admin) external; } abstract contract DegenFarmBase is ERC1155Receiver, Ownable { enum AnimalType { Cow, Horse, Rabbit, Chicken, Pig, Cat, Dog, Goose, Goat, Sheep, Snake, Fish, Frog, Worm, Lama, Mouse, Camel, Donkey, Bee, Duck, GenesisEgg // 20 } enum Rarity { Normie, // 0 Chad, // 1 Degen, // 2 Unique // 3 } enum Result {Fail, Dung, Chad, Degen} //External conatrct addresses used with this farm. struct AddressRegistry { address land; address creatures; address inventory; address bagstoken; address dungtoken; } //Degens Farm Key numbers struct CreaturesCount { uint16 totalNormie; uint16 leftNormie; uint16 totalChad; uint16 leftChadToDiscover; uint16 totalDegen; uint16 leftDegenToDiscover; uint16 leftChadFarmAttempts; uint16 leftDegenFarmAttempts; } //Land count record struct LandCount { uint16 total; uint16 left; } // Record represent one farming act struct FarmRecord { uint256 creatureId; uint256 landId; uint256 harvestTime; uint256[] amuletsPrice1; uint256[] amuletsPrice2; Result harvest; uint256 harvestId; //new NFT tokenId bool[3] commonAmuletInitialHold; } // Bonus for better harvest struct Bonus { uint16 amuletHold; uint16 amuletBullTrend; uint16 inventoryHold; } uint8 constant public CREATURE_TYPE_COUNT_MAX = 20; //how much creatures types may be used //Creature probubility multiplier, scaled with 100. 3.00 - 300, 3.05 - 305 etc // so we need additional divide on 100 in formula uint32 constant public CREATURE_P_MULT = 230; uint16 public MAX_ALL_NORMIES = getCreatureTypeCount() * getNormieCountInType(); //subj uint256 constant public NFT_ID_MULTIPLIER = 10000; //must be set more then all Normies count uint256 constant public FARM_DUNG_AMOUNT = 250e32; //per one harvest uint16 constant public BONUS_POINTS_AMULET_HOLD = 10; uint16 constant public BONUS_POINTS_AMULET_BULL_TREND = 90; //Common Amulet addresses address[3] public COMMON_AMULETS = [ 0xa0246c9032bC3A600820415aE600c6388619A14D, 0x87d73E916D7057945c9BcD8cdd94e42A6F47f776, 0x126c121f99e1E211dF2e5f8De2d96Fa36647c855 ]; bool public REVEAL_ENABLED = false; bool public FARMING_ENABLED = false; address public priceProvider; IEggs public eggs; address[][CREATURE_TYPE_COUNT_MAX] public amulets; //amulets for creatures AddressRegistry public farm; LandCount public landCount; //common token price snapshots mapping(uint256 => uint256[3]) public commonAmuletPrices; mapping(address => uint256) public maxAmuletBalances; // mapping from user to his(her) staked tools // Index of uint256[6] represent tool NFT itemID mapping(address => uint256[6]) public userStakedTools; uint16 public allNormiesesLeft; CreaturesCount[CREATURE_TYPE_COUNT_MAX] public creaturesBorn; FarmRecord[] farming; event Reveal(uint256 indexed _tokenId, bool _isCreature, uint8 _animalType); event Harvest( uint256 indexed _eggId, address farmer, uint8 result , uint16 baseChance, uint16 amuletHold, uint16 amuletBullTrend, uint16 inventoryHold ); constructor ( address _land, address _creatures, address _inventory, address _bagstoken, address _dungtoken, IEggs _eggs ) { farm.land = _land; farm.creatures = _creatures; farm.inventory = _inventory; farm.bagstoken = _bagstoken; farm.dungtoken = _dungtoken; // Index of creaturesBorn in this initial setting // must NOT exceed CREATURE_TYPE_COUNT for (uint i = 0; i < getCreatureTypeCount(); i++) { creaturesBorn[i] = CreaturesCount( getNormieCountInType(), // totalNormie; getNormieCountInType(), // leftNormie; getChadCountInType(), // totalChad; getChadCountInType(), // leftChadToDiscover; 1, // totalDegen; 1, // leftDegenToDiscover; getNormieCountInType(), // leftChadFarmAttempts; getChadCountInType()); // leftDegenFarmAttempts; } landCount = LandCount(getMaxLands(), getMaxLands()); allNormiesesLeft = MAX_ALL_NORMIES; eggs = _eggs; } /** * @dev Changes inventory contract */ function setInventory(address _inventory) external onlyOwner { farm.inventory = _inventory; } function reveal(uint count) external { require(_isRevelEnabled(), "Please wait for reveal enabled."); require(count > 0, "Count must be positive"); require(count <= 8, "Count must less than 9"); // random limit require( IERC20(farm.bagstoken).allowance(msg.sender, address(this)) >= count*1, "Please approve your BAGS token to this contract." ); require( IERC20(farm.bagstoken).transferFrom(msg.sender, address(this), count*1) ); uint randomSeed = uint(keccak256(abi.encodePacked(block.timestamp, msg.sender))); // random seed for 8 reveals (8x32=256) for (uint i = 0; i < count; i++) { _reveal(randomSeed); randomSeed = randomSeed / 0x100000000; // shift right 32 bits } } event Log(string mess); /** * @dev Start farming process. New NFT - Egg will minted for user * @param _creatureId - NFT tokenId, caller must be owner of this token * @param _landId -- NFT tokenId, caller must be owner of this token */ function farmDeploy(uint256 _creatureId, uint256 _landId) external { require(FARMING_ENABLED == true, "Chief Farmer not enable yet"); require(ICreatures(farm.creatures).ownerOf(_creatureId) == msg.sender, "Need to be Creature Owner" ); require(ILand(farm.land).ownerOf(_landId) == msg.sender, "Need to be Land Owner" ); (uint8 crType, uint8 crRarity) = ICreatures(farm.creatures).getTypeAndRarity(_creatureId); require((DegenFarmBase.Rarity)(crRarity) == Rarity.Normie || (DegenFarmBase.Rarity)(crRarity) == Rarity.Chad, "Can farm only Normie and Chad"); //Check that farming available yet if (crRarity == 0) { require(creaturesBorn[crType].leftChadToDiscover > 0, "No more chads left"); } else { require(creaturesBorn[crType].leftDegenToDiscover > 0, "No more Degen left"); } //1. Lets make amulet price snapshot //1.1. First we need creat array with properly elements count uint256[] memory prices1 = new uint256[](amulets[crType].length); uint256[] memory prices2 = new uint256[](amulets[crType].length); prices1 = _getExistingAmuletsPrices(amulets[crType]); //2.Check and save Common Amulets price(if not exist yet) _saveCommonAmuletPrices(block.timestamp); //3. Save deploy record farming.push( FarmRecord({ creatureId: _creatureId, landId: _landId, harvestTime: block.timestamp + getFarmingDuration(), amuletsPrice1: prices1, amuletsPrice2: prices2, harvest: Result.Fail, harvestId: 0, commonAmuletInitialHold: _getCommonAmuletsHoldState(msg.sender) //save initial hold state }) ); // Let's mint Egg. eggs.mint( msg.sender, // farmer farming.length - 1 // tokenId ); //STAKE LAND and Creatures!!!! ILand(farm.land).transferFrom(msg.sender, address(this), _landId); ICreatures(farm.creatures).transferFrom(msg.sender, address(this), _creatureId); } /** * @dev Finish farming process. Egg NFT will be burn * @param _deployId - NFT tokenId, caller must be owner of this token */ function harvest(uint256 _deployId) external { require(eggs.ownerOf(_deployId) == msg.sender, "This is NOT YOUR EGG"); FarmRecord storage f = farming[_deployId]; require(f.harvestTime <= block.timestamp, "To early for harvest"); //Lets Calculate Dung/CHAD-DEGEN chance Result farmingResult; Bonus memory bonus; //1. BaseChance (uint8 crType, uint8 crRarity) = ICreatures(farm.creatures).getTypeAndRarity( f.creatureId ); uint16 baseChance; if (crRarity == 0) { //Try farm CHAD. So if there is no CHADs any more we must return assets if (creaturesBorn[crType].leftChadToDiscover == 0) { _endFarming(_deployId, Result.Fail); return; } baseChance = creaturesBorn[crType].leftChadToDiscover * 100 /(creaturesBorn[crType].leftChadFarmAttempts); //Decrease appropriate farm ATTEMPTS COUNT!!! creaturesBorn[crType].leftChadFarmAttempts -= 1; } else { //Try farm DEGEN. So if there is no DEGENSs any more we must return assets if (creaturesBorn[crType].leftDegenToDiscover == 0) { _endFarming(_deployId, Result.Fail); return; } baseChance = creaturesBorn[crType].leftDegenToDiscover * 100 /(creaturesBorn[crType].leftDegenFarmAttempts); //Decrease appropriate farm ATTEMPTS COUNT!!! creaturesBorn[crType].leftDegenFarmAttempts -= 1; } ////////////////////////////////////////////// // 2. Bonus for amulet token ***HOLD*** // 3. Bonus for amulets BULLs trend ////////////////////////////////////////////// bonus.amuletHold = 0; bonus.amuletBullTrend = 0; //Check common amulets _saveCommonAmuletPrices(block.timestamp); //Get current hold stae for (uint8 i = 0; i < COMMON_AMULETS.length; i ++){ if (f.commonAmuletInitialHold[i] && _getCommonAmuletsHoldState(msg.sender)[i]) { //token was hold at deploy time and now - iT IS GOOD //Lets check max Balance, because //bonus.amuletHold = userAmuletBalance/maxAmuletBalances*BONUS_POINTS_AMULET_HOLD _checkAndSaveMaxAmuletPrice(COMMON_AMULETS[i]); bonus.amuletHold = uint16( IERC20(COMMON_AMULETS[i]).balanceOf(msg.sender) * 100 / maxAmuletBalances[COMMON_AMULETS[i]] * BONUS_POINTS_AMULET_HOLD / 100 //100 used for scale ); //Lets check Bull TREND if (_getCommonAmuletPrices(f.harvestTime - getFarmingDuration())[i] < _getCommonAmuletPrices(block.timestamp)[i] ) { bonus.amuletBullTrend = BONUS_POINTS_AMULET_BULL_TREND; } break; } } //Ok, if there is NO common amulets lets check personal uint256[] memory prices2 = new uint256[](amulets[crType].length); prices2 = _getExistingAmuletsPrices(amulets[crType]); if (bonus.amuletHold != BONUS_POINTS_AMULET_HOLD) { for (uint8 i=0; i < f.amuletsPrice1.length; i ++){ if (f.amuletsPrice1[i] > 0 && prices2[i] > 0){ //Lets check max Balance, because //bonus.amuletHold = userAmuletBalance/maxAmuletBalances*BONUS_POINTS_AMULET_HOLD _checkAndSaveMaxAmuletPrice(amulets[i][crType]); bonus.amuletHold = uint16( IERC20(amulets[i][crType]).balanceOf(msg.sender) * 100 //100 used for scale / maxAmuletBalances[amulets[i][crType]] * BONUS_POINTS_AMULET_HOLD /100 ); //Lets check Bull TREND if (f.amuletsPrice1[i] < prices2[i]) { bonus.amuletBullTrend = BONUS_POINTS_AMULET_BULL_TREND; } break; } } } ////////////////////////////////////////////// ////////////////////////////////////////////// //4. Bonus for inventory ////////////////////////////////////////////// bonus.inventoryHold = 0; if (userStakedTools[msg.sender].length > 0) { for (uint8 i=0; i<userStakedTools[msg.sender].length; i++) { if (userStakedTools[msg.sender][i] > 0){ bonus.inventoryHold = bonus.inventoryHold + IInventory(farm.inventory).getToolBoost(i); } } } ////////////////////////////////////////////// uint16 allBonus = bonus.amuletHold + bonus.amuletBullTrend + bonus.inventoryHold; uint8 chanceOfRarityUP = uint8( (baseChance + allBonus) * 100 / (100 + allBonus) ); uint8[] memory choiceWeight = new uint8[](2); choiceWeight[0] = chanceOfRarityUP; choiceWeight[1] = 100 - chanceOfRarityUP; uint8 choice = uint8(_getWeightedChoice(choiceWeight)); if (choice == 0) { f.harvestId = (crRarity + 1) * NFT_ID_MULTIPLIER + _deployId; // Mint new chad/degen uint32 index; //Decrease appropriate CREATRURE COUNT if (crRarity + 1 == uint8(Rarity.Chad)) { index = creaturesBorn[crType].totalChad - creaturesBorn[crType].leftChadToDiscover + 1; creaturesBorn[crType].leftChadToDiscover -= 1; farmingResult = Result.Chad; } else if (crRarity + 1 == uint8(Rarity.Degen)) { index = creaturesBorn[crType].totalDegen - creaturesBorn[crType].leftDegenToDiscover + 1; creaturesBorn[crType].leftDegenToDiscover -= 1; farmingResult = Result.Degen; } ICreatures(farm.creatures).mint( msg.sender, (crRarity + 1) * NFT_ID_MULTIPLIER + _deployId, // new iD crType, //AnimalType crRarity + 1, index // index ); } else { //Mint new dung IDung(farm.dungtoken).mint(msg.sender, FARM_DUNG_AMOUNT); farmingResult = Result.Dung; } //BURN Land ILand(farm.land).burn(f.landId); _endFarming(_deployId, farmingResult); emit Harvest( _deployId, msg.sender, uint8(farmingResult), baseChance, bonus.amuletHold, bonus.amuletBullTrend, bonus.inventoryHold ); } /** * @dev Stake one inventory item * @param _itemId - NFT tokenId, caller must be owner of this token */ function stakeOneTool(uint8 _itemId) external { _stakeOneTool(_itemId); } /** * @dev UnStake one inventory item * @param _itemId - NFT tokenId */ function unstakeOneTool(uint8 _itemId) external { _unstakeOneTool(_itemId); } ///////////////////////////////////////////////////// //// Admin functions /////// ///////////////////////////////////////////////////// function setOneCommonAmulet(uint8 _index, address _token) external onlyOwner { COMMON_AMULETS[_index] = _token; } function setAmuletForOneCreature(uint8 _index, address[] memory _tokens) external onlyOwner { delete amulets[_index]; amulets[_index] = _tokens; } function setPriceProvider(address _priceProvider) external onlyOwner { priceProvider = _priceProvider; } function enableReveal(bool _isEnabled) external onlyOwner { REVEAL_ENABLED = _isEnabled; } function enableFarming(bool _isEnabled) external onlyOwner { FARMING_ENABLED = _isEnabled; } //////////////////////////////////////// /// Proxy for NFT Operators mamnage // //////////////////////////////////////// function addOperator(address _contract, address newOperator) external onlyOwner { IOperatorManage(_contract).addOperator(newOperator); } function removeOperator(address _contract, address oldOperator) external onlyOwner { IOperatorManage(_contract).removeOperator(oldOperator); } function reclaimToken(address _contract, IERC20 anyTokens, address _admin) external onlyOwner { IOperatorManage(_contract).withdrawERC20(anyTokens, _admin); } //////////////////////////////////////////////////////// function getCreatureAmulets(uint8 _creatureType) external view returns (address[] memory) { return _getCreatureAmulets(_creatureType); } function _getCreatureAmulets(uint8 _creatureType) internal view returns (address[] memory) { return amulets[_creatureType]; } function getCreatureStat(uint8 _creatureType) external view returns ( uint16, uint16, uint16, uint16, uint16, uint16, uint16, uint16 ) { CreaturesCount storage stat = creaturesBorn[_creatureType]; return ( stat.totalNormie, stat.leftNormie, stat.totalChad, stat.leftChadToDiscover, stat.totalDegen, stat.leftDegenToDiscover, stat.leftChadFarmAttempts, stat.leftDegenFarmAttempts ); } function getWeightedChoice(uint8[] memory _weights) external view returns (uint8){ return _getWeightedChoice(_weights); } function _getWeightedChoice(uint8[] memory _weights) internal view returns (uint8){ uint randomSeed = uint(keccak256(abi.encodePacked(block.timestamp, msg.sender))); return _getWeightedChoice2(_weights, randomSeed); } function getFarmingById(uint256 _farmingId) external view returns (FarmRecord memory) { return farming[_farmingId]; } function getCommonAmuletPrices(uint256 _timestamp) external view returns (uint256[3] memory) { return _getCommonAmuletPrices(_timestamp); } function getOneAmuletPrice(address _token) external view returns (uint256) { return _getOneAmuletPrice(_token); } /////////////////////////////////////////////// /// Internals /////// /////////////////////////////////////////////// /** * @dev Save farming results in storage and mint * appropriate token (NFT, ERC20 or None) */ function _endFarming(uint256 _deployId, Result _res) internal { //TODO need refactor if EGGs will be FarmRecord storage f = farming[_deployId]; f.harvest = _res; // unstake creature ICreatures(farm.creatures).transferFrom(address(this), msg.sender, f.creatureId); eggs.burn(_deployId); // Burn EGG if (_res == Result.Fail) { //unstake land (if staked) if (ILand(farm.land).ownerOf(f.landId) == address(this)){ ILand(farm.land).transferFrom(address(this), msg.sender, f.landId); } emit Harvest( _deployId, msg.sender, uint8(_res), 0, //baseChance 0, //bonus.amuletHold, 0, //bonus.amuletBullTrend, 0 //bonus.inventoryHold ); } } function _stakeOneTool(uint8 _itemId) internal { require(IInventory(farm.inventory).balanceOf(msg.sender, _itemId) >= 1, "You must own this tool for stake!" ); //Before stake we need two checks. //1. Removed //2. Cant`t stake one tool more than one item require(userStakedTools[msg.sender][_itemId] == 0, "Tool is already staked"); //stake IInventory(farm.inventory).safeTransferFrom( msg.sender, address(this), _itemId, 1, bytes('0') ); userStakedTools[msg.sender][_itemId] = block.timestamp; } function _unstakeOneTool(uint8 _itemId) internal { require(userStakedTools[msg.sender][_itemId] > 0, "This tool is not staked yet"); require(block.timestamp - userStakedTools[msg.sender][_itemId] >= getToolUnstakeDelay(), "Cant unstake earlier than a week" ); userStakedTools[msg.sender][_itemId] = 0; IInventory(farm.inventory).safeTransferFrom( address(this), msg.sender, _itemId, 1, bytes('0') ); } function _saveCommonAmuletPrices(uint256 _timestamp) internal { //Lets check if price NOT exist for this timestamp - lets save it if (commonAmuletPrices[_timestamp][0] == 0) { for (uint8 i=0; i < COMMON_AMULETS.length; i++){ commonAmuletPrices[_timestamp][i] = _getOneAmuletPrice(COMMON_AMULETS[i]); } } } function _checkAndSaveMaxAmuletPrice(address _amulet) internal { if (IERC20(_amulet).balanceOf(msg.sender) > maxAmuletBalances[_amulet] ) { maxAmuletBalances[_amulet] = IERC20(_amulet).balanceOf(msg.sender); } } function _getCommonAmuletPrices(uint256 _timestamp) internal view returns (uint256[3] memory) { //Lets check if price allready exist for this timestamp - just return it if (commonAmuletPrices[_timestamp][0] != 0) { return commonAmuletPrices[_timestamp]; } //If price is not exist lets get it from oracles uint256[3] memory res; for (uint8 i=0; i < COMMON_AMULETS.length; i++){ res[i] = _getOneAmuletPrice(COMMON_AMULETS[i]); } return res; } function _getCommonAmuletsHoldState(address _farmer) internal view returns (bool[3] memory) { //If token balance =0 - set false bool[3] memory res; for (uint8 i=0; i < COMMON_AMULETS.length; i++){ if (IERC20(COMMON_AMULETS[i]).balanceOf(_farmer) > 0){ res[i] = true; } else { // Set to zero if token balance is 0 res[i] = false; } } return res; } function _getExistingAmuletsPrices(address[] memory _tokens) internal view returns (uint256[] memory) { uint256[] memory res = new uint256[](_tokens.length); for (uint8 i=0; i < _tokens.length; i++){ if (IERC20(_tokens[i]).balanceOf(msg.sender) > 0){ res[i] = _getOneAmuletPrice(_tokens[i]); } else { // Set to zero if token balance is 0 res[i] = 0; } } return res; } function _getOneAmuletPrice(address _token) internal view returns (uint256) { return IAmuletPriceProvider(priceProvider).getLastPrice(_token); } function _isRevelEnabled() internal view returns (bool) { return REVEAL_ENABLED; } function _reveal(uint randomSeed) internal { require ((landCount.left + allNormiesesLeft) > 0, "Sorry, no more reveal!"); //1. Lets choose Land OR Creature, % //So we have two possible results. 1 - Land, 0 - Creature. // sum of weights = 100, lets define weigth for Creature uint8[] memory choiceWeight = new uint8[](2); choiceWeight[0] = uint8( uint32(allNormiesesLeft) * CREATURE_P_MULT // * 100 removed due CREATURE_P_MULT / (CREATURE_P_MULT * uint32(allNormiesesLeft) / 100 + uint32(landCount.left)) ); choiceWeight[1] = 100 - choiceWeight[0]; uint8 choice = uint8(_getWeightedChoice2(choiceWeight, randomSeed)); //Check that choice can be executed if (choice != 0 && landCount.left == 0) { //There are no more Lands. So we need change choice choice = 0; } if (choice == 0) { // create creature uint8[] memory choiceWeight0 = new uint8[](getCreatureTypeCount()); //2. Ok, Creature will be born. But what kind of? for (uint8 i = 0; i < getCreatureTypeCount(); i ++) { choiceWeight0[i] = uint8(creaturesBorn[i].leftNormie); } choice = uint8(_getWeightedChoice2(choiceWeight0, randomSeed / 0x10000)); // shift right 16 bits ICreatures(farm.creatures).mint( msg.sender, MAX_ALL_NORMIES - allNormiesesLeft, choice, //AnimalType 0, creaturesBorn[choice].totalNormie - creaturesBorn[choice].leftNormie + 1 // index ); emit Reveal(MAX_ALL_NORMIES - allNormiesesLeft, true, choice); allNormiesesLeft -= 1; creaturesBorn[choice].leftNormie -= 1; } else { // create land ILand(farm.land).mint( msg.sender, getMaxLands() - landCount.left ); emit Reveal(getMaxLands() - landCount.left , false, 0); landCount.left -= 1; } } function _getWeightedChoice2(uint8[] memory _weights, uint randomSeed) internal view returns (uint8){ uint256 sum_of_weights; for (uint8 i = 0; i < _weights.length; i++) { sum_of_weights += _weights[i]; } uint256 rnd = randomSeed % sum_of_weights; for (uint8 i = 0; i < _weights.length; i++) { if (rnd < _weights[i]) { return i; } rnd -= _weights[i]; } return 0; } /** @dev Handles the receipt of a single ERC1155 token type. This function is called at the end of a `safeTransferFrom` after the balance has been updated. To accept the transfer, this must return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` (i.e. 0xf23a6e61, or its own function selector). @param operator The address which initiated the transfer (i.e. msg.sender) @param from The address which previously owned the token @param id The ID of the token being transferred @param value The amount of tokens being transferred @param data Additional data with no specified format @return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` if transfer is allowed */ function onERC1155Received( address operator, address from, uint256 id, uint256 value, bytes calldata data ) external override returns(bytes4) { return bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)")); } /** @dev Handles the receipt of a multiple ERC1155 token types. This function is called at the end of a `safeBatchTransferFrom` after the balances have been updated. To accept the transfer(s), this must return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` (i.e. 0xbc197c81, or its own function selector). @param operator The address which initiated the batch transfer (i.e. msg.sender) @param from The address which previously owned the token @param ids An array containing ids of each token being transferred (order and length must match values array) @param values An array containing amounts of each token being transferred (order and length must match ids array) @param data Additional data with no specified format @return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` if transfer is allowed */ function onERC1155BatchReceived( address operator, address from, uint256[] calldata ids, uint256[] calldata values, bytes calldata data ) external override returns(bytes4) { return bytes4(keccak256("onERC1155BatchReceived(address,address,uint256,uint256,bytes)")); } function getCreatureTypeCount() virtual internal view returns (uint16); function getFarmingDuration() virtual internal view returns (uint); function getToolUnstakeDelay() virtual internal view returns (uint); function getNormieCountInType() virtual internal view returns (uint16); function getChadCountInType() virtual internal view returns (uint16); function getMaxLands() virtual internal view returns (uint16); function getUsersTokens(address _owner) external view returns (uint256[] memory) { return eggs.getUsersTokens(_owner); } }
// SPDX-License-Identifier: MIT // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./DegensFarmBase.sol"; contract DegenFarmLite is DegenFarmBase { uint8 constant public CREATURE_TYPE_COUNT= 2; //how much creatures types may be used uint256 constant public FARMING_DURATION = 168 seconds; //in seconds //uint256 constant public NEXT_FARMING_DELAY = 1 minutes; uint256 constant public TOOL_UNSTAKE_DELAY = 1 minutes; uint256 constant public REVEAL_THRESHOLD = 0; //90% from MAX_BAGS uint16 constant public NORMIE_COUNT_IN_TYPE = 20; uint16 constant public CHAD_COUNT_IN_TYPE = 5; uint16 constant public MAX_LANDS = 100; constructor ( address _land, address _creatures, address _inventory, address _bagstoken, address _dungtoken, IEggs _eggs ) DegenFarmBase(_land, _creatures, _inventory, _bagstoken, _dungtoken, _eggs) { require(CREATURE_TYPE_COUNT <= CREATURE_TYPE_COUNT_MAX, "CREATURE_TYPE_COUNT is greater than CREATURE_TYPE_COUNT_MAX"); // Rinkeby amulet addrresses amulets[0] = [0xD533a949740bb3306d119CC777fa900bA034cd52, 0x1F573D6Fb3F13d689FF844B4cE37794d79a7FF1C]; amulets[1] = [0x1f9840a85d5aF5bf1D1762F925BDADdC4201F984, 0x111111111117dC0aa78b770fA6A738034120C302]; } function getCreatureTypeCount() override internal view returns (uint16) { return CREATURE_TYPE_COUNT; } function getFarmingDuration() override internal view returns (uint) { return FARMING_DURATION; } function getNormieCountInType() override internal view returns (uint16) { return NORMIE_COUNT_IN_TYPE; } function getChadCountInType() override internal view returns (uint16) { return CHAD_COUNT_IN_TYPE; } function getMaxLands() override internal view returns (uint16) { return MAX_LANDS; } function getToolUnstakeDelay() override internal view returns (uint) { return TOOL_UNSTAKE_DELAY; } }
// SPDX-License-Identifier: MIT // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./ERC721URIStorage.sol"; contract Eggs is ERC721URIStorage { mapping(address => bool) public trusted_markets; event TrustedMarket(address indexed _market, bool _state); constructor() ERC721("Degen$ Farm Eggs", "EGG") { } function mint( address to, uint256 tokenId ) external onlyOwner { _mint(to, tokenId); } function setTrustedMarket(address _market, bool _state) external onlyOwner { trusted_markets[_market] = _state; emit TrustedMarket(_market, _state); } function getUsersTokens(address _owner) external view returns (uint256[] memory) { //We can return only uint256[] memory, but we cant use push // with memory arrays. //https://docs.soliditylang.org/en/v0.7.4/types.html#allocating-memory-arrays uint256 n = balanceOf(_owner); uint256[] memory result = new uint256[](n); for (uint16 i=0; i < n; i++) { result[i]=tokenOfOwnerByIndex(_owner, i); } return result; } function baseURI() public view override returns (string memory) { return 'http://degens.farm/meta/eggs/'; } /** * @dev Overriding standart function for gas safe traiding with trusted parts like DegenFarm * Requirements: * * - `from` and `to` cannot be the zero address. * - `caller` must be added to trustedMarkets. */ function transferFrom(address from, address to, uint256 tokenId) public override { if (trusted_markets[msg.sender]) { _transfer(from, to, tokenId); } else { super.transferFrom(from, to, tokenId); } } function burn(uint256 tokenId) external onlyOwner { _burn(tokenId); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @dev Library for managing an enumerable variant of Solidity's * https://solidity.readthedocs.io/en/latest/types.html#mapping-types[`mapping`] * type. * * Maps have the following properties: * * - Entries are added, removed, and checked for existence in constant time * (O(1)). * - Entries are enumerated in O(n). No guarantees are made on the ordering. * * ``` * contract Example { * // Add the library methods * using EnumerableMap for EnumerableMap.UintToAddressMap; * * // Declare a set state variable * EnumerableMap.UintToAddressMap private myMap; * } * ``` * * As of v3.0.0, only maps of type `uint256 -> address` (`UintToAddressMap`) are * supported. */ library EnumerableMap { // To implement this library for multiple types with as little code // repetition as possible, we write it in terms of a generic Map type with // bytes32 keys and values. // The Map implementation uses private functions, and user-facing // implementations (such as Uint256ToAddressMap) are just wrappers around // the underlying Map. // This means that we can only create new EnumerableMaps for types that fit // in bytes32. struct MapEntry { bytes32 _key; bytes32 _value; } struct Map { // Storage of map keys and values MapEntry[] _entries; // Position of the entry defined by a key in the `entries` array, plus 1 // because index 0 means a key is not in the map. mapping (bytes32 => uint256) _indexes; } /** * @dev Adds a key-value pair to a map, or updates the value for an existing * key. O(1). * * Returns true if the key was added to the map, that is if it was not * already present. */ function _set(Map storage map, bytes32 key, bytes32 value) private returns (bool) { // We read and store the key's index to prevent multiple reads from the same storage slot uint256 keyIndex = map._indexes[key]; if (keyIndex == 0) { // Equivalent to !contains(map, key) map._entries.push(MapEntry({ _key: key, _value: value })); // The entry is stored at length-1, but we add 1 to all indexes // and use 0 as a sentinel value map._indexes[key] = map._entries.length; return true; } else { map._entries[keyIndex - 1]._value = value; return false; } } /** * @dev Removes a key-value pair from a map. O(1). * * Returns true if the key was removed from the map, that is if it was present. */ function _remove(Map storage map, bytes32 key) private returns (bool) { // We read and store the key's index to prevent multiple reads from the same storage slot uint256 keyIndex = map._indexes[key]; if (keyIndex != 0) { // Equivalent to contains(map, key) // To delete a key-value pair from the _entries array in O(1), we swap the entry to delete with the last one // in the array, and then remove the last entry (sometimes called as 'swap and pop'). // This modifies the order of the array, as noted in {at}. uint256 toDeleteIndex = keyIndex - 1; uint256 lastIndex = map._entries.length - 1; // When the entry to delete is the last one, the swap operation is unnecessary. However, since this occurs // so rarely, we still do the swap anyway to avoid the gas cost of adding an 'if' statement. MapEntry storage lastEntry = map._entries[lastIndex]; // Move the last entry to the index where the entry to delete is map._entries[toDeleteIndex] = lastEntry; // Update the index for the moved entry map._indexes[lastEntry._key] = toDeleteIndex + 1; // All indexes are 1-based // Delete the slot where the moved entry was stored map._entries.pop(); // Delete the index for the deleted slot delete map._indexes[key]; return true; } else { return false; } } /** * @dev Returns true if the key is in the map. O(1). */ function _contains(Map storage map, bytes32 key) private view returns (bool) { return map._indexes[key] != 0; } /** * @dev Returns the number of key-value pairs in the map. O(1). */ function _length(Map storage map) private view returns (uint256) { return map._entries.length; } /** * @dev Returns the key-value pair stored at position `index` in the map. O(1). * * Note that there are no guarantees on the ordering of entries inside the * array, and it may change when more entries are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function _at(Map storage map, uint256 index) private view returns (bytes32, bytes32) { require(map._entries.length > index, "EnumerableMap: index out of bounds"); MapEntry storage entry = map._entries[index]; return (entry._key, entry._value); } /** * @dev Tries to returns the value associated with `key`. O(1). * Does not revert if `key` is not in the map. */ function _tryGet(Map storage map, bytes32 key) private view returns (bool, bytes32) { uint256 keyIndex = map._indexes[key]; if (keyIndex == 0) return (false, 0); // Equivalent to contains(map, key) return (true, map._entries[keyIndex - 1]._value); // All indexes are 1-based } /** * @dev Returns the value associated with `key`. O(1). * * Requirements: * * - `key` must be in the map. */ function _get(Map storage map, bytes32 key) private view returns (bytes32) { uint256 keyIndex = map._indexes[key]; require(keyIndex != 0, "EnumerableMap: nonexistent key"); // Equivalent to contains(map, key) return map._entries[keyIndex - 1]._value; // All indexes are 1-based } /** * @dev Same as {_get}, with a custom error message when `key` is not in the map. * * CAUTION: This function is deprecated because it requires allocating memory for the error * message unnecessarily. For custom revert reasons use {_tryGet}. */ function _get(Map storage map, bytes32 key, string memory errorMessage) private view returns (bytes32) { uint256 keyIndex = map._indexes[key]; require(keyIndex != 0, errorMessage); // Equivalent to contains(map, key) return map._entries[keyIndex - 1]._value; // All indexes are 1-based } // UintToAddressMap struct UintToAddressMap { Map _inner; } /** * @dev Adds a key-value pair to a map, or updates the value for an existing * key. O(1). * * Returns true if the key was added to the map, that is if it was not * already present. */ function set(UintToAddressMap storage map, uint256 key, address value) internal returns (bool) { return _set(map._inner, bytes32(key), bytes32(uint256(uint160(value)))); } /** * @dev Removes a value from a set. O(1). * * Returns true if the key was removed from the map, that is if it was present. */ function remove(UintToAddressMap storage map, uint256 key) internal returns (bool) { return _remove(map._inner, bytes32(key)); } /** * @dev Returns true if the key is in the map. O(1). */ function contains(UintToAddressMap storage map, uint256 key) internal view returns (bool) { return _contains(map._inner, bytes32(key)); } /** * @dev Returns the number of elements in the map. O(1). */ function length(UintToAddressMap storage map) internal view returns (uint256) { return _length(map._inner); } /** * @dev Returns the element stored at position `index` in the set. O(1). * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(UintToAddressMap storage map, uint256 index) internal view returns (uint256, address) { (bytes32 key, bytes32 value) = _at(map._inner, index); return (uint256(key), address(uint160(uint256(value)))); } /** * @dev Tries to returns the value associated with `key`. O(1). * Does not revert if `key` is not in the map. * * _Available since v3.4._ */ function tryGet(UintToAddressMap storage map, uint256 key) internal view returns (bool, address) { (bool success, bytes32 value) = _tryGet(map._inner, bytes32(key)); return (success, address(uint160(uint256(value)))); } /** * @dev Returns the value associated with `key`. O(1). * * Requirements: * * - `key` must be in the map. */ function get(UintToAddressMap storage map, uint256 key) internal view returns (address) { return address(uint160(uint256(_get(map._inner, bytes32(key))))); } /** * @dev Same as {get}, with a custom error message when `key` is not in the map. * * CAUTION: This function is deprecated because it requires allocating memory for the error * message unnecessarily. For custom revert reasons use {tryGet}. */ function get(UintToAddressMap storage map, uint256 key, string memory errorMessage) internal view returns (address) { return address(uint160(uint256(_get(map._inner, bytes32(key), errorMessage)))); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @dev Library for managing * https://en.wikipedia.org/wiki/Set_(abstract_data_type)[sets] of primitive * types. * * Sets have the following properties: * * - Elements are added, removed, and checked for existence in constant time * (O(1)). * - Elements are enumerated in O(n). No guarantees are made on the ordering. * * ``` * contract Example { * // Add the library methods * using EnumerableSet for EnumerableSet.AddressSet; * * // Declare a set state variable * EnumerableSet.AddressSet private mySet; * } * ``` * * As of v3.3.0, sets of type `bytes32` (`Bytes32Set`), `address` (`AddressSet`) * and `uint256` (`UintSet`) are supported. */ library EnumerableSet { // To implement this library for multiple types with as little code // repetition as possible, we write it in terms of a generic Set type with // bytes32 values. // The Set implementation uses private functions, and user-facing // implementations (such as AddressSet) are just wrappers around the // underlying Set. // This means that we can only create new EnumerableSets for types that fit // in bytes32. struct Set { // Storage of set values bytes32[] _values; // Position of the value in the `values` array, plus 1 because index 0 // means a value is not in the set. mapping (bytes32 => uint256) _indexes; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function _add(Set storage set, bytes32 value) private returns (bool) { if (!_contains(set, value)) { set._values.push(value); // The value is stored at length-1, but we add 1 to all indexes // and use 0 as a sentinel value set._indexes[value] = set._values.length; return true; } else { return false; } } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function _remove(Set storage set, bytes32 value) private returns (bool) { // We read and store the value's index to prevent multiple reads from the same storage slot uint256 valueIndex = set._indexes[value]; if (valueIndex != 0) { // Equivalent to contains(set, value) // To delete an element from the _values array in O(1), we swap the element to delete with the last one in // the array, and then remove the last element (sometimes called as 'swap and pop'). // This modifies the order of the array, as noted in {at}. uint256 toDeleteIndex = valueIndex - 1; uint256 lastIndex = set._values.length - 1; // When the value to delete is the last one, the swap operation is unnecessary. However, since this occurs // so rarely, we still do the swap anyway to avoid the gas cost of adding an 'if' statement. bytes32 lastvalue = set._values[lastIndex]; // Move the last value to the index where the value to delete is set._values[toDeleteIndex] = lastvalue; // Update the index for the moved value set._indexes[lastvalue] = toDeleteIndex + 1; // All indexes are 1-based // Delete the slot where the moved value was stored set._values.pop(); // Delete the index for the deleted slot delete set._indexes[value]; return true; } else { return false; } } /** * @dev Returns true if the value is in the set. O(1). */ function _contains(Set storage set, bytes32 value) private view returns (bool) { return set._indexes[value] != 0; } /** * @dev Returns the number of values on the set. O(1). */ function _length(Set storage set) private view returns (uint256) { return set._values.length; } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function _at(Set storage set, uint256 index) private view returns (bytes32) { require(set._values.length > index, "EnumerableSet: index out of bounds"); return set._values[index]; } // Bytes32Set struct Bytes32Set { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(Bytes32Set storage set, bytes32 value) internal returns (bool) { return _add(set._inner, value); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(Bytes32Set storage set, bytes32 value) internal returns (bool) { return _remove(set._inner, value); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(Bytes32Set storage set, bytes32 value) internal view returns (bool) { return _contains(set._inner, value); } /** * @dev Returns the number of values in the set. O(1). */ function length(Bytes32Set storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(Bytes32Set storage set, uint256 index) internal view returns (bytes32) { return _at(set._inner, index); } // AddressSet struct AddressSet { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(AddressSet storage set, address value) internal returns (bool) { return _add(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(AddressSet storage set, address value) internal returns (bool) { return _remove(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(AddressSet storage set, address value) internal view returns (bool) { return _contains(set._inner, bytes32(uint256(uint160(value)))); } /** * @dev Returns the number of values in the set. O(1). */ function length(AddressSet storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(AddressSet storage set, uint256 index) internal view returns (address) { return address(uint160(uint256(_at(set._inner, index)))); } // UintSet struct UintSet { Set _inner; } /** * @dev Add a value to a set. O(1). * * Returns true if the value was added to the set, that is if it was not * already present. */ function add(UintSet storage set, uint256 value) internal returns (bool) { return _add(set._inner, bytes32(value)); } /** * @dev Removes a value from a set. O(1). * * Returns true if the value was removed from the set, that is if it was * present. */ function remove(UintSet storage set, uint256 value) internal returns (bool) { return _remove(set._inner, bytes32(value)); } /** * @dev Returns true if the value is in the set. O(1). */ function contains(UintSet storage set, uint256 value) internal view returns (bool) { return _contains(set._inner, bytes32(value)); } /** * @dev Returns the number of values on the set. O(1). */ function length(UintSet storage set) internal view returns (uint256) { return _length(set._inner); } /** * @dev Returns the value stored at position `index` in the set. O(1). * * Note that there are no guarantees on the ordering of values inside the * array, and it may change when more values are added or removed. * * Requirements: * * - `index` must be strictly less than {length}. */ function at(UintSet storage set, uint256 index) internal view returns (uint256) { return uint256(_at(set._inner, index)); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; import "./IERC1155Receiver.sol"; import "./ERC165.sol"; /** * @dev _Available since v3.1._ */ abstract contract ERC1155Receiver is ERC165, IERC1155Receiver { constructor() internal { _registerInterface( ERC1155Receiver(address(0)).onERC1155Received.selector ^ ERC1155Receiver(address(0)).onERC1155BatchReceived.selector ); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; import "./IERC165.sol"; /** * @dev Implementation of the {IERC165} interface. * * Contracts may inherit from this and call {_registerInterface} to declare * their support of an interface. */ abstract contract ERC165 is IERC165 { /* * bytes4(keccak256('supportsInterface(bytes4)')) == 0x01ffc9a7 */ bytes4 private constant _INTERFACE_ID_ERC165 = 0x01ffc9a7; /** * @dev Mapping of interface ids to whether or not it's supported. */ mapping(bytes4 => bool) private _supportedInterfaces; constructor () internal { // Derived contracts need only register support for their own interfaces, // we register support for ERC165 itself here _registerInterface(_INTERFACE_ID_ERC165); } /** * @dev See {IERC165-supportsInterface}. * * Time complexity O(1), guaranteed to always use less than 30 000 gas. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return _supportedInterfaces[interfaceId]; } /** * @dev Registers the contract as an implementer of the interface defined by * `interfaceId`. Support of the actual ERC165 interface is automatic and * registering its interface id is not required. * * See {IERC165-supportsInterface}. * * Requirements: * * - `interfaceId` cannot be the ERC165 invalid interface (`0xffffffff`). */ function _registerInterface(bytes4 interfaceId) internal virtual { require(interfaceId != 0xffffffff, "ERC165: invalid interface id"); _supportedInterfaces[interfaceId] = true; } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; import "./Context.sol"; import "./IERC721.sol"; import "./IERC721Metadata.sol"; import "./IERC721Enumerable.sol"; import "./IERC721Receiver.sol"; import "./ERC165.sol"; import "./SafeMath.sol"; import "./Address.sol"; import "./EnumerableSet.sol"; import "./EnumerableMap.sol"; import "./Strings.sol"; /** * @title ERC721 Non-Fungible Token Standard basic implementation * @dev see https://eips.ethereum.org/EIPS/eip-721 */ contract ERC721 is Context, ERC165, IERC721, IERC721Metadata, IERC721Enumerable { using SafeMath for uint256; using Address for address; using EnumerableSet for EnumerableSet.UintSet; using EnumerableMap for EnumerableMap.UintToAddressMap; using Strings for uint256; // Equals to `bytes4(keccak256("onERC721Received(address,address,uint256,bytes)"))` // which can be also obtained as `IERC721Receiver(0).onERC721Received.selector` bytes4 private constant _ERC721_RECEIVED = 0x150b7a02; // Mapping from holder address to their (enumerable) set of owned tokens mapping (address => EnumerableSet.UintSet) private _holderTokens; // Enumerable mapping from token ids to their owners EnumerableMap.UintToAddressMap private _tokenOwners; // Mapping from token ID to approved address mapping (uint256 => address) private _tokenApprovals; // Mapping from owner to operator approvals mapping (address => mapping (address => bool)) private _operatorApprovals; // Token name string private _name; // Token symbol string private _symbol; // Optional mapping for token URIs mapping (uint256 => string) private _tokenURIs; // Base URI string private _baseURI; /* * bytes4(keccak256('balanceOf(address)')) == 0x70a08231 * bytes4(keccak256('ownerOf(uint256)')) == 0x6352211e * bytes4(keccak256('approve(address,uint256)')) == 0x095ea7b3 * bytes4(keccak256('getApproved(uint256)')) == 0x081812fc * bytes4(keccak256('setApprovalForAll(address,bool)')) == 0xa22cb465 * bytes4(keccak256('isApprovedForAll(address,address)')) == 0xe985e9c5 * bytes4(keccak256('transferFrom(address,address,uint256)')) == 0x23b872dd * bytes4(keccak256('safeTransferFrom(address,address,uint256)')) == 0x42842e0e * bytes4(keccak256('safeTransferFrom(address,address,uint256,bytes)')) == 0xb88d4fde * * => 0x70a08231 ^ 0x6352211e ^ 0x095ea7b3 ^ 0x081812fc ^ * 0xa22cb465 ^ 0xe985e9c5 ^ 0x23b872dd ^ 0x42842e0e ^ 0xb88d4fde == 0x80ac58cd */ bytes4 private constant _INTERFACE_ID_ERC721 = 0x80ac58cd; /* * bytes4(keccak256('name()')) == 0x06fdde03 * bytes4(keccak256('symbol()')) == 0x95d89b41 * bytes4(keccak256('tokenURI(uint256)')) == 0xc87b56dd * * => 0x06fdde03 ^ 0x95d89b41 ^ 0xc87b56dd == 0x5b5e139f */ bytes4 private constant _INTERFACE_ID_ERC721_METADATA = 0x5b5e139f; /* * bytes4(keccak256('totalSupply()')) == 0x18160ddd * bytes4(keccak256('tokenOfOwnerByIndex(address,uint256)')) == 0x2f745c59 * bytes4(keccak256('tokenByIndex(uint256)')) == 0x4f6ccce7 * * => 0x18160ddd ^ 0x2f745c59 ^ 0x4f6ccce7 == 0x780e9d63 */ bytes4 private constant _INTERFACE_ID_ERC721_ENUMERABLE = 0x780e9d63; /** * @dev Initializes the contract by setting a `name` and a `symbol` to the token collection. */ constructor (string memory name_, string memory symbol_) public { _name = name_; _symbol = symbol_; // register the supported interfaces to conform to ERC721 via ERC165 _registerInterface(_INTERFACE_ID_ERC721); _registerInterface(_INTERFACE_ID_ERC721_METADATA); _registerInterface(_INTERFACE_ID_ERC721_ENUMERABLE); } /** * @dev See {IERC721-balanceOf}. */ function balanceOf(address owner) public view virtual override returns (uint256) { require(owner != address(0), "ERC721: balance query for the zero address"); return _holderTokens[owner].length(); } /** * @dev See {IERC721-ownerOf}. */ function ownerOf(uint256 tokenId) public view virtual override returns (address) { return _tokenOwners.get(tokenId, "ERC721: owner query for nonexistent token"); } /** * @dev See {IERC721Metadata-name}. */ function name() public view virtual override returns (string memory) { return _name; } /** * @dev See {IERC721Metadata-symbol}. */ function symbol() public view virtual override returns (string memory) { return _symbol; } /** * @dev See {IERC721Metadata-tokenURI}. */ function tokenURI(uint256 tokenId) public view virtual override returns (string memory) { require(_exists(tokenId), "ERC721Metadata: URI query for nonexistent token"); string memory _tokenURI = _tokenURIs[tokenId]; string memory base = baseURI(); // If there is no base URI, return the token URI. if (bytes(base).length == 0) { return _tokenURI; } // If both are set, concatenate the baseURI and tokenURI (via abi.encodePacked). if (bytes(_tokenURI).length > 0) { return string(abi.encodePacked(base, _tokenURI)); } // If there is a baseURI but no tokenURI, concatenate the tokenID to the baseURI. return string(abi.encodePacked(base, tokenId.toString())); } /** * @dev Returns the base URI set via {_setBaseURI}. This will be * automatically added as a prefix in {tokenURI} to each token's URI, or * to the token ID if no specific URI is set for that token ID. */ function baseURI() public view virtual returns (string memory) { return _baseURI; } /** * @dev See {IERC721Enumerable-tokenOfOwnerByIndex}. */ function tokenOfOwnerByIndex(address owner, uint256 index) public view virtual override returns (uint256) { return _holderTokens[owner].at(index); } /** * @dev See {IERC721Enumerable-totalSupply}. */ function totalSupply() public view virtual override returns (uint256) { // _tokenOwners are indexed by tokenIds, so .length() returns the number of tokenIds return _tokenOwners.length(); } /** * @dev See {IERC721Enumerable-tokenByIndex}. */ function tokenByIndex(uint256 index) public view virtual override returns (uint256) { (uint256 tokenId, ) = _tokenOwners.at(index); return tokenId; } /** * @dev See {IERC721-approve}. */ function approve(address to, uint256 tokenId) public virtual override { address owner = ERC721.ownerOf(tokenId); require(to != owner, "ERC721: approval to current owner"); require(_msgSender() == owner || ERC721.isApprovedForAll(owner, _msgSender()), "ERC721: approve caller is not owner nor approved for all" ); _approve(to, tokenId); } /** * @dev See {IERC721-getApproved}. */ function getApproved(uint256 tokenId) public view virtual override returns (address) { require(_exists(tokenId), "ERC721: approved query for nonexistent token"); return _tokenApprovals[tokenId]; } /** * @dev See {IERC721-setApprovalForAll}. */ function setApprovalForAll(address operator, bool approved) public virtual override { require(operator != _msgSender(), "ERC721: approve to caller"); _operatorApprovals[_msgSender()][operator] = approved; emit ApprovalForAll(_msgSender(), operator, approved); } /** * @dev See {IERC721-isApprovedForAll}. */ function isApprovedForAll(address owner, address operator) public view virtual override returns (bool) { return _operatorApprovals[owner][operator]; } /** * @dev See {IERC721-transferFrom}. */ function transferFrom(address from, address to, uint256 tokenId) public virtual override { //solhint-disable-next-line max-line-length require(_isApprovedOrOwner(_msgSender(), tokenId), "ERC721: transfer caller is not owner nor approved"); _transfer(from, to, tokenId); } /** * @dev See {IERC721-safeTransferFrom}. */ function safeTransferFrom(address from, address to, uint256 tokenId) public virtual override { safeTransferFrom(from, to, tokenId, ""); } /** * @dev See {IERC721-safeTransferFrom}. */ function safeTransferFrom(address from, address to, uint256 tokenId, bytes memory _data) public virtual override { require(_isApprovedOrOwner(_msgSender(), tokenId), "ERC721: transfer caller is not owner nor approved"); _safeTransfer(from, to, tokenId, _data); } /** * @dev Safely transfers `tokenId` token from `from` to `to`, checking first that contract recipients * are aware of the ERC721 protocol to prevent tokens from being forever locked. * * `_data` is additional data, it has no specified format and it is sent in call to `to`. * * This internal function is equivalent to {safeTransferFrom}, and can be used to e.g. * implement alternative mechanisms to perform token transfer, such as signature-based. * * Requirements: * * - `from` cannot be the zero address. * - `to` cannot be the zero address. * - `tokenId` token must exist and be owned by `from`. * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer. * * Emits a {Transfer} event. */ function _safeTransfer(address from, address to, uint256 tokenId, bytes memory _data) internal virtual { _transfer(from, to, tokenId); require(_checkOnERC721Received(from, to, tokenId, _data), "ERC721: transfer to non ERC721Receiver implementer"); } /** * @dev Returns whether `tokenId` exists. * * Tokens can be managed by their owner or approved accounts via {approve} or {setApprovalForAll}. * * Tokens start existing when they are minted (`_mint`), * and stop existing when they are burned (`_burn`). */ function _exists(uint256 tokenId) internal view virtual returns (bool) { return _tokenOwners.contains(tokenId); } /** * @dev Returns whether `spender` is allowed to manage `tokenId`. * * Requirements: * * - `tokenId` must exist. */ function _isApprovedOrOwner(address spender, uint256 tokenId) internal view virtual returns (bool) { require(_exists(tokenId), "ERC721: operator query for nonexistent token"); address owner = ERC721.ownerOf(tokenId); return (spender == owner || getApproved(tokenId) == spender || ERC721.isApprovedForAll(owner, spender)); } /** * @dev Safely mints `tokenId` and transfers it to `to`. * * Requirements: d* * - `tokenId` must not exist. * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer. * * Emits a {Transfer} event. */ function _safeMint(address to, uint256 tokenId) internal virtual { _safeMint(to, tokenId, ""); } /** * @dev Same as {xref-ERC721-_safeMint-address-uint256-}[`_safeMint`], with an additional `data` parameter which is * forwarded in {IERC721Receiver-onERC721Received} to contract recipients. */ function _safeMint(address to, uint256 tokenId, bytes memory _data) internal virtual { _mint(to, tokenId); require(_checkOnERC721Received(address(0), to, tokenId, _data), "ERC721: transfer to non ERC721Receiver implementer"); } /** * @dev Mints `tokenId` and transfers it to `to`. * * WARNING: Usage of this method is discouraged, use {_safeMint} whenever possible * * Requirements: * * - `tokenId` must not exist. * - `to` cannot be the zero address. * * Emits a {Transfer} event. */ function _mint(address to, uint256 tokenId) internal virtual { require(to != address(0), "ERC721: mint to the zero address"); require(!_exists(tokenId), "ERC721: token already minted"); _beforeTokenTransfer(address(0), to, tokenId); _holderTokens[to].add(tokenId); _tokenOwners.set(tokenId, to); emit Transfer(address(0), to, tokenId); } /** * @dev Destroys `tokenId`. * The approval is cleared when the token is burned. * * Requirements: * * - `tokenId` must exist. * * Emits a {Transfer} event. */ function _burn(uint256 tokenId) internal virtual { address owner = ERC721.ownerOf(tokenId); // internal owner _beforeTokenTransfer(owner, address(0), tokenId); // Clear approvals _approve(address(0), tokenId); // Clear metadata (if any) if (bytes(_tokenURIs[tokenId]).length != 0) { delete _tokenURIs[tokenId]; } _holderTokens[owner].remove(tokenId); _tokenOwners.remove(tokenId); emit Transfer(owner, address(0), tokenId); } /** * @dev Transfers `tokenId` from `from` to `to`. * As opposed to {transferFrom}, this imposes no restrictions on msg.sender. * * Requirements: * * - `to` cannot be the zero address. * - `tokenId` token must be owned by `from`. * * Emits a {Transfer} event. */ function _transfer(address from, address to, uint256 tokenId) internal virtual { require(ERC721.ownerOf(tokenId) == from, "ERC721: transfer of token that is not own"); // internal owner require(to != address(0), "ERC721: transfer to the zero address"); _beforeTokenTransfer(from, to, tokenId); // Clear approvals from the previous owner _approve(address(0), tokenId); _holderTokens[from].remove(tokenId); _holderTokens[to].add(tokenId); _tokenOwners.set(tokenId, to); emit Transfer(from, to, tokenId); } /** * @dev Sets `_tokenURI` as the tokenURI of `tokenId`. * * Requirements: * * - `tokenId` must exist. */ function _setTokenURI(uint256 tokenId, string memory _tokenURI) internal virtual { require(_exists(tokenId), "ERC721Metadata: URI set of nonexistent token"); _tokenURIs[tokenId] = _tokenURI; } /** * @dev Internal function to set the base URI for all token IDs. It is * automatically added as a prefix to the value returned in {tokenURI}, * or to the token ID if {tokenURI} is empty. */ function _setBaseURI(string memory baseURI_) internal virtual { _baseURI = baseURI_; } /** * @dev Internal function to invoke {IERC721Receiver-onERC721Received} on a target address. * The call is not executed if the target address is not a contract. * * @param from address representing the previous owner of the given token ID * @param to target address that will receive the tokens * @param tokenId uint256 ID of the token to be transferred * @param _data bytes optional data to send along with the call * @return bool whether the call correctly returned the expected magic value */ function _checkOnERC721Received(address from, address to, uint256 tokenId, bytes memory _data) private returns (bool) { if (!to.isContract()) { return true; } bytes memory returndata = to.functionCall(abi.encodeWithSelector( IERC721Receiver(to).onERC721Received.selector, _msgSender(), from, tokenId, _data ), "ERC721: transfer to non ERC721Receiver implementer"); bytes4 retval = abi.decode(returndata, (bytes4)); return (retval == _ERC721_RECEIVED); } function _approve(address to, uint256 tokenId) private { _tokenApprovals[tokenId] = to; emit Approval(ERC721.ownerOf(tokenId), to, tokenId); // internal owner } /** * @dev Hook that is called before any token transfer. This includes minting * and burning. * * Calling conditions: * * - When `from` and `to` are both non-zero, ``from``'s `tokenId` will be * transferred to `to`. * - When `from` is zero, `tokenId` will be minted for `to`. * - When `to` is zero, ``from``'s `tokenId` will be burned. * - `from` cannot be the zero address. * - `to` cannot be the zero address. * * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks]. */ function _beforeTokenTransfer(address from, address to, uint256 tokenId) internal virtual { } }
// SPDX-License-Identifier: MIT pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./ERC721.sol"; import "./Operators.sol"; /** * @dev this contract used just for override some * OpneZeppelin tokenURI() behavior * so we need redeclare _tokenURIs becouse in OpenZeppelin * ERC721 it has private visibility */ abstract contract ERC721URIStorage is ERC721, Operators { using Strings for uint256; // Optional mapping for token URIs mapping (uint256 => string) private _tokenURIs; /** * @dev See {IERC721Metadata-tokenURI}. */ function tokenURI(uint256 tokenId) public view virtual override returns (string memory) { require(_exists(tokenId), "ERC721URIStorage: URI query for nonexistent token"); string memory _tokenURI = _tokenURIs[tokenId]; string memory base = baseURI(); // If there is no base URI, return the token URI. if (bytes(base).length == 0) { return _tokenURI; } // If both are set, concatenate the baseURI and tokenURI (via abi.encodePacked). if (bytes(_tokenURI).length > 0) { //return string(abi.encodePacked(base, _tokenURI)); //Due customer requirements return _tokenURI; } return super.tokenURI(tokenId); } /** * @dev Sets `_tokenURI` as the tokenURI of `tokenId`. * * Requirements: * * - `tokenId` must exist. */ function _setTokenURI(uint256 tokenId, string memory _tokenURI) internal virtual override { require(_exists(tokenId), "ERC721URIStorage: URI set of nonexistent token"); _tokenURIs[tokenId] = _tokenURI; } /** * @dev Destroys `tokenId`. * The approval is cleared when the token is burned. * * Requirements: * * - `tokenId` must exist. * * Emits a {Transfer} event. */ function _burn(uint256 tokenId) internal virtual override { super._burn(tokenId); if (bytes(_tokenURIs[tokenId]).length != 0) { delete _tokenURIs[tokenId]; } } function setURI(uint256 tokenId, string calldata _tokenURI) external onlyOperator { _setTokenURI(tokenId, _tokenURI); } function setURIBatch(uint256[] calldata tokenId, string[] calldata _tokenURI) external onlyOperator { require(tokenId.length == _tokenURI.length, "tokenId length is not equal to _tokenURI length"); for (uint i = 0; i < tokenId.length; i++) { _setTokenURI(tokenId[i], _tokenURI[i]); } } address public signerAddress; function setSigner(address _newSigner) external onlyOwner { signerAddress = _newSigner; } function hashArguments(uint256 tokenId, string calldata _tokenURI) public pure returns (bytes32 msgHash) { msgHash = keccak256(abi.encode(tokenId, _tokenURI)); } function getSigner(uint256 tokenId, string calldata _tokenURI, uint8 _v, bytes32 _r, bytes32 _s) public pure returns (address) { bytes32 msgHash = hashArguments(tokenId, _tokenURI); return ecrecover(msgHash, _v, _r, _s); } function isValidSignature(uint256 tokenId, string calldata _tokenURI, uint8 _v, bytes32 _r, bytes32 _s) public view returns (bool) { return getSigner(tokenId, _tokenURI, _v, _r, _s) == signerAddress; } /** * @dev Sets token URI using signature * This method can be called by anyone, who has signature, * that was created by signer role */ function setURISigned(uint256 tokenId, string calldata _tokenURI, uint8 _v, bytes32 _r, bytes32 _s) external { require(isValidSignature(tokenId, _tokenURI, _v, _r, _s), "Invalid signature"); _setTokenURI(tokenId, _tokenURI); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.2 <0.8.0; import "./IERC165.sol"; /** * @dev Required interface of an ERC1155 compliant contract, as defined in the * https://eips.ethereum.org/EIPS/eip-1155[EIP]. * * _Available since v3.1._ */ interface IERC1155 is IERC165 { /** * @dev Emitted when `value` tokens of token type `id` are transferred from `from` to `to` by `operator`. */ event TransferSingle(address indexed operator, address indexed from, address indexed to, uint256 id, uint256 value); /** * @dev Equivalent to multiple {TransferSingle} events, where `operator`, `from` and `to` are the same for all * transfers. */ event TransferBatch(address indexed operator, address indexed from, address indexed to, uint256[] ids, uint256[] values); /** * @dev Emitted when `account` grants or revokes permission to `operator` to transfer their tokens, according to * `approved`. */ event ApprovalForAll(address indexed account, address indexed operator, bool approved); /** * @dev Emitted when the URI for token type `id` changes to `value`, if it is a non-programmatic URI. * * If an {URI} event was emitted for `id`, the standard * https://eips.ethereum.org/EIPS/eip-1155#metadata-extensions[guarantees] that `value` will equal the value * returned by {IERC1155MetadataURI-uri}. */ event URI(string value, uint256 indexed id); /** * @dev Returns the amount of tokens of token type `id` owned by `account`. * * Requirements: * * - `account` cannot be the zero address. */ function balanceOf(address account, uint256 id) external view returns (uint256); /** * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {balanceOf}. * * Requirements: * * - `accounts` and `ids` must have the same length. */ function balanceOfBatch(address[] calldata accounts, uint256[] calldata ids) external view returns (uint256[] memory); /** * @dev Grants or revokes permission to `operator` to transfer the caller's tokens, according to `approved`, * * Emits an {ApprovalForAll} event. * * Requirements: * * - `operator` cannot be the caller. */ function setApprovalForAll(address operator, bool approved) external; /** * @dev Returns true if `operator` is approved to transfer ``account``'s tokens. * * See {setApprovalForAll}. */ function isApprovedForAll(address account, address operator) external view returns (bool); /** * @dev Transfers `amount` tokens of token type `id` from `from` to `to`. * * Emits a {TransferSingle} event. * * Requirements: * * - `to` cannot be the zero address. * - If the caller is not `from`, it must be have been approved to spend ``from``'s tokens via {setApprovalForAll}. * - `from` must have a balance of tokens of type `id` of at least `amount`. * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the * acceptance magic value. */ function safeTransferFrom(address from, address to, uint256 id, uint256 amount, bytes calldata data) external; /** * @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {safeTransferFrom}. * * Emits a {TransferBatch} event. * * Requirements: * * - `ids` and `amounts` must have the same length. * - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the * acceptance magic value. */ function safeBatchTransferFrom(address from, address to, uint256[] calldata ids, uint256[] calldata amounts, bytes calldata data) external; }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; import "./IERC165.sol"; /** * _Available since v3.1._ */ interface IERC1155Receiver is IERC165 { /** @dev Handles the receipt of a single ERC1155 token type. This function is called at the end of a `safeTransferFrom` after the balance has been updated. To accept the transfer, this must return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` (i.e. 0xf23a6e61, or its own function selector). @param operator The address which initiated the transfer (i.e. msg.sender) @param from The address which previously owned the token @param id The ID of the token being transferred @param value The amount of tokens being transferred @param data Additional data with no specified format @return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` if transfer is allowed */ function onERC1155Received( address operator, address from, uint256 id, uint256 value, bytes calldata data ) external returns(bytes4); /** @dev Handles the receipt of a multiple ERC1155 token types. This function is called at the end of a `safeBatchTransferFrom` after the balances have been updated. To accept the transfer(s), this must return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` (i.e. 0xbc197c81, or its own function selector). @param operator The address which initiated the batch transfer (i.e. msg.sender) @param from The address which previously owned the token @param ids An array containing ids of each token being transferred (order and length must match values array) @param values An array containing amounts of each token being transferred (order and length must match ids array) @param data Additional data with no specified format @return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` if transfer is allowed */ function onERC1155BatchReceived( address operator, address from, uint256[] calldata ids, uint256[] calldata values, bytes calldata data ) external returns(bytes4); }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <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); }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @dev Interface of the ERC20 standard as defined in the EIP. */ interface IERC20 { /** * @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 `recipient`. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transfer(address recipient, uint256 amount) external returns (bool); /** * @dev Returns the remaining number of tokens that `spender` will be * allowed to spend on behalf of `owner` through {transferFrom}. This is * zero by default. * * This value changes when {approve} or {transferFrom} are called. */ function allowance(address owner, address spender) external view returns (uint256); /** * @dev Sets `amount` as the allowance of `spender` over the caller's tokens. * * Returns a boolean value indicating whether the operation succeeded. * * IMPORTANT: Beware that changing an allowance with this method brings the risk * that someone may use both the old and the new allowance by unfortunate * transaction ordering. One possible solution to mitigate this race * condition is to first reduce the spender's allowance to 0 and set the * desired value afterwards: * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729 * * Emits an {Approval} event. */ function approve(address spender, uint256 amount) external returns (bool); /** * @dev Moves `amount` tokens from `sender` to `recipient` using the * allowance mechanism. `amount` is then deducted from the caller's * allowance. * * Returns a boolean value indicating whether the operation succeeded. * * Emits a {Transfer} event. */ function transferFrom(address sender, address recipient, uint256 amount) external returns (bool); /** * @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); }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.2 <0.8.0; import "./IERC165.sol"; /** * @dev Required interface of an ERC721 compliant contract. */ interface IERC721 is IERC165 { /** * @dev Emitted when `tokenId` token is transferred from `from` to `to`. */ event Transfer(address indexed from, address indexed to, uint256 indexed tokenId); /** * @dev Emitted when `owner` enables `approved` to manage the `tokenId` token. */ event Approval(address indexed owner, address indexed approved, uint256 indexed tokenId); /** * @dev Emitted when `owner` enables or disables (`approved`) `operator` to manage all of its assets. */ event ApprovalForAll(address indexed owner, address indexed operator, bool approved); /** * @dev Returns the number of tokens in ``owner``'s account. */ function balanceOf(address owner) external view returns (uint256 balance); /** * @dev Returns the owner of the `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function ownerOf(uint256 tokenId) external view returns (address owner); /** * @dev Safely transfers `tokenId` token from `from` to `to`, checking first that contract recipients * are aware of the ERC721 protocol to prevent tokens from being forever locked. * * Requirements: * * - `from` cannot be the zero address. * - `to` cannot be the zero address. * - `tokenId` token must exist and be owned by `from`. * - If the caller is not `from`, it must be have been allowed to move this token by either {approve} or {setApprovalForAll}. * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer. * * Emits a {Transfer} event. */ function safeTransferFrom(address from, address to, uint256 tokenId) external; /** * @dev Transfers `tokenId` token from `from` to `to`. * * WARNING: Usage of this method is discouraged, use {safeTransferFrom} whenever possible. * * Requirements: * * - `from` cannot be the zero address. * - `to` cannot be the zero address. * - `tokenId` token must be owned by `from`. * - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}. * * Emits a {Transfer} event. */ function transferFrom(address from, address to, uint256 tokenId) external; /** * @dev Gives permission to `to` to transfer `tokenId` token to another account. * The approval is cleared when the token is transferred. * * Only a single account can be approved at a time, so approving the zero address clears previous approvals. * * Requirements: * * - The caller must own the token or be an approved operator. * - `tokenId` must exist. * * Emits an {Approval} event. */ function approve(address to, uint256 tokenId) external; /** * @dev Returns the account approved for `tokenId` token. * * Requirements: * * - `tokenId` must exist. */ function getApproved(uint256 tokenId) external view returns (address operator); /** * @dev Approve or remove `operator` as an operator for the caller. * Operators can call {transferFrom} or {safeTransferFrom} for any token owned by the caller. * * Requirements: * * - The `operator` cannot be the caller. * * Emits an {ApprovalForAll} event. */ function setApprovalForAll(address operator, bool _approved) external; /** * @dev Returns if the `operator` is allowed to manage all of the assets of `owner`. * * See {setApprovalForAll} */ function isApprovedForAll(address owner, address operator) external view returns (bool); /** * @dev Safely transfers `tokenId` token from `from` to `to`. * * Requirements: * * - `from` cannot be the zero address. * - `to` cannot be the zero address. * - `tokenId` token must exist and be owned by `from`. * - If the caller is not `from`, it must be approved to move this token by either {approve} or {setApprovalForAll}. * - If `to` refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer. * * Emits a {Transfer} event. */ function safeTransferFrom(address from, address to, uint256 tokenId, bytes calldata data) external; }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.2 <0.8.0; import "./IERC721.sol"; /** * @title ERC-721 Non-Fungible Token Standard, optional enumeration extension * @dev See https://eips.ethereum.org/EIPS/eip-721 */ interface IERC721Enumerable is IERC721 { /** * @dev Returns the total amount of tokens stored by the contract. */ function totalSupply() external view returns (uint256); /** * @dev Returns a token ID owned by `owner` at a given `index` of its token list. * Use along with {balanceOf} to enumerate all of ``owner``'s tokens. */ function tokenOfOwnerByIndex(address owner, uint256 index) external view returns (uint256 tokenId); /** * @dev Returns a token ID at a given `index` of all the tokens stored by the contract. * Use along with {totalSupply} to enumerate all tokens. */ function tokenByIndex(uint256 index) external view returns (uint256); }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.2 <0.8.0; import "./IERC721.sol"; /** * @title ERC-721 Non-Fungible Token Standard, optional metadata extension * @dev See https://eips.ethereum.org/EIPS/eip-721 */ interface IERC721Metadata is IERC721 { /** * @dev Returns the token collection name. */ function name() external view returns (string memory); /** * @dev Returns the token collection symbol. */ function symbol() external view returns (string memory); /** * @dev Returns the Uniform Resource Identifier (URI) for `tokenId` token. */ function tokenURI(uint256 tokenId) external view returns (string memory); }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @title ERC721 token receiver interface * @dev Interface for any contract that wants to support safeTransfers * from ERC721 asset contracts. */ interface IERC721Receiver { /** * @dev Whenever an {IERC721} `tokenId` token is transferred to this contract via {IERC721-safeTransferFrom} * by `operator` from `from`, this function is called. * * It must return its Solidity selector to confirm the token transfer. * If any other value is returned or the interface is not implemented by the recipient, the transfer will be reverted. * * The selector can be obtained in Solidity with `IERC721.onERC721Received.selector`. */ function onERC721Received(address operator, address from, uint256 tokenId, bytes calldata data) external returns (bytes4); }
// SPDX-License-Identifier: MIT // Degen Farm: El Dorado. Collectible NFT game pragma solidity ^0.7.4; pragma experimental ABIEncoderV2; import "./ERC721URIStorage.sol"; contract Land is ERC721URIStorage { uint constant public MAP_HEIGHT = 50; uint constant public LAND_TYPE_COUNT = 5; enum LandType { None, Clay, Chalky, Sandy, Loamy, Peaty } struct LandPiece { LandType atype; // uint8 int32 x; int32 y; } mapping (uint256 => LandPiece) public lands; mapping(address => bool) public trusted_markets; event TrustedMarket(address indexed _market, bool _state); constructor(string memory name_, string memory symbol_) ERC721(name_, symbol_) { } function mint(address to, uint256 tokenId) external onlyOwner { int32 x = (int32)(tokenId / MAP_HEIGHT); int32 y = (int32)(tokenId % MAP_HEIGHT); LandPiece memory land = LandPiece(_createLandType(x, y), x, y); lands[tokenId] = land; _mint(to, tokenId); } function _createLandType(int32 x, int32 y) internal returns (LandType) { uint256 rnd = uint(keccak256(abi.encodePacked(block.timestamp, msg.sender, totalSupply()))) % LAND_TYPE_COUNT; return (LandType)(rnd + 1); } function burn(uint256 tokenId) external { _burn(tokenId); } function setTrustedMarket(address _market, bool _state) external onlyOwner { trusted_markets[_market] = _state; emit TrustedMarket(_market, _state); } function getUsersTokens(address _owner) external view returns (uint256[] memory) { //https://docs.soliditylang.org/en/v0.7.4/types.html#allocating-memory-arrays //So first we need calc size of array to be returned uint256 n = balanceOf(_owner); uint256[] memory result = new uint256[](n); for (uint16 i=0; i < n; i++) { result[i]=tokenOfOwnerByIndex(_owner, i); } return result; } function baseURI() public view override returns (string memory) { return 'http://degens.farm/meta/lands/'; } /** * @dev Overriding standart function for gas safe traiding with trusted parts like DegenFarm * Requirements: * * - `from` and `to` cannot be the zero address. * - `caller` must be added to trustedMarkets. */ function transferFrom(address from, address to, uint256 tokenId) public override { if (trusted_markets[msg.sender]) { _transfer(from, to, tokenId); } else { super.transferFrom(from, to, tokenId); } } }
// SPDX-License-Identifier: MIT // Degen Farm. Collectible NFT game pragma solidity ^0.7.4; import "./IERC20.sol"; import "./Ownable.sol"; contract Operators is Ownable { mapping (address=>bool) operatorAddress; modifier onlyOperator() { require(isOperator(msg.sender), "Access denied"); _; } function isOwner(address _addr) public view returns (bool) { return owner() == _addr; } function isOperator(address _addr) public view returns (bool) { return operatorAddress[_addr] || isOwner(_addr); } function addOperator(address _newOperator) external onlyOwner { require(_newOperator != address(0), "New operator is empty"); operatorAddress[_newOperator] = true; } function removeOperator(address _oldOperator) external onlyOwner { delete(operatorAddress[_oldOperator]); } /** * @dev Owner can claim any tokens that transferred * to this contract address */ function withdrawERC20(IERC20 _tokenContract, address _admin) external onlyOwner { uint256 balance = _tokenContract.balanceOf(address(this)); _tokenContract.transfer(_admin, balance); } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; import "./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 () internal { address msgSender = _msgSender(); _owner = msgSender; emit OwnershipTransferred(address(0), msgSender); } /** * @dev Returns the address of the current owner. */ function owner() public view virtual returns (address) { return _owner; } /** * @dev Throws if called by any account other than the owner. */ modifier onlyOwner() { require(owner() == _msgSender(), "Ownable: caller is not the owner"); _; } /** * @dev Leaves the contract without owner. It will not be possible to call * `onlyOwner` functions anymore. Can only be called by the current owner. * * NOTE: Renouncing ownership will leave the contract without an owner, * thereby removing any functionality that is only available to the owner. */ function renounceOwnership() public virtual onlyOwner { emit OwnershipTransferred(_owner, address(0)); _owner = address(0); } /** * @dev Transfers ownership of the contract to a new account (`newOwner`). * Can only be called by the current owner. */ function transferOwnership(address newOwner) public virtual onlyOwner { require(newOwner != address(0), "Ownable: new owner is the zero address"); emit OwnershipTransferred(_owner, newOwner); _owner = newOwner; } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @dev Wrappers over Solidity's arithmetic operations with added overflow * checks. * * Arithmetic operations in Solidity wrap on overflow. This can easily result * in bugs, because programmers usually assume that an overflow raises an * error, which is the standard behavior in high level programming languages. * `SafeMath` restores this intuition by reverting the transaction when an * operation overflows. * * Using this library instead of the unchecked operations eliminates an entire * class of bugs, so it's recommended to use it always. */ library SafeMath { /** * @dev Returns the addition of two unsigned integers, with an overflow flag. * * _Available since v3.4._ */ function tryAdd(uint256 a, uint256 b) internal pure returns (bool, uint256) { uint256 c = a + b; if (c < a) return (false, 0); return (true, c); } /** * @dev Returns the substraction of two unsigned integers, with an overflow flag. * * _Available since v3.4._ */ function trySub(uint256 a, uint256 b) internal pure returns (bool, uint256) { if (b > a) return (false, 0); return (true, a - b); } /** * @dev Returns the multiplication of two unsigned integers, with an overflow flag. * * _Available since v3.4._ */ function tryMul(uint256 a, uint256 b) internal pure returns (bool, uint256) { // Gas optimization: this is cheaper than requiring 'a' not being zero, but the // benefit is lost if 'b' is also tested. // See: https://github.com/OpenZeppelin/openzeppelin-contracts/pull/522 if (a == 0) return (true, 0); uint256 c = a * b; if (c / a != b) return (false, 0); return (true, c); } /** * @dev Returns the division of two unsigned integers, with a division by zero flag. * * _Available since v3.4._ */ function tryDiv(uint256 a, uint256 b) internal pure returns (bool, uint256) { if (b == 0) return (false, 0); return (true, a / b); } /** * @dev Returns the remainder of dividing two unsigned integers, with a division by zero flag. * * _Available since v3.4._ */ function tryMod(uint256 a, uint256 b) internal pure returns (bool, uint256) { if (b == 0) return (false, 0); return (true, a % b); } /** * @dev Returns the addition of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `+` operator. * * Requirements: * * - Addition cannot overflow. */ function add(uint256 a, uint256 b) internal pure returns (uint256) { uint256 c = a + b; require(c >= a, "SafeMath: addition overflow"); return c; } /** * @dev Returns the subtraction of two unsigned integers, reverting on * overflow (when the result is negative). * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b) internal pure returns (uint256) { require(b <= a, "SafeMath: subtraction overflow"); return a - b; } /** * @dev Returns the multiplication of two unsigned integers, reverting on * overflow. * * Counterpart to Solidity's `*` operator. * * Requirements: * * - Multiplication cannot overflow. */ function mul(uint256 a, uint256 b) internal pure returns (uint256) { if (a == 0) return 0; uint256 c = a * b; require(c / a == b, "SafeMath: multiplication overflow"); return c; } /** * @dev Returns the integer division of two unsigned integers, reverting on * division by zero. The result is rounded towards zero. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b) internal pure returns (uint256) { require(b > 0, "SafeMath: division by zero"); return a / b; } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * reverting when dividing by zero. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b) internal pure returns (uint256) { require(b > 0, "SafeMath: modulo by zero"); return a % b; } /** * @dev Returns the subtraction of two unsigned integers, reverting with custom message on * overflow (when the result is negative). * * CAUTION: This function is deprecated because it requires allocating memory for the error * message unnecessarily. For custom revert reasons use {trySub}. * * Counterpart to Solidity's `-` operator. * * Requirements: * * - Subtraction cannot overflow. */ function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b <= a, errorMessage); return a - b; } /** * @dev Returns the integer division of two unsigned integers, reverting with custom message on * division by zero. The result is rounded towards zero. * * CAUTION: This function is deprecated because it requires allocating memory for the error * message unnecessarily. For custom revert reasons use {tryDiv}. * * Counterpart to Solidity's `/` operator. Note: this function uses a * `revert` opcode (which leaves remaining gas untouched) while Solidity * uses an invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b > 0, errorMessage); return a / b; } /** * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo), * reverting with custom message when dividing by zero. * * CAUTION: This function is deprecated because it requires allocating memory for the error * message unnecessarily. For custom revert reasons use {tryMod}. * * Counterpart to Solidity's `%` operator. This function uses a `revert` * opcode (which leaves remaining gas untouched) while Solidity uses an * invalid opcode to revert (consuming all remaining gas). * * Requirements: * * - The divisor cannot be zero. */ function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) { require(b > 0, errorMessage); return a % b; } }
// SPDX-License-Identifier: MIT pragma solidity >=0.6.0 <0.8.0; /** * @dev String operations. */ library Strings { /** * @dev Converts a `uint256` to its ASCII `string` representation. */ function toString(uint256 value) internal pure returns (string memory) { // Inspired by OraclizeAPI's implementation - MIT licence // https://github.com/oraclize/ethereum-api/blob/b42146b063c7d6ee1358846c198246239e9360e8/oraclizeAPI_0.4.25.sol if (value == 0) { return "0"; } uint256 temp = value; uint256 digits; while (temp != 0) { digits++; temp /= 10; } bytes memory buffer = new bytes(digits); uint256 index = digits - 1; temp = value; while (temp != 0) { buffer[index--] = bytes1(uint8(48 + temp % 10)); temp /= 10; } return string(buffer); } }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
[{"inputs":[{"internalType":"string","name":"name_","type":"string"},{"internalType":"string","name":"symbol_","type":"string"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"approved","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"_market","type":"address"},{"indexed":false,"internalType":"bool","name":"_state","type":"bool"}],"name":"TrustedMarket","type":"event"},{"inputs":[{"internalType":"address","name":"_newOperator","type":"address"}],"name":"addOperator","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"animals","outputs":[{"internalType":"enum Creatures.AnimalType","name":"atype","type":"uint8"},{"internalType":"enum Creatures.Rarity","name":"rarity","type":"uint8"},{"internalType":"uint32","name":"index","type":"uint32"},{"internalType":"uint64","name":"birthday","type":"uint64"},{"internalType":"string","name":"name","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"baseURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_tokenURI","type":"string"},{"internalType":"uint8","name":"_v","type":"uint8"},{"internalType":"bytes32","name":"_r","type":"bytes32"},{"internalType":"bytes32","name":"_s","type":"bytes32"}],"name":"getSigner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokenId","type":"uint256"}],"name":"getTypeAndRarity","outputs":[{"internalType":"uint8","name":"","type":"uint8"},{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_owner","type":"address"}],"name":"getUsersTokens","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_tokenURI","type":"string"}],"name":"hashArguments","outputs":[{"internalType":"bytes32","name":"msgHash","type":"bytes32"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_addr","type":"address"}],"name":"isOperator","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_addr","type":"address"}],"name":"isOwner","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_tokenURI","type":"string"},{"internalType":"uint8","name":"_v","type":"uint8"},{"internalType":"bytes32","name":"_r","type":"bytes32"},{"internalType":"bytes32","name":"_s","type":"bytes32"}],"name":"isValidSignature","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"uint8","name":"_animalType","type":"uint8"},{"internalType":"uint8","name":"_rarity","type":"uint8"},{"internalType":"uint32","name":"index","type":"uint32"}],"name":"mint","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"ownerOf","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_oldOperator","type":"address"}],"name":"removeOperator","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"_data","type":"bytes"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_name","type":"string"}],"name":"setName","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_newSigner","type":"address"}],"name":"setSigner","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_market","type":"address"},{"internalType":"bool","name":"_state","type":"bool"}],"name":"setTrustedMarket","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_tokenURI","type":"string"}],"name":"setURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"tokenId","type":"uint256[]"},{"internalType":"string[]","name":"_tokenURI","type":"string[]"}],"name":"setURIBatch","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"string","name":"_tokenURI","type":"string"},{"internalType":"uint8","name":"_v","type":"uint8"},{"internalType":"bytes32","name":"_r","type":"bytes32"},{"internalType":"bytes32","name":"_s","type":"bytes32"}],"name":"setURISigned","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"signerAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"index","type":"uint256"}],"name":"tokenByIndex","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"uint256","name":"index","type":"uint256"}],"name":"tokenOfOwnerByIndex","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"trusted_markets","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"contract IERC20","name":"_tokenContract","type":"address"},{"internalType":"address","name":"_admin","type":"address"}],"name":"withdrawERC20","outputs":[],"stateMutability":"nonpayable","type":"function"}]
Contract Creation Code
60806040523480156200001157600080fd5b5060405162003602380380620036028339810160408190526200003491620002e7565b8181620000486301ffc9a760e01b6200010f565b81516200005d90600690602085019062000198565b5080516200007390600790602084019062000198565b50620000866380ac58cd60e01b6200010f565b62000098635b5e139f60e01b6200010f565b620000aa63780e9d6360e01b6200010f565b5060009050620000b962000194565b600a80546001600160a01b0319166001600160a01b038316908117909155604051919250906000907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908290a35050506200034e565b6001600160e01b031980821614156200016f576040805162461bcd60e51b815260206004820152601c60248201527f4552433136353a20696e76616c696420696e7465726661636520696400000000604482015290519081900360640190fd5b6001600160e01b0319166000908152602081905260409020805460ff19166001179055565b3390565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282620001d057600085556200021b565b82601f10620001eb57805160ff19168380011785556200021b565b828001600101855582156200021b579182015b828111156200021b578251825591602001919060010190620001fe565b50620002299291506200022d565b5090565b5b808211156200022957600081556001016200022e565b600082601f83011262000255578081fd5b81516001600160401b03808211156200026a57fe5b6040516020601f8401601f19168201810183811183821017156200028a57fe5b80604052508194508382528681858801011115620002a757600080fd5b600092505b83831015620002cb5785830181015182840182015291820191620002ac565b83831115620002dd5760008185840101525b5050505092915050565b60008060408385031215620002fa578182fd5b82516001600160401b038082111562000311578384fd5b6200031f8683870162000244565b9350602085015191508082111562000335578283fd5b50620003448582860162000244565b9150509250929050565b6132a4806200035e6000396000f3fe608060405234801561001057600080fd5b50600436106102485760003560e01c806385aa84b61161013b578063a22cb465116100b8578063e8c9a3b31161007c578063e8c9a3b314610504578063e985e9c514610517578063eb46a4661461052a578063f2fde38b1461053d578063fe55932a1461055057610248565b8063a22cb465146104a5578063ac8a584a146104b8578063b88d4fde146104cb578063c87b56dd146104de578063d7a377a1146104f157610248565b806395d89b41116100ff57806395d89b4114610432578063963513ca1461043a5780639870d7fe1461044d578063998dd3ca146104605780639ed4f2561461048457610248565b806385aa84b6146103de578063862440e2146103f157806389dd289f146104045780638da5cb5b146104175780639456fbcc1461041f57610248565b80634f6ccce7116101c95780636c0360eb1161018d5780636c0360eb146103955780636c19e7831461039d5780636d70f7ae146103b057806370a08231146103c3578063715018a6146103d657610248565b80634f6ccce714610334578063509044be14610347578063540d259e146103675780635b7633d01461037a5780636352211e1461038257610248565b806318160ddd1161021057806318160ddd146102d357806323b872dd146102e85780632f54bf6e146102fb5780632f745c591461030e57806342842e0e1461032157610248565b806301b98ea01461024d57806301ffc9a71461026257806306fdde031461028b578063081812fc146102a0578063095ea7b3146102c0575b600080fd5b61026061025b366004612b0c565b610563565b005b610275610270366004612b74565b61065d565b6040516102829190612d1f565b60405180910390f35b610293610680565b6040516102829190612d9f565b6102b36102ae366004612bae565b610716565b6040516102829190612cc7565b6102606102ce366004612a76565b610778565b6102db61084e565b6040516102829190612d2a565b6102606102f6366004612942565b61085f565b6102756103093660046128ee565b610892565b6102db61031c366004612a76565b6108b6565b61026061032f366004612942565b6108e1565b6102db610342366004612bae565b6108fc565b61035a6103553660046128ee565b610912565b6040516102829190612cdb565b610260610375366004612c0f565b6109a6565b6102b3610a18565b6102b3610390366004612bae565b610a27565b610293610a4f565b6102606103ab3660046128ee565b610a6f565b6102756103be3660046128ee565b610af3565b6102db6103d13660046128ee565b610b1e565b610260610b86565b6102b36103ec366004612c0f565b610c32565b6102606103ff366004612bc6565b610c9e565b6102db610412366004612bc6565b610d28565b6102b3610d5e565b61026061042d366004612b9c565b610d6d565b610293610eca565b610275610448366004612c0f565b610f2b565b61026061045b3660046128ee565b610f5d565b61047361046e366004612bae565b611036565b604051610282959493929190612d51565b610497610492366004612bae565b611109565b604051610282929190612f6f565b6102606104b3366004612a45565b611153565b6102606104c63660046128ee565b611258565b6102606104d9366004612982565b6112db565b6102936104ec366004612bae565b611339565b6102606104ff366004612a45565b61143a565b610260610512366004612aa1565b6114fc565b61027561052536600461290a565b6116a2565b6102756105383660046128ee565b6116d0565b61026061054b3660046128ee565b6116e5565b61026061055e366004612bc6565b6117e8565b61056c33610af3565b6105ad576040805162461bcd60e51b815260206004820152600d60248201526c1058d8d95cdcc819195b9a5959609a1b604482015290519081900360640190fd5b8281146105d55760405162461bcd60e51b81526004016105cc90612db2565b60405180910390fd5b60005b838110156106565761064e8585838181106105ef57fe5b9050602002013584848481811061060257fe5b90506020028101906106149190612f83565b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b6001016105d8565b5050505050565b6001600160e01b0319811660009081526020819052604090205460ff165b919050565b60068054604080516020601f600260001961010060018816150201909516949094049384018190048102820181019092528281526060939092909183018282801561070c5780601f106106e15761010080835404028352916020019161070c565b820191906000526020600020905b8154815290600101906020018083116106ef57829003601f168201915b5050505050905090565b6000610721826118b9565b61075c5760405162461bcd60e51b815260040180806020018281038252602c815260200180613179602c913960400191505060405180910390fd5b506000908152600460205260409020546001600160a01b031690565b600061078382610a27565b9050806001600160a01b0316836001600160a01b031614156107d65760405162461bcd60e51b815260040180806020018281038252602181526020018061321d6021913960400191505060405180910390fd5b806001600160a01b03166107e86118c6565b6001600160a01b031614806108045750610804816105256118c6565b61083f5760405162461bcd60e51b81526004018080602001828103825260388152602001806130cc6038913960400191505060405180910390fd5b61084983836118ca565b505050565b600061085a6002611938565b905090565b336000908152600f602052604090205460ff161561088757610882838383611943565b610849565b610849838383611a8f565b6000816001600160a01b03166108a6610d5e565b6001600160a01b03161492915050565b6001600160a01b03821660009081526001602052604081206108d89083611ae6565b90505b92915050565b610849838383604051806020016040528060008152506112db565b60008061090a600284611af2565b509392505050565b6060600061091f83610b1e565b90506060816001600160401b038111801561093957600080fd5b50604051908082528060200260200182016040528015610963578160200160208202803683370190505b50905060005b828161ffff16101561090a57610983858261ffff166108b6565b828261ffff168151811061099357fe5b6020908102919091010152600101610969565b6109b4868686868686610f2b565b6109d05760405162461bcd60e51b81526004016105cc90612e01565b610a108686868080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b505050505050565b600d546001600160a01b031681565b60006108db8260405180606001604052806029815260200161312e6029913960029190611b10565b606060405180606001604052806022815260200161300260229139905090565b610a776118c6565b6001600160a01b0316610a88610d5e565b6001600160a01b031614610ad1576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b600d80546001600160a01b0319166001600160a01b0392909216919091179055565b6001600160a01b0381166000908152600b602052604081205460ff16806108db57506108db82610892565b60006001600160a01b038216610b655760405162461bcd60e51b815260040180806020018281038252602a815260200180613104602a913960400191505060405180910390fd5b6001600160a01b03821660009081526001602052604090206108db90611938565b610b8e6118c6565b6001600160a01b0316610b9f610d5e565b6001600160a01b031614610be8576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b600a546040516000916001600160a01b0316907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908390a3600a80546001600160a01b0319169055565b600080610c40888888610d28565b905060018186868660405160008152602001604052604051610c659493929190612d33565b6020604051602081039080840390855afa158015610c87573d6000803e3d6000fd5b5050604051601f1901519998505050505050505050565b610ca733610af3565b610ce8576040805162461bcd60e51b815260206004820152600d60248201526c1058d8d95cdcc819195b9a5959609a1b604482015290519081900360640190fd5b6108498383838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b6000838383604051602001610d3f93929190612f39565b6040516020818303038152906040528051906020012090509392505050565b600a546001600160a01b031690565b610d756118c6565b6001600160a01b0316610d86610d5e565b6001600160a01b031614610dcf576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6000826001600160a01b03166370a08231306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060206040518083038186803b158015610e1e57600080fd5b505afa158015610e32573d6000803e3d6000fd5b505050506040513d6020811015610e4857600080fd5b50516040805163a9059cbb60e01b81526001600160a01b0385811660048301526024820184905291519293509085169163a9059cbb916044808201926020929091908290030181600087803b158015610ea057600080fd5b505af1158015610eb4573d6000803e3d6000fd5b505050506040513d602081101561065657600080fd5b60078054604080516020601f600260001961010060018816150201909516949094049384018190048102820181019092528281526060939092909183018282801561070c5780601f106106e15761010080835404028352916020019161070c565b600d546000906001600160a01b0316610f48888888888888610c32565b6001600160a01b031614979650505050505050565b610f656118c6565b6001600160a01b0316610f76610d5e565b6001600160a01b031614610fbf576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b038116611012576040805162461bcd60e51b81526020600482015260156024820152744e6577206f70657261746f7220697320656d70747960581b604482015290519081900360640190fd5b6001600160a01b03166000908152600b60205260409020805460ff19166001179055565b600e60209081526000918252604091829020805460018083018054865160026101009483161585026000190190921691909104601f810187900487028201870190975286815260ff80851697938504169562010000850463ffffffff169566010000000000009095046001600160401b03169493919291908301828280156110ff5780601f106110d4576101008083540402835291602001916110ff565b820191906000526020600020905b8154815290600101906020018083116110e257829003601f168201915b5050505050905085565b6000818152600e6020526040812054819060ff16601481111561112857fe5b6000848152600e6020526040902054610100900460ff16600381111561114a57fe5b91509150915091565b61115b6118c6565b6001600160a01b0316826001600160a01b031614156111c1576040805162461bcd60e51b815260206004820152601960248201527f4552433732313a20617070726f766520746f2063616c6c657200000000000000604482015290519081900360640190fd5b80600560006111ce6118c6565b6001600160a01b03908116825260208083019390935260409182016000908120918716808252919093529120805460ff1916921515929092179091556112126118c6565b6001600160a01b03167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c318360405180821515815260200191505060405180910390a35050565b6112606118c6565b6001600160a01b0316611271610d5e565b6001600160a01b0316146112ba576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b03166000908152600b60205260409020805460ff19169055565b6112ec6112e66118c6565b83611b27565b6113275760405162461bcd60e51b815260040180806020018281038252603181526020018061323e6031913960400191505060405180910390fd5b61133384848484611bc3565b50505050565b6060611344826118b9565b6113605760405162461bcd60e51b81526004016105cc90612e7a565b6000828152600c602090815260409182902080548351601f60026000196101006001861615020190931692909204918201849004840281018401909452808452606093928301828280156113f55780601f106113ca576101008083540402835291602001916113f5565b820191906000526020600020905b8154815290600101906020018083116113d857829003601f168201915b505050505090506060611406610a4f565b905080516000141561141a5750905061067b565b8151156114295750905061067b565b61143284611c15565b949350505050565b6114426118c6565b6001600160a01b0316611453610d5e565b6001600160a01b03161461149c576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b0382166000818152600f602052604090819020805460ff1916841515179055517f735768a8abddcbaa527672c7b507c39cdfee45818f675893d3ccf2326523c09e906114f0908490612d1f565b60405180910390a25050565b6115046118c6565b6001600160a01b0316611515610d5e565b6001600160a01b03161461155e576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6115688585611e98565b6040518060a001604052808460ff16601481111561158257fe5b601481111561158d57fe5b81526020018360ff1660038111156115a157fe5b60038111156115ac57fe5b815263ffffffff83166020808301919091526001600160401b034216604080840191909152805180830182526000808252606090940152878352600e909152902081518154829060ff1916600183601481111561160557fe5b021790555060208201518154829061ff00191661010083600381111561162757fe5b02179055506040820151815460608401516001600160401b03166601000000000000026dffffffffffffffff0000000000001963ffffffff909316620100000265ffffffff000019909216919091179190911617815560808201518051611698916001840191602090910190612740565b5050505050505050565b6001600160a01b03918216600090815260056020908152604080832093909416825291909152205460ff1690565b600f6020526000908152604090205460ff1681565b6116ed6118c6565b6001600160a01b03166116fe610d5e565b6001600160a01b031614611747576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b03811661178c5760405162461bcd60e51b81526004018080602001828103825260268152602001806130566026913960400191505060405180910390fd5b600a546040516001600160a01b038084169216907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a3600a80546001600160a01b0319166001600160a01b0392909216919091179055565b336117f284610a27565b6001600160a01b0316146118185760405162461bcd60e51b81526004016105cc90612ecb565b6000838152600e6020526040902060019081015460029181161561010002600019011604156118595760405162461bcd60e51b81526004016105cc90612f02565b6000838152600e602052604090206113339060010183836127cc565b61187e826118b9565b61189a5760405162461bcd60e51b81526004016105cc90612e2c565b6000828152600c60209081526040909120825161084992840190612740565b60006108db600283611fc6565b3390565b600081815260046020526040902080546001600160a01b0319166001600160a01b03841690811790915581906118ff82610a27565b6001600160a01b03167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a45050565b60006108db82611fd2565b826001600160a01b031661195682610a27565b6001600160a01b03161461199b5760405162461bcd60e51b81526004018080602001828103825260298152602001806131c56029913960400191505060405180910390fd5b6001600160a01b0382166119e05760405162461bcd60e51b815260040180806020018281038252602481526020018061307c6024913960400191505060405180910390fd5b6119eb838383610849565b6119f66000826118ca565b6001600160a01b0383166000908152600160205260409020611a189082611fd6565b506001600160a01b0382166000908152600160205260409020611a3b9082611fe2565b50611a4860028284611fee565b5080826001600160a01b0316846001600160a01b03167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4505050565b611aa0611a9a6118c6565b82611b27565b611adb5760405162461bcd60e51b815260040180806020018281038252603181526020018061323e6031913960400191505060405180910390fd5b610849838383611943565b60006108d88383612004565b6000808080611b018686612068565b909450925050505b9250929050565b6000611b1d8484846120e3565b90505b9392505050565b6000611b32826118b9565b611b6d5760405162461bcd60e51b815260040180806020018281038252602c8152602001806130a0602c913960400191505060405180910390fd5b6000611b7883610a27565b9050806001600160a01b0316846001600160a01b03161480611bb35750836001600160a01b0316611ba884610716565b6001600160a01b0316145b80611432575061143281856116a2565b611bce848484611943565b611bda848484846121ad565b6113335760405162461bcd60e51b81526004018080602001828103825260328152602001806130246032913960400191505060405180910390fd5b6060611c20826118b9565b611c5b5760405162461bcd60e51b815260040180806020018281038252602f8152602001806131ee602f913960400191505060405180910390fd5b60008281526008602090815260409182902080548351601f6002600019610100600186161502019093169290920491820184900484028101840190945280845260609392830182828015611cf05780601f10611cc557610100808354040283529160200191611cf0565b820191906000526020600020905b815481529060010190602001808311611cd357829003601f168201915b505050505090506060611d01610a4f565b9050805160001415611d155750905061067b565b815115611dd65780826040516020018083805190602001908083835b60208310611d505780518252601f199092019160209182019101611d31565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b60208310611d985780518252601f199092019160209182019101611d79565b6001836020036101000a038019825116818451168082178552505050505050905001925050506040516020818303038152906040529250505061067b565b80611de085612315565b6040516020018083805190602001908083835b60208310611e125780518252601f199092019160209182019101611df3565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b60208310611e5a5780518252601f199092019160209182019101611e3b565b6001836020036101000a0380198251168184511680821785525050505050509050019250505060405160208183030381529060405292505050919050565b6001600160a01b038216611ef3576040805162461bcd60e51b815260206004820181905260248201527f4552433732313a206d696e7420746f20746865207a65726f2061646472657373604482015290519081900360640190fd5b611efc816118b9565b15611f4e576040805162461bcd60e51b815260206004820152601c60248201527f4552433732313a20746f6b656e20616c7265616479206d696e74656400000000604482015290519081900360640190fd5b611f5a60008383610849565b6001600160a01b0382166000908152600160205260409020611f7c9082611fe2565b50611f8960028284611fee565b5060405181906001600160a01b038416906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a45050565b60006108d883836123ef565b5490565b60006108d88383612407565b60006108d883836124cd565b6000611b1d84846001600160a01b038516612517565b815460009082106120465760405162461bcd60e51b8152600401808060200182810382526022815260200180612fe06022913960400191505060405180910390fd5b82600001828154811061205557fe5b9060005260206000200154905092915050565b8154600090819083106120ac5760405162461bcd60e51b81526004018080602001828103825260228152602001806131576022913960400191505060405180910390fd5b60008460000184815481106120bd57fe5b906000526020600020906002020190508060000154816001015492509250509250929050565b6000828152600184016020526040812054828161217e5760405162461bcd60e51b81526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561214357818101518382015260200161212b565b50505050905090810190601f1680156121705780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b5084600001600182038154811061219157fe5b9060005260206000209060020201600101549150509392505050565b60006121c1846001600160a01b03166125ae565b6121cd57506001611432565b60606122db630a85bd0160e11b6121e26118c6565b88878760405160240180856001600160a01b03168152602001846001600160a01b0316815260200183815260200180602001828103825283818151815260200191508051906020019080838360005b83811015612249578181015183820152602001612231565b50505050905090810190601f1680156122765780820380516001836020036101000a031916815260200191505b5095505050505050604051602081830303815290604052906001600160e01b0319166020820180516001600160e01b038381831617835250505050604051806060016040528060328152602001613024603291396001600160a01b03881691906125b4565b905060008180602001905160208110156122f457600080fd5b50516001600160e01b031916630a85bd0160e11b1492505050949350505050565b60608161233a57506040805180820190915260018152600360fc1b602082015261067b565b8160005b811561235257600101600a8204915061233e565b6060816001600160401b038111801561236a57600080fd5b506040519080825280601f01601f191660200182016040528015612395576020820181803683370190505b50859350905060001982015b83156123e657600a840660300160f81b828280600190039350815181106123c457fe5b60200101906001600160f81b031916908160001a905350600a840493506123a1565b50949350505050565b60009081526001919091016020526040902054151590565b600081815260018301602052604081205480156124c3578354600019808301919081019060009087908390811061243a57fe5b906000526020600020015490508087600001848154811061245757fe5b60009182526020808320909101929092558281526001898101909252604090209084019055865487908061248757fe5b600190038181906000526020600020016000905590558660010160008781526020019081526020016000206000905560019450505050506108db565b60009150506108db565b60006124d983836123ef565b61250f575081546001818101845560008481526020808220909301849055845484825282860190935260409020919091556108db565b5060006108db565b60008281526001840160205260408120548061257c575050604080518082018252838152602080820184815286546001818101895560008981528481209551600290930290950191825591519082015586548684528188019092529290912055611b20565b8285600001600183038154811061258f57fe5b9060005260206000209060020201600101819055506000915050611b20565b3b151590565b6060611b1d8484600085856125c8856125ae565b612619576040805162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015290519081900360640190fd5b60006060866001600160a01b031685876040518082805190602001908083835b602083106126585780518252601f199092019160209182019101612639565b6001836020036101000a03801982511681845116808217855250505050505090500191505060006040518083038185875af1925050503d80600081146126ba576040519150601f19603f3d011682016040523d82523d6000602084013e6126bf565b606091505b50915091506126cf8282866126da565b979650505050505050565b606083156126e9575081611b20565b8251156126f95782518084602001fd5b60405162461bcd60e51b815260206004820181815284516024840152845185939192839260440191908501908083836000831561214357818101518382015260200161212b565b828054600181600116156101000203166002900490600052602060002090601f01602090048101928261277657600085556127bc565b82601f1061278f57805160ff19168380011785556127bc565b828001600101855582156127bc579182015b828111156127bc5782518255916020019190600101906127a1565b506127c8929150612848565b5090565b828054600181600116156101000203166002900490600052602060002090601f01602090048101928261280257600085556127bc565b82601f1061281b5782800160ff198235161785556127bc565b828001600101855582156127bc579182015b828111156127bc57823582559160200191906001019061282d565b5b808211156127c85760008155600101612849565b60008083601f84011261286e578182fd5b5081356001600160401b03811115612884578182fd5b6020830191508360208083028501011115611b0957600080fd5b60008083601f8401126128af578182fd5b5081356001600160401b038111156128c5578182fd5b602083019150836020828501011115611b0957600080fd5b803560ff8116811461067b57600080fd5b6000602082840312156128ff578081fd5b8135611b2081612fc7565b6000806040838503121561291c578081fd5b823561292781612fc7565b9150602083013561293781612fc7565b809150509250929050565b600080600060608486031215612956578081fd5b833561296181612fc7565b9250602084013561297181612fc7565b929592945050506040919091013590565b60008060008060808587031215612997578081fd5b84356129a281612fc7565b93506020858101356129b381612fc7565b93506040860135925060608601356001600160401b03808211156129d5578384fd5b818801915088601f8301126129e8578384fd5b8135818111156129f457fe5b604051601f8201601f1916810185018381118282101715612a1157fe5b60405281815283820185018b1015612a27578586fd5b81858501868301379081019093019390935250939692955090935050565b60008060408385031215612a57578182fd5b8235612a6281612fc7565b915060208301358015158114612937578182fd5b60008060408385031215612a88578182fd5b8235612a9381612fc7565b946020939093013593505050565b600080600080600060a08688031215612ab8578081fd5b8535612ac381612fc7565b945060208601359350612ad8604087016128dd565b9250612ae6606087016128dd565b9150608086013563ffffffff81168114612afe578182fd5b809150509295509295909350565b60008060008060408587031215612b21578384fd5b84356001600160401b0380821115612b37578586fd5b612b438883890161285d565b90965094506020870135915080821115612b5b578384fd5b50612b688782880161285d565b95989497509550505050565b600060208284031215612b85578081fd5b81356001600160e01b031981168114611b20578182fd5b6000806040838503121561291c578182fd5b600060208284031215612bbf578081fd5b5035919050565b600080600060408486031215612bda578081fd5b8335925060208401356001600160401b03811115612bf6578182fd5b612c028682870161289e565b9497909650939450505050565b60008060008060008060a08789031215612c27578384fd5b8635955060208701356001600160401b03811115612c43578485fd5b612c4f89828a0161289e565b9096509450612c629050604088016128dd565b925060608701359150608087013590509295509295509295565b60008151808452815b81811015612ca157602081850181015186830182015201612c85565b81811115612cb25782602083870101525b50601f01601f19169290920160200192915050565b6001600160a01b0391909116815260200190565b6020808252825182820181905260009190848201906040850190845b81811015612d1357835183529284019291840191600101612cf7565b50909695505050505050565b901515815260200190565b90815260200190565b93845260ff9290921660208401526040830152606082015260800190565b600060158710612d5d57fe5b86825260048610612d6a57fe5b85602083015263ffffffff851660408301526001600160401b038416606083015260a060808301526126cf60a0830184612c7c565b6000602082526108d86020830184612c7c565b6020808252602f908201527f746f6b656e4964206c656e677468206973206e6f7420657175616c20746f205f60408201526e0e8ded6cadcaaa49240d8cadccee8d608b1b606082015260800190565b602080825260119082015270496e76616c6964207369676e617475726560781b604082015260600190565b6020808252602e908201527f45524337323155524953746f726167653a2055524920736574206f66206e6f6e60408201526d32bc34b9ba32b73a103a37b5b2b760911b606082015260800190565b60208082526031908201527f45524337323155524953746f726167653a2055524920717565727920666f72206040820152703737b732bc34b9ba32b73a103a37b5b2b760791b606082015260800190565b6020808252601a908201527f4f6e6c79206f776e65722063616e206368616e6765206e616d65000000000000604082015260600190565b6020808252601f908201527f546865206e616d652068617320616c7265616479206265656e20676976656e00604082015260600190565b60008482526040602083015282604083015282846060840137818301606090810191909152601f909201601f1916010192915050565b60ff92831681529116602082015260400190565b6000808335601e19843603018112612f99578283fd5b8301803591506001600160401b03821115612fb2578283fd5b602001915036819003821315611b0957600080fd5b6001600160a01b0381168114612fdc57600080fd5b5056fe456e756d657261626c655365743a20696e646578206f7574206f6620626f756e6473687474703a2f2f646567656e732e6661726d2f6d6574612f6372656174757265732f4552433732313a207472616e7366657220746f206e6f6e20455243373231526563656976657220696d706c656d656e7465724f776e61626c653a206e6577206f776e657220697320746865207a65726f20616464726573734552433732313a207472616e7366657220746f20746865207a65726f20616464726573734552433732313a206f70657261746f7220717565727920666f72206e6f6e6578697374656e7420746f6b656e4552433732313a20617070726f76652063616c6c6572206973206e6f74206f776e6572206e6f7220617070726f76656420666f7220616c6c4552433732313a2062616c616e636520717565727920666f7220746865207a65726f20616464726573734552433732313a206f776e657220717565727920666f72206e6f6e6578697374656e7420746f6b656e456e756d657261626c654d61703a20696e646578206f7574206f6620626f756e64734552433732313a20617070726f76656420717565727920666f72206e6f6e6578697374656e7420746f6b656e4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65724552433732313a207472616e73666572206f6620746f6b656e2074686174206973206e6f74206f776e4552433732314d657461646174613a2055524920717565727920666f72206e6f6e6578697374656e7420746f6b656e4552433732313a20617070726f76616c20746f2063757272656e74206f776e65724552433732313a207472616e736665722063616c6c6572206973206e6f74206f776e6572206e6f7220617070726f766564a2646970667358221220308c7d0f38216f626771d86f2b5b3091893bd5f12659a801a1f13db0060ec78f64736f6c63430007040033000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000015446567656e24204661726d20437265617475726573000000000000000000000000000000000000000000000000000000000000000000000000000000000000054352454154000000000000000000000000000000000000000000000000000000
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106102485760003560e01c806385aa84b61161013b578063a22cb465116100b8578063e8c9a3b31161007c578063e8c9a3b314610504578063e985e9c514610517578063eb46a4661461052a578063f2fde38b1461053d578063fe55932a1461055057610248565b8063a22cb465146104a5578063ac8a584a146104b8578063b88d4fde146104cb578063c87b56dd146104de578063d7a377a1146104f157610248565b806395d89b41116100ff57806395d89b4114610432578063963513ca1461043a5780639870d7fe1461044d578063998dd3ca146104605780639ed4f2561461048457610248565b806385aa84b6146103de578063862440e2146103f157806389dd289f146104045780638da5cb5b146104175780639456fbcc1461041f57610248565b80634f6ccce7116101c95780636c0360eb1161018d5780636c0360eb146103955780636c19e7831461039d5780636d70f7ae146103b057806370a08231146103c3578063715018a6146103d657610248565b80634f6ccce714610334578063509044be14610347578063540d259e146103675780635b7633d01461037a5780636352211e1461038257610248565b806318160ddd1161021057806318160ddd146102d357806323b872dd146102e85780632f54bf6e146102fb5780632f745c591461030e57806342842e0e1461032157610248565b806301b98ea01461024d57806301ffc9a71461026257806306fdde031461028b578063081812fc146102a0578063095ea7b3146102c0575b600080fd5b61026061025b366004612b0c565b610563565b005b610275610270366004612b74565b61065d565b6040516102829190612d1f565b60405180910390f35b610293610680565b6040516102829190612d9f565b6102b36102ae366004612bae565b610716565b6040516102829190612cc7565b6102606102ce366004612a76565b610778565b6102db61084e565b6040516102829190612d2a565b6102606102f6366004612942565b61085f565b6102756103093660046128ee565b610892565b6102db61031c366004612a76565b6108b6565b61026061032f366004612942565b6108e1565b6102db610342366004612bae565b6108fc565b61035a6103553660046128ee565b610912565b6040516102829190612cdb565b610260610375366004612c0f565b6109a6565b6102b3610a18565b6102b3610390366004612bae565b610a27565b610293610a4f565b6102606103ab3660046128ee565b610a6f565b6102756103be3660046128ee565b610af3565b6102db6103d13660046128ee565b610b1e565b610260610b86565b6102b36103ec366004612c0f565b610c32565b6102606103ff366004612bc6565b610c9e565b6102db610412366004612bc6565b610d28565b6102b3610d5e565b61026061042d366004612b9c565b610d6d565b610293610eca565b610275610448366004612c0f565b610f2b565b61026061045b3660046128ee565b610f5d565b61047361046e366004612bae565b611036565b604051610282959493929190612d51565b610497610492366004612bae565b611109565b604051610282929190612f6f565b6102606104b3366004612a45565b611153565b6102606104c63660046128ee565b611258565b6102606104d9366004612982565b6112db565b6102936104ec366004612bae565b611339565b6102606104ff366004612a45565b61143a565b610260610512366004612aa1565b6114fc565b61027561052536600461290a565b6116a2565b6102756105383660046128ee565b6116d0565b61026061054b3660046128ee565b6116e5565b61026061055e366004612bc6565b6117e8565b61056c33610af3565b6105ad576040805162461bcd60e51b815260206004820152600d60248201526c1058d8d95cdcc819195b9a5959609a1b604482015290519081900360640190fd5b8281146105d55760405162461bcd60e51b81526004016105cc90612db2565b60405180910390fd5b60005b838110156106565761064e8585838181106105ef57fe5b9050602002013584848481811061060257fe5b90506020028101906106149190612f83565b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b6001016105d8565b5050505050565b6001600160e01b0319811660009081526020819052604090205460ff165b919050565b60068054604080516020601f600260001961010060018816150201909516949094049384018190048102820181019092528281526060939092909183018282801561070c5780601f106106e15761010080835404028352916020019161070c565b820191906000526020600020905b8154815290600101906020018083116106ef57829003601f168201915b5050505050905090565b6000610721826118b9565b61075c5760405162461bcd60e51b815260040180806020018281038252602c815260200180613179602c913960400191505060405180910390fd5b506000908152600460205260409020546001600160a01b031690565b600061078382610a27565b9050806001600160a01b0316836001600160a01b031614156107d65760405162461bcd60e51b815260040180806020018281038252602181526020018061321d6021913960400191505060405180910390fd5b806001600160a01b03166107e86118c6565b6001600160a01b031614806108045750610804816105256118c6565b61083f5760405162461bcd60e51b81526004018080602001828103825260388152602001806130cc6038913960400191505060405180910390fd5b61084983836118ca565b505050565b600061085a6002611938565b905090565b336000908152600f602052604090205460ff161561088757610882838383611943565b610849565b610849838383611a8f565b6000816001600160a01b03166108a6610d5e565b6001600160a01b03161492915050565b6001600160a01b03821660009081526001602052604081206108d89083611ae6565b90505b92915050565b610849838383604051806020016040528060008152506112db565b60008061090a600284611af2565b509392505050565b6060600061091f83610b1e565b90506060816001600160401b038111801561093957600080fd5b50604051908082528060200260200182016040528015610963578160200160208202803683370190505b50905060005b828161ffff16101561090a57610983858261ffff166108b6565b828261ffff168151811061099357fe5b6020908102919091010152600101610969565b6109b4868686868686610f2b565b6109d05760405162461bcd60e51b81526004016105cc90612e01565b610a108686868080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b505050505050565b600d546001600160a01b031681565b60006108db8260405180606001604052806029815260200161312e6029913960029190611b10565b606060405180606001604052806022815260200161300260229139905090565b610a776118c6565b6001600160a01b0316610a88610d5e565b6001600160a01b031614610ad1576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b600d80546001600160a01b0319166001600160a01b0392909216919091179055565b6001600160a01b0381166000908152600b602052604081205460ff16806108db57506108db82610892565b60006001600160a01b038216610b655760405162461bcd60e51b815260040180806020018281038252602a815260200180613104602a913960400191505060405180910390fd5b6001600160a01b03821660009081526001602052604090206108db90611938565b610b8e6118c6565b6001600160a01b0316610b9f610d5e565b6001600160a01b031614610be8576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b600a546040516000916001600160a01b0316907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908390a3600a80546001600160a01b0319169055565b600080610c40888888610d28565b905060018186868660405160008152602001604052604051610c659493929190612d33565b6020604051602081039080840390855afa158015610c87573d6000803e3d6000fd5b5050604051601f1901519998505050505050505050565b610ca733610af3565b610ce8576040805162461bcd60e51b815260206004820152600d60248201526c1058d8d95cdcc819195b9a5959609a1b604482015290519081900360640190fd5b6108498383838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061187592505050565b6000838383604051602001610d3f93929190612f39565b6040516020818303038152906040528051906020012090509392505050565b600a546001600160a01b031690565b610d756118c6565b6001600160a01b0316610d86610d5e565b6001600160a01b031614610dcf576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6000826001600160a01b03166370a08231306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060206040518083038186803b158015610e1e57600080fd5b505afa158015610e32573d6000803e3d6000fd5b505050506040513d6020811015610e4857600080fd5b50516040805163a9059cbb60e01b81526001600160a01b0385811660048301526024820184905291519293509085169163a9059cbb916044808201926020929091908290030181600087803b158015610ea057600080fd5b505af1158015610eb4573d6000803e3d6000fd5b505050506040513d602081101561065657600080fd5b60078054604080516020601f600260001961010060018816150201909516949094049384018190048102820181019092528281526060939092909183018282801561070c5780601f106106e15761010080835404028352916020019161070c565b600d546000906001600160a01b0316610f48888888888888610c32565b6001600160a01b031614979650505050505050565b610f656118c6565b6001600160a01b0316610f76610d5e565b6001600160a01b031614610fbf576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b038116611012576040805162461bcd60e51b81526020600482015260156024820152744e6577206f70657261746f7220697320656d70747960581b604482015290519081900360640190fd5b6001600160a01b03166000908152600b60205260409020805460ff19166001179055565b600e60209081526000918252604091829020805460018083018054865160026101009483161585026000190190921691909104601f810187900487028201870190975286815260ff80851697938504169562010000850463ffffffff169566010000000000009095046001600160401b03169493919291908301828280156110ff5780601f106110d4576101008083540402835291602001916110ff565b820191906000526020600020905b8154815290600101906020018083116110e257829003601f168201915b5050505050905085565b6000818152600e6020526040812054819060ff16601481111561112857fe5b6000848152600e6020526040902054610100900460ff16600381111561114a57fe5b91509150915091565b61115b6118c6565b6001600160a01b0316826001600160a01b031614156111c1576040805162461bcd60e51b815260206004820152601960248201527f4552433732313a20617070726f766520746f2063616c6c657200000000000000604482015290519081900360640190fd5b80600560006111ce6118c6565b6001600160a01b03908116825260208083019390935260409182016000908120918716808252919093529120805460ff1916921515929092179091556112126118c6565b6001600160a01b03167f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c318360405180821515815260200191505060405180910390a35050565b6112606118c6565b6001600160a01b0316611271610d5e565b6001600160a01b0316146112ba576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b03166000908152600b60205260409020805460ff19169055565b6112ec6112e66118c6565b83611b27565b6113275760405162461bcd60e51b815260040180806020018281038252603181526020018061323e6031913960400191505060405180910390fd5b61133384848484611bc3565b50505050565b6060611344826118b9565b6113605760405162461bcd60e51b81526004016105cc90612e7a565b6000828152600c602090815260409182902080548351601f60026000196101006001861615020190931692909204918201849004840281018401909452808452606093928301828280156113f55780601f106113ca576101008083540402835291602001916113f5565b820191906000526020600020905b8154815290600101906020018083116113d857829003601f168201915b505050505090506060611406610a4f565b905080516000141561141a5750905061067b565b8151156114295750905061067b565b61143284611c15565b949350505050565b6114426118c6565b6001600160a01b0316611453610d5e565b6001600160a01b03161461149c576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b0382166000818152600f602052604090819020805460ff1916841515179055517f735768a8abddcbaa527672c7b507c39cdfee45818f675893d3ccf2326523c09e906114f0908490612d1f565b60405180910390a25050565b6115046118c6565b6001600160a01b0316611515610d5e565b6001600160a01b03161461155e576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6115688585611e98565b6040518060a001604052808460ff16601481111561158257fe5b601481111561158d57fe5b81526020018360ff1660038111156115a157fe5b60038111156115ac57fe5b815263ffffffff83166020808301919091526001600160401b034216604080840191909152805180830182526000808252606090940152878352600e909152902081518154829060ff1916600183601481111561160557fe5b021790555060208201518154829061ff00191661010083600381111561162757fe5b02179055506040820151815460608401516001600160401b03166601000000000000026dffffffffffffffff0000000000001963ffffffff909316620100000265ffffffff000019909216919091179190911617815560808201518051611698916001840191602090910190612740565b5050505050505050565b6001600160a01b03918216600090815260056020908152604080832093909416825291909152205460ff1690565b600f6020526000908152604090205460ff1681565b6116ed6118c6565b6001600160a01b03166116fe610d5e565b6001600160a01b031614611747576040805162461bcd60e51b815260206004820181905260248201526000805160206131a5833981519152604482015290519081900360640190fd5b6001600160a01b03811661178c5760405162461bcd60e51b81526004018080602001828103825260268152602001806130566026913960400191505060405180910390fd5b600a546040516001600160a01b038084169216907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a3600a80546001600160a01b0319166001600160a01b0392909216919091179055565b336117f284610a27565b6001600160a01b0316146118185760405162461bcd60e51b81526004016105cc90612ecb565b6000838152600e6020526040902060019081015460029181161561010002600019011604156118595760405162461bcd60e51b81526004016105cc90612f02565b6000838152600e602052604090206113339060010183836127cc565b61187e826118b9565b61189a5760405162461bcd60e51b81526004016105cc90612e2c565b6000828152600c60209081526040909120825161084992840190612740565b60006108db600283611fc6565b3390565b600081815260046020526040902080546001600160a01b0319166001600160a01b03841690811790915581906118ff82610a27565b6001600160a01b03167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92560405160405180910390a45050565b60006108db82611fd2565b826001600160a01b031661195682610a27565b6001600160a01b03161461199b5760405162461bcd60e51b81526004018080602001828103825260298152602001806131c56029913960400191505060405180910390fd5b6001600160a01b0382166119e05760405162461bcd60e51b815260040180806020018281038252602481526020018061307c6024913960400191505060405180910390fd5b6119eb838383610849565b6119f66000826118ca565b6001600160a01b0383166000908152600160205260409020611a189082611fd6565b506001600160a01b0382166000908152600160205260409020611a3b9082611fe2565b50611a4860028284611fee565b5080826001600160a01b0316846001600160a01b03167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef60405160405180910390a4505050565b611aa0611a9a6118c6565b82611b27565b611adb5760405162461bcd60e51b815260040180806020018281038252603181526020018061323e6031913960400191505060405180910390fd5b610849838383611943565b60006108d88383612004565b6000808080611b018686612068565b909450925050505b9250929050565b6000611b1d8484846120e3565b90505b9392505050565b6000611b32826118b9565b611b6d5760405162461bcd60e51b815260040180806020018281038252602c8152602001806130a0602c913960400191505060405180910390fd5b6000611b7883610a27565b9050806001600160a01b0316846001600160a01b03161480611bb35750836001600160a01b0316611ba884610716565b6001600160a01b0316145b80611432575061143281856116a2565b611bce848484611943565b611bda848484846121ad565b6113335760405162461bcd60e51b81526004018080602001828103825260328152602001806130246032913960400191505060405180910390fd5b6060611c20826118b9565b611c5b5760405162461bcd60e51b815260040180806020018281038252602f8152602001806131ee602f913960400191505060405180910390fd5b60008281526008602090815260409182902080548351601f6002600019610100600186161502019093169290920491820184900484028101840190945280845260609392830182828015611cf05780601f10611cc557610100808354040283529160200191611cf0565b820191906000526020600020905b815481529060010190602001808311611cd357829003601f168201915b505050505090506060611d01610a4f565b9050805160001415611d155750905061067b565b815115611dd65780826040516020018083805190602001908083835b60208310611d505780518252601f199092019160209182019101611d31565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b60208310611d985780518252601f199092019160209182019101611d79565b6001836020036101000a038019825116818451168082178552505050505050905001925050506040516020818303038152906040529250505061067b565b80611de085612315565b6040516020018083805190602001908083835b60208310611e125780518252601f199092019160209182019101611df3565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b60208310611e5a5780518252601f199092019160209182019101611e3b565b6001836020036101000a0380198251168184511680821785525050505050509050019250505060405160208183030381529060405292505050919050565b6001600160a01b038216611ef3576040805162461bcd60e51b815260206004820181905260248201527f4552433732313a206d696e7420746f20746865207a65726f2061646472657373604482015290519081900360640190fd5b611efc816118b9565b15611f4e576040805162461bcd60e51b815260206004820152601c60248201527f4552433732313a20746f6b656e20616c7265616479206d696e74656400000000604482015290519081900360640190fd5b611f5a60008383610849565b6001600160a01b0382166000908152600160205260409020611f7c9082611fe2565b50611f8960028284611fee565b5060405181906001600160a01b038416906000907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908290a45050565b60006108d883836123ef565b5490565b60006108d88383612407565b60006108d883836124cd565b6000611b1d84846001600160a01b038516612517565b815460009082106120465760405162461bcd60e51b8152600401808060200182810382526022815260200180612fe06022913960400191505060405180910390fd5b82600001828154811061205557fe5b9060005260206000200154905092915050565b8154600090819083106120ac5760405162461bcd60e51b81526004018080602001828103825260228152602001806131576022913960400191505060405180910390fd5b60008460000184815481106120bd57fe5b906000526020600020906002020190508060000154816001015492509250509250929050565b6000828152600184016020526040812054828161217e5760405162461bcd60e51b81526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561214357818101518382015260200161212b565b50505050905090810190601f1680156121705780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b5084600001600182038154811061219157fe5b9060005260206000209060020201600101549150509392505050565b60006121c1846001600160a01b03166125ae565b6121cd57506001611432565b60606122db630a85bd0160e11b6121e26118c6565b88878760405160240180856001600160a01b03168152602001846001600160a01b0316815260200183815260200180602001828103825283818151815260200191508051906020019080838360005b83811015612249578181015183820152602001612231565b50505050905090810190601f1680156122765780820380516001836020036101000a031916815260200191505b5095505050505050604051602081830303815290604052906001600160e01b0319166020820180516001600160e01b038381831617835250505050604051806060016040528060328152602001613024603291396001600160a01b03881691906125b4565b905060008180602001905160208110156122f457600080fd5b50516001600160e01b031916630a85bd0160e11b1492505050949350505050565b60608161233a57506040805180820190915260018152600360fc1b602082015261067b565b8160005b811561235257600101600a8204915061233e565b6060816001600160401b038111801561236a57600080fd5b506040519080825280601f01601f191660200182016040528015612395576020820181803683370190505b50859350905060001982015b83156123e657600a840660300160f81b828280600190039350815181106123c457fe5b60200101906001600160f81b031916908160001a905350600a840493506123a1565b50949350505050565b60009081526001919091016020526040902054151590565b600081815260018301602052604081205480156124c3578354600019808301919081019060009087908390811061243a57fe5b906000526020600020015490508087600001848154811061245757fe5b60009182526020808320909101929092558281526001898101909252604090209084019055865487908061248757fe5b600190038181906000526020600020016000905590558660010160008781526020019081526020016000206000905560019450505050506108db565b60009150506108db565b60006124d983836123ef565b61250f575081546001818101845560008481526020808220909301849055845484825282860190935260409020919091556108db565b5060006108db565b60008281526001840160205260408120548061257c575050604080518082018252838152602080820184815286546001818101895560008981528481209551600290930290950191825591519082015586548684528188019092529290912055611b20565b8285600001600183038154811061258f57fe5b9060005260206000209060020201600101819055506000915050611b20565b3b151590565b6060611b1d8484600085856125c8856125ae565b612619576040805162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015290519081900360640190fd5b60006060866001600160a01b031685876040518082805190602001908083835b602083106126585780518252601f199092019160209182019101612639565b6001836020036101000a03801982511681845116808217855250505050505090500191505060006040518083038185875af1925050503d80600081146126ba576040519150601f19603f3d011682016040523d82523d6000602084013e6126bf565b606091505b50915091506126cf8282866126da565b979650505050505050565b606083156126e9575081611b20565b8251156126f95782518084602001fd5b60405162461bcd60e51b815260206004820181815284516024840152845185939192839260440191908501908083836000831561214357818101518382015260200161212b565b828054600181600116156101000203166002900490600052602060002090601f01602090048101928261277657600085556127bc565b82601f1061278f57805160ff19168380011785556127bc565b828001600101855582156127bc579182015b828111156127bc5782518255916020019190600101906127a1565b506127c8929150612848565b5090565b828054600181600116156101000203166002900490600052602060002090601f01602090048101928261280257600085556127bc565b82601f1061281b5782800160ff198235161785556127bc565b828001600101855582156127bc579182015b828111156127bc57823582559160200191906001019061282d565b5b808211156127c85760008155600101612849565b60008083601f84011261286e578182fd5b5081356001600160401b03811115612884578182fd5b6020830191508360208083028501011115611b0957600080fd5b60008083601f8401126128af578182fd5b5081356001600160401b038111156128c5578182fd5b602083019150836020828501011115611b0957600080fd5b803560ff8116811461067b57600080fd5b6000602082840312156128ff578081fd5b8135611b2081612fc7565b6000806040838503121561291c578081fd5b823561292781612fc7565b9150602083013561293781612fc7565b809150509250929050565b600080600060608486031215612956578081fd5b833561296181612fc7565b9250602084013561297181612fc7565b929592945050506040919091013590565b60008060008060808587031215612997578081fd5b84356129a281612fc7565b93506020858101356129b381612fc7565b93506040860135925060608601356001600160401b03808211156129d5578384fd5b818801915088601f8301126129e8578384fd5b8135818111156129f457fe5b604051601f8201601f1916810185018381118282101715612a1157fe5b60405281815283820185018b1015612a27578586fd5b81858501868301379081019093019390935250939692955090935050565b60008060408385031215612a57578182fd5b8235612a6281612fc7565b915060208301358015158114612937578182fd5b60008060408385031215612a88578182fd5b8235612a9381612fc7565b946020939093013593505050565b600080600080600060a08688031215612ab8578081fd5b8535612ac381612fc7565b945060208601359350612ad8604087016128dd565b9250612ae6606087016128dd565b9150608086013563ffffffff81168114612afe578182fd5b809150509295509295909350565b60008060008060408587031215612b21578384fd5b84356001600160401b0380821115612b37578586fd5b612b438883890161285d565b90965094506020870135915080821115612b5b578384fd5b50612b688782880161285d565b95989497509550505050565b600060208284031215612b85578081fd5b81356001600160e01b031981168114611b20578182fd5b6000806040838503121561291c578182fd5b600060208284031215612bbf578081fd5b5035919050565b600080600060408486031215612bda578081fd5b8335925060208401356001600160401b03811115612bf6578182fd5b612c028682870161289e565b9497909650939450505050565b60008060008060008060a08789031215612c27578384fd5b8635955060208701356001600160401b03811115612c43578485fd5b612c4f89828a0161289e565b9096509450612c629050604088016128dd565b925060608701359150608087013590509295509295509295565b60008151808452815b81811015612ca157602081850181015186830182015201612c85565b81811115612cb25782602083870101525b50601f01601f19169290920160200192915050565b6001600160a01b0391909116815260200190565b6020808252825182820181905260009190848201906040850190845b81811015612d1357835183529284019291840191600101612cf7565b50909695505050505050565b901515815260200190565b90815260200190565b93845260ff9290921660208401526040830152606082015260800190565b600060158710612d5d57fe5b86825260048610612d6a57fe5b85602083015263ffffffff851660408301526001600160401b038416606083015260a060808301526126cf60a0830184612c7c565b6000602082526108d86020830184612c7c565b6020808252602f908201527f746f6b656e4964206c656e677468206973206e6f7420657175616c20746f205f60408201526e0e8ded6cadcaaa49240d8cadccee8d608b1b606082015260800190565b602080825260119082015270496e76616c6964207369676e617475726560781b604082015260600190565b6020808252602e908201527f45524337323155524953746f726167653a2055524920736574206f66206e6f6e60408201526d32bc34b9ba32b73a103a37b5b2b760911b606082015260800190565b60208082526031908201527f45524337323155524953746f726167653a2055524920717565727920666f72206040820152703737b732bc34b9ba32b73a103a37b5b2b760791b606082015260800190565b6020808252601a908201527f4f6e6c79206f776e65722063616e206368616e6765206e616d65000000000000604082015260600190565b6020808252601f908201527f546865206e616d652068617320616c7265616479206265656e20676976656e00604082015260600190565b60008482526040602083015282604083015282846060840137818301606090810191909152601f909201601f1916010192915050565b60ff92831681529116602082015260400190565b6000808335601e19843603018112612f99578283fd5b8301803591506001600160401b03821115612fb2578283fd5b602001915036819003821315611b0957600080fd5b6001600160a01b0381168114612fdc57600080fd5b5056fe456e756d657261626c655365743a20696e646578206f7574206f6620626f756e6473687474703a2f2f646567656e732e6661726d2f6d6574612f6372656174757265732f4552433732313a207472616e7366657220746f206e6f6e20455243373231526563656976657220696d706c656d656e7465724f776e61626c653a206e6577206f776e657220697320746865207a65726f20616464726573734552433732313a207472616e7366657220746f20746865207a65726f20616464726573734552433732313a206f70657261746f7220717565727920666f72206e6f6e6578697374656e7420746f6b656e4552433732313a20617070726f76652063616c6c6572206973206e6f74206f776e6572206e6f7220617070726f76656420666f7220616c6c4552433732313a2062616c616e636520717565727920666f7220746865207a65726f20616464726573734552433732313a206f776e657220717565727920666f72206e6f6e6578697374656e7420746f6b656e456e756d657261626c654d61703a20696e646578206f7574206f6620626f756e64734552433732313a20617070726f76656420717565727920666f72206e6f6e6578697374656e7420746f6b656e4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65724552433732313a207472616e73666572206f6620746f6b656e2074686174206973206e6f74206f776e4552433732314d657461646174613a2055524920717565727920666f72206e6f6e6578697374656e7420746f6b656e4552433732313a20617070726f76616c20746f2063757272656e74206f776e65724552433732313a207472616e736665722063616c6c6572206973206e6f74206f776e6572206e6f7220617070726f766564a2646970667358221220308c7d0f38216f626771d86f2b5b3091893bd5f12659a801a1f13db0060ec78f64736f6c63430007040033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000015446567656e24204661726d20437265617475726573000000000000000000000000000000000000000000000000000000000000000000000000000000000000054352454154000000000000000000000000000000000000000000000000000000
-----Decoded View---------------
Arg [0] : name_ (string): Degen$ Farm Creatures
Arg [1] : symbol_ (string): CREAT
-----Encoded View---------------
6 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000040
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000080
Arg [2] : 0000000000000000000000000000000000000000000000000000000000000015
Arg [3] : 446567656e24204661726d204372656174757265730000000000000000000000
Arg [4] : 0000000000000000000000000000000000000000000000000000000000000005
Arg [5] : 4352454154000000000000000000000000000000000000000000000000000000
Deployed Bytecode Sourcemap
171:2836:2:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2316:330:9;;;;;;:::i;:::-;;:::i;:::-;;999:150:7;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;4560:100:8;;;:::i;:::-;;;;;;;:::i;7346:221::-;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;6876:404::-;;;;;;:::i;:::-;;:::i;6354:211::-;;;:::i;:::-;;;;;;;:::i;2745:259:2:-;;;;;;:::i;:::-;;:::i;345:101:22:-;;;;;;:::i;:::-;;:::i;6116:162:8:-;;;;;;:::i;:::-;;:::i;8612:151::-;;;;;;:::i;:::-;;:::i;6642:172::-;;;;;;:::i;:::-;;:::i;1988:363:2:-;;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;3713:249:9:-;;;;;;:::i;:::-;;:::i;2654:28::-;;;:::i;4316:177:8:-;;;;;;:::i;:::-;;:::i;2359:126:2:-;;;:::i;2691:103:9:-;;;;;;:::i;:::-;;:::i;454:128:22:-;;;;;;:::i;:::-;;:::i;4033:221:8:-;;;;;;:::i;:::-;;:::i;1763:148:23:-;;;:::i;2999:277:9:-;;;;;;:::i;:::-;;:::i;2175:133::-;;;;;;:::i;:::-;;:::i;2802:189::-;;;;;;:::i;:::-;;:::i;1112:87:23:-;;;:::i;1025:213:22:-;;;;;;:::i;:::-;;:::i;4729:104:8:-;;;:::i;3284:247:9:-;;;;;;:::i;:::-;;:::i;590:190:22:-;;;;;;:::i;:::-;;:::i;726:42:2:-;;;;;;:::i;:::-;;:::i;:::-;;;;;;;;;;;:::i;1809:171::-;;;;;;:::i;:::-;;:::i;:::-;;;;;;;;:::i;7639:295:8:-;;;;;;:::i;:::-;;:::i;788:121:22:-;;;;;;:::i;:::-;;:::i;8834:285:8:-;;;;;;:::i;:::-;;:::i;598:752:9:-;;;;;;:::i;:::-;;:::i;1628:173:2:-;;;;;;:::i;:::-;;:::i;1002:319::-;;;;;;:::i;:::-;;:::i;8005:164:8:-;;;;;;:::i;:::-;;:::i;777:47:2:-;;;;;;:::i;:::-;;:::i;2066:244:23:-;;;;;;:::i;:::-;;:::i;1329:291:2:-;;;;;;:::i;:::-;;:::i;2316:330:9:-;277:22:22;288:10;277;:22::i;:::-;269:48;;;;;-1:-1:-1;;;269:48:22;;;;;;;;;;;;-1:-1:-1;;;269:48:22;;;;;;;;;;;;;;;2435:34:9;;::::1;2427:94;;;;-1:-1:-1::0;;;2427:94:9::1;;;;;;;:::i;:::-;;;;;;;;;2537:6;2532:107;2549:18:::0;;::::1;2532:107;;;2589:38;2602:7;;2610:1;2602:10;;;;;;;;;;;;;2614:9;;2624:1;2614:12;;;;;;;;;;;;;;;;;;:::i;:::-;2589:38;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;::::0;::::1;::::0;;;;-1:-1:-1;2589:12:9::1;::::0;-1:-1:-1;;;2589:38:9:i:1;:::-;2569:3;;2532:107;;;;2316:330:::0;;;;:::o;999:150:7:-;-1:-1:-1;;;;;;1108:33:7;;1084:4;1108:33;;;;;;;;;;;;;999:150;;;;:::o;4560:100:8:-;4647:5;4640:12;;;;;;;;-1:-1:-1;;4640:12:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4614:13;;4640:12;;4647:5;;4640:12;;4647:5;4640:12;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4560:100;:::o;7346:221::-;7422:7;7450:16;7458:7;7450;:16::i;:::-;7442:73;;;;-1:-1:-1;;;7442:73:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;7535:24:8;;;;:15;:24;;;;;;-1:-1:-1;;;;;7535:24:8;;7346:221::o;6876:404::-;6957:13;6973:23;6988:7;6973:14;:23::i;:::-;6957:39;;7021:5;-1:-1:-1;;;;;7015:11:8;:2;-1:-1:-1;;;;;7015:11:8;;;7007:57;;;;-1:-1:-1;;;7007:57:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;7101:5;-1:-1:-1;;;;;7085:21:8;:12;:10;:12::i;:::-;-1:-1:-1;;;;;7085:21:8;;:69;;;;7110:44;7134:5;7141:12;:10;:12::i;7110:44::-;7077:161;;;;-1:-1:-1;;;7077:161:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;7251:21;7260:2;7264:7;7251:8;:21::i;:::-;6876:404;;;:::o;6354:211::-;6415:7;6536:21;:12;:19;:21::i;:::-;6529:28;;6354:211;:::o;2745:259:2:-;2857:10;2841:27;;;;:15;:27;;;;;;;;2837:158;;;2885:28;2895:4;2901:2;2905:7;2885:9;:28::i;:::-;2837:158;;;2946:37;2965:4;2971:2;2975:7;2946:18;:37::i;345:101:22:-;398:4;433:5;-1:-1:-1;;;;;422:16:22;:7;:5;:7::i;:::-;-1:-1:-1;;;;;422:16:22;;;345:101;-1:-1:-1;;345:101:22:o;6116:162:8:-;-1:-1:-1;;;;;6240:20:8;;6213:7;6240:20;;;:13;:20;;;;;:30;;6264:5;6240:23;:30::i;:::-;6233:37;;6116:162;;;;;:::o;8612:151::-;8716:39;8733:4;8739:2;8743:7;8716:39;;;;;;;;;;;;:16;:39::i;6642:172::-;6717:7;;6759:22;:12;6775:5;6759:15;:22::i;:::-;-1:-1:-1;6737:44:8;6642:172;-1:-1:-1;;;6642:172:8:o;1988:363:2:-;2051:16;2128:9;2140:17;2150:6;2140:9;:17::i;:::-;2128:29;;2170:23;2210:1;-1:-1:-1;;;;;2196:16:2;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;2196:16:2;;2170:42;;2228:8;2223:96;2244:1;2240;:5;;;2223:96;;;2277:30;2297:6;2305:1;2277:30;;:19;:30::i;:::-;2267:6;2274:1;2267:9;;;;;;;;;;;;;;;;;;;:40;2247:3;;2223:96;;3713:249:9;3841:48;3858:7;3867:9;;3878:2;3882;3886;3841:16;:48::i;:::-;3833:78;;;;-1:-1:-1;;;3833:78:9;;;;;;;:::i;:::-;3922:32;3935:7;3944:9;;3922:32;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;3922:12:9;;-1:-1:-1;;;3922:32:9:i;:::-;3713:249;;;;;;:::o;2654:28::-;;;-1:-1:-1;;;;;2654:28:9;;:::o;4316:177:8:-;4388:7;4415:70;4432:7;4415:70;;;;;;;;;;;;;;;;;:12;;:70;:16;:70::i;2359:126:2:-;2408:13;2434:43;;;;;;;;;;;;;;;;;;;2359:126;:::o;2691:103:9:-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;2760:13:9::1;:26:::0;;-1:-1:-1;;;;;;2760:26:9::1;-1:-1:-1::0;;;;;2760:26:9;;;::::1;::::0;;;::::1;::::0;;2691:103::o;454:128:22:-;-1:-1:-1;;;;;534:22:22;;510:4;534:22;;;:15;:22;;;;;;;;;:40;;;560:14;568:5;560:7;:14::i;4033:221:8:-;4105:7;-1:-1:-1;;;;;4133:19:8;;4125:74;;;;-1:-1:-1;;;4125:74:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;4217:20:8;;;;;;:13;:20;;;;;:29;;:27;:29::i;1763:148:23:-;1343:12;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;1854:6:::1;::::0;1833:40:::1;::::0;1870:1:::1;::::0;-1:-1:-1;;;;;1854:6:23::1;::::0;1833:40:::1;::::0;1870:1;;1833:40:::1;1884:6;:19:::0;;-1:-1:-1;;;;;;1884:19:23::1;::::0;;1763:148::o;2999:277:9:-;3144:7;3169:15;3187:33;3201:7;3210:9;;3187:13;:33::i;:::-;3169:51;;3238:30;3248:7;3257:2;3261;3265;3238:30;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;3238:30:9;;-1:-1:-1;;3238:30:9;;;2999:277;-1:-1:-1;;;;;;;;;2999:277:9:o;2175:133::-;277:22:22;288:10;277;:22::i;:::-;269:48;;;;;-1:-1:-1;;;269:48:22;;;;;;;;;;;;-1:-1:-1;;;269:48:22;;;;;;;;;;;;;;;2268:32:9::1;2281:7;2290:9;;2268:32;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;::::0;::::1;::::0;;;;-1:-1:-1;2268:12:9::1;::::0;-1:-1:-1;;;2268:32:9:i:1;2802:189::-:0;2899:15;2963:7;2972:9;;2952:30;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;2942:41;;;;;;2932:51;;2802:189;;;;;:::o;1112:87:23:-;1185:6;;-1:-1:-1;;;;;1185:6:23;1112:87;:::o;1025:213:22:-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;1122:15:22::1;1140:14;-1:-1:-1::0;;;;;1140:24:22::1;;1173:4;1140:39;;;;;;;;;;;;;-1:-1:-1::0;;;;;1140:39:22::1;;;;;;;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;;;;;;;;::::0;::::1;;-1:-1:-1::0;1140:39:22;1190:40:::1;::::0;;-1:-1:-1;;;1190:40:22;;-1:-1:-1;;;;;1190:40:22;;::::1;;::::0;::::1;::::0;;;;;;;;;1140:39;;-1:-1:-1;1190:23:22;;::::1;::::0;::::1;::::0;:40;;;;;1140:39:::1;::::0;1190:40;;;;;;;;-1:-1:-1;1190:23:22;:40;::::1;;::::0;::::1;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;;;;;;;;::::0;::::1;4729:104:8::0;4818:7;4811:14;;;;;;;;-1:-1:-1;;4811:14:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4785:13;;4811:14;;4818:7;;4811:14;;4818:7;4811:14;;;;;;;;;;;;;;;;;;;;;;;;3284:247:9;3510:13;;3436:4;;-1:-1:-1;;;;;3510:13:9;3465:41;3475:7;3484:9;;3495:2;3499;3503;3465:9;:41::i;:::-;-1:-1:-1;;;;;3465:58:9;;;3284:247;-1:-1:-1;;;;;;;3284:247:9:o;590:190:22:-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;-1:-1:-1;;;;;671:26:22;::::1;663:60;;;::::0;;-1:-1:-1;;;663:60:22;;::::1;;::::0;::::1;::::0;::::1;::::0;;;;-1:-1:-1;;;663:60:22;;;;;;;;;;;;;::::1;;-1:-1:-1::0;;;;;736:29:22::1;;::::0;;;:15:::1;:29;::::0;;;;:36;;-1:-1:-1;;736:36:22::1;768:4;736:36;::::0;;590:190::o;726:42:2:-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;726:42:2;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;726:42:2;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;1809:171::-;1875:5;1914:17;;;:7;:17;;;;;:23;1875:5;;1914:23;;1908:30;;;;;;;;1946:17;;;;:7;:17;;;;;:24;;;;;;1940:31;;;;;;;;1900:72;;;;1809:171;;;:::o;7639:295:8:-;7754:12;:10;:12::i;:::-;-1:-1:-1;;;;;7742:24:8;:8;-1:-1:-1;;;;;7742:24:8;;;7734:62;;;;;-1:-1:-1;;;7734:62:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;7854:8;7809:18;:32;7828:12;:10;:12::i;:::-;-1:-1:-1;;;;;7809:32:8;;;;;;;;;;;;;;;;;-1:-1:-1;7809:32:8;;;:42;;;;;;;;;;;;:53;;-1:-1:-1;;7809:53:8;;;;;;;;;;;7893:12;:10;:12::i;:::-;-1:-1:-1;;;;;7878:48:8;;7917:8;7878:48;;;;;;;;;;;;;;;;;;;;7639:295;;:::o;788:121:22:-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;-1:-1:-1;;;;;871:29:22::1;;::::0;;;:15:::1;:29;::::0;;;;864:37;;-1:-1:-1;;864:37:22::1;::::0;;788:121::o;8834:285:8:-;8966:41;8985:12;:10;:12::i;:::-;8999:7;8966:18;:41::i;:::-;8958:103;;;;-1:-1:-1;;;8958:103:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;9072:39;9086:4;9092:2;9096:7;9105:5;9072:13;:39::i;:::-;8834:285;;;;:::o;598:752:9:-;671:13;705:16;713:7;705;:16::i;:::-;697:78;;;;-1:-1:-1;;;697:78:9;;;;;;;:::i;:::-;814:19;;;;:10;:19;;;;;;;;;788:45;;;;;;-1:-1:-1;;788:45:9;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:23;;:45;;;814:19;788:45;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;844:18;865:9;:7;:9::i;:::-;844:30;;956:4;950:18;972:1;950:23;946:72;;;-1:-1:-1;997:9:9;-1:-1:-1;990:16:9;;946:72;1122:23;;:27;1118:182;;-1:-1:-1;1279:9:9;-1:-1:-1;1272:16:9;;1118:182;1319:23;1334:7;1319:14;:23::i;:::-;1312:30;598:752;-1:-1:-1;;;;598:752:9:o;1628:173:2:-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;-1:-1:-1;;;;;1714:24:2;::::1;;::::0;;;:15:::1;:24;::::0;;;;;;:33;;-1:-1:-1;;1714:33:2::1;::::0;::::1;;;::::0;;1763:30;::::1;::::0;::::1;::::0;1714:33;;1763:30:::1;:::i;:::-;;;;;;;;1628:173:::0;;:::o;1002:319::-;1343:12:23;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;1181:18:2::1;1187:2;1191:7;1181:5;:18::i;:::-;1229:84;;;;;;;;1247:11;1236:23;;;;;;;;;;1229:84;;;;;;;;;;;;1268:7;1261:15;;;;;;;;;;1229:84;;;;;;;;::::0;;::::1;::::0;::::1;;::::0;;::::1;::::0;;;;-1:-1:-1;;;;;1292:15:2::1;1229:84;::::0;;;;;;;;;;;;::::1;::::0;;-1:-1:-1;1229:84:2;;;;;;;;1210:16;;;:7:::1;:16:::0;;;;;:103;;;;:16;;-1:-1:-1;;1210:103:2::1;::::0;;::::1;::::0;::::1;;;;;;;;::::0;;-1:-1:-1;1210:103:2::1;::::0;::::1;::::0;;;;;-1:-1:-1;;1210:103:2::1;;::::0;::::1;::::0;::::1;;;;;;;;::::0;;-1:-1:-1;1210:103:2::1;::::0;::::1;::::0;;;::::1;::::0;::::1;::::0;-1:-1:-1;;;;;1210:103:2::1;::::0;::::1;-1:-1:-1::0;;1210:103:2::1;::::0;;::::1;::::0;::::1;-1:-1:-1::0;;1210:103:2;;::::1;::::0;;;::::1;::::0;;;::::1;;::::0;;::::1;::::0;::::1;::::0;;;::::1;::::0;-1:-1:-1;1210:103:2;::::1;::::0;::::1;::::0;;::::1;::::0;::::1;:::i;:::-;-1:-1:-1::0;;;;;;;;1002:319:2:o;8005:164:8:-;-1:-1:-1;;;;;8126:25:8;;;8102:4;8126:25;;;:18;:25;;;;;;;;:35;;;;;;;;;;;;;;;8005:164::o;777:47:2:-;;;;;;;;;;;;;;;:::o;2066:244:23:-;1343:12;:10;:12::i;:::-;-1:-1:-1;;;;;1332:23:23;:7;:5;:7::i;:::-;-1:-1:-1;;;;;1332:23:23;;1324:68;;;;;-1:-1:-1;;;1324:68:23;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;1324:68:23;;;;;;;;;;;;;;;-1:-1:-1;;;;;2155:22:23;::::1;2147:73;;;;-1:-1:-1::0;;;2147:73:23::1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2257:6;::::0;2236:38:::1;::::0;-1:-1:-1;;;;;2236:38:23;;::::1;::::0;2257:6:::1;::::0;2236:38:::1;::::0;2257:6:::1;::::0;2236:38:::1;2285:6;:17:::0;;-1:-1:-1;;;;;;2285:17:23::1;-1:-1:-1::0;;;;;2285:17:23;;;::::1;::::0;;;::::1;::::0;;2066:244::o;1329:291:2:-;1434:10;1414:16;1422:7;1414;:16::i;:::-;-1:-1:-1;;;;;1414:30:2;;1406:69;;;;-1:-1:-1;;;1406:69:2;;;;;;;:::i;:::-;1500:16;;;;:7;:16;;;;;:21;;;;1494:35;;;;;;;;-1:-1:-1;;1494:35:2;;;:40;1486:84;;;;-1:-1:-1;;;1486:84:2;;;;;;;:::i;:::-;1583:16;;;;:7;:16;;;;;:29;;:21;;1607:5;;1583:29;:::i;1506:226:9:-;1615:16;1623:7;1615;:16::i;:::-;1607:75;;;;-1:-1:-1;;;1607:75:9;;;;;;;:::i;:::-;1693:19;;;;:10;:19;;;;;;;;:31;;;;;;;;:::i;10586:127:8:-;10651:4;10675:30;:12;10697:7;10675:21;:30::i;613:106:1:-;701:10;613:106;:::o;16493:183:8:-;16559:24;;;;:15;:24;;;;;:29;;-1:-1:-1;;;;;;16559:29:8;-1:-1:-1;;;;;16559:29:8;;;;;;;;:24;;16613:23;16559:24;16613:14;:23::i;:::-;-1:-1:-1;;;;;16604:46:8;;;;;;;;;;;16493:183;;:::o;8036:123:11:-;8105:7;8132:19;8140:3;8132:7;:19::i;14016:599:8:-;14141:4;-1:-1:-1;;;;;14114:31:8;:23;14129:7;14114:14;:23::i;:::-;-1:-1:-1;;;;;14114:31:8;;14106:85;;;;-1:-1:-1;;;14106:85:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;14228:16:8;;14220:65;;;;-1:-1:-1;;;14220:65:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;14298:39;14319:4;14325:2;14329:7;14298:20;:39::i;:::-;14402:29;14419:1;14423:7;14402:8;:29::i;:::-;-1:-1:-1;;;;;14444:19:8;;;;;;:13;:19;;;;;:35;;14471:7;14444:26;:35::i;:::-;-1:-1:-1;;;;;;14490:17:8;;;;;;:13;:17;;;;;:30;;14512:7;14490:21;:30::i;:::-;-1:-1:-1;14533:29:8;:12;14550:7;14559:2;14533:16;:29::i;:::-;;14599:7;14595:2;-1:-1:-1;;;;;14580:27:8;14589:4;-1:-1:-1;;;;;14580:27:8;;;;;;;;;;;14016:599;;;:::o;8236:305::-;8397:41;8416:12;:10;:12::i;:::-;8430:7;8397:18;:41::i;:::-;8389:103;;;;-1:-1:-1;;;8389:103:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8505:28;8515:4;8521:2;8525:7;8505:9;:28::i;9543:137:12:-;9614:7;9649:22;9653:3;9665:5;9649:3;:22::i;8498:236:11:-;8578:7;;;;8638:22;8642:3;8654:5;8638:3;:22::i;:::-;8607:53;;-1:-1:-1;8607:53:11;-1:-1:-1;;;8498:236:11;;;;;;:::o;9784:213::-;9891:7;9942:44;9947:3;9967;9973:12;9942:4;:44::i;:::-;9934:53;-1:-1:-1;9784:213:11;;;;;;:::o;10880:355:8:-;10973:4;10998:16;11006:7;10998;:16::i;:::-;10990:73;;;;-1:-1:-1;;;10990:73:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;11074:13;11090:23;11105:7;11090:14;:23::i;:::-;11074:39;;11143:5;-1:-1:-1;;;;;11132:16:8;:7;-1:-1:-1;;;;;11132:16:8;;:51;;;;11176:7;-1:-1:-1;;;;;11152:31:8;:20;11164:7;11152:11;:20::i;:::-;-1:-1:-1;;;;;11152:31:8;;11132:51;:94;;;;11187:39;11211:5;11218:7;11187:23;:39::i;10001:272::-;10115:28;10125:4;10131:2;10135:7;10115:9;:28::i;:::-;10162:48;10185:4;10191:2;10195:7;10204:5;10162:22;:48::i;:::-;10154:111;;;;-1:-1:-1;;;10154:111:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4904:792;4977:13;5011:16;5019:7;5011;:16::i;:::-;5003:76;;;;-1:-1:-1;;;5003:76:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5118:19;;;;:10;:19;;;;;;;;;5092:45;;;;;;-1:-1:-1;;5092:45:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:23;;:45;;;5118:19;5092:45;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5148:18;5169:9;:7;:9::i;:::-;5148:30;;5260:4;5254:18;5276:1;5254:23;5250:72;;;-1:-1:-1;5301:9:8;-1:-1:-1;5294:16:8;;5250:72;5426:23;;:27;5422:108;;5501:4;5507:9;5484:33;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;5484:33:8;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;5484:33:8;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;5484:33:8;;;;;;;;;;;;;-1:-1:-1;;5484:33:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5470:48;;;;;;5422:108;5662:4;5668:18;:7;:16;:18::i;:::-;5645:42;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;5645:42:8;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;5645:42:8;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;5645:42:8;;;;;;;;;;;;;-1:-1:-1;;5645:42:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5631:57;;;;4904:792;;;:::o;12501:404::-;-1:-1:-1;;;;;12581:16:8;;12573:61;;;;;-1:-1:-1;;;12573:61:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;12654:16;12662:7;12654;:16::i;:::-;12653:17;12645:58;;;;;-1:-1:-1;;;12645:58:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;12716:45;12745:1;12749:2;12753:7;12716:20;:45::i;:::-;-1:-1:-1;;;;;12774:17:8;;;;;;:13;:17;;;;;:30;;12796:7;12774:21;:30::i;:::-;-1:-1:-1;12817:29:8;:12;12834:7;12843:2;12817:16;:29::i;:::-;-1:-1:-1;12864:33:8;;12889:7;;-1:-1:-1;;;;;12864:33:8;;;12881:1;;12864:33;;12881:1;;12864:33;12501:404;;:::o;7797:151:11:-;7881:4;7905:35;7915:3;7935;7905:9;:35::i;4615:110::-;4698:19;;4615:110::o;8630:137:12:-;8700:4;8724:35;8732:3;8752:5;8724:7;:35::i;8323:131::-;8390:4;8414:32;8419:3;8439:5;8414:4;:32::i;7220:185:11:-;7309:4;7333:64;7338:3;7358;-1:-1:-1;;;;;7372:23:11;;7333:4;:64::i;4581:204:12:-;4676:18;;4648:7;;4676:26;-1:-1:-1;4668:73:12;;;;-1:-1:-1;;;4668:73:12;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4759:3;:11;;4771:5;4759:18;;;;;;;;;;;;;;;;4752:25;;4581:204;;;;:::o;5080:279:11:-;5184:19;;5147:7;;;;5184:27;-1:-1:-1;5176:74:11;;;;-1:-1:-1;;;5176:74:11;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5263:22;5288:3;:12;;5301:5;5288:19;;;;;;;;;;;;;;;;;;5263:44;;5326:5;:10;;;5338:5;:12;;;5318:33;;;;;5080:279;;;;;:::o;6577:319::-;6671:7;6710:17;;;:12;;;:17;;;;;;6761:12;6746:13;6738:36;;;;-1:-1:-1;;;6738:36:11;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;6828:3;:12;;6852:1;6841:8;:12;6828:26;;;;;;;;;;;;;;;;;;:33;;;6821:40;;;6577:319;;;;;:::o;15881:604:8:-;16002:4;16029:15;:2;-1:-1:-1;;;;;16029:13:8;;:15::i;:::-;16024:60;;-1:-1:-1;16068:4:8;16061:11;;16024:60;16094:23;16120:252;-1:-1:-1;;;16233:12:8;:10;:12::i;:::-;16260:4;16279:7;16301:5;16136:181;;;;;;-1:-1:-1;;;;;16136:181:8;;;;;;-1:-1:-1;;;;;16136:181:8;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;16136:181:8;;;;;;;-1:-1:-1;;;;;16136:181:8;;;;;;;;;;;16120:252;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;16120:15:8;;;:252;:15;:252::i;:::-;16094:278;;16383:13;16410:10;16399:32;;;;;;;;;;;;;;;-1:-1:-1;16399:32:8;-1:-1:-1;;;;;;16450:26:8;-1:-1:-1;;;16450:26:8;;-1:-1:-1;;;15881:604:8;;;;;;:::o;221:746:25:-;277:13;498:10;494:53;;-1:-1:-1;525:10:25;;;;;;;;;;;;-1:-1:-1;;;525:10:25;;;;;;494:53;572:5;557:12;613:78;620:9;;613:78;;646:8;;677:2;669:10;;;;613:78;;;701:19;733:6;-1:-1:-1;;;;;723:17:25;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;723:17:25;-1:-1:-1;795:5:25;;-1:-1:-1;701:39:25;-1:-1:-1;;;767:10:25;;811:117;818:9;;811:117;;887:2;880:4;:9;875:2;:14;862:29;;844:6;851:7;;;;;;;844:15;;;;;;;;;;;:47;-1:-1:-1;;;;;844:47:25;;;;;;;;-1:-1:-1;914:2:25;906:10;;;;811:117;;;-1:-1:-1;952:6:25;221:746;-1:-1:-1;;;;221:746:25:o;4395:125:11:-;4466:4;4490:17;;;:12;;;;;:17;;;;;;:22;;;4395:125::o;2283:1544:12:-;2349:4;2488:19;;;:12;;;:19;;;;;;2524:15;;2520:1300;;2959:18;;-1:-1:-1;;2910:14:12;;;;2959:22;;;;2886:21;;2959:3;;:22;;3246;;;;;;;;;;;;;;3226:42;;3392:9;3363:3;:11;;3375:13;3363:26;;;;;;;;;;;;;;;;;;;:38;;;;3469:23;;;3511:1;3469:12;;;:23;;;;;;3495:17;;;3469:43;;3621:17;;3469:3;;3621:17;;;;;;;;;;;;;;;;;;;;;;3716:3;:12;;:19;3729:5;3716:19;;;;;;;;;;;3709:26;;;3759:4;3752:11;;;;;;;;2520:1300;3803:5;3796:12;;;;;1693:414;1756:4;1778:21;1788:3;1793:5;1778:9;:21::i;:::-;1773:327;;-1:-1:-1;1816:23:12;;;;;;;;:11;:23;;;;;;;;;;;;;1999:18;;1977:19;;;:12;;;:19;;;;;;:40;;;;2032:11;;1773:327;-1:-1:-1;2083:5:12;2076:12;;1895:692:11;1971:4;2106:17;;;:12;;;:17;;;;;;2140:13;2136:444;;-1:-1:-1;;2225:38:11;;;;;;;;;;;;;;;;;;2207:57;;;;;;;;:12;:57;;;;;;;;;;;;;;;;;;;;;;;;2422:19;;2402:17;;;:12;;;:17;;;;;;;:39;2456:11;;2136:444;2536:5;2500:3;:12;;2524:1;2513:8;:12;2500:26;;;;;;;;;;;;;;;;;;:33;;:41;;;;2563:5;2556:12;;;;;751:422:0;1118:20;1157:8;;;751:422::o;3669:195::-;3772:12;3804:52;3826:6;3834:4;3840:1;3843:12;3772;4973:18;4984:6;4973:10;:18::i;:::-;4965:60;;;;;-1:-1:-1;;;4965:60:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;5099:12;5113:23;5140:6;-1:-1:-1;;;;;5140:11:0;5160:5;5168:4;5140:33;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;5140:33:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5098:75;;;;5191:52;5209:7;5218:10;5230:12;5191:17;:52::i;:::-;5184:59;4721:530;-1:-1:-1;;;;;;;4721:530:0:o;7261:742::-;7376:12;7405:7;7401:595;;;-1:-1:-1;7436:10:0;7429:17;;7401:595;7550:17;;:21;7546:439;;7813:10;7807:17;7874:15;7861:10;7857:2;7853:19;7846:44;7761:148;7949:20;;-1:-1:-1;;;7949:20:0;;;;;;;;;;;;;;;;;7956:12;;7949:20;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;14:412:26;;;155:3;148:4;140:6;136:17;132:27;122:2;;180:8;170;163:26;122:2;-1:-1:-1;210:20:26;;-1:-1:-1;;;;;242:30:26;;239:2;;;292:8;282;275:26;239:2;336:4;328:6;324:17;312:29;;399:3;392:4;384;376:6;372:17;364:6;360:30;356:41;353:50;350:2;;;416:1;413;406:12;431:378;;;549:3;542:4;534:6;530:17;526:27;516:2;;574:8;564;557:26;516:2;-1:-1:-1;604:20:26;;-1:-1:-1;;;;;636:30:26;;633:2;;;686:8;676;669:26;633:2;730:4;722:6;718:17;706:29;;782:3;775:4;766:6;758;754:19;750:30;747:39;744:2;;;799:1;796;789:12;814:158;882:20;;942:4;931:16;;921:27;;911:2;;962:1;959;952:12;977:259;;1089:2;1077:9;1068:7;1064:23;1060:32;1057:2;;;1110:6;1102;1095:22;1057:2;1154:9;1141:23;1173:33;1200:5;1173:33;:::i;1241:402::-;;;1370:2;1358:9;1349:7;1345:23;1341:32;1338:2;;;1391:6;1383;1376:22;1338:2;1435:9;1422:23;1454:33;1481:5;1454:33;:::i;:::-;1506:5;-1:-1:-1;1563:2:26;1548:18;;1535:32;1576:35;1535:32;1576:35;:::i;:::-;1630:7;1620:17;;;1328:315;;;;;:::o;1648:470::-;;;;1794:2;1782:9;1773:7;1769:23;1765:32;1762:2;;;1815:6;1807;1800:22;1762:2;1859:9;1846:23;1878:33;1905:5;1878:33;:::i;:::-;1930:5;-1:-1:-1;1987:2:26;1972:18;;1959:32;2000:35;1959:32;2000:35;:::i;:::-;1752:366;;2054:7;;-1:-1:-1;;;2108:2:26;2093:18;;;;2080:32;;1752:366::o;2123:1316::-;;;;;2295:3;2283:9;2274:7;2270:23;2266:33;2263:2;;;2317:6;2309;2302:22;2263:2;2361:9;2348:23;2380:33;2407:5;2380:33;:::i;:::-;2432:5;-1:-1:-1;2456:2:26;2495:18;;;2482:32;2523:35;2482:32;2523:35;:::i;:::-;2577:7;-1:-1:-1;2631:2:26;2616:18;;2603:32;;-1:-1:-1;2686:2:26;2671:18;;2658:32;-1:-1:-1;;;;;2739:14:26;;;2736:2;;;2771:6;2763;2756:22;2736:2;2814:6;2803:9;2799:22;2789:32;;2859:7;2852:4;2848:2;2844:13;2840:27;2830:2;;2886:6;2878;2871:22;2830:2;2931;2918:16;2957:2;2949:6;2946:14;2943:2;;;2963:9;2943:2;3003;2997:9;3076:2;3053:17;;-1:-1:-1;;3049:31:26;3037:44;;3033:53;;3101:18;;;3121:22;;;3098:46;3095:2;;;3147:9;3095:2;3174;3167:22;3198;;;3239:15;;;3235:24;;3232:37;-1:-1:-1;3229:2:26;;;3287:6;3279;3272:22;3229:2;3348:6;3343:2;3339;3335:11;3330:2;3322:6;3318:15;3305:50;3375:19;;;3371:28;;;3364:44;;;;-1:-1:-1;2253:1186:26;;;;-1:-1:-1;2253:1186:26;;-1:-1:-1;;2253:1186:26:o;3444:438::-;;;3570:2;3558:9;3549:7;3545:23;3541:32;3538:2;;;3591:6;3583;3576:22;3538:2;3635:9;3622:23;3654:33;3681:5;3654:33;:::i;:::-;3706:5;-1:-1:-1;3763:2:26;3748:18;;3735:32;3805:15;;3798:23;3786:36;;3776:2;;3841:6;3833;3826:22;3887:327;;;4016:2;4004:9;3995:7;3991:23;3987:32;3984:2;;;4037:6;4029;4022:22;3984:2;4081:9;4068:23;4100:33;4127:5;4100:33;:::i;:::-;4152:5;4204:2;4189:18;;;;4176:32;;-1:-1:-1;;;3974:240:26:o;4219:655::-;;;;;;4394:3;4382:9;4373:7;4369:23;4365:33;4362:2;;;4416:6;4408;4401:22;4362:2;4460:9;4447:23;4479:33;4506:5;4479:33;:::i;:::-;4531:5;-1:-1:-1;4583:2:26;4568:18;;4555:32;;-1:-1:-1;4606:38:26;4640:2;4625:18;;4606:38;:::i;:::-;4596:48;;4663:38;4697:2;4686:9;4682:18;4663:38;:::i;:::-;4653:48;;4753:3;4742:9;4738:19;4725:33;4802:10;4793:7;4789:24;4780:7;4777:37;4767:2;;4833:6;4825;4818:22;4767:2;4861:7;4851:17;;;4352:522;;;;;;;;:::o;4879:843::-;;;;;5090:2;5078:9;5069:7;5065:23;5061:32;5058:2;;;5111:6;5103;5096:22;5058:2;5156:9;5143:23;-1:-1:-1;;;;;5226:2:26;5218:6;5215:14;5212:2;;;5247:6;5239;5232:22;5212:2;5291:84;5367:7;5358:6;5347:9;5343:22;5291:84;:::i;:::-;5394:8;;-1:-1:-1;5265:110:26;-1:-1:-1;5482:2:26;5467:18;;5454:32;;-1:-1:-1;5498:16:26;;;5495:2;;;5532:6;5524;5517:22;5495:2;;5576:86;5654:7;5643:8;5632:9;5628:24;5576:86;:::i;:::-;5048:674;;;;-1:-1:-1;5681:8:26;-1:-1:-1;;;;5048:674:26:o;5727:306::-;;5838:2;5826:9;5817:7;5813:23;5809:32;5806:2;;;5859:6;5851;5844:22;5806:2;5890:23;;-1:-1:-1;;;;;;5942:32:26;;5932:43;;5922:2;;5994:6;5986;5979:22;6038:417;;;6182:2;6170:9;6161:7;6157:23;6153:32;6150:2;;;6203:6;6195;6188:22;6460:190;;6572:2;6560:9;6551:7;6547:23;6543:32;6540:2;;;6593:6;6585;6578:22;6540:2;-1:-1:-1;6621:23:26;;6530:120;-1:-1:-1;6530:120:26:o;6655:501::-;;;;6804:2;6792:9;6783:7;6779:23;6775:32;6772:2;;;6825:6;6817;6810:22;6772:2;6866:9;6853:23;6843:33;;6927:2;6916:9;6912:18;6899:32;-1:-1:-1;;;;;6946:6:26;6943:30;6940:2;;;6991:6;6983;6976:22;6940:2;7035:61;7088:7;7079:6;7068:9;7064:22;7035:61;:::i;:::-;6762:394;;7115:8;;-1:-1:-1;7009:87:26;;-1:-1:-1;;;;6762:394:26:o;7161:711::-;;;;;;;7359:3;7347:9;7338:7;7334:23;7330:33;7327:2;;;7381:6;7373;7366:22;7327:2;7422:9;7409:23;7399:33;;7483:2;7472:9;7468:18;7455:32;-1:-1:-1;;;;;7502:6:26;7499:30;7496:2;;;7547:6;7539;7532:22;7496:2;7591:61;7644:7;7635:6;7624:9;7620:22;7591:61;:::i;:::-;7671:8;;-1:-1:-1;7565:87:26;-1:-1:-1;7725:38:26;;-1:-1:-1;7759:2:26;7744:18;;7725:38;:::i;:::-;7715:48;;7810:2;7799:9;7795:18;7782:32;7772:42;;7861:3;7850:9;7846:19;7833:33;7823:43;;7317:555;;;;;;;;:::o;7877:478::-;;7959:5;7953:12;7986:6;7981:3;7974:19;8011:3;8023:162;8037:6;8034:1;8031:13;8023:162;;;8099:4;8155:13;;;8151:22;;8145:29;8127:11;;;8123:20;;8116:59;8052:12;8023:162;;;8203:6;8200:1;8197:13;8194:2;;;8269:3;8262:4;8253:6;8248:3;8244:16;8240:27;8233:40;8194:2;-1:-1:-1;8337:2:26;8316:15;-1:-1:-1;;8312:29:26;8303:39;;;;8344:4;8299:50;;7929:426;-1:-1:-1;;7929:426:26:o;8360:203::-;-1:-1:-1;;;;;8524:32:26;;;;8506:51;;8494:2;8479:18;;8461:102::o;8568:635::-;8739:2;8791:21;;;8861:13;;8764:18;;;8883:22;;;8568:635;;8739:2;8962:15;;;;8936:2;8921:18;;;8568:635;9008:169;9022:6;9019:1;9016:13;9008:169;;;9083:13;;9071:26;;9152:15;;;;9117:12;;;;9044:1;9037:9;9008:169;;;-1:-1:-1;9194:3:26;;8719:484;-1:-1:-1;;;;;;8719:484:26:o;9208:187::-;9373:14;;9366:22;9348:41;;9336:2;9321:18;;9303:92::o;9400:177::-;9546:25;;;9534:2;9519:18;;9501:76::o;9582:398::-;9809:25;;;9882:4;9870:17;;;;9865:2;9850:18;;9843:45;9919:2;9904:18;;9897:34;9962:2;9947:18;;9940:34;9796:3;9781:19;;9763:217::o;9985:662::-;;10265:2;10257:6;10254:14;10244:2;;10272:9;10244:2;10310:6;10299:9;10292:25;10347:1;10339:6;10336:13;10326:2;;10353:9;10326:2;10400:6;10395:2;10384:9;10380:18;10373:34;10455:10;10447:6;10443:23;10438:2;10427:9;10423:18;10416:51;-1:-1:-1;;;;;10507:6:26;10503:31;10498:2;10487:9;10483:18;10476:59;10572:3;10566;10555:9;10551:19;10544:32;10593:48;10636:3;10625:9;10621:19;10613:6;10593:48;:::i;10652:222::-;;10801:2;10790:9;10783:21;10821:47;10864:2;10853:9;10849:18;10841:6;10821:47;:::i;10879:411::-;11081:2;11063:21;;;11120:2;11100:18;;;11093:30;11159:34;11154:2;11139:18;;11132:62;-1:-1:-1;;;11225:2:26;11210:18;;11203:45;11280:3;11265:19;;11053:237::o;11295:341::-;11497:2;11479:21;;;11536:2;11516:18;;;11509:30;-1:-1:-1;;;11570:2:26;11555:18;;11548:47;11627:2;11612:18;;11469:167::o;11641:410::-;11843:2;11825:21;;;11882:2;11862:18;;;11855:30;11921:34;11916:2;11901:18;;11894:62;-1:-1:-1;;;11987:2:26;11972:18;;11965:44;12041:3;12026:19;;11815:236::o;12056:413::-;12258:2;12240:21;;;12297:2;12277:18;;;12270:30;12336:34;12331:2;12316:18;;12309:62;-1:-1:-1;;;12402:2:26;12387:18;;12380:47;12459:3;12444:19;;12230:239::o;12474:350::-;12676:2;12658:21;;;12715:2;12695:18;;;12688:30;12754:28;12749:2;12734:18;;12727:56;12815:2;12800:18;;12648:176::o;12829:355::-;13031:2;13013:21;;;13070:2;13050:18;;;13043:30;13109:33;13104:2;13089:18;;13082:61;13175:2;13160:18;;13003:181::o;13371:464::-;;13558:6;13547:9;13540:25;13601:2;13596;13585:9;13581:18;13574:30;13640:6;13635:2;13624:9;13620:18;13613:34;13697:6;13689;13684:2;13673:9;13669:18;13656:48;13724:22;;;13748:2;13720:31;;;13713:45;;;;13819:2;13798:15;;;-1:-1:-1;;13794:29:26;13779:45;13775:54;;13530:305;-1:-1:-1;;13530:305:26:o;13840:262::-;14036:4;14024:17;;;14006:36;;14078:17;;14073:2;14058:18;;14051:45;13994:2;13979:18;;13961:141::o;14107:534::-;;;14251:11;14238:25;14345:2;14341:7;14330:8;14314:14;14310:29;14306:43;14286:18;14282:68;14272:2;;14367:4;14361;14354:18;14272:2;14397:33;;14449:20;;;-1:-1:-1;;;;;;14481:30:26;;14478:2;;;14527:4;14521;14514:18;14478:2;14563:4;14551:17;;-1:-1:-1;14594:14:26;14590:27;;;14580:38;;14577:2;;;14631:1;14628;14621:12;14646:133;-1:-1:-1;;;;;14723:31:26;;14713:42;;14703:2;;14769:1;14766;14759:12;14703:2;14693:86;:::o
Swarm Source
ipfs://308c7d0f38216f626771d86f2b5b3091893bd5f12659a801a1f13db0060ec78f
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
[ Download: CSV Export ]
A token is a representation of an on-chain or off-chain asset. The token page shows information such as price, total supply, holders, transfers and social links. Learn more about this page in our Knowledge Base.