Skip to content

Commit

Permalink
Format code in markdown
Browse files Browse the repository at this point in the history
  • Loading branch information
0xPhaze committed Mar 8, 2023
1 parent 565d767 commit 37c09c3
Show file tree
Hide file tree
Showing 29 changed files with 414 additions and 410 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -8,19 +8,20 @@ Suppose that the following code to initiate L2 deposits from L1. The first examp

```solidity
uint256 public constant STARKNET_FIELD_PRIME; // the prime order P of the elliptic curve used
IERC20 public constant token; //some token to deposit on L2
IERC20 public constant token; // some token to deposit on L2
event Deposited(uint256 sender, uint256 amount);
function badDepositToL2(uint256 to, uint256 amount) public returns (bool) {
token.transferFrom(to, address(this),amount);
emit Deposited(to,amount); // this message gets processed on L2
function badDepositToL2(uint256 to, uint256 amount) public returns (bool) {
token.transferFrom(to, address(this), amount);
emit Deposited(to, amount); // this message gets processed on L2
return true;
}
function betterDepositToL2(uint256 to, uint256 amount) public returns (bool) {
require(to !=0 && to < STARKNET_FIELD_PRIME, "invalid address"); //verifies 0 < to < P
token.transferFrom(to, address(this),amount);
emit Deposited(to,amount); // this message gets processed on L2
function betterDepositToL2(uint256 to, uint256 amount) public returns (bool) {
require(to != 0 && to < STARKNET_FIELD_PRIME, "invalid address"); // verifies 0 < to < P
token.transferFrom(to, address(this), amount);
emit Deposited(to, amount); // this message gets processed on L2
return true;
}
```
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,12 @@ For instance, a message can fail to be processed if there is a sudden spike in t
Suppose that the following code to initiate L2 deposits from L1, taking the tokens from the user:

