From 6e9372a3e861cc17e2c4d9ef4dfc00797a47391f Mon Sep 17 00:00:00 2001 From: Elle Mouton Date: Fri, 23 May 2025 16:11:27 +0200 Subject: [PATCH 1/4] chanbackup: make sure onion addresses are covered in tests --- chanbackup/backup_test.go | 1 + chanbackup/multi_test.go | 2 +- chanbackup/single_test.go | 9 +++++++-- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/chanbackup/backup_test.go b/chanbackup/backup_test.go index 46ccf4c24..46696da76 100644 --- a/chanbackup/backup_test.go +++ b/chanbackup/backup_test.go @@ -156,6 +156,7 @@ func TestFetchStaticChanBackups(t *testing.T) { chanSource.chans[randomChan2.FundingOutpoint] = randomChan2 chanSource.addAddrsForNode(randomChan1.IdentityPub, []net.Addr{addr1}) chanSource.addAddrsForNode(randomChan2.IdentityPub, []net.Addr{addr2}) + chanSource.addAddrsForNode(randomChan2.IdentityPub, []net.Addr{addr3}) // With the channel source populated, we'll now attempt to create a set // of backups for all the channels. This should succeed, as all items diff --git a/chanbackup/multi_test.go b/chanbackup/multi_test.go index a296f914e..eeff81788 100644 --- a/chanbackup/multi_test.go +++ b/chanbackup/multi_test.go @@ -22,7 +22,7 @@ func TestMultiPackUnpack(t *testing.T) { t.Fatalf("unable to gen channel: %v", err) } - single := NewSingle(channel, []net.Addr{addr1, addr2}) + single := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) originalSingles = append(originalSingles, single) multi.StaticBackups = append(multi.StaticBackups, single) diff --git a/chanbackup/single_test.go b/chanbackup/single_test.go index 0fe402926..78957f38b 100644 --- a/chanbackup/single_test.go +++ b/chanbackup/single_test.go @@ -18,6 +18,7 @@ import ( "github.com/lightningnetwork/lnd/lnencrypt" "github.com/lightningnetwork/lnd/lnwire" "github.com/lightningnetwork/lnd/shachain" + "github.com/lightningnetwork/lnd/tor" "github.com/stretchr/testify/require" ) @@ -36,6 +37,10 @@ var ( addr1, _ = net.ResolveTCPAddr("tcp", "10.0.0.2:9000") addr2, _ = net.ResolveTCPAddr("tcp", "10.0.0.3:9000") + addr3 = &tor.OnionAddr{ + OnionService: "3g2upl4pq6kufc4m.onion", + Port: 9735, + } ) func assertSingleEqual(t *testing.T, a, b Single) { @@ -309,7 +314,7 @@ func TestSinglePackUnpack(t *testing.T) { channel, err := genRandomOpenChannelShell() require.NoError(t, err, "unable to gen open channel") - singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2}) + singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) keyRing := &lnencrypt.MockKeyRing{} @@ -634,7 +639,7 @@ func TestSingleUnconfirmedChannel(t *testing.T) { channel.ShortChannelID.BlockHeight = 0 channel.FundingBroadcastHeight = fundingBroadcastHeight - singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2}) + singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) keyRing := &lnencrypt.MockKeyRing{} // Pack it and then unpack it again to make sure everything is written From a15489159af984cf562ca322c0dc790493019ea8 Mon Sep 17 00:00:00 2001 From: Elle Mouton Date: Fri, 23 May 2025 16:12:28 +0200 Subject: [PATCH 2/4] lnwire: remove duplicated logic Use existing serialisation helpers for serialising TC Pand Onion addresses in WriteElement. --- lnwire/lnwire.go | 68 ++---------------------------------------------- 1 file changed, 2 insertions(+), 66 deletions(-) diff --git a/lnwire/lnwire.go b/lnwire/lnwire.go index 4d2b814e5..bb0fd55f7 100644 --- a/lnwire/lnwire.go +++ b/lnwire/lnwire.go @@ -339,76 +339,12 @@ func WriteElement(w *bytes.Buffer, element interface{}) error { } case *net.TCPAddr: - if e == nil { - return fmt.Errorf("cannot write nil TCPAddr") - } - - if e.IP.To4() != nil { - var descriptor [1]byte - descriptor[0] = uint8(tcp4Addr) - if _, err := w.Write(descriptor[:]); err != nil { - return err - } - - var ip [4]byte - copy(ip[:], e.IP.To4()) - if _, err := w.Write(ip[:]); err != nil { - return err - } - } else { - var descriptor [1]byte - descriptor[0] = uint8(tcp6Addr) - if _, err := w.Write(descriptor[:]); err != nil { - return err - } - var ip [16]byte - copy(ip[:], e.IP.To16()) - if _, err := w.Write(ip[:]); err != nil { - return err - } - } - var port [2]byte - binary.BigEndian.PutUint16(port[:], uint16(e.Port)) - if _, err := w.Write(port[:]); err != nil { + if err := WriteTCPAddr(w, e); err != nil { return err } case *tor.OnionAddr: - if e == nil { - return errors.New("cannot write nil onion address") - } - - var suffixIndex int - switch len(e.OnionService) { - case tor.V2Len: - descriptor := []byte{byte(v2OnionAddr)} - if _, err := w.Write(descriptor); err != nil { - return err - } - suffixIndex = tor.V2Len - tor.OnionSuffixLen - case tor.V3Len: - descriptor := []byte{byte(v3OnionAddr)} - if _, err := w.Write(descriptor); err != nil { - return err - } - suffixIndex = tor.V3Len - tor.OnionSuffixLen - default: - return errors.New("unknown onion service length") - } - - host, err := tor.Base32Encoding.DecodeString( - e.OnionService[:suffixIndex], - ) - if err != nil { - return err - } - if _, err := w.Write(host); err != nil { - return err - } - - var port [2]byte - binary.BigEndian.PutUint16(port[:], uint16(e.Port)) - if _, err := w.Write(port[:]); err != nil { + if err := WriteOnionAddr(w, e); err != nil { return err } From 412e05f85f57002a6a73e6bca6ca0f8d74c20a5e Mon Sep 17 00:00:00 2001 From: Elle Mouton Date: Fri, 23 May 2025 16:14:47 +0200 Subject: [PATCH 3/4] lnwire: add *OpaqueAddrs case in WriteElements And then expand the chanbackup unit tests to cover such a case. --- chanbackup/backup_test.go | 1 + chanbackup/multi_test.go | 4 +++- chanbackup/single_test.go | 13 +++++++++++-- lnwire/lnwire.go | 5 +++++ 4 files changed, 20 insertions(+), 3 deletions(-) diff --git a/chanbackup/backup_test.go b/chanbackup/backup_test.go index 46696da76..d36fa385b 100644 --- a/chanbackup/backup_test.go +++ b/chanbackup/backup_test.go @@ -157,6 +157,7 @@ func TestFetchStaticChanBackups(t *testing.T) { chanSource.addAddrsForNode(randomChan1.IdentityPub, []net.Addr{addr1}) chanSource.addAddrsForNode(randomChan2.IdentityPub, []net.Addr{addr2}) chanSource.addAddrsForNode(randomChan2.IdentityPub, []net.Addr{addr3}) + chanSource.addAddrsForNode(randomChan2.IdentityPub, []net.Addr{addr4}) // With the channel source populated, we'll now attempt to create a set // of backups for all the channels. This should succeed, as all items diff --git a/chanbackup/multi_test.go b/chanbackup/multi_test.go index eeff81788..3350c773c 100644 --- a/chanbackup/multi_test.go +++ b/chanbackup/multi_test.go @@ -22,7 +22,9 @@ func TestMultiPackUnpack(t *testing.T) { t.Fatalf("unable to gen channel: %v", err) } - single := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) + single := NewSingle( + channel, []net.Addr{addr1, addr2, addr3, addr4}, + ) originalSingles = append(originalSingles, single) multi.StaticBackups = append(multi.StaticBackups, single) diff --git a/chanbackup/single_test.go b/chanbackup/single_test.go index 78957f38b..b3c7471a3 100644 --- a/chanbackup/single_test.go +++ b/chanbackup/single_test.go @@ -41,6 +41,11 @@ var ( OnionService: "3g2upl4pq6kufc4m.onion", Port: 9735, } + addr4 = &lnwire.OpaqueAddrs{ + // The first byte must be an address type we are not yet aware + // of for it to be a valid OpaqueAddrs. + Payload: []byte{math.MaxUint8, 1, 2, 3, 4}, + } ) func assertSingleEqual(t *testing.T, a, b Single) { @@ -314,7 +319,9 @@ func TestSinglePackUnpack(t *testing.T) { channel, err := genRandomOpenChannelShell() require.NoError(t, err, "unable to gen open channel") - singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) + singleChanBackup := NewSingle( + channel, []net.Addr{addr1, addr2, addr3, addr4}, + ) keyRing := &lnencrypt.MockKeyRing{} @@ -639,7 +646,9 @@ func TestSingleUnconfirmedChannel(t *testing.T) { channel.ShortChannelID.BlockHeight = 0 channel.FundingBroadcastHeight = fundingBroadcastHeight - singleChanBackup := NewSingle(channel, []net.Addr{addr1, addr2, addr3}) + singleChanBackup := NewSingle( + channel, []net.Addr{addr1, addr2, addr3, addr4}, + ) keyRing := &lnencrypt.MockKeyRing{} // Pack it and then unpack it again to make sure everything is written diff --git a/lnwire/lnwire.go b/lnwire/lnwire.go index bb0fd55f7..fa43d25bf 100644 --- a/lnwire/lnwire.go +++ b/lnwire/lnwire.go @@ -348,6 +348,11 @@ func WriteElement(w *bytes.Buffer, element interface{}) error { return err } + case *OpaqueAddrs: + if err := WriteOpaqueAddrs(w, e); err != nil { + return err + } + case []net.Addr: // First, we'll encode all the addresses into an intermediate // buffer. We need to do this in order to compute the total From 9d54dbcd642ab6ca3b08071a0127e10d2a6c8f90 Mon Sep 17 00:00:00 2001 From: Elle Mouton Date: Fri, 23 May 2025 16:17:11 +0200 Subject: [PATCH 4/4] docs: add release notes for 0.19.1 --- docs/release-notes/release-notes-0.19.1.md | 80 ++++++++++++++++++++++ 1 file changed, 80 insertions(+) create mode 100644 docs/release-notes/release-notes-0.19.1.md diff --git a/docs/release-notes/release-notes-0.19.1.md b/docs/release-notes/release-notes-0.19.1.md new file mode 100644 index 000000000..dd3557db8 --- /dev/null +++ b/docs/release-notes/release-notes-0.19.1.md @@ -0,0 +1,80 @@ +# Release Notes +- [Bug Fixes](#bug-fixes) +- [New Features](#new-features) + - [Functional Enhancements](#functional-enhancements) + - [RPC Additions](#rpc-additions) + - [lncli Additions](#lncli-additions) +- [Improvements](#improvements) + - [Functional Updates](#functional-updates) + - [RPC Updates](#rpc-updates) + - [lncli Updates](#lncli-updates) + - [Breaking Changes](#breaking-changes) + - [Performance Improvements](#performance-improvements) + - [Deprecations](#deprecations) +- [Technical and Architectural Updates](#technical-and-architectural-updates) + - [BOLT Spec Updates](#bolt-spec-updates) + - [Testing](#testing) + - [Database](#database) + - [Code Health](#code-health) + - [Tooling and Documentation](#tooling-and-documentation) + +# Bug Fixes + +* [Fix a serialisation bug](https://github.com/lightningnetwork/lnd/pull/9856) + that would occur when an attempt was made to write a backup file for a channel + peer that has advertised an address that we do not yet know how to parse. + +# New Features + +## Functional Enhancements + +## RPC Additions + +## lncli Additions + +# Improvements +## Functional Updates + +## RPC Updates + +## lncli Updates + +## Code Health + +## Breaking Changes +## Performance Improvements + +## Deprecations + +### ⚠️ **Warning:** The following RPCs will be removed in release version **0.21**: + +| Deprecated RPC Method | REST Equivalent | HTTP Method | Path | Replaced By | +|----------------------|----------------|-------------|------------------------------|------------------| +| [`lnrpc.SendToRoute`](https://lightning.engineering/api-docs/api/lnd/lightning/send-to-route/index.html)
[`routerrpc.SendToRoute`](https://lightning.engineering/api-docs/api/lnd/router/send-to-route/) | ❌ (No direct REST equivalent) | — | — | [`routerrpc.SendToRouteV2`](https://lightning.engineering/api-docs/api/lnd/router/send-to-route-v2/) | +| [`lnrpc.SendPayment`](https://lightning.engineering/api-docs/api/lnd/lightning/send-payment/)
[`routerrpc.SendPayment`](https://lightning.engineering/api-docs/api/lnd/router/send-payment/) | ✅ | `POST` | `/v1/channels/transaction-stream` | [`routerrpc.SendPaymentV2`](https://lightning.engineering/api-docs/api/lnd/router/send-payment-v2/index.html) | +| [`lnrpc.SendToRouteSync`](https://lightning.engineering/api-docs/api/lnd/lightning/send-to-route-sync/index.html) | ✅ | `POST` | `/v1/channels/transactions/route` | [`routerrpc.SendToRouteV2`](https://lightning.engineering/api-docs/api/lnd/router/send-to-route-v2/) | +| [`lnrpc.SendPaymentSync`](https://lightning.engineering/api-docs/api/lnd/lightning/send-payment-sync/index.html) | ✅ | `POST` | `/v1/channels/transactions` | [`routerrpc.SendPaymentV2`](https://lightning.engineering/api-docs/api/lnd/router/send-payment-v2/index.html) | +| [`router.TrackPayment`](https://lightning.engineering/api-docs/api/lnd/router/track-payment/index.html) | ❌ (No direct REST equivalent) | — | — | [`routerrpc.TrackPaymentV2`](https://lightning.engineering/api-docs/api/lnd/router/track-payment-v2/) | + +🚨 **Users are strongly encouraged** to transition to the new **V2 methods** before release **0.21** to ensure compatibility: + +| New RPC Method | REST Equivalent | HTTP Method | Path | +|---------------|----------------|-------------|------------------------| +| [`routerrpc.SendToRouteV2`](https://lightning.engineering/api-docs/api/lnd/router/send-to-route-v2/) | ✅ | `POST` | `/v2/router/route/send` | +| [`routerrpc.SendPaymentV2`](https://lightning.engineering/api-docs/api/lnd/router/send-payment-v2/index.html) | ✅ | `POST` | `/v2/router/send` | +| [`routerrpc.TrackPaymentV2`](https://lightning.engineering/api-docs/api/lnd/router/track-payment-v2/) | ✅ | `GET` | `/v2/router/track/{payment_hash}` | + +# Technical and Architectural Updates +## BOLT Spec Updates + +## Testing + +## Database + +## Code Health + +## Tooling and Documentation + +# Contributors (Alphabetical Order) + +* Elle Mouton