• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

lightningnetwork / lnd / 13211764208

08 Feb 2025 03:08AM UTC coverage: 49.288% (-9.5%) from 58.815%
13211764208

Pull #9489

github

calvinrzachman
itest: verify switchrpc server enforces send then track

We prevent the rpc server from allowing onion dispatches for
attempt IDs which have already been tracked by rpc clients.

This helps protect the client from leaking a duplicate onion
attempt. NOTE: This is not the only method for solving this
issue! The issue could be addressed via careful client side
programming which accounts for the uncertainty and async
nature of dispatching onions to a remote process via RPC.
This would require some lnd ChannelRouter changes for how
we intend to use these RPCs though.
Pull Request #9489: multi: add BuildOnion, SendOnion, and TrackOnion RPCs

474 of 990 new or added lines in 11 files covered. (47.88%)

27321 existing lines in 435 files now uncovered.

101192 of 205306 relevant lines covered (49.29%)

1.54 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

73.3
/input/witnessgen.go
1
package input
2

3
import (
4
        "fmt"
5

6
        "github.com/btcsuite/btcd/txscript"
7
        "github.com/btcsuite/btcd/wire"
8
        "github.com/lightningnetwork/lnd/lntypes"
9
)
10

11
// WitnessGenerator represents a function that is able to generate the final
12
// witness for a particular public key script. Additionally, if required, this
13
// function will also return the sigScript for spending nested P2SH witness
14
// outputs. This function acts as an abstraction layer, hiding the details of
15
// the underlying script.
16
type WitnessGenerator func(tx *wire.MsgTx, hc *txscript.TxSigHashes,
17
        inputIndex int) (*Script, error)
18

19
// WitnessType determines how an output's witness will be generated. This
20
// interface can be implemented to be used for custom sweep scripts if the
21
// pre-defined StandardWitnessType list doesn't provide a suitable one.
22
type WitnessType interface {
23
        // String returns a human readable version of the WitnessType.
24
        String() string
25

26
        // WitnessGenerator will return a WitnessGenerator function that an
27
        // output uses to generate the witness and optionally the sigScript for
28
        // a sweep transaction.
29
        WitnessGenerator(signer Signer,
30
                descriptor *SignDescriptor) WitnessGenerator
31

32
        // SizeUpperBound returns the maximum length of the witness of this
33
        // WitnessType if it would be included in a tx. It also returns if the
34
        // output itself is a nested p2sh output, if so then we need to take
35
        // into account the extra sigScript data size.
36
        SizeUpperBound() (lntypes.WeightUnit, bool, error)
37

38
        // AddWeightEstimation adds the estimated size of the witness in bytes
39
        // to the given weight estimator.
40
        AddWeightEstimation(e *TxWeightEstimator) error
41
}
42

43
// StandardWitnessType is a numeric representation of standard pre-defined types
44
// of witness configurations.
45
type StandardWitnessType uint16
46

47
// A compile time check to ensure StandardWitnessType implements the
48
// WitnessType interface.
49
var _ WitnessType = (StandardWitnessType)(0)
50

