Contract 0x90249ed4d69d70e709ffcd8bee2c5a566f65dade 7

DeFi  
 

Contract Overview

AugustusSwapper by ParaSwap
Balance:
0 MATIC

MATIC Value:
$0.00

Token:
 
Txn Hash Method
Block
From
To
Value [Txn Fee]
0x7158064594b017cf0bc0d8d7b0c3f95bc581890d8d750f2516a79bc4d4ebb035Simple Swap286383952022-05-22 17:41:15188 days 6 hrs ago0xdfe9fc6f911aa4b2fa373bd45e4f72549d11639e IN  AugustusSwapper by ParaSwap0 MATIC0.0020026225 33.7
0x9b14d3b0eb00817c0a7a7e13d917458ea9635f950b70ed108b36d5419cd853beSimple Swap283920642022-05-16 14:20:09194 days 9 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.022168100
0x500cd8a3d07b1bbe85f3850fe6f141eb87abd109bf53d4c9e5a8afaf0a7ae3e9Simple Swap280737812022-05-08 13:41:50202 days 10 hrs ago0x2eb0867866ec27b4c91e0780794ebb35e5b4f477 IN  AugustusSwapper by ParaSwap0.94 MATIC0.0070889 35
0x4e4967e675b42271a3759c674b12815aec081b138ff2b656428ecad5bfcd1168Simple Swap277178652022-04-29 13:24:20211 days 10 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.0130232460
0xbb89008685586bd45680bc240c34625219591d4fd8cc67a476e97f8dc007cea3Mega Swap276767282022-04-28 12:21:35212 days 11 hrs agoAugury Finance: Community Wallet IN  AugustusSwapper by ParaSwap0 MATIC0.060301278 51
0xb2d0a695f7ad0e4c219c751a59bd98e524b529bf5b933ddf7ce8fbc64486120dSimple Swap276766982022-04-28 12:20:35212 days 11 hrs agoAugury Finance: Community Wallet IN  AugustusSwapper by ParaSwap0 MATIC0.011152792 46
0x91763123e0c2e21e10297470d850fae58d81c5a2a4e77611dfe3002088ecb140Simple Swap273282662022-04-19 15:23:19221 days 8 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.011377298 53
0xdb03b5a04362433499d55e7da9913d232ac7414542323aa162f7280f261e213eSimple Swap271327632022-04-14 16:13:25226 days 7 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.009333322 43
0x5af1148da238986eeb602717798bc9b028e90aeea85ba0d5ea3113b389e990e1Simple Swap270106042022-04-11 13:58:08229 days 9 hrs ago0x4b8b30b37c9bee318136b593ae301d2f9073db93 IN  AugustusSwapper by ParaSwap0 MATIC0.028263145 41
0x196f06263e3fab8cff7e6588a6035962dbacb87fded3f6e597a52bd49bde8a6dSimple Swap269770732022-04-10 17:52:05230 days 5 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.00781394436
0xb7ef55746df0fb95c7fe18332fb8de73bd996ae9849afe2621a594f31bb1d10aSimple Swap269022422022-04-08 19:41:09232 days 4 hrs ago0x3351b913d9b37abbbfc057224aa38547f485cbed IN  AugustusSwapper by ParaSwap0 MATIC0.0118278655
0x7dc1e4de08be4e3c31cfdcb6416b624bc96ea8b68902c08607af6c1f664fba02Multi Swap265530042022-03-30 21:13:16241 days 2 hrs ago0xf0cc6c3e0122748388d8fb33a38ee876339b447b IN  AugustusSwapper by ParaSwap0 MATIC0.01370534436
0xd8a0a382d835e29b9b2fc177bafcb17d630dafd90ba350aa785a4a7effdc8ddbMega Swap265175642022-03-29 23:29:59242 days 15 mins ago0xe8bca870337eb54c3ef39791922bd6fdcf76bc3f IN  AugustusSwapper by ParaSwap163 MATIC0.018248154 46
0x469f7b336ca37c5f531926252e17bd1636aecaf3aef1e1a8c1e43951591afe06Multi Swap265008252022-03-29 12:58:40242 days 10 hrs ago0x9f19c30ba446080f6a4b37d851db36b5037acfd9 IN  AugustusSwapper by ParaSwap0 MATIC0.01154016 40
0x941522616cd44ba29a52ceead513692dcf6d8c4750313473c9908532da24a92fSimple Swap264959472022-03-29 10:05:56242 days 13 hrs ago0x164cc2ebad84efa8c8fd79b97b6effcb9fe373e2 IN  AugustusSwapper by ParaSwap0 MATIC0.0071010336 32.1
0x52b48e328d412d6c12a08135ce571f281aef56ebeaf3860c745b5d0493108c1eSimple Swap264666832022-03-28 16:23:18243 days 7 hrs ago0x8ea8721f27efcaabb3901ed6756505ab873f15a7 IN  AugustusSwapper by ParaSwap0 MATIC0.006951 40
0x47e3a694bf2b9d3b7daea38226e071c3f3571bbcde9d9350f4ed0912b002928eMulti Swap263731692022-03-26 6:33:14245 days 17 hrs ago0xcec6605d05788a02cf4c7ac20116e0612a820251 IN  AugustusSwapper by ParaSwap50 MATIC0.0126351888 34.4
0x9f4b955df02cda02814e9826aeccbce732a18c716f2e491bb3f43b35339d58f8Simple Swap263247262022-03-25 0:08:35246 days 23 hrs ago0x0a14f771c714a47b75546550c4c83b8b36d2db40 IN  AugustusSwapper by ParaSwap0 MATIC0.010550738 47.3
0x0e54c4d4b5a91ed475922f404f5e8bba16134b0ea2a8b940e47e4e5f03a0f8daSimple Swap263219452022-03-24 22:28:45247 days 1 hr agoAugury Finance: Community Wallet IN  AugustusSwapper by ParaSwap0 MATIC0.0171641 50
0xc25040fbbaca76c36d712881c776c0a668cbbb716b9c6edac960d1e8ef3b2812Mega Swap262958352022-03-24 6:18:13247 days 17 hrs ago0xfbf2e062628c0669ca2b439cf2758d1e04c47587 IN  AugustusSwapper by ParaSwap0 MATIC0.0028491564 36.1
0x8c1a2e68634f68299636780da27368cdda29a338ceb1f82eb6a4def64e9441a4Mega Swap262958342022-03-24 6:18:11247 days 17 hrs ago0xfbf2e062628c0669ca2b439cf2758d1e04c47587 IN  AugustusSwapper by ParaSwap0 MATIC0.0024215633 32.3
0xc8273b766cbae4a3d1595f04921f4bc055826fec454906064769c13e6d6d18e2Mega Swap262958342022-03-24 6:18:11247 days 17 hrs ago0xfbf2e062628c0669ca2b439cf2758d1e04c47587 IN  AugustusSwapper by ParaSwap0 MATIC0.0466156152 37.6
0xa812b98891541be9334f33c2be35d826e37b836f8268ffa14716a2d24388a558Simple Swap262797792022-03-23 20:22:52248 days 3 hrs ago0x087cb7e8d1af9372d14b860ead3166ced7079d68 IN  AugustusSwapper by ParaSwap0 MATIC0.003592942149 30.569125363
0x3b4b3945b3773641f0475b7b590c4f97c3efcb17abfab02aa33f6641a6d6c4bcSimple Swap262795512022-03-23 20:12:52248 days 3 hrs ago0x087cb7e8d1af9372d14b860ead3166ced7079d68 IN  AugustusSwapper by ParaSwap0 MATIC0.006785974058 31.049700109
0x5b8e517607835d0d9cd28c0e23e13586af31769f68951b1c52d4b012474ede12Simple Swap262425232022-03-22 21:52:09249 days 1 hr ago0xc9056d1e2c75a7078c4c15d4443cb6d397035793 IN  AugustusSwapper by ParaSwap9.925596979791607 MATIC0.00474571494831.935740758
[ Download CSV Export 

OVERVIEW

A contract router responsible for making swaps.

Latest 25 internal transaction
Parent Txn Hash Block From To Value
0x2d4bdbf1276605548b2ca5f323cd81caa4474c752a41d769968385b14e19ef26355133082022-11-12 11:19:4314 days 12 hrs ago AugustusSwapper by ParaSwap 0xe7cbbd11be7f993197aef41c2d6df6e5f6867d890.01 MATIC
0x2d4bdbf1276605548b2ca5f323cd81caa4474c752a41d769968385b14e19ef26355133082022-11-12 11:19:4314 days 12 hrs ago 0xc590175e458b83680867afd273527ff58f74c02b AugustusSwapper by ParaSwap0.01 MATIC
0x500cd8a3d07b1bbe85f3850fe6f141eb87abd109bf53d4c9e5a8afaf0a7ae3e9280737812022-05-08 13:41:50202 days 10 hrs ago AugustusSwapper by ParaSwap 0x1de7a822a3c3dc50ee63cc06babde277a876909e0.94 MATIC
0x0f51197138d18e8cbb0c07d5d481fb2dbb526acf9e29b535e6ec063715091194276935232022-04-28 22:44:32212 days 1 hr ago AugustusSwapper by ParaSwap 0xe7cbbd11be7f993197aef41c2d6df6e5f6867d890.3 MATIC
0x0f51197138d18e8cbb0c07d5d481fb2dbb526acf9e29b535e6ec063715091194276935232022-04-28 22:44:32212 days 1 hr ago 0xc590175e458b83680867afd273527ff58f74c02b AugustusSwapper by ParaSwap0.3 MATIC
0x80c60d404df735b5383cc3da49cc688b047c26135ce0a86c4fe01a5f26704c9f276935232022-04-28 22:44:32212 days 1 hr ago AugustusSwapper by ParaSwap 0xb88891076e2d610b8d93cc98f54e30f33577905775 MATIC
0x80c60d404df735b5383cc3da49cc688b047c26135ce0a86c4fe01a5f26704c9f276935232022-04-28 22:44:32212 days 1 hr ago 0xc590175e458b83680867afd273527ff58f74c02b AugustusSwapper by ParaSwap75 MATIC
0xd8a0a382d835e29b9b2fc177bafcb17d630dafd90ba350aa785a4a7effdc8ddb265175642022-03-29 23:29:59242 days 15 mins ago AugustusSwapper by ParaSwap Polygon: WMATIC Token71.72 MATIC
0xd8a0a382d835e29b9b2fc177bafcb17d630dafd90ba350aa785a4a7effdc8ddb265175642022-03-29 23:29:59242 days 15 mins ago AugustusSwapper by ParaSwap Polygon: WMATIC Token91.28 MATIC
0x47e3a694bf2b9d3b7daea38226e071c3f3571bbcde9d9350f4ed0912b002928e263731692022-03-26 6:33:14245 days 17 hrs ago AugustusSwapper by ParaSwap Polygon: WMATIC Token13 MATIC
0x47e3a694bf2b9d3b7daea38226e071c3f3571bbcde9d9350f4ed0912b002928e263731692022-03-26 6:33:14245 days 17 hrs ago AugustusSwapper by ParaSwap Polygon: WMATIC Token37 MATIC
0x9f4b955df02cda02814e9826aeccbce732a18c716f2e491bb3f43b35339d58f8263247262022-03-25 0:08:35246 days 23 hrs ago AugustusSwapper by ParaSwap0x0a14f771c714a47b75546550c4c83b8b36d2db4042.83571557900549663 MATIC
0x9f4b955df02cda02814e9826aeccbce732a18c716f2e491bb3f43b35339d58f8263247262022-03-25 0:08:35246 days 23 hrs ago AugustusSwapper by ParaSwap0x814fc9298548a68562c254d04aa9175aa7bb822a0.032288227823370978 MATIC
0x9f4b955df02cda02814e9826aeccbce732a18c716f2e491bb3f43b35339d58f8263247262022-03-25 0:08:35246 days 23 hrs ago AugustusSwapper by ParaSwap0xd43324eb6f31f86e361b48185797b339242f95f40.182966624332435537 MATIC
0x9f4b955df02cda02814e9826aeccbce732a18c716f2e491bb3f43b35339d58f8263247262022-03-25 0:08:35246 days 23 hrs ago 0xb88891076e2d610b8d93cc98f54e30f335779057 AugustusSwapper by ParaSwap43.050970431161303145 MATIC
0xc8273b766cbae4a3d1595f04921f4bc055826fec454906064769c13e6d6d18e2262958342022-03-24 6:18:11247 days 17 hrs ago AugustusSwapper by ParaSwap Polygon: WMATIC Token20.90411747390211797 MATIC
0xc8273b766cbae4a3d1595f04921f4bc055826fec454906064769c13e6d6d18e2262958342022-03-24 6:18:11247 days 17 hrs ago Polygon: WMATIC Token AugustusSwapper by ParaSwap20.90411747390211797 MATIC
0xa812b98891541be9334f33c2be35d826e37b836f8268ffa14716a2d24388a558262797792022-03-23 20:22:52248 days 3 hrs ago AugustusSwapper by ParaSwap0x087cb7e8d1af9372d14b860ead3166ced7079d681.269717994311506702 MATIC
0xa812b98891541be9334f33c2be35d826e37b836f8268ffa14716a2d24388a558262797792022-03-23 20:22:52248 days 3 hrs ago AugustusSwapper by ParaSwap0x814fc9298548a68562c254d04aa9175aa7bb822a0.000957073865058925 MATIC
0xa812b98891541be9334f33c2be35d826e37b836f8268ffa14716a2d24388a558262797792022-03-23 20:22:52248 days 3 hrs ago AugustusSwapper by ParaSwap0xd43324eb6f31f86e361b48185797b339242f95f40.005423418568667239 MATIC
0xa812b98891541be9334f33c2be35d826e37b836f8268ffa14716a2d24388a558262797792022-03-23 20:22:52248 days 3 hrs ago Polygon: WMATIC Token AugustusSwapper by ParaSwap1.276098486745232866 MATIC
0x5b8e517607835d0d9cd28c0e23e13586af31769f68951b1c52d4b012474ede12262425232022-03-22 21:52:09249 days 1 hr ago AugustusSwapper by ParaSwap 0xc28c10a7e5953bafdf7b1cc4821a2b860adf92559.925596979791607971 MATIC
0xe0e8a34507eafcf0c23d4a58af4ce7b5134e11bfa1b3a430feb7a4df345ce6c2262425172022-03-22 21:51:57249 days 1 hr ago AugustusSwapper by ParaSwap 0xc28c10a7e5953bafdf7b1cc4821a2b860adf92559.925596979791607971 MATIC
0x8e93ff0255db15a9d4bff17bd6be4dc530617e5864ca0eef15215f998e8324ee262355892022-03-22 17:36:33249 days 6 hrs ago AugustusSwapper by ParaSwap 0xe7cbbd11be7f993197aef41c2d6df6e5f6867d899.929964466329351755 MATIC
0x3bff41d39a70e53e2b0f844a1c175b193adb71a4beb5e242b8967d7834ea607e262222122022-03-22 9:48:10249 days 13 hrs ago AugustusSwapper by ParaSwap 0x4c28f48448720e9000907bc2611f73022fdce1fa94 MATIC
[ Download CSV Export 
Loading
This contract may be a proxy contract. Click on More Options and select Is this a proxy? to confirm and enable the "Read as Proxy" & "Write as Proxy" tabs.

Contract Source Code Verified (Exact Match)

Contract Name:
AugustusSwapper

Compiler Version
v0.7.5+commit.eb77ed08

Optimization Enabled:
Yes with 20000 runs

Other Settings:
default evmVersion, None license

Contract Source Code (Solidity)

/**
 *Submitted for verification at polygonscan.com on 2021-06-09
*/

// File: original_contracts/IWhitelisted.sol

pragma solidity 0.7.5;


interface IWhitelisted {

    function hasRole(
        bytes32 role,
        address account
    )
        external
        view
        returns (bool);

    function WHITELISTED_ROLE() external view returns(bytes32);
}

// File: openzeppelin-solidity/contracts/token/ERC20/IERC20.sol



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);
}

// File: original_contracts/lib/IExchange.sol

pragma solidity 0.7.5;



/**
* @dev This interface should be implemented by all exchanges which needs to integrate with the paraswap protocol
*/
interface IExchange {

    /**
   * @dev The function which performs the swap on an exchange.
   * Exchange needs to implement this method in order to support swapping of tokens through it
   * @param fromToken Address of the source token
   * @param toToken Address of the destination token
   * @param fromAmount Amount of source tokens to be swapped
   * @param toAmount Minimum destination token amount expected out of this swap
   * @param exchange Internal exchange or factory contract address for the exchange. For example Registry address for the Uniswap
   * @param payload Any exchange specific data which is required can be passed in this argument in encoded format which
   * will be decoded by the exchange. Each exchange will publish it's own decoding/encoding mechanism
   */
   //TODO: REMOVE RETURN STATEMENT
    function swap(
        IERC20 fromToken,
        IERC20 toToken,
        uint256 fromAmount,
        uint256 toAmount,
        address exchange,
        bytes calldata payload) external payable;

  /**
   * @dev The function which performs the swap on an exchange.
   * Exchange needs to implement this method in order to support swapping of tokens through it
   * @param fromToken Address of the source token
   * @param toToken Address of the destination token
   * @param fromAmount Max Amount of source tokens to be swapped
   * @param toAmount Destination token amount expected out of this swap
   * @param exchange Internal exchange or factory contract address for the exchange. For example Registry address for the Uniswap
   * @param payload Any exchange specific data which is required can be passed in this argument in encoded format which
   * will be decoded by the exchange. Each exchange will publish it's own decoding/encoding mechanism
   */
    function buy(
        IERC20 fromToken,
        IERC20 toToken,
        uint256 fromAmount,
        uint256 toAmount,
        address exchange,
        bytes calldata payload) external payable;

    /**
   * @dev This function is used to perform onChainSwap. It build all the parameters onchain. Basically the information
   * encoded in payload param of swap will calculated in this case
   * Exchange needs to implement this method in order to support swapping of tokens through it
   * @param fromToken Address of the source token
   * @param toToken Address of the destination token
   * @param fromAmount Amount of source tokens to be swapped
   * @param toAmount Minimum destination token amount expected out of this swap
   */
    function onChainSwap(
        IERC20 fromToken,
        IERC20 toToken,
        uint256 fromAmount,
        uint256 toAmount
    ) external payable returns (uint256);

    /**
    * @dev Certain adapters/exchanges needs to be initialized.
    * This method will be called from Augustus
    */
    function initialize(bytes calldata data) external;

    /**
    * @dev Returns unique identifier for the adapter
    */
    function getKey() external pure returns(bytes32);
}

// File: openzeppelin-solidity/contracts/math/SafeMath.sol



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, 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) {
        return sub(a, b, "SafeMath: subtraction overflow");
    }

    /**
     * @dev Returns the subtraction of two unsigned integers, reverting with custom message on
     * overflow (when the result is negative).
     *
     * 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);
        uint256 c = a - b;

        return c;
    }

    /**
     * @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) {
        // 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 0;
        }

        uint256 c = a * b;
        require(c / a == b, "SafeMath: multiplication overflow");

        return c;
    }

    /**
     * @dev Returns the integer division of two unsigned integers. Reverts 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) {
        return div(a, b, "SafeMath: division by zero");
    }

    /**
     * @dev Returns the integer division of two unsigned integers. Reverts with custom message 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, string memory errorMessage) internal pure returns (uint256) {
        require(b > 0, errorMessage);
        uint256 c = a / b;
        // assert(a == b * c + a % b); // There is no case in which this doesn't hold

        return c;
    }

    /**
     * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
     * Reverts 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) {
        return mod(a, b, "SafeMath: modulo by zero");
    }

    /**
     * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
     * Reverts with custom message 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, string memory errorMessage) internal pure returns (uint256) {
        require(b != 0, errorMessage);
        return a % b;
    }
}

// File: original_contracts/lib/SafeERC20.sol

pragma solidity 0.7.5;




library Address {

    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;
    }

    function functionCall(address target, bytes memory data, string memory errorMessage) internal returns (bytes memory) {
        return functionCallWithValue(target, data, 0, errorMessage);
    }

    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);
    }

    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);
            }
        }
    }
}


library SafeERC20 {
    using SafeMath for uint256;
    using Address for address;

    function safeTransfer(IERC20 token, address to, uint256 value) internal {
        _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));
    }

    function safeTransferFrom(IERC20 token, address from, address to, uint256 value) internal {
        _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));
    }

    /**
     * @dev Deprecated. This function has issues similar to the ones found in
     * {IERC20-approve}, and its usage is discouraged.
     *
     * Whenever possible, use {safeIncreaseAllowance} and
     * {safeDecreaseAllowance} instead.
     */
    function safeApprove(IERC20 token, address spender, uint256 value) internal {
        // safeApprove should only be called when setting an initial allowance,
        // or when resetting it to zero. To increase and decrease it, use
        // 'safeIncreaseAllowance' and 'safeDecreaseAllowance'
        // solhint-disable-next-line max-line-length
        require((value == 0) || (token.allowance(address(this), spender) == 0),
            "SafeERC20: approve from non-zero to non-zero allowance"
        );
        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));
    }

    function safeIncreaseAllowance(IERC20 token, address spender, uint256 value) internal {
        uint256 newAllowance = token.allowance(address(this), spender).add(value);
        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));
    }

    /**
     * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
     * on the return value: the return value is optional (but if data is returned, it must not be false).
     * @param token The token targeted by the call.
     * @param data The call data (encoded using abi.encode or one of its variants).
     */
    function _callOptionalReturn(IERC20 token, bytes memory data) private {
        // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since
        // we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that
        // the target address contains contract code and also asserts for success in the low-level call.

        bytes memory returndata = address(token).functionCall(data, "SafeERC20: low-level call failed");
        if (returndata.length > 0) { // Return data is optional
            // solhint-disable-next-line max-line-length
            require(abi.decode(returndata, (bool)), "SafeERC20: ERC20 operation did not succeed");
        }
    }
}

// File: original_contracts/ITokenTransferProxy.sol

pragma solidity 0.7.5;


interface ITokenTransferProxy {

    function transferFrom(
        address token,
        address from,
        address to,
        uint256 amount
    )
        external;

    function freeReduxTokens(address user, uint256 tokensToFree) external;
}

// File: original_contracts/lib/Utils.sol

pragma solidity 0.7.5;






