Tokens & Bonding Curves
Bonding Curves

Bonding Curves

Every Superhero community token is priced by one deterministic function of its own supply. Buying mints new tokens and moves you up the curve; selling burns tokens and moves you down it. Because price is computed from supply, there is always a quote and always liquidity. There is no order book, no matching engine and no counterparty on the other side of your trade.

Superhero uses an exponential curve, implemented by the BondingCurveExponential contract. The contract evaluates e^x as a bounded Taylor series in integer arithmetic (at most 100 terms, stopping as soon as a term floors to zero), which is what curve_type() means when it returns "TAYLOR_EXPONENTIAL_V1". The series agrees with the closed form below to within 4e-19 AE at every supply in the examples below. The integer the contract returns is the price you are charged; Curve Parameters & Units has a reference implementation that reproduces it exactly.

The formulas

buy(x)  = 0.001 · e^(0.00000001 · x) − 0.0009999

sell(x) = buy(x) · 0.995

x is the circulating supply in whole tokens; the result is the instantaneous (spot) price in AE per token at that supply. Three constants do all the work:

ConstantValueStored on-chain asRole
a0.001a = 10^15Scale factor on the exponential
k0.00000001 (1e-8)k = 10^10Growth rate per token of supply
c0.0009999not storedOffset that pulls the launch price down to a near-zero number

The contract holds a and k scaled by 10^18, plus initial_price = 10^11, the spot price at supply zero, 0.0000001 AE. The offset c is a − initial_price and is never stored. See Curve Parameters & Units for the full constant table.

At supply 0 the spot price is 0.001 − 0.0009999 = 0.0000001 AE, one ten-millionth of an AE per token. The curve is almost flat at the start and steep later.

What you pay is never the spot price. It is the integral of the curve across the range of supply you are minting into:

buy price   = ∫ from supply to (supply + amount) of buy(x) dx

sell return = ∫ from (supply − amount) to supply of sell(x) dx

