ERC-XXXX: NFT-Bound Prediction Markets (LMSR pricing, on-chain state)

ERC-XXXX: NFT-Bound Prediction Markets (LMSR pricing, on-chain state)

Abstract

This proposes a standard for prediction markets bound one-to-one to NFTs. Each ERC-721 token is a single binary (YES/NO) market — not a receipt for a market held elsewhere. The market’s state (question text, current odds, pool balance, resolution status) lives on-chain and is rendered as the token’s tokenURI SVG, so the NFT is self-contained and legible in any wallet.

Pricing uses an on-chain Logarithmic Market Scoring Rule (LMSR) with a fixed liquidity parameter b, settled in the native chain currency. The token holder sets the market’s question, earns a per-trade fee for the life of that token, and can reset the market to a new question after resolution. Resolution is oracle-driven with an optimistic dispute window.

The design intent is broader than prediction markets as they exist today: it collapses the launch mechanics that made permissionless token launchers explode (Pump.fun) into the settlement clarity of a prediction market (Polymarket). The result is a launchable, ownable, tradeable market primitive — a market you mint the way you’d mint a token, and hold the way you’d hold a fee-bearing position.

Motivation

The thesis: the next launch primitive is a market, not a coin

Permissionless token launchers demonstrated enormous latent demand for launching — millions of users want to create the thing others trade, not just trade what exists. But a launched memecoin is an opaque instrument. Its price is a candle chart abstracted away from any real question; new users cannot reason about whether it is “cheap,” “expensive,” or “topped,” and the launcher captures none of the ongoing volume it created.

A binary market fixes the legibility problem. A market attached to a plain-language question (“Will X happen by date Y?”) is dramatically easier for a non-expert to reason about than a token chart:

  • YES is a buy. NO is a sell. The two-sided action maps onto an intuition every newcomer already has.
  • Total volume is still total volume — the social/attention metric traders already track survives the translation.
  • There are no candles, no market-cap math, and no “is this the top” — the entire mental model is one question and two buttons.

This standard proposes that markets become the launch primitive: a creator mints a market the same way they’d mint a token, sets a question, and — critically — owns the fee stream that market generates for its entire life. The launcher is finally aligned with the volume they create.

Why bind the market to an ERC-721 token

Existing prediction-market designs treat a market as either (a) a protocol-owned singleton (Augur, Polymarket) or (b) an ephemeral database row with an on-chain payout. Both give up the composability that makes tokens interesting:

  • You can’t transfer a market, or list one for sale on an NFT marketplace.
  • You can’t display a market’s live state in a wallet’s NFT view without off-chain metadata.
  • The market’s economic upside (fees) can’t be sold or delegated separately from the market itself.

Binding a market to an ERC-721 token solves all three. The market has an owner (the token holder), can be traded, and renders self-contained state to any ERC-721-aware surface. Question ownership becomes a transferable, cash-flowing right rather than a smart-contract permission entry. Selling the NFT sells the market and its future fee stream together — the holder is, in effect, selling a productive asset.

Anti-fragmentation: one NFT, one market

A launcher’s failure mode is copy-paste warfare: a popular launch is instantly cloned to siphon its attention and volume (“vamping”). Because each token here is a single distinct market with its own liquidity, price history, and accrued fees, there is no clone that captures the original’s state. Duplicating the token does not duplicate the market. A market’s liquidity, track record, and fee stream are bound to exactly one token and are not forkable by copying an address. This removes the adversarial player-vs-player dynamic that plagues fungible launches and gives each market a durable identity.

Specification

A conforming contract MUST implement ERC-721 and MUST expose the following interface. Pricing math, resolution flow, and rendering are specified below.

interface IOFT /* is IERC721 */ {
  // ----- Market lifecycle -----
  function setQuestion(uint256 tokenId, string calldata question, uint64 lockTime) external;
  function resetMarket(uint256 tokenId, string calldata newQuestion, uint64 lockTime) external;

  // ----- Trading -----
  function buy(uint256 tokenId, bool outcome, uint256 minShares) external payable returns (uint256 shares);
  function sell(uint256 tokenId, bool outcome, uint256 shares, uint256 minReturn) external returns (uint256 payout);
  function redeem(uint256 tokenId) external returns (uint256 payout);
  function refund(uint256 tokenId) external returns (uint256 refunded);

  // ----- Resolution -----
  function resolve(uint256 tokenId, bool outcome) external;
  function dispute(uint256 tokenId, bool proposedOutcome) external payable;

  // ----- Views -----
  function marketState(uint256 tokenId) external view returns (MarketState memory);
  function priceOf(uint256 tokenId, bool outcome) external view returns (uint256 priceWad);
  function costToBuy(uint256 tokenId, bool outcome, uint256 shares) external view returns (uint256 cost);
}

