From c109d5e7223c1fce4d34e1ea202314d896adbe32 Mon Sep 17 00:00:00 2001 From: ThomasV Date: Sat, 7 Jan 2023 12:20:03 +0100 Subject: [PATCH] lnwire: update csv files with recent BOLTs Note: there are no more optional fields in msgdata, per https://github.com/lightning/bolts/commit/f068dd0d8dfa5ae75feedd99f269e23be4777381 --- electrum/lnonion.py | 4 +-- electrum/lnpeer.py | 21 ++++++++------- electrum/lnwire/README.md | 4 ++- electrum/lnwire/onion_wire.csv | 47 +++++++++++++++++++--------------- electrum/lnwire/peer_wire.csv | 27 +++++++++++-------- electrum/lnworker.py | 2 +- electrum/tests/test_lnmsg.py | 29 --------------------- 7 files changed, 60 insertions(+), 74 deletions(-) diff --git a/electrum/lnonion.py b/electrum/lnonion.py index cbf7ca2fd..8b353aeb8 100644 --- a/electrum/lnonion.py +++ b/electrum/lnonion.py @@ -122,7 +122,7 @@ class OnionHopsDataSingle: # called HopData in lnd else: # tlv payload_fd = io.BytesIO() OnionWireSerializer.write_tlv_stream(fd=payload_fd, - tlv_stream_name="tlv_payload", + tlv_stream_name="payload", **self.payload) payload_bytes = payload_fd.getvalue() with io.BytesIO() as fd: @@ -157,7 +157,7 @@ class OnionHopsDataSingle: # called HopData in lnd raise Exception(f"unexpected EOF") ret = OnionHopsDataSingle(is_tlv_payload=True) ret.payload = OnionWireSerializer.read_tlv_stream(fd=io.BytesIO(hop_payload), - tlv_stream_name="tlv_payload") + tlv_stream_name="payload") ret.hmac = fd.read(PER_HOP_HMAC_SIZE) assert len(ret.hmac) == PER_HOP_HMAC_SIZE return ret diff --git a/electrum/lnpeer.py b/electrum/lnpeer.py index f83db1ba5..273626295 100644 --- a/electrum/lnpeer.py +++ b/electrum/lnpeer.py @@ -552,7 +552,7 @@ class Peer(Logger): def on_reply_channel_range(self, payload): first = payload['first_blocknum'] num = payload['number_of_blocks'] - complete = bool(int.from_bytes(payload['complete'], 'big')) + complete = bool(int.from_bytes(payload['sync_complete'], 'big')) encoded = payload['encoded_short_ids'] ids = self.decode_short_ids(encoded) #self.logger.info(f"on_reply_channel_range. >>> first_block {first}, num_blocks {num}, num_ids {len(ids)}, complete {repr(payload['complete'])}") @@ -1273,7 +1273,7 @@ class Peer(Logger): chan.peer_state = PeerState.GOOD if chan.is_funded() and their_next_local_ctn == next_local_ctn == 1: - self.send_funding_locked(chan) + self.send_channel_ready(chan) # checks done if chan.is_funded() and chan.config[LOCAL].funding_locked_received: self.mark_open(chan) @@ -1282,20 +1282,23 @@ class Peer(Logger): if chan.get_state() == ChannelState.SHUTDOWN: await self.send_shutdown(chan) - def send_funding_locked(self, chan: Channel): + def send_channel_ready(self, chan: Channel): channel_id = chan.channel_id per_commitment_secret_index = RevocationStore.START_INDEX - 1 - per_commitment_point_second = secret_to_pubkey(int.from_bytes( + second_per_commitment_point = secret_to_pubkey(int.from_bytes( get_per_commitment_secret_from_seed(chan.config[LOCAL].per_commitment_secret_seed, per_commitment_secret_index), 'big')) - # note: if funding_locked was not yet received, we might send it multiple times - self.send_message("funding_locked", channel_id=channel_id, next_per_commitment_point=per_commitment_point_second) + # note: if 'channel_ready' was not yet received, we might send it multiple times + self.send_message( + "channel_ready", + channel_id=channel_id, + second_per_commitment_point=second_per_commitment_point) if chan.is_funded() and chan.config[LOCAL].funding_locked_received: self.mark_open(chan) - def on_funding_locked(self, chan: Channel, payload): - self.logger.info(f"on_funding_locked. channel: {bh2u(chan.channel_id)}") + def on_channel_ready(self, chan: Channel, payload): + self.logger.info(f"on_channel_ready. channel: {bh2u(chan.channel_id)}") if not chan.config[LOCAL].funding_locked_received: - their_next_point = payload["next_per_commitment_point"] + their_next_point = payload["second_per_commitment_point"] chan.config[REMOTE].next_per_commitment_point = their_next_point chan.config[LOCAL].funding_locked_received = True self.lnworker.save_channel(chan) diff --git a/electrum/lnwire/README.md b/electrum/lnwire/README.md index 72fd48f37..2d9ef69c0 100644 --- a/electrum/lnwire/README.md +++ b/electrum/lnwire/README.md @@ -1,5 +1,7 @@ -These files are generated from the BOLT repository: +These files have been generated from the BOLT repository: ``` $ python3 tools/extract-formats.py 01-*.md 02-*.md 07-*.md > peer_wire.csv $ python3 tools/extract-formats.py 04-*.md > onion_wire.csv ``` + +Note: Trampoline messages were added manually to onion_wire.csv diff --git a/electrum/lnwire/onion_wire.csv b/electrum/lnwire/onion_wire.csv index 3001f3f62..07b10cdd8 100644 --- a/electrum/lnwire/onion_wire.csv +++ b/electrum/lnwire/onion_wire.csv @@ -1,23 +1,25 @@ -tlvtype,tlv_payload,amt_to_forward,2 -tlvdata,tlv_payload,amt_to_forward,amt_to_forward,tu64, -tlvtype,tlv_payload,outgoing_cltv_value,4 -tlvdata,tlv_payload,outgoing_cltv_value,outgoing_cltv_value,tu32, -tlvtype,tlv_payload,short_channel_id,6 -tlvdata,tlv_payload,short_channel_id,short_channel_id,short_channel_id, -tlvtype,tlv_payload,payment_data,8 -tlvdata,tlv_payload,payment_data,payment_secret,byte,32 -tlvdata,tlv_payload,payment_data,total_msat,tu64, -tlvtype,tlv_payload,invoice_features,66097 -tlvdata,tlv_payload,invoice_features,invoice_features,u64, -tlvtype,tlv_payload,outgoing_node_id,66098 -tlvdata,tlv_payload,outgoing_node_id,outgoing_node_id,byte,33 -tlvtype,tlv_payload,invoice_routing_info,66099 -tlvdata,tlv_payload,invoice_routing_info,invoice_routing_info,byte,... -tlvtype,tlv_payload,trampoline_onion_packet,66100 -tlvdata,tlv_payload,trampoline_onion_packet,version,byte,1 -tlvdata,tlv_payload,trampoline_onion_packet,public_key,byte,33 -tlvdata,tlv_payload,trampoline_onion_packet,hops_data,byte,400 -tlvdata,tlv_payload,trampoline_onion_packet,hmac,byte,32 +tlvtype,payload,amt_to_forward,2 +tlvdata,payload,amt_to_forward,amt_to_forward,tu64, +tlvtype,payload,outgoing_cltv_value,4 +tlvdata,payload,outgoing_cltv_value,outgoing_cltv_value,tu32, +tlvtype,payload,short_channel_id,6 +tlvdata,payload,short_channel_id,short_channel_id,short_channel_id, +tlvtype,payload,payment_data,8 +tlvdata,payload,payment_data,payment_secret,byte,32 +tlvdata,payload,payment_data,total_msat,tu64, +tlvtype,payload,payment_metadata,16 +tlvdata,payload,payment_metadata,payment_metadata,byte,... +tlvtype,payload,invoice_features,66097 +tlvdata,payload,invoice_features,invoice_features,u64, +tlvtype,payload,outgoing_node_id,66098 +tlvdata,payload,outgoing_node_id,outgoing_node_id,byte,33 +tlvtype,payload,invoice_routing_info,66099 +tlvdata,payload,invoice_routing_info,invoice_routing_info,byte,... +tlvtype,payload,trampoline_onion_packet,66100 +tlvdata,payload,trampoline_onion_packet,version,byte,1 +tlvdata,payload,trampoline_onion_packet,public_key,byte,33 +tlvdata,payload,trampoline_onion_packet,hops_data,byte,400 +tlvdata,payload,trampoline_onion_packet,hmac,byte,32 msgtype,invalid_realm,PERM|1 msgtype,temporary_node_failure,NODE|2 msgtype,permanent_node_failure,PERM|NODE|2 @@ -57,8 +59,11 @@ msgdata,final_incorrect_cltv_expiry,cltv_expiry,u32, msgtype,final_incorrect_htlc_amount,19 msgdata,final_incorrect_htlc_amount,incoming_htlc_amt,u64, msgtype,channel_disabled,UPDATE|20 +msgdata,channel_disabled,disabled_flags,u16, +msgdata,channel_disabled,len,u16, +msgdata,channel_disabled,channel_update,byte,len msgtype,expiry_too_far,21 msgtype,invalid_onion_payload,PERM|22 -msgdata,invalid_onion_payload,type,varint, +msgdata,invalid_onion_payload,type,bigsize, msgdata,invalid_onion_payload,offset,u16, msgtype,mpp_timeout,23 diff --git a/electrum/lnwire/peer_wire.csv b/electrum/lnwire/peer_wire.csv index 87bd89f77..b4018f0fc 100644 --- a/electrum/lnwire/peer_wire.csv +++ b/electrum/lnwire/peer_wire.csv @@ -6,6 +6,8 @@ msgdata,init,features,byte,flen msgdata,init,tlvs,init_tlvs, tlvtype,init_tlvs,networks,1 tlvdata,init_tlvs,networks,chains,chain_hash,... +tlvtype,init_tlvs,remote_addr,3 +tlvdata,init_tlvs,remote_addr,data,byte,... msgtype,error,17 msgdata,error,channel_id,channel_id, msgdata,error,len,u16, @@ -87,9 +89,12 @@ msgdata,funding_created,signature,signature, msgtype,funding_signed,35 msgdata,funding_signed,channel_id,channel_id, msgdata,funding_signed,signature,signature, -msgtype,funding_locked,36 -msgdata,funding_locked,channel_id,channel_id, -msgdata,funding_locked,next_per_commitment_point,point, +msgtype,channel_ready,36 +msgdata,channel_ready,channel_id,channel_id, +msgdata,channel_ready,second_per_commitment_point,point, +msgdata,channel_ready,tlvs,channel_ready_tlvs, +tlvtype,channel_ready_tlvs,short_channel_id,1 +tlvdata,channel_ready_tlvs,short_channel_id,alias,short_channel_id, msgtype,shutdown,38 msgdata,shutdown,channel_id,channel_id, msgdata,shutdown,len,u16, @@ -139,8 +144,8 @@ msgtype,channel_reestablish,136 msgdata,channel_reestablish,channel_id,channel_id, msgdata,channel_reestablish,next_commitment_number,u64, msgdata,channel_reestablish,next_revocation_number,u64, -msgdata,channel_reestablish,your_last_per_commitment_secret,byte,32,option_data_loss_protect,option_static_remotekey -msgdata,channel_reestablish,my_current_per_commitment_point,point,,option_data_loss_protect,option_static_remotekey +msgdata,channel_reestablish,your_last_per_commitment_secret,byte,32 +msgdata,channel_reestablish,my_current_per_commitment_point,point, msgtype,announcement_signatures,259 msgdata,announcement_signatures,channel_id,channel_id, msgdata,announcement_signatures,short_channel_id,short_channel_id, @@ -180,35 +185,35 @@ msgdata,channel_update,cltv_expiry_delta,u16, msgdata,channel_update,htlc_minimum_msat,u64, msgdata,channel_update,fee_base_msat,u32, msgdata,channel_update,fee_proportional_millionths,u32, -msgdata,channel_update,htlc_maximum_msat,u64,,option_channel_htlc_max +msgdata,channel_update,htlc_maximum_msat,u64, msgtype,query_short_channel_ids,261,gossip_queries msgdata,query_short_channel_ids,chain_hash,chain_hash, msgdata,query_short_channel_ids,len,u16, msgdata,query_short_channel_ids,encoded_short_ids,byte,len msgdata,query_short_channel_ids,tlvs,query_short_channel_ids_tlvs, tlvtype,query_short_channel_ids_tlvs,query_flags,1 -tlvdata,query_short_channel_ids_tlvs,query_flags,encoding_type,u8, +tlvdata,query_short_channel_ids_tlvs,query_flags,encoding_type,byte, tlvdata,query_short_channel_ids_tlvs,query_flags,encoded_query_flags,byte,... msgtype,reply_short_channel_ids_end,262,gossip_queries msgdata,reply_short_channel_ids_end,chain_hash,chain_hash, -msgdata,reply_short_channel_ids_end,complete,byte, +msgdata,reply_short_channel_ids_end,full_information,byte, msgtype,query_channel_range,263,gossip_queries msgdata,query_channel_range,chain_hash,chain_hash, msgdata,query_channel_range,first_blocknum,u32, msgdata,query_channel_range,number_of_blocks,u32, msgdata,query_channel_range,tlvs,query_channel_range_tlvs, tlvtype,query_channel_range_tlvs,query_option,1 -tlvdata,query_channel_range_tlvs,query_option,query_option_flags,varint, +tlvdata,query_channel_range_tlvs,query_option,query_option_flags,bigsize, msgtype,reply_channel_range,264,gossip_queries msgdata,reply_channel_range,chain_hash,chain_hash, msgdata,reply_channel_range,first_blocknum,u32, msgdata,reply_channel_range,number_of_blocks,u32, -msgdata,reply_channel_range,complete,byte, +msgdata,reply_channel_range,sync_complete,byte, msgdata,reply_channel_range,len,u16, msgdata,reply_channel_range,encoded_short_ids,byte,len msgdata,reply_channel_range,tlvs,reply_channel_range_tlvs, tlvtype,reply_channel_range_tlvs,timestamps_tlv,1 -tlvdata,reply_channel_range_tlvs,timestamps_tlv,encoding_type,u8, +tlvdata,reply_channel_range_tlvs,timestamps_tlv,encoding_type,byte, tlvdata,reply_channel_range_tlvs,timestamps_tlv,encoded_timestamps,byte,... tlvtype,reply_channel_range_tlvs,checksums_tlv,3 tlvdata,reply_channel_range_tlvs,checksums_tlv,checksums,channel_update_checksums,... diff --git a/electrum/lnworker.py b/electrum/lnworker.py index 1290396d3..9e01c9ebf 100644 --- a/electrum/lnworker.py +++ b/electrum/lnworker.py @@ -1002,7 +1002,7 @@ class LNWallet(LNWorker): elif chan.get_state() == ChannelState.FUNDED: peer = self._peers.get(chan.node_id) if peer and peer.is_initialized(): - peer.send_funding_locked(chan) + peer.send_channel_ready(chan) elif chan.get_state() == ChannelState.OPEN: peer = self._peers.get(chan.node_id) diff --git a/electrum/tests/test_lnmsg.py b/electrum/tests/test_lnmsg.py index 790a481bf..57e8f2ea6 100644 --- a/electrum/tests/test_lnmsg.py +++ b/electrum/tests/test_lnmsg.py @@ -213,35 +213,6 @@ class TestLNMsg(TestCaseForTestnet): ), decode_msg(bfh("01020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000043497fd7f826957108f4a30fd9cec3aeba79972084e90ead01ea33090000000000d43100006f00025e6ed0830100009000000000000000c8000001f400000023000000003b9aca00"))) - def test_encode_decode_msg__missing_optional_field_will_not_appear_in_decoded_dict(self): - # "channel_update": optional field "htlc_maximum_msat" missing -> does not get put into dict - self.assertEqual(bfh("01020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000043497fd7f826957108f4a30fd9cec3aeba79972084e90ead01ea33090000000000d43100006f00025e6ed0830100009000000000000000c8000001f400000023"), - encode_msg( - "channel_update", - short_channel_id=ShortChannelID.from_components(54321, 111, 2), - channel_flags=b'\x00', - message_flags=b'\x01', - cltv_expiry_delta=144, - htlc_minimum_msat=200, - fee_base_msat=500, - fee_proportional_millionths=35, - chain_hash=constants.net.rev_genesis_bytes(), - timestamp=1584320643, - )) - self.assertEqual(('channel_update', - {'chain_hash': b'CI\x7f\xd7\xf8&\x95q\x08\xf4\xa3\x0f\xd9\xce\xc3\xae\xbay\x97 \x84\xe9\x0e\xad\x01\xea3\t\x00\x00\x00\x00', - 'channel_flags': b'\x00', - 'cltv_expiry_delta': 144, - 'fee_base_msat': 500, - 'fee_proportional_millionths': 35, - 'htlc_minimum_msat': 200, - 'message_flags': b'\x01', - 'short_channel_id': b'\x00\xd41\x00\x00o\x00\x02', - 'signature': bytes(64), - 'timestamp': 1584320643} - ), - decode_msg(bfh("01020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000043497fd7f826957108f4a30fd9cec3aeba79972084e90ead01ea33090000000000d43100006f00025e6ed0830100009000000000000000c8000001f400000023"))) - def test_encode_decode_msg__ints_can_be_passed_as_bytes(self): self.assertEqual(bfh("01020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000043497fd7f826957108f4a30fd9cec3aeba79972084e90ead01ea33090000000000d43100006f00025e6ed0830100009000000000000000c8000001f400000023000000003b9aca00"), encode_msg(