Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Certora] Handle overflows #105

Open
wants to merge 21 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 15 additions & 9 deletions certora/specs/Delegation.spec
Original file line number Diff line number Diff line change
Expand Up @@ -216,28 +216,34 @@ rule delegatingWithSigUpdatesVotingPower(env e, DelegationToken.Delegation deleg
}

// Check that the updated voting power of a delegatee after a transfer is lesser than or equal to the total supply of tokens.
rule updatedDelegatedVPLTEqTotalSupply(env e, address to, uint256 amount) {
rule updatedDelegatedVPLTEqTotalSupply(address from, address to) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
rule updatedDelegatedVPLTEqTotalSupply(address from, address to) {
rule updatedDelegatedVPLTEqTotalSupply(env e, address from, address to) {

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In this case, let's not do this change. This is because the environment e is ghost, and we want to use this rule as an invariant later. An invariant would not have this environment parameter, so it would make it confusing

uint256 balanceOfFromBefore = balanceOf(from);
uint256 delegatedVotingPowerDelegateeToBefore = delegatedVotingPower(delegatee(to));
uint256 totalSupplyBefore = totalSupply();
env e;
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved

require e.msg.value == 0;
require e.msg.sender != 0;
require e.msg.sender == from;
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved

require amount <= balanceOf(e.msg.sender);
require delegatee(to) != delegatee(e.msg.sender);
require from != 0;
require delegatee(to) != delegatee(from);
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved

requireInvariant sumOfTwoDelegatedVPLTEqTotalVP();
assert isTotalSupplyGTEqSumOfVotingPower();

// This require avoids an impossible revert as zeroVirtualVotingPower operations comme from munging.
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved
require delegatee(e.msg.sender) == 0 => currentContract._zeroVirtualVotingPower >= balanceOf(e.msg.sender);
require delegatee(from) == 0 => currentContract._zeroVirtualVotingPower >= balanceOfFromBefore;


// This invariant can't be required as it's using a parameterized variable.
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved
// But it is proven by delegatedLTEqDelegateeVP.
require delegatee(e.msg.sender) != 0 => delegatedVotingPower(delegatee(e.msg.sender)) >= balanceOf(e.msg.sender);
require delegatee(from) != 0 => delegatedVotingPower(delegatee(from)) >= balanceOfFromBefore;

delegate@withrevert(e, e.msg.sender);
delegate@withrevert(e, from);

assert(!lastReverted);
colin-morpho marked this conversation as resolved.
Show resolved Hide resolved

assert delegatee(e.msg.sender) == e.msg.sender;
assert delegatee(from) == from;

colin-morpho marked this conversation as resolved.
Show resolved Hide resolved
assert delegatedVotingPower(to) + amount <= totalSupply();
assert delegatedVotingPowerDelegateeToBefore + balanceOfFromBefore <= totalSupplyBefore;
}
10 changes: 4 additions & 6 deletions certora/specs/RevertsERC20.spec
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,8 @@ rule transferRevertConditions(env e, address to, uint256 amount) {

// Safe require as it proven in rule updatedDelegatedVPLTEqTotalSupply.
require
e.msg.sender != 0 => e.msg.value == 0 =>
amount <= balanceOfSenderBefore =>
delegatee(to) != delegatee(e.msg.sender) => recipientVotingPowerBefore + amount <= totalSupply();
e.msg.sender != 0 =>
delegatee(to) != delegatee(e.msg.sender) => recipientVotingPowerBefore + balanceOfSenderBefore <= totalSupply();

transfer@withrevert(e, to, amount);
assert lastReverted <=> e.msg.sender == 0 || to == 0 || balanceOfSenderBefore < amount || e.msg.value != 0;
Expand All @@ -43,9 +42,8 @@ rule transferFromRevertConditions(env e, address from, address to, uint256 amoun

// Safe require as it proven in rule updatedDelegatedVPLTEqTotalSupply.
require
from != 0 => e.msg.value == 0 =>
amount <= balanceOfHolderBefore =>
delegatee(to) != delegatee(from) => recipientVotingPowerBefore + amount <= totalSupply();
from != 0 =>
delegatee(to) != delegatee(from) => recipientVotingPowerBefore + balanceOfHolderBefore <= totalSupply();

transferFrom@withrevert(e, from, to, amount);

Expand Down