Defensive Protocol Design - Smart Contracts
When designing a new protocol it can be all too easy to focus on the design goals and how your dApp enables users to carry out operations. However, unlike usual apps, dApps must place a far greater significance on security as the safety of user funds hinges on developer design decisions.
This issue has become a talking point with the recent exploit of Balancer Finance and collapse of Stream Finance. The former happening due to a rounding error in pool accounting despite numerous audits, sizable bug bounties and an experienced development team. While the latter occurred due to risk management negligence by a fund manager. The causes could not be more different and yet both underline the need for defensive protocol designs.
In this article we will discuss situations similar to Balancer’s, discussing options that developers can employ to drastically reduce the likelihood of finding critical vulnerabilities in smart contracts and reducing severity if they are exploited.
Circuit breakers and bots, automated or manual
Firstly, when designing a dApp it is worth taking time to consider what circumstances are likely to occur in a system. These can then be used to add limits on acceptable bounds within a protocol. A common example is with lending markets, if the market average interest for an asset sits around 5% a year and suddenly rises to 90% within one transaction, this is highly unlikely to be a legitimate transaction. Circuit breakers could then be written into the contracts to prevent such transactions occurring, these are unlikely to inhibit regular users but provide a useful roadblock against exploits.
As this logic would be publicly accessible it is possible a malicious actor might seek to bypass such counter measures by splitting their exploit into multiple transactions that get near to, but do not exceed such circuit breaker values. This is where manual circuit breakers can add value, the protocol also has an offchain bot that looks for irregular activities and has the ability to pause the protocol if these are detected. The advantage of an offchain solution is that the criteria to trigger this can be private, giving attackers less information. Automated conditional pausing leads to quicker reactions to market conditions in times of blockchain congestion, though developers must stress test functionality to ensure persistent operation during atypical gas conditions and RPC/API response times.
One example of bot malfunction was a reference auction client written by Maker DAO that was intended to bid on DAI troves in order to liquidate insolvent loans. The auction bot had worked smoothly in typical gas conditions but had not been programmed sufficiently to deal with gas congestion experienced on March 12th 2020. This led to all instances of the auction bot failing to bid on active auctions and other actors being able to claim delinquent loan collateral without offering the typical repayment amount. Such situations can be avoided by allowing dynamic gas limits on offchain bots, detecting failed or stalled transactions with retry strategies and developing multiple clients to execute actions.
One potential downside to circuit breakers is that if they are too sensitive they may trigger during genuine user transactions and cause frustration using the dApp. However, with careful fine-tuning these occurrences can be reduced.
Compound Finance, a collateralised lending protocol, used circuit breakers to respond to a recent threat. Their platform was impacted by the recent shockwave of Stream Finance’s collapse. They had enabled lending against Elixir Finance’s deUSD and sdeUSD tokens which was known to have some exposure to Stream Finance and was experiencing a depeg as a result. Gauntlet, a risk advisory body for Compound, proposed freezing further borrowing of other stablecoins until updates could be made to the protocol to prevent users borrowing against deUSD/sdeUSD. Freezing further borrowing prevented holders of deUSD/sdeUSD draining available funds from Compound and handing off the bad debt to other Compound Finance users.
Slow scaling and assets supply caps
One simple mechanism to limit damage can be to reduce the value of assets managed by a protocol initially. This can be done by making use of beta testing and later in live deployments by utilising asset caps, for example a lending project might limit the amount of assets that can be supplied or borrowed.
If testnet deployments are coupled with an active security posture such as bug bounties and further audits this can allow projects to detect problems prior to using the contracts with real money.
Once deployed, projects can then slowly scale by introducing asset deposit maximums. This allows confidence to grow in the system design and minimises the impact of hacks, making recovery and relaunch of the project far more likely to occur. If done properly, such limits can drive interest, as users may be competing to take part if the economic incentives are good.
An example of this was with Abracadabra.money, an Omnichain DeFi lending platform, who in October 2025 were the subject of a hack. The attack targeted six deprecated lending contracts and resulted in the loss of $1.8 million in the MIM token. While a harsh lesson, the protocol was saved from total ruin by the use of lending limits on the affected contracts. The DAO was then able to use treasury funds to patch over the damage done, preventing the hack further affecting the other holders of $43 million MIM in circulation.
Abnormal event tracking both in contracts and offchain
Similar to the use of offchain circuit breakers, it can be useful for a project to monitor day-to-day usage, as not all vulnerabilities are instantaneous single transactions. By building knowledge on the average number and type of transactions a protocol receives, models can be built that can flag anomalies to developers for further scrutiny. By observing this data developers can also detect unintentional design anomalies based on real usage and correct issues before exploitation.
YieldBasis, a volatile token liquidity providing protocol building on top of Curve Finance’s crvUSD stablecoin have been making extensive use of performance analysis to track the expected performance of their deployed pools. While formulas can be designed and performance predicted, several other aspects of markets are difficult to predict with certainty due to market dynamics. Rising gas prices can impact the ability for arbitrageurs to make trades in a speedy manner which for YieldBasis is a core assumption of their asset rebalancing process. After launching their pools they noted that the price crash of October 10th 2025 led to some impermanent loss for pool liquidity providers.
In discussing their performance, YieldBasis noted that increased liquidity would reduce the volatility of pool returns by increasing arbitrage returns and incentivising balancing trades even when market gas prices were high. This was effected by YieldBasis raising each of their pool caps from $20 million to $50 million and sponsoring partner liquidity in crvUSD pools to enable more efficient swap routes.
Principle of Least Access/Role based access control
Even if the underlying economic theory of a protocol is rigourous, it can be possible for projects to be their own undoing due to lax governance design. While mutability via governance and proxy designs can be tempting, this can also become a threat. Liquity, a DeFi over-collateralised lending protocol, chose to launch immutable contracts for their stablecoins LUSD and BOLD and so gained favour among users who wish to minimize threat vectors while operating in DeFi. Users of LUSD or BOLD stablecoins can feel safer knowing the protocol team cannot disable or change the system design.
When privileged roles are determined to be necessary, roles should have fine grained access and be split between different accounts to reduce the impact if one role account is compromised by an external party or ex-member.
In discussing circuit breakers we touched on the idea of offchain bots that can pause contract functionality. This is an example of utilising role access to allow additional security functionality without risking user assets. Because such bot roles must be automated they are more likely to be hijacked than more secure actors such as hardware wallets or multi-sigs. Therefore, they benefit greatly from making use of the “least privilege possible” concept. Under this concept they can be blocked from accessing other admin functions while maintaining rapid response times for pausing contracts.
This concept should be applied to all actors with roles within the protocol to prevent risks associated with account takeovers or rogue employees. One example of where better role control would have helped was the draining of funds from Pump.fun, a memecoin launchpad protocol by a disgruntled employee. The former employee used privileged access to protocol private keys in order to access admin only functions allowing him to steal user funds.
Multi-sig wallets and simulations
This attack on Pump.fun could have been avoided had their development team exclusively used multi-signature accounts. A multi-sig is a specialised smart contract which requires signatures from multiple externally owned accounts to execute transactions. Non-automated roles in protocols should be operated by strong multi-sig smart contracts with unique, responsive signers to make compromising admin roles significantly harder.
While more difficult to compromise, multi-sig accounts are just the first step. Attacks such as Bybit’s frontend spoofing that lost the exchange $1.4 billion from their multi-sig wallet, highlight the need for proactive layered defenses in management of treasury accounts. Use of external tools such as Tenderly, OpenZeppelin’s Safe Utils and local testnets using toolsets such as Forge to simulate transactions and verify protocol upgrades or transactions will occur as expected are a must.
While development teams lie outside the protocol itself it is important to consider personal operation security measures particularly when they intersect with protocol safety. The Bybit attack stemmed from the compromised development system of a developer from a different company, Safe Wallet, the multi-sig platform Bybit made use of. Increasingly, as smart contract developers become accustomed to better design practices, the industry is seeing more indirect attacks propagating. Such as compromising developer systems in order to gain access to private keys or front-end management systems.
Developers should be cautious about contact from third parties, hesitant to download software and protect development dependencies with careful versioning. Airgapped isolated development systems are advisable and care must be taken when installing plugins to common development tools to ensure the correct ones are used, instead of typo-squatted or doppelganger plug-ins. One quick heuristic to use is checking the publish date of an add-on. Typically, fake plug-ins are reported and removed preventing longevity, though caution is still advised as this will not protect against hijacked plug-ins.
For other issues to consider with DAO governance see our previous article.
Worst case modelling during design
Part of the design cycle for a protocol should include speculation of how mechanisms could go wrong and what worst-case scenarios would look like. This process is important to help steer protocol security design and is also useful for informing auditors, who the project might later work with, what risks have been anticipated and what mindset the developers have adopted.
Projects should look at the intended protocol actions and theorise what would constitute system failures, both severe and more moderate failures such as temporary Denial-of-Service. Researching about past black swan events and how affected protocols specifically suffered during these can help with threat modelling.
Once this process has been carried out, measures can then be taken to reduce the impact of such failures as detailed below.
Defensive code design
With patterns developing in how smart contract attacks occur specific strategies have arisen to combat common attack approaches. Most developers are familiar with reentrancy attacks and the resulting use of reentrancy guards to prevent multiple function calls within the same transaction.
The earlier mentioned onchain circuit breakers are also another example of defensive code design. Other strategies that can be applied, include preventing multiple protocol actions in the same transaction, while a similar principle to reentrancy guards, this applies a looser common sense approach that the average user is unlikely to take an action then reverse it in the same interaction.
Examples of this include depositing to a lending market or DEX and then withdrawing in the same transaction. Use of this mechanism must be well thought out, in the latter example advanced genuine users may seek to provide brief “Just-In-Time” liquidity to a DEX pair due to a particularly large trade. Not allowing such an action may then negatively impact the effective price of the trader, damaging real use cases. Defensive designs need to be reasonable and mindful of niche real applications that they may block.
Another method of defensive design is the isolation of user assets to different contracts, or if assets are pooled, then strict accounting checks should be completed at the end of every call to ensure balances have only changed in the expected ways. Gearbox, a lending protocol, made use of user isolation by having a contract generation event incentivised by an airdrop to participants. These contracts then formed isolated borrowing accounts which could be reassigned to different users and allowed complex lending activities which were isolated from one another, reducing the risk of systematic failure bankrupting the system.
Another common consideration is ensuring smart wallets can make use of a dApp. It is a common pitfall to attempt to force the caller to be an EOA under the assumption that a smart contract would only call your protocol maliciously. This assumption is flawed and restrictive but also typical mechanisms for achieving this may not be fit for form. One typical method is to ensure msg.sender == tx.origin as this used to be a mechanism to ensure the caller is an EOA however, with the introduction of the Pectra update this assumption no longer holds true due to Account Abstraction.
Defence in depth
Incorrect safety assumptions such as detecting the message sender mentioned above can invalidate security assumptions that are integral to a protocol’s design safety. While creating invariants about a project can be helpful for reasoning about the state space of achievable operations, it is best to use multiple defensive measures in sequence so that if one fails the others hold.
A common example is not using an oracle for a stablecoin as its value should normally be $1 and hardcoding this value as a result. While usually true, this assumption can have devastating consequences if it becomes untrue. For this reason it is important to design multiple checks in protocols, then should one invariant be found untrue the other processes can continue to protect the system.
An example of this might be generating a price oracle from multiple sources. This way if one source becomes inaccurate the system can be designed to discard its impact such as by using the median oracle value.
Other defensive design decisions such as reentrancy guards can feed into this concept. While a developer may not be able to envision a vulnerability stemming from reentrancy, these guards can be employed to block such situations arising if a function is found to enable this type of manipulation.
The BOLD stablecoin developed by Liquity, a DeFi over-collateralised lending protocol, makes use of defence in depth in their collateral oracle design. The protocol supports the liquid staking tokens stETH and rETH as well as native ETH for collateral. These are priced using Chainlink price feeds while paying attention to the timestamp of the last price update. If this becomes stale then that collateral branch enters a shutdown mode preventing further borrowing from occurring while still allowing operations that can reduce user debt. This helps prevent protocol attacks in the event of oracle downtime.
Advanced testing and auditing
After these processes have been completed protocols should look to extensively test their protocol behaviour internally by making use of unit and integration tests. If time allows, fuzz tests and invariant analysis should also be explored. Unit tests allow quick verification that incremental codebase changes have not altered intended behaviour, while integration tests ensure end-to-end actions that may incorporate other protocols perform as intended.
Fuzz testing and invariant tests allow for more complex tests that may find edge cases which would be difficult for manual review or unit tests to imagine. While such boundary cases may not occur during typical use, it is valuable to discover these, as attackers will often look to manipulate protocol state into bizarre states where an invariant no longer holds true.
After this, teams should look to have their code reviewed by auditors, allowing sufficient time given the scale of the codebase and preferably with a mind for running multiple audit reviews that run sequentially with different audit companies.
Bug bounties and clear security communication channels
Finally, if all else fails it is important to have established contact methods, and if possible, rewards for responsible disclosure of vulnerabilities found by white-hat hackers. Protocols should look to partner with a bounty platform such as Immunefi and offer rewards that compensate fairly, reflecting the cost of damage prevented. Such security contact methods should be easily accessible and commented in all code deployed onchain. Preferably, several contact methods should be provided such as a security specific e-mail as well as other low friction and anonymous methods of contact with an aim to reducing barriers to reporting issues as much as possible.
Teams should set up a framework of responsible team members who can be contacted to report issues and test their response resolution protocol to ensure if a real issue occurs they are well prepared to handle it.
Fire drills save lives
Even if all these preventative steps are taken exploits can still happen, so protocols should establish frameworks that can be followed if the worst happens. This should include internal information about whom to contact, clear instructions on how to freeze all aspects of the system and contact details for useful third party contacts such as SEAL 911.
The team should maintain a directory of contacts relating to integrated tokens and services of their protocol with notes about what measures each stakeholder can effect, though this should strictly be a backup owing to the mercurial nature of responses. While some tokens or chains have the ability to freeze accounts or prevent hacked funds from moving, they can often be reticent to do this due to the legal implications that may stem from intervention.
Once a threat has been contained, the system should not go live again until the root cause of a vulnerability is fully understood and mitigated, or the protocol may face copycat attacks as Compound saw with the COMP minting bug.
This issue occurred when an excess of COMP governance tokens were minted. Some users noticed this excess and stole these tokens through crafted transaction calls. Compound reacted and triggered the necessary changes to halt further losses, but due to the time delay enforced by their governance contracts as a protection for current users, they could only watch as other users then copied the exploit transaction to claim additional tokens for free.
Once the fix was implemented the total funds drained stood at $147 million, though some claimers later returned funds to the Compound governance address.
Conclusion
It is worth keeping in mind that exploits risk more than the funds at risk, usually protocols that survive a significant hack can find it difficult to attract new users, regain market confidence or source new investors. If teams understand and implement the protections raised in this article, their protocol will stand a much better chance of long term success. The methods used to protect each protocol will vary based on the design. While protocols should be protecting against edges cases they must also be cautious to ensure that protective measures do not lock genuine customer funds.