Skip to content

Commit 4a633da

Browse files
committed
Add rescuefunding and signrescuefunding commands
1 parent a95f475 commit 4a633da

File tree

10 files changed

+530
-127
lines changed

10 files changed

+530
-127
lines changed

README.md

Lines changed: 82 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,9 @@
1616
+ [genimportscript](#genimportscript)
1717
+ [forceclose](#forceclose)
1818
+ [rescueclosed](#rescueclosed)
19+
+ [rescuefunding](#rescuefunding)
1920
+ [showrootkey](#showrootkey)
21+
+ [signrescuefunding](#signrescuefunding)
2022
+ [summary](#summary)
2123
+ [sweeptimelock](#sweeptimelock)
2224
+ [vanitygen](#vanitygen)
@@ -207,21 +209,23 @@ Help Options:
207209
-h, --help Show this help message
208210
209211
Available commands:
210-
chanbackup Create a channel.backup file from a channel database.
211-
compactdb Open a source channel.db database file in safe/read-only mode and copy it to a fresh database, compacting it in the process.
212-
derivekey Derive a key with a specific derivation path from the BIP32 HD root key.
213-
dumpbackup Dump the content of a channel.backup file.
214-
dumpchannels Dump all channel information from lnd's channel database.
215-
filterbackup Filter an lnd channel.backup file and remove certain channels.
216-
fixoldbackup Fixes an old channel.backup file that is affected by the lnd issue #3881 (unable to derive shachain root key).
217-
forceclose Force-close the last state that is in the channel.db provided.
218-
genimportscript Generate a script containing the on-chain keys of an lnd wallet that can be imported into other software like bitcoind.
219-
rescueclosed Try finding the private keys for funds that are in outputs of remotely force-closed channels.
220-
showrootkey Extract and show the BIP32 HD root key from the 24 word lnd aezeed.
221-
summary Compile a summary about the current state of channels.
222-
sweeptimelock Sweep the force-closed state after the time lock has expired.
223-
vanitygen Generate a seed with a custom lnd node identity public key that starts with the given p
224-
walletinfo Shows relevant information about an lnd wallet.db file and optionally extracts the BIP32 HD root key.
212+
chanbackup Create a channel.backup file from a channel database.
213+
compactdb Open a source channel.db database file in safe/read-only mode and copy it to a fresh database, compacting it in the process.
214+
derivekey Derive a key with a specific derivation path from the BIP32 HD root key.
215+
dumpbackup Dump the content of a channel.backup file.
216+
dumpchannels Dump all channel information from lnd's channel database.
217+
filterbackup Filter an lnd channel.backup file and remove certain channels.
218+
fixoldbackup Fixes an old channel.backup file that is affected by the lnd issue #3881 (unable to derive shachain root key).
219+
forceclose Force-close the last state that is in the channel.db provided.
220+
genimportscript Generate a script containing the on-chain keys of an lnd wallet that can be imported into other software like bitcoind.
221+
rescueclosed Try finding the private keys for funds that are in outputs of remotely force-closed channels.
222+
rescuefunding Rescue funds locked in a funding multisig output that never resulted in a proper channel. This is the command the initiator of the channel needs to run.
223+
showrootkey Extract and show the BIP32 HD root key from the 24 word lnd aezeed.
224+
signrescuefunding Rescue funds locked in a funding multisig output that never resulted in a proper channel. This is the command the remote node (the non-initiator) of the channel needs to run.
225+
summary Compile a summary about the current state of channels.
226+
sweeptimelock Sweep the force-closed state after the time lock has expired.
227+
vanitygen Generate a seed with a custom lnd node identity public key that starts with the given prefix.
228+
walletinfo Shows relevant information about an lnd wallet.db file and optionally extracts the BIP32 HD root key.
225229
```
226230

227231
## Commands
@@ -479,6 +483,43 @@ chantools --fromsummary results/summary-xxxx-yyyy.json \
479483
--rootkey xprvxxxxxxxxxx
480484
```
481485

486+
### rescuefunding
487+
488+
```text
489+
Usage:
490+
chantools [OPTIONS] rescuefunding [rescuefunding-OPTIONS]
491+
492+
[rescuefunding command options]
493+
--rootkey= BIP32 HD root key to use. Leave empty to prompt for lnd 24 word aezeed.
494+
--channeldb= The lnd channel.db file to rescue a channel from. Must contain the pending channel specified with --channelpoint.
495+
--channelpoint= The funding transaction outpoint of the channel to rescue (<txid>:<txindex>) as it is recorded in the DB.
496+
--confirmedchannelpoint= The channel outpoint that got confirmed on chain (<txid>:<txindex>). Normally this is the same as the --channelpoint so it will be set to that value if this is left empty.
497+
--sweepaddr= The address to sweep the rescued funds to.
498+
--satperbyte= The fee rate to use in satoshis/vByte.
499+
```
500+
501+
This is part 1 of a two phase process to rescue a channel funding output that
502+
was created on chain by accident but never resulted in a proper channel and no
503+
commitment transactions exist to spend the funds locked in the 2-of-2 multisig.
504+
505+
**You need the cooperation of the channel partner (remote node) for this to
506+
work**! They need to run the second command of this process:
507+
[`signrescuefunding`](#signrescuefunding)
508+
509+
Example command (run against the channel DB of the initiator node):
510+
511+
```bash
512+
chantools rescuefunding \
513+
--channeldb ~/.lnd/data/graph/mainnet/channel.db \
514+
--channelpoint xxxxxxx:xx \
515+
--sweepaddr bc1qxxxxxxxxx \
516+
--satperbyte 10 \
517+
--rootkey xprvxxxxxxxxxx
518+
```
519+
520+
If successful, this will create a PSBT that then has to be sent to the channel
521+
partner (remote node operator).
522+
482523
### showrootkey
483524

484525
This command converts the 24 word `lnd` aezeed phrase and password to the BIP32
@@ -491,6 +532,32 @@ Example command:
491532
chantools showrootkey
492533
```
493534

535+
### signrescuefunding
536+
537+
```text
538+
Usage:
539+
chantools [OPTIONS] signrescuefunding [signrescuefunding-OPTIONS]
540+
541+
[signrescuefunding command options]
542+
--rootkey= BIP32 HD root (m/) key to derive the key for our part of the signature from.
543+
--psbt= The Partially Signed Bitcoin Transaction that was provided by the initiator of the channel to rescue.
544+
```
545+
546+
This is part 2 of a two phase process to rescue a channel funding output that
547+
was created on chain by accident but never resulted in a proper channel and no
548+
commitment transactions exist to spend the funds locked in the 2-of-2 multisig.
549+
550+
Example command (run by the non-initiator of the channel):
551+
552+
```bash
553+
chantools signrescuefunding \
554+
--psbt <the_base64_encoded_psbt_from_step_1> \
555+
--rootkey xprvxxxxxxxxxx
556+
```
557+
558+
If successful, this will create a final on-chain transaction that can be
559+
broadcast by any Bitcoin node.
560+
494561
### summary
495562

496563
```text

cmd/chantools/main.go

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import (
2323

2424
const (
2525
defaultAPIURL = "https://blockstream.info/api"
26-
version = "0.3.0"
26+
version = "0.4.0"
2727
)
2828

2929
var (
@@ -137,12 +137,20 @@ func runCommandParser() error {
137137
"public key that starts with the given prefix.", "",
138138
&vanityGenCommand{},
139139
)
140-
// TODO: uncomment when command is fully implemented.
141-
//_, _ = parser.AddCommand(
142-
// "rescuefunding", "Rescue funds locked in a funding multisig "+
143-
// "output that never resulted in a proper channel.", "",
144-
// &rescueFundingCommand{},
145-
//)
140+
_, _ = parser.AddCommand(
141+
"rescuefunding", "Rescue funds locked in a funding multisig "+
142+
"output that never resulted in a proper channel. This "+
143+
"is the command the initiator of the channel needs to "+
144+
"run.", "",
145+
&rescueFundingCommand{},
146+
)
147+
_, _ = parser.AddCommand(
148+
"signrescuefunding", "Rescue funds locked in a funding "+
149+
"multisig output that never resulted in a proper "+
150+
"channel. This is the command the remote node (the non"+
151+
"-initiator) of the channel needs to run.", "",
152+
&signRescueFundingCommand{},
153+
)
146154

147155
_, err := parser.Parse()
148156
return err

0 commit comments

Comments
 (0)