The spread (the community DAO's share) is the area between the two curves:

spread = ∫ from 0 to supply of buy(x) dx  −  ∫ from 0 to supply of sell(x) dx

Integrating the curve

For F'(x) = a·e^(k·x) − c:

F(x) = (a / k) · e^(k · x) − c · x

with a = 0.001, k = 0.00000001, c = 0.0009999:

a / k = 0.001 / 0.00000001 = 100000

F(x) = 100000 · e^(0.00000001 · x) − 0.0009999 · x

So the cost of buying n tokens starting from supply S is:

cost(S, n) = F(S + n) − F(S)
           = 100000 · ( e^(0.00000001·(S+n)) − e^(0.00000001·S) ) − 0.0009999 · n

That is the whole pricing model. Everything below is arithmetic on this one line.

Worked example 1: 1,000 tokens at supply 0

cost(0, 1000) = 100000 · ( e^(0.00000001 · 1000) − e^0 ) − 0.0009999 · 1000
              = 100000 · ( e^0.00001 − 1 ) − 0.9999

e^0.00001      = 1.000010000050000166667…
e^0.00001 − 1  = 0.000010000050000166667…
× 100000       = 1.0000050000166667…
− 0.9999       = 0.0001050000166667…

cost = 0.000105000017 AE   (about 0.000105 AE)

The average price paid is 0.000105000017 / 1000 = 1.05000017e-7 AE per token, against a spot price of 1.0e-7 AE when you started. You paid 5.00% above spot for a thousand tokens, because by the thousandth token the spot price had already risen to 1.10e-7 AE.

Worked example 2: 1,000 tokens at supply 10,000,000

cost(10000000, 1000)
  = 100000 · ( e^(0.00000001 · 10001000) − e^(0.00000001 · 10000000) ) − 0.9999
  = 100000 · ( e^0.10001 − e^0.1 ) − 0.9999

e^0.1       = 1.10517091807564762481…
e^0.10001   = 1.10518196984008711139…
difference  = 0.00001105176444865756…
× 100000    = 1.10517644394865756…
− 0.9999    = 0.10527644394865756…

cost = 0.105276443949 AE

The same thousand tokens now cost 0.10528 AE instead of 0.000105 AE, about 1,003 times more. Average price 1.052764e-4 AE, spot price at supply 10,000,000 1.052709e-4 AE: this time you paid only 0.0052% above spot.

The same trade size is proportionally far more expensive near supply zero than deep into the curve. Near zero, the −0.0009999 offset has cancelled almost all of 0.001·e^(kx), so the tiny residual price doubles over a very short span of supply. Further out, the offset is negligible and the curve is locally almost linear, so a thousand tokens barely move it.

Curve slippage

You are charged the area under a rising curve, but the quoted spot price is only its height at the left-hand edge. The bigger the trade, the worse your average fill. All of these are buys starting from supply 10,000,000, where spot is 1.052709e-4 AE:

Tokens boughtTotal AE costAverage price (AE)Average vs spot
1,0000.1052761.05276e-4+0.0052%
100,00010.5823691.05824e-4+0.525%
1,000,000110.8152381.10815e-4+5.267%
10,000,0001,624.1840081.62418e-4+54.29%
50,000,00021,699.7882314.33996e-4+312.3%

Buying 10,000,000 tokens in one transaction doubles the supply and costs a 54% premium to spot. Splitting the order does not help: the curve is path-independent, so ten buys of 1,000,000 from a rising supply cost exactly the same total as one buy of 10,000,000. Only trade size and starting supply change your average price.

A large sell realises an average price below the quoted spot for the same reason, in reverse. minimal_return_required protects you from that. See Buying & Selling.

Shape of the curve

Both curves over the first 100 million tokens of supply, with # the buy curve and . the sell curve where it separates:

        price (AE per token)
 1.72e-03 |                                                      ##
          |                                                    ##.
          |                                                 ###
 1.37e-03 |                                               ##.
          |                                            ###
          |                                         ###
 1.03e-03 |                                      ###
          |                                   ###
          |                               ####
 6.87e-04 |                           ####
          |                       ####
          |                   ####
 3.44e-04 |              #####
          |         #####
          |    #####
 0.00e+00 |####
          +--------------------------------------------------------
          0             25M           50M           75M        100M
                              supply (tokens)

The sell curve sits 0.5% below the buy curve everywhere. The gap between them is the DAO's cut: small per trade, meaningful in aggregate. Spot prices at a few reference supplies:

SupplyBuy spot (AE)Sell spot (AE)
01.000000e-79.950000e-8
1,000,0001.015017e-51.009942e-5
10,000,0001.052709e-41.047446e-4
50,000,0006.488213e-46.455772e-4
100,000,0001.718382e-31.709790e-3
200,000,0006.389156e-36.357210e-3

The curve is tuned on the expectation that only 10–20% of the total supply will ever be reached, which is why the interesting price action is packed into the first couple of hundred million tokens.

Why the reserve is always solvent

The sell curve sits strictly below the buy curve at every supply level, so the AE paid into the sale contract always exceeds the AE it could ever be asked to pay out. Selling the entire circulating supply back to the curve is always possible.

At a supply of 10,000,000 tokens, buyers have paid in 518.09 AE in total, and selling every one of those tokens back would return 515.50 AE. The 2.59 AE difference is the DAO's accumulated spread, and it never has to be given back.

The spread

The sell() curve returns 99.5% of buy(), and the sale contract adds a 0.5% affiliation fee on buys, so the total spread between buy and sell price is 1% of the curve value: 0.5% to the community DAO and 0.5% to the affiliation system.

From the buyer's side: you hand over 1.005 × the curve integral and can immediately sell back for 0.995 × it, so a round trip at unchanged supply returns 0.995 / 1.005 = 0.99502… of what you paid, a 0.995% loss on an instant round trip. See Fees & Slippage for the full breakdown and Risks for what that means for a position.

Compared with other curve families

PropertySuperhero (exponential)Linear curveConstant product (Uniswap-style)
Price ruleprice = a·e^(k·supply) − cprice = m·supply + bprice = reserve_y / reserve_x, with x·y = k
What backs itAE reserve accumulated from buysAE reserve accumulated from buysTwo-sided pool funded by liquidity providers
Who supplies liquidityNobody: the contract mints and burnsNobodyLiquidity providers, who can withdraw
SupplyElastic: minted on buy, burned on sellElasticFixed; the pool only swaps existing tokens
Price at zero activityDefined by the formulaDefined by the formulaUndefined until someone seeds the pool
Cost of a tradeIntegral of the curve over the minted rangeIntegral of the curve over the minted rangeDetermined by the invariant x·y = k
Price impact of a big buyCompounding: grows exponentiallyProportional to sizeGrows as the pool is drained; unbounded
Fee model1% spread baked into two curvesImplementation-definedExplicit swap fee (e.g. 0.30%) to LPs
Rug-pull surfaceNo LP to withdrawNo LP to withdrawLPs can remove liquidity

Two practical consequences. There is no liquidity to pull: the reserve is held by the sale contract and is sufficient to redeem everything. And an exponential curve punishes large late buys much harder than a constant-product pool of comparable depth. The price impact of doubling the supply is a factor of e^(k·supply), not a bounded ratio.

Community tokens trade only against their own curve. Superhero's AMM for ordinary token pairs is the DEX.

Reading the curve from the contract

EntrypointReturns
calculate_buy_price(total_supply, count)Cost to buy count tokens from total_supply, in aettos
calculate_sell_return(total_supply, sell_tokens)AE returned for selling sell_tokens, in aettos
buy_curve(x) / sell_curve(x)The spot curve value as a Frac.frac rational
buy_price(total_supply) / sell_price(total_supply)The same value rounded to an integer (see below)
get_k(), get_initial_price(), get_minimum_count()10^10, 10^11, 10^12
get_sell_return_percentage()9950; the sell factor is 9950 / 10000 = 0.995
curve_type(), supported_decimals()"TAYLOR_EXPONENTIAL_V1", 18

Every one of these takes and returns integers in the contract's own units. Read Curve Parameters & Units before calling them. Passing whole tokens where the contract expects 18-decimal units gives an answer that is wrong by a factor of 10^18.

buy_price() and sell_price() round a value like 1.05e-4 AE per token to an integer, so buy_price() returns 1 and sell_price() returns 0 for every supply under roughly 690 million tokens. Use calculate_buy_price and calculate_sell_return for quotes, or buy_curve for the exact spot value.

get_minimum_count() returns 10^12, and every pricing call requires count >= minimum_count (MINIMUM_TOKENS_REQUIRED). Since counts are in 18-decimal units that floor is 10^-6 tokens, a guard against a trade rounding to zero inside the integer arithmetic, not an order minimum. It fires when a caller passes a whole-token count where the contract expected token decimal units.

Related