2018-09-21 20:49:58 +03:00
|
|
|
package sweep
|
|
|
|
|
|
|
|
import (
|
|
|
|
"github.com/btcsuite/btcd/txscript"
|
|
|
|
"github.com/btcsuite/btcd/wire"
|
|
|
|
"github.com/lightningnetwork/lnd/lnwallet"
|
|
|
|
)
|
|
|
|
|
2018-09-26 18:59:30 +03:00
|
|
|
// Input contains all data needed to construct a sweep tx input.
|
|
|
|
type Input interface {
|
2018-09-21 20:49:58 +03:00
|
|
|
// Outpoint returns the reference to the output being spent, used to
|
|
|
|
// construct the corresponding transaction input.
|
|
|
|
OutPoint() *wire.OutPoint
|
|
|
|
|
|
|
|
// WitnessType returns an enum specifying the type of witness that must
|
|
|
|
// be generated in order to spend this output.
|
|
|
|
WitnessType() lnwallet.WitnessType
|
|
|
|
|
2018-10-18 02:27:11 +03:00
|
|
|
// SignDesc returns a reference to a spendable output's sign
|
|
|
|
// descriptor, which is used during signing to compute a valid witness
|
|
|
|
// that spends this output.
|
2018-09-21 20:49:58 +03:00
|
|
|
SignDesc() *lnwallet.SignDescriptor
|
|
|
|
|
|
|
|
// BuildWitness returns a valid witness allowing this output to be
|
|
|
|
// spent, the witness should be attached to the transaction at the
|
|
|
|
// location determined by the given `txinIdx`.
|
|
|
|
BuildWitness(signer lnwallet.Signer, txn *wire.MsgTx,
|
|
|
|
hashCache *txscript.TxSigHashes,
|
|
|
|
txinIdx int) ([][]byte, error)
|
2018-09-26 18:59:30 +03:00
|
|
|
|
|
|
|
// BlocksToMaturity returns the relative timelock, as a number of
|
|
|
|
// blocks, that must be built on top of the confirmation height before
|
|
|
|
// the output can be spent. For non-CSV locked inputs this is always
|
|
|
|
// zero.
|
|
|
|
BlocksToMaturity() uint32
|
2018-09-21 20:49:58 +03:00
|
|
|
}
|
|
|
|
|
2018-09-26 21:00:10 +03:00
|
|
|
type inputKit struct {
|
2018-09-26 18:59:30 +03:00
|
|
|
outpoint wire.OutPoint
|
|
|
|
witnessType lnwallet.WitnessType
|
|
|
|
signDesc lnwallet.SignDescriptor
|
|
|
|
}
|
2018-09-21 20:49:58 +03:00
|
|
|
|
2018-10-18 02:27:11 +03:00
|
|
|
// OutPoint returns the breached output's identifier that is to be included as
|
|
|
|
// a transaction input.
|
2018-09-26 21:00:10 +03:00
|
|
|
func (i *inputKit) OutPoint() *wire.OutPoint {
|
|
|
|
return &i.outpoint
|
2018-09-26 18:59:30 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
// WitnessType returns the type of witness that must be generated to spend the
|
|
|
|
// breached output.
|
2018-09-26 21:00:10 +03:00
|
|
|
func (i *inputKit) WitnessType() lnwallet.WitnessType {
|
|
|
|
return i.witnessType
|
2018-09-26 18:59:30 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
// SignDesc returns the breached output's SignDescriptor, which is used during
|
|
|
|
// signing to compute the witness.
|
2018-09-26 21:00:10 +03:00
|
|
|
func (i *inputKit) SignDesc() *lnwallet.SignDescriptor {
|
|
|
|
return &i.signDesc
|
|
|
|
}
|
|
|
|
|
|
|
|
// BaseInput contains all the information needed to sweep a basic output
|
|
|
|
// (CSV/CLTV/no time lock)
|
|
|
|
type BaseInput struct {
|
|
|
|
inputKit
|
|
|
|
}
|
|
|
|
|
|
|
|
// MakeBaseInput assembles a new BaseInput that can be used to construct a
|
|
|
|
// sweep transaction.
|
2018-10-18 02:27:11 +03:00
|
|
|
func MakeBaseInput(outpoint *wire.OutPoint, witnessType lnwallet.WitnessType,
|
2018-09-26 21:00:10 +03:00
|
|
|
signDescriptor *lnwallet.SignDescriptor) BaseInput {
|
|
|
|
|
|
|
|
return BaseInput{
|
|
|
|
inputKit{
|
|
|
|
outpoint: *outpoint,
|
|
|
|
witnessType: witnessType,
|
|
|
|
signDesc: *signDescriptor,
|
|
|
|
},
|
|
|
|
}
|
2018-09-26 18:59:30 +03:00
|
|
|
}
|
2018-09-21 20:49:58 +03:00
|
|
|
|
2018-09-26 18:59:30 +03:00
|
|
|
// BuildWitness computes a valid witness that allows us to spend from the
|
|
|
|
// breached output. It does so by generating the witness generation function,
|
2018-10-18 02:27:11 +03:00
|
|
|
// which is parameterized primarily by the witness type and sign descriptor.
|
|
|
|
// The method then returns the witness computed by invoking this function.
|
2018-09-26 18:59:30 +03:00
|
|
|
func (bi *BaseInput) BuildWitness(signer lnwallet.Signer, txn *wire.MsgTx,
|
|
|
|
hashCache *txscript.TxSigHashes, txinIdx int) ([][]byte, error) {
|
|
|
|
|
|
|
|
witnessFunc := bi.witnessType.GenWitnessFunc(
|
|
|
|
signer, bi.SignDesc(),
|
|
|
|
)
|
|
|
|
|
|
|
|
return witnessFunc(txn, hashCache, txinIdx)
|
2018-09-21 20:49:58 +03:00
|
|
|
}
|
2018-09-26 18:59:30 +03:00
|
|
|
|
|
|
|
// BlocksToMaturity returns the relative timelock, as a number of blocks, that
|
|
|
|
// must be built on top of the confirmation height before the output can be
|
|
|
|
// spent. For non-CSV locked inputs this is always zero.
|
|
|
|
func (bi *BaseInput) BlocksToMaturity() uint32 {
|
|
|
|
return 0
|
|
|
|
}
|
|
|
|
|
2018-09-26 21:00:10 +03:00
|
|
|
// HtlcSucceedInput constitutes a sweep input that needs a pre-image. The input
|
2018-10-18 02:27:11 +03:00
|
|
|
// is expected to reside on the commitment tx of the remote party and should
|
|
|
|
// not be a second level tx output.
|
2018-09-26 21:00:10 +03:00
|
|
|
type HtlcSucceedInput struct {
|
|
|
|
inputKit
|
|
|
|
|
|
|
|
preimage []byte
|
|
|
|
}
|
|
|
|
|
|
|
|
// MakeHtlcSucceedInput assembles a new redeem input that can be used to
|
|
|
|
// construct a sweep transaction.
|
|
|
|
func MakeHtlcSucceedInput(outpoint *wire.OutPoint,
|
|
|
|
signDescriptor *lnwallet.SignDescriptor,
|
|
|
|
preimage []byte) HtlcSucceedInput {
|
|
|
|
|
|
|
|
return HtlcSucceedInput{
|
|
|
|
inputKit: inputKit{
|
|
|
|
outpoint: *outpoint,
|
|
|
|
witnessType: lnwallet.HtlcAcceptedRemoteSuccess,
|
|
|
|
signDesc: *signDescriptor,
|
|
|
|
},
|
|
|
|
preimage: preimage,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// BuildWitness computes a valid witness that allows us to spend from the
|
2018-10-18 02:27:11 +03:00
|
|
|
// breached output. For HtlcSpendInput it will need to make the preimage part
|
|
|
|
// of the witness.
|
2018-09-26 21:00:10 +03:00
|
|
|
func (h *HtlcSucceedInput) BuildWitness(signer lnwallet.Signer, txn *wire.MsgTx,
|
|
|
|
hashCache *txscript.TxSigHashes, txinIdx int) ([][]byte, error) {
|
|
|
|
|
|
|
|
desc := h.signDesc
|
|
|
|
desc.SigHashes = hashCache
|
|
|
|
desc.InputIndex = txinIdx
|
|
|
|
|
|
|
|
return lnwallet.SenderHtlcSpendRedeem(
|
|
|
|
signer, &desc, txn,
|
|
|
|
h.preimage,
|
|
|
|
)
|
|
|
|
}
|
|
|
|
|
|
|
|
// BlocksToMaturity returns the relative timelock, as a number of blocks, that
|
|
|
|
// must be built on top of the confirmation height before the output can be
|
|
|
|
// spent.
|
|
|
|
func (h *HtlcSucceedInput) BlocksToMaturity() uint32 {
|
|
|
|
return 0
|
|
|
|
}
|
|
|
|
|
2018-10-18 02:27:11 +03:00
|
|
|
// Compile-time constraints to ensure each input struct implement the Input
|
|
|
|
// interface.
|
2018-09-26 18:59:30 +03:00
|
|
|
var _ Input = (*BaseInput)(nil)
|
2018-09-26 21:00:10 +03:00
|
|
|
var _ Input = (*HtlcSucceedInput)(nil)
|