Documentation

Complete guide and documentation for the Pyth Mega Pool

The pool contract allows users to pool USDC funds to purchase tickets from the Megapot contract, with winnings distributed proportionally based on each user's contributions. It includes mechanisms to ensure fairness and minimize trust in the pool administrator.

Normal Flow

The smart contract operates in a cycle with three main stages: accepting contributions, purchasing tickets, and checking for jackpot winnings. Below is how each stage works.

1. Accepting Contributions (Default State)

In its default state, the contract accepts USDC contributions from participants via the deposit function. Users send USDC to the contract, but only in whole USDC amounts (e.g., 1 USDC, 5 USDC, not 1.5 USDC). To ensure contributions are properly recorded, users must use the deposit function rather than sending USDC directly to the contract's address. Each deposit is tracked, updating the user's lifetime contribution. This allows the contract to fairly allocate winnings based on contributions.

2. Purchasing Tickets (buyTickets Function)

The pool administrator periodically executes the buyTickets function (currently on a weekly basis, but subject to change). The administrator reviews the total USDC contributed since the last buyTickets call (i.e., the past week's contributions) and uses these funds to purchase lottery tickets from the Megapot contract on behalf of the pool. Once buyTickets is executed, the contract enters a "locked state," preventing new contributions until the jackpot results are checked.

3. Checking Jackpot Result (checkJackpot function)

Any participant can call the checkJackpot function 24 hours after the buyTickets transaction. This function queries the Megapot contract to determine if any of the pool's tickets won the jackpot.

If the pool wins: The winnings are withdrawn and allocated to contributors proportionally based on their lifetime contributions relative to the total lifetime contributions in the pool. Contributors can then call the claimWinnings function during a 30-day claim period to receive their share of the jackpot in USDC.

If the pool does not win: The contract returns to its default state, allowing new contributions for the next cycle.

Pool Integrity Concerns

1. Trust-Minimization (Preventing Administrator Misuse)

A major concern is that if the pool wins the jackpot, the administrator might try to withdraw all the winnings, leaving contributors with nothing. The contract prevents this through the following mechanism:

When buyTickets is executed, the emergencyWithdraw function—which allows the administrator to withdraw USDC—is locked indefinitely.

When someone calls checkJackpot (24 hours after buyTickets), the contract checks for winnings:

  • If the pool wins, the emergencyWithdraw function remains locked for 30 days, allowing contributors to claim their winnings.
  • If the pool does not win, the emergencyWithdraw function is unlocked.

Users must trust the administrator to use contributed funds to purchase tickets, but this can be verified on-chain by checking buyTickets transactions and interactions with the Megapot contract. The emergencyWithdraw function exists to prevent funds from being permanently locked in the contract, but its locking mechanism ensures it cannot be abused during a winning round.

2. Preventing Contribution Manipulation

Users might try to increase their share of winnings by depositing large amounts of USDC after learning the pool has won the jackpot, especially since Megapot's results may be public before checkJackpot is called. The contract prevents this by locking the deposit function as soon as buyTickets is executed. New contributions are blocked until checkJackpot confirms the outcome:

  • If no jackpot is won, the deposit function is unlocked, allowing contributions for the next cycle.
  • If the pool wins, the deposit function remains locked during the 30-day claim period, preventing users from altering their contribution proportions.