Contract Overview
Balance: 0 Ether
Ether Value: $0
Transactions: 4 txns
Misc:
Address Watch: Add To Watch List
Contract Creator: 0x5c3070137783e35f6b7d02fdb8c31ca5a475df53at txn 0x92fc0ad363aa83c837b00e3ad10b2ddfbc0a980f7b435e09a15873ca5fa89c72
Token Balance:
 Latest 4 txns

TxHash Age From To Value [TxFee]
0x8205736857c3fbf97c7ebf54de0708fc5071bd5ba95cbb3b97053361e28c39334 hrs 38 mins ago0x9610751e6bfdfe87a1c2cbfb040b612ae974e1ac  IN   0x30db195677484f1afc0b2e804eada1d2b3a17ed30 Ether0.000129138
0xc99aaf23a3faf269e1a4f7e76fc5e780fc6a27518d3d9c0875e17a3d3e9d3c6770 days 6 hrs ago0xde42b8f8421141b7d9c697c4111918f04fb19d9b  IN   0x30db195677484f1afc0b2e804eada1d2b3a17ed30.01 Ether0.00063
0x0994be4046c5c26e135daca10f8068ef628de9352dc47347b72de3978bae5fcd127 days 12 hrs ago0x9610751e6bfdfe87a1c2cbfb040b612ae974e1ac  IN   0x30db195677484f1afc0b2e804eada1d2b3a17ed30.5 Ether0.0004026495
0x0d92b7c1875ff0a9d722bcef3403117c64b2cd1e190d9c61eb52b747131ce09c127 days 13 hrs ago0xeb4046810260201f895ff652a011bc6d941af033  IN   0x30db195677484f1afc0b2e804eada1d2b3a17ed30.5 Ether0.0002491665
[ Download CSV Export  ] 
 Internal Transactions as a result of Contract Execution
 Latest 2 Internal Transactions

ParentTxHash Block Age From To Value
0x8205736857c3fbf97c7ebf54de0708fc5071bd5ba95cbb3b97053361e28c393369099534 hrs 38 mins ago0x30db195677484f1afc0b2e804eada1d2b3a17ed30x9610751e6bfdfe87a1c2cbfb040b612ae974e1ac0.5 Ether
0x92fc0ad363aa83c837b00e3ad10b2ddfbc0a980f7b435e09a15873ca5fa89c726097773134 days 12 hrs ago0x5c3070137783e35f6b7d02fdb8c31ca5a475df53  Contract Creation0 Ether
[ Download CSV Export  ] 
Warning: The Compiled Contract might be susceptible to ExpExponentCleanup (medium/high-severity), EventStructWrongData (very low-severity) SolidityCompiler Bugs.

Contract Source Code Verified (Exact Match)
Contract Name: WgdSale
Compiler Text: v0.4.24+commit.e67f0147
Optimization Enabled: Yes
Runs (Optimiser):  200



  Contract Source Code   Find Similiar Contracts

pragma solidity ^0.4.24;

/**
 * Powered by Daonomic (https://daonomic.io)
 */

/**
 * @title ERC20Basic
 * @dev Simpler version of ERC20 interface
 * See https://github.com/ethereum/EIPs/issues/179
 */
contract ERC20Basic {
  function totalSupply() public view returns (uint256);
  function balanceOf(address who) public view returns (uint256);
  function transfer(address to, uint256 value) public returns (bool);
  event Transfer(address indexed from, address indexed to, uint256 value);
}

/**
 * @title ERC20 interface
 * @dev see https://github.com/ethereum/EIPs/issues/20
 */
contract ERC20 is ERC20Basic {
  function allowance(address owner, address spender)
    public view returns (uint256);

  function transferFrom(address from, address to, uint256 value)
    public returns (bool);

  function approve(address spender, uint256 value) public returns (bool);
  event Approval(
    address indexed owner,
    address indexed spender,
    uint256 value
  );
}

/**
 * @title SafeERC20
 * @dev Wrappers around ERC20 operations that throw on failure.
 * To use this library you can add a `using SafeERC20 for ERC20;` statement to your contract,
 * which allows you to call the safe operations as `token.safeTransfer(...)`, etc.
 */
library SafeERC20 {
  function safeTransfer(ERC20Basic token, address to, uint256 value) internal {
    require(token.transfer(to, value));
  }

  function safeTransferFrom(
    ERC20 token,
    address from,
    address to,
    uint256 value
  )
    internal
  {
    require(token.transferFrom(from, to, value));
  }

  function safeApprove(ERC20 token, address spender, uint256 value) internal {
    require(token.approve(spender, value));
  }
}

/**
 * @title SafeMath
 * @dev Math operations with safety checks that throw on error
 */
