Created
January 27, 2025 11:50
-
-
Save killerstorm/81fc6d4e5a3f4c9077b664ba14900f42 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
contract EthGrowthToken { | |
uint256 ethBalance = 0; | |
uint constant depositFeePc = 1; | |
uint constant withdrawFeePc = 1; | |
// Following function implement growth logic: | |
// ether can be converted to and from tokens according to a current price which | |
// is calculated as (ethBalance / totalTokens), however we charge deposit | |
// and withdraw fees which increase the price of the token. | |
function () { | |
if (msg.value > 0) { | |
uint256 depositFee = msg.value * depositFeePc / 100; | |
uint256 boughtTokens; | |
if (totalTokens > 0 && ethBalance > 0) { // ethBalance check is actually unnecessary | |
// we multiply received value by the amount of tokens one wei can buy | |
// (which is the inverse of price of one token in wei) | |
boughtTokens = ((msg.value - depositFee) * totalTokens) / ethBalance; | |
} else { | |
boughtTokens = msg.value - depositFee; | |
} | |
balanceOf[msg.sender] += boughtTokens; | |
ethBalance += msg.value; | |
totalTokens += boughtTokens; | |
Transfer(address(0), msg.sender, boughtTokens); | |
} | |
} | |
function withdraw (uint _value) { | |
if (balanceOf[msg.sender] >= _value) { | |
// we calculate how much ether one gets by multiplying an amount in tokens | |
// by price of one token in wei (i.e. how much wei exists for every token) | |
uint ethValue = (_value * ethBalance) / totalTokens; | |
uint withdrawFee = ethValue * withdrawFeePc / 100; | |
ethValue -= withdrawFee; | |
if (ethValue > ethBalance) throw; // this should never happen | |
balanceOf[msg.sender] -= _value; | |
msg.sender.send(ethValue); | |
Transfer(msg.sender, address(0), _value); | |
} else throw; | |
} | |
// The rest is vanilla token contract based on this one: | |
// https://github.com/ConsenSys/Tokens/blob/432e282b05fd17e35ab48ef8c9e18514eaaa2ec9/Token_Contracts/contracts/Standard_Token.sol | |
// except special handling of transfer to address zero: it is interpreted as | |
// withdraw. | |
mapping (address => uint256) public balanceOf; | |
mapping (address => mapping (address => uint256)) allowed; | |
uint256 totalTokens = 0; | |
event Transfer(address indexed _from, address indexed _to, uint256 _value); | |
event Approval(address indexed _owner, address indexed _spender, uint256 _value); | |
function transfer(address _to, uint256 _value) returns (bool success) { | |
if (_to == address(0)) { | |
withdraw(_value); | |
return true; | |
} | |
if (balanceOf[msg.sender] >= _value) { | |
balanceOf[msg.sender] -= _value; | |
balanceOf[_to] += _value; | |
return true; | |
} else { | |
return false; | |
} | |
} | |
function transferFrom(address _from, address _to, uint256 _value) returns (bool success) { | |
if (_to == address(0)) throw; // TODO: withdraw cannot be done via transferFrom | |
if (balanceOf[_from] >= _value && allowed[_from][msg.sender] >= _value && _value > 0) { | |
balanceOf[_to] += _value; | |
Transfer(_from, _to, _value); | |
balanceOf[_from] -= _value; | |
allowed[_from][msg.sender] -= _value; | |
return true; | |
} else { return false; } | |
} | |
function totalSupply() constant returns (uint256 supply) { | |
return totalTokens; | |
} | |
function approve(address _spender, uint256 _value) returns (bool success) { | |
allowed[msg.sender][_spender] = _value; | |
Approval(msg.sender, _spender, _value); | |
return true; | |
} | |
function allowance(address _owner, address _spender) constant returns (uint256 remaining) { | |
return allowed[_owner][_spender]; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment