Skip to content

Instantly share code, notes, and snippets.

View bartubozkurt's full-sized avatar
🎯
Focusing

Bartu Bozkurt bartubozkurt

🎯
Focusing
View GitHub Profile
@bartubozkurt
bartubozkurt / DivideBeforeMultiply.sol
Last active February 2, 2023 11:10
DivideBeforeMultiply.sol
/* Bad */
int totalValue = 275000;
int percentage = 2;
for (uint i = 0; i < 30; i++) {
totalValue += totalValue * percentage / 100;
}
/*
Exact value: 498124.436
Result: 498108
*/
/* Bad */
pragma solidity =0.4.11;
contract Bad {
mapping(address => uint256) balances;
function badWithdraw(uint256 amounts) public {
require(amounts <= balances[msg.sender]);
balances[msg.sender] -= amounts;
(bool success, bytes memory data) = msg.sender.call{value: amounts}("");
require(success);
}
/* Bad */
contract TimedCrowdsale {
event Finished();
event notFinished();
// Sale should finish exactly at January 1, 2019
function isSaleFinished() private returns (bool) {
return block.timestamp >= 1546300800;
}
/* Bad */
function getRandomNum() public view returns(uint256 randomNum_) {
randomNum_ = uint256(keccak256(block.blockhash(block.number - 1), now))
}
/* Better */
// Using VRF by Chainlink
// https://docs.chain.link/docs/vrf/v2/examples/get-a-random-number/
/* Bad */
string private password;
/* Better */
// string private password
// shouldn't store the password on blockchain
/* Bad */
function badWithdraw(uint amounts) public {
require(amounts <= balances[msg.sender]); // 1.π—–π—›π—˜π—–π—ž
// there is no risk of reentrancy because transfer is 2300 gas
msg.sender.transfer(amounts) // 3.π—œπ—‘π—§π—˜π—₯π—”π—–π—§π—œπ—’π—‘
balances[msg.sender] - amounts; // 2.π—˜π—™π—™π—˜π—–π—§π—¦
}
/* Better */
function goodWithdraw(uint amounts) public {
contract Guarded {
...
bool locked = false;
function withdraw() external {
require(!locked, "Reentrant call detected!");
locked = true;
...
locked = false;
address token;
mapping(address => uint) canBorrowAmount;
/* Bad */
function badBorrow(uint amounts) public {
require(amounts <= canBorrowAmount[msg.sender]); // 1.π—–π—›π—˜π—–π—ž
IERC777(token).transfer(msg.sender, amounts) // 3.π—œπ—‘π—§π—˜π—₯π—”π—–π—§π—œπ—’π—‘
canBorrowAmount[msg.sender] - amounts; // 2.π—˜π—™π—™π—˜π—–π—§π—¦
}
/* Better */
/* Bad */
function badWithdraw(uint amounts) public {
require(amounts <= balances[msg.sender]); // 1.π—–π—›π—˜π—–π—ž
(bool success, bytes memory data)
= msg.sender.call{value: amounts}(""); // 3.π—œπ—‘π—§π—˜π—₯π—”π—–π—§π—œπ—’π—‘
require(success);
balances[msg.sender] - amounts; // 2.π—˜π—™π—™π—˜π—–π—§π—¦
}
/* Better */
/* Bad */
contract Bad {
function badDelegate(address _yourContract, bytes calldata _data) payable public returns (bytes memory) {
(bool success, bytes memory data) = _yourContract.delegatecall(_data);
require(success);
return data;
}
}
/* Vulnerability
Anyone can destroy the Bad contract using by β€œselfdestruct”