For the complete documentation index, see llms.txt. This page is also available as Markdown.

59844 sc insight incorrect and misleading events when adding levels in stargatenft

Submitted on Nov 16th 2025 at 10:44:17 UTC by @blackgrease for Audit Comp | Vechain | Stargate Hayabusa

  • Report ID: #59844

  • Report Type: Smart Contract

  • Report severity: Insight

  • Target: https://github.com/immunefi-team/audit-comp-vechain-stargate-hayabusa/tree/main/packages/contracts/contracts/StargateNFT/libraries/Levels.sol

Description

Affected Files: StargateNFT.sol and Levels

The StargateNFT inherits the Levels library allowing levels to be added into the contract by an address with the LEVEL_OPERATOR_ROLE privilege (set by protocol). However, when adding a level the addLevel function emits incorrect/misleading events. Specifically, the function emits:

  • LevelUpdated: misleading and incorrect because this is an addition operation and not updating an existing level.

  • LevelCirculatingSupplyUpdated: misleading and incorrect because this is an addition operation (not an update). Also the oldCirculatingSupply value is 0 which isn't useful.

  • LevelCapUpdated: again, not an updating operation; the oldCap parameter is meaningless.

A stack trace of the emitted events:

│   │   │   ├─ emit LevelUpdated(levelId: 4, name: "Thunder Boosted", isX: false, maturityBlocks: 7200, scaledRewardFactor: 1, vetAmountRequiredToStake: 500000000000000000000 [5e20])
│   │   │   ├─ emit LevelCirculatingSupplyUpdated(levelId: 4, oldCirculatingSupply: 0, newCirculatingSupply: 0)
│   │   │   ├─ emit LevelCapUpdated(levelId: 4, oldCap: 0, newCap: 1000000000 [1e9])

These events are emitted by Levels::updateLevel. Note: in version 3 of StargateNFT the updateLevel function is no longer exposed. Documentation confirms removal of setters: StargateNFT#L92 "Removed setters to optimize contract size: setStargateDelegation, setLegacyNodes, updateLevelCap, updateLevel".

The addLevel function should emit its own unique event that accurately represents the addition operation and contains meaningful data.

The Associated Code

StargateNFT wrapper:

Levels library (relevant extract):

Impact

This is classified as an Insight under "Code Optimizations and Enhancements". Incorrect or misleading event emission can confuse indexers, analytics services, and anyone relying on on-chain events to understand protocol state changes. The semantics of "add" differ from "update" and should be represented distinctly.

Mitigation

Create and emit a new event that accurately represents level addition. Suggested event:

Change Levels::addLevel to emit the new event instead of the three misleading events. Example patch:

This preserves accurate semantics and removes confusing old* fields that are meaningless for additions.

https://gist.github.com/blackgrease/e056f70903d89aea4fe1ddda4461a862

Proof of Concept

A runnable Foundry PoC is provided in the private gist at the link above. Run:

forge test --mt testAddLevelInccorectEventEmitted -C ./packages/contracts -vvvv

PoC Description

1

Add a level to the contract using the LEVEL_OPERATOR_ROLE.

2

Retrieve the emitted event logs.

3

Confirm the stored event logs match what is (incorrectly) expected to be emitted from the contract.

Stack Trace (for convenience)

Hardhat conversion to Foundry

1

Start: clone the repository

git clone https://github.com/immunefi-team/audit-comp-vechain-stargate-hayabusa.git cd audit-comp-vechain-stargate-hayabusa/

2

Install dependencies:

forge install foundry-rs/forge-std

3

Install OpenZeppelin upgradeable contracts:

forge install OpenZeppelin/openzeppelin-contracts-upgradeable@v5.0.2

4

Install OpenZeppelin contracts (used in test):

forge install OpenZeppelin/openzeppelin-contracts@v5.0.2

5

Compile and run the PoC:

forge compile ./packages/contracts/ (warnings can be ignored)

forge test --mt testAddLevelInccorectEventEmitted -C ./packages/contracts -vvvv


If you want, I can:

  • produce a minimal patch (diff) that adds the NewLevelAdded event and replaces the three emits in Levels::addLevel, or

  • open a suggested PR message and commit body consistent with the repo style.

Was this helpful?