Proposing Carbon - DRAFT (DEPRECATED)

Important Note on Maker Fee Readiness:

At the time of writing the specific implementation of the maker fee has not been finalized. This topic has been actively discussed on DAO meetings, and the general consensus view is that it is preferable to have this aspect of the system active at Carbon’s initial deployment. The major talking points were that there is little benefit to withholding such an insignificant component from the system, and that if doing so represents a significant advantage in the early phases of the protocol adoption, then let that be evidence that the maker fee is too high. In other words, if there is an incentive to participate only because the maker fee is currently absent, then it has failed in its ambition to be an innocuous element. Secondly, fears that adding additional costs over time could be conflated with bait-and-switch tactics were also voiced, and that presenting the system in completeness would avert such unfavorable impressions.

The author acknowledges the validity of these concerns; however, it is worth asking if they are sufficient to keep an early deployment on hold, if the maker fee logic remains unfinished. Readers are reminded of the views expressed above, where a successful maker fee policy is espoused to be one which is of such little consequence to individual users that its presence is barely an inconvenience. Ultimately, taker fees can and should represent the vast majority of the protocol’s revenue. If the maker fee is that much of a sticking point with respect to the concerns raised, it may be worth reexamining its proposed settings.

This proposal asks that the DAO approve Carbon’s deployment at its earliest available state, with or without the maker fee component.


Fees, Initial Settings and Management Responsibilities:

Taker Fees:

  • Proposed to begin at 0.20% (20 bps), and taken variably from either the QUOTE or BASE token, dependent on the specific function call as outlined above.

  • Applied protocol-wide, without bias for certain tokens or token pairs.

  • Accumulate to the protocol itself, and not its users.

  • Taker fees are a global setting, which the BancorDAO may change via the governance process.

Maker Fees:

  • Suggested target a fixed value, paid in the native gas token of the blockchain (or acyclic graph) on which the contract interaction occurs.

  • Categorized into 5 discrete types:

    • Strategy/Order Creation,
    • Increase Strategy/Order Funding,
    • Decrease Strategy/Order Funding,
    • Edit Strategy/Order Settings,
    • Pause Trading.
  • Each of the initial maker fee quantities on Ethereum is proposed to be 0.0005 ETH (approximately $1).

  • Applied protocol-wide, without bias for certain tokens or token pairs.

  • Accumulate to the protocol itself, and not its users.

  • Each maker fee category is a discrete value which the BancorDAO may change via the governance process.

Ongoing Management:

  • No more than 180 days should pass between a formal DAO review process of Carbon’s fee settings, across all its deployments.

  • If no changes to the fee settings are warranted, proposals should be submitted for a DAO decision within the 180 window all the same.

  • There are no categorical consequences, or recourse actions proposed if more than 180 days should pass between fee adjustments and review; the purpose of this section is for the DAO to signal its acknowledgement and understanding of its responsibilities, and establish a process to assist self-organization.


Recovery of BNT from the Market, and Deficit Repair on Legacy Products:

An objective articulated by the BancorDAO, as ratified in a prior vote, is to return the token balances on V2.1 and V3 to surplus via the recovery of BNT from the market. The DAO determined that Carbon’s protocol-accumulated fees be used for this purpose, exclusively. However, the precise mechanism was not established by the prior vote. With this proposal, the specifics of the BNT burning process are proposed.


Modified Bancor Vortex Contract:

As outlined in the preceding sections, protocol fees can accumulate in any token comprising an active trading pair, as well as the gas token of the blockchain (or acyclic graph) Carbon is deployed on. Bancor’s legacy protocols (V2.1 and V3) have many existing pairs with BNT, and an existing smart contract implementation (the Bancor Vortex) is superbly suited to utilizing the network’s capabilities to recover and destroy BNT. The following illustration is provided to supplant the prior descriptions of the Bancor Vortex.