LMSR pricing. Cost function C(q_yes, q_no) = b · ln(exp(q_yes/b) + exp(q_no/b)). Trade cost is C(q_new) − C(q_current). The price of an outcome is exp(q_i/b) / (exp(q_yes/b) + exp(q_no/b)). Implementations MUST use fixed-point math with at least 18 decimals of precision (PRBMath, ABDK, or equivalent). b is set at market creation and is immutable per cycle.

Fees. A conforming implementation MUST support:

  • ownerFeeBps — accrued to the NFT holder, paid on every buy and sell.
  • protocolFeeBps — accrued to a treasury address set at deploy.

Both are basis-point values. Fee accrual is per-market, so a market transfer transfers the fee stream with the token. This is the mechanism that makes the token a productive, sellable asset: the holder earns on every trade for the life of the market, and that right moves with the NFT.

Resolution. Two-phase:

  1. Propose. After lockTime, an oracle or permitted resolver calls resolve(tokenId, outcome), starting a dispute window (e.g. 24h).
  2. Dispute. During the window, anyone can call dispute(tokenId, proposedOutcome) with a bonded challenge. Disputed markets fall back to a slower resolution path (e.g. UMA, a second oracle, or owner-signed).

Rendering. tokenURI returns a data URI containing an SVG that renders the question text, current YES/NO prices, pool balance, and resolution state. This MUST be self-contained (no external image URLs, no IPFS dependency) so the market is legible in a wallet even if the frontend is offline. Legibility is a first-class goal of this standard: the on-chain render is what lets a non-expert read a market at a glance.

Rationale

Why one NFT per market instead of ERC-1155 or a market registry? ERC-721 is the only widely-supported “one owner per thing” primitive with existing marketplace liquidity, wallet display, and royalty enforcement. A market registry inside a single contract loses transfer semantics — and transfer semantics are precisely what make the fee stream a sellable asset.

Why LMSR over CPMM (Uniswap-style)? LMSR gives bounded loss for the market maker (bounded by b), guarantees a price is always quotable regardless of liquidity, and requires no initial liquidity provision from an LP. For binary outcomes with unknown volume this is well-studied and strictly better than CPMM. It also means a freshly-minted market is immediately tradeable with a coherent price — essential when the design goal is “mint and it’s live.”

Why native currency instead of a wrapped stable? Removes one dependency and one approval step, which matters for the newcomer flow the design targets. Implementations MAY offer an ERC-20 variant; the base spec is native.

Why owner-set questions rather than protocol-set? It makes the token productive — the holder decides what market their NFT represents each cycle. Combined with reset semantics, one NFT can serve many markets over its lifetime, and the owner keeps earning across all of them.

Backwards Compatibility

Fully compatible with ERC-721, ERC-2981 (royalties on secondary sales), and ERC-165 (interface detection). Existing NFT marketplaces will display and trade these tokens without modification.

Security Considerations

  • LMSR precision. Naïve fixed-point exp/ln can drift. Reference implementations should include invariant tests asserting price_yes + price_no ≈ 1 within tolerance across the full range of q.
  • Reentrancy on payout. sell, redeem, and refund transfer native currency. Standard checks-effects-interactions and reentrancy guards apply.
  • Fee accounting on transfer. Owner-fee accrual MUST be settled on NFT transfer so buyers don’t inherit unclaimed fees and sellers don’t lose them.
  • Oracle capture. The propose → dispute flow assumes an honest oracle most of the time. Implementations should document their fallback resolver and dispute-bond sizing.
  • Refund path. If a market never resolves (oracle silence beyond a timeout), a permissionless refund path MUST return all trader collateral pro rata.

Open Questions

Feedback appreciated specifically on:

  1. Interface surface. Is resetMarket distinct enough from setQuestion to justify a separate function, or should question-setting on a resolved market implicitly reset?
  2. Multi-outcome extension. Should the spec accommodate N-ary outcomes at the interface level, or is binary the base and N-ary a separate ERC? (The “YES is a buy / NO is a sell” legibility argument is strongest for binary — worth weighing against expressiveness.)
  3. Dispute-bond currency. Native or ERC-20? Native keeps dependencies low but denominates the bond in a volatile asset.
  4. SVG rendering budget. Full on-chain SVG has a gas cost. Is a base64 data URI acceptable, or should a lightweight thumbnail + separate marketMetadataURI be normative?
  5. b (liquidity depth) mutability. Fixed per cycle is simplest and safest. Some implementations want dynamic b for capital efficiency — accommodate in the standard, or leave to an extension?

A reference implementation is in progress and will be linked once the discussion settles enough to freeze the interface. Feedback especially welcome from anyone who has worked on LMSR precision, oracle escalation, or on-chain SVG rendering.

Thanks for reading.

twitter: oftrobinhood · site: oftrh.xyz

1 Like