51
// NOTE: When adding a new `StandardWitnessType`, also update the `WitnessType`
52
// protobuf enum and the `allWitnessTypes` map in the `walletrpc` package.
53
const (
54
        // CommitmentTimeLock is a witness that allows us to spend our output
55
        // on our local commitment transaction after a relative lock-time
56
        // lockout.
57
        CommitmentTimeLock StandardWitnessType = 0
58

59
        // CommitmentNoDelay is a witness that allows us to spend a settled
60
        // no-delay output immediately on a counterparty's commitment
61
        // transaction.
62
        CommitmentNoDelay StandardWitnessType = 1
63

64
        // CommitmentRevoke is a witness that allows us to sweep the settled
65
        // output of a malicious counterparty's who broadcasts a revoked
66
        // commitment transaction.
67
        CommitmentRevoke StandardWitnessType = 2
68

69
        // HtlcOfferedRevoke is a witness that allows us to sweep an HTLC which
70
        // we offered to the remote party in the case that they broadcast a
71
        // revoked commitment state.
72
        HtlcOfferedRevoke StandardWitnessType = 3
73

74
        // HtlcAcceptedRevoke is a witness that allows us to sweep an HTLC
75
        // output sent to us in the case that the remote party broadcasts a
76
        // revoked commitment state.
77
        HtlcAcceptedRevoke StandardWitnessType = 4
78

79
        // HtlcOfferedTimeoutSecondLevel is a witness that allows us to sweep
80
        // an HTLC output that we extended to a party, but was never fulfilled.
81
        // This HTLC output isn't directly on the commitment transaction, but
82
        // is the result of a confirmed second-level HTLC transaction. As a
83
        // result, we can only spend this after a CSV delay.
84
        HtlcOfferedTimeoutSecondLevel StandardWitnessType = 5
85

86
        // HtlcOfferedTimeoutSecondLevelInputConfirmed is a witness that allows
87
        // us to sweep an HTLC output that we extended to a party, but was
88
        // never fulfilled. This _is_ the HTLC output directly on our
89
        // commitment transaction, and the input to the second-level HTLC
90
        // timeout transaction. It can only be spent after CLTV expiry, and
91
        // commitment confirmation.
92
        HtlcOfferedTimeoutSecondLevelInputConfirmed StandardWitnessType = 15
93

94
        // HtlcAcceptedSuccessSecondLevel is a witness that allows us to sweep
95
        // an HTLC output that was offered to us, and for which we have a
96
        // payment preimage. This HTLC output isn't directly on our commitment
97
        // transaction, but is the result of confirmed second-level HTLC
98
        // transaction. As a result, we can only spend this after a CSV delay.
99
        HtlcAcceptedSuccessSecondLevel StandardWitnessType = 6
100

101
        // HtlcAcceptedSuccessSecondLevelInputConfirmed is a witness that
102
        // allows us to sweep an HTLC output that was offered to us, and for
103
        // which we have a payment preimage. This _is_ the HTLC output directly
104
        // on our commitment transaction, and the input to the second-level
105
        // HTLC success transaction.  It can only be spent after the commitment
106
        // has confirmed.
107
        HtlcAcceptedSuccessSecondLevelInputConfirmed StandardWitnessType = 16
108

109
        // HtlcOfferedRemoteTimeout is a witness that allows us to sweep an
110
        // HTLC that we offered to the remote party which lies in the
111
        // commitment transaction of the remote party. We can spend this output
112
        // after the absolute CLTV timeout of the HTLC as passed.
113
        HtlcOfferedRemoteTimeout StandardWitnessType = 7
114

115
        // HtlcAcceptedRemoteSuccess is a witness that allows us to sweep an
116
        // HTLC that was offered to us by the remote party. We use this witness
117
        // in the case that the remote party goes to chain, and we know the
118
        // pre-image to the HTLC. We can sweep this without any additional
119
        // timeout.
120
        HtlcAcceptedRemoteSuccess StandardWitnessType = 8
121

122
        // HtlcSecondLevelRevoke is a witness that allows us to sweep an HTLC
123
        // from the remote party's commitment transaction in the case that the
124
        // broadcast a revoked commitment, but then also immediately attempt to
125
        // go to the second level to claim the HTLC.
126
        HtlcSecondLevelRevoke StandardWitnessType = 9
127

128
        // WitnessKeyHash is a witness type that allows us to spend a regular
129
        // p2wkh output that's sent to an output which is under complete
130
        // control of the backing wallet.
131
        WitnessKeyHash StandardWitnessType = 10
132

133
        // NestedWitnessKeyHash is a witness type that allows us to sweep an
134
        // output that sends to a nested P2SH script that pays to a key solely
135
        // under our control. The witness generated needs to include the
136
        NestedWitnessKeyHash StandardWitnessType = 11
137

138
        // CommitSpendNoDelayTweakless is similar to the CommitSpendNoDelay
139
        // type, but it omits the tweak that randomizes the key we need to
140
        // spend with a channel peer supplied set of randomness.
141
        CommitSpendNoDelayTweakless StandardWitnessType = 12
142

143
        // CommitmentToRemoteConfirmed is a witness that allows us to spend our
144
        // output on the counterparty's commitment transaction after a
145
        // confirmation.
146
        CommitmentToRemoteConfirmed StandardWitnessType = 13
147

148
        // CommitmentAnchor is a witness that allows us to spend our anchor on
149
        // the commitment transaction.
150
        CommitmentAnchor StandardWitnessType = 14
151

152
        // LeaseCommitmentTimeLock is a witness that allows us to spend our
153
        // output on our local commitment transaction after a relative and
154
        // absolute lock-time lockout as part of the script enforced lease
155
        // commitment type.
156
        LeaseCommitmentTimeLock StandardWitnessType = 17
157

158
        // LeaseCommitmentToRemoteConfirmed is a witness that allows us to spend
159
        // our output on the counterparty's commitment transaction after a
160
        // confirmation and absolute locktime as part of the script enforced
161
        // lease commitment type.
162
        LeaseCommitmentToRemoteConfirmed StandardWitnessType = 18
163

164
        // LeaseHtlcOfferedTimeoutSecondLevel is a witness that allows us to
165
        // sweep an HTLC output that we extended to a party, but was never
166
        // fulfilled. This HTLC output isn't directly on the commitment
167
        // transaction, but is the result of a confirmed second-level HTLC
168
        // transaction. As a result, we can only spend this after a CSV delay
169
        // and CLTV locktime as part of the script enforced lease commitment
170
        // type.
171
        LeaseHtlcOfferedTimeoutSecondLevel StandardWitnessType = 19
172

173
        // LeaseHtlcAcceptedSuccessSecondLevel is a witness that allows us to
174
        // sweep an HTLC output that was offered to us, and for which we have a
175
        // payment preimage. This HTLC output isn't directly on our commitment
176
        // transaction, but is the result of confirmed second-level HTLC
177
        // transaction. As a result, we can only spend this after a CSV delay
178
        // and CLTV locktime as part of the script enforced lease commitment
179
        // type.
180
        LeaseHtlcAcceptedSuccessSecondLevel StandardWitnessType = 20
181

182
        // TaprootPubKeySpend is a witness type that allows us to spend a
183
        // regular p2tr output that's sent to an output which is under complete
184
        // control of the backing wallet.
185
        TaprootPubKeySpend StandardWitnessType = 21
186

187
        // TaprootLocalCommitSpend is a witness type that allows us to spend
188
        // our settled local commitment after a CSV delay when we force close
189
        // the channel.
190
        TaprootLocalCommitSpend StandardWitnessType = 22
191

192
        // TaprootRemoteCommitSpend is a witness type that allows us to spend
193
        // our settled local commitment after a CSV delay when the remote party
194
        // has force closed the channel.
195
        TaprootRemoteCommitSpend StandardWitnessType = 23
196

197
        // TaprootAnchorSweepSpend is the witness type we'll use for spending
198
        // our own anchor output.
199
        TaprootAnchorSweepSpend StandardWitnessType = 24
200

201
        // TaprootHtlcOfferedTimeoutSecondLevel is a witness that allows us to
202
        // timeout an HTLC we offered to the remote party on our commitment
203
        // transaction. We use this when we need to go on chain to time out an
204
        // HTLC.
205
        TaprootHtlcOfferedTimeoutSecondLevel StandardWitnessType = 25
206

207
        // TaprootHtlcAcceptedSuccessSecondLevel is a witness that allows us to
208
        // sweep an HTLC we accepted on our commitment transaction after we go
209
        // to the second level on chain.
210
        TaprootHtlcAcceptedSuccessSecondLevel StandardWitnessType = 26
211

212
        // TaprootHtlcSecondLevelRevoke is a witness that allows us to sweep an
213
        // HTLC on the revoked transaction of the remote party that goes to the
214
        // second level.
215
        TaprootHtlcSecondLevelRevoke StandardWitnessType = 27
216

217
        // TaprootHtlcAcceptedRevoke is a witness that allows us to sweep an
218
        // HTLC sent to us by the remote party in the event that they broadcast
219
        // a revoked state.
220
        TaprootHtlcAcceptedRevoke StandardWitnessType = 28
221

222
        // TaprootHtlcOfferedRevoke is a witness that allows us to sweep an
223
        // HTLC we offered to the remote party if they broadcast a revoked
224
        // commitment.
225
        TaprootHtlcOfferedRevoke StandardWitnessType = 29
226

227
        // TaprootHtlcOfferedRemoteTimeout is a witness that allows us to sweep
228
        // an HTLC we offered to the remote party that lies on the commitment
229
        // transaction for the remote party. We can spend this output after the
230
        // absolute CLTV timeout of the HTLC as passed.
231
        TaprootHtlcOfferedRemoteTimeout StandardWitnessType = 30
232

233
        // TaprootHtlcLocalOfferedTimeout is a witness type that allows us to
234
        // sign the second level HTLC timeout transaction when spending from an
235
        // HTLC residing on our local commitment transaction.
236
        //
237
        // This is used by the sweeper to re-sign inputs if it needs to
238
        // aggregate several second level HTLCs.
239
        TaprootHtlcLocalOfferedTimeout StandardWitnessType = 31
240

241
        // TaprootHtlcAcceptedRemoteSuccess is a witness that allows us to
242
        // sweep an HTLC that was offered to us by the remote party for a
243
        // taproot channels. We use this witness in the case that the remote
244
        // party goes to chain, and we know the pre-image to the HTLC. We can
245
        // sweep this without any additional timeout.
246
        TaprootHtlcAcceptedRemoteSuccess StandardWitnessType = 32
247

248
        // TaprootHtlcAcceptedLocalSuccess is a witness type that allows us to
249
        // sweep the HTLC offered to us on our local commitment transaction.
250
        // We'll use this when we need to go on chain to sweep the HTLC. In
251
        // this case, this is the second level HTLC success transaction.
252
        TaprootHtlcAcceptedLocalSuccess StandardWitnessType = 33
253

254
        // TaprootCommitmentRevoke is a witness that allows us to sweep the
255
        // settled output of a malicious counterparty's who broadcasts a
256
        // revoked taproot commitment transaction.
257
        TaprootCommitmentRevoke StandardWitnessType = 34
258
)
259

