Token HMX

 

Overview ERC20

Price
$7.33 @ 0.002413 ETH (+12.67%)
Fully Diluted Market Cap
Total Supply:
2,222,916.421428 HMX

Holders:
3,300 addresses
Contract:
0x83d6c8C06ac276465e4C92E7aC8C23740F4351400x83d6c8C06ac276465e4C92E7aC8C23740F435140

Decimals:
18

Official Site:

Social Profiles:

Filtered by Token Holder (HMX: HMX Token)

Balance
757.734756383861255227 HMX

Value
$5,554.20 ( ~1.8285 ETH) [0.0341%]
0x83d6c8c06ac276465e4c92e7ac8c23740f435140
Loading
[ Download CSV Export  ] 
Loading
[ Download CSV Export  ] 
Loading

OVERVIEW

HMX is a decentralized perpetual protocol with a cross-margin and multi-asset collateral support on Arbitrum.


Update? Click here to update the token ICO / general information
# Exchange Pair Price  24H Volume % Volume
1
Uniswap V3 (Arbitrum One)
0X83D6C8C06AC276465E4C92E7AC8C23740F435140-0X82AF49447D8A07E3BD95BD0D56F35241523FBAB1$7.32
0.0001152 Btc
$102,056.00
14,908.907 0X83D6C8C06AC276465E4C92E7AC8C23740F435140
94.3451%
2
Gate.io
HMX-USDT$7.55
0.0001188 Btc
$6,115.06
893.614 HMX
5.6549%

Contract Source Code Verified (Exact Match)

Contract Name:
RemoteHMX

Compiler Version
v0.8.18+commit.87f61d96

Optimization Enabled:
Yes with 1 runs

Other Settings:
default evmVersion, MIT license

Contract Source Code (Solidity Multiple files format)

File 21 of 21: RemoteHMX.sol
// SPDX-License-Identifier: MIT
//   _   _ __  ____  __
//  | | | |  \/  \ \/ /
//  | |_| | |\/| |\  /
//  |  _  | |  | |/  \
//  |_| |_|_|  |_/_/\_\
pragma solidity 0.8.18;

import {OFTV2} from "./OFTV2.sol";

contract RemoteHMX is OFTV2 {
  constructor(address _layerZeroEndpoint, uint8 _sharedDecimals)
    OFTV2("HMX", "HMX", _sharedDecimals, _layerZeroEndpoint)
  {}
}

File 1 of 21: BaseOFTV2.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

import "./OFTCoreV2.sol";
import "./IOFTV2.sol";
import "./ERC165.sol";

abstract contract BaseOFTV2 is OFTCoreV2, ERC165, IOFTV2 {
  constructor(uint8 _sharedDecimals, address _lzEndpoint)
    OFTCoreV2(_sharedDecimals, _lzEndpoint)
  {}

  /**
   *
   * public functions
   *
   */
  function sendFrom(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    LzCallParams calldata _callParams
  ) public payable virtual override {
    _send(
      _from,
      _dstChainId,
      _toAddress,
      _amount,
      _callParams.refundAddress,
      _callParams.zroPaymentAddress,
      _callParams.adapterParams
    );
  }

  function sendAndCall(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes calldata _payload,
    uint64 _dstGasForCall,
    LzCallParams calldata _callParams
  ) public payable virtual override {
    _sendAndCall(
      _from,
      _dstChainId,
      _toAddress,
      _amount,
      _payload,
      _dstGasForCall,
      _callParams.refundAddress,
      _callParams.zroPaymentAddress,
      _callParams.adapterParams
    );
  }

  /**
   *
   * public view functions
   *
   */
  function supportsInterface(bytes4 interfaceId)
    public
    view
    virtual
    override(ERC165, IERC165)
    returns (bool)
  {
    return interfaceId == type(IOFTV2).interfaceId
      || super.supportsInterface(interfaceId);
  }

  function estimateSendFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bool _useZro,
    bytes calldata _adapterParams
  ) public view virtual override returns (uint256 nativeFee, uint256 zroFee) {
    return _estimateSendFee(
      _dstChainId, _toAddress, _amount, _useZro, _adapterParams
    );
  }

  function estimateSendAndCallFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes calldata _payload,
    uint64 _dstGasForCall,
    bool _useZro,
    bytes calldata _adapterParams
  ) public view virtual override returns (uint256 nativeFee, uint256 zroFee) {
    return _estimateSendAndCallFee(
      _dstChainId,
      _toAddress,
      _amount,
      _payload,
      _dstGasForCall,
      _useZro,
      _adapterParams
    );
  }

  function circulatingSupply() public view virtual override returns (uint256);

  function token() public view virtual override returns (address);
}

File 2 of 21: BytesLib.sol
// SPDX-License-Identifier: Unlicense
/*
 * @title Solidity Bytes Arrays Utils
 * @author Gonçalo Sá <[email protected]>
 *
 * @dev Bytes tightly packed arrays utility library for ethereum contracts written in Solidity.
 *      The library lets you concatenate, slice and type cast bytes arrays both in memory and storage.
 */
pragma solidity >=0.8.0 <0.9.0;

library BytesLib {
  function concat(bytes memory _preBytes, bytes memory _postBytes)
    internal
    pure
    returns (bytes memory)
  {
    bytes memory tempBytes;

    assembly {
      // Get a location of some free memory and store it in tempBytes as
      // Solidity does for memory variables.
      tempBytes := mload(0x40)

      // Store the length of the first bytes array at the beginning of
      // the memory for tempBytes.
      let length := mload(_preBytes)
      mstore(tempBytes, length)

      // Maintain a memory counter for the current write location in the
      // temp bytes array by adding the 32 bytes for the array length to
      // the starting location.
      let mc := add(tempBytes, 0x20)
      // Stop copying when the memory counter reaches the length of the
      // first bytes array.
      let end := add(mc, length)

      for {
        // Initialize a copy counter to the start of the _preBytes data,
        // 32 bytes into its memory.
        let cc := add(_preBytes, 0x20)
      } lt(mc, end) {
        // Increase both counters by 32 bytes each iteration.
        mc := add(mc, 0x20)
        cc := add(cc, 0x20)
      } {
        // Write the _preBytes data into the tempBytes memory 32 bytes
        // at a time.
        mstore(mc, mload(cc))
      }

      // Add the length of _postBytes to the current length of tempBytes
      // and store it as the new length in the first 32 bytes of the
      // tempBytes memory.
      length := mload(_postBytes)
      mstore(tempBytes, add(length, mload(tempBytes)))

      // Move the memory counter back from a multiple of 0x20 to the
      // actual end of the _preBytes data.
      mc := end
      // Stop copying when the memory counter reaches the new combined
      // length of the arrays.
      end := add(mc, length)

      for { let cc := add(_postBytes, 0x20) } lt(mc, end) {
        mc := add(mc, 0x20)
        cc := add(cc, 0x20)
      } { mstore(mc, mload(cc)) }

      // Update the free-memory pointer by padding our last write location
      // to 32 bytes: add 31 bytes to the end of tempBytes to move to the
      // next 32 byte block, then round down to the nearest multiple of
      // 32. If the sum of the length of the two arrays is zero then add
      // one before rounding down to leave a blank 32 bytes (the length block with 0).
      mstore(
        0x40,
        and(
          add(add(end, iszero(add(length, mload(_preBytes)))), 31),
          not(31) // Round down to the nearest 32 bytes.
        )
      )
    }

    return tempBytes;
  }

  function concatStorage(bytes storage _preBytes, bytes memory _postBytes)
    internal
  {
    assembly {
      // Read the first 32 bytes of _preBytes storage, which is the length
      // of the array. (We don't need to use the offset into the slot
      // because arrays use the entire slot.)
      let fslot := sload(_preBytes.slot)
      // Arrays of 31 bytes or less have an even value in their slot,
      // while longer arrays have an odd value. The actual length is
      // the slot divided by two for odd values, and the lowest order
      // byte divided by two for even values.
      // If the slot is even, bitwise and the slot with 255 and divide by
      // two to get the length. If the slot is odd, bitwise and the slot
      // with -1 and divide by two.
      let slength :=
        div(and(fslot, sub(mul(0x100, iszero(and(fslot, 1))), 1)), 2)
      let mlength := mload(_postBytes)
      let newlength := add(slength, mlength)
      // slength can contain both the length and contents of the array
      // if length < 32 bytes so let's prepare for that
      // v. http://solidity.readthedocs.io/en/latest/miscellaneous.html#layout-of-state-variables-in-storage
      switch add(lt(slength, 32), lt(newlength, 32))
      case 2 {
        // Since the new array still fits in the slot, we just need to
        // update the contents of the slot.
        // uint256(bytes_storage) = uint256(bytes_storage) + uint256(bytes_memory) + new_length
        sstore(
          _preBytes.slot,
          // all the modifications to the slot are inside this
          // next block
          add(
            // we can just add to the slot contents because the
            // bytes we want to change are the LSBs
            fslot,
            add(
              mul(
                div(
                  // load the bytes from memory
                  mload(add(_postBytes, 0x20)),
                  // zero all bytes to the right
                  exp(0x100, sub(32, mlength))
                ),
                // and now shift left the number of bytes to
                // leave space for the length in the slot
                exp(0x100, sub(32, newlength))
              ),
              // increase length by the double of the memory
              // bytes length
              mul(mlength, 2)
            )
          )
        )
      }
      case 1 {
        // The stored value fits in the slot, but the combined value
        // will exceed it.
        // get the keccak hash to get the contents of the array
        mstore(0x0, _preBytes.slot)
        let sc := add(keccak256(0x0, 0x20), div(slength, 32))

        // save new length
        sstore(_preBytes.slot, add(mul(newlength, 2), 1))

        // The contents of the _postBytes array start 32 bytes into
        // the structure. Our first read should obtain the `submod`
        // bytes that can fit into the unused space in the last word
        // of the stored array. To get this, we read 32 bytes starting
        // from `submod`, so the data we read overlaps with the array
        // contents by `submod` bytes. Masking the lowest-order
        // `submod` bytes allows us to add that value directly to the
        // stored value.

        let submod := sub(32, slength)
        let mc := add(_postBytes, submod)
        let end := add(_postBytes, mlength)
        let mask := sub(exp(0x100, submod), 1)

        sstore(
          sc,
          add(
            and(
              fslot,
              0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00
            ),
            and(mload(mc), mask)
          )
        )

        for {
          mc := add(mc, 0x20)
          sc := add(sc, 1)
        } lt(mc, end) {
          sc := add(sc, 1)
          mc := add(mc, 0x20)
        } { sstore(sc, mload(mc)) }

        mask := exp(0x100, sub(mc, end))

        sstore(sc, mul(div(mload(mc), mask), mask))
      }
      default {
        // get the keccak hash to get the contents of the array
        mstore(0x0, _preBytes.slot)
        // Start copying to the last used word of the stored array.
        let sc := add(keccak256(0x0, 0x20), div(slength, 32))

        // save new length
        sstore(_preBytes.slot, add(mul(newlength, 2), 1))

        // Copy over the first `submod` bytes of the new data as in
        // case 1 above.
        let slengthmod := mod(slength, 32)
        let mlengthmod := mod(mlength, 32)
        let submod := sub(32, slengthmod)
        let mc := add(_postBytes, submod)
        let end := add(_postBytes, mlength)
        let mask := sub(exp(0x100, submod), 1)

        sstore(sc, add(sload(sc), and(mload(mc), mask)))

        for {
          sc := add(sc, 1)
          mc := add(mc, 0x20)
        } lt(mc, end) {
          sc := add(sc, 1)
          mc := add(mc, 0x20)
        } { sstore(sc, mload(mc)) }

        mask := exp(0x100, sub(mc, end))

        sstore(sc, mul(div(mload(mc), mask), mask))
      }
    }
  }

  function slice(bytes memory _bytes, uint256 _start, uint256 _length)
    internal
    pure
    returns (bytes memory)
  {
    require(_length + 31 >= _length, "slice_overflow");
    require(_bytes.length >= _start + _length, "slice_outOfBounds");

    bytes memory tempBytes;

    assembly {
      switch iszero(_length)
      case 0 {
        // Get a location of some free memory and store it in tempBytes as
        // Solidity does for memory variables.
        tempBytes := mload(0x40)

        // The first word of the slice result is potentially a partial
        // word read from the original array. To read it, we calculate
        // the length of that partial word and start copying that many
        // bytes into the array. The first word we copy will start with
        // data we don't care about, but the last `lengthmod` bytes will
        // land at the beginning of the contents of the new array. When
        // we're done copying, we overwrite the full first word with
        // the actual length of the slice.
        let lengthmod := and(_length, 31)

        // The multiplication in the next line is necessary
        // because when slicing multiples of 32 bytes (lengthmod == 0)
        // the following copy loop was copying the origin's length
        // and then ending prematurely not copying everything it should.
        let mc := add(add(tempBytes, lengthmod), mul(0x20, iszero(lengthmod)))
        let end := add(mc, _length)

        for {
          // The multiplication in the next line has the same exact purpose
          // as the one above.
          let cc :=
            add(add(add(_bytes, lengthmod), mul(0x20, iszero(lengthmod))), _start)
        } lt(mc, end) {
          mc := add(mc, 0x20)
          cc := add(cc, 0x20)
        } { mstore(mc, mload(cc)) }

        mstore(tempBytes, _length)

        //update free-memory pointer
        //allocating the array padded to 32 bytes like the compiler does now
        mstore(0x40, and(add(mc, 31), not(31)))
      }
      //if we want a zero-length slice let's just return a zero-length array
      default {
        tempBytes := mload(0x40)
        //zero out the 32 bytes slice we are about to return
        //we need to do it because Solidity does not garbage collect
        mstore(tempBytes, 0)

        mstore(0x40, add(tempBytes, 0x20))
      }
    }

    return tempBytes;
  }

  function toAddress(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (address)
  {
    require(_bytes.length >= _start + 20, "toAddress_outOfBounds");
    address tempAddress;

    assembly {
      tempAddress :=
        div(mload(add(add(_bytes, 0x20), _start)), 0x1000000000000000000000000)
    }

    return tempAddress;
  }

  function toUint8(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint8)
  {
    require(_bytes.length >= _start + 1, "toUint8_outOfBounds");
    uint8 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x1), _start))
    }

    return tempUint;
  }

  function toUint16(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint16)
  {
    require(_bytes.length >= _start + 2, "toUint16_outOfBounds");
    uint16 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x2), _start))
    }

    return tempUint;
  }

  function toUint32(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint32)
  {
    require(_bytes.length >= _start + 4, "toUint32_outOfBounds");
    uint32 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x4), _start))
    }

    return tempUint;
  }

  function toUint64(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint64)
  {
    require(_bytes.length >= _start + 8, "toUint64_outOfBounds");
    uint64 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x8), _start))
    }

    return tempUint;
  }

  function toUint96(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint96)
  {
    require(_bytes.length >= _start + 12, "toUint96_outOfBounds");
    uint96 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0xc), _start))
    }

    return tempUint;
  }

  function toUint128(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint128)
  {
    require(_bytes.length >= _start + 16, "toUint128_outOfBounds");
    uint128 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x10), _start))
    }

    return tempUint;
  }

  function toUint256(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (uint256)
  {
    require(_bytes.length >= _start + 32, "toUint256_outOfBounds");
    uint256 tempUint;

    assembly {
      tempUint := mload(add(add(_bytes, 0x20), _start))
    }

    return tempUint;
  }

  function toBytes32(bytes memory _bytes, uint256 _start)
    internal
    pure
    returns (bytes32)
  {
    require(_bytes.length >= _start + 32, "toBytes32_outOfBounds");
    bytes32 tempBytes32;

    assembly {
      tempBytes32 := mload(add(add(_bytes, 0x20), _start))
    }

    return tempBytes32;
  }

  function equal(bytes memory _preBytes, bytes memory _postBytes)
    internal
    pure
    returns (bool)
  {
    bool success = true;

    assembly {
      let length := mload(_preBytes)

      // if lengths don't match the arrays are not equal
      switch eq(length, mload(_postBytes))
      case 1 {
        // cb is a circuit breaker in the for loop since there's
        //  no said feature for inline assembly loops
        // cb = 1 - don't breaker
        // cb = 0 - break
        let cb := 1

        let mc := add(_preBytes, 0x20)
        let end := add(mc, length)

        for { let cc := add(_postBytes, 0x20) }
        // the next line is the loop condition:
        // while(uint256(mc < end) + cb == 2)
        eq(add(lt(mc, end), cb), 2) {
          mc := add(mc, 0x20)
          cc := add(cc, 0x20)
        } {
          // if any of these checks fails then arrays are not equal
          if iszero(eq(mload(mc), mload(cc))) {
            // unsuccess:
            success := 0
            cb := 0
          }
        }
      }
      default {
        // unsuccess:
        success := 0
      }
    }

    return success;
  }

  function equalStorage(bytes storage _preBytes, bytes memory _postBytes)
    internal
    view
    returns (bool)
  {
    bool success = true;

    assembly {
      // we know _preBytes_offset is 0
      let fslot := sload(_preBytes.slot)
      // Decode the length of the stored array like in concatStorage().
      let slength :=
        div(and(fslot, sub(mul(0x100, iszero(and(fslot, 1))), 1)), 2)
      let mlength := mload(_postBytes)

      // if lengths don't match the arrays are not equal
      switch eq(slength, mlength)
      case 1 {
        // slength can contain both the length and contents of the array
        // if length < 32 bytes so let's prepare for that
        // v. http://solidity.readthedocs.io/en/latest/miscellaneous.html#layout-of-state-variables-in-storage
        if iszero(iszero(slength)) {
          switch lt(slength, 32)
          case 1 {
            // blank the last byte which is the length
            fslot := mul(div(fslot, 0x100), 0x100)

            if iszero(eq(fslot, mload(add(_postBytes, 0x20)))) {
              // unsuccess:
              success := 0
            }
          }
          default {
            // cb is a circuit breaker in the for loop since there's
            //  no said feature for inline assembly loops
            // cb = 1 - don't breaker
            // cb = 0 - break
            let cb := 1

            // get the keccak hash to get the contents of the array
            mstore(0x0, _preBytes.slot)
            let sc := keccak256(0x0, 0x20)

            let mc := add(_postBytes, 0x20)
            let end := add(mc, mlength)

            // the next line is the loop condition:
            // while(uint256(mc < end) + cb == 2)
            for {} eq(add(lt(mc, end), cb), 2) {
              sc := add(sc, 1)
              mc := add(mc, 0x20)
            } {
              if iszero(eq(sload(sc), mload(mc))) {
                // unsuccess:
                success := 0
                cb := 0
              }
            }
          }
        }
      }
      default {
        // unsuccess:
        success := 0
      }
    }

    return success;
  }
}

File 3 of 21: Context.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)

pragma solidity ^0.8.0;

/**
 * @dev Provides information about the current execution context, including the
 * sender of the transaction and its data. While these are generally available
 * via msg.sender and msg.data, they should not be accessed in such a direct
 * manner, since when dealing with meta-transactions the account sending and
 * paying for execution may not be the actual sender (as far as an application
 * is concerned).
 *
 * This contract is only required for intermediate, library-like contracts.
 */
abstract contract Context {
  function _msgSender() internal view virtual returns (address) {
    return msg.sender;
  }

  function _msgData() internal view virtual returns (bytes calldata) {
    return msg.data;
  }
}

File 4 of 21: ERC165.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/introspection/ERC165.sol)

pragma solidity ^0.8.0;

import "./IERC165.sol";

/**
 * @dev Implementation of the {IERC165} interface.
 *
 * Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check
 * for the additional interface id that will be supported. For example:
 *
 * ```solidity
 * function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
 *     return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId);
 * }
 * ```
 *
 * Alternatively, {ERC165Storage} provides an easier to use but more expensive implementation.
 */
abstract contract ERC165 is IERC165 {
  /**
   * @dev See {IERC165-supportsInterface}.
   */
  function supportsInterface(bytes4 interfaceId)
    public
    view
    virtual
    override
    returns (bool)
  {
    return interfaceId == type(IERC165).interfaceId;
  }
}

File 5 of 21: ERC20.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (token/ERC20/ERC20.sol)

pragma solidity ^0.8.0;

import "./IERC20.sol";
import "./IERC20Metadata.sol";
import "./Context.sol";

/**
 * @dev Implementation of the {IERC20} interface.
 *
 * This implementation is agnostic to the way tokens are created. This means
 * that a supply mechanism has to be added in a derived contract using {_mint}.
 * For a generic mechanism see {ERC20PresetMinterPauser}.
 *
 * TIP: For a detailed writeup see our guide
 * https://forum.openzeppelin.com/t/how-to-implement-erc20-supply-mechanisms/226[How
 * to implement supply mechanisms].
 *
 * We have followed general OpenZeppelin Contracts guidelines: functions revert
 * instead returning `false` on failure. This behavior is nonetheless
 * conventional and does not conflict with the expectations of ERC20
 * applications.
 *
 * Additionally, an {Approval} event is emitted on calls to {transferFrom}.
 * This allows applications to reconstruct the allowance for all accounts just
 * by listening to said events. Other implementations of the EIP may not emit
 * these events, as it isn't required by the specification.
 *
 * Finally, the non-standard {decreaseAllowance} and {increaseAllowance}
 * functions have been added to mitigate the well-known issues around setting
 * allowances. See {IERC20-approve}.
 */
contract ERC20 is Context, IERC20, IERC20Metadata {
  mapping(address => uint256) private _balances;

  mapping(address => mapping(address => uint256)) private _allowances;

  uint256 private _totalSupply;

  string private _name;
  string private _symbol;

  /**
   * @dev Sets the values for {name} and {symbol}.
   *
   * The default value of {decimals} is 18. To select a different value for
   * {decimals} you should overload it.
   *
   * All two of these values are immutable: they can only be set once during
   * construction.
   */
  constructor(string memory name_, string memory symbol_) {
    _name = name_;
    _symbol = symbol_;
  }

  /**
   * @dev Returns the name of the token.
   */
  function name() public view virtual override returns (string memory) {
    return _name;
  }

  /**
   * @dev Returns the symbol of the token, usually a shorter version of the
   * name.
   */
  function symbol() public view virtual override returns (string memory) {
    return _symbol;
  }

  /**
   * @dev Returns the number of decimals used to get its user representation.
   * For example, if `decimals` equals `2`, a balance of `505` tokens should
   * be displayed to a user as `5.05` (`505 / 10 ** 2`).
   *
   * Tokens usually opt for a value of 18, imitating the relationship between
   * Ether and Wei. This is the value {ERC20} uses, unless this function is
   * overridden;
   *
   * NOTE: This information is only used for _display_ purposes: it in
   * no way affects any of the arithmetic of the contract, including
   * {IERC20-balanceOf} and {IERC20-transfer}.
   */
  function decimals() public view virtual override returns (uint8) {
    return 18;
  }

  /**
   * @dev See {IERC20-totalSupply}.
   */
  function totalSupply() public view virtual override returns (uint256) {
    return _totalSupply;
  }

  /**
   * @dev See {IERC20-balanceOf}.
   */
  function balanceOf(address account)
    public
    view
    virtual
    override
    returns (uint256)
  {
    return _balances[account];
  }

  /**
   * @dev See {IERC20-transfer}.
   *
   * Requirements:
   *
   * - `to` cannot be the zero address.
   * - the caller must have a balance of at least `amount`.
   */
  function transfer(address to, uint256 amount)
    public
    virtual
    override
    returns (bool)
  {
    address owner = _msgSender();
    _transfer(owner, to, amount);
    return true;
  }

  /**
   * @dev See {IERC20-allowance}.
   */
  function allowance(address owner, address spender)
    public
    view
    virtual
    override
    returns (uint256)
  {
    return _allowances[owner][spender];
  }

  /**
   * @dev See {IERC20-approve}.
   *
   * NOTE: If `amount` is the maximum `uint256`, the allowance is not updated on
   * `transferFrom`. This is semantically equivalent to an infinite approval.
   *
   * Requirements:
   *
   * - `spender` cannot be the zero address.
   */
  function approve(address spender, uint256 amount)
    public
    virtual
    override
    returns (bool)
  {
    address owner = _msgSender();
    _approve(owner, spender, amount);
    return true;
  }

  /**
   * @dev See {IERC20-transferFrom}.
   *
   * Emits an {Approval} event indicating the updated allowance. This is not
   * required by the EIP. See the note at the beginning of {ERC20}.
   *
   * NOTE: Does not update the allowance if the current allowance
   * is the maximum `uint256`.
   *
   * Requirements:
   *
   * - `from` and `to` cannot be the zero address.
   * - `from` must have a balance of at least `amount`.
   * - the caller must have allowance for ``from``'s tokens of at least
   * `amount`.
   */
  function transferFrom(address from, address to, uint256 amount)
    public
    virtual
    override
    returns (bool)
  {
    address spender = _msgSender();
    _spendAllowance(from, spender, amount);
    _transfer(from, to, amount);
    return true;
  }

  /**
   * @dev Atomically increases the allowance granted to `spender` by the caller.
   *
   * This is an alternative to {approve} that can be used as a mitigation for
   * problems described in {IERC20-approve}.
   *
   * Emits an {Approval} event indicating the updated allowance.
   *
   * Requirements:
   *
   * - `spender` cannot be the zero address.
   */
  function increaseAllowance(address spender, uint256 addedValue)
    public
    virtual
    returns (bool)
  {
    address owner = _msgSender();
    _approve(owner, spender, allowance(owner, spender) + addedValue);
    return true;
  }

  /**
   * @dev Atomically decreases the allowance granted to `spender` by the caller.
   *
   * This is an alternative to {approve} that can be used as a mitigation for
   * problems described in {IERC20-approve}.
   *
   * Emits an {Approval} event indicating the updated allowance.
   *
   * Requirements:
   *
   * - `spender` cannot be the zero address.
   * - `spender` must have allowance for the caller of at least
   * `subtractedValue`.
   */
  function decreaseAllowance(address spender, uint256 subtractedValue)
    public
    virtual
    returns (bool)
  {
    address owner = _msgSender();
    uint256 currentAllowance = allowance(owner, spender);
    require(
      currentAllowance >= subtractedValue,
      "ERC20: decreased allowance below zero"
    );
    unchecked {
      _approve(owner, spender, currentAllowance - subtractedValue);
    }

    return true;
  }

  /**
   * @dev Moves `amount` of tokens from `from` to `to`.
   *
   * This internal function is equivalent to {transfer}, and can be used to
   * e.g. implement automatic token fees, slashing mechanisms, etc.
   *
   * Emits a {Transfer} event.
   *
   * Requirements:
   *
   * - `from` cannot be the zero address.
   * - `to` cannot be the zero address.
   * - `from` must have a balance of at least `amount`.
   */
  function _transfer(address from, address to, uint256 amount) internal virtual {
    require(from != address(0), "ERC20: transfer from the zero address");
    require(to != address(0), "ERC20: transfer to the zero address");

    _beforeTokenTransfer(from, to, amount);

    uint256 fromBalance = _balances[from];
    require(fromBalance >= amount, "ERC20: transfer amount exceeds balance");
    unchecked {
      _balances[from] = fromBalance - amount;
      // Overflow not possible: the sum of all balances is capped by totalSupply, and the sum is preserved by
      // decrementing then incrementing.
      _balances[to] += amount;
    }

    emit Transfer(from, to, amount);

    _afterTokenTransfer(from, to, amount);
  }

  /**
   * @dev Creates `amount` tokens and assigns them to `account`, increasing
   * the total supply.
   *
   * Emits a {Transfer} event with `from` set to the zero address.
   *
   * Requirements:
   *
   * - `account` cannot be the zero address.
   */
  function _mint(address account, uint256 amount) internal virtual {
    require(account != address(0), "ERC20: mint to the zero address");

    _beforeTokenTransfer(address(0), account, amount);

    _totalSupply += amount;
    unchecked {
      // Overflow not possible: balance + amount is at most totalSupply + amount, which is checked above.
      _balances[account] += amount;
    }
    emit Transfer(address(0), account, amount);

    _afterTokenTransfer(address(0), account, amount);
  }

  /**
   * @dev Destroys `amount` tokens from `account`, reducing the
   * total supply.
   *
   * Emits a {Transfer} event with `to` set to the zero address.
   *
   * Requirements:
   *
   * - `account` cannot be the zero address.
   * - `account` must have at least `amount` tokens.
   */
  function _burn(address account, uint256 amount) internal virtual {
    require(account != address(0), "ERC20: burn from the zero address");

    _beforeTokenTransfer(account, address(0), amount);

    uint256 accountBalance = _balances[account];
    require(accountBalance >= amount, "ERC20: burn amount exceeds balance");
    unchecked {
      _balances[account] = accountBalance - amount;
      // Overflow not possible: amount <= accountBalance <= totalSupply.
      _totalSupply -= amount;
    }

    emit Transfer(account, address(0), amount);

    _afterTokenTransfer(account, address(0), amount);
  }

  /**
   * @dev Sets `amount` as the allowance of `spender` over the `owner` s tokens.
   *
   * This internal function is equivalent to `approve`, and can be used to
   * e.g. set automatic allowances for certain subsystems, etc.
   *
   * Emits an {Approval} event.
   *
   * Requirements:
   *
   * - `owner` cannot be the zero address.
   * - `spender` cannot be the zero address.
   */
  function _approve(address owner, address spender, uint256 amount)
    internal
    virtual
  {
    require(owner != address(0), "ERC20: approve from the zero address");
    require(spender != address(0), "ERC20: approve to the zero address");

    _allowances[owner][spender] = amount;
    emit Approval(owner, spender, amount);
  }

  /**
   * @dev Updates `owner` s allowance for `spender` based on spent `amount`.
   *
   * Does not update the allowance amount in case of infinite allowance.
   * Revert if not enough allowance is available.
   *
   * Might emit an {Approval} event.
   */
  function _spendAllowance(address owner, address spender, uint256 amount)
    internal
    virtual
  {
    uint256 currentAllowance = allowance(owner, spender);
    if (currentAllowance != type(uint256).max) {
      require(currentAllowance >= amount, "ERC20: insufficient allowance");
      unchecked {
        _approve(owner, spender, currentAllowance - amount);
      }
    }
  }

  /**
   * @dev Hook that is called before any transfer of tokens. This includes
   * minting and burning.
   *
   * Calling conditions:
   *
   * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens
   * will be transferred to `to`.
   * - when `from` is zero, `amount` tokens will be minted for `to`.
   * - when `to` is zero, `amount` of ``from``'s tokens will be burned.
   * - `from` and `to` are never both zero.
   *
   * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
   */
  function _beforeTokenTransfer(address from, address to, uint256 amount)
    internal
    virtual
  {}

  /**
   * @dev Hook that is called after any transfer of tokens. This includes
   * minting and burning.
   *
   * Calling conditions:
   *
   * - when `from` and `to` are both non-zero, `amount` of ``from``'s tokens
   * has been transferred to `to`.
   * - when `from` is zero, `amount` tokens have been minted for `to`.
   * - when `to` is zero, `amount` of ``from``'s tokens have been burned.
   * - `from` and `to` are never both zero.
   *
   * To learn more about hooks, head to xref:ROOT:extending-contracts.adoc#using-hooks[Using Hooks].
   */
  function _afterTokenTransfer(address from, address to, uint256 amount)
    internal
    virtual
  {}
}