Assume that after a period of time, the protocol has accumulated 1,234.56 USDC, 65,43.21 USDT, 10,987.65 DAI, 1.23 wBTC and 4.32 ETH in fees. A caller may choose any set of these tokens to swap into BNT via its own liquidity pools, and the Vortex contract offers a small incentive in return. The incentive is equal to 2% of the total recovered BNT, up to a maximum of 100 BNT, which is returned to the caller.

In this hypothetical, the caller has selected USDC, USDT and DAI for the Vortex to use. Each of these token balances are routed through the liquidity pools on Bancor V2.1 and V3. For the sake of demonstration, the simulated USDC, USDT and DAI pools contain precise liquidity amounts of $2M, $4M, and $8M, and their fee settings are 0.2%, 0.2%, and 0.3%, respectively. The simulated BNT price is $0.50. This Vortex call results in the recovery of 37,328.16 BNT.

Since 2% of the recovered BNT amount is > 100 BNT, the burn reward defaults to 100 BNT. The remaining 37,328.16 BNT are destroyed.

It is important to note that the prior vote specified that 100% of the accumulated protocol fees be used to destroy BNT. However, without a caller incentive to interact with the Vortex contract, it is not clear how to maintain a consistent turnover rate. Therefore, this proposal asks the BancorDAO to approve the policy and implementation described above for any token pairs that exist on V2.1 and V3, with the express understanding that a minimum of 98% of protocol fees are used for this purpose (rather than 100%). It is noteworthy that 98% is the worst-case scenario. With reference to the figure above, it is trivial to demonstrate that effective burn efficiencies more than 99% of the protocol fees value are unremarkable.


Clarification - Carbon Vortex Contract:

For clarity - this section of the proposal discusses adapting the Bancor Vortex contract for use with Carbon, where the destination token is BNT, not vBNT, in alignment with the unambiguous precedent already established.



Standardizing Bancor Vortex Contract:

The Bancor Vortex is now 2 years old, and the underlying concept has already been subject to substantial revisions. Notably, the advantages of its dependence on vBNT is no longer a clear advantage as the paradigms on which this system was founded are no longer in effect, and the BNT vBNT pair is essentially at parity.

To maintain a clean implementation, this proposal asks for the vBNT burning actions of the legacy products (V2.1 and V3) to be superseded with direct destruction of BNT. Thus, the Bancor Vortex contracts will be general, and equally applicable in all contexts involving the recovery of BNT from the market, and returning all instances of deficit back to surplus.



Clarification - Carbon Vortex Contract:

For clarity - this section of the proposal proposes to bring the implementation of the Bancor Vortex on V2.1 and V3 in-line with the proposed implementation on Carbon. Therefore, there will be one universal Vortex contract, which exchanges protocol fees for BNT, and burns it.


BNT Burning:

BNT Burning Mechanism on Carbon:

  • The protocol’s accumulated token balances from taker and maker fees will be prominently displayed on Carbon’s complement analytics dashboard.
  • The Bancor Vortex contract will be modified for use with Carbon, and will offer 2% of the exchanged value in BNT, up to a maximum of 100 BNT, back to the caller as an incentive.
  • Therefore a revision to the existing precedent is required: “no less than 98%, and up to 100% of the protocol fees from Carbon should be used to recover BNT from the market, and destroy it”, where the difference is attributed exclusively to the effective cost of incentivizing the Vortex contract’s caller.
  • Therefore, any protocol fees denominated in a token that is paired with BNT on V2.1 or V3 can be serviced easily by the community.
  • Tokens not paired with BNT on V2.1 or V3 will be held in the protocol wallet until an alternative mechanism is proposed that does not have this limitation.


Standardization of Bancor Vortex Modifications:

  • With this proposal, the changes to the Bancor Vortex contract are proposed to be made standard.
  • The standardization means that on Bancor V2.1 and V.3, as on Carbon, protocol fees are used to recover BNT and destroy it directly.
  • Approval of this part of the proposal signals that the BancorDAO understands that vBNT will no longer serve a use case as part of the Vortex mechanism.

Voting Instructions:

