contract Token is Pausable{
    using SafeMath for uint256;

    string public constant name = "High Reward Coin";
    string public constant symbol = "HRC";
    uint8 public constant decimals = 18;

    uint256 public totalSupply;

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

    mapping (address => bool) public unpausedWallet;

    bool public mintingFinished = false;

    uint256 public totalMigrated;
    address public migrationAgent;

    event Transfer(address indexed from, address indexed to, uint256 value);
    event Approval(address indexed owner, address indexed spender, uint256 value);

    event Mint(address indexed to, uint256 amount);
    event MintFinished();

    event Migrate(address indexed _from, address indexed _to, uint256 _value);

    modifier canMint() {
        require(!mintingFinished);
        _;
    }

     function Token() public {
         owner = 0x0;
     }

     function setOwner() public{
         require(owner == 0x0);
         owner = msg.sender;
     }

    // Balance of the specified address
    function balanceOf(address _owner) public constant returns (uint256 balance) {
        return balances[_owner];
    }

    // Transfer of tokens from one account to another
    function transfer(address _to, uint256 _value) public whenNotPaused returns (bool) {
        require (_value > 0);
        balances[msg.sender] = balances[msg.sender].sub(_value);
        balances[_to] = balances[_to].add(_value);
        Transfer(msg.sender, _to, _value);
        return true;
    }

    // Returns the number of tokens that _owner trusted to spend from his account _spender
    function allowance(address _owner, address _spender) public constant returns (uint256 remaining) {
        return allowed[_owner][_spender];
    }

    // Trust _sender and spend _value tokens from your account
    function approve(address _spender, uint256 _value) public returns (bool) {

        // To change the approve amount you first have to reduce the addresses
        //  allowance to zero by calling `approve(_spender, 0)` if it is not
        //  already 0 to mitigate the race condition described here:
        //  https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729
        require((_value == 0) || (allowed[msg.sender][_spender] == 0));

        allowed[msg.sender][_spender] = _value;
        Approval(msg.sender, _spender, _value);
        return true;
    }

    // Transfer of tokens from the trusted address _from to the address _to in the number _value
    function transferFrom(address _from, address _to, uint256 _value) public whenNotPaused returns (bool) {
        var _allowance = allowed[_from][msg.sender];

        // Check is not needed because sub(_allowance, _value) will already throw if this condition is not met
        // require (_value <= _allowance);

        require (_value > 0);

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

    // Issue new tokens to the address _to in the amount _amount. Available to the owner of the contract (contract Crowdsale)
    function mint(address _to, uint256 _amount) public onlyOwner canMint returns (bool) {
        totalSupply = totalSupply.add(_amount);
        balances[_to] = balances[_to].add(_amount);
        Mint(_to, _amount);
        Transfer(0x0, _to, _amount);
        return true;
    }

    // Stop the release of tokens. This is not possible to cancel. Available to the owner of the contract.
//    function finishMinting() public onlyOwner returns (bool) {
//        mintingFinished = true;
//        MintFinished();
//        return true;
//    }

    // Redefinition of the method of the returning status of the "Exchange pause".
    // Never for the owner of an unpaused wallet.
    function paused() public constant returns(bool) {
        return super.paused() && !unpausedWallet[msg.sender];
    }


    // Add a wallet ignoring the "Exchange pause". Available to the owner of the contract.
    function addUnpausedWallet(address _wallet) public onlyOwner {
        unpausedWallet[_wallet] = true;
    }

    // Remove the wallet ignoring the "Exchange pause". Available to the owner of the contract.
    function delUnpausedWallet(address _wallet) public onlyOwner {
         unpausedWallet[_wallet] = false;
    }

    // Enable the transfer of current tokens to others. Only 1 time. Disabling this is not possible.
    // Available to the owner of the contract.
    function setMigrationAgent(address _migrationAgent) public onlyOwner {
        require(migrationAgent == 0x0);
        migrationAgent = _migrationAgent;
    }

    // Reissue your tokens.
    function migrate() public
    {
        uint256 value = balances[msg.sender];
        require(value > 0);

        totalSupply = totalSupply.sub(value);
        totalMigrated = totalMigrated.add(value);
        MigrationAgent(migrationAgent).migrateFrom(msg.sender, value);
        Migrate(msg.sender,migrationAgent,value);
        balances[msg.sender] = 0;
    }
}
// (A2)
// Contract token
function delUnpausedWallet(address _wallet) public onlyOwner {
     unpausedWallet[_wallet] = false;
}

// Remove the wallet ignoring the "Exchange pause". Available to the owner of the contract.