diff --git a/Makefile b/Makefile index f2d2c1038900..3dde35d9cda0 100644 --- a/Makefile +++ b/Makefile @@ -308,13 +308,19 @@ endif ifeq ($(SUPPRESS_GENERATION),1) SHA256STAMP_CHANGED = false SHA256STAMP = exit 1 +SHA256STAMP_CHANGED_ALL = false +SHA256STAMP_ALL = exit 1 else # Git doesn't maintain timestamps, so we only regen if sources actually changed: # We place the SHA inside some generated files so we can tell if they need updating. # Usage: $(call SHA256STAMP_CHANGED) -SHA256STAMP_CHANGED = [ x"`sed -n 's/.*SHA256STAMP:\([a-f0-9]*\).*/\1/p' $@ 2>/dev/null`" != x"`cat $(sort $(filter-out FORCE,$^)) | $(SHA256SUM) | cut -c1-64`" ] +SHA256STAMP_CHANGED = [ x"`sed -n 's/.*SHA256STAMP:\([a-f0-9]*\).*/\1/p' $@ 2>/dev/null`" != x"`cat $(sort $(filter-out FORCE,$<)) | $(SHA256SUM) | cut -c1-64`" ] # Usage: $(call SHA256STAMP,commentprefix,commentpostfix) -SHA256STAMP = echo "$(1) SHA256STAMP:"`cat $(sort $(filter-out FORCE,$^)) | $(SHA256SUM) | cut -c1-64`"$(2)" >> $@ +SHA256STAMP = echo "$(1) SHA256STAMP:"`cat $(sort $(filter-out FORCE,$<)) | $(SHA256SUM) | cut -c1-64`"$(2)" >> $@ + +SHA256STAMP_CHANGED_ALL = [ x"`sed -n 's/.*SHA256STAMP:\([a-f0-9]*\).*/\1/p' $@ 2>/dev/null`" != x"`cat $(sort $(filter-out FORCE,$^)) | $(SHA256SUM) | cut -c1-64`" ] +# Usage: $(call SHA256STAMP,commentprefix,commentpostfix) +SHA256STAMP_ALL = echo "$(1) SHA256STAMP:"`cat $(sort $(filter-out FORCE,$^)) | $(SHA256SUM) | cut -c1-64`"$(2)" >> $@ endif # generate-wire.py --page [header|impl] hdrfilename wirename < csv > file diff --git a/bitcoin/short_channel_id.h b/bitcoin/short_channel_id.h index bac77d8d8b06..4465da462003 100644 --- a/bitcoin/short_channel_id.h +++ b/bitcoin/short_channel_id.h @@ -37,6 +37,13 @@ static inline u32 short_channel_id_blocknum(const struct short_channel_id *scid) return scid->u64 >> 40; } +static inline bool is_stub_scid(const struct short_channel_id *scid) +{ + return scid ? scid->u64 >> 40 == 1 && + ((scid->u64 >> 16) & 0x00FFFFFF) == 1 && + (scid->u64 & 0xFFFF) == 1 : false; +} + static inline u32 short_channel_id_txnum(const struct short_channel_id *scid) { return (scid->u64 >> 16) & 0x00FFFFFF; diff --git a/common/Makefile b/common/Makefile index 3665baf4f4ca..d18494317c67 100644 --- a/common/Makefile +++ b/common/Makefile @@ -91,7 +91,7 @@ COMMON_SRC_NOGEN := \ common/wire_error.c -COMMON_SRC_GEN := common/status_wiregen.c common/peer_status_wiregen.c +COMMON_SRC_GEN := common/status_wiregen.c common/peer_status_wiregen.c common/scb_wiregen.c COMMON_HEADERS_NOGEN := $(COMMON_SRC_NOGEN:.c=.h) \ common/closing_fee.h \ @@ -105,13 +105,16 @@ COMMON_HEADERS_NOGEN := $(COMMON_SRC_NOGEN:.c=.h) \ common/overflows.h \ common/tx_roles.h -COMMON_HEADERS_GEN := common/htlc_state_names_gen.h common/status_wiregen.h common/peer_status_wiregen.h +COMMON_HEADERS_GEN := common/htlc_state_names_gen.h common/status_wiregen.h common/peer_status_wiregen.h common/scb_wiregen.h COMMON_HEADERS := $(COMMON_HEADERS_GEN) $(COMMON_HEADERS_NOGEN) COMMON_SRC := $(COMMON_SRC_NOGEN) $(COMMON_SRC_GEN) COMMON_OBJS := $(COMMON_SRC:.c=.o) +common/scb_wiregen.h_args := -s +common/scb_wiregen.c_args := -s + # Check that all h and c files are in the Makefile! check-common-files: @$(call VERBOSE, "MISSING-SRC common", [ "$(filter-out $(COMMON_SRC), $(wildcard common/*.c))" = "" ]) diff --git a/common/scb_wire.csv b/common/scb_wire.csv new file mode 100644 index 000000000000..f27667caf5fb --- /dev/null +++ b/common/scb_wire.csv @@ -0,0 +1,21 @@ +#include +#include +#include +#include +#include +#include + +# scb_chan stores min. info required to sweep the peer's force close. +subtype,scb_chan +subtypedata,scb_chan,id,u64, +subtypedata,scb_chan,cid,channel_id, +subtypedata,scb_chan,node_id,node_id, +subtypedata,scb_chan,addr,wireaddr_internal, +subtypedata,scb_chan,funding,bitcoin_outpoint, +subtypedata,scb_chan,funding_sats,amount_sat, +subtypedata,scb_chan,type,channel_type, +msgtype,static_chan_backup,6135, +msgdata,static_chan_backup,version,u64, +msgdata,static_chan_backup,timestamp,u32, +msgdata,static_chan_backup,num,u16, +msgdata,static_chan_backup,channels,scb_chan,num diff --git a/common/test/run-lease_rates.c b/common/test/run-lease_rates.c index 5d8b7d0e8597..31da81c7d317 100644 --- a/common/test/run-lease_rates.c +++ b/common/test/run-lease_rates.c @@ -15,7 +15,7 @@ bool fromwire_bool(const u8 **cursor UNNEEDED, size_t *max UNNEEDED) void *fromwire_fail(const u8 **cursor UNNEEDED, size_t *max UNNEEDED) { fprintf(stderr, "fromwire_fail called!\n"); abort(); } /* Generated stub for fromwire_lease_rates */ -void fromwire_lease_rates(const u8 **cursor UNNEEDED, size_t *plen UNNEEDED, struct lease_rates *lease_rates UNNEEDED) +bool fromwire_lease_rates(const u8 **cursor UNNEEDED, size_t *plen UNNEEDED, struct lease_rates *lease_rates UNNEEDED) { fprintf(stderr, "fromwire_lease_rates called!\n"); abort(); } /* Generated stub for fromwire_secp256k1_ecdsa_signature */ void fromwire_secp256k1_ecdsa_signature(const u8 **cursor UNNEEDED, size_t *max UNNEEDED, diff --git a/doc/Makefile b/doc/Makefile index e3b8b47546bd..f9375b406289 100644 --- a/doc/Makefile +++ b/doc/Makefile @@ -24,6 +24,7 @@ MANPAGES := doc/lightning-cli.1 \ doc/lightning-delpay.7 \ doc/lightning-disableoffer.7 \ doc/lightning-disconnect.7 \ + doc/lightning-emergencyrecover.7 \ doc/lightning-feerates.7 \ doc/lightning-fetchinvoice.7 \ doc/lightning-fundchannel.7 \ @@ -46,6 +47,7 @@ MANPAGES := doc/lightning-cli.1 \ doc/lightning-listpays.7 \ doc/lightning-listpeers.7 \ doc/lightning-listsendpays.7 \ + doc/lightning-makesecret.7 \ doc/lightning-multifundchannel.7 \ doc/lightning-multiwithdraw.7 \ doc/lightning-newaddr.7 \ @@ -60,6 +62,7 @@ MANPAGES := doc/lightning-cli.1 \ doc/lightning-pay.7 \ doc/lightning-parsefeerate.7 \ doc/lightning-plugin.7 \ + doc/lightning-recoverchannel.7 \ doc/lightning-reserveinputs.7 \ doc/lightning-sendinvoice.7 \ doc/lightning-sendonion.7 \ @@ -69,6 +72,7 @@ MANPAGES := doc/lightning-cli.1 \ doc/lightning-setchannelfee.7 \ doc/lightning-sendcustommsg.7 \ doc/lightning-signmessage.7 \ + doc/lightning-staticbackup.7 \ doc/lightning-txprepare.7 \ doc/lightning-txdiscard.7 \ doc/lightning-txsend.7 \ diff --git a/doc/index.rst b/doc/index.rst index abf699ff89d5..3d92e23ac223 100644 --- a/doc/index.rst +++ b/doc/index.rst @@ -47,6 +47,7 @@ Core Lightning Documentation lightning-delpay lightning-disableoffer lightning-disconnect + lightning-emergencyrecover lightning-feerates lightning-fetchinvoice lightning-fundchannel @@ -75,6 +76,7 @@ Core Lightning Documentation lightning-listpeers lightning-listsendpays lightning-listtransactions + lightning-makesecret lightning-multifundchannel lightning-multiwithdraw lightning-newaddr @@ -90,6 +92,7 @@ Core Lightning Documentation lightning-pay lightning-ping lightning-plugin + lightning-recoverchannel lightning-reserveinputs lightning-sendcustommsg lightning-sendinvoice @@ -101,6 +104,7 @@ Core Lightning Documentation lightning-setchannelfee lightning-signmessage lightning-signpsbt + lightning-staticbackup lightning-stop lightning-txdiscard lightning-txprepare diff --git a/doc/lightning-addgossip.7.md b/doc/lightning-addgossip.7.md index fba520c5a5f9..a23abf111ce4 100644 --- a/doc/lightning-addgossip.7.md +++ b/doc/lightning-addgossip.7.md @@ -42,4 +42,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:1a64fbaed63ffee21df3d46956a6dca193982b1b135a9b095e68652a720c77ac) +[comment]: # ( SHA256STAMP:c801b02463804504c2387387a36a6739351330a2c496aaa10de2b1f49c36ed32) diff --git a/doc/lightning-autocleaninvoice.7.md b/doc/lightning-autocleaninvoice.7.md index 9cb826748fe6..8dffb14781d9 100644 --- a/doc/lightning-autocleaninvoice.7.md +++ b/doc/lightning-autocleaninvoice.7.md @@ -50,4 +50,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:4506a00326dbfa7d44cbf891ad31cbfa66351d852aa0c58735bae03d32938edb) +[comment]: # ( SHA256STAMP:c5aedf100597dd0bd1bbbdf82964327035cd49df00d7b0aef6454e3b1ef39dbc) diff --git a/doc/lightning-check.7.md b/doc/lightning-check.7.md index 500e2aa43692..243160cf8f68 100644 --- a/doc/lightning-check.7.md +++ b/doc/lightning-check.7.md @@ -40,4 +40,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:10d986d91af6315ee755d119cb1b77f306e2360105191116282f3faead350ce8) +[comment]: # ( SHA256STAMP:c676fc0dbfdabc729b3fdbee7e64c91f8180100c9945db06cbaed955a3d63cfc) diff --git a/doc/lightning-checkmessage.7.md b/doc/lightning-checkmessage.7.md index 9ccf3c13e23a..010caba3db46 100644 --- a/doc/lightning-checkmessage.7.md +++ b/doc/lightning-checkmessage.7.md @@ -50,4 +50,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6df0e61e28118786861aacc073e3289268fe1b00837c3fd02a537aa13e5acae5) +[comment]: # ( SHA256STAMP:7dcca1fd1708d93b4a0c9b83955630fc4f551c4ffd452fb866c624c72aeaa44d) diff --git a/doc/lightning-close.7.md b/doc/lightning-close.7.md index b49e59f56832..97ded08c8e02 100644 --- a/doc/lightning-close.7.md +++ b/doc/lightning-close.7.md @@ -133,4 +133,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:3540adff8d75123f90598a2c0657924c0d5a53aa26716980f9a59879fcfb1f6b) +[comment]: # ( SHA256STAMP:3b645a2105f2b428889d097283cb56ba9c8d6cba90343ac779f2fb6e26a1c202) diff --git a/doc/lightning-connect.7.md b/doc/lightning-connect.7.md index ff4cfcb73b3a..afd919a43ac2 100644 --- a/doc/lightning-connect.7.md +++ b/doc/lightning-connect.7.md @@ -50,7 +50,7 @@ RETURN VALUE [comment]: # (GENERATE-FROM-SCHEMA-START) On success, an object is returned, containing: - **id** (pubkey): the peer we connected to -- **features** (hex): BOLT 9 features bitmap offered by peer in init message (globalfeatures and features combined) +- **features** (hex): BOLT 9 features bitmap offered by peer - **direction** (string): Whether they initiated connection or we did (one of "in", "out") - **address** (object): Address information (mainly useful if **direction** is *out*): - **type** (string): Type of connection (*torv2*/*torv3* only if **direction** is *out*) (one of "local socket", "ipv4", "ipv6", "torv2", "torv3") @@ -97,4 +97,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:540ce22f5d912b59732b8b2659e4a950d1344eb926901e26476a246d9eb473b8) +[comment]: # ( SHA256STAMP:ad52e3b3042a8910c106e0730d9d54d09ebdd3cffdb6ba3fd776f8ec4be57e46) diff --git a/doc/lightning-createinvoice.7.md b/doc/lightning-createinvoice.7.md index ba27e08b6878..f960b936f193 100644 --- a/doc/lightning-createinvoice.7.md +++ b/doc/lightning-createinvoice.7.md @@ -74,4 +74,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:b07a315a6460449b64ab848ce9fc4cfe6ac862d63c8ab922434238a2b83d7902) +[comment]: # ( SHA256STAMP:34ba2cc01db3e516b257dbe6a47cf764d1e34b85ee89fd4b49aed1fc2e0bb0ba) diff --git a/doc/lightning-createonion.7.md b/doc/lightning-createonion.7.md index 484a7cad0631..38184588635b 100644 --- a/doc/lightning-createonion.7.md +++ b/doc/lightning-createonion.7.md @@ -132,4 +132,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:eabebca3c38ac8e01fb9a0891bde7913ce2832b7ee179c0b4617d104a0e6c009) +[comment]: # ( SHA256STAMP:d313a15317ee4b09d151312071fb6aa2f7fc16128ca4485096783347bffdeca2) diff --git a/doc/lightning-datastore.7.md b/doc/lightning-datastore.7.md index 18683e36ceeb..95e7df0e0701 100644 --- a/doc/lightning-datastore.7.md +++ b/doc/lightning-datastore.7.md @@ -65,4 +65,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:89e1f4926dd83df233b92aae626de776ec3bb2d29887ec29e8cf479ee2a16b85) +[comment]: # ( SHA256STAMP:ce6a72f08dd7f6026eab58bb6ea732aead4512e714fab4f9a1cf54cdb1374f59) diff --git a/doc/lightning-decode.7.md b/doc/lightning-decode.7.md index de4dc749d058..7c916562b30f 100644 --- a/doc/lightning-decode.7.md +++ b/doc/lightning-decode.7.md @@ -181,4 +181,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6ccf1b9195e64f897f65198a81c47bbd7e16387e4bdc74d624e2ec04a24e9873) +[comment]: # ( SHA256STAMP:bc3778965137591623ce08ff51adf411bc42e6d1a4200692961b69962da39be7) diff --git a/doc/lightning-decodepay.7.md b/doc/lightning-decodepay.7.md index 6990389855c5..336508033225 100644 --- a/doc/lightning-decodepay.7.md +++ b/doc/lightning-decodepay.7.md @@ -70,4 +70,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:a606b0d0594d48c619a8d34c7c0d0996982db10f1423841f269e89004a19fa98) +[comment]: # ( SHA256STAMP:e6e27ff57a8e26db5d4bba8be2a5faa6f1c58b20ef625f371e6e66d17932f8a0) diff --git a/doc/lightning-deldatastore.7.md b/doc/lightning-deldatastore.7.md index 0c75bd165d16..d35ccf971751 100644 --- a/doc/lightning-deldatastore.7.md +++ b/doc/lightning-deldatastore.7.md @@ -48,4 +48,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:ac7468cf6eadc8ab85216b4d5ecb55a32f3d0bc84180f477151c3748901824de) +[comment]: # ( SHA256STAMP:83a7e89ed44c6dbf744d1327337e29393f9095628bd95fffe59ec5014ee0a483) diff --git a/doc/lightning-delexpiredinvoice.7.md b/doc/lightning-delexpiredinvoice.7.md index 45cf12cbcede..67b15092a3a2 100644 --- a/doc/lightning-delexpiredinvoice.7.md +++ b/doc/lightning-delexpiredinvoice.7.md @@ -38,4 +38,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:20cca78dbc3681427e1d536ba2f81e0bc05e2b5209edf884137f2ad25e642e84) +[comment]: # ( SHA256STAMP:c71baf4b5863fd6f4d2ba21a97d4106195ba10c5add21087142b1a5ee533da91) diff --git a/doc/lightning-delinvoice.7.md b/doc/lightning-delinvoice.7.md index 0ee5773e2195..7e5ca099a9f8 100644 --- a/doc/lightning-delinvoice.7.md +++ b/doc/lightning-delinvoice.7.md @@ -78,4 +78,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:407d741b622621da127dc1e55c98c299ace970f8244bc14574dddcafbf9aa1fc) +[comment]: # ( SHA256STAMP:a24e80716475dea15f9762cf50382f21e3e09b803a669e217923d7019cd526e0) diff --git a/doc/lightning-delpay.7.md b/doc/lightning-delpay.7.md index a5c32f37f68a..3a4f9a05d3b9 100644 --- a/doc/lightning-delpay.7.md +++ b/doc/lightning-delpay.7.md @@ -101,4 +101,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:af8299cd87efe8254969069851d99bffffa033013f4a8b9fc94cdab6cfa0ff78) +[comment]: # ( SHA256STAMP:ecdf9fe432142054328abb6aa3f76b726968dd28db1fc26875a81f291e10135a) diff --git a/doc/lightning-disableoffer.7.md b/doc/lightning-disableoffer.7.md index 652d4fdd2694..0d0702e2a8b5 100644 --- a/doc/lightning-disableoffer.7.md +++ b/doc/lightning-disableoffer.7.md @@ -74,4 +74,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:a7dbc87d991d1040283b5fbfe732fb9bc7c81efad3aa8b5bfb11ffe59ed3f069) +[comment]: # ( SHA256STAMP:d91f424d5374fd26d4d85df10f9e5eb092e5b0e1bac8dae44b98d844a55b6e22) diff --git a/doc/lightning-disconnect.7.md b/doc/lightning-disconnect.7.md index d1ec7f708e43..8f3fe0e163cd 100644 --- a/doc/lightning-disconnect.7.md +++ b/doc/lightning-disconnect.7.md @@ -59,4 +59,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:1a64fbaed63ffee21df3d46956a6dca193982b1b135a9b095e68652a720c77ac) +[comment]: # ( SHA256STAMP:c801b02463804504c2387387a36a6739351330a2c496aaa10de2b1f49c36ed32) diff --git a/doc/lightning-emergencyrecover.7.md b/doc/lightning-emergencyrecover.7.md new file mode 100644 index 000000000000..29e582e117a4 --- /dev/null +++ b/doc/lightning-emergencyrecover.7.md @@ -0,0 +1,43 @@ +lightning-emergencyrecover -- Command for recovering channels from the emergency.recovery file in the lightning directory +========================================================================================================================= + +SYNOPSIS +-------- + +**emergencyrecover** + +DESCRIPTION +----------- + +The **emergencyrecover** RPC command fetches data from the emergency.recover +file and tries to reconnect to the peer and force him to close the channel. +The data in this file has enough information to reconnect and sweep the funds. + +This recovery method is not spontaneous and it depends on the peer, so it should +be used as a last resort to recover the funds stored in a channel in case of severe +data loss. + +RETURN VALUE +------------ + +On success, an object is returned, containing: +- **stubs** (array of hexs): + - Each item is the channel ID of the channel successfully inserted + + +AUTHOR +------ + +Aditya <> is mainly responsible. + +SEE ALSO +-------- + +lightning-getsharedsecret(7) + +RESOURCES +--------- + +Main web site: + +[comment]: # ( SHA256STAMP:9cfaa9eb4609b36accc3e3b12a352c00ddd402307e4461f4df274146d12f6eb0) \ No newline at end of file diff --git a/doc/lightning-feerates.7.md b/doc/lightning-feerates.7.md index f4669205e81a..345e1fe1ab5b 100644 --- a/doc/lightning-feerates.7.md +++ b/doc/lightning-feerates.7.md @@ -119,4 +119,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:8fe321fcba7b3a471f4f83f98638dbc820fc0abe91f3d53ca55fdb0222e17a8d) +[comment]: # ( SHA256STAMP:96fde8cf67c9b0dda5a1866dfadfb1d7da7e593b3080948662070382d4a9537f) diff --git a/doc/lightning-fetchinvoice.7.md b/doc/lightning-fetchinvoice.7.md index a0d5235e901a..d0bc02d6502a 100644 --- a/doc/lightning-fetchinvoice.7.md +++ b/doc/lightning-fetchinvoice.7.md @@ -88,4 +88,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:fa4e9733716ba263e8288613633ec7e0e466c13fc8067b11588bfd3c88901672) +[comment]: # ( SHA256STAMP:83fcb7141eefc0e5d5bd1d23f6d05f1d32514bad53ed52fc61604ce049c75d54) diff --git a/doc/lightning-fundchannel.7.md b/doc/lightning-fundchannel.7.md index fe44b2a21f8e..420892526988 100644 --- a/doc/lightning-fundchannel.7.md +++ b/doc/lightning-fundchannel.7.md @@ -114,4 +114,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:4bde4785d98f4fdb74ea2415b89ddc864fdf09bd9a30f8056a376aaa668a84b8) +[comment]: # ( SHA256STAMP:d396512cad4bfd533dda947a12aee0aecda05e39c2a7ad7e6b04a3602fbae85d) diff --git a/doc/lightning-fundchannel_cancel.7.md b/doc/lightning-fundchannel_cancel.7.md index 55133d9109b8..fbc49b7054b5 100644 --- a/doc/lightning-fundchannel_cancel.7.md +++ b/doc/lightning-fundchannel_cancel.7.md @@ -59,4 +59,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:d433fc29ad064a09c92160038973c7161bb56947166a2701c0d5d278e276917c) +[comment]: # ( SHA256STAMP:a670eb1f4475ad33b3fc20994205adbf12fad8bb93e5e805e0b8a8ea1db15136) diff --git a/doc/lightning-fundchannel_complete.7.md b/doc/lightning-fundchannel_complete.7.md index e1690fe2074e..5a71e2490af5 100644 --- a/doc/lightning-fundchannel_complete.7.md +++ b/doc/lightning-fundchannel_complete.7.md @@ -61,4 +61,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6fad848d20b3e0a6085790085b0aa91d24cc33e4b0127fc40521ce9c102182d1) +[comment]: # ( SHA256STAMP:f7b14faee0218a2eee7c0df17c52b1d4502c898d1767644bd891027116eb8868) diff --git a/doc/lightning-fundchannel_start.7.md b/doc/lightning-fundchannel_start.7.md index c0d22abcdf37..490650442fb8 100644 --- a/doc/lightning-fundchannel_start.7.md +++ b/doc/lightning-fundchannel_start.7.md @@ -83,4 +83,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6dc3dd4d3d65baa617b285fd3f6e746d62e2806635a8f8852fd3a94ef6fe3e6a) +[comment]: # ( SHA256STAMP:5062025dc172a552f1a33fd1e3600c0fbfc1405f030ea049da88da30a5035456) diff --git a/doc/lightning-funderupdate.7.md b/doc/lightning-funderupdate.7.md index 700ecb9bfc98..2e8999cfc891 100644 --- a/doc/lightning-funderupdate.7.md +++ b/doc/lightning-funderupdate.7.md @@ -146,4 +146,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:01be8ecebe9025991de323bde9bc41591a9cde1b106fa01fc328451d31eb9a70) +[comment]: # ( SHA256STAMP:7fb486ed4c0ec0e72c51bc5a167a1280a9572c61c9467b5819e6624a54877cfb) diff --git a/doc/lightning-fundpsbt.7.md b/doc/lightning-fundpsbt.7.md index 177d26f21ea7..0b138e9fc852 100644 --- a/doc/lightning-fundpsbt.7.md +++ b/doc/lightning-fundpsbt.7.md @@ -114,4 +114,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:635cc321d158bcdb3ca24f13c9955cc9b867e34247c1cf3d91edbbe21eb06a48) +[comment]: # ( SHA256STAMP:0cd239969d70c9261f0d7309762e3d2e646ddd0c62dc7dd8b08515c03cc5385b) diff --git a/doc/lightning-getinfo.7.md b/doc/lightning-getinfo.7.md index 8330ee0052b1..234e9da8641f 100644 --- a/doc/lightning-getinfo.7.md +++ b/doc/lightning-getinfo.7.md @@ -128,4 +128,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:52175b0eced3ed2992d27b983b50afe080134702874116ce0c8355a8adddd440) +[comment]: # ( SHA256STAMP:aedad2e6949f96d8d331e39c17effe5786816729562987b058d146b4b94286cb) diff --git a/doc/lightning-getlog.7.md b/doc/lightning-getlog.7.md index 8007f70ae2a0..5b625f04ec74 100644 --- a/doc/lightning-getlog.7.md +++ b/doc/lightning-getlog.7.md @@ -90,4 +90,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:963fc75819ffb63271f25e31f30a6fe54457803d8bf296556589f76874fb39c0) +[comment]: # ( SHA256STAMP:46482f3cc6b332b284cae1b1e5477b19e227cb6c1cd1086452d28f0887433cb1) diff --git a/doc/lightning-getroute.7.md b/doc/lightning-getroute.7.md index 7a6ec76c831f..1e7fb5d48b3b 100644 --- a/doc/lightning-getroute.7.md +++ b/doc/lightning-getroute.7.md @@ -309,4 +309,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:3494cb4003abfe32e8942ec5d92d0c464815d5e65edf29087cd2193eb414d694) +[comment]: # ( SHA256STAMP:db8834d9a318688d2c4801b85f06aa5afb3120e064b3654433469bca09e776a0) diff --git a/doc/lightning-getsharedsecret.7.md b/doc/lightning-getsharedsecret.7.md index 72b24eedc6db..505986a6e957 100644 --- a/doc/lightning-getsharedsecret.7.md +++ b/doc/lightning-getsharedsecret.7.md @@ -91,4 +91,4 @@ RESOURCES * Main web site: -[comment]: # ( SHA256STAMP:e54898c6b950be6242a641212b71b6ce33ea31068f3572cd42be5d2b87365eb7) +[comment]: # ( SHA256STAMP:47c5b466b02b80d40937f40c725733f72c20f3bc26cc7f4dacd5ef858ab0282b) diff --git a/doc/lightning-help.7.md b/doc/lightning-help.7.md index 061e97771d1a..5c5dbc2e36e5 100644 --- a/doc/lightning-help.7.md +++ b/doc/lightning-help.7.md @@ -67,4 +67,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:262fdbfc6ea8142c57637e5c48a9536b0e8577ef823ebfc830cc0c14d56fb08d) +[comment]: # ( SHA256STAMP:881f00fb7943bc1655c054488643a4da37742b6705924f0ba33366e8cf3f2b93) diff --git a/doc/lightning-invoice.7.md b/doc/lightning-invoice.7.md index a0da46b86389..c08f2dfec3e5 100644 --- a/doc/lightning-invoice.7.md +++ b/doc/lightning-invoice.7.md @@ -117,4 +117,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:834b9d7b84845d423a677662b66b9109b3b8c4b7219a91d98f2817561d68a8cd) +[comment]: # ( SHA256STAMP:ea76df1915a45de45039cbbe8add3fe86416f7cba133d8f0d364d28ef276198c) diff --git a/doc/lightning-keysend.7.md b/doc/lightning-keysend.7.md index da48b95f89a9..515998e9b8c2 100644 --- a/doc/lightning-keysend.7.md +++ b/doc/lightning-keysend.7.md @@ -114,4 +114,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:449315de94f49452c3d485775dd97bc2517763be420ebc74024914680359d1ff) +[comment]: # ( SHA256STAMP:f8e12220302756c5a95eef2ec428c1d7adaba3025b0716e6b6581f783d92b648) diff --git a/doc/lightning-listchannels.7.md b/doc/lightning-listchannels.7.md index 54286a9b365c..fff0edda2972 100644 --- a/doc/lightning-listchannels.7.md +++ b/doc/lightning-listchannels.7.md @@ -45,7 +45,7 @@ On success, an object containing **channels** is returned. It is an array of ob - **fee_per_millionth** (u32): Proportional fee changed by *source* to use this channel, in parts-per-million - **delay** (u32): The number of blocks delay required by *source* to use this channel - **htlc_minimum_msat** (msat): The smallest payment *source* will allow via this channel -- **features** (hex): BOLT #9 features bitmap for this channel in channel_announcement message +- **features** (hex): BOLT #9 features bitmap for this channel - **htlc_maximum_msat** (msat, optional): The largest payment *source* will allow via this channel [comment]: # (GENERATE-FROM-SCHEMA-END) @@ -78,4 +78,4 @@ Lightning RFC site - BOLT \#7: -[comment]: # ( SHA256STAMP:e27d51a95411739ee10b082beaca55e33de4b2177b0e39df2223700c3141bc02) +[comment]: # ( SHA256STAMP:43c6c45c0672482610c1bdd607d5bf6ed26d6c42cfc4fbde4a5d24f2eb1d9a2d) diff --git a/doc/lightning-listconfigs.7 b/doc/lightning-listconfigs.7 index 7ab2c1168bb7..2d5e89bbd00c 100644 --- a/doc/lightning-listconfigs.7 +++ b/doc/lightning-listconfigs.7 @@ -33,7 +33,6 @@ showing default values (\fBdev-\fR options are not shown)\. On success, an object is returned, containing: - .RS .IP \[bu] \fB# version\fR (string, optional): Special field indicating the current version @@ -174,7 +173,6 @@ On success, an object is returned, containing: On failure, one of the following error codes may be returned: - .RS .IP \[bu] -32602: Error in given parameters or field with \fIconfig\fR name doesn't exist\. @@ -286,4 +284,4 @@ Vincenzo Palazzo \fI wrote the initial versi Main web site: \fIhttps://github.com/ElementsProject/lightning\fR -\" SHA256STAMP:67e5f100671ed8ef0e490caa46d57dc73e7443caa86a85f32806a0e8183cd1b8 +\" SHA256STAMP:7ac9ef3477f64fd3a4181cb27b8810ecf2c1a082688180716adfe79843ab09aa diff --git a/doc/lightning-listconfigs.7.md b/doc/lightning-listconfigs.7.md index f304e2057b33..f42a96a500b9 100644 --- a/doc/lightning-listconfigs.7.md +++ b/doc/lightning-listconfigs.7.md @@ -212,4 +212,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:ebc37d1f9cb452d312285a8168d2bb6da2d1dba08db56bbb8d3d7f47b58d7fa4) +[comment]: # ( SHA256STAMP:4645e3f14c53ccc23b2ed42c2886064e5d718a8eef5e6bd6dd3a932cadfd8e8f) diff --git a/doc/lightning-listdatastore.7.md b/doc/lightning-listdatastore.7.md index 5b0ecb0171e5..b3e65602f234 100644 --- a/doc/lightning-listdatastore.7.md +++ b/doc/lightning-listdatastore.7.md @@ -46,4 +46,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:1e5d31c36f5aa2d2cb6bedb07a94b18880ba95529885c104b177d91bf251d420) +[comment]: # ( SHA256STAMP:6c6f4c08a88b2a8c8cdc4c36783da86d8e8de0d5ee39261f3304e0eb41f0eb41) diff --git a/doc/lightning-listforwards.7.md b/doc/lightning-listforwards.7.md index 0af6cf491488..8a2ae806053d 100644 --- a/doc/lightning-listforwards.7.md +++ b/doc/lightning-listforwards.7.md @@ -59,4 +59,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:c8adfa0a6dcae939c5da919d7996261db8663a871210e33b426c3b40c30d7b29) +[comment]: # ( SHA256STAMP:de237318dfea0b02d6ca34710432a3b739012beb84f74e41e720cd9889675954) diff --git a/doc/lightning-listfunds.7.md b/doc/lightning-listfunds.7.md index 1ce69088b37b..12d060c9e22a 100644 --- a/doc/lightning-listfunds.7.md +++ b/doc/lightning-listfunds.7.md @@ -68,4 +68,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:fdc550a0ff11f6fbbf51c29340c0494077d831566ae7ab008cce4b93034a76c5) +[comment]: # ( SHA256STAMP:61be4b00c0485edccb986e1f066cf18a5c9fdb8bca94adc12f0a87a36041a93a) diff --git a/doc/lightning-listinvoices.7.md b/doc/lightning-listinvoices.7.md index 0524f5904352..52ab2d14fc8f 100644 --- a/doc/lightning-listinvoices.7.md +++ b/doc/lightning-listinvoices.7.md @@ -56,4 +56,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:1178a5178a20b2aca9c52fe39e332bd1d6c4f20fa302639bed0fbfc6eb348c40) +[comment]: # ( SHA256STAMP:7e45fcb50a446f35e441df4a6c04626a045d237407231bde044c95aabc689519) diff --git a/doc/lightning-listnodes.7.md b/doc/lightning-listnodes.7.md index 314530684752..7a36dd71a55d 100644 --- a/doc/lightning-listnodes.7.md +++ b/doc/lightning-listnodes.7.md @@ -34,7 +34,7 @@ On success, an object containing **nodes** is returned. It is an array of objec If **last_timestamp** is present: - **alias** (string): The fun alias this node advertized (up to 32 characters) - **color** (hex): The favorite RGB color this node advertized (always 6 characters) - - **features** (hex): BOLT #9 features bitmap this node advertized in node_announcement message + - **features** (hex): BOLT #9 features bitmap this node advertized - **addresses** (array of objects): The addresses this node advertized: - **type** (string): Type of connection (one of "dns", "ipv4", "ipv6", "torv2", "torv3", "websocket") - **port** (u16): port number @@ -95,4 +95,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:85400c9c1741943e2e02935b4f14fd187a7db6056410e42adec07ef3c6772f5f) +[comment]: # ( SHA256STAMP:df4e056ac91672041b38811329eb7555636c7b4d4985456894255a7b8e11bf54) diff --git a/doc/lightning-listoffers.7.md b/doc/lightning-listoffers.7.md index 7a5b76965cc9..b684d749ec9a 100644 --- a/doc/lightning-listoffers.7.md +++ b/doc/lightning-listoffers.7.md @@ -80,4 +80,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:5cae5e0e423e66b02602ecc433de9686b16630979e794944059c65a100f54f9e) +[comment]: # ( SHA256STAMP:aad235e8255da495032f638a7066b05d651e2c99b668f7b3afffb21d908c788a) diff --git a/doc/lightning-listpays.7.md b/doc/lightning-listpays.7.md index 8f098ec98273..f8c44bfb85f8 100644 --- a/doc/lightning-listpays.7.md +++ b/doc/lightning-listpays.7.md @@ -57,4 +57,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:3c158259410ff8eb81669e26eca9ee53017002d739f89e7f0e2fd8e61edb8a14) +[comment]: # ( SHA256STAMP:ec7234aa1ec9979cdc71a5bfe861296ba90efdf30236922a822b2ecab6fd9635) diff --git a/doc/lightning-listpeers.7.md b/doc/lightning-listpeers.7.md index 170db4166712..1a5961802349 100644 --- a/doc/lightning-listpeers.7.md +++ b/doc/lightning-listpeers.7.md @@ -384,4 +384,4 @@ Main web site: Lightning RFC site (BOLT \#9): -[comment]: # ( SHA256STAMP:fcfc465cbbe95430f4fc6473099142c576883e333ef9fe31d04372f411e49f6d) +[comment]: # ( SHA256STAMP:c26d3094925387ee935efc6351400bca374c361e5956ff13f10b228773f8e389) diff --git a/doc/lightning-listsendpays.7.md b/doc/lightning-listsendpays.7.md index c2511d09f583..174ebde0d294 100644 --- a/doc/lightning-listsendpays.7.md +++ b/doc/lightning-listsendpays.7.md @@ -61,4 +61,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:eaa0b4c6309d45bc2a72baf44288f1faa75d7f6ff2e8bf6d03be53747fe82c84) +[comment]: # ( SHA256STAMP:fa2e28ae1fdc4df5357ecc12984b2ec478cd591868484613dccf455cbc502fd9) diff --git a/doc/lightning-listtransactions.7.md b/doc/lightning-listtransactions.7.md index ed219f631076..f90eb7c04380 100644 --- a/doc/lightning-listtransactions.7.md +++ b/doc/lightning-listtransactions.7.md @@ -104,4 +104,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:74408f25dcf548f1389ab41123748297ba3116ad75afb41b86ecca453b95fec8) +[comment]: # ( SHA256STAMP:4d5d2f1cea0668b3e58e73a93fe6d217ac4a8c740bed09fcdce21c9e72daae99) diff --git a/doc/lightning-makesecret.7.md b/doc/lightning-makesecret.7.md new file mode 100644 index 000000000000..2fdbf9755ae2 --- /dev/null +++ b/doc/lightning-makesecret.7.md @@ -0,0 +1,44 @@ +lightning-makesecret -- Command for deriving pseudorandom key from HSM +===================================================================== + +SYNOPSIS +-------- + +**makesecret** *info_hex* + +DESCRIPTION +----------- + +The **makesecret** RPC command derives a secret key from the HSM_secret. + +The *info_hex* can be any hex data. + +RETURN VALUE +------------ + +[comment]: # (GENERATE-FROM-SCHEMA-START) +On success, an object is returned, containing: +- **secret** (secret): the pseudorandom key derived from HSM_secret (always 64 characters) + +[comment]: # (GENERATE-FROM-SCHEMA-END) + + +The following error codes may occur: +- -1: Catchall nonspecific error. + +AUTHOR +------ + +Aditya <> is mainly responsible. + +SEE ALSO +-------- + +lightning-getsharedsecret(7) + +RESOURCES +--------- + +Main web site: + +[comment]: # ( SHA256STAMP:1bd94ffa8440041efafe93440d9828be6baca199b0f5cb73220e4482582bf01d) diff --git a/doc/lightning-multifundchannel.7.md b/doc/lightning-multifundchannel.7.md index bd492f8920ce..a9e75bb6283e 100644 --- a/doc/lightning-multifundchannel.7.md +++ b/doc/lightning-multifundchannel.7.md @@ -158,4 +158,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:a6358ad8d361ae4104c727e6b8ab342923a613b78d5f13552794f827a1125e8b) +[comment]: # ( SHA256STAMP:49c7f69eb4b532802c465ac5d0421cdad176f6a28c4c8e4c1c3ee0a94faad5bf) diff --git a/doc/lightning-multiwithdraw.7.md b/doc/lightning-multiwithdraw.7.md index 4242f4c0aeef..2e39c8876df2 100644 --- a/doc/lightning-multiwithdraw.7.md +++ b/doc/lightning-multiwithdraw.7.md @@ -71,4 +71,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:044cdcd69e6ece931b6d0f9b25dd842fd456ee479725e610c03694210256583f) +[comment]: # ( SHA256STAMP:1fe5147036f714c8f9185dd482a1bfa3e3ac5c4d0b6603fba1bc2b78de591b8f) diff --git a/doc/lightning-newaddr.7 b/doc/lightning-newaddr.7 index 56d9bc736919..2d76029e774b 100644 --- a/doc/lightning-newaddr.7 +++ b/doc/lightning-newaddr.7 @@ -32,7 +32,6 @@ To send an on-chain payment \fIfrom\fR the Core Lightning node wallet, use \fBwi On success, an object is returned, containing: - .RS .IP \[bu] \fBbech32\fR (string, optional): The bech32 (native segwit) address @@ -57,4 +56,4 @@ Felix \fI is mainly responsible\. Main web site: \fIhttps://github.com/ElementsProject/lightning\fR -\" SHA256STAMP:51dfdd41da7c5ff7dc82c1782f3f8f8448a99f9d0d243fb57443cf1b2d929372 +\" SHA256STAMP:62fcbc384a244851f34f9d30a7e5ae79c767fc6bca96b818ec8e11619afc397d diff --git a/doc/lightning-newaddr.7.md b/doc/lightning-newaddr.7.md index 55e8235b4eac..80865b8ddfe6 100644 --- a/doc/lightning-newaddr.7.md +++ b/doc/lightning-newaddr.7.md @@ -57,4 +57,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:1a7b5336bdb0dbc93c9e160bb36c20c0d0d3fb908bdd85a84499fbc99680f3a6) +[comment]: # ( SHA256STAMP:550089858649865ed4d23384dcc5deeef314f5a1976a9610e611dbe17c1063d6) diff --git a/doc/lightning-notifications.7.md b/doc/lightning-notifications.7.md index 5667fb773bc2..0bf4ddcbf03f 100644 --- a/doc/lightning-notifications.7.md +++ b/doc/lightning-notifications.7.md @@ -102,4 +102,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:1a64fbaed63ffee21df3d46956a6dca193982b1b135a9b095e68652a720c77ac) +[comment]: # ( SHA256STAMP:c801b02463804504c2387387a36a6739351330a2c496aaa10de2b1f49c36ed32) diff --git a/doc/lightning-offer.7.md b/doc/lightning-offer.7.md index 22b903efbbf3..5bc01dfa858a 100644 --- a/doc/lightning-offer.7.md +++ b/doc/lightning-offer.7.md @@ -134,4 +134,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:4bbcec9c30f77239db780945965ad5cccf702365c3e592921fac57ed6bfd080f) +[comment]: # ( SHA256STAMP:3b7b337e724de4cd867dbbf65700a20d92db728892394f4d0229af70659fd7e2) diff --git a/doc/lightning-offerout.7.md b/doc/lightning-offerout.7.md index e74589c02193..f96d19149508 100644 --- a/doc/lightning-offerout.7.md +++ b/doc/lightning-offerout.7.md @@ -99,4 +99,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:fb60c3239f3d47b421f842304263ec73f864a307b77e39265653c3e85880a483) +[comment]: # ( SHA256STAMP:4ef2ac36e19f11e81645fb0b94fe7f4d7dad74faf7c77628e29967d9f1192154) diff --git a/doc/lightning-openchannel_abort.7.md b/doc/lightning-openchannel_abort.7.md index 77748c6af79d..f05fba23f54e 100644 --- a/doc/lightning-openchannel_abort.7.md +++ b/doc/lightning-openchannel_abort.7.md @@ -54,4 +54,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:78d6fbc1044e3a499ca618ea71845aa04043f46c169f4f50763644c7a3e35572) +[comment]: # ( SHA256STAMP:014c926a7202b951a2407b1a9996c90d4dd68aadfdbdb04311b280c016d538dc) diff --git a/doc/lightning-openchannel_bump.7.md b/doc/lightning-openchannel_bump.7.md index a863eb0fcf31..66028426b0c3 100644 --- a/doc/lightning-openchannel_bump.7.md +++ b/doc/lightning-openchannel_bump.7.md @@ -80,4 +80,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:0b3c4fc19cdad9162b91585c4af2dc5293ecd8925628d10b612cd777dcdedeea) +[comment]: # ( SHA256STAMP:2846dc5350c8a1ac5d0e33fc52a37f5e535e6db5b4080ae2be9c3df428ccf122) diff --git a/doc/lightning-openchannel_init.7.md b/doc/lightning-openchannel_init.7.md index e67a14150800..d8df70e08b97 100644 --- a/doc/lightning-openchannel_init.7.md +++ b/doc/lightning-openchannel_init.7.md @@ -102,4 +102,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:bd405699ff27104ccc97dec81be9de1e7459c91333d78616268e4e9c198ee5af) +[comment]: # ( SHA256STAMP:70ebfff5ce81962cf574b39cb3d95206b1f1541d24b8a3a0380b6f0b594d0ca4) diff --git a/doc/lightning-openchannel_signed.7.md b/doc/lightning-openchannel_signed.7.md index 51dec370a7bf..72972f6eda48 100644 --- a/doc/lightning-openchannel_signed.7.md +++ b/doc/lightning-openchannel_signed.7.md @@ -66,4 +66,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:d85297e1ab0b3bbf206082c479dcfdc6469461e531321ce5576c6ff7f296d481) +[comment]: # ( SHA256STAMP:304d819b092e1d9ce7b4cd8ef08ecdd7952b454fed59e908ab1af02b50e9a0b0) diff --git a/doc/lightning-openchannel_update.7.md b/doc/lightning-openchannel_update.7.md index 55618e278c32..aa01a08a8147 100644 --- a/doc/lightning-openchannel_update.7.md +++ b/doc/lightning-openchannel_update.7.md @@ -71,4 +71,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:22ff9536e97ea194d9d9ba10a4f3244a0818a1605502b7ed25241a3a97f041d1) +[comment]: # ( SHA256STAMP:1a29b970038901773c6712c5e9267ae2c0ed3e9d4b11543d287c272a031003c1) diff --git a/doc/lightning-parsefeerate.7.md b/doc/lightning-parsefeerate.7.md index d46d7f22c4b9..b521e8cdc1e1 100644 --- a/doc/lightning-parsefeerate.7.md +++ b/doc/lightning-parsefeerate.7.md @@ -43,4 +43,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:045cab2977c7fcc12ed5267d4007a704028a00bc07f90265ed1cd7a46a414e63) +[comment]: # ( SHA256STAMP:f3498aa6f16d5be0a49896ae67144558df1baa223ac396a90ddf2d89a42ff395) diff --git a/doc/lightning-pay.7.md b/doc/lightning-pay.7.md index 223bfb086f75..8301fbb602ff 100644 --- a/doc/lightning-pay.7.md +++ b/doc/lightning-pay.7.md @@ -165,4 +165,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:b8ff255c1f4d284535d70f13d3bd85c3d20ef8fdee081835a57fb04528311db6) +[comment]: # ( SHA256STAMP:aa9dad9f5f97e1ad3a1a79c923dd57a685d7fada1545987f8ca8021ed92aa4eb) diff --git a/doc/lightning-ping.7.md b/doc/lightning-ping.7.md index 0088748d9024..d77129a4a5ef 100644 --- a/doc/lightning-ping.7.md +++ b/doc/lightning-ping.7.md @@ -69,4 +69,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:a78a1d58cfe1fbf654ee58aad20ffcaa075f63bd8774c64be5ec28857e95ae3b) +[comment]: # ( SHA256STAMP:59da52931ba9cb4c192ab81973efed2246baa9a97aded29e2c4cf280972c9a9a) diff --git a/doc/lightning-plugin.7.md b/doc/lightning-plugin.7.md index a79cb4d7b92b..82177d676207 100644 --- a/doc/lightning-plugin.7.md +++ b/doc/lightning-plugin.7.md @@ -81,4 +81,4 @@ RESOURCES Main web site: [writing plugins]: PLUGINS.md -[comment]: # ( SHA256STAMP:5c3b25ecb137bfe7a81f80f0b4183a9e1282530ebfac3b1bc05fc5406f59cfc7) +[comment]: # ( SHA256STAMP:4ed30fb62c37111ea06b55d1252727c9c56fabd40e9e1f50083c99de74b8dfa1) diff --git a/doc/lightning-recoverchannel.7.md b/doc/lightning-recoverchannel.7.md new file mode 100644 index 000000000000..c1d2e32da78e --- /dev/null +++ b/doc/lightning-recoverchannel.7.md @@ -0,0 +1,45 @@ +lightning-recoverchannel -- Command for recovering channels bundeled in an array in the form of *Static Backup* +=============================================================================================================== + +SYNOPSIS +-------- + +**recoverchannel** *scb* + +DESCRIPTION +----------- + +The **recoverchannel** RPC command tries to force the peer (with whom you +already had a channel) to close the channel and sweeps on-chain fund. This +method is not spontaneous and depends on the peer, so use it in case of +severe data loss. + +The *scb* parameter is an array containing minimum required info to +reconnect and sweep funds. You can get the scb for already stored channels +by using the RPC command 'staticbackup' + + +RETURN VALUE +------------ + +On success, an object is returned, containing: +- **stubs** (array of hexs): + - Each item is the channel ID of the channel successfully inserted + + +AUTHOR +------ + +Aditya <> is mainly responsible. + +SEE ALSO +-------- + +lightning-getsharedsecret(7) + +RESOURCES +--------- + +Main web site: + +[comment]: # ( SHA256STAMP:9cfaa9eb4609b36accc3e3b12a352c00ddd402307e4461f4df274146d12f6eb0) \ No newline at end of file diff --git a/doc/lightning-reserveinputs.7.md b/doc/lightning-reserveinputs.7.md index 2cdc30649b10..c8562d838158 100644 --- a/doc/lightning-reserveinputs.7.md +++ b/doc/lightning-reserveinputs.7.md @@ -63,4 +63,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:a675e16a820eca4da07743ace010deaa12aa51d2c3d73d4db6b32ffb8ee65f7a) +[comment]: # ( SHA256STAMP:45c13e920465d313c693db6bfea8ac2f66d1e40226ef78241f82f51df9b715b2) diff --git a/doc/lightning-sendcustommsg.7.md b/doc/lightning-sendcustommsg.7.md index 5d3b8492046a..601e91e43cfa 100644 --- a/doc/lightning-sendcustommsg.7.md +++ b/doc/lightning-sendcustommsg.7.md @@ -68,4 +68,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:f07e2df415b1ec2ad7b19acdd2909616d7aa54bb3c5ae69359d4c8b87ee839bf) +[comment]: # ( SHA256STAMP:29749d2978455477670d15627d51a6c1e9493136431539640a81e85ab7104d4e) diff --git a/doc/lightning-sendinvoice.7.md b/doc/lightning-sendinvoice.7.md index 5fc675ed1f6b..8f3e262b1465 100644 --- a/doc/lightning-sendinvoice.7.md +++ b/doc/lightning-sendinvoice.7.md @@ -78,4 +78,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:b4cf6c380589a566c695e96f3668294b4411a57c7724aa68b293bac9e2194462) +[comment]: # ( SHA256STAMP:d227800f16140429a3352bc28f023df8d03c93a54012efcdfdd1f307511c4356) diff --git a/doc/lightning-sendonion.7.md b/doc/lightning-sendonion.7.md index 72aec8dfbd78..321a4ad4a339 100644 --- a/doc/lightning-sendonion.7.md +++ b/doc/lightning-sendonion.7.md @@ -128,4 +128,4 @@ RESOURCES Main web site: [bolt04]: https://github.com/lightningnetwork/lightning-rfc/blob/master/04-onion-routing.md -[comment]: # ( SHA256STAMP:d2f4991d271147dd8c13859376f36f2d8843a96034e818a434555a09bf6fd003) +[comment]: # ( SHA256STAMP:4e329c9768eb9d53d3b1068b18c7eaad46f75fa1a57724be4cbb64dc3c324a04) diff --git a/doc/lightning-sendonionmessage.7.md b/doc/lightning-sendonionmessage.7.md index 7da3b9d96b0b..6e1db0a41204 100644 --- a/doc/lightning-sendonionmessage.7.md +++ b/doc/lightning-sendonionmessage.7.md @@ -43,4 +43,4 @@ Main web site: [bolt04]: https://github.com/lightningnetwork/lightning-rfc/blob/master/04-onion-routing.md -[comment]: # ( SHA256STAMP:39a66bd8e28db8780d7b1365372f7cc638b32a80bb5515657d381b4520f06901) +[comment]: # ( SHA256STAMP:19732c05461b56bb430b3fe568deba807f29a31324252fe748b859b028e649f3) diff --git a/doc/lightning-sendpay.7.md b/doc/lightning-sendpay.7.md index f332e812f269..57b4f24e4366 100644 --- a/doc/lightning-sendpay.7.md +++ b/doc/lightning-sendpay.7.md @@ -139,4 +139,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:a7f55104f3bdb21057a410a33902b92aca38aaa83b1e0e7e6876a911316132ed) +[comment]: # ( SHA256STAMP:9d998118234ab83c68d5add16a10b870edf4530c4a2c9e904b0f581b261611d1) diff --git a/doc/lightning-sendpsbt.7.md b/doc/lightning-sendpsbt.7.md index fd150b9d38fa..b6473480bfb8 100644 --- a/doc/lightning-sendpsbt.7.md +++ b/doc/lightning-sendpsbt.7.md @@ -65,4 +65,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:044cdcd69e6ece931b6d0f9b25dd842fd456ee479725e610c03694210256583f) +[comment]: # ( SHA256STAMP:1fe5147036f714c8f9185dd482a1bfa3e3ac5c4d0b6603fba1bc2b78de591b8f) diff --git a/doc/lightning-setchannel.7.md b/doc/lightning-setchannel.7.md index 6a724c9cdd7c..e39691f252d4 100644 --- a/doc/lightning-setchannel.7.md +++ b/doc/lightning-setchannel.7.md @@ -103,4 +103,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:a38b5ea12566d9e40eab07b95a90007bf66373ac1189f458d1678634522575b3) +[comment]: # ( SHA256STAMP:53cf2c58a961078e501b6034e3eed1c5c2d70ed02fc5b167b26ff43c2e2d196f) diff --git a/doc/lightning-setchannelfee.7.md b/doc/lightning-setchannelfee.7.md index 75a4147b861a..a9a23070b01e 100644 --- a/doc/lightning-setchannelfee.7.md +++ b/doc/lightning-setchannelfee.7.md @@ -82,4 +82,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:2245fde48f1858886e0f484cb3d96331fef9c41b0081ae51478d912189c38907) +[comment]: # ( SHA256STAMP:ac1cbc87d916cec68cea18d43dc561b3dd655a7f6e2bdaec1a4ebf47bb32b4ad) diff --git a/doc/lightning-signmessage.7.md b/doc/lightning-signmessage.7.md index 86fa363fd986..93608b1dbdf5 100644 --- a/doc/lightning-signmessage.7.md +++ b/doc/lightning-signmessage.7.md @@ -41,4 +41,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:028ade4d84a65b0438347897f4ff5cfc99b5f22d8320b606c9630a1f9da16ef2) +[comment]: # ( SHA256STAMP:137e80fcb45c2e93058a869cb991c4aac31dace621f5941e91b9039290659648) diff --git a/doc/lightning-signpsbt.7.md b/doc/lightning-signpsbt.7.md index cef87f311044..6ebc481dd830 100644 --- a/doc/lightning-signpsbt.7.md +++ b/doc/lightning-signpsbt.7.md @@ -71,4 +71,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:5f7bc2a5f8b6fe72bf70caa3ff14d6f1260c2d366becbc7798ee3bb0374e0b1b) +[comment]: # ( SHA256STAMP:a64f3742f0c66ddf203afa3f69859d4385c4156fe99c30f0931e41ce95d944b1) diff --git a/doc/lightning-staticbackup.7.md b/doc/lightning-staticbackup.7.md new file mode 100644 index 000000000000..8cb5bfa1ceaa --- /dev/null +++ b/doc/lightning-staticbackup.7.md @@ -0,0 +1,38 @@ +lightning-staticbacup -- Command for deriving getting SCB of all the existing channels +====================================================================================== + +SYNOPSIS +-------- + +**staticbackup** + +DESCRIPTION +----------- + +The **staticbackup** RPC command returns an object with SCB of all the channels in an array. + + +RETURN VALUE +------------ + +On success, an object is returned, containing: +- **scb** (array of hexs): + - Each item is SCB of a channel in TLV format + + +AUTHOR +------ + +Aditya <> is mainly responsible. + +SEE ALSO +-------- + +lightning-getsharedsecret(7) + +RESOURCES +--------- + +Main web site: + +[comment]: # ( SHA256STAMP:9cfaa9eb4609b36accc3e3b12a352c00ddd402307e4461f4df274146d12f6eb0) diff --git a/doc/lightning-stop.7.md b/doc/lightning-stop.7.md index cb83aad34ead..d3c452b42e94 100644 --- a/doc/lightning-stop.7.md +++ b/doc/lightning-stop.7.md @@ -42,4 +42,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:bbdf7415bc7de519ca944c28326c334d9f014f4c987d7e3017ac628c6d1c55ec) +[comment]: # ( SHA256STAMP:a83ac745b36e0e3d00ba11f036cec93973773f47e1265eb5c70a3d3298e58e4b) diff --git a/doc/lightning-txdiscard.7.md b/doc/lightning-txdiscard.7.md index 1144328306a5..b0475e342e4a 100644 --- a/doc/lightning-txdiscard.7.md +++ b/doc/lightning-txdiscard.7.md @@ -44,4 +44,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:ced935d8d9047fe1dfb746fc72aafc5b99a8b7b639f854a56478884e5205ffb9) +[comment]: # ( SHA256STAMP:8a6857f312d202e3328443d6ca25b5318d6b5d8fe5655ff6c70466e54c5cd42d) diff --git a/doc/lightning-txprepare.7.md b/doc/lightning-txprepare.7.md index 8b9f16fb4fe1..c22437fd5c37 100644 --- a/doc/lightning-txprepare.7.md +++ b/doc/lightning-txprepare.7.md @@ -84,4 +84,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:f16a12290870442316c8f3fb552627637610ab6a7cfed9082089040c78dce2be) +[comment]: # ( SHA256STAMP:c32c4fe613e5fa173d26bb144fb173d34d2c9181f4eb5da7ef413d41f44f95d7) diff --git a/doc/lightning-txsend.7.md b/doc/lightning-txsend.7.md index 8bb18b6c1893..2d2673093a92 100644 --- a/doc/lightning-txsend.7.md +++ b/doc/lightning-txsend.7.md @@ -44,4 +44,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:5bf27f1cbcb247cde5c5570f90be77fc7e8b3e8c80622e75c31e6ac445f2b910) +[comment]: # ( SHA256STAMP:1934c53b0448f872c17b35cfd76b887f3599924213d29ba249b076ff5503be42) diff --git a/doc/lightning-unreserveinputs.7.md b/doc/lightning-unreserveinputs.7.md index 869adbb3f576..323f24f63e0b 100644 --- a/doc/lightning-unreserveinputs.7.md +++ b/doc/lightning-unreserveinputs.7.md @@ -53,4 +53,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:f7aca3e1a40d66e07986cb9e98033e815c4eea2237dc75664a6c47951a8132ed) +[comment]: # ( SHA256STAMP:86bf213ca69b042fec2cf4241875a923db21aef9830e690bd1fb495ffd120966) diff --git a/doc/lightning-utxopsbt.7.md b/doc/lightning-utxopsbt.7.md index bc20d1830cf7..1bf65387c3ae 100644 --- a/doc/lightning-utxopsbt.7.md +++ b/doc/lightning-utxopsbt.7.md @@ -99,4 +99,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:3c3734a0eb4c2fabf216e11e729ad582cb1fb91dbcb8d2bfc44d56f3206f20fc) +[comment]: # ( SHA256STAMP:5037d26b92d3481a9eac98f509ac2dcee3f3185d6783f3a549d06a9e2e5e1a5f) diff --git a/doc/lightning-waitanyinvoice.7.md b/doc/lightning-waitanyinvoice.7.md index 525503312e0a..a19b6850ddff 100644 --- a/doc/lightning-waitanyinvoice.7.md +++ b/doc/lightning-waitanyinvoice.7.md @@ -73,4 +73,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6c4df3bb97df9f87583725ef31e803900ac548e17506692f9da365a3e4bbf18f) +[comment]: # ( SHA256STAMP:b781ec3594dc6b0ac3091fc2d6561aae91f93a00a922f90285bf8828270ae26c) diff --git a/doc/lightning-waitblockheight.7.md b/doc/lightning-waitblockheight.7.md index 7eae32216db4..b3405d2ba238 100644 --- a/doc/lightning-waitblockheight.7.md +++ b/doc/lightning-waitblockheight.7.md @@ -38,4 +38,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:98f9993935e2820e8e407d1743764346ca6fa1b72228cc82827617a2ed3f3c80) +[comment]: # ( SHA256STAMP:c0440c779f4274b2e2bf4c9e5889a3ef9855c9e9a698d5a50dd8d80eb35c0683) diff --git a/doc/lightning-waitinvoice.7.md b/doc/lightning-waitinvoice.7.md index d568183afa98..b3b645b3fcb2 100644 --- a/doc/lightning-waitinvoice.7.md +++ b/doc/lightning-waitinvoice.7.md @@ -58,4 +58,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:6c4df3bb97df9f87583725ef31e803900ac548e17506692f9da365a3e4bbf18f) +[comment]: # ( SHA256STAMP:b781ec3594dc6b0ac3091fc2d6561aae91f93a00a922f90285bf8828270ae26c) diff --git a/doc/lightning-waitsendpay.7.md b/doc/lightning-waitsendpay.7.md index a44abd8e3ac9..1801159b33cf 100644 --- a/doc/lightning-waitsendpay.7.md +++ b/doc/lightning-waitsendpay.7.md @@ -101,4 +101,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:96e5cfd0bd6f2d6b7a25a60f846283592404cee07ef142e58cd56929cc6923c9) +[comment]: # ( SHA256STAMP:8b5a3a8ce1f3c2dcd3e2b8a262d15bcd61700f971830e939a841352aa9d0f849) diff --git a/doc/lightning-withdraw.7.md b/doc/lightning-withdraw.7.md index 3658341455db..e71f951348aa 100644 --- a/doc/lightning-withdraw.7.md +++ b/doc/lightning-withdraw.7.md @@ -73,4 +73,4 @@ RESOURCES Main web site: -[comment]: # ( SHA256STAMP:cef8d48a59313019e671900621426733d47be2f0c22d5cb2d06ce0b9b7d43592) +[comment]: # ( SHA256STAMP:ee610c5e83e620125e8583022768f0c3293db2326e879b248e67eaddd655c18e) diff --git a/doc/schemas/emergencyrecover.request.json b/doc/schemas/emergencyrecover.request.json new file mode 100644 index 000000000000..f99496c5ac84 --- /dev/null +++ b/doc/schemas/emergencyrecover.request.json @@ -0,0 +1,7 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "required": [], + "additionalProperties": false, + "properties": {} +} diff --git a/doc/schemas/emergencyrecover.schema.json b/doc/schemas/emergencyrecover.schema.json new file mode 100644 index 000000000000..127dfbc6bf43 --- /dev/null +++ b/doc/schemas/emergencyrecover.schema.json @@ -0,0 +1,17 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "stubs" + ], + "properties": { + "stubs": { + "type": "array", + "items": { + "type": "string", + "description": "Channel IDs of channels successfully inserted." + } + } + } +} diff --git a/doc/schemas/makesecret.request.json b/doc/schemas/makesecret.request.json new file mode 100644 index 000000000000..a43ac493e2bd --- /dev/null +++ b/doc/schemas/makesecret.request.json @@ -0,0 +1,14 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "info_hex" + ], + "properties": { + "info": { + "type": "hex", + "description": "This will be used for deriving the secret" + } + } +} diff --git a/doc/schemas/makesecret.schema.json b/doc/schemas/makesecret.schema.json new file mode 100644 index 000000000000..ce17c2fcb7cd --- /dev/null +++ b/doc/schemas/makesecret.schema.json @@ -0,0 +1,16 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "secret" + ], + "properties": { + "secret": { + "type": "secret", + "description": "the pseudorandom key derived from HSM_secret", + "maxLength": 64, + "minLength": 64 + } + } +} diff --git a/doc/schemas/recoverchannel.request.json b/doc/schemas/recoverchannel.request.json new file mode 100644 index 000000000000..ea6701bc2000 --- /dev/null +++ b/doc/schemas/recoverchannel.request.json @@ -0,0 +1,15 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "scb" + ], + "scb": { + "type": "array", + "description": "SCB of the channels in an array", + "items": { + "type": "hexstr" + } + } +} diff --git a/doc/schemas/recoverchannel.schema.json b/doc/schemas/recoverchannel.schema.json new file mode 100644 index 000000000000..127dfbc6bf43 --- /dev/null +++ b/doc/schemas/recoverchannel.schema.json @@ -0,0 +1,17 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "stubs" + ], + "properties": { + "stubs": { + "type": "array", + "items": { + "type": "string", + "description": "Channel IDs of channels successfully inserted." + } + } + } +} diff --git a/doc/schemas/staticbackup.request.json b/doc/schemas/staticbackup.request.json new file mode 100644 index 000000000000..f99496c5ac84 --- /dev/null +++ b/doc/schemas/staticbackup.request.json @@ -0,0 +1,7 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "required": [], + "additionalProperties": false, + "properties": {} +} diff --git a/doc/schemas/staticbackup.schema.json b/doc/schemas/staticbackup.schema.json new file mode 100644 index 000000000000..73b7009e7311 --- /dev/null +++ b/doc/schemas/staticbackup.schema.json @@ -0,0 +1,17 @@ +{ + "$schema": "http://json-schema.org/draft-07/schema#", + "type": "object", + "additionalProperties": false, + "required": [ + "scb" + ], + "properties": { + "scb": { + "type": "array", + "items": { + "type": "string", + "description": "SCB of a channel in TLV format" + } + } + } +} diff --git a/hsmd/hsmd.c b/hsmd/hsmd.c index 0c354a7edbd3..85875bf30e44 100644 --- a/hsmd/hsmd.c +++ b/hsmd/hsmd.c @@ -660,6 +660,7 @@ static struct io_plan *handle_client(struct io_conn *conn, struct client *c) case WIRE_HSMD_ECDH_REQ: case WIRE_HSMD_CHECK_FUTURE_SECRET: case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY: + case WIRE_HSMD_DERIVE_SECRET: case WIRE_HSMD_CANNOUNCEMENT_SIG_REQ: case WIRE_HSMD_NODE_ANNOUNCEMENT_SIG_REQ: case WIRE_HSMD_CUPDATE_SIG_REQ: @@ -681,6 +682,7 @@ static struct io_plan *handle_client(struct io_conn *conn, struct client *c) case WIRE_HSMD_SIGN_WITHDRAWAL_REPLY: case WIRE_HSMD_SIGN_INVOICE_REPLY: case WIRE_HSMD_INIT_REPLY: + case WIRE_HSMD_DERIVE_SECRET_REPLY: case WIRE_HSMSTATUS_CLIENT_BAD_REQUEST: case WIRE_HSMD_SIGN_COMMITMENT_TX_REPLY: case WIRE_HSMD_VALIDATE_COMMITMENT_TX_REPLY: diff --git a/hsmd/hsmd_wire.csv b/hsmd/hsmd_wire.csv index a62edce8c520..26d552e5b354 100644 --- a/hsmd/hsmd_wire.csv +++ b/hsmd/hsmd_wire.csv @@ -281,3 +281,11 @@ msgdata,hsmd_sign_option_will_fund_offer,channel_fee_proportional_basis_max,u16, msgtype,hsmd_sign_option_will_fund_offer_reply,126 msgdata,hsmd_sign_option_will_fund_offer_reply,rsig,secp256k1_ecdsa_signature, + +# Reply with the derived secret +msgtype,hsmd_derive_secret_reply,27 +msgdata,hsmd_derive_secret_reply,secret,secret, + +msgtype,hsmd_derive_secret,127 +msgdata,hsmd_derive_secret,len,u16, +msgdata,hsmd_derive_secret,info,u8,len diff --git a/hsmd/libhsmd.c b/hsmd/libhsmd.c index 84f78de344d7..a641e3f87d2e 100644 --- a/hsmd/libhsmd.c +++ b/hsmd/libhsmd.c @@ -23,11 +23,13 @@ struct secret *dev_force_bip32_seed; #endif /*~ Nobody will ever find it here! hsm_secret is our root secret, the bip32 - * tree and bolt12 payer_id keys are derived from that, and cached here. */ + * tree, bolt12 payer_id keys and derived_secret are derived from that, and + * cached here. */ struct { struct secret hsm_secret; struct ext_key bip32; secp256k1_keypair bolt12; + struct secret derived_secret; } secretstuff; /* Have we initialized the secretstuff? */ @@ -117,6 +119,7 @@ bool hsmd_check_client_capabilities(struct hsmd_client *client, case WIRE_HSMD_SIGN_MESSAGE: case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY: case WIRE_HSMD_SIGN_BOLT12: + case WIRE_HSMD_DERIVE_SECRET: return (client->capabilities & HSM_CAP_MASTER) != 0; /*~ These are messages sent by the HSM so we should never receive them. */ @@ -145,6 +148,7 @@ bool hsmd_check_client_capabilities(struct hsmd_client *client, case WIRE_HSMD_SIGN_MESSAGE_REPLY: case WIRE_HSMD_GET_OUTPUT_SCRIPTPUBKEY_REPLY: case WIRE_HSMD_SIGN_BOLT12_REPLY: + case WIRE_HSMD_DERIVE_SECRET_REPLY: break; } return false; @@ -257,6 +261,22 @@ static void hsm_channel_secret_base(struct secret *channel_seed_base) "peer seed", strlen("peer seed")); } +/* This will derive pseudorandom secret Key from a derived key */ +static u8 *handle_derive_secret(struct hsmd_client *c, const u8 *msg_in) +{ + u8 *info; + struct secret secret; + + if (!fromwire_hsmd_derive_secret(tmpctx, msg_in, &info)) + return hsmd_status_malformed_request(c, msg_in); + + hkdf_sha256(&secret, sizeof(struct secret), NULL, 0, + &secretstuff.derived_secret, sizeof(&secretstuff.derived_secret), + info, tal_bytelen(info)); + + return towire_hsmd_derive_secret_reply(NULL, &secret); +} + /*~ This gets the seed for this particular channel. */ static void get_channel_seed(const struct node_id *peer_id, u64 dbid, struct secret *channel_seed) @@ -1593,9 +1613,12 @@ u8 *hsmd_handle_client_message(const tal_t *ctx, struct hsmd_client *client, return handle_sign_remote_htlc_to_us(client, msg); case WIRE_HSMD_SIGN_DELAYED_PAYMENT_TO_US: return handle_sign_delayed_payment_to_us(client, msg); + case WIRE_HSMD_DERIVE_SECRET: + return handle_derive_secret(client, msg); case WIRE_HSMD_DEV_MEMLEAK: case WIRE_HSMD_ECDH_RESP: + case WIRE_HSMD_DERIVE_SECRET_REPLY: case WIRE_HSMD_CANNOUNCEMENT_SIG_REPLY: case WIRE_HSMD_CUPDATE_SIG_REPLY: case WIRE_HSMD_CLIENT_HSMFD_REPLY: @@ -1760,6 +1783,12 @@ u8 *hsmd_init(struct secret hsm_secret, sizeof(secretstuff.hsm_secret), "onion reply secret", strlen("onion reply secret")); + /* We derive the derived_secret key for generating pseudorandom keys + * by taking input string from the makesecret RPC */ + hkdf_sha256(&secretstuff.derived_secret, sizeof(struct secret), NULL, 0, + &secretstuff.hsm_secret, sizeof(secretstuff.hsm_secret), + "derived secrets", strlen("derived secrets")); + /*~ Note: marshalling a bip32 tree only marshals the public side, * not the secrets! So we're not actually handing them out here! */ diff --git a/lightningd/Makefile b/lightningd/Makefile index f1f1607ea388..cf997370ce96 100644 --- a/lightningd/Makefile +++ b/lightningd/Makefile @@ -90,6 +90,7 @@ LIGHTNINGD_COMMON_OBJS := \ common/features.o \ common/fee_states.o \ common/peer_status_wiregen.o \ + common/scb_wiregen.o \ common/status_levels.o \ common/status_wiregen.o \ common/hash_u5.o \ diff --git a/lightningd/channel.c b/lightningd/channel.c index e1f059bc4752..06a7c63615e5 100644 --- a/lightningd/channel.c +++ b/lightningd/channel.c @@ -212,6 +212,7 @@ struct channel *new_unsaved_channel(struct peer *peer, channel->openchannel_signed_cmd = NULL; channel->state = DUALOPEND_OPEN_INIT; channel->owner = NULL; + channel->scb = NULL; memset(&channel->billboard, 0, sizeof(channel->billboard)); channel->billboard.transient = tal_fmt(channel, "%s", "Empty channel init'd"); @@ -419,6 +420,14 @@ struct channel *new_channel(struct peer *peer, u64 dbid, channel->owner = NULL; memset(&channel->billboard, 0, sizeof(channel->billboard)); channel->billboard.transient = tal_strdup(channel, transient_billboard); + channel->scb = tal(channel, struct scb_chan); + channel->scb->id = dbid; + channel->scb->addr = peer->addr; + channel->scb->node_id = peer->id; + channel->scb->funding = *funding; + channel->scb->cid = *cid; + channel->scb->funding_sats = funding_sats; + channel->scb->type = channel_type_dup(channel->scb, type); if (!log) { channel->log = new_log(channel, @@ -447,9 +456,11 @@ struct channel *new_channel(struct peer *peer, u64 dbid, channel->our_msat = our_msat; channel->msat_to_us_min = msat_to_us_min; channel->msat_to_us_max = msat_to_us_max; - channel->last_tx = tal_steal(channel, last_tx); - channel->last_tx->chainparams = chainparams; - channel->last_tx_type = TX_UNKNOWN; + channel->last_tx = tal_steal(channel, last_tx); + if (channel->last_tx) { + channel->last_tx->chainparams = chainparams; + channel->last_tx_type = TX_UNKNOWN; + } channel->last_sig = *last_sig; channel->last_htlc_sigs = tal_steal(channel, last_htlc_sigs); channel->channel_info = *channel_info; @@ -523,6 +534,12 @@ struct channel *new_channel(struct peer *peer, u64 dbid, txfilter_add_scriptpubkey(peer->ld->owned_txfilter, take(p2wpkh_for_keyidx(NULL, peer->ld, channel->final_key_idx))); + /* scid is NULL when opening a new channel so we don't + * need to set error in that case as well */ + if (is_stub_scid(scid)) + channel->error = towire_errorfmt(peer->ld, + &channel->cid, + "We can't be together anymore."); return channel; } @@ -768,6 +785,11 @@ void channel_fail_permanent(struct channel *channel, const char *fmt, ...) { + /* Don't do anything if it's an stub channel because + * peer has already closed it unilatelrally. */ + if (is_stub_scid(channel->scid)) + return; + struct lightningd *ld = channel->peer->ld; va_list ap; char *why; diff --git a/lightningd/channel.h b/lightningd/channel.h index fbe86a63f916..8851bd72ff08 100644 --- a/lightningd/channel.h +++ b/lightningd/channel.h @@ -3,6 +3,7 @@ #include "config.h" #include #include +#include #include #include #include @@ -260,6 +261,10 @@ struct channel { /* Latest channel_update, for use in error messages. */ u8 *channel_update; + + /* `Channel-shell` of this channel + * (Minimum information required to backup this channel). */ + struct scb_chan *scb; }; /* For v2 opens, a channel that has not yet been committed/saved to disk */ diff --git a/lightningd/dual_open_control.c b/lightningd/dual_open_control.c index d72a688f05de..cac1152aae8c 100644 --- a/lightningd/dual_open_control.c +++ b/lightningd/dual_open_control.c @@ -1228,6 +1228,14 @@ wallet_commit_channel(struct lightningd *ld, &commitment_feerate); channel->min_possible_feerate = commitment_feerate; channel->max_possible_feerate = commitment_feerate; + channel->scb = tal(channel, struct scb_chan); + channel->scb->id = channel->dbid; + channel->scb->addr = channel->peer->addr; + channel->scb->node_id = channel->peer->id; + channel->scb->funding = *funding; + channel->scb->cid = channel->cid; + channel->scb->funding_sats = total_funding; + channel->scb->type = channel_type_dup(channel->scb, channel->type); /* We are connected */ channel->connected = true; diff --git a/lightningd/hsm_control.c b/lightningd/hsm_control.c index 9a49c03df79d..d5f6413a98fe 100644 --- a/lightningd/hsm_control.c +++ b/lightningd/hsm_control.c @@ -4,7 +4,9 @@ #include #include #include +#include #include +#include #include #include #include @@ -146,6 +148,45 @@ static struct command_result *json_getsharedsecret(struct command *cmd, return command_success(cmd, response); } +static struct command_result *json_makesecret(struct command *cmd, + const char *buffer, + const jsmntok_t *obj UNNEEDED, + const jsmntok_t *params) +{ + u8 *info; + struct json_stream *response; + struct secret secret; + + if (!param(cmd, buffer, params, + p_req("info_hex", param_bin_from_hex, &info), + NULL)) + return command_param_failed(); + + u8 *msg = towire_hsmd_derive_secret(cmd, info); + if (!wire_sync_write(cmd->ld->hsm_fd, take(msg))) + return command_fail(cmd, LIGHTNINGD, + "Could not write to HSM: %s", strerror(errno)); + + + msg = wire_sync_read(tmpctx, cmd->ld->hsm_fd); + if (!fromwire_hsmd_derive_secret_reply(msg, &secret)) + return command_fail(cmd, LIGHTNINGD, + "Bad reply from HSM: %s", strerror(errno)); + + + response = json_stream_success(cmd); + json_add_secret(response, "secret", &secret); + return command_success(cmd, response); +} + +static const struct json_command makesecret_command = { + "makesecret", + "utility", + &json_makesecret, + "Get a pseudorandom secret key, using an info string." +}; +AUTODATA(json_command, &makesecret_command); + static const struct json_command getsharedsecret_command = { "getsharedsecret", "utility", /* FIXME: Or "crypto"? */ diff --git a/lightningd/onchain_control.c b/lightningd/onchain_control.c index 1c22cc1b9627..2e8919751509 100644 --- a/lightningd/onchain_control.c +++ b/lightningd/onchain_control.c @@ -669,8 +669,17 @@ enum watch_result onchaind_funding_spent(struct channel *channel, channel->final_key_idx); return KEEP_WATCHING; } - /* This could be a mutual close, but it doesn't matter. */ - bitcoin_txid(channel->last_tx, &our_last_txid); + + /* This could be a mutual close, but it doesn't matter. + * We don't need this for stub channels as well */ + if (!is_stub_scid(channel->scid)) + bitcoin_txid(channel->last_tx, &our_last_txid); + else + /* Dummy txid for stub channel to make valgrind happy. */ + bitcoin_txid_from_hex("80cea306607b708a03a1854520729d" + "a884e4317b7b51f3d4a622f88176f5e034", + 64, + &our_last_txid); /* We try to get the feerate for each transaction type, 0 if estimation * failed. */ diff --git a/lightningd/opening_control.c b/lightningd/opening_control.c index a6b8d75325d8..c2f02819ff9e 100644 --- a/lightningd/opening_control.c +++ b/lightningd/opening_control.c @@ -13,6 +13,7 @@ #include #include #include +#include #include #include #include @@ -1229,6 +1230,208 @@ static struct command_result *json_fundchannel_start(struct command *cmd, return command_still_pending(cmd); } +static struct channel *stub_chan(struct command *cmd, + u64 id, + struct node_id nodeid, + struct channel_id cid, + struct bitcoin_outpoint funding, + struct wireaddr_internal addr, + struct amount_sat funding_sats, + struct channel_type *type) +{ + struct basepoints basepoints; + struct bitcoin_signature *sig; + struct channel *channel; + struct channel_config *our_config; + struct channel_config *their_config; + struct channel_info *channel_info; + struct lightningd *ld; + struct peer *peer; + struct pubkey localFundingPubkey; + struct pubkey pk; + struct short_channel_id *scid; + u32 blockht; + u32 feerate; + u8 *dummy_sig = tal_hexdata(cmd, + "30450221009b2e0eef267b94c3899fb0dc73750" + "12e2cee4c10348a068fe78d1b82b4b1403602207" + "7c3fad3adac2ddf33f415e45f0daf6658b7a0b09" + "647de4443938ae2dbafe2b9" "01", + 144); + + peer = new_peer(cmd->ld, + 0, + &nodeid, + &addr, + false); + + ld = cmd->ld; + feerate = FEERATE_FLOOR; + + sig = tal(cmd, struct bitcoin_signature); + signature_from_der(dummy_sig, + tal_bytelen(dummy_sig) + ,sig); + + if (!pubkey_from_der(tal_hexdata(cmd, + type_to_string(tmpctx, + struct node_id, + &nodeid), + 66), + 33, + &pk)) + { + fatal("Invalid node id!"); + } + + get_channel_basepoints(ld, + &nodeid, + id, + &basepoints, + &localFundingPubkey); + + channel_info = tal(cmd, + struct channel_info); + + our_config = tal(cmd, struct channel_config); + their_config = tal(cmd, struct channel_config); + + /* FIXME: Makeake these a pointer, so they could be NULL */ + memset(our_config, 0, sizeof(struct channel_config)); + memset(their_config, 0, sizeof(struct channel_config)); + channel_info->their_config = *their_config; + channel_info->theirbase = basepoints; + channel_info->remote_fundingkey = pk; + channel_info->remote_per_commit = pk; + channel_info->old_remote_per_commit = pk; + + blockht = 100; + scid = tal(cmd, struct short_channel_id); + + /*To indicate this is an stub channel we keep it's scid to 1x1x1.*/ + if (!mk_short_channel_id(scid, 1, 1, 1)) + fatal("Failed to make short channel 1x1x1!"); + + /* Channel Shell with Dummy data(mostly) */ + channel = new_channel(peer, id, + NULL, /* No shachain yet */ + CHANNELD_NORMAL, + LOCAL, + NULL, + "restored from static channel backup", + 0, our_config, + 0, + 1, 1, 1, + &funding, + funding_sats, + AMOUNT_MSAT(0), + AMOUNT_SAT(0), + true, /* !remote_funding_locked */ + scid, + scid, + scid, + &cid, + /* The three arguments below are msatoshi_to_us, + * msatoshi_to_us_min, and msatoshi_to_us_max. + * Because, this is a newly-funded channel, + * all three are same value. */ + AMOUNT_MSAT(0), + AMOUNT_MSAT(0), /* msat_to_us_min */ + AMOUNT_MSAT(0), /* msat_to_us_max */ + NULL, + sig, + NULL, /* No HTLC sigs */ + channel_info, + new_fee_states(cmd, LOCAL, &feerate), + NULL, /* No shutdown_scriptpubkey[REMOTE] */ + NULL, + 1, false, + NULL, /* No commit sent */ + /* If we're fundee, could be a little before this + * in theory, but it's only used for timing out. */ + get_network_blockheight(ld->topology), + FEERATE_FLOOR, + funding_sats.satoshis / MINIMUM_TX_WEIGHT * 1000 /* Raw: convert to feerate */, + false, + &basepoints, + &localFundingPubkey, + NULL, + ld->config.fee_base, + ld->config.fee_per_satoshi, + NULL, + 0, 0, + type, + NUM_SIDES, /* closer not yet known */ + REASON_REMOTE, + NULL, + take(new_height_states(ld->wallet, LOCAL, + &blockht)), + 0, NULL, 0, 0, /* No leases on v1s */ + ld->config.htlc_minimum_msat, + ld->config.htlc_maximum_msat); + + return channel; +} + +static struct command_result *json_recoverchannel(struct command *cmd, + const char *buffer, + const jsmntok_t *obj UNNEEDED, + const jsmntok_t *params) +{ + const jsmntok_t *scb, *t; + size_t i; + struct json_stream *response; + struct scb_chan *scb_chan = tal(cmd, struct scb_chan); + + if (!param(cmd, buffer, params, + p_req("scb", param_array, &scb), + NULL)) + return command_param_failed(); + + response = json_stream_success(cmd); + + json_array_start(response, "stubs"); + json_for_each_arr(i,t,scb){ + + char *token = json_strdup(tmpctx, buffer, t); + const u8 *scb_arr = tal_hexdata(cmd, token, strlen(token)); + size_t scblen = tal_count(scb_arr); + + scb_chan = fromwire_scb_chan(cmd ,&scb_arr, &scblen); + + if (scb_chan == NULL) { + log_broken(cmd->ld->log, "SCB is invalid!"); + continue; + } + + struct lightningd *ld = cmd->ld; + struct channel *channel= stub_chan(cmd, + scb_chan->id, + scb_chan->node_id, + scb_chan->cid, + scb_chan->funding, + scb_chan->addr, + scb_chan->funding_sats, + scb_chan->type); + + /* Now we put this in the database. */ + wallet_channel_insert(ld->wallet, channel); + + /* Watch the Funding */ + channel_watch_funding(ld, channel); + + json_add_channel_id(response, NULL, &scb_chan->cid); + } + + /* This will try to reconnect to the peers and start + * initiating the process */ + setup_peers(cmd->ld); + + json_array_end(response); + + return command_success(cmd, response); +} + static const struct json_command fundchannel_start_command = { "fundchannel_start", "channels", @@ -1254,3 +1457,13 @@ static const struct json_command fundchannel_complete_command = { "with {psbt}. Returns true on success, false otherwise." }; AUTODATA(json_command, &fundchannel_complete_command); + +static const struct json_command json_commitchan_command = { + "recoverchannel", + "channels", + json_recoverchannel, + "Populate the DB with a channel and peer" + "Used for recovering the channel using DLP." + "This needs param in the form of an array [scb1,scb2,...]" +}; +AUTODATA(json_command, &json_commitchan_command); diff --git a/lightningd/peer_control.c b/lightningd/peer_control.c index 40bb56812f6f..4a0b4c8a08cd 100644 --- a/lightningd/peer_control.c +++ b/lightningd/peer_control.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include #include @@ -1535,8 +1536,9 @@ static enum watch_result funding_depth_cb(struct lightningd *ld, const char *txidstr; struct short_channel_id scid; - /* Sanity check */ - if (!check_funding_tx(tx, channel)) { + /* Sanity check, but we'll have to make an exception + * for stub channels(1x1x1) */ + if (!check_funding_tx(tx, channel) && !is_stub_scid(channel->scid)) { channel_internal_error(channel, "Bad tx %s: %s", type_to_string(tmpctx, struct bitcoin_txid, txid), @@ -1591,13 +1593,15 @@ static enum watch_result funding_depth_cb(struct lightningd *ld, return DELETE_WATCH; } - /* If we restart, we could already have peer->scid from database */ + /* If we restart, we could already have peer->scid from database, + * we don't need to update scid for stub channels(1x1x1) */ if (!channel->scid) { channel->scid = tal(channel, struct short_channel_id); *channel->scid = scid; wallet_channel_save(ld->wallet, channel); - } else if (!short_channel_id_eq(channel->scid, &scid)) { + } else if (!short_channel_id_eq(channel->scid, &scid) && + !is_stub_scid(channel->scid)) { /* This normally restarts channeld, initialized with updated scid * and also adds it (at least our halve_chan) to rtable. */ channel_fail_reconnect(channel, @@ -1757,6 +1761,57 @@ static const struct json_command listpeers_command = { /* Comment added to satisfice AUTODATA */ AUTODATA(json_command, &listpeers_command); +static void json_add_scb(struct command *cmd, + const char *fieldname, + struct json_stream *response, + struct channel *c) +{ + u8 *scb = tal_arr(cmd, u8, 0); + + towire_scb_chan(&scb, c->scb); + json_add_hex_talarr(response, fieldname, + scb); +} + +/* This will return a SCB for all the channels currently loaded + * in the in-memory channel */ +static struct command_result *json_staticbackup(struct command *cmd, + const char *buffer, + const jsmntok_t *obj UNNEEDED, + const jsmntok_t *params) +{ + struct json_stream *response; + struct peer *peer; + struct channel *channel; + + if (!param(cmd, buffer, params, NULL)) + return command_param_failed(); + + response = json_stream_success(cmd); + + json_array_start(response, "scb"); + + list_for_each(&cmd->ld->peers, peer, list) + list_for_each(&peer->channels, channel, list){ + if (!channel->scb) + continue; + json_add_scb(cmd, NULL, response, channel); + } + json_array_end(response); + + return command_success(cmd, response); +} + +static const struct json_command staticbackup_command = { + "staticbackup", + "backup", + json_staticbackup, + "Returns SCB of all the channels currently present in the DB" +}; +/* Comment added to satisfice AUTODATA */ +AUTODATA(json_command, &staticbackup_command); + + struct command_result * command_find_channel(struct command *cmd, const char *buffer, const jsmntok_t *tok, diff --git a/lightningd/test/run-invoice-select-inchan.c b/lightningd/test/run-invoice-select-inchan.c index 01699c8b49a9..fab4c8a481a6 100644 --- a/lightningd/test/run-invoice-select-inchan.c +++ b/lightningd/test/run-invoice-select-inchan.c @@ -694,6 +694,9 @@ u8 *towire_onchaind_dev_memleak(const tal_t *ctx UNNEEDED) /* Generated stub for towire_openingd_dev_memleak */ u8 *towire_openingd_dev_memleak(const tal_t *ctx UNNEEDED) { fprintf(stderr, "towire_openingd_dev_memleak called!\n"); abort(); } +/* Generated stub for towire_scb_chan */ +void towire_scb_chan(u8 **p UNNEEDED, const struct scb_chan *scb_chan UNNEEDED) +{ fprintf(stderr, "towire_scb_chan called!\n"); abort(); } /* Generated stub for towire_warningfmt */ u8 *towire_warningfmt(const tal_t *ctx UNNEEDED, const struct channel_id *channel UNNEEDED, diff --git a/plugins/.gitignore b/plugins/.gitignore index 389469cf0de3..3c340b67de4f 100644 --- a/plugins/.gitignore +++ b/plugins/.gitignore @@ -10,3 +10,4 @@ pay spenderp topology txprepare +chanbackup \ No newline at end of file diff --git a/plugins/Makefile b/plugins/Makefile index bae7bfa4e583..c69297569a5a 100644 --- a/plugins/Makefile +++ b/plugins/Makefile @@ -4,6 +4,9 @@ PLUGIN_PAY_OBJS := $(PLUGIN_PAY_SRC:.c=.o) PLUGIN_AUTOCLEAN_SRC := plugins/autoclean.c PLUGIN_AUTOCLEAN_OBJS := $(PLUGIN_AUTOCLEAN_SRC:.c=.o) +PLUGIN_chanbackup_SRC := plugins/chanbackup.c +PLUGIN_chanbackup_OBJS := $(PLUGIN_chanbackup_SRC:.c=.o) + PLUGIN_TOPOLOGY_SRC := plugins/topology.c PLUGIN_TOPOLOGY_OBJS := $(PLUGIN_TOPOLOGY_SRC:.c=.o) @@ -55,6 +58,7 @@ PLUGIN_FUNDER_OBJS := $(PLUGIN_FUNDER_SRC:.c=.o) PLUGIN_ALL_SRC := \ $(PLUGIN_AUTOCLEAN_SRC) \ + $(PLUGIN_chanbackup_SRC) \ $(PLUGIN_BCLI_SRC) \ $(PLUGIN_FETCHINVOICE_SRC) \ $(PLUGIN_FUNDER_SRC) \ @@ -77,6 +81,7 @@ PLUGIN_ALL_OBJS := $(PLUGIN_ALL_SRC:.c=.o) C_PLUGINS := \ plugins/autoclean \ + plugins/chanbackup \ plugins/bcli \ plugins/fetchinvoice \ plugins/funder \ @@ -140,6 +145,7 @@ PLUGIN_COMMON_OBJS := \ common/psbt_open.o \ common/pseudorand.o \ common/random_select.o \ + common/scb_wiregen.o \ common/setup.o \ common/status_levels.o \ common/type_to_string.o \ @@ -160,6 +166,8 @@ plugins/pay: bitcoin/chainparams.o $(PLUGIN_PAY_OBJS) $(PLUGIN_LIB_OBJS) $(PLUGI plugins/autoclean: bitcoin/chainparams.o $(PLUGIN_AUTOCLEAN_OBJS) $(PLUGIN_LIB_OBJS) $(PLUGIN_COMMON_OBJS) $(JSMN_OBJS) $(CCAN_OBJS) +plugins/chanbackup: bitcoin/chainparams.o $(PLUGIN_chanbackup_OBJS) $(PLUGIN_LIB_OBJS) $(PLUGIN_COMMON_OBJS) $(JSMN_OBJS) $(CCAN_OBJS) + # Topology wants to decode node_announcement, and peer_wiregen which # pulls in some of bitcoin/. plugins/topology: common/route.o common/dijkstra.o common/gossmap.o common/fp16.o bitcoin/chainparams.o wire/peer$(EXP)_wiregen.o wire/channel_type_wiregen.o bitcoin/block.o bitcoin/preimage.o $(PLUGIN_TOPOLOGY_OBJS) $(PLUGIN_LIB_OBJS) $(PLUGIN_COMMON_OBJS) $(JSMN_OBJS) $(CCAN_OBJS) diff --git a/plugins/chanbackup.c b/plugins/chanbackup.c new file mode 100644 index 000000000000..cd8376be433a --- /dev/null +++ b/plugins/chanbackup.c @@ -0,0 +1,419 @@ +#include "config.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define HEADER_LEN crypto_secretstream_xchacha20poly1305_HEADERBYTES +#define ABYTES crypto_secretstream_xchacha20poly1305_ABYTES + +/* VERSION is the current version of the data encrypted in the file */ +#define VERSION ((u64)1) + +/* Global secret object to keep the derived encryption key for the SCB */ +static struct secret secret; + +/* Helper to fetch out SCB from the RPC call */ +static bool json_to_scb_chan(const char *buffer, + const jsmntok_t *tok, + struct scb_chan ***channels) +{ + size_t i; + const jsmntok_t *t; + *channels = tok->size ? tal_arr(tmpctx, + struct scb_chan *, + tok->size) : NULL; + + json_for_each_arr(i, t, tok) { + const u8 *scb_tmp = tal_hexdata(tmpctx, + json_strdup(tmpctx, + buffer, + t), + strlen(json_strdup(tmpctx, + buffer, + t))); + size_t scblen_tmp = tal_count(scb_tmp); + + (*channels)[i] = fromwire_scb_chan(tmpctx, + &scb_tmp, + &scblen_tmp); + } + + return true; +} + +/* This writes encrypted static backup in the recovery file */ +static void write_scb(struct plugin *p, + int fd, + struct scb_chan **scb_chan_arr) +{ + u32 timestamp = time_now().ts.tv_sec; + + u8 *decrypted_scb = towire_static_chan_backup(tmpctx, + VERSION, + timestamp, + cast_const2(const struct scb_chan **, + scb_chan_arr)); + + u8 *encrypted_scb = tal_arr(tmpctx, + u8, + tal_bytelen(decrypted_scb) + + ABYTES + + HEADER_LEN); + + crypto_secretstream_xchacha20poly1305_state crypto_state; + + if (crypto_secretstream_xchacha20poly1305_init_push(&crypto_state, + encrypted_scb, + (&secret)->data) != 0) + { + plugin_err(p, "Can't encrypt the data!"); + return; + } + + if (crypto_secretstream_xchacha20poly1305_push(&crypto_state, + encrypted_scb + + HEADER_LEN, + NULL, decrypted_scb, + tal_bytelen(decrypted_scb), + /* Additional data and tag */ + NULL, 0, 0)) { + plugin_err(p, "Can't encrypt the data!"); + return; + } + + if (!write_all(fd, encrypted_scb, tal_bytelen(encrypted_scb))) { + unlink_noerr("scb.tmp"); + plugin_err(p, "Writing encrypted SCB: %s", + strerror(errno)); + } + +} + +/* checks if the SCB file exists, creates a new one in case it doesn't. */ +static void maybe_create_new_scb(struct plugin *p, + struct scb_chan **channels) +{ + + /* Note that this is opened for write-only, even though the permissions + * are set to read-only. That's perfectly valid! */ + int fd = open("emergency.recover", O_CREAT|O_EXCL|O_WRONLY, 0400); + if (fd < 0) { + /* Don't do anything if the file already exists. */ + if (errno == EEXIST) + return; + plugin_err(p, "creating: %s", strerror(errno)); + } + + /* Comes here only if the file haven't existed before */ + unlink_noerr("emergency.recover"); + + /* This couldn't give EEXIST because we call unlink_noerr("scb.tmp") + * in INIT */ + fd = open("scb.tmp", O_CREAT|O_EXCL|O_WRONLY, 0400); + if (fd < 0) + plugin_err(p, "Opening: %s", strerror(errno)); + + plugin_log(p, LOG_INFORM, "Creating Emergency Recovery"); + + write_scb(p, fd, channels); + + /* fsync (mostly!) ensures that the file has reached the disk. */ + if (fsync(fd) != 0) { + unlink_noerr("scb.tmp"); + plugin_err(p, "fsync : %s", strerror(errno)); + } + + /* This should never fail if fsync succeeded. But paranoia good, and + * bugs exist. */ + if (close(fd) != 0) { + unlink_noerr("scb.tmp"); + plugin_err(p, "closing: %s", strerror(errno)); + } + + /* We actually need to sync the *directory itself* to make sure the + * file exists! You're only allowed to open directories read-only in + * modern Unix though. */ + fd = open(".", O_RDONLY); + if (fd < 0) + plugin_err(p, "Opening: %s", strerror(errno)); + + if (fsync(fd) != 0) { + unlink_noerr("scb.tmp"); + plugin_err(p, "closing: %s", strerror(errno)); + } + + /* This will never fail, if fsync worked! */ + close(fd); + + /* This will update the scb file */ + rename("scb.tmp", "emergency.recover"); +} + + +/* Returns decrypted SCB in form of a u8 array */ +static u8 *decrypt_scb(struct plugin *p) +{ + struct stat st; + int fd = open("emergency.recover", O_RDONLY); + + if (stat("emergency.recover", &st) != 0) + plugin_err(p, "SCB file is corrupted!: %s", + strerror(errno)); + + u8 final[st.st_size]; + + if (!read_all(fd, &final, st.st_size)) { + plugin_log(p, LOG_DBG, "SCB file is corrupted!: %s", + strerror(errno)); + return NULL; + } + + crypto_secretstream_xchacha20poly1305_state crypto_state; + + if (st.st_size < ABYTES + + HEADER_LEN) + plugin_err(p, "SCB file is corrupted!"); + + u8 *ans = tal_arr(tmpctx, u8, st.st_size - + ABYTES - + HEADER_LEN); + + /* The header part */ + if (crypto_secretstream_xchacha20poly1305_init_pull(&crypto_state, + final, + (&secret)->data) != 0) + { + plugin_err(p, "SCB file is corrupted!"); + } + + if (crypto_secretstream_xchacha20poly1305_pull(&crypto_state, ans, + NULL, 0, + final + + HEADER_LEN, + st.st_size - + HEADER_LEN, + NULL, 0) != 0) { + plugin_err(p, "SCB file is corrupted!"); + } + + if (close(fd) != 0) + plugin_err(p, "Closing: %s", strerror(errno)); + + return ans; +} + +static struct command_result *after_recover_rpc(struct command *cmd, + const char *buf, + const jsmntok_t *params, + void *cb_arg UNUSED) +{ + + size_t i; + const jsmntok_t *t; + struct json_stream *response; + + response = jsonrpc_stream_success(cmd); + + json_for_each_obj(i, t, params) + json_add_tok(response, json_strdup(tmpctx, buf, t), t+1, buf); + + return command_finished(cmd, response); +} + +/* Recovers the channels by making RPC to `recoverchannel` */ +static struct command_result *json_emergencyrecover(struct command *cmd, + const char *buf, + const jsmntok_t *params) +{ + struct out_req *req; + u64 version; + u32 timestamp; + struct scb_chan **scb; + + if (!param(cmd, buf, params, NULL)) + return command_param_failed(); + + u8 *res = decrypt_scb(cmd->plugin); + + if (!fromwire_static_chan_backup(cmd, + res, + &version, + ×tamp, + &scb)) { + plugin_err(cmd->plugin, "Corrupted SCB!"); + } + + if (version != VERSION) { + plugin_err(cmd->plugin, + "Incompatible version, Contact the admin!"); + } + + req = jsonrpc_request_start(cmd->plugin, cmd, "recoverchannel", + after_recover_rpc, + &forward_error, NULL); + + json_array_start(req->js, "scb"); + for (size_t i=0; ijs, NULL, scb_hex, tal_bytelen(scb_hex)); + } + json_array_end(req->js); + + return send_outreq(cmd->plugin, req); +} + +static void update_scb(struct plugin *p, struct scb_chan **channels) +{ + + /* If the temp file existed before, remove it */ + unlink_noerr("scb.tmp"); + + int fd = open("scb.tmp", O_CREAT|O_EXCL|O_WRONLY, 0400); + if (fd<0) + plugin_err(p, "Opening: %s", strerror(errno)); + + plugin_log(p, LOG_DBG, "Updating the SCB file..."); + + write_scb(p, fd, channels); + + /* fsync (mostly!) ensures that the file has reached the disk. */ + if (fsync(fd) != 0) { + unlink_noerr("scb.tmp"); + } + + /* This should never fail if fsync succeeded. But paranoia good, and + * bugs exist. */ + if (close(fd) != 0) { + unlink_noerr("scb.tmp"); + } + /* We actually need to sync the *directory itself* to make sure the + * file exists! You're only allowed to open directories read-only in + * modern Unix though. */ + fd = open(".", O_RDONLY); + if (fd < 0) { + plugin_log(p, LOG_DBG, "Opening: %s", strerror(errno)); + } + if (fsync(fd) != 0) { + unlink_noerr("scb.tmp"); + } + close(fd); + + /* This will atomically replace the main file */ + rename("scb.tmp", "emergency.recover"); +} + +static struct command_result *after_staticbackup(struct command *cmd, + const char *buf, + const jsmntok_t *params, + void *cb_arg UNUSED) +{ + struct scb_chan **scb_chan; + const jsmntok_t *scbs = json_get_member(buf, params, "scb"); + json_to_scb_chan(buf, scbs, &scb_chan); + plugin_log(cmd->plugin, LOG_INFORM, "Updating the SCB"); + + update_scb(cmd->plugin, scb_chan); + return notification_handled(cmd); +} + +static struct command_result *json_state_changed(struct command *cmd, + const char *buf, + const jsmntok_t *params) +{ + const jsmntok_t *notiftok = json_get_member(buf, + params, + "channel_state_changed"), + *statetok = json_get_member(buf, notiftok, "new_state"); + + /* FIXME: I wanted to update the file on CHANNELD_AWAITING_LOCKIN, + * But I don't get update for it, maybe because there is + * no previous_state, also apparently `channel_opened` gets published + * when *peer* funded a channel with us? + * So, is their no way to get a notif on CHANNELD_AWAITING_LOCKIN? */ + if (json_tok_streq(buf, statetok, "CLOSED") || + json_tok_streq(buf, statetok, "CHANNELD_NORMAL")) { + + struct out_req *req; + req = jsonrpc_request_start(cmd->plugin, + cmd, + "staticbackup", + after_staticbackup, + &forward_error, + NULL); + + return send_outreq(cmd->plugin, req); + } + + return notification_handled(cmd); +} + +static const char *init(struct plugin *p, + const char *buf UNUSED, + const jsmntok_t *config UNUSED) +{ + struct scb_chan **scb_chan; + const char *info = "scb secret"; + u8 *info_hex = tal_dup_arr(tmpctx, u8, (u8*)info, strlen(info), 0); + + rpc_scan(p, "staticbackup", + take(json_out_obj(NULL, NULL, NULL)), + "{scb:%}", JSON_SCAN(json_to_scb_chan, &scb_chan)); + + rpc_scan(p, "makesecret", + take(json_out_obj(NULL, "info_hex", + tal_hexstr(tmpctx, + info_hex, + tal_bytelen(info_hex)))), + "{secret:%}", JSON_SCAN(json_to_secret, &secret)); + + plugin_log(p, LOG_DBG, "Chanbackup Initialised!"); + + /* flush the tmp file, if exists */ + unlink_noerr("scb.tmp"); + + maybe_create_new_scb(p, scb_chan); + + return NULL; +} + +static const struct plugin_notification notifs[] = { + { + "channel_state_changed", + json_state_changed, + } +}; + +static const struct plugin_command commands[] = { { + "emergencyrecover", + "recovery", + "Populates the DB with stub channels", + "returns stub channel-id's on completion", + json_emergencyrecover, + } +}; + +int main(int argc, char *argv[]) +{ + setup_locale(); + plugin_main(argv, init, PLUGIN_RESTARTABLE, true, NULL, + commands, ARRAY_SIZE(commands), + notifs, ARRAY_SIZE(notifs), NULL, 0, + NULL, 0, /* Notification topics we publish */ + NULL); +} diff --git a/tests/test_misc.py b/tests/test_misc.py index 79d74b2553d9..bafd139114e8 100644 --- a/tests/test_misc.py +++ b/tests/test_misc.py @@ -2271,6 +2271,66 @@ def test_getsharedsecret(node_factory): == l2.rpc.getsharedsecret(l1.info["id"])["shared_secret"]) +@pytest.mark.developer("needs --dev-force-privkey") +def test_makesecret(node_factory): + """ + Test makesecret command. + """ + + l1 = node_factory.get_node(options={"dev-force-privkey": "1212121212121212121212121212121212121212121212121212121212121212"}) + secret = l1.rpc.makesecret("73636220736563726574")["secret"] + + assert (secret == "04fe01631fcedc8d91f39ab43244e63afebaed68ee21d2f1c325fd1242726a18") + + +def test_staticbackup(node_factory): + """ + Test staticbackup + """ + l1, l2 = node_factory.get_nodes(2, opts=[{}, {}]) + l1.rpc.connect(l2.info['id'], 'localhost', l2.port) + c12, _ = l1.fundchannel(l2, 10**5) + + # Comparing the channelID, scb_chan has the channel ID starting from the 8th byte + # and it's own length is 32 byte, hence 16 + 64. + assert (len(l1.rpc.staticbackup()["scb"]) == 1 + and l1.rpc.staticbackup()["scb"][0][16: 16 + 64] == _["channel_id"]) + + +def test_recoverchannel(node_factory): + """ + Test recoverchannel + """ + l1 = node_factory.get_node() + stubs = l1.rpc.recoverchannel(["0000000000000001c3a7b9d74a174497122bc52d74d6d69836acadc77e0429c6d8b68b48d5c9139a022d223620a359a47ff7f7ac447c85c46c923da53389221a0054c11c1e3ca31d5904017f0000019f0bc3a7b9d74a174497122bc52d74d6d69836acadc77e0429c6d8b68b48d5c9139a0000000000000000000186a000021000"])["stubs"] + + assert len(stubs) == 1 + assert stubs[0] == "c3a7b9d74a174497122bc52d74d6d69836acadc77e0429c6d8b68b48d5c9139a" + + +@unittest.skipIf(os.getenv('TEST_DB_PROVIDER', 'sqlite3') != 'sqlite3', "deletes database, which is assumed sqlite3") +def test_emergencyrecover(node_factory, bitcoind): + """ + Test emergencyrecover + """ + l1, l2 = node_factory.get_nodes(2, opts=[{}, {}]) + l1.rpc.connect(l2.info['id'], 'localhost', l2.port) + c12, _ = l1.fundchannel(l2, 10**5) + + l1.stop() + + os.unlink(os.path.join(l1.daemon.lightning_dir, TEST_NETWORK, "lightningd.sqlite3")) + + l1.start() + assert l1.daemon.is_in_log('Server started with public key') + stubs = l1.rpc.emergencyrecover()["stubs"] + assert len(stubs) == 1 + assert stubs[0] == _["channel_id"] + + listfunds = l1.rpc.listfunds()["channels"][0] + assert listfunds["short_channel_id"] == "1x1x1" + + def test_commitfee_option(node_factory): """Sanity check for the --commit-fee startup option.""" l1, l2 = node_factory.get_nodes(2, opts=[{"commit-fee": "200"}, {}]) diff --git a/tools/fromschema.py b/tools/fromschema.py index 350736f0530c..a8708c5fe215 100755 --- a/tools/fromschema.py +++ b/tools/fromschema.py @@ -127,6 +127,17 @@ def output_members(sub, indent=''): # Remove deprecated and stub properties, collect warnings # (Stubs required to keep additionalProperties: false happy) + + # FIXME: It fails for schemas which have only an array type with + # no properties, ex: + # "abcd": { + # "type": "array", + # "items": { + # "type": "whatever", + # "description": "efgh" + # } + # } + # Checkout the schema of `staticbackup`. for p in list(sub['properties'].keys()): if len(sub['properties'][p]) == 0 or 'deprecated' in sub['properties'][p]: del sub['properties'][p] diff --git a/tools/gen/header_template b/tools/gen/header_template index 35e62e60aeea..4b7188555f5e 100644 --- a/tools/gen/header_template +++ b/tools/gen/header_template @@ -148,7 +148,7 @@ void towire_${subtype.name}(u8 **p, const ${subtype.type_name()} *${subtype.name % if subtype.is_varsize(): ${subtype.type_name()} *fromwire_${subtype.name}(const tal_t *ctx, const u8 **cursor, size_t *plen); % else: -void fromwire_${subtype.name}(const u8 **cursor, size_t *plen, ${subtype.type_name()} *${subtype.name}); +bool fromwire_${subtype.name}(const u8 **cursor, size_t *plen, ${subtype.type_name()} *${subtype.name}); % endif % endfor diff --git a/tools/gen/impl_template b/tools/gen/impl_template index 3d013f7f144d..cb3d1f77b206 100644 --- a/tools/gen/impl_template +++ b/tools/gen/impl_template @@ -151,7 +151,7 @@ ${static}void towire_${subtype.name}(u8 **p, const ${subtype.type_name()} *${sub ${static}${subtype.type_name()} * fromwire_${subtype.name}(const tal_t *ctx, const u8 **cursor, size_t *plen) % else: -${static}void fromwire_${subtype.name}(${'const tal_t *ctx, ' if subtype.needs_context() else ''}const u8 **cursor, size_t *plen, ${subtype.type_name()} *${subtype.name}) +${static}bool fromwire_${subtype.name}(${'const tal_t *ctx, ' if subtype.needs_context() else ''}const u8 **cursor, size_t *plen, ${subtype.type_name()} *${subtype.name}) % endif { % if subtype.is_varsize(): @@ -175,6 +175,9 @@ ${static}void fromwire_${subtype.name}(${'const tal_t *ctx, ' if subtype.needs_c % if subtype.is_varsize(): return ${subtype.name}; +% else: + + return *cursor != NULL; % endif } % endfor ## END Subtypes diff --git a/tools/generate-wire.py b/tools/generate-wire.py index e0476b11f4d2..19e658d936a5 100755 --- a/tools/generate-wire.py +++ b/tools/generate-wire.py @@ -244,7 +244,7 @@ class Type(FieldSet): 'tx_parts', 'wally_psbt', 'wally_tx', - 'channel_type', + 'scb_chan', ] # Some BOLT types are re-typed based on their field name diff --git a/wallet/Makefile b/wallet/Makefile index 05ce68de4593..13c0e7d71137 100644 --- a/wallet/Makefile +++ b/wallet/Makefile @@ -33,8 +33,8 @@ WALLET_SQL_FILES := \ wallet/test/run-wallet.c \ wallet/statements_gettextgen.po: $(WALLET_SQL_FILES) $(FORCE) - @if $(call SHA256STAMP_CHANGED); then \ - $(call VERBOSE,"xgettext $@",xgettext -kNAMED_SQL -kSQL --add-location --no-wrap --omit-header -o $@ $(WALLET_SQL_FILES) && $(call SHA256STAMP,# ,)); \ + @if $(call SHA256STAMP_CHANGED_ALL); then \ + $(call VERBOSE,"xgettext $@",xgettext -kNAMED_SQL -kSQL --add-location --no-wrap --omit-header -o $@ $(WALLET_SQL_FILES) && $(call SHA256STAMP_ALL,# ,)); \ fi wallet/db_%_sqlgen.c: wallet/statements_gettextgen.po devtools/sql-rewrite.py $(FORCE) diff --git a/wallet/test/run-wallet.c b/wallet/test/run-wallet.c index 65cf287f89aa..94cb6a29e8e5 100644 --- a/wallet/test/run-wallet.c +++ b/wallet/test/run-wallet.c @@ -809,6 +809,9 @@ u8 *towire_required_channel_feature_missing(const tal_t *ctx UNNEEDED) /* Generated stub for towire_required_node_feature_missing */ u8 *towire_required_node_feature_missing(const tal_t *ctx UNNEEDED) { fprintf(stderr, "towire_required_node_feature_missing called!\n"); abort(); } +/* Generated stub for towire_scb_chan */ +void towire_scb_chan(u8 **p UNNEEDED, const struct scb_chan *scb_chan UNNEEDED) +{ fprintf(stderr, "towire_scb_chan called!\n"); abort(); } /* Generated stub for towire_temporary_channel_failure */ u8 *towire_temporary_channel_failure(const tal_t *ctx UNNEEDED, const u8 *channel_update UNNEEDED) { fprintf(stderr, "towire_temporary_channel_failure called!\n"); abort(); } diff --git a/wallet/wallet.c b/wallet/wallet.c index efd966d32a74..6f6c6b699a86 100644 --- a/wallet/wallet.c +++ b/wallet/wallet.c @@ -1114,6 +1114,7 @@ wallet_stmt2inflight(struct wallet *w, struct db_stmt *stmt, struct amount_msat lease_fee; struct bitcoin_outpoint funding; struct bitcoin_signature last_sig; + struct bitcoin_tx *last_tx; struct channel_inflight *inflight; secp256k1_ecdsa_signature *lease_commit_sig; @@ -1149,12 +1150,19 @@ wallet_stmt2inflight(struct wallet *w, struct db_stmt *stmt, db_col_ignore(stmt, "lease_fee"); } + /* last_tx is null for stub channels used for recovering funds through + * Static channel backups. */ + if (!db_col_is_null(stmt, "last_tx")) + last_tx = db_col_psbt_to_tx(tmpctx, stmt, "last_tx"); + else + last_tx = NULL; + inflight = new_inflight(chan, &funding, db_col_int(stmt, "funding_feerate"), funding_sat, our_funding_sat, db_col_psbt(tmpctx, stmt, "funding_psbt"), - db_col_psbt_to_tx(tmpctx, stmt, "last_tx"), + last_tx, last_sig, db_col_int(stmt, "lease_expiry"), lease_commit_sig, @@ -1260,6 +1268,7 @@ static struct channel *wallet_stmt2channel(struct wallet *w, struct db_stmt *stm struct bitcoin_outpoint funding; struct bitcoin_outpoint *shutdown_wrong_funding; struct bitcoin_signature last_sig; + struct bitcoin_tx *last_tx; u8 *remote_shutdown_scriptpubkey; u8 *local_shutdown_scriptpubkey; struct changed_htlc *last_sent_commit; @@ -1445,6 +1454,13 @@ static struct channel *wallet_stmt2channel(struct wallet *w, struct db_stmt *stm else type = channel_type_none(NULL); + /* last_tx is null for stub channels used for recovering funds through + * Static channel backups. */ + if (!db_col_is_null(stmt, "last_tx")) + last_tx = db_col_psbt_to_tx(tmpctx, stmt, "last_tx"); + else + last_tx = NULL; + chan = new_channel(peer, db_col_u64(stmt, "id"), &wshachain, db_col_int(stmt, "state"), @@ -1469,7 +1485,7 @@ static struct channel *wallet_stmt2channel(struct wallet *w, struct db_stmt *stm our_msat, msat_to_us_min, /* msatoshi_to_us_min */ msat_to_us_max, /* msatoshi_to_us_max */ - db_col_psbt_to_tx(tmpctx, stmt, "last_tx"), + last_tx, &last_sig, wallet_htlc_sigs_load(tmpctx, w, db_col_u64(stmt, "id"), @@ -1914,7 +1930,10 @@ void wallet_channel_save(struct wallet *w, struct channel *chan) db_bind_talarr(stmt, 17, chan->shutdown_scriptpubkey[REMOTE]); db_bind_u64(stmt, 18, chan->final_key_idx); db_bind_u64(stmt, 19, chan->our_config.id); - db_bind_psbt(stmt, 20, chan->last_tx->psbt); + if (chan->last_tx) + db_bind_psbt(stmt, 20, chan->last_tx->psbt); + else + db_bind_null(stmt, 20); db_bind_signature(stmt, 21, &chan->last_sig.s); db_bind_int(stmt, 22, chan->last_was_revoke); db_bind_int(stmt, 23, chan->min_possible_feerate);