File 6 of 21: ExcessivelySafeCall.sol
// SPDX-License-Identifier: MIT OR Apache-2.0
pragma solidity >=0.7.6;

library ExcessivelySafeCall {
  uint256 constant LOW_28_MASK =
    0x00000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffff;

  /// @notice Use when you _really_ really _really_ don't trust the called
  /// contract. This prevents the called contract from causing reversion of
  /// the caller in as many ways as we can.
  /// @dev The main difference between this and a solidity low-level call is
  /// that we limit the number of bytes that the callee can cause to be
  /// copied to caller memory. This prevents stupid things like malicious
  /// contracts returning 10,000,000 bytes causing a local OOG when copying
  /// to memory.
  /// @param _target The address to call
  /// @param _gas The amount of gas to forward to the remote contract
  /// @param _maxCopy The maximum number of bytes of returndata to copy
  /// to memory.
  /// @param _calldata The data to send to the remote contract
  /// @return success and returndata, as `.call()`. Returndata is capped to
  /// `_maxCopy` bytes.
  function excessivelySafeCall(
    address _target,
    uint256 _gas,
    uint16 _maxCopy,
    bytes memory _calldata
  ) internal returns (bool, bytes memory) {
    // set up for assembly call
    uint256 _toCopy;
    bool _success;
    bytes memory _returnData = new bytes(_maxCopy);
    // dispatch message to recipient
    // by assembly calling "handle" function
    // we call via assembly to avoid memcopying a very large returndata
    // returned by a malicious contract
    assembly {
      _success :=
        call(
          _gas, // gas
          _target, // recipient
          0, // ether value
          add(_calldata, 0x20), // inloc
          mload(_calldata), // inlen
          0, // outloc
          0 // outlen
        )
      // limit our copy to 256 bytes
      _toCopy := returndatasize()
      if gt(_toCopy, _maxCopy) { _toCopy := _maxCopy }
      // Store the length of the copied bytes
      mstore(_returnData, _toCopy)
      // copy the bytes from returndata[0:_toCopy]
      returndatacopy(add(_returnData, 0x20), 0, _toCopy)
    }
    return (_success, _returnData);
  }

  /// @notice Use when you _really_ really _really_ don't trust the called
  /// contract. This prevents the called contract from causing reversion of
  /// the caller in as many ways as we can.
  /// @dev The main difference between this and a solidity low-level call is
  /// that we limit the number of bytes that the callee can cause to be
  /// copied to caller memory. This prevents stupid things like malicious
  /// contracts returning 10,000,000 bytes causing a local OOG when copying
  /// to memory.
  /// @param _target The address to call
  /// @param _gas The amount of gas to forward to the remote contract
  /// @param _maxCopy The maximum number of bytes of returndata to copy
  /// to memory.
  /// @param _calldata The data to send to the remote contract
  /// @return success and returndata, as `.call()`. Returndata is capped to
  /// `_maxCopy` bytes.
  function excessivelySafeStaticCall(
    address _target,
    uint256 _gas,
    uint16 _maxCopy,
    bytes memory _calldata
  ) internal view returns (bool, bytes memory) {
    // set up for assembly call
    uint256 _toCopy;
    bool _success;
    bytes memory _returnData = new bytes(_maxCopy);
    // dispatch message to recipient
    // by assembly calling "handle" function
    // we call via assembly to avoid memcopying a very large returndata
    // returned by a malicious contract
    assembly {
      _success :=
        staticcall(
          _gas, // gas
          _target, // recipient
          add(_calldata, 0x20), // inloc
          mload(_calldata), // inlen
          0, // outloc
          0 // outlen
        )
      // limit our copy to 256 bytes
      _toCopy := returndatasize()
      if gt(_toCopy, _maxCopy) { _toCopy := _maxCopy }
      // Store the length of the copied bytes
      mstore(_returnData, _toCopy)
      // copy the bytes from returndata[0:_toCopy]
      returndatacopy(add(_returnData, 0x20), 0, _toCopy)
    }
    return (_success, _returnData);
  }

  /**
   * @notice Swaps function selectors in encoded contract calls
   * @dev Allows reuse of encoded calldata for functions with identical
   * argument types but different names. It simply swaps out the first 4 bytes
   * for the new selector. This function modifies memory in place, and should
   * only be used with caution.
   * @param _newSelector The new 4-byte selector
   * @param _buf The encoded contract args
   */
  function swapSelector(bytes4 _newSelector, bytes memory _buf) internal pure {
    require(_buf.length >= 4);
    uint256 _mask = LOW_28_MASK;
    assembly {
      // load the first word of
      let _word := mload(add(_buf, 0x20))
      // mask out the top 4 bytes
      // /x
      _word := and(_word, _mask)
      _word := or(_newSelector, _word)
      mstore(add(_buf, 0x20), _word)
    }
  }
}

File 7 of 21: ICommonOFT.sol
// SPDX-License-Identifier: MIT

pragma solidity >=0.5.0;

import "./IERC165.sol";

/**
 * @dev Interface of the IOFT core standard
 */
interface ICommonOFT is IERC165 {
  struct LzCallParams {
    address payable refundAddress;
    address zroPaymentAddress;
    bytes adapterParams;
  }

  /**
   * @dev estimate send token `_tokenId` to (`_dstChainId`, `_toAddress`)
   * _dstChainId - L0 defined chain id to send tokens too
   * _toAddress - dynamic bytes array which contains the address to whom you are sending tokens to on the dstChain
   * _amount - amount of the tokens to transfer
   * _useZro - indicates to use zro to pay L0 fees
   * _adapterParam - flexible bytes array to indicate messaging adapter services in L0
   */
  function estimateSendFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bool _useZro,
    bytes calldata _adapterParams
  ) external view returns (uint256 nativeFee, uint256 zroFee);

  function estimateSendAndCallFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes calldata _payload,
    uint64 _dstGasForCall,
    bool _useZro,
    bytes calldata _adapterParams
  ) external view returns (uint256 nativeFee, uint256 zroFee);

  /**
   * @dev returns the circulating amount of tokens on current chain
   */
  function circulatingSupply() external view returns (uint256);

  /**
   * @dev returns the address of the ERC20 token
   */
  function token() external view returns (address);
}

File 8 of 21: IERC165.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/introspection/IERC165.sol)

pragma solidity ^0.8.0;

/**
 * @dev Interface of the ERC165 standard, as defined in the
 * https://eips.ethereum.org/EIPS/eip-165[EIP].
 *
 * Implementers can declare support of contract interfaces, which can then be
 * queried by others ({ERC165Checker}).
 *
 * For an implementation, see {ERC165}.
 */
interface IERC165 {
  /**
   * @dev Returns true if this contract implements the interface defined by
   * `interfaceId`. See the corresponding
   * https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]
   * to learn more about how these ids are created.
   *
   * This function call must use less than 30 000 gas.
   */
  function supportsInterface(bytes4 interfaceId) external view returns (bool);
}

File 9 of 21: IERC20.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol)

pragma solidity ^0.8.0;

/**
 * @dev Interface of the ERC20 standard as defined in the EIP.
 */
interface IERC20 {
  /**
   * @dev Emitted when `value` tokens are moved from one account (`from`) to
   * another (`to`).
   *
   * Note that `value` may be zero.
   */
  event Transfer(address indexed from, address indexed to, uint256 value);

  /**
   * @dev Emitted when the allowance of a `spender` for an `owner` is set by
   * a call to {approve}. `value` is the new allowance.
   */
  event Approval(address indexed owner, address indexed spender, uint256 value);

  /**
   * @dev Returns the amount of tokens in existence.
   */
  function totalSupply() external view returns (uint256);

  /**
   * @dev Returns the amount of tokens owned by `account`.
   */
  function balanceOf(address account) external view returns (uint256);

  /**
   * @dev Moves `amount` tokens from the caller's account to `to`.
   *
   * Returns a boolean value indicating whether the operation succeeded.
   *
   * Emits a {Transfer} event.
   */
  function transfer(address to, uint256 amount) external returns (bool);

  /**
   * @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 `from` to `to` 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 from, address to, uint256 amount)
    external
    returns (bool);
}

File 10 of 21: IERC20Metadata.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/IERC20Metadata.sol)

pragma solidity ^0.8.0;

import "./IERC20.sol";

/**
 * @dev Interface for the optional metadata functions from the ERC20 standard.
 *
 * _Available since v4.1._
 */
interface IERC20Metadata is IERC20 {
  /**
   * @dev Returns the name of the token.
   */
  function name() external view returns (string memory);

  /**
   * @dev Returns the symbol of the token.
   */
  function symbol() external view returns (string memory);

  /**
   * @dev Returns the decimals places of the token.
   */
  function decimals() external view returns (uint8);
}

File 11 of 21: ILayerZeroEndpoint.sol
// SPDX-License-Identifier: MIT

pragma solidity >=0.5.0;

import "./ILayerZeroUserApplicationConfig.sol";

interface ILayerZeroEndpoint is ILayerZeroUserApplicationConfig {
  // @notice send a LayerZero message to the specified address at a LayerZero endpoint.
  // @param _dstChainId - the destination chain identifier
  // @param _destination - the address on destination chain (in bytes). address length/format may vary by chains
  // @param _payload - a custom bytes payload to send to the destination contract
  // @param _refundAddress - if the source transaction is cheaper than the amount of value passed, refund the additional amount to this address
  // @param _zroPaymentAddress - the address of the ZRO token holder who would pay for the transaction
  // @param _adapterParams - parameters for custom functionality. e.g. receive airdropped native gas from the relayer on destination
  function send(
    uint16 _dstChainId,
    bytes calldata _destination,
    bytes calldata _payload,
    address payable _refundAddress,
    address _zroPaymentAddress,
    bytes calldata _adapterParams
  ) external payable;

  // @notice used by the messaging library to publish verified payload
  // @param _srcChainId - the source chain identifier
  // @param _srcAddress - the source contract (as bytes) at the source chain
  // @param _dstAddress - the address on destination chain
  // @param _nonce - the unbound message ordering nonce
  // @param _gasLimit - the gas limit for external contract execution
  // @param _payload - verified payload to send to the destination contract
  function receivePayload(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    address _dstAddress,
    uint64 _nonce,
    uint256 _gasLimit,
    bytes calldata _payload
  ) external;

  // @notice get the inboundNonce of a lzApp from a source chain which could be EVM or non-EVM chain
  // @param _srcChainId - the source chain identifier
  // @param _srcAddress - the source chain contract address
  function getInboundNonce(uint16 _srcChainId, bytes calldata _srcAddress)
    external
    view
    returns (uint64);

  // @notice get the outboundNonce from this source chain which, consequently, is always an EVM
  // @param _srcAddress - the source chain contract address
  function getOutboundNonce(uint16 _dstChainId, address _srcAddress)
    external
    view
    returns (uint64);

  // @notice gets a quote in source native gas, for the amount that send() requires to pay for message delivery
  // @param _dstChainId - the destination chain identifier
  // @param _userApplication - the user app address on this EVM chain
  // @param _payload - the custom message to send over LayerZero
  // @param _payInZRO - if false, user app pays the protocol fee in native token
  // @param _adapterParam - parameters for the adapter service, e.g. send some dust native token to dstChain
  function estimateFees(
    uint16 _dstChainId,
    address _userApplication,
    bytes calldata _payload,
    bool _payInZRO,
    bytes calldata _adapterParam
  ) external view returns (uint256 nativeFee, uint256 zroFee);

  // @notice get this Endpoint's immutable source identifier
  function getChainId() external view returns (uint16);

  // @notice the interface to retry failed message on this Endpoint destination
  // @param _srcChainId - the source chain identifier
  // @param _srcAddress - the source chain contract address
  // @param _payload - the payload to be retried
  function retryPayload(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    bytes calldata _payload
  ) external;

  // @notice query if any STORED payload (message blocking) at the endpoint.
  // @param _srcChainId - the source chain identifier
  // @param _srcAddress - the source chain contract address
  function hasStoredPayload(uint16 _srcChainId, bytes calldata _srcAddress)
    external
    view
    returns (bool);

  // @notice query if the _libraryAddress is valid for sending msgs.
  // @param _userApplication - the user app address on this EVM chain
  function getSendLibraryAddress(address _userApplication)
    external
    view
    returns (address);

  // @notice query if the _libraryAddress is valid for receiving msgs.
  // @param _userApplication - the user app address on this EVM chain
  function getReceiveLibraryAddress(address _userApplication)
    external
    view
    returns (address);

  // @notice query if the non-reentrancy guard for send() is on
  // @return true if the guard is on. false otherwise
  function isSendingPayload() external view returns (bool);

  // @notice query if the non-reentrancy guard for receive() is on
  // @return true if the guard is on. false otherwise
  function isReceivingPayload() external view returns (bool);

  // @notice get the configuration of the LayerZero messaging library of the specified version
  // @param _version - messaging library version
  // @param _chainId - the chainId for the pending config change
  // @param _userApplication - the contract address of the user application
  // @param _configType - type of configuration. every messaging library has its own convention.
  function getConfig(
    uint16 _version,
    uint16 _chainId,
    address _userApplication,
    uint256 _configType
  ) external view returns (bytes memory);

  // @notice get the send() LayerZero messaging library version
  // @param _userApplication - the contract address of the user application
  function getSendVersion(address _userApplication)
    external
    view
    returns (uint16);

  // @notice get the lzReceive() LayerZero messaging library version
  // @param _userApplication - the contract address of the user application
  function getReceiveVersion(address _userApplication)
    external
    view
    returns (uint16);
}

File 12 of 21: ILayerZeroReceiver.sol
// SPDX-License-Identifier: MIT

pragma solidity >=0.5.0;

interface ILayerZeroReceiver {
  // @notice LayerZero endpoint will invoke this function to deliver the message on the destination
  // @param _srcChainId - the source endpoint identifier
  // @param _srcAddress - the source sending contract address from the source chain
  // @param _nonce - the ordered message nonce
  // @param _payload - the signed payload is the UA bytes has encoded to be sent
  function lzReceive(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes calldata _payload
  ) external;
}

File 13 of 21: ILayerZeroUserApplicationConfig.sol
// SPDX-License-Identifier: MIT

pragma solidity >=0.5.0;

interface ILayerZeroUserApplicationConfig {
  // @notice set the configuration of the LayerZero messaging library of the specified version
  // @param _version - messaging library version
  // @param _chainId - the chainId for the pending config change
  // @param _configType - type of configuration. every messaging library has its own convention.
  // @param _config - configuration in the bytes. can encode arbitrary content.
  function setConfig(
    uint16 _version,
    uint16 _chainId,
    uint256 _configType,
    bytes calldata _config
  ) external;

  // @notice set the send() LayerZero messaging library version to _version
  // @param _version - new messaging library version
  function setSendVersion(uint16 _version) external;

  // @notice set the lzReceive() LayerZero messaging library version to _version
  // @param _version - new messaging library version
  function setReceiveVersion(uint16 _version) external;

  // @notice Only when the UA needs to resume the message flow in blocking mode and clear the stored payload
  // @param _srcChainId - the chainId of the source chain
  // @param _srcAddress - the contract address of the source contract at the source chain
  function forceResumeReceive(uint16 _srcChainId, bytes calldata _srcAddress)
    external;
}

File 14 of 21: IOFTReceiverV2.sol
// SPDX-License-Identifier: BUSL-1.1

pragma solidity >=0.5.0;

interface IOFTReceiverV2 {
  /**
   * @dev Called by the OFT contract when tokens are received from source chain.
   * @param _srcChainId The chain id of the source chain.
   * @param _srcAddress The address of the OFT token contract on the source chain.
   * @param _nonce The nonce of the transaction on the source chain.
   * @param _from The address of the account who calls the sendAndCall() on the source chain.
   * @param _amount The amount of tokens to transfer.
   * @param _payload Additional data with no specified format.
   */
  function onOFTReceived(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes32 _from,
    uint256 _amount,
    bytes calldata _payload
  ) external;
}

File 15 of 21: IOFTV2.sol
// SPDX-License-Identifier: MIT

pragma solidity >=0.5.0;

import "./ICommonOFT.sol";

/**
 * @dev Interface of the IOFT core standard
 */
interface IOFTV2 is ICommonOFT {
  /**
   * @dev send `_amount` amount of token to (`_dstChainId`, `_toAddress`) from `_from`
   * `_from` the owner of token
   * `_dstChainId` the destination chain identifier
   * `_toAddress` can be any size depending on the `dstChainId`.
   * `_amount` the quantity of tokens in wei
   * `_refundAddress` the address LayerZero refunds if too much message fee is sent
   * `_zroPaymentAddress` set to address(0x0) if not paying in ZRO (LayerZero Token)
   * `_adapterParams` is a flexible bytes array to indicate messaging adapter services
   */
  function sendFrom(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    LzCallParams calldata _callParams
  ) external payable;

  function sendAndCall(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes calldata _payload,
    uint64 _dstGasForCall,
    LzCallParams calldata _callParams
  ) external payable;
}

File 16 of 21: LzApp.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

import "./Ownable.sol";
import "./ILayerZeroReceiver.sol";
import "./ILayerZeroUserApplicationConfig.sol";
import "./ILayerZeroEndpoint.sol";
import "./BytesLib.sol";

/*
 * a generic LzReceiver implementation
 */
abstract contract LzApp is
  Ownable,
  ILayerZeroReceiver,
  ILayerZeroUserApplicationConfig
{
  using BytesLib for bytes;

  // ua can not send payload larger than this by default, but it can be changed by the ua owner
  uint256 public constant DEFAULT_PAYLOAD_SIZE_LIMIT = 10000;

  ILayerZeroEndpoint public immutable lzEndpoint;
  mapping(uint16 => bytes) public trustedRemoteLookup;
  mapping(uint16 => mapping(uint16 => uint256)) public minDstGasLookup;
  mapping(uint16 => uint256) public payloadSizeLimitLookup;
  address public precrime;

  event SetPrecrime(address precrime);
  event SetTrustedRemote(uint16 _remoteChainId, bytes _path);
  event SetTrustedRemoteAddress(uint16 _remoteChainId, bytes _remoteAddress);
  event SetMinDstGas(uint16 _dstChainId, uint16 _type, uint256 _minDstGas);

  constructor(address _endpoint) {
    lzEndpoint = ILayerZeroEndpoint(_endpoint);
  }

  function lzReceive(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes calldata _payload
  ) public virtual override {
    // lzReceive must be called by the endpoint for security
    require(
      _msgSender() == address(lzEndpoint), "LzApp: invalid endpoint caller"
    );

    bytes memory trustedRemote = trustedRemoteLookup[_srcChainId];
    // if will still block the message pathway from (srcChainId, srcAddress). should not receive message from untrusted remote.
    require(
      _srcAddress.length == trustedRemote.length && trustedRemote.length > 0
        && keccak256(_srcAddress) == keccak256(trustedRemote),
      "LzApp: invalid source sending contract"
    );

    _blockingLzReceive(_srcChainId, _srcAddress, _nonce, _payload);
  }

  // abstract function - the default behaviour of LayerZero is blocking. See: NonblockingLzApp if you dont need to enforce ordered messaging
  function _blockingLzReceive(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload
  ) internal virtual;

  function _lzSend(
    uint16 _dstChainId,
    bytes memory _payload,
    address payable _refundAddress,
    address _zroPaymentAddress,
    bytes memory _adapterParams,
    uint256 _nativeFee
  ) internal virtual {
    bytes memory trustedRemote = trustedRemoteLookup[_dstChainId];
    require(
      trustedRemote.length != 0,
      "LzApp: destination chain is not a trusted source"
    );
    _checkPayloadSize(_dstChainId, _payload.length);
    lzEndpoint.send{value: _nativeFee}(
      _dstChainId,
      trustedRemote,
      _payload,
      _refundAddress,
      _zroPaymentAddress,
      _adapterParams
    );
  }

  function _checkGasLimit(
    uint16 _dstChainId,
    uint16 _type,
    bytes memory _adapterParams,
    uint256 _extraGas
  ) internal view virtual {
    uint256 providedGasLimit = _getGasLimit(_adapterParams);
    uint256 minGasLimit = minDstGasLookup[_dstChainId][_type] + _extraGas;
    require(minGasLimit > 0, "LzApp: minGasLimit not set");
    require(providedGasLimit >= minGasLimit, "LzApp: gas limit is too low");
  }

  function _getGasLimit(bytes memory _adapterParams)
    internal
    pure
    virtual
    returns (uint256 gasLimit)
  {
    require(_adapterParams.length >= 34, "LzApp: invalid adapterParams");
    assembly {
      gasLimit := mload(add(_adapterParams, 34))
    }
  }

  function _checkPayloadSize(uint16 _dstChainId, uint256 _payloadSize)
    internal
    view
    virtual
  {
    uint256 payloadSizeLimit = payloadSizeLimitLookup[_dstChainId];
    if (payloadSizeLimit == 0) {
      // use default if not set
      payloadSizeLimit = DEFAULT_PAYLOAD_SIZE_LIMIT;
    }
    require(
      _payloadSize <= payloadSizeLimit, "LzApp: payload size is too large"
    );
  }

  //---------------------------UserApplication config----------------------------------------
  function getConfig(
    uint16 _version,
    uint16 _chainId,
    address,
    uint256 _configType
  ) external view returns (bytes memory) {
    return lzEndpoint.getConfig(_version, _chainId, address(this), _configType);
  }

  // generic config for LayerZero user Application
  function setConfig(
    uint16 _version,
    uint16 _chainId,
    uint256 _configType,
    bytes calldata _config
  ) external override onlyOwner {
    lzEndpoint.setConfig(_version, _chainId, _configType, _config);
  }

  function setSendVersion(uint16 _version) external override onlyOwner {
    lzEndpoint.setSendVersion(_version);
  }

  function setReceiveVersion(uint16 _version) external override onlyOwner {
    lzEndpoint.setReceiveVersion(_version);
  }

  function forceResumeReceive(uint16 _srcChainId, bytes calldata _srcAddress)
    external
    override
    onlyOwner
  {
    lzEndpoint.forceResumeReceive(_srcChainId, _srcAddress);
  }

  // _path = abi.encodePacked(remoteAddress, localAddress)
  // this function set the trusted path for the cross-chain communication
  function setTrustedRemote(uint16 _remoteChainId, bytes calldata _path)
    external
    onlyOwner
  {
    trustedRemoteLookup[_remoteChainId] = _path;
    emit SetTrustedRemote(_remoteChainId, _path);
  }

  function setTrustedRemoteAddress(
    uint16 _remoteChainId,
    bytes calldata _remoteAddress
  ) external onlyOwner {
    trustedRemoteLookup[_remoteChainId] =
      abi.encodePacked(_remoteAddress, address(this));
    emit SetTrustedRemoteAddress(_remoteChainId, _remoteAddress);
  }

  function getTrustedRemoteAddress(uint16 _remoteChainId)
    external
    view
    returns (bytes memory)
  {
    bytes memory path = trustedRemoteLookup[_remoteChainId];
    require(path.length != 0, "LzApp: no trusted path record");
    return path.slice(0, path.length - 20); // the last 20 bytes should be address(this)
  }

  function setPrecrime(address _precrime) external onlyOwner {
    precrime = _precrime;
    emit SetPrecrime(_precrime);
  }

  function setMinDstGas(uint16 _dstChainId, uint16 _packetType, uint256 _minGas)
    external
    onlyOwner
  {
    require(_minGas > 0, "LzApp: invalid minGas");
    minDstGasLookup[_dstChainId][_packetType] = _minGas;
    emit SetMinDstGas(_dstChainId, _packetType, _minGas);
  }

  // if the size is 0, it means default size limit
  function setPayloadSizeLimit(uint16 _dstChainId, uint256 _size)
    external
    onlyOwner
  {
    payloadSizeLimitLookup[_dstChainId] = _size;
  }

  //--------------------------- VIEW FUNCTION ----------------------------------------
  function isTrustedRemote(uint16 _srcChainId, bytes calldata _srcAddress)
    external
    view
    returns (bool)
  {
    bytes memory trustedSource = trustedRemoteLookup[_srcChainId];
    return keccak256(trustedSource) == keccak256(_srcAddress);
  }
}

File 17 of 21: NonblockingLzApp.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

import "./LzApp.sol";
import "./ExcessivelySafeCall.sol";

/*
 * the default LayerZero messaging behaviour is blocking, i.e. any failed message will block the channel
 * this abstract class try-catch all fail messages and store locally for future retry. hence, non-blocking
 * NOTE: if the srcAddress is not configured properly, it will still block the message pathway from (srcChainId, srcAddress)
 */
abstract contract NonblockingLzApp is LzApp {
  using ExcessivelySafeCall for address;

  constructor(address _endpoint) LzApp(_endpoint) {}

  mapping(uint16 => mapping(bytes => mapping(uint64 => bytes32))) public
    failedMessages;

  event MessageFailed(
    uint16 _srcChainId,
    bytes _srcAddress,
    uint64 _nonce,
    bytes _payload,
    bytes _reason
  );
  event RetryMessageSuccess(
    uint16 _srcChainId, bytes _srcAddress, uint64 _nonce, bytes32 _payloadHash
  );

  // overriding the virtual function in LzReceiver
  function _blockingLzReceive(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload
  ) internal virtual override {
    (bool success, bytes memory reason) = address(this).excessivelySafeCall(
      gasleft(),
      150,
      abi.encodeWithSelector(
        this.nonblockingLzReceive.selector,
        _srcChainId,
        _srcAddress,
        _nonce,
        _payload
      )
    );
    // try-catch all errors/exceptions
    if (!success) {
      _storeFailedMessage(_srcChainId, _srcAddress, _nonce, _payload, reason);
    }
  }

  function _storeFailedMessage(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload,
    bytes memory _reason
  ) internal virtual {
    failedMessages[_srcChainId][_srcAddress][_nonce] = keccak256(_payload);
    emit MessageFailed(_srcChainId, _srcAddress, _nonce, _payload, _reason);
  }

  function nonblockingLzReceive(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes calldata _payload
  ) public virtual {
    // only internal transaction
    require(
      _msgSender() == address(this), "NonblockingLzApp: caller must be LzApp"
    );
    _nonblockingLzReceive(_srcChainId, _srcAddress, _nonce, _payload);
  }

  //@notice override this function
  function _nonblockingLzReceive(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload
  ) internal virtual;

  function retryMessage(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes calldata _payload
  ) public payable virtual {
    // assert there is message to retry
    bytes32 payloadHash = failedMessages[_srcChainId][_srcAddress][_nonce];
    require(payloadHash != bytes32(0), "NonblockingLzApp: no stored message");
    require(
      keccak256(_payload) == payloadHash, "NonblockingLzApp: invalid payload"
    );
    // clear the stored message
    failedMessages[_srcChainId][_srcAddress][_nonce] = bytes32(0);
    // execute the message. revert if it fails again
    _nonblockingLzReceive(_srcChainId, _srcAddress, _nonce, _payload);
    emit RetryMessageSuccess(_srcChainId, _srcAddress, _nonce, payloadHash);
  }
}

File 18 of 21: OFTCoreV2.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

import "./NonblockingLzApp.sol";
import "./ExcessivelySafeCall.sol";
import "./ICommonOFT.sol";
import "./IOFTReceiverV2.sol";

abstract contract OFTCoreV2 is NonblockingLzApp {
  using BytesLib for bytes;
  using ExcessivelySafeCall for address;

  uint256 public constant NO_EXTRA_GAS = 0;

  // packet type
  uint8 public constant PT_SEND = 0;
  uint8 public constant PT_SEND_AND_CALL = 1;

  uint8 public immutable sharedDecimals;

  bool public useCustomAdapterParams;
  mapping(uint16 => mapping(bytes => mapping(uint64 => bool))) public
    creditedPackets;

  /**
   * @dev Emitted when `_amount` tokens are moved from the `_sender` to (`_dstChainId`, `_toAddress`)
   * `_nonce` is the outbound nonce
   */
  event SendToChain(
    uint16 indexed _dstChainId,
    address indexed _from,
    bytes32 indexed _toAddress,
    uint256 _amount
  );

  /**
   * @dev Emitted when `_amount` tokens are received from `_srcChainId` into the `_toAddress` on the local chain.
   * `_nonce` is the inbound nonce.
   */
  event ReceiveFromChain(
    uint16 indexed _srcChainId, address indexed _to, uint256 _amount
  );

  event SetUseCustomAdapterParams(bool _useCustomAdapterParams);

  event CallOFTReceivedSuccess(
    uint16 indexed _srcChainId, bytes _srcAddress, uint64 _nonce, bytes32 _hash
  );

  event NonContractAddress(address _address);

  // _sharedDecimals should be the minimum decimals on all chains
  constructor(uint8 _sharedDecimals, address _lzEndpoint)
    NonblockingLzApp(_lzEndpoint)
  {
    sharedDecimals = _sharedDecimals;
  }

  /**
   *
   * public functions
   *
   */
  function callOnOFTReceived(
    uint16 _srcChainId,
    bytes calldata _srcAddress,
    uint64 _nonce,
    bytes32 _from,
    address _to,
    uint256 _amount,
    bytes calldata _payload,
    uint256 _gasForCall
  ) public virtual {
    require(_msgSender() == address(this), "OFTCore: caller must be OFTCore");

    // send
    _amount = _transferFrom(address(this), _to, _amount);
    emit ReceiveFromChain(_srcChainId, _to, _amount);

    // call
    IOFTReceiverV2(_to).onOFTReceived{gas: _gasForCall}(
      _srcChainId, _srcAddress, _nonce, _from, _amount, _payload
    );
  }

  function setUseCustomAdapterParams(bool _useCustomAdapterParams)
    public
    virtual
    onlyOwner
  {
    useCustomAdapterParams = _useCustomAdapterParams;
    emit SetUseCustomAdapterParams(_useCustomAdapterParams);
  }

  /**
   *
   * internal functions
   *
   */
  function _estimateSendFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bool _useZro,
    bytes memory _adapterParams
  ) internal view virtual returns (uint256 nativeFee, uint256 zroFee) {
    // mock the payload for sendFrom()
    bytes memory payload = _encodeSendPayload(_toAddress, _ld2sd(_amount));
    return lzEndpoint.estimateFees(
      _dstChainId, address(this), payload, _useZro, _adapterParams
    );
  }