library SafeMath {

  /**
  * @dev Multiplies two numbers, throws on overflow.
  */
  function mul(uint256 a, uint256 b) internal pure returns (uint256 c) {
    // Gas optimization: this is cheaper than asserting 'a' not being zero, but the
    // benefit is lost if 'b' is also tested.
    // See: https://github.com/OpenZeppelin/openzeppelin-solidity/pull/522
    if (a == 0) {
      return 0;
    }

    c = a * b;
    assert(c / a == b);
    return c;
  }

  /**
  * @dev Integer division of two numbers, truncating the quotient.
  */
  function div(uint256 a, uint256 b) internal pure returns (uint256) {
    // assert(b > 0); // Solidity automatically throws when dividing by 0
    // uint256 c = a / b;
    // assert(a == b * c + a % b); // There is no case in which this doesn't hold
    return a / b;
  }

  /**
  * @dev Subtracts two numbers, throws on overflow (i.e. if subtrahend is greater than minuend).
  */
  function sub(uint256 a, uint256 b) internal pure returns (uint256) {
    assert(b <= a);
    return a - b;
  }

  /**
  * @dev Adds two numbers, throws on overflow.
  */
  function add(uint256 a, uint256 b) internal pure returns (uint256 c) {
    c = a + b;
    assert(c >= a);
    return c;
  }
}

/**
 * @title Basic token
 * @dev Basic version of StandardToken, with no allowances.
 */
contract BasicToken is ERC20Basic {
  using SafeMath for uint256;

  mapping(address => uint256) balances;

  uint256 totalSupply_;

  /**
  * @dev Total number of tokens in existence
  */
  function totalSupply() public view returns (uint256) {
    return totalSupply_;
  }

  /**
  * @dev Transfer token for a specified address
  * @param _to The address to transfer to.
  * @param _value The amount to be transferred.
  */
  function transfer(address _to, uint256 _value) public returns (bool) {
    require(_to != address(0));
    require(_value <= balances[msg.sender]);

    balances[msg.sender] = balances[msg.sender].sub(_value);
    balances[_to] = balances[_to].add(_value);
    emit Transfer(msg.sender, _to, _value);
    return true;
  }

  /**
  * @dev Gets the balance of the specified address.
  * @param _owner The address to query the the balance of.
  * @return An uint256 representing the amount owned by the passed address.
  */
  function balanceOf(address _owner) public view returns (uint256) {
    return balances[_owner];
  }

}

/**
 * @title Burnable Token
 * @dev Token that can be irreversibly burned (destroyed).
 */
contract BurnableToken is BasicToken {

  event Burn(address indexed burner, uint256 value);

  /**
   * @dev Burns a specific amount of tokens.
   * @param _value The amount of token to be burned.
   */
  function burn(uint256 _value) public {
    _burn(msg.sender, _value);
  }

  function _burn(address _who, uint256 _value) internal {
    require(_value <= balances[_who]);
    // no need to require value <= totalSupply, since that would imply the
    // sender's balance is greater than the totalSupply, which *should* be an assertion failure

    balances[_who] = balances[_who].sub(_value);
    totalSupply_ = totalSupply_.sub(_value);
    emit Burn(_who, _value);
    emit Transfer(_who, address(0), _value);
  }
}

/**
 * @title Standard ERC20 token
 *
 * @dev Implementation of the basic standard token.
 * https://github.com/ethereum/EIPs/issues/20
 * Based on code by FirstBlood: https://github.com/Firstbloodio/token/blob/master/smart_contract/FirstBloodToken.sol
 */
contract StandardToken is ERC20, BasicToken {

  mapping (address => mapping (address => uint256)) internal allowed;


  /**
   * @dev Transfer tokens from one address to another
   * @param _from address The address which you want to send tokens from
   * @param _to address The address which you want to transfer to
   * @param _value uint256 the amount of tokens to be transferred
   */
  function transferFrom(
    address _from,
    address _to,
    uint256 _value
  )
    public
    returns (bool)
  {
    require(_to != address(0));
    require(_value <= balances[_from]);
    require(_value <= allowed[_from][msg.sender]);

    balances[_from] = balances[_from].sub(_value);
    balances[_to] = balances[_to].add(_value);
    allowed[_from][msg.sender] = allowed[_from][msg.sender].sub(_value);
    emit Transfer(_from, _to, _value);
    return true;
  }

  /**
   * @dev Approve the passed address to spend the specified amount of tokens on behalf of msg.sender.
   * 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
   * @param _spender The address which will spend the funds.
   * @param _value The amount of tokens to be spent.
   */
  function approve(address _spender, uint256 _value) public returns (bool) {
    allowed[msg.sender][_spender] = _value;
    emit Approval(msg.sender, _spender, _value);
    return true;
  }

  /**
   * @dev Function to check the amount of tokens that an owner allowed to a spender.
   * @param _owner address The address which owns the funds.
   * @param _spender address The address which will spend the funds.
   * @return A uint256 specifying the amount of tokens still available for the spender.
   */
  function allowance(
    address _owner,
    address _spender
   )
    public
    view
    returns (uint256)
  {
    return allowed[_owner][_spender];
  }

  /**
   * @dev Increase the amount of tokens that an owner allowed to a spender.
   * approve should be called when allowed[_spender] == 0. To increment
   * allowed value is better to use this function to avoid 2 calls (and wait until
   * the first transaction is mined)
   * From MonolithDAO Token.sol
   * @param _spender The address which will spend the funds.
   * @param _addedValue The amount of tokens to increase the allowance by.
   */
  function increaseApproval(
    address _spender,
    uint256 _addedValue
  )
    public
    returns (bool)
  {
    allowed[msg.sender][_spender] = (
      allowed[msg.sender][_spender].add(_addedValue));
    emit Approval(msg.sender, _spender, allowed[msg.sender][_spender]);
    return true;
  }

  /**
   * @dev Decrease the amount of tokens that an owner allowed to a spender.
   * approve should be called when allowed[_spender] == 0. To decrement
   * allowed value is better to use this function to avoid 2 calls (and wait until
   * the first transaction is mined)
   * From MonolithDAO Token.sol
   * @param _spender The address which will spend the funds.
   * @param _subtractedValue The amount of tokens to decrease the allowance by.
   */
  function decreaseApproval(
    address _spender,
    uint256 _subtractedValue
  )
    public
    returns (bool)
  {
    uint256 oldValue = allowed[msg.sender][_spender];
    if (_subtractedValue > oldValue) {
      allowed[msg.sender][_spender] = 0;
    } else {
      allowed[msg.sender][_spender] = oldValue.sub(_subtractedValue);
    }
    emit Approval(msg.sender, _spender, allowed[msg.sender][_spender]);
    return true;
  }

}

