Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Spec for CLOB shared order margin #2372

Open
barnabee opened this issue Sep 23, 2024 · 1 comment
Open

Spec for CLOB shared order margin #2372

barnabee opened this issue Sep 23, 2024 · 1 comment

Comments

@barnabee
Copy link
Member

barnabee commented Sep 23, 2024

Overview

Note: this ticket now covers only shared order margin on the CLOB. vAMM shared pools are now covered in a separate ticket as they do not require (and will not use) the new shared order margin account.

See this comment below for a more concrete and simplified MVO design.

This enhancement will relax the capital requirements for posting order volume on the book to allow a large (orders of magnitude) increase in the number of markets that can be effectively quoted with a given amount of capital.

This can be done by taking into account the sequential nature of transaction processing, and the fact that after each transaction we can reduce or cancel posted order volume if the party can no longer meet the margin requirements if it trades.

This is similar conceptually to the existing functionality that cancels orders if the party can't support them due to market market losses on the same key, but where order margin is considered to be at least partially shared between orders on multiple markets.

Position margin remains per-market. This ticket is not about "risk universes" or any form of correlation based per market netting, collateralisation, etc. such as would be required to offset position margin between different markets.

This feature must be designed to be safe. Specifically it must continue to guarantee that:

  1. protocol users cannot open an un[der]funded position; and
  2. protocol users cannot "spoof" the market by posting order volume that is unlikely to be tradable.

Notes:

  • Some of the features and controls described below may not be needed in a first version, or may best split into separate tickets when it comes to implementation. However it is important that whatever is delivered to a mainnet-ready release is designed to be useful to real users and for the goal of efficiently and safely supporting large numbers of markets with liquidity.

  • There is absolutely no intention here to allow the same shared margin account to work across vAMM and order book liquidity. Those can continue to be treated as separate "keys".

Please use comments on this issue to discuss the proposed design, with the aim of getting to a point where this is ready to be formalised in a spec PR, where discussion on implementation details can continue.

Proposed theory of operation

The feature would work by allowing sets of limit orders across multiple markets to be backed by the same virtual key / funding pool, rather than having funds reserved per market to cover the worst case orders on that market only. The system would still always cover the worst case position margin increase from any given single transaction on any given market. But, after a trade occurs, it may be necessary to reduce the posted order volume on any number of markets using the same shared order margin account to ensure that whatever may happen in the next transaction can still be covered. In fact, it is already the case that an event in transaction N can cause orders to be cancelled/parked and therefore not be available in transacton N+1, this will simply add another way this can happen.