260
// String returns a human readable version of the target WitnessType.
261
//
262
// NOTE: This is part of the WitnessType interface.
263
func (wt StandardWitnessType) String() string {
3✔
264
        switch wt {
3✔
265
        case CommitmentTimeLock:
3✔
266
                return "CommitmentTimeLock"
3✔
267

268
        case CommitmentToRemoteConfirmed:
3✔
269
                return "CommitmentToRemoteConfirmed"
3✔
270

271
        case CommitmentAnchor:
3✔
272
                return "CommitmentAnchor"
3✔
273

274
        case CommitmentNoDelay:
3✔
275
                return "CommitmentNoDelay"
3✔
276

277
        case CommitSpendNoDelayTweakless:
3✔
278
                return "CommitmentNoDelayTweakless"
3✔
279

280
        case CommitmentRevoke:
3✔
281
                return "CommitmentRevoke"
3✔
282

283
        case HtlcOfferedRevoke:
×
284
                return "HtlcOfferedRevoke"
×
285

286
        case HtlcAcceptedRevoke:
×
287
                return "HtlcAcceptedRevoke"
×
288

289
        case HtlcOfferedTimeoutSecondLevel:
3✔
290
                return "HtlcOfferedTimeoutSecondLevel"
3✔
291

292
        case HtlcOfferedTimeoutSecondLevelInputConfirmed:
3✔
293
                return "HtlcOfferedTimeoutSecondLevelInputConfirmed"
3✔
294

295
        case HtlcAcceptedSuccessSecondLevel:
3✔
296
                return "HtlcAcceptedSuccessSecondLevel"
3✔
297

298
        case HtlcAcceptedSuccessSecondLevelInputConfirmed:
3✔
299
                return "HtlcAcceptedSuccessSecondLevelInputConfirmed"
3✔
300

301
        case HtlcOfferedRemoteTimeout:
3✔
302
                return "HtlcOfferedRemoteTimeout"
3✔
303

304
        case HtlcAcceptedRemoteSuccess:
3✔
305
                return "HtlcAcceptedRemoteSuccess"
3✔
306

307
        case HtlcSecondLevelRevoke:
×
308
                return "HtlcSecondLevelRevoke"
×
309

310
        case WitnessKeyHash:
3✔
311
                return "WitnessKeyHash"
3✔
312

313
        case NestedWitnessKeyHash:
3✔
314
                return "NestedWitnessKeyHash"
3✔
315

316
        case LeaseCommitmentTimeLock:
3✔
317
                return "LeaseCommitmentTimeLock"
3✔
318

319
        case LeaseCommitmentToRemoteConfirmed:
3✔
320
                return "LeaseCommitmentToRemoteConfirmed"
3✔
321

322
        case LeaseHtlcOfferedTimeoutSecondLevel:
3✔
323
                return "LeaseHtlcOfferedTimeoutSecondLevel"
3✔
324

325
        case LeaseHtlcAcceptedSuccessSecondLevel:
3✔
326
                return "LeaseHtlcAcceptedSuccessSecondLevel"
3✔
327

328
        case TaprootPubKeySpend:
3✔
329
                return "TaprootPubKeySpend"
3✔
330

331
        case TaprootLocalCommitSpend:
3✔
332
                return "TaprootLocalCommitSpend"
3✔
333

334
        case TaprootRemoteCommitSpend:
3✔
335
                return "TaprootRemoteCommitSpend"
3✔
336

337
        case TaprootAnchorSweepSpend:
3✔
338
                return "TaprootAnchorSweepSpend"
3✔
339

340
        case TaprootHtlcOfferedTimeoutSecondLevel:
3✔
341
                return "TaprootHtlcOfferedTimeoutSecondLevel"
3✔
342

343
        case TaprootHtlcAcceptedSuccessSecondLevel:
3✔
344
                return "TaprootHtlcAcceptedSuccessSecondLevel"
3✔
345

346
        case TaprootHtlcSecondLevelRevoke:
×
347
                return "TaprootHtlcSecondLevelRevoke"
×
348

349
        case TaprootHtlcAcceptedRevoke:
3✔
350
                return "TaprootHtlcAcceptedRevoke"
3✔
351

352
        case TaprootHtlcOfferedRevoke:
3✔
353
                return "TaprootHtlcOfferedRevoke"
3✔
354

355
        case TaprootHtlcOfferedRemoteTimeout:
3✔
356
                return "TaprootHtlcOfferedRemoteTimeout"
3✔
357

358
        case TaprootHtlcLocalOfferedTimeout:
3✔
359
                return "TaprootHtlcLocalOfferedTimeout"
3✔
360

361
        case TaprootHtlcAcceptedRemoteSuccess:
3✔
362
                return "TaprootHtlcAcceptedRemoteSuccess"
3✔
363

364
        case TaprootHtlcAcceptedLocalSuccess:
3✔
365
                return "TaprootHtlcAcceptedLocalSuccess"
3✔
366

367
        case TaprootCommitmentRevoke:
3✔
368
                return "TaprootCommitmentRevoke"
3✔
369

370
        default:
×
371
                return fmt.Sprintf("Unknown WitnessType: %v", uint32(wt))
×
372
        }
373
}
374

