Ante Tests Explained: Ribbon Finance

Ante
Ante Labs

--

This post is intended to be a technical overview of the Ribbon Ante Tests and their mechanics.

Background

Ribbon is a DeFi protocol that helps users access DeFi structured products. Their Theta Vault product offers yield through an automated options strategy (the main V2 products at the moment automate weekly covered call strategies).

Ante hosts real-time incentivized on-chain smart contract tests (”Ante Tests”) that pay out when code fails. This aligns teams and users and makes code trust explicit, resulting in a safer, more composable Web3 ecosystem. Responsible protocol teams can explicitly put “skin in the game” by staking their Ante Tests (which anyone can also challenge or stake), boosting their “Decentralized Trust Score”. In turn, developers can reference Ante trust scores to build more safely on top of protocols, and users can more clearly see community trust in protocols real-time.

Ribbon TVL Plunge Test

Code; Live test

AnteRibbonV2ThetaVaultPlungeTest checks that the TVL for any tested Ribbon V2 Theta Vault doesn’t fall by 90% from the time the test is deployed. While TVL is an imperfect metric for overall protocol success, it is a useful proxy for any number of catastrophic scenarios such as:

  • Ribbon usage has declined precipitously
  • Ribbon funds have been drained by a hack/exploit

Basically, if the TVL in the Ribbon V2 Theta Vaults has plunged over 90%, something catastrophic has likely befallen Ribbon.

How it works

The test checks the ETH Covered Call V2 and WBTC Covered Call V2 Theta Vaults. Upon instantiating the Ante Test, the test iterates through the list of vaults and calculates the precise failure threshold for each vault by multiplying the current balance by the drop threshold — 10%.

AnteRibbonV2ThetaVaultPlungeTest.sol, lines 38–44

When checkTestPasses() is called by a challenger, the test iterates through the same set of vaults and compares each vault’s balance to its corresponding failure threshold. If any of the vaults’ TVL is below its threshold, then the entire Ante Test fails and challengers can claim funds.

AnteRibbonV2ThetaVaultPlungeTest.sol, lines 65–73

Let’s take a closer look at how vault balances are calculated in the calculateAssetBalance() helper function. The underlying tokens controlled by the vault are split between two main contracts through the vault lifecycle:

  • Opyn MarginPool contract when underlying has been used to mint call options
  • Ribbon vault contract in basically any other situation: if Ribbon users deposit mid-cycle; if all the options don’t sell out that week; if its auction profits; if users have queued for withdrawal but not withdrawn yet; if options have been settled for the week and not yet used to mint next week’s options

The sum of these two balances represent the total current asset balance “in” a Ribbon vault (technically, tokens could also be held very briefly in the EasyAuction contract after people buy options but it is promptly transferred back to the Ribbon vault).

Note that we also assume that there is only one type of collateral asset in a Theta Vault. This is currently true for the two vaults tested by this Ante Test, but as the contracts are upgradeable we can’t guarantee this will always be the case.

AnteRibbonV2ThetaVaultPlungeTest.sol, lines 49–60

The reason we don’t just use Ribbon’s totalBalance() function and roll our own calculation logic in an independent calculateAssetBalance() function is because we can increase the surface area of potential vulnerabilities covered.

If we were to use the internal Ribbon state to calculate balance, since the contracts are upgradeable, there is a potential situation where an attacker could seize upgrade permissions then replace the contract with a malicious one that steals the funds but doesn’t change vaultState.lockedAmount. Another possible attack vector could be a bug in the RibbonV2 Theta Vaults which allows an attacker to steal funds but leaves vaultState.lockedAmount unchanged. In either of these cases, an Ante Test checking Ribbon’s internal state variables for balance could show the test still passing even though funds were no longer SAFU.

As a general principle, writing test logic that doesn’t depend strongly on the tested contract’s own internal state helps make the test more robust against false negatives.

Ribbon Multisig Token Test

Code; Live test

AnteRibbonMultisigRBNTest checks that the Ribbon multisig wallet always holds at least 1 million $RBN. Failure would indicate a catastrophic scenario with a >99% drop in RBN balance (currently ~140M), which could mean that the multisig had been hacked or the team had rugged.

How it works

The failure threshold is set in the constructor of the test:

AnteRibbonMultisigRBNTest.sol, lines 27–32

The balance check is super straightforward: as long as the Ribbon multisig address still holds 1M or greater of $RBN, the test passes.

AnteRibbonMultisigRBNTest.sol, lines 36–38

Pretty simple, right? But these are often the kind of fundamental assumptions that we want to make sure hold true for a protocol.

Conclusion

We all know DeFi can be a dangerous place. Smart contracts can be opaque to your average DeFi user, and bad actors abound. Ante helps make code risk explicit, helping you make informed decisions about which protocols you use. Staking their tests could show a core team’s alignment with the community and their commitment to responsible code security. It’s a hard-to-fake signal of confidence in their code (literally skin in the game).

If you would like to learn more about how Ante could be useful for your protocol team, please reach out to us at signup.ante.xyz, read the docs at docs.ante.finance, or follow the team on Twitter and join our Discord for more web3 security discussions!

--

--

Ante
Ante Labs

Building a Smart Tests Community for @AnteFinance