  function _estimateSendAndCallFee(
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes memory _payload,
    uint64 _dstGasForCall,
    bool _useZro,
    bytes memory _adapterParams
  ) internal view virtual returns (uint256 nativeFee, uint256 zroFee) {
    // mock the payload for sendAndCall()
    bytes memory payload = _encodeSendAndCallPayload(
      msg.sender, _toAddress, _ld2sd(_amount), _payload, _dstGasForCall
    );
    return lzEndpoint.estimateFees(
      _dstChainId, address(this), payload, _useZro, _adapterParams
    );
  }

  function _nonblockingLzReceive(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload
  ) internal virtual override {
    uint8 packetType = _payload.toUint8(0);

    if (packetType == PT_SEND) {
      _sendAck(_srcChainId, _srcAddress, _nonce, _payload);
    } else if (packetType == PT_SEND_AND_CALL) {
      _sendAndCallAck(_srcChainId, _srcAddress, _nonce, _payload);
    } else {
      revert("OFTCore: unknown packet type");
    }
  }

  function _send(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    address payable _refundAddress,
    address _zroPaymentAddress,
    bytes memory _adapterParams
  ) internal virtual returns (uint256 amount) {
    _checkAdapterParams(_dstChainId, PT_SEND, _adapterParams, NO_EXTRA_GAS);

    (amount,) = _removeDust(_amount);
    amount = _debitFrom(_from, _dstChainId, _toAddress, amount); // amount returned should not have dust
    require(amount > 0, "OFTCore: amount too small");

    bytes memory lzPayload = _encodeSendPayload(_toAddress, _ld2sd(amount));
    _lzSend(
      _dstChainId,
      lzPayload,
      _refundAddress,
      _zroPaymentAddress,
      _adapterParams,
      msg.value
    );

    emit SendToChain(_dstChainId, _from, _toAddress, amount);
  }

  function _sendAck(
    uint16 _srcChainId,
    bytes memory,
    uint64,
    bytes memory _payload
  ) internal virtual {
    (address to, uint64 amountSD) = _decodeSendPayload(_payload);
    if (to == address(0)) {
      to = address(0xdead);
    }

    uint256 amount = _sd2ld(amountSD);
    amount = _creditTo(_srcChainId, to, amount);

    emit ReceiveFromChain(_srcChainId, to, amount);
  }

  function _sendAndCall(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount,
    bytes memory _payload,
    uint64 _dstGasForCall,
    address payable _refundAddress,
    address _zroPaymentAddress,
    bytes memory _adapterParams
  ) internal virtual returns (uint256 amount) {
    _checkAdapterParams(
      _dstChainId, PT_SEND_AND_CALL, _adapterParams, _dstGasForCall
    );

    (amount,) = _removeDust(_amount);
    amount = _debitFrom(_from, _dstChainId, _toAddress, amount);
    require(amount > 0, "OFTCore: amount too small");

    // encode the msg.sender into the payload instead of _from
    bytes memory lzPayload = _encodeSendAndCallPayload(
      msg.sender, _toAddress, _ld2sd(amount), _payload, _dstGasForCall
    );
    _lzSend(
      _dstChainId,
      lzPayload,
      _refundAddress,
      _zroPaymentAddress,
      _adapterParams,
      msg.value
    );

    emit SendToChain(_dstChainId, _from, _toAddress, amount);
  }

  function _sendAndCallAck(
    uint16 _srcChainId,
    bytes memory _srcAddress,
    uint64 _nonce,
    bytes memory _payload
  ) internal virtual {
    (
      bytes32 from,
      address to,
      uint64 amountSD,
      bytes memory payloadForCall,
      uint64 gasForCall
    ) = _decodeSendAndCallPayload(_payload);

    bool credited = creditedPackets[_srcChainId][_srcAddress][_nonce];
    uint256 amount = _sd2ld(amountSD);

    // credit to this contract first, and then transfer to receiver only if callOnOFTReceived() succeeds
    if (!credited) {
      amount = _creditTo(_srcChainId, address(this), amount);
      creditedPackets[_srcChainId][_srcAddress][_nonce] = true;
    }

    if (!_isContract(to)) {
      emit NonContractAddress(to);
      return;
    }

    // workaround for stack too deep
    uint16 srcChainId = _srcChainId;
    bytes memory srcAddress = _srcAddress;
    uint64 nonce = _nonce;
    bytes memory payload = _payload;
    bytes32 from_ = from;
    address to_ = to;
    uint256 amount_ = amount;
    bytes memory payloadForCall_ = payloadForCall;

    // no gas limit for the call if retry
    uint256 gas = credited ? gasleft() : gasForCall;
    (bool success, bytes memory reason) = address(this).excessivelySafeCall(
      gasleft(),
      150,
      abi.encodeWithSelector(
        this.callOnOFTReceived.selector,
        srcChainId,
        srcAddress,
        nonce,
        from_,
        to_,
        amount_,
        payloadForCall_,
        gas
      )
    );

    if (success) {
      bytes32 hash = keccak256(payload);
      emit CallOFTReceivedSuccess(srcChainId, srcAddress, nonce, hash);
    } else {
      // store the failed message into the nonblockingLzApp
      _storeFailedMessage(srcChainId, srcAddress, nonce, payload, reason);
    }
  }

  function _isContract(address _account) internal view returns (bool) {
    return _account.code.length > 0;
  }

  function _checkAdapterParams(
    uint16 _dstChainId,
    uint16 _pkType,
    bytes memory _adapterParams,
    uint256 _extraGas
  ) internal virtual {
    if (useCustomAdapterParams) {
      _checkGasLimit(_dstChainId, _pkType, _adapterParams, _extraGas);
    } else {
      require(
        _adapterParams.length == 0, "OFTCore: _adapterParams must be empty."
      );
    }
  }

  function _ld2sd(uint256 _amount) internal view virtual returns (uint64) {
    uint256 amountSD = _amount / _ld2sdRate();
    require(amountSD <= type(uint64).max, "OFTCore: amountSD overflow");
    return uint64(amountSD);
  }

  function _sd2ld(uint64 _amountSD) internal view virtual returns (uint256) {
    return _amountSD * _ld2sdRate();
  }

  function _removeDust(uint256 _amount)
    internal
    view
    virtual
    returns (uint256 amountAfter, uint256 dust)
  {
    dust = _amount % _ld2sdRate();
    amountAfter = _amount - dust;
  }

  function _encodeSendPayload(bytes32 _toAddress, uint64 _amountSD)
    internal
    view
    virtual
    returns (bytes memory)
  {
    return abi.encodePacked(PT_SEND, _toAddress, _amountSD);
  }

  function _decodeSendPayload(bytes memory _payload)
    internal
    view
    virtual
    returns (address to, uint64 amountSD)
  {
    require(
      _payload.toUint8(0) == PT_SEND && _payload.length == 41,
      "OFTCore: invalid payload"
    );

    to = _payload.toAddress(13); // drop the first 12 bytes of bytes32
    amountSD = _payload.toUint64(33);
  }

  function _encodeSendAndCallPayload(
    address _from,
    bytes32 _toAddress,
    uint64 _amountSD,
    bytes memory _payload,
    uint64 _dstGasForCall
  ) internal view virtual returns (bytes memory) {
    return abi.encodePacked(
      PT_SEND_AND_CALL,
      _toAddress,
      _amountSD,
      _addressToBytes32(_from),
      _dstGasForCall,
      _payload
    );
  }

  function _decodeSendAndCallPayload(bytes memory _payload)
    internal
    view
    virtual
    returns (
      bytes32 from,
      address to,
      uint64 amountSD,
      bytes memory payload,
      uint64 dstGasForCall
    )
  {
    require(_payload.toUint8(0) == PT_SEND_AND_CALL, "OFTCore: invalid payload");

    to = _payload.toAddress(13); // drop the first 12 bytes of bytes32
    amountSD = _payload.toUint64(33);
    from = _payload.toBytes32(41);
    dstGasForCall = _payload.toUint64(73);
    payload = _payload.slice(81, _payload.length - 81);
  }

  function _addressToBytes32(address _address)
    internal
    pure
    virtual
    returns (bytes32)
  {
    return bytes32(uint256(uint160(_address)));
  }

  function _debitFrom(
    address _from,
    uint16 _dstChainId,
    bytes32 _toAddress,
    uint256 _amount
  ) internal virtual returns (uint256);

  function _creditTo(uint16 _srcChainId, address _toAddress, uint256 _amount)
    internal
    virtual
    returns (uint256);

  function _transferFrom(address _from, address _to, uint256 _amount)
    internal
    virtual
    returns (uint256);

  function _ld2sdRate() internal view virtual returns (uint256);
}

File 19 of 21: OFTV2.sol
// SPDX-License-Identifier: MIT

pragma solidity ^0.8.0;

import "./ERC20.sol";
import "./BaseOFTV2.sol";

contract OFTV2 is BaseOFTV2, ERC20 {
  uint256 internal immutable ld2sdRate;

  constructor(
    string memory _name,
    string memory _symbol,
    uint8 _sharedDecimals,
    address _lzEndpoint
  ) ERC20(_name, _symbol) BaseOFTV2(_sharedDecimals, _lzEndpoint) {
    uint8 decimals = decimals();
    require(
      _sharedDecimals <= decimals, "OFT: sharedDecimals must be <= decimals"
    );
    ld2sdRate = 10 ** (decimals - _sharedDecimals);
  }

  /**
   *
   * public functions
   *
   */
  function circulatingSupply() public view virtual override returns (uint256) {
    return totalSupply();
  }

  function token() public view virtual override returns (address) {
    return address(this);
  }

  /**
   *
   * internal functions
   *
   */
  function _debitFrom(address _from, uint16, bytes32, uint256 _amount)
    internal
    virtual
    override
    returns (uint256)
  {
    address spender = _msgSender();
    if (_from != spender) _spendAllowance(_from, spender, _amount);
    _burn(_from, _amount);
    return _amount;
  }

  function _creditTo(uint16, address _toAddress, uint256 _amount)
    internal
    virtual
    override
    returns (uint256)
  {
    _mint(_toAddress, _amount);
    return _amount;
  }

  function _transferFrom(address _from, address _to, uint256 _amount)
    internal
    virtual
    override
    returns (uint256)
  {
    address spender = _msgSender();
    // if transfer from this contract, no need to check allowance
    if (_from != address(this) && _from != spender) {
      _spendAllowance(_from, spender, _amount);
    }
    _transfer(_from, _to, _amount);
    return _amount;
  }

  function _ld2sdRate() internal view virtual override returns (uint256) {
    return ld2sdRate;
  }
}

File 20 of 21: Ownable.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.7.0) (access/Ownable.sol)

pragma solidity ^0.8.0;

import "./Context.sol";

/**
 * @dev Contract module which provides a basic access control mechanism, where
 * there is an account (an owner) that can be granted exclusive access to
 * specific functions.
 *
 * By default, the owner account will be the one that deploys the contract. This
 * can later be changed with {transferOwnership}.
 *
 * This module is used through inheritance. It will make available the modifier
 * `onlyOwner`, which can be applied to your functions to restrict their use to
 * the owner.
 */
abstract contract Ownable is Context {
  address private _owner;

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

  /**
   * @dev Initializes the contract setting the deployer as the initial owner.
   */
  constructor() {
    _transferOwnership(_msgSender());
  }

  /**
   * @dev Throws if called by any account other than the owner.
   */
  modifier onlyOwner() {
    _checkOwner();
    _;
  }

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

  /**
   * @dev Throws if the sender is not the owner.
   */
  function _checkOwner() internal view virtual {
    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 {
    _transferOwnership(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");
    _transferOwnership(newOwner);
  }

  /**
   * @dev Transfers ownership of the contract to a new account (`newOwner`).
   * Internal function without access restriction.
   */
  function _transferOwnership(address newOwner) internal virtual {
    address oldOwner = _owner;
    _owner = newOwner;
    emit OwnershipTransferred(oldOwner, newOwner);
  }
}

Contract Security Audit

Contract ABI

[{"inputs":[{"internalType":"address","name":"_layerZeroEndpoint","type":"address"},{"internalType":"uint8","name":"_sharedDecimals","type":"uint8"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"spender","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"indexed":false,"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"indexed":false,"internalType":"uint64","name":"_nonce","type":"uint64"},{"indexed":false,"internalType":"bytes32","name":"_hash","type":"bytes32"}],"name":"CallOFTReceivedSuccess","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"indexed":false,"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"indexed":false,"internalType":"uint64","name":"_nonce","type":"uint64"},{"indexed":false,"internalType":"bytes","name":"_payload","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"_reason","type":"bytes"}],"name":"MessageFailed","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"_address","type":"address"}],"name":"NonContractAddress","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"indexed":true,"internalType":"address","name":"_to","type":"address"},{"indexed":false,"internalType":"uint256","name":"_amount","type":"uint256"}],"name":"ReceiveFromChain","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"indexed":false,"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"indexed":false,"internalType":"uint64","name":"_nonce","type":"uint64"},{"indexed":false,"internalType":"bytes32","name":"_payloadHash","type":"bytes32"}],"name":"RetryMessageSuccess","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"indexed":true,"internalType":"address","name":"_from","type":"address"},{"indexed":true,"internalType":"bytes32","name":"_toAddress","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"_amount","type":"uint256"}],"name":"SendToChain","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"indexed":false,"internalType":"uint16","name":"_type","type":"uint16"},{"indexed":false,"internalType":"uint256","name":"_minDstGas","type":"uint256"}],"name":"SetMinDstGas","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"precrime","type":"address"}],"name":"SetPrecrime","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"_remoteChainId","type":"uint16"},{"indexed":false,"internalType":"bytes","name":"_path","type":"bytes"}],"name":"SetTrustedRemote","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint16","name":"_remoteChainId","type":"uint16"},{"indexed":false,"internalType":"bytes","name":"_remoteAddress","type":"bytes"}],"name":"SetTrustedRemoteAddress","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bool","name":"_useCustomAdapterParams","type":"bool"}],"name":"SetUseCustomAdapterParams","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"value","type":"uint256"}],"name":"Transfer","type":"event"},{"inputs":[],"name":"DEFAULT_PAYLOAD_SIZE_LIMIT","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"NO_EXTRA_GAS","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"PT_SEND","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"PT_SEND_AND_CALL","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"spender","type":"address"}],"name":"allowance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"spender","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"approve","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"internalType":"uint64","name":"_nonce","type":"uint64"},{"internalType":"bytes32","name":"_from","type":"bytes32"},{"internalType":"address","name":"_to","type":"address"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"bytes","name":"_payload","type":"bytes"},{"internalType":"uint256","name":"_gasForCall","type":"uint256"}],"name":"callOnOFTReceived","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"circulatingSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"","type":"uint16"},{"internalType":"bytes","name":"","type":"bytes"},{"internalType":"uint64","name":"","type":"uint64"}],"name":"creditedPackets","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"decimals","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"spender","type":"address"},{"internalType":"uint256","name":"subtractedValue","type":"uint256"}],"name":"decreaseAllowance","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"bytes32","name":"_toAddress","type":"bytes32"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"bytes","name":"_payload","type":"bytes"},{"internalType":"uint64","name":"_dstGasForCall","type":"uint64"},{"internalType":"bool","name":"_useZro","type":"bool"},{"internalType":"bytes","name":"_adapterParams","type":"bytes"}],"name":"estimateSendAndCallFee","outputs":[{"internalType":"uint256","name":"nativeFee","type":"uint256"},{"internalType":"uint256","name":"zroFee","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"bytes32","name":"_toAddress","type":"bytes32"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"bool","name":"_useZro","type":"bool"},{"internalType":"bytes","name":"_adapterParams","type":"bytes"}],"name":"estimateSendFee","outputs":[{"internalType":"uint256","name":"nativeFee","type":"uint256"},{"internalType":"uint256","name":"zroFee","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"","type":"uint16"},{"internalType":"bytes","name":"","type":"bytes"},{"internalType":"uint64","name":"","type":"uint64"}],"name":"failedMessages","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"}],"name":"forceResumeReceive","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_version","type":"uint16"},{"internalType":"uint16","name":"_chainId","type":"uint16"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"_configType","type":"uint256"}],"name":"getConfig","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_remoteChainId","type":"uint16"}],"name":"getTrustedRemoteAddress","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"spender","type":"address"},{"internalType":"uint256","name":"addedValue","type":"uint256"}],"name":"increaseAllowance","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"}],"name":"isTrustedRemote","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"lzEndpoint","outputs":[{"internalType":"contract ILayerZeroEndpoint","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"internalType":"uint64","name":"_nonce","type":"uint64"},{"internalType":"bytes","name":"_payload","type":"bytes"}],"name":"lzReceive","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"","type":"uint16"},{"internalType":"uint16","name":"","type":"uint16"}],"name":"minDstGasLookup","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"internalType":"uint64","name":"_nonce","type":"uint64"},{"internalType":"bytes","name":"_payload","type":"bytes"}],"name":"nonblockingLzReceive","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint16","name":"","type":"uint16"}],"name":"payloadSizeLimitLookup","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"precrime","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_srcChainId","type":"uint16"},{"internalType":"bytes","name":"_srcAddress","type":"bytes"},{"internalType":"uint64","name":"_nonce","type":"uint64"},{"internalType":"bytes","name":"_payload","type":"bytes"}],"name":"retryMessage","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"_from","type":"address"},{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"bytes32","name":"_toAddress","type":"bytes32"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"bytes","name":"_payload","type":"bytes"},{"internalType":"uint64","name":"_dstGasForCall","type":"uint64"},{"components":[{"internalType":"address payable","name":"refundAddress","type":"address"},{"internalType":"address","name":"zroPaymentAddress","type":"address"},{"internalType":"bytes","name":"adapterParams","type":"bytes"}],"internalType":"struct ICommonOFT.LzCallParams","name":"_callParams","type":"tuple"}],"name":"sendAndCall","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address","name":"_from","type":"address"},{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"bytes32","name":"_toAddress","type":"bytes32"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"components":[{"internalType":"address payable","name":"refundAddress","type":"address"},{"internalType":"address","name":"zroPaymentAddress","type":"address"},{"internalType":"bytes","name":"adapterParams","type":"bytes"}],"internalType":"struct ICommonOFT.LzCallParams","name":"_callParams","type":"tuple"}],"name":"sendFrom","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_version","type":"uint16"},{"internalType":"uint16","name":"_chainId","type":"uint16"},{"internalType":"uint256","name":"_configType","type":"uint256"},{"internalType":"bytes","name":"_config","type":"bytes"}],"name":"setConfig","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"uint16","name":"_packetType","type":"uint16"},{"internalType":"uint256","name":"_minGas","type":"uint256"}],"name":"setMinDstGas","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_dstChainId","type":"uint16"},{"internalType":"uint256","name":"_size","type":"uint256"}],"name":"setPayloadSizeLimit","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_precrime","type":"address"}],"name":"setPrecrime","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_version","type":"uint16"}],"name":"setReceiveVersion","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_version","type":"uint16"}],"name":"setSendVersion","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_remoteChainId","type":"uint16"},{"internalType":"bytes","name":"_path","type":"bytes"}],"name":"setTrustedRemote","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"_remoteChainId","type":"uint16"},{"internalType":"bytes","name":"_remoteAddress","type":"bytes"}],"name":"setTrustedRemoteAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bool","name":"_useCustomAdapterParams","type":"bool"}],"name":"setUseCustomAdapterParams","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"sharedDecimals","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"token","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transfer","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"transferFrom","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint16","name":"","type":"uint16"}],"name":"trustedRemoteLookup","outputs":[{"internalType":"bytes","name":"","type":"bytes"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"useCustomAdapterParams","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"}]

