Diminished returns for gaugeWeight voters if they stake before applyGaugeLoss
for all slashable stakers
#1055
Labels
bug
Something isn't working
downgraded by judge
Judge downgraded the risk level of this issue
duplicate-262
grade-c
QA (Quality Assurance)
Assets are not at risk. State handling, function incorrect as to spec, issues with clarity, syntax
sufficient quality report
This report is of sufficient quality
unsatisfactory
does not satisfy C4 submission criteria; not eligible for awards
Lines of code
https://github.com/code-423n4/2023-12-ethereumcreditguild/blob/2376d9af792584e3d15ec9c32578daa33bb56b43/src/governance/ProfitManager.sol#L396-L399
https://github.com/code-423n4/2023-12-ethereumcreditguild/blob/2376d9af792584e3d15ec9c32578daa33bb56b43/src/tokens/GuildToken.sol#L147
Vulnerability details
Proof of Concept
A Gauge weight can be increased in 2 ways: directly, by GUILD holders by calling
guild.incrementGauge
and by SurplusGuildMinter(SGM) stakers whostake CREDIT (sent to ProfitManager - used as first-loss capital) and minting Guild (hold by SGM address).
Slashing events can happen from 2 reasons:
When bad debt is realized:
Regarding (D), for gauge weight to be decremented,
guild.applyGaugeLoss
is expected to be called for all users who voted for that gauge.The users who increase gaugeWeight after
notifyGaugeLoss
(t0) is called and before last user is slashed viaapplyGaugeLoss
(t1) will getdiminished
guildSplit
returns for the profit accumulated in the same [t0, t1] interval.The reason for this lies in how
gaugeProfitIndex
is calculated:gaugeProfitIndex[gauge] = _gaugeProfitIndex + (amountForGuild * 1e18) / _gaugeWeight;
_gaugeWeight
does not reflect the real, updated gaugeWeight untilapplyGaugeLoss
is called for all gauge weight voting users.Even if it's known that
applyGaugeLoss
must be called to decrement gauge weight for slashed users the risk of diminished returns was not considered.Users who allocate gaugeWeight are exposed to slashing but don't get their fair share of interest.
Coded PoC:
Add following test in GuildToken.t.sol file and run it with
forge test --mt testDiminishedGuildSplitReturns -vvv
NOTE:
SGM.getRewards
must be updated, otherwise other bug will interfere with this test: cacheuserStake = _stakes[user][term];
before comparing it withlastGaugeLoss
Tools Used
Manual review
Recommended Mitigation Steps
Consider disallow gaugeWeight voting until all addresses have been slashed (via applyGaugeLoss).
Assessed type
Error
The text was updated successfully, but these errors were encountered: