ETH Price: $2,042.16 (+6.67%)
 

Overview

Max Total Supply

10,000 SU

Holders

3

Transfers

-
0

Market

Onchain Market Cap

-

Circulating Supply Market Cap

-

Other Info

Token Contract (WITH 0 Decimals)

Loading...
Loading
Loading...
Loading
Loading...
Loading

Click here to update the token information / general information
# Exchange Pair Price  24H Volume % Volume

Contract Source Code Verified (Exact Match)

Contract Name:
SuMain

Compiler Version
v0.4.21+commit.dfe3193c

Optimization Enabled:
Yes with 200 runs

Other Settings:
default evmVersion
/**
 *Submitted for verification at Etherscan.io on 2018-03-19
*/

pragma solidity ^0.4.21;

/******************************************************************************\
*..................................SU.SQUARES..................................*
*.......................Blockchain.rentable.advertising........................*
*..............................................................................*
* First, I just want to say we are so excited and humbled to get this far and  *
* that you're even reading this. So thank you!                                 *
*                                                                              *
* This file is organized into multiple contracts that separate functionality   *
* into logical parts. The deployed contract, SuMain, is at the bottom and      *
* includes the rest of the file using inheritance.                             *
*                                                                              *
*  - ERC165, ERC721: These interfaces follow the official EIPs                 *
*  - AccessControl: A reusable CEO/CFO/COO access model                        *
*  - PublishInterfaces: An implementation of ERC165                            *
*  - SuNFT: An implementation of ERC721                                        *
*  - SuOperation: The actual square data and the personalize function          *
*  - SuPromo, SuVending: How we sell or grant squares                          *
*..............................................................................*
*............................Su.&.William.Entriken.............................*
*...................................(c) 2018...................................*
\******************************************************************************/

/* AccessControl.sol **********************************************************/

/// @title Reusable three-role access control inspired by CryptoKitties
/// @author William Entriken (https://phor.net)
/// @dev Keep the CEO wallet stored offline, I warned you
contract AccessControl {
    /// @notice The account that can only reassign executive accounts
    address public executiveOfficerAddress;

    /// @notice The account that can collect funds from this contract
    address public financialOfficerAddress;

    /// @notice The account with administrative control of this contract
    address public operatingOfficerAddress;

    function AccessControl() internal {
        executiveOfficerAddress = msg.sender;
    }

    /// @dev Only allowed by executive officer
    modifier onlyExecutiveOfficer() {
        require(msg.sender == executiveOfficerAddress);
        _;
    }

    /// @dev Only allowed by financial officer
    modifier onlyFinancialOfficer() {
        require(msg.sender == financialOfficerAddress);
        _;
    }

    /// @dev Only allowed by operating officer
    modifier onlyOperatingOfficer() {
        require(msg.sender == operatingOfficerAddress);
        _;
    }

    /// @notice Reassign the executive officer role
    /// @param _executiveOfficerAddress new officer address
    function setExecutiveOfficer(address _executiveOfficerAddress)
        external
        onlyExecutiveOfficer
    {
        require(_executiveOfficerAddress != address(0));
        executiveOfficerAddress = _executiveOfficerAddress;
    }

    /// @notice Reassign the financial officer role
    /// @param _financialOfficerAddress new officer address
    function setFinancialOfficer(address _financialOfficerAddress)
        external
        onlyExecutiveOfficer
    {
        require(_financialOfficerAddress != address(0));
        financialOfficerAddress = _financialOfficerAddress;
    }

    /// @notice Reassign the operating officer role
    /// @param _operatingOfficerAddress new officer address
    function setOperatingOfficer(address _operatingOfficerAddress)
        external
        onlyExecutiveOfficer
    {
        require(_operatingOfficerAddress != address(0));
        operatingOfficerAddress = _operatingOfficerAddress;
    }

    /// @notice Collect funds from this contract
    function withdrawBalance() external onlyFinancialOfficer {
        financialOfficerAddress.transfer(address(this).balance);
    }
}

/* ERC165.sol *****************************************************************/

/// @title ERC-165 Standard Interface Detection
/// @dev See https://github.com/ethereum/EIPs/blob/master/EIPS/eip-165.md
interface ERC165 {
    function supportsInterface(bytes4 interfaceID) external view returns (bool);
}

/* ERC721.sol *****************************************************************/

/// @title ERC-721 Non-Fungible Token Standard
/// @dev See https://github.com/ethereum/EIPs/blob/master/EIPS/eip-721.md
contract ERC721 is ERC165 {
    event Transfer(address indexed _from, address indexed _to, uint256 _tokenId);
    event Approval(address indexed _owner, address indexed _approved, uint256 _tokenId);
    event ApprovalForAll(address indexed _owner, address indexed _operator, bool _approved);
    function balanceOf(address _owner) external view returns (uint256);
    function ownerOf(uint256 _tokenId) external view returns (address);
    function safeTransferFrom(address _from, address _to, uint256 _tokenId, bytes data) external payable;
    function safeTransferFrom(address _from, address _to, uint256 _tokenId) external payable;
    function transferFrom(address _from, address _to, uint256 _tokenId) external payable;
    function approve(address _approved, uint256 _tokenId) external payable;
    function setApprovalForAll(address _operator, bool _approved) external;
    function getApproved(uint256 _tokenId) external view returns (address);
    function isApprovedForAll(address _owner, address _operator) external view returns (bool);
}

/// @title ERC-721 Non-Fungible Token Standard
interface ERC721TokenReceiver {
	function onERC721Received(address _from, uint256 _tokenId, bytes data) external returns(bytes4);
}

/// @title ERC-721 Non-Fungible Token Standard, optional metadata extension
interface ERC721Metadata /* is ERC721 */ {
    function name() external pure returns (string _name);
    function symbol() external pure returns (string _symbol);
    function tokenURI(uint256 _tokenId) external view returns (string);
}

/// @title ERC-721 Non-Fungible Token Standard, optional enumeration extension
interface ERC721Enumerable /* is ERC721 */ {
    function totalSupply() external view returns (uint256);
    function tokenByIndex(uint256 _index) external view returns (uint256);
    function tokenOfOwnerByIndex(address _owner, uint256 _index) external view returns (uint256);
}

/* PublishInterfaces.sol ******************************************************/

/// @title A reusable contract to comply with ERC-165
/// @author William Entriken (https://phor.net)
contract PublishInterfaces is ERC165 {
    /// @dev Every interface that we support
    mapping(bytes4 => bool) internal supportedInterfaces;

    function PublishInterfaces() internal {
        supportedInterfaces[0x01ffc9a7] = true; // ERC165
    }

    /// @notice Query if a contract implements an interface
    /// @param interfaceID The interface identifier, as specified in ERC-165
    /// @dev Interface identification is specified in ERC-165. This function
    ///  uses less than 30,000 gas.
    /// @return `true` if the contract implements `interfaceID` and
    ///  `interfaceID` is not 0xffffffff, `false` otherwise
    function supportsInterface(bytes4 interfaceID) external view returns (bool) {
        return supportedInterfaces[interfaceID] && (interfaceID != 0xffffffff);
    }
}

/* SuNFT.sol ******************************************************************/