60e06040523480156200001157600080fd5b50604051620047a4380380620047a48339810160408190526200003491620001c9565b604051806040016040528060038152602001620909ab60eb1b815250604051806040016040528060038152602001620909ab60eb1b81525082848383838381818080620000906200008a6200017060201b60201c565b62000174565b6001600160a01b0316608052505060ff1660a05250600b9050620000b58382620002bd565b50600c620000c48282620002bd565b5050506000620000d9620001c460201b60201c565b90508060ff168360ff161115620001465760405162461bcd60e51b815260206004820152602760248201527f4f46543a20736861726564446563696d616c73206d757374206265203c3d20646044820152666563696d616c7360c81b606482015260840160405180910390fd5b6200015283826200039f565b6200015f90600a620004be565b60c05250620004d695505050505050565b3390565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b601290565b60008060408385031215620001dd57600080fd5b82516001600160a01b0381168114620001f557600080fd5b602084015190925060ff811681146200020d57600080fd5b809150509250929050565b634e487b7160e01b600052604160045260246000fd5b600181811c908216806200024357607f821691505b6020821081036200026457634e487b7160e01b600052602260045260246000fd5b50919050565b601f821115620002b857600081815260208120601f850160051c81016020861015620002935750805b601f850160051c820191505b81811015620002b4578281556001016200029f565b5050505b505050565b81516001600160401b03811115620002d957620002d962000218565b620002f181620002ea84546200022e565b846200026a565b602080601f831160018114620003295760008415620003105750858301515b600019600386901b1c1916600185901b178555620002b4565b600085815260208120601f198616915b828110156200035a5788860151825594840194600190910190840162000339565b5085821015620003795787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b634e487b7160e01b600052601160045260246000fd5b60ff8281168282160390811115620003bb57620003bb62000389565b92915050565b600181815b8085111562000402578160001904821115620003e657620003e662000389565b80851615620003f457918102915b93841c9390800290620003c6565b509250929050565b6000826200041b57506001620003bb565b816200042a57506000620003bb565b81600181146200044357600281146200044e576200046e565b6001915050620003bb565b60ff84111562000462576200046262000389565b50506001821b620003bb565b5060208310610133831016604e8410600b841016171562000493575081810a620003bb565b6200049f8383620003c1565b8060001904821115620004b657620004b662000389565b029392505050565b6000620004cf60ff8416836200040a565b9392505050565b60805160a05160c05161425f620005456000396000612be5015260006105a001526000818161076a0152818161091a01528181610c3201528181610cf201528181610eaf0152818161151c01528181611ad401528181611fcb015281816123cf0152612b26015261425f6000f3fe6080604052600436106102435760003560e01c80621d35671461024857806301ffc9a71461026a57806306fdde031461029f57806307e0db17146102c1578063095ea7b3146102e15780630df374831461030157806310ddb1371461032157806318160ddd1461034157806323b872dd14610360578063313ce56714610380578063365260b4146103a257806339509351146103d75780633d8b38f6146103f75780633f1f4fa41461041757806342d65a8d1461044457806344770515146104645780634c42899a146104795780635b8c41e61461048e57806366ad5c8a146104dd578063695ef6bf146104fd57806370a0823114610510578063715018a6146105465780637533d7881461055b57806376203b481461057b578063857749b01461058e5780638cfd8f5c146105c25780638da5cb5b146105fa5780639358928b1461061c578063950c8a741461063157806395d89b41146106515780639bdb9812146106665780639f38369a146106b8578063a457c2d7146106d8578063a4c51df5146106f8578063a6c3d16514610718578063a9059cbb14610738578063b353aaa714610758578063baf3292d1461078c578063c4461834146107ac578063cbed8b9c146107c2578063d1deba1f146107e2578063dd62ed3e146107f5578063df2a5b3b14610815578063e6a20ae614610835578063eab45d9c1461084a578063eaffd49a1461086a578063eb8d72b71461088a578063ed629c5c146108aa578063f2fde38b146108c4578063f5ecbdbc146108e4578063fc0c546a14610904575b600080fd5b34801561025457600080fd5b5061026861026336600461322a565b610917565b005b34801561027657600080fd5b5061028a6102853660046132bd565b610b48565b60405190151581526020015b60405180910390f35b3480156102ab57600080fd5b506102b4610b7f565b6040516102969190613337565b3480156102cd57600080fd5b506102686102dc36600461334a565b610c11565b3480156102ed57600080fd5b5061028a6102fc36600461337a565b610c9a565b34801561030d57600080fd5b5061026861031c3660046133a6565b610cb2565b34801561032d57600080fd5b5061026861033c36600461334a565b610cd1565b34801561034d57600080fd5b50600a545b604051908152602001610296565b34801561036c57600080fd5b5061028a61037b3660046133c2565b610d29565b34801561038c57600080fd5b5060125b60405160ff9091168152602001610296565b3480156103ae57600080fd5b506103c26103bd366004613413565b610d4d565b60408051928352602083019190915201610296565b3480156103e357600080fd5b5061028a6103f236600461337a565b610da2565b34801561040357600080fd5b5061028a610412366004613478565b610dc4565b34801561042357600080fd5b5061035261043236600461334a565b60036020526000908152604090205481565b34801561045057600080fd5b5061026861045f366004613478565b610e90565b34801561047057600080fd5b50610352600081565b34801561048557600080fd5b50610390600081565b34801561049a57600080fd5b506103526104a9366004613537565b6005602090815260009384526040808520845180860184018051928152908401958401959095209452929052825290205481565b3480156104e957600080fd5b506102686104f836600461322a565b610f16565b61026861050b3660046135ef565b610ff2565b34801561051c57600080fd5b5061035261052b366004613662565b6001600160a01b031660009081526008602052604090205490565b34801561055257600080fd5b5061026861105d565b34801561056757600080fd5b506102b461057636600461334a565b611071565b61026861058936600461367f565b61110b565b34801561059a57600080fd5b506103907f000000000000000000000000000000000000000000000000000000000000000081565b3480156105ce57600080fd5b506103526105dd366004613731565b600260209081526000928352604080842090915290825290205481565b34801561060657600080fd5b5061060f6111ba565b6040516102969190613764565b34801561062857600080fd5b506103526111c9565b34801561063d57600080fd5b5060045461060f906001600160a01b031681565b34801561065d57600080fd5b506102b46111d9565b34801561067257600080fd5b5061028a610681366004613537565b6007602090815260009384526040808520845180860184018051928152908401958401959095209452929052825290205460ff1681565b3480156106c457600080fd5b506102b46106d336600461334a565b6111e8565b3480156106e457600080fd5b5061028a6106f336600461337a565b6112fe565b34801561070457600080fd5b506103c2610713366004613778565b611379565b34801561072457600080fd5b50610268610733366004613478565b611408565b34801561074457600080fd5b5061028a61075336600461337a565b611491565b34801561076457600080fd5b5061060f7f000000000000000000000000000000000000000000000000000000000000000081565b34801561079857600080fd5b506102686107a7366004613662565b61149f565b3480156107b857600080fd5b5061035261271081565b3480156107ce57600080fd5b506102686107dd366004613831565b6114fd565b6102686107f036600461322a565b611587565b34801561080157600080fd5b5061035261081036600461389f565b61179d565b34801561082157600080fd5b506102686108303660046138d8565b6117c8565b34801561084157600080fd5b50610390600181565b34801561085657600080fd5b50610268610865366004613914565b61187a565b34801561087657600080fd5b5061026861088536600461392f565b6118c3565b34801561089657600080fd5b506102686108a5366004613478565b6119d0565b3480156108b657600080fd5b5060065461028a9060ff1681565b3480156108d057600080fd5b506102686108df366004613662565b611a2a565b3480156108f057600080fd5b506102b46108ff3660046139f7565b611aa3565b34801561091057600080fd5b503061060f565b337f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316146109945760405162461bcd60e51b815260206004820152601e60248201527f4c7a4170703a20696e76616c696420656e64706f696e742063616c6c6572000060448201526064015b60405180910390fd5b61ffff8616600090815260016020526040812080546109b290613a44565b80601f01602080910402602001604051908101604052809291908181526020018280546109de90613a44565b8015610a2b5780601f10610a0057610100808354040283529160200191610a2b565b820191906000526020600020905b815481529060010190602001808311610a0e57829003601f168201915b50505050509050805186869050148015610a46575060008151115b8015610a6e575080516020820120604051610a649088908890613a78565b6040518091039020145b610ac95760405162461bcd60e51b815260206004820152602660248201527f4c7a4170703a20696e76616c696420736f757263652073656e64696e6720636f6044820152651b9d1c9858dd60d21b606482015260840161098b565b610b3f8787878080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8a018190048102820181019092528881528a935091508890889081908401838280828437600092019190915250611b5492505050565b50505050505050565b60006001600160e01b03198216631f7ecdf760e01b1480610b7957506301ffc9a760e01b6001600160e01b03198316145b92915050565b6060600b8054610b8e90613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054610bba90613a44565b8015610c075780601f10610bdc57610100808354040283529160200191610c07565b820191906000526020600020905b815481529060010190602001808311610bea57829003601f168201915b5050505050905090565b610c19611bcd565b6040516307e0db1760e01b815261ffff821660048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316906307e0db17906024015b600060405180830381600087803b158015610c7f57600080fd5b505af1158015610c93573d6000803e3d6000fd5b5050505050565b600033610ca8818585611c2c565b5060019392505050565b610cba611bcd565b61ffff909116600090815260036020526040902055565b610cd9611bcd565b6040516310ddb13760e01b815261ffff821660048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b0316906310ddb13790602401610c65565b600033610d37858285611d50565b610d42858585611dca565b506001949350505050565b600080610d938888888888888080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250611f6392505050565b91509150965096945050505050565b600033610ca8818585610db5838361179d565b610dbf9190613a9e565b611c2c565b61ffff831660009081526001602052604081208054829190610de590613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054610e1190613a44565b8015610e5e5780601f10610e3357610100808354040283529160200191610e5e565b820191906000526020600020905b815481529060010190602001808311610e4157829003601f168201915b505050505090508383604051610e75929190613a78565b60405180910390208180519060200120149150509392505050565b610e98611bcd565b6040516342d65a8d60e01b81526001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016906342d65a8d90610ee890869086908690600401613ada565b600060405180830381600087803b158015610f0257600080fd5b505af1158015610b3f573d6000803e3d6000fd5b333014610f745760405162461bcd60e51b815260206004820152602660248201527f4e6f6e626c6f636b696e674c7a4170703a2063616c6c6572206d7573742062656044820152650204c7a4170760d41b606482015260840161098b565b610fea8686868080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f89018190048102820181019092528781528993509150879087908190840183828082843760009201919091525061205792505050565b505050505050565b610fea858585856110066020870187613662565b6110166040880160208901613662565b6110236040890189613af8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506120dd92505050565b611065611bcd565b61106f6000612187565b565b6001602052600090815260409020805461108a90613a44565b80601f01602080910402602001604051908101604052809291908181526020018280546110b690613a44565b80156111035780601f106110d857610100808354040283529160200191611103565b820191906000526020600020905b8154815290600101906020018083116110e657829003601f168201915b505050505081565b6111af8888888888888080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152508a92506111589150506020890189613662565b61116860408a0160208b01613662565b61117560408b018b613af8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506121d792505050565b505050505050505050565b6000546001600160a01b031690565b60006111d4600a5490565b905090565b6060600c8054610b8e90613a44565b61ffff811660009081526001602052604081208054606092919061120b90613a44565b80601f016020809104026020016040519081016040528092919081815260200182805461123790613a44565b80156112845780601f1061125957610100808354040283529160200191611284565b820191906000526020600020905b81548152906001019060200180831161126757829003601f168201915b5050505050905080516000036112dc5760405162461bcd60e51b815260206004820152601d60248201527f4c7a4170703a206e6f20747275737465642070617468207265636f7264000000604482015260640161098b565b6112f76000601483516112ef9190613b3e565b839190612295565b9392505050565b6000338161130c828661179d565b90508381101561136c5760405162461bcd60e51b815260206004820152602560248201527f45524332303a2064656372656173656420616c6c6f77616e63652062656c6f77604482015264207a65726f60d81b606482015260840161098b565b610d428286868403611c2c565b6000806113f68b8b8b8b8b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8d018190048102820181019092528b81528e93508d9250908c908c90819084018382808284376000920191909152506123a292505050565b91509150995099975050505050505050565b611410611bcd565b81813060405160200161142593929190613b51565b60408051601f1981840301815291815261ffff85166000908152600160205220906114509082613bcd565b507f8c0400cfe2d1199b1a725c78960bcc2a344d869b80590d0f2bd005db15a572ce83838360405161148493929190613ada565b60405180910390a1505050565b600033610ca8818585611dca565b6114a7611bcd565b600480546001600160a01b0319166001600160a01b0383161790556040517f5db758e995a17ec1ad84bdef7e8c3293a0bd6179bcce400dff5d4c3d87db726b906114f2908390613764565b60405180910390a150565b611505611bcd565b6040516332fb62e760e21b81526001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169063cbed8b9c906115599088908890889088908890600401613c86565b600060405180830381600087803b15801561157357600080fd5b505af11580156111af573d6000803e3d6000fd5b61ffff861660009081526005602052604080822090516115aa9088908890613a78565b90815260408051602092819003830190206001600160401b0387166000908152925290205490508061162a5760405162461bcd60e51b815260206004820152602360248201527f4e6f6e626c6f636b696e674c7a4170703a206e6f2073746f726564206d65737360448201526261676560e81b606482015260840161098b565b80838360405161163b929190613a78565b60405180910390201461169a5760405162461bcd60e51b815260206004820152602160248201527f4e6f6e626c6f636b696e674c7a4170703a20696e76616c6964207061796c6f616044820152601960fa1b606482015260840161098b565b61ffff871660009081526005602052604080822090516116bd9089908990613a78565b90815260408051602092819003830181206001600160401b038916600090815290845282902093909355601f88018290048202830182019052868252611755918991899089908190840183828082843760009201919091525050604080516020601f8a018190048102820181019092528881528a93509150889088908190840183828082843760009201919091525061205792505050565b7fc264d91f3adc5588250e1551f547752ca0cfa8f6b530d243b9f9f4cab10ea8e5878787878560405161178c959493929190613cbf565b60405180910390a150505050505050565b6001600160a01b03918216600090815260096020908152604080832093909416825291909152205490565b6117d0611bcd565b600081116118185760405162461bcd60e51b81526020600482015260156024820152744c7a4170703a20696e76616c6964206d696e47617360581b604482015260640161098b565b61ffff83811660008181526002602090815260408083209487168084529482529182902085905581519283528201929092529081018290527f9d5c7c0b934da8fefa9c7760c98383778a12dfbfc0c3b3106518f43fb9508ac090606001611484565b611882611bcd565b6006805460ff19168215159081179091556040519081527f1584ad594a70cbe1e6515592e1272a987d922b097ead875069cebe8b40c004a4906020016114f2565b3330146119125760405162461bcd60e51b815260206004820152601f60248201527f4f4654436f72653a2063616c6c6572206d757374206265204f4654436f726500604482015260640161098b565b61191d30868661245d565b9350846001600160a01b03168a61ffff166000805160206141ea8339815191528660405161194d91815260200190565b60405180910390a3604051633fe79aed60e11b81526001600160a01b03861690637fcf35da908390611991908e908e908e908e908e908d908d908d90600401613cfa565b600060405180830381600088803b1580156119ab57600080fd5b5087f11580156119bf573d6000803e3d6000fd5b505050505050505050505050505050565b6119d8611bcd565b61ffff831660009081526001602052604090206119f6828483613d57565b507ffa41487ad5d6728f0b19276fa1eddc16558578f5109fc39d2dc33c3230470dab83838360405161148493929190613ada565b611a32611bcd565b6001600160a01b038116611a975760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b606482015260840161098b565b611aa081612187565b50565b604051633d7b2f6f60e21b815261ffff808616600483015284166024820152306044820152606481018290526060907f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03169063f5ecbdbc90608401600060405180830381865afa158015611b23573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052611b4b9190810190613e10565b95945050505050565b600080611bb75a60966366ad5c8a60e01b89898989604051602401611b7c9493929190613e7d565b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b031990931692909217909152309291906124af565b9150915081610fea57610fea8686868685612539565b33611bd66111ba565b6001600160a01b03161461106f5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604482015260640161098b565b6001600160a01b038316611c8e5760405162461bcd60e51b8152602060048201526024808201527f45524332303a20617070726f76652066726f6d20746865207a65726f206164646044820152637265737360e01b606482015260840161098b565b6001600160a01b038216611cef5760405162461bcd60e51b815260206004820152602260248201527f45524332303a20617070726f766520746f20746865207a65726f206164647265604482015261737360f01b606482015260840161098b565b6001600160a01b0383811660008181526009602090815260408083209487168084529482529182902085905590518481527f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925910160405180910390a3505050565b6000611d5c848461179d565b90506000198114611dc45781811015611db75760405162461bcd60e51b815260206004820152601d60248201527f45524332303a20696e73756666696369656e7420616c6c6f77616e6365000000604482015260640161098b565b611dc48484848403611c2c565b50505050565b6001600160a01b038316611e2e5760405162461bcd60e51b815260206004820152602560248201527f45524332303a207472616e736665722066726f6d20746865207a65726f206164604482015264647265737360d81b606482015260840161098b565b6001600160a01b038216611e905760405162461bcd60e51b815260206004820152602360248201527f45524332303a207472616e7366657220746f20746865207a65726f206164647260448201526265737360e81b606482015260840161098b565b6001600160a01b03831660009081526008602052604090205481811015611f085760405162461bcd60e51b815260206004820152602660248201527f45524332303a207472616e7366657220616d6f756e7420657863656564732062604482015265616c616e636560d01b606482015260840161098b565b6001600160a01b03808516600081815260086020526040808220868603905592861680825290839020805486019055915160008051602061420a83398151915290611f569086815260200190565b60405180910390a3611dc4565b6000806000611fb187611f75886125db565b6040805160006020820152602181019390935260c09190911b6001600160c01b0319166041830152805160298184030181526049909201905290565b60405163040a7bb160e41b81529091506001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016906340a7bb1090612008908b90309086908b908b90600401613ebb565b6040805180830381865afa158015612024573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906120489190613f0f565b92509250509550959350505050565b60006120638282612646565b905060ff811661207e57612079858585856126a2565b610c93565b60001960ff8216016120965761207985858585612720565b60405162461bcd60e51b815260206004820152601c60248201527b4f4654436f72653a20756e6b6e6f776e207061636b6574207479706560201b604482015260640161098b565b60006120eb87828481612929565b6120f4856129a3565b509050612103888888846129cb565b9050600081116121255760405162461bcd60e51b815260040161098b90613f33565b600061213487611f75846125db565b90506121448882878787346129fd565b86896001600160a01b03168961ffff166000805160206141ca8339815191528560405161217391815260200190565b60405180910390a450979650505050505050565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006121ef896001846001600160401b038916612929565b6121f8876129a3565b5090506122078a8a8a846129cb565b9050600081116122295760405162461bcd60e51b815260040161098b90613f33565b6000612240338a612239856125db565b8a8a612ba2565b90506122508a82878787346129fd565b888b6001600160a01b03168b61ffff166000805160206141ca8339815191528560405161227f91815260200190565b60405180910390a4509998505050505050505050565b6060816122a381601f613a9e565b10156122e25760405162461bcd60e51b815260206004820152600e60248201526d736c6963655f6f766572666c6f7760901b604482015260640161098b565b6122ec8284613a9e565b845110156123305760405162461bcd60e51b8152602060048201526011602482015270736c6963655f6f75744f66426f756e647360781b604482015260640161098b565b60608215801561234f5760405191506000825260208201604052612399565b6040519150601f8416801560200281840101858101878315602002848b0101015b81831015612388578051835260209283019201612370565b5050858452601f01601f1916604052505b50949350505050565b60008060006123b5338a6122398b6125db565b60405163040a7bb160e41b81529091506001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016906340a7bb109061240c908d90309086908b908b90600401613ebb565b6040805180830381865afa158015612428573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061244c9190613f0f565b925092505097509795505050505050565b600033306001600160a01b0386161480159061248b5750806001600160a01b0316856001600160a01b031614155b1561249b5761249b858285611d50565b6124a6858585611dca565b50909392505050565b6000606060008060008661ffff166001600160401b038111156124d4576124d46134ca565b6040519080825280601f01601f1916602001820160405280156124fe576020820181803683370190505b50905060008087516020890160008d8df191503d925086831115612520578692505b828152826000602083013e909890975095505050505050565b8180519060200120600560008761ffff1661ffff1681526020019081526020016000208560405161256a9190613f66565b9081526040805191829003602090810183206001600160401b0388166000908152915220919091557fe183f33de2837795525b4792ca4cd60535bd77c53b7e7030060bfcf5734d6b0c906125c79087908790879087908790613f82565b60405180910390a15050505050565b505050565b6000806125e6612be3565b6125f09084613fea565b90506001600160401b03811115610b795760405162461bcd60e51b815260206004820152601a6024820152794f4654436f72653a20616d6f756e745344206f766572666c6f7760301b604482015260640161098b565b6000612653826001613a9e565b835110156126995760405162461bcd60e51b8152602060048201526013602482015272746f55696e74385f6f75744f66426f756e647360681b604482015260640161098b565b50016001015190565b6000806126ae83612c07565b90925090506001600160a01b0382166126c75761dead91505b60006126d282612c61565b90506126df878483612c7e565b9050826001600160a01b03168761ffff166000805160206141ea8339815191528360405161270f91815260200190565b60405180910390a350505050505050565b600080600080600061273186612c91565b945094509450945094506000600760008b61ffff1661ffff168152602001908152602001600020896040516127669190613f66565b90815260408051602092819003830190206001600160401b038b166000908152925281205460ff16915061279985612c61565b905081612807576127ab8b3083612c7e565b61ffff8c166000908152600760205260409081902090519192506001916127d3908d90613f66565b90815260408051602092819003830190206001600160401b038d16600090815292529020805460ff19169115159190911790555b6001600160a01b0386163b612859577f9aedf5fdba8716db3b6705ca00150643309995d4f818a249ed6dde6677e7792d866040516128459190613764565b60405180910390a150505050505050611dc4565b8a8a8a8a8a8a868a60008a612877578b6001600160401b0316612879565b5a5b90506000806128ab5a609663eaffd49a60e01b8e8e8e8d8d8d8d8d604051602401611b7c989796959493929190613ffe565b915091508115612904578751602089012060405161ffff8d16907fb8890edbfc1c74692f527444645f95489c3703cc2df42e4a366f5d06fa6cd884906128f6908e908e908690614072565b60405180910390a250612911565b6129118b8b8b8b85612539565b50505050505050505050505050505050505050505050565b60065460ff16156129455761294084848484612d1d565b611dc4565b815115611dc45760405162461bcd60e51b815260206004820152602660248201527f4f4654436f72653a205f61646170746572506172616d73206d7573742062652060448201526532b6b83a3c9760d11b606482015260840161098b565b6000806129ae612be3565b6129b890846140a0565b90506129c48184613b3e565b9150915091565b6000336001600160a01b03861681146129e9576129e9868285611d50565b6129f38684612df7565b5090949350505050565b61ffff861660009081526001602052604081208054612a1b90613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054612a4790613a44565b8015612a945780601f10612a6957610100808354040283529160200191612a94565b820191906000526020600020905b815481529060010190602001808311612a7757829003601f168201915b505050505090508051600003612b055760405162461bcd60e51b815260206004820152603060248201527f4c7a4170703a2064657374696e6174696f6e20636861696e206973206e6f742060448201526f61207472757374656420736f7572636560801b606482015260840161098b565b612b10878751612f19565b60405162c5803160e81b81526001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169063c5803100908490612b67908b9086908c908c908c908c906004016140b4565b6000604051808303818588803b158015612b8057600080fd5b505af1158015612b94573d6000803e3d6000fd5b505050505050505050505050565b6060600185856001600160a01b0389168587604051602001612bc99695949392919061411b565b604051602081830303815290604052905095945050505050565b7f000000000000000000000000000000000000000000000000000000000000000090565b60008080612c158482612646565b60ff16148015612c26575082516029145b612c425760405162461bcd60e51b815260040161098b90614180565b612c4d83600d612f8a565b9150612c5a836021612fef565b9050915091565b6000612c6b612be3565b610b79906001600160401b0384166141b2565b6000612c8a838361304c565b5092915050565b600080806060816001612ca48783612646565b60ff1614612cc45760405162461bcd60e51b815260040161098b90614180565b612ccf86600d612f8a565b9350612cdc866021612fef565b9250612ce98660296130fb565b9450612cf6866049612fef565b9050612d126051808851612d0a9190613b3e565b889190612295565b915091939590929450565b6000612d2883613159565b61ffff808716600090815260026020908152604080832093891683529290529081205491925090612d5a908490613a9e565b905060008111612da95760405162461bcd60e51b815260206004820152601a602482015279131e905c1c0e881b5a5b91d85cd31a5b5a5d081b9bdd081cd95d60321b604482015260640161098b565b80821015610fea5760405162461bcd60e51b815260206004820152601b60248201527a4c7a4170703a20676173206c696d697420697320746f6f206c6f7760281b604482015260640161098b565b6001600160a01b038216612e575760405162461bcd60e51b815260206004820152602160248201527f45524332303a206275726e2066726f6d20746865207a65726f206164647265736044820152607360f81b606482015260840161098b565b6001600160a01b03821660009081526008602052604090205481811015612ecb5760405162461bcd60e51b815260206004820152602260248201527f45524332303a206275726e20616d6f756e7420657863656564732062616c616e604482015261636560f01b606482015260840161098b565b6001600160a01b03831660008181526008602090815260408083208686039055600a805487900390555185815291929160008051602061420a833981519152910160405180910390a3505050565b61ffff821660009081526003602052604081205490819003612f3a57506127105b808211156125d65760405162461bcd60e51b815260206004820181905260248201527f4c7a4170703a207061796c6f61642073697a6520697320746f6f206c61726765604482015260640161098b565b6000612f97826014613a9e565b83511015612fdf5760405162461bcd60e51b8152602060048201526015602482015274746f416464726573735f6f75744f66426f756e647360581b604482015260640161098b565b500160200151600160601b900490565b6000612ffc826008613a9e565b835110156130435760405162461bcd60e51b8152602060048201526014602482015273746f55696e7436345f6f75744f66426f756e647360601b604482015260640161098b565b50016008015190565b6001600160a01b0382166130a25760405162461bcd60e51b815260206004820152601f60248201527f45524332303a206d696e7420746f20746865207a65726f206164647265737300604482015260640161098b565b80600a60008282546130b49190613a9e565b90915550506001600160a01b03821660008181526008602090815260408083208054860190555184815260008051602061420a833981519152910160405180910390a35050565b6000613108826020613a9e565b835110156131505760405162461bcd60e51b8152602060048201526015602482015274746f427974657333325f6f75744f66426f756e647360581b604482015260640161098b565b50016020015190565b60006022825110156131ac5760405162461bcd60e51b815260206004820152601c60248201527b4c7a4170703a20696e76616c69642061646170746572506172616d7360201b604482015260640161098b565b506022015190565b803561ffff811681146131c657600080fd5b919050565b60008083601f8401126131dd57600080fd5b5081356001600160401b038111156131f457600080fd5b60208301915083602082850101111561320c57600080fd5b9250929050565b80356001600160401b03811681146131c657600080fd5b6000806000806000806080878903121561324357600080fd5b61324c876131b4565b955060208701356001600160401b038082111561326857600080fd5b6132748a838b016131cb565b909750955085915061328860408a01613213565b9450606089013591508082111561329e57600080fd5b506132ab89828a016131cb565b979a9699509497509295939492505050565b6000602082840312156132cf57600080fd5b81356001600160e01b0319811681146112f757600080fd5b60005b838110156133025781810151838201526020016132ea565b50506000910152565b600081518084526133238160208601602086016132e7565b601f01601f19169290920160200192915050565b6020815260006112f7602083018461330b565b60006020828403121561335c57600080fd5b6112f7826131b4565b6001600160a01b0381168114611aa057600080fd5b6000806040838503121561338d57600080fd5b823561339881613365565b946020939093013593505050565b600080604083850312156133b957600080fd5b613398836131b4565b6000806000606084860312156133d757600080fd5b83356133e281613365565b925060208401356133f281613365565b929592945050506040919091013590565b803580151581146131c657600080fd5b60008060008060008060a0878903121561342c57600080fd5b613435876131b4565b9550602087013594506040870135935061345160608801613403565b925060808701356001600160401b0381111561346c57600080fd5b6132ab89828a016131cb565b60008060006040848603121561348d57600080fd5b613496846131b4565b925060208401356001600160401b038111156134b157600080fd5b6134bd868287016131cb565b9497909650939450505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715613508576135086134ca565b604052919050565b60006001600160401b03821115613529576135296134ca565b50601f01601f191660200190565b60008060006060848603121561354c57600080fd5b613555846131b4565b925060208401356001600160401b0381111561357057600080fd5b8401601f8101861361358157600080fd5b803561359461358f82613510565b6134e0565b8181528760208385010111156135a957600080fd5b816020840160208301376000602083830101528094505050506135ce60408501613213565b90509250925092565b6000606082840312156135e957600080fd5b50919050565b600080600080600060a0868803121561360757600080fd5b853561361281613365565b9450613620602087016131b4565b9350604086013592506060860135915060808601356001600160401b0381111561364957600080fd5b613655888289016135d7565b9150509295509295909350565b60006020828403121561367457600080fd5b81356112f781613365565b60008060008060008060008060e0898b03121561369b57600080fd5b88356136a681613365565b97506136b460208a016131b4565b9650604089013595506060890135945060808901356001600160401b03808211156136de57600080fd5b6136ea8c838d016131cb565b90965094508491506136fe60a08c01613213565b935060c08b013591508082111561371457600080fd5b506137218b828c016135d7565b9150509295985092959890939650565b6000806040838503121561374457600080fd5b61374d836131b4565b915061375b602084016131b4565b90509250929050565b6001600160a01b0391909116815260200190565b600080600080600080600080600060e08a8c03121561379657600080fd5b61379f8a6131b4565b985060208a0135975060408a0135965060608a01356001600160401b03808211156137c957600080fd5b6137d58d838e016131cb565b90985096508691506137e960808d01613213565b95506137f760a08d01613403565b945060c08c013591508082111561380d57600080fd5b5061381a8c828d016131cb565b915080935050809150509295985092959850929598565b60008060008060006080868803121561384957600080fd5b613852866131b4565b9450613860602087016131b4565b93506040860135925060608601356001600160401b0381111561388257600080fd5b61388e888289016131cb565b969995985093965092949392505050565b600080604083850312156138b257600080fd5b82356138bd81613365565b915060208301356138cd81613365565b809150509250929050565b6000806000606084860312156138ed57600080fd5b6138f6846131b4565b9250613904602085016131b4565b9150604084013590509250925092565b60006020828403121561392657600080fd5b6112f782613403565b6000806000806000806000806000806101008b8d03121561394f57600080fd5b6139588b6131b4565b995060208b01356001600160401b038082111561397457600080fd5b6139808e838f016131cb565b909b50995089915061399460408e01613213565b985060608d0135975060808d013591506139ad82613365565b90955060a08c0135945060c08c013590808211156139ca57600080fd5b506139d78d828e016131cb565b9150809450508092505060e08b013590509295989b9194979a5092959850565b60008060008060808587031215613a0d57600080fd5b613a16856131b4565b9350613a24602086016131b4565b92506040850135613a3481613365565b9396929550929360600135925050565b600181811c90821680613a5857607f821691505b6020821081036135e957634e487b7160e01b600052602260045260246000fd5b8183823760009101908152919050565b634e487b7160e01b600052601160045260246000fd5b80820180821115610b7957610b79613a88565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b61ffff84168152604060208201526000611b4b604083018486613ab1565b6000808335601e19843603018112613b0f57600080fd5b8301803591506001600160401b03821115613b2957600080fd5b60200191503681900382131561320c57600080fd5b81810381811115610b7957610b79613a88565b8284823760609190911b6001600160601b0319169101908152601401919050565b601f8211156125d657600081815260208120601f850160051c81016020861015613b995750805b601f850160051c820191505b81811015610fea57828155600101613ba5565b600019600383901b1c191660019190911b1790565b81516001600160401b03811115613be657613be66134ca565b613bfa81613bf48454613a44565b84613b72565b602080601f831160018114613c295760008415613c175750858301515b613c218582613bb8565b865550610fea565b600085815260208120601f198616915b82811015613c5857888601518255948401946001909101908401613c39565b5085821015613c765787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600061ffff808816835280871660208401525084604083015260806060830152613cb4608083018486613ab1565b979650505050505050565b61ffff86168152608060208201526000613cdd608083018688613ab1565b6001600160401b0394909416604083015250606001529392505050565b61ffff8916815260c060208201526000613d1860c08301898b613ab1565b6001600160401b0388166040840152606083018790526080830186905282810360a0840152613d48818587613ab1565b9b9a5050505050505050505050565b6001600160401b03831115613d6e57613d6e6134ca565b613d8283613d7c8354613a44565b83613b72565b6000601f841160018114613db05760008515613d9e5750838201355b613da88682613bb8565b845550610c93565b600083815260209020601f19861690835b82811015613de15786850135825560209485019460019092019101613dc1565b5086821015613dfe5760001960f88860031b161c19848701351681555b505060018560011b0183555050505050565b600060208284031215613e2257600080fd5b81516001600160401b03811115613e3857600080fd5b8201601f81018413613e4957600080fd5b8051613e5761358f82613510565b818152856020838501011115613e6c57600080fd5b611b4b8260208301602086016132e7565b61ffff85168152608060208201526000613e9a608083018661330b565b6001600160401b03851660408401528281036060840152613cb4818561330b565b61ffff861681526001600160a01b038516602082015260a060408201819052600090613ee99083018661330b565b84151560608401528281036080840152613f03818561330b565b98975050505050505050565b60008060408385031215613f2257600080fd5b505080516020909101519092909150565b60208082526019908201527813d19510dbdc994e88185b5bdd5b9d081d1bdbc81cdb585b1b603a1b604082015260600190565b60008251613f788184602087016132e7565b9190910192915050565b61ffff8616815260a060208201526000613f9f60a083018761330b565b6001600160401b03861660408401528281036060840152613fc0818661330b565b90508281036080840152613f03818561330b565b634e487b7160e01b600052601260045260246000fd5b600082613ff957613ff9613fd4565b500490565b600061010061ffff8b16835280602084015261401c8184018b61330b565b6001600160401b038a166040850152606084018990526001600160a01b038816608085015260a0840187905283810360c0850152905061405c818661330b565b9150508260e08301529998505050505050505050565b606081526000614085606083018661330b565b6001600160401b039490941660208301525060400152919050565b6000826140af576140af613fd4565b500690565b61ffff8716815260c0602082015260006140d160c083018861330b565b82810360408401526140e3818861330b565b6001600160a01b0387811660608601528616608085015283810360a0850152905061410e818561330b565b9998505050505050505050565b6001600160f81b031960f888901b168152600181018690526001600160c01b031960c086811b821660218401526029830186905284901b166049820152815160009061416e8160518501602087016132e7565b91909101605101979650505050505050565b60208082526018908201527713d19510dbdc994e881a5b9d985b1a59081c185e5b1bd85960421b604082015260600190565b8082028115828204841417610b7957610b79613a8856fed81fc9b8523134ed613870ed029d6170cbb73aa6a6bc311b9a642689fb9df59abf551ec93859b170f9b2141bd9298bf3f64322c6f7beb2543a0cb669834118bfddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3efa2646970667358221220a7b0819d130228de1a73b45a5ca5c5bbf706857759be311e9f5dbbb4a705146464736f6c634300081200330000000000000000000000003c2269811836af69497e5f486a85d7316753cf620000000000000000000000000000000000000000000000000000000000000009

