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 14 commits into
base: main
Choose a base branch
from
Open

[Certora] Handle overflows #105

wants to merge 14 commits into from

Conversation

colin-morpho
Copy link
Contributor

@colin-morpho colin-morpho commented Dec 16, 2024

Replace absurd revert conditions with safe requirements that have been proven.
Fixes a very small typo in the certora/README.md.
Closes #97.
Fixes #107.

@colin-morpho colin-morpho linked an issue Dec 16, 2024 that may be closed by this pull request
@colin-morpho colin-morpho self-assigned this Dec 16, 2024
MathisGD
MathisGD previously approved these changes Dec 16, 2024
@colin-morpho
Copy link
Contributor Author

I think it's even possible to actually require the invariants themselves.

Copy link
Contributor

@QGarchery QGarchery left a comment

Choose a reason for hiding this comment

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

Looks great, but it seems like there are more of the same to do in MintBurn specification. For example:

toVotingPowerBefore + amount > max_uint256;

@colin-morpho
Copy link
Contributor Author

colin-morpho commented Dec 16, 2024

I think it's even possible to actually require the invariants themselves.

Actually it isn't because the invriants require the munging setup which introduce new possible owerflows related to the zero virtual voting power.

toVotingPowerBefore + amount > max_uint256;

@QGarchery I think this is a legitimate reason to revert, isn't it?

Fixed in 6ab5bad.

@QGarchery
Copy link
Contributor

A couple more to fix :

assert e.msg.sender == 0x0 || fromBalanceBefore < amount || fromVotingPowerBefore < amount ;

@colin-morpho
Copy link
Contributor Author

A couple more to fix :

@QGarchery, I haven't managed to get these ones do not go through because of the same reason as :

Actually it isn't because the invriants require the munging setup which introduce new possible owerflows related to the zero virtual voting power.

In particular, when votes are delegated to zero, burn subtracts the amount from the zeroVirtualVotingPower causing a revert that is caught by fromVotingPowerBefore < amount .

@QGarchery
Copy link
Contributor

In particular, when votes are delegated to zero, burn subtracts the amount from the zeroVirtualVotingPower causing a revert that is caught by fromVotingPowerBefore < amount

Good point, but I think we can still frame it in terms of a "safe require". Here the invariant that we would want is that the balance of the sender is less that _zeroVirtualVotingPower in case where the sender delegates to 0

@colin-morpho
Copy link
Contributor Author

colin-morpho commented Dec 16, 2024

Good point, but I think we can still frame it in terms of a "safe require". Here the invariant that we would want is that the balance of the sender is less that _zeroVirtualVotingPower in case where the sender delegates to 0

Just requiring the delegatee(from) == 0 => fromBalanceBefore <= _zeroVirtualVotingPower isn't enough (see this run), it looks like the prover isn't able to figure out that amount <= fromBalanceBefore <= fromVotingPowerBefore.

certora/specs/ERC20.spec Outdated Show resolved Hide resolved
certora/specs/ERC20.spec Outdated Show resolved Hide resolved

// Check that the delegated voting power of a delegatee after an update is lesser than or equal to the total supply of tokens.
rule updatedDelegatedVPLTEqTotalSupply(env e, address to, uint256 amount) {
// Safe require as implementation woud revert.
Copy link
Contributor

Choose a reason for hiding this comment

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

Which implementation ? This is not as other rules, this one is to be used as an invariant. This means that you can require what you want, it will just have to be added in the premisses. For example, if you have the following rule:

require A;
require B;
assert C;

then later on you will be able to have the following "safe require":
require A => B => C;

Copy link
Contributor Author

Choose a reason for hiding this comment

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

You're right indeed!

Copy link
Contributor Author

@colin-morpho colin-morpho Jan 16, 2025

Choose a reason for hiding this comment

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

I changed the require in fdbcc97.

Copy link
Contributor

Choose a reason for hiding this comment

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

The commit linked does not change this part of the code right ?

Copy link
Contributor

@QGarchery QGarchery Jan 16, 2025

Choose a reason for hiding this comment

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

The new code still mentions "safe require because XXX implementation would revert", but this rule is not tied to any particular function called. Indeed this will be used as an invariant.
Those require statements are "safe" because then you would add them as premises when you use use that property. This is the same as in my message above, by doing require A => B => C. This would be similar as doing requireInvariant inv() if inv is the invariant A => B => C. You wouldn't say that, in such an invariant, A or B is a safe premise because a particular implementation would revert

certora/specs/Delegation.spec Outdated Show resolved Hide resolved
certora/specs/RevertsERC20.spec Outdated Show resolved Hide resolved
certora/specs/RevertsERC20.spec Outdated Show resolved Hide resolved
certora/specs/Delegation.spec Outdated Show resolved Hide resolved
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Unsound "safe" require delegatedLTEqDelegateeVP [Certora] Check underflow and overflows.
3 participants