The upgradability of the TransparentUpgradeableProxy
is effectively bricked due to the unexpected inputs provided to its constructor. This creates a critical vulnerability, rendering the contract's upgradeability non-functional. The issue arises because the constructor deploys a new ProxyAdmin
instance, while an existing ProxyAdmin
instance is also passed as an input. This results in a conflict where the ownership and administrative control mechanisms are misaligned, ultimately making it impossible to upgrade the contract's implementation.
The function createNewDAOMembership
creates a new DAO membership by deploying a TransparentUpgradeableProxy
. The TransparentUpgradeableProxy
constructor accepts three parameters: address _logic
, address initialOwner
, and bytes memory _data
. The constructor implementation is as follows:
As shown in the code, the TransparentUpgradeableProxy
constructor deploys a new instance of the ProxyAdmin
contract, with the specified initialOwner
as its owner.
The createNewDAOMembership
function, however, contains the following logic:
Here, the createNewDAOMembership
function passes an existing ProxyAdmin
instance (proxyAdmin
) to the constructor of TransparentUpgradeableProxy
. However, the TransparentUpgradeableProxy
constructor also deploys its own ProxyAdmin
instance. As a result, the following issues arise:
The admin of the TransparentUpgradeableProxy
is a newly deployed ProxyAdmin
instance.
The owner of this new ProxyAdmin
instance is another ProxyAdmin
instance, as the owner of the ProxyAdmin
contract is set during its construction.
Consequently:
The deployer of the MembershipFactory
contract indirectly owns the ProxyAdmin
controlling the proxy, as they own the initial ProxyAdmin
instance.
Since the ownership of the ProxyAdmin
contract is itself assigned to another ProxyAdmin
, there is no direct mechanism to update the ownership of the controlling ProxyAdmin
.
This design flaw creates a situation where the TransparentUpgradeableProxy
's implementation contract cannot be upgraded, as there is no accessible mechanism to change the admin or update the logic.
This issue highlights a critical gap in the contract design, as the ownership hierarchy inadvertently renders the upgradeability of the proxy non-functional. To resolve this, the contract design must be adjusted to avoid redundant or conflicting ownership assignments.
Upgrade to a new implementation is not possible
Manual review
Input initialOwner
instead of instance of ProxyAdmin
in createNewDAOMembership
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.