59657 sc high delegators lose first reward period when delegating to pending validators

Submitted on Nov 14th 2025 at 14:51:14 UTC by @danvinci_20 for Audit Comp | Vechain | Stargate Hayabusaarrow-up-right

  • Report ID: #59657

  • Report Type: Smart Contract

  • Report severity: High

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

  • Impacts: Theft of unclaimed yield

Description

Summary

When delegating to a validator that is in the pending phase, the protocol initializes:

lastClaimedPeriod[tokenId] = completedPeriods + 1;

Because the reward calculation always starts from:

nextClaimablePeriod = lastClaimedPeriod[tokenId] + 1;

the delegator permanently loses rewards for the first active period of the new delegation when the validator was pending. The code assumes delegation starts in the next period, but for pending validators the actual delegation startPeriod is completedPeriods + 1. By shifting lastClaimedPeriod forward by one, the protocol skips the first eligible reward period, causing loss of user rewards.

Vulnerability Details

Relevant code paths during delegation:

Reward calculation logic:

Sequence of effects:

1

Step: Setting lastClaimedPeriod

Setting lastClaimedPeriod = completedPeriods + 1.

2

Step: nextClaimablePeriod becomes shifted

This makes nextClaimablePeriod = completedPeriods + 2. However, if the validator is PENDING, the delegation actually starts at completedPeriods + 1. The first active period (completedPeriods + 1) is skipped and becomes unclaimable.

Impact

Users lose one full period of rewards when delegating to a validator that is still in the pending phase.

Recommendation

Safely handle delegations to pending validators so users do not lose rewards for the first active period. (No code changes are provided here; implementors should ensure lastClaimedPeriod does not advance past the delegation startPeriod for pending validators, or initialize it to the correct previous completed period such that the first active period remains claimable.)

Proof of Concept

chevron-rightTest to reproduce (add to Delegation.test.ts)hashtag

Run:

Test:

Observed output:

References

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

circle-info

No code changes are included in this report. Implementers should ensure lastClaimedPeriod is initialized or adjusted so it does not skip the delegation startPeriod when validators are pending.

Was this helpful?