GitHub Advisoryadvisory · Go
GHSA-p7gw-2pcp-5pf8 Klever: Marketplace settlement mints KLV when referral % + royalty % exceed the bid (negative seller share silently skipped)
CRITICAL
Official page ↗
- Aliases
- CVE-2026-54754
- Ecosystem
- Go
- Packages
- github.com/klever-io/klever-go
- Severity
- Critical
- CVSS vector
- CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:C/C:N/I:H/A:H
- Weaknesses
- CWE-191, CWE-367, CWE-682
- Reviewed
- 2026-08-28
Affected packages
• Go github.com/klever-io/klever-go: < 1.7.19 → fixed in 1.7.19
Description
Summary
When a marketplace order is settled (`MarketBuy` / `BuyItNow`, and auction `Claim`), the buyer's
payment is split three ways — referral, royalties, and the seller (market-order owner)
remainder:
```
marketOwnerAmount = CurrentBid − referralAmount − royaltiesAmount
```
Referral and royalties are paid out unconditionally, but the seller remainder is only paid
when positive (`computeMarketOwnerAmount` returns `Ok` and pays nothing when the amount is
` bid`, the surplus
`(referralAmount + royaltiesAmount − bid)` is minted.
2. The combined ≤100% invariant is enforced only at listing time
`Sell` (`market.go:908`) correctly rejects a listing whose combined cut exceeds 100%:
```go
if asset.Royalties.MarketPercentage + marketplace.ReferralPercentage > core.HundredPercent {
return transaction.Transaction_ParameterInvalid, common.ErrInvalidValue
}
```
…and snapshots referral into the order, but not royalty (`market.go:997-998`):
```go
marketOrder := &kapps.MarketOrderData{
// ...
ReferralPercentage: marketplace.ReferralPercentage, // snapshotted
RoyaltiesFixedDeposit: asset.Royalties.MarketFixed, // snapshotted
// NOTE: asset.Royalties.MarketPercentage is NOT snapshotted -> read live at buy
}
```
`MarketOrderData` has no field for the royalty percentage (`kapps/market.pb.go`), so settlement
always re-reads it live from the (mutable) asset.
3. Royalty % is mutable after listing
`core/kapp/kda/trigger.go` — `handleUpdateRoyaltiesNFTandSFT` (L613+) lets the asset owner overwrite
`asset.Royalties.MarketPercentage` (L670) with only a per-field ` The shipped emergency-guard source documents this exact vector:
> *"The royalty percentage is read live at buy time, so a listing made now can be weaponised later
> via UpdateRoyalties."* (`common/emergencyGuard.go`)
Net effect: `referralAmount + royaltiesAmount = bid + bid = 2·bid`; `marketOwnerAmount = −bid`
(skipped); `bid` KLV minted per settlement, paid to attacker-controlled addresses.
---
Proof of Concept
A. Committed regression test (deterministic, runnable today)
`core/kapp/market/market_test.go` — `TestMarketKApp_ExecuteBuyMarket_RoyaltyReferralInflation`.
It builds an order with `ReferralPercentage = 100%` and an asset with `MarketPercentage = 100%`
(the attacker is both the referral and the royalty address), then settles a `bid` of
`25,600,000 KLV` (`25600000000000` base units):
```bash
go test ./core/kapp/market/ -run TestMarketKApp_ExecuteBuyMarket_RoyaltyReferralInflation -v
```
• `FixDisabled_MintsKLVFromThinAir`: settlement returns `Ok`; the attacker address ends with
`2·bid` credited while only `bid` was paid in — i.e. `bid` KLV minted.
• `FixEnabled_RejectsInflation`: with `FixMarketBuyOverflow` on, settlement returns
`Transaction_AmountInvalid` and the attacker balance stays `0` — no payout runs.
B. End-to-end on a local node (the real attack path)
A single-node local network is sufficient. The exploit is four transactions from one ordinary
funded account; nothing privileged is required.
1. Create an NFT collection you own, with `royalties.marketPercentage = 0` and a royalties
address you control.
2. Create a marketplace with `referralPercentage = 10000` (100%) and a referral address you
control (`CreateMarketplace`).
3. List one NFT for sale (`Sell`) on that marketplace. The `Sell` check passes because
`0 (royalty) + 10000 (referral) = 10000 = HundredPercent`. The order snapshots
`ReferralPercentage = 10000`.
4. Raise the royalty on the asset to 100% (`AssetTrigger / UpdateRoyalties`,
`marketPercentage = 10…
Related
Alias · CVE (1)
- CVE-2026-54754 Klever-Go is the Go implementation of the Klever blockchain protocol. vulnerability