forked from Bitatlas/NewERC20coin
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathERC20demo.sol
109 lines (88 loc) · 4.3 KB
/
ERC20demo.sol
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
106
107
108
109
pragma solidity ^0.6.7;
interface ERC20 {
function totalSupply() external view returns (uint _totalSupply);
function balanceOf(address _owner) external view returns (uint balance);
function transfer(address _to, uint _value) external returns (bool success);
function transferFrom(address _from, address _to, uint _value) external returns (bool success);
function approve(address _spender, uint _value) external returns (bool success);
function allowance(address _owner, address _spender) external view returns (uint remaining);
event Transfer(address indexed _from, address indexed _to, uint _value);
event Approval(address indexed _owner, address indexed _spender, uint _value);
}
// this is the basics of creating an ERC20 token
//change the name Henri and the symbol to whatever you would like
contract Loeker is ERC20 {
string public constant symbol = "HEN";
string public constant name = "Henri";
uint8 public constant decimals = 18;
//1,000,000+18 zeros
uint private constant __totalSupply = 1000000000000000000000000;
//this mapping is where we store the balances of an address
mapping (address => uint) private __balanceOf;
//This is a mapping of a mapping. This is for the approval function to determine how much an address can spend
mapping (address => mapping (address => uint)) private __allowances;
//the creator of the contract has the total supply and no one can create tokens
constructor() public {
__balanceOf[msg.sender] = __totalSupply;
}
//constant value that does not change/ returns the amount of initial tokens to display
function totalSupply() public view override returns (uint _totalSupply) {
_totalSupply = __totalSupply;
}
//returns the balance of a specific address
function balanceOf(address _addr) public view override returns (uint balance) {
return __balanceOf[_addr];
}
//transfer an amount of tokens to another address. The transfer needs to be >0
//does the msg.sender have enough tokens to forfill the transfer
//decrease the balance of the sender and increase the balance of the to address
function transfer(address _to, uint _value) public override returns (bool success) {
if (_value > 0 && _value <= balanceOf(msg.sender)) {
__balanceOf[msg.sender] -= _value;
__balanceOf[_to] += _value;
emit Transfer(msg.sender, _to, _value);
return true;
}
return false;
}
//this allows someone else (a 3rd party) to transfer from my wallet to someone elses wallet
//If the 3rd party has an allowance of >0
//and the value to transfer is >0
//and the allowance is >= the value of the transfer
//and it is not a contract
//perform the transfer by increasing the to account and decreasing the from accounts
function transferFrom(address _from, address _to, uint _value) public override returns (bool success) {
if (__allowances[_from][msg.sender] > 0 &&
_value >0 &&
__allowances[_from][msg.sender] >= _value
// the to address is not a contract
&& !isContract(_to)) {
__balanceOf[_from] -= _value;
__balanceOf[_to] += _value;
emit Transfer(_from, _to, _value);
return true;
}
return false;
}
//This check is to determine if we are sending to a contract?
//Is there code at this address? If the code size is greater then 0 then it is a contract.
function isContract(address _addr) public view returns (bool) {
uint codeSize;
//in line assembly code
assembly {
codeSize := extcodesize(_addr)
}
// i=s code size > 0 then true
return codeSize > 0;
}
//allows a spender address to spend a specific amount of value
function approve(address _spender, uint _value) external override returns (bool success) {
__allowances[msg.sender][_spender] = _value;
emit Approval(msg.sender, _spender, _value);
return true;
}
//shows how much a spender has the approval to spend to a specific address
function allowance(address _owner, address _spender) external override view returns (uint remaining) {
return __allowances[_owner][_spender];
}
}