/**
 * @title Standard Burnable Token
 * @dev Adds burnFrom method to ERC20 implementations
 */
contract StandardBurnableToken is BurnableToken, StandardToken {

  /**
   * @dev Burns a specific amount of tokens from the target address and decrements allowance
   * @param _from address The address which you want to send tokens from
   * @param _value uint256 The amount of token to be burned
   */
  function burnFrom(address _from, uint256 _value) public {
    require(_value <= allowed[_from][msg.sender]);
    // Should https://github.com/OpenZeppelin/zeppelin-solidity/issues/707 be accepted,
    // this function needs to emit an event with the updated approval.
    allowed[_from][msg.sender] = allowed[_from][msg.sender].sub(_value);
    _burn(_from, _value);
  }
}

contract WgdToken is StandardBurnableToken {
  string public constant name = "webGold";
  string public constant symbol = "WGD";
  uint8 public constant decimals = 18;

  uint256 constant TOTAL = 387500000000000000000000000;

  constructor() public {
    balances[msg.sender] = TOTAL;
    totalSupply_ = TOTAL;
    emit Transfer(address(0), msg.sender, TOTAL);
  }
}

/**
 * @title Ownable
 * @dev The Ownable contract has an owner address, and provides basic authorization control
 * functions, this simplifies the implementation of "user permissions".
 */
contract Ownable {
  address public owner;


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


  /**
   * @dev The Ownable constructor sets the original `owner` of the contract to the sender
   * account.
   */
  constructor() public {
    owner = msg.sender;
  }

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

  /**
   * @dev Allows the current owner to relinquish control of the contract.
   * @notice Renouncing to ownership will leave the contract without an owner.
   * It will not be possible to call the functions with the `onlyOwner`
   * modifier anymore.
   */
  function renounceOwnership() public onlyOwner {
    emit OwnershipRenounced(owner);
    owner = address(0);
  }

  /**
   * @dev Allows the current owner to transfer control of the contract to a newOwner.
   * @param _newOwner The address to transfer ownership to.
   */
  function transferOwnership(address _newOwner) public onlyOwner {
    _transferOwnership(_newOwner);
  }

  /**
   * @dev Transfers control of the contract to a newOwner.
   * @param _newOwner The address to transfer ownership to.
   */
  function _transferOwnership(address _newOwner) internal {
    require(_newOwner != address(0));
    emit OwnershipTransferred(owner, _newOwner);
    owner = _newOwner;
  }
}

/**
 * @title Crowdsale
 * @dev Crowdsale is a base contract for managing a token crowdsale,
 * allowing investors to purchase tokens with ether. This contract implements
 * such functionality in its most fundamental form and can be extended to provide additional
 * functionality and/or custom behavior.
 * The external interface represents the basic interface for purchasing tokens, and conform
 * the base architecture for crowdsales. They are *not* intended to be modified / overriden.
 * The internal interface conforms the extensible and modifiable surface of crowdsales. Override
 * the methods to add functionality. Consider using 'super' where appropiate to concatenate
 * behavior.
 */
