Created
January 3, 2018 14:07
-
-
Save AlexShkor/42bf4d6c40741fa3b2dae96b9aa6b1bb to your computer and use it in GitHub Desktop.
This file contains 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
pragma solidity ^0.4.17; | |
contract AtomicSwap { | |
enum State { Empty, Initiator, Participant } | |
struct Swap { | |
uint initTimestamp; | |
uint refundTime; | |
bytes20 hashedSecret; | |
bytes32 secret; | |
address initiator; | |
address participant; | |
uint256 value; | |
bool emptied; | |
State state; | |
} | |
mapping(bytes20 => Swap) public swaps; | |
event Refunded(uint _refundTime); | |
event Redeemed(uint _redeemTime); | |
function AtomicSwap() {} | |
modifier isRefundable(bytes20 _hashedSecret) { | |
require(block.timestamp > swaps[_hashedSecret].initTimestamp + swaps[_hashedSecret].refundTime); | |
require(swaps[_hashedSecret].emptied == false); | |
_; | |
} | |
modifier isRedeemable(bytes20 _hashedSecret, bytes32 _secret) { | |
require(ripemd160(_secret) == _hashedSecret); | |
require(block.timestamp < swaps[_hashedSecret].initTimestamp + swaps[_hashedSecret].refundTime); | |
require(swaps[_hashedSecret].emptied == false); | |
_; | |
} | |
function getHash(bytes32 secret) constant returns(bytes20){ | |
return ripemd160(secret); | |
} | |
function doesMatch(bytes20 _hashedSecret, bytes32 _secret) constant returns (bool){ | |
return ripemd160(_secret) == _hashedSecret; | |
} | |
modifier isInitiator(bytes20 _hashedSecret) { | |
require(msg.sender == swaps[_hashedSecret].initiator); | |
_; | |
} | |
modifier isNotInitiated(bytes20 _hashedSecret) { | |
require(swaps[_hashedSecret].state == State.Empty); | |
_; | |
} | |
function initiate (bytes20 _hashedSecret,address _participant) | |
payable | |
isNotInitiated(_hashedSecret) | |
{ | |
swaps[_hashedSecret].refundTime = 48 hours; | |
swaps[_hashedSecret].initTimestamp = block.timestamp; | |
swaps[_hashedSecret].hashedSecret = _hashedSecret; | |
swaps[_hashedSecret].participant = _participant; | |
swaps[_hashedSecret].initiator = msg.sender; | |
swaps[_hashedSecret].state = State.Initiator; | |
swaps[_hashedSecret].value = msg.value; | |
} | |
function participate(bytes20 _hashedSecret,address _initiator) | |
payable | |
isNotInitiated(_hashedSecret) | |
{ | |
swaps[_hashedSecret].refundTime = 24 hours; | |
swaps[_hashedSecret].initTimestamp = block.timestamp; | |
swaps[_hashedSecret].participant = msg.sender; | |
swaps[_hashedSecret].initiator = _initiator; | |
swaps[_hashedSecret].value = msg.value; | |
swaps[_hashedSecret].hashedSecret = _hashedSecret; | |
swaps[_hashedSecret].state = State.Participant; | |
} | |
function redeem(bytes32 _secret, bytes20 _hashedSecret) | |
isRedeemable(_hashedSecret, _secret) | |
{ | |
if(swaps[_hashedSecret].state == State.Participant){ | |
swaps[_hashedSecret].initiator.transfer(swaps[_hashedSecret].value); | |
} | |
if(swaps[_hashedSecret].state == State.Initiator){ | |
swaps[_hashedSecret].participant.transfer(swaps[_hashedSecret].value); | |
} | |
swaps[_hashedSecret].emptied = true; | |
Redeemed(block.timestamp); | |
swaps[_hashedSecret].secret = _secret; | |
} | |
function refund(bytes20 _hashedSecret) | |
isRefundable(_hashedSecret) | |
{ | |
if(swaps[_hashedSecret].state == State.Participant){ | |
swaps[_hashedSecret].participant.transfer(swaps[_hashedSecret].value); | |
} | |
if(swaps[_hashedSecret].state == State.Initiator){ | |
swaps[_hashedSecret].initiator.transfer(swaps[_hashedSecret].value); | |
} | |
swaps[_hashedSecret].emptied = true; | |
Refunded(block.timestamp); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment