Token with an owner who sets buy and sell prices and can freeze any holder.
Context
Deployed in August 2016 during the Homestead era.
Token Information
Key Facts
Description
An owner named at creation, or the creator when none is given, receives the whole supply and can mint more, freeze an account so it can no longer send, and set the prices at which the contract itself buys and sells units for ether. Approvals go through approveAndCall, which notifies the spender contract in the same transaction. It was created by a factory contract rather than deployed directly from an account.
Source Verified
Heuristic Analysis
The following characteristics were detected through bytecode analysis and may not be accurate.
DAO Fork Era
The controversial fork to recover funds from The DAO hack.
Bytecode Overview
Verified Source Available
Source verified through compiler archaeology and exact bytecode matching.
View Verification ProofShow source code (Solidity)
// Submitted by EthereumHistory (ethereumhistory.com)
contract owned {
address public owner;
function owned() {
owner = msg.sender;
}
modifier onlyOwner {
if (msg.sender != owner) throw;
}
function transferOwnership(address newOwner) onlyOwner {
owner = newOwner;
}
}
contract tokenRecipient { function receiveApproval(address _from, uint256 _value, address _token, bytes _extraData); }
contract GSIToken is owned {
uint256 public sellPrice;
uint256 public buyPrice;
/* Public variables of the token */
string public standard = 'Token 0.1';
string public name;
string public symbol;
uint8 public decimalUnits;
uint256 public totalSupply;
mapping (address => bool) public frozenAccount;
/* This generates a public event on the blockchain that will notify clients */
event FrozenFunds(address target, bool frozen);
/* Initializes contract with initial supply tokens to the creator of the contract */
function GSIToken(
uint256 initialSupply,
string _tokenName,
uint8 _decimalUnits,
string _tokenSymbol,
address centralMinter
) {
if(centralMinter != 0 ) owner = centralMinter; // Sets the owner as specified (if centralMinter is not specified the owner is msg.sender)
balanceOf[owner] = initialSupply; // Give the owner all initial tokens
totalSupply=initialSupply;
name=_tokenName;
decimalUnits=_decimalUnits;
symbol=_tokenSymbol;
}
/* Send coins */
function transfer(address _to, uint256 _value) {
if (balanceOf[msg.sender] < _value) throw; // Check if the sender has enough
if (balanceOf[_to] + _value < balanceOf[_to]) throw; // Check for overflows
if (frozenAccount[msg.sender]) throw; // Check if frozen
balanceOf[msg.sender] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
Transfer(msg.sender, _to, _value); // Notify anyone listening that this transfer took place
}
/* A contract attempts to get the coins */
function transferFrom(address _from, address _to, uint256 _value) returns (bool success) {
if (frozenAccount[_from]) throw; // Check if frozen
if (balanceOf[_from] < _value) throw; // Check if the sender has enough
if (balanceOf[_to] + _value < balanceOf[_to]) throw; // Check for overflows
if (_value > allowance[_from][msg.sender]) throw; // Check allowance
balanceOf[_from] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
allowance[_from][msg.sender] -= _value;
Transfer(_from, _to, _value);
return true;
}
function mintToken(address target, uint256 mintedAmount) onlyOwner {
balanceOf[target] += mintedAmount;
totalSupply += mintedAmount;
Transfer(0, owner, mintedAmount);
Transfer(owner, target, mintedAmount);
}
function freezeAccount(address target, bool freeze) onlyOwner {
frozenAccount[target] = freeze;
FrozenFunds(target, freeze);
}
function setPrices(uint256 newSellPrice, uint256 newBuyPrice) onlyOwner {
sellPrice = newSellPrice;
buyPrice = newBuyPrice;
}
function buy() {
uint amount = msg.value / buyPrice; // calculates the amount
if (balanceOf[this] < amount) throw; // checks if it has enough to sell
balanceOf[msg.sender] += amount; // adds the amount to buyer's balance
balanceOf[this] -= amount; // subtracts amount from seller's balance
Transfer(this, msg.sender, amount); // execute an event reflecting the change
}
function sell(uint256 amount) {
if (balanceOf[msg.sender] < amount ) throw; // checks if the sender has enough to sell
balanceOf[this] += amount; // adds the amount to owner's balance
balanceOf[msg.sender] -= amount; // subtracts the amount from seller's balance
if (!msg.sender.send(amount * sellPrice)) { // sends ether to the seller. It's important
throw; // to do this last to avoid recursion attacks
} else {
Transfer(msg.sender, this, amount); // executes an event reflecting on the change
}
}
/* This creates an array with all balances */
mapping (address => uint256) public balanceOf;
mapping (address => mapping (address => uint256)) public allowance;
/* This generates a public event on the blockchain that will notify clients */
event Transfer(address indexed from, address indexed to, uint256 value);
/* Allow another contract to spend some tokens in your behalf */
function approveAndCall(address _spender, uint256 _value, bytes _extraData)
returns (bool success) {
allowance[msg.sender][_spender] = _value;
tokenRecipient spender = tokenRecipient(_spender);
spender.receiveApproval(msg.sender, _value, this, _extraData);
return true;
}
/* This unnamed function is called whenever someone tries to send ether to it */
function () {
throw; // Prevents accidental sending of ether
}
}
contract GSI is owned {
event OracleRequest(address target);
GSIToken public greenToken;
GSIToken public greyToken;
uint256 public requiredGas;
uint256 public secondsBetweenReadings;
mapping(address=>Reading) public lastReading;
mapping(address=>Reading) public requestReading;
mapping(address=>uint8) public freeReadings;
struct Reading {
uint256 timestamp;
uint256 value;
string zip;
}
function GSI() {
greenToken = new GSIToken(
0,
'GreenPower',
0,
'P+',
this
);
//greenToken.mintToken(msg.sender,10000);
greyToken = new GSIToken(
0,
'GreyPower',
0,
'P-',
this
);
}
function oracalizeReading(uint256 _reading,string _zip) {
if(msg.value<requiredGas) {
if(freeReadings[msg.sender]==0) throw;
freeReadings[msg.sender]--;
}
if(_reading<lastReading[msg.sender].value) throw;
if(_reading<requestReading[msg.sender].value) throw;
if(now<lastReading[msg.sender].timestamp+secondsBetweenReadings) throw;
//lastReading[msg.sender]=requestReading[msg.sender];
requestReading[msg.sender]=Reading(now,_reading,_zip);
OracleRequest(msg.sender);
owner.send(msg.value);
}
function setReadingDelay(uint256 delay) onlyOwner {
secondsBetweenReadings=delay;
}
function assignFreeReadings(address _receiver,uint8 _count) onlyOwner {
freeReadings[_receiver]+=_count;
}
function mintGreen(address recipient,uint256 tokens) onlyOwner {
greenToken.mintToken(recipient, tokens);
}
function mintGrey(address recipient,uint256 tokens) onlyOwner {
greyToken.mintToken(recipient, tokens);
}
function commitReading(address recipient,uint256 timestamp,uint256 reading,string zip) onlyOwner {
if(this.balance>0) {
owner.send(this.balance);
}
lastReading[recipient]=Reading(timestamp,reading,zip);
}
function setOracleGas(uint256 _requiredGas) onlyOwner {
requiredGas=_requiredGas;
}
function() {
if(msg.value>0) {
owner.send(msg.value);
}
}
}External Links
Related contracts
GreenPower
Same deployerCertificate token for renewable generation, owner priced and freezable.
0xa37fb3...ea0020August 22, 2016GreenPower
Same deployerRenewable generation certificate, a later revision of the same accounting system.
0x55e7c4...25e012August 26, 2016TT
Same eraA fixed-supply token with direct transfers only, deployed July 2016.
0xf78bdd...f9d225July 20, 2016shares
Same eraAn early on-chain corporation contract by cryptonomica.net, representing company shares as ERC-20 tokens with embedded voting — deployed hours before the DAO ha
0x684282...9a33b5July 20, 2016MyToken
Same eraA fixed-supply token with transfers and allowance spending, deployed July 2016.
0x0eb106...9be583July 23, 2016ReplayProtection
Same eraAlex Van de Sande's post-DAO-fork ETH/ETC replay-protection splitter. Routes ether or ERC20 tokens to different recipients depending on which chain it runs on.
0x64668c...456541July 27, 2016