This report is an in the wild story of attackers compromising many contracts in a subtle way. The name says it all: Clandestine Proxy In the Middle of Proxy (CPIMP).
Smart contract deployment of upgradable contracts typically works in two types: deploy the code and then call an initialization function. Unless specifically checked, the initialize function can be called by attackers before the real user sets malicious settings. In reality, if this happened, a legitimate developer should recognize the failure and just try again. At least, that's the argument I've been hearing for a long time. So, what's different here?
Attackers were able to backdoor the contracts without being noticed - real value was being accrued in these contracts for several weeks as well. The malicious actors were monitoring the intended implementation and deployment procedures. Instead of the normal flow of going from the proxy to the proxy implementation, a contract was added in the middle, similar to a MitM attack.
To make matters even scarier, most blockchain explorers could not tell the difference! The implementation was shown as the correct one in the explorer. Events and storage slot contests even look correct. Even the deployment showed the incorrect events. Developers just weren't being careful enough upon review.
Many project contracts were backdoored, such as EtherFi and Pendle. The malicious actors were waiting for the right moment to profit, but it was caught first. The authors of the post contacted SEAL 911 to start a war room. To not freak out the attackers and get them to exploit things now, it had to be coordinated. This meant getting all affected protocols into a war room at once. Although every remediation was custom, most of the funds were recovered!
So, how did the backdoor work? It was sophisicated with persistence, detection evasion and more. First, it added functionality to become the "Super-Admin" to override ownership for ugprades, drains and executions. This allowed the malicious owner to do whatever they wanted.
To make it more persistent, it restored itself in the implementation slot - this meant that not even upgrades could remove it. On L2s, if the Super Admin account had been denylisted, they had signed executions that still worked. Even crazier, they added batched direct storage writes in calls as well.
Some implementations contained anti-recovery protection. By reviewing balance checks before/after a call, it would prevent 90% of funds from being taken at once. That's pretty devious!
The coolest part about this is by far the reason EtherScan finds the wrong implementation contract - the main reason most developers were tricked. The detection of Etherscan consults multiple storage slots that are defined in various proxy implementations IN ORDER. By placing the legitimate implementation address at the old proxy implementations slot (defined by a standard), Etherscan would find the incorrect address! Amazing work and it makes me think that Etherscan should have a fat bug bounty program.
Overall, great research in detecting, documenting, and mitigating this vulnerability. In the future, I will be more hesitant about allowing initialization functions to be frontran. Neat!