Skip to content

Instantly share code, notes, and snippets.

@bobkilla
Last active April 25, 2018 11:20
Show Gist options
  • Save bobkilla/0f0ef8f425ad16f8f33b44506019908b to your computer and use it in GitHub Desktop.
Save bobkilla/0f0ef8f425ad16f8f33b44506019908b to your computer and use it in GitHub Desktop.
/**
* @title Rock Paper Scissors Lizard Spock
* @author Nicolas Wagner - <nicolas@kleros.io>
*/
/* 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. */
pragma solidity ^0.4.22;
contract AbstractRPS {
address public j1; // The first player creating the contract.
address public j2; // The second player.
enum Move {Null, Rock, Paper, Scissors, Spock, Lizard} // Possible moves. Note that if the parity of the moves is the same the lower one wins, otherwise the higher one.
bytes32 public c1Hash; // Commitment of j1.
Move public c2; // Move of j2. Move.Null before he played.
uint256 public stake; // Amout bet by each party.
// constructor(bytes32 _c1Hash, address _j2) public payable;
function play(Move _c2) public payable;
function solve(Move _c1, uint256 _salt) public
function win(Move _c1, Move _c2) private pure returns (bool w);
}
contract RPS is AbstractRPS {
/** @dev Constructor. Must send the amount at stake when creating the contract. Note that the move and salt must be saved.
* @param _c1Hash Must be equal to keccak256(c1,salt) where c1 is the move of the j1.
*/
constructor RPS(bytes32 _c1Hash, address _j2) public payable {
// set up j1 with msg.sender, then j2 and c1
// set up stake with msg.value
}
/** @dev To be called by j2 and provided stake.
* @param _c2 The move submitted by j2.
*/
function play(Move _c2) public payable {
// check if J2 has not played yet
// check if J2 paid the stake
// check if J2 calls this function
// set up c2
}
/** @dev To be called by j1. Reveal the move and send the ETH to the winning party or split them.
* @param _c1 The move played by j1.
* @param _salt The salt used when submitting the commitment when the constructor was called.
*/
function solve(Move _c1, uint256 _salt) public {
// check if J2 have played
// check if J1 calls this function
// verify the value is the commited one
if (win(c1,_c2))
// send the total amount to j1 with j1.transfer(amount)
else if (win(_c2,c1))
// send the total amount to j2
else {
// same move
// so withdraw amount for j1 and j2
}
// reset the stake
}
/** @dev Is this move winning over the other.
* @param _m1 The first move.
* @param _m2 The move the first move is considered again.
* @return w True if c1 beats c2. False if c1 is beaten by c2 or in case of tie.
*/
function win(Move _m1, Move _m2) private pure returns (bool w) {
if (_m1 == _m2)
return false; // They played the same so no winner.
else if (// if these moves are even or odd)
// if the first move is higher than 2nd move, the first wins else return false
else
// if the first move is lower than 2nd move, the second player wins else return false
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment