extension-bolt: taproot gossip (features 70/71/72/73/74/75) - #1059
extension-bolt: taproot gossip (features 70/71/72/73/74/75)#1059ellemouton wants to merge 20 commits into
Conversation
|
Thanks to @rustyrussell , @joostjager & @GeorgeTsagk for the initial set of comments on the pre-draft PR! I will carry over some of the comments over to this PR so that a discussion can take place :) |
ellemouton
left a comment
There was a problem hiding this comment.
Carry-over comments from the pre-draft PR
| This document aims to update the gossip protocol defined in [BOLT 7][bolt-7] to | ||
| allow for advertisement and verification of taproot channels. An entirely new | ||
| set of gossip messages are defined that use [BIP-340][bip-340] signatures and | ||
| that use a purely TLV based schema. |
There was a problem hiding this comment.
The problem with TLV is that you now need everyone to check that compulsory fields are present. But some fields don't actually make sense as optional. We end up needing another version anyway.
There was a problem hiding this comment.
I think the simplicity of using tlv for everything might be more future proof & less complicated in the end. For example, if we decide on a compulsory field now but then later on add a new one, it will have to be TLV and then we have to have 2 ways of checking that compulsory fields are present vs something clean like tlvstream.MustHaveTypes(1, 2, 3, 4, ...)
We end up needing another version anyway.
This is true but by using TLV for everything, adding a new version due to the change of 1 compulsory field becomes easier to define in the spec I think. Instead of needing to define a whole new message, can just say "drop this tlv field and add this other tlv field".
There was a problem hiding this comment.
You can't though, because that would not be backwards compatible :( So you actually do have compulsory fields, which cannot be removed, until everyone upgrades.
It's actually simpler to define a new type in that case!
There was a problem hiding this comment.
is that you now need everyone to check that compulsory fields are present. But some fields don't actually make sense as optional
Isn't this already the case for all the other TLV extensions we've added over time?
I think one scenario that optional fields can be useful is if say in the channel announcements, we allow the advertiser to include/omit information that enables verification of complete channel output binding (so the individual keys, and tweak -- which would just be the bip86 tweak if that was used).
There was a problem hiding this comment.
Isn't this already the case for all the other TLV extensions we've added over time?
Yeah plus one for this question. If we later add compulsory fields, they would be via TLV and there would be some feature bit associated with understanding the version of the message that includes this field. So the benefit of doing only TLV is that all mandatory fields (ones added now and ones we add later on) are checked in the same way.
There was a problem hiding this comment.
I like some of the lessons from protobufs: the message gets defined completely separately from the business logic (ie the validation checking if all the wanted fields are there) and then it is always possible to add more fields or remove any fields.
There was a problem hiding this comment.
Perhaps worth a quick discussion at the spec meeting.
| For legacy channels, these last two proofs are made possible by including four | ||
| separate signatures in the `channel_announcement`. However, [BIP-340][bip-340] | ||
| signatures and the MuSig2 protocol allow us to now aggregate these four | ||
| signatures into a single one. Verifiers will then be able to aggregate the four | ||
| keys (`bitcoin_key_1`, `bitcoin_key_2`, `node_ID_1` and `node_ID_2`) using | ||
| MuSig2 key aggregation and then they can do a single signature verification | ||
| check instead of four individual checks. |
There was a problem hiding this comment.
Can we weaken this (and future proof it) a little, by publishing only the taproot_output_key? Sure, that means any taproot output can pretend to be a channel, but this is also a feature.
There was a problem hiding this comment.
I think there is some benefit to proving a binding to the LN context at least a little bit.
We could possibly just advertise the taproot_internal_key though (although I need to check the musig verification math for this). Kinda nice to, at least initially, to prove that the output cant be spent via the script path (via BIP86) as this at least gives spammers some deterrence... although perhaps not enough - interested to hear what people think re preventing spam of non-channels in the "only advertise the taproot_output_key" case
There was a problem hiding this comment.
I think that perhaps the "only announce taproot_output_key" scenario only works in full Gossip 2.0 where you have to prove you have some bitcoin in order to announce channels. But in this proposal (gossip 1.5), I think that might not be the case.
There was a problem hiding this comment.
Gossip v2 detached the proof-of-utxo from the channels in two ways:
- You could use any UTXO proofs
- The proofs were per-node, and not per-channel.
This is the former, without the latter. It allows for us to change to a different Taproot scheme in future if we wanted, without updating gossip, but still requires a proof-per-channel. Say, gossip 1.75?
There was a problem hiding this comment.
It allows for us to change to a different Taproot scheme in future if we wanted
Could you perhaps give an example? Do you mean like: we could possibly use the same gossip for a future channel factory or something in which case the internal key itself would be derived in a different way? (ie, something other than a 2-of-2 multisig)
If that is the case, then how about we make the "binding level" optional. Ie, we make the bitcoin_key_1, bitcoin_key_2 and tapteak fields optional and then if they are present, nodes can choose to be more strict with their verification or not.
| - MUST set `chain_hash` to the 32-byte hash that uniquely identifies the chain | ||
| that the channel was opened within: | ||
| - for the _Bitcoin blockchain_: | ||
| - MUST set `chain_hash` value (encoded in hex) equal | ||
| to `6fe28c0ab6f1b372c1a6a246ae63f74f931e8365e15a089c68d6190000000000`. |
There was a problem hiding this comment.
I suggest the same trick we use for offers: omitting this field means it is 6fe28c0ab6f1b372c1a6a246ae63f74f931e8365e15a089c68d6190000000000. And you must omit the field if it would be 6fe28c0ab6f1b372c1a6a246ae63f74f931e8365e15a089c68d6190000000000 (remember: both sides need to agree on exactly what this message looks like!).
Note also: I like the use of the TLV here. Because if we want to later, we can adapt this for pre-taproot channels, which would require more / different sigs. Though maybe they'll all close by the time v1-apocolypse is here?
There was a problem hiding this comment.
Cool - yeah I like the idea.
I have heard a few oppositions to assuming defaults though so just gonna leave this thread open to leave room for people to discuss. But personally, I dont see why a default is that bad.
| 9. subtype: `dns_hostname` | ||
| 10. data: | ||
| * [`...*utf8`:`hostname`] | ||
| * [`tu16`:`port`] |
There was a problem hiding this comment.
And if port is 0, say it's 9735?
There was a problem hiding this comment.
same here as for the above re defaults
| 2. data (tlv_stream): | ||
| 1. type: 0 (`channel_id`) | ||
| 2. data: | ||
| * [`channel_id`:`channel_id`] |
There was a problem hiding this comment.
I would definitely not use a TLV for channel_id. Every other message starts with channel_id, we should keep it fixed. The other two fields, well, they're OK, but it seems weird that they're optional.
There was a problem hiding this comment.
Yes, especially since this is not a gossip message, but a peer message which is much easier to upgrade.
| verify taproot channels. This part of the update affects the | ||
| `announcement_signatures` and `channel_announcement` messages. | ||
|
|
||
| The opportunity is also taken to rework the `node_announcement` and |
There was a problem hiding this comment.
Could you also not take this opportunity and keep using ecdsa signatures for those? That seems to reduce the delta of this proposal significantly, and maybe without loss of functionality for the user?
There was a problem hiding this comment.
yes we could definitely do this. but:
- getting to use schnorr sigs for them is quite beneficial for things like multi-key backed nodes
- see the section on "Bootstrapping Taproot Gossip", it is not necessary for nodes to use the new announcement message straight away. They can use the old one for as long as they like.
There was a problem hiding this comment.
Yeah don't see a good reason to not just use schnorr everywhere. For node anns, this means you can actually create a composite node that's actually composed of multiple entities, either via musig2 or FROST (tho FORST integration at the channel level has some other implications re shachain).
| signatures at the time of spending the output. This extra cost provided some | ||
| extra deterrence for attackers. This deterrence is not present with P2TR | ||
| transactions. | ||
| 3. The owners of `bitcoin_key_1` and `bitcoin_key_2` agree to be associated with |
There was a problem hiding this comment.
Since the public announcements of channels pretty much reveal what the output is being used for, would it be fair to mention that this mainly benefits private channels?
Different phrasing: Taproot outputs all do look the same regardless of being used for a channel or not, but any participant in LN will eventually receive a (public) channel announcement that marks some taproot UTXO as a channel, so effectively it's only the private channels that can remain "incognito"
| To also prevent nodes from building up too large of a burst-buffer with which | ||
| they can spam the network and to give a limit to how low the block height on a | ||
| `node_announcement_2` can be: nodes should not be allowed to use a block height | ||
| smaller 1440 (~ a day worth of blocks) below the current block height. |
There was a problem hiding this comment.
I'm not sure if this spam prevention works in all scenarios:
- A has a block height of 800,144 and sends B a channel_update_2 with height 800,000
- B has a block height of 800,145 and rejects the channel_update_2
There was a problem hiding this comment.
That would be a big issue if implementations defaulted on using the lowest possible block in order to keep a high update budget.
Couldn't this be resolved on the implementation side? (i.e. use a height of -143 blocks instead of -144 to avoid this race condition)
There was a problem hiding this comment.
That's a good point, a buffer of blocks could be used here to avoid this issue
There was a problem hiding this comment.
You can't do this, since you can't tell if it's old or deliberately backdated. The two weeks comes from the fact that we expire gossip messages after that time currently, anyway. You're supposed to update rebroadcast say every 13 days, which is a compromise between spamminess and proof-of-life.
There was a problem hiding this comment.
You can't do this
are you referring to the idea of the burst-buffer in general?
since you can't tell if it's old or deliberately backdated
does it matter? surely we can just say it is not old if it is the highest height that we have seen? (just like the current rules for "timestamp" used in current gossip)/
| To also prevent nodes from building up too large of a burst-buffer with which | ||
| they can spam the network and to give a limit to how low the block height on a | ||
| `node_announcement_2` can be: nodes should not be allowed to use a block height | ||
| smaller 1440 (~ a day worth of blocks) below the current block height. |
There was a problem hiding this comment.
| smaller 1440 (~ a day worth of blocks) below the current block height. | |
| smaller 144 (~ a day worth of blocks) below the current block height. |
There was a problem hiding this comment.
ah - silly me. I actually meant to say 2 weeks worth of blocks (which would be 2016). i must have confused myself here 🙃
It is also semi arbitrary. We need to look at how fast gossip tends to spread
TheBlueMatt
left a comment
There was a problem hiding this comment.
I don't think we should even consider redoing gossip unless we take the opportunity to build in the obvious trivial privacy improvements.
|
|
||
| ## Timestamp fields | ||
|
|
||
| In this document, the `timestamp` fields in messages are block heights instead |
There was a problem hiding this comment.
Then let's call them block height?
| 13. type: 6 (`bitcoin_key_1`) | ||
| 14. data: | ||
| * [`point`:`point`] | ||
| 15. type: 7 (`bitcoin_key_2`) |
There was a problem hiding this comment.
Strong NACK on including both Bitcoin keys here - we have an opportunity to get some incredibly nontrivial privacy by letting folks being outside UTXOs for channel proofs here - setting up the verification end to support that by not including both Bitcoin keys and instead just including the aggregate that's already on chain is trivial and I don't really see why we should avoid it here. We'll have to add a protocol in the future where one node can offer an alternative UTXO and signature in the signature message, but we can do that later.
There was a problem hiding this comment.
See my response to Rusty's comment above. Basically: I think we can go full-ghost mode once we do Gossip 2.0 (overcommit stuff) but before that (gossip 1.5 aka this) we should have at least some binding to the LN context. The way the proposal is currently designed, nodes can prove that the output cant be spent along the script path. Yes, perhaps we can smush the 2 bitcoin keys into one (i would just need to check that the musig verification can still work)
There was a problem hiding this comment.
we should have at least some binding to the LN context
Why? Your response to Rusty's above comment doesn't seem to explain why you think we should try to tie this to lightning more, but I don't really get it - its trivial not to, and a super great outcome if we dont bind it! In general, I'd say it should be considered an explicit goal to not "bind to the lightning context", especially given there's no additional complexity to doing so, even better it (I think?) reduces the size of the gossip!
There was a problem hiding this comment.
Yes, perhaps we can smush the 2 bitcoin keys into one (i would just need to check that the musig verification can still work)
Each key is tweaked individually and then added together, so this would require providing the tweaks for the node keys and including the bitcoin keys as one with their individual tweaks pre-applied.
If we choose to go with the taproot output key, then we'll have to deal with recursive MuSig2, which I believe we're still waiting on a security proof for. I guess we'd still have to handle recursive MuSig2 if either of the node keys are also multi-sig.
There was a problem hiding this comment.
Basically: I think we can go full-ghost mode once we do Gossip 2.0 (overcommit stuff) but before that (gossip 1.5 aka this) we should have at least some binding to the LN context. The way the proposal is currently designed, nodes can prove that the output cant be spent along the script path.
IIUC, it's important that node1 and node2 prove to each other that script path spends are impossible. But I don't see a reason we need to prove that to the rest of the network.
There was a problem hiding this comment.
it's important that node1 and node2 prove to each other that script path spends are impossible. But I don't see a reason we need to prove that to the rest of the network.
i don't think they need to prove this to eachother. They would not have generated the same output key & hence would not have produced the correct signatures if either node added a script path. They would not be able to hide such a path from the peer.
The reason for the "proving to the network" part is similar to today's reason for advertising the 2 keys: today we prove that the output can only be spent via a 2-of-2 multisig? this makes it a bit more difficult for an attacker to create fake spam since they are now limited in how they can spend the utxo since they would now have to pay more for spending from it (2 sigs). That disincentive is not available with taproot - so the idea here is that we at least show the network that we are limiting how the utxo can be spent in some way - by showing that we cant spend via a script path. But perhaps this is too "cosmetic" to consider sufficient in any case.
So i think the main thing we should iron out is: do we want to be able to prove (ie, do we care) that the utxo is created via a 2-of-2 musig2 or not. Perhaps a good topic for today's spec call
There was a problem hiding this comment.
That disincentive is not available with taproot - so the idea here is that we at least show the network that we are limiting how the utxo can be spent in some way - by showing that we cant spend via a script path. But perhaps this is too "cosmetic" to consider sufficient in any case.
The "no-script-path" limitation seems insignificant to me. I suspect most P2TR outputs today don't have a script path anyway.
So i think the main thing we should iron out is: do we want to be able to prove (ie, do we care) that the utxo is created via a 2-of-2 musig2 or not.
In the taproot world there's no fee difference between musig and single sig UTXOs. So spam prevention doesn't seem a compelling reason to prove a UTXO is a musig.
It seems to me that proof-of-UTXO is a "good enough" spam prevention. In fact, we're talking about moving to overcommit in the future, which would be a weaker spam prevention than is being proposed right here.
There was a problem hiding this comment.
yep - so I think the next version is gonna make this tweak optional. So by default, nodes will just use the output key found on chain & then if nodes want to include things like the 2 keys used in the musig2 & if they want to add a tweak then they can do so optionally.
| * [`chain_hash`:`chain_hash`] | ||
| 7. type: 3 (`short_channel_id`) | ||
| 8. data: | ||
| * [`short_channel_id`:`short_channel_id`] |
There was a problem hiding this comment.
IMO we should have an option for a channel to not include an SCID at all, rather allowing a node to overcommit their balance by simply saying "I already have channel(s) that have utxos, let me announce more without a proof up to multiplier N by not including a proof on this channel".
This would also imply that we should move the UTXO profs to the node announcements, but we don't strictly have to - it works fine without that.
We'll have to define a protocol to negotiate such an announcement, but that can happen later and is rather trivial.
There was a problem hiding this comment.
IMO we should have an option for a channel to not include an SCID at all
since it is TLV, it can always be made optional in future.
rather allowing a node to overcommit their balance
I think you are referring to the full on Gossip 2.0 proposal. This proposal is the more vanilla gossip 1.5 that was discussed in oakland.
There was a problem hiding this comment.
Why not just make it optional now? There's a bunch of complexity to adding the negotiation of building gossip with overcommit, so I wouldn't expect to actually build that now, but there's very little complexity to allowing overcommit now (with the exception of bikeshedding over the ratio 😂, but I'm open to someone rolling a die :)), so it seems like we should just do that?
There was a problem hiding this comment.
here's a bunch of complexity to adding the negotiation of building gossip with overcommit, so I wouldn't expect to actually build that now, but there's very little complexity to allowing overcommit now
Could you expand on the details a bit?
There was a problem hiding this comment.
There's two ways to do overcommit on the receiver's-side, one a trivial modification of this existing logic, the other more "clean", but a bit more work.
In the simplest version, we (a) make the bitcoin point optional, if its not provided (b) an extra bit has to be set somewhere indicating if this channel should count against the overcommit of node_1 or node_2, and (c) the short_channel_id should be greater than some number far, far into the future as an indication that its not a real channel (and to ensure receiving gossip always still works by making sure channels with utxo proofs come "before" channels without in scid-order).
Then we'd have to define some overcommit ratio (let's roll a dice or bikeshed for months), and a receiver of such a message must track the current amount of bitcoin in utxo-proven channels for each node in their graph, as well as the amount of channels which did not have a utxo proof, and if the utxo-proven channel amount is < amount of non-utxo-proven channels * the overcommit ratio the channels with the lowest (highest? whatever) fake scids are removed.
The alternative way to do this which is maybe cleaner but more of an overhaul would be to move the UTXO proofs entirely outside of the channel announcements and into the node announcements, relying exclusively on the overcommit format described above in channel announcements, and calculating against the total proven in the node announcement.
There's no need to describe the messages to actually negotiate this new format in announcement_signatures (its not complicated, we could, but if you're trying to reduce new things here its fine not to, IMO), but I think its important to actually get it on the validating/receiving end sooner rather than later.
There was a problem hiding this comment.
Then we'd have to define some overcommit ratio (let's roll a dice or bikeshed for months), and a receiver of such a message must track the current amount of bitcoin in utxo-proven channels for each node in their graph, as well as the amount of channels which did not have a utxo proof, and if the utxo-proven channel amount is < amount of non-utxo-proven channels * the overcommit ratio the channels with the lowest (highest? whatever) fake scids are removed.
Should the overcommit amount depend on bitcoin amount in proven channels, or on number of proven channels?
Chain fees scale with number of proven channels, but not necessarily with bitcoin amount in channels. So I think number of proven channels provides stronger spam protection.
(Sorry if this was discussed in Oakland or elsewhere, I'm new here.)
There was a problem hiding this comment.
IMO we should have an option for a channel to not include an SCID at all, rather allowing a node to overcommit their balance by simply saying "I already have channel(s) that have utxos, let me announce more without a proof up to multiplier N by not including a proof on this channel".
This is a somewhat unsettling proposition that I'm encountering for the first time. Has this been discussed anywhere as to why people think it's a good idea? I find it unusual that we are suggesting things that resemble leverage/fractional reserve at the protocol level in Bitcoin.
|
|
||
| A node can be assumed to understand the new gossip v2 messages if: | ||
|
|
||
| - They advertise `option_taproot_gossip` in a legacy `node_announcement` message |
| These extra requirements only apply if the `option_taproot` channel type is set | ||
| in the `open_channel` message. |
There was a problem hiding this comment.
Pretty sure everyone supports option_channel_type these days, but if either node doesn't support it then we should rely on the features shared between both nodes.
There was a problem hiding this comment.
IMO channel type becomes even more important in this scenario as one may want to still preferentially open the old segwit v0 channel with certain peers. Assuming the advertised feature bits tell the complete story would implicltly mean that the taproot chans are the new "default", which likely won't be the case for some time (eg: zero fee anchors isn't yet the default for all impls).
There was a problem hiding this comment.
Assuming the advertised feature bits tell the complete story would implicltly mean that the taproot chans are the new "default", which likely won't be the case for some time
It's also less future proof. Even if we want TR channels to be assumed default which @Roasbeef already points out is unlikely to be the case for a while, in the future we may have a new default preferred channel type as the network continues to develop and mature.
| - MUST send the `announcement_signatures_2` message. | ||
| - MUST NOT send `announcement_signatures_2` messages until `channel_ready` |
There was a problem hiding this comment.
| - MUST send the `announcement_signatures_2` message. | |
| - MUST NOT send `announcement_signatures_2` messages until `channel_ready` | |
| - MUST send the `announcement_signatures_2` message once `channel_ready` |
| 13. type: 6 (`bitcoin_key_1`) | ||
| 14. data: | ||
| * [`point`:`point`] | ||
| 15. type: 7 (`bitcoin_key_2`) |
There was a problem hiding this comment.
Yes, perhaps we can smush the 2 bitcoin keys into one (i would just need to check that the musig verification can still work)
Each key is tweaked individually and then added together, so this would require providing the tweaks for the node keys and including the bitcoin keys as one with their individual tweaks pre-applied.
If we choose to go with the taproot output key, then we'll have to deal with recursive MuSig2, which I believe we're still waiting on a security proof for. I guess we'd still have to handle recursive MuSig2 if either of the node keys are also multi-sig.
|
|
||
| ## Query Messages | ||
|
|
||
| TODO: any updates that need to happen to this section? |
There was a problem hiding this comment.
We'll likely want to extend query_channel_range and gossip_timestamp_filter with new bits to specify if we should only receive legacy, taproot, or both.
There was a problem hiding this comment.
true 👍 will work on that section once there is more consensus around the general gossip direction
| * [`chain_hash`:`chain_hash`] | ||
| 7. type: 3 (`short_channel_id`) | ||
| 8. data: | ||
| * [`short_channel_id`:`short_channel_id`] |
There was a problem hiding this comment.
Then we'd have to define some overcommit ratio (let's roll a dice or bikeshed for months), and a receiver of such a message must track the current amount of bitcoin in utxo-proven channels for each node in their graph, as well as the amount of channels which did not have a utxo proof, and if the utxo-proven channel amount is < amount of non-utxo-proven channels * the overcommit ratio the channels with the lowest (highest? whatever) fake scids are removed.
Should the overcommit amount depend on bitcoin amount in proven channels, or on number of proven channels?
Chain fees scale with number of proven channels, but not necessarily with bitcoin amount in channels. So I think number of proven channels provides stronger spam protection.
(Sorry if this was discussed in Oakland or elsewhere, I'm new here.)
| 13. type: 6 (`bitcoin_key_1`) | ||
| 14. data: | ||
| * [`point`:`point`] | ||
| 15. type: 7 (`bitcoin_key_2`) |
There was a problem hiding this comment.
Basically: I think we can go full-ghost mode once we do Gossip 2.0 (overcommit stuff) but before that (gossip 1.5 aka this) we should have at least some binding to the LN context. The way the proposal is currently designed, nodes can prove that the output cant be spent along the script path.
IIUC, it's important that node1 and node2 prove to each other that script path spends are impossible. But I don't see a reason we need to prove that to the rest of the network.
| This document aims to update the gossip protocol defined in [BOLT 7][bolt-7] to | ||
| allow for advertisement and verification of taproot channels. An entirely new | ||
| set of gossip messages are defined that use [BIP-340][bip-340] signatures and | ||
| that use a purely TLV based schema. |
There was a problem hiding this comment.
is that you now need everyone to check that compulsory fields are present. But some fields don't actually make sense as optional
Isn't this already the case for all the other TLV extensions we've added over time?
I think one scenario that optional fields can be useful is if say in the channel announcements, we allow the advertiser to include/omit information that enables verification of complete channel output binding (so the individual keys, and tweak -- which would just be the bip86 tweak if that was used).
| [BOLT 7][bolt-7] was designed around P2WSH funding transactions. For these | ||
| channels, the `channel_announcement` message is used to advertise the channel to | ||
| the rest of the network. Nodes in the network use the content of this message to | ||
| prove that the channel is sufficiently bound to the Lightning Network context |
There was a problem hiding this comment.
Explicitly mention that the LN context here meant a 2-of-2 p2wsh script? Then also the cross signing on the peer layer.
| verify taproot channels. This part of the update affects the | ||
| `announcement_signatures` and `channel_announcement` messages. | ||
|
|
||
| The opportunity is also taken to rework the `node_announcement` and |
There was a problem hiding this comment.
Yeah don't see a good reason to not just use schnorr everywhere. For node anns, this means you can actually create a composite node that's actually composed of multiple entities, either via musig2 or FROST (tho FORST integration at the channel level has some other implications re shachain).
| along with a [BIP86 tweak][bip86-tweak]. This provides a slightly weaker | ||
| binding to the LN context than legacy channels do but at least somewhat | ||
| limits how the output can be spent due to the script-path being disabled. | ||
| The context binding with legacy channels is greater because an attacker |
There was a problem hiding this comment.
Maybe more accurate to say faking a signal with the legacy protocol is more expensive due to additional on chain fees? Basically as a side effect of the keyspend path reducing on chain fees for cooperative contract paths.
|
|
||
| ### Rate Limiting | ||
|
|
||
| A block height based timestamp results in more natural rate limiting for gossip |
There was a problem hiding this comment.
Pretty cool how we can indirectly gain global rate limiting by using block hashes. I think this has a few implications for the ways channel_updates work in the network today:
- Any attempts to use
max_htlcto leak out the available bandwidth for a channel (so increase/decrease with each forward) can be rate limited at a global level. - Protocols that would directly require a node to trigger a specific channel update are now less attractive from an incentives PoV as: those updates would eat into the node's available set of global updates within a block interval.
- Nodes can still do more rapid updates by sending their new
channel_updatein an onion error directly to the sender.
Also some implementations have extensions to the gossip query protocol to support timestamp channel update syncing, which can now be updated to use block height based syncing instead.
There was a problem hiding this comment.
Any attempts to use max_htlc to leak out the available bandwidth for a channel (so increase/decrease with each forward) can be rate limited at a global level
do you mean that some nodes explicitly try to leak their own available bandwidth via the use of a channel_update message?
| These extra requirements only apply if the `option_taproot` channel type is set | ||
| in the `open_channel` message. |
There was a problem hiding this comment.
IMO channel type becomes even more important in this scenario as one may want to still preferentially open the old segwit v0 channel with certain peers. Assuming the advertised feature bits tell the complete story would implicltly mean that the taproot chans are the new "default", which likely won't be the case for some time (eg: zero fee anchors isn't yet the default for all impls).
|
|
||
| 1. `tlv_stream`: `channel_ready_tlvs` | ||
| 2. types: | ||
| 1. type: 0 (`announcement_node_pubnonce`) |
There was a problem hiding this comment.
I think it's possible to only send a single (pre aggregated nonce) here, so then the final step would be just combining 2 signatures instead of 4. IIUC, this would require nested musig2 though, which I don't think any one has actually implemented in full.
There was a problem hiding this comment.
ok cool I will need to look into nested musig2
|
|
||
| ### `channel_ready` Extensions | ||
|
|
||
| These extensions only apply if the `option_taproot` channel type was set in the |
There was a problem hiding this comment.
Should specify that these values only need to be attached if an announcement signatures message hasn't already been full constructed.
We also need to think about the restart implications here as well. Eg: lnd today will sign then stash the ann_sig message to read from disk to send to the remote party. However if each time we reconnect a new set of nonces is exchanged, then we'll need to wait for chan_reest to be sent (channel_ready isn't always sent once a channel is fully operational and has had updates), then we'll need to be ready to regen+ sign again.
There was a problem hiding this comment.
Should specify that these values only need to be attached if an announcement signatures message hasn't already been full constructed.
What do you mean? When would one be in a situation where the announcment sig message is fully constructed but you then need to send channel_ready again?
There was a problem hiding this comment.
then we'll need to wait for chan_reest to be sent (channel_ready isn't always sent once a channel is fully operational and has had updates), then we'll need to be ready to regen+ sign again.
Ok, so you are saying we might need to add these fields to chan_reest as-well?
| two nonces. The `announcement_node_nonce` is for `node_ID_x` and the | ||
| `announcement_bitcoin_nonce` is for `bitcoin_key_x`. | ||
|
|
||
| Since the channel can only be announced once the `channel_ready` messages have |
There was a problem hiding this comment.
See comment above: channel_ready isn't always sent on reconnect. So if a channel is used before the gossip advertisement is finished, then the nonces won't be available to advertise.
| * [`point`:`node_id`] | ||
| 9. type: 4 (`color`) | ||
| 10. data: | ||
| * [`rgb_color`:`rgb_color`] |
There was a problem hiding this comment.
Maybe remove the color field? Don't think it was ever seriously used....
On the other hand, if we go TLV everywhere, then it matters less as including it is optional.
There was a problem hiding this comment.
i've made it an odd number so it is optional :)
4d9883a to
534af57
Compare
There was a problem hiding this comment.
Thanks for the initial review everyone!
Made some of the more minor updates. I'm gonna wait until after the spec meeting in NYC before making any changes regarding the channel proofs.
Here is a small list of things that need to be answered:
- do we want to go full TLV or does that just not make sense?
- should we use recursive musig2 for the announcement sigs or leave it as a 4-or-4 for now with perhaps leaving enough wiggle room to upgrade to recursive musig2 in future.
- are we ok with only announcing the SCID (and hence just the taproot-output-key) or do we want to at least give nodes the option of adding the
bitcoin_key_1/2andtap-tweakto the channel announcement. - can we assume dynamic commitments will be in place to upgrade legacy channels to taproot channels which will then be able to use the new gossip messages (in other words, does everyone agree that the new gossip messages should not support advertising legacy channels)?
| This document aims to update the gossip protocol defined in [BOLT 7][bolt-7] to | ||
| allow for advertisement and verification of taproot channels. An entirely new | ||
| set of gossip messages are defined that use [BIP-340][bip-340] signatures and | ||
| that use a purely TLV based schema. |
There was a problem hiding this comment.
Isn't this already the case for all the other TLV extensions we've added over time?
Yeah plus one for this question. If we later add compulsory fields, they would be via TLV and there would be some feature bit associated with understanding the version of the message that includes this field. So the benefit of doing only TLV is that all mandatory fields (ones added now and ones we add later on) are checked in the same way.
| For legacy channels, these last two proofs are made possible by including four | ||
| separate signatures in the `channel_announcement`. However, [BIP-340][bip-340] | ||
| signatures and the MuSig2 protocol allow us to now aggregate these four | ||
| signatures into a single one. Verifiers will then be able to aggregate the four | ||
| keys (`bitcoin_key_1`, `bitcoin_key_2`, `node_ID_1` and `node_ID_2`) using | ||
| MuSig2 key aggregation and then they can do a single signature verification | ||
| check instead of four individual checks. |
There was a problem hiding this comment.
It allows for us to change to a different Taproot scheme in future if we wanted
Could you perhaps give an example? Do you mean like: we could possibly use the same gossip for a future channel factory or something in which case the internal key itself would be derived in a different way? (ie, something other than a 2-of-2 multisig)
If that is the case, then how about we make the "binding level" optional. Ie, we make the bitcoin_key_1, bitcoin_key_2 and tapteak fields optional and then if they are present, nodes can choose to be more strict with their verification or not.
|
|
||
| ### Rate Limiting | ||
|
|
||
| A block height based timestamp results in more natural rate limiting for gossip |
There was a problem hiding this comment.
Any attempts to use max_htlc to leak out the available bandwidth for a channel (so increase/decrease with each forward) can be rate limited at a global level
do you mean that some nodes explicitly try to leak their own available bandwidth via the use of a channel_update message?
| To also prevent nodes from building up too large of a burst-buffer with which | ||
| they can spam the network and to give a limit to how low the block height on a | ||
| `node_announcement_2` can be: nodes should not be allowed to use a block height | ||
| smaller 1440 (~ a day worth of blocks) below the current block height. |
There was a problem hiding this comment.
You can't do this
are you referring to the idea of the burst-buffer in general?
since you can't tell if it's old or deliberately backdated
does it matter? surely we can just say it is not old if it is the highest height that we have seen? (just like the current rules for "timestamp" used in current gossip)/
| - Nodes are encouraged to actively connect to other nodes that advertise the | ||
| `option_taproot_gossip` feature bit as this is the only way in which they | ||
| will learn about taproot channel announcements and updates. | ||
| - Nodes should not use the new `node_announcement_2` message until they have |
There was a problem hiding this comment.
If they don't use node_announcement_2 at all, then none of their taproot channels will propagate.
Why not? they can still send out channel_announcement_2 . and their (legacy) node_announcement will have the feature bit in it that informs nodes that they support taproot chans which hopefully encourages those nodes to connect to them so that their channel_announcement_2 messages will propogate.
What's the rationale here?
The main reason was so that legacy nodes continue to get updates about the node while they have a channel (legacy) that mean something to the legacy node.
|
|
||
| ## Query Messages | ||
|
|
||
| TODO: any updates that need to happen to this section? |
There was a problem hiding this comment.
true 👍 will work on that section once there is more consensus around the general gossip direction
| * [`point`:`node_id`] | ||
| 9. type: 4 (`color`) | ||
| 10. data: | ||
| * [`rgb_color`:`rgb_color`] |
There was a problem hiding this comment.
i've made it an odd number so it is optional :)
| This document aims to update the gossip protocol defined in [BOLT 7][bolt-7] to | ||
| allow for advertisement and verification of taproot channels. An entirely new | ||
| set of gossip messages are defined that use [BIP-340][bip-340] signatures and | ||
| that use a purely TLV based schema. |
There was a problem hiding this comment.
I like some of the lessons from protobufs: the message gets defined completely separately from the business logic (ie the validation checking if all the wanted fields are there) and then it is always possible to add more fields or remove any fields.
| This document aims to update the gossip protocol defined in [BOLT 7][bolt-7] to | ||
| allow for advertisement and verification of taproot channels. An entirely new | ||
| set of gossip messages are defined that use [BIP-340][bip-340] signatures and | ||
| that use a purely TLV based schema. |
There was a problem hiding this comment.
Perhaps worth a quick discussion at the spec meeting.
|
|
||
| 1. `tlv_stream`: `channel_ready_tlvs` | ||
| 2. types: | ||
| 1. type: 0 (`announcement_node_pubnonce`) |
There was a problem hiding this comment.
ok cool I will need to look into nested musig2
|
note from @rustyrussell - would be good to support legacy updates in the new messages in order to take advantage of the new |
|
Hey everyone! Was planning on having this doc updated by today but got side tracked a bit. Will aim to have the updated changes pushed by the time of the next bi-monthly meeting. In the meantime, here is a summary of what I plan to update as a result of the discussions from the NYC meeting. Let me know if something looks off. 1. Plan for a future where the script can be anythingInstead of requiring the channel peers to specify the two bitcoin keys in the So to cater for this future, we can say that
For the signers, this would mean the following:
The verifier will be able to verify both types from the get go. 2. Plan for a future where not every channel announcement contains UTXO proofWe want to allow the flexibility so that in future we dont need to tie every channel to a UTXO but instead use the rule of "here is a channel without a proof, please look at all the other open channels I have announced with a proof and use that to determine if I do infact have the allowance to open one without" What I took away from the meeting is that to create a sort of carve-out for that future, what we will do today is to start putting the channel capacity in the Let me know if I missed something here. 3. Message structuresNew type definitions:
|
| derived by aggregating all the `node_ID` and `bitcoin_key` public keys. The | ||
| signature for this key will thus be created by aggregating (via MuSig2) four | ||
| partial signatures. One for each of the keys: `node_ID_1`, `node_ID_2`, | ||
| `bitcoin_key_1` and `bitcoin_key_2`. A nonce will need to be generated and |
There was a problem hiding this comment.
| `bitcoin_key_1` and `bitcoin_key_2`. A nonce will need to be generated and | |
| `bitcoin_key_1` and `bitcoin_key_2`. A (MuSig2) nonce will need to be generated and |
| been exchanged and since it is generally preferred to keep nonce exchanges as | ||
| Just In Time as possible, the nonces are exchanged via the `channel_ready` |
There was a problem hiding this comment.
Can we include a citation for the Just In Time preference? Reading BIP327, it seems to suggest in bullet 3 that it doesn't really matter how early you exchange them since it is valid to do so even before the exact signing participants have been determined.
| - otherwise: | ||
| - MUST NOT send the `announcement_signatures_2` message. |
There was a problem hiding this comment.
Isn't this message constructable before the 6conf requirement? If we send the announcement_signatures_2 message after channel_ready but before 6 confs, how should the peer respond?
There was a problem hiding this comment.
good point.
I took the original logic from the legacy announcement_signatures. But yeah - perhaps it is possible to construct it sooner as long as it isnt broadcast before 6 confs
- Fix node_announcement_2_tlvs schema ordering so tools/extract-formats.py
parses it (each type immediately followed by its data); tighten
[type:name] whitespace.
- Rename two stragglers: channel_announcement_v2 -> channel_announcement_2
and announcement_signatures_v2 -> announcement_signatures_2 (only the
feature/option name keeps the v2).
- Spell out MsgHash("channel_update_2", "signature", m) in the
channel_update_2 signature requirement, and note that the MsgHash
tagged-hash format matches BOLT 12.
- Use truncated integer types (tu64/tu32) for capacity_satoshis,
htlc_minimum_msat, htlc_maximum_msat, fee_base_msat and
fee_proportional_millionths to save bytes.
- Fix typo: node_2's "will know" list now references node_ID_2 (not 1).
- Update MuSig2 spec references from the Jonas Nick draft to the final
BIP327 location.
h/t @rustyrussell
h/t @MPins
…tname - Remove the "SHOULD set at least one of types 7-10" sender rule from node_announcement_2; it duplicates the more specific SHOULD on the next line that already lists each address type by name. - Rename `hostname` to `dns_hostname` in the receiver's port-0 rule so it matches the field name used everywhere else in the section. h/t @rustyrussell
The existing spec said "message: byte array" without defining what that byte sequence is, leaving room for implementations to disagree on what exactly is signed by every channel/node/update signature in this BOLT. Spell it out: the canonical concatenation of every TLV record whose type falls in the signed range (0..=159 and 1e9..=3e9-1), serialised `<bigsize type><bigsize length><value>` in strictly ascending type order, with no outer length prefix, no message-type prefix, and no contribution from TLVs that are absent from the wire (even when a default is defined). Test vectors in Appendix B are still TODO and remain the canonical interop check. h/t @t-bast h/t @rustyrussell
Port Rusty's "clarify receiver requirements" changes: - Replace the "MUST verify integrity AND authenticity" anti-pattern in the channel_announcement_2 reader with an explicit presence check up front (short_channel_id, outpoint, capacity_satoshis, node_id_1, node_id_2, signature) plus concrete warning/close/ignore actions if the signature is invalid. - Add the same presence check to the channel_update_2 reader (short_channel_id, block_height, signature). - Extend the node_announcement_2 reader's presence check to include type 160 (signature) alongside features/block_height/node_id. - Standardise on "MUST ignore the message" everywhere; drop the legacy "MUST NOT process the message further" wording. - Refer to TLV fields by name as well as number in sender/receiver rules (e.g. "type 0 (features)") so the spec stays readable when types are renumbered later. - Bump the channel-forget delay from 12 to 72 blocks to match BOLT 7. - Add tor_v3_address to the port-not-zero rules for node_announcement_2 in both sender and receiver. h/t @rustyrussell
….239 BOLT 12 has long since updated where its signature TLVs live and what counts as the signed TLV range. Align this BOLT with that: - Signed TLV range now 0..=239 (was 0..=159). - Signature TLV moves from type 160 to type 240 in `channel_announcement_2`, `node_announcement_2` and `channel_update_2`. h/t @rustyrussell
…list Port Rusty's rewrite of the channel_announcement_2 reader requirements. The previous text scattered the validation rules between the receiver section and a long "Verifying the channel_announcement_2 signature" appendix split into 3-of-3 and 4-of-4 sub-cases. Implementers asked repeatedly for a straight-line checklist, so: - Replace the receiver block with a linear sequence of checks: UTXO lookup -> output amount >= capacity_satoshis -> short_channel_id and outpoint both match the output -> channel announcement validation. - Add a "Channel announcement validation" sub-section right after the receiver block that walks the scriptpubkey shape (P2WSH vs P2TR), bitcoin-key presence, MuSig2 aggregation and signature verification end-to-end. - Delete the entire "Verifying the channel_announcement_2 signature" appendix; everything it said is now in the new sub-section. - The new section also tightens semantics: it is now an explicit validation failure when only one of bitcoin_key_1/bitcoin_key_2 is present, and the P2WSH script form uses BOLT 3 sorted keys (lesser before greater). - TapTweak is now expressed using BOLT 12's tagged-hash function `H` rather than BIP340's `hash_TapTweak`/`hash_name(x)` naming. h/t @rustyrussell
…te_2 wire encodings
Two encoding tightenings from review:
- gossip_timestamp_filter (BOLT 7): the previously-split
`first_block` (type 2) and `block_height_range` (type 4) TLVs are
always set together. Collapse them into a single TLV at type 2
(`block_height_range`) carrying `{u32 first_block_height, tu32
num_blocks}`. Saves a TLV header and removes the "type 4 without
type 2" malformed case.
- channel_update_2.short_channel_id: switch the field type from
`short_channel_id` to `sciddir_or_pubkey` (constrained to the
`sciddir` form), reusing BOLT 1's existing 9-byte
`<dirbyte><scid>` encoding. The direction byte fully captures the
"which side of the channel sent this" information that the
separate type-8 `second_peer` flag used to encode, so the
`second_peer` TLV is removed. Sender/receiver requirements are
updated to set/check the direction byte and use it to pick which
`node_id` to verify the signature against.
h/t @t-bast
h/t @rustyrussell
The receiver requirement and field description already required the sciddir form of sciddir_or_pubkey for channel_update_2's short_channel_id, but the sender requirements only set the direction byte without first saying the form was forced. State it explicitly so a writer of the spec text doesn't need to infer it from the dirbyte rule. h/t @rustyrussell
Per TheBlueMatt's review, channel_update_2 should advertise inbound fees while we still have the freedom to choose a clean encoding. New gossip lets us make them positive-only (no negative-fee discount support), which keeps both the wire format and the routing logic simple. Two new TLVs are added to channel_update_2: - type 20: `inbound_fee_base_msat` (tu32, default 0) - type 22: `inbound_fee_proportional_millionths` (tu32, default 0) A surcharge that the forwarding node adds for HTLCs that arrived on this channel, regardless of the outgoing channel. The total fee a sender computes for a `in -> out` hop is the sum of the outbound fee on `out` and the inbound fee on `in`. h/t @TheBlueMatt
Same 32-byte wire encoding, just reuse BOLT 1's named `sha256` type instead of the anonymous `32*byte` so the schema reads consistently alongside the other 32-byte fields in this message (txid, etc.). h/t @rustyrussell
t-bast and rusty pushed back on the modified MuSig2 used by
announcement_signatures_2: the per-key signing is already vanilla
MuSig2, but the sender was pre-aggregating its two partial sigs
(node + bitcoin) into a single 32-byte value, which forced a
non-standard partial-signature verification routine on the receiver.
A few-bytes saving on a small, rarely-exchanged message wasn't worth
maintaining a divergent MuSig2 interface.
Switch to the vanilla 4-of-4 layout:
- announcement_signatures_2.partial_signatures (type 4) is now a
64-byte TLV carrying both partial sigs side by side:
`[partial_signature:node_partial_signature][partial_signature:bitcoin_partial_signature]`.
- The Partial Signature Calculation appendix no longer aggregates the
two partial sigs before transmission; each node sends its two raw
MuSig2 partial signatures.
- The Partial Signature Verification appendix is replaced by a thin
wrapper around the standard `MuSig2.PartialSigVerify` routine
applied once per partial signature.
- The final BIP340 signature in channel_announcement_2 is now an
ordinary `MuSig2.PartialSigAgg` over all four partial signatures
once both `announcement_signatures_2` messages have been exchanged.
Also fix two stale references in the same area: the message to be
signed is `MsgHash("channel_announcement_2", "signature", m)` (the
old text dropped the `_2` suffix), and `m` is the canonical
signed-range TLV byte sequence defined in "Pure TLV messages", not
just "the serialisation of the message tlv stream".
h/t @t-bast
h/t @rustyrussell
The original draft tied the whole announcement-signing flow to channel_ready: nonces were exchanged in channel_ready, and on reconnection channel_ready was re-sent to restart the signing. That works for the initial funding transaction only -- it has no way to re-announce a spliced channel under its new funding tx, and conflates "channel is open" with "please redo announcement". Restructure the announcement-signing trigger to be funding-tx-aware: - Define splice_locked_tlvs carrying the same announcement_node_pubnonce and announcement_bitcoin_pubnonce TLVs as channel_ready_tlvs. After a splice reaches acceptable depth, both peers exchange splice_locked with these nonces and then run announcement_signatures_2 against the new funding tx. - Extend channel_reestablish_tlvs with a new announcement_nonces TLV (type 7) carrying the two 66-byte nonces, and allocate bit 1 of my_current_funding_locked.retransmit_flags to mean "retransmit announcement_signatures_2 for my_current_funding_locked_txid". On reconnection, a node that still needs the peer's announcement_signatures_2 (initial open or any splice) sets bit 1 and includes fresh nonces. channel_ready is no longer re-sent to retrigger announcement signing. - Add a funding_txid TLV (type 6) to announcement_signatures_2 so the message names its funding transaction explicitly rather than by short_channel_id alone. For splices where multiple candidate funding txs may have existed at different points this is the unambiguous binding. - Tighten the announcement_signatures_2 sender and recipient rules to reference funding_txid throughout, and to use the new channel_reestablish flow on reconnect rather than channel_ready retransmission. h/t @t-bast
The MsgHash definition under "Signature Message Construction" claimed to be the same tagged-hash format as BOLT 12 (and was meant to be the standard BIP340 tagged hash applied to the signed-range TLV bytes), but the literal formula wrapped the message in an extra inner SHA256: SHA256(SHA256(tag) || SHA256(tag) || SHA256(message)) That's not what BIP340 or BOLT 12 define, and no implementation constructs the hash that way. BOLT 12 §"Signature Calculation" defines H(tag, msg) as SHA256(SHA256(tag) || SHA256(tag) || msg) with no inner pre-hash, and BIP340's tagged-hash form is the same. Drop the inner SHA256 around `message` so the formula actually matches the standard. h/t @t-bast h/t @rustyrussell
The Rate Limiting rationale described an unbounded backdate window: the lowest allowed `block_height` was just the per-message anchor (the channel funding block for `channel_update_2`, or the oldest channel's funding block for `node_announcement_2`). A node whose anchor sat far in the past -- e.g. a channel funded months ago that has been quiet -- could legally emit one update per intervening block, undermining the one-message-per-block rate-limit story. In practice peers would drop those messages anyway via the legacy gossip staleness window, but the spec didn't say so, leaving room for implementations to disagree on what is acceptable to send or relay. Tighten the rule by giving the backdate range an explicit lower bound: - Define `max_backdate_blocks = 2016` (approximately two weeks at the Bitcoin block interval of ten minutes) in the Rate Limiting rationale, with a note that the value matches the staleness window used for legacy gossip in BOLT 7. - Scope the rationale to `channel_update_2` and `node_announcement_2` explicitly. `channel_announcement_2`'s blockheight is tied to its on-chain funding tx and not sender-chosen, so it is out of scope. - Add a sender-side `MUST NOT` to both messages refusing `block_height < current_block_height - max_backdate_blocks`, and a matching receiver-side `SHOULD` ignore when this is violated so the cap is enforced end-to-end rather than relying on relay/pruning policy alone. No change for `channel_announcement_2`. h/t @jharveyb
dda5bee to
4eef3df
Compare
|
rebased & addressed all recent comments! thanks yall 🙏 |
…proot-gossip The branch behind this PR pulls the lnwire gossip v2 messages in line with the review-driven updates on the BOLT taproot-gossip extension (lightning/bolts#1059). Record the change in the 0.22.0 release notes under "BOLT Spec Updates" so the PR check is satisfied and downstream implementors get a heads-up about the wire-format shifts.
| the node charges for forwarding an HTLC that *arrived* on this channel, | ||
| regardless of which channel it is forwarded out via. This fee is positive | ||
| only (`tu32`), meaning a node MAY surcharge for receiving HTLCs over the | ||
| channel but MUST NOT advertise a discount. |
There was a problem hiding this comment.
I'm not sure "MUST NOT advertise a discount" makes sense here - its not just MUST NOT its "can not" because there is simply no way to encode it at all.
|
Is there a way to avoid claiming three feature bits? |
| - validation fails | ||
| - otherwise (P2TR): | ||
| - Let P_internal = KeyAgg(MuSig2.KeySort(`bitcoin_key_1`, `bitcoin_key_2`)) | ||
| - if `merkle_root_hash` is not present: | ||
| - if `taproot_key` != P_internal: | ||
| - validation fails | ||
| - otherwise: | ||
| - let `p` = `bytes(P_internal)` | ||
| - let `t = H("TapTweak", p || merkle_root_hash)` where `H` is the BIP340 tagged hash function defined in [BOLT #12][bolt-12] | ||
| - if `taproot_key != P_internal + t*G`: | ||
| - validation fails | ||
| - Let P_agg = MuSig2.KeyAgg(MuSig2.KeySort(`node_id_1`, `node_id_2`, `bitcoin_key_1`, `bitcoin_key_2`)) | ||
| - otherwise (not both bitcoin_key fields): | ||
| - if either `bitcoin_key_1` or `bitcoin_key_2` are present: | ||
| - validation fails | ||
| - Let P_agg = MuSig2.KeyAgg(MuSig2.KeySort(`node_id_1`, `node_id_2`, taproot_key)) |
There was a problem hiding this comment.
I may be missing context but I do not understand why allow the option of specifying bitcoin_key_1/2 but no merkle_root_hash in the case of a P2TR? For how simple taproot channels are constructed, the merkle_root_hash will need to be present and if this is some construct outside of simple taproot channels, then the bitcoin keys can be omitted and use the public key in the taproot output directly.
| * `bip340sig`: a 64-byte bitcoin Elliptic Curve Schnorr signature as | ||
| per [BIP-340][bip-340]. | ||
| * `partial_signature`: a 32-byte partial MuSig2 signature as defined | ||
| in [BIP-MuSig2][bip-musig2]. | ||
| * `public_nonce`: a 66-byte public nonce as defined in [BIP-MuSig2][bip-musig2]. | ||
| * `utf8`: a byte as part of a UTF-8 string. A writer MUST ensure an array of | ||
| these is a valid UTF-8 string, a reader MAY reject any messages containing an | ||
| array of these which is not a valid UTF-8 string. |
There was a problem hiding this comment.
do bip340sig and utf8 need to be specified here given that they are already in bolt-01?
| - `node_2` will know: | ||
| - `bitcoin_priv_key_2`, `node_ID_priv_key_2`, | ||
| - `bitcoin_key_1`, | ||
| - `node_ID_2`, |
There was a problem hiding this comment.
similar from another comment above but shouldn't this be node_ID_1? and for node_1 above it should be node_ID_2 since this to specify that the node knows the others public key.
| - Let `signing_node_id` be `node_id_1` if the `short_channel_id` direction | ||
| byte is `0`, and `node_id_2` otherwise. | ||
| - If the channel-id portion of `short_channel_id` does NOT match a previous | ||
| `channel_announcement_2` or `channel_announcement`, OR if the channel has |
There was a problem hiding this comment.
I don't think this should have channel_announcement since as mentioned above they are to be treated separate.
|
Hey everyone - sad to say i'm leaving the bitcoin/lightning space for now. So I wont be working on this any further. |
|
Hi everyone, just to let you know that from Lightning Labs side, I'll be taking over the Gossip 1.75 project. |
Overview
The initial version of the Lightning Network gossip protocol as defined in
BOLT 7 was designed around P2WSH funding transactions. For these
channels, the
channel_announcementmessage is used to advertise thechannel to the rest of the network. Nodes in the network use the content
of this message to prove that the channel is sufficiently bound to the
Lightning Network context and that it is owned by the nodes advertising
the channel. This proof and verification protocol is, however, not
compatible with SegWit V1 (P2TR) outputs and so cannot be used to
advertise the channels defined in the Simple Taproot Channel proposal.
This document thus aims to define an updated gossip protocol that will
allow nodes to both advertise and verify taproot channels. This part of the
update affects the
announcement_signaturesandchannel_announcementmessages.The opportunity is also taken to rework the
node_announcementandchannel_updatemessages to take advantage of BIP-340 signatures andTLV fields. Timestamp fields are also updated to be block heights instead of
Unix timestamps.