BIP 23 - BancorDAO Authorization of Carbon Deployment on Ethereum Mainnet:

This decision relates to Carbon, as described in the litepaper, white paper, and its ancillary simulation and research materials as they appear on GitHub and JupyLite .

  • Vote FOR to agree to the deployment of Carbon on Ethereum mainnet.

  • Vote AGAINST to disagree to the deployment of Carbon on Ethereum mainnet.

BIP 24 - Taker Fee Implementation and Initial Settings:

This decision relates to the initial value of the taker fee on Carbon, and is contingent on the authorization of the BancorDAO to deploy the proposed Carbon protocol on Ethereum mainnet.

  • Vote FOR to agree to the proposed taker fee implementation, and initial value of 0.2% (20 bps), applied protocol-wide to all tokens and token pairs.

  • Vote AGAINST to defeat the proposal, requiring either a future proposal for a new taker fee concept, quantity, or to indicate you would prefer no taker fee at all.

BIP 25 - Maker Fee Implementation and Initial Settings:

This decision relates to the tentative maker fee implementation, where fees are collected in the gas token of the chain Carbon is deployed on, and targets an approximate $1 value (0.0005 ETH) at the time of writing, with its initial deployment on Ethereum.

  • Vote FOR to agree to the five proposed maker fee categories, and initial settings of 0.0005 ETH (approx. $1 at the time of writing) for each, which is applied equally to all maker actions, regardless of the position size.

  • Vote AGAINST to defeat the proposal, requiring either a future proposal for a new maker fee concept, quantity, or to indicate you would prefer no maker fee at all.

BIP 26 - BancorDAO Authorization of Carbon Deployment on Ethereum Mainnet in Lieu of Maker Fee Implementation:

This decision relates to the approval of Carbon’s deployment at its soonest available date, with or without a finalized maker fee implementation.

  • Vote FOR to agree to an initial Carbon deployment, with or without a maker fee implementation.

  • Vote AGAINST to require a maker fee implementation prior to the initial release of Carbon.

BIP 27 - Protocol Fee Maintenance Policy:

This decision relates to the proposed constancy requirement and DAO process for maintaining reasonable fee values for Carbon, wherever it is deployed.

  • Vote FOR to agree that a maximum 180 day period between proposal submissions to review protocol fee settings for Carbon, wherever it is deployed, should become part of the DAO canon.

  • Vote AGAINST to disagree to the fee review policy, requiring either a future proposal for a different policy, or no policy at all.

BIP 28 - BNT Burning Policy and Procedures on Carbon:

This decision relates to the proposed use of the Bancor Vortex to perform exchange between the protocol’s accumulated tokens and BNT for the purpose of returning token balances on Bancor’s legacy protocols to surplus.

  • Vote FOR to agree to the proposed Vortex implementation, and the following revision to a prior vote: “no less than 98% and up to 100% of the protocol fees from Carbon should be used to recover BNT for the express purpose of burning it, where the difference between the burning efficiency and 100% is attributable to the cost of incentivizing the contract’s caller”.

  • Vote AGAINST to disagree with the proposed use of the Bancor Vortex, and/or the provided revisions to the prior vote, requiring a future proposal.


BIP 29 - Standardization of the Vortex contracts:

This decision relates to the proposed changes to the Bancor Vortex contracts, where BNT becomes the exclusive target of the Vortex, rather than vBNT, for the purpose of returning token balances on Bancor’s legacy protocols to surplus.

  • Vote FOR to agree to the proposed standards, thus removing Vortex dependence on vBNT.

  • Vote AGAINST to indicate that two separate procedures should be maintained (one for Carbon, and one for Bancor’s legacy products V2.1 and V3) where the procedure on Carbon results in the destruction of BNT directly, and the procedure on V2.1 and V3 results in the destruction of vBNT via an intermediate swap.



Taker Fees Discussion Section Generator:

from tabulate import tabulate
from decimal import Decimal, getcontext
import textwrap
getcontext().prec = 100