contract DaonomicCrowdsale {
  using SafeMath for uint256;

  // Amount of wei raised
  uint256 public weiRaised;

  /**
   * @dev This event should be emitted when user buys something
   */
  event Purchase(address indexed buyer, address token, uint256 value, uint256 sold, uint256 bonus, bytes txId);
  /**
   * @dev Should be emitted if new payment method added
   */
  event RateAdd(address token);
  /**
   * @dev Should be emitted if payment method removed
   */
  event RateRemove(address token);

  // -----------------------------------------
  // Crowdsale external interface
  // -----------------------------------------

  /**
   * @dev fallback function ***DO NOT OVERRIDE***
   */
  function () external payable {
    buyTokens(msg.sender);
  }

  /**
   * @dev low level token purchase ***DO NOT OVERRIDE***
   * @param _beneficiary Address performing the token purchase
   */
  function buyTokens(address _beneficiary) public payable {

    uint256 weiAmount = msg.value;
    _preValidatePurchase(_beneficiary, weiAmount);

    // calculate token amount to be created
    (uint256 tokens, uint256 left) = _getTokenAmount(weiAmount);
    uint256 weiEarned = weiAmount.sub(left);
    uint256 bonus = _getBonus(tokens);
    uint256 withBonus = tokens.add(bonus);

    // update state
    weiRaised = weiRaised.add(weiEarned);

    _processPurchase(_beneficiary, withBonus);
    emit Purchase(
      _beneficiary,
      address(0),
        weiEarned,
      tokens,
      bonus,
      ""
    );

    _updatePurchasingState(_beneficiary, weiEarned, withBonus);
    _postValidatePurchase(_beneficiary, weiEarned);

    if (left > 0) {
      _beneficiary.transfer(left);
    }
  }

  // -----------------------------------------
  // Internal interface (extensible)
  // -----------------------------------------

  /**
   * @dev Validation of an incoming purchase. Use require statements to revert state when conditions are not met. Use super to concatenate validations.
   * @param _beneficiary Address performing the token purchase
   * @param _weiAmount Value in wei involved in the purchase
   */
  function _preValidatePurchase(
    address _beneficiary,
    uint256 _weiAmount
  )
    internal
  {
    require(_beneficiary != address(0));
    require(_weiAmount != 0);
  }

  /**
   * @dev Validation of an executed purchase. Observe state and use revert statements to undo rollback when valid conditions are not met.
   * @param _beneficiary Address performing the token purchase
   * @param _weiAmount Value in wei involved in the purchase
   */
  function _postValidatePurchase(
    address _beneficiary,
    uint256 _weiAmount
  )
    internal
  {
    // optional override
  }

  /**
   * @dev Source of tokens. Override this method to modify the way in which the crowdsale ultimately gets and sends its tokens.
   * @param _beneficiary Address performing the token purchase
   * @param _tokenAmount Number of tokens to be emitted
   */
  function _deliverTokens(
    address _beneficiary,
    uint256 _tokenAmount
  ) internal;

  /**
   * @dev Executed when a purchase has been validated and is ready to be executed. Not necessarily emits/sends tokens.
   * @param _beneficiary Address receiving the tokens
   * @param _tokenAmount Number of tokens to be purchased
   */
  function _processPurchase(
    address _beneficiary,
    uint256 _tokenAmount
  )
    internal
  {
    _deliverTokens(_beneficiary, _tokenAmount);
  }

  /**
   * @dev Override for extensions that require an internal state to check for validity (current user contributions, etc.)
   * @param _beneficiary Address receiving the tokens
   * @param _weiAmount Value in wei involved in the purchase
   */
  function _updatePurchasingState(
    address _beneficiary,
    uint256 _weiAmount,
    uint256 _tokens
  )
    internal
  {
    // optional override
  }

  /**
   * @dev Override to extend the way in which ether is converted to tokens.
   * @param _weiAmount Value in wei to be converted into tokens
   * @return Number of tokens that can be purchased with the specified _weiAmount
   *         and wei left (if no more tokens can be sold)
   */
  function _getTokenAmount(uint256 _weiAmount) internal view returns (uint256, uint256);

  function _getBonus(uint256 _tokens) internal view returns (uint256);
}

contract Whitelist {
  function isInWhitelist(address addr) public view returns (bool);
}

contract WhitelistDaonomicCrowdsale is Ownable, DaonomicCrowdsale {
  Whitelist[] public whitelists;

  constructor (Whitelist[] _whitelists) public {
    whitelists = _whitelists;
  }

  function setWhitelists(Whitelist[] _whitelists) onlyOwner public {
    whitelists = _whitelists;
  }

  function getWhitelists() view public returns (Whitelist[]) {
    return whitelists;
  }

  function _preValidatePurchase(
    address _beneficiary,
    uint256 _weiAmount
  ) internal {
    super._preValidatePurchase(_beneficiary, _weiAmount);
    require(canBuy(_beneficiary), "investor is not verified by Whitelists");
  }

  function canBuy(address _beneficiary) constant public returns (bool) {
    for (uint i = 0; i < whitelists.length; i++) {
      if (whitelists[i].isInWhitelist(_beneficiary)) {
        return true;
      }
    }
    return false;
  }
}

contract RefundableDaonomicCrowdsale is DaonomicCrowdsale {
  event Refund(address _address, uint256 investment);
  mapping(address => uint256) public investments;

  function claimRefund() public {
    require(isRefundable());
    require(investments[msg.sender] > 0);

    uint investment = investments[msg.sender];
    investments[msg.sender] = 0;

    msg.sender.transfer(investment);
    emit Refund(msg.sender, investment);
  }

  function isRefundable() public view returns (bool);

  function _updatePurchasingState(
    address _beneficiary,
    uint256 _weiAmount,
    uint256 _tokens
  ) internal {
    super._updatePurchasingState(_beneficiary, _weiAmount, _tokens);
    investments[_beneficiary] = investments[_beneficiary].add(_weiAmount);
  }
}