This works by adding a new "shared order margin account" type, where a shared margin account can be created / enabled by a key for any set of one or more markets (as a simplification, having a single shared order margin account per { public_key, settlement_asset }, would be acceptable (users can use multiple keys if they wish to share only among subsets of marketd). In either case it is likely that any given market should be allowed to appear in at most one shared order margin account per Vega key.

Under this propoal, we would relax the current requirement that a certain amount of capital be moved to a per-market [order] margin account to cover the worst case additional margin liabilities of the orders in a market executing. Instead, the requirement would now be that the combination of the per-market [order] margin balance plus the relevant shared margin account balance must cover these liabilities (in addition to the margin required by the open position, if any).

This new account type would automatically source and release funds from the owning key's general account, to make sure that the margin requirements of each individual market are satisfied by the combination of per-market margin account(s) plus the shared order margin account.

Handling changes to shared margin

Doing the above without adding any additional logic would allow a situation to arise where after an order on market A trades, there would not be enough funds to cover the margin for a previously accepted order on market B, as it may be relying on funds in the shared order margin account that have already been used.

In order to prevent this, open orders on other markets held by the same key and using the same shared order margin account may need to be adjusted after an order trades to fit within the available collateral.

  • Llimit orders could use a number of strategies:
    • cancel entire orders, starting with the worst priced ordeers that are "driving" the largest liability until there are no orders or the orders that remain can be covered by the margin available across the per-market and shared margin accounts.
    • park entire orders using the strategy above, so they can be restored if more collateral becomes available for shared margin
    • as above but also scale the order size up and down, only park orders where the size is scaled to zero

Isolated margin

For isolated margin the shared order margin account plus what's on each market would need to cover all in-scope markets, so the shared order margin account would not necessarily contain the exact amount required for each market (unlike order margin accounts for isolated margin). For some markets it may be over-collateralised, but it can never be allowed to be undercollateralised for the currently configuredmargin ratio.

This should be fine, as long as the correct amounts are transferred if a position is incurred and when maintaining the per-acount order margin.

Ensuring continuity / spoofing protection

In a naïve implementation, if may be possible to spoof a market or create "flaky" liquidity by configuring orders across a large nunber of markets and/or in such a way that a small number of orders (or even a single order) sat at the top of the book on one market would effectively cause all other displayed liquidity to be removed if it trades.

We need to think about how to keep this operating well and prevent the most obviously stupid or nefarious configurations.

The following ideas might be a starting point:

  1. Require some % of the order margin (set by a { market | network } parameter) to be in the per-market [order] margin account. This could be done automatically with the [order] margin account being filled exactly as it is today but with the fractional rather than full required amount being placed in the account. The shared margin account would then need to cover the remainder, with more being added to it if needed, and the order being rejected if there's not enough collateral to do so. The benefit of this is that it puts limits on the total amount of overcommitment of margin.

  2. Set some { market | network } parameter to place an upper limit on the amount of the margin available to a market (shared order margin plus that market's specific order and position accounts) that it can use. This would need to use something like the "margin available to a market" as defined above because:

    • Using the total margin of all types for all markets in the shared set would allow scenarios where a currently small market can take all the available shared margin
    • Using just a maximum percentage of the shared margin rather than all margin available to a market allows margin to "drain" over time from shared order margin into position margin until all margin is locked up in one market's position
    • This would enable the restriction and thus order size on other markets to be updated sanely based on what's really available to them even when one or two markets end up eating a very large share of the margin, perhaps due to MTM losses.

It would be important to allow these to be switched off (parameter = 0/100%/etc.) if so desired.

The effect of these two needs some thought, but they would seemingly allow users to be prevented from supplying liquiidty across a large number of markets in a way that is going to be too exploitable or extremely flaky. It could be argued that 2 might not be needed at a network/market level and should only be an optional tool for LPs to help them maintain continuity of liquidity across a large number of markets. If an LP wanted to provide more liquidity to very specific markets they could separate them into other shared pools together or supply some on another key without shared liquidity at all.

Allowing user control

Users may prefer that one large or heavily traded market be prevented from pushing out all the others. Per-key parameters could be used to set limits on on the amount of orders that can be posted to a market given the total amount of shared margin available and the amount of order and/or position margin currently exclusively allocated to a market. The goal might be to implement a maximum total dominance of any one market or a maximum rate of growth for the amount of the total margin (shared order, order, and position) allocated exclusively to any given market.

One option would be to allow the user to optionally configure a version of option 2 under "Ensuring continuity / spoofing protection" above, with a more restrictive parameter to keep things more distributed. In facf it is possible that this option would be better off as an optional user control rather than market enforced.

It is not clear to me if this is needed, maybe users can manage it themselves. The risk, though, is that the correct sizing is dynamic as available collateral changes and without some kind of bot, users may not get the result they want. This could potentially be complemented well by the position disposal algorithm (#2368) especially if there is symbiosis between the rate of position accumulation and disposal.

See this comment below for a more concrete and simplified MVO design.

@barnabee barnabee changed the title Spec for shared/virtual liquidity Spec for shared order margin ("virtual liquidity") Sep 23, 2024
@davidsiska-vega davidsiska-vega added this to the 🕌 Genbu Temple milestone Oct 7, 2024
@barnabee
Copy link
Member Author

barnabee commented Oct 9, 2024

To summarise how an MVP of this feature might work for CLOB orders:

1. Shared order margin account

Note: this ticket makes an assumption that the required margin for a { key, market} is always comprised of position margin (the margin required for the open position if there were no active orders) and order margin (the difference between the total margin required for the open position plus active orders and the position margin. Currently this is implemented explicitly when in isolated margin mode (where separate margin and order margin accounts are used) but is implicit in cross-margin mode (where the combined total margin is held in the margin account and the order margin account type is not used). The implementation of this feature does not require cross-margin mode be changed to use the order margin account. However, it is important to understand the concepts and definition of position margin and order margin given at the start of this note, and if the order margin account isn't used in cross margin, it will be necessary to track of these amounts in the app state.

  • New state and parameters

    • A per-key option to enable shared order margin that defaults to disabled if not set explicitly

    • A network parameter exclusive order margin fraction (may be anywhere between 0 and 1 inclusive)

  • When enabled:

    • An account of type shared order margin account is created for each { key, settlement asset } with at least one position (i.e. the accont is created as needed the first time a key with the feature enabled places an order involving a given settlement asset).

    • The position margin and exclusive_order_margin_fraction × order_margin amounts will be held in the market specific margin accounts as normal (either combined, in account type==margin for cross margin, or separately in accounts type==margin and type==order_margin for isolated margin).

      • Funds are moved in and out of the per-market margin accounts as the required margin changes exactly as they are today, it is simply that the required margin for orders held per market is now only a fraction of the total order margin as specified by the exclusive order margin fraction parameter, which may be zero or 1 (100%).
    • At least the remainder of the order margin ((1-exclusive_order_margin_fraction) × order_margin) must be held in the shared order margin account:

      • If the shared order margin account contains insufficient funds to cover the largest order margin remainder the additional required funds are moved from the general account as required (this must be done as soon as funds are needed).

      • If there is not enough in the general account, quoted volume reduction (see below) occurs for the affected markets (i.e. those requiring more total order margin than is available) only.

      • If there is more in the shared order margin account than is needed to cover the largest order margin remainder, the additional funds are moved back to the general account (this could be done periodically rather than immediately, if it is beneficial for performance reasons).

    • When an order trades and additional position margin is required, it should be moved from accounts in this order:

      • Proportion of per-market order margin account balance that is no longer required (if any)
      • Proportion shared order margin account balance that is no longer required (if any)
      • General account
      • Shared order margin
      • Per-market order margin
    • If after new position margin is allocated, there is not enough order margin to cover the open orders on one or more markets, quoted volume reduction (see below) occurs.

2. Quoted volume reduction for CLOB orders

Quoted volume reduction is the process of scaling down the quoted volume on a market to fit within the total funds available for order margin across the per-market order margin account, the shared order margin account, and the general account.

On each affected market, working from highest to loweest exclusive order margin account balance in order, the following process is repeated until all margin requirements, namely the order margin and exclusive order margin requirements are met:

  • Cancel the order least likely to trade (furthest from the current price) on the side of the book that is driving the order margin requirement (that is, on the side with the highest order margin requirement). If both sides have exactly the same order margin requirement, then cancel whichever (either the buy or sell) order least likely to trade has the smallest margin requirement. If both of these orders have the same margin requirement, cancel either order.

    • Re-evaluate whether the margin requirements for that market are now met for that market, repeat if necessary.

@barnabee barnabee changed the title Spec for shared order margin ("virtual liquidity") Spec for CLOB shared order margin Oct 17, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants