Total raised
undefined ETH
first collector
top collector
latest collector
Tokenless AMM
December 19th, 2021
tags: alex-blog

As the year ends, I spend my weekends writing long romantic letters to my accountant explaining the process of minting an NFT, fractionalizing it into a million tokens, and market making it across multiple AMMs.

One of the more nuanced interactions is how liquidity providing is treated from a tax perspective, and how it impacts a trader's profit.

All regimes may treat it differently, but notably in the U.S. and Germany, adding and removing liquidity is equivalent to buying and selling a token. The implications are far reaching, as they directly impact the overall return of liquidity positions on AMMs.

Sparked by a tweet from Gabriel Shapiro, I am going to explain how a tokenless AMM could be built using Primitive.


Quick Note

There will be two instances that moves tokens, depositing and withdrawing, creating taxable events. Ideally, these two instances will be spread out long enough to not incur short-term capital gains tax (if in the U.S.), with lots of return optimizing activity between (that does not touch tokens).

From the perspective of the tokenless AMM smart contract

Step 1: Accept deposits of one token.

The "pure" smart contract will need to take deposits from a user, denominated in ideally a single token like USDC or ETH. This balance will then be used in an ethereal sense, i.e. it will only be converted back to the token on withdrawal.

Step 2: Deposit into the Primitive Engine contract’s internal balances

Each token pair has its own Primitive Engine smart contract deployed, which AMM pools can then be created for. Tokens for that pair can be deposited in advance, crediting an internal account to be used for any future actions, i.e. adding liquidity or swapping. This can be done atomically as well, so a user's initial deposit is combined with this internal balance deposit.

Step 3: Manage liquidity positions entirely using internal balances

The user can choose how they want to update their position: remove from one pool, add it to another, or zap into a new one. It would be possible to do this without ever moving tokens if its pools in the same pair! The state changes, not the tokens.

If it were pools from different pairs, the "pure" smart contract would swap tokens into a common denominator asset, like USDC, then deposit into the internal balance of the other pair. From there, the internal balances can be used to do the same actions.

Step 4: Extend features to use other composable protocols

One clear example would be getting leverage on internal balances. Originally explored in this smart contract repository: v1-cross-margin-spec, using internal balances as collateral to gain access to more internal balances is something in reach! There are many levels of complexity for this, but a cool idea is to net out collateral requirements using active liquidity positions.

Step 5: Extend features to other ecosystems

Another example is adding collateral to a Maker vault, and rather than minting Dai, it mints a Primitive internal balance of Dai, making it available to be provided as liquidity. This would allow the collateral to be monetized through AMM swap fees, without ever touching the Dai directly.

Open Question

Does this actually avoid some of the tax pitfalls of LP tokens? What else can be improved at the smart contract level to mitigate tax obligations?


It's extremely exciting to explore yield optimizing strategies. The ideas outlined here don't exist yet! To implement it, I recommend you read the Primitive introduction post on mirror.

Arweave TX
Ethereum Address
Content Digest