contract WgdSale is WhitelistDaonomicCrowdsale, RefundableDaonomicCrowdsale {
  using SafeERC20 for WgdToken;

  event Buyback(address indexed addr, uint256 tokens, uint256 value);

  WgdToken public token;

  uint256 constant public FOR_SALE = 300000000000000000000000000;
  uint256 constant public MINIMAL_WEI = 500000000000000000;
  uint256 constant public END = 1541592000;

  //stages
  uint256 constant STAGE1 = 20000000000000000000000000;
  uint256 constant STAGE2 = 60000000000000000000000000;
  uint256 constant STAGE3 = 140000000000000000000000000;
  uint256 constant STAGE4 = 300000000000000000000000000;

  //rates
  uint256 constant RATE1 = 28000;
  uint256 constant RATE2 = 24000;
  uint256 constant RATE3 = 22000;
  uint256 constant RATE4 = 20000;

  //bonus stages
  uint256 constant BONUS_STAGE1 = 100000000000000000000000;
  uint256 constant BONUS_STAGE2 = 500000000000000000000000;
  uint256 constant BONUS_STAGE3 = 1000000000000000000000000;
  uint256 constant BONUS_STAGE4 = 5000000000000000000000000;

  //bonuses
  uint256 constant BONUS1 = 1000000000000000000000;
  uint256 constant BONUS2 = 25000000000000000000000;
  uint256 constant BONUS3 = 100000000000000000000000;
  uint256 constant BONUS4 = 750000000000000000000000;

  uint256 public sold;

  constructor(WgdToken _token, Whitelist[] _whitelists)
  WhitelistDaonomicCrowdsale(_whitelists) public {
    token = _token;
    emit RateAdd(address(0));
  }

  function _preValidatePurchase(
    address _beneficiary,
    uint256 _weiAmount
  ) internal {
    super._preValidatePurchase(_beneficiary, _weiAmount);
    require(_weiAmount >= MINIMAL_WEI);
  }

  /**
   * @dev function for Daonomic UI
   */
  function getRate(address _token) public view returns (uint256) {
    if (_token == address(0)) {
      (,, uint256 rate) = getStage(sold);
      return rate.mul(10 ** 18);
    } else {
      return 0;
    }
  }

  /**
   * @dev Executes buyback
   * @dev burns all allowed tokens and returns back Eth
   * @dev call token.approve before calling this function
   */
  function buyback() public {
    (uint8 stage,,) = getStage(sold);
    require(stage > 0, "buyback doesn't work on stage 0");

    uint256 approved = token.allowance(msg.sender, this);
    uint256 inCirculation = token.totalSupply().sub(token.balanceOf(this));
    uint256 value = approved.mul(address(this).balance).div(inCirculation);

    token.burnFrom(msg.sender, approved);
    msg.sender.transfer(value);
    emit Buyback(msg.sender, approved, value);
  }

  function _deliverTokens(
    address _beneficiary,
    uint256 _tokenAmount
  ) internal {
    token.safeTransfer(_beneficiary, _tokenAmount);
  }

  function _getBonus(uint256 _tokens) internal view returns (uint256) {
    return getRealAmountBonus(FOR_SALE, sold, _tokens);
  }

  function getRealAmountBonus(uint256 _forSale, uint256 _sold, uint256 _tokens) public pure returns (uint256) {
    uint256 bonus = getAmountBonus(_tokens);
    uint256 left = _forSale.sub(_sold).sub(_tokens);
    if (left > bonus) {
      return bonus;
    } else {
      return left;
    }
  }

  function _getTokenAmount(uint256 _weiAmount) internal view returns (uint256, uint256) {
    return getTokenAmount(sold, _weiAmount);
  }

  function getTokenAmount(uint256 _sold, uint256 _weiAmount) public view returns (uint256 tokens, uint256 left) {
    left = _weiAmount;
    while (left > 0) {
      (uint256 currentTokens, uint256 currentLeft) = getTokensForStage(_sold.add(tokens), left);
      if (left == currentLeft) {
        return (tokens, left);
      }
      left = currentLeft;
      tokens = tokens.add(currentTokens);
    }
  }

  /**
   * @dev Calculates tokens for this stage
   * @return Number of tokens that can be purchased in this stage + wei left
   */
  function getTokensForStage(uint256 _sold, uint256 _weiAmount) public view returns (uint256 tokens, uint256 left) {
    (uint8 stage, uint256 limit, uint256 rate) = getStage(_sold);
    if (stage == 4) {
      return (0, _weiAmount);
    }
    if (stage == 0 && now > END) {
      revert("Sale is refundable, unable to buy");
    }
    tokens = _weiAmount.mul(rate);
    left = 0;
    (uint8 newStage,,) = getStage(_sold.add(tokens));
    if (newStage != stage) {
      tokens = limit.sub(_sold);
      //alternative to Math.ceil(tokens / rate)
      uint256 weiSpent = (tokens.add(rate).sub(1)).div(rate);
      left = _weiAmount.sub(weiSpent);
    }
  }

  function _updatePurchasingState(
    address _beneficiary,
    uint256 _weiAmount,
    uint256 _tokens
  ) internal {
    super._updatePurchasingState(_beneficiary, _weiAmount, _tokens);

    sold = sold.add(_tokens);
  }

  function isRefundable() public view returns (bool) {
    (uint8 stage,,) = getStage(sold);
    return now > END && stage == 0;
  }

  function getStage(uint256 _sold) public pure returns (uint8 stage, uint256 limit, uint256 rate) {
    if (_sold < STAGE1) {
      return (0, STAGE1, RATE1);
    } else if (_sold < STAGE2) {
      return (1, STAGE2, RATE2);
    } else if (_sold < STAGE3) {
      return (2, STAGE3, RATE3);
    } else if (_sold < STAGE4) {
      return (3, STAGE4, RATE4);
    } else {
      return (4, 0, 0);
    }
  }

  function getAmountBonus(uint256 _tokens) public pure returns (uint256) {
    if (_tokens < BONUS_STAGE1) {
      return 0;
    } else if (_tokens < BONUS_STAGE2) {
      return BONUS1;
    } else if (_tokens < BONUS_STAGE3) {
      return BONUS2;
    } else if (_tokens < BONUS_STAGE4) {
      return BONUS3;
    } else {
      return BONUS4;
    }
  }
}

    Contract ABI  