ONE = Decimal("1")
TWO = Decimal("2")

# Curve Parameters
P_a = Decimal("2.3456")
P_b = Decimal("1.2345")
B = Decimal.sqrt(P_b)
S = Decimal.sqrt(P_a) - Decimal.sqrt(P_b)
y_int = Decimal("1000")
y = Decimal("500")
fee = Decimal("0.002")

def print_parameter_table():
    table = (("Curve Parameter", "Value", "Notes"),
             ("$B$", f"{B:.6f}", "The highest ask (y = BASE), or lowest bid (y = QUOTE) boundary metric, depending on context."),
             ("$S$", f"{S:.6f}", "The range width parameter."),
             ("$y_{int}$", f"{y_int:.6f}", "The curve capacity metric."),
             ("$y$", f"{y:.6f}", "The remaining token balance"),
             ("$fee$", f"{fee:.6f}", "The protocol fee setting."))
    print(tabulate(table, headers = "firstrow", tablefmt = "pipe", floatfmt = ".6f", numalign = "right", stralign = "left"))

def print_summary_table(scenario_1, scenario_2):
    table = (("Scenario", "Taker Sent", "Taker Received", "Maker Sent", "Maker Received", "Protocol Fee Collected"), scenario_1, scenario_2)
    print(tabulate(table, headers = "firstrow", tablefmt = "pipe", floatfmt = ".6f", numalign = "right", stralign = "right"))

def print_trade_by_target_text(taker_sends_1, maker_sends_1, taker_receives_1, protocol_receives_1):
    text = (f"The taker requests to send exactly {taker_sends_1:.6f} QUOTE tokens to the protocol, all of which is swapped against the maker's order, and returns a value of {maker_sends_1:.6f} BASE tokens. Of the {maker_sends_1:.6f} BASE tokens relinquished by the maker's order, the taker keeps {taker_receives_1:.6f} BASE, and the protocol keeps {protocol_receives_1:.6f} BASE.")
    print(textwrap.fill(text, width = 132))

def print_trade_by_source_text(taker_receives_2, maker_receives_2, taker_sends_2, protocol_receives_2):
    text = (f"The taker requests to receive exactly {taker_receives_2:.6f} BASE tokens from the protocol. To satisfy the requirements of the maker's order, exactly {maker_receives_2:.6f} QUOTE tokens must be exchanged (ignoring the fee). After adjusting for the protocol fee, the taker must send a total of {taker_sends_2:.6f} QUOTE tokens to the protocol. The protocol keeps {protocol_receives_2:.6f} QUOTE tokens, and the remaining {maker_receives_2:.6f} QUOTE tokens are exchanged with the maker's order for {taker_receives_2:.6f} BASE tokens, which are sent from the protocol to the taker.")
    print(textwrap.fill(text, width = 132))

text_functions = [print_trade_by_target_text, print_trade_by_source_text]

def trade_by_target(maker_receives):
    maker_sends = maker_receives*(B*y_int + S*y)**TWO/(maker_receives*S*(B*y_int + S*y) + y_int**TWO)

def trade_by_source(maker_sends):
    maker_receives = (maker_sends*y_int**TWO)/((S*y + B*y_int)*(B*y_int + S*(y - maker_sends)))

swap_functions = [trade_by_target, trade_by_source]

def apply_fee_trade_by_target(maker_sends):
    taker_receives = maker_sends*(ONE - fee)
    protocol_receives = maker_sends*fee
    return(taker_receives, protocol_receives)

def apply_fee_trade_by_source(maker_receives):
    taker_sends = maker_receives/(ONE - fee)
    protocol_receives = taker_sends - maker_receives
    return(taker_sends, protocol_receives)

fee_functions = [apply_fee_trade_by_target, apply_fee_trade_by_source]
protocol_fees = ["BASE", "QUOTE"]

