Tadle

Tadle
DeFiFoundry
27,750 USDC
View results
Submission Details
Severity: medium
Invalid

The `SystemConfig::getPlatformFeeRate` returns `basePlatformFeeRate` for any user if their `userPlatformFeeRate[_user]` is 0, which can conflict the intention of the protocol owner if the 0 fee is intentionally set for someone as a promotion

Summary

In the function SystemConfig::updateUserPlatformFeeRate(), the protocol owner has the authority to set any number as the platform fee for any individual user, as long as _platformFeeRate <= Constants.PLATFORM_FEE_DECIMAL_SCALER. This means it's totally reasonable in business sense that, the protocol owner has full authority to set it as a very low number for certain users, likely in the event of a marketing promotion for a limited period of time. He can set it as 1 (effectively 0.0001% in this protocol), which is an extremely small number just next to 0; or he can set it to 0 directly, meaning free platform fee for now. The updateUserPlatformFeeRate() function totally allow the owner to do that.

However, the logic in the function SystemConfig::getPlatformFeeRate() returns basePlatformFeeRate (which is 0.5% by default according to the natspec) for any user if their userPlatformFeeRate[_user] is 0. It's obvious that the design behind this line of code is to prepare for the uninitialized cases, where all the uint256 numbers are falsely number 0 by default; however, it cannot distinguish the cases where the protocol owner intentionally wanted to use the number 0 as a promotion for certain users.

Vulnerability Details

Let's take a look at the code below:

function getPlatformFeeRate(address _user) external view returns (uint256) {
if (userPlatformFeeRate[_user] == 0) {
return basePlatformFeeRate;
}
return userPlatformFeeRate[_user];
}

We can compare the two cases below:

  1. The protocol owner set the platform fee as 1 for a certain user, then the function getPlatformFeeRate will return 1, which means 0.0001% in business term.

  2. The protocol owner set the platform fee as 0 for a certain user as a promotion rate for a limited time, but the function getPlatformFeeRate will return basePlatformFeeRate, which by default is 0.5% in business term.

The protocol owner input two very close numbers (1 and 0) in cases above, but the return values are drastically different.

Impact

In the real world, a free platform fee for a limited time is a common marketing campaign. However, this bug in the code leads to the consequence that the protocol owner is unable to set it as 0 for anybody, and the best number he can use is 1 (0.0001%), which itself is a weird number to use. This logical bug invalidates the intended functionality of customizable user-specific fee rates. It's business impact makes it an M severity issue.

Tools Used

Manual Review

Recommendations

  • A clear distinction needs to be managed between users who should not have any fee (0% rate) and those whose fee rate has not been set (and therefore should inherit the basePlatformFeeRate).

  • To resolve this, a separate flag or marker could be used to indicate users with explicitly no fees

Updates

Lead Judging Commences

0xnevi Lead Judge
12 months ago
0xnevi Lead Judge 12 months ago
Submission Judgement Published
Invalidated
Reason: Design choice

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.