317 lines
13 KiB
Markdown
317 lines
13 KiB
Markdown
|
BSIP: 0017
|
||
|
Title: Revive BitAssets after global settlement
|
||
|
Authors: Peter Conrad <conrad@quisquis.de>
|
||
|
Status: Draft
|
||
|
Type: Protocol
|
||
|
Created: 2016-10-27
|
||
|
Discussion: https://bitsharestalk.org/index.php/topic,23334.0.html
|
||
|
Copyright: Public Domain
|
||
|
|
||
|
# Abstract
|
||
|
|
||
|
BitAssets, i. e. market-pegged assets (MPA) like bitUSD and prediction
|
||
|
markets (PM) in BitShares can suffer a "global settlement" event. After
|
||
|
global settlement, the asset is effectively rendered useless. This BSIP
|
||
|
proposes a protocol change to enable resolving a global settlement so
|
||
|
that affected assets can be "reset" and put to good use again.
|
||
|
|
||
|
# Motivation
|
||
|
|
||
|
Market-pegged assets, aka SmartCoins, and to some extent Prediction
|
||
|
Markets are among the core features of the BitShares blockchain and as
|
||
|
such provide one of our USPs.
|
||
|
|
||
|
MPAs can suffer a "black swan" event. A black swan occurs when the least
|
||
|
collateralized short position has insufficient collateral to buy back
|
||
|
the borrowed SmartCoins at the current feed price. What happens then is
|
||
|
that the MPA is tagged with a "settlement price", defined as the
|
||
|
collateral ratio of the least collateralized short. All short positions
|
||
|
are closed automatically, by collecting sufficient collateral into a
|
||
|
settlement pool and paying out the remainder to the short's owners. MPA
|
||
|
holders can use the forced settlement operation to receive their share
|
||
|
from the settlement pool in exchange for their MPAs. (Actually there's a
|
||
|
bug that prevents this currently, but that's the way it is intended to
|
||
|
work.)
|
||
|
|
||
|
A technically quite similar mechanism is used to settle PMs. In a PM,
|
||
|
shorters and holders are betting on the outcome of a specific event.
|
||
|
Once the actual outcome has materialized, the PM is settled by setting a
|
||
|
settlement price.
|
||
|
|
||
|
Both MPAs that have suffered a black swan and PMs that have seen
|
||
|
settlement are effectively dead. They can still be transferred or
|
||
|
traded, but they can no longer be shorted. Eventually, all significant
|
||
|
holders wlll have settled their positions, and some dust will remain
|
||
|
scattered all over the place, where the value of the dust position is
|
||
|
lower than the fees required to get rid of it.
|
||
|
|
||
|
Allowing MPAs and PMs to be revived after a settlement event will
|
||
|
greatly increase the usefulness of both types of assets. Increased
|
||
|
usefulness will hopefully boost adoption.
|
||
|
|
||
|
# Rationale
|
||
|
|
||
|
After a global settlement, the value of the unit in question is fixed
|
||
|
relative to the underlying asset. This means that any exchange of an
|
||
|
amount of the asset in question for the underlying asset at the
|
||
|
settlement price does not financially damage the previous owner of the
|
||
|
exchanged asset.
|
||
|
|
||
|
Reviving bitassets is beneficial for the network as a whole. This
|
||
|
justifies decisions in favour of the network, as long as financial
|
||
|
damage to anyone is avoided. Any acceptable financial damage must be in
|
||
|
the range of rounding errors that are to be expected when dealing with
|
||
|
the assets in question.
|
||
|
|
||
|
In that regard, the "override_transfer" permission, which usually
|
||
|
regulates forced transfers of a bitasset by the issuer, can be ignored
|
||
|
for the purpose of reviving an asset.
|
||
|
|
||
|
# Specification
|
||
|
|
||
|
## revive_asset operation
|
||
|
|
||
|
A new operation will be introduced that performs the revival. The fee
|
||
|
for this operation SHOULD be significant, because it is a
|
||
|
computationally intensive operation.
|
||
|
|
||
|
The operation has a single parameter, the asset to be revived.
|
||
|
|
||
|
The operation requires a signature from the asset's issuer authority.
|
||
|
|
||
|
The operation can only be invoked under the following conditions:
|
||
|
|
||
|
* The asset has a settlement_price, either from a black swan or from an
|
||
|
asset_global_settle operation. Note that this is possible only for MPAs and
|
||
|
PMs.
|
||
|
* The global settlement event has happened at least 28 days ago.
|
||
|
This parameter requires further discussion, see below.
|
||
|
|
||
|
To execute the operation, all open positions of the asset to be revived are
|
||
|
looked up and handled as described below.
|
||
|
|
||
|
## Open Positions and How to Handle Them
|
||
|
|
||
|
In the following, SWAN is the asset to be revived. BACK is the asset backing
|
||
|
SWAN.
|
||
|
|
||
|
### force_settlement_object
|
||
|
|
||
|
Forced settlements have an expiry date. After that date, they are cancelled if
|
||
|
the underlying asset has a settlement_price. For SWAN this is the case, so these
|
||
|
are resolved automatically after some time. Because "some time" can be quite
|
||
|
long though, it is better to resolve this in a quicker way.
|
||
|
|
||
|
Resolution: cancel them all at the time of the black swan. This is a softfork.
|
||
|
|
||
|
### limit_order_object
|
||
|
|
||
|
Limit orders can either buy or sell SWAN. In the case of a sell, the order holds
|
||
|
some amount of SWAN. Sell orders MUST be cancelled to revive the asset. Buy
|
||
|
orders SHOULD be cancelled, because the price offered may be based on outdated
|
||
|
information.
|
||
|
|
||
|
Resolution: Cancel all orders where either the asset to sell or the asset to
|
||
|
receive equals SWAN. An index on limit_order_object::price::quote::asset_id will
|
||
|
be added to speed up lookups.
|
||
|
|
||
|
### call_order_object
|
||
|
|
||
|
Calls on SWAN are resolved when global settlement happens. So at the time of
|
||
|
revival none of these exist.
|
||
|
|
||
|
However, calls may exist with SWAN as collateral. Suppose that DUCK is an asset
|
||
|
that is backed by SWAN. Calls on DUCK cannot be cancelled.
|
||
|
|
||
|
Resolution: Modify DUCK to be backed by BACK instead of SWAN. Modify all DUCK
|
||
|
calls accordingly. Remove price feeds from DUCK.
|
||
|
|
||
|
This solution requires further discussion.
|
||
|
|
||
|
### vesting_balance_object
|
||
|
|
||
|
A vesting_balance_object can hold a vesting balance of SWAN for a given account.
|
||
|
Vesting balances can vest with different strategies (linear or coin-days).
|
||
|
|
||
|
Resolution: for every non-zero vesting balance of SWAN, create (if necessary) a
|
||
|
vesting balance for BACK with an equivalent vesting policy and adjust balance
|
||
|
and policy parameters accordingly. An index on
|
||
|
vesting_balance_object::asset::asset_id will be added to speed up lookups.
|
||
|
|
||
|
### balance_object
|
||
|
|
||
|
Balance objects (not to be confused with account_balance objects) contain
|
||
|
genesis balances, possibly with linear vesting. This should be a rare case in
|
||
|
BitShares-2.0, but it is a possible case and requires resolution.
|
||
|
|
||
|
Resolution: all balances of SWAN are replaced with equivalent balances of BACK.
|
||
|
An index on balance_object::asset_type will be added to speed up lookups.
|
||
|
|
||
|
### blinded_balance_object
|
||
|
|
||
|
Blinded balances are part of the stealth feature of Graphene. A blinded balance
|
||
|
has only an asset id, but no (visible) amount. The only visible thing is the
|
||
|
total of all blinded balances of that asset type, which is a field in the
|
||
|
asset's dynamic data.
|
||
|
|
||
|
Resolution:
|
||
|
|
||
|
1. A part of the settlement_fund will be set aside for settling blinded
|
||
|
balances. For this, a new object type "blinded_settlement_object" will be
|
||
|
introduced that carries the blinded_settlement_fund and the remaining total
|
||
|
blinded amount.
|
||
|
2. The blinded_balance_object will receive an additional optional field that may
|
||
|
contain a reference to a blinded_settlement_fund. blinded_balances with such
|
||
|
a reference may only be withdrawn from, together with other blinded_balances
|
||
|
carrying the same reference, but they cannot be transferred anymore.
|
||
|
Note: special care needs to be taken in the fee handling here. Using the
|
||
|
blinded balance together with the SWAN fee pool must be avoided. Instead,
|
||
|
the BACK fee pool must be used (if at all).
|
||
|
3. Upon withdrawal, the amount withdrawn is immediately converted to BACK, from
|
||
|
the blinded_settlement_fund. If the amount withdrawn is equal to the total
|
||
|
remaining blinded amount, the remaining blinded_settlement_fund is paid out
|
||
|
to the withdrawer and the object is deleted.
|
||
|
|
||
|
Note that the pair (SWAN, blinded_settlement_object) creates a kind of virtual
|
||
|
asset that should not be mixed with "pure" SWAN balances by existing user
|
||
|
interfaces.
|
||
|
|
||
|
An index on blinded_balance_object::asset_id will be added to speed up lookups.
|
||
|
|
||
|
### blinded_settlement_object
|
||
|
|
||
|
This object type does not exist yet. It is introduced by the mechanism to handle
|
||
|
blinded SWAN balances, as described above.
|
||
|
|
||
|
Resolution: blinded_settlement_objects holding SWAN are immediately converted to
|
||
|
BACK.
|
||
|
|
||
|
### account_balance_object
|
||
|
|
||
|
This is what holds the actual balances of an account. Each such object refers to
|
||
|
a specific account and asset. Account_balances of SWAN can be converted into
|
||
|
BACK at any time via the forced settlement feature.
|
||
|
|
||
|
Resolution: account balances of SWAN are converted into BACK immediately.
|
||
|
|
||
|
### asset_bitasset_data_object
|
||
|
|
||
|
This object defines (among other things) if an asset is in global settlement.
|
||
|
|
||
|
Resolution:
|
||
|
|
||
|
* pay out remaining settlement_fund to issuer (if any)
|
||
|
* nullify settlement_price / force_settled_volume
|
||
|
* empty feed list / unset current_feed
|
||
|
* empty options.whitelist_authorities and set white_list in options.flags
|
||
|
|
||
|
The latter requires discussion.
|
||
|
|
||
|
### asset_dynamic_data_object
|
||
|
|
||
|
This object logs the existing amount of SWAN (total and blinded). It also
|
||
|
contains the fee pool.
|
||
|
|
||
|
Resolution: set accumulated_fees to 0 and adjust current_supply accordingly.
|
||
|
The issuer will be compensated for the lost fees by receiving the remainder of
|
||
|
the settlement_fund. After all the previous resolutions have been executed, the
|
||
|
current_supply and the confidential_supply must be 0.
|
||
|
|
||
|
## Additional changes
|
||
|
|
||
|
### Bugfix: MPAs that have seen a black swan cannot be settled after the price feed expires
|
||
|
|
||
|
It has turned out that force-settling an MPA requires a valid price feed even
|
||
|
when the MPA has a settlement_price set. This is clearly a bug, since in that
|
||
|
case the settlement price is independent from the price feed. Furthermore,
|
||
|
publishing price feeds is no longer possible after a black swan, so the time
|
||
|
when settlement is possible at all is limited to the expiration period of the
|
||
|
price feed of the MPA.
|
||
|
|
||
|
This needs to be fixed. See https://github.com/cryptonomex/graphene/issues/664#issuecomment-254056746
|
||
|
for a discussion.
|
||
|
|
||
|
### New chain parameter: minimum_time_before_asset_revival
|
||
|
|
||
|
This parameter defines the minimum required time between a global settlement
|
||
|
event on an asset and the revival of that same asset. The parameter will be
|
||
|
modifiable by the committee and defaults to 4 weeks (28 days). See discussion
|
||
|
below.
|
||
|
|
||
|
# Discussion
|
||
|
|
||
|
## minimum_time_before_asset_revival
|
||
|
|
||
|
A quick cycle of global settlement and revival is likely to cause confusion
|
||
|
among an asset's users (holders and shorters). There is even limited potential
|
||
|
to abuse this feature. Therefore it is reasonable to enforce a minimum time
|
||
|
before revival, allowing users to get informed about the asset's situation and
|
||
|
the resolution process that affects them.
|
||
|
|
||
|
## Dependent Assets
|
||
|
|
||
|
As described above, assets may exist that use SWAN as collateral. Short
|
||
|
positions in such assets must be resolved somehow. The proposed resolution is
|
||
|
quite harsh, in that it modifies the asset that uses SWAN as collateral.
|
||
|
|
||
|
It is reasonable insofar as SWAN effectively represents the value of a fixed
|
||
|
amount of BACK, which means that an asset backed by SWAN is *actually* backed
|
||
|
by BACK. The proposed resolution only makes that explicit.
|
||
|
|
||
|
There is a related comment in the source code (https://github.com/cryptonomex/graphene/blob/f1b19b15629cd02669a94f2af16eeaec7f54b3f6/libraries/chain/include/graphene/chain/protocol/asset_ops.hpp#L160 ):
|
||
|
|
||
|
> If this asset is used as backing for other bitassets, those bitassets will be
|
||
|
force settled at their current price.
|
||
|
|
||
|
This is not reflected in the actual implementation AFAICS.
|
||
|
|
||
|
Better suggestions are welcome.
|
||
|
|
||
|
## Flags and permissions
|
||
|
|
||
|
As described above, the revival operation will set the whitelist flag and
|
||
|
permission of the revived asset. The purpose of this is to prevent the asset
|
||
|
from immediately becoming active again, before the issuer has a chance to
|
||
|
modify other asset parameters. For example, after reviving a prediction market,
|
||
|
the owner might want to update the asset description before starting the next
|
||
|
round of predictions.
|
||
|
|
||
|
## Affected Parties
|
||
|
|
||
|
### Exchanges
|
||
|
|
||
|
An exchange holding SWAN will have its SWAN exchanged for BACK just like anyone
|
||
|
else. The exchange will probably have SWAN balances in its internal ledgers,
|
||
|
which belong to the users of the exchange. The exchange MUST be notified of the
|
||
|
settlement and it MUST modify its internal ledger, replacing SWAN balances
|
||
|
with BACK balances.
|
||
|
|
||
|
Exchanges SHOULD perform this operation independently from the revival, i. e.
|
||
|
before the revival is triggered. They can do this by force-settling their SWAN
|
||
|
holdings.
|
||
|
|
||
|
### (Other) Users
|
||
|
|
||
|
Users holding SWAN will have their holdings replaced with an equivalent amount
|
||
|
of BACK, at the settlement_price. This does not damage the holder financially,
|
||
|
see above.
|
||
|
|
||
|
### Asset Owners (aka Issuers)
|
||
|
|
||
|
The issuer of an asset to be revived should know what he is doing. Invoking the
|
||
|
revive_asset operation is a wilful act. If he isn't happy with the effect of the
|
||
|
operation he simply should not invoke it.
|
||
|
|
||
|
Issuers of assets backed by a revived assets are affected too, but they have no
|
||
|
choice. See discussion about Dependent Assets above.
|
||
|
|
||
|
# Summary
|
||
|
|
||
|
This proposal discusses a set of changes to bring back a "stuck" asset into a
|
||
|
usable state.
|
||
|
|
||
|
Not all shareholders need to understand the technical details of the proposal,
|
||
|
however, they should be aware of the implications of these changes. It is
|
||
|
particularly important to understand how the revival of an asset affects the
|
||
|
different parties, i. e. holders, shorters, traders and issuers.
|