/// @title Compliance with ERC-721 for Su Squares
/// @dev This implementation assumes:
///  - A fixed supply of NFTs, cannot mint or burn
///  - ids are numbered sequentially starting at 1.
///  - NFTs are initially assigned to this contract
///  - This contract does not externally call its own functions
/// @author William Entriken (https://phor.net)
contract SuNFT is ERC165, ERC721, ERC721Metadata, ERC721Enumerable, PublishInterfaces {
    /// @dev The authorized address for each NFT
    mapping (uint256 => address) internal tokenApprovals;

    /// @dev The authorized operators for each address
    mapping (address => mapping (address => bool)) internal operatorApprovals;

    /// @dev Guarantees msg.sender is the owner of _tokenId
    /// @param _tokenId The token to validate belongs to msg.sender
    modifier onlyOwnerOf(uint256 _tokenId) {
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        // assert(msg.sender != address(this))
        require(msg.sender == owner);
        _;
    }
    
    modifier mustBeOwnedByThisContract(uint256 _tokenId) {
        require(_tokenId >= 1 && _tokenId <= TOTAL_SUPPLY);
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        require(owner == address(0) || owner == address(this));
        _;
    }
    
    modifier canOperate(uint256 _tokenId) {
        // assert(msg.sender != address(this))
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        require(msg.sender == owner || operatorApprovals[owner][msg.sender]);
        _;
    }
    
    modifier canTransfer(uint256 _tokenId) {
        // assert(msg.sender != address(this))
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        require(msg.sender == owner || 
          msg.sender == tokenApprovals[_tokenId] || 
          operatorApprovals[msg.sender][msg.sender]);
        _;
    }
    
    modifier mustBeValidToken(uint256 _tokenId) {
        require(_tokenId >= 1 && _tokenId <= TOTAL_SUPPLY);
        _;
    }
    
    /// @dev This emits when ownership of any NFT changes by any mechanism.
    ///  This event emits when NFTs are created (`from` == 0) and destroyed
    ///  (`to` == 0). Exception: during contract creation, any number of NFTs
    ///  may be created and assigned without emitting Transfer. At the time of
    ///  any transfer, the approved address for that NFT (if any) is reset to none.
    event Transfer(address indexed _from, address indexed _to, uint256 _tokenId);

    /// @dev This emits when the approved address for an NFT is changed or
    ///  reaffirmed. The zero address indicates there is no approved address.
    ///  When a Transfer event emits, this also indicates that the approved
    ///  address for that NFT (if any) is reset to none.
    event Approval(address indexed _owner, address indexed _approved, uint256 _tokenId);

    /// @dev This emits when an operator is enabled or disabled for an owner.
    ///  The operator can manage all NFTs of the owner.
    event ApprovalForAll(address indexed _owner, address indexed _operator, bool _approved);

    /// @notice Count all NFTs assigned to an owner
    /// @dev NFTs assigned to the zero address are considered invalid, and this
    ///  function throws for queries about the zero address.
    /// @param _owner An address for whom to query the balance
    /// @return The number of NFTs owned by `_owner`, possibly zero
    function balanceOf(address _owner) external view returns (uint256) {
        require(_owner != address(0));
        return _tokensOfOwnerWithSubstitutions[_owner].length;
    }

    /// @notice Find the owner of an NFT
    /// @param _tokenId The identifier for an NFT
    /// @dev NFTs assigned to zero address are considered invalid, and queries
    ///  about them do throw.
    /// @return The address of the owner of the NFT
    function ownerOf(uint256 _tokenId) 
        external
        view
        mustBeValidToken(_tokenId)
        returns (address _owner)
    {
        _owner = _tokenOwnerWithSubstitutions[_tokenId];
        // Handle substitutions
        if (_owner == address(0)) {
            _owner = address(this);
        }
    }

    /// @notice Transfers the ownership of an NFT from one address to another address
    /// @dev Throws unless `msg.sender` is the current owner, an authorized
    ///  operator, or the approved address for this NFT. Throws if `_from` is
    ///  not the current owner. Throws if `_to` is the zero address. Throws if
    ///  `_tokenId` is not a valid NFT. When transfer is complete, this function
    ///  checks if `_to` is a smart contract (code size > 0). If so, it calls
    ///  `onERC721Received` on `_to` and throws if the return value is not
    ///  `bytes4(keccak256("onERC721Received(address,uint256,bytes)"))`.
    /// @param _from The current owner of the NFT
    /// @param _to The new owner
    /// @param _tokenId The NFT to transfer
    /// @param data Additional data with no specified format, sent in call to `_to`
    function safeTransferFrom(address _from, address _to, uint256 _tokenId, bytes data) external payable
    {
        _safeTransferFrom(_from, _to, _tokenId, data);
    }
	
    /// @notice Transfers the ownership of an NFT from one address to another address
    /// @dev This works identically to the other function with an extra data parameter,
    ///  except this function just sets data to ""
    /// @param _from The current owner of the NFT
    /// @param _to The new owner
    /// @param _tokenId The NFT to transfer
    function safeTransferFrom(address _from, address _to, uint256 _tokenId) external payable
    {
        _safeTransferFrom(_from, _to, _tokenId, "");
    }

    /// @notice Transfer ownership of an NFT -- THE CALLER IS RESPONSIBLE
    ///  TO CONFIRM THAT `_to` IS CAPABLE OF RECEIVING NFTS OR ELSE
    ///  THEY MAY BE PERMANENTLY LOST
    /// @dev Throws unless `msg.sender` is the current owner, an authorized
    ///  operator, or the approved address for this NFT. Throws if `_from` is
    ///  not the current owner. Throws if `_to` is the zero address. Throws if
    ///  `_tokenId` is not a valid NFT.
    /// @param _from The current owner of the NFT
    /// @param _to The new owner
    /// @param _tokenId The NFT to transfer
    function transferFrom(address _from, address _to, uint256 _tokenId)
        external
        payable
        mustBeValidToken(_tokenId)
        canTransfer(_tokenId)
    {
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        // Handle substitutions
        if (owner == address(0)) {
            owner = address(this);
        }
        require(owner == _from);
        require(_to != address(0));
        _transfer(_tokenId, _to);
    }

    /// @notice Set or reaffirm the approved address for an NFT
    /// @dev The zero address indicates there is no approved address.
    /// @dev Throws unless `msg.sender` is the current NFT owner, or an authorized
    ///  operator of the current owner.
    /// @param _approved The new approved NFT controller
    /// @param _tokenId The NFT to approve
    function approve(address _approved, uint256 _tokenId)
        external
        payable
        // assert(mustBeValidToken(_tokenId))
        canOperate(_tokenId)
    {
        address _owner = _tokenOwnerWithSubstitutions[_tokenId];
        // Handle substitutions
        if (_owner == address(0)) {
            _owner = address(this);
        }
        tokenApprovals[_tokenId] = _approved;
        emit Approval(_owner, _approved, _tokenId);
    }

    /// @notice Enable or disable approval for a third party ("operator") to manage
    ///  all your asset.
    /// @dev Emits the ApprovalForAll event
    /// @param _operator Address to add to the set of authorized operators.
    /// @param _approved True if the operators is approved, false to revoke approval
    function setApprovalForAll(address _operator, bool _approved) external {
        operatorApprovals[msg.sender][_operator] = _approved;
        emit ApprovalForAll(msg.sender, _operator, _approved);
    }

    /// @notice Get the approved address for a single NFT
    /// @dev Throws if `_tokenId` is not a valid NFT
    /// @param _tokenId The NFT to find the approved address for
    /// @return The approved address for this NFT, or the zero address if there is none
    function getApproved(uint256 _tokenId)
        external
        view
        mustBeValidToken(_tokenId)
        returns (address)
    {
        return tokenApprovals[_tokenId];        
    }

    /// @notice Query if an address is an authorized operator for another address
    /// @param _owner The address that owns the NFTs
    /// @param _operator The address that acts on behalf of the owner
    /// @return True if `_operator` is an approved operator for `_owner`, false otherwise
    function isApprovedForAll(address _owner, address _operator) external view returns (bool) {
        return operatorApprovals[_owner][_operator];
    }
    
    // COMPLIANCE WITH ERC721Metadata //////////////////////////////////////////

    /// @notice A descriptive name for a collection of NFTs in this contract
    function name() external pure returns (string) {
        return "Su Squares";
    }

    /// @notice An abbreviated name for NFTs in this contract
    function symbol() external pure returns (string) {
        return "SU";
    }

    /// @notice A distinct Uniform Resource Identifier (URI) for a given asset.
    /// @dev Throws if `_tokenId` is not a valid NFT. URIs are defined in RFC
    ///  3986. The URI may point to a JSON file that conforms to the "ERC721
    ///  Metadata JSON Schema".
    function tokenURI(uint256 _tokenId) 
        external
        view
        mustBeValidToken(_tokenId)
        returns (string _tokenURI)
    {
        _tokenURI = "https://tenthousandsu.com/erc721/00000.json";
        bytes memory _tokenURIBytes = bytes(_tokenURI);
        _tokenURIBytes[33] = byte(48+(_tokenId / 10000) % 10);
        _tokenURIBytes[34] = byte(48+(_tokenId / 1000) % 10);
        _tokenURIBytes[35] = byte(48+(_tokenId / 100) % 10);
        _tokenURIBytes[36] = byte(48+(_tokenId / 10) % 10);
        _tokenURIBytes[37] = byte(48+(_tokenId / 1) % 10);
        
    }

    // COMPLIANCE WITH ERC721Enumerable ////////////////////////////////////////

    /// @notice Count NFTs tracked by this contract
    /// @return A count of valid NFTs tracked by this contract, where each one of
    ///  them has an assigned and queryable owner not equal to the zero address
    function totalSupply() external view returns (uint256) {
        return TOTAL_SUPPLY;
    }

    /// @notice Enumerate valid NFTs
    /// @dev Throws if `_index` >= `totalSupply()`.
    /// @param _index A counter less than `totalSupply()`
    /// @return The token identifier for the `_index`th NFT,
    ///  (sort order not specified)
    function tokenByIndex(uint256 _index) external view returns (uint256) {
        require(_index < TOTAL_SUPPLY);
        return _index + 1;
    }

    /// @notice Enumerate NFTs assigned to an owner
    /// @dev Throws if `_index` >= `balanceOf(_owner)` or if
    ///  `_owner` is the zero address, representing invalid NFTs.
    /// @param _owner An address where we are interested in NFTs owned by them
    /// @param _index A counter less than `balanceOf(_owner)`
    /// @return The token identifier for the `_index`th NFT assigned to `_owner`,
    ///   (sort order not specified)
    function tokenOfOwnerByIndex(address _owner, uint256 _index) external view returns (uint256 _tokenId) {
        require(_owner != address(0));
        require(_index < _tokensOfOwnerWithSubstitutions[_owner].length);
        _tokenId = _tokensOfOwnerWithSubstitutions[_owner][_index];
        // Handle substitutions
        if (_owner == address(this)) {
            if (_tokenId == 0) {
                _tokenId = _index + 1;
            }
        }
    }

    // INTERNAL INTERFACE //////////////////////////////////////////////////////

    /// @dev Actually do a transfer, does NO precondition checking
    function _transfer(uint256 _tokenId, address _to) internal {
        // Here are the preconditions we are not checking:
        // assert(canTransfer(_tokenId))
        // assert(mustBeValidToken(_tokenId))
        require(_to != address(0));

        // Find the FROM address
        address fromWithSubstitution = _tokenOwnerWithSubstitutions[_tokenId];
        address from = fromWithSubstitution;
        if (fromWithSubstitution == address(0)) {
            from = address(this);
        }

        // Take away from the FROM address
        // The Entriken algorithm for deleting from an indexed, unsorted array
        uint256 indexToDeleteWithSubstitution = _ownedTokensIndexWithSubstitutions[_tokenId];
        uint256 indexToDelete;
        if (indexToDeleteWithSubstitution == 0) {
            indexToDelete = _tokenId - 1;
        } else {
            indexToDelete = indexToDeleteWithSubstitution - 1;
        }
        if (indexToDelete != _tokensOfOwnerWithSubstitutions[from].length - 1) {
            uint256 lastNftWithSubstitution = _tokensOfOwnerWithSubstitutions[from][_tokensOfOwnerWithSubstitutions[from].length - 1];
            uint256 lastNft = lastNftWithSubstitution;
            if (lastNftWithSubstitution == 0) {
                // assert(from ==  address(0) || from == address(this));
                lastNft = _tokensOfOwnerWithSubstitutions[from].length;
            }
            _tokensOfOwnerWithSubstitutions[from][indexToDelete] = lastNft;
            _ownedTokensIndexWithSubstitutions[lastNft] = indexToDelete + 1;
        }
        delete _tokensOfOwnerWithSubstitutions[from][_tokensOfOwnerWithSubstitutions[from].length - 1]; // get gas back
        _tokensOfOwnerWithSubstitutions[from].length--;
        // Right now _ownedTokensIndexWithSubstitutions[_tokenId] is invalid, set it below based on the new owner

        // Give to the TO address
        _tokensOfOwnerWithSubstitutions[_to].push(_tokenId);
        _ownedTokensIndexWithSubstitutions[_tokenId] = (_tokensOfOwnerWithSubstitutions[_to].length - 1) + 1;

        // External processing
        _tokenOwnerWithSubstitutions[_tokenId] = _to;
        tokenApprovals[_tokenId] = address(0);
        emit Transfer(from, _to, _tokenId);
    }
    
    // PRIVATE STORAGE AND FUNCTIONS ///////////////////////////////////////////

    uint256 private constant TOTAL_SUPPLY = 10000; // SOLIDITY ISSUE #3356 make this immutable

    bytes4 private constant ERC721_RECEIVED = bytes4(keccak256("onERC721Received(address,uint256,bytes)"));
    
    /// @dev The owner of each NFT
    ///  If value == address(0), NFT is owned by address(this)
    ///  If value != address(0), NFT is owned by value
    ///  assert(This contract never assigns awnerhip to address(0) or destroys NFTs)
    ///  See commented out code in constructor, saves hella gas
    mapping (uint256 => address) private _tokenOwnerWithSubstitutions;

    /// @dev The list of NFTs owned by each address
    ///  Nomenclature: this[key][index] = value
    ///  If key != address(this) or value != 0, then value represents an NFT
    ///  If key == address(this) and value == 0, then index + 1 is the NFT
    ///  assert(0 is not a valid NFT)
    ///  See commented out code in constructor, saves hella gas
    mapping (address => uint256[]) private _tokensOfOwnerWithSubstitutions;
    
    /// @dev (Location + 1) of each NFT in its owner's list
    ///  Nomenclature: this[key] = value
    ///  If value != 0, _tokensOfOwnerWithSubstitutions[owner][value - 1] = nftId
    ///  If value == 0, _tokensOfOwnerWithSubstitutions[owner][key - 1] = nftId
    ///  assert(2**256-1 is not a valid NFT)
    ///  See commented out code in constructor, saves hella gas
    mapping (uint256 => uint256) private _ownedTokensIndexWithSubstitutions;

    // Due to implementation choices (no mint, no burn, contiguous NFT ids), it
    // is not necessary to keep an array of NFT ids nor where each NFT id is
    // located in that array.
    // address[] private nftIds;
    // mapping (uint256 => uint256) private nftIndexOfId;
    
    function SuNFT() internal {
        // Publish interfaces with ERC-165
        supportedInterfaces[0x6466353c] = true; // ERC721
        supportedInterfaces[0x5b5e139f] = true; // ERC721Metadata
        supportedInterfaces[0x780e9d63] = true; // ERC721Enumerable
        
        // The effect of substitution makes storing address(this), address(this)
        // ..., address(this) for a total of TOTAL_SUPPLY times unnecessary at
        // deployment time
        // for (uint256 i = 1; i <= TOTAL_SUPPLY; i++) {
        //     _tokenOwnerWithSubstitutions[i] = address(this);
        // }

        // The effect of substitution makes storing 1, 2, ..., TOTAL_SUPPLY
        // unnecessary at deployment time
        _tokensOfOwnerWithSubstitutions[address(this)].length = TOTAL_SUPPLY;
        // for (uint256 i = 0; i < TOTAL_SUPPLY; i++) {
        //     _tokensOfOwnerWithSubstitutions[address(this)][i] = i + 1;
        // }
        // for (uint256 i = 1; i <= TOTAL_SUPPLY; i++) {
        //     _ownedTokensIndexWithSubstitutions[i] = i - 1;
        // }
    }
    
    /// @dev Actually perform the safeTransferFrom
    function _safeTransferFrom(address _from, address _to, uint256 _tokenId, bytes data)
        private
        mustBeValidToken(_tokenId)
        canTransfer(_tokenId)
    {
        address owner = _tokenOwnerWithSubstitutions[_tokenId];
        // Handle substitutions
        if (owner == address(0)) {
            owner = address(this);
        }
        require(owner == _from);
        require(_to != address(0));
        _transfer(_tokenId, _to);
        
        // Do the callback after everything is done to avoid reentrancy attack
        uint256 codeSize;
        assembly { codeSize := extcodesize(_to) }
        if (codeSize == 0) {
            return;
        }
        bytes4 retval = ERC721TokenReceiver(_to).onERC721Received(_from, _tokenId, data);
        require(retval == ERC721_RECEIVED);
    }    
}