library Utils {
    using SafeMath for uint256;
    using SafeERC20 for IERC20;

    address constant ETH_ADDRESS = address(
        0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE
    );

    address constant WETH_ADDRESS = address(
        0x0d500B1d8E8eF31E21C99d1Db9A6444d3ADf1270
    );

    uint256 constant MAX_UINT = 2 ** 256 - 1;

    /**
   * @param fromToken Address of the source token
   * @param fromAmount Amount of source tokens to be swapped
   * @param toAmount Minimum destination token amount expected out of this swap
   * @param expectedAmount Expected amount of destination tokens without slippage
   * @param beneficiary Beneficiary address
   * 0 then 100% will be transferred to beneficiary. Pass 10000 for 100%
   * @param referrer referral id
   * @param useReduxToken whether to use redux token or not
   * @param path Route to be taken for this swap to take place

   */
    struct SellData {
        address fromToken;
        uint256 fromAmount;
        uint256 toAmount;
        uint256 expectedAmount;
        address payable beneficiary;
        string referrer;
        bool useReduxToken;
        Utils.Path[] path;

    }

    struct MegaSwapSellData {
        address fromToken;
        uint256 fromAmount;
        uint256 toAmount;
        uint256 expectedAmount;
        address payable beneficiary;
        string referrer;
        bool useReduxToken;
        Utils.MegaSwapPath[] path;
    }

    struct BuyData {
        address fromToken;
        address toToken;
        uint256 fromAmount;
        uint256 toAmount;
        address payable beneficiary;
        string referrer;
        bool useReduxToken;
        Utils.BuyRoute[] route;
    }

    struct Route {
        address payable exchange;
        address targetExchange;
        uint percent;
        bytes payload;
        uint256 networkFee;//Network fee is associated with 0xv3 trades
    }

    struct MegaSwapPath {
        uint256 fromAmountPercent;
        Path[] path;
    }

    struct Path {
        address to;
        uint256 totalNetworkFee;//Network fee is associated with 0xv3 trades
        Route[] routes;
    }

    struct BuyRoute {
        address payable exchange;
        address targetExchange;
        uint256 fromAmount;
        uint256 toAmount;
        bytes payload;
        uint256 networkFee;//Network fee is associated with 0xv3 trades
    }

    function ethAddress() internal pure returns (address) {return ETH_ADDRESS;}

    function wethAddress() internal pure returns (address) {return WETH_ADDRESS;}

    function maxUint() internal pure returns (uint256) {return MAX_UINT;}

    function approve(
        address addressToApprove,
        address token,
        uint256 amount
    ) internal {
        if (token != ETH_ADDRESS) {
            IERC20 _token = IERC20(token);

            uint allowance = _token.allowance(address(this), addressToApprove);

            if (allowance < amount) {
                _token.safeApprove(addressToApprove, 0);
                _token.safeIncreaseAllowance(addressToApprove, MAX_UINT);
            }
        }
    }

    function transferTokens(
        address token,
        address payable destination,
        uint256 amount
    )
    internal
    {
        if (amount > 0) {
            if (token == ETH_ADDRESS) {
                (bool result, ) = destination.call{value: amount, gas: 4000}("");
                require(result, "Failed to transfer Ether");
            }
            else {
                IERC20(token).safeTransfer(destination, amount);
            }
        }

    }

    function tokenBalance(
        address token,
        address account
    )
    internal
    view
    returns (uint256)
    {
        if (token == ETH_ADDRESS) {
            return account.balance;
        } else {
            return IERC20(token).balanceOf(account);
        }
    }

    /**
    * @dev Helper method to refund gas using gas tokens
    */
    function refundGas(
        address account,
        address tokenTransferProxy,
        uint256 initialGas
    )
        internal
    {
        uint256 freeBase = 14154;
        uint256 freeToken = 6870;
        uint256 reimburse = 24000;

        uint256 tokens = initialGas.sub(
            gasleft()).add(freeBase).div(reimburse.mul(2).sub(freeToken)
        );

        freeGasTokens(account, tokenTransferProxy, tokens);
    }

    /**
    * @dev Helper method to free gas tokens
    */
    function freeGasTokens(address account, address tokenTransferProxy, uint256 tokens) internal {

        uint256 tokensToFree = tokens;
        uint256 safeNumTokens = 0;
        uint256 gas = gasleft();

        if (gas >= 27710) {
            safeNumTokens = gas.sub(27710).div(1148 + 5722 + 150);
        }

        if (tokensToFree > safeNumTokens) {
            tokensToFree = safeNumTokens;
        }
        ITokenTransferProxy(tokenTransferProxy).freeReduxTokens(account, tokensToFree);
    }
}

// File: openzeppelin-solidity/contracts/GSN/Context.sol



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;
    }
}

// File: openzeppelin-solidity/contracts/access/Ownable.sol



pragma solidity >=0.6.0 <0.8.0;

/**
 * @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 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;
    }
}

// File: original_contracts/IReduxToken.sol

pragma solidity 0.7.5;

interface IReduxToken {

    function freeUpTo(uint256 value) external returns (uint256 freed);

    function freeFromUpTo(address from, uint256 value) external returns (uint256 freed);

    function mint(uint256 value) external;
}

// File: original_contracts/TokenTransferProxy.sol

pragma solidity 0.7.5;







/**
* @dev Allows owner of the contract to transfer tokens on behalf of user.
* User will need to approve this contract to spend tokens on his/her behalf
* on Paraswap platform
*/
contract TokenTransferProxy is Ownable, ITokenTransferProxy {
    using SafeERC20 for IERC20;

    IReduxToken public reduxToken;

    constructor(address _reduxToken) public {
        reduxToken = IReduxToken(_reduxToken);
    }

    /**
    * @dev Allows owner of the contract to transfer tokens on user's behalf
    * @dev Swapper contract will be the owner of this contract
    * @param token Address of the token
    * @param from Address from which tokens will be transferred
    * @param to Receipent address of the tokens
    * @param amount Amount of tokens to transfer
    */
    function transferFrom(
        address token,
        address from,
        address to,
        uint256 amount
    )
        external
        override
        onlyOwner
    {
        IERC20(token).safeTransferFrom(from, to, amount);
    }

    function freeReduxTokens(address user, uint256 tokensToFree) external override onlyOwner {
        reduxToken.freeFromUpTo(user, tokensToFree);
    }

}

// File: original_contracts/IPartnerRegistry.sol

pragma solidity 0.7.5;


interface IPartnerRegistry {

    function getPartnerContract(string calldata referralId) external view returns(address);

}

// File: original_contracts/IPartner.sol

pragma solidity 0.7.5;


interface IPartner {

    function getPartnerInfo() external view returns(
        address payable feeWallet,
        uint256 fee,
        uint256 partnerShare,
        uint256 paraswapShare,
        bool positiveSlippageToUser,
        bool noPositiveSlippage
    );
}

// File: original_contracts/lib/TokenFetcherAugustus.sol

pragma solidity 0.7.5;



contract TokenFetcherAugustus {

    address internal _owner;

    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);

    /**
     * @dev Returns the address of the current owner.
     */
    function owner() public view returns (address) {
        return _owner;
    }

    /**
     * @dev Throws if called by any account other than the owner.
     */
    modifier onlyOwner() {
        require(_owner == msg.sender, "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 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 onlyOwner {
        require(newOwner != address(0), "Ownable: new owner is the zero address");
        emit OwnershipTransferred(_owner, newOwner);
        _owner = newOwner;
    }
    /**
    * @dev Allows owner of the contract to transfer any tokens which are assigned to the contract
    * This method is for safety if by any chance tokens or ETHs are assigned to the contract by mistake
    * @dev token Address of the token to be transferred
    * @dev destination Recepient of the token
    * @dev amount Amount of tokens to be transferred
    */
    function transferTokens(
        address token,
        address payable destination,
        uint256 amount
    )
        external
        onlyOwner
    {
        Utils.transferTokens(token, destination, amount);
    }
}

// File: original_contracts/IWETH.sol

pragma solidity 0.7.5;



abstract contract IWETH is IERC20 {
    function deposit() external virtual payable;
    function withdraw(uint256 amount) external virtual;
}

// File: original_contracts/IUniswapProxy.sol

pragma solidity 0.7.5;


interface IUniswapProxy {
    function swapOnUniswap(
        uint256 amountIn,
        uint256 amountOutMin,
        address[] calldata path
    )
        external
        returns (uint256);

    function swapOnUniswapFork(
        address factory,
        bytes32 initCode,
        uint256 amountIn,
        uint256 amountOutMin,
        address[] calldata path
    )
        external
        returns (uint256);

    function buyOnUniswap(
        uint256 amountInMax,
        uint256 amountOut,
        address[] calldata path
    )
        external
        returns (uint256 tokensSold);

    function buyOnUniswapFork(
        address factory,
        bytes32 initCode,
        uint256 amountInMax,
        uint256 amountOut,
        address[] calldata path
    )
        external
        returns (uint256 tokensSold);

   function setupTokenSpender(address tokenSpender) external;

}

// File: original_contracts/AdapterStorage.sol

pragma solidity 0.7.5;



contract AdapterStorage {

    mapping (bytes32 => bool) internal adapterInitialized;
    mapping (bytes32 => bytes) internal adapterVsData;
    ITokenTransferProxy internal _tokenTransferProxy;

    function isInitialized(bytes32 key) public view returns(bool) {
        return adapterInitialized[key];
    }

    function getData(bytes32 key) public view returns(bytes memory) {
        return adapterVsData[key];
    }

    function getTokenTransferProxy() public view returns (address) {
        return address(_tokenTransferProxy);
    }
}

// File: original_contracts/AugustusSwapper.sol

pragma solidity 0.7.5;
pragma experimental ABIEncoderV2;













contract AugustusSwapper is AdapterStorage, TokenFetcherAugustus {
    using SafeMath for uint256;

    IWhitelisted private _whitelisted;

    IPartnerRegistry private _partnerRegistry;

    address payable private _feeWallet;

    address private _uniswapProxy;

    address private _pendingUniswapProxy;

    uint256 private _changeRequestedBlock;

    //Number of blocks after which UniswapProxy change can be confirmed
    uint256 private _timelock;

    event Swapped(
        address initiator,
        address indexed beneficiary,
        address indexed srcToken,
        address indexed destToken,
        uint256 srcAmount,
        uint256 receivedAmount,
        uint256 expectedAmount,
        string referrer
    );

    event Bought(
        address initiator,
        address indexed beneficiary,
        address indexed srcToken,
        address indexed destToken,
        uint256 srcAmount,
        uint256 receivedAmount,
        string referrer
    );

    event FeeTaken(
        uint256 fee,
        uint256 partnerShare,
        uint256 paraswapShare
    );

    event AdapterInitialized(address indexed adapter);

    modifier onlySelf() {
        require(
            msg.sender == address(this),
            "AugustusSwapper: Invalid access"
        );
        _;
    }

    receive () payable external {

    }

    function getTimeLock() external view returns(uint256) {
      return _timelock;
    }

    function initialize(
        address whitelist,
        address reduxToken,
        address partnerRegistry,
        address payable feeWallet,
        address uniswapProxy,
        uint256 timelock
    )
        external
    {
        require(address(_tokenTransferProxy) == address(0), "Contract already initialized!!");
        _partnerRegistry = IPartnerRegistry(partnerRegistry);
        TokenTransferProxy lTokenTransferProxy = new TokenTransferProxy(reduxToken);
        _tokenTransferProxy = ITokenTransferProxy(lTokenTransferProxy);
        _whitelisted = IWhitelisted(whitelist);
        _feeWallet = feeWallet;
        _uniswapProxy = uniswapProxy;
        _owner = msg.sender;
        _timelock = timelock;
    }

    function initializeAdapter(address adapter, bytes calldata data) external onlyOwner {

        require(
            _whitelisted.hasRole(_whitelisted.WHITELISTED_ROLE(), adapter),
            "Exchange not whitelisted"
        );
        (bool success,) = adapter.delegatecall(abi.encodeWithSelector(IExchange.initialize.selector, data));
        require(success, "Failed to initialize adapter");
        emit AdapterInitialized(adapter);
    }

    function getPendingUniswapProxy() external view returns(address) {
      return  _pendingUniswapProxy;
    }

    function getChangeRequestedBlock() external view returns(uint256) {
      return _changeRequestedBlock;
    }

    function getUniswapProxy() external view returns(address) {
        return _uniswapProxy;
    }

    function getVersion() external view returns(string memory) {
        return "4.0.0";
    }

    function getPartnerRegistry() external view returns(address) {
        return address(_partnerRegistry);
    }

    function getWhitelistAddress() external view returns(address) {
        return address(_whitelisted);
    }

    function getFeeWallet() external view returns(address) {
        return _feeWallet;
    }

    function changeUniswapProxy(address uniswapProxy) external onlyOwner {
        require(uniswapProxy != address(0), "Invalid address");
        _changeRequestedBlock = block.number;
        _pendingUniswapProxy = uniswapProxy;
    }

    function confirmUniswapProxyChange() external onlyOwner {
        require(
            block.number >= _changeRequestedBlock.add(_timelock),
            "Time lock check failed"
        );

        require(_pendingUniswapProxy != address(0), "No pending request");

        _changeRequestedBlock = 0;
        _uniswapProxy = _pendingUniswapProxy;
        _pendingUniswapProxy = address(0);
    }

    function setFeeWallet(address payable feeWallet) external onlyOwner {
        require(feeWallet != address(0), "Invalid address");
        _feeWallet = feeWallet;
    }

    function setPartnerRegistry(address partnerRegistry) external onlyOwner {
        require(partnerRegistry != address(0), "Invalid address");
        _partnerRegistry = IPartnerRegistry(partnerRegistry);
    }

    function setWhitelistAddress(address whitelisted) external onlyOwner {
        require(whitelisted != address(0), "Invalid whitelist address");
        _whitelisted = IWhitelisted(whitelisted);
    }

    function swapOnUniswap(
        uint256 amountIn,
        uint256 amountOutMin,
        address[] calldata path,
        uint8 referrer
    )
        external
        payable
    {
        //DELEGATING CALL TO THE ADAPTER
        (bool success, bytes memory result) = _uniswapProxy.delegatecall(
            abi.encodeWithSelector(
                IUniswapProxy.swapOnUniswap.selector,
                amountIn,
                amountOutMin,
                path
            )
        );
        require(success, "Call to uniswap proxy failed");

    }

    function buyOnUniswap(
        uint256 amountInMax,
        uint256 amountOut,
        address[] calldata path,
        uint8 referrer
    )
        external
        payable
    {
        //DELEGATING CALL TO THE ADAPTER
        (bool success, bytes memory result) = _uniswapProxy.delegatecall(
            abi.encodeWithSelector(
                IUniswapProxy.buyOnUniswap.selector,
                amountInMax,
                amountOut,
                path
            )
        );
        require(success, "Call to uniswap proxy failed");

    }

    function buyOnUniswapFork(
        address factory,
        bytes32 initCode,
        uint256 amountInMax,
        uint256 amountOut,
        address[] calldata path,
        uint8 referrer
    )
        external
        payable
    {
        //DELEGATING CALL TO THE ADAPTER
        (bool success, bytes memory result) = _uniswapProxy.delegatecall(
            abi.encodeWithSelector(
                IUniswapProxy.buyOnUniswapFork.selector,
                factory,
                initCode,
                amountInMax,
                amountOut,
                path
            )
        );
        require(success, "Call to uniswap proxy failed");

    }

    function swapOnUniswapFork(
        address factory,
        bytes32 initCode,
        uint256 amountIn,
        uint256 amountOutMin,
        address[] calldata path,
        uint8 referrer
    )
        external
        payable

    {
        //DELEGATING CALL TO THE ADAPTER
        (bool success, bytes memory result) = _uniswapProxy.delegatecall(
            abi.encodeWithSelector(
                IUniswapProxy.swapOnUniswapFork.selector,
                factory,
                initCode,
                amountIn,
                amountOutMin,
                path
            )
        );
        require(success, "Call to uniswap proxy failed");

    }

    function simplBuy(
        address fromToken,
        address toToken,
        uint256 fromAmount,
        uint256 toAmount,
        address[] memory callees,
        bytes memory exchangeData,
        uint256[] memory startIndexes,
        uint256[] memory values,
        address payable beneficiary,
        string memory referrer,
        bool useReduxToken
    )
        external
        payable

    {
        beneficiary = beneficiary == address(0) ? msg.sender : beneficiary;
        uint receivedAmount = performSimpleSwap(
            fromToken,
            toToken,
            fromAmount,
            toAmount,
            toAmount,//expected amount and to amount are same in case of buy
            callees,
            exchangeData,
            startIndexes,
            values,
            beneficiary,
            referrer,
            useReduxToken
        );

        uint256 remainingAmount = Utils.tokenBalance(
            fromToken,
            address(this)
        );

        if (remainingAmount > 0) {
            Utils.transferTokens(address(fromToken), msg.sender, remainingAmount);
        }

        emit Bought(
            msg.sender,
            beneficiary,
            fromToken,
            toToken,
            fromAmount,
            receivedAmount,
            referrer
        );
    }

    function approve(
        address token,
        address to,
        uint256 amount
    )
        external
        onlySelf
    {
        Utils.approve(to, token, amount);
    }

    function simpleSwap(
        address fromToken,
        address toToken,
        uint256 fromAmount,
        uint256 toAmount,
        uint256 expectedAmount,
        address[] memory callees,
        bytes memory exchangeData,
        uint256[] memory startIndexes,
        uint256[] memory values,
        address payable beneficiary,
        string memory referrer,
        bool useReduxToken
    )
        public
        payable
        returns (uint256 receivedAmount)
    {
        beneficiary = beneficiary == address(0) ? msg.sender : beneficiary;
        receivedAmount = performSimpleSwap(
            fromToken,
            toToken,
            fromAmount,
            toAmount,
            expectedAmount,
            callees,
            exchangeData,
            startIndexes,
            values,
            beneficiary,
            referrer,
            useReduxToken
        );

        emit Swapped(
            msg.sender,
            beneficiary,
            fromToken,
            toToken,
            fromAmount,
            receivedAmount,
            expectedAmount,
            referrer
        );

        return receivedAmount;
    }

    function transferTokensFromProxy(
        address token,
        uint256 amount
    )
      private
    {
        if (token != Utils.ethAddress()) {
            _tokenTransferProxy.transferFrom(
                token,
                msg.sender,
                address(this),
                amount
            );
        }
    }

    function performSimpleSwap(
        address fromToken,
        address toToken,
        uint256 fromAmount,
        uint256 toAmount,
        uint256 expectedAmount,
        address[] memory callees,
        bytes memory exchangeData,
        uint256[] memory startIndexes,
        uint256[] memory values,
        address payable beneficiary,
        string memory referrer,
        bool useReduxToken
    )
        private
        returns (uint256 receivedAmount)
    {
        require(toAmount > 0, "toAmount is too low");
        require(
            callees.length + 1 == startIndexes.length,
            "Start indexes must be 1 greater then number of callees"
        );

        uint initialGas = gasleft();

        //If source token is not ETH than transfer required amount of tokens
        //from sender to this contract
        transferTokensFromProxy(fromToken, fromAmount);

        for (uint256 i = 0; i < callees.length; i++) {
            require(
                callees[i] != address(_tokenTransferProxy),
                "Can not call TokenTransferProxy Contract"
            );

            bool result = externalCall(
                callees[i], //destination
                values[i], //value to send
                startIndexes[i], // start index of call data
                startIndexes[i + 1].sub(startIndexes[i]), // length of calldata
                exchangeData// total calldata
            );
            require(result, "External call failed");
        }

        receivedAmount = Utils.tokenBalance(
            toToken,
            address(this)
        );

        require(
            receivedAmount >= toAmount,
            "Received amount of tokens are less then expected"
        );

        takeFeeAndTransferTokens(
            toToken,
            expectedAmount,
            receivedAmount,
            beneficiary,
            referrer
        );

        if (useReduxToken) {
            Utils.refundGas(msg.sender, address(_tokenTransferProxy), initialGas);
        }

        return receivedAmount;
    }

    /**
   * @dev This function sends the WETH returned during the exchange to the user.
   * @param token: The WETH Address
   */
    function withdrawAllWETH(IWETH token) external onlySelf {
        uint256 amount = token.balanceOf(address(this));
        token.withdraw(amount);
    }

    /**
   * @dev The function which performs the multi path swap.
   * @param data Data required to perform swap.
   */
    function multiSwap(
        Utils.SellData memory data
    )
        public
        payable
        returns (uint256)
    {
        uint initialGas = gasleft();

        address fromToken = data.fromToken;
        uint256 fromAmount = data.fromAmount;
        uint256 toAmount = data.toAmount;
        uint256 expectedAmount = data.expectedAmount;
        address payable beneficiary = data.beneficiary == address(0) ? msg.sender : data.beneficiary;
        string memory referrer = data.referrer;
        Utils.Path[] memory path = data.path;
        address toToken = path[path.length - 1].to;
        bool useReduxToken = data.useReduxToken;

        //Referral can never be empty
        require(bytes(referrer).length > 0, "Invalid referrer");

        require(toAmount > 0, "To amount can not be 0");

        //if fromToken is not ETH then transfer tokens from user to this contract
        if (fromToken != Utils.ethAddress()) {
            _tokenTransferProxy.transferFrom(
                fromToken,
                msg.sender,
                address(this),
                fromAmount
            );
        }

        performSwap(
            fromToken,
            fromAmount,
            path
        );


        uint256 receivedAmount = Utils.tokenBalance(
            toToken,
            address(this)
        );

        require(
            receivedAmount >= toAmount,
            "Received amount of tokens are less then expected"
        );


        takeFeeAndTransferTokens(
            toToken,
            expectedAmount,
            receivedAmount,
            beneficiary,
            referrer
        );

        if (useReduxToken) {
            Utils.refundGas(msg.sender, address(_tokenTransferProxy), initialGas);
        }

        emit Swapped(
            msg.sender,
            beneficiary,
            fromToken,
            toToken,
            fromAmount,
            receivedAmount,
            expectedAmount,
            referrer
        );

        return receivedAmount;
    }

    /**
   * @dev The function which performs the mega path swap.
   * @param data Data required to perform swap.
   */
    function megaSwap(
        Utils.MegaSwapSellData memory data
    )
        public
        payable
        returns (uint256)
    {
        uint initialGas = gasleft();

        address fromToken = data.fromToken;
        uint256 fromAmount = data.fromAmount;
        uint256 toAmount = data.toAmount;
        uint256 expectedAmount = data.expectedAmount;
        address payable beneficiary = data.beneficiary == address(0) ? msg.sender : data.beneficiary;
        string memory referrer = data.referrer;
        Utils.MegaSwapPath[] memory path = data.path;
        address toToken = path[0].path[path[0].path.length - 1].to;
        bool useReduxToken = data.useReduxToken;

        //Referral can never be empty
        require(bytes(referrer).length > 0, "Invalid referrer");

        require(toAmount > 0, "To amount can not be 0");

        //if fromToken is not ETH then transfer tokens from user to this contract
        if (fromToken != Utils.ethAddress()) {
            _tokenTransferProxy.transferFrom(
                fromToken,
                msg.sender,
                address(this),
                fromAmount
            );
        }

        for (uint8 i = 0; i < uint8(path.length); i++) {
            uint256 _fromAmount = fromAmount.mul(path[i].fromAmountPercent).div(10000);
            if (i == path.length - 1) {
                _fromAmount = Utils.tokenBalance(address(fromToken), address(this));
            }
            performSwap(
                fromToken,
                _fromAmount,
                path[i].path
            );
        }

        uint256 receivedAmount = Utils.tokenBalance(
            toToken,
            address(this)
        );

        require(
            receivedAmount >= toAmount,
            "Received amount of tokens are less then expected"
        );


        takeFeeAndTransferTokens(
            toToken,
            expectedAmount,
            receivedAmount,
            beneficiary,
            referrer
        );

        if (useReduxToken) {
            Utils.refundGas(msg.sender, address(_tokenTransferProxy), initialGas);
        }

        emit Swapped(
            msg.sender,
            beneficiary,
            fromToken,
            toToken,
            fromAmount,
            receivedAmount,
            expectedAmount,
            referrer
        );

        return receivedAmount;
    }

    /**
   * @dev The function which performs the single path buy.
   * @param data Data required to perform swap.
   */
    function buy(
        Utils.BuyData memory data
    )
        public
        payable
        returns (uint256)
    {

        address fromToken = data.fromToken;
        uint256 fromAmount = data.fromAmount;
        uint256 toAmount = data.toAmount;
        address payable beneficiary = data.beneficiary == address(0) ? msg.sender : data.beneficiary;
        string memory referrer = data.referrer;
        Utils.BuyRoute[] memory route = data.route;
        address toToken = data.toToken;
        bool useReduxToken = data.useReduxToken;

        //Referral id can never be empty
        require(bytes(referrer).length > 0, "Invalid referrer");

        require(toAmount > 0, "To amount can not be 0");

        uint256 receivedAmount = performBuy(
            fromToken,
            toToken,
            fromAmount,
            toAmount,
            route,
            useReduxToken
        );

        takeFeeAndTransferTokens(
            toToken,
            toAmount,
            receivedAmount,
            beneficiary,
            referrer
        );

        uint256 remainingAmount = Utils.tokenBalance(
            fromToken,
            address(this)
        );

        if (remainingAmount > 0) {
            Utils.transferTokens(fromToken, msg.sender, remainingAmount);
        }

        emit Bought(
            msg.sender,
            beneficiary,
            fromToken,
            toToken,
            fromAmount,
            receivedAmount,
            referrer
        );

        return receivedAmount;
    }

    //Helper function to transfer final amount to the beneficiaries
    function takeFeeAndTransferTokens(
        address toToken,
        uint256 expectedAmount,
        uint256 receivedAmount,
        address payable beneficiary,
        string memory referrer

    )
        private
    {
        uint256 remainingAmount = receivedAmount;

        address partnerContract = _partnerRegistry.getPartnerContract(referrer);

        //Take partner fee
        ( uint256 fee ) = _takeFee(
            toToken,
            receivedAmount,
            expectedAmount,
            partnerContract
        );
        remainingAmount = receivedAmount.sub(fee);

        //If there is a positive slippage after taking partner fee then 50% goes to paraswap and 50% to the user
        if ((remainingAmount > expectedAmount) && fee == 0) {
            uint256 positiveSlippageShare = remainingAmount.sub(expectedAmount).div(2);
            remainingAmount = remainingAmount.sub(positiveSlippageShare);
            Utils.transferTokens(toToken, _feeWallet, positiveSlippageShare);
        }

        Utils.transferTokens(toToken, beneficiary, remainingAmount);


    }

    /**
    * @dev Source take from GNOSIS MultiSigWallet
    * @dev https://github.com/gnosis/MultiSigWallet/blob/master/contracts/MultiSigWallet.sol
    */
    function externalCall(
        address destination,
        uint256 value,
        uint256 dataOffset,
        uint dataLength,
        bytes memory data
    )
    private
    returns (bool)
    {
        bool result = false;

        assembly {
            let x := mload(0x40)   // "Allocate" memory for output (0x40 is where "free memory" pointer is stored by convention)

            let d := add(data, 32) // First 32 bytes are the padded length of data, so exclude that
            result := call(
                sub(gas(), 34710), // 34710 is the value that solidity is currently emitting
                // It includes callGas (700) + callVeryLow (3, to pay for SUB) + callValueTransferGas (9000) +
                // callNewAccountGas (25000, in case the destination address does not exist and needs creating)
                destination,
                value,
                add(d, dataOffset),
                dataLength, // Size of the input (in bytes) - this is what fixes the padding problem
                x,
                0                  // Output is ignored, therefore the output size is zero
            )
        }
        return result;
    }

    //Helper function to perform swap
    function performSwap(
        address fromToken,
        uint256 fromAmount,
        Utils.Path[] memory path
    )
        private
    {

        require(path.length > 0, "Path not provided for swap");

        //Assuming path will not be too long to reach out of gas exception
        for (uint i = 0; i < path.length; i++) {
            //_fromToken will be either fromToken or toToken of the previous path
            address _fromToken = i > 0 ? path[i - 1].to : fromToken;
            address _toToken = path[i].to;

            uint256 _fromAmount = i > 0 ? Utils.tokenBalance(_fromToken, address(this)) : fromAmount;
            if (i > 0 && _fromToken == Utils.ethAddress()) {
                _fromAmount = _fromAmount.sub(path[i].totalNetworkFee);
            }

            for (uint j = 0; j < path[i].routes.length; j++) {
                Utils.Route memory route = path[i].routes[j];

                //Check if exchange is supported
                require(
                    _whitelisted.hasRole(_whitelisted.WHITELISTED_ROLE(), route.exchange),
                    "Exchange not whitelisted"
                );

                //Calculating tokens to be passed to the relevant exchange
                //percentage should be 200 for 2%
                uint fromAmountSlice = _fromAmount.mul(route.percent).div(10000);
                uint256 value = route.networkFee;

                if (i > 0 && j == path[i].routes.length.sub(1)) {
                    uint256 remBal = Utils.tokenBalance(address(_fromToken), address(this));

                    fromAmountSlice = remBal;

                    if (address(_fromToken) == Utils.ethAddress()) {
                        //subtract network fee
                        fromAmountSlice = fromAmountSlice.sub(value);
                    }
                }

                //DELEGATING CALL TO THE ADAPTER
                (bool success,) = route.exchange.delegatecall(
                    abi.encodeWithSelector(
                        IExchange.swap.selector,
                        _fromToken,
                        _toToken,
                        fromAmountSlice,
                        1,
                        route.targetExchange,
                        route.payload
                    )
                );

                require(success, "Call to adapter failed");
            }
        }
    }

    //Helper function to perform swap
    function performBuy(
        address fromToken,
        address toToken,
        uint256 fromAmount,
        uint256 toAmount,
        Utils.BuyRoute[] memory routes,
        bool useReduxToken
    )
        private
        returns(uint256)
    {
        uint initialGas = gasleft();

        //if fromToken is not ETH then transfer tokens from user to this contract
        if (fromToken != Utils.ethAddress()) {
            _tokenTransferProxy.transferFrom(
                fromToken,
                msg.sender,
                address(this),
                fromAmount
            );
        }

        for (uint j = 0; j < routes.length; j++) {
            Utils.BuyRoute memory route = routes[j];

            //Check if exchange is supported
            require(
                _whitelisted.hasRole(_whitelisted.WHITELISTED_ROLE(), route.exchange),
                "Exchange not whitelisted"
            );

            //delegate Call to the exchange
            (bool success,) = route.exchange.delegatecall(
                abi.encodeWithSelector(
                    IExchange.buy.selector,
                    fromToken,
                    toToken,
                    route.fromAmount,
                    route.toAmount,
                    route.targetExchange,
                    route.payload
                )
            );
            require(success, "Call to adapter failed");
        }

        uint256 receivedAmount = Utils.tokenBalance(
            toToken,
            address(this)
        );
        require(
            receivedAmount >= toAmount,
            "Received amount of tokens are less then expected tokens"
        );

        if (useReduxToken) {
            Utils.refundGas(msg.sender, address(_tokenTransferProxy), initialGas);
        }
        return receivedAmount;
    }

    function _takeFee(
        address toToken,
        uint256 receivedAmount,
        uint256 expectedAmount,
        address partnerContract
    )
        private
        returns(uint256 fee)
    {
        //If there is no partner associated with the referral id then no fee will be taken
        if (partnerContract == address(0)) {
            return (0);
        }

        (
            address payable partnerFeeWallet,
            uint256 feePercent,
            uint256 partnerSharePercent,
            ,
            bool positiveSlippageToUser,
            bool noPositiveSlippage
        ) = IPartner(partnerContract).getPartnerInfo();

        uint256 partnerShare = 0;
        uint256 paraswapShare = 0;

        if (!noPositiveSlippage && feePercent <= 50 && receivedAmount > expectedAmount) {
            uint256 halfPositiveSlippage = receivedAmount.sub(expectedAmount).div(2);
            //Calculate total fee to be taken
            fee = expectedAmount.mul(feePercent).div(10000);
            //Calculate partner's share
            partnerShare = fee.mul(partnerSharePercent).div(10000);
            //All remaining fee is paraswap's share
            paraswapShare = fee.sub(partnerShare);
            paraswapShare = paraswapShare.add(halfPositiveSlippage);

            fee = fee.add(halfPositiveSlippage);

            if (!positiveSlippageToUser) {
                partnerShare = partnerShare.add(halfPositiveSlippage);
                fee = fee.add(halfPositiveSlippage);
            }
        }
        else {
            //Calculate total fee to be taken
            fee = receivedAmount.mul(feePercent).div(10000);
            //Calculate partner's share
            partnerShare = fee.mul(partnerSharePercent).div(10000);
            //All remaining fee is paraswap's share
            paraswapShare = fee.sub(partnerShare);
        }
        Utils.transferTokens(toToken, partnerFeeWallet, partnerShare);
        Utils.transferTokens(toToken, _feeWallet, paraswapShare);

        emit FeeTaken(fee, partnerShare, paraswapShare);
        return (fee);
    }
}

