Docs

How it works

Two documents from the repository: how the ratchet works, and what can go wrong.

Mechanics

File: docs/en/MECHANICS.md

Reference document, written for a non-engineer reader who can follow a formula. Source of truth: core/src/lib.rs (the code is authoritative, this document explains it) and core/src/tests.rs (what is proven). Date: 2026-10-09. Status: program not deployed.

Two sentences carry the product. They live in config/brand.ts and must not be reworded:

The pump pays you, even if you never sell. And once acquired, nothing can take it back.

This document explains exactly what these two sentences mean, and nothing more.

Vocabulary: throughout this document, "token" means the smallest unit of the token (with 6 decimals, 1 displayed token = 1,000,000 units). "Lamport" is the smallest unit of SOL (1 SOL = 1,000,000,000 lamports).


1. What the ratchet does in 5 lines

  1. Each launch has a curve that sells tokens. The program counts how many tokens have left the curve: that is sold. It also remembers the highest level sold has ever reached: that is high_water.
  2. When a buy pushes sold above high_water, a share of that buy's fee (30% of the fee on the new ground) is credited to the holders who held tokens before that buy.
  3. This credit is recorded in a per-token counter, acc_per_token, which only ever goes up. Nobody, and no instruction, can make it go down.
  4. A sell lowers sold, but touches neither high_water, nor acc_per_token, nor anything already credited to anyone.
  5. The credited lamports sit in a reserve that only the holder can empty, to their own wallet, at any time, with no fee, forever.

2. The state

Per launch (Launch account)

FieldTypeWhat it is
curve_supply64-bit integerTotal number of tokens the curve can sell before graduation.
sold64-bit integerTokens currently out of the curve. Goes up on a buy, down on a sell.
high_water64-bit integerThe highest sold ever reached. Never goes down.
acc_per_token128-bit integer, fixed pointLamports credited per token held, multiplied by 10^12 (SCALE). Never goes down.
carry128-bit integerThe remainder of the division of the last credit, carried over to the next credit. Never thrown away.
reserve_in64-bit integerTotal lamports that have ever entered the ratchet reserve.
reserve_claimed64-bit integerTotal lamports that have ever been claimed out of the reserve.
clicks64-bit integerNumber of new highs (display only).
frozen_at_graduationbooleanTrue after graduation. No more credit after that. Claims stay open.
pooladdressThe Raydium CP-Swap pool opened by migrate (§9). All zero before that.