Deployed Bytecode

0x6080604052600436106102435760003560e01c80621d35671461024857806301ffc9a71461026a57806306fdde031461029f57806307e0db17146102c1578063095ea7b3146102e15780630df374831461030157806310ddb1371461032157806318160ddd1461034157806323b872dd14610360578063313ce56714610380578063365260b4146103a257806339509351146103d75780633d8b38f6146103f75780633f1f4fa41461041757806342d65a8d1461044457806344770515146104645780634c42899a146104795780635b8c41e61461048e57806366ad5c8a146104dd578063695ef6bf146104fd57806370a0823114610510578063715018a6146105465780637533d7881461055b57806376203b481461057b578063857749b01461058e5780638cfd8f5c146105c25780638da5cb5b146105fa5780639358928b1461061c578063950c8a741461063157806395d89b41146106515780639bdb9812146106665780639f38369a146106b8578063a457c2d7146106d8578063a4c51df5146106f8578063a6c3d16514610718578063a9059cbb14610738578063b353aaa714610758578063baf3292d1461078c578063c4461834146107ac578063cbed8b9c146107c2578063d1deba1f146107e2578063dd62ed3e146107f5578063df2a5b3b14610815578063e6a20ae614610835578063eab45d9c1461084a578063eaffd49a1461086a578063eb8d72b71461088a578063ed629c5c146108aa578063f2fde38b146108c4578063f5ecbdbc146108e4578063fc0c546a14610904575b600080fd5b34801561025457600080fd5b5061026861026336600461322a565b610917565b005b34801561027657600080fd5b5061028a6102853660046132bd565b610b48565b60405190151581526020015b60405180910390f35b3480156102ab57600080fd5b506102b4610b7f565b6040516102969190613337565b3480156102cd57600080fd5b506102686102dc36600461334a565b610c11565b3480156102ed57600080fd5b5061028a6102fc36600461337a565b610c9a565b34801561030d57600080fd5b5061026861031c3660046133a6565b610cb2565b34801561032d57600080fd5b5061026861033c36600461334a565b610cd1565b34801561034d57600080fd5b50600a545b604051908152602001610296565b34801561036c57600080fd5b5061028a61037b3660046133c2565b610d29565b34801561038c57600080fd5b5060125b60405160ff9091168152602001610296565b3480156103ae57600080fd5b506103c26103bd366004613413565b610d4d565b60408051928352602083019190915201610296565b3480156103e357600080fd5b5061028a6103f236600461337a565b610da2565b34801561040357600080fd5b5061028a610412366004613478565b610dc4565b34801561042357600080fd5b5061035261043236600461334a565b60036020526000908152604090205481565b34801561045057600080fd5b5061026861045f366004613478565b610e90565b34801561047057600080fd5b50610352600081565b34801561048557600080fd5b50610390600081565b34801561049a57600080fd5b506103526104a9366004613537565b6005602090815260009384526040808520845180860184018051928152908401958401959095209452929052825290205481565b3480156104e957600080fd5b506102686104f836600461322a565b610f16565b61026861050b3660046135ef565b610ff2565b34801561051c57600080fd5b5061035261052b366004613662565b6001600160a01b031660009081526008602052604090205490565b34801561055257600080fd5b5061026861105d565b34801561056757600080fd5b506102b461057636600461334a565b611071565b61026861058936600461367f565b61110b565b34801561059a57600080fd5b506103907f000000000000000000000000000000000000000000000000000000000000000981565b3480156105ce57600080fd5b506103526105dd366004613731565b600260209081526000928352604080842090915290825290205481565b34801561060657600080fd5b5061060f6111ba565b6040516102969190613764565b34801561062857600080fd5b506103526111c9565b34801561063d57600080fd5b5060045461060f906001600160a01b031681565b34801561065d57600080fd5b506102b46111d9565b34801561067257600080fd5b5061028a610681366004613537565b6007602090815260009384526040808520845180860184018051928152908401958401959095209452929052825290205460ff1681565b3480156106c457600080fd5b506102b46106d336600461334a565b6111e8565b3480156106e457600080fd5b5061028a6106f336600461337a565b6112fe565b34801561070457600080fd5b506103c2610713366004613778565b611379565b34801561072457600080fd5b50610268610733366004613478565b611408565b34801561074457600080fd5b5061028a61075336600461337a565b611491565b34801561076457600080fd5b5061060f7f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf6281565b34801561079857600080fd5b506102686107a7366004613662565b61149f565b3480156107b857600080fd5b5061035261271081565b3480156107ce57600080fd5b506102686107dd366004613831565b6114fd565b6102686107f036600461322a565b611587565b34801561080157600080fd5b5061035261081036600461389f565b61179d565b34801561082157600080fd5b506102686108303660046138d8565b6117c8565b34801561084157600080fd5b50610390600181565b34801561085657600080fd5b50610268610865366004613914565b61187a565b34801561087657600080fd5b5061026861088536600461392f565b6118c3565b34801561089657600080fd5b506102686108a5366004613478565b6119d0565b3480156108b657600080fd5b5060065461028a9060ff1681565b3480156108d057600080fd5b506102686108df366004613662565b611a2a565b3480156108f057600080fd5b506102b46108ff3660046139f7565b611aa3565b34801561091057600080fd5b503061060f565b337f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf626001600160a01b0316146109945760405162461bcd60e51b815260206004820152601e60248201527f4c7a4170703a20696e76616c696420656e64706f696e742063616c6c6572000060448201526064015b60405180910390fd5b61ffff8616600090815260016020526040812080546109b290613a44565b80601f01602080910402602001604051908101604052809291908181526020018280546109de90613a44565b8015610a2b5780601f10610a0057610100808354040283529160200191610a2b565b820191906000526020600020905b815481529060010190602001808311610a0e57829003601f168201915b50505050509050805186869050148015610a46575060008151115b8015610a6e575080516020820120604051610a649088908890613a78565b6040518091039020145b610ac95760405162461bcd60e51b815260206004820152602660248201527f4c7a4170703a20696e76616c696420736f757263652073656e64696e6720636f6044820152651b9d1c9858dd60d21b606482015260840161098b565b610b3f8787878080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8a018190048102820181019092528881528a935091508890889081908401838280828437600092019190915250611b5492505050565b50505050505050565b60006001600160e01b03198216631f7ecdf760e01b1480610b7957506301ffc9a760e01b6001600160e01b03198316145b92915050565b6060600b8054610b8e90613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054610bba90613a44565b8015610c075780601f10610bdc57610100808354040283529160200191610c07565b820191906000526020600020905b815481529060010190602001808311610bea57829003601f168201915b5050505050905090565b610c19611bcd565b6040516307e0db1760e01b815261ffff821660048201527f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf626001600160a01b0316906307e0db17906024015b600060405180830381600087803b158015610c7f57600080fd5b505af1158015610c93573d6000803e3d6000fd5b5050505050565b600033610ca8818585611c2c565b5060019392505050565b610cba611bcd565b61ffff909116600090815260036020526040902055565b610cd9611bcd565b6040516310ddb13760e01b815261ffff821660048201527f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf626001600160a01b0316906310ddb13790602401610c65565b600033610d37858285611d50565b610d42858585611dca565b506001949350505050565b600080610d938888888888888080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250611f6392505050565b91509150965096945050505050565b600033610ca8818585610db5838361179d565b610dbf9190613a9e565b611c2c565b61ffff831660009081526001602052604081208054829190610de590613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054610e1190613a44565b8015610e5e5780601f10610e3357610100808354040283529160200191610e5e565b820191906000526020600020905b815481529060010190602001808311610e4157829003601f168201915b505050505090508383604051610e75929190613a78565b60405180910390208180519060200120149150509392505050565b610e98611bcd565b6040516342d65a8d60e01b81526001600160a01b037f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf6216906342d65a8d90610ee890869086908690600401613ada565b600060405180830381600087803b158015610f0257600080fd5b505af1158015610b3f573d6000803e3d6000fd5b333014610f745760405162461bcd60e51b815260206004820152602660248201527f4e6f6e626c6f636b696e674c7a4170703a2063616c6c6572206d7573742062656044820152650204c7a4170760d41b606482015260840161098b565b610fea8686868080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f89018190048102820181019092528781528993509150879087908190840183828082843760009201919091525061205792505050565b505050505050565b610fea858585856110066020870187613662565b6110166040880160208901613662565b6110236040890189613af8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506120dd92505050565b611065611bcd565b61106f6000612187565b565b6001602052600090815260409020805461108a90613a44565b80601f01602080910402602001604051908101604052809291908181526020018280546110b690613a44565b80156111035780601f106110d857610100808354040283529160200191611103565b820191906000526020600020905b8154815290600101906020018083116110e657829003601f168201915b505050505081565b6111af8888888888888080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152508a92506111589150506020890189613662565b61116860408a0160208b01613662565b61117560408b018b613af8565b8080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506121d792505050565b505050505050505050565b6000546001600160a01b031690565b60006111d4600a5490565b905090565b6060600c8054610b8e90613a44565b61ffff811660009081526001602052604081208054606092919061120b90613a44565b80601f016020809104026020016040519081016040528092919081815260200182805461123790613a44565b80156112845780601f1061125957610100808354040283529160200191611284565b820191906000526020600020905b81548152906001019060200180831161126757829003601f168201915b5050505050905080516000036112dc5760405162461bcd60e51b815260206004820152601d60248201527f4c7a4170703a206e6f20747275737465642070617468207265636f7264000000604482015260640161098b565b6112f76000601483516112ef9190613b3e565b839190612295565b9392505050565b6000338161130c828661179d565b90508381101561136c5760405162461bcd60e51b815260206004820152602560248201527f45524332303a2064656372656173656420616c6c6f77616e63652062656c6f77604482015264207a65726f60d81b606482015260840161098b565b610d428286868403611c2c565b6000806113f68b8b8b8b8b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525050604080516020601f8d018190048102820181019092528b81528e93508d9250908c908c90819084018382808284376000920191909152506123a292505050565b91509150995099975050505050505050565b611410611bcd565b81813060405160200161142593929190613b51565b60408051601f1981840301815291815261ffff85166000908152600160205220906114509082613bcd565b507f8c0400cfe2d1199b1a725c78960bcc2a344d869b80590d0f2bd005db15a572ce83838360405161148493929190613ada565b60405180910390a1505050565b600033610ca8818585611dca565b6114a7611bcd565b600480546001600160a01b0319166001600160a01b0383161790556040517f5db758e995a17ec1ad84bdef7e8c3293a0bd6179bcce400dff5d4c3d87db726b906114f2908390613764565b60405180910390a150565b611505611bcd565b6040516332fb62e760e21b81526001600160a01b037f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf62169063cbed8b9c906115599088908890889088908890600401613c86565b600060405180830381600087803b15801561157357600080fd5b505af11580156111af573d6000803e3d6000fd5b61ffff861660009081526005602052604080822090516115aa9088908890613a78565b90815260408051602092819003830190206001600160401b0387166000908152925290205490508061162a5760405162461bcd60e51b815260206004820152602360248201527f4e6f6e626c6f636b696e674c7a4170703a206e6f2073746f726564206d65737360448201526261676560e81b606482015260840161098b565b80838360405161163b929190613a78565b60405180910390201461169a5760405162461bcd60e51b815260206004820152602160248201527f4e6f6e626c6f636b696e674c7a4170703a20696e76616c6964207061796c6f616044820152601960fa1b606482015260840161098b565b61ffff871660009081526005602052604080822090516116bd9089908990613a78565b90815260408051602092819003830181206001600160401b038916600090815290845282902093909355601f88018290048202830182019052868252611755918991899089908190840183828082843760009201919091525050604080516020601f8a018190048102820181019092528881528a93509150889088908190840183828082843760009201919091525061205792505050565b7fc264d91f3adc5588250e1551f547752ca0cfa8f6b530d243b9f9f4cab10ea8e5878787878560405161178c959493929190613cbf565b60405180910390a150505050505050565b6001600160a01b03918216600090815260096020908152604080832093909416825291909152205490565b6117d0611bcd565b600081116118185760405162461bcd60e51b81526020600482015260156024820152744c7a4170703a20696e76616c6964206d696e47617360581b604482015260640161098b565b61ffff83811660008181526002602090815260408083209487168084529482529182902085905581519283528201929092529081018290527f9d5c7c0b934da8fefa9c7760c98383778a12dfbfc0c3b3106518f43fb9508ac090606001611484565b611882611bcd565b6006805460ff19168215159081179091556040519081527f1584ad594a70cbe1e6515592e1272a987d922b097ead875069cebe8b40c004a4906020016114f2565b3330146119125760405162461bcd60e51b815260206004820152601f60248201527f4f4654436f72653a2063616c6c6572206d757374206265204f4654436f726500604482015260640161098b565b61191d30868661245d565b9350846001600160a01b03168a61ffff166000805160206141ea8339815191528660405161194d91815260200190565b60405180910390a3604051633fe79aed60e11b81526001600160a01b03861690637fcf35da908390611991908e908e908e908e908e908d908d908d90600401613cfa565b600060405180830381600088803b1580156119ab57600080fd5b5087f11580156119bf573d6000803e3d6000fd5b505050505050505050505050505050565b6119d8611bcd565b61ffff831660009081526001602052604090206119f6828483613d57565b507ffa41487ad5d6728f0b19276fa1eddc16558578f5109fc39d2dc33c3230470dab83838360405161148493929190613ada565b611a32611bcd565b6001600160a01b038116611a975760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b606482015260840161098b565b611aa081612187565b50565b604051633d7b2f6f60e21b815261ffff808616600483015284166024820152306044820152606481018290526060907f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf626001600160a01b03169063f5ecbdbc90608401600060405180830381865afa158015611b23573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052611b4b9190810190613e10565b95945050505050565b600080611bb75a60966366ad5c8a60e01b89898989604051602401611b7c9493929190613e7d565b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b031990931692909217909152309291906124af565b9150915081610fea57610fea8686868685612539565b33611bd66111ba565b6001600160a01b03161461106f5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604482015260640161098b565b6001600160a01b038316611c8e5760405162461bcd60e51b8152602060048201526024808201527f45524332303a20617070726f76652066726f6d20746865207a65726f206164646044820152637265737360e01b606482015260840161098b565b6001600160a01b038216611cef5760405162461bcd60e51b815260206004820152602260248201527f45524332303a20617070726f766520746f20746865207a65726f206164647265604482015261737360f01b606482015260840161098b565b6001600160a01b0383811660008181526009602090815260408083209487168084529482529182902085905590518481527f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925910160405180910390a3505050565b6000611d5c848461179d565b90506000198114611dc45781811015611db75760405162461bcd60e51b815260206004820152601d60248201527f45524332303a20696e73756666696369656e7420616c6c6f77616e6365000000604482015260640161098b565b611dc48484848403611c2c565b50505050565b6001600160a01b038316611e2e5760405162461bcd60e51b815260206004820152602560248201527f45524332303a207472616e736665722066726f6d20746865207a65726f206164604482015264647265737360d81b606482015260840161098b565b6001600160a01b038216611e905760405162461bcd60e51b815260206004820152602360248201527f45524332303a207472616e7366657220746f20746865207a65726f206164647260448201526265737360e81b606482015260840161098b565b6001600160a01b03831660009081526008602052604090205481811015611f085760405162461bcd60e51b815260206004820152602660248201527f45524332303a207472616e7366657220616d6f756e7420657863656564732062604482015265616c616e636560d01b606482015260840161098b565b6001600160a01b03808516600081815260086020526040808220868603905592861680825290839020805486019055915160008051602061420a83398151915290611f569086815260200190565b60405180910390a3611dc4565b6000806000611fb187611f75886125db565b6040805160006020820152602181019390935260c09190911b6001600160c01b0319166041830152805160298184030181526049909201905290565b60405163040a7bb160e41b81529091506001600160a01b037f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf6216906340a7bb1090612008908b90309086908b908b90600401613ebb565b6040805180830381865afa158015612024573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906120489190613f0f565b92509250509550959350505050565b60006120638282612646565b905060ff811661207e57612079858585856126a2565b610c93565b60001960ff8216016120965761207985858585612720565b60405162461bcd60e51b815260206004820152601c60248201527b4f4654436f72653a20756e6b6e6f776e207061636b6574207479706560201b604482015260640161098b565b60006120eb87828481612929565b6120f4856129a3565b509050612103888888846129cb565b9050600081116121255760405162461bcd60e51b815260040161098b90613f33565b600061213487611f75846125db565b90506121448882878787346129fd565b86896001600160a01b03168961ffff166000805160206141ca8339815191528560405161217391815260200190565b60405180910390a450979650505050505050565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b60006121ef896001846001600160401b038916612929565b6121f8876129a3565b5090506122078a8a8a846129cb565b9050600081116122295760405162461bcd60e51b815260040161098b90613f33565b6000612240338a612239856125db565b8a8a612ba2565b90506122508a82878787346129fd565b888b6001600160a01b03168b61ffff166000805160206141ca8339815191528560405161227f91815260200190565b60405180910390a4509998505050505050505050565b6060816122a381601f613a9e565b10156122e25760405162461bcd60e51b815260206004820152600e60248201526d736c6963655f6f766572666c6f7760901b604482015260640161098b565b6122ec8284613a9e565b845110156123305760405162461bcd60e51b8152602060048201526011602482015270736c6963655f6f75744f66426f756e647360781b604482015260640161098b565b60608215801561234f5760405191506000825260208201604052612399565b6040519150601f8416801560200281840101858101878315602002848b0101015b81831015612388578051835260209283019201612370565b5050858452601f01601f1916604052505b50949350505050565b60008060006123b5338a6122398b6125db565b60405163040a7bb160e41b81529091506001600160a01b037f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf6216906340a7bb109061240c908d90309086908b908b90600401613ebb565b6040805180830381865afa158015612428573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061244c9190613f0f565b925092505097509795505050505050565b600033306001600160a01b0386161480159061248b5750806001600160a01b0316856001600160a01b031614155b1561249b5761249b858285611d50565b6124a6858585611dca565b50909392505050565b6000606060008060008661ffff166001600160401b038111156124d4576124d46134ca565b6040519080825280601f01601f1916602001820160405280156124fe576020820181803683370190505b50905060008087516020890160008d8df191503d925086831115612520578692505b828152826000602083013e909890975095505050505050565b8180519060200120600560008761ffff1661ffff1681526020019081526020016000208560405161256a9190613f66565b9081526040805191829003602090810183206001600160401b0388166000908152915220919091557fe183f33de2837795525b4792ca4cd60535bd77c53b7e7030060bfcf5734d6b0c906125c79087908790879087908790613f82565b60405180910390a15050505050565b505050565b6000806125e6612be3565b6125f09084613fea565b90506001600160401b03811115610b795760405162461bcd60e51b815260206004820152601a6024820152794f4654436f72653a20616d6f756e745344206f766572666c6f7760301b604482015260640161098b565b6000612653826001613a9e565b835110156126995760405162461bcd60e51b8152602060048201526013602482015272746f55696e74385f6f75744f66426f756e647360681b604482015260640161098b565b50016001015190565b6000806126ae83612c07565b90925090506001600160a01b0382166126c75761dead91505b60006126d282612c61565b90506126df878483612c7e565b9050826001600160a01b03168761ffff166000805160206141ea8339815191528360405161270f91815260200190565b60405180910390a350505050505050565b600080600080600061273186612c91565b945094509450945094506000600760008b61ffff1661ffff168152602001908152602001600020896040516127669190613f66565b90815260408051602092819003830190206001600160401b038b166000908152925281205460ff16915061279985612c61565b905081612807576127ab8b3083612c7e565b61ffff8c166000908152600760205260409081902090519192506001916127d3908d90613f66565b90815260408051602092819003830190206001600160401b038d16600090815292529020805460ff19169115159190911790555b6001600160a01b0386163b612859577f9aedf5fdba8716db3b6705ca00150643309995d4f818a249ed6dde6677e7792d866040516128459190613764565b60405180910390a150505050505050611dc4565b8a8a8a8a8a8a868a60008a612877578b6001600160401b0316612879565b5a5b90506000806128ab5a609663eaffd49a60e01b8e8e8e8d8d8d8d8d604051602401611b7c989796959493929190613ffe565b915091508115612904578751602089012060405161ffff8d16907fb8890edbfc1c74692f527444645f95489c3703cc2df42e4a366f5d06fa6cd884906128f6908e908e908690614072565b60405180910390a250612911565b6129118b8b8b8b85612539565b50505050505050505050505050505050505050505050565b60065460ff16156129455761294084848484612d1d565b611dc4565b815115611dc45760405162461bcd60e51b815260206004820152602660248201527f4f4654436f72653a205f61646170746572506172616d73206d7573742062652060448201526532b6b83a3c9760d11b606482015260840161098b565b6000806129ae612be3565b6129b890846140a0565b90506129c48184613b3e565b9150915091565b6000336001600160a01b03861681146129e9576129e9868285611d50565b6129f38684612df7565b5090949350505050565b61ffff861660009081526001602052604081208054612a1b90613a44565b80601f0160208091040260200160405190810160405280929190818152602001828054612a4790613a44565b8015612a945780601f10612a6957610100808354040283529160200191612a94565b820191906000526020600020905b815481529060010190602001808311612a7757829003601f168201915b505050505090508051600003612b055760405162461bcd60e51b815260206004820152603060248201527f4c7a4170703a2064657374696e6174696f6e20636861696e206973206e6f742060448201526f61207472757374656420736f7572636560801b606482015260840161098b565b612b10878751612f19565b60405162c5803160e81b81526001600160a01b037f0000000000000000000000003c2269811836af69497e5f486a85d7316753cf62169063c5803100908490612b67908b9086908c908c908c908c906004016140b4565b6000604051808303818588803b158015612b8057600080fd5b505af1158015612b94573d6000803e3d6000fd5b505050505050505050505050565b6060600185856001600160a01b0389168587604051602001612bc99695949392919061411b565b604051602081830303815290604052905095945050505050565b7f000000000000000000000000000000000000000000000000000000003b9aca0090565b60008080612c158482612646565b60ff16148015612c26575082516029145b612c425760405162461bcd60e51b815260040161098b90614180565b612c4d83600d612f8a565b9150612c5a836021612fef565b9050915091565b6000612c6b612be3565b610b79906001600160401b0384166141b2565b6000612c8a838361304c565b5092915050565b600080806060816001612ca48783612646565b60ff1614612cc45760405162461bcd60e51b815260040161098b90614180565b612ccf86600d612f8a565b9350612cdc866021612fef565b9250612ce98660296130fb565b9450612cf6866049612fef565b9050612d126051808851612d0a9190613b3e565b889190612295565b915091939590929450565b6000612d2883613159565b61ffff808716600090815260026020908152604080832093891683529290529081205491925090612d5a908490613a9e565b905060008111612da95760405162461bcd60e51b815260206004820152601a602482015279131e905c1c0e881b5a5b91d85cd31a5b5a5d081b9bdd081cd95d60321b604482015260640161098b565b80821015610fea5760405162461bcd60e51b815260206004820152601b60248201527a4c7a4170703a20676173206c696d697420697320746f6f206c6f7760281b604482015260640161098b565b6001600160a01b038216612e575760405162461bcd60e51b815260206004820152602160248201527f45524332303a206275726e2066726f6d20746865207a65726f206164647265736044820152607360f81b606482015260840161098b565b6001600160a01b03821660009081526008602052604090205481811015612ecb5760405162461bcd60e51b815260206004820152602260248201527f45524332303a206275726e20616d6f756e7420657863656564732062616c616e604482015261636560f01b606482015260840161098b565b6001600160a01b03831660008181526008602090815260408083208686039055600a805487900390555185815291929160008051602061420a833981519152910160405180910390a3505050565b61ffff821660009081526003602052604081205490819003612f3a57506127105b808211156125d65760405162461bcd60e51b815260206004820181905260248201527f4c7a4170703a207061796c6f61642073697a6520697320746f6f206c61726765604482015260640161098b565b6000612f97826014613a9e565b83511015612fdf5760405162461bcd60e51b8152602060048201526015602482015274746f416464726573735f6f75744f66426f756e647360581b604482015260640161098b565b500160200151600160601b900490565b6000612ffc826008613a9e565b835110156130435760405162461bcd60e51b8152602060048201526014602482015273746f55696e7436345f6f75744f66426f756e647360601b604482015260640161098b565b50016008015190565b6001600160a01b0382166130a25760405162461bcd60e51b815260206004820152601f60248201527f45524332303a206d696e7420746f20746865207a65726f206164647265737300604482015260640161098b565b80600a60008282546130b49190613a9e565b90915550506001600160a01b03821660008181526008602090815260408083208054860190555184815260008051602061420a833981519152910160405180910390a35050565b6000613108826020613a9e565b835110156131505760405162461bcd60e51b8152602060048201526015602482015274746f427974657333325f6f75744f66426f756e647360581b604482015260640161098b565b50016020015190565b60006022825110156131ac5760405162461bcd60e51b815260206004820152601c60248201527b4c7a4170703a20696e76616c69642061646170746572506172616d7360201b604482015260640161098b565b506022015190565b803561ffff811681146131c657600080fd5b919050565b60008083601f8401126131dd57600080fd5b5081356001600160401b038111156131f457600080fd5b60208301915083602082850101111561320c57600080fd5b9250929050565b80356001600160401b03811681146131c657600080fd5b6000806000806000806080878903121561324357600080fd5b61324c876131b4565b955060208701356001600160401b038082111561326857600080fd5b6132748a838b016131cb565b909750955085915061328860408a01613213565b9450606089013591508082111561329e57600080fd5b506132ab89828a016131cb565b979a9699509497509295939492505050565b6000602082840312156132cf57600080fd5b81356001600160e01b0319811681146112f757600080fd5b60005b838110156133025781810151838201526020016132ea565b50506000910152565b600081518084526133238160208601602086016132e7565b601f01601f19169290920160200192915050565b6020815260006112f7602083018461330b565b60006020828403121561335c57600080fd5b6112f7826131b4565b6001600160a01b0381168114611aa057600080fd5b6000806040838503121561338d57600080fd5b823561339881613365565b946020939093013593505050565b600080604083850312156133b957600080fd5b613398836131b4565b6000806000606084860312156133d757600080fd5b83356133e281613365565b925060208401356133f281613365565b929592945050506040919091013590565b803580151581146131c657600080fd5b60008060008060008060a0878903121561342c57600080fd5b613435876131b4565b9550602087013594506040870135935061345160608801613403565b925060808701356001600160401b0381111561346c57600080fd5b6132ab89828a016131cb565b60008060006040848603121561348d57600080fd5b613496846131b4565b925060208401356001600160401b038111156134b157600080fd5b6134bd868287016131cb565b9497909650939450505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f191681016001600160401b0381118282101715613508576135086134ca565b604052919050565b60006001600160401b03821115613529576135296134ca565b50601f01601f191660200190565b60008060006060848603121561354c57600080fd5b613555846131b4565b925060208401356001600160401b0381111561357057600080fd5b8401601f8101861361358157600080fd5b803561359461358f82613510565b6134e0565b8181528760208385010111156135a957600080fd5b816020840160208301376000602083830101528094505050506135ce60408501613213565b90509250925092565b6000606082840312156135e957600080fd5b50919050565b600080600080600060a0868803121561360757600080fd5b853561361281613365565b9450613620602087016131b4565b9350604086013592506060860135915060808601356001600160401b0381111561364957600080fd5b613655888289016135d7565b9150509295509295909350565b60006020828403121561367457600080fd5b81356112f781613365565b60008060008060008060008060e0898b03121561369b57600080fd5b88356136a681613365565b97506136b460208a016131b4565b9650604089013595506060890135945060808901356001600160401b03808211156136de57600080fd5b6136ea8c838d016131cb565b90965094508491506136fe60a08c01613213565b935060c08b013591508082111561371457600080fd5b506137218b828c016135d7565b9150509295985092959890939650565b6000806040838503121561374457600080fd5b61374d836131b4565b915061375b602084016131b4565b90509250929050565b6001600160a01b0391909116815260200190565b600080600080600080600080600060e08a8c03121561379657600080fd5b61379f8a6131b4565b985060208a0135975060408a0135965060608a01356001600160401b03808211156137c957600080fd5b6137d58d838e016131cb565b90985096508691506137e960808d01613213565b95506137f760a08d01613403565b945060c08c013591508082111561380d57600080fd5b5061381a8c828d016131cb565b915080935050809150509295985092959850929598565b60008060008060006080868803121561384957600080fd5b613852866131b4565b9450613860602087016131b4565b93506040860135925060608601356001600160401b0381111561388257600080fd5b61388e888289016131cb565b969995985093965092949392505050565b600080604083850312156138b257600080fd5b82356138bd81613365565b915060208301356138cd81613365565b809150509250929050565b6000806000606084860312156138ed57600080fd5b6138f6846131b4565b9250613904602085016131b4565b9150604084013590509250925092565b60006020828403121561392657600080fd5b6112f782613403565b6000806000806000806000806000806101008b8d03121561394f57600080fd5b6139588b6131b4565b995060208b01356001600160401b038082111561397457600080fd5b6139808e838f016131cb565b909b50995089915061399460408e01613213565b985060608d0135975060808d013591506139ad82613365565b90955060a08c0135945060c08c013590808211156139ca57600080fd5b506139d78d828e016131cb565b9150809450508092505060e08b013590509295989b9194979a5092959850565b60008060008060808587031215613a0d57600080fd5b613a16856131b4565b9350613a24602086016131b4565b92506040850135613a3481613365565b9396929550929360600135925050565b600181811c90821680613a5857607f821691505b6020821081036135e957634e487b7160e01b600052602260045260246000fd5b8183823760009101908152919050565b634e487b7160e01b600052601160045260246000fd5b80820180821115610b7957610b79613a88565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b61ffff84168152604060208201526000611b4b604083018486613ab1565b6000808335601e19843603018112613b0f57600080fd5b8301803591506001600160401b03821115613b2957600080fd5b60200191503681900382131561320c57600080fd5b81810381811115610b7957610b79613a88565b8284823760609190911b6001600160601b0319169101908152601401919050565b601f8211156125d657600081815260208120601f850160051c81016020861015613b995750805b601f850160051c820191505b81811015610fea57828155600101613ba5565b600019600383901b1c191660019190911b1790565b81516001600160401b03811115613be657613be66134ca565b613bfa81613bf48454613a44565b84613b72565b602080601f831160018114613c295760008415613c175750858301515b613c218582613bb8565b865550610fea565b600085815260208120601f198616915b82811015613c5857888601518255948401946001909101908401613c39565b5085821015613c765787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b600061ffff808816835280871660208401525084604083015260806060830152613cb4608083018486613ab1565b979650505050505050565b61ffff86168152608060208201526000613cdd608083018688613ab1565b6001600160401b0394909416604083015250606001529392505050565b61ffff8916815260c060208201526000613d1860c08301898b613ab1565b6001600160401b0388166040840152606083018790526080830186905282810360a0840152613d48818587613ab1565b9b9a5050505050505050505050565b6001600160401b03831115613d6e57613d6e6134ca565b613d8283613d7c8354613a44565b83613b72565b6000601f841160018114613db05760008515613d9e5750838201355b613da88682613bb8565b845550610c93565b600083815260209020601f19861690835b82811015613de15786850135825560209485019460019092019101613dc1565b5086821015613dfe5760001960f88860031b161c19848701351681555b505060018560011b0183555050505050565b600060208284031215613e2257600080fd5b81516001600160401b03811115613e3857600080fd5b8201601f81018413613e4957600080fd5b8051613e5761358f82613510565b818152856020838501011115613e6c57600080fd5b611b4b8260208301602086016132e7565b61ffff85168152608060208201526000613e9a608083018661330b565b6001600160401b03851660408401528281036060840152613cb4818561330b565b61ffff861681526001600160a01b038516602082015260a060408201819052600090613ee99083018661330b565b84151560608401528281036080840152613f03818561330b565b98975050505050505050565b60008060408385031215613f2257600080fd5b505080516020909101519092909150565b60208082526019908201527813d19510dbdc994e88185b5bdd5b9d081d1bdbc81cdb585b1b603a1b604082015260600190565b60008251613f788184602087016132e7565b9190910192915050565b61ffff8616815260a060208201526000613f9f60a083018761330b565b6001600160401b03861660408401528281036060840152613fc0818661330b565b90508281036080840152613f03818561330b565b634e487b7160e01b600052601260045260246000fd5b600082613ff957613ff9613fd4565b500490565b600061010061ffff8b16835280602084015261401c8184018b61330b565b6001600160401b038a166040850152606084018990526001600160a01b038816608085015260a0840187905283810360c0850152905061405c818661330b565b9150508260e08301529998505050505050505050565b606081526000614085606083018661330b565b6001600160401b039490941660208301525060400152919050565b6000826140af576140af613fd4565b500690565b61ffff8716815260c0602082015260006140d160c083018861330b565b82810360408401526140e3818861330b565b6001600160a01b0387811660608601528616608085015283810360a0850152905061410e818561330b565b9998505050505050505050565b6001600160f81b031960f888901b168152600181018690526001600160c01b031960c086811b821660218401526029830186905284901b166049820152815160009061416e8160518501602087016132e7565b91909101605101979650505050505050565b60208082526018908201527713d19510dbdc994e881a5b9d985b1a59081c185e5b1bd85960421b604082015260600190565b8082028115828204841417610b7957610b79613a8856fed81fc9b8523134ed613870ed029d6170cbb73aa6a6bc311b9a642689fb9df59abf551ec93859b170f9b2141bd9298bf3f64322c6f7beb2543a0cb669834118bfddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3efa2646970667358221220a7b0819d130228de1a73b45a5ca5c5bbf706857759be311e9f5dbbb4a705146464736f6c63430008120033

Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)