```solidity
IERC20 public constant token; //some token to deposit on L2
IERC20 public constant token; // some token to deposit on L2
function depositToL2(uint256 to, uint256 amount) public returns (bool) {
function depositToL2(uint256 to, uint256 amount) public returns (bool) {
require(token.transferFrom(to, address(this), amount));
..
StarknetCore.sendMessageToL2(..);
...
StarknetCore.sendMessageToL2(...);
return true;
}
```
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,31 +17,31 @@ from openzeppelin.a import A
from openzeppelin.b import B
@external
func increase_balance_a{
func increase_balance_a {
syscall_ptr : felt*, pedersen_ptr : HashBuiltin*,
range_check_ptr}(amount : felt):
A.increase_balance(amount)
return ()
end
@external
func increase_balance_b{
func increase_balance_b {
syscall_ptr : felt*, pedersen_ptr : HashBuiltin*,
range_check_ptr}(amount : felt):
B.increase_balance(amount)
return ()
end
@view
func get_balance_a{
func get_balance_a {
syscall_ptr : felt*, pedersen_ptr : HashBuiltin*,
range_check_ptr}() -> (res : felt):
let (res) = A.get_balance()
return (res)
end
@view
func get_balance_b{
func get_balance_b {
syscall_ptr : felt*, pedersen_ptr : HashBuiltin*,
range_check_ptr}() -> (res : felt):
let (res) = B.get_balance()
Expand Down
30 changes: 15 additions & 15 deletions program-analysis/echidna/advanced/collecting-a-corpus.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,19 +13,19 @@ We will see how to collect and use a corpus of transactions with Echidna. The ta

```Solidity
contract C {
bool value_found = false;
function magic(uint magic_1, uint magic_2, uint magic_3, uint magic_4) public {
require(magic_1 == 42);
require(magic_2 == 129);
require(magic_3 == magic_4+333);
value_found = true;
return;
}
function echidna_magic_values() public returns (bool) {
return !value_found;
}
bool value_found = false;
function magic(uint256 magic_1, uint256 magic_2, uint256 magic_3, uint256 magic_4) public {
require(magic_1 == 42);
require(magic_2 == 129);
require(magic_3 == magic_4 + 333);
value_found = true;
return;
}
function echidna_magic_values() public returns (bool) {
return !value_found;
}
}
```

Expand Down Expand Up @@ -69,7 +69,7 @@ Echidna still cannot find the correct magic value. We can verify where it gets s
```
r |contract C {
bool value_found = false;
r | function magic(uint magic_1, uint magic_2, uint magic_3, uint magic_4) public {
r | function magic(uint256 magic_1, uint256 magic_2, uint256 magic_3, uint256 magic_4) public {
r | require(magic_1 == 42);
r | require(magic_2 == 129);
r | require(magic_3 == magic_4+333);
Expand Down Expand Up @@ -164,7 +164,7 @@ This time, the property is violated immediately. We can verify that another `cov
```
*r |contract C {
bool value_found = false;
*r | function magic(uint magic_1, uint magic_2, uint magic_3, uint magic_4) public {
*r | function magic(uint256 magic_1, uint256 magic_2, uint256 magic_3, uint256 magic_4) public {
*r | require(magic_1 == 42);
*r | require(magic_2 == 129);
*r | require(magic_3 == magic_4+333);
Expand Down
2 changes: 1 addition & 1 deletion program-analysis/echidna/advanced/end-to-end-testing.md
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ import "../SimpleStorage.sol";
contract E2E {
SimpleStorage st = SimpleStorage(0x871DD7C2B4b25E1Aa18728e9D5f2Af4C4e431f5c);
function crytic_const_storage() public returns(bool) {
function crytic_const_storage() public returns (bool) {
return st.storedData() == 89;
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,24 +15,25 @@ We will see how to find the transactions with high gas consumption with Echidna.

```solidity
contract C {
uint state;
function expensive(uint8 times) internal {
for(uint8 i=0; i < times; i++)
state = state + i;
}
function f(uint x, uint y, uint8 times) public {
if (x == 42 && y == 123)
expensive(times);
else
state = 0;
}
function echidna_test() public returns (bool) {
return true;
}
uint256 state;
function expensive(uint8 times) internal {
for (uint8 i = 0; i < times; i++) {
state = state + i;
}
}
function f(uint256 x, uint256 y, uint8 times) public {
if (x == 42 && y == 123) {
expensive(times);
} else {
state = 0;
}
}
function echidna_test() public returns (bool) {
return true;
}
}
```

Expand Down Expand Up @@ -101,10 +102,10 @@ contract C {
function pop() public {
addrs.pop();
}
function clear() public{
function clear() public {
addrs.length = 0;
}
function check() public{
function check() public {
for(uint256 i = 0; i < addrs.length; i++)
for(uint256 j = i+1; j < addrs.length; j++)
if (addrs[i] == addrs[j])
Expand Down
34 changes: 16 additions & 18 deletions program-analysis/echidna/advanced/hevm-cheats-to-test-permit.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

## Introduction

[EIP 2612](https://eips.ethereum.org/EIPS/eip-2612) introduces the function `permit(address owner, address spender, uint value, uint deadline, uint8 v, bytes32 r, bytes32 s)` to the ERC20 abi. This function essentially takes in signature parameters generated through ECDSA combined with the [EIP 712](https://eips.ethereum.org/EIPS/eip-712) standard for typed data hashing, and recovers the author of the signature through `ecrecover()`. It then sets `allowances[owner][spender]` to `value`.
[EIP 2612](https://eips.ethereum.org/EIPS/eip-2612) introduces the function `permit(address owner, address spender, uint256 value, uint256 deadline, uint8 v, bytes32 r, bytes32 s)` to the ERC20 abi. This function essentially takes in signature parameters generated through ECDSA combined with the [EIP 712](https://eips.ethereum.org/EIPS/eip-712) standard for typed data hashing, and recovers the author of the signature through `ecrecover()`. It then sets `allowances[owner][spender]` to `value`.

## Uses

Expand All @@ -17,24 +17,22 @@ We use solmate’s implementation of the ERC20 standard that includes the permit
In our `TestDepositWithPermit` contract, we need to have the signature signed by an owner for validation. To do this, we can use `hevm`’s `sign` cheatcode, which takes in a message and a private key and creates a valid signature. For this example, we use the private key `0x02` and the following signed message, which essentially represents the permit signature following EIP 712:

```solidity
keccak256(
abi.encodePacked(
"\x19\x01",
asset.DOMAIN_SEPARATOR(),
keccak256(
abi.encode(
keccak256(
"Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"
),
owner,
spender,
assetAmount,
asset.nonces(owner),
block.timestamp
)
)
keccak256(
abi.encodePacked(
"\x19\x01",
asset.DOMAIN_SEPARATOR(),
keccak256(
abi.encode(
keccak256("Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"),
owner,
spender,
assetAmount,
asset.nonces(owner),
block.timestamp
)
);
)
)
);
```

The helper function `getSignature(address owner, address spender, uint256 assetAmount)` returns a valid signature generated via the `sign` cheatcode. Note that the sign cheatcode leaks the private key and thus it is best to use dummy keys when testing. Our keypair data was taken from [this site](https://privatekeys.pw/keys/ethereum/1). Now to test out the signature, we will mint a random amount to the `OWNER` address, the address corresponding to private key `0x02`, which was the signer of the permit signature. We then see if we can use that signature to transfer the owner’s tokens to ourselves.
Expand Down
28 changes: 10 additions & 18 deletions program-analysis/echidna/advanced/optimization_mode.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,10 @@ Optimization mode is a experimental feature that allows to define a special func
and returns a `int256`. Echidna will try find a sequence of transactions to maximize the value returned:

```solidity
function echidna_opt_function() public view returns (int256) {
// if it reverts, Echidna will assumed it returned type(int256).min
return ..;
}
function echidna_opt_function() public view returns (int256) {
// if it reverts, Echidna will assumed it returned type(int256).min
return ...;
}
```

## Optimizing with Echidna
Expand All @@ -29,23 +29,15 @@ In this example, the target is the following smart contract (_[../example/opt.so
contract TestDutchAuctionOptimization {
int256 maxPriceDifference;
function setMaxPriceDifference(
uint256 startPrice,
uint256 endPrice,
uint256 startTime,
uint256 endTime
) public {
if (endTime < (startTime + 900)) {
revert();
}
if (startPrice <= endPrice) {
revert();
}
uint256 numerator = (startPrice - endPrice) *
(block.timestamp - startTime);
function setMaxPriceDifference(uint256 startPrice, uint256 endPrice, uint256 startTime, uint256 endTime) public {
if (endTime < (startTime + 900)) revert();
if (startPrice <= endPrice) revert();
uint256 numerator = (startPrice - endPrice) * (block.timestamp - startTime);
uint256 denominator = endTime - startTime;
uint256 stepDecrease = numerator / denominator;
uint256 currentAuctionPrice = startPrice - stepDecrease;
if (currentAuctionPrice < endPrice) {
maxPriceDifference = int256(endPrice - currentAuctionPrice);
}
Expand Down
Loading

0 comments on commit 37c09c3

Please sign in to comment.