The MysteryBox::changeOwner function is marked as public but does not implement any access-security modifier, such as onlyOwner. This function enables any address to change the MysteryBox::owner storage variable, thus enabling anyone to tamper with the protocol and access functions intended only to be used by the contract owner.
The function is missing access control modifier to probihit users from misusing the protocol.
Any caller may change the contract owner to themselves and then use functions that are meant to be used only for the owner. This way, any user may withdraw the funds from the protocol since the MysteryBox::withdrawFunds checks, that the caller is the owner.
Attack vector / PoC:
Owner deploys the contract to the chain and deployers address is saved in the MysteryBox::owner variable.
Any user can call the MysteryBox::changeOwner function since it is marked as public and change the storage variable MysteryBox::owner to a new value
PoC:
Insert the code below to the TestMysteryBox.t.sol suite and run the test.
Code output:
Original owner: , owner: [0x7c8999dC9a822c1f0Df42023113EDB4FDd543266]
Txn caller: , ECRecover: [0x0000000000000000000000000000000000000001]
New owner: , ECRecover: [0x0000000000000000000000000000000000000001]
Static analysis
Utilize either onlyOwner contract by OpenZeppelin, or implement own onlyOwner modifier that will be checking that the caller is a contract owner. The MysteryBox::changeOwner should be marked as onlyOwner.
A simple modifier may look similar to this:
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.