/* SuOperation.sol ************************************************************/

/// @title The features that square owners can use
/// @author William Entriken (https://phor.net)
/// @dev See SuMain contract documentation for detail on how contracts interact.
contract SuOperation is SuNFT {
    /// @dev The personalization of a square has changed
    event Personalized(uint256 _nftId);
    
    /// @dev The main SuSquare struct. The owner may set these properties, subject
    ///  subject to certain rules. The actual 10x10 image is rendered on our
    ///  website using this data.
    struct SuSquare {
        /// @dev This increments on each update
        uint256 version;
        
        /// @dev A 10x10 pixel image, stored 8-bit RGB values from left-to-right
        ///  and top-to-bottom order (normal English reading order). So it is
        ///  exactly 300 bytes. Or it is an empty array.
        ///  So the first byte is the red channel for the top-left pixel, then
        ///  the blue, then the green, and then next is the red channel for the
        ///  pixel to the right of the first pixel.
        bytes rgbData;

        /// @dev The title of this square, at most 64 bytes,
        string title;

        /// @dev The URL of this square, at most 100 bytes, or empty string
        string href;
    }

    /// @notice All the Su Squares that ever exist or will exist. Each Su Square
    ///  represents a square on our webpage in a 100x100 grid. The squares are
    ///  arranged in left-to-right, top-to-bottom order. In other words, normal
    ///  English reading order. So suSquares[1] is the top-left location and
    ///  suSquares[100] is the top-right location. And suSquares[101] is
    ///  directly below suSquares[1]. 
    /// @dev There is no suSquares[0] -- that is an unused array index.
    SuSquare[10001] public suSquares;
    
    /// @notice Update the contents of your square, the first 3 personalizations
    ///  for a square are free then cost 10 finney (0.01 ether) each
    /// @param _squareId The top-left is 1, to its right is 2, ..., top-right is
    ///  100 and then 101 is below 1... the last one at bottom-right is 10000
    /// @param _squareId A 10x10 image for your square, in 8-bit RGB words
    ///  ordered like the squares are ordered. See Imagemagick's command
    ///  convert -size 10x10 -depth 8 in.rgb out.png
    /// @param _title A description of your square (max 64 bytes UTF-8)
    /// @param _href A hyperlink for your square (max 96 bytes)
    function personalizeSquare(
        uint256 _squareId,
        bytes _rgbData,
        string _title,
        string _href
    )
        external
        onlyOwnerOf(_squareId)
        payable
    {
        require(bytes(_title).length <= 64);
        require(bytes(_href).length <= 96);
        require(_rgbData.length == 300);
        suSquares[_squareId].version++;
        suSquares[_squareId].rgbData = _rgbData;
        suSquares[_squareId].title = _title;
        suSquares[_squareId].href = _href;
        if (suSquares[_squareId].version > 3) {
            require(msg.value == 10 finney);
        }
        emit Personalized(_squareId);
    }
}

