From 43d7dd3d99b7cd9b889e8baa02f2d47670bff379 Mon Sep 17 00:00:00 2001 From: "Johan T. Halseth" Date: Sun, 17 Dec 2017 16:13:23 +0100 Subject: [PATCH] lnd: make NumRequiredConfs and RequiredRemoteDelay scale with chanAmt This commit makes the value returned fomr NumRequiredConfs and RequiredRemoteDelay used during the funding process scale linearly with the channel size. This is done to ensure that in cases there are more at stake in a channel, we have more time to react to reorgs, or unilateral closes. If the user explicitly specified values for these two at startup, we return those instead, without doing the scaling. --- lnd.go | 71 +++++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 63 insertions(+), 8 deletions(-) diff --git a/lnd.go b/lnd.go index 19a94b63..af9e0bb4 100644 --- a/lnd.go +++ b/lnd.go @@ -298,16 +298,71 @@ func lndMain() error { return nil, fmt.Errorf("unable to find channel") }, DefaultRoutingPolicy: activeChainControl.routingPolicy, - NumRequiredConfs: func(chanAmt btcutil.Amount, pushAmt lnwire.MilliSatoshi) uint16 { - // TODO(roasbeef): add configurable mapping - // * simple switch initially - // * assign coefficient, etc - return uint16(cfg.Bitcoin.DefaultNumChanConfs) + NumRequiredConfs: func(chanAmt btcutil.Amount, + pushAmt lnwire.MilliSatoshi) uint16 { + // For large channels we increase the number + // of confirmations we require for the + // channel to be considered open. As it is + // always the responder that gets to choose + // value, the pushAmt is value being pushed + // to us. This means we have more to lose + // in the case this gets re-orged out, and + // we will require more confirmations before + // we consider it open. + // TODO(halseth): Use Litecoin params in case + // of LTC channels. + + // In case the user has explicitly specified + // a default value for the number of + // confirmations, we use it. + defaultConf := uint16(cfg.Bitcoin.DefaultNumChanConfs) + if defaultConf != 0 { + return defaultConf + } + + // If not we return a value scaled linearly + // between 3 and 6, depending on channel size. + // TODO(halseth): Use 1 as minimum? + minConf := uint64(3) + maxConf := uint64(6) + maxChannelSize := uint64( + lnwire.NewMSatFromSatoshis(maxFundingAmount)) + stake := lnwire.NewMSatFromSatoshis(chanAmt) + pushAmt + conf := maxConf * uint64(stake) / maxChannelSize + if conf < minConf { + conf = minConf + } + if conf > maxConf { + conf = maxConf + } + return uint16(conf) }, RequiredRemoteDelay: func(chanAmt btcutil.Amount) uint16 { - // TODO(roasbeef): add additional hooks for - // configuration - return 4 + // We scale the remote CSV delay (the time the + // remote have to claim funds in case of a unilateral + // close) linearly from minRemoteDelay blocks + // for small channels, to maxRemoteDelay blocks + // for channels of size maxFundingAmount. + // TODO(halseth): Litecoin parameter for LTC. + + // In case the user has explicitly specified + // a default value for the remote delay, we + // use it. + defaultDelay := uint16(cfg.Bitcoin.DefaultRemoteDelay) + if defaultDelay > 0 { + return defaultDelay + } + + // If not we scale according to channel size. + delay := uint16(maxRemoteDelay * + chanAmt / maxFundingAmount) + if delay < minRemoteDelay { + delay = minRemoteDelay + } + if delay > maxRemoteDelay { + delay = maxRemoteDelay + } + return delay }, }) if err != nil {