diff --git a/doc/lightning-listconfigs.7 b/doc/lightning-listconfigs.7 index d946d1e03a7c..e781d0019d63 100644 --- a/doc/lightning-listconfigs.7 +++ b/doc/lightning-listconfigs.7 @@ -122,6 +122,10 @@ On success, an object is returned, containing: .IP \[bu] \fBmax-concurrent-htlcs\fR (u32, optional): \fBmax-concurrent-htlcs\fR field from config or cmdline, or default .IP \[bu] +\fBhtlc-minimum-msat\fR (msat, optional): \fBhtlc-minimum-msat\fR field from config or cmdline, or default +.IP \[bu] +\fBhtlc-maximum-msat\fR (msat, optional): \fBhtlc-maximum-msat\fR field from config or cmdline, or default +.IP \[bu] \fBmax-dust-htlc-exposure-msat\fR (msat, optional): \fBmax-dust-htlc-exposure-mast\fR field from config or cmdline, or default .IP \[bu] \fBmin-capacity-sat\fR (u64, optional): \fBmin-capacity-sat\fR field from config or cmdline, or default @@ -140,6 +144,8 @@ On success, an object is returned, containing: .IP \[bu] \fBdisable-dns\fR (boolean, optional): \fBtrue\fR if \fBdisable-dns\fR was set in config or cmdline .IP \[bu] +\fBdisable-ip-discovery\fR (boolean, optional): \fBtrue\fR if \fBdisable-ip-discovery\fR was set in config or cmdline +.IP \[bu] \fBencrypted-hsm\fR (boolean, optional): \fBtrue\fR if \fBencrypted-hsm\fR was set in config or cmdline .IP \[bu] \fBrpc-file-mode\fR (string, optional): \fBrpc-file-mode\fR field from config or cmdline, or default @@ -276,4 +282,4 @@ Vincenzo Palazzo \fI wrote the initial versi Main web site: \fIhttps://github.com/ElementsProject/lightning\fR -\" SHA256STAMP:759090c2619cd40cba89b670ea16d4885f9aea520588d30d0ee8041369d5b91e +\" SHA256STAMP:8d8f73010f55f3af6e050c944cf7670109224b3cf3166cc754047f6e20beef20 diff --git a/doc/lightning-listconfigs.7.md b/doc/lightning-listconfigs.7.md index c6cdf6290720..5b285b663c47 100644 --- a/doc/lightning-listconfigs.7.md +++ b/doc/lightning-listconfigs.7.md @@ -71,6 +71,8 @@ On success, an object is returned, containing: - **rescan** (integer, optional): `rescan` field from config or cmdline, or default - **fee-per-satoshi** (u32, optional): `fee-per-satoshi` field from config or cmdline, or default - **max-concurrent-htlcs** (u32, optional): `max-concurrent-htlcs` field from config or cmdline, or default +- **htlc-minimum-msat** (msat, optional): `htlc-minimum-msat` field from config or cmdline, or default +- **htlc-maximum-msat** (msat, optional): `htlc-maximum-msat` field from config or cmdline, or default - **max-dust-htlc-exposure-msat** (msat, optional): `max-dust-htlc-exposure-mast` field from config or cmdline, or default - **min-capacity-sat** (u64, optional): `min-capacity-sat` field from config or cmdline, or default - **addr** (string, optional): `addr` field from config or cmdline (can be more than one) @@ -80,6 +82,7 @@ On success, an object is returned, containing: - **autolisten** (boolean, optional): `autolisten` field from config or cmdline, or default - **proxy** (string, optional): `proxy` field from config or cmdline, or default - **disable-dns** (boolean, optional): `true` if `disable-dns` was set in config or cmdline +- **disable-ip-discovery** (boolean, optional): `true` if `disable-ip-discovery` was set in config or cmdline - **encrypted-hsm** (boolean, optional): `true` if `encrypted-hsm` was set in config or cmdline - **rpc-file-mode** (string, optional): `rpc-file-mode` field from config or cmdline, or default - **log-level** (string, optional): `log-level` field from config or cmdline, or default @@ -208,4 +211,4 @@ RESOURCES --------- Main web site: -[comment]: # ( SHA256STAMP:59b197ad256bd701744ed5aa9f663166e48ef6320cf3a1538af0bd855daa3186) +[comment]: # ( SHA256STAMP:ebc37d1f9cb452d312285a8168d2bb6da2d1dba08db56bbb8d3d7f47b58d7fa4) diff --git a/doc/lightningd-config.5.md b/doc/lightningd-config.5.md index 9fe83e46fb05..c7a7e97b3948 100644 --- a/doc/lightningd-config.5.md +++ b/doc/lightningd-config.5.md @@ -278,6 +278,23 @@ values), and the order is "opening", "mutual_close", "unilateral_close", You would usually put this option in the per-chain config file, to avoid setting it on Bitcoin mainnet! e.g. `~rusty/.lightning/regtest/config`. + **htlc-minimum-msat**=*MILLISATOSHI* +Default: 0. Sets the minimal allowed HTLC value for newly created channels. +If you want to change the `htlc_minimum_msat` for existing channels, use the +RPC call lightning-setchannel(7). + + **htlc-maximum-msat**=*MILLISATOSHI* +Default: unset (no limit). Sets the maximum allowed HTLC value for newly created +channels. If you want to change the `htlc_maximum_msat` for existing channels, +use the RPC call lightning-setchannel(7). + + **disable-ip-discovery** +Turn off public IP discovery to send `node_announcement` updates that contain +the discovered IP with TCP port 9735 as announced address. If unset and you +open TCP port 9735 on your router towords your node, your node will remain +connectable on changing IP addresses. Note: Will always be disabled if you use +'always-use-proxy'. + ### Lightning channel and HTLC options **large-channels** diff --git a/doc/schemas/listconfigs.schema.json b/doc/schemas/listconfigs.schema.json index ac041bf8dea8..c3215e8e9ed2 100644 --- a/doc/schemas/listconfigs.schema.json +++ b/doc/schemas/listconfigs.schema.json @@ -187,6 +187,14 @@ "type": "u32", "description": "`max-concurrent-htlcs` field from config or cmdline, or default" }, + "htlc-minimum-msat": { + "type": "msat", + "description": "`htlc-minimum-msat` field from config or cmdline, or default" + }, + "htlc-maximum-msat": { + "type": "msat", + "description": "`htlc-maximum-msat` field from config or cmdline, or default" + }, "max-dust-htlc-exposure-msat": { "type": "msat", "description": "`max-dust-htlc-exposure-mast` field from config or cmdline, or default" @@ -223,6 +231,10 @@ "type": "boolean", "description": "`true` if `disable-dns` was set in config or cmdline" }, + "disable-ip-discovery": { + "type": "boolean", + "description": "`true` if `disable-ip-discovery` was set in config or cmdline" + }, "encrypted-hsm": { "type": "boolean", "description": "`true` if `encrypted-hsm` was set in config or cmdline" diff --git a/lightningd/lightningd.h b/lightningd/lightningd.h index 973db2a7c863..57b5a4d9c97f 100644 --- a/lightningd/lightningd.h +++ b/lightningd/lightningd.h @@ -33,6 +33,10 @@ struct config { /* htlcs per channel */ u32 max_concurrent_htlcs; + /* htlc min/max values */ + struct amount_msat htlc_minimum_msat; + struct amount_msat htlc_maximum_msat; + /* Max amount of dust allowed per channel */ struct amount_msat max_dust_htlc_exposure_msat; @@ -52,6 +56,9 @@ struct config { /* Are we allowed to use DNS lookup for peers. */ bool use_dns; + /* Turn off IP address announcement discovered via peer `remote_addr` */ + bool disable_ip_discovery; + /* Minimal amount of effective funding_satoshis for accepting channels */ u64 min_capacity_sat; diff --git a/lightningd/opening_common.c b/lightningd/opening_common.c index 7442cea19a93..f866a91f5be0 100644 --- a/lightningd/opening_common.c +++ b/lightningd/opening_common.c @@ -147,7 +147,7 @@ void channel_config(struct lightningd *ld, = ld->config.max_dust_htlc_exposure_msat; /* Don't care */ - ours->htlc_minimum = AMOUNT_MSAT(0); + ours->htlc_minimum = ld->config.htlc_minimum_msat; /* BOLT #2: * diff --git a/lightningd/opening_control.c b/lightningd/opening_control.c index 87ffc1984baf..9499a76e3e41 100644 --- a/lightningd/opening_control.c +++ b/lightningd/opening_control.c @@ -211,8 +211,8 @@ wallet_commit_channel(struct lightningd *ld, take(new_height_states(NULL, uc->fc ? LOCAL : REMOTE, &lease_start_blockheight)), 0, NULL, 0, 0, /* No leases on v1s */ - AMOUNT_MSAT(0), /* No htlc_minimum_msat */ - AMOUNT_MSAT(-1ULL)); /* No htlc_maximum_msat */ + ld->config.htlc_minimum_msat, + ld->config.htlc_maximum_msat); /* Now we finally put it in the database. */ wallet_channel_insert(ld->wallet, channel); diff --git a/lightningd/options.c b/lightningd/options.c index e756854929ec..5f95ea6f8493 100644 --- a/lightningd/options.c +++ b/lightningd/options.c @@ -757,6 +757,10 @@ static const struct config testnet_config = { /* Testnet blockspace is free. */ .max_concurrent_htlcs = 483, + /* channel defaults for htlc min/max values */ + .htlc_minimum_msat = AMOUNT_MSAT(0), + .htlc_maximum_msat = AMOUNT_MSAT(-1ULL), /* no limit */ + /* Max amount of dust allowed per channel (50ksat) */ .max_dust_htlc_exposure_msat = AMOUNT_MSAT(50000000), @@ -780,6 +784,9 @@ static const struct config testnet_config = { .use_dns = true, + /* Turn off IP address announcement discovered via peer `remote_addr` */ + .disable_ip_discovery = false, + /* Sets min_effective_htlc_capacity - at 1000$/BTC this is 10ct */ .min_capacity_sat = 10000, @@ -806,6 +813,10 @@ static const struct config mainnet_config = { /* While up to 483 htlcs are possible we do 30 by default (as eclair does) to save blockspace */ .max_concurrent_htlcs = 30, + /* defaults for htlc min/max values */ + .htlc_minimum_msat = AMOUNT_MSAT(0), + .htlc_maximum_msat = AMOUNT_MSAT(-1ULL), /* no limit */ + /* Max amount of dust allowed per channel (50ksat) */ .max_dust_htlc_exposure_msat = AMOUNT_MSAT(50000000), @@ -839,6 +850,9 @@ static const struct config mainnet_config = { .use_dns = true, + /* Turn off IP address announcement discovered via peer `remote_addr` */ + .disable_ip_discovery = false, + /* Sets min_effective_htlc_capacity - at 1000$/BTC this is 10ct */ .min_capacity_sat = 10000, @@ -1102,6 +1116,12 @@ static void register_opts(struct lightningd *ld) opt_register_arg("--fee-per-satoshi", opt_set_u32, opt_show_u32, &ld->config.fee_per_satoshi, "Microsatoshi fee for every satoshi in HTLC"); + opt_register_arg("--htlc-minimum-msat", opt_set_msat, NULL, + &ld->config.htlc_minimum_msat, + "The default minimal value an HTLC must carry in order to be forwardable for new channels"); + opt_register_arg("--htlc-maximum-msat", opt_set_msat, NULL, + &ld->config.htlc_maximum_msat, + "The default maximal value an HTLC must carry in order to be forwardable for new channel"); opt_register_arg("--max-concurrent-htlcs", opt_set_u32, opt_show_u32, &ld->config.max_concurrent_htlcs, "Number of HTLCs one channel can handle concurrently. Should be between 1 and 483"); @@ -1120,6 +1140,9 @@ static void register_opts(struct lightningd *ld) opt_register_arg("--announce-addr", opt_add_announce_addr, NULL, ld, "Set an IP address (v4 or v6) or .onion v3 to announce, but not listen on"); + opt_register_noarg("--disable-ip-discovery", opt_set_bool, + &ld->config.disable_ip_discovery, + "Turn off announcement of discovered public IPs"); opt_register_noarg("--offline", opt_set_offline, ld, "Start in offline-mode (do not automatically reconnect and do not accept incoming connections)"); diff --git a/lightningd/peer_control.c b/lightningd/peer_control.c index 6bfd09f689dd..c5e6de37cc96 100644 --- a/lightningd/peer_control.c +++ b/lightningd/peer_control.c @@ -1070,7 +1070,7 @@ static void update_remote_addr(struct lightningd *ld, const struct node_id peer_id) { /* failsafe to prevent privacy leakage. */ - if (ld->always_use_proxy) + if (ld->always_use_proxy || ld->config.disable_ip_discovery) return; switch (remote_addr->type) { diff --git a/tests/test_connection.py b/tests/test_connection.py index 4e5eb8be1753..79bb419f3675 100644 --- a/tests/test_connection.py +++ b/tests/test_connection.py @@ -120,6 +120,38 @@ def test_remote_addr(node_factory, bitcoind): assert address['port'] == 9735 +@pytest.mark.developer("needs DEVELOPER=1 for having localhost remote_addr and fast gossip") +def test_remote_addr_disabled(node_factory, bitcoind): + """Simply tests that IP address discovery annoucements can be turned off + """ + opts = {'announce-addr': [], 'disable-ip-discovery': None, 'may_reconnect': True} + l1, l2, l3 = node_factory.get_nodes(3, opts=opts) + + # l1->l2 + l2.rpc.connect(l1.info['id'], 'localhost', l1.port) + l2.daemon.wait_for_log("Peer says it sees our address as: 127.0.0.1:[0-9]{5}") + l1.fundchannel(l2) + bitcoind.generate_block(5) + l1.daemon.wait_for_log(f"Received node_announcement for node {l2.info['id']}") + # l2->l3 + l2.rpc.connect(l3.info['id'], 'localhost', l3.port) + l2.daemon.wait_for_log("Peer says it sees our address as: 127.0.0.1:[0-9]{5}") + l2.fundchannel(l3) + bitcoind.generate_block(5) + + # restart both and wait for channels to be ready + l1.restart() + l2.rpc.connect(l1.info['id'], 'localhost', l1.port) + l2.daemon.wait_for_log("Already have funding locked in") + l3.restart() + l2.rpc.connect(l3.info['id'], 'localhost', l3.port) + l2.daemon.wait_for_log("Already have funding locked in") + + # if ip discovery would have been enabled, we would have send an updated + # node_annoucement by now. Check we didn't... + assert not l2.daemon.is_in_log("Update our node_announcement for discovered address") + + def test_connect_standard_addr(node_factory): """Test standard node@host:port address """ diff --git a/tests/test_pay.py b/tests/test_pay.py index 1a4c23f50419..56def1c0caec 100644 --- a/tests/test_pay.py +++ b/tests/test_pay.py @@ -2376,6 +2376,29 @@ def test_setchannel_all(node_factory, bitcoind): assert result['channels'][1]['maximum_htlc_out_msat'] == 0xCAFE +@pytest.mark.developer("updates are delayed without --dev-fast-gossip") +def test_setchannel_startup_opts(node_factory, bitcoind): + """Tests that custom config/cmdline options are applied correctly when set + """ + opts = { + 'fee-base': 2, + 'fee-per-satoshi': 3, + 'htlc-minimum-msat': '4msat', + 'htlc-maximum-msat': '5msat' + } + l1, l2 = node_factory.line_graph(2, opts=opts, wait_for_announce=True) + + result = l2.rpc.listchannels()['channels'] + assert result[0]['base_fee_millisatoshi'] == 2 + assert result[0]['fee_per_millionth'] == 3 + assert result[0]['htlc_minimum_msat'] == Millisatoshi(4) + assert result[0]['htlc_maximum_msat'] == Millisatoshi(5) + assert result[1]['base_fee_millisatoshi'] == 2 + assert result[1]['fee_per_millionth'] == 3 + assert result[1]['htlc_minimum_msat'] == Millisatoshi(4) + assert result[1]['htlc_maximum_msat'] == Millisatoshi(5) + + @pytest.mark.developer("gossip without DEVELOPER=1 is slow") def test_channel_spendable(node_factory, bitcoind): """Test that spendable_msat is accurate"""