/* SuPromo.sol ****************************************************************/

/// @title A limited pre-sale and promotional giveaway.
/// @author William Entriken (https://phor.net)
/// @dev See SuMain contract documentation for detail on how contracts interact.
contract SuPromo is AccessControl, SuNFT {
    uint256 constant PROMO_CREATION_LIMIT = 5000;

    /// @notice How many promo squares were granted
    uint256 public promoCreatedCount;

    /// @notice BEWARE, this does not use a safe transfer mechanism!
    ///  You must manually check the receiver can accept NFTs
    function grantToken(uint256 _tokenId, address _newOwner)
        external
        onlyOperatingOfficer
        mustBeValidToken(_tokenId)
        mustBeOwnedByThisContract(_tokenId)
    {
        require(promoCreatedCount < PROMO_CREATION_LIMIT);
        promoCreatedCount++;
        _transfer(_tokenId, _newOwner);
    }
}

/* SuVending.sol **************************************************************/

/// @title A token vending machine
/// @author William Entriken (https://phor.net)
/// @dev See SuMain contract documentation for detail on how contracts interact.
contract SuVending is SuNFT {
    uint256 constant SALE_PRICE = 500 finney; // 0.5 ether

    /// @notice The price is always 0.5 ether, and you can buy any available square
    ///  Be sure you are calling this from a regular account (not a smart contract)
    ///  or if you are calling from a smart contract, make sure it can use
    ///  ERC-721 non-fungible tokens
    function purchase(uint256 _nftId)
        external
        payable
        mustBeValidToken(_nftId)
        mustBeOwnedByThisContract(_nftId)
    {
        require(msg.value == SALE_PRICE);
        _transfer(_nftId, msg.sender);
    }
}