def perform_swap(input_array):
    scenarios = []
    for i, j in enumerate(input_array):
        print(f"##### *Scenario {i + 1}:*")
        output = swap_functions[i](j)
        fee_adjusted_outputs = fee_functions[i](output)
        scenario_template = [f"{i + 1}", f"{j:.6f} QUOTE", f"{j:.6f} BASE", f"{j:.6f} BASE", f"{j:.6f} QUOTE", f"{fee_adjusted_outputs[1]:.6f} {'BASE' if i == 0 else 'QUOTE'}"]
        scenario_template[2 - i] = f"{fee_adjusted_outputs[0]:.6f} {'BASE' if i == 0 else 'QUOTE'}"
        scenario_template[3 + i] = f"{output:.6f} {'BASE' if i == 0 else 'QUOTE'}"
        text_functions[i](j, output, fee_adjusted_outputs[0], fee_adjusted_outputs[1])

def numerator(seed_input, fee_multiplier):
    return(seed_input*fee_multiplier*(B*y_int + S*y)**TWO)

def denominator(seed_input, fee_multiplier):
    return(S*seed_input*fee_multiplier*(B*y_int + S*y) + y_int**TWO)

def create_examples(seed_input):
    example_1_scenario_1 = example_2_scenario_1 = example_3_scenario_1 = seed_input
    example_1_scenario_2 = numerator(seed_input, ONE)/denominator(seed_input, ONE)
    example_2_scenario_2 = numerator(seed_input, ONE - fee)/denominator(seed_input, ONE)
    example_3_scenario_2 = numerator(seed_input, ONE - fee)/denominator(seed_input, ONE - fee)
    return((example_1_scenario_1, example_1_scenario_2),
           (example_2_scenario_1, example_2_scenario_2),
           (example_3_scenario_1, example_3_scenario_2))

def write_taker_fees_proposal_section(seed_input = Decimal('10')):
    swaps = create_examples(seed_input)
    subheadings = ("Constant Maker Send and Receive Amounts.",
                   "Constant Taker Receive Amount.",
                   "Constant Taker Send Amount.")
    for i, input_array in enumerate(swaps):
        print(f"#### Example {i + 1}: {subheadings[i]}")
        scenario_1, scenario_2 =  perform_swap(input_array)
        print(f"##### *Example {i + 1} Summary:*")
        print_summary_table(scenario_1, scenario_2)


Re: BIP28. Not impressed with how quickly commitment to the recovery percentage has dropped from 100% to (no less than) 90%. Is there no way for the protocol to just eat the cost and automate the conversion procedure, rather than requiring manual intervention every time?

Re: BIP29. In a recent proposal about adjusting the vortex fee share, we were told that we can’t reduce the vortex to 10% on the DAI pool; “since the vortex is a global parameter, if changed, it affects all pools in the same way”. That means that no individual pool can be adjusted according to its deficit state, and all v2/v3 LPs keep giving virtually all their fees to the protocol, gaining no benefit from remaining as LPs. So if the v2/v3 vortex is superceded by a universal Carbon+v2/v3 vortex, doesn’t that mean there’s even less chance of v2/v3 LPs ever having the fee share adjusted to a beneficial ratio again? So there’ll be even less incentivisation for any existing LPs to remain LPs as soon as their deficit reaches tolerable levels.

It sounds like if the universal/standardised vortex takes over, existing LPs lose 100% of all their fees earned (bringing v3 LPs in line with v2), and the only person who benefits from fees is the manual function caller, who wouldn’t earn the fees in their choice of TKN even if its an existing LP calling the function. If that’s the case, then I don’t see the net benefit in forcing v2/v3s into the Carbon vortex under a standardisation, rather than maintaining as is and having Carbon run its own separate vortex.


Easily voting “For” on all of these.


I wish there was an easy way. Not to worry - that 10% number is arbitrary. I would support a lower incentive, and happy to edit the proposal. What number would you think reasonable, keeping in mind that the caller must foot the gas cost. Maybe 5%?

I would much prefer to write that no less than 95% and up to 100% of the fees result in burning BNT. We could go lower. Even a 2% incentive is tenable, it just means the burns will be less frequent. I don’t think that is too big a concern, though.