375
// WitnessGenerator will return a WitnessGenerator function that an output uses
376
// to generate the witness and optionally the sigScript for a sweep
377
// transaction. The sigScript will be generated if the witness type warrants
378
// one for spending, such as the NestedWitnessKeyHash witness type.
379
//
380
// NOTE: This is part of the WitnessType interface.
381
func (wt StandardWitnessType) WitnessGenerator(signer Signer,
382
        descriptor *SignDescriptor) WitnessGenerator {
3✔
383

3✔
384
        return func(tx *wire.MsgTx, hc *txscript.TxSigHashes,
3✔
385
                inputIndex int) (*Script, error) {
6✔
386

3✔
387
                // TODO(roasbeef): copy the desc?
3✔
388
                desc := descriptor
3✔
389
                desc.SigHashes = hc
3✔
390
                desc.InputIndex = inputIndex
3✔
391

3✔
392
                switch wt {
3✔
393
                case CommitmentTimeLock, LeaseCommitmentTimeLock:
3✔
394
                        witness, err := CommitSpendTimeout(signer, desc, tx)
3✔
395
                        if err != nil {
3✔
396
                                return nil, err
×
397
                        }
×
398

399
                        return &Script{
3✔
400
                                Witness: witness,
3✔
401
                        }, nil
3✔
402

403
                case CommitmentToRemoteConfirmed, LeaseCommitmentToRemoteConfirmed:
3✔
404
                        witness, err := CommitSpendToRemoteConfirmed(
3✔
405
                                signer, desc, tx,
3✔
406
                        )
3✔
407
                        if err != nil {
3✔
408
                                return nil, err
×
409
                        }
×
410

411
                        return &Script{
3✔
412
                                Witness: witness,
3✔
413
                        }, nil
3✔
414

415
                case CommitmentAnchor:
3✔
416
                        witness, err := CommitSpendAnchor(signer, desc, tx)
3✔
417
                        if err != nil {
3✔
418
                                return nil, err
×
419
                        }
×
420

421
                        return &Script{
3✔
422
                                Witness: witness,
3✔
423
                        }, nil
3✔
424

425
                case CommitmentNoDelay:
3✔
426
                        witness, err := CommitSpendNoDelay(signer, desc, tx, false)
3✔
427
                        if err != nil {
3✔
428
                                return nil, err
×
429
                        }
×
430

431
                        return &Script{
3✔
432
                                Witness: witness,
3✔
433
                        }, nil
3✔
434

435
                case CommitSpendNoDelayTweakless:
3✔
436
                        witness, err := CommitSpendNoDelay(signer, desc, tx, true)
3✔
437
                        if err != nil {
3✔
438
                                return nil, err
×
439
                        }
×
440

441
                        return &Script{
3✔
442
                                Witness: witness,
3✔
443
                        }, nil
3✔
444

445
                case CommitmentRevoke:
3✔
446
                        witness, err := CommitSpendRevoke(signer, desc, tx)
3✔
447
                        if err != nil {
3✔
448
                                return nil, err
×
449
                        }
×
450

451
                        return &Script{
3✔
452
                                Witness: witness,
3✔
453
                        }, nil
3✔
454

UNCOV
455
                case HtlcOfferedRevoke:
×
UNCOV
456
                        witness, err := ReceiverHtlcSpendRevoke(signer, desc, tx)
×
UNCOV
457
                        if err != nil {
×
458
                                return nil, err
×
459
                        }
×
460

UNCOV
461
                        return &Script{
×
UNCOV
462
                                Witness: witness,
×
UNCOV
463
                        }, nil
×
464

UNCOV
465
                case HtlcAcceptedRevoke:
×
UNCOV
466
                        witness, err := SenderHtlcSpendRevoke(signer, desc, tx)
×
UNCOV
467
                        if err != nil {
×
468
                                return nil, err
×
469
                        }
×
470

UNCOV
471
                        return &Script{
×
UNCOV
472
                                Witness: witness,
×
UNCOV
473
                        }, nil
×
474

475
                case HtlcOfferedTimeoutSecondLevel,
476
                        LeaseHtlcOfferedTimeoutSecondLevel,
477
                        HtlcAcceptedSuccessSecondLevel,
478
                        LeaseHtlcAcceptedSuccessSecondLevel:
3✔
479

3✔
480
                        witness, err := HtlcSecondLevelSpend(signer, desc, tx)
3✔
481
                        if err != nil {
3✔
482
                                return nil, err
×
483
                        }
×
484

485
                        return &Script{
3✔
486
                                Witness: witness,
3✔
487
                        }, nil
3✔
488

489
                case HtlcOfferedRemoteTimeout:
3✔
490
                        // We pass in a value of -1 for the timeout, as we
3✔
491
                        // expect the caller to have already set the lock time
3✔
492
                        // value.
3✔
493
                        witness, err := ReceiverHtlcSpendTimeout(signer, desc, tx, -1)
3✔
494
                        if err != nil {
3✔
495
                                return nil, err
×
496
                        }
×
497

498
                        return &Script{
3✔
499
                                Witness: witness,
3✔
500
                        }, nil
3✔
501

UNCOV
502
                case HtlcSecondLevelRevoke:
×
UNCOV
503
                        witness, err := HtlcSpendRevoke(signer, desc, tx)
×
UNCOV
504
                        if err != nil {
×
505
                                return nil, err
×
506
                        }
×
507

UNCOV
508
                        return &Script{
×
UNCOV
509
                                Witness: witness,
×
UNCOV
510
                        }, nil
×
511

512
                case WitnessKeyHash:
3✔
513
                        fallthrough
3✔
514
                case TaprootPubKeySpend:
3✔
515
                        fallthrough
3✔
516
                case NestedWitnessKeyHash:
3✔
517
                        return signer.ComputeInputScript(tx, desc)
3✔
518

519
                case TaprootLocalCommitSpend:
3✔
520
                        // Ensure that the sign desc has the proper sign method
3✔
521
                        // set, and a valid prev output fetcher.
3✔
522
                        desc.SignMethod = TaprootScriptSpendSignMethod
3✔
523

3✔
524
                        // The control block bytes must be set at this point.
3✔
525
                        if desc.ControlBlock == nil {
3✔
526
                                return nil, fmt.Errorf("control block must " +
×
527
                                        "be set for taproot spend")
×
528
                        }
×
529

530
                        witness, err := TaprootCommitSpendSuccess(
3✔
531
                                signer, desc, tx, nil,
3✔
532
                        )
3✔
533
                        if err != nil {
3✔
534
                                return nil, err
×
535
                        }
×
536

537
                        return &Script{
3✔
538
                                Witness: witness,
3✔
539
                        }, nil
3✔
540

541
                case TaprootRemoteCommitSpend:
3✔
542
                        // Ensure that the sign desc has the proper sign method
3✔
543
                        // set, and a valid prev output fetcher.
3✔
544
                        desc.SignMethod = TaprootScriptSpendSignMethod
3✔
545

3✔
546
                        // The control block bytes must be set at this point.
3✔
547
                        if desc.ControlBlock == nil {
3✔
548
                                return nil, fmt.Errorf("control block must " +
×
549
                                        "be set for taproot spend")
×
550
                        }
×
551

552
                        witness, err := TaprootCommitRemoteSpend(
3✔
553
                                signer, desc, tx, nil,
3✔
554
                        )
3✔
555
                        if err != nil {
3✔
556
                                return nil, err
×
557
                        }
×
558

559
                        return &Script{
3✔
560
                                Witness: witness,
3✔
561
                        }, nil
3✔
562

563
                case TaprootAnchorSweepSpend:
3✔
564
                        // Ensure that the sign desc has the proper sign method
3✔
565
                        // set, and a valid prev output fetcher.
3✔
566
                        desc.SignMethod = TaprootKeySpendSignMethod
3✔
567

3✔
568
                        // The tap tweak must be set at this point.
3✔
569
                        if desc.TapTweak == nil {
3✔
570
                                return nil, fmt.Errorf("tap tweak must be " +
×
571
                                        "set for keyspend")
×
572
                        }
×
573

574
                        witness, err := TaprootAnchorSpend(
3✔
575
                                signer, desc, tx,
3✔
576
                        )
3✔
577
                        if err != nil {
3✔
578
                                return nil, err
×
579
                        }
×
580

581
                        return &Script{
3✔
582
                                Witness: witness,
3✔
583
                        }, nil
3✔
584

585
                case TaprootHtlcOfferedTimeoutSecondLevel,
586
                        TaprootHtlcAcceptedSuccessSecondLevel:
3✔
587
                        // Ensure that the sign desc has the proper sign method
3✔
588
                        // set, and a valid prev output fetcher.
3✔
589
                        desc.SignMethod = TaprootScriptSpendSignMethod
3✔
590

3✔
591
                        // The control block bytes must be set at this point.
3✔
592
                        if desc.ControlBlock == nil {
3✔
593
                                return nil, fmt.Errorf("control block must " +
×
594
                                        "be set for taproot spend")
×
595
                        }
×
596

597
                        witness, err := TaprootHtlcSpendSuccess(
3✔
598
                                signer, desc, tx, nil, nil,
3✔
599
                        )
3✔
600
                        if err != nil {
3✔
601
                                return nil, err
×
602
                        }
×
603

604
                        return &Script{
3✔
605
                                Witness: witness,
3✔
606
                        }, nil
3✔
607

608
                case TaprootHtlcSecondLevelRevoke:
×
609
                        // Ensure that the sign desc has the proper sign method
×
610
                        // set, and a valid prev output fetcher.
×
611
                        desc.SignMethod = TaprootKeySpendSignMethod
×
612

×
613
                        // The tap tweak must be set at this point.
×
614
                        if desc.TapTweak == nil {
×
615
                                return nil, fmt.Errorf("tap tweak must be " +
×
616
                                        "set for keyspend")
×
617
                        }
×
618

619
                        witness, err := TaprootHtlcSpendRevoke(
×
620
                                signer, desc, tx,
×
621
                        )
×
622
                        if err != nil {
×
623
                                return nil, err
×
624
                        }
×
625

626
                        return &Script{
×
627
                                Witness: witness,
×
628
                        }, nil
×
629

630
                case TaprootHtlcOfferedRevoke:
3✔
631
                        // Ensure that the sign desc has the proper sign method
3✔
632
                        // set, and a valid prev output fetcher.
3✔
633
                        desc.SignMethod = TaprootKeySpendSignMethod
3✔
634

3✔
635
                        // The tap tweak must be set at this point.
3✔
636
                        if desc.TapTweak == nil {
3✔
637
                                return nil, fmt.Errorf("tap tweak must be " +
×
638
                                        "set for keyspend")
×
639
                        }
×
640

641
                        witness, err := SenderHTLCScriptTaprootRevoke(
3✔
642
                                signer, desc, tx,
3✔
643
                        )
3✔
644
                        if err != nil {
3✔
645
                                return nil, err
×
646
                        }
×
647

648
                        return &Script{
3✔
649
                                Witness: witness,
3✔
650
                        }, nil
3✔
651

652
                case TaprootHtlcAcceptedRevoke:
3✔
653
                        // Ensure that the sign desc has the proper sign method
3✔
654
                        // set, and a valid prev output fetcher.
3✔
655
                        desc.SignMethod = TaprootKeySpendSignMethod
3✔
656

3✔
657
                        // The tap tweak must be set at this point.
3✔
658
                        if desc.TapTweak == nil {
3✔
659
                                return nil, fmt.Errorf("tap tweak must be " +
×
660
                                        "set for keyspend")
×
661
                        }
×
662

663
                        witness, err := ReceiverHTLCScriptTaprootRevoke(
3✔
664
                                signer, desc, tx,
3✔
665
                        )
3✔
666
                        if err != nil {
3✔
667
                                return nil, err
×
668
                        }
×
669

670
                        return &Script{
3✔
671
                                Witness: witness,
3✔
672
                        }, nil
3✔
673

674
                case TaprootHtlcOfferedRemoteTimeout:
3✔
675
                        // Ensure that the sign desc has the proper sign method
3✔
676
                        // set, and a valid prev output fetcher.
3✔
677
                        desc.SignMethod = TaprootScriptSpendSignMethod
3✔
678

3✔
679
                        // The control block bytes must be set at this point.
3✔
680
                        if desc.ControlBlock == nil {
3✔
681
                                return nil, fmt.Errorf("control block " +
×
682
                                        "must be set for taproot spend")
×
683
                        }
×
684

685
                        witness, err := ReceiverHTLCScriptTaprootTimeout(
3✔
686
                                signer, desc, tx, -1, nil, nil,
3✔
687
                        )
3✔
688
                        if err != nil {
3✔
689
                                return nil, err
×
690
                        }
×
691

692
                        return &Script{
3✔
693
                                Witness: witness,
3✔
694
                        }, nil
3✔
695

696
                case TaprootCommitmentRevoke:
3✔
697
                        // Ensure that the sign desc has the proper sign method
3✔
698
                        // set, and a valid prev output fetcher.
3✔
699
                        desc.SignMethod = TaprootScriptSpendSignMethod
3✔
700

3✔
701
                        // The control block bytes must be set at this point.
3✔
702
                        if desc.ControlBlock == nil {
3✔
703
                                return nil, fmt.Errorf("control block " +
×
704
                                        "must be set for taproot spend")
×
705
                        }
×
706

707
                        witness, err := TaprootCommitSpendRevoke(
3✔
708
                                signer, desc, tx, nil,
3✔
709
                        )
3✔
710
                        if err != nil {
3✔
711
                                return nil, err
×
712
                        }
×
713

714
                        return &Script{
3✔
715
                                Witness: witness,
3✔
716
                        }, nil
3✔
717

718
                default:
×
719
                        return nil, fmt.Errorf("unknown witness type: %v", wt)
×
720
                }
721
        }
722
}
723

