Gearbox-protocol / core-v3

Other
28 stars 4 forks source link

test: minimal invariant tests #195

Open lekhovitsky opened 6 months ago

lekhovitsky commented 6 months ago

Stateful fuzzing of Gearbox is not an easy endeavour. Some actions in staking, gauge or pool contracts are fairly predictable. Most useful actions that can potentially lead to breaking important invariants are on the credit side though, and boi is it hard to fuzz those! Even verifying that a given multicall works is complicated, generating a random one that is guaranteed not to revert is nearly impossible because of all liquidity, solvency and economic security limits present in the system.

Without much hope to make fuzzer explore all the state space, this test suite's main goal's become to make us think deeply about the invariants: what are they? which ones are important? which actions can, in principle, be used to break a given invariant? After answering those questions, fuzzing in the head doesn't differ much from automated fuzzing (especially since there are no intractable math-heavy invariants).

In terms of organization, the suite consists of multiple test contracts (invariant/tests/), each implementing a different scenario of interest. Such contracts first deploy needed parts of the system (invariant/Deployer.sol) and prepare fuzz handlers (invariant/handlers/) in the setUp() function, and then pick which of existing invariants (invariant/Invariants.sol) should be asserted.