Repository navigation
Expand file tree
/
Copy pathERC777ERC20BaseToken.sol
More file actions
105 lines (90 loc) · 4.19 KB
/
Copy pathERC777ERC20BaseToken.sol
File metadata and controls
105 lines (90 loc) · 4.19 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
pragma solidity ^0.4.24;
import { ERC20Token } from "./ERC20Token.sol";
import { ERC777BaseToken } from "./ERC777BaseToken.sol";
contract ERC777ERC20BaseToken is ERC20Token, ERC777BaseToken {
bool internal mErc20compatible;
mapping(address => mapping(address => uint256)) internal mAllowed;
constructor(
string _name,
string _symbol,
uint256 _granularity,
address[] _defaultOperators
)
internal ERC777BaseToken(_name, _symbol, _granularity, _defaultOperators)
{
mErc20compatible = true;
setInterfaceImplementation("ERC20Token", this);
}
/// @notice This modifier is applied to erc20 obsolete methods that are
/// implemented only to maintain backwards compatibility. When the erc20
/// compatibility is disabled, this methods will fail.
modifier erc20 () {
require(mErc20compatible, "ERC20 is disabled");
_;
}
/// @notice For Backwards compatibility
/// @return The decimls of the token. Forced to 18 in ERC777.
function decimals() public erc20 view returns (uint8) { return uint8(18); }
/// @notice ERC20 backwards compatible transfer.
/// @param _to The address of the recipient
/// @param _amount The number of tokens to be transferred
/// @return `true`, if the transfer can't be done, it should fail.
function transfer(address _to, uint256 _amount) public erc20 returns (bool success) {
doSend(msg.sender, msg.sender, _to, _amount, "", "", false);
return true;
}
/// @notice ERC20 backwards compatible transferFrom.
/// @param _from The address holding the tokens being transferred
/// @param _to The address of the recipient
/// @param _amount The number of tokens to be transferred
/// @return `true`, if the transfer can't be done, it should fail.
function transferFrom(address _from, address _to, uint256 _amount) public erc20 returns (bool success) {
require(_amount <= mAllowed[_from][msg.sender], "Not enough funds allowed");
// Cannot be after doSend because of tokensReceived re-entry
mAllowed[_from][msg.sender] = mAllowed[_from][msg.sender].sub(_amount);
doSend(msg.sender, _from, _to, _amount, "", "", false);
return true;
}
/// @notice ERC20 backwards compatible approve.
/// `msg.sender` approves `_spender` to spend `_amount` tokens on its behalf.
/// @param _spender The address of the account able to transfer the tokens
/// @param _amount The number of tokens to be approved for transfer
/// @return `true`, if the approve can't be done, it should fail.
function approve(address _spender, uint256 _amount) public erc20 returns (bool success) {
mAllowed[msg.sender][_spender] = _amount;
emit Approval(msg.sender, _spender, _amount);
return true;
}
/// @notice ERC20 backwards compatible allowance.
/// This function makes it easy to read the `allowed[]` map
/// @param _owner The address of the account that owns the token
/// @param _spender The address of the account able to transfer the tokens
/// @return Amount of remaining tokens of _owner that _spender is allowed
/// to spend
function allowance(address _owner, address _spender) public erc20 view returns (uint256 remaining) {
return mAllowed[_owner][_spender];
}
function doSend(
address _operator,
address _from,
address _to,
uint256 _amount,
bytes _data,
bytes _operatorData,
bool _preventLocking
)
internal
{
super.doSend(_operator, _from, _to, _amount, _data, _operatorData, _preventLocking);
if (mErc20compatible) { emit Transfer(_from, _to, _amount); }
}
function doBurn(address _operator, address _tokenHolder, uint256 _amount, bytes _data, bytes _operatorData)
internal
{
super.doBurn(_operator, _tokenHolder, _amount, _data, _operatorData);
if (mErc20compatible) { emit Transfer(_tokenHolder, 0x0, _amount); }
}
}