[{"constant":true,"inputs":[],"name":"sold","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"_beneficiary","type":"address"}],"name":"canBuy","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"_sold","type":"uint256"},{"name":"_weiAmount","type":"uint256"}],"name":"getTokenAmount","outputs":[{"name":"tokens","type":"uint256"},{"name":"left","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"isRefundable","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"_sold","type":"uint256"}],"name":"getStage","outputs":[{"name":"stage","type":"uint8"},{"name":"limit","type":"uint256"},{"name":"rate","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":false,"inputs":[{"name":"_whitelists","type":"address[]"}],"name":"setWhitelists","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_token","type":"address"}],"name":"getRate","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"weiRaised","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[],"name":"renounceOwnership","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_sold","type":"uint256"},{"name":"_weiAmount","type":"uint256"}],"name":"getTokensForStage","outputs":[{"name":"tokens","type":"uint256"},{"name":"left","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"FOR_SALE","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"owner","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"","type":"address"}],"name":"investments","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[],"name":"claimRefund","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_forSale","type":"uint256"},{"name":"_sold","type":"uint256"},{"name":"_tokens","type":"uint256"}],"name":"getRealAmountBonus","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[],"name":"MINIMAL_WEI","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"getWhitelists","outputs":[{"name":"","type":"address[]"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"_tokens","type":"uint256"}],"name":"getAmountBonus","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":false,"inputs":[{"name":"_beneficiary","type":"address"}],"name":"buyTokens","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[],"name":"END","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[],"name":"buyback","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"token","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"","type":"uint256"}],"name":"whitelists","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"_token","type":"address"},{"name":"_whitelists","type":"address[]"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"payable":true,"stateMutability":"payable","type":"fallback"},{"anonymous":false,"inputs":[{"indexed":true,"name":"addr","type":"address"},{"indexed":false,"name":"tokens","type":"uint256"},{"indexed":false,"name":"value","type":"uint256"}],"name":"Buyback","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"name":"_address","type":"address"},{"indexed":false,"name":"investment","type":"uint256"}],"name":"Refund","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"buyer","type":"address"},{"indexed":false,"name":"token","type":"address"},{"indexed":false,"name":"value","type":"uint256"},{"indexed":false,"name":"sold","type":"uint256"},{"indexed":false,"name":"bonus","type":"uint256"},{"indexed":false,"name":"txId","type":"bytes"}],"name":"Purchase","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"name":"token","type":"address"}],"name":"RateAdd","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"name":"token","type":"address"}],"name":"RateRemove","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"previousOwner","type":"address"}],"name":"OwnershipRenounced","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"previousOwner","type":"address"},{"indexed":true,"name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"}]

  Contract Creation Code Switch To Opcodes View
