Skip to content

Draft: Proto: move stake updating functions

Context

Objectives:

  • make sure that invariants relating staking balances to account balances are enforced at a single location
  • remove redundant representation of delegates, i.e. the constructor DelegateBalance is removed

By-product:

  • A transfer between two accounts sharing the same delegate does not update staking balances

Examples:

  • the case of frozen deposits before and after the change. Before, one had to be careful and not forget to update staking balances at each transfer. After updating staking balances is taken care of by Token.transfer
    Before:
 (* In delegate_storage *)
 let punish_double_baking ctxt delegate (level : Level_repr.t) =
  ...
  Token.transfer
    ctxt
    (`Frozen_deposits delegate)
    `Double_signing_punishments
    amount_to_burn
  >>=? fun (ctxt, balance_updates) ->
  Stake_storage.remove_stake ctxt delegate amount_to_burn >>=? fun ctxt ->
  Storage.Slashed_deposits.find (ctxt, level.cycle) (level.level, delegate)
  >>=? fun slashed ->
  ...

After:

  (* In delegate_storage *)
  let punish_double_baking ctxt delegate (level : Level_repr.t) =
  ...
  Token.transfer
    ctxt
    (`Frozen_deposits delegate)
    `Double_signing_punishments
    amount_to_burn
  >>=? fun (ctxt, balance_updates) ->
  Storage.Slashed_deposits.find (ctxt, level.cycle) (level.level, delegate)
  >>=? fun slashed ->
  ...
  • transfers to or from the constructor DelegateBalance become normal transfers from or to Contract
    Before:
  (* In delegate_storage *)
 let freeze_deposits ?(origin = Receipt_repr.Block_application) ctxt ~new_cycle
    ~balance_updates =
    ....
      if Tez_repr.(current_amount > maximum_stake_to_be_deposited) then
        Tez_repr.(current_amount -? maximum_stake_to_be_deposited)
        >>?= fun to_reimburse ->
        Token.transfer
          ~origin
          ctxt
          (`Frozen_deposits delegate)
          (`Delegate_balance delegate)
          to_reimburse
        >|=? fun (ctxt, bupds) -> 

After:

  (* In delegate_storage *)
 let freeze_deposits ?(origin = Receipt_repr.Block_application) ctxt ~new_cycle
    ~balance_updates =
    ....
      if Tez_repr.(current_amount > maximum_stake_to_be_deposited) then
        Tez_repr.(current_amount -? maximum_stake_to_be_deposited)
        >>?= fun to_reimburse ->
        Token.transfer
          ~origin
          ctxt
          (`Frozen_deposits delegate)
          (`Contract delegate_contract)
          to_reimburse
        >|=? fun (ctxt, bupds) ->

Manually testing the MR

  • Every commit has been committed once the integration tests for token, frozen bonds and delegation passes locally
dune exec src/proto_alpha/lib_protocol/test/integration/main.exe -- test "^token"
dune exec src/proto_alpha/lib_protocol/test/integration/main.exe -- test "^frozen bonds"
dune exec src/proto_alpha/lib_protocol/test/integration/consensus/main.exe -- test "^delegation"
  • The integration tests for token has been enriched with tests validating the staking movement by token in a dedicated commit: Proto: tests delegation management from token module (I do not put the hash as the review period might modified it).

  • A replay-test is coming soon.

Checklist

  • Document the interface of any function added or modified (see the coding guidelines)
  • Document any change to the user interface, including configuration parameters (see node configuration)
  • Provide automatic testing (see the testing guide).
  • For new features and bug fixes, add an item in the appropriate changelog (docs/protocols/alpha.rst for the protocol and the environment, CHANGES.rst at the root of the repository for everything else).
  • Select suitable reviewers using the Reviewers field below.
  • Select as Assignee the next person who should take action on that MR
Edited by Zay Dargaye

Merge request reports