0000000000000000000000003c2269811836af69497e5f486a85d7316753cf620000000000000000000000000000000000000000000000000000000000000009

-----Decoded View---------------
Arg [0] : _layerZeroEndpoint (address): 0x3c2269811836af69497E5F486A85D7316753cf62
Arg [1] : _sharedDecimals (uint8): 9

-----Encoded View---------------
2 Constructor Arguments found :
Arg [0] : 0000000000000000000000003c2269811836af69497e5f486a85d7316753cf62
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000009


Deployed ByteCode Sourcemap

211:162:20:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;1167:785:15;;;;;;;;;;-1:-1:-1;1167:785:15;;;;;:::i;:::-;;:::i;:::-;;1247:233:0;;;;;;;;;;-1:-1:-1;1247:233:0;;;;;:::i;:::-;;:::i;:::-;;;2029:14:21;;2022:22;2004:41;;1992:2;1977:18;1247:233:0;;;;;;;;2085:92:4;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;4575:115:15:-;;;;;;;;;;-1:-1:-1;4575:115:15;;;;;:::i;:::-;;:::i;4272:201:4:-;;;;;;;;;;-1:-1:-1;4272:201:4;;;;;:::i;:::-;;:::i;6429:147:15:-;;;;;;;;;;-1:-1:-1;6429:147:15;;;;;:::i;:::-;;:::i;4694:121::-;;;;;;;;;;-1:-1:-1;4694:121:15;;;;;:::i;:::-;;:::i;3109:100:4:-;;;;;;;;;;-1:-1:-1;3192:12:4;;3109:100;;;3860:25:21;;;3848:2;3833:18;3109:100:4;3714:177:21;5001:256:4;;;;;;;;;;-1:-1:-1;5001:256:4;;;;;:::i;:::-;;:::i;2972:85::-;;;;;;;;;;-1:-1:-1;3050:2:4;2972:85;;;4529:4:21;4517:17;;;4499:36;;4487:2;4472:18;2972:85:4;4357:184:21;1484:329:0;;;;;;;;;;-1:-1:-1;1484:329:0;;;;;:::i;:::-;;:::i;:::-;;;;5577:25:21;;;5633:2;5618:18;;5611:34;;;;5550:18;1484:329:0;5403:248:21;5626:234:4;;;;;;;;;;-1:-1:-1;5626:234:4;;;;;:::i;:::-;;:::i;6667:251:15:-;;;;;;;;;;-1:-1:-1;6667:251:15;;;;;:::i;:::-;;:::i;735:56::-;;;;;;;;;;-1:-1:-1;735:56:15;;;;;:::i;:::-;;;;;;;;;;;;;;4819:184;;;;;;;;;;-1:-1:-1;4819:184:15;;;;;:::i;:::-;;:::i;308:40:17:-;;;;;;;;;;;;347:1;308:40;;370:33;;;;;;;;;;;;402:1;370:33;;605:89:16;;;;;;;;;;-1:-1:-1;605:89:16;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;1914:360;;;;;;;;;;-1:-1:-1;1914:360:16;;;;;:::i;:::-;;:::i;344:371:0:-;;;;;;:::i;:::-;;:::i;3259:141:4:-;;;;;;;;;;-1:-1:-1;3259:141:4;;;;;:::i;:::-;-1:-1:-1;;;;;3377:18:4;3353:7;3377:18;;;:9;:18;;;;;;;3259:141;1752:95:19;;;;;;;;;;;;;:::i;608:51:15:-;;;;;;;;;;-1:-1:-1;608:51:15;;;;;:::i;:::-;;:::i;719:475:0:-;;;;;;:::i;:::-;;:::i;454:37:17:-;;;;;;;;;;;;;;;663:68:15;;;;;;;;;;-1:-1:-1;663:68:15;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;1158:79:19;;;;;;;;;;;;;:::i;:::-;;;;;;;:::i;604:107:18:-;;;;;;;;;;;;;:::i;795:23:15:-;;;;;;;;;;-1:-1:-1;795:23:15;;;;-1:-1:-1;;;;;795:23:15;;;2280:96:4;;;;;;;;;;;;;:::i;534:87:17:-;;;;;;;;;;-1:-1:-1;534:87:17;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5638:326:15;;;;;;;;;;-1:-1:-1;5638:326:15;;;;;:::i;:::-;;:::i;6317:427:4:-;;;;;;;;;;-1:-1:-1;6317:427:4;;;;;:::i;:::-;;:::i;1817:461:0:-;;;;;;;;;;-1:-1:-1;1817:461:0;;;;;:::i;:::-;;:::i;5348:286:15:-;;;;;;;;;;-1:-1:-1;5348:286:15;;;;;:::i;:::-;;:::i;3578:193:4:-;;;;;;;;;;-1:-1:-1;3578:193:4;;;;;:::i;:::-;;:::i;558:46:15:-;;;;;;;;;;;;;;;5968:123;;;;;;;;;;-1:-1:-1;5968:123:15;;;;;:::i;:::-;;:::i;495:58::-;;;;;;;;;;;;548:5;495:58;;4352:219;;;;;;;;;;-1:-1:-1;4352:219:15;;;;;:::i;:::-;;:::i;2469:751:16:-;;;;;;:::i;:::-;;:::i;3821:165:4:-;;;;;;;;;;-1:-1:-1;3821:165:4;;;;;:::i;:::-;;:::i;6095:279:15:-;;;;;;;;;;-1:-1:-1;6095:279:15;;;;;:::i;:::-;;:::i;407:42:17:-;;;;;;;;;;;;448:1;407:42;;2244:224;;;;;;;;;;-1:-1:-1;2244:224:17;;;;;:::i;:::-;;:::i;1657:583::-;;;;;;;;;;-1:-1:-1;1657:583:17;;;;;:::i;:::-;;:::i;5140:204:15:-;;;;;;;;;;-1:-1:-1;5140:204:15;;;;;:::i;:::-;;:::i;496:34:17:-;;;;;;;;;;-1:-1:-1;496:34:17;;;;;;;;1986:188:19;;;;;;;;;;-1:-1:-1;1986:188:19;;;;;:::i;:::-;;:::i;4071:226:15:-;;;;;;;;;;-1:-1:-1;4071:226:15;;;;;:::i;:::-;;:::i;715:95:18:-;;;;;;;;;;-1:-1:-1;800:4:18;715:95;;1167:785:15;713:10:2;1424::15;-1:-1:-1;;;;;1400:35:15;;1385:90;;;;-1:-1:-1;;;1385:90:15;;15390:2:21;1385:90:15;;;15372:21:21;15429:2;15409:18;;;15402:30;15468:32;15448:18;;;15441:60;15518:18;;1385:90:15;;;;;;;;;1511:32;;;1482:26;1511:32;;;:19;:32;;;;;1482:61;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;1714:13;:20;1692:11;;:18;;:42;:70;;;;;1761:1;1738:13;:20;:24;1692:70;:132;;;;-1:-1:-1;1800:24:15;;;;;;1774:22;;;;1784:11;;;;1774:22;:::i;:::-;;;;;;;;:50;1692:132;1677:201;;;;-1:-1:-1;;;1677:201:15;;16410:2:21;1677:201:15;;;16392:21:21;16449:2;16429:18;;;16422:30;16488:34;16468:18;;;16461:62;-1:-1:-1;;;16539:18:21;;;16532:36;16585:19;;1677:201:15;16208:402:21;1677:201:15;1885:62;1904:11;1917;;1885:62;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;1885:62:15;;;;;;;;;;;;;;;;;;;;;;1930:6;;-1:-1:-1;1885:62:15;-1:-1:-1;1938:8:15;;;;;;1885:62;;1938:8;;;;1885:62;;;;;;;;;-1:-1:-1;1885:18:15;;-1:-1:-1;;;1885:62:15:i;:::-;1318:634;1167:785;;;;;;:::o;1247:233:0:-;1369:4;-1:-1:-1;;;;;;1390:39:0;;-1:-1:-1;;;1390:39:0;;:85;;-1:-1:-1;;;;;;;;;;947:40:3;;;1439:36:0;1383:92;1247:233;-1:-1:-1;;1247:233:0:o;2085:92:4:-;2139:13;2167:5;2160:12;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2085:92;:::o;4575:115:15:-;1065:13:19;:11;:13::i;:::-;4650:35:15::1;::::0;-1:-1:-1;;;4650:35:15;;16789:6:21;16777:19;;4650:35:15::1;::::0;::::1;16759:38:21::0;4650:10:15::1;-1:-1:-1::0;;;;;4650:25:15::1;::::0;::::1;::::0;16732:18:21;;4650:35:15::1;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;;;;;;4575:115:::0;:::o;4272:201:4:-;4371:4;713:10:2;4419:32:4;713:10:2;4435:7:4;4444:6;4419:8;:32::i;:::-;-1:-1:-1;4464:4:4;;4272:201;-1:-1:-1;;;4272:201:4:o;6429:147:15:-;1065:13:19;:11;:13::i;:::-;6528:35:15::1;::::0;;::::1;;::::0;;;:22:::1;:35;::::0;;;;:43;6429:147::o;4694:121::-;1065:13:19;:11;:13::i;:::-;4772:38:15::1;::::0;-1:-1:-1;;;4772:38:15;;16789:6:21;16777:19;;4772:38:15::1;::::0;::::1;16759::21::0;4772:10:15::1;-1:-1:-1::0;;;;;4772:28:15::1;::::0;::::1;::::0;16732:18:21;;4772:38:15::1;16615:188:21::0;5001:256:4;5114:4;713:10:2;5164:38:4;5180:4;713:10:2;5195:6:4;5164:15;:38::i;:::-;5208:27;5218:4;5224:2;5228:6;5208:9;:27::i;:::-;-1:-1:-1;5248:4:4;;5001:256;-1:-1:-1;;;;5001:256:4:o;1484:329:0:-;1673:17;1692:14;1721:87;1745:11;1758:10;1770:7;1779;1788:14;;1721:87;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;1721:16:0;;-1:-1:-1;;;1721:87:0:i;:::-;1714:94;;;;1484:329;;;;;;;;;:::o;5626:234:4:-;5726:4;713:10:2;5774:64:4;713:10:2;5790:7:4;5827:10;5799:25;713:10:2;5790:7:4;5799:9;:25::i;:::-;:38;;;;:::i;:::-;5774:8;:64::i;6667:251:15:-;6818:32;;;6775:4;6818:32;;;:19;:32;;;;;6789:61;;6775:4;;6818:32;6789:61;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;6901:11;;6891:22;;;;;;;:::i;:::-;;;;;;;;6873:13;6863:24;;;;;;:50;6856:57;;;6667:251;;;;;:::o;4819:184::-;1065:13:19;:11;:13::i;:::-;4943:55:15::1;::::0;-1:-1:-1;;;4943:55:15;;-1:-1:-1;;;;;4943:10:15::1;:29;::::0;::::1;::::0;:55:::1;::::0;4973:11;;4986;;;;4943:55:::1;;;:::i;:::-;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;1914:360:16::0;713:10:2;2145:4:16;2121:29;2106:92;;;;-1:-1:-1;;;2106:92:16;;17874:2:21;2106:92:16;;;17856:21:21;17913:2;17893:18;;;17886:30;17952:34;17932:18;;;17925:62;-1:-1:-1;;;18003:18:21;;;17996:36;18049:19;;2106:92:16;17672:402:21;2106:92:16;2204:65;2226:11;2239;;2204:65;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;2204:65:16;;;;;;;;;;;;;;;;;;;;;;2252:6;;-1:-1:-1;2204:65:16;-1:-1:-1;2260:8:16;;;;;;2204:65;;2260:8;;;;2204:65;;;;;;;;;-1:-1:-1;2204:21:16;;-1:-1:-1;;;2204:65:16:i;:::-;1914:360;;;;;;:::o;344:371:0:-;531:179;544:5;557:11;576:10;594:7;609:25;;;;:11;:25;:::i;:::-;642:29;;;;;;;;:::i;:::-;679:25;;;;:11;:25;:::i;:::-;531:179;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;531:5:0;;-1:-1:-1;;;531:179:0:i;1752:95:19:-;1065:13;:11;:13::i;:::-;1812:30:::1;1839:1;1812:18;:30::i;:::-;1752:95::o:0;608:51:15:-;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::o;719:475:0:-;965:224;985:5;998:11;1017:10;1035:7;1050:8;;965:224;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;1066:14:0;;-1:-1:-1;1088:25:0;;-1:-1:-1;;1088:25:0;;;:11;:25;:::i;:::-;1121:29;;;;;;;;:::i;:::-;1158:25;;;;:11;:25;:::i;:::-;965:224;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;965:12:0;;-1:-1:-1;;;965:224:0:i;:::-;;719:475;;;;;;;;:::o;1158:79:19:-;1204:7;1226:6;-1:-1:-1;;;;;1226:6:19;;1158:79::o;604:107:18:-;671:7;693:13;3192:12:4;;;3109:100;693:13:18;686:20;;604:107;:::o;2280:96:4:-;2336:13;2364:7;2357:14;;;;;:::i;5638:326:15:-;5771:35;;;5751:17;5771:35;;;:19;:35;;;;;5751:55;;5729:12;;5751:17;5771:35;5751:55;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;5820:4;:11;5835:1;5820:16;5812:58;;;;-1:-1:-1;;;5812:58:15;;19067:2:21;5812:58:15;;;19049:21:21;19106:2;19086:18;;;19079:30;19145:31;19125:18;;;19118:59;19194:18;;5812:58:15;18865:353:21;5812:58:15;5883:31;5894:1;5911:2;5897:4;:11;:16;;;;:::i;:::-;5883:4;;:31;:10;:31::i;:::-;5876:38;5638:326;-1:-1:-1;;;5638:326:15:o;6317:427:4:-;6422:4;713:10:2;6422:4:4;6497:25;713:10:2;6514:7:4;6497:9;:25::i;:::-;6470:52;;6563:15;6543:16;:35;;6528:103;;;;-1:-1:-1;;;6528:103:4;;19558:2:21;6528:103:4;;;19540:21:21;19597:2;19577:18;;;19570:30;19636:34;19616:18;;;19609:62;-1:-1:-1;;;19687:18:21;;;19680:35;19732:19;;6528:103:4;19356:401:21;6528:103:4;6655:60;6664:5;6671:7;6699:15;6680:16;:34;6655:8;:60::i;1817:461:0:-;2069:17;2088:14;2117:156;2148:11;2167:10;2185:7;2200:8;;2117:156;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;2117:156:0;;;;;;;;;;;;;;;;;;;;;;2216:14;;-1:-1:-1;2238:7:0;;-1:-1:-1;2117:156:0;2253:14;;;;;;2117:156;;2253:14;;;;2117:156;;;;;;;;;-1:-1:-1;2117:23:0;;-1:-1:-1;;;2117:156:0:i;:::-;2110:163;;;;1817:461;;;;;;;;;;;;:::o;5348:286:15:-;1065:13:19;:11;:13::i;:::-;5533:14:15::1;;5557:4;5516:47;;;;;;;;;;:::i;:::-;;::::0;;-1:-1:-1;;5516:47:15;;::::1;::::0;;;;;;5472:35:::1;::::0;::::1;;::::0;;;:19:::1;5516:47;5472:35:::0;;;:91:::1;::::0;:35;:91:::1;:::i;:::-;;5574:55;5598:14;5614;;5574:55;;;;;;;;:::i;:::-;;;;;;;;5348:286:::0;;;:::o;3578:193:4:-;3673:4;713:10:2;3721:28:4;713:10:2;3738:2:4;3742:6;3721:9;:28::i;5968:123:15:-;1065:13:19;:11;:13::i;:::-;6033:8:15::1;:20:::0;;-1:-1:-1;;;;;;6033:20:15::1;-1:-1:-1::0;;;;;6033:20:15;::::1;;::::0;;6064:22:::1;::::0;::::1;::::0;::::1;::::0;6033:20;;6064:22:::1;:::i;:::-;;;;;;;;5968:123:::0;:::o;4352:219::-;1065:13:19;:11;:13::i;:::-;4504:62:15::1;::::0;-1:-1:-1;;;4504:62:15;;-1:-1:-1;;;;;4504:10:15::1;:20;::::0;::::1;::::0;:62:::1;::::0;4525:8;;4535;;4545:11;;4558:7;;;;4504:62:::1;;;:::i;:::-;;;;;;;;;;;;;;;;;;::::0;::::1;;;;;;;;;;;;::::0;::::1;;;;2469:751:16::0;2690:27;;;2668:19;2690:27;;;:14;:27;;;;;;:40;;;;2718:11;;;;2690:40;:::i;:::-;;;;;;;;;;;;;;;;-1:-1:-1;;;;;2690:48:16;;;;;;;;;;;;-1:-1:-1;2690:48:16;2744:73;;;;-1:-1:-1;;;2744:73:16;;23022:2:21;2744:73:16;;;23004:21:21;23061:2;23041:18;;;23034:30;23100:34;23080:18;;;23073:62;-1:-1:-1;;;23151:18:21;;;23144:33;23194:19;;2744:73:16;22820:399:21;2744:73:16;2861:11;2848:8;;2838:19;;;;;;;:::i;:::-;;;;;;;;:34;2823:92;;;;-1:-1:-1;;;2823:92:16;;23426:2:21;2823:92:16;;;23408:21:21;23465:2;23445:18;;;23438:30;23504:34;23484:18;;;23477:62;-1:-1:-1;;;23555:18:21;;;23548:31;23596:19;;2823:92:16;23224:397:21;2823:92:16;2953:27;;;3012:1;2953:27;;;:14;:27;;;;;;:40;;;;2981:11;;;;2953:40;:::i;:::-;;;;;;;;;;;;;;;;-1:-1:-1;;;;;2953:48:16;;;;;;;;;;;;:61;;;;3073:65;;;;;;;;;;;;;;;;;;;3095:11;;3108;;3073:65;;;;;;3108:11;3073:65;;3108:11;3073:65;;;;;;;;;-1:-1:-1;;3073:65:16;;;;;;;;;;;;;;;;;;;;;;3121:6;;-1:-1:-1;3073:65:16;-1:-1:-1;3129:8:16;;;;;;3073:65;;3129:8;;;;3073:65;;;;;;;;;-1:-1:-1;3073:21:16;;-1:-1:-1;;;3073:65:16:i;:::-;3149:66;3169:11;3182;;3195:6;3203:11;3149:66;;;;;;;;;;:::i;:::-;;;;;;;;2622:598;2469:751;;;;;;:::o;3821:165:4:-;-1:-1:-1;;;;;3954:18:4;;;3930:7;3954:18;;;:11;:18;;;;;;;;:27;;;;;;;;;;;;;3821:165::o;6095:279:15:-;1065:13:19;:11;:13::i;:::-;6227:1:15::1;6217:7;:11;6209:45;;;::::0;-1:-1:-1;;;6209:45:15;;24326:2:21;6209:45:15::1;::::0;::::1;24308:21:21::0;24365:2;24345:18;;;24338:30;-1:-1:-1;;;24384:18:21;;;24377:51;24445:18;;6209:45:15::1;24124:345:21::0;6209:45:15::1;6260:28;::::0;;::::1;;::::0;;;:15:::1;:28;::::0;;;;;;;:41;;::::1;::::0;;;;;;;;;;:51;;;6322:47;;24697:34:21;;;24747:18;;24740:43;;;;24799:18;;;24792:34;;;6322:47:15::1;::::0;24660:2:21;24645:18;6322:47:15::1;24474:358:21::0;2244:224:17;1065:13:19;:11;:13::i;:::-;2354:22:17::1;:48:::0;;-1:-1:-1;;2354:48:17::1;::::0;::::1;;::::0;;::::1;::::0;;;2413:50:::1;::::0;2004:41:21;;;2413:50:17::1;::::0;1992:2:21;1977:18;2413:50:17::1;1864:187:21::0;1657:583:17;713:10:2;1927:4:17;1903:29;1895:73;;;;-1:-1:-1;;;1895:73:17;;25039:2:21;1895:73:17;;;25021:21:21;25078:2;25058:18;;;25051:30;25117:33;25097:18;;;25090:61;25168:18;;1895:73:17;24837:355:21;1895:73:17;1997:42;2019:4;2026:3;2031:7;1997:13;:42::i;:::-;1987:52;;2080:3;-1:-1:-1;;;;;2050:43:17;2067:11;2050:43;;-1:-1:-1;;;;;;;;;;;2085:7:17;2050:43;;;;3860:25:21;;3848:2;3833:18;;3714:177;2050:43:17;;;;;;;;2112:123;;-1:-1:-1;;;2112:123:17;;-1:-1:-1;;;;;2112:33:17;;;;;2151:11;;2112:123;;2171:11;;2184;;;;2197:6;;2205:5;;2212:7;;2221:8;;;;2112:123;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;1657:583;;;;;;;;;;:::o;5140:204:15:-;1065:13:19;:11;:13::i;:::-;5246:35:15::1;::::0;::::1;;::::0;;;:19:::1;:35;::::0;;;;:43:::1;5284:5:::0;;5246:35;:43:::1;:::i;:::-;;5300:39;5317:14;5333:5;;5300:39;;;;;;;;:::i;1986:188:19:-:0;1065:13;:11;:13::i;:::-;-1:-1:-1;;;;;2070:22:19;::::1;2062:73;;;::::0;-1:-1:-1;;;2062:73:19;;27364:2:21;2062:73:19::1;::::0;::::1;27346:21:21::0;27403:2;27383:18;;;27376:30;27442:34;27422:18;;;27415:62;-1:-1:-1;;;27493:18:21;;;27486:36;27539:19;;2062:73:19::1;27162:402:21::0;2062:73:19::1;2141:28;2160:8;2141:18;:28::i;:::-;1986:188:::0;:::o;4071:226:15:-;4224:68;;-1:-1:-1;;;4224:68:15;;27806:6:21;27839:15;;;4224:68:15;;;27821:34:21;27891:15;;27871:18;;;27864:43;4273:4:15;27923:18:21;;;27916:60;27992:18;;;27985:34;;;4197:12:15;;4224:10;-1:-1:-1;;;;;4224:20:15;;;;27768:19:21;;4224:68:15;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;4224:68:15;;;;;;;;;;;;:::i;:::-;4217:75;4071:226;-1:-1:-1;;;;;4071:226:15:o;996:576:16:-;1161:12;1175:19;1198:225;1239:9;1256:3;1299:34;;;1343:11;1364;1385:6;1401:8;1267:150;;;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;1267:150:16;;;;;;;;;;;;;;-1:-1:-1;;;;;1267:150:16;-1:-1:-1;;;;;;1267:150:16;;;;;;;;;;1206:4;;1198:225;;:33;:225::i;:::-;1160:263;;;;1473:7;1468:100;;1490:71;1510:11;1523;1536:6;1544:8;1554:6;1490:19;:71::i;1302:124:19:-;713:10:2;1361:7:19;:5;:7::i;:::-;-1:-1:-1;;;;;1361:23:19;;1353:68;;;;-1:-1:-1;;;1353:68:19;;29446:2:21;1353:68:19;;;29428:21:21;;;29465:18;;;29458:30;29524:34;29504:18;;;29497:62;29576:18;;1353:68:19;29244:356:21;9946:332:4;-1:-1:-1;;;;;10053:19:4;;10045:68;;;;-1:-1:-1;;;10045:68:4;;29807:2:21;10045:68:4;;;29789:21:21;29846:2;29826:18;;;29819:30;29885:34;29865:18;;;29858:62;-1:-1:-1;;;29936:18:21;;;29929:34;29980:19;;10045:68:4;29605:400:21;10045:68:4;-1:-1:-1;;;;;10127:21:4;;10119:68;;;;-1:-1:-1;;;10119:68:4;;30212:2:21;10119:68:4;;;30194:21:21;30251:2;30231:18;;;30224:30;30290:34;30270:18;;;30263:62;-1:-1:-1;;;30341:18:21;;;30334:32;30383:19;;10119:68:4;30010:398:21;10119:68:4;-1:-1:-1;;;;;10194:18:4;;;;;;;:11;:18;;;;;;;;:27;;;;;;;;;;;;;:36;;;10241:32;;3860:25:21;;;10241:32:4;;3833:18:21;10241:32:4;;;;;;;9946:332;;;:::o;10541:381::-;10647:24;10674:25;10684:5;10691:7;10674:9;:25::i;:::-;10647:52;;-1:-1:-1;;10709:16:4;:37;10705:213;;10784:6;10764:16;:26;;10756:68;;;;-1:-1:-1;;;10756:68:4;;30615:2:21;10756:68:4;;;30597:21:21;30654:2;30634:18;;;30627:30;30693:31;30673:18;;;30666:59;30742:18;;10756:68:4;30413:353:21;10756:68:4;10852:51;10861:5;10868:7;10896:6;10877:16;:25;10852:8;:51::i;:::-;10641:281;10541:381;;;:::o;7168:726::-;-1:-1:-1;;;;;7260:18:4;;7252:68;;;;-1:-1:-1;;;7252:68:4;;30973:2:21;7252:68:4;;;30955:21:21;31012:2;30992:18;;;30985:30;31051:34;31031:18;;;31024:62;-1:-1:-1;;;31102:18:21;;;31095:35;31147:19;;7252:68:4;30771:401:21;7252:68:4;-1:-1:-1;;;;;7334:16:4;;7326:64;;;;-1:-1:-1;;;7326:64:4;;31379:2:21;7326:64:4;;;31361:21:21;31418:2;31398:18;;;31391:30;31457:34;31437:18;;;31430:62;-1:-1:-1;;;31508:18:21;;;31501:33;31551:19;;7326:64:4;31177:399:21;7326:64:4;-1:-1:-1;;;;;7464:15:4;;7442:19;7464:15;;;:9;:15;;;;;;7493:21;;;;7485:72;;;;-1:-1:-1;;;7485:72:4;;31783:2:21;7485:72:4;;;31765:21:21;31822:2;31802:18;;;31795:30;31861:34;31841:18;;;31834:62;-1:-1:-1;;;31912:18:21;;;31905:36;31958:19;;7485:72:4;31581:402:21;7485:72:4;-1:-1:-1;;;;;7581:15:4;;;;;;;:9;:15;;;;;;7599:20;;;7581:38;;7778:13;;;;;;;;;;:23;;;;;;7819:26;;-1:-1:-1;;;;;;;;;;;7819:26:4;;;7613:6;3860:25:21;;3848:2;3833:18;;3714:177;7819:26:4;;;;;;;;7852:37;11476:101;2518:446:17;2699:17;2718:14;2779:20;2802:47;2821:10;2833:15;2840:7;2833:6;:15::i;:::-;9217:48;;;402:1;9217:48;;;36092:49:21;36157:11;;;36150:27;;;;36241:3;36211:16;;;;-1:-1:-1;;;;;;36207:47:21;36193:12;;;36186:69;9217:48:17;;;;;;;;;36271:12:21;;;;9217:48:17;;;9075:195;2802:47;2862:97;;-1:-1:-1;;;2862:97:17;;2779:70;;-1:-1:-1;;;;;;2862:10:17;:23;;;;:97;;2893:11;;2914:4;;2779:70;;2930:7;;2939:14;;2862:97;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;2855:104;;;;;2518:446;;;;;;;;:::o;3539:485::-;3706:16;3725:19;:8;3706:16;3725;:19::i;:::-;3706:38;-1:-1:-1;3755:21:17;;;3751:269;;3786:52;3795:11;3808;3821:6;3829:8;3786;:52::i;:::-;3751:269;;;-1:-1:-1;;3855:30:17;;;;3851:169;;3895:59;3911:11;3924;3937:6;3945:8;3895:15;:59::i;3851:169::-;3975:38;;-1:-1:-1;;;3975:38:17;;33087:2:21;3975:38:17;;;33069:21:21;33126:2;33106:18;;;33099:30;-1:-1:-1;;;33145:18:21;;;33138:58;33213:18;;3975:38:17;32885:352:21;4028:813:17;4262:14;4284:71;4304:11;4262:14;4326;4262;4284:19;:71::i;:::-;4374:20;4386:7;4374:11;:20::i;:::-;-1:-1:-1;4362:32:17;-1:-1:-1;4409:50:17;4420:5;4427:11;4440:10;4362:32;4409:10;:50::i;:::-;4400:59;;4522:1;4513:6;:10;4505:48;;;;-1:-1:-1;;;4505:48:17;;;;;;;:::i;:::-;4560:22;4585:46;4604:10;4616:14;4623:6;4616;:14::i;4585:46::-;4560:71;;4637:136;4652:11;4671:9;4688:14;4710:18;4736:14;4758:9;4637:7;:136::i;:::-;4817:10;4810:5;-1:-1:-1;;;;;4785:51:17;4797:11;4785:51;;-1:-1:-1;;;;;;;;;;;4829:6:17;4785:51;;;;3860:25:21;;3848:2;3833:18;;3714:177;4785:51:17;;;;;;;;4278:563;4028:813;;;;;;;;;:::o;2318:173:19:-;2387:16;2406:6;;-1:-1:-1;;;;;2418:17:19;;;-1:-1:-1;;;;;;2418:17:19;;;;;;2446:40;;2406:6;;;;;;;2446:40;;2387:16;2446:40;2381:110;2318:173;:::o;5244:977:17:-;5539:14;5561:94;5588:11;448:1;5619:14;-1:-1:-1;;;;;5561:94:17;;:19;:94::i;:::-;5674:20;5686:7;5674:11;:20::i;:::-;-1:-1:-1;5662:32:17;-1:-1:-1;5709:50:17;5720:5;5727:11;5740:10;5662:32;5709:10;:50::i;:::-;5700:59;;5782:1;5773:6;:10;5765:48;;;;-1:-1:-1;;;5765:48:17;;;;;;;:::i;:::-;5883:22;5908:103;5941:10;5953;5965:14;5972:6;5965;:14::i;:::-;5981:8;5991:14;5908:25;:103::i;:::-;5883:128;;6017:136;6032:11;6051:9;6068:14;6090:18;6116:14;6138:9;6017:7;:136::i;:::-;6197:10;6190:5;-1:-1:-1;;;;;6165:51:17;6177:11;6165:51;;-1:-1:-1;;;;;;;;;;;6209:6:17;6165:51;;;;3860:25:21;;3848:2;3833:18;;3714:177;6165:51:17;;;;;;;;5555:666;5244:977;;;;;;;;;;;:::o;7916:2384:1:-;8020:12;8066:7;8050:12;8066:7;8060:2;8050:12;:::i;:::-;:23;;8042:50;;;;-1:-1:-1;;;8042:50:1;;33798:2:21;8042:50:1;;;33780:21:21;33837:2;33817:18;;;33810:30;-1:-1:-1;;;33856:18:21;;;33849:44;33910:18;;8042:50:1;33596:338:21;8042:50:1;8123:16;8132:7;8123:6;:16;:::i;:::-;8106:6;:13;:33;;8098:63;;;;-1:-1:-1;;;8098:63:1;;34141:2:21;8098:63:1;;;34123:21:21;34180:2;34160:18;;;34153:30;-1:-1:-1;;;34199:18:21;;;34192:47;34256:18;;8098:63:1;33939:341:21;8098:63:1;8168:22;8221:15;;8243:1687;;;;10051:4;10045:11;10032:24;;10213:1;10202:9;10195:20;10253:4;10242:9;10238:20;10232:4;10225:34;8214:2053;;8243:1687;8401:4;8395:11;8382:24;;8988:2;8979:7;8975:16;9330:9;9323:17;9317:4;9313:28;9301:9;9290;9286:25;9282:60;9370:7;9366:2;9362:16;9596:6;9582:9;9575:17;9569:4;9565:28;9553:9;9545:6;9541:22;9537:57;9533:70;9388:335;9621:3;9617:2;9614:11;9388:335;;;9711:9;;9700:21;;9652:4;9644:13;;;;9674;9388:335;;;-1:-1:-1;;9733:26:1;;;9917:2;9900:11;-1:-1:-1;;9896:25:1;9890:4;9883:39;-1:-1:-1;8214:2053:1;-1:-1:-1;10286:9:1;7916:2384;-1:-1:-1;;;;7916:2384:1:o;2968:567:17:-;3210:17;3229:14;3293:20;3316:104;3349:10;3361;3373:15;3380:7;3373:6;:15::i;3316:104::-;3433:97;;-1:-1:-1;;;3433:97:17;;3293:127;;-1:-1:-1;;;;;;3433:10:17;:23;;;;:97;;3464:11;;3485:4;;3293:127;;3501:7;;3510:14;;3433:97;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;3426:104;;;;;2968:567;;;;;;;;;;:::o;1338:401:18:-;1457:7;713:10:2;1597:4:18;-1:-1:-1;;;;;1580:22:18;;;;;;:42;;;1615:7;-1:-1:-1;;;;;1606:16:18;:5;-1:-1:-1;;;;;1606:16:18;;;1580:42;1576:103;;;1632:40;1648:5;1655:7;1664;1632:15;:40::i;:::-;1684:30;1694:5;1701:3;1706:7;1684:9;:30::i;:::-;-1:-1:-1;1727:7:18;;1338:401;-1:-1:-1;;;1338:401:18:o;1084:1102:5:-;1223:4;1229:12;1281:15;1302:13;1321:24;1358:8;1348:19;;-1:-1:-1;;;;;1348:19:5;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;1348:19:5;;1321:46;;1804:1;1781;1750:9;1744:16;1718:4;1707:9;1703:20;1675:1;1643:7;1620:4;1604:221;1584:241;;1880:16;1869:27;;1918:8;1909:7;1906:21;1903:48;;;1941:8;1930:19;;1903:48;2024:7;2011:11;2004:28;2132:7;2129:1;2122:4;2109:11;2105:22;2090:50;2159:8;;;;-1:-1:-1;1084:1102:5;-1:-1:-1;;;;;;1084:1102:5:o;1576:334:16:-;1819:8;1809:19;;;;;;1758:14;:27;1773:11;1758:27;;;;;;;;;;;;;;;1786:11;1758:40;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;-1:-1:-1;;;;;1758:48:16;;;;;;;;;:70;;;;1839:66;;;;1853:11;;1866;;1799:6;;1887:8;;1897:7;;1839:66;:::i;:::-;;;;;;;;1576:334;;;;;:::o;11476:101:4:-;;;;:::o;8525:226:17:-;8589:6;8603:16;8632:12;:10;:12::i;:::-;8622:22;;:7;:22;:::i;:::-;8603:41;-1:-1:-1;;;;;;8658:28:17;;;8650:67;;;;-1:-1:-1;;;8650:67:17;;35760:2:21;8650:67:17;;;35742:21:21;35799:2;35779:18;;;35772:30;-1:-1:-1;;;35818:18:21;;;35811:56;35884:18;;8650:67:17;35558:350:21;10656:287:1;10745:5;10785:10;:6;10794:1;10785:10;:::i;:::-;10768:6;:13;:27;;10760:59;;;;-1:-1:-1;;;10760:59:1;;36496:2:21;10760:59:1;;;36478:21:21;36535:2;36515:18;;;36508:30;-1:-1:-1;;;36554:18:21;;;36547:49;36613:18;;10760:59:1;36294:343:21;10760:59:1;-1:-1:-1;10881:29:1;10897:3;10881:29;10875:36;;10656:287::o;4845:395:17:-;4972:10;4984:15;5003:28;5022:8;5003:18;:28::i;:::-;4971:60;;-1:-1:-1;4971:60:17;-1:-1:-1;;;;;;5041:16:17;;5037:57;;5080:6;5067:20;;5037:57;5100:14;5117:16;5124:8;5117:6;:16::i;:::-;5100:33;;5148:34;5158:11;5171:2;5175:6;5148:9;:34::i;:::-;5139:43;;5224:2;-1:-1:-1;;;;;5194:41:17;5211:11;5194:41;;-1:-1:-1;;;;;;;;;;;5228:6:17;5194:41;;;;3860:25:21;;3848:2;3833:18;;3714:177;5194:41:17;;;;;;;;4965:275;;;4845:395;;;;:::o;6225:1798::-;6385:12;6405:10;6423:15;6446:27;6481:17;6507:35;6533:8;6507:25;:35::i;:::-;6377:165;;;;;;;;;;6549:13;6565:15;:28;6581:11;6565:28;;;;;;;;;;;;;;;6594:11;6565:41;;;;;;:::i;:::-;;;;;;;;;;;;;;;;-1:-1:-1;;;;;6565:49:17;;;;;;;;;;;;;;-1:-1:-1;6637:16:17;6644:8;6637:6;:16::i;:::-;6620:33;;6770:8;6765:148;;6797:45;6807:11;6828:4;6835:6;6797:9;:45::i;:::-;6850:28;;;;;;;:15;:28;;;;;;;:41;;6788:54;;-1:-1:-1;6902:4:17;;6850:41;;6879:11;;6850:41;:::i;:::-;;;;;;;;;;;;;;;;-1:-1:-1;;;;;6850:49:17;;;;;;;;;;:56;;-1:-1:-1;;6850:56:17;;;;;;;;;;6765:148;-1:-1:-1;;;;;8108:20:17;;;6919:78;;6954:22;6973:2;6954:22;;;;;;:::i;:::-;;;;;;;;6984:7;;;;;;;;;6919:78;7060:11;7103;7135:6;7170:8;7200:4;7224:2;7250:6;7293:14;7040:17;7370:8;:33;;7393:10;-1:-1:-1;;;;;7370:33:17;;;;7381:9;7370:33;7356:47;;7410:12;7424:19;7447:284;7488:9;7505:3;7548:31;;;7589:10;7609;7629:5;7644;7659:3;7672:7;7689:15;7714:3;7516:209;;;;;;;;;;;;;;;:::i;7447:284::-;7409:322;;;;7742:7;7738:281;;;7774:18;;;;;;7805:59;;;;;;;;;;7840:10;;7852:5;;7774:18;;7805:59;:::i;:::-;;;;;;;;7751:120;7738:281;;;7945:67;7965:10;7977;7989:5;7996:7;8005:6;7945:19;:67::i;:::-;6371:1652;;;;;;;;;;;;;;;;;;6225:1798;;;;:::o;8141:380::-;8301:22;;;;8297:220;;;8333:63;8348:11;8361:7;8370:14;8386:9;8333:14;:63::i;:::-;8297:220;;;8434:21;;:26;8417:93;;;;-1:-1:-1;;;8417:93:17;;38128:2:21;8417:93:17;;;38110:21:21;38167:2;38147:18;;;38140:30;38206:34;38186:18;;;38179:62;-1:-1:-1;;;38257:18:21;;;38250:36;38303:19;;8417:93:17;37926:402:21;8875:196:17;8960:19;8981:12;9020;:10;:12::i;:::-;9010:22;;:7;:22;:::i;:::-;9003:29;-1:-1:-1;9052:14:17;9003:29;9052:7;:14;:::i;:::-;9038:28;;8875:196;;;:::o;860:287:18:-;980:7;713:10:2;-1:-1:-1;;;;;1037:16:18;;;;1033:62;;1055:40;1071:5;1078:7;1087;1055:15;:40::i;:::-;1101:21;1107:5;1114:7;1101:5;:21::i;:::-;-1:-1:-1;1135:7:18;;860:287;-1:-1:-1;;;;860:287:18:o;2250:621:15:-;2499:32;;;2470:26;2499:32;;;:19;:32;;;;;2470:61;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2552:13;:20;2576:1;2552:25;2537:104;;;;-1:-1:-1;;;2537:104:15;;38652:2:21;2537:104:15;;;38634:21:21;38691:2;38671:18;;;38664:30;38730:34;38710:18;;;38703:62;-1:-1:-1;;;38781:18:21;;;38774:46;38837:19;;2537:104:15;38450:412:21;2537:104:15;2647:47;2665:11;2678:8;:15;2647:17;:47::i;:::-;2700:166;;-1:-1:-1;;;2700:166:15;;-1:-1:-1;;;;;2700:10:15;:15;;;;2723:10;;2700:166;;2742:11;;2761:13;;2782:8;;2798:14;;2820:18;;2846:14;;2700:166;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2464:407;2250:621;;;;;;:::o;9638:372:17:-;9827:12;448:1;9902:10;9920:9;-1:-1:-1;;;;;10703:26:17;;9969:14;9991:8;9854:151;;;;;;;;;;;;;:::i;:::-;;;;;;;;;;;;;9847:158;;9638:372;;;;;;;:::o;1743:98:18:-;1827:9;;1743:98::o;9274:360:17:-;9372:10;;;9424:19;:8;9372:10;9424:16;:19::i;:::-;:30;;;:55;;;;;9458:8;:15;9477:2;9458:21;9424:55;9409:110;;;;-1:-1:-1;;;9409:110:17;;;;;;;:::i;:::-;9531:22;:8;9550:2;9531:18;:22::i;:::-;9526:27;-1:-1:-1;9608:21:17;:8;9626:2;9608:17;:21::i;:::-;9597:32;;9274:360;;;:::o;8755:116::-;8820:7;8854:12;:10;:12::i;:::-;8842:24;;-1:-1:-1;;;;;8842:24:17;;;:::i;1151:183:18:-;1266:7;1283:26;1289:10;1301:7;1283:5;:26::i;:::-;-1:-1:-1;1322:7:18;1151:183;-1:-1:-1;;1151:183:18:o;10014:561:17:-;10126:12;;;10187:20;10126:12;448:1;10258:19;:8;10126:12;10258:16;:19::i;:::-;:39;;;10250:76;;;;-1:-1:-1;;;10250:76:17;;;;;;;:::i;:::-;10338:22;:8;10357:2;10338:18;:22::i;:::-;10333:27;-1:-1:-1;10415:21:17;:8;10433:2;10415:17;:21::i;:::-;10404:32;-1:-1:-1;10449:22:17;:8;10468:2;10449:18;:22::i;:::-;10442:29;-1:-1:-1;10493:21:17;:8;10511:2;10493:17;:21::i;:::-;10477:37;;10530:40;10545:2;10567;10549:8;:15;:20;;;;:::i;:::-;10530:8;;:40;:14;:40::i;:::-;10520:50;;10014:561;;;;;;;:::o;2875:426:15:-;3029:24;3056:28;3069:14;3056:12;:28::i;:::-;3112;;;;3090:19;3112:28;;;:15;:28;;;;;;;;:35;;;;;;;;;;;;3029:55;;-1:-1:-1;3090:19:15;3112:47;;3150:9;;3112:47;:::i;:::-;3090:69;;3187:1;3173:11;:15;3165:54;;;;-1:-1:-1;;;3165:54:15;;41168:2:21;3165:54:15;;;41150:21:21;41207:2;41187:18;;;41180:30;-1:-1:-1;;;41226:18:21;;;41219:56;41292:18;;3165:54:15;40966:350:21;3165:54:15;3253:11;3233:16;:31;;3225:71;;;;-1:-1:-1;;;3225:71:15;;41523:2:21;3225:71:15;;;41505:21:21;41562:2;41542:18;;;41535:30;-1:-1:-1;;;41581:18:21;;;41574:57;41648:18;;3225:71:15;41321:351:21;8944:607:4;-1:-1:-1;;;;;9023:21:4;;9015:67;;;;-1:-1:-1;;;9015:67:4;;41879:2:21;9015:67:4;;;41861:21:21;41918:2;41898:18;;;41891:30;41957:34;41937:18;;;41930:62;-1:-1:-1;;;42008:18:21;;;42001:31;42049:19;;9015:67:4;41677:397:21;9015:67:4;-1:-1:-1;;;;;9170:18:4;;9145:22;9170:18;;;:9;:18;;;;;;9202:24;;;;9194:71;;;;-1:-1:-1;;;9194:71:4;;42281:2:21;9194:71:4;;;42263:21:21;42320:2;42300:18;;;42293:30;42359:34;42339:18;;;42332:62;-1:-1:-1;;;42410:18:21;;;42403:32;42452:19;;9194:71:4;42079:398:21;9194:71:4;-1:-1:-1;;;;;9289:18:4;;;;;;:9;:18;;;;;;;;9310:23;;;9289:44;;9414:12;:22;;;;;;;9454:37;3860:25:21;;;9289:18:4;;;-1:-1:-1;;;;;;;;;;;9454:37:4;3833:18:21;9454:37:4;;;;;;;11476:101;;;:::o;3576:397:15:-;3714:35;;;3687:24;3714:35;;;:22;:35;;;;;;;3759:21;;;3755:119;;-1:-1:-1;548:5:15;3755:119;3910:16;3894:12;:32;;3879:89;;;;-1:-1:-1;;;3879:89:15;;42684:2:21;3879:89:15;;;42666:21:21;;;42703:18;;;42696:30;42762:34;42742:18;;;42735:62;42814:18;;3879:89:15;42482:356:21;10304:348:1;10395:7;10437:11;:6;10446:2;10437:11;:::i;:::-;10420:6;:13;:28;;10412:62;;;;-1:-1:-1;;;10412:62:1;;43045:2:21;10412:62:1;;;43027:21:21;43084:2;43064:18;;;43057:30;-1:-1:-1;;;43103:18:21;;;43096:51;43164:18;;10412:62:1;42843:345:21;10412:62:1;-1:-1:-1;10556:30:1;10572:4;10556:30;10550:37;-1:-1:-1;;;10546:71:1;;;10304:348::o;11537:291::-;11627:6;11668:10;:6;11677:1;11668:10;:::i;:::-;11651:6;:13;:27;;11643:60;;;;-1:-1:-1;;;11643:60:1;;43395:2:21;11643:60:1;;;43377:21:21;43434:2;43414:18;;;43407:30;-1:-1:-1;;;43453:18:21;;;43446:50;43513:18;;11643:60:1;43193:344:21;11643:60:1;-1:-1:-1;11766:29:1;11782:3;11766:29;11760:36;;11537:291::o;8155:493:4:-;-1:-1:-1;;;;;8234:21:4;;8226:65;;;;-1:-1:-1;;;8226:65:4;;43744:2:21;8226:65:4;;;43726:21:21;43783:2;43763:18;;;43756:30;43822:33;43802:18;;;43795:61;43873:18;;8226:65:4;43542:355:21;8226:65:4;8370:6;8354:12;;:22;;;;;;;:::i;:::-;;;;-1:-1:-1;;;;;;;8506:18:4;;;;;;:9;:18;;;;;;;;:28;;;;;;8551:37;3860:25:21;;;-1:-1:-1;;;;;;;;;;;8551:37:4;3833:18:21;8551:37:4;;;;;;;8155:493;;:::o;12730:306:1:-;12821:7;12863:11;:6;12872:2;12863:11;:::i;:::-;12846:6;:13;:28;;12838:62;;;;-1:-1:-1;;;12838:62:1;;44104:2:21;12838:62:1;;;44086:21:21;44143:2;44123:18;;;44116:30;-1:-1:-1;;;44162:18:21;;;44155:51;44223:18;;12838:62:1;43902:345:21;12838:62:1;-1:-1:-1;12970:30:1;12986:4;12970:30;12964:37;;12730:306::o;3305:267:15:-;3403:16;3462:2;3437:14;:21;:27;;3429:68;;;;-1:-1:-1;;;3429:68:15;;44454:2:21;3429:68:15;;;44436:21:21;44493:2;44473:18;;;44466:30;-1:-1:-1;;;44512:18:21;;;44505:58;44580:18;;3429:68:15;44252:352:21;3429:68:15;-1:-1:-1;3558:2:15;3538:23;3532:30;;3305:267::o;14:159:21:-;81:20;;141:6;130:18;;120:29;;110:57;;163:1;160;153:12;110:57;14:159;;;:::o;178:347::-;229:8;239:6;293:3;286:4;278:6;274:17;270:27;260:55;;311:1;308;301:12;260:55;-1:-1:-1;334:20:21;;-1:-1:-1;;;;;366:30:21;;363:50;;;409:1;406;399:12;363:50;446:4;438:6;434:17;422:29;;498:3;491:4;482:6;474;470:19;466:30;463:39;460:59;;;515:1;512;505:12;460:59;178:347;;;;;:::o;530:171::-;597:20;;-1:-1:-1;;;;;646:30:21;;636:41;;626:69;;691:1;688;681:12;706:862;812:6;820;828;836;844;852;905:3;893:9;884:7;880:23;876:33;873:53;;;922:1;919;912:12;873:53;945:28;963:9;945:28;:::i;:::-;935:38;-1:-1:-1;1024:2:21;1009:18;;996:32;-1:-1:-1;;;;;1077:14:21;;;1074:34;;;1104:1;1101;1094:12;1074:34;1143:58;1193:7;1184:6;1173:9;1169:22;1143:58;:::i;:::-;1220:8;;-1:-1:-1;1117:84:21;-1:-1:-1;1117:84:21;;-1:-1:-1;1274:37:21;1307:2;1292:18;;1274:37;:::i;:::-;1264:47;;1364:2;1353:9;1349:18;1336:32;1320:48;;1393:2;1383:8;1380:16;1377:36;;;1409:1;1406;1399:12;1377:36;;1448:60;1500:7;1489:8;1478:9;1474:24;1448:60;:::i;:::-;706:862;;;;-1:-1:-1;706:862:21;;-1:-1:-1;706:862:21;;1527:8;;706:862;-1:-1:-1;;;706:862:21:o;1573:286::-;1631:6;1684:2;1672:9;1663:7;1659:23;1655:32;1652:52;;;1700:1;1697;1690:12;1652:52;1726:23;;-1:-1:-1;;;;;;1778:32:21;;1768:43;;1758:71;;1825:1;1822;1815:12;2056:250;2141:1;2151:113;2165:6;2162:1;2159:13;2151:113;;;2241:11;;;2235:18;2222:11;;;2215:39;2187:2;2180:10;2151:113;;;-1:-1:-1;;2298:1:21;2280:16;;2273:27;2056:250::o;2311:271::-;2353:3;2391:5;2385:12;2418:6;2413:3;2406:19;2434:76;2503:6;2496:4;2491:3;2487:14;2480:4;2473:5;2469:16;2434:76;:::i;:::-;2564:2;2543:15;-1:-1:-1;;2539:29:21;2530:39;;;;2571:4;2526:50;;2311:271;-1:-1:-1;;2311:271:21:o;2587:220::-;2736:2;2725:9;2718:21;2699:4;2756:45;2797:2;2786:9;2782:18;2774:6;2756:45;:::i;2812:184::-;2870:6;2923:2;2911:9;2902:7;2898:23;2894:32;2891:52;;;2939:1;2936;2929:12;2891:52;2962:28;2980:9;2962:28;:::i;3001:131::-;-1:-1:-1;;;;;3076:31:21;;3066:42;;3056:70;;3122:1;3119;3112:12;3137:315;3205:6;3213;3266:2;3254:9;3245:7;3241:23;3237:32;3234:52;;;3282:1;3279;3272:12;3234:52;3321:9;3308:23;3340:31;3365:5;3340:31;:::i;:::-;3390:5;3442:2;3427:18;;;;3414:32;;-1:-1:-1;;;3137:315:21:o;3457:252::-;3524:6;3532;3585:2;3573:9;3564:7;3560:23;3556:32;3553:52;;;3601:1;3598;3591:12;3553:52;3624:28;3642:9;3624:28;:::i;3896:456::-;3973:6;3981;3989;4042:2;4030:9;4021:7;4017:23;4013:32;4010:52;;;4058:1;4055;4048:12;4010:52;4097:9;4084:23;4116:31;4141:5;4116:31;:::i;:::-;4166:5;-1:-1:-1;4223:2:21;4208:18;;4195:32;4236:33;4195:32;4236:33;:::i;:::-;3896:456;;4288:7;;-1:-1:-1;;;4342:2:21;4327:18;;;;4314:32;;3896:456::o;4546:160::-;4611:20;;4667:13;;4660:21;4650:32;;4640:60;;4696:1;4693;4686:12;4711:687;4813:6;4821;4829;4837;4845;4853;4906:3;4894:9;4885:7;4881:23;4877:33;4874:53;;;4923:1;4920;4913:12;4874:53;4946:28;4964:9;4946:28;:::i;:::-;4936:38;;5021:2;5010:9;5006:18;4993:32;4983:42;;5072:2;5061:9;5057:18;5044:32;5034:42;;5095:35;5126:2;5115:9;5111:18;5095:35;:::i;:::-;5085:45;-1:-1:-1;5181:3:21;5166:19;;5153:33;-1:-1:-1;;;;;5198:30:21;;5195:50;;;5241:1;5238;5231:12;5195:50;5280:58;5330:7;5321:6;5310:9;5306:22;5280:58;:::i;5656:481::-;5734:6;5742;5750;5803:2;5791:9;5782:7;5778:23;5774:32;5771:52;;;5819:1;5816;5809:12;5771:52;5842:28;5860:9;5842:28;:::i;:::-;5832:38;-1:-1:-1;5921:2:21;5906:18;;5893:32;-1:-1:-1;;;;;5937:30:21;;5934:50;;;5980:1;5977;5970:12;5934:50;6019:58;6069:7;6060:6;6049:9;6045:22;6019:58;:::i;:::-;5656:481;;6096:8;;-1:-1:-1;5993:84:21;;-1:-1:-1;;;;5656:481:21:o;6142:127::-;6203:10;6198:3;6194:20;6191:1;6184:31;6234:4;6231:1;6224:15;6258:4;6255:1;6248:15;6274:275;6345:2;6339:9;6410:2;6391:13;;-1:-1:-1;;6387:27:21;6375:40;;-1:-1:-1;;;;;6430:34:21;;6466:22;;;6427:62;6424:88;;;6492:18;;:::i;:::-;6528:2;6521:22;6274:275;;-1:-1:-1;6274:275:21:o;6554:186::-;6602:4;-1:-1:-1;;;;;6624:30:21;;6621:56;;;6657:18;;:::i;:::-;-1:-1:-1;6723:2:21;6702:15;-1:-1:-1;;6698:29:21;6729:4;6694:40;;6554:186::o;6745:815::-;6829:6;6837;6845;6898:2;6886:9;6877:7;6873:23;6869:32;6866:52;;;6914:1;6911;6904:12;6866:52;6937:28;6955:9;6937:28;:::i;:::-;6927:38;-1:-1:-1;7016:2:21;7001:18;;6988:32;-1:-1:-1;;;;;7032:30:21;;7029:50;;;7075:1;7072;7065:12;7029:50;7098:22;;7151:4;7143:13;;7139:27;-1:-1:-1;7129:55:21;;7180:1;7177;7170:12;7129:55;7216:2;7203:16;7241:48;7257:31;7285:2;7257:31;:::i;:::-;7241:48;:::i;:::-;7312:2;7305:5;7298:17;7352:7;7347:2;7342;7338;7334:11;7330:20;7327:33;7324:53;;;7373:1;7370;7363:12;7324:53;7428:2;7423;7419;7415:11;7410:2;7403:5;7399:14;7386:45;7472:1;7467:2;7462;7455:5;7451:14;7447:23;7440:34;7493:5;7483:15;;;;;7517:37;7550:2;7539:9;7535:18;7517:37;:::i;:::-;7507:47;;6745:815;;;;;:::o;7747:160::-;7812:5;7857:2;7848:6;7843:3;7839:16;7835:25;7832:45;;;7873:1;7870;7863:12;7832:45;-1:-1:-1;7895:6:21;7747:160;-1:-1:-1;7747:160:21:o;7912:711::-;8038:6;8046;8054;8062;8070;8123:3;8111:9;8102:7;8098:23;8094:33;8091:53;;;8140:1;8137;8130:12;8091:53;8179:9;8166:23;8198:31;8223:5;8198:31;:::i;:::-;8248:5;-1:-1:-1;8272:37:21;8305:2;8290:18;;8272:37;:::i;:::-;8262:47;-1:-1:-1;8356:2:21;8341:18;;8328:32;;-1:-1:-1;8407:2:21;8392:18;;8379:32;;-1:-1:-1;8462:3:21;8447:19;;8434:33;-1:-1:-1;;;;;8479:30:21;;8476:50;;;8522:1;8519;8512:12;8476:50;8545:72;8609:7;8600:6;8589:9;8585:22;8545:72;:::i;:::-;8535:82;;;7912:711;;;;;;;;:::o;8628:247::-;8687:6;8740:2;8728:9;8719:7;8715:23;8711:32;8708:52;;;8756:1;8753;8746:12;8708:52;8795:9;8782:23;8814:31;8839:5;8814:31;:::i;9103:1093::-;9257:6;9265;9273;9281;9289;9297;9305;9313;9366:3;9354:9;9345:7;9341:23;9337:33;9334:53;;;9383:1;9380;9373:12;9334:53;9422:9;9409:23;9441:31;9466:5;9441:31;:::i;:::-;9491:5;-1:-1:-1;9515:37:21;9548:2;9533:18;;9515:37;:::i;:::-;9505:47;-1:-1:-1;9599:2:21;9584:18;;9571:32;;-1:-1:-1;9650:2:21;9635:18;;9622:32;;-1:-1:-1;9705:3:21;9690:19;;9677:33;-1:-1:-1;;;;;9759:14:21;;;9756:34;;;9786:1;9783;9776:12;9756:34;9825:58;9875:7;9866:6;9855:9;9851:22;9825:58;:::i;:::-;9902:8;;-1:-1:-1;9799:84:21;-1:-1:-1;9799:84:21;;-1:-1:-1;9956:38:21;9989:3;9974:19;;9956:38;:::i;:::-;9946:48;;10047:3;10036:9;10032:19;10019:33;10003:49;;10077:2;10067:8;10064:16;10061:36;;;10093:1;10090;10083:12;10061:36;;10116:74;10182:7;10171:8;10160:9;10156:24;10116:74;:::i;:::-;10106:84;;;9103:1093;;;;;;;;;;;:::o;10201:256::-;10267:6;10275;10328:2;10316:9;10307:7;10303:23;10299:32;10296:52;;;10344:1;10341;10334:12;10296:52;10367:28;10385:9;10367:28;:::i;:::-;10357:38;;10414:37;10447:2;10436:9;10432:18;10414:37;:::i;:::-;10404:47;;10201:256;;;;;:::o;10462:203::-;-1:-1:-1;;;;;10626:32:21;;;;10608:51;;10596:2;10581:18;;10462:203::o;10670:1069::-;10800:6;10808;10816;10824;10832;10840;10848;10856;10864;10917:3;10905:9;10896:7;10892:23;10888:33;10885:53;;;10934:1;10931;10924:12;10885:53;10957:28;10975:9;10957:28;:::i;:::-;10947:38;-1:-1:-1;11032:2:21;11017:18;;11004:32;;-1:-1:-1;11083:2:21;11068:18;;11055:32;;-1:-1:-1;11138:2:21;11123:18;;11110:32;-1:-1:-1;;;;;11191:14:21;;;11188:34;;;11218:1;11215;11208:12;11188:34;11257:58;11307:7;11298:6;11287:9;11283:22;11257:58;:::i;:::-;11334:8;;-1:-1:-1;11231:84:21;-1:-1:-1;11231:84:21;;-1:-1:-1;11388:38:21;11421:3;11406:19;;11388:38;:::i;:::-;11378:48;;11445:36;11476:3;11465:9;11461:19;11445:36;:::i;:::-;11435:46;;11534:3;11523:9;11519:19;11506:33;11490:49;;11564:2;11554:8;11551:16;11548:36;;;11580:1;11577;11570:12;11548:36;;11619:60;11671:7;11660:8;11649:9;11645:24;11619:60;:::i;:::-;11593:86;;11698:8;11688:18;;;11725:8;11715:18;;;10670:1069;;;;;;;;;;;:::o;11979:622::-;12074:6;12082;12090;12098;12106;12159:3;12147:9;12138:7;12134:23;12130:33;12127:53;;;12176:1;12173;12166:12;12127:53;12199:28;12217:9;12199:28;:::i;:::-;12189:38;;12246:37;12279:2;12268:9;12264:18;12246:37;:::i;:::-;12236:47;-1:-1:-1;12330:2:21;12315:18;;12302:32;;-1:-1:-1;12385:2:21;12370:18;;12357:32;-1:-1:-1;;;;;12401:30:21;;12398:50;;;12444:1;12441;12434:12;12398:50;12483:58;12533:7;12524:6;12513:9;12509:22;12483:58;:::i;:::-;11979:622;;;;-1:-1:-1;11979:622:21;;-1:-1:-1;12560:8:21;;12457:84;11979:622;-1:-1:-1;;;11979:622:21:o;12606:388::-;12674:6;12682;12735:2;12723:9;12714:7;12710:23;12706:32;12703:52;;;12751:1;12748;12741:12;12703:52;12790:9;12777:23;12809:31;12834:5;12809:31;:::i;:::-;12859:5;-1:-1:-1;12916:2:21;12901:18;;12888:32;12929:33;12888:32;12929:33;:::i;:::-;12981:7;12971:17;;;12606:388;;;;;:::o;12999:324::-;13074:6;13082;13090;13143:2;13131:9;13122:7;13118:23;13114:32;13111:52;;;13159:1;13156;13149:12;13111:52;13182:28;13200:9;13182:28;:::i;:::-;13172:38;;13229:37;13262:2;13251:9;13247:18;13229:37;:::i;:::-;13219:47;;13313:2;13302:9;13298:18;13285:32;13275:42;;12999:324;;;;;:::o;13328:180::-;13384:6;13437:2;13425:9;13416:7;13412:23;13408:32;13405:52;;;13453:1;13450;13443:12;13405:52;13476:26;13492:9;13476:26;:::i;13513:1205::-;13655:6;13663;13671;13679;13687;13695;13703;13711;13719;13727;13780:3;13768:9;13759:7;13755:23;13751:33;13748:53;;;13797:1;13794;13787:12;13748:53;13820:28;13838:9;13820:28;:::i;:::-;13810:38;-1:-1:-1;13899:2:21;13884:18;;13871:32;-1:-1:-1;;;;;13952:14:21;;;13949:34;;;13979:1;13976;13969:12;13949:34;14018:58;14068:7;14059:6;14048:9;14044:22;14018:58;:::i;:::-;14095:8;;-1:-1:-1;13992:84:21;-1:-1:-1;13992:84:21;;-1:-1:-1;14149:37:21;14182:2;14167:18;;14149:37;:::i;:::-;14139:47;;14233:2;14222:9;14218:18;14205:32;14195:42;;14287:3;14276:9;14272:19;14259:33;14246:46;;14301:31;14326:5;14301:31;:::i;:::-;14351:5;;-1:-1:-1;14403:3:21;14388:19;;14375:33;;-1:-1:-1;14461:3:21;14446:19;;14433:33;;14478:16;;;14475:36;;;14507:1;14504;14497:12;14475:36;;14546:60;14598:7;14587:8;14576:9;14572:24;14546:60;:::i;:::-;14520:86;;14625:8;14615:18;;;14652:8;14642:18;;;14707:3;14696:9;14692:19;14679:33;14669:43;;13513:1205;;;;;;;;;;;;;:::o;14723:460::-;14807:6;14815;14823;14831;14884:3;14872:9;14863:7;14859:23;14855:33;14852:53;;;14901:1;14898;14891:12;14852:53;14924:28;14942:9;14924:28;:::i;:::-;14914:38;;14971:37;15004:2;14993:9;14989:18;14971:37;:::i;:::-;14961:47;;15058:2;15047:9;15043:18;15030:32;15071:31;15096:5;15071:31;:::i;:::-;14723:460;;;;-1:-1:-1;15121:5:21;;15173:2;15158:18;15145:32;;-1:-1:-1;;14723:460:21:o;15547:380::-;15626:1;15622:12;;;;15669;;;15690:61;;15744:4;15736:6;15732:17;15722:27;;15690:61;15797:2;15789:6;15786:14;15766:18;15763:38;15760:161;;15843:10;15838:3;15834:20;15831:1;15824:31;15878:4;15875:1;15868:15;15906:4;15903:1;15896:15;15932:271;16115:6;16107;16102:3;16089:33;16071:3;16141:16;;16166:13;;;16141:16;15932:271;-1:-1:-1;15932:271:21:o;16808:127::-;16869:10;16864:3;16860:20;16857:1;16850:31;16900:4;16897:1;16890:15;16924:4;16921:1;16914:15;16940:125;17005:9;;;17026:10;;;17023:36;;;17039:18;;:::i;17070:266::-;17158:6;17153:3;17146:19;17210:6;17203:5;17196:4;17191:3;17187:14;17174:43;-1:-1:-1;17262:1:21;17237:16;;;17255:4;17233:27;;;17226:38;;;;17318:2;17297:15;;;-1:-1:-1;;17293:29:21;17284:39;;;17280:50;;17070:266::o;17341:326::-;17536:6;17528;17524:19;17513:9;17506:38;17580:2;17575;17564:9;17560:18;17553:30;17487:4;17600:61;17657:2;17646:9;17642:18;17634:6;17626;17600:61;:::i;18339:521::-;18416:4;18422:6;18482:11;18469:25;18576:2;18572:7;18561:8;18545:14;18541:29;18537:43;18517:18;18513:68;18503:96;;18595:1;18592;18585:12;18503:96;18622:33;;18674:20;;;-1:-1:-1;;;;;;18706:30:21;;18703:50;;;18749:1;18746;18739:12;18703:50;18782:4;18770:17;;-1:-1:-1;18813:14:21;18809:27;;;18799:38;;18796:58;;;18850:1;18847;18840:12;19223:128;19290:9;;;19311:11;;;19308:37;;;19325:18;;:::i;19762:352::-;19973:6;19965;19960:3;19947:33;20068:2;20039:15;;;;-1:-1:-1;;;;;;20035:45:21;19999:16;;20024:57;;;20105:2;20097:11;;19762:352;-1:-1:-1;19762:352:21:o;20244:544::-;20345:2;20340:3;20337:11;20334:448;;;20381:1;20406:5;20402:2;20395:17;20451:4;20447:2;20437:19;20521:2;20509:10;20505:19;20502:1;20498:27;20492:4;20488:38;20557:4;20545:10;20542:20;20539:47;;;-1:-1:-1;20580:4:21;20539:47;20635:2;20630:3;20626:12;20623:1;20619:20;20613:4;20609:31;20599:41;;20690:82;20708:2;20701:5;20698:13;20690:82;;;20753:17;;;20734:1;20723:13;20690:82;;20793:166;-1:-1:-1;;20921:1:21;20917:11;;;20913:24;20909:29;20899:40;20945:1;20941:11;;;;20896:57;;20793:166::o;20964:1348::-;21082:10;;-1:-1:-1;;;;;21104:30:21;;21101:56;;;21137:18;;:::i;:::-;21166:96;21255:6;21215:38;21247:4;21241:11;21215:38;:::i;:::-;21209:4;21166:96;:::i;:::-;21317:4;;21381:2;21370:14;;21398:1;21393:662;;;;22099:1;22116:6;22113:89;;;-1:-1:-1;22168:19:21;;;22162:26;22113:89;22228:67;22288:6;22281:5;22228:67;:::i;:::-;22222:4;22215:81;;21363:943;;21393:662;20191:1;20184:14;;;20228:4;20215:18;;-1:-1:-1;;21429:20:21;;;21546:236;21560:7;21557:1;21554:14;21546:236;;;21649:19;;;21643:26;21628:42;;21741:27;;;;21709:1;21697:14;;;;21576:19;;21546:236;;;21550:3;21810:6;21801:7;21798:19;21795:201;;;21871:19;;;21865:26;-1:-1:-1;;21954:1:21;21950:14;;;21966:3;21946:24;21942:37;21938:42;21923:58;21908:74;;21795:201;-1:-1:-1;;;;;22042:1:21;22026:14;;;22022:22;22009:36;;-1:-1:-1;20964:1348:21:o;22317:498::-;22517:4;22546:6;22591:2;22583:6;22579:15;22568:9;22561:34;22643:2;22635:6;22631:15;22626:2;22615:9;22611:18;22604:43;;22683:6;22678:2;22667:9;22663:18;22656:34;22726:3;22721:2;22710:9;22706:18;22699:31;22747:62;22804:3;22793:9;22789:19;22781:6;22773;22747:62;:::i;:::-;22739:70;22317:498;-1:-1:-1;;;;;;;22317:498:21:o;23626:493::-;23875:6;23867;23863:19;23852:9;23845:38;23919:3;23914:2;23903:9;23899:18;23892:31;23826:4;23940:62;23997:3;23986:9;23982:19;23974:6;23966;23940:62;:::i;:::-;-1:-1:-1;;;;;24038:31:21;;;;24058:2;24018:18;;24011:59;-1:-1:-1;24101:2:21;24086:18;24079:34;23932:70;23626:493;-1:-1:-1;;;23626:493:21:o;25197:753::-;25530:6;25522;25518:19;25507:9;25500:38;25574:3;25569:2;25558:9;25554:18;25547:31;25481:4;25601:62;25658:3;25647:9;25643:19;25635:6;25627;25601:62;:::i;:::-;-1:-1:-1;;;;;25699:31:21;;25719:2;25679:18;;25672:59;25762:2;25747:18;;25740:34;;;25805:3;25790:19;;25783:35;;;25855:22;;;25849:3;25834:19;;25827:51;25895:49;25859:6;25929;25921;25895:49;:::i;:::-;25887:57;25197:753;-1:-1:-1;;;;;;;;;;;25197:753:21:o;25955:1202::-;-1:-1:-1;;;;;26069:27:21;;26066:53;;;26099:18;;:::i;:::-;26128:93;26217:3;26177:38;26209:4;26203:11;26177:38;:::i;:::-;26171:4;26128:93;:::i;:::-;26247:1;26272:2;26267:3;26264:11;26289:1;26284:615;;;;26943:1;26960:3;26957:93;;;-1:-1:-1;27016:19:21;;;27003:33;26957:93;27076:64;27136:3;27129:5;27076:64;:::i;:::-;27070:4;27063:78;;26257:894;;26284:615;20191:1;20184:14;;;20228:4;20215:18;;-1:-1:-1;;26320:17:21;;;26420:9;26442:229;26456:7;26453:1;26450:14;26442:229;;;26545:19;;;26532:33;26517:49;;26652:4;26637:20;;;;26605:1;26593:14;;;;26472:12;26442:229;;;26446:3;26699;26690:7;26687:16;26684:159;;;26823:1;26819:6;26813:3;26807;26804:1;26800:11;26796:21;26792:34;26788:39;26775:9;26770:3;26766:19;26753:33;26749:79;26741:6;26734:95;26684:159;;;26886:1;26880:3;26877:1;26873:11;26869:19;26863:4;26856:33;26257:894;;25955:1202;;;:::o;28030:647::-;28109:6;28162:2;28150:9;28141:7;28137:23;28133:32;28130:52;;;28178:1;28175;28168:12;28130:52;28205:16;;-1:-1:-1;;;;;28233:30:21;;28230:50;;;28276:1;28273;28266:12;28230:50;28299:22;;28352:4;28344:13;;28340:27;-1:-1:-1;28330:55:21;;28381:1;28378;28371:12;28330:55;28410:2;28404:9;28435:48;28451:31;28479:2;28451:31;:::i;28435:48::-;28506:2;28499:5;28492:17;28546:7;28541:2;28536;28532;28528:11;28524:20;28521:33;28518:53;;;28567:1;28564;28557:12;28518:53;28580:67;28644:2;28639;28632:5;28628:14;28623:2;28619;28615:11;28580:67;:::i;28682:557::-;28939:6;28931;28927:19;28916:9;28909:38;28983:3;28978:2;28967:9;28963:18;28956:31;28890:4;29010:46;29051:3;29040:9;29036:19;29028:6;29010:46;:::i;:::-;-1:-1:-1;;;;;29092:31:21;;29112:2;29072:18;;29065:59;29160:22;;;29155:2;29140:18;;29133:50;29200:33;29164:6;29218;29200:33;:::i;31988:642::-;32269:6;32257:19;;32239:38;;-1:-1:-1;;;;;32313:32:21;;32308:2;32293:18;;32286:60;32333:3;32377:2;32362:18;;32355:31;;;-1:-1:-1;;32409:46:21;;32435:19;;32427:6;32409:46;:::i;:::-;32505:6;32498:14;32491:22;32486:2;32475:9;32471:18;32464:50;32563:9;32555:6;32551:22;32545:3;32534:9;32530:19;32523:51;32591:33;32617:6;32609;32591:33;:::i;:::-;32583:41;31988:642;-1:-1:-1;;;;;;;;31988:642:21:o;32635:245::-;32714:6;32722;32775:2;32763:9;32754:7;32750:23;32746:32;32743:52;;;32791:1;32788;32781:12;32743:52;-1:-1:-1;;32814:16:21;;32870:2;32855:18;;;32849:25;32814:16;;32849:25;;-1:-1:-1;32635:245:21:o;33242:349::-;33444:2;33426:21;;;33483:2;33463:18;;;33456:30;-1:-1:-1;;;33517:2:21;33502:18;;33495:55;33582:2;33567:18;;33242:349::o;34285:287::-;34414:3;34452:6;34446:13;34468:66;34527:6;34522:3;34515:4;34507:6;34503:17;34468:66;:::i;:::-;34550:16;;;;;34285:287;-1:-1:-1;;34285:287:21:o;34577:719::-;34880:6;34872;34868:19;34857:9;34850:38;34924:3;34919:2;34908:9;34904:18;34897:31;34831:4;34951:46;34992:3;34981:9;34977:19;34969:6;34951:46;:::i;:::-;-1:-1:-1;;;;;35033:31:21;;35053:2;35013:18;;35006:59;35101:22;;;35096:2;35081:18;;35074:50;35147:33;35105:6;35165;35147:33;:::i;:::-;35133:47;;35229:9;35221:6;35217:22;35211:3;35200:9;35196:19;35189:51;35257:33;35283:6;35275;35257:33;:::i;35301:127::-;35362:10;35357:3;35353:20;35350:1;35343:31;35393:4;35390:1;35383:15;35417:4;35414:1;35407:15;35433:120;35473:1;35499;35489:35;;35504:18;;:::i;:::-;-1:-1:-1;35538:9:21;;35433:120::o;36642:891::-;36962:4;36991:3;37033:6;37025;37021:19;37010:9;37003:38;37077:2;37072;37061:9;37057:18;37050:30;37103:45;37144:2;37133:9;37129:18;37121:6;37103:45;:::i;:::-;-1:-1:-1;;;;;37184:31:21;;37204:2;37164:18;;37157:59;37247:2;37232:18;;37225:34;;;-1:-1:-1;;;;;37296:32:21;;37290:3;37275:19;;37268:61;37316:3;37345:19;;37338:35;;;37410:22;;;37404:3;37389:19;;37382:51;37089:59;-1:-1:-1;37450:33:21;37089:59;37468:6;37450:33;:::i;:::-;37442:41;;;37520:6;37514:3;37503:9;37499:19;37492:35;36642:891;;;;;;;;;;;:::o;37538:383::-;37739:2;37728:9;37721:21;37702:4;37759:45;37800:2;37789:9;37785:18;37777:6;37759:45;:::i;:::-;-1:-1:-1;;;;;37840:31:21;;;;37835:2;37820:18;;37813:59;-1:-1:-1;37860:2:21;37888:18;37881:34;37751:53;37538:383;-1:-1:-1;37538:383:21:o;38333:112::-;38365:1;38391;38381:35;;38396:18;;:::i;:::-;-1:-1:-1;38430:9:21;;38333:112::o;38867:840::-;39216:6;39208;39204:19;39193:9;39186:38;39260:3;39255:2;39244:9;39240:18;39233:31;39167:4;39287:46;39328:3;39317:9;39313:19;39305:6;39287:46;:::i;:::-;39381:9;39373:6;39369:22;39364:2;39353:9;39349:18;39342:50;39415:33;39441:6;39433;39415:33;:::i;:::-;-1:-1:-1;;;;;39522:15:21;;;39517:2;39502:18;;39495:43;39575:15;;39569:3;39554:19;;39547:44;39628:22;;;39475:3;39607:19;;39600:51;39401:47;-1:-1:-1;39668:33:21;39401:47;39686:6;39668:33;:::i;:::-;39660:41;38867:840;-1:-1:-1;;;;;;;;;38867:840:21:o;39712:723::-;-1:-1:-1;;;;;;40029:3:21;40007:16;;;40003:36;39991:49;;40065:1;40056:11;;40049:27;;;-1:-1:-1;;;;;;40107:3:21;40153:16;;;40149:25;;40144:2;40135:12;;40128:47;40200:2;40191:12;;40184:28;;;40246:16;;;40242:25;40237:2;40228:12;;40221:47;40291:13;;-1:-1:-1;;40313:75:21;40291:13;40376:2;40367:12;;40360:4;40348:17;;40313:75;:::i;:::-;40408:16;;;;40426:2;40404:25;;39712:723;-1:-1:-1;;;;;;;39712:723:21:o;40440:348::-;40642:2;40624:21;;;40681:2;40661:18;;;40654:30;-1:-1:-1;;;40715:2:21;40700:18;;40693:54;40779:2;40764:18;;40440:348::o;40793:168::-;40866:9;;;40897;;40914:15;;;40908:22;;40894:37;40884:71;;40935:18;;:::i

Metadata Hash

ipfs://a7b0819d130228de1a73b45a5ca5c5bbf706857759be311e9f5dbbb4a7051464
Loading