Contract Security Audit

Contract ABI

[{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"adapter","type":"address"}],"name":"AdapterInitialized","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"initiator","type":"address"},{"indexed":true,"internalType":"address","name":"beneficiary","type":"address"},{"indexed":true,"internalType":"address","name":"srcToken","type":"address"},{"indexed":true,"internalType":"address","name":"destToken","type":"address"},{"indexed":false,"internalType":"uint256","name":"srcAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"receivedAmount","type":"uint256"},{"indexed":false,"internalType":"string","name":"referrer","type":"string"}],"name":"Bought","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"fee","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"partnerShare","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"paraswapShare","type":"uint256"}],"name":"FeeTaken","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":false,"internalType":"address","name":"initiator","type":"address"},{"indexed":true,"internalType":"address","name":"beneficiary","type":"address"},{"indexed":true,"internalType":"address","name":"srcToken","type":"address"},{"indexed":true,"internalType":"address","name":"destToken","type":"address"},{"indexed":false,"internalType":"uint256","name":"srcAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"receivedAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"expectedAmount","type":"uint256"},{"indexed":false,"internalType":"string","name":"referrer","type":"string"}],"name":"Swapped","type":"event"},{"inputs":[{"internalType":"address","name":"token","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"fromToken","type":"address"},{"internalType":"address","name":"toToken","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"address payable","name":"beneficiary","type":"address"},{"internalType":"string","name":"referrer","type":"string"},{"internalType":"bool","name":"useReduxToken","type":"bool"},{"components":[{"internalType":"address payable","name":"exchange","type":"address"},{"internalType":"address","name":"targetExchange","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"bytes","name":"payload","type":"bytes"},{"internalType":"uint256","name":"networkFee","type":"uint256"}],"internalType":"struct Utils.BuyRoute[]","name":"route","type":"tuple[]"}],"internalType":"struct Utils.BuyData","name":"data","type":"tuple"}],"name":"buy","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"amountInMax","type":"uint256"},{"internalType":"uint256","name":"amountOut","type":"uint256"},{"internalType":"address[]","name":"path","type":"address[]"},{"internalType":"uint8","name":"referrer","type":"uint8"}],"name":"buyOnUniswap","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"factory","type":"address"},{"internalType":"bytes32","name":"initCode","type":"bytes32"},{"internalType":"uint256","name":"amountInMax","type":"uint256"},{"internalType":"uint256","name":"amountOut","type":"uint256"},{"internalType":"address[]","name":"path","type":"address[]"},{"internalType":"uint8","name":"referrer","type":"uint8"}],"name":"buyOnUniswapFork","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"uniswapProxy","type":"address"}],"name":"changeUniswapProxy","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"confirmUniswapProxyChange","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"getChangeRequestedBlock","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"key","type":"bytes32"}],"name":"getData","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getFeeWallet","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getPartnerRegistry","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getPendingUniswapProxy","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getTimeLock","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getTokenTransferProxy","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getUniswapProxy","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getVersion","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getWhitelistAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"whitelist","type":"address"},{"internalType":"address","name":"reduxToken","type":"address"},{"internalType":"address","name":"partnerRegistry","type":"address"},{"internalType":"address payable","name":"feeWallet","type":"address"},{"internalType":"address","name":"uniswapProxy","type":"address"},{"internalType":"uint256","name":"timelock","type":"uint256"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"adapter","type":"address"},{"internalType":"bytes","name":"data","type":"bytes"}],"name":"initializeAdapter","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"key","type":"bytes32"}],"name":"isInitialized","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"fromToken","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"uint256","name":"expectedAmount","type":"uint256"},{"internalType":"address payable","name":"beneficiary","type":"address"},{"internalType":"string","name":"referrer","type":"string"},{"internalType":"bool","name":"useReduxToken","type":"bool"},{"components":[{"internalType":"uint256","name":"fromAmountPercent","type":"uint256"},{"components":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"totalNetworkFee","type":"uint256"},{"components":[{"internalType":"address payable","name":"exchange","type":"address"},{"internalType":"address","name":"targetExchange","type":"address"},{"internalType":"uint256","name":"percent","type":"uint256"},{"internalType":"bytes","name":"payload","type":"bytes"},{"internalType":"uint256","name":"networkFee","type":"uint256"}],"internalType":"struct Utils.Route[]","name":"routes","type":"tuple[]"}],"internalType":"struct Utils.Path[]","name":"path","type":"tuple[]"}],"internalType":"struct Utils.MegaSwapPath[]","name":"path","type":"tuple[]"}],"internalType":"struct Utils.MegaSwapSellData","name":"data","type":"tuple"}],"name":"megaSwap","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[{"components":[{"internalType":"address","name":"fromToken","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"uint256","name":"expectedAmount","type":"uint256"},{"internalType":"address payable","name":"beneficiary","type":"address"},{"internalType":"string","name":"referrer","type":"string"},{"internalType":"bool","name":"useReduxToken","type":"bool"},{"components":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"totalNetworkFee","type":"uint256"},{"components":[{"internalType":"address payable","name":"exchange","type":"address"},{"internalType":"address","name":"targetExchange","type":"address"},{"internalType":"uint256","name":"percent","type":"uint256"},{"internalType":"bytes","name":"payload","type":"bytes"},{"internalType":"uint256","name":"networkFee","type":"uint256"}],"internalType":"struct Utils.Route[]","name":"routes","type":"tuple[]"}],"internalType":"struct Utils.Path[]","name":"path","type":"tuple[]"}],"internalType":"struct Utils.SellData","name":"data","type":"tuple"}],"name":"multiSwap","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address payable","name":"feeWallet","type":"address"}],"name":"setFeeWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"partnerRegistry","type":"address"}],"name":"setPartnerRegistry","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"whitelisted","type":"address"}],"name":"setWhitelistAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"fromToken","type":"address"},{"internalType":"address","name":"toToken","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"address[]","name":"callees","type":"address[]"},{"internalType":"bytes","name":"exchangeData","type":"bytes"},{"internalType":"uint256[]","name":"startIndexes","type":"uint256[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"},{"internalType":"address payable","name":"beneficiary","type":"address"},{"internalType":"string","name":"referrer","type":"string"},{"internalType":"bool","name":"useReduxToken","type":"bool"}],"name":"simplBuy","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"fromToken","type":"address"},{"internalType":"address","name":"toToken","type":"address"},{"internalType":"uint256","name":"fromAmount","type":"uint256"},{"internalType":"uint256","name":"toAmount","type":"uint256"},{"internalType":"uint256","name":"expectedAmount","type":"uint256"},{"internalType":"address[]","name":"callees","type":"address[]"},{"internalType":"bytes","name":"exchangeData","type":"bytes"},{"internalType":"uint256[]","name":"startIndexes","type":"uint256[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"},{"internalType":"address payable","name":"beneficiary","type":"address"},{"internalType":"string","name":"referrer","type":"string"},{"internalType":"bool","name":"useReduxToken","type":"bool"}],"name":"simpleSwap","outputs":[{"internalType":"uint256","name":"receivedAmount","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"amountIn","type":"uint256"},{"internalType":"uint256","name":"amountOutMin","type":"uint256"},{"internalType":"address[]","name":"path","type":"address[]"},{"internalType":"uint8","name":"referrer","type":"uint8"}],"name":"swapOnUniswap","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"factory","type":"address"},{"internalType":"bytes32","name":"initCode","type":"bytes32"},{"internalType":"uint256","name":"amountIn","type":"uint256"},{"internalType":"uint256","name":"amountOutMin","type":"uint256"},{"internalType":"address[]","name":"path","type":"address[]"},{"internalType":"uint8","name":"referrer","type":"uint8"}],"name":"swapOnUniswapFork","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"token","type":"address"},{"internalType":"address payable","name":"destination","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transferTokens","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"contract IWETH","name":"token","type":"address"}],"name":"withdrawAllWETH","outputs":[],"stateMutability":"nonpayable","type":"function"},{"stateMutability":"payable","type":"receive"}]

608060405234801561001057600080fd5b506158c7806100206000396000f3fe608060405260043610620002355760003560e01c806395b6ef0c1162000139578063d2c4b59811620000c1578063ec1d21dd116200008b578063f7b637bb116200006d578063f7b637bb14620005d2578063f9355f721462000606578063f95a49eb146200061d576200023d565b8063ec1d21dd1462000596578063f2fde38b14620005ad576200023d565b8063d2c4b598146200050f578063db21e48d1462000527578063e1829cfe146200054c578063e1f21c671462000571576200023d565b8063a64b6e5f1162000103578063a64b6e5f14620004a3578063a745d5bd14620004c8578063b69bd7aa14620004e0578063cfc0afeb14620004f8576200023d565b806395b6ef0c146200042a578063a224c745146200044f578063a27e8b6b1462000474578063a4a6c336146200048b576200023d565b806354f6127f11620001bd5780638da5cb5b11620001875780638da5cb5b14620003be5780638f00eccb14620003d657806390d49b9d14620003ed578063915eb9731462000412576200023d565b806354f6127f146200034557806358b9d179146200036a578063715018a614620003815780638c3e9f461462000399576200023d565b80631880021911620001ff5780631880021914620002d95780632af3feb014620002fe5780633363522614620003165780635459060d146200032d576200023d565b80630863b7ac146200024257806308defdee146200025b5780630d8e6e2c146200028b578063119a5e9614620002b2576200023d565b366200023d57005b600080fd5b620002596200025336600462003d68565b62000634565b005b3480156200026857600080fd5b506200027362000770565b60405162000282919062004298565b60405180910390f35b3480156200029857600080fd5b50620002a36200077f565b60405162000282919062004488565b348015620002bf57600080fd5b50620002ca620007b6565b60405162000282919062004b98565b348015620002e657600080fd5b5062000259620002f836600462003df2565b620007bc565b3480156200030b57600080fd5b506200027362000a53565b620002596200032736600462003d68565b62000a62565b3480156200033a57600080fd5b506200027362000ab6565b3480156200035257600080fd5b50620002a36200036436600462003e98565b62000ac5565b620002596200037b36600462004191565b62000b88565b3480156200038e57600080fd5b506200025962000cb5565b348015620003a657600080fd5b5062000259620003b836600462003942565b62000d44565b348015620003cb57600080fd5b506200027362000dd4565b620002ca620003e7366004620040ac565b62000de3565b348015620003fa57600080fd5b50620002596200040c36600462003942565b6200104e565b3480156200041f57600080fd5b5062000273620010de565b3480156200043757600080fd5b50620002596200044936600462003a35565b620010ed565b3480156200045c57600080fd5b50620002596200046e36600462003942565b62001207565b620002596200048536600462003ab8565b62001297565b3480156200049857600080fd5b50620002596200135c565b348015620004b057600080fd5b5062000259620004c2366004620039f0565b6200142b565b348015620004d557600080fd5b50620002ca6200146a565b348015620004ed57600080fd5b506200027362001470565b620002ca6200050936600462003bfc565b6200147f565b3480156200051c57600080fd5b50620002736200150b565b3480156200053457600080fd5b50620002596200054636600462003942565b6200151a565b3480156200055957600080fd5b50620002596200056b36600462003942565b620015ae565b3480156200057e57600080fd5b506200025962000590366004620039f0565b620016f0565b620002ca620005a736600462003fc7565b6200171f565b348015620005ba57600080fd5b5062000259620005cc36600462003942565b62001976565b348015620005df57600080fd5b50620005f7620005f136600462003e98565b62001a40565b60405162000282919062004437565b620002596200061736600462004191565b62001a55565b620002ca6200062e36600462003eca565b62001aa5565b6007546040516000916060916001600160a01b03909116907ff5661034000000000000000000000000000000000000000000000000000000009062000688908c908c908c908c908c908c90602401620043e7565b60408051601f198184030181529181526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff00000000000000000000000000000000000000000000000000000000909416939093179092529051620006f5919062004277565b600060405180830381855af49150503d806000811462000732576040519150601f19603f3d011682016040523d82523d6000602084013e62000737565b606091505b509150915081620007655760405162461bcd60e51b81526004016200075c9062004792565b60405180910390fd5b505050505050505050565b6007546001600160a01b031690565b60408051808201909152600581527f342e302e30000000000000000000000000000000000000000000000000000000602082015290565b600a5490565b6003546001600160a01b03163314620007e95760405162461bcd60e51b81526004016200075c9062004970565b60048054604080517f7a3226ec00000000000000000000000000000000000000000000000000000000815290516001600160a01b03909216926391d14854928492637a3226ec9281810192602092909190829003018186803b1580156200084f57600080fd5b505afa15801562000864573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200088a919062003eb1565b856040518363ffffffff1660e01b8152600401620008aa92919062004442565b60206040518083038186803b158015620008c357600080fd5b505afa158015620008d8573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620008fe919062003e79565b6200091d5760405162461bcd60e51b81526004016200075c9062004837565b6000836001600160a01b031663439fab9160e01b84846040516024016200094692919062004459565b60408051601f198184030181529181526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff00000000000000000000000000000000000000000000000000000000909416939093179092529051620009b3919062004277565b600060405180830381855af49150503d8060008114620009f0576040519150601f19603f3d011682016040523d82523d6000602084013e620009f5565b606091505b505090508062000a195760405162461bcd60e51b81526004016200075c90620046ed565b6040516001600160a01b038516907f4aa65286df310c4e8390d962c75f50380b8260d96ea27cf14847cd683e22d9db90600090a250505050565b6008546001600160a01b031690565b6007546040516000916060916001600160a01b03909116907fc03786b0000000000000000000000000000000000000000000000000000000009062000688908c908c908c908c908c908c90602401620043e7565b6006546001600160a01b031690565b60008181526001602081815260409283902080548451600294821615610100027fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0190911693909304601f8101839004830284018301909452838352606093909183018282801562000b7b5780601f1062000b4f5761010080835404028352916020019162000b7b565b820191906000526020600020905b81548152906001019060200180831162000b5d57829003601f168201915b505050505090505b919050565b6007546040516000916060916001600160a01b03909116907f54840d1a000000000000000000000000000000000000000000000000000000009062000bd8908a908a908a908a9060240162004ba1565b60408051601f198184030181529181526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff0000000000000000000000000000000000000000000000000000000090941693909317909252905162000c45919062004277565b600060405180830381855af49150503d806000811462000c82576040519150601f19603f3d011682016040523d82523d6000602084013e62000c87565b606091505b50915091508162000cac5760405162461bcd60e51b81526004016200075c9062004792565b50505050505050565b6003546001600160a01b0316331462000ce25760405162461bcd60e51b81526004016200075c9062004970565b6003546040516000916001600160a01b0316907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908390a3600380547fffffffffffffffffffffffff0000000000000000000000000000000000000000169055565b6003546001600160a01b0316331462000d715760405162461bcd60e51b81526004016200075c9062004970565b6001600160a01b03811662000d9a5760405162461bcd60e51b81526004016200075c90620044d4565b600580547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091179055565b6003546001600160a01b031690565b6000805a835160208501516040860151606087015160808801519495509293919290916000906001600160a01b03161562000e2357876080015162000e25565b335b60a089015160e08a01518051929350909160009082907fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff810190811062000e6857fe5b602002602001015160000151905060008b60c001519050600084511162000ea35760405162461bcd60e51b81526004016200075c9062004724565b6000871162000ec65760405162461bcd60e51b81526004016200075c9062004b61565b62000ed062001bee565b6001600160a01b0316896001600160a01b03161462000f6f576002546040517f15dacbea0000000000000000000000000000000000000000000000000000000081526001600160a01b03909116906315dacbea9062000f3a908c90339030908e9060040162004336565b600060405180830381600087803b15801562000f5557600080fd5b505af115801562000f6a573d6000803e3d6000fd5b505050505b62000f7c89898562001c06565b600062000f8a8330620020bd565b90508781101562000faf5760405162461bcd60e51b81526004016200075c9062004a13565b62000fbe83888389896200219b565b811562000fdf5760025462000fdf9033906001600160a01b03168d620022cd565b826001600160a01b03168a6001600160a01b0316876001600160a01b03167f9cc2048b8af5eadff75759a3169b369efc538fb79c760fd396a4b355410b41b7338d868d8c60405162001036959493929190620042e6565b60405180910390a49c9b505050505050505050505050565b6003546001600160a01b031633146200107b5760405162461bcd60e51b81526004016200075c9062004970565b6001600160a01b038116620010a45760405162461bcd60e51b81526004016200075c90620044d4565b600680547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091179055565b6004546001600160a01b031690565b6002546001600160a01b031615620011195760405162461bcd60e51b81526004016200075c9062004800565b600580547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b03861617905560405160009086906200115f906200331f565b6200116b919062004298565b604051809103906000f08015801562001188573d6000803e3d6000fd5b50600280547fffffffffffffffffffffffff00000000000000000000000000000000000000009081166001600160a01b0393841617909155600480548216998316999099179098556006805489169582169590951790945550600780548716929093169190911790915560038054339516949094179093555050600a55565b6003546001600160a01b03163314620012345760405162461bcd60e51b81526004016200075c9062004970565b6001600160a01b0381166200125d5760405162461bcd60e51b81526004016200075c90620045fc565b600480547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091179055565b6001600160a01b03831615620012ae5782620012b0565b335b92506000620012ca8c8c8c8c8d8d8d8d8d8d8d8d6200231d565b90506000620012da8d30620020bd565b90508015620012f057620012f08d338362002501565b8b6001600160a01b03168d6001600160a01b0316866001600160a01b03167ff0be17aaae5a3633105aafe0689d8beb04dc66d5c51babf7086efebbb4e7ba82338f878a604051620013459493929190620042ac565b60405180910390a450505050505050505050505050565b6003546001600160a01b03163314620013895760405162461bcd60e51b81526004016200075c9062004970565b600a546009546200139a91620025d3565b431015620013bc5760405162461bcd60e51b81526004016200075c90620047c9565b6008546001600160a01b0316620013e75760405162461bcd60e51b81526004016200075c906200486e565b600060095560088054600780547fffffffffffffffffffffffff00000000000000000000000000000000000000009081166001600160a01b03841617909155169055565b6003546001600160a01b03163314620014585760405162461bcd60e51b81526004016200075c9062004970565b6200146583838362002501565b505050565b60095490565b6005546001600160a01b031690565b60006001600160a01b038416156200149857836200149a565b335b9350620014b28d8d8d8d8d8d8d8d8d8d8d8d6200231d565b90508b6001600160a01b03168d6001600160a01b0316856001600160a01b03167f9cc2048b8af5eadff75759a3169b369efc538fb79c760fd396a4b355410b41b7338f868f8a60405162001036959493929190620042e6565b6002546001600160a01b031690565b6003546001600160a01b03163314620015475760405162461bcd60e51b81526004016200075c9062004970565b6001600160a01b038116620015705760405162461bcd60e51b81526004016200075c90620044d4565b43600955600880547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091179055565b333014620015d05760405162461bcd60e51b81526004016200075c90620049a5565b6040517f70a082310000000000000000000000000000000000000000000000000000000081526000906001600160a01b038316906370a08231906200161a90309060040162004298565b60206040518083038186803b1580156200163357600080fd5b505afa15801562001648573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200166e919062003eb1565b6040517f2e1a7d4d0000000000000000000000000000000000000000000000000000000081529091506001600160a01b03831690632e1a7d4d90620016b890849060040162004b98565b600060405180830381600087803b158015620016d357600080fd5b505af1158015620016e8573d6000803e3d6000fd5b505050505050565b333014620017125760405162461bcd60e51b81526004016200075c90620049a5565b62001465828483620025fb565b6000805a835160208501516040860151606087015160808801519495509293919290916000906001600160a01b0316156200175f57876080015162001761565b335b905060608860a00151905060608960e0015190506000816000815181106200178557fe5b602002602001015160200151600183600081518110620017a157fe5b602002602001015160200151510381518110620017ba57fe5b602002602001015160000151905060008b60c0015190506000845111620017f55760405162461bcd60e51b81526004016200075c9062004724565b60008711620018185760405162461bcd60e51b81526004016200075c9062004b61565b6200182262001bee565b6001600160a01b0316896001600160a01b031614620018c1576002546040517f15dacbea0000000000000000000000000000000000000000000000000000000081526001600160a01b03909116906315dacbea906200188c908c90339030908e9060040162004336565b600060405180830381600087803b158015620018a757600080fd5b505af1158015620018bc573d6000803e3d6000fd5b505050505b60005b835160ff168160ff16101562001967576000620019146127106200190d878560ff1681518110620018f157fe5b6020026020010151600001518d6200272190919063ffffffff16565b9062002761565b905060018551038260ff1614156200193557620019328b30620020bd565b90505b6200195d8b82878560ff16815181106200194b57fe5b60200260200101516020015162001c06565b50600101620018c4565b50600062000f8a8330620020bd565b6003546001600160a01b03163314620019a35760405162461bcd60e51b81526004016200075c9062004970565b6001600160a01b038116620019cc5760405162461bcd60e51b81526004016200075c9062004568565b6003546040516001600160a01b038084169216907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a3600380547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091179055565b60009081526020819052604090205460ff1690565b6007546040516000916060916001600160a01b03909116907f935fb84b000000000000000000000000000000000000000000000000000000009062000bd8908a908a908a908a9060240162004ba1565b805160408201516060830151608084015160009392919084906001600160a01b03161562001ad857856080015162001ada565b335b60a087015160e0880151602089015160c08a0151835194955092939192909162001b185760405162461bcd60e51b81526004016200075c9062004724565b6000861162001b3b5760405162461bcd60e51b81526004016200075c9062004b61565b600062001b4d89848a8a8887620027a5565b905062001b5e83888389896200219b565b600062001b6c8a30620020bd565b9050801562001b825762001b828a338362002501565b836001600160a01b03168a6001600160a01b0316886001600160a01b03167ff0be17aaae5a3633105aafe0689d8beb04dc66d5c51babf7086efebbb4e7ba82338d878c60405162001bd79493929190620042ac565b60405180910390a4509a9950505050505050505050565b73eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee90565b600081511162001c2a5760405162461bcd60e51b81526004016200075c906200475b565b60005b8151811015620020b757600080821162001c48578462001c65565b82600183038151811062001c5857fe5b6020026020010151600001515b9050600083838151811062001c7657fe5b6020026020010151600001519050600080841162001c95578562001ca1565b62001ca18330620020bd565b905060008411801562001cce575062001cb962001bee565b6001600160a01b0316836001600160a01b0316145b1562001d045762001d0185858151811062001ce557fe5b6020026020010151602001518262002b5a90919063ffffffff16565b90505b60005b85858151811062001d1457fe5b60200260200101516040015151811015620020a65762001d336200332d565b86868151811062001d4057fe5b602002602001015160400151828151811062001d5857fe5b60209081029190910181015160048054604080517f7a3226ec00000000000000000000000000000000000000000000000000000000815290519395506001600160a01b03909116936391d14854938593637a3226ec9380820193929190829003018186803b15801562001dca57600080fd5b505afa15801562001ddf573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001e05919062003eb1565b83516040517fffffffff0000000000000000000000000000000000000000000000000000000060e085901b16815262001e4392919060040162004442565b60206040518083038186803b15801562001e5c57600080fd5b505afa15801562001e71573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001e97919062003e79565b62001eb65760405162461bcd60e51b81526004016200075c9062004837565b600062001ed86127106200190d8460400151876200272190919063ffffffff16565b6080830151909150871580159062001f1d575062001f1a60018a8a8151811062001efe57fe5b6020026020010151604001515162002b5a90919063ffffffff16565b84145b1562001f6b57600062001f318830620020bd565b905080925062001f4062001bee565b6001600160a01b0316886001600160a01b0316141562001f695762001f66838362002b5a565b92505b505b8251602084015160608501516040516000936001600160a01b0316927fb69cbf9f000000000000000000000000000000000000000000000000000000009262001fc2928d928d928a92600192919060240162004360565b60408051601f198184030181529181526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff000000000000000000000000000000000000000000000000000000009094169390931790925290516200202f919062004277565b600060405180830381855af49150503d80600081146200206c576040519150601f19603f3d011682016040523d82523d6000602084013e62002071565b606091505b5050905080620020955760405162461bcd60e51b81526004016200075c9062004939565b50506001909201915062001d079050565b50506001909201915062001c2d9050565b50505050565b60006001600160a01b03831673eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee1415620020f757506001600160a01b0381163162002195565b6040517f70a082310000000000000000000000000000000000000000000000000000000081526001600160a01b038416906370a08231906200213e90859060040162004298565b60206040518083038186803b1580156200215757600080fd5b505afa1580156200216c573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062002192919062003eb1565b90505b92915050565b6005546040517fa38aa34600000000000000000000000000000000000000000000000000000000815284916000916001600160a01b039091169063a38aa34690620021eb90869060040162004488565b60206040518083038186803b1580156200220457600080fd5b505afa15801562002219573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200223f919062003961565b90506000620022518887898562002b9e565b90506200225f868262002b5a565b925086831180156200226f575080155b15620022b65760006200228960026200190d868b62002b5a565b905062002297848262002b5a565b600654909450620022b4908a906001600160a01b03168362002501565b505b620022c388868562002501565b5050505050505050565b61374a611ad6615dc060006200230e620022f584620022ee85600262002721565b9062002b5a565b6200190d86620023075a8a9062002b5a565b90620025d3565b905062000cac87878362002da6565b6000808a11620023415760405162461bcd60e51b81526004016200075c9062004902565b8551885160010114620023685760405162461bcd60e51b81526004016200075c906200450b565b60005a9050620023798e8d62002e61565b60005b89518110156200248e576002548a516001600160a01b03909116908b9083908110620023a457fe5b60200260200101516001600160a01b03161415620023d65760405162461bcd60e51b81526004016200075c9062004633565b6000620024628b8381518110620023e957fe5b6020026020010151898481518110620023fe57fe5b60200260200101518b85815181106200241357fe5b60200260200101516200245b8d87815181106200242c57fe5b60200260200101518e88600101815181106200244457fe5b602002602001015162002b5a90919063ffffffff16565b8e62002ed9565b905080620024845760405162461bcd60e51b81526004016200075c90620049dc565b506001016200237c565b506200249b8d30620020bd565b91508a821015620024c05760405162461bcd60e51b81526004016200075c9062004a13565b620024cf8d8b8488886200219b565b8215620024f057600254620024f09033906001600160a01b031683620022cd565b509c9b505050505050505050505050565b801562001465576001600160a01b03831673eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee1415620025bd576000826001600160a01b031682610fa0906040516200254d9062004295565b600060405180830381858888f193505050503d80600081146200258d576040519150601f19603f3d011682016040523d82523d6000602084013e62002592565b606091505b5050905080620025b65760405162461bcd60e51b81526004016200075c906200449d565b5062001465565b620014656001600160a01b038416838362002f03565b600082820183811015620021925760405162461bcd60e51b81526004016200075c90620045c5565b6001600160a01b03821673eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee1462001465576040517fdd62ed3e00000000000000000000000000000000000000000000000000000000815282906000906001600160a01b0383169063dd62ed3e906200266e90309089906004016200431c565b60206040518083038186803b1580156200268757600080fd5b505afa1580156200269c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620026c2919062003eb1565b9050828110156200271a57620026e46001600160a01b03831686600062002f8a565b6200271a6001600160a01b038316867fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff62003073565b5050505050565b600082620027325750600062002195565b828202828482816200274057fe5b0414620021925760405162461bcd60e51b81526004016200075c90620048a5565b60006200219283836040518060400160405280601a81526020017f536166654d6174683a206469766973696f6e206279207a65726f00000000000081525062003122565b6000805a9050620027b562001bee565b6001600160a01b0316886001600160a01b03161462002854576002546040517f15dacbea0000000000000000000000000000000000000000000000000000000081526001600160a01b03909116906315dacbea906200281f908b90339030908c9060040162004336565b600060405180830381600087803b1580156200283a57600080fd5b505af11580156200284f573d6000803e3d6000fd5b505050505b60005b845181101562002af9576200286b6200336e565b8582815181106200287857fe5b60209081029190910181015160048054604080517f7a3226ec00000000000000000000000000000000000000000000000000000000815290519395506001600160a01b03909116936391d14854938593637a3226ec9380820193929190829003018186803b158015620028ea57600080fd5b505afa158015620028ff573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062002925919062003eb1565b83516040517fffffffff0000000000000000000000000000000000000000000000000000000060e085901b1681526200296392919060040162004442565b60206040518083038186803b1580156200297c57600080fd5b505afa15801562002991573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620029b7919062003e79565b620029d65760405162461bcd60e51b81526004016200075c9062004837565b600081600001516001600160a01b0316635f0a186260e01b8c8c856040015186606001518760200151886080015160405160240162002a1b96959493929190620043a5565b60408051601f198184030181529181526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff0000000000000000000000000000000000000000000000000000000090941693909317909252905162002a88919062004277565b600060405180830381855af49150503d806000811462002ac5576040519150601f19603f3d011682016040523d82523d6000602084013e62002aca565b606091505b505090508062002aee5760405162461bcd60e51b81526004016200075c9062004939565b505060010162002857565b50600062002b088830620020bd565b90508581101562002b2d5760405162461bcd60e51b81526004016200075c9062004690565b831562002b4e5760025462002b4e9033906001600160a01b031684620022cd565b98975050505050505050565b60006200219283836040518060400160405280601e81526020017f536166654d6174683a207375627472616374696f6e206f766572666c6f7700008152506200315f565b60006001600160a01b03821662002bb85750600062002d9e565b6000806000806000866001600160a01b0316630c51ff046040518163ffffffff1660e01b815260040160c06040518083038186803b15801562002bfa57600080fd5b505afa15801562002c0f573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062002c35919062003980565b95509550509450945094506000808215801562002c53575060328611155b801562002c5f5750898b115b1562002cf957600062002c7960026200190d8e8e62002b5a565b905062002c8e6127106200190d8d8a62002721565b985062002ca36127106200190d8b8962002721565b925062002cb1898462002b5a565b915062002cbf8282620025d3565b915062002ccd8982620025d3565b98508462002cf25762002ce18382620025d3565b925062002cef8982620025d3565b98505b5062002d32565b62002d0c6127106200190d8d8962002721565b975062002d216127106200190d8a8862002721565b915062002d2f888362002b5a565b90505b62002d3f8c888462002501565b60065462002d59908d906001600160a01b03168362002501565b7fb9f46e095476339db7821812d7e8ca40dad9d9b08ba10b54eb67faacc2aa558288838360405162002d8e9392919062004bc3565b60405180910390a1505050505050505b949350505050565b806000805a9050616c3e811062002dcf5762002dcc611b6c6200190d83616c3e62002b5a565b91505b8183111562002ddc578192505b6040517fdd1fe62c0000000000000000000000000000000000000000000000000000000081526001600160a01b0386169063dd1fe62c9062002e2590899087906004016200441e565b600060405180830381600087803b15801562002e4057600080fd5b505af115801562002e55573d6000803e3d6000fd5b50505050505050505050565b62002e6b62001bee565b6001600160a01b0316826001600160a01b03161462002ed5576002546040517f15dacbea0000000000000000000000000000000000000000000000000000000081526001600160a01b03909116906315dacbea90620016b890859033903090879060040162004336565b5050565b6000806000905060405160208401600082878984018b8d6187965a03f19998505050505050505050565b620014658363a9059cbb60e01b848460405160240162002f259291906200441e565b60408051601f198184030181529190526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff00000000000000000000000000000000000000000000000000000000909316929092179091526200318e565b8015806200303257506040517fdd62ed3e0000000000000000000000000000000000000000000000000000000081526001600160a01b0384169063dd62ed3e9062002fdc90309086906004016200431c565b60206040518083038186803b15801562002ff557600080fd5b505afa1580156200300a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062003030919062003eb1565b155b620030515760405162461bcd60e51b81526004016200075c9062004b04565b620014658363095ea7b360e01b848460405160240162002f259291906200441e565b6000620030fe82856001600160a01b031663dd62ed3e30876040518363ffffffff1660e01b8152600401620030aa9291906200431c565b60206040518083038186803b158015620030c357600080fd5b505afa158015620030d8573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062002307919062003eb1565b9050620020b78463095ea7b360e01b858460405160240162002f259291906200441e565b60008183620031465760405162461bcd60e51b81526004016200075c919062004488565b5060008385816200315357fe5b049150505b9392505050565b60008184841115620031865760405162461bcd60e51b81526004016200075c919062004488565b505050900390565b6060620031e5826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316620032259092919063ffffffff16565b80519091501562001465578080602001905181019062003206919062003e79565b620014655760405162461bcd60e51b81526004016200075c9062004aa7565b606062002d9e8484600085856200323c85620032db565b6200325b5760405162461bcd60e51b81526004016200075c9062004a70565b60006060866001600160a01b031685876040516200327a919062004277565b60006040518083038185875af1925050503d8060008114620032b9576040519150601f19603f3d011682016040523d82523d6000602084013e620032be565b606091505b5091509150620032d0828286620032e1565b979650505050505050565b3b151590565b60608315620032f257508162003158565b825115620033035782518084602001fd5b8160405162461bcd60e51b81526004016200075c919062004488565b610c1d8062004c7583390190565b6040518060a0016040528060006001600160a01b0316815260200160006001600160a01b031681526020016000815260200160608152602001600081525090565b6040518060c0016040528060006001600160a01b0316815260200160006001600160a01b03168152602001600081526020016000815260200160608152602001600081525090565b803562000b838162004c4c565b60008083601f840112620033d5578182fd5b50813567ffffffffffffffff811115620033ed578182fd5b60208301915083602080830285010111156200340857600080fd5b9250929050565b600082601f83011262003420578081fd5b813562003437620034318262004bfe565b62004bd9565b8181529150602080830190848101818402860182018710156200345957600080fd5b60005b8481101562003485578135620034728162004c4c565b845292820192908201906001016200345c565b505050505092915050565b600082601f830112620034a1578081fd5b8135620034b2620034318262004bfe565b818152915060208083019084810160005b8481101562003485578135870160c080601f19838c03011215620034e657600080fd5b6040805182810167ffffffffffffffff82821081831117156200350557fe5b81845262003515898701620033b6565b835262003524848701620033b6565b8984015260609150818601358484015260809350838601358284015260a0915081860135818111156200355657600080fd5b620035668f8b838a0101620038c4565b94840194909452509390920135928201929092528552509282019290820190600101620034c3565b600082601f8301126200359f578081fd5b8135620035b0620034318262004bfe565b818152915060208083019084810160005b84811015620034855781358701604080601f19838c03011215620035e457600080fd5b805181810167ffffffffffffffff82821081831117156200360157fe5b8184528488013583529284013592808411156200361d57600080fd5b50506200362f8b878486010162003648565b81870152865250509282019290820190600101620035c1565b600082601f83011262003659578081fd5b6200366962003431833562004bfe565b823581529050602080820190830160005b84358110156200384957813585016060601f198289030112156200369d57600080fd5b60405180606082011067ffffffffffffffff60608301111715620036bd57fe5b60608101604052620036d3602083013562004c4c565b602082013581526040820135602082015267ffffffffffffffff60608301351115620036fe57600080fd5b60608201358201915087603f8301126200371757600080fd5b6200372a62003431602084013562004bfe565b60208381013582528101906040840160005b60208601358110156200382a578135860160a07fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc0828f030112156200378057600080fd5b6040518060a082011067ffffffffffffffff60a08301111715620037a057fe5b60a08101604052620037b560408301620033b6565b8152620037c560608301620033b6565b60208201526080820135604082015267ffffffffffffffff60a08301351115620037ee57600080fd5b620038038e604060a0850135850101620038c4565b606082015260c091909101356080820152845260209384019391909101906001016200373c565b505060408301525084525060209283019291909101906001016200367a565b50505092915050565b600082601f83011262003863578081fd5b813562003874620034318262004bfe565b8181529150602080830190848101818402860182018710156200389657600080fd5b60005b84811015620034855781358452928201929082019060010162003899565b803562000b838162004c65565b600082601f830112620038d5578081fd5b813567ffffffffffffffff811115620038ea57fe5b620038ff6020601f19601f8401160162004bd9565b91508082528360208285010111156200391757600080fd5b8060208401602084013760009082016020015292915050565b803560ff8116811462000b8357600080fd5b60006020828403121562003954578081fd5b8135620021928162004c4c565b60006020828403121562003973578081fd5b8151620021928162004c4c565b60008060008060008060c0878903121562003999578182fd5b8651620039a68162004c4c565b809650506020870151945060408701519350606087015192506080870151620039cf8162004c65565b60a0880151909250620039e28162004c65565b809150509295509295509295565b60008060006060848603121562003a05578081fd5b833562003a128162004c4c565b9250602084013562003a248162004c4c565b929592945050506040919091013590565b60008060008060008060c0878903121562003a4e578384fd5b863562003a5b8162004c4c565b9550602087013562003a6d8162004c4c565b9450604087013562003a7f8162004c4c565b9350606087013562003a918162004c4c565b9250608087013562003aa38162004c4c565b8092505060a087013590509295509295509295565b60008060008060008060008060008060006101608c8e03121562003ada578889fd5b62003ae58c620033b6565b9a5062003af560208d01620033b6565b995060408c0135985060608c0135975067ffffffffffffffff8060808e0135111562003b1f578586fd5b62003b318e60808f01358f016200340f565b97508060a08e0135111562003b44578586fd5b62003b568e60a08f01358f01620038c4565b96508060c08e0135111562003b69578586fd5b62003b7b8e60c08f01358f0162003852565b95508060e08e0135111562003b8e578485fd5b62003ba08e60e08f01358f0162003852565b945062003bb16101008e01620033b6565b9350806101208e0135111562003bc5578283fd5b5062003bd98d6101208e01358e01620038c4565b915062003bea6101408d01620038b7565b90509295989b509295989b9093969950565b6000806000806000806000806000806000806101808d8f03121562003c1f578586fd5b62003c2a8d620033b6565b9b5062003c3a60208e01620033b6565b9a5060408d0135995060608d0135985060808d0135975067ffffffffffffffff60a08e0135111562003c6a578586fd5b62003c7c8e60a08f01358f016200340f565b965067ffffffffffffffff60c08e0135111562003c97578586fd5b62003ca98e60c08f01358f01620038c4565b955067ffffffffffffffff60e08e0135111562003cc4578081fd5b62003cd68e60e08f01358f0162003852565b945067ffffffffffffffff6101008e0135111562003cf2578081fd5b62003d058e6101008f01358f0162003852565b935062003d166101208e01620033b6565b925067ffffffffffffffff6101408e0135111562003d32578081fd5b62003d458e6101408f01358f01620038c4565b915062003d566101608e01620038b7565b90509295989b509295989b509295989b565b600080600080600080600060c0888a03121562003d83578081fd5b873562003d908162004c4c565b9650602088013595506040880135945060608801359350608088013567ffffffffffffffff81111562003dc1578182fd5b62003dcf8a828b01620033c3565b909450925062003de4905060a0890162003930565b905092959891949750929550565b60008060006040848603121562003e07578081fd5b833562003e148162004c4c565b9250602084013567ffffffffffffffff8082111562003e31578283fd5b818601915086601f83011262003e45578283fd5b81358181111562003e54578384fd5b87602082850101111562003e66578384fd5b6020830194508093505050509250925092565b60006020828403121562003e8b578081fd5b8151620021928162004c65565b60006020828403121562003eaa578081fd5b5035919050565b60006020828403121562003ec3578081fd5b5051919050565b60006020828403121562003edc578081fd5b813567ffffffffffffffff8082111562003ef4578283fd5b818401915061010080838703121562003f0b578384fd5b62003f168162004bd9565b905062003f2383620033b6565b815262003f3360208401620033b6565b6020820152604083013560408201526060830135606082015262003f5a60808401620033b6565b608082015260a08301358281111562003f71578485fd5b62003f7f87828601620038c4565b60a08301525062003f9360c08401620038b7565b60c082015260e08301358281111562003faa578485fd5b62003fb88782860162003490565b60e08301525095945050505050565b60006020828403121562003fd9578081fd5b813567ffffffffffffffff8082111562003ff1578283fd5b818401915061010080838703121562004008578384fd5b620040138162004bd9565b90506200402083620033b6565b81526020830135602082015260408301356040820152606083013560608201526200404e60808401620033b6565b608082015260a08301358281111562004065578485fd5b6200407387828601620038c4565b60a0830152506200408760c08401620038b7565b60c082015260e0830135828111156200409e578485fd5b62003fb8878286016200358e565b600060208284031215620040be578081fd5b813567ffffffffffffffff80821115620040d6578283fd5b8184019150610100808387031215620040ed578384fd5b620040f88162004bd9565b90506200410583620033b6565b81526020830135602082015260408301356040820152606083013560608201526200413360808401620033b6565b608082015260a0830135828111156200414a578485fd5b6200415887828601620038c4565b60a0830152506200416c60c08401620038b7565b60c082015260e08301358281111562004183578485fd5b62003fb88782860162003648565b600080600080600060808688031215620041a9578283fd5b8535945060208601359350604086013567ffffffffffffffff811115620041ce578384fd5b620041dc88828901620033c3565b9094509250620041f190506060870162003930565b90509295509295909350565b60008284526020808501945082825b858110156200423e578135620042228162004c4c565b6001600160a01b0316875295820195908201906001016200420c565b509495945050505050565b600081518084526200426381602086016020860162004c1d565b601f01601f19169290920160200192915050565b600082516200428b81846020870162004c1d565b9190910192915050565b90565b6001600160a01b0391909116815260200190565b60006001600160a01b038616825284602083015283604083015260806060830152620042dc608083018462004249565b9695505050505050565b60006001600160a01b038716825285602083015284604083015283606083015260a06080830152620032d060a083018462004249565b6001600160a01b0392831681529116602082015260400190565b6001600160a01b039485168152928416602084015292166040820152606081019190915260800190565b60006001600160a01b038089168352808816602084015286604084015260ff8616606084015280851660808401525060c060a083015262002b4e60c083018462004249565b60006001600160a01b038089168352808816602084015286604084015285606084015280851660808401525060c060a083015262002b4e60c083018462004249565b60006001600160a01b038816825286602083015285604083015284606083015260a0608083015262002b4e60a083018486620041fd565b6001600160a01b03929092168252602082015260400190565b901515815260200190565b9182526001600160a01b0316602082015260400190565b60006020825282602083015282846040840137818301604090810191909152601f909201601f19160101919050565b60006020825262002192602083018462004249565b60208082526018908201527f4661696c656420746f207472616e736665722045746865720000000000000000604082015260600190565b6020808252600f908201527f496e76616c696420616464726573730000000000000000000000000000000000604082015260600190565b60208082526036908201527f537461727420696e6465786573206d757374206265203120677265617465722060408201527f7468656e206e756d626572206f662063616c6c65657300000000000000000000606082015260800190565b60208082526026908201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160408201527f6464726573730000000000000000000000000000000000000000000000000000606082015260800190565b6020808252601b908201527f536166654d6174683a206164646974696f6e206f766572666c6f770000000000604082015260600190565b60208082526019908201527f496e76616c69642077686974656c697374206164647265737300000000000000604082015260600190565b60208082526028908201527f43616e206e6f742063616c6c20546f6b656e5472616e7366657250726f78792060408201527f436f6e7472616374000000000000000000000000000000000000000000000000606082015260800190565b60208082526037908201527f526563656976656420616d6f756e74206f6620746f6b656e7320617265206c6560408201527f7373207468656e20657870656374656420746f6b656e73000000000000000000606082015260800190565b6020808252601c908201527f4661696c656420746f20696e697469616c697a65206164617074657200000000604082015260600190565b60208082526010908201527f496e76616c696420726566657272657200000000000000000000000000000000604082015260600190565b6020808252601a908201527f50617468206e6f742070726f766964656420666f722073776170000000000000604082015260600190565b6020808252601c908201527f43616c6c20746f20756e69737761702070726f7879206661696c656400000000604082015260600190565b60208082526016908201527f54696d65206c6f636b20636865636b206661696c656400000000000000000000604082015260600190565b6020808252601e908201527f436f6e747261637420616c726561647920696e697469616c697a656421210000604082015260600190565b60208082526018908201527f45786368616e6765206e6f742077686974656c69737465640000000000000000604082015260600190565b60208082526012908201527f4e6f2070656e64696e6720726571756573740000000000000000000000000000604082015260600190565b60208082526021908201527f536166654d6174683a206d756c7469706c69636174696f6e206f766572666c6f60408201527f7700000000000000000000000000000000000000000000000000000000000000606082015260800190565b60208082526013908201527f746f416d6f756e7420697320746f6f206c6f7700000000000000000000000000604082015260600190565b60208082526016908201527f43616c6c20746f2061646170746572206661696c656400000000000000000000604082015260600190565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b6020808252601f908201527f4175677573747573537761707065723a20496e76616c69642061636365737300604082015260600190565b60208082526014908201527f45787465726e616c2063616c6c206661696c6564000000000000000000000000604082015260600190565b60208082526030908201527f526563656976656420616d6f756e74206f6620746f6b656e7320617265206c6560408201527f7373207468656e20657870656374656400000000000000000000000000000000606082015260800190565b6020808252601d908201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604082015260600190565b6020808252602a908201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e60408201527f6f74207375636365656400000000000000000000000000000000000000000000606082015260800190565b60208082526036908201527f5361666545524332303a20617070726f76652066726f6d206e6f6e2d7a65726f60408201527f20746f206e6f6e2d7a65726f20616c6c6f77616e636500000000000000000000606082015260800190565b60208082526016908201527f546f20616d6f756e742063616e206e6f74206265203000000000000000000000604082015260600190565b90815260200190565b600085825284602083015260606040830152620042dc606083018486620041fd565b9283526020830191909152604082015260600190565b60405181810167ffffffffffffffff8111828210171562004bf657fe5b604052919050565b600067ffffffffffffffff82111562004c1357fe5b5060209081020190565b60005b8381101562004c3a57818101518382015260200162004c20565b83811115620020b75750506000910152565b6001600160a01b038116811462004c6257600080fd5b50565b801515811462004c6257600080fdfe608060405234801561001057600080fd5b50604051610c1d380380610c1d83398101604081905261002f916100ac565b60006100396100a8565b600080546001600160a01b0319166001600160a01b0383169081178255604051929350917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908290a350600180546001600160a01b0319166001600160a01b03929092169190911790556100da565b3390565b6000602082840312156100bd578081fd5b81516001600160a01b03811681146100d3578182fd5b9392505050565b610b34806100e96000396000f3fe608060405234801561001057600080fd5b50600436106100725760003560e01c80638da5cb5b116100505780638da5cb5b146100b2578063dd1fe62c146100ba578063f2fde38b146100cd57610072565b806315dacbea14610077578063715018a61461008c5780637fb9312714610094575b600080fd5b61008a6100853660046107bf565b6100e0565b005b61008a61016d565b61009c610238565b6040516100a99190610886565b60405180910390f35b61009c610254565b61008a6100c8366004610809565b610270565b61008a6100db3660046107a5565b61037b565b6100e86104b1565b60005473ffffffffffffffffffffffffffffffffffffffff908116911614610145576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a09565b60405180910390fd5b61016773ffffffffffffffffffffffffffffffffffffffff85168484846104b5565b50505050565b6101756104b1565b60005473ffffffffffffffffffffffffffffffffffffffff9081169116146101c9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a09565b6000805460405173ffffffffffffffffffffffffffffffffffffffff909116907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908390a3600080547fffffffffffffffffffffffff0000000000000000000000000000000000000000169055565b60015473ffffffffffffffffffffffffffffffffffffffff1681565b60005473ffffffffffffffffffffffffffffffffffffffff1690565b6102786104b1565b60005473ffffffffffffffffffffffffffffffffffffffff9081169116146102cc576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a09565b6001546040517f079d229f00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff9091169063079d229f9061032490859085906004016108d8565b602060405180830381600087803b15801561033e57600080fd5b505af1158015610352573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906103769190610852565b505050565b6103836104b1565b60005473ffffffffffffffffffffffffffffffffffffffff9081169116146103d7576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a09565b73ffffffffffffffffffffffffffffffffffffffff8116610424576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c9061094f565b6000805460405173ffffffffffffffffffffffffffffffffffffffff808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b3390565b610167846323b872dd60e01b8585856040516024016104d6939291906108a7565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08184030181529190526020810180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167fffffffff000000000000000000000000000000000000000000000000000000009093169290921790915260606105b5826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c65648152508573ffffffffffffffffffffffffffffffffffffffff166106099092919063ffffffff16565b80519091501561037657808060200190518101906105d39190610832565b610376576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a75565b60606106188484600085610622565b90505b9392505050565b60608247101561065e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c906109ac565b61066785610724565b61069d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c90610a3e565b600060608673ffffffffffffffffffffffffffffffffffffffff1685876040516106c7919061086a565b60006040518083038185875af1925050503d8060008114610704576040519150601f19603f3d011682016040523d82523d6000602084013e610709565b606091505b509150915061071982828661072e565b979650505050505050565b803b15155b919050565b6060831561073d57508161061b565b82511561074d5782518084602001fd5b816040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161013c91906108fe565b803573ffffffffffffffffffffffffffffffffffffffff8116811461072957600080fd5b6000602082840312156107b6578081fd5b61061b82610781565b600080600080608085870312156107d4578283fd5b6107dd85610781565b93506107eb60208601610781565b92506107f960408601610781565b9396929550929360600135925050565b6000806040838503121561081b578182fd5b61082483610781565b946020939093013593505050565b600060208284031215610843578081fd5b8151801515811461061b578182fd5b600060208284031215610863578081fd5b5051919050565b6000825161087c818460208701610ad2565b9190910192915050565b73ffffffffffffffffffffffffffffffffffffffff91909116815260200190565b73ffffffffffffffffffffffffffffffffffffffff9384168152919092166020820152604081019190915260600190565b73ffffffffffffffffffffffffffffffffffffffff929092168252602082015260400190565b600060208252825180602084015261091d816040850160208701610ad2565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169190910160400192915050565b60208082526026908201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160408201527f6464726573730000000000000000000000000000000000000000000000000000606082015260800190565b60208082526026908201527f416464726573733a20696e73756666696369656e742062616c616e636520666f60408201527f722063616c6c0000000000000000000000000000000000000000000000000000606082015260800190565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b6020808252601d908201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604082015260600190565b6020808252602a908201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e60408201527f6f74207375636365656400000000000000000000000000000000000000000000606082015260800190565b60005b83811015610aed578181015183820152602001610ad5565b83811115610167575050600091015256fea2646970667358221220a59b13a9ed0e21c2fd8e94dc04c81a235f03e4cd419638647768c7e4b61975cb64736f6c63430007050033a26469706673582212206313a958e5fd033a8dcd116b8902de6862ad7f1874fa0d683d889a4d142cdedd64736f6c63430007050033

Deployed ByteCode Sourcemap

31827:28542:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;38429:688;;;;;;:::i;:::-;;:::i;:::-;;34773:97;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;:::-;;;;;;;;34878:92;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;33229:87::-;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;34075:453::-;;;;;;;;;;-1:-1:-1;34075:453:0;;;;;:::i;:::-;;:::i;34536:110::-;;;;;;;;;;;;;:::i;37737:684::-;;;;;;:::i;:::-;;:::i;35215:91::-;;;;;;;;;;;;;:::i;31451:108::-;;;;;;;;;;-1:-1:-1;31451:108:0;;;;;:::i;:::-;;:::i;36579:572::-;;;;;;:::i;:::-;;:::i;28668:140::-;;;;;;;;;;;;;:::i;36150:211::-;;;;;;;;;;-1:-1:-1;36150:211:0;;;;;:::i;:::-;;:::i;28028:79::-;;;;;;;;;;;;;:::i;44824:2097::-;;;;;;:::i;:::-;;:::i;35971:171::-;;;;;;;;;;-1:-1:-1;35971:171:0;;;;;:::i;:::-;;:::i;35098:109::-;;;;;;;;;;;;;:::i;33324:743::-;;;;;;;;;;-1:-1:-1;33324:743:0;;;;;:::i;:::-;;:::i;36369:202::-;;;;;;;;;;-1:-1:-1;36369:202:0;;;;;:::i;:::-;;:::i;39125:1376::-;;;;;;:::i;:::-;;:::i;35557:406::-;;;;;;;;;;;;;:::i;29584:227::-;;;;;;;;;;-1:-1:-1;29584:227:0;;;;;:::i;:::-;;:::i;34654:111::-;;;;;;;;;;;;;:::i;34978:112::-;;;;;;;;;;;;;:::i;40703:1206::-;;;;;;:::i;:::-;;:::i;31567:117::-;;;;;;;;;;;;;:::i;35314:235::-;;;;;;;;;;-1:-1:-1;35314:235:0;;;;;:::i;:::-;;:::i;44536:155::-;;;;;;;;;;-1:-1:-1;44536:155:0;;;;;:::i;:::-;;:::i;40509:186::-;;;;;;;;;;-1:-1:-1;40509:186:0;;;;;:::i;:::-;;:::i;47053:2455::-;;;;;;:::i;:::-;;:::i;28963:236::-;;;;;;;;;;-1:-1:-1;28963:236:0;;;;;:::i;:::-;;:::i;31332:111::-;;;;;;;;;;-1:-1:-1;31332:111:0;;;;;:::i;:::-;;:::i;:::-;;;;;;;:::i;37159:570::-;;;;;;:::i;:::-;;:::i;49641:1591::-;;;;;;:::i;:::-;;:::i;38429:688::-;38766:13;;38807:230;;38729:12;;38743:19;;-1:-1:-1;;;;;38766:13:0;;;;38848:40;;38807:230;;38907:7;;38933:8;;38960;;38987:12;;39018:4;;;;38807:230;;;:::i;:::-;;;;-1:-1:-1;;38807:230:0;;;;;;;;;;;;;;;;;;;;;;;;;;;38766:282;;;;38807:230;38766:282;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;38728:320;;;;39067:7;39059:48;;;;-1:-1:-1;;;39059:48:0;;;;;;;:::i;:::-;;;;;;;;;38429:688;;;;;;;;;:::o;34773:97::-;34849:13;;-1:-1:-1;;;;;34849:13:0;34773:97;:::o;34878:92::-;34948:14;;;;;;;;;;;;;;;;;34878:92;:::o;33229:87::-;33299:9;;33229:87;:::o;34075:453::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;34194:12:::1;::::0;;34215:31:::1;::::0;;;;;;;-1:-1:-1;;;;;34194:12:0;;::::1;::::0;:20:::1;::::0;:12;;34215:29:::1;::::0;:31;;::::1;::::0;::::1;::::0;;;;;;;;;34194:12;34215:31;::::1;;::::0;::::1;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;34248:7;34194:62;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;34172:136;;;;-1:-1:-1::0;;;34172:136:0::1;;;;;;;:::i;:::-;34320:12;34337:7;-1:-1:-1::0;;;;;34337:20:0::1;34381:29;;;34412:4;;34358:59;;;;;;;;;:::i;:::-;;::::0;;-1:-1:-1;;34358:59:0;;::::1;::::0;;;;;;::::1;::::0;::::1;::::0;;::::1;;::::0;;;::::1;::::0;;;::::1;::::0;;;34337:81;;::::1;::::0;34358:59;34337:81:::1;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;34319:99;;;34437:7;34429:48;;;;-1:-1:-1::0;;;34429:48:0::1;;;;;;;:::i;:::-;34493:27;::::0;-1:-1:-1;;;;;34493:27:0;::::1;::::0;::::1;::::0;;;::::1;28308:1;34075:453:::0;;;:::o;34536:110::-;34618:20;;-1:-1:-1;;;;;34618:20:0;34536:110;:::o;37737:684::-;38071:13;;38112:229;;38034:12;;38048:19;;-1:-1:-1;;;;;38071:13:0;;;;38153:39;;38112:229;;38211:7;;38237:8;;38264:11;;38294:9;;38322:4;;;;38112:229;;;:::i;35215:91::-;35288:10;;-1:-1:-1;;;;;35288:10:0;35215:91;:::o;31451:108::-;31533:18;;;;:13;:18;;;;;;;;;31526:25;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;31501:12;;31533:18;;31526:25;;31533:18;31526:25;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;31451:108;;;;:::o;36579:572::-;36857:13;;36898:173;;36820:12;;36834:19;;-1:-1:-1;;;;;36857:13:0;;;;36939:36;;36898:173;;36994:8;;37021:12;;37052:4;;;;36898:173;;;:::i;:::-;;;;-1:-1:-1;;36898:173:0;;;;;;;;;;;;;;;;;;;;;;;;;;;36857:225;;;;36898:173;36857:225;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;36819:263;;;;37101:7;37093:48;;;;-1:-1:-1;;;37093:48:0;;;;;;;:::i;:::-;36579:572;;;;;;;:::o;28668:140::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;28751:6:::1;::::0;28730:40:::1;::::0;28767:1:::1;::::0;-1:-1:-1;;;;;28751:6:0::1;::::0;28730:40:::1;::::0;28767:1;;28730:40:::1;28781:6;:19:::0;;;::::1;::::0;;28668:140::o;36150:211::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;36241:29:0;::::1;36233:57;;;;-1:-1:-1::0;;;36233:57:0::1;;;;;;;:::i;:::-;36301:16;:52:::0;;;::::1;-1:-1:-1::0;;;;;36301:52:0;;;::::1;::::0;;;::::1;::::0;;36150:211::o;28028:79::-;28093:6;;-1:-1:-1;;;;;28093:6:0;28028:79;:::o;44824:2097::-;44938:7;44963:15;44981:9;45023:14;;45069:15;;;;45114:13;;;;45163:19;;;;45223:16;;;;44963:27;;-1:-1:-1;45023:14:0;;45069:15;;45114:13;;45003:17;;-1:-1:-1;;;;;45223:30:0;;:62;;45269:4;:16;;;45223:62;;;45256:10;45223:62;45321:13;;;;45372:9;;;;45415:11;;45193:92;;-1:-1:-1;45321:13:0;;45392:15;;45372:9;;45415:15;;;;45410:21;;;;;;;;;;;;:24;;;45392:42;;45445:18;45466:4;:18;;;45445:39;;45569:1;45550:8;45544:22;:26;45536:55;;;;-1:-1:-1;;;45536:55:0;;;;;;;:::i;:::-;45623:1;45612:8;:12;45604:47;;;;-1:-1:-1;;;45604:47:0;;;;;;;:::i;:::-;45764:18;:16;:18::i;:::-;-1:-1:-1;;;;;45751:31:0;:9;-1:-1:-1;;;;;45751:31:0;;45747:229;;45799:19;;:165;;;;;-1:-1:-1;;;;;45799:19:0;;;;:32;;:165;;45850:9;;45878:10;;45915:4;;45939:10;;45799:165;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;45747:229;45988:90;46014:9;46038:10;46063:4;45988:11;:90::i;:::-;46093:22;46118:79;46151:7;46181:4;46118:18;:79::i;:::-;46093:104;;46250:8;46232:14;:26;;46210:124;;;;-1:-1:-1;;;46210:124:0;;;;;;;:::i;:::-;46349:164;46388:7;46410:14;46439;46468:11;46494:8;46349:24;:164::i;:::-;46530:13;46526:115;;;46596:19;;46560:69;;46576:10;;-1:-1:-1;;;;;46596:19:0;46618:10;46560:15;:69::i;:::-;46755:7;-1:-1:-1;;;;;46658:221:0;46731:9;-1:-1:-1;;;;;46658:221:0;46705:11;-1:-1:-1;;;;;46658:221:0;;46680:10;46777;46802:14;46831;46860:8;46658:221;;;;;;;;;;:::i;:::-;;;;;;;;46899:14;44824:2097;-1:-1:-1;;;;;;;;;;;;44824:2097:0:o;35971:171::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;36058:23:0;::::1;36050:51;;;;-1:-1:-1::0;;;36050:51:0::1;;;;;;;:::i;:::-;36112:10;:22:::0;;;::::1;-1:-1:-1::0;;;;;36112:22:0;;;::::1;::::0;;;::::1;::::0;;35971:171::o;35098:109::-;35186:12;;-1:-1:-1;;;;;35186:12:0;35098:109;:::o;33324:743::-;33586:19;;-1:-1:-1;;;;;33586:19:0;33578:42;33570:85;;;;-1:-1:-1;;;33570:85:0;;;;;;;:::i;:::-;33666:16;:52;;;;-1:-1:-1;;;;;33666:52:0;;;;;33770:34;;-1:-1:-1;;33793:10:0;;33770:34;;;:::i;:::-;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;33815:19:0;:62;;;;;;-1:-1:-1;;;;;33815:62:0;;;;;;;33888:12;:38;;;;;;;;;;;;;;33937:10;:22;;;;;;;;;;;;;;-1:-1:-1;33970:13:0;:28;;;;;;;;;;;;;;;34009:6;:19;;34018:10;34009:19;;;;;;;;;-1:-1:-1;;34039:9:0;:20;33324:743::o;36369:202::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;36457:25:0;::::1;36449:63;;;;-1:-1:-1::0;;;36449:63:0::1;;;;;;;:::i;:::-;36523:12;:40:::0;;;::::1;-1:-1:-1::0;;;;;36523:40:0;;;::::1;::::0;;;::::1;::::0;;36369:202::o;39125:1376::-;-1:-1:-1;;;;;39572:25:0;;;:52;;39613:11;39572:52;;;39600:10;39572:52;39558:66;;39635:19;39657:374;39689:9;39713:7;39735:10;39760:8;39783;39861:7;39883:12;39910;39937:6;39958:11;39984:8;40007:13;39657:17;:374::i;:::-;39635:396;;40044:23;40070:81;40103:9;40135:4;40070:18;:81::i;:::-;40044:107;-1:-1:-1;40168:19:0;;40164:121;;40204:69;40233:9;40245:10;40257:15;40204:20;:69::i;:::-;40398:7;-1:-1:-1;;;;;40302:191:0;40374:9;-1:-1:-1;;;;;40302:191:0;40348:11;-1:-1:-1;;;;;40302:191:0;;40323:10;40420;40445:14;40474:8;40302:191;;;;;;;;;:::i;:::-;;;;;;;;39125:1376;;;;;;;;;;;;;:::o;35557:406::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;35688:9:::1;::::0;35662:21:::1;::::0;:36:::1;::::0;:25:::1;:36::i;:::-;35646:12;:52;;35624:124;;;;-1:-1:-1::0;;;35624:124:0::1;;;;;;;:::i;:::-;35769:20;::::0;-1:-1:-1;;;;;35769:20:0::1;35761:65;;;;-1:-1:-1::0;;;35761:65:0::1;;;;;;;:::i;:::-;35863:1;35839:21;:25:::0;35891:20:::1;::::0;;35875:13:::1;:36:::0;;;;;::::1;-1:-1:-1::0;;;;;35891:20:0;::::1;35875:36;::::0;;;35922:33:::1;::::0;;35557:406::o;29584:227::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;29755:48:::1;29776:5;29783:11;29796:6;29755:20;:48::i;:::-;29584:227:::0;;;:::o;34654:111::-;34736:21;;34654:111;:::o;34978:112::-;35065:16;;-1:-1:-1;;;;;35065:16:0;34978:112;:::o;40703:1206::-;41169:22;-1:-1:-1;;;;;41223:25:0;;;:52;;41264:11;41223:52;;;41251:10;41223:52;41209:66;;41303:325;41335:9;41359:7;41381:10;41406:8;41429:14;41458:7;41480:12;41507;41534:6;41555:11;41581:8;41604:13;41303:17;:325::i;:::-;41286:342;;41743:7;-1:-1:-1;;;;;41646:221:0;41719:9;-1:-1:-1;;;;;41646:221:0;41693:11;-1:-1:-1;;;;;41646:221:0;;41668:10;41765;41790:14;41819;41848:8;41646:221;;;;;;;;;;:::i;31567:117::-;31656:19;;-1:-1:-1;;;;;31656:19:0;31567:117;:::o;35314:235::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;35402:26:0;::::1;35394:54;;;;-1:-1:-1::0;;;35394:54:0::1;;;;;;;:::i;:::-;35483:12;35459:21;:36:::0;35506:20:::1;:35:::0;;;::::1;-1:-1:-1::0;;;;;35506:35:0;;;::::1;::::0;;;::::1;::::0;;35314:235::o;44536:155::-;33069:10;33091:4;33069:27;33047:108;;;;-1:-1:-1;;;33047:108:0;;;;;;;:::i;:::-;44620:30:::1;::::0;;;;44603:14:::1;::::0;-1:-1:-1;;;;;44620:15:0;::::1;::::0;::::1;::::0;:30:::1;::::0;44644:4:::1;::::0;44620:30:::1;;;:::i;:::-;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;44661:22;::::0;;;;44603:47;;-1:-1:-1;;;;;;44661:14:0;::::1;::::0;::::1;::::0;:22:::1;::::0;44603:47;;44661:22:::1;;;:::i;:::-;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;33166:1;44536:155:::0;:::o;40509:186::-;33069:10;33091:4;33069:27;33047:108;;;;-1:-1:-1;;;33047:108:0;;;;;;;:::i;:::-;40655:32:::1;40669:2;40673:5;40680:6;40655:13;:32::i;47053:2455::-:0;47174:7;47199:15;47217:9;47259:14;;47305:15;;;;47350:13;;;;47399:19;;;;47459:16;;;;47199:27;;-1:-1:-1;47259:14:0;;47305:15;;47350:13;;47239:17;;-1:-1:-1;;;;;47459:30:0;;:62;;47505:4;:16;;;47459:62;;;47492:10;47459:62;47429:92;;47532:22;47557:4;:13;;;47532:38;;47581:32;47616:4;:9;;;47581:44;;47636:15;47654:4;47659:1;47654:7;;;;;;;;;;;;;;:12;;;47689:1;47667:4;47672:1;47667:7;;;;;;;;;;;;;;:12;;;:19;:23;47654:37;;;;;;;;;;;;;;:40;;;47636:58;;47705:18;47726:4;:18;;;47705:39;;47829:1;47810:8;47804:22;:26;47796:55;;;;-1:-1:-1;;;47796:55:0;;;;;;;:::i;:::-;47883:1;47872:8;:12;47864:47;;;;-1:-1:-1;;;47864:47:0;;;;;;;:::i;:::-;48024:18;:16;:18::i;:::-;-1:-1:-1;;;;;48011:31:0;:9;-1:-1:-1;;;;;48011:31:0;;48007:229;;48059:19;;:165;;;;;-1:-1:-1;;;;;48059:19:0;;;;:32;;:165;;48110:9;;48138:10;;48175:4;;48199:10;;48059:165;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;48007:229;48253:7;48248:420;48276:4;:11;48266:22;;:1;:22;;;48248:420;;;48310:19;48332:52;48378:5;48332:41;48347:4;48352:1;48347:7;;;;;;;;;;;;;;;;:25;;;48332:10;:14;;:41;;;;:::i;:::-;:45;;:52::i;:::-;48310:74;;48422:1;48408:4;:11;:15;48403:1;:20;;;48399:128;;;48458:53;48485:9;48505:4;48458:18;:53::i;:::-;48444:67;;48399:128;48541:115;48571:9;48599:11;48629:4;48634:1;48629:7;;;;;;;;;;;;;;;;:12;;;48541:11;:115::i;:::-;-1:-1:-1;48290:3:0;;48248:420;;;;48680:22;48705:79;48738:7;48768:4;48705:18;:79::i;28963:236::-;28240:6;;-1:-1:-1;;;;;28240:6:0;28250:10;28240:20;28232:65;;;;-1:-1:-1;;;28232:65:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;29044:22:0;::::1;29036:73;;;;-1:-1:-1::0;;;29036:73:0::1;;;;;;;:::i;:::-;29146:6;::::0;29125:38:::1;::::0;-1:-1:-1;;;;;29125:38:0;;::::1;::::0;29146:6:::1;::::0;29125:38:::1;::::0;29146:6:::1;::::0;29125:38:::1;29174:6;:17:::0;;;::::1;-1:-1:-1::0;;;;;29174:17:0;;;::::1;::::0;;;::::1;::::0;;28963:236::o;31332:111::-;31388:4;31412:23;;;;;;;;;;;;;;31332:111::o;37159:570::-;37436:13;;37477:172;;37399:12;;37413:19;;-1:-1:-1;;;;;37436:13:0;;;;37518:35;;37477:172;;37572:11;;37602:9;;37630:4;;;;37477:172;;;:::i;49641:1591::-;49795:14;;49841:15;;;;49886:13;;;;49940:16;;;;49748:7;;49795:14;49841:15;49886:13;49748:7;;-1:-1:-1;;;;;49940:30:0;;:62;;49986:4;:16;;;49940:62;;;49973:10;49940:62;50038:13;;;;50094:10;;;;50133:12;;;;50177:18;;;;50258:22;;49910:92;;-1:-1:-1;50038:13:0;;50094:10;;50133:12;;50250:55;;;;-1:-1:-1;;;50250:55:0;;;;;;;:::i;:::-;50337:1;50326:8;:12;50318:47;;;;-1:-1:-1;;;50318:47:0;;;;;;;:::i;:::-;50378:22;50403:163;50428:9;50452:7;50474:10;50499:8;50522:5;50542:13;50403:10;:163::i;:::-;50378:188;;50579:158;50618:7;50640:8;50663:14;50692:11;50718:8;50579:24;:158::i;:::-;50750:23;50776:81;50809:9;50841:4;50776:18;:81::i;:::-;50750:107;-1:-1:-1;50874:19:0;;50870:112;;50910:60;50931:9;50942:10;50954:15;50910:20;:60::i;:::-;51095:7;-1:-1:-1;;;;;50999:191:0;51071:9;-1:-1:-1;;;;;50999:191:0;51045:11;-1:-1:-1;;;;;50999:191:0;;51020:10;51117;51142:14;51171:8;50999:191;;;;;;;;;:::i;:::-;;;;;;;;-1:-1:-1;51210:14:0;49641:1591;-1:-1:-1;;;;;;;;;;49641:1591:0:o;19555:75::-;17226:42;19555:75;:::o;53846:2443::-;54023:1;54009:4;:11;:15;54001:54;;;;-1:-1:-1;;;54001:54:0;;;;;;;:::i;:::-;54149:6;54144:2138;54165:4;:11;54161:1;:15;54144:2138;;;54281:18;54306:1;54302;:5;:34;;54327:9;54302:34;;;54310:4;54319:1;54315;:5;54310:11;;;;;;;;;;;;;;:14;;;54302:34;54281:55;;54351:16;54370:4;54375:1;54370:7;;;;;;;;;;;;;;:10;;;54351:29;;54397:19;54423:1;54419;:5;:66;;54475:10;54419:66;;;54427:45;54446:10;54466:4;54427:18;:45::i;:::-;54397:88;;54508:1;54504;:5;:41;;;;;54527:18;:16;:18::i;:::-;-1:-1:-1;;;;;54513:32:0;:10;-1:-1:-1;;;;;54513:32:0;;54504:41;54500:136;;;54580:40;54596:4;54601:1;54596:7;;;;;;;;;;;;;;:23;;;54580:11;:15;;:40;;;;:::i;:::-;54566:54;;54500:136;54657:6;54652:1619;54673:4;54678:1;54673:7;;;;;;;;;;;;;;:14;;;:21;54669:1;:25;54652:1619;;;54720:24;;:::i;:::-;54747:4;54752:1;54747:7;;;;;;;;;;;;;;:14;;;54762:1;54747:17;;;;;;;;;;;;;;;;;;;54865:12;;;54886:31;;;;;;;;54747:17;;-1:-1:-1;;;;;;54865:12:0;;;;:20;;:12;;54886:29;;:31;;;;54747:17;54886:31;;;;;;;54865:12;54886:31;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;54919:14;;54865:69;;;;;;;;;;;;;54919:14;54865:69;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;54835:167;;;;-1:-1:-1;;;54835:167:0;;;;;;;:::i;:::-;55150:20;55173:41;55208:5;55173:30;55189:5;:13;;;55173:11;:15;;:30;;;;:::i;:41::-;55249:16;;;;55150:64;;-1:-1:-1;55290:5:0;;;;;:42;;;55304:28;55330:1;55304:4;55309:1;55304:7;;;;;;;;;;;;;;:14;;;:21;:25;;:28;;;;:::i;:::-;55299:1;:33;55290:42;55286:425;;;55357:14;55374:54;55401:10;55422:4;55374:18;:54::i;:::-;55357:71;;55471:6;55453:24;;55529:18;:16;:18::i;:::-;-1:-1:-1;;;;;55506:41:0;55514:10;-1:-1:-1;;;;;55506:41:0;;55502:190;;;55642:26;:15;55662:5;55642:19;:26::i;:::-;55624:44;;55502:190;55286:425;;55799:14;;56090:20;;;;56137:13;;;;55849:324;;55782:12;;-1:-1:-1;;;;;55799:27:0;;55898:23;;55849:324;;55948:10;;55985:8;;56020:15;;56062:1;;56090:20;56137:13;55849:324;;;:::i;:::-;;;;-1:-1:-1;;55849:324:0;;;;;;;;;;;;;;;;;;;;;;;;;;;55799:393;;;;55849:324;55799:393;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;55781:411;;;56221:7;56213:42;;;;-1:-1:-1;;;56213:42:0;;;;;;;:::i;:::-;-1:-1:-1;;54696:3:0;;;;;-1:-1:-1;54652:1619:0;;-1:-1:-1;54652:1619:0;;-1:-1:-1;;54178:3:0;;;;;-1:-1:-1;54144:2138:0;;-1:-1:-1;54144:2138:0;;;53846:2443;;;:::o;20792:296::-;20909:7;-1:-1:-1;;;;;20938:20:0;;17226:42;20938:20;20934:147;;;-1:-1:-1;;;;;;20982:15:0;;;20975:22;;20934:147;21037:32;;;;;-1:-1:-1;;;;;21037:23:0;;;;;:32;;21061:7;;21037:32;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;21030:39;;20934:147;20792:296;;;;:::o;51309:1120::-;51627:16;;:45;;;;;51574:14;;51548:23;;-1:-1:-1;;;;;51627:16:0;;;;:35;;:45;;51663:8;;51627:45;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;51601:71;;51715:11;51731:129;51754:7;51776:14;51805;51834:15;51731:8;:129::i;:::-;51713:147;-1:-1:-1;51889:23:0;:14;51713:147;51889:18;:23::i;:::-;51871:41;;52062:14;52044:15;:32;52043:46;;;;-1:-1:-1;52081:8:0;;52043:46;52039:307;;;52106:29;52138:42;52178:1;52138:35;:15;52158:14;52138:19;:35::i;:42::-;52106:74;-1:-1:-1;52213:42:0;:15;52106:74;52213:19;:42::i;:::-;52300:10;;52195:60;;-1:-1:-1;52270:64:0;;52291:7;;-1:-1:-1;;;;;52300:10:0;52312:21;52270:20;:64::i;:::-;52039:307;;52358:59;52379:7;52388:11;52401:15;52358:20;:59::i;:::-;51309:1120;;;;;;;;:::o;21170:448::-;21341:5;21377:4;21412:5;21322:16;21447:100;21505:31;21377:4;21505:16;21412:5;21519:1;21505:13;:16::i;:::-;:20;;:31::i;:::-;21447:53;21491:8;21447:39;21476:9;21447:10;;:14;:39::i;:::-;:43;;:53::i;:100::-;21430:117;;21560:50;21574:7;21583:18;21603:6;21560:13;:50::i;42269:2124::-;42726:22;42785:1;42774:8;:12;42766:44;;;;-1:-1:-1;;;42766:44:0;;;;;;;:::i;:::-;42865:12;:19;42843:7;:14;42860:1;42843:18;:41;42821:145;;;;-1:-1:-1;;;42821:145:0;;;;;;;:::i;:::-;42979:15;42997:9;42979:27;;43137:46;43161:9;43172:10;43137:23;:46::i;:::-;43201:9;43196:606;43220:7;:14;43216:1;:18;43196:606;;;43304:19;;43282:10;;-1:-1:-1;;;;;43304:19:0;;;;43282:7;;43290:1;;43282:10;;;;;;;;;;;;-1:-1:-1;;;;;43282:42:0;;;43256:144;;;;-1:-1:-1;;;43256:144:0;;;;;;;:::i;:::-;43417:11;43431:305;43462:7;43470:1;43462:10;;;;;;;;;;;;;;43505:6;43512:1;43505:9;;;;;;;;;;;;;;43549:12;43562:1;43549:15;;;;;;;;;;;;;;43611:40;43635:12;43648:1;43635:15;;;;;;;;;;;;;;43611:12;43624:1;43628;43624:5;43611:19;;;;;;;;;;;;;;:23;;:40;;;;:::i;:::-;43692:12;43431;:305::i;:::-;43417:319;;43759:6;43751:39;;;;-1:-1:-1;;;43751:39:0;;;;;;;:::i;:::-;-1:-1:-1;43236:3:0;;43196:606;;;;43831:79;43864:7;43894:4;43831:18;:79::i;:::-;43814:96;;43963:8;43945:14;:26;;43923:124;;;;-1:-1:-1;;;43923:124:0;;;;;;;:::i;:::-;44060:164;44099:7;44121:14;44150;44179:11;44205:8;44060:24;:164::i;:::-;44241:13;44237:115;;;44307:19;;44271:69;;44287:10;;-1:-1:-1;;;;;44307:19:0;44329:10;44271:15;:69::i;:::-;44364:21;42269:2124;;;;;;;;;;;;;;:::o;20297:487::-;20449:10;;20445:330;;-1:-1:-1;;;;;20480:20:0;;17226:42;20480:20;20476:288;;;20522:11;20539;-1:-1:-1;;;;;20539:16:0;20563:6;20576:4;20539:46;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;20521:64;;;20612:6;20604:43;;;;-1:-1:-1;;;20604:43:0;;;;;;;:::i;:::-;20476:288;;;;20701:47;-1:-1:-1;;;;;20701:26:0;;20728:11;20741:6;20701:26;:47::i;7346:181::-;7404:7;7436:5;;;7460:6;;;;7452:46;;;;-1:-1:-1;;;7452:46:0;;;;;;;:::i;19800:489::-;-1:-1:-1;;;;;19932:20:0;;17226:42;19932:20;19928:354;;20032:49;;;;;19992:5;;19969:13;;-1:-1:-1;;;;;20032:16:0;;;;;:49;;20057:4;;20064:16;;20032:49;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;20015:66;;20114:6;20102:9;:18;20098:173;;;20141:39;-1:-1:-1;;;;;20141:18:0;;20160:16;20178:1;20141:18;:39::i;:::-;20199:56;-1:-1:-1;;;;;20199:28:0;;20228:16;17420:12;20199:28;:56::i;:::-;19928:354;;19800:489;;;:::o;8700:471::-;8758:7;9003:6;8999:47;;-1:-1:-1;9033:1:0;9026:8;;8999:47;9070:5;;;9074:1;9070;:5;:1;9094:5;;;;;:10;9086:56;;;;-1:-1:-1;;;9086:56:0;;;;;;;:::i;9647:132::-;9705:7;9732:39;9736:1;9739;9732:39;;;;;;;;;;;;;;;;;:3;:39::i;56336:1881::-;56577:7;56602:15;56620:9;56602:27;;56742:18;:16;:18::i;:::-;-1:-1:-1;;;;;56729:31:0;:9;-1:-1:-1;;;;;56729:31:0;;56725:229;;56777:19;;:165;;;;;-1:-1:-1;;;;;56777:19:0;;;;:32;;:165;;56828:9;;56856:10;;56893:4;;56917:10;;56777:165;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;56725:229;56971:6;56966:826;56987:6;:13;56983:1;:17;56966:826;;;57022:27;;:::i;:::-;57052:6;57059:1;57052:9;;;;;;;;;;;;;;;;;;;57150:12;;;57171:31;;;;;;;;57052:9;;-1:-1:-1;;;;;;57150:12:0;;;;:20;;:12;;57171:29;;:31;;;;57052:9;57171:31;;;;;;;57150:12;57171:31;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;57204:14;;57150:69;;;;;;;;;;;;;57204:14;57150:69;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;57124:155;;;;-1:-1:-1;;;57124:155:0;;;;;;;:::i;:::-;57342:12;57359:5;:14;;;-1:-1:-1;;;;;57359:27:0;57450:22;;;57495:9;57527:7;57557:5;:16;;;57596:5;:14;;;57633:5;:20;;;57676:5;:13;;;57405:303;;;;;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;57405:303:0;;;;;;;;;;;;;;;;;;;;;;;;;;;57359:364;;;;57405:303;57359:364;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;57341:382;;;57746:7;57738:42;;;;-1:-1:-1;;;57738:42:0;;;;;;;:::i;:::-;-1:-1:-1;;57002:3:0;;56966:826;;;;57804:22;57829:79;57862:7;57892:4;57829:18;:79::i;:::-;57804:104;;57959:8;57941:14;:26;;57919:131;;;;-1:-1:-1;;;57919:131:0;;;;;;;:::i;:::-;58067:13;58063:115;;;58133:19;;58097:69;;58113:10;;-1:-1:-1;;;;;58133:19:0;58155:10;58097:15;:69::i;:::-;58195:14;56336:1881;-1:-1:-1;;;;;;;;56336:1881:0:o;7810:136::-;7868:7;7895:43;7899:1;7902;7895:43;;;;;;;;;;;;;;;;;:3;:43::i;58225:2141::-;58410:11;-1:-1:-1;;;;;58535:29:0;;58531:72;;-1:-1:-1;58589:1:0;58581:10;;58531:72;58630:32;58677:18;58710:27;58767;58809:23;58855:15;-1:-1:-1;;;;;58846:40:0;;:42;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;58615:273;;;;;;;;;;;58901:20;58936:21;58979:18;58978:19;:39;;;;;59015:2;59001:10;:16;;58978:39;:74;;;;;59038:14;59021;:31;58978:74;58974:1163;;;59069:28;59100:41;59139:1;59100:34;:14;59119;59100:18;:34::i;:41::-;59069:72;-1:-1:-1;59209:41:0;59244:5;59209:30;:14;59228:10;59209:18;:30::i;:41::-;59203:47;-1:-1:-1;59321:39:0;59354:5;59321:28;59203:47;59329:19;59321:7;:28::i;:39::-;59306:54;-1:-1:-1;59444:21:0;:3;59306:54;59444:7;:21::i;:::-;59428:37;-1:-1:-1;59496:39:0;59428:37;59514:20;59496:17;:39::i;:::-;59480:55;-1:-1:-1;59558:29:0;:3;59566:20;59558:7;:29::i;:::-;59552:35;;59609:22;59604:171;;59667:38;:12;59684:20;59667:16;:38::i;:::-;59652:53;-1:-1:-1;59730:29:0;:3;59738:20;59730:7;:29::i;:::-;59724:35;;59604:171;58974:1163;;;;59869:41;59904:5;59869:30;:14;59888:10;59869:18;:30::i;:41::-;59863:47;-1:-1:-1;59981:39:0;60014:5;59981:28;59863:47;59989:19;59981:7;:28::i;:39::-;59966:54;-1:-1:-1;60104:21:0;:3;59966:54;60104:7;:21::i;:::-;60088:37;;58974:1163;60147:61;60168:7;60177:16;60195:12;60147:20;:61::i;:::-;60249:10;;60219:56;;60240:7;;-1:-1:-1;;;;;60249:10:0;60261:13;60219:20;:56::i;:::-;60293:42;60302:3;60307:12;60321:13;60293:42;;;;;;;;:::i;:::-;;;;;;;;60346:12;;;;;;;58225:2141;;;;;;;:::o;21688:513::-;21817:6;21794:20;;21884:9;21870:23;;21917:5;21910:3;:12;21906:98;;21955:37;21974:17;21955:14;:3;21963:5;21955:7;:14::i;:37::-;21939:53;;21906:98;22035:13;22020:12;:28;22016:89;;;22080:13;22065:28;;22016:89;22115:78;;;;;-1:-1:-1;;;;;22115:55:0;;;;;:78;;22171:7;;22180:12;;22115:78;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;21688:513;;;;;;:::o;41917:344::-;42050:18;:16;:18::i;:::-;-1:-1:-1;;;;;42041:27:0;:5;-1:-1:-1;;;;;42041:27:0;;42037:217;;42085:19;;:157;;;;;-1:-1:-1;;;;;42085:19:0;;;;:32;;:157;;42136:5;;42160:10;;42197:4;;42221:6;;42085:157;;;:::i;42037:217::-;41917:344;;:::o;52599:1200::-;52792:4;52814:11;52828:5;52814:19;;52885:4;52879:11;53021:2;53015:4;53011:13;53668:1;53648;53546:10;53516;53513:1;53509:18;53485:5;53455:11;53147:5;53140;53136:17;53113:644;53103:654;52599:1200;-1:-1:-1;;;;;;;;;52599:1200:0:o;13926:177::-;14009:86;14029:5;14059:23;;;14084:2;14088:5;14036:58;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;14036:58:0;;;;;;;;;;;;;;;;;;;;;;;;;;;14009:19;:86::i;14585:622::-;14955:10;;;14954:62;;-1:-1:-1;14971:39:0;;;;;-1:-1:-1;;;;;14971:15:0;;;;;:39;;14995:4;;15002:7;;14971:39;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:44;14954:62;14946:152;;;;-1:-1:-1;;;14946:152:0;;;;;;;:::i;:::-;15109:90;15129:5;15159:22;;;15183:7;15192:5;15136:62;;;;;;;;;:::i;15215:286::-;15312:20;15335:50;15379:5;15335;-1:-1:-1;;;;;15335:15:0;;15359:4;15366:7;15335:39;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:50::-;15312:73;;15396:97;15416:5;15446:22;;;15470:7;15479:12;15423:69;;;;;;;;;:::i;10275:278::-;10361:7;10396:12;10389:5;10381:28;;;;-1:-1:-1;;;10381:28:0;;;;;;;;:::i;:::-;;10420:9;10436:1;10432;:5;;;;;;;-1:-1:-1;;10275:278:0;;;;;;:::o;8249:192::-;8335:7;8371:12;8363:6;;;;8355:29;;;;-1:-1:-1;;;8355:29:0;;;;;;;;:::i;:::-;-1:-1:-1;;;8407:5:0;;;8249:192::o;15892:761::-;16316:23;16342:69;16370:4;16342:69;;;;;;;;;;;;;;;;;16350:5;-1:-1:-1;;;;;16342:27:0;;;:69;;;;;:::i;:::-;16426:17;;16316:95;;-1:-1:-1;16426:21:0;16422:224;;16568:10;16557:30;;;;;;;;;;;;:::i;:::-;16549:85;;;;-1:-1:-1;;;16549:85:0;;;;;;;:::i;12342:195::-;12445:12;12477:52;12499:6;12507:4;12513:1;12516:12;12445;12797:18;12808:6;12797:10;:18::i;:::-;12789:60;;;;-1:-1:-1;;;12789:60:0;;;;;;;:::i;:::-;12923:12;12937:23;12964:6;-1:-1:-1;;;;;12964:11:0;12984:5;12992:4;12964:33;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;12922:75;;;;13015:52;13033:7;13042:10;13054:12;13015:17;:52::i;:::-;13008:59;12545:530;-1:-1:-1;;;;;;;12545:530:0:o;11912:422::-;12279:20;12318:8;;;11912:422::o;13083:742::-;13198:12;13227:7;13223:595;;;-1:-1:-1;13258:10:0;13251:17;;13223:595;13372:17;;:21;13368:439;;13635:10;13629:17;13696:15;13683:10;13679:2;13675:19;13668:44;13583:148;13778:12;13771:20;;-1:-1:-1;;;13771:20:0;;;;;;;;:::i;-1:-1:-1:-;;;;;;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;14:138:1:-;84:20;;113:33;84:20;113:33;:::i;157:404::-;;;290:3;283:4;275:6;271:17;267:27;257:2;;315:8;305;298:26;257:2;-1:-1:-1;345:20:1;;388:18;377:30;;374:2;;;427:8;417;410:26;374:2;471:4;463:6;459:17;447:29;;534:3;527:4;519;511:6;507:17;499:6;495:30;491:41;488:50;485:2;;;551:1;548;541:12;485:2;247:314;;;;;:::o;566:769::-;;679:3;672:4;664:6;660:17;656:27;646:2;;701:5;694;687:20;646:2;745:6;732:20;770:69;785:53;831:6;785:53;:::i;:::-;770:69;:::i;:::-;873:21;;;761:78;-1:-1:-1;913:4:1;933:14;;;;967:15;;;1013;;;1001:28;;997:37;;994:46;-1:-1:-1;991:2:1;;;1053:1;1050;1043:12;991:2;1075:1;1085:244;1099:6;1096:1;1093:13;1085:244;;;1174:3;1161:17;1191:33;1218:5;1191:33;:::i;:::-;1237:18;;1275:12;;;;1307;;;;1121:1;1114:9;1085:244;;;1089:3;;;;;636:699;;;;:::o;1340:1672::-;;1462:3;1455:4;1447:6;1443:17;1439:27;1429:2;;1484:5;1477;1470:20;1429:2;1528:6;1515:20;1553:69;1568:53;1614:6;1568:53;:::i;1553:69::-;1656:21;;;1544:78;-1:-1:-1;1696:4:1;1716:14;;;;1750:15;;;1783:1;1793:1213;1807:6;1804:1;1801:13;1793:1213;;;1891:3;1878:17;1870:6;1866:30;1919:4;2030:2;-1:-1:-1;;1956:2:1;1951:3;1947:12;1943:85;1939:94;1936:2;;;2046:1;2043;2036:12;1936:2;2073;2108;2102:9;2154:2;2146:6;2142:15;2180:18;2252:6;2240:10;2237:22;2232:2;2220:10;2217:18;2214:46;2211:2;;;2263:9;2211:2;2298:10;2294:2;2287:22;2337:33;2366:2;2362;2358:11;2337:33;:::i;:::-;2329:6;2322:49;2408:33;2437:2;2433;2429:11;2408:33;:::i;:::-;2403:2;2395:6;2391:15;2384:58;2465:2;2455:12;;2525:2;2521;2517:11;2504:25;2499:2;2491:6;2487:15;2480:50;2553:3;2543:13;;2614:2;2610;2606:11;2593:25;2588:2;2580:6;2576:15;2569:50;2642:3;2632:13;;2695:2;2691;2687:11;2674:25;2728:2;2718:8;2715:16;2712:2;;;2744:1;2741;2734:12;2712:2;2785:51;2832:3;2827:2;2816:8;2812:2;2808:17;2804:26;2785:51;:::i;:::-;2768:15;;;2761:76;;;;-1:-1:-1;2887:11:1;;;;2874:25;2857:15;;;2850:50;;;;2913:19;;-1:-1:-1;2952:12:1;;;;2984;;;;1829:1;1822:9;1793:1213;;3017:1327;;3143:3;3136:4;3128:6;3124:17;3120:27;3110:2;;3165:5;3158;3151:20;3110:2;3209:6;3196:20;3234:69;3249:53;3295:6;3249:53;:::i;3234:69::-;3337:21;;;3225:78;-1:-1:-1;3377:4:1;3397:14;;;;3431:15;;;3464:1;3474:864;3488:6;3485:1;3482:13;3474:864;;;3572:3;3559:17;3551:6;3547:30;3600:4;3711:2;-1:-1:-1;;3637:2:1;3632:3;3628:12;3624:85;3620:94;3617:2;;;3727:1;3724;3717:12;3617:2;3764;3758:9;3810:2;3802:6;3798:15;3836:18;3908:6;3896:10;3893:22;3888:2;3876:10;3873:18;3870:46;3867:2;;;3919:9;3867:2;3943:22;;;4006:11;;;3993:25;3978:41;;4061:11;;;4048:25;;4089:16;;;4086:2;;;4118:1;4115;4108:12;4086:2;;;4159:72;4227:3;4222:2;4211:8;4207:2;4203:17;4199:26;4159:72;:::i;:::-;4142:15;;;4135:97;4245:19;;-1:-1:-1;;4284:12:1;;;;4316;;;;3510:1;3503:9;3474:864;;4349:2844;;4467:3;4460:4;4452:6;4448:17;4444:27;4434:2;;4489:5;4482;4475:20;4434:2;4515:83;4530:67;4589:6;4576:20;4530:67;:::i;4515:83::-;4646:20;;4632:35;;4506:92;-1:-1:-1;4694:4:1;4683:16;;;;4719:17;;4754:1;4764:2423;4791:6;4778:20;4775:1;4772:27;4764:2423;;;4876:3;4863:17;4855:6;4851:30;4988:4;-1:-1:-1;;4914:2:1;4909:3;4905:12;4901:85;4897:96;4894:2;;;5006:1;5003;4996:12;4894:2;5043;5037:9;5130:6;5123:4;5115:6;5111:17;5108:29;5087:18;5080:4;5072:6;5068:17;5065:41;5062:76;5059:2;;;5141:9;5059:2;5188:4;5180:6;5176:17;5172:2;5165:29;5207:55;5255:4;5251:2;5247:13;5234:27;5207:55;:::i;:::-;5311:4;5307:2;5303:13;5290:27;5282:6;5275:43;5378:2;5374;5370:11;5357:25;5350:4;5342:6;5338:17;5331:52;5431:18;5423:4;5419:2;5415:13;5402:27;5399:51;5396:2;;;5463:1;5460;5453:12;5396:2;5519:4;5515:2;5511:13;5498:27;5494:2;5490:36;5480:46;;5566:3;5561:2;5557;5553:11;5549:21;5539:2;;5584:1;5581;5574:12;5539:2;5614:90;5629:74;5696:4;5692:2;5688:13;5675:27;5629:74;:::i;5614:90::-;5783:4;5775:13;;;5762:27;5748:42;;5812:16;;;5862:2;5854:11;;5889:1;5903:1131;5952:4;5948:2;5944:13;5931:27;5926:3;5923:36;5903:1131;;;6056:5;6043:19;6039:2;6035:28;6174:4;6105:66;6100:2;6095:3;6091:12;6087:85;6083:96;6080:2;;;6192:1;6189;6182:12;6080:2;6235;6229:9;6330:8;6323:4;6313:8;6309:19;6306:33;6285:18;6278:4;6268:8;6264:19;6261:43;6258:82;6255:2;;;6343:9;6255:2;6396:4;6386:8;6382:19;6378:2;6371:31;6436:33;6465:2;6461;6457:11;6436:33;:::i;:::-;6426:8;6419:51;6515:35;6544:4;6540:2;6536:13;6515:35;:::i;:::-;6508:4;6498:8;6494:19;6487:64;6615:3;6611:2;6607:12;6594:26;6589:2;6579:8;6575:17;6568:53;6673:18;6665:4;6661:2;6657:13;6644:27;6641:51;6638:2;;;6705:1;6702;6695:12;6638:2;6754:70;6820:3;6815:2;6806:4;6802:2;6798:13;6785:27;6781:2;6777:36;6773:45;6754:70;:::i;:::-;6747:4;6733:19;;6726:99;6890:3;6882:12;;;;6869:26;6863:3;6849:18;;6842:54;6913:23;;6973:4;6962:16;;;;7004;;;;;5990:1;5981:11;5903:1131;;;-1:-1:-1;;7066:2:1;7054:15;;7047:30;-1:-1:-1;7090:19:1;;-1:-1:-1;7138:4:1;7129:14;;;;7163;;;;;4814:1;4807:9;4764:2423;;;4768:3;;;4424:2769;;;;:::o;7198:692::-;;7311:3;7304:4;7296:6;7292:17;7288:27;7278:2;;7333:5;7326;7319:20;7278:2;7377:6;7364:20;7402:69;7417:53;7463:6;7417:53;:::i;7402:69::-;7505:21;;;7393:78;-1:-1:-1;7545:4:1;7565:14;;;;7599:15;;;7645;;;7633:28;;7629:37;;7626:46;-1:-1:-1;7623:2:1;;;7685:1;7682;7675:12;7623:2;7707:1;7717:167;7731:6;7728:1;7725:13;7717:167;;;7792:17;;7780:30;;7830:12;;;;7862;;;;7753:1;7746:9;7717:167;;7895:132;7962:20;;7991:30;7962:20;7991:30;:::i;8032:580::-;;8129:3;8122:4;8114:6;8110:17;8106:27;8096:2;;8151:5;8144;8137:20;8096:2;8195:6;8182:20;8225:18;8217:6;8214:30;8211:2;;;8247:9;8211:2;8276:117;8387:4;-1:-1:-1;;8311:4:1;8303:6;8299:17;8295:90;8291:101;8276:117;:::i;:::-;8267:126;;8416:6;8409:5;8402:21;8470:3;8463:4;8454:6;8446;8442:19;8438:30;8435:39;8432:2;;;8487:1;8484;8477:12;8432:2;8550:6;8543:4;8535:6;8531:17;8524:4;8517:5;8513:16;8500:57;8604:1;8577:18;;;8597:4;8573:29;8566:40;8581:5;8086:526;-1:-1:-1;;8086:526:1:o;8617:158::-;8685:20;;8745:4;8734:16;;8724:27;;8714:2;;8765:1;8762;8755:12;8780:259;;8892:2;8880:9;8871:7;8867:23;8863:32;8860:2;;;8913:6;8905;8898:22;8860:2;8957:9;8944:23;8976:33;9003:5;8976:33;:::i;9044:263::-;;9167:2;9155:9;9146:7;9142:23;9138:32;9135:2;;;9188:6;9180;9173:22;9135:2;9225:9;9219:16;9244:33;9271:5;9244:33;:::i;9584:717::-;;;;;;;9794:3;9782:9;9773:7;9769:23;9765:33;9762:2;;;9816:6;9808;9801:22;9762:2;9853:9;9847:16;9872:33;9899:5;9872:33;:::i;:::-;9924:5;9914:15;;;9969:2;9958:9;9954:18;9948:25;9938:35;;10013:2;10002:9;9998:18;9992:25;9982:35;;10057:2;10046:9;10042:18;10036:25;10026:35;;10106:3;10095:9;10091:19;10085:26;10120:32;10144:7;10120:32;:::i;:::-;10223:3;10208:19;;10202:26;10171:7;;-1:-1:-1;10237:32:1;10202:26;10237:32;:::i;:::-;10288:7;10278:17;;;9752:549;;;;;;;;:::o;10306:478::-;;;;10460:2;10448:9;10439:7;10435:23;10431:32;10428:2;;;10481:6;10473;10466:22;10428:2;10525:9;10512:23;10544:33;10571:5;10544:33;:::i;:::-;10596:5;-1:-1:-1;10653:2:1;10638:18;;10625:32;10666:35;10625:32;10666:35;:::i;:::-;10418:366;;10720:7;;-1:-1:-1;;;10774:2:1;10759:18;;;;10746:32;;10418:366::o;10789:910::-;;;;;;;10994:3;10982:9;10973:7;10969:23;10965:33;10962:2;;;11016:6;11008;11001:22;10962:2;11060:9;11047:23;11079:33;11106:5;11079:33;:::i;:::-;11131:5;-1:-1:-1;11188:2:1;11173:18;;11160:32;11201:35;11160:32;11201:35;:::i;:::-;11255:7;-1:-1:-1;11314:2:1;11299:18;;11286:32;11327:35;11286:32;11327:35;:::i;:::-;11381:7;-1:-1:-1;11440:2:1;11425:18;;11412:32;11453:35;11412:32;11453:35;:::i;:::-;11507:7;-1:-1:-1;11566:3:1;11551:19;;11538:33;11580:35;11538:33;11580:35;:::i;:::-;11634:7;11624:17;;;11688:3;11677:9;11673:19;11660:33;11650:43;;10952:747;;;;;;;;:::o;12179:1718::-;;;;;;;;;;;;12561:3;12549:9;12540:7;12536:23;12532:33;12529:2;;;12583:6;12575;12568:22;12529:2;12611:31;12632:9;12611:31;:::i;:::-;12601:41;;12661:40;12697:2;12686:9;12682:18;12661:40;:::i;:::-;12651:50;;12748:2;12737:9;12733:18;12720:32;12710:42;;12799:2;12788:9;12784:18;12771:32;12761:42;;12822:18;12890:2;12883:3;12872:9;12868:19;12855:33;12852:41;12849:2;;;12911:6;12903;12896:22;12849:2;12939:94;13025:7;13017:3;13006:9;13002:19;12989:33;12978:9;12974:49;12939:94;:::i;:::-;12929:104;;13083:2;13076:3;13065:9;13061:19;13048:33;13045:41;13042:2;;;13104:6;13096;13089:22;13042:2;13132:78;13202:7;13194:3;13183:9;13179:19;13166:33;13155:9;13151:49;13132:78;:::i;:::-;13122:88;;13260:2;13253:3;13242:9;13238:19;13225:33;13222:41;13219:2;;;13281:6;13273;13266:22;13219:2;13309:94;13395:7;13387:3;13376:9;13372:19;13359:33;13348:9;13344:49;13309:94;:::i;:::-;13299:104;;13453:2;13446:3;13435:9;13431:19;13418:33;13415:41;13412:2;;;13474:6;13466;13459:22;13412:2;13502:94;13588:7;13580:3;13569:9;13565:19;13552:33;13541:9;13537:49;13502:94;:::i;:::-;13492:104;;13615:41;13651:3;13640:9;13636:19;13615:41;:::i;:::-;13605:51;;13706:2;13699:3;13688:9;13684:19;13671:33;13668:41;13665:2;;;13727:6;13719;13712:22;13665:2;;13755:78;13825:7;13817:3;13806:9;13802:19;13789:33;13778:9;13774:49;13755:78;:::i;:::-;13745:88;;13853:38;13886:3;13875:9;13871:19;13853:38;:::i;:::-;13842:49;;12519:1378;;;;;;;;;;;;;;:::o;13902:1838::-;;;;;;;;;;;;;14302:3;14290:9;14281:7;14277:23;14273:33;14270:2;;;14324:6;14316;14309:22;14270:2;14352:31;14373:9;14352:31;:::i;:::-;14342:41;;14402:40;14438:2;14427:9;14423:18;14402:40;:::i;:::-;14392:50;;14489:2;14478:9;14474:18;14461:32;14451:42;;14540:2;14529:9;14525:18;14512:32;14502:42;;14591:3;14580:9;14576:19;14563:33;14553:43;;14646:18;14639:3;14628:9;14624:19;14611:33;14608:57;14605:2;;;14683:6;14675;14668:22;14605:2;14711:94;14797:7;14789:3;14778:9;14774:19;14761:33;14750:9;14746:49;14711:94;:::i;:::-;14701:104;;14855:18;14848:3;14837:9;14833:19;14820:33;14817:57;14814:2;;;14892:6;14884;14877:22;14814:2;14920:78;14990:7;14982:3;14971:9;14967:19;14954:33;14943:9;14939:49;14920:78;:::i;:::-;14910:88;;15048:18;15041:3;15030:9;15026:19;15013:33;15010:57;15007:2;;;15086:7;15077;15070:24;15007:2;15115:94;15201:7;15193:3;15182:9;15178:19;15165:33;15154:9;15150:49;15115:94;:::i;:::-;15105:104;;15259:18;15252:3;15241:9;15237:19;15224:33;15221:57;15218:2;;;15297:7;15288;15281:24;15218:2;15326:94;15412:7;15404:3;15393:9;15389:19;15376:33;15365:9;15361:49;15326:94;:::i;:::-;15316:104;;15439:41;15475:3;15464:9;15460:19;15439:41;:::i;:::-;15429:51;;15530:18;15523:3;15512:9;15508:19;15495:33;15492:57;15489:2;;;15568:7;15559;15552:24;15489:2;15598:78;15668:7;15660:3;15649:9;15645:19;15632:33;15621:9;15617:49;15598:78;:::i;:::-;15587:89;;15696:38;15729:3;15718:9;15714:19;15696:38;:::i;:::-;15685:49;;14260:1480;;;;;;;;;;;;;;:::o;15745:879::-;;;;;;;;15975:3;15963:9;15954:7;15950:23;15946:33;15943:2;;;15997:6;15989;15982:22;15943:2;16041:9;16028:23;16060:33;16087:5;16060:33;:::i;:::-;16112:5;-1:-1:-1;16164:2:1;16149:18;;16136:32;;-1:-1:-1;16215:2:1;16200:18;;16187:32;;-1:-1:-1;16266:2:1;16251:18;;16238:32;;-1:-1:-1;16321:3:1;16306:19;;16293:33;16349:18;16338:30;;16335:2;;;16386:6;16378;16371:22;16335:2;16430:76;16498:7;16489:6;16478:9;16474:22;16430:76;:::i;:::-;16525:8;;-1:-1:-1;16404:102:1;-1:-1:-1;16579:39:1;;-1:-1:-1;16613:3:1;16598:19;;16579:39;:::i;:::-;16569:49;;15933:691;;;;;;;;;;:::o;16629:778::-;;;;16777:2;16765:9;16756:7;16752:23;16748:32;16745:2;;;16798:6;16790;16783:22;16745:2;16842:9;16829:23;16861:33;16888:5;16861:33;:::i;:::-;16913:5;-1:-1:-1;16969:2:1;16954:18;;16941:32;16992:18;17022:14;;;17019:2;;;17054:6;17046;17039:22;17019:2;17097:6;17086:9;17082:22;17072:32;;17142:7;17135:4;17131:2;17127:13;17123:27;17113:2;;17169:6;17161;17154:22;17113:2;17214;17201:16;17240:2;17232:6;17229:14;17226:2;;;17261:6;17253;17246:22;17226:2;17311:7;17306:2;17297:6;17293:2;17289:15;17285:24;17282:37;17279:2;;;17337:6;17329;17322:22;17279:2;17373;17369;17365:11;17355:21;;17395:6;17385:16;;;;;16735:672;;;;;:::o;17412:257::-;;17532:2;17520:9;17511:7;17507:23;17503:32;17500:2;;;17553:6;17545;17538:22;17500:2;17590:9;17584:16;17609:30;17633:5;17609:30;:::i;17674:190::-;;17786:2;17774:9;17765:7;17761:23;17757:32;17754:2;;;17807:6;17799;17792:22;17754:2;-1:-1:-1;17835:23:1;;17744:120;-1:-1:-1;17744:120:1:o;17869:194::-;;17992:2;17980:9;17971:7;17967:23;17963:32;17960:2;;;18013:6;18005;17998:22;17960:2;-1:-1:-1;18041:16:1;;17950:113;-1:-1:-1;17950:113:1:o;18346:1262::-;;18482:2;18470:9;18461:7;18457:23;18453:32;18450:2;;;18503:6;18495;18488:22;18450:2;18548:9;18535:23;18577:18;18618:2;18610:6;18607:14;18604:2;;;18639:6;18631;18624:22;18604:2;18682:6;18671:9;18667:22;18657:32;;18708:6;18748:2;18743;18734:7;18730:16;18726:25;18723:2;;;18769:6;18761;18754:22;18723:2;18800:18;18815:2;18800:18;:::i;:::-;18787:31;;18841:24;18862:2;18841:24;:::i;:::-;18834:5;18827:39;18898:33;18927:2;18923;18919:11;18898:33;:::i;:::-;18893:2;18886:5;18882:14;18875:57;18985:2;18981;18977:11;18964:25;18959:2;18952:5;18948:14;18941:49;19043:2;19039;19035:11;19022:25;19017:2;19010:5;19006:14;18999:49;19081:34;19110:3;19106:2;19102:12;19081:34;:::i;:::-;19075:3;19068:5;19064:15;19057:59;19162:3;19158:2;19154:12;19141:26;19192:2;19182:8;19179:16;19176:2;;;19213:6;19205;19198:22;19176:2;19255:46;19293:7;19282:8;19278:2;19274:17;19255:46;:::i;:::-;19249:3;19242:5;19238:15;19231:71;;19335:31;19361:3;19357:2;19353:12;19335:31;:::i;:::-;19329:3;19322:5;19318:15;19311:56;19413:3;19409:2;19405:12;19392:26;19443:2;19433:8;19430:16;19427:2;;;19464:6;19456;19449:22;19427:2;19506:71;19569:7;19558:8;19554:2;19550:17;19506:71;:::i;:::-;19500:3;19489:15;;19482:96;-1:-1:-1;19493:5:1;18440:1168;-1:-1:-1;;;;;18440:1168:1:o;19613:1267::-;;19758:2;19746:9;19737:7;19733:23;19729:32;19726:2;;;19779:6;19771;19764:22;19726:2;19824:9;19811:23;19853:18;19894:2;19886:6;19883:14;19880:2;;;19915:6;19907;19900:22;19880:2;19958:6;19947:9;19943:22;19933:32;;19984:6;20024:2;20019;20010:7;20006:16;20002:25;19999:2;;;20045:6;20037;20030:22;19999:2;20076:18;20091:2;20076:18;:::i;:::-;20063:31;;20117:24;20138:2;20117:24;:::i;:::-;20110:5;20103:39;20195:2;20191;20187:11;20174:25;20169:2;20162:5;20158:14;20151:49;20253:2;20249;20245:11;20232:25;20227:2;20220:5;20216:14;20209:49;20311:2;20307;20303:11;20290:25;20285:2;20278:5;20274:14;20267:49;20349:34;20378:3;20374:2;20370:12;20349:34;:::i;:::-;20343:3;20336:5;20332:15;20325:59;20430:3;20426:2;20422:12;20409:26;20460:2;20450:8;20447:16;20444:2;;;20481:6;20473;20466:22;20444:2;20523:46;20561:7;20550:8;20546:2;20542:17;20523:46;:::i;:::-;20517:3;20510:5;20506:15;20499:71;;20603:31;20629:3;20625:2;20621:12;20603:31;:::i;:::-;20597:3;20590:5;20586:15;20579:56;20681:3;20677:2;20673:12;20660:26;20711:2;20701:8;20698:16;20695:2;;;20732:6;20724;20717:22;20695:2;20774:75;20841:7;20830:8;20826:2;20822:17;20774:75;:::i;20885:1251::-;;21022:2;21010:9;21001:7;20997:23;20993:32;20990:2;;;21043:6;21035;21028:22;20990:2;21088:9;21075:23;21117:18;21158:2;21150:6;21147:14;21144:2;;;21179:6;21171;21164:22;21144:2;21222:6;21211:9;21207:22;21197:32;;21248:6;21288:2;21283;21274:7;21270:16;21266:25;21263:2;;;21309:6;21301;21294:22;21263:2;21340:18;21355:2;21340:18;:::i;:::-;21327:31;;21381:24;21402:2;21381:24;:::i;:::-;21374:5;21367:39;21459:2;21455;21451:11;21438:25;21433:2;21426:5;21422:14;21415:49;21517:2;21513;21509:11;21496:25;21491:2;21484:5;21480:14;21473:49;21575:2;21571;21567:11;21554:25;21549:2;21542:5;21538:14;21531:49;21613:34;21642:3;21638:2;21634:12;21613:34;:::i;:::-;21607:3;21600:5;21596:15;21589:59;21694:3;21690:2;21686:12;21673:26;21724:2;21714:8;21711:16;21708:2;;;21745:6;21737;21730:22;21708:2;21787:46;21825:7;21814:8;21810:2;21806:17;21787:46;:::i;:::-;21781:3;21774:5;21770:15;21763:71;;21867:31;21893:3;21889:2;21885:12;21867:31;:::i;:::-;21861:3;21854:5;21850:15;21843:56;21945:3;21941:2;21937:12;21924:26;21975:2;21965:8;21962:16;21959:2;;;21996:6;21988;21981:22;21959:2;22038:67;22097:7;22086:8;22082:2;22078:17;22038:67;:::i;22340:672::-;;;;;;22536:3;22524:9;22515:7;22511:23;22507:33;22504:2;;;22558:6;22550;22543:22;22504:2;22599:9;22586:23;22576:33;;22656:2;22645:9;22641:18;22628:32;22618:42;;22711:2;22700:9;22696:18;22683:32;22738:18;22730:6;22727:30;22724:2;;;22775:6;22767;22760:22;22724:2;22819:76;22887:7;22878:6;22867:9;22863:22;22819:76;:::i;:::-;22914:8;;-1:-1:-1;22793:102:1;-1:-1:-1;22968:38:1;;-1:-1:-1;23002:2:1;22987:18;;22968:38;:::i;:::-;22958:48;;22494:518;;;;;;;;:::o;23017:555::-;;23123:6;23118:3;23111:19;23149:4;23178:2;23173:3;23169:12;23162:19;;23204:5;23227:3;23239:308;23253:6;23250:1;23247:13;23239:308;;;23330:6;23317:20;23350:35;23377:7;23350:35;:::i;:::-;-1:-1:-1;;;;;23410:56:1;23398:69;;23487:12;;;;23522:15;;;;23275:1;23268:9;23239:308;;;-1:-1:-1;23563:3:1;;23101:471;-1:-1:-1;;;;;23101:471:1:o;23577:318::-;;23658:5;23652:12;23685:6;23680:3;23673:19;23701:63;23757:6;23750:4;23745:3;23741:14;23734:4;23727:5;23723:16;23701:63;:::i;:::-;23809:2;23797:15;-1:-1:-1;;23793:88:1;23784:98;;;;23884:4;23780:109;;23628:267;-1:-1:-1;;23628:267:1:o;23900:274::-;;24067:6;24061:13;24083:53;24129:6;24124:3;24117:4;24109:6;24105:17;24083:53;:::i;:::-;24152:16;;;;;24037:137;-1:-1:-1;;24037:137:1:o;24179:205::-;24379:3;24370:14::o;24389:226::-;-1:-1:-1;;;;;24553:55:1;;;;24535:74;;24523:2;24508:18;;24490:125::o;24859:493::-;;-1:-1:-1;;;;;25104:6:1;25100:55;25089:9;25082:74;25192:6;25187:2;25176:9;25172:18;25165:34;25235:6;25230:2;25219:9;25215:18;25208:34;25278:3;25273:2;25262:9;25258:18;25251:31;25299:47;25341:3;25330:9;25326:19;25318:6;25299:47;:::i;:::-;25291:55;25072:280;-1:-1:-1;;;;;;25072:280:1:o;25357:565::-;;-1:-1:-1;;;;;25630:6:1;25626:55;25615:9;25608:74;25718:6;25713:2;25702:9;25698:18;25691:34;25761:6;25756:2;25745:9;25741:18;25734:34;25804:6;25799:2;25788:9;25784:18;25777:34;25848:3;25842;25831:9;25827:19;25820:32;25869:47;25911:3;25900:9;25896:19;25888:6;25869:47;:::i;25927:327::-;-1:-1:-1;;;;;26180:15:1;;;26162:34;;26232:15;;26227:2;26212:18;;26205:43;26089:2;26074:18;;26056:198::o;26259:495::-;-1:-1:-1;;;;;26585:15:1;;;26567:34;;26637:15;;;26632:2;26617:18;;26610:43;26689:15;;26684:2;26669:18;;26662:43;26736:2;26721:18;;26714:34;;;;26493:3;26478:19;;26460:294::o;26759:683::-;;-1:-1:-1;;;;;27125:2:1;27117:6;27113:15;27102:9;27095:34;27177:2;27169:6;27165:15;27160:2;27149:9;27145:18;27138:43;27217:6;27212:2;27201:9;27197:18;27190:34;27272:4;27264:6;27260:17;27255:2;27244:9;27240:18;27233:45;27327:2;27319:6;27315:15;27309:3;27298:9;27294:19;27287:44;;27368:3;27362;27351:9;27347:19;27340:32;27389:47;27431:3;27420:9;27416:19;27408:6;27389:47;:::i;27447:666::-;;-1:-1:-1;;;;;27807:2:1;27799:6;27795:15;27784:9;27777:34;27859:2;27851:6;27847:15;27842:2;27831:9;27827:18;27820:43;27899:6;27894:2;27883:9;27879:18;27872:34;27942:6;27937:2;27926:9;27922:18;27915:34;27998:2;27990:6;27986:15;27980:3;27969:9;27965:19;27958:44;;28039:3;28033;28022:9;28018:19;28011:32;28060:47;28102:3;28091:9;28087:19;28079:6;28060:47;:::i;28118:630::-;;-1:-1:-1;;;;;28423:6:1;28419:55;28408:9;28401:74;28511:6;28506:2;28495:9;28491:18;28484:34;28554:6;28549:2;28538:9;28534:18;28527:34;28597:6;28592:2;28581:9;28577:18;28570:34;28641:3;28635;28624:9;28620:19;28613:32;28662:80;28737:3;28726:9;28722:19;28714:6;28706;28662:80;:::i;28753:297::-;-1:-1:-1;;;;;28945:55:1;;;;28927:74;;29032:2;29017:18;;29010:34;28915:2;28900:18;;28882:168::o;29055:187::-;29220:14;;29213:22;29195:41;;29183:2;29168:18;;29150:92::o;29247:297::-;29421:25;;;-1:-1:-1;;;;;29482:55:1;29477:2;29462:18;;29455:83;29409:2;29394:18;;29376:168::o;29859:450::-;;30016:2;30005:9;29998:21;30055:6;30050:2;30039:9;30035:18;30028:34;30112:6;30104;30099:2;30088:9;30084:18;30071:48;30139:22;;;30163:2;30135:31;;;30128:45;;;;30225:2;30213:15;;;-1:-1:-1;;30209:88:1;30194:104;30190:113;;29988:321;-1:-1:-1;29988:321:1:o;30314:219::-;;30461:2;30450:9;30443:21;30481:46;30523:2;30512:9;30508:18;30500:6;30481:46;:::i;30764:348::-;30966:2;30948:21;;;31005:2;30985:18;;;30978:30;31044:26;31039:2;31024:18;;31017:54;31103:2;31088:18;;30938:174::o;31117:339::-;31319:2;31301:21;;;31358:2;31338:18;;;31331:30;31397:17;31392:2;31377:18;;31370:45;31447:2;31432:18;;31291:165::o;31461:418::-;31663:2;31645:21;;;31702:2;31682:18;;;31675:30;31741:34;31736:2;31721:18;;31714:62;31812:24;31807:2;31792:18;;31785:52;31869:3;31854:19;;31635:244::o;31884:402::-;32086:2;32068:21;;;32125:2;32105:18;;;32098:30;32164:34;32159:2;32144:18;;32137:62;32235:8;32230:2;32215:18;;32208:36;32276:3;32261:19;;32058:228::o;32291:351::-;32493:2;32475:21;;;32532:2;32512:18;;;32505:30;32571:29;32566:2;32551:18;;32544:57;32633:2;32618:18;;32465:177::o;32647:349::-;32849:2;32831:21;;;32888:2;32868:18;;;32861:30;32927:27;32922:2;32907:18;;32900:55;32987:2;32972:18;;32821:175::o;33001:404::-;33203:2;33185:21;;;33242:2;33222:18;;;33215:30;33281:34;33276:2;33261:18;;33254:62;33352:10;33347:2;33332:18;;33325:38;33395:3;33380:19;;33175:230::o;33410:419::-;33612:2;33594:21;;;33651:2;33631:18;;;33624:30;33690:34;33685:2;33670:18;;33663:62;33761:25;33756:2;33741:18;;33734:53;33819:3;33804:19;;33584:245::o;33834:352::-;34036:2;34018:21;;;34075:2;34055:18;;;34048:30;34114;34109:2;34094:18;;34087:58;34177:2;34162:18;;34008:178::o;34598:340::-;34800:2;34782:21;;;34839:2;34819:18;;;34812:30;34878:18;34873:2;34858:18;;34851:46;34929:2;34914:18;;34772:166::o;34943:350::-;35145:2;35127:21;;;35184:2;35164:18;;;35157:30;35223:28;35218:2;35203:18;;35196:56;35284:2;35269:18;;35117:176::o;35298:352::-;35500:2;35482:21;;;35539:2;35519:18;;;35512:30;35578;35573:2;35558:18;;35551:58;35641:2;35626:18;;35472:178::o;35655:346::-;35857:2;35839:21;;;35896:2;35876:18;;;35869:30;35935:24;35930:2;35915:18;;35908:52;35992:2;35977:18;;35829:172::o;36006:354::-;36208:2;36190:21;;;36247:2;36227:18;;;36220:30;36286:32;36281:2;36266:18;;36259:60;36351:2;36336:18;;36180:180::o;36365:348::-;36567:2;36549:21;;;36606:2;36586:18;;;36579:30;36645:26;36640:2;36625:18;;36618:54;36704:2;36689:18;;36539:174::o;36718:342::-;36920:2;36902:21;;;36959:2;36939:18;;;36932:30;36998:20;36993:2;36978:18;;36971:48;37051:2;37036:18;;36892:168::o;37065:397::-;37267:2;37249:21;;;37306:2;37286:18;;;37279:30;37345:34;37340:2;37325:18;;37318:62;37416:3;37411:2;37396:18;;37389:31;37452:3;37437:19;;37239:223::o;37467:343::-;37669:2;37651:21;;;37708:2;37688:18;;;37681:30;37747:21;37742:2;37727:18;;37720:49;37801:2;37786:18;;37641:169::o;37815:346::-;38017:2;37999:21;;;38056:2;38036:18;;;38029:30;38095:24;38090:2;38075:18;;38068:52;38152:2;38137:18;;37989:172::o;38166:356::-;38368:2;38350:21;;;38387:18;;;38380:30;38446:34;38441:2;38426:18;;38419:62;38513:2;38498:18;;38340:182::o;38527:355::-;38729:2;38711:21;;;38768:2;38748:18;;;38741:30;38807:33;38802:2;38787:18;;38780:61;38873:2;38858:18;;38701:181::o;38887:344::-;39089:2;39071:21;;;39128:2;39108:18;;;39101:30;39167:22;39162:2;39147:18;;39140:50;39222:2;39207:18;;39061:170::o;39236:412::-;39438:2;39420:21;;;39477:2;39457:18;;;39450:30;39516:34;39511:2;39496:18;;39489:62;39587:18;39582:2;39567:18;;39560:46;39638:3;39623:19;;39410:238::o;39653:353::-;39855:2;39837:21;;;39894:2;39874:18;;;39867:30;39933:31;39928:2;39913:18;;39906:59;39997:2;39982:18;;39827:179::o;40011:406::-;40213:2;40195:21;;;40252:2;40232:18;;;40225:30;40291:34;40286:2;40271:18;;40264:62;40362:12;40357:2;40342:18;;40335:40;40407:3;40392:19;;40185:232::o;40422:418::-;40624:2;40606:21;;;40663:2;40643:18;;;40636:30;40702:34;40697:2;40682:18;;40675:62;40773:24;40768:2;40753:18;;40746:52;40830:3;40815:19;;40596:244::o;40845:346::-;41047:2;41029:21;;;41086:2;41066:18;;;41059:30;41125:24;41120:2;41105:18;;41098:52;41182:2;41167:18;;41019:172::o;41196:177::-;41342:25;;;41330:2;41315:18;;41297:76::o;41378:436::-;;41623:6;41612:9;41605:25;41666:6;41661:2;41650:9;41646:18;41639:34;41709:2;41704;41693:9;41689:18;41682:30;41729:79;41804:2;41793:9;41789:18;41781:6;41773;41729:79;:::i;41819:319::-;42021:25;;;42077:2;42062:18;;42055:34;;;;42120:2;42105:18;;42098:34;42009:2;41994:18;;41976:162::o;42143:242::-;42213:2;42207:9;42243:17;;;42290:18;42275:34;;42311:22;;;42272:62;42269:2;;;42337:9;42269:2;42364;42357:22;42187:198;;-1:-1:-1;42187:198:1:o;42390:183::-;;42489:18;42481:6;42478:30;42475:2;;;42511:9;42475:2;-1:-1:-1;42562:4:1;42543:17;;;42539:28;;42465:108::o;42578:258::-;42650:1;42660:113;42674:6;42671:1;42668:13;42660:113;;;42750:11;;;42744:18;42731:11;;;42724:39;42696:2;42689:10;42660:113;;;42791:6;42788:1;42785:13;42782:2;;;-1:-1:-1;;42826:1:1;42808:16;;42801:27;42631:205::o;42841:156::-;-1:-1:-1;;;;;42922:5:1;42918:54;42911:5;42908:65;42898:2;;42987:1;42984;42977:12;42898:2;42888:109;:::o;43002:120::-;43090:5;43083:13;43076:21;43069:5;43066:32;43056:2;;43112:1;43109;43102:12

Swarm Source

ipfs://6313a958e5fd033a8dcd116b8902de6862ad7f1874fa0d683d889a4d142cdedd
Block Transaction Gas Used Reward
Age Block Fee Address BC Fee Address Voting Power Jailed Incoming
Block Uncle Number Difficulty Gas Used Reward
Loading
Loading
Make sure to use the "Vote Down" button for any spammy posts, and the "Vote Up" for interesting conversations.