lnwallet: pack htlcView.{OurUpdates|TheirUpdates} into Dual.

This commit moves the collection of updates behind a Dual structure.
This allows us in a later commit to index into it via a ChannelParty
parameter which will simplify the loops in evaluateHTLCView.
This commit is contained in:
Keagan McClelland committed 2024-10-14 09:33:38 -06:00
1 parent 1b2cb14254
commit 4b2a4e36ad
3 files changed
+44 -38

No files matched your search

+32 -29
View File
@@ -2675,11 +2675,8 @@ type HtlcView struct {
// created using this view. // created using this view.
NextHeight uint64 NextHeight uint64
// OurUpdates are our outgoing HTLCs. // Updates is a Dual of the Local and Remote HTLCs.
OurUpdates []*paymentDescriptor Updates lntypes.Dual[[]*paymentDescriptor]
// TheirUpdates are their incoming HTLCs.
TheirUpdates []*paymentDescriptor
// FeePerKw is the fee rate in sat/kw of the commitment transaction. // FeePerKw is the fee rate in sat/kw of the commitment transaction.
FeePerKw chainfee.SatPerKWeight FeePerKw chainfee.SatPerKWeight
@@ -2688,13 +2685,13 @@ type HtlcView struct {
// AuxOurUpdates returns the outgoing HTLCs as a read-only copy of // AuxOurUpdates returns the outgoing HTLCs as a read-only copy of
// AuxHtlcDescriptors. // AuxHtlcDescriptors.
func (v *HtlcView) AuxOurUpdates() []AuxHtlcDescriptor { func (v *HtlcView) AuxOurUpdates() []AuxHtlcDescriptor {
return fn.Map(newAuxHtlcDescriptor, v.OurUpdates) return fn.Map(newAuxHtlcDescriptor, v.Updates.Local)
} }
// AuxTheirUpdates returns the incoming HTLCs as a read-only copy of // AuxTheirUpdates returns the incoming HTLCs as a read-only copy of
// AuxHtlcDescriptors. // AuxHtlcDescriptors.
func (v *HtlcView) AuxTheirUpdates() []AuxHtlcDescriptor { func (v *HtlcView) AuxTheirUpdates() []AuxHtlcDescriptor {
return fn.Map(newAuxHtlcDescriptor, v.TheirUpdates) return fn.Map(newAuxHtlcDescriptor, v.Updates.Remote)
} }
// fetchHTLCView returns all the candidate HTLC updates which should be // fetchHTLCView returns all the candidate HTLC updates which should be
@@ -2728,8 +2725,10 @@ func (lc *LightningChannel) fetchHTLCView(theirLogIndex,
} }
return &HtlcView{ return &HtlcView{
OurUpdates: ourHTLCs, Updates: lntypes.Dual[[]*paymentDescriptor]{
TheirUpdates: theirHTLCs, Local: ourHTLCs,
Remote: theirHTLCs,
},
} }
} }
@@ -2853,15 +2852,15 @@ func (lc *LightningChannel) fetchCommitmentView(
// commitment are mutated, we'll manually copy over each HTLC to its // commitment are mutated, we'll manually copy over each HTLC to its
// respective slice. // respective slice.
c.outgoingHTLCs = make( c.outgoingHTLCs = make(
[]paymentDescriptor, len(filteredHTLCView.OurUpdates), []paymentDescriptor, len(filteredHTLCView.Updates.Local),
) )
for i, htlc := range filteredHTLCView.OurUpdates { for i, htlc := range filteredHTLCView.Updates.Local {
c.outgoingHTLCs[i] = *htlc c.outgoingHTLCs[i] = *htlc
} }
c.incomingHTLCs = make( c.incomingHTLCs = make(
[]paymentDescriptor, len(filteredHTLCView.TheirUpdates), []paymentDescriptor, len(filteredHTLCView.Updates.Remote),
) )
for i, htlc := range filteredHTLCView.TheirUpdates { for i, htlc := range filteredHTLCView.Updates.Remote {
c.incomingHTLCs[i] = *htlc c.incomingHTLCs[i] = *htlc
} }
@@ -2916,7 +2915,7 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
// First we run through non-add entries in both logs, populating the // First we run through non-add entries in both logs, populating the
// skip sets. // skip sets.
for _, entry := range view.OurUpdates { for _, entry := range view.Updates.Local {
switch entry.EntryType { switch entry.EntryType {
// Skip adds for now. They will be processed below. // Skip adds for now. They will be processed below.
case Add: case Add:
@@ -2961,7 +2960,7 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
} }
// Do the same for our peer's updates. // Do the same for our peer's updates.
for _, entry := range view.TheirUpdates { for _, entry := range view.Updates.Remote {
switch entry.EntryType { switch entry.EntryType {
// Skip adds for now. They will be processed below. // Skip adds for now. They will be processed below.
case Add: case Add:
@@ -3007,7 +3006,7 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
// Next we take a second pass through all the log entries, skipping any // Next we take a second pass through all the log entries, skipping any
// settled HTLCs, and debiting the chain state balance due to any newly // settled HTLCs, and debiting the chain state balance due to any newly
// added HTLCs. // added HTLCs.
for _, entry := range view.OurUpdates { for _, entry := range view.Updates.Local {
isAdd := entry.EntryType == Add isAdd := entry.EntryType == Add
if skipUs.Contains(entry.HtlcIndex) || !isAdd { if skipUs.Contains(entry.HtlcIndex) || !isAdd {
continue continue
@@ -3024,11 +3023,11 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
) )
} }
newView.OurUpdates = append(newView.OurUpdates, entry) newView.Updates.Local = append(newView.Updates.Local, entry)
} }
// Again, we do the same for our peer's updates. // Again, we do the same for our peer's updates.
for _, entry := range view.TheirUpdates { for _, entry := range view.Updates.Remote {
isAdd := entry.EntryType == Add isAdd := entry.EntryType == Add
if skipThem.Contains(entry.HtlcIndex) || !isAdd { if skipThem.Contains(entry.HtlcIndex) || !isAdd {
continue continue
@@ -3045,7 +3044,7 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
) )
} }
newView.TheirUpdates = append(newView.TheirUpdates, entry) newView.Updates.Remote = append(newView.Updates.Remote, entry)
} }
// Create a function that is capable of identifying whether or not the // Create a function that is capable of identifying whether or not the
@@ -3075,10 +3074,12 @@ func (lc *LightningChannel) evaluateHTLCView(view *HtlcView, ourBalance,
// Collect all of the updates that haven't had their commit heights set // Collect all of the updates that haven't had their commit heights set
// for the commitment chain corresponding to whoseCommitmentChain. // for the commitment chain corresponding to whoseCommitmentChain.
uncommittedUpdates := lntypes.Dual[[]*paymentDescriptor]{ uncommittedUpdates := lntypes.MapDual(
Local: fn.Filter(isUncommitted, view.OurUpdates), view.Updates,
Remote: fn.Filter(isUncommitted, view.TheirUpdates), func(us []*paymentDescriptor) []*paymentDescriptor {
} return fn.Filter(isUncommitted, us)
},
)
return newView, uncommittedUpdates, nil return newView, uncommittedUpdates, nil
} }
@@ -3746,10 +3747,12 @@ func (lc *LightningChannel) validateCommitmentSanity(theirLogCounter,
// appropriate update log, in order to validate the sanity of the // appropriate update log, in order to validate the sanity of the
// commitment resulting from _actually adding_ this HTLC to the state. // commitment resulting from _actually adding_ this HTLC to the state.
if predictOurAdd != nil { if predictOurAdd != nil {
view.OurUpdates = append(view.OurUpdates, predictOurAdd) view.Updates.Local = append(view.Updates.Local, predictOurAdd)
} }
if predictTheirAdd != nil { if predictTheirAdd != nil {
view.TheirUpdates = append(view.TheirUpdates, predictTheirAdd) view.Updates.Remote = append(
view.Updates.Remote, predictTheirAdd,
)
} }
ourBalance, theirBalance, commitWeight, filteredView, err := lc.computeView( ourBalance, theirBalance, commitWeight, filteredView, err := lc.computeView(
@@ -3904,7 +3907,7 @@ func (lc *LightningChannel) validateCommitmentSanity(theirLogCounter,
// First check that the remote updates won't violate it's channel // First check that the remote updates won't violate it's channel
// constraints. // constraints.
err = validateUpdates( err = validateUpdates(
filteredView.TheirUpdates, &lc.channelState.RemoteChanCfg, filteredView.Updates.Remote, &lc.channelState.RemoteChanCfg,
) )
if err != nil { if err != nil {
return err return err
@@ -3913,7 +3916,7 @@ func (lc *LightningChannel) validateCommitmentSanity(theirLogCounter,
// Secondly check that our updates won't violate our channel // Secondly check that our updates won't violate our channel
// constraints. // constraints.
err = validateUpdates( err = validateUpdates(
filteredView.OurUpdates, &lc.channelState.LocalChanCfg, filteredView.Updates.Local, &lc.channelState.LocalChanCfg,
) )
if err != nil { if err != nil {
return err return err
@@ -4700,7 +4703,7 @@ func (lc *LightningChannel) computeView(view *HtlcView,
// Now go through all HTLCs at this stage, to calculate the total // Now go through all HTLCs at this stage, to calculate the total
// weight, needed to calculate the transaction fee. // weight, needed to calculate the transaction fee.
var totalHtlcWeight lntypes.WeightUnit var totalHtlcWeight lntypes.WeightUnit
for _, htlc := range filteredHTLCView.OurUpdates { for _, htlc := range filteredHTLCView.Updates.Local {
if HtlcIsDust( if HtlcIsDust(
lc.channelState.ChanType, false, whoseCommitChain, lc.channelState.ChanType, false, whoseCommitChain,
feePerKw, htlc.Amount.ToSatoshis(), dustLimit, feePerKw, htlc.Amount.ToSatoshis(), dustLimit,
@@ -4711,7 +4714,7 @@ func (lc *LightningChannel) computeView(view *HtlcView,
totalHtlcWeight += input.HTLCWeight totalHtlcWeight += input.HTLCWeight
} }
for _, htlc := range filteredHTLCView.TheirUpdates { for _, htlc := range filteredHTLCView.Updates.Remote {
if HtlcIsDust( if HtlcIsDust(
lc.channelState.ChanType, true, whoseCommitChain, lc.channelState.ChanType, true, whoseCommitChain,
feePerKw, htlc.Amount.ToSatoshis(), dustLimit, feePerKw, htlc.Amount.ToSatoshis(), dustLimit,
+8 -5
View File
@@ -8941,9 +8941,11 @@ func TestEvaluateView(t *testing.T) {
} }
view := &HtlcView{ view := &HtlcView{
OurUpdates: test.ourHtlcs, Updates: lntypes.Dual[[]*paymentDescriptor]{
TheirUpdates: test.theirHtlcs, Local: test.ourHtlcs,
FeePerKw: feePerKw, Remote: test.theirHtlcs,
},
FeePerKw: feePerKw,
} }
var ( var (
@@ -8996,11 +8998,12 @@ func TestEvaluateView(t *testing.T) {
} }
checkExpectedHtlcs( checkExpectedHtlcs(
t, result.OurUpdates, test.ourExpectedHtlcs, t, result.Updates.Local, test.ourExpectedHtlcs,
) )
checkExpectedHtlcs( checkExpectedHtlcs(
t, result.TheirUpdates, test.theirExpectedHtlcs, t, result.Updates.Remote,
test.theirExpectedHtlcs,
) )
if lc.channelState.TotalMSatSent != test.expectSent { if lc.channelState.TotalMSatSent != test.expectSent {
+4 -4
View File
@@ -702,7 +702,7 @@ func (cb *CommitmentBuilder) createUnsignedCommitmentTx(ourBalance,
} }
numHTLCs := int64(0) numHTLCs := int64(0)
for _, htlc := range filteredHTLCView.OurUpdates { for _, htlc := range filteredHTLCView.Updates.Local {
if HtlcIsDust( if HtlcIsDust(
cb.chanState.ChanType, false, whoseCommit, feePerKw, cb.chanState.ChanType, false, whoseCommit, feePerKw,
htlc.Amount.ToSatoshis(), dustLimit, htlc.Amount.ToSatoshis(), dustLimit,
@@ -713,7 +713,7 @@ func (cb *CommitmentBuilder) createUnsignedCommitmentTx(ourBalance,
numHTLCs++ numHTLCs++
} }
for _, htlc := range filteredHTLCView.TheirUpdates { for _, htlc := range filteredHTLCView.Updates.Remote {
if HtlcIsDust( if HtlcIsDust(
cb.chanState.ChanType, true, whoseCommit, feePerKw, cb.chanState.ChanType, true, whoseCommit, feePerKw,
htlc.Amount.ToSatoshis(), dustLimit, htlc.Amount.ToSatoshis(), dustLimit,
@@ -827,7 +827,7 @@ func (cb *CommitmentBuilder) createUnsignedCommitmentTx(ourBalance,
// purposes of sorting. // purposes of sorting.
cltvs := make([]uint32, len(commitTx.TxOut)) cltvs := make([]uint32, len(commitTx.TxOut))
htlcIndexes := make([]input.HtlcIndex, len(commitTx.TxOut)) htlcIndexes := make([]input.HtlcIndex, len(commitTx.TxOut))
for _, htlc := range filteredHTLCView.OurUpdates { for _, htlc := range filteredHTLCView.Updates.Local {
if HtlcIsDust( if HtlcIsDust(
cb.chanState.ChanType, false, whoseCommit, feePerKw, cb.chanState.ChanType, false, whoseCommit, feePerKw,
htlc.Amount.ToSatoshis(), dustLimit, htlc.Amount.ToSatoshis(), dustLimit,
@@ -855,7 +855,7 @@ func (cb *CommitmentBuilder) createUnsignedCommitmentTx(ourBalance,
cltvs = append(cltvs, htlc.Timeout) //nolint cltvs = append(cltvs, htlc.Timeout) //nolint
htlcIndexes = append(htlcIndexes, htlc.HtlcIndex) //nolint htlcIndexes = append(htlcIndexes, htlc.HtlcIndex) //nolint
} }
for _, htlc := range filteredHTLCView.TheirUpdates { for _, htlc := range filteredHTLCView.Updates.Remote {
if HtlcIsDust( if HtlcIsDust(
cb.chanState.ChanType, true, whoseCommit, feePerKw, cb.chanState.ChanType, true, whoseCommit, feePerKw,
htlc.Amount.ToSatoshis(), dustLimit, htlc.Amount.ToSatoshis(), dustLimit,