Illuvium (Part 4 - Staking V2)

QuantstampFiles named in the report

Quantstamp reviewed Illuvium (Illuvium (Part 4 - Staking V2)) on 17 Mar 2022: 19 findings, 0 critical; 15 marked fixed, 4 acknowledged.

No open critical findings
Open the reportOpen Illuvium’s security record

Report hosted on certificate.quantstamp.com.

Trustblock does not review code.

Findings19

Statuses are the security firm’s own, from its report.

SeverityOpenAcknowledgedFixed
Critical000
High011
Medium002
Low0312
HighMissing function callFixed

The comment on the following line is not implemented; only one value (`subVaultRewards `) is updated. ``` // subYieldRewards and subVaultRewards needs to be updated on every `_processRewards` call user.subVaultRewards = uint256(user.totalWeight).weightToReward(vaultRewardsPerWeight); ```

MediumUnchecked Return ValuesFixed

The function `stake` calls `transferFrom` but ignores the return value; function `unstake` calls `transfer` and also ignores the return value.

MediumUnlimited ApprovalsFixed

In `sendILVRewards`, there are approvals with `type(uint256).max` which is dangerous if something goes wrong.

LowEvent `LogMigrateUser` Could Present More InformationFixed

The function `migrateUser(...)` contains the following: `emit LogMigrateUser(msg.sender, _to)`. Perhaps adding more information to this log would help in future investigations.

LowExternal Functions of `ILVPool.sol` can be Called by AnyoneFixed

The functions from this file can be called by anyone. However, the code comment states that “External `MigrateLockedStakes` call, [is] used in Sushi LP pool”.

LowIncorrect `paramIndex`Fixed

In `CorePool.sol`, lines 274 and 275 `paramIndex` for `_initTime` and `_weight` are off-by-one. Similarly, line 40 in `VaultRecipient.sol` has an incorrect `paramIndex`.

LowIncorrect and Unclear `Keccak256`Fixed

In `ILVPool.sol`, the hash comment `bytes4(keccak256("_migrateYieldWeights(bytes32[],uint256,uint256")))` in function `_migrateYieldWeights` does not have the closing bracket for `_migrateYieldWeights` inside the quote. In `CorePool.sol`, the hash `0x867a0347` is not explained when it should be.

LowIndistinguishable Return ValueFixed

In `getV1StakePosition`, the value zero is returned if the stake id provided is not found. However, this value is also returned if the stake is the first entry.

LowOwnership can be RenouncedFixed

All files that inherit from the `Ownable` contract could be left with no owner if the latter renounces his ownership. As one potential consequence, that could prevents update to the deployed contracts, requiring re-deploys and potential downtime.

LowPoorly Named Function: `CorePool.migrateUser(…)`Fixed

The function `migrateUser(...)` is related to migrations of wallets of the same user, and not migrating users from V1 to V2. Thus, we encourage the team to provide a better name for this function.

Show 5 more
LowReview the Visibility of State VariablesFixed

The proper declaration of the visibility of state variables is a good programming practice and it also reduces the final contract size. Public variables increase the contract size:for each public variable, the solidity compiler automatically generates the `getter` and `setter`[functions](https://docs.soliditylang.org/en/v0.6.10/contracts.html#visibility-and-getters). For instance, we do not see a reason for declaring the following state variables as `public` in `Vault.sol`: - `Pools public pools;` - `IUniswapV2Router02 public sushiRouter` and - `IERC20 public ilv`.

LowState Variables can Change when the Contract is PausedFixed

The functions `migrateUser(...)`, `sync()`, `receiveVaultRewards(...)`, `setWeight(...)`, and `pendingRewards(...)`can be called when the contract is paused. This can be dangerous since they change state variables.

LowSuboptimal CodeFixed

The contract size can be optimized by turning `modifiers` into `functions`, as shown in the example below: ``` modifier checkStuff() {} function doSomething() checkStuff {} ``` The `function doSomething()` can rewritten without modifiers as: ``` function checkStuff() private {} function doSomething() { checkStuff(); } ```

LowUnrestricted `endTime`Fixed

In `setEndTime`, there is no sanity checks for the new value. It could be before the current time, or interact with existing pools in unexpected ways.

LowUnsafe CastFixed

The function `unstake` in `FlashPool.sol` converts a `uint256` to a `unit128` without checking that the cast is safe. Similar issues - with as small a bit width as 64 - exist elsewhere in the contract. These issues are found in `CorePool.sol` as well.

Contracts in scope

No deployed address is recorded for this audit.

The report names a repository or files. Open the report to see its scope.

Repository and files the report names (31)

  • contracts/mocks/PoolFactoryUpgrade.sol
  • contracts/mocks/FlashPoolMock.sol
  • contracts/interfaces/IERC20Mintable.sol
  • contracts/ILVPool.sol
  • contracts/FlashPool.sol
  • contracts/mocks/FlashPoolUpgrade.sol
  • contracts/base/FactoryControlled.sol
  • contracts/PoolFactory.sol
  • contracts/base/Timestamp.sol
  • contracts/mocks/ERC20Mock.sol
  • contracts/interfaces/IFactory.sol
  • contracts/mocks/ILVPoolUpgrade.sol
  • contracts/mocks/WETHMock.sol
  • contracts/interfaces/IUniswapV2Router02.sol
  • contracts/interfaces/IUniswapV2Router01.sol
  • contracts/base/VaultRecipient.sol
  • contracts/libraries/ErrorHandler.sol
  • contracts/mocks/CorePoolV1Mock.sol
  • contracts/mocks/SushiLPPoolUpgrade.sol
  • contracts/interfaces/ICorePool.sol
  • contracts/Vault.sol
  • contracts/mocks/ILVPoolMock.sol
  • contracts/mocks/PoolFactoryMock.sol
  • contracts/SushiLPPool.sol
  • contracts/interfaces/ICorePoolV1.sol
  • contracts/mocks/SushiLPPoolMock.sol
  • contracts/libraries/SafeCast.sol
  • contracts/base/V2Migrator.sol
  • contracts/base/CorePool.sol
  • contracts/interfaces/IILVPool.sol
  • contracts/libraries/Stake.sol

Part of Illuvium’s security record

Illuvium
Audits6 audits by 4 firmsLast audit Oct 2025, by Cyfrin.
Critical findingsNo open critical findingsAcross 6 reports.
Open Illuvium’s security record

Security firm

Quantstamp

236 projects reviewed · 332 reports · latest Oct 2026

See Quantstamp’s audits

Something wrong on this page? A missing report, a wrong date, a finding that was fixed since. Tell us and we check it against its source.

Tell us