724
// SizeUpperBound returns the maximum length of the witness of this witness
725
// type if it would be included in a tx. We also return if the output itself is
726
// a nested p2sh output, if so then we need to take into account the extra
727
// sigScript data size.
728
//
729
// NOTE: This is part of the WitnessType interface.
730
func (wt StandardWitnessType) SizeUpperBound() (lntypes.WeightUnit,
731
        bool, error) {
3✔
732

3✔
733
        switch wt {
3✔
734
        // Outputs on a remote commitment transaction that pay directly to us.
735
        case CommitSpendNoDelayTweakless:
3✔
736
                fallthrough
3✔
737
        case WitnessKeyHash:
3✔
738
                fallthrough
3✔
739
        case CommitmentNoDelay:
3✔
740
                return P2WKHWitnessSize, false, nil
3✔
741

742
        // Outputs on a past commitment transaction that pay directly
743
        // to us.
744
        case CommitmentTimeLock:
3✔
745
                return ToLocalTimeoutWitnessSize, false, nil
3✔
746
        case LeaseCommitmentTimeLock:
3✔
747
                size := ToLocalTimeoutWitnessSize +
3✔
748
                        LeaseWitnessScriptSizeOverhead
3✔
749

3✔
750
                return lntypes.WeightUnit(size), false, nil
3✔
751

752
        // 1 CSV time locked output to us on remote commitment.
753
        case CommitmentToRemoteConfirmed:
3✔
754
                return ToRemoteConfirmedWitnessSize, false, nil
3✔
755
        case LeaseCommitmentToRemoteConfirmed:
3✔
756
                size := ToRemoteConfirmedWitnessSize +
3✔
757
                        LeaseWitnessScriptSizeOverhead
3✔
758

3✔
759
                return lntypes.WeightUnit(size), false, nil
3✔
760

761
        // Anchor output on the commitment transaction.
762
        case CommitmentAnchor:
3✔
763
                return AnchorWitnessSize, false, nil
3✔
764

765
        // Outgoing second layer HTLC's that have confirmed within the
766
        // chain, and the output they produced is now mature enough to
767
        // sweep.
768
        case HtlcOfferedTimeoutSecondLevel:
3✔
769
                return ToLocalTimeoutWitnessSize, false, nil
3✔
770
        case LeaseHtlcOfferedTimeoutSecondLevel:
3✔
771
                size := ToLocalTimeoutWitnessSize +
3✔
772
                        LeaseWitnessScriptSizeOverhead
3✔
773

3✔
774
                return lntypes.WeightUnit(size), false, nil
3✔
775

776
        // Input to the outgoing HTLC second layer timeout transaction.
777
        case HtlcOfferedTimeoutSecondLevelInputConfirmed:
3✔
778
                return OfferedHtlcTimeoutWitnessSizeConfirmed, false, nil
3✔
779

780
        // Incoming second layer HTLC's that have confirmed within the
781
        // chain, and the output they produced is now mature enough to
782
        // sweep.
783
        case HtlcAcceptedSuccessSecondLevel:
3✔
784
                return ToLocalTimeoutWitnessSize, false, nil
3✔
785
        case LeaseHtlcAcceptedSuccessSecondLevel:
3✔
786
                size := ToLocalTimeoutWitnessSize +
3✔
787
                        LeaseWitnessScriptSizeOverhead
3✔
788

3✔
789
                return lntypes.WeightUnit(size), false, nil
3✔
790

791
        // Input to the incoming second-layer HTLC success transaction.
792
        case HtlcAcceptedSuccessSecondLevelInputConfirmed:
3✔
793
                return AcceptedHtlcSuccessWitnessSizeConfirmed, false, nil
3✔
794

795
        // An HTLC on the commitment transaction of the remote party,
796
        // that has had its absolute timelock expire.
797
        case HtlcOfferedRemoteTimeout:
3✔
798
                return AcceptedHtlcTimeoutWitnessSize, false, nil
3✔
799

800
        // An HTLC on the commitment transaction of the remote party,
801
        // that can be swept with the preimage.
802
        case HtlcAcceptedRemoteSuccess:
3✔
803
                return OfferedHtlcSuccessWitnessSize, false, nil
3✔
804

805
        // A nested P2SH input that has a p2wkh witness script. We'll mark this
806
        // as nested P2SH so the caller can estimate the weight properly
807
        // including the sigScript.
808
        case NestedWitnessKeyHash:
3✔
809
                return P2WKHWitnessSize, true, nil
3✔
810

811
        // The revocation output on a revoked commitment transaction.
812
        case CommitmentRevoke:
3✔
813
                return ToLocalPenaltyWitnessSize, false, nil
3✔
814

815
        // The revocation output on a revoked HTLC that we offered to the remote
816
        // party.
UNCOV
817
        case HtlcOfferedRevoke:
×
UNCOV
818
                return OfferedHtlcPenaltyWitnessSize, false, nil
×
819

820
        // The revocation output on a revoked HTLC that was sent to us.
UNCOV
821
        case HtlcAcceptedRevoke:
×
UNCOV
822
                return AcceptedHtlcPenaltyWitnessSize, false, nil
×
823

824
        // The revocation output of a second level output of an HTLC.
UNCOV
825
        case HtlcSecondLevelRevoke:
×
UNCOV
826
                return ToLocalPenaltyWitnessSize, false, nil
×
827

828
        case TaprootPubKeySpend:
3✔
829
                return TaprootKeyPathCustomSighashWitnessSize, false, nil
3✔
830

831
        // Sweeping a self output after a delay for taproot channels.
832
        case TaprootLocalCommitSpend:
3✔
833
                return TaprootToLocalWitnessSize, false, nil
3✔
834

835
        // Sweeping a self output after the remote party fro ce closes. Must
836
        // wait 1 CSV.
837
        case TaprootRemoteCommitSpend:
3✔
838
                return TaprootToRemoteWitnessSize, false, nil
3✔
839

840
        // Sweeping our anchor output with a key spend witness.
841
        case TaprootAnchorSweepSpend:
3✔
842
                return TaprootAnchorWitnessSize, false, nil
3✔
843

844
        case TaprootHtlcOfferedTimeoutSecondLevel,
845
                TaprootHtlcAcceptedSuccessSecondLevel:
3✔
846

3✔
847
                return TaprootSecondLevelHtlcWitnessSize, false, nil
3✔
848

849
        case TaprootHtlcSecondLevelRevoke:
×
850
                return TaprootSecondLevelRevokeWitnessSize, false, nil
×
851

852
        case TaprootHtlcAcceptedRevoke:
3✔
853
                return TaprootAcceptedRevokeWitnessSize, false, nil
3✔
854

855
        case TaprootHtlcOfferedRevoke:
3✔
856
                return TaprootOfferedRevokeWitnessSize, false, nil
3✔
857

858
        case TaprootHtlcOfferedRemoteTimeout:
3✔
859
                return TaprootHtlcOfferedRemoteTimeoutWitnessSize, false, nil
3✔
860

861
        case TaprootHtlcLocalOfferedTimeout:
3✔
862
                return TaprootOfferedLocalTimeoutWitnessSize, false, nil
3✔
863

864
        case TaprootHtlcAcceptedRemoteSuccess:
3✔
865
                return TaprootHtlcAcceptedRemoteSuccessWitnessSize, false, nil
3✔
866

867
        case TaprootHtlcAcceptedLocalSuccess:
3✔
868
                return TaprootHtlcAcceptedLocalSuccessWitnessSize, false, nil
3✔
869

870
        case TaprootCommitmentRevoke:
3✔
871
                return TaprootToLocalRevokeWitnessSize, false, nil
3✔
872
        }
873

874
        return 0, false, fmt.Errorf("unexpected witness type: %v", wt)
×
875
}
876

877
// AddWeightEstimation adds the estimated size of the witness in bytes to the
878
// given weight estimator.
879
//
880
// NOTE: This is part of the WitnessType interface.
881
func (wt StandardWitnessType) AddWeightEstimation(e *TxWeightEstimator) error {
3✔
882
        // For fee estimation purposes, we'll now attempt to obtain an
3✔
883
        // upper bound on the weight this input will add when fully
3✔
884
        // populated.
3✔
885
        size, isNestedP2SH, err := wt.SizeUpperBound()
3✔
886
        if err != nil {
3✔
887
                return err
×
888
        }
×
889

890
        // If this is a nested P2SH input, then we'll need to factor in
891
        // the additional data push within the sigScript.
892
        if isNestedP2SH {
6✔
893
                e.AddNestedP2WSHInput(size)
3✔
894
        } else {
6✔
895
                e.AddWitnessInput(size)
3✔
896
        }
3✔
897

898
        return nil
3✔
899
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc