Skip to content

Instantly share code, notes, and snippets.

@CashBag
Last active January 11, 2018 12:40
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save CashBag/ddab853dfc696dcc0b34bbf76ba33074 to your computer and use it in GitHub Desktop.
Save CashBag/ddab853dfc696dcc0b34bbf76ba33074 to your computer and use it in GitHub Desktop.
CashBag Token Sale

README

This README is to provide s short overview of the CashBag Token Sale solidity pages.

What is this repository for?

Quick summary

Version 1

How do I get set up?

Install mist

Ensure there are ETH in your wallet account

Create a multisig contract with multiple wallet accounts

Create a new contract for using the token code

Create a new contract using the crowdsale code and the token address and the multisig address

pragma solidity 0.4.18;
/**
* @title SafeMath
* @dev Math operations with safety checks that throw on error
*/
library SafeMath {
function mul(uint256 a, uint256 b) internal pure returns (uint256) {
if (a == 0) {
return 0;
}
uint256 c = a * b;
assert(c / a == b);
return c;
}
function div(uint256 a, uint256 b) internal pure returns (uint256) {
// assert(b > 0); // Solidity automatically throws when dividing by 0
uint256 c = a / b;
// assert(a == b * c + a % b); // There is no case in which this doesn't hold
return c;
}
function sub(uint256 a, uint256 b) internal pure returns (uint256) {
assert(b <= a);
return a - b;
}
function add(uint256 a, uint256 b) internal pure returns (uint256) {
uint256 c = a + b;
assert(c >= a);
return c;
}
}
interface token {
function transfer(address receiver, uint amount) public;
}
/**
* @title Ownable
* @dev The Ownable contract has an owner address, and provides basic authorization control
* functions, this simplifies the implementation of "user permissions".
*/
contract Ownable {
address public owner;
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
/**
* @dev The Ownable constructor sets the original `owner` of the contract to the sender
* account.
*/
function Ownable() public {
owner = msg.sender;
}
/**
* @dev Throws if called by any account other than the owner.
*/
modifier onlyOwner() {
require(msg.sender == owner);
_;
}
/**
* @dev Allows the current owner to transfer control of the contract to a newOwner.
* @param newOwner The address to transfer ownership to.
*/
function transferOwnership(address newOwner) public onlyOwner {
require(newOwner != address(0));
OwnershipTransferred(owner, newOwner);
owner = newOwner;
}
}
/*
* Haltable
*
* Abstract contract that allows children to implement an
* emergency stop mechanism. Differs from Pausable by causing a throw when in halt mode.
*
*
* Originally envisioned in FirstBlood ICO contract.
*/
contract Haltable is Ownable {
bool public halted;
modifier stopInEmergency {
if (halted) revert();
_;
}
modifier onlyInEmergency {
if (!halted) revert();
_;
}
// called by the owner on emergency, triggers stopped state
function halt() external onlyOwner {
halted = true;
}
// called by the owner on end of emergency, returns to normal state
function unhalt() external onlyOwner onlyInEmergency {
halted = false;
}
}
////////////////////////////////////////////////////////////////////////////////////////
contract Crowdsale is Haltable {
using SafeMath for uint256;
event GoalReached(address beneficiary, uint amountRaised);
event FundTransfer(address backer, uint amount, bool isContribution);
// Crowdsale end time has been changed
event EndsAtChanged(uint deadline);
event CSClosed(bool crowdsaleClosed);
address public beneficiary;
uint public fundingGoal;
uint public amountRaised;
uint public amountAvailable;
uint public deadline;
uint public price;
token public tokenReward;
mapping(address => uint256) public balanceOf;
bool public fundingGoalReached = false;
bool public crowdsaleClosed = false;
uint public numTokensLeft;
uint public numTokensSold;
/* the UNIX timestamp end date of the crowdsale */
// uint public newDeadline;
/**
* Constrctor function
*
* Setup the owner
*/
function Crowdsale(
address ifSuccessfulSendTo,
uint fundingGoalInEthers,
// uint durationInMinutes,
// uint etherCostOfEachToken,
address addressOfTokenUsedAsReward,
// uint _start,
uint unixTimestampEnd,
uint initialTokenSupply
) public {
owner = msg.sender;
if(unixTimestampEnd == 0) {
revert();
}
uint dec = 1000000000;
//numTokensLeft = initialTokenSupply * 1000000000;
numTokensLeft = initialTokenSupply.mul(dec);
deadline = unixTimestampEnd;
// Don't mess the dates
if(now >= deadline) {
revert();
}
beneficiary = ifSuccessfulSendTo;
fundingGoal = fundingGoalInEthers * 1 ether;
price = 0.000000000000166666 ether;
tokenReward = token(addressOfTokenUsedAsReward);
}
/**
* Fallback function
*
* The function without name is the default function that is called whenever anyone sends funds to a contract
*/
function () public stopInEmergency payable {
require(!crowdsaleClosed);
uint amount = msg.value;
uint leastAmount = 100000000000;
uint numTokens = amount.div(price);
uint stageTwo = 1512050080; // 11/30/2017 @ 1:54pm (UTC)
uint stageThree = 1512055080;// 11/10/2017 @ 10:00am (UTC) - 1800 / 30min
uint stageFour = 1512133080;// 11/10/2017 @ 15:00pm (UTC)
uint numBonusTokens;
uint totalNumTokens;
/////////////////////////////
// Next step is to add in a check to see once the new price goes live
////////////////////////////
if(now < stageTwo)
{
// 20% bonus
numBonusTokens = (numTokens.div(100)).mul(20);
totalNumTokens = numTokens.add(numBonusTokens);
}
else if(now < stageThree){
// 15% bonus
numBonusTokens = (numTokens.div(100)).mul(15);
totalNumTokens = numTokens.add(numBonusTokens);
}
else if(now < stageFour){
// 10% bonus
//numBonusTokens = (numTokens / 20) * 2;
numBonusTokens = (numTokens.div(100)).mul(10);
totalNumTokens = numTokens.add(numBonusTokens);
}
else{
numBonusTokens = 0;
totalNumTokens = numTokens.add(numBonusTokens);
}
// do not sell less than 100 tokens at a time.
if (numTokens <= leastAmount) {
revert();
} else {
// balanceOf[msg.sender] += amount;
// amountRaised += amount;
// amountAvailable += amount;
// numTokensSold += totalNumTokens;
// numTokensLeft -= totalNumTokens;
balanceOf[msg.sender] = balanceOf[msg.sender].add(amount);
amountRaised = amountRaised.add(amount);
amountAvailable = amountAvailable.add(amount);
numTokensSold = numTokensSold.add(totalNumTokens);
numTokensLeft = numTokensLeft.sub(totalNumTokens);
tokenReward.transfer(msg.sender, totalNumTokens);
FundTransfer(msg.sender, amount, true);
}
}
/**
* Withdraw the funds
*
* Checks to see if goal or time limit has been reached, and if so, and the funding goal was reached,
* sends the entire amount to the beneficiary. If goal was not reached, each contributor can withdraw
* the amount they contributed.
*/
function safeWithdrawal() public onlyOwner{
if(amountAvailable < 0)
{
revert();
}
else
{
uint amtA = amountAvailable;
amountAvailable = 0;
beneficiary.transfer(amtA);
}
}
///////////////////////////////////////////////////////////
// Withdraw tokens
///////////////////////////////////////////////////////////
function withdrawTheUnsoldTokens() public onlyOwner afterDeadline{
if(numTokensLeft <= 0)
{
revert();
}
else
{
uint ntl = numTokensLeft;
numTokensLeft=0;
tokenReward.transfer(beneficiary, ntl);
crowdsaleClosed = true;
CSClosed(crowdsaleClosed);
}
}
/////////////////////////////////////////////////////////////
// give the crowdsale a new newDeadline
////////////////////////////////////////////////////////////
modifier afterDeadline() { if (now >= deadline) _; }
function setDeadline(uint time) public onlyOwner {
if(now > time || msg.sender==beneficiary)
{
revert(); // Don't change past
}
deadline = time;
EndsAtChanged(deadline);
}
///////////////////////////////////////////////////////////////////////////////////////////////
}
pragma solidity 0.4.18;
// ----------------------------------------------------------------------------
//
// Symbol : CBC
// Name : CashBag Coin
// Total supply: 367,000,000.000000000000000000
// Decimals : 9
//
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
// Safe maths
// ----------------------------------------------------------------------------
library SafeMath {
function add(uint a, uint b) internal pure returns (uint c) {
c = a + b;
require(c >= a);
}
function sub(uint a, uint b) internal pure returns (uint c) {
require(b <= a);
c = a - b;
}
function mul(uint a, uint b) internal pure returns (uint c) {
c = a * b;
require(a == 0 || c / a == b);
}
function div(uint a, uint b) internal pure returns (uint c) {
require(b > 0);
c = a / b;
}
}
// ----------------------------------------------------------------------------
// ERC Token Standard #20 Interface
// https://github.com/ethereum/EIPs/blob/master/EIPS/eip-20-token-standard.md
// ----------------------------------------------------------------------------
contract ERC20Interface {
function totalSupply() public constant returns (uint);
function balanceOf(address tokenOwner) public constant returns (uint balance);
function allowance(address tokenOwner, address spender) public constant returns (uint remaining);
function transfer(address to, uint tokens) public returns (bool success);
function approve(address spender, uint tokens) public returns (bool success);
function transferFrom(address from, address to, uint tokens) public returns (bool success);
event Transfer(address indexed from, address indexed to, uint tokens);
event Approval(address indexed tokenOwner, address indexed spender, uint tokens);
}
// ----------------------------------------------------------------------------
// Contract function to receive approval and execute function in one call
//
// Borrowed from MiniMeToken
// ----------------------------------------------------------------------------
contract ApproveAndCallFallBack {
function receiveApproval(address from, uint256 tokens, address token, bytes data) public;
}
// ----------------------------------------------------------------------------
// Owned contract
// ----------------------------------------------------------------------------
contract Owned {
address public owner;
address public newOwner;
event OwnershipTransferred(address indexed _from, address indexed _to);
function Owned() public {
owner = msg.sender;
}
modifier onlyOwner {
require(msg.sender == owner);
_;
}
function transferOwnership(address _newOwner) public onlyOwner {
newOwner = _newOwner;
}
function acceptOwnership() public {
require(msg.sender == newOwner);
OwnershipTransferred(owner, newOwner);
owner = newOwner;
newOwner = address(0);
}
}
// ----------------------------------------------------------------------------
// ERC20 Token, with the addition of symbol, name and decimals and an
// initial fixed supply
// ----------------------------------------------------------------------------
contract FixedSupplyToken is ERC20Interface, Owned {
using SafeMath for uint;
string public symbol;
string public name;
uint8 public decimals;
uint public _totalSupply;
mapping(address => uint) balances;
mapping(address => mapping(address => uint)) allowed;
// ------------------------------------------------------------------------
// Constructor
// ------------------------------------------------------------------------
function FixedSupplyToken() public {
symbol = "CBC";
name = "CashBag Coin";
decimals = 9;
_totalSupply = 367000000 * 10 ** uint(decimals);
balances[owner] = _totalSupply;
Transfer(address(0), owner, _totalSupply);
}
// ------------------------------------------------------------------------
// Total supply
// ------------------------------------------------------------------------
function totalSupply() public constant returns (uint) {
return _totalSupply - balances[address(0)];
}
// ------------------------------------------------------------------------
// Get the token balance for account `tokenOwner`
// ------------------------------------------------------------------------
function balanceOf(address tokenOwner) public constant returns (uint balance) {
return balances[tokenOwner];
}
// ------------------------------------------------------------------------
// Transfer the balance from token owner's account to `to` account
// - Owner's account must have sufficient balance to transfer
// - 0 value transfers are allowed
// ------------------------------------------------------------------------
function transfer(address to, uint tokens) public returns (bool success) {
balances[msg.sender] = balances[msg.sender].sub(tokens);
balances[to] = balances[to].add(tokens);
Transfer(msg.sender, to, tokens);
return true;
}
// ------------------------------------------------------------------------
// Token owner can approve for `spender` to transferFrom(...) `tokens`
// from the token owner's account
//
// https://github.com/ethereum/EIPs/blob/master/EIPS/eip-20-token-standard.md
// recommends that there are no checks for the approval double-spend attack
// as this should be implemented in user interfaces
// ------------------------------------------------------------------------
function approve(address spender, uint tokens) public returns (bool success) {
allowed[msg.sender][spender] = tokens;
Approval(msg.sender, spender, tokens);
return true;
}
// ------------------------------------------------------------------------
// Transfer `tokens` from the `from` account to the `to` account
//
// The calling account must already have sufficient tokens approve(...)-d
// for spending from the `from` account and
// - From account must have sufficient balance to transfer
// - Spender must have sufficient allowance to transfer
// - 0 value transfers are allowed
// ------------------------------------------------------------------------
function transferFrom(address from, address to, uint tokens) public returns (bool success) {
balances[from] = balances[from].sub(tokens);
allowed[from][msg.sender] = allowed[from][msg.sender].sub(tokens);
balances[to] = balances[to].add(tokens);
Transfer(from, to, tokens);
return true;
}
// ------------------------------------------------------------------------
// Returns the amount of tokens approved by the owner that can be
// transferred to the spender's account
// ------------------------------------------------------------------------
function allowance(address tokenOwner, address spender) public constant returns (uint remaining) {
return allowed[tokenOwner][spender];
}
// ------------------------------------------------------------------------
// Token owner can approve for `spender` to transferFrom(...) `tokens`
// from the token owner's account. The `spender` contract function
// `receiveApproval(...)` is then executed
// ------------------------------------------------------------------------
function approveAndCall(address spender, uint tokens, bytes data) public returns (bool success) {
allowed[msg.sender][spender] = tokens;
Approval(msg.sender, spender, tokens);
ApproveAndCallFallBack(spender).receiveApproval(msg.sender, tokens, this, data);
return true;
}
// ------------------------------------------------------------------------
// Don't accept ETH
// ------------------------------------------------------------------------
function() public payable {
revert();
}
// ------------------------------------------------------------------------
// Owner can transfer out any accidentally sent ERC20 tokens
// ------------------------------------------------------------------------
function transferAnyERC20Token(address tokenAddress, uint tokens) public onlyOwner returns (bool success) {
return ERC20Interface(tokenAddress).transfer(owner, tokens);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment