Skip to content

Commit

Permalink
Update messaging and serialization (#163)
Browse files Browse the repository at this point in the history
* Update messaging and serialization

* Replace collection prefixes with bigsize instead of u16

* add test vectors

* Use old serialization format for oracle messages

* Add temporary contract id to offer message

* Rename leftEndPoint to endPoint

* Update test vectors

* Fix forgotten types

* Replace bigsize with u64 in payout curve and numeric outcome

* Update test vectors

* use bigsize for vector prefix in rounding intervals

* Update test vectors setting base as u16

* Update test vector with fix to precision field

* Update test vectors to include temporary contract id in offer message

* Add protocol version to accept message

* Add protocol version to sign message

* Fix test vectors
  • Loading branch information
Tibo-lg authored Jun 12, 2022
1 parent 160eb36 commit 8ecdf2a
Show file tree
Hide file tree
Showing 18 changed files with 19,521 additions and 149 deletions.
256 changes: 146 additions & 110 deletions Messaging.md

Large diffs are not rendered by default.

15 changes: 7 additions & 8 deletions NumericOutcome.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,18 +66,17 @@ up in the case of a tie.

#### Rounding Interval Serialization

1. type: 42788 (`rounding_intervals_v0`)
2. data:
* [`u16`:`num_rounding_intervals`]
* [`bigsize`:`begin_interval_1`]
* [`bigsize`:`rounding_mod_1`]
1. data:
* [`bigsize`:`num_rounding_intervals`]
* [`u64`:`begin_interval_1`]
* [`u64`:`rounding_mod_1`]
* ...
* [`bigsize`:`begin_interval_num_rounding_intervals`]
* [`bigsize`:`rounding_mod_num_rounding_intervals`]
* [`u64`:`begin_interval_num_rounding_intervals`]
* [`u64`:`rounding_mod_num_rounding_intervals`]

`num_rounding_intervals` is the number of rounding intervals specified in this function and can be
zero in which case a rounding modulus of `1` is used everywhere.
Each serialized rounding interval consists of two `bigsize` integers.
Each serialized rounding interval consists of two `u64` integers.

The first integer is called `begin_interval` and refers to the x-coordinate (`event_outcome`) at which this range begins.
The second integer is called `rounding_mod` and contains the rounding modulus to be used in this range.
Expand Down
54 changes: 28 additions & 26 deletions PayoutCurve.md
Original file line number Diff line number Diff line change
Expand Up @@ -65,24 +65,23 @@ interpolation points.

In this section we detail the TLV serialization for a general `payout_function`.

#### Version 0 payout_function
#### payout_function

1. type: 42790 (`payout_function_v0`)
2. data:
* [`u16`:`num_pieces`]
* [`bigsize`:`endpoint_0`]
* [`bigsize`:`endpoint_payout_0`]
1. data:
* [`bigsize`:`num_pieces`]
* [`u64`:`endpoint_0`]
* [`u64`:`endpoint_payout_0`]
* [`u16`:`extra_precision_0`]
* [`payout_curve_piece`:`piece_1`]
* [`bigsize`:`endpoint_1`]
* [`u64`:`endpoint_1`]
* ...
* [`payout_curve_piece`:`piece_num_pieces`]
* [`bigsize`:`endpoint_num_pieces`]
* [`bigsize`:`endpoint_payout_num_pieces`]
* [`u64`:`endpoint_num_pieces`]
* [`u64`:`endpoint_payout_num_pieces`]
* [`u16`:`extra_precision_num_pieces`]

`num_pieces` is the number of `payout_curve_pieces` which make up the payout curve along with their endpoints.
Each endpoint consists of a two `bigsize` integers and a `u16`.
Each endpoint consists of a two `u64` and a `u16`.

The first integer is called `endpoint` and contains the actual `event_outcome` which corresponds to an x-coordinate
on the payout curve which is a boundary between curve pieces.
Expand Down Expand Up @@ -158,15 +157,16 @@ where a spline is made up of polynomial pieces so that the resulting interpolati

#### Polynomial Serialization

1. type: 42792 (`polynomial_payout_curve_piece`)
2. data:
* [`u16`:`num_pts`]
* [`bigsize`:`event_outcome_1`]
* [`bigsize`:`outcome_payout_1`]
1. implements: `payout_curve_piece`
1. type: 0
1. data:
* [`bigsize`:`num_pts`]
* [`u64`:`event_outcome_1`]
* [`u64`:`outcome_payout_1`]
* [`u16`:`extra_precision_1`]
* ...
* [`bigsize`:`event_outcome_num_pts`]
* [`bigsize`:`outcome_payout_num_pts`]
* [`u64`:`event_outcome_num_pts`]
* [`u64`:`outcome_payout_num_pts`]
* [`u16`:`extra_precision_num_pts`]

`num_pts` is the number of midpoints specified in this curve piece which will be used along with the surrounding `endpoint`s to perform interpolation.
Expand Down Expand Up @@ -206,31 +206,33 @@ set `f_1 = b = c = 0, a = 1, d = constant, f_2 = constant'`.

#### Hyperbola Serialization

1. type: 42794 (`hyperbola_payout_curve_piece`)
2. data:

1. implements: `payout_curve_piece`
1. type: 1
1. data:
* [`bool`:`use_positive_piece`]
* [`bool`:`translate_outcome_sign`]
* [`bigsize`:`translate_outcome`]
* [`u64`:`translate_outcome`]
* [`u16`:`translate_outcome_extra_precision`]
* [`bool`:`translate_payout_sign`]
* [`bigsize`:`translate_payout`]
* [`u64`:`translate_payout`]
* [`u16`:`translate_payout_extra_precision`]
* [`bool`:`a_sign`]
* [`bigsize`:`a`]
* [`u64`:`a`]
* [`u16`:`a_extra_precision`]
* [`bool`:`b_sign`]
* [`bigsize`:`b`]
* [`u64`:`b`]
* [`u16`:`b_extra_precision`]
* [`bool`:`c_sign`]
* [`bigsize`:`c`]
* [`u64`:`c`]
* [`u16`:`c_extra_precision`]
* [`bool`:`d_sign`]
* [`bigsize`:`d`]
* [`u64`:`d`]
* [`u16`:`d_extra_precision`]

If `use_positive_piece` is set to true, then `y_1` is used, otherwise `y_2` is used.

Then there are six numeric values represented as a `bool` sign set to true for positive numbers and false for negative ones, a `bigsize` integer, and a `u16` extra precision.
Then there are six numeric values represented as a `bool` sign set to true for positive numbers and false for negative ones, a `u64` integer, and a `u16` extra precision.
To be precise, the numbers used should be: (`num_sign`)( `num + double(num_extra_precision) >> 16`).

The fields `translate_outcome` and `translate_payout` correspond to the values `f_1` and `f_2` respectively.
Expand Down
29 changes: 24 additions & 5 deletions Protocol.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,21 +66,29 @@ the funding transaction and CETs.

1. type: 42778 (`offer_dlc_v0`)
2. data:
* [`u32`: `protocol_version`]
* [`byte`:`contract_flags`]
* [`chain_hash`:`chain_hash`]
* [`32*byte`:`temporary_contract_id`]
* [`contract_info`:`contract_info`]
* [`point`:`funding_pubkey`]
* [`spk`:`payout_spk`]
* [`u64`:`payout_serial_id`]
* [`u64`:`offer_collateral_satoshis`]
* [`u16`:`num_funding_inputs`]
* [`bigsize`:`num_funding_inputs`]
* [`num_funding_inputs*funding_input`:`funding_inputs`]
* [`spk`:`change_spk`]
* [`u64`:`change_serial_id`]
* [`u64`:`fund_output_serial_id`]
* [`u64`:`feerate_per_vb`]
* [`u32`:`cet_locktime`]
* [`u32`:`refund_locktime`]
* [`offer_tlvs`: `tlvs`]

[//]: # (TODO: `protocol_version` should be advertised by DLC nodes in the future)
The `protocol_version` value denotes the version of the protocol that the offering node is proposing.
If the receiving node does not support the requested version, it should ignore the message.
The current protocol version is `1`.

No bits of `contract_flags` are currently defined, this field should be ignored.

Expand All @@ -90,6 +98,8 @@ The existence of the `chain_hash` allows nodes to open contracts
across many distinct blockchains as well as have contracts within multiple
blockchains opened to the same peer (if it supports the target chains).

The `temporary_contract_id` is used to identify the contract on a per-peer basis until the funding transaction is established, at which point it is replaced by the contract_id, which is derived from the funding transaction.

`contract_info` specifies the contract to be constructed and the oracles to be used.

`funding_pubkey` is the public key in the 2-of-2 multisig script of
Expand Down Expand Up @@ -123,7 +133,8 @@ The sending node MUST:

- set undefined bits in `contract_flags` to 0.
- ensure the `chain_hash` value identifies the chain it wishes to open the contract within.
- set `payout_spk` and `change_spk` to a [standard script pubkey](#script-pubkey-standardness-definition)
- set `temporary_contract_id` to a random value.
- set `payout_spk` and `change_spk` to a [standard script pubkey](#script-pubkey-standardness-definition).
- set `funding_pubkey` to a valid secp256k1 pubkey in compressed format.
- set `offer_collateral_satoshis` to a value greater than or equal to 1000.
- set `cet_locktime` and `refund_locktime` to either both be UNIX timestamps, or both be block heights as distinguished [here](https://en.bitcoin.it/wiki/NLockTime).
Expand All @@ -142,6 +153,7 @@ The sending node SHOULD:

The receiving node MUST:

- ensure that the `temporary_contract_id` is unique from any other contract ID with the same peer.
- ignore undefined bits in `contract_flags`.

The receiving node MAY reject the contract if:
Expand All @@ -156,6 +168,7 @@ The receiving node MAY reject the contract if:
The receiving node MUST reject the contract if:

- the `chain_hash` value is set to a hash of a chain that is unknown to the receiver.
- the `temporary_contract_id` is not unique from any other contract ID with the same peer.
- the `contract_info` refers to events unknown to the receiver.
- the `contract_info` refers to an oracle unknown or inaccessible to the receiver.
- `payout_spk` or `change_spk` are not a [standard script pubkey](#script-pubkey-standardness-definition).
Expand All @@ -176,25 +189,28 @@ and closing transactions.

1. type: 42780 (`accept_dlc_v0`)
2. data:
* [`u32`: `protocol_version`]
* [`32*byte`:`temporary_contract_id`]
* [`u64`:`accept_collateral_satoshis`]
* [`point`:`funding_pubkey`]
* [`spk`:`payout_spk`]
* [`u64`:`payout_serial_id`]
* [`u16`:`num_funding_inputs`]
* [`bigsize`:`num_funding_inputs`]
* [`num_funding_inputs*funding_input`:`funding_inputs`]
* [`spk`:`change_spk`]
* [`u64`:`change_serial_id`]
* [`cet_adaptor_signatures`:`cet_adaptor_signatures`]
* [`signature`:`refund_signature`]
* [`negotiation_fields`:`negotiation_fields`]
* [`negotiation_fields`:`negotiation_fields`] (Optional: 1)
* [`accept_tlvs`: `tlvs`]

#### Requirements

The `temporary_contract_id` MUST be the SHA256 hash of the `offer_dlc` message.
The `temporary_contract_id` MUST be the same as the `temporary_contract_id` in the `offer_contract` message.

The sender MUST:

- set `protocol_version` to the same value as the one in the received `offer_dlc` message.
- set `accept_collateral_satoshis` to equal the `offer_dlc`'s `contract_info` `total_collateral` minus the `offer_collateral_satoshis`.
- set `payout_spk` and `change_spk` to a [standard script pubkey](#script-pubkey-standardness-definition)
- set `cet_adaptor_signatures` to valid adaptor signatures, using its `funding_pubkey` for each CET, as defined in the [transaction specification](Transactions.md#contract-execution-transaction) and using signature public keys computed using the `offer_dlc`'s `contract_info` and `oracle_info` as adaptor points.
Expand Down Expand Up @@ -243,15 +259,18 @@ This message introduces the [`contract_id`](#definition-of-contract_id) to ident

1. type: 42782 (`sign_dlc_v0`)
2. data:
* [`u32`: `protocol_version`]
* [`contract_id`:`contract_id`]
* [`cet_adaptor_signatures`:`cet_adaptor_signatures`]
* [`signature`:`refund_signature`]
* [`funding_signatures`:`funding_signatures`]
* [`sign_tlvs`: `tlvs`]

#### Requirements

The sender MUST:

- set `protocol_version` to the same value as the one in the sent `offer_dlc` message.
- set `contract_id` by exclusive-OR of the `funding_txid`, the `funding_output_index` and the `temporary_contract_id` from the `offer_dlc` and `accept_dlc` messages.
- set `cet_adaptor_signatures` to valid adaptor signatures, using its `funding_pubkey` for each CET, as defined in the [transaction specification](Transactions.md#contract-execution-transaction) and using signature public keys computed using the `offer_dlc`'s `contract_info` and `oracle_info` as adaptor points.
- include an adaptor signature in `cet_adaptor_signatures` for every event specified in the `offer_dlc`'s `contract_info`.
Expand Down
Loading

0 comments on commit 8ecdf2a

Please sign in to comment.