Part 2

Zaros
PerpetualsDEXFoundrySolidity
70,000 USDC
View results
Submission Details
Severity: medium
Valid

Market Credit Delegation Weights Are Incorrectly Distributed

Summary

Credit delegation weights are incorrectly distributed inside Vault::updateVaultAndCreditDelegationWeight, causing each market to receive 100% of vault's credit capacity instead of its proper share.

Vulnerability Details

https://github.com/Cyfrin/2025-01-zaros-part-2/blob/35deb3e92b2a32cd304bf61d27e6071ef36e446d/src/market-making/leaves/Vault.sol#L521C1-L534C6

In Vault::updateVaultAndCreditDelegationWeight it is distributing 100% of the vaults credit capacity to each market instead of splitting the total credit delegation weight equally among the markets as shares:

@> uint128 newWeight = uint128(IERC4626(self.indexToken).totalAssets());
for (uint256 i; i < connectedMarketsIdsCache.length; i++) {
@> creditDelegation.weight = newWeight; // Each market gets FULL weight
}
self.totalCreditDelegationWeight = newWeight;

The document states:

/// @param weight Used to calculate the delegation's share of the vault's available credit capacity.

Weight should represent each market's share of total capacity.

Impact

  • Markets all receive 100% of the total credit delegation instead of a equally split share

  • This effectively duplicates the vault's credit capacity for each market

Tools Used

Foundry

Recommendations

Change it so its equal share and handle any left over to go to the last market to prevent any remainder

- uint128 newWeight = uint128(IERC4626(self.indexToken).totalAssets());
+ uint128 newTotalWeight = uint128(IERC4626(self.indexToken).totalAssets());
+ uint128 perMarketWeight = newTotalWeight / uint128(connectedMarketsIdsCache.length);
+ // Track remaining for rounding
+ uint128 remainingWeight = newTotalWeight;
for (uint256 i; i < connectedMarketsIdsCache.length; i++) {
// load the credit delegation to the given market id
CreditDelegation.Data storage creditDelegation =
CreditDelegation.load(self.id, connectedMarkets.at(i).toUint128());
+ if (i == connectedMarketsIdsCache.length - 1) {
+ // Last market gets remainder to handle rounding
+ creditDelegation.weight = remainingWeight;
+ } else {
+ creditDelegation.weight = perMarketWeight;
+ remainingWeight -= perMarketWeight;
+ }
+ }
- creditDelegation.weight = newWeight;
// update the vault weight
- self.totalCreditDelegationWeight = newWeight;
+ self.totalCreditDelegationWeight = newTotalWeight;
Updates

Lead Judging Commences

inallhonesty Lead Judge 6 months ago
Submission Judgement Published
Validated
Assigned finding tags:

Market Credit Delegation Weights Are Incorrectly Distributed

Support

FAQs

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