{
  "language": "Solidity",
  "sources": {
    "contracts/dnsregistrar/MappingPublicSuffixList.sol": {
      "content": "pragma solidity ^0.8.4;\n\nimport \"../dnssec-oracle/BytesUtils.sol\";\nimport \"./PublicSuffixList.sol\";\n\n/**\n * @dev A public suffix list that treats all TLDs as public suffixes.\n */\ncontract TLDPublicSuffixList is PublicSuffixList {\n    using BytesUtils for bytes;\n\n    function isPublicSuffix(\n        bytes calldata name\n    ) external view override returns (bool) {\n        uint256 labellen = name.readUint8(0);\n        return labellen > 0 && name.readUint8(labellen + 1) == 0;\n    }\n}\n"
    },
    "contracts/dnsregistrar/PublicSuffixList.sol": {
      "content": "pragma solidity ^0.8.4;\n\ninterface PublicSuffixList {\n    function isPublicSuffix(bytes calldata name) external view returns (bool);\n}\n"
    },
    "contracts/dnsregistrar/SimplePublicSuffixList.sol": {
      "content": "pragma solidity ^0.8.4;\npragma experimental ABIEncoderV2;\n\nimport \"../root/Ownable.sol\";\nimport \"./PublicSuffixList.sol\";\n\ncontract SimplePublicSuffixList is PublicSuffixList, Ownable {\n    mapping(bytes => bool) suffixes;\n\n    event SuffixAdded(bytes suffix);\n\n    function addPublicSuffixes(bytes[] memory names) public onlyOwner {\n        for (uint256 i = 0; i < names.length; i++) {\n            suffixes[names[i]] = true;\n            emit SuffixAdded(names[i]);\n        }\n    }\n\n    function isPublicSuffix(\n        bytes calldata name\n    ) external view override returns (bool) {\n        return suffixes[name];\n    }\n}\n"
    },
    "contracts/dnssec-oracle/BytesUtils.sol": {
      "content": "pragma solidity ^0.8.4;\n\nlibrary BytesUtils {\n    error OffsetOutOfBoundsError(uint256 offset, uint256 length);\n\n    /*\n     * @dev Returns the keccak-256 hash of a byte range.\n     * @param self The byte string to hash.\n     * @param offset The position to start hashing at.\n     * @param len The number of bytes to hash.\n     * @return The hash of the byte range.\n     */\n    function keccak(\n        bytes memory self,\n        uint256 offset,\n        uint256 len\n    ) internal pure returns (bytes32 ret) {\n        require(offset + len <= self.length);\n        assembly {\n            ret := keccak256(add(add(self, 32), offset), len)\n        }\n    }\n\n    /*\n     * @dev Returns a positive number if `other` comes lexicographically after\n     *      `self`, a negative number if it comes before, or zero if the\n     *      contents of the two bytes are equal.\n     * @param self The first bytes to compare.\n     * @param other The second bytes to compare.\n     * @return The result of the comparison.\n     */\n    function compare(\n        bytes memory self,\n        bytes memory other\n    ) internal pure returns (int256) {\n        return compare(self, 0, self.length, other, 0, other.length);\n    }\n\n    /*\n     * @dev Returns a positive number if `other` comes lexicographically after\n     *      `self`, a negative number if it comes before, or zero if the\n     *      contents of the two bytes are equal. Comparison is done per-rune,\n     *      on unicode codepoints.\n     * @param self The first bytes to compare.\n     * @param offset The offset of self.\n     * @param len    The length of self.\n     * @param other The second bytes to compare.\n     * @param otheroffset The offset of the other string.\n     * @param otherlen    The length of the other string.\n     * @return The result of the comparison.\n     */\n    function compare(\n        bytes memory self,\n        uint256 offset,\n        uint256 len,\n        bytes memory other,\n        uint256 otheroffset,\n        uint256 otherlen\n    ) internal pure returns (int256) {\n        if (offset + len > self.length) {\n            revert OffsetOutOfBoundsError(offset + len, self.length);\n        }\n        if (otheroffset + otherlen > other.length) {\n            revert OffsetOutOfBoundsError(otheroffset + otherlen, other.length);\n        }\n\n        uint256 shortest = len;\n        if (otherlen < len) shortest = otherlen;\n\n        uint256 selfptr;\n        uint256 otherptr;\n\n        assembly {\n            selfptr := add(self, add(offset, 32))\n            otherptr := add(other, add(otheroffset, 32))\n        }\n        for (uint256 idx = 0; idx < shortest; idx += 32) {\n            uint256 a;\n            uint256 b;\n            assembly {\n                a := mload(selfptr)\n                b := mload(otherptr)\n            }\n            if (a != b) {\n                // Mask out irrelevant bytes and check again\n                uint256 mask;\n                if (shortest - idx >= 32) {\n                    mask = type(uint256).max;\n                } else {\n                    mask = ~(2 ** (8 * (idx + 32 - shortest)) - 1);\n                }\n                int256 diff = int256(a & mask) - int256(b & mask);\n                if (diff != 0) return diff;\n            }\n            selfptr += 32;\n            otherptr += 32;\n        }\n\n        return int256(len) - int256(otherlen);\n    }\n\n    /*\n     * @dev Returns true if the two byte ranges are equal.\n     * @param self The first byte range to compare.\n     * @param offset The offset into the first byte range.\n     * @param other The second byte range to compare.\n     * @param otherOffset The offset into the second byte range.\n     * @param len The number of bytes to compare\n     * @return True if the byte ranges are equal, false otherwise.\n     */\n    function equals(\n        bytes memory self,\n        uint256 offset,\n        bytes memory other,\n        uint256 otherOffset,\n        uint256 len\n    ) internal pure returns (bool) {\n        return keccak(self, offset, len) == keccak(other, otherOffset, len);\n    }\n\n    /*\n     * @dev Returns true if the two byte ranges are equal with offsets.\n     * @param self The first byte range to compare.\n     * @param offset The offset into the first byte range.\n     * @param other The second byte range to compare.\n     * @param otherOffset The offset into the second byte range.\n     * @return True if the byte ranges are equal, false otherwise.\n     */\n    function equals(\n        bytes memory self,\n        uint256 offset,\n        bytes memory other,\n        uint256 otherOffset\n    ) internal pure returns (bool) {\n        return\n            keccak(self, offset, self.length - offset) ==\n            keccak(other, otherOffset, other.length - otherOffset);\n    }\n\n    /*\n     * @dev Compares a range of 'self' to all of 'other' and returns True iff\n     *      they are equal.\n     * @param self The first byte range to compare.\n     * @param offset The offset into the first byte range.\n     * @param other The second byte range to compare.\n     * @return True if the byte ranges are equal, false otherwise.\n     */\n    function equals(\n        bytes memory self,\n        uint256 offset,\n        bytes memory other\n    ) internal pure returns (bool) {\n        return\n            self.length == offset + other.length &&\n            equals(self, offset, other, 0, other.length);\n    }\n\n    /*\n     * @dev Returns true if the two byte ranges are equal.\n     * @param self The first byte range to compare.\n     * @param other The second byte range to compare.\n     * @return True if the byte ranges are equal, false otherwise.\n     */\n    function equals(\n        bytes memory self,\n        bytes memory other\n    ) internal pure returns (bool) {\n        return\n            self.length == other.length &&\n            equals(self, 0, other, 0, self.length);\n    }\n\n    /*\n     * @dev Returns the 8-bit number at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes\n     * @return The specified 8 bits of the string, interpreted as an integer.\n     */\n    function readUint8(\n        bytes memory self,\n        uint256 idx\n    ) internal pure returns (uint8 ret) {\n        return uint8(self[idx]);\n    }\n\n    /*\n     * @dev Returns the 16-bit number at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes\n     * @return The specified 16 bits of the string, interpreted as an integer.\n     */\n    function readUint16(\n        bytes memory self,\n        uint256 idx\n    ) internal pure returns (uint16 ret) {\n        require(idx + 2 <= self.length);\n        assembly {\n            ret := and(mload(add(add(self, 2), idx)), 0xFFFF)\n        }\n    }\n\n    /*\n     * @dev Returns the 32-bit number at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes\n     * @return The specified 32 bits of the string, interpreted as an integer.\n     */\n    function readUint32(\n        bytes memory self,\n        uint256 idx\n    ) internal pure returns (uint32 ret) {\n        require(idx + 4 <= self.length);\n        assembly {\n            ret := and(mload(add(add(self, 4), idx)), 0xFFFFFFFF)\n        }\n    }\n\n    /*\n     * @dev Returns the 32 byte value at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes\n     * @return The specified 32 bytes of the string.\n     */\n    function readBytes32(\n        bytes memory self,\n        uint256 idx\n    ) internal pure returns (bytes32 ret) {\n        require(idx + 32 <= self.length);\n        assembly {\n            ret := mload(add(add(self, 32), idx))\n        }\n    }\n\n    /*\n     * @dev Returns the 32 byte value at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes\n     * @return The specified 32 bytes of the string.\n     */\n    function readBytes20(\n        bytes memory self,\n        uint256 idx\n    ) internal pure returns (bytes20 ret) {\n        require(idx + 20 <= self.length);\n        assembly {\n            ret := and(\n                mload(add(add(self, 32), idx)),\n                0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF000000000000000000000000\n            )\n        }\n    }\n\n    /*\n     * @dev Returns the n byte value at the specified index of self.\n     * @param self The byte string.\n     * @param idx The index into the bytes.\n     * @param len The number of bytes.\n     * @return The specified 32 bytes of the string.\n     */\n    function readBytesN(\n        bytes memory self,\n        uint256 idx,\n        uint256 len\n    ) internal pure returns (bytes32 ret) {\n        require(len <= 32);\n        require(idx + len <= self.length);\n        assembly {\n            let mask := not(sub(exp(256, sub(32, len)), 1))\n            ret := and(mload(add(add(self, 32), idx)), mask)\n        }\n    }\n\n    function memcpy(uint256 dest, uint256 src, uint256 len) private pure {\n        // Copy word-length chunks while possible\n        for (; len >= 32; len -= 32) {\n            assembly {\n                mstore(dest, mload(src))\n            }\n            dest += 32;\n            src += 32;\n        }\n\n        // Copy remaining bytes\n        unchecked {\n            uint256 mask = (256 ** (32 - len)) - 1;\n            assembly {\n                let srcpart := and(mload(src), not(mask))\n                let destpart := and(mload(dest), mask)\n                mstore(dest, or(destpart, srcpart))\n            }\n        }\n    }\n\n    /*\n     * @dev Copies a substring into a new byte string.\n     * @param self The byte string to copy from.\n     * @param offset The offset to start copying at.\n     * @param len The number of bytes to copy.\n     */\n    function substring(\n        bytes memory self,\n        uint256 offset,\n        uint256 len\n    ) internal pure returns (bytes memory) {\n        require(offset + len <= self.length);\n\n        bytes memory ret = new bytes(len);\n        uint256 dest;\n        uint256 src;\n\n        assembly {\n            dest := add(ret, 32)\n            src := add(add(self, 32), offset)\n        }\n        memcpy(dest, src, len);\n\n        return ret;\n    }\n\n    // Maps characters from 0x30 to 0x7A to their base32 values.\n    // 0xFF represents invalid characters in that range.\n    bytes constant base32HexTable =\n        hex\"00010203040506070809FFFFFFFFFFFFFF0A0B0C0D0E0F101112131415161718191A1B1C1D1E1FFFFFFFFFFFFFFFFFFFFF0A0B0C0D0E0F101112131415161718191A1B1C1D1E1F\";\n\n    /**\n     * @dev Decodes unpadded base32 data of up to one word in length.\n     * @param self The data to decode.\n     * @param off Offset into the string to start at.\n     * @param len Number of characters to decode.\n     * @return The decoded data, left aligned.\n     */\n    function base32HexDecodeWord(\n        bytes memory self,\n        uint256 off,\n        uint256 len\n    ) internal pure returns (bytes32) {\n        require(len <= 52);\n\n        uint256 ret = 0;\n        uint8 decoded;\n        for (uint256 i = 0; i < len; i++) {\n            bytes1 char = self[off + i];\n            require(char >= 0x30 && char <= 0x7A);\n            decoded = uint8(base32HexTable[uint256(uint8(char)) - 0x30]);\n            require(decoded <= 0x20);\n            if (i == len - 1) {\n                break;\n            }\n            ret = (ret << 5) | decoded;\n        }\n\n        uint256 bitlen = len * 5;\n        if (len % 8 == 0) {\n            // Multiple of 8 characters, no padding\n            ret = (ret << 5) | decoded;\n        } else if (len % 8 == 2) {\n            // Two extra characters - 1 byte\n            ret = (ret << 3) | (decoded >> 2);\n            bitlen -= 2;\n        } else if (len % 8 == 4) {\n            // Four extra characters - 2 bytes\n            ret = (ret << 1) | (decoded >> 4);\n            bitlen -= 4;\n        } else if (len % 8 == 5) {\n            // Five extra characters - 3 bytes\n            ret = (ret << 4) | (decoded >> 1);\n            bitlen -= 1;\n        } else if (len % 8 == 7) {\n            // Seven extra characters - 4 bytes\n            ret = (ret << 2) | (decoded >> 3);\n            bitlen -= 3;\n        } else {\n            revert();\n        }\n\n        return bytes32(ret << (256 - bitlen));\n    }\n\n    /**\n     * @dev Finds the first occurrence of the byte `needle` in `self`.\n     * @param self The string to search\n     * @param off The offset to start searching at\n     * @param len The number of bytes to search\n     * @param needle The byte to search for\n     * @return The offset of `needle` in `self`, or 2**256-1 if it was not found.\n     */\n    function find(\n        bytes memory self,\n        uint256 off,\n        uint256 len,\n        bytes1 needle\n    ) internal pure returns (uint256) {\n        for (uint256 idx = off; idx < off + len; idx++) {\n            if (self[idx] == needle) {\n                return idx;\n            }\n        }\n        return type(uint256).max;\n    }\n}\n"
    },
    "contracts/root/Ownable.sol": {
      "content": "pragma solidity ^0.8.4;\n\ncontract Ownable {\n    address public owner;\n\n    event OwnershipTransferred(\n        address indexed previousOwner,\n        address indexed newOwner\n    );\n\n    modifier onlyOwner() {\n        require(isOwner(msg.sender));\n        _;\n    }\n\n    constructor() public {\n        owner = msg.sender;\n    }\n\n    function transferOwnership(address newOwner) public onlyOwner {\n        emit OwnershipTransferred(owner, newOwner);\n        owner = newOwner;\n    }\n\n    function isOwner(address addr) public view returns (bool) {\n        return owner == addr;\n    }\n}\n"
    }
  },
  "settings": {
    "optimizer": {
      "enabled": true,
      "runs": 1200
    },
    "outputSelection": {
      "*": {
        "*": [
          "abi",
          "evm.bytecode",
          "evm.deployedBytecode",
          "evm.methodIdentifiers",
          "metadata",
          "devdoc",
          "userdoc",
          "storageLayout",
          "evm.gasEstimates"
        ],
        "": [
          "ast"
        ]
      }
    },
    "metadata": {
      "useLiteralContent": true
    }
  }
}