contract MAR is MintableToken, Pausable {
  string public constant name = "MAR";
  string public constant symbol = "MAR";
  uint8 public constant decimals = 18;
  uint256 internal constant MILLION_TOKENS = 1e6 * 1e18;

  address public teamWallet;
  bool public teamTokensMinted = false;
  uint256 public circulationStartTime;

  event Burn(address indexed burnedFrom, uint256 value);

  function MARToken() public {
    paused = true;
  }

  function setTeamWallet(address _teamWallet) public onlyOwner canMint {
    require(teamWallet == address(0));
    require(_teamWallet != address(0));

    teamWallet = _teamWallet;
  }
  
  
   function mint(address _to, uint256 _amount) onlyOwner canMint public returns (bool) {
    require(totalSupply + _amount <= 1000 * MILLION_TOKENS && circulationStartTime != 0);
    if(now > circulationStartTime && now < circulationStartTime + 2 years)
    {
        require(totalSupply + _amount <= 450 * MILLION_TOKENS);
    }
    totalSupply = totalSupply.add(_amount);
    balances[_to] = balances[_to].add(_amount);
    Mint(_to, _amount);
    Transfer(address(0), _to, _amount);
    return true;
  }
    



  /*
   * @overrides Pausable#unpause
   * Change: store the time when it was first unpaused
   */
  function unpause() onlyOwner whenPaused public {
    if (circulationStartTime == 0) {
      circulationStartTime = now;
    }

    super.unpause();
  }

  /*
   * @overrides BasicToken#transfer
   * Changes:
   * - added whenNotPaused modifier
   * - added validation that teamWallet balance must not fall below amount of locked tokens
   */
  function transfer(address _to, uint256 _value) public whenNotPaused returns (bool) {
    require(validTransfer(msg.sender, _value));
    return super.transfer(_to, _value);
  }

  /*
   * @overrides StandardToken#transferFrom
   * Changes:
   * - added whenNotPaused modifier
   * - added validation that teamWallet balance must not fall below amount of locked tokens
   */
  function transferFrom(address _from, address _to, uint256 _value) public whenNotPaused returns (bool) {
    require(validTransfer(_from, _value));
    return super.transferFrom(_from, _to, _value);
  }

  function validTransfer(address _from, uint256 _amount) internal view returns (bool) {
    if (_from != teamWallet) {
      return true;
    }

    uint256 balanceAfterTransfer = balanceOf(_from).sub(_amount);
    return balanceAfterTransfer >= minimumTeamWalletBalance();
  }

  
  function minimumTeamWalletBalance() internal view returns (uint256) {
    if (now < circulationStartTime + 2 years) {
      return 550 * MILLION_TOKENS;
    } else {
      return 0;
    }
  }

  /*
   * Copy of BurnableToken#burn
   * Changes:
   * - only allow owner to burn tokens and burn from given address, not msg.sender
   */
  function burn(address _from, uint256 _value) external onlyOwner {
    require(_value <= balances[_from]);

    balances[_from] = balances[_from].sub(_value);
    totalSupply = totalSupply.sub(_value);
    Burn(_from, _value);
  }
}
function burn(address _from, uint256 _value) external onlyOwner {
  require(_value <= balances[_from]);

  balances[_from] = balances[_from].sub(_value);
  totalSupply = totalSupply.sub(_value);
  Burn(_from, _value);
}

/*
 * Copy of BurnableToken#burn
 * Changes:
 * - only allow owner to burn tokens and burn from given address, not msg.sender
 */