It is true that the Vortex contracts use global values - they do not have a per-token setting. However, nothing proposed here affects that limitation. Its not clear (to me) how the burning of BNT directly (instead of vBNT) impacts the liklihood of a future beneficial ratio proposal. Having said that, I would prefer that users do withdraw when their liquidity pools are back in surplus. My only ambition for the past year (feels like a lifetime now) is to recover the state of V2.1 and V3, with the target being that every LP can withdraw everything in entirety. I am not afraid of everyone pulling their liquidity when it is back in surplus. On the contrary - that is the goal.


I am going to be AFK for about 9-10 hours. I will be back to respond to any comments/questions that may have accumulated during that time ASAP.


I believe the impact on likelihood of a future beneficial ratio proposal there is that people invested in the success of Carbon (and thereby adjustments to its parameters) will only care about BNT buying/burning mechanisms, since they’ll never have existed in a context of earning fees from the protocol. The higher that is, the better for them. Their primary source of benefit is either meant to be use of Carbon for automated trading, or speculation on BNT appreciation due to Carbon’s pro-BNT buy/burn mechanics.

Meanwhile, v2/v3 LPs were supposed to benefit from protocol use through fees accrued in TKN. So if the vortex is universal, it seems that the goals of the two groups will not be aligned if we get to a point where deficit is reduced; Carbon natives will want to preserve system that maximises return for BNT, whilst Bancor TKN LPs would like to finally earn some actual TKN fees again. But if we acknowledge (as you and other contributors seem to have done) that v2 and v3 are essentially abandonware and LPs are actively encouraged to leave Bancor as soon as their deficit is tenable, then I suppose the thought of them earning fees for LPing (and thus adjusting the ratio in a universal vortex) doesn’t really matter.



I think a good approach would be to write a proposal, that explicitly addresses what should happen as the protocol returns to surplus. I would be very happy to work on it with you.

For example, we could start with V3 on a per-token basis. Once a token is back to surplus, we can propose that the trading liquidity be reduced, and the off-curve liquidity increased to be precisely the number required to cover all deposits.

Unfortunately we dont have that kind of flexibility on V2.1, but we can work on something.

Then, we can mandate that once every single token on V2.1 and V3 is back to surplus (these can be done separately), that the Vortex contract is retired completely on these legacy protocols.

If you like, I could draft something? I would prefer we work together on it, but I can at least get the process started.


Imo, Mark’s reply below is a good concession. But I think in reality the DAO would almost always vote to keep the vortex burning.
There is a lot of Protocol Owned liquidity that can earn fees and burn more BNT for us, while users withdrawing their LP will just burn more BNT.
We have seen that more TVL doesn’t correlate with the same increase in fees, even more, so more TVL can actually be more damaging as the IL can rack up more.

I think we should incentivize users to go to Carbon as much as possible and just let Bancor be an arbitrage protocol.
Carbon will just be that much more efficient at managing liquidity and with the dev manpower being as stretched as it is, deploying too many hours on a semi-death (no offense) protocol seems like a waste.


  • DAO will probably always vote to keep the vortex burning as there will be cases of POL outweighing lps anyway
  • We don’t necessarily need more TVL, probably need to actually disable trading liquidity in a lot of pools cause of IL
  • Focus should be as much as possible to incentivize users to go to Carbon as it’s much more efficient
  • Limited manpower makes our resources stretched thin thus we need to make hard choices in what to support and whatnot.

To also add, will probably be voting yes on all proposals, but we should maybe take a look at the vortex payment fee. We shouldn’t fall into the same trap as what we had at the beginning when we were paying vortex initiators way too much money. So much money that even with the reduction we implemented it still was more than profitable enough.

Tagging Mark also.


Yep, agreed.

Let’s roll it back to something like 2%? I can edit the proposal later today.


would this mean that all these BIPs will go live on snapshot together at the same time and votes would have to vote on each one separately?