Ratchet balance of the reserve = reserve_in − reserve_claimed. On top of this, the reserve account (an address belonging to the program) also holds a fixed rent floor: at create_launch the program tops the reserve account (and the curve's SOL account) up to the rent-exempt minimum of an empty Solana account (890,880 lamports today), paid by the launch creator. That floor is never counted in reserve_in and is not claimable by anyone. So the SOL the reserve account must contain is: rent floor + reserve_in − reserve_claimed.

Per holder (Holder account, one per launch/wallet pair)

FieldWhat it is
balance_trackedTokens bought on the curve and not sold back. During the curve the tokens are held in escrow in the program's vault, so this number is the balance.
debtThe value of acc_per_token at this holder's last settlement.
creditedLamports acquired and not yet claimed. Only settlement increases it; only a claim resets it to zero. Selling does not touch it.
claimed_totalTotal claimed over the holder's lifetime (display).
withdrawnTrue once the tokens have been withdrawn from escrow after graduation.

The constants (fixed in the program, no instruction changes them)

ConstantValueMeaning
TRADE_FEE_BPS100Trading fee: 1.00% of the SOL amount of every buy and every sell. This is the standard market fee; the ratchet redistributes a share of it, it does not add to it.
RATCHET_BPS3,000Share of the fee on new ground that goes to the ratchet: 30%.
CREATOR_FEE_BPS5,000Share of the remainder that goes to the creator: 50%. The platform receives the rest.
SCALE10^12Precision of acc_per_token.

3. The accumulation formula (what a buy does)

A buy of n tokens with a total fee fee (in lamports) does the following, in this order:

circulating_before = sold                         (the tokens already held by others)
new_sold           = sold + n

if new_sold > high_water :                        (there is new ground)
    new_ground            = new_sold − high_water
    if circulating_before > 0 :
        fee_on_new_ground = fee × new_ground / n                   (pro rata of the buy)
        ratchet_share     = fee_on_new_ground × 3,000 / 10,000      (30%)
        numerator         = ratchet_share × 10^12 + carry
        acc_per_token     = acc_per_token + (numerator ÷ circulating_before)   (integer division)
        carry             = numerator modulo circulating_before                (the remainder, kept)
        reserve_in        = reserve_in + ratchet_share
    high_water = new_sold
    clicks     = clicks + 1

sold = new_sold
remainder  = fee − ratchet_share
creator    = remainder × 5,000 / 10,000
platform   = remainder − creator

Three points to remember:

  • Only new ground counts. If new_sold does not exceed high_water, ratchet_share = 0 and the whole fee goes to creator/platform.
  • The credit goes to the tokens that were there before. The divisor is circulating_before, not new_sold. The n tokens that have just been bought receive nothing from their own buy.
  • Nothing is lost in the division. The remainder goes into carry and will be added to the numerator of the next high.

One exception on the creator and platform shares, in the on-chain program: a creator or platform share is paid only if the receiving wallet ends up at or above the Solana rent-exempt minimum. If a share would leave that wallet below it (for example, a wallet emptied to 0 lamports receiving a small share), that share is kept by the trader: on a buy it is not charged, on a sell it is paid to the seller. This exists so that a fee wallet can never block a trade. The ratchet share is not affected.

Worked example

Before the buy: sold = 1,500,000, high_water = 2,000,000, acc_per_token = 0, carry = 0. (Someone has sold since the last high: sold has gone back down below high_water.)

A buyer buys n = 1,000,000 tokens for 2,000,000,000 lamports (2 SOL). Fee: 1% = fee = 20,000,000 lamports.

new_sold           = 1,500,000 + 1,000,000 = 2,500,000      > 2,000,000 : new ground
new_ground         = 2,500,000 − 2,000,000 = 500,000        (only half of the buy)
fee_on_new_ground  = 20,000,000 × 500,000 / 1,000,000 = 10,000,000 lamports
ratchet_share      = 10,000,000 × 3,000 / 10,000     = 3,000,000 lamports  → reserve
numerator          = 3,000,000 × 10^12 + 0           = 3 × 10^18
acc_per_token      = 0 + 3 × 10^18 ÷ 1,500,000       = 2,000,000,000,000   (i.e. 2 lamports per token)
carry              = 3 × 10^18 mod 1,500,000         = 0
high_water         = 2,500,000 ;  sold = 2,500,000 ;  clicks + 1
remainder          = 20,000,000 − 3,000,000 = 17,000,000
creator            = 8,500,000 ;  platform = 8,500,000

The 1,500,000 tokens that were held before this buy are now credited with 2 lamports each. The buyer's 1,000,000 tokens: nothing, for this buy.

The same example with a remainder (carry)

If circulating_before had been 1,400,000 instead of 1,500,000:

3 × 10^18 ÷ 1,400,000 = 2,142,857,142,857   remainder 200,000
acc_per_token += 2,142,857,142,857         (≈ 2.142857 lamports per token)
carry          = 200,000                   (in units of 10^-12 lamport: 0.0000002 lamport in total)

This remainder of 200,000 will be added to the numerator of the next high. It is not thrown away. It represents less than one lamport in total, but the rule is: nothing is thrown away.


4. The settlement formula (settle)

Settlement turns the rise of acc_per_token into concrete lamports for a holder. It is a single internal function, called first by every instruction (buy, sell, claim, graduation/withdrawal). There is no path that changes a holder's balance without settling it first.

delta     = acc_per_token − debt                 (cannot be negative: acc never goes down)
pending   = balance_tracked × delta ÷ 10^12      (integer division)
credited  = credited + pending
debt      = acc_per_token

Calling settle twice in a row gives 0 the second time: delta = 0. It is idempotent.

Worked example

Take the example from §3: acc_per_token went from 0 to 2,000,000,000,000.

A holder holds balance_tracked = 300,000 tokens, last settled when acc_per_token was 0 (debt = 0).

delta    = 2,000,000,000,000 − 0 = 2,000,000,000,000
pending  = 300,000 × 2,000,000,000,000 ÷ 10^12 = 600,000 lamports
credited = 0 + 600,000
debt     = 2,000,000,000,000

This holder has 600,000 lamports acquired. They can claim them now or in three years; it is the same number.

Example of rounding down

With the carry variant from §3 (delta = 2,142,857,142,857) and a holder of 7 tokens:

pending = 7 × 2,142,857,142,857 ÷ 10^12 = 14,999,999,999,999 ÷ 10^12 = 14 lamports (not 15)

Rounding is always down for the holder. The fraction of a lamport stays in the reserve. It is claimable by nobody: not by the holder, not by the creator, not by the platform. See SECURITY.md, section "Arithmetic".


5. The monotonicity invariant and why it holds

The claim: acc_per_token never goes down, high_water never goes down, credited only goes down when the holder claims it themselves.

Why this is true, instruction by instruction:

Instructionhigh_wateracc_per_tokencredited (of a holder)
buygoes up if new ground, otherwise unchangedgoes up if new ground and circulating > 0, otherwise unchangedgoes up (settlement), never goes down
sellunchangedunchangedgoes up (settlement), never goes down
claimunchangedunchangedgoes up (settlement) then set to zero and paid to the holder
graduation (migrate)unchangedunchangedunchanged
post-graduation withdrawalunchangedunchangedgoes up (settlement), never goes down

In the code, the only line that writes acc_per_token is an addition. The only line that writes high_water is high_water = new_sold inside an if new_sold > high_water. The only line that writes credited downward is credited = 0 in the claim, after paying exactly that amount to the holder. There is no administration instruction: nothing can decrement these fields, reset them to zero, or freeze them other than graduation.

What is proven by the tests (core/src/tests.rs): the invariant is checked after every operation over 10,000 random adversarial sequences (prop_monotone_10k, up to 60 operations each, including full sells, round trips, buys exactly at the high, buys one token above the high, bundles of 30 buys, claims, graduation, exhaustion of the curve) and over four sequences of 5,000 operations (adversarial_long_sequences).

Full-sell test (sell_everything_keeps_credit_and_claim_still_works): a holder accumulates credit, sells 100% of their position, then everyone sells 99% of the rest. Their credited has not moved by a single lamport. They claim: they receive exactly that amount. They claim a second time: 0, with no error.

This is the exact meaning of "once acquired, nothing can take it back".


6. Why wash trading brings nothing

The ratchet does not look at volume. It only looks at whether sold goes above its all-time maximum. Buying then selling back brings sold back to the same point: the second buy crosses no new ground.

The test wash_trading_1000_round_trips_earns_nothing_beyond_new_ground:

  • Two holders A and B each hold 10,000 tokens. high_water = 20,000.
  • A wash trader makes 1,000 round trips: buys 5,000 tokens, sells 5,000 tokens back, with a fee of 50,000 lamports on every buy and every sell.
  • Total fees paid by the wash trader: 2,000 × 50,000 = 100,000,000 lamports.
  • What entered the ratchet reserve: 15,000 lamports, all of it on the first trip (5,000 tokens of new ground × 100% of the buy × 30% of 50,000). The other 999 trips: new ground = 0, credit = 0, acc_per_token unchanged.

In other words: 0.015% of the wash-trading fees fed the ratchet, and only because the first buy was a real new high. The wash trader paid 100 million lamports in fees to credit 15,000 lamports to the other holders, and nothing to themselves (their tokens were not there before their own buy).

Wash trading does not "pump" the ratchet. On a buy that crosses no new ground, and on every sell, the whole fee goes to the creator and the platform: the wash trader only pays them fees. In the test above, out of 100,000,000 lamports of fees, only 15,000 (the new ground of the first round trip) went to the ratchet, and all the rest went to the creator and the platform.


7. Same slot, bundles

On Solana several transactions can be executed in the same slot, or even grouped together. This changes nothing: the program executes the buys one after the other and each buy sees the state left by the previous one.

Test bundle_of_30_buys_crosses_ground_once: high_water = 100,000, sold has gone back down to 40,000. A bundle of 30 buys of 4,000 tokens (120,000 in total) brings sold up to 160,000.

  • The first 15 buys (40,000 → 100,000) cross no new ground: 0 credit.
  • The next 15 (100,000 → 160,000) cross 60,000 tokens of new ground, only once, in 15 pieces of 4,000.
  • Sum of new ground = 60,000 = 160,000 − 100,000. Not 120,000. Not twice 60,000.
  • With 1,000 lamports of fee per token: reserve = 60,000 × 1,000 × 30% = 18,000,000 lamports.

Test bundle_vs_single_buy_same_ground_same_reserve: 30 small buys covering the same ground as a single large buy put the same lamports into the reserve, up to rounding (at most 1 lamport of difference per buy).

A buyer who splits their buy credits neither more nor less. A buyer who places themselves just before a large buy in the same slot is treated exactly like someone who had held their tokens from the start: the test sniper_earns_exactly_holding_period checks that a "sniper" who enters just before a high and exits just after is credited the same amount as a long-term holder, for that event, neither more nor less. The ratchet pays for holding at the moment of the high, nothing else.


8. First buyer

On the very first buy, circulating_before = 0: nobody held anything before. The program credits nobody and performs no division (no division by zero). The whole fee goes to creator/platform. high_water takes the value of this buy.

Test first_buyer_credits_nobody_no_div_by_zero: reserve = 0, acc_per_token = 0, high_water = n, creator + platform = total fee.

The first buyer is not credited for their own buy. They will be credited starting from the second buy that goes beyond theirs, like everyone else.


9. Graduation and lazy settlement

Graduation is the migrate instruction. Anyone can call it, with no arguments, once the curve is fully sold (sold >= curve_supply, otherwise CurveNotComplete). In one atomic instruction it:

  1. sets frozen_at_graduation = true;
  2. moves the 206.9M tokens never sold (TOTAL_SUPPLY − sold) and the curve's SOL, minus MIGRATION_OVERHEAD (0.25 SOL, which pays Raydium's 0.15 SOL create-pool fee and the rent of the pool's accounts), into a new Raydium CP-Swap pool (program and 0.25% fee tier fixed in the program);
  3. burns every LP token it receives: nobody can withdraw that pool's liquidity;
  4. closes the temporary accounts (their rent goes back to whoever paid it) and sends what is left of the 0.25 SOL plus the curve account's remaining lamports to the launch creator. The curve account ends at 0 lamports. The pool's address is recorded in Launch.pool.

The pool opens at the last curve price, to within about 0.3% (the effect of holding back 0.25 SOL). Until migrate succeeds, the curve stays open for sells: there is no state where the SOL is stuck and the exit is closed. If the call into Raydium fails, the whole instruction is reverted and nothing has changed.

From then on:

  • no more buys or sells on the curve (error Frozen);
  • acc_per_token, high_water, carry and reserve_in never change again;
  • claims and token withdrawal remain available, with no time limit.

The program does not "settle" every holder at graduation. It does not need to. Since acc_per_token is constant after the freeze, settling a holder will give exactly the same delta, and therefore exactly the same lamports, whether it is done in the second of graduation or months later. This is what is called lazy settlement: it happens when the holder shows up.

Test graduation_lazy_settle_is_exact: 50 holders, 2,000 random operations, graduation. Each holder's settlement is computed at the moment of graduation (the "eager" version) and compared with the settlement done later on the live state (the "lazy" version). The 50 values are identical to the lamport.

Test graduation_freezes_exactly_and_claims_forever: after graduation, buy and sell fail, a second graduation fails, acc_per_token and reserve_in have not moved, claims work, token withdrawal works, and when everyone has claimed at most 2 lamports of dust remain in the reserve (in the accounting; on-chain, the reserve account also still holds its rent floor from §2, which belongs to nobody's credit).

On-chain test graduation_boundary_and_claim_forever (the built program, next to the real Raydium CP-Swap mainnet program): migrate called by an arbitrary wallet, the pool holds the curve's SOL minus the overhead and the 206.9M tokens, the LP is burned, the curve account is empty, the caller pays only the transaction fee, then withdrawn tokens are sold into the Raydium pool. Test migrate_guards: migrate too early or with another fee tier fails, and a sell is still possible on a full curve as long as migrate has not happened.

Sentence from brand.ts: "The ratchet runs during the curve. After graduation it stops, and what you acquired stays yours."


10. Claiming

The claim (claim):

  1. settles the holder (§4);
  2. pays credited lamports from the reserve to the holder's wallet, and to that wallet only;
  3. resets credited to 0, increments claimed_total and reserve_claimed.

Zero fee taken by the program (the Solana network charges its own transaction fees; the program adds nothing). No access control: any holder, at any time, before or after graduation. No pause: there is no pause instruction in the program. Claiming while credited = 0 returns 0 and causes no error.

The program does not know the time. There is no deadline, no expiry, no "claim before". This cannot change: there is no time field in the state.


11. Token escrow during the curve and withdraw_frozen

During the curve, bought tokens are not sent to the buyer's wallet. They stay in a vault belonging to the program, and the Holder account records balance_tracked. This number is what settlement uses.

Why: if tokens circulated freely during the curve, the program would have to follow every transfer (via a "transfer hook") to know who holds what, and any tracking error would distort the credits. With escrow, the tracked balance is the real balance, by construction. No hook, no drift.

Consequence: during the curve, the tokens are not visible in the wallet, and cannot be transferred out of the program. They can be sold on the curve (sell), and that is all.

After migrate, the holder calls withdraw_frozen:

  1. settles the holder (the credit is kept);
  2. transfers balance_tracked tokens from the vault to the holder's token account;
  3. sets balance_tracked = 0 and withdrawn = true.

They can then trade their tokens on the Raydium pool. Their credit remains claimable after the withdrawal (test settle_first_graduate_withdraw and withdraw_requires_graduation_and_keeps_credit). Calling withdraw_frozen before graduation fails (NotGraduated), and so does calling it before the pool exists (NotMigrated): no token leaves escrow before migrate, so nobody can open a competing pool at another price before it.

After the withdrawal, the program no longer follows these tokens, and there is nothing left to follow: the ratchet has stopped.


12. The fee split in bps

Three numbers, displayed on each token's page, fixed at launch, identical for all launches of this version of the program:

DisplayedValueOn what
Trading fee100 bps (1.00%)The SOL amount of every buy and every sell.
Ratchet share3,000 bps (30%)Of the fee on the new ground of a buy.
Creator share5,000 bps (50%)Of the remainder of the fee after the ratchet share. The platform gets the rest.

What this means in practice, relative to the amount of a buy:

SituationRatchetCreatorPlatform
The buy is 100% new ground30 bps35 bps35 bps
The buy is 50% new ground (example from §3)15 bps42.5 bps42.5 bps
No new ground, or any sell0 bps50 bps50 bps

The ratchet does not add to the 1% fee. It is a share of it. On a buy with no new ground, the fee is the same and goes entirely to creator/platform.

(As stated in §3: if a creator or platform share would leave the receiving wallet below the Solana rent-exempt minimum, that share is not paid to it and stays with the trader. The ratchet column is never affected.)


13. What the program does NOT know

This must be said as clearly as the rest.

  • The price. There is no price in the program. No oracle, no price feed, no average. The "high" is the maximum of sold, an integer the program owns itself. A new high of sold is not a new high of the price in SOL, let alone in dollars.
  • Time. There is no clock in the state. The program does not know how long you have held, nor what time it is. That is why claims never expire, and also why there is no bonus for holding longer.
  • Who holds after graduation. Once the tokens are withdrawn from escrow, they circulate freely and the program no longer sees them. It does not try to see them: the ratchet has stopped.
  • Who you are. No list, no identity check, no wallet privilege. The launch creator has no power over the ratchet; they receive their share of the fee, and that is all.
  • What the token is worth. The program redistributes a share of a fee in lamports. It does not know, and cannot know, whether the token itself is worth anything. See docs/RISKS.md.

Risks

File: docs/en/RISKS.md

Date: 2026-10-09. Status: program not deployed, update authority not revoked.

This document lists the reasons why you can lose money on a TOPPD launch, or why TOPPD itself can fail. It is written without softening. If a sentence in this document sounds like marketing to you, that is a mistake: report it.

The mechanisms mentioned are described in docs/MECHANICS.md. What the program protects is set out in SECURITY.md. This document only covers what that protection does not cover.


1. The amounts can be tiny (risk no. 1)

The ratchet redistributes 30% of the 1% fee on the new ground of a buy. Not 30% of the volume. Not 30% of the fee. 30% of the part of the fee that corresponds to tokens never sold before, divided among all the tokens already in circulation.

In practice: on a 1 SOL buy that is entirely new ground, the ratchet receives 0.003 SOL (3,000,000 lamports), shared among all existing holders pro rata. A holder who holds 1% of the circulating supply receives 30,000 lamports, i.e. 0.00003 SOL. If the buy is only half new ground, it is half that. If the token no longer makes new highs, it is zero.

Once the discovery phase is over, most buys happen below the all-time high and credit nothing. The ratchet is a mechanism that pays when the high is extended, not a regular flow.

The real orders of magnitude, measured by simulation on the trajectories of existing launches, are in research/G2.md. That document now exists (research/G2.md, dated 2026-10-09); its numbers are not repeated here because they are being recomputed. Read them there, with their sample and their date. Its headline figures and their measurement date must be displayed on every token page. If G2 shows that the amounts are negligible for a median holder, that is a fact to display, not to hide.

2. Late entrants fund the ratchet of earlier ones

This is a real transfer, not a metaphor. When you buy on new ground, 30% of the fee on that ground goes to the people who held before you. You receive nothing from your own buy. You will only receive something if someone after you pushes sold even higher.

Sentence from config/brand.ts, displayed mandatorily on every launch page:

The later you enter, the more you feed other people's ratchet before filling your own.

The later you enter in the life of the curve, the larger the ground already taken compared with the ground that remains, and the lower the probability that a new high comes after you. The last buyer before graduation funds everyone and is funded by no one.

The only defence is to measure this transfer and display it. The G7 measurement (net contribution by entry rank: how much a holder who entered at rank k paid into other people's ratchet versus how much they acquired) must be displayed on every page, with its calculation date. There is no mechanical defence: the mechanism is this transfer.

3. A large holder who never sells captures most of it

Credit is pro rata to the tokens held at the moment of each high. A wallet that buys early, buys big, and never sells is present at every high with a large share of the circulating supply. It mechanically captures the largest share of every click.

Nothing in the program caps this. There is no per-wallet limit, no tapering, no list. The launch creator, if they buy first and buy a lot, is in this position.

An ordinary holder should expect to receive a share of the ratchet proportional to their share of the supply, that is, small if they are small. The ratchet does not correct concentration; it reflects it.

4. The ratchet only runs during the curve

After graduation, frozen_at_graduation is true and no credit is ever added again. The token then trades on the Raydium CP-Swap pool that migrate opens, outside the program, and the program no longer sees anything.

Sentence from config/brand.ts:

The ratchet runs during the curve. After graduation it stops, and what you acquired stays yours.

If the token goes up 100x after graduation, the ratchet receives nothing. If you buy after graduation, you are never credited with anything: there is no more ratchet. The window during which the mechanism works is short, and it is the most volatile one.

There will be no "continuation" of the ratchet on the AMM via a transfer hook: it would break aggregator routing (Jupiter) and make the token unsellable on most interfaces. This is a final choice.

5. Competitors can copy it in two weeks

The mechanism fits in ~400 lines of pure Rust, publicly documented in this repository. An existing launchpad, which already has users, liquidity and a brand, can integrate it in two weeks. There is no secret, no technical barrier, no patent.

The G1 research work (research/G1.md, 2026-10-09) found no live product with this trigger. This means the idea is new at the time this document is written. It does not mean it will stay new.

If you hold a TOPPD launch because "TOPPD has an advantage", that is not a lasting advantage.

6. The token can be worth zero while the ratchet does not go down

Sentence from config/brand.ts, displayed mandatorily at the same size as the ratchet on every page:

The ratchet cannot go down. The token can go to zero. Both are true at the same time.

You need to understand why both hold together. The ratchet counts lamports in SOL that are already in a reserve: those lamports exist, are claimable, and nobody can take them back. The token is something else: its price depends on what someone is willing to pay, and nobody is obliged to pay anything.

Ordinary scenario: you buy 1 SOL of the token. The curve makes a few highs, you are credited with 50,000 lamports (0.00005 SOL). Everyone sells, the token is worth zero. You have lost 1 SOL and you have acquired 0.00005 SOL. Both sentences were true. You have lost 99.995% of your stake.

The ratchet is not insurance. It is not a floor. In most cases it does not reduce the loss on the token in any meaningful way. It is an acquired share of a fee, full stop.

7. Program risk

Bugs

The arithmetic core (core/src/lib.rs) is tested on more than 10,000 adversarial sequences with invariants checked after every operation. The Solana wrapper (programs/peaked) is written and built for Solana; the built program runs in LiteSVM, an in-process Solana runtime, next to the real Raydium CP-Swap mainnet program, through 12 on-chain tests in tests-rs/ that replay every operation against the core to the lamport, including the full migrate to Raydium. It has never run on a live validator, nor on devnet. None of this is a formal proof, and none of it is an audit. A bug in the core, in the Solana wrapper (programs/peaked), in account handling, in Token-2022 mint validation, or in a dependency, can lose the reserve, the escrow vault, or both.

The code has not been audited. It must not be deployed to production before an external audit. As long as this sentence is in this document, it is true.

Dependency on Raydium

Graduation (migrate) calls the Raydium CP-Swap program, whose address, fee tier and interface are fixed in TOPPD. TOPPD does not control Raydium. If Raydium changed that program in a way TOPPD does not expect (different accounts, a create-pool fee above the 0.25 SOL held back, the fee tier removed), migrate would fail. The curve would then stay open and sellable, and claims stay open, but the token could not move to a pool, and the escrowed tokens could not be withdrawn, until TOPPD is upgraded, which requires the update authority below. It was tested against Raydium's program as it was on 2026-10-09, not against what it may become.

Update authority not revoked

As long as the program's update authority has not been revoked, the person who holds it can replace the program with anything, including a program that empties the reserve and the vault. Everything SECURITY.md describes (no pause, no admin withdrawal, no rate change) holds only for the deployed code, and an authority holder can change that code.

Status as of 2026-10-09: not deployed, authority not revoked. The deployment script keeps the authority on the deployer key. The two acceptable end states are described in SECURITY.md: revocation after audit (recommended), or a timelock of at least 72 hours with an on-chain event at every proposal. As long as one of the two is not in place and verifiable by you, you are trusting a person, not a program.

8. Dust risk

Credits are in lamports, rounded down. A small holder on a quiet launch can have a credit of a few hundred lamports. A claim transaction costs at least 5,000 lamports in Solana network fees (base fee per signature), plus any priority fees, and the Holder account had to be created (rent) at the first buy.

If your credit is lower than the cost of the transaction, claiming costs you more than you receive. The credit stays in the reserve, claimable forever, but economically it is lost. The program does nothing about this: no batching, no automatic payout, no threshold. It cannot: it knows neither the price of SOL nor the cost of transactions.

Fractions of a lamport lost to rounding stay in the reserve permanently and are claimable by nobody.

9. Concentration risk

Beyond the large holder of §3: if the top 10 wallets hold 60% of the circulating supply, they receive 60% of every click. The creator can be one of these 10. Several wallets belonging to the same person can be among them and are indistinguishable to the program.

High concentration also means these wallets can make the price collapse by selling, and that their already-acquired share of the ratchet does not move when they do. A large holder who captured most of the ratchet and then sells everything has been paid twice: by the ratchet and by their sale. The program does not prevent this and does not try to.

The share of the top 10 wallets must be displayed live on every page.

10. Regulatory risk

TOPPD distributes, by a rule fixed in a program, a share of a fee flow to the holders of a token, pro rata to their holding. A token that entitles its holder to a share of revenue simply by holding it looks more like a financial product, from a regulator's point of view, than like a memecoin with no right attached.

The question to put to a licensed professional (a lawyer specialising in financial markets and digital assets law, in each targeted jurisdiction) before any public launch is the following:

Does a token whose program automatically credits its holders, pro rata, with a fraction of the platform's transaction fees constitute a security, a financial instrument, a collective investment product or a regulated digital asset within the meaning of the applicable law (in particular: the Howey test and federal/state legislation in the United States; the MiCA regulation and national texts in the European Union; local law elsewhere), and what obligations (registration, prospectus, licensing, access restrictions by jurisdiction, disclosure obligations) follow from it for the platform operator, for the launch creator and for the holders?

This document does not answer this question. The authors of this repository are not qualified to answer it, and the choice of the word "acquired" throughout the communication does not change the legal nature of the mechanism. The vocabulary is chosen to be accurate, not to get around anything. No public launch must take place before a written opinion from a licensed professional has been obtained.

11. Post-graduation liquidity risk, outside the program

After graduation, the token lives on a Raydium CP-Swap pool that TOPPD opens but does not control. migrate puts the curve's SOL (minus 0.25 SOL held back for Raydium's costs) and the 206.9M unsold tokens into it and burns every LP token, so that starting liquidity cannot be withdrawn by anyone. The usual risks still apply in full and TOPPD changes nothing about them:

  • the pool's liquidity can be low and the slippage huge;
  • the pool opens within about 0.3% of the last curve price, not exactly at it;
  • the price can go to zero with no buyer;
  • the tokens must first be withdrawn from escrow (withdraw_frozen) before they can be sold on the pool: a holder who does not make this transaction cannot sell;
  • the pool's behaviour after it opens (fees, Raydium's own code and upgrades) is Raydium's, not TOPPD's;
  • routing through aggregators is not assured.

The ratchet already acquired does not depend on the AMM. Everything else does.

12. What TOPPD does not do

Sentence from config/brand.ts:

TOPPD makes a share of the fee acquired by holders. It does not make the token good.

TOPPD does not provide:

  • any selection of tokens: launch creation is permissionless, anyone launches anything;
  • any verification of the creator;
  • any protection against a price collapse;
  • any protection against multiple wallets, snipers or bots;
  • any assurance of liquidity;
  • any automatic payout (you have to claim);
  • any advice: the ratchet says nothing about the quality of a launch, and a high ratchet can very well go with a token that was pumped and then abandoned.

A TOPPD launch is a memecoin on a curve, with, in addition, a share of fees acquired by holders during the curve. Take that share away, and what is left is a memecoin on a curve, with all the risks of a memecoin on a curve.


What we display so that this can be checked

On the page of every launch, with no way to hide it, at the same size as the ratchet: the headline figures of G2 (simulated amounts per median holder, with the measurement date) or the words "not measured" as long as research/G2.md does not exist; the G7 curve (net contribution by entry rank, with the calculation date); the share of the top 10 wallets in the circulating supply, live, read from the chain; the three fee shares in bps (100 / 3,000 / 5,000) as written in the program; the status of the update authority (revoked, timelock, or not revoked) with the link to the on-chain proof; the four honesty sentences from config/brand.ts. Every displayed measurement carries its date. Any measurement without a date is a display defect to be fixed.