60806040523480156200001157600080fd5b50604051620015c3380380620015c383398101604052805160208083015160008054600160a060020a0319163317905590920180519192909182916200005d91600291840190620000b7565b505060048054600160a060020a031916600160a060020a038416179055604080516000815290517f7fa3995810e92a3f38bcfa9eb48e2e5b8eceb6ff181c6d57445f1126b0cd6873916020908290030190a150506200014b565b8280548282559060005260206000209081019282156200010f579160200282015b828111156200010f5782518254600160a060020a031916600160a060020a03909116178255602090920191600190910190620000d8565b506200011d92915062000121565b5090565b6200014891905b808211156200011d578054600160a060020a031916815560010162000128565b90565b611468806200015b6000396000f30060806040526004361061013d5763ffffffff7c010000000000000000000000000000000000000000000000000000000060003504166302c7e7af81146101485780630808f3eb1461016f5780630bc1236e146101a45780632c1fecfe146101d85780632e325020146101ed57806335b3f6091461022757806337cef7911461027c5780634042b66f1461029d578063715018a6146102b257806373139c0d146102c757806374467a1e146102e25780638da5cb5b146102f757806396b9886214610328578063b5545a3c14610349578063bb471d731461035e578063bc6fd6d91461037c578063c35dcf9014610391578063c4ccf6ea146103f6578063ec8ac4d81461040e578063efe7a50414610422578063f2fde38b14610437578063f8ec691114610458578063fc0c546a1461046d578063fe4d5add14610482575b6101463361049a565b005b34801561015457600080fd5b5061015d6105c9565b60408051918252519081900360200190f35b34801561017b57600080fd5b50610190600160a060020a03600435166105cf565b604080519115158252519081900360200190f35b3480156101b057600080fd5b506101bf6004356024356106aa565b6040805192835260208301919091528051918290030190f35b3480156101e457600080fd5b50610190610706565b3480156101f957600080fd5b50610205600435610733565b6040805160ff9094168452602084019290925282820152519081900360600190f35b34801561023357600080fd5b5060408051602060048035808201358381028086018501909652808552610146953695939460249493850192918291850190849080828437509497506108029650505050505050565b34801561028857600080fd5b5061015d600160a060020a0360043516610830565b3480156102a957600080fd5b5061015d61087c565b3480156102be57600080fd5b50610146610882565b3480156102d357600080fd5b506101bf6004356024356108ee565b3480156102ee57600080fd5b5061015d610a6b565b34801561030357600080fd5b5061030c610a7a565b60408051600160a060020a039092168252519081900360200190f35b34801561033457600080fd5b5061015d600160a060020a0360043516610a89565b34801561035557600080fd5b50610146610a9b565b34801561036a57600080fd5b5061015d600435602435604435610b4b565b34801561038857600080fd5b5061015d610b8e565b34801561039d57600080fd5b506103a6610b9a565b60408051602080825283518183015283519192839290830191858101910280838360005b838110156103e25781810151838201526020016103ca565b505050509050019250505060405180910390f35b34801561040257600080fd5b5061015d600435610bfd565b610146600160a060020a036004351661049a565b34801561042e57600080fd5b5061015d610c94565b34801561044357600080fd5b50610146600160a060020a0360043516610c9c565b34801561046457600080fd5b50610146610cbf565b34801561047957600080fd5b5061030c61101b565b34801561048e57600080fd5b5061030c60043561102a565b346000808080806104ab8787611052565b6104b486611071565b90955093506104c9868563ffffffff61108916565b92506104d4856110a0565b91506104e6858363ffffffff6110ba16565b6001549091506104fc908463ffffffff6110ba16565b60015561050987826110c7565b604080516000808252602082018690528183018890526060820185905260a0608083018190528201529051600160a060020a038916917f1dc3ba42f43a2d69b1bb6ba35c2669366a3c9fb238ef437219fce6430f573b8e919081900360e00190a26105758784836110d1565b61057f878461082c565b60008411156105c057604051600160a060020a0388169085156108fc029086906000818181858888f193505050501580156105be573d6000803e3d6000fd5b505b50505050505050565b60055481565b6000805b60025481101561069f5760028054829081106105eb57fe5b6000918252602080832090910154604080517f09fd8212000000000000000000000000000000000000000000000000000000008152600160a060020a038881166004830152915191909216936309fd821293602480850194919392918390030190829087803b15801561065d57600080fd5b505af1158015610671573d6000803e3d6000fd5b505050506040513d602081101561068757600080fd5b50511561069757600191506106a4565b6001016105d3565b600091505b50919050565b60008181805b60008311156106fd576106d26106cc878663ffffffff6110ba16565b846108ee565b91509150808314156106e3576106fd565b9150816106f6848363ffffffff6110ba16565b93506106b0565b50509250929050565b600080610714600554610733565b50509050635be2d3c04211801561072c575060ff8116155b91505b5090565b60008060006a108b2a2c280290940000008410156107665750600091506a108b2a2c280290940000009050616d606107fb565b6a31a17e847807b1bc0000008410156107945750600191506a31a17e847807b1bc0000009050615dc06107fb565b6a73ce27351811f40c0000008410156107c25750600291506a73ce27351811f40c00000090506155f06107fb565b6af8277896582678ac0000008410156107f05750600391506af8277896582678ac0000009050614e206107fb565b506004915060009050805b9193909250565b600054600160a060020a0316331461081957600080fd5b805161082c9060029060208401906113a3565b5050565b600080600160a060020a03831615156108735761084e600554610733565b925061086c9150829050670de0b6b3a764000063ffffffff6110f716565b91506106a4565b600091506106a4565b60015481565b600054600160a060020a0316331461089957600080fd5b60008054604051600160a060020a03909116917ff8df31144d9c2f0f6b59d69b8b98abd5459d07f2742c4df920b25aae33c6482091a26000805473ffffffffffffffffffffffffffffffffffffffff19169055565b600080600080600080600061090289610733565b9450945094508460ff16600414156109205760009650879550610a5f565b60ff85161580156109345750635be2d3c042115b156109c657604080517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602160248201527f53616c6520697320726566756e6461626c652c20756e61626c6520746f20627560448201527f7900000000000000000000000000000000000000000000000000000000000000606482015290519081900360840190fd5b6109d6888463ffffffff6110f716565b9650600095506109f46109ef8a8963ffffffff6110ba16565b610733565b505091508460ff168260ff16141515610a5f57610a17848a63ffffffff61108916565b9650610a4a83610a3e6001610a328b8463ffffffff6110ba16565b9063ffffffff61108916565b9063ffffffff61112016565b9050610a5c888263ffffffff61108916565b95505b50505050509250929050565b6af8277896582678ac00000081565b600054600160a060020a031681565b60036020526000908152604090205481565b6000610aa5610706565b1515610ab057600080fd5b3360009081526003602052604081205411610aca57600080fd5b5033600081815260036020526040808220805490839055905190929183156108fc02918491818181858888f19350505050158015610b0c573d6000803e3d6000fd5b50604080513381526020810183905281517fbb28353e4598c3b9199101a66e0989549b659a59a54d2c27fbb183f1932c8e6d929181900390910190a150565b6000806000610b5984610bfd565b9150610b6f84610a32888863ffffffff61108916565b905081811115610b8157819250610b85565b8092505b50509392505050565b6706f05b59d3b2000081565b60606002805480602002602001604051908101604052809291908181526020018280548015610bf257602002820191906000526020600020905b8154600160a060020a03168152600190910190602001808311610bd4575b505050505090505b90565b600069152d02c7e14af6800000821015610c1957506000610c8f565b6969e10de76676d0800000821015610c3b5750683635c9adc5dea00000610c8f565b69d3c21bcecceda1000000821015610c5e575069054b40b1f852bda00000610c8f565b6a0422ca8b0a00a425000000821015610c82575069152d02c7e14af6800000610c8f565b50699ed194db19b238c000005b919050565b635be2d3c081565b600054600160a060020a03163314610cb357600080fd5b610cbc81611135565b50565b600080600080610cd0600554610733565b5090945050600060ff851611610d4757604080517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601f60248201527f6275796261636b20646f65736e277420776f726b206f6e207374616765203000604482015290519081900360640190fd5b60048054604080517fdd62ed3e000000000000000000000000000000000000000000000000000000008152339381019390935230602484015251600160a060020a039091169163dd62ed3e9160448083019260209291908290030181600087803b158015610db457600080fd5b505af1158015610dc8573d6000803e3d6000fd5b505050506040513d6020811015610dde57600080fd5b505160048054604080517f70a08231000000000000000000000000000000000000000000000000000000008152309381019390935251929550610f0f92600160a060020a03909116916370a082319160248083019260209291908290030181600087803b158015610e4e57600080fd5b505af1158015610e62573d6000803e3d6000fd5b505050506040513d6020811015610e7857600080fd5b505160048054604080517f18160ddd0000000000000000000000000000000000000000000000000000000081529051600160a060020a03909216926318160ddd9282820192602092908290030181600087803b158015610ed757600080fd5b505af1158015610eeb573d6000803e3d6000fd5b505050506040513d6020811015610f0157600080fd5b50519063ffffffff61108916565b9150610f2682610a3e85303163ffffffff6110f716565b60048054604080517f79cc679000000000000000000000000000000000000000000000000000000000815233938101939093526024830187905251929350600160a060020a0316916379cc67909160448082019260009290919082900301818387803b158015610f9557600080fd5b505af1158015610fa9573d6000803e3d6000fd5b505060405133925083156108fc02915083906000818181858888f19350505050158015610fda573d6000803e3d6000fd5b506040805184815260208101839052815133927f2dcc2439519c7d06fca9f8ae01e07f4f3c6ca21b5cdf8eff42cb75cf34d223c9928290030190a250505050565b600454600160a060020a031681565b600280548290811061103857fe5b600091825260209091200154600160a060020a0316905081565b61105c82826111b2565b6706f05b59d3b2000081101561082c57600080fd5b600080611080600554846106aa565b91509150915091565b60008282111561109557fe5b508082035b92915050565b600061109a6af8277896582678ac00000060055484610b4b565b8181018281101561109a57fe5b61082c8282611258565b6110dc838383611275565b6005546110ef908263ffffffff6110ba16565b600555505050565b60008215156111085750600061109a565b5081810281838281151561111857fe5b041461109a57fe5b6000818381151561112d57fe5b049392505050565b600160a060020a038116151561114a57600080fd5b60008054604051600160a060020a03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a36000805473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a0392909216919091179055565b6111bc82826112ca565b6111c5826105cf565b151561082c57604080517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602660248201527f696e766573746f72206973206e6f74207665726966696564206279205768697460448201527f656c697374730000000000000000000000000000000000000000000000000000606482015290519081900360840190fd5b60045461082c90600160a060020a0316838363ffffffff6112eb16565b61128083838361139e565b600160a060020a0383166000908152600360205260409020546112a9908363ffffffff6110ba16565b600160a060020a039093166000908152600360205260409020929092555050565b600160a060020a03821615156112df57600080fd5b80151561082c57600080fd5b82600160a060020a031663a9059cbb83836040518363ffffffff167c01000000000000000000000000000000000000000000000000000000000281526004018083600160a060020a0316600160a060020a0316815260200182815260200192505050602060405180830381600087803b15801561136757600080fd5b505af115801561137b573d6000803e3d6000fd5b505050506040513d602081101561139157600080fd5b5051151561139e57600080fd5b505050565b828054828255906000526020600020908101928215611405579160200282015b82811115611405578251825473ffffffffffffffffffffffffffffffffffffffff1916600160a060020a039091161782556020909201916001909101906113c3565b5061072f92610bfa9250905b8082111561072f57805473ffffffffffffffffffffffffffffffffffffffff191681556001016114115600a165627a7a723058200b9c6b94f72b102a3dc31bb62a73e7aae614c0bf2f85061e530bf7bc64c5c26500290000000000000000000000002c6fc5bb896707254b8d4786532c456a1b534fc200000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000001000000000000000000000000e5fa6942a9662787c52e2ac1c61b895c580f799a

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

-----Encoded View---------------
4 Constructor Arguments found :
Arg [0] : 0000000000000000000000002c6fc5bb896707254b8d4786532c456a1b534fc2
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000040
Arg [2] : 0000000000000000000000000000000000000000000000000000000000000001
Arg [3] : 000000000000000000000000e5fa6942a9662787c52e2ac1c61b895c580f799a


   Swarm Source:
bzzr://0b9c6b94f72b102a3dc31bb62a73e7aae614c0bf2f85061e530bf7bc64c5c265

 

View All
Block Age transaction Difficulty GasUsed Reward
View All
Block Age UncleNumber Difficulty GasUsed Reward
Make sure to use the "Vote Down" button for any spammy posts, and the "Vote Up" for interesting conversations.