diff options
Diffstat (limited to 'packages/contracts/src/2.0.0/tokens/ERC20Token')
4 files changed, 237 insertions, 39 deletions
diff --git a/packages/contracts/src/2.0.0/tokens/ERC20Token/ERC20Token.sol b/packages/contracts/src/2.0.0/tokens/ERC20Token/ERC20Token.sol index d9950145d..5ef5ee7ce 100644 --- a/packages/contracts/src/2.0.0/tokens/ERC20Token/ERC20Token.sol +++ b/packages/contracts/src/2.0.0/tokens/ERC20Token/ERC20Token.sol @@ -21,15 +21,21 @@ pragma solidity 0.4.24; import "./IERC20Token.sol"; -contract ERC20Token is IERC20Token { +contract ERC20Token is + IERC20Token +{ mapping (address => uint256) internal balances; mapping (address => mapping (address => uint256)) internal allowed; - uint256 public totalSupply; + uint256 internal _totalSupply; + /// @dev send `value` token to `to` from `msg.sender` + /// @param _to The address of the recipient + /// @param _value The amount of token to be transferred + /// @return True if transfer was successful function transfer(address _to, uint256 _value) - public + external returns (bool) { require( @@ -38,16 +44,32 @@ contract ERC20Token is IERC20Token { ); require( balances[_to] + _value >= balances[_to], - "OVERFLOW" + "UINT256_OVERFLOW" ); + balances[msg.sender] -= _value; balances[_to] += _value; - emit Transfer(msg.sender, _to, _value); + + emit Transfer( + msg.sender, + _to, + _value + ); + return true; } - function transferFrom(address _from, address _to, uint256 _value) - public + /// @dev send `value` token to `to` from `from` on the condition it is approved by `from` + /// @param _from The address of the sender + /// @param _to The address of the recipient + /// @param _value The amount of token to be transferred + /// @return True if transfer was successful + function transferFrom( + address _from, + address _to, + uint256 _value + ) + external returns (bool) { require( @@ -60,34 +82,65 @@ contract ERC20Token is IERC20Token { ); require( balances[_to] + _value >= balances[_to], - "OVERFLOW" + "UINT256_OVERFLOW" ); + balances[_to] += _value; balances[_from] -= _value; allowed[_from][msg.sender] -= _value; - emit Transfer(_from, _to, _value); + + emit Transfer( + _from, + _to, + _value + ); + return true; } + /// @dev `msg.sender` approves `_spender` to spend `_value` tokens + /// @param _spender The address of the account able to transfer the tokens + /// @param _value The amount of wei to be approved for transfer + /// @return Always true if the call has enough gas to complete execution function approve(address _spender, uint256 _value) - public + external returns (bool) { allowed[msg.sender][_spender] = _value; - emit Approval(msg.sender, _spender, _value); + emit Approval( + msg.sender, + _spender, + _value + ); return true; } + /// @dev Query total supply of token + /// @return Total supply of token + function totalSupply() + external + view + returns (uint256) + { + return _totalSupply; + } + + /// @dev Query the balance of owner + /// @param _owner The address from which the balance will be retrieved + /// @return Balance of owner function balanceOf(address _owner) - public + external view returns (uint256) { return balances[_owner]; } + /// @param _owner The address of the account owning tokens + /// @param _spender The address of the account able to transfer the tokens + /// @return Amount of remaining tokens allowed to spent function allowance(address _owner, address _spender) - public + external view returns (uint256) { diff --git a/packages/contracts/src/2.0.0/tokens/ERC20Token/IERC20Token.sol b/packages/contracts/src/2.0.0/tokens/ERC20Token/IERC20Token.sol index 5ee5e1011..258d47393 100644 --- a/packages/contracts/src/2.0.0/tokens/ERC20Token/IERC20Token.sol +++ b/packages/contracts/src/2.0.0/tokens/ERC20Token/IERC20Token.sol @@ -21,54 +21,67 @@ pragma solidity 0.4.24; contract IERC20Token { - /// @notice send `value` token to `to` from `msg.sender` + // solhint-disable no-simple-event-func-name + event Transfer( + address indexed _from, + address indexed _to, + uint256 _value + ); + + event Approval( + address indexed _owner, + address indexed _spender, + uint256 _value + ); + + /// @dev send `value` token to `to` from `msg.sender` /// @param _to The address of the recipient /// @param _value The amount of token to be transferred - /// @return Whether the transfer was successful or not + /// @return True if transfer was successful function transfer(address _to, uint256 _value) - public + external returns (bool); - /// @notice send `value` token to `to` from `from` on the condition it is approved by `from` + /// @dev send `value` token to `to` from `from` on the condition it is approved by `from` /// @param _from The address of the sender /// @param _to The address of the recipient /// @param _value The amount of token to be transferred - /// @return Whether the transfer was successful or not - function transferFrom(address _from, address _to, uint256 _value) - public + /// @return True if transfer was successful + function transferFrom( + address _from, + address _to, + uint256 _value + ) + external returns (bool); - /// @notice `msg.sender` approves `_spender` to spend `_value` tokens + /// @dev `msg.sender` approves `_spender` to spend `_value` tokens /// @param _spender The address of the account able to transfer the tokens /// @param _value The amount of wei to be approved for transfer - /// @return Whether the approval was successful or not + /// @return Always true if the call has enough gas to complete execution function approve(address _spender, uint256 _value) - public + external returns (bool); + /// @dev Query total supply of token + /// @return Total supply of token + function totalSupply() + external + view + returns (uint256); + /// @param _owner The address from which the balance will be retrieved - /// @return The balance + /// @return Balance of owner function balanceOf(address _owner) - public view + external + view returns (uint256); /// @param _owner The address of the account owning tokens /// @param _spender The address of the account able to transfer the tokens /// @return Amount of remaining tokens allowed to spent function allowance(address _owner, address _spender) - public view + external + view returns (uint256); - - // solhint-disable-next-line no-simple-event-func-name - event Transfer( - address indexed _from, - address indexed _to, - uint256 _value - ); - - event Approval( - address indexed _owner, - address indexed _spender, - uint256 _value - ); } diff --git a/packages/contracts/src/2.0.0/tokens/ERC20Token/MintableERC20Token.sol b/packages/contracts/src/2.0.0/tokens/ERC20Token/MintableERC20Token.sol new file mode 100644 index 000000000..cd1c7b4bb --- /dev/null +++ b/packages/contracts/src/2.0.0/tokens/ERC20Token/MintableERC20Token.sol @@ -0,0 +1,61 @@ +/* + + Copyright 2018 ZeroEx Intl. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +*/ + +pragma solidity 0.4.24; + +import "../../utils/SafeMath/SafeMath.sol"; +import "./UnlimitedAllowanceERC20Token.sol"; + + +contract MintableERC20Token is + SafeMath, + UnlimitedAllowanceERC20Token +{ + + /// @dev Mints new tokens + /// @param _to Address of the beneficiary that will own the minted token + /// @param _value Amount of tokens to mint + function _mint(address _to, uint256 _value) + internal + { + balances[_to] = safeAdd(_value, balances[_to]); + _totalSupply = safeAdd(_totalSupply, _value); + + emit Transfer( + address(0), + _to, + _value + ); + } + + /// @dev Mints new tokens + /// @param _owner Owner of tokens that will be burned + /// @param _value Amount of tokens to burn + function _burn(address _owner, uint256 _value) + internal + { + balances[_owner] = safeSub(balances[_owner], _value); + _totalSupply = safeSub(_totalSupply, _value); + + emit Transfer( + _owner, + address(0), + _value + ); + } +} diff --git a/packages/contracts/src/2.0.0/tokens/ERC20Token/UnlimitedAllowanceERC20Token.sol b/packages/contracts/src/2.0.0/tokens/ERC20Token/UnlimitedAllowanceERC20Token.sol new file mode 100644 index 000000000..e6f7c063e --- /dev/null +++ b/packages/contracts/src/2.0.0/tokens/ERC20Token/UnlimitedAllowanceERC20Token.sol @@ -0,0 +1,71 @@ +/* + + Copyright 2018 ZeroEx Intl. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +*/ + +pragma solidity 0.4.24; + +import "../ERC20Token/ERC20Token.sol"; + + +contract UnlimitedAllowanceERC20Token is + ERC20Token +{ + + uint256 constant internal MAX_UINT = 2**256 - 1; + + /// @dev ERC20 transferFrom, modified such that an allowance of MAX_UINT represents an unlimited allowance. See https://github.com/ethereum/EIPs/issues/717 + /// @param _from Address to transfer from. + /// @param _to Address to transfer to. + /// @param _value Amount to transfer. + /// @return Success of transfer. + function transferFrom( + address _from, + address _to, + uint256 _value + ) + external + returns (bool) + { + uint256 allowance = allowed[_from][msg.sender]; + require( + balances[_from] >= _value, + "ERC20_INSUFFICIENT_BALANCE" + ); + require( + allowance >= _value, + "ERC20_INSUFFICIENT_ALLOWANCE" + ); + require( + balances[_to] + _value >= balances[_to], + "UINT256_OVERFLOW" + ); + + balances[_to] += _value; + balances[_from] -= _value; + if (allowance < MAX_UINT) { + allowed[_from][msg.sender] -= _value; + } + + emit Transfer( + _from, + _to, + _value + ); + + return true; + } +} |