/* SuMain.sol *****************************************************************/

/// @title The features that deed owners can use
/// @author William Entriken (https://phor.net)
/// @dev See SuMain contract documentation for detail on how contracts interact.
contract SuMain is AccessControl, SuNFT, SuOperation, SuVending, SuPromo {
    function SuMain() public {
    }
}

Contract Security Audit

Contract ABI

API
[{"constant":true,"inputs":[],"name":"executiveOfficerAddress","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"interfaceID","type":"bytes4"}],"name":"supportsInterface","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"promoCreatedCount","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"name","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[{"name":"_tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_approved","type":"address"},{"name":"_tokenId","type":"uint256"}],"name":"approve","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":false,"inputs":[{"name":"_tokenId","type":"uint256"},{"name":"_newOwner","type":"address"}],"name":"grantToken","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"totalSupply","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_to","type":"address"},{"name":"_tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":false,"inputs":[{"name":"_operatingOfficerAddress","type":"address"}],"name":"setOperatingOfficer","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_owner","type":"address"},{"name":"_index","type":"uint256"}],"name":"tokenOfOwnerByIndex","outputs":[{"name":"_tokenId","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_to","type":"address"},{"name":"_tokenId","type":"uint256"}],"name":"safeTransferFrom","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[{"name":"_index","type":"uint256"}],"name":"tokenByIndex","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[],"name":"withdrawBalance","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_tokenId","type":"uint256"}],"name":"ownerOf","outputs":[{"name":"_owner","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"operatingOfficerAddress","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"_owner","type":"address"}],"name":"balanceOf","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_squareId","type":"uint256"},{"name":"_rgbData","type":"bytes"},{"name":"_title","type":"string"},{"name":"_href","type":"string"}],"name":"personalizeSquare","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[],"name":"symbol","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":false,"inputs":[{"name":"_operator","type":"address"},{"name":"_approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"financialOfficerAddress","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_from","type":"address"},{"name":"_to","type":"address"},{"name":"_tokenId","type":"uint256"},{"name":"data","type":"bytes"}],"name":"safeTransferFrom","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[{"name":"_tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"name":"_tokenURI","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_financialOfficerAddress","type":"address"}],"name":"setFinancialOfficer","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_owner","type":"address"},{"name":"_operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_executiveOfficerAddress","type":"address"}],"name":"setExecutiveOfficer","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"name":"_nftId","type":"uint256"}],"name":"purchase","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[{"name":"","type":"uint256"}],"name":"suSquares","outputs":[{"name":"version","type":"uint256"},{"name":"rgbData","type":"bytes"},{"name":"title","type":"string"},{"name":"href","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"name":"_nftId","type":"uint256"}],"name":"Personalized","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"_from","type":"address"},{"indexed":true,"name":"_to","type":"address"},{"indexed":false,"name":"_tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"_owner","type":"address"},{"indexed":true,"name":"_approved","type":"address"},{"indexed":false,"name":"_tokenId","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"_owner","type":"address"},{"indexed":true,"name":"_operator","type":"address"},{"indexed":false,"name":"_approved","type":"bool"}],"name":"ApprovalForAll","type":"event"}]

606060405234156200001057600080fd5b60008054600160a060020a03191633600160a060020a039081169190911782557f28b0ef64f7e82d3b26f3fd404bd0151552f792965f39c29ae82c0a78df67af9c805460ff1990811660019081179092557fd1937f36823354dfe8fc4fecdaaf31c1d82bafb512cc0f14d076e0ce399f798680548216831790557fcca39824a677cee72cd3539fc56c0e5a676a28b60617ea00a9d38305722c8b6480548216831790557f785e4d925c4778965a1107f0c202069d496d641ab5dd08a13bd2b783950e105f805490911690911790553016815260076020526040902061271090620000fb908262000102565b5062000152565b8154818355818115116200012957600083815260209020620001299181019083016200012e565b505050565b6200014f91905b808211156200014b576000815560010162000135565b5090565b90565b61196780620001626000396000f3006060604052600436106101685763ffffffff7c010000000000000000000000000000000000000000000000000000000060003504166215be71811461016d57806301ffc9a71461019c57806305e45546146101d057806306fdde03146101f5578063081812fc1461027f578063095ea7b314610295578063133252a6146102ae57806318160ddd146102d057806323b872dd146102e35780632aad292e146103005780632f745c591461031f57806342842e0e146103415780634f6ccce71461035e5780635fd8c710146103745780636352211e146103875780636bfa5edc1461039d57806370a08231146103b057806376f14c98146103cf57806395d89b41146103fe578063a22cb46514610411578063abe088a714610435578063b88d4fde14610448578063c87b56dd14610474578063d978a0d31461048a578063e985e9c5146104a9578063ec13df6b146104ce578063efef39a1146104ed578063ffa6ab44146104f8575b600080fd5b341561017857600080fd5b61018061065f565b604051600160a060020a03909116815260200160405180910390f35b34156101a757600080fd5b6101bc600160e060020a03196004351661066e565b604051901515815260200160405180910390f35b34156101db57600080fd5b6101e36106a7565b60405190815260200160405180910390f35b341561020057600080fd5b6102086106ae565b60405160208082528190810183818151815260200191508051906020019080838360005b8381101561024457808201518382015260200161022c565b50505050905090810190601f1680156102715780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b341561028a57600080fd5b6101806004356106f0565b6102ac600160a060020a0360043516602435610732565b005b34156102b957600080fd5b6102ac600435600160a060020a036024351661082d565b34156102db57600080fd5b6101e36108f7565b6102ac600160a060020a03600435811690602435166044356108fd565b341561030b57600080fd5b6102ac600160a060020a03600435166109ff565b341561032a57600080fd5b6101e3600160a060020a0360043516602435610a5e565b6102ac600160a060020a0360043581169060243516604435610af5565b341561036957600080fd5b6101e3600435610b14565b341561037f57600080fd5b6102ac610b2b565b341561039257600080fd5b610180600435610b81565b34156103a857600080fd5b610180610bcb565b34156103bb57600080fd5b6101e3600160a060020a0360043516610bda565b6102ac600480359060248035808201929081013591604435808201929081013591606435908101910135610c0d565b341561040957600080fd5b610208610d55565b341561041c57600080fd5b6102ac600160a060020a03600435166024351515610d96565b341561044057600080fd5b610180610e06565b6102ac600160a060020a0360048035821691602480359091169160443591606435908101910135610e15565b341561047f57600080fd5b610208600435610e50565b341561049557600080fd5b6102ac600160a060020a0360043516610fee565b34156104b457600080fd5b6101bc600160a060020a036004358116906024351661104d565b34156104d957600080fd5b6102ac600160a060020a036004351661107b565b6102ac6004356110da565b341561050357600080fd5b61050e600435611180565b60405180858152602001806020018060200180602001848103845287818151815260200191508051906020019080838360005b83811015610559578082015183820152602001610541565b50505050905090810190601f1680156105865780820380516001836020036101000a031916815260200191505b50848103835286818151815260200191508051906020019080838360005b838110156105bc5780820151838201526020016105a4565b50505050905090810190601f1680156105e95780820380516001836020036101000a031916815260200191505b50848103825285818151815260200191508051906020019080838360005b8381101561061f578082015183820152602001610607565b50505050905090810190601f16801561064c5780820380516001836020036101000a031916815260200191505b5097505050505050505060405180910390f35b600054600160a060020a031681565b600160e060020a0319811660009081526003602052604081205460ff1680156106a15750600160e060020a031980831614155b92915050565b619c4d5481565b6106b6611871565b60408051908101604052600a81527f5375205371756172657300000000000000000000000000000000000000000000602082015290505b90565b6000816001811015801561070657506127108111155b151561071157600080fd5b600083815260046020526040902054600160a060020a031691505b50919050565b6000818152600660205260408120548290600160a060020a039081169033168114806107845750600160a060020a038082166000908152600560209081526040808320339094168352929052205460ff165b151561078f57600080fd5b600084815260066020526040902054600160a060020a031692508215156107b4573092505b60008481526004602052604090819020805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0388811691821790925591908516907f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9259087905190815260200160405180910390a35050505050565b60025433600160a060020a0390811691161461084857600080fd5b816001811015801561085c57506127108111155b151561086757600080fd5b8260006001821015801561087d57506127108211155b151561088857600080fd5b50600081815260066020526040902054600160a060020a03168015806108bf575030600160a060020a031681600160a060020a0316145b15156108ca57600080fd5b619c4d5461138890106108dc57600080fd5b619c4d805460010190556108f0858561137c565b5050505050565b61271090565b6000816001811015801561091357506127108111155b151561091e57600080fd5b6000838152600660205260409020548390600160a060020a03908116903316811480610964575060008281526004602052604090205433600160a060020a039081169116145b8061098f5750600160a060020a033316600090815260056020908152604080832090915290205460ff165b151561099a57600080fd5b600085815260066020526040902054600160a060020a031693508315156109bf573093505b600160a060020a03848116908816146109d757600080fd5b600160a060020a03861615156109ec57600080fd5b6109f6858761137c565b50505050505050565b60005433600160a060020a03908116911614610a1a57600080fd5b600160a060020a0381161515610a2f57600080fd5b6002805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b6000600160a060020a0383161515610a7557600080fd5b600160a060020a0383166000908152600760205260409020548210610a9957600080fd5b600160a060020a0383166000908152600760205260409020805483908110610abd57fe5b906000526020600020900154905030600160a060020a031683600160a060020a031614156106a1578015156106a15750600101919050565b610b0f8383836020604051908101604052600081526115eb565b505050565b60006127108210610b2457600080fd5b5060010190565b60015433600160a060020a03908116911614610b4657600080fd5b600154600160a060020a039081169030163180156108fc0290604051600060405180830381858888f193505050501515610b7f57600080fd5b565b60008160018110158015610b9757506127108111155b1515610ba257600080fd5b600083815260066020526040902054600160a060020a0316915081151561072c57503092915050565b600254600160a060020a031681565b6000600160a060020a0382161515610bf157600080fd5b50600160a060020a031660009081526007602052604090205490565b6000878152600660205260409020548790600160a060020a039081169033168114610c3757600080fd5b6040851115610c4557600080fd5b6060831115610c5357600080fd5b61012c8714610c6157600080fd5b6009896127118110610c6f57fe5b6004020180546001019055878760098b6127118110610c8a57fe5b600402016001019190610c9e929190611883565b50858560098b6127118110610caf57fe5b600402016002019190610cc3929190611883565b50838360098b6127118110610cd457fe5b600402016003019190610ce8929190611883565b50600360098a6127118110610cf957fe5b60040201541115610d1757662386f26fc100003414610d1757600080fd5b7f95820ed330d949e85d003e7c553aa060e3cdffc1f8af4eb8c9cf988dca7878328960405190815260200160405180910390a1505050505050505050565b610d5d611871565b60408051908101604052600281527f53550000000000000000000000000000000000000000000000000000000000006020820152905090565b33600160a060020a0390811660008181526005602090815260408083209487168084529490915290819020805460ff19168515151790557f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c3190849051901515815260200160405180910390a35050565b600154600160a060020a031681565b6108f085858585858080601f0160208091040260200160405190810160405281815292919060208401838380828437506115eb945050505050565b610e58611871565b610e60611871565b8260018110158015610e7457506127108111155b1515610e7f57600080fd5b60606040519081016040908152602b82527f68747470733a2f2f74656e74686f7573616e6473752e636f6d2f65726337323160208301527f2f30303030302e6a736f6e000000000000000000000000000000000000000000908201529250829150600a61271085040660300160f860020a0282602181518110610efe57fe5b906020010190600160f860020a031916908160001a905350600a6103e885040660300160f860020a0282602281518110610f3457fe5b906020010190600160f860020a031916908160001a905350600a606485040660300160f860020a0282602381518110610f6957fe5b906020010190600160f860020a031916908160001a905350600a8085040660300160f860020a0282602481518110610f9d57fe5b906020010190600160f860020a031916908160001a905350600a840660300160f860020a0282602581518110610fcf57fe5b906020010190600160f860020a031916908160001a9053505050919050565b60005433600160a060020a0390811691161461100957600080fd5b600160a060020a038116151561101e57600080fd5b6001805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b600160a060020a03918216600090815260056020908152604080832093909416825291909152205460ff1690565b60005433600160a060020a0390811691161461109657600080fd5b600160a060020a03811615156110ab57600080fd5b6000805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b80600181101580156110ee57506127108111155b15156110f957600080fd5b8160006001821015801561110f57506127108211155b151561111a57600080fd5b50600081815260066020526040902054600160a060020a0316801580611151575030600160a060020a031681600160a060020a0316145b151561115c57600080fd5b346706f05b59d3b200001461117057600080fd5b61117a843361137c565b50505050565b600981612711811061118e57fe5b60040201600091509050806000015490806001018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156112365780601f1061120b57610100808354040283529160200191611236565b820191906000526020600020905b81548152906001019060200180831161121957829003601f168201915b505050505090806002018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156112d45780601f106112a9576101008083540402835291602001916112d4565b820191906000526020600020905b8154815290600101906020018083116112b757829003601f168201915b505050505090806003018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156113725780601f1061134757610100808354040283529160200191611372565b820191906000526020600020905b81548152906001019060200180831161135557829003601f168201915b5050505050905084565b60008080808080600160a060020a038716151561139857600080fd5b600088815260066020526040902054600160a060020a031695508594508415156113c0573094505b60008881526008602052604090205493508315156113e3576001880392506113ea565b6001840392505b600160a060020a0385166000908152600760205260409020546000190183146114b557600160a060020a03851660009081526007602052604090208054600019810190811061143557fe5b9060005260206000209001549150819050816000141561146a5750600160a060020a0384166000908152600760205260409020545b600160a060020a038516600090815260076020526040902080548291908590811061149157fe5b60009182526020808320909101929092558281526008909152604090206001840190555b600160a060020a0385166000908152600760205260409020805460001981019081106114dd57fe5b60009182526020808320909101829055600160a060020a03871682526007905260409020805490611512906000198301611901565b50600160a060020a038716600090815260076020526040902080546001810161153b8382611901565b5060009182526020808320919091018a9055600160a060020a03808a16808452600783526040808520548d8652600885528186205560068452808520805473ffffffffffffffffffffffffffffffffffffffff19908116841790915560049094529384902080549093169092559091908716907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908b905190815260200160405180910390a35050505050505050565b6000806000846001811015801561160457506127108111155b151561160f57600080fd5b6000868152600660205260409020548690600160a060020a03908116903316811480611655575060008281526004602052604090205433600160a060020a039081169116145b806116805750600160a060020a033316600090815260056020908152604080832090915290205460ff165b151561168b57600080fd5b600088815260066020526040902054600160a060020a031695508515156116b0573095505b600160a060020a03868116908b16146116c857600080fd5b600160a060020a03891615156116dd57600080fd5b6116e7888a61137c565b883b94508415156116f757611865565b88600160a060020a031663f0b9e5ba8b8a8a6040518463ffffffff167c01000000000000000000000000000000000000000000000000000000000281526004018084600160a060020a0316600160a060020a0316815260200183815260200180602001828103825283818151815260200191508051906020019080838360005b8381101561178f578082015183820152602001611777565b50505050905090810190601f1680156117bc5780820380516001836020036101000a031916815260200191505b50945050505050602060405180830381600087803b15156117dc57600080fd5b5af115156117e957600080fd5b5050506040518051905093506040517f6f6e455243373231526563656976656428616464726573732c75696e7432353681527f2c627974657329000000000000000000000000000000000000000000000000006020820152602701604051908190039020600160e060020a031985811691161461186557600080fd5b50505050505050505050565b60206040519081016040526000815290565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106118c45782800160ff198235161785556118f1565b828001600101855582156118f1579182015b828111156118f15782358255916020019190600101906118d6565b506118fd929150611921565b5090565b815481835581811511610b0f57600083815260209020610b0f9181019083015b6106ed91905b808211156118fd57600081556001016119275600a165627a7a723058201ea9aaee21e636445f4dc5d5326f064b32923cb04128721c5842d5c66670a72f0029

Deployed Bytecode

0x6060604052600436106101685763ffffffff7c010000000000000000000000000000000000000000000000000000000060003504166215be71811461016d57806301ffc9a71461019c57806305e45546146101d057806306fdde03146101f5578063081812fc1461027f578063095ea7b314610295578063133252a6146102ae57806318160ddd146102d057806323b872dd146102e35780632aad292e146103005780632f745c591461031f57806342842e0e146103415780634f6ccce71461035e5780635fd8c710146103745780636352211e146103875780636bfa5edc1461039d57806370a08231146103b057806376f14c98146103cf57806395d89b41146103fe578063a22cb46514610411578063abe088a714610435578063b88d4fde14610448578063c87b56dd14610474578063d978a0d31461048a578063e985e9c5146104a9578063ec13df6b146104ce578063efef39a1146104ed578063ffa6ab44146104f8575b600080fd5b341561017857600080fd5b61018061065f565b604051600160a060020a03909116815260200160405180910390f35b34156101a757600080fd5b6101bc600160e060020a03196004351661066e565b604051901515815260200160405180910390f35b34156101db57600080fd5b6101e36106a7565b60405190815260200160405180910390f35b341561020057600080fd5b6102086106ae565b60405160208082528190810183818151815260200191508051906020019080838360005b8381101561024457808201518382015260200161022c565b50505050905090810190601f1680156102715780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b341561028a57600080fd5b6101806004356106f0565b6102ac600160a060020a0360043516602435610732565b005b34156102b957600080fd5b6102ac600435600160a060020a036024351661082d565b34156102db57600080fd5b6101e36108f7565b6102ac600160a060020a03600435811690602435166044356108fd565b341561030b57600080fd5b6102ac600160a060020a03600435166109ff565b341561032a57600080fd5b6101e3600160a060020a0360043516602435610a5e565b6102ac600160a060020a0360043581169060243516604435610af5565b341561036957600080fd5b6101e3600435610b14565b341561037f57600080fd5b6102ac610b2b565b341561039257600080fd5b610180600435610b81565b34156103a857600080fd5b610180610bcb565b34156103bb57600080fd5b6101e3600160a060020a0360043516610bda565b6102ac600480359060248035808201929081013591604435808201929081013591606435908101910135610c0d565b341561040957600080fd5b610208610d55565b341561041c57600080fd5b6102ac600160a060020a03600435166024351515610d96565b341561044057600080fd5b610180610e06565b6102ac600160a060020a0360048035821691602480359091169160443591606435908101910135610e15565b341561047f57600080fd5b610208600435610e50565b341561049557600080fd5b6102ac600160a060020a0360043516610fee565b34156104b457600080fd5b6101bc600160a060020a036004358116906024351661104d565b34156104d957600080fd5b6102ac600160a060020a036004351661107b565b6102ac6004356110da565b341561050357600080fd5b61050e600435611180565b60405180858152602001806020018060200180602001848103845287818151815260200191508051906020019080838360005b83811015610559578082015183820152602001610541565b50505050905090810190601f1680156105865780820380516001836020036101000a031916815260200191505b50848103835286818151815260200191508051906020019080838360005b838110156105bc5780820151838201526020016105a4565b50505050905090810190601f1680156105e95780820380516001836020036101000a031916815260200191505b50848103825285818151815260200191508051906020019080838360005b8381101561061f578082015183820152602001610607565b50505050905090810190601f16801561064c5780820380516001836020036101000a031916815260200191505b5097505050505050505060405180910390f35b600054600160a060020a031681565b600160e060020a0319811660009081526003602052604081205460ff1680156106a15750600160e060020a031980831614155b92915050565b619c4d5481565b6106b6611871565b60408051908101604052600a81527f5375205371756172657300000000000000000000000000000000000000000000602082015290505b90565b6000816001811015801561070657506127108111155b151561071157600080fd5b600083815260046020526040902054600160a060020a031691505b50919050565b6000818152600660205260408120548290600160a060020a039081169033168114806107845750600160a060020a038082166000908152600560209081526040808320339094168352929052205460ff165b151561078f57600080fd5b600084815260066020526040902054600160a060020a031692508215156107b4573092505b60008481526004602052604090819020805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0388811691821790925591908516907f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9259087905190815260200160405180910390a35050505050565b60025433600160a060020a0390811691161461084857600080fd5b816001811015801561085c57506127108111155b151561086757600080fd5b8260006001821015801561087d57506127108211155b151561088857600080fd5b50600081815260066020526040902054600160a060020a03168015806108bf575030600160a060020a031681600160a060020a0316145b15156108ca57600080fd5b619c4d5461138890106108dc57600080fd5b619c4d805460010190556108f0858561137c565b5050505050565b61271090565b6000816001811015801561091357506127108111155b151561091e57600080fd5b6000838152600660205260409020548390600160a060020a03908116903316811480610964575060008281526004602052604090205433600160a060020a039081169116145b8061098f5750600160a060020a033316600090815260056020908152604080832090915290205460ff165b151561099a57600080fd5b600085815260066020526040902054600160a060020a031693508315156109bf573093505b600160a060020a03848116908816146109d757600080fd5b600160a060020a03861615156109ec57600080fd5b6109f6858761137c565b50505050505050565b60005433600160a060020a03908116911614610a1a57600080fd5b600160a060020a0381161515610a2f57600080fd5b6002805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b6000600160a060020a0383161515610a7557600080fd5b600160a060020a0383166000908152600760205260409020548210610a9957600080fd5b600160a060020a0383166000908152600760205260409020805483908110610abd57fe5b906000526020600020900154905030600160a060020a031683600160a060020a031614156106a1578015156106a15750600101919050565b610b0f8383836020604051908101604052600081526115eb565b505050565b60006127108210610b2457600080fd5b5060010190565b60015433600160a060020a03908116911614610b4657600080fd5b600154600160a060020a039081169030163180156108fc0290604051600060405180830381858888f193505050501515610b7f57600080fd5b565b60008160018110158015610b9757506127108111155b1515610ba257600080fd5b600083815260066020526040902054600160a060020a0316915081151561072c57503092915050565b600254600160a060020a031681565b6000600160a060020a0382161515610bf157600080fd5b50600160a060020a031660009081526007602052604090205490565b6000878152600660205260409020548790600160a060020a039081169033168114610c3757600080fd5b6040851115610c4557600080fd5b6060831115610c5357600080fd5b61012c8714610c6157600080fd5b6009896127118110610c6f57fe5b6004020180546001019055878760098b6127118110610c8a57fe5b600402016001019190610c9e929190611883565b50858560098b6127118110610caf57fe5b600402016002019190610cc3929190611883565b50838360098b6127118110610cd457fe5b600402016003019190610ce8929190611883565b50600360098a6127118110610cf957fe5b60040201541115610d1757662386f26fc100003414610d1757600080fd5b7f95820ed330d949e85d003e7c553aa060e3cdffc1f8af4eb8c9cf988dca7878328960405190815260200160405180910390a1505050505050505050565b610d5d611871565b60408051908101604052600281527f53550000000000000000000000000000000000000000000000000000000000006020820152905090565b33600160a060020a0390811660008181526005602090815260408083209487168084529490915290819020805460ff19168515151790557f17307eab39ab6107e8899845ad3d59bd9653f200f220920489ca2b5937696c3190849051901515815260200160405180910390a35050565b600154600160a060020a031681565b6108f085858585858080601f0160208091040260200160405190810160405281815292919060208401838380828437506115eb945050505050565b610e58611871565b610e60611871565b8260018110158015610e7457506127108111155b1515610e7f57600080fd5b60606040519081016040908152602b82527f68747470733a2f2f74656e74686f7573616e6473752e636f6d2f65726337323160208301527f2f30303030302e6a736f6e000000000000000000000000000000000000000000908201529250829150600a61271085040660300160f860020a0282602181518110610efe57fe5b906020010190600160f860020a031916908160001a905350600a6103e885040660300160f860020a0282602281518110610f3457fe5b906020010190600160f860020a031916908160001a905350600a606485040660300160f860020a0282602381518110610f6957fe5b906020010190600160f860020a031916908160001a905350600a8085040660300160f860020a0282602481518110610f9d57fe5b906020010190600160f860020a031916908160001a905350600a840660300160f860020a0282602581518110610fcf57fe5b906020010190600160f860020a031916908160001a9053505050919050565b60005433600160a060020a0390811691161461100957600080fd5b600160a060020a038116151561101e57600080fd5b6001805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b600160a060020a03918216600090815260056020908152604080832093909416825291909152205460ff1690565b60005433600160a060020a0390811691161461109657600080fd5b600160a060020a03811615156110ab57600080fd5b6000805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b80600181101580156110ee57506127108111155b15156110f957600080fd5b8160006001821015801561110f57506127108211155b151561111a57600080fd5b50600081815260066020526040902054600160a060020a0316801580611151575030600160a060020a031681600160a060020a0316145b151561115c57600080fd5b346706f05b59d3b200001461117057600080fd5b61117a843361137c565b50505050565b600981612711811061118e57fe5b60040201600091509050806000015490806001018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156112365780601f1061120b57610100808354040283529160200191611236565b820191906000526020600020905b81548152906001019060200180831161121957829003601f168201915b505050505090806002018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156112d45780601f106112a9576101008083540402835291602001916112d4565b820191906000526020600020905b8154815290600101906020018083116112b757829003601f168201915b505050505090806003018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156113725780601f1061134757610100808354040283529160200191611372565b820191906000526020600020905b81548152906001019060200180831161135557829003601f168201915b5050505050905084565b60008080808080600160a060020a038716151561139857600080fd5b600088815260066020526040902054600160a060020a031695508594508415156113c0573094505b60008881526008602052604090205493508315156113e3576001880392506113ea565b6001840392505b600160a060020a0385166000908152600760205260409020546000190183146114b557600160a060020a03851660009081526007602052604090208054600019810190811061143557fe5b9060005260206000209001549150819050816000141561146a5750600160a060020a0384166000908152600760205260409020545b600160a060020a038516600090815260076020526040902080548291908590811061149157fe5b60009182526020808320909101929092558281526008909152604090206001840190555b600160a060020a0385166000908152600760205260409020805460001981019081106114dd57fe5b60009182526020808320909101829055600160a060020a03871682526007905260409020805490611512906000198301611901565b50600160a060020a038716600090815260076020526040902080546001810161153b8382611901565b5060009182526020808320919091018a9055600160a060020a03808a16808452600783526040808520548d8652600885528186205560068452808520805473ffffffffffffffffffffffffffffffffffffffff19908116841790915560049094529384902080549093169092559091908716907fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef908b905190815260200160405180910390a35050505050505050565b6000806000846001811015801561160457506127108111155b151561160f57600080fd5b6000868152600660205260409020548690600160a060020a03908116903316811480611655575060008281526004602052604090205433600160a060020a039081169116145b806116805750600160a060020a033316600090815260056020908152604080832090915290205460ff165b151561168b57600080fd5b600088815260066020526040902054600160a060020a031695508515156116b0573095505b600160a060020a03868116908b16146116c857600080fd5b600160a060020a03891615156116dd57600080fd5b6116e7888a61137c565b883b94508415156116f757611865565b88600160a060020a031663f0b9e5ba8b8a8a6040518463ffffffff167c01000000000000000000000000000000000000000000000000000000000281526004018084600160a060020a0316600160a060020a0316815260200183815260200180602001828103825283818151815260200191508051906020019080838360005b8381101561178f578082015183820152602001611777565b50505050905090810190601f1680156117bc5780820380516001836020036101000a031916815260200191505b50945050505050602060405180830381600087803b15156117dc57600080fd5b5af115156117e957600080fd5b5050506040518051905093506040517f6f6e455243373231526563656976656428616464726573732c75696e7432353681527f2c627974657329000000000000000000000000000000000000000000000000006020820152602701604051908190039020600160e060020a031985811691161461186557600080fd5b50505050505050505050565b60206040519081016040526000815290565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106118c45782800160ff198235161785556118f1565b828001600101855582156118f1579182015b828111156118f15782358255916020019190600101906118d6565b506118fd929150611921565b5090565b815481835581811511610b0f57600083815260209020610b0f9181019083015b6106ed91905b808211156118fd57600081556001016119275600a165627a7a723058201ea9aaee21e636445f4dc5d5326f064b32923cb04128721c5842d5c66670a72f0029

Swarm Source

bzzr://1ea9aaee21e636445f4dc5d5326f064b32923cb04128721c5842d5c66670a72f
Loading...
Loading
Loading...
Loading
[ Download: CSV Export  ]
[ Download: CSV Export  ]

A token is a representation of an on-chain or off-chain asset. The token page shows information such as price, total supply, holders, transfers and social links. Learn more about this page in our Knowledge Base.