Capminal contracts: CAPU mint over-issuance in one call
Capminal contracts - CAPU mint curve priced at the pre-mint rate (single-call over-issuance); CapStaking V1 keeps the 5x multiplier without a lock (GHSA-2qg4-mp8w-wr59)
The mint-curve flaw is fixed by PR #4 (merged as 3e26129) and live on Base since the ScapStaking proxy upgrade of 2026-09-06. The CapStaking V1 flaw is not fixed: V1 is deprecated and holds no funds. Track the fix at Capminal/capminal-contracts#4.
- Product
- Capminal contracts (ScapStaking / CAPU and CapStaking V1 on Base) in Capminal/capminal-contracts
- Affected versions
- capminal-contracts through fd55909 (the 2026-06-02 public release), and the ScapStaking implementation live on Base until the 2026-09-06 upgrade. CapStaking V1 is deprecated and will not be fixed.
- Severity
- HIGH
- Status
- Patched
- Weaknesses
- CWE-682Incorrect Calculation
- GitHub advisory
- GHSA-2qg4-mp8w-wr59
Published by the maintainer on 2026-09-06 - CVE
- Pending (requested from MITRE)
- Published
- Credit
- Finder: Aaron Elijah Mars of Aeon. Tool: Aeon (https://www.aeon.fun).
What users should do now
Capminal users do not need to do anything. The fix is already live: the ScapStaking proxy on Base was upgraded in place on 2026-09-06, with no state migration.
- Integrators: read mint quotes from
pendingMintAmounton the live proxy. You can confirm the upgrade by checking that the proxy0x92ee42A61CF55642949B4fE74bB4796978ddB47apoints at implementation0x24300091331452485BD174B3eE9942cd908417D0. - Do not integrate against or deploy
CapStakingV1. If an off-chain reward system ever took snapshots of V1sharesOf, do not reuse them. - Anyone who copied this code: take the changes from #4 (merge
3e26129) and drop the single-ratecomputeMintAmount.
Summary
Capminal lets users stake CAP for non-transferable sCAP, then lock sCAP to mint CAPU, the token that grants daily AI credit on the Capminal LLM Gateway. CAPU gets more expensive as its supply grows: the price per CAPU follows a curve that rises steeply past a target supply. Before the fix, the contract read the price once, at the supply before the mint, and used that one price for the whole mint. A single large mint was therefore priced entirely at its cheapest starting point and issued far more CAPU than the curve allows. Separately, the older CapStaking V1 contract let a matured long lock keep its 5x multiplier on new deposits that were not locked at all.
Affected versions
- Mint curve (F1, high).
projects/capu(ScapStakingwith theMintRateMathlibrary) throughfd55909, the 2026-06-02 public release. On Base mainnet, theScapStakingproxy0x92ee42A61CF55642949B4fE74bB4796978ddB47aran the affected logic through implementation0x526943E98846072A9C3cbA1Aa5a1Da2ef7681a73until block 50956383 (2026-09-06). - CapStaking V1 multiplier (F2).
projects/cap-staking(CapStaking), all versions. Capminal reports V1 is fully withdrawn (totalStaked == 0) and marked it deprecated in the repository. It was replaced by the CAPU system, which has no lock multiplier.
Impact
- (F1) Over-issuance from a single mint. The mint price should be summed across the supply the mint itself creates. The code used only the starting price. On the live parameters, Capminal and we both reproduced that one mint of 126,000,000 CAP returned 99.91 CAPU, against 57.46 CAPU for the same capital priced along the curve: about 74% too much. Extra CAPU means extra daily inference credit and dilutes everyone else's share of the capped supply. Capminal saw no sign it was used in production: supply sat at about 0.87x target and was spread across normal users.
- (F1b) Mint lockout, informational. Because one call could push CAPU supply far past target, a large enough mint could push the curve into a math overflow and block all later mints and quotes until the admin reset the parameters. At the current production parameters this needs more CAP than exists (about 1.16 billion against a 1 billion total supply), so it is not reachable today. It was reachable near launch, when supply was close to zero.
- (F2) 5x multiplier without a lock. In
CapStakingV1, adding to an existing position with a shorter lock recomputed shares at the old, higher multiplier but did not push the unlock time forward. Once a 96-week lock had matured, new deposits earned the full 5x share weight while staying withdrawable right away. No on-chain funds were at risk; the effect falls on any off-chain reward split that readssharesOfortotalShares. V1 holds no funds today.
A working exploit is withheld.
Affected code
Permalinks at the vulnerable commit fd55909.
- Single-rate pricing, one rate applied to the whole amount: MintRateMath.sol#L57-L70
- Mint path reading the pre-mint supply: ScapStaking.sol#L242-L248 (
lockAndMintCapu) and the same pricing in the quote: ScapStaking.sol#L322 (pendingMintAmount) - F1b, the final multiply that overflows before the named
ExponentTooLargeguard can fire: MintRateMath.sol#L47-L54 - F2, the shorter-lock branch keeps the old multiplier and never updates
unlockTime: CapStaking.sol#L80-L83, unlike the sibling branch at CapStaking.sol#L89-L92
Fix
- #4 (merged as 3e26129) prices a mint against the supply it creates.
lockAndMintCapuandpendingMintAmountnow callcomputeMintAmountIntegrated, which walks the curve in small steps (at mosttargetSupply / 64each, at most 128 steps) and re-prices after each one. The step rule rounds in the protocol's favour, so splitting a mint cannot get more than the exact curve. The old single-ratecomputeMintAmountis removed. - The same change makes
setMintRateParamstest-price a mint before saving new parameters, so a bad setting cannot lock minting, and guards the final multiply so the curve ceiling fails with the namedExponentTooLargeerror instead of an overflow (F1b). TheScapLockedevent now reports the rate actually charged. - Deployment: Capminal upgraded the
ScapStakingproxy on Base to implementation0x24300091331452485BD174B3eE9942cd908417D0in block 50956383 (upgrade transaction). We checked on chain that the proxy's implementation slot now holds that address, and held the old implementation in the block before. After the upgrade, Capminal reports the 126M CAP quote fell from 96.65 to 55.98 CAPU at the then-current supply. - F2 is not fixed.
CapStakingV1 is deprecated, holds no funds, and the lock multiplier was removed from the system that replaced it.
Detection (for defenders)
For F1, look at ScapLocked events from the ScapStaking proxy before block 50956383 and compare the CAPU minted by unusually large single locks with what the curve would give for the same sCAP; a large gap points to a mint that used the flaw. Any deployment of this code still calling computeMintAmount is affected. For F2, look for V1 positions whose shares reflect a long lock multiplier while their unlock time had already passed when new CAP was added. A working exploit is withheld.
Timeline
- Capminal publishes the contracts (fd55909).
- Reported privately to Capminal; Capminal confirms and reproduces the mint-curve flaw against its live Base deployment.
- Filed as GitHub advisory GHSA-2qg4-mp8w-wr59 once Private Vulnerability Reporting was enabled. Capminal merges #2 and #3, aligning the docs with production and marking CapStaking V1 deprecated.
- Capminal merges the fix (#4), upgrades the
ScapStakingproxy on Base in block 50956383, and publishes the advisory. - CVE ID requested from MITRE.
- Asked the maintainer to request a CVE from GitHub (issue #5).
Credit
Finder: Aaron Elijah Mars of Aeon. Tool: Aeon.
References
- Fix PR (merged 2026-09-06): Capminal/capminal-contracts#4, merge commit 3e26129
- Fixed deployment:
ScapStakingproxy upgrade on Base, upgrade transaction, new implementation 0x2430...17D0 - GitHub advisory: GHSA-2qg4-mp8w-wr59
- CVE: pending (requested from MITRE; maintainer asked to request one from GitHub in issue #5)
- Affected repository: Capminal/capminal-contracts