Merge pull request #3665 from joostjager/resolver-constructors
cnct: add resolver constructors
This commit is contained in:
commit
76c2b2cea2
@ -440,7 +440,7 @@ func (b *boltArbitratorLog) CommitState(s ArbitratorState) error {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (b *boltArbitratorLog) FetchUnresolvedContracts() ([]ContractResolver, error) {
|
||||
resKit := ResolverKit{
|
||||
resolverCfg := ResolverConfig{
|
||||
ChannelArbitratorConfig: b.cfg,
|
||||
Checkpoint: b.checkpointContract,
|
||||
}
|
||||
@ -469,56 +469,38 @@ func (b *boltArbitratorLog) FetchUnresolvedContracts() ([]ContractResolver, erro
|
||||
|
||||
switch resType {
|
||||
case resolverTimeout:
|
||||
timeoutRes := &htlcTimeoutResolver{}
|
||||
if err := timeoutRes.Decode(resReader); err != nil {
|
||||
return err
|
||||
}
|
||||
timeoutRes.AttachResolverKit(resKit)
|
||||
|
||||
res = timeoutRes
|
||||
res, err = newTimeoutResolverFromReader(
|
||||
resReader, resolverCfg,
|
||||
)
|
||||
|
||||
case resolverSuccess:
|
||||
successRes := &htlcSuccessResolver{}
|
||||
if err := successRes.Decode(resReader); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
res = successRes
|
||||
res, err = newSuccessResolverFromReader(
|
||||
resReader, resolverCfg,
|
||||
)
|
||||
|
||||
case resolverOutgoingContest:
|
||||
outContestRes := &htlcOutgoingContestResolver{
|
||||
htlcTimeoutResolver: htlcTimeoutResolver{},
|
||||
}
|
||||
if err := outContestRes.Decode(resReader); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
res = outContestRes
|
||||
res, err = newOutgoingContestResolverFromReader(
|
||||
resReader, resolverCfg,
|
||||
)
|
||||
|
||||
case resolverIncomingContest:
|
||||
inContestRes := &htlcIncomingContestResolver{
|
||||
htlcSuccessResolver: htlcSuccessResolver{},
|
||||
}
|
||||
if err := inContestRes.Decode(resReader); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
res = inContestRes
|
||||
res, err = newIncomingContestResolverFromReader(
|
||||
resReader, resolverCfg,
|
||||
)
|
||||
|
||||
case resolverUnilateralSweep:
|
||||
sweepRes := &commitSweepResolver{}
|
||||
if err := sweepRes.Decode(resReader); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
res = sweepRes
|
||||
res, err = newCommitSweepResolverFromReader(
|
||||
resReader, resolverCfg,
|
||||
)
|
||||
|
||||
default:
|
||||
return fmt.Errorf("unknown resolver type: %v", resType)
|
||||
}
|
||||
|
||||
resKit.Quit = make(chan struct{})
|
||||
res.AttachResolverKit(resKit)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
contracts = append(contracts, res)
|
||||
return nil
|
||||
})
|
||||
|
@ -1685,7 +1685,7 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
|
||||
// We'll create the resolver kit that we'll be cloning for each
|
||||
// resolver so they each can do their duty.
|
||||
resKit := ResolverKit{
|
||||
resolverCfg := ResolverConfig{
|
||||
ChannelArbitratorConfig: c.cfg,
|
||||
Checkpoint: func(res ContractResolver) error {
|
||||
return c.log.InsertUnresolvedContracts(res)
|
||||
@ -1733,14 +1733,10 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
continue
|
||||
}
|
||||
|
||||
resKit.Quit = make(chan struct{})
|
||||
resolver := &htlcSuccessResolver{
|
||||
htlcResolution: resolution,
|
||||
broadcastHeight: height,
|
||||
payHash: htlc.RHash,
|
||||
htlcAmt: htlc.Amt,
|
||||
ResolverKit: resKit,
|
||||
}
|
||||
resolver := newSuccessResolver(
|
||||
resolution, height,
|
||||
htlc.RHash, htlc.Amt, resolverCfg,
|
||||
)
|
||||
htlcResolvers = append(htlcResolvers, resolver)
|
||||
}
|
||||
|
||||
@ -1761,14 +1757,10 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
continue
|
||||
}
|
||||
|
||||
resKit.Quit = make(chan struct{})
|
||||
resolver := &htlcTimeoutResolver{
|
||||
htlcResolution: resolution,
|
||||
broadcastHeight: height,
|
||||
htlcIndex: htlc.HtlcIndex,
|
||||
htlcAmt: htlc.Amt,
|
||||
ResolverKit: resKit,
|
||||
}
|
||||
resolver := newTimeoutResolver(
|
||||
resolution, height, htlc.HtlcIndex,
|
||||
htlc.Amt, resolverCfg,
|
||||
)
|
||||
htlcResolvers = append(htlcResolvers, resolver)
|
||||
}
|
||||
|
||||
@ -1798,18 +1790,11 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
ChanID: c.cfg.ShortChanID,
|
||||
}
|
||||
|
||||
resKit.Quit = make(chan struct{})
|
||||
resolver := &htlcIncomingContestResolver{
|
||||
htlcExpiry: htlc.RefundTimeout,
|
||||
circuitKey: circuitKey,
|
||||
htlcSuccessResolver: htlcSuccessResolver{
|
||||
htlcResolution: resolution,
|
||||
broadcastHeight: height,
|
||||
payHash: htlc.RHash,
|
||||
htlcAmt: htlc.Amt,
|
||||
ResolverKit: resKit,
|
||||
},
|
||||
}
|
||||
resolver := newIncomingContestResolver(
|
||||
htlc.RefundTimeout, circuitKey,
|
||||
resolution, height, htlc.RHash,
|
||||
htlc.Amt, resolverCfg,
|
||||
)
|
||||
htlcResolvers = append(htlcResolvers, resolver)
|
||||
}
|
||||
|
||||
@ -1831,16 +1816,10 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
continue
|
||||
}
|
||||
|
||||
resKit.Quit = make(chan struct{})
|
||||
resolver := &htlcOutgoingContestResolver{
|
||||
htlcTimeoutResolver: htlcTimeoutResolver{
|
||||
htlcResolution: resolution,
|
||||
broadcastHeight: height,
|
||||
htlcIndex: htlc.HtlcIndex,
|
||||
htlcAmt: htlc.Amt,
|
||||
ResolverKit: resKit,
|
||||
},
|
||||
}
|
||||
resolver := newOutgoingContestResolver(
|
||||
resolution, height, htlc.HtlcIndex,
|
||||
htlc.Amt, resolverCfg,
|
||||
)
|
||||
htlcResolvers = append(htlcResolvers, resolver)
|
||||
}
|
||||
}
|
||||
@ -1850,14 +1829,10 @@ func (c *ChannelArbitrator) prepContractResolutions(
|
||||
// a resolver to sweep our commitment output (but only if it wasn't
|
||||
// trimmed).
|
||||
if contractResolutions.CommitResolution != nil {
|
||||
resKit.Quit = make(chan struct{})
|
||||
resolver := &commitSweepResolver{
|
||||
commitResolution: *contractResolutions.CommitResolution,
|
||||
broadcastHeight: height,
|
||||
chanPoint: c.cfg.ChanPoint,
|
||||
ResolverKit: resKit,
|
||||
}
|
||||
|
||||
resolver := newCommitSweepResolver(
|
||||
*contractResolutions.CommitResolution,
|
||||
height, c.cfg.ChanPoint, resolverCfg,
|
||||
)
|
||||
htlcResolvers = append(htlcResolvers, resolver)
|
||||
}
|
||||
|
||||
|
@ -36,7 +36,20 @@ type commitSweepResolver struct {
|
||||
// chanPoint is the channel point of the original contract.
|
||||
chanPoint wire.OutPoint
|
||||
|
||||
ResolverKit
|
||||
contractResolverKit
|
||||
}
|
||||
|
||||
// newCommitSweepResolver instantiates a new direct commit output resolver.
|
||||
func newCommitSweepResolver(res lnwallet.CommitOutputResolution,
|
||||
broadcastHeight uint32,
|
||||
chanPoint wire.OutPoint, resCfg ResolverConfig) *commitSweepResolver {
|
||||
|
||||
return &commitSweepResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
commitResolution: res,
|
||||
broadcastHeight: broadcastHeight,
|
||||
chanPoint: chanPoint,
|
||||
}
|
||||
}
|
||||
|
||||
// ResolverKey returns an identifier which should be globally unique for this
|
||||
@ -80,7 +93,7 @@ func (c *commitSweepResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
case <-c.Quit:
|
||||
case <-c.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -138,7 +151,7 @@ func (c *commitSweepResolver) Resolve() (ContractResolver, error) {
|
||||
|
||||
log.Infof("ChannelPoint(%v) commit tx is fully resolved by "+
|
||||
"sweep tx: %v", c.chanPoint, sweepResult.Tx.TxHash())
|
||||
case <-c.Quit:
|
||||
case <-c.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -180,7 +193,7 @@ func (c *commitSweepResolver) Resolve() (ContractResolver, error) {
|
||||
log.Errorf("unable to Checkpoint: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
case <-c.Quit:
|
||||
case <-c.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -206,7 +219,7 @@ func (c *commitSweepResolver) Resolve() (ContractResolver, error) {
|
||||
log.Infof("ChannelPoint(%v) commit tx is fully resolved, at height: %v",
|
||||
c.chanPoint, confInfo.BlockHeight)
|
||||
|
||||
case <-c.Quit:
|
||||
case <-c.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -221,7 +234,7 @@ func (c *commitSweepResolver) Resolve() (ContractResolver, error) {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (c *commitSweepResolver) Stop() {
|
||||
close(c.Quit)
|
||||
close(c.quit)
|
||||
}
|
||||
|
||||
// IsResolved returns true if the stored state in the resolve is fully
|
||||
@ -262,44 +275,40 @@ func (c *commitSweepResolver) Encode(w io.Writer) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the passed Reader
|
||||
// instance, returning an active ContractResolver instance.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (c *commitSweepResolver) Decode(r io.Reader) error {
|
||||
// newCommitSweepResolverFromReader attempts to decode an encoded
|
||||
// ContractResolver from the passed Reader instance, returning an active
|
||||
// ContractResolver instance.
|
||||
func newCommitSweepResolverFromReader(r io.Reader, resCfg ResolverConfig) (
|
||||
*commitSweepResolver, error) {
|
||||
|
||||
c := &commitSweepResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
}
|
||||
|
||||
if err := decodeCommitResolution(r, &c.commitResolution); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if err := binary.Read(r, endian, &c.resolved); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if err := binary.Read(r, endian, &c.broadcastHeight); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
_, err := io.ReadFull(r, c.chanPoint.Hash[:])
|
||||
if err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
err = binary.Read(r, endian, &c.chanPoint.Index)
|
||||
if err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Previously a sweep tx was deserialized at this point. Refactoring
|
||||
// removed this, but keep in mind that this data may still be present in
|
||||
// the database.
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully decoded
|
||||
// from its stored format. This struct delivers a generic tool kit that
|
||||
// resolvers need to complete their duty.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (c *commitSweepResolver) AttachResolverKit(r ResolverKit) {
|
||||
c.ResolverKit = r
|
||||
return c, nil
|
||||
}
|
||||
|
||||
// A compile time assertion to ensure commitSweepResolver meets the
|
||||
|
@ -46,16 +46,6 @@ type ContractResolver interface {
|
||||
// passed Writer.
|
||||
Encode(w io.Writer) error
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the
|
||||
// passed Reader instance, returning an active ContractResolver
|
||||
// instance.
|
||||
Decode(r io.Reader) error
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully
|
||||
// decoded from its stored format. This struct delivers a generic tool
|
||||
// kit that resolvers need to complete their duty.
|
||||
AttachResolverKit(ResolverKit)
|
||||
|
||||
// Stop signals the resolver to cancel any current resolution
|
||||
// processes, and suspend.
|
||||
Stop()
|
||||
@ -69,10 +59,9 @@ type reportingContractResolver interface {
|
||||
report() *ContractReport
|
||||
}
|
||||
|
||||
// ResolverKit is meant to be used as a mix-in struct to be embedded within a
|
||||
// given ContractResolver implementation. It contains all the items that a
|
||||
// resolver requires to carry out its duties.
|
||||
type ResolverKit struct {
|
||||
// ResolverConfig contains the externally supplied configuration items that are
|
||||
// required by a ContractResolver implementation.
|
||||
type ResolverConfig struct {
|
||||
// ChannelArbitratorConfig contains all the interfaces and closures
|
||||
// required for the resolver to interact with outside sub-systems.
|
||||
ChannelArbitratorConfig
|
||||
@ -81,8 +70,23 @@ type ResolverKit struct {
|
||||
// should write the state of the resolver to persistent storage, and
|
||||
// return a non-nil error upon success.
|
||||
Checkpoint func(ContractResolver) error
|
||||
}
|
||||
|
||||
Quit chan struct{}
|
||||
// contractResolverKit is meant to be used as a mix-in struct to be embedded within a
|
||||
// given ContractResolver implementation. It contains all the common items that
|
||||
// a resolver requires to carry out its duties.
|
||||
type contractResolverKit struct {
|
||||
ResolverConfig
|
||||
|
||||
quit chan struct{}
|
||||
}
|
||||
|
||||
// newContractResolverKit instantiates the mix-in struct.
|
||||
func newContractResolverKit(cfg ResolverConfig) *contractResolverKit {
|
||||
return &contractResolverKit{
|
||||
ResolverConfig: cfg,
|
||||
quit: make(chan struct{}),
|
||||
}
|
||||
}
|
||||
|
||||
var (
|
||||
|
@ -5,11 +5,12 @@ import (
|
||||
"errors"
|
||||
"io"
|
||||
|
||||
"github.com/btcsuite/btcutil"
|
||||
"github.com/lightningnetwork/lnd/channeldb"
|
||||
"github.com/lightningnetwork/lnd/invoices"
|
||||
|
||||
"github.com/btcsuite/btcutil"
|
||||
"github.com/lightningnetwork/lnd/lntypes"
|
||||
"github.com/lightningnetwork/lnd/lnwallet"
|
||||
"github.com/lightningnetwork/lnd/lnwire"
|
||||
)
|
||||
|
||||
// htlcIncomingContestResolver is a ContractResolver that's able to resolve an
|
||||
@ -34,6 +35,24 @@ type htlcIncomingContestResolver struct {
|
||||
htlcSuccessResolver
|
||||
}
|
||||
|
||||
// newIncomingContestResolver instantiates a new incoming htlc contest resolver.
|
||||
func newIncomingContestResolver(htlcExpiry uint32,
|
||||
circuitKey channeldb.CircuitKey, res lnwallet.IncomingHtlcResolution,
|
||||
broadcastHeight uint32, payHash lntypes.Hash,
|
||||
htlcAmt lnwire.MilliSatoshi,
|
||||
resCfg ResolverConfig) *htlcIncomingContestResolver {
|
||||
|
||||
success := newSuccessResolver(
|
||||
res, broadcastHeight, payHash, htlcAmt, resCfg,
|
||||
)
|
||||
|
||||
return &htlcIncomingContestResolver{
|
||||
htlcExpiry: htlcExpiry,
|
||||
circuitKey: circuitKey,
|
||||
htlcSuccessResolver: *success,
|
||||
}
|
||||
}
|
||||
|
||||
// Resolve attempts to resolve this contract. As we don't yet know of the
|
||||
// preimage for the contract, we'll wait for one of two things to happen:
|
||||
//
|
||||
@ -68,7 +87,7 @@ func (h *htlcIncomingContestResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
currentHeight = newBlock.Height
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -239,7 +258,7 @@ func (h *htlcIncomingContestResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, h.Checkpoint(h)
|
||||
}
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
}
|
||||
@ -271,7 +290,7 @@ func (h *htlcIncomingContestResolver) report() *ContractReport {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcIncomingContestResolver) Stop() {
|
||||
close(h.Quit)
|
||||
close(h.quit)
|
||||
}
|
||||
|
||||
// IsResolved returns true if the stored state in the resolve is fully
|
||||
@ -296,27 +315,27 @@ func (h *htlcIncomingContestResolver) Encode(w io.Writer) error {
|
||||
return h.htlcSuccessResolver.Encode(w)
|
||||
}
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the passed Reader
|
||||
// instance, returning an active ContractResolver instance.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcIncomingContestResolver) Decode(r io.Reader) error {
|
||||
// newIncomingContestResolverFromReader attempts to decode an encoded ContractResolver
|
||||
// from the passed Reader instance, returning an active ContractResolver
|
||||
// instance.
|
||||
func newIncomingContestResolverFromReader(r io.Reader, resCfg ResolverConfig) (
|
||||
*htlcIncomingContestResolver, error) {
|
||||
|
||||
h := &htlcIncomingContestResolver{}
|
||||
|
||||
// We'll first read the one field unique to this resolver.
|
||||
if err := binary.Read(r, endian, &h.htlcExpiry); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Then we'll decode our internal resolver.
|
||||
return h.htlcSuccessResolver.Decode(r)
|
||||
}
|
||||
successResolver, err := newSuccessResolverFromReader(r, resCfg)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
h.htlcSuccessResolver = *successResolver
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully decoded
|
||||
// from its stored format. This struct delivers a generic tool kit that
|
||||
// resolvers need to complete their duty.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcIncomingContestResolver) AttachResolverKit(r ResolverKit) {
|
||||
h.ResolverKit = r
|
||||
return h, nil
|
||||
}
|
||||
|
||||
// A compile time assertion to ensure htlcIncomingContestResolver meets the
|
||||
|
@ -199,17 +199,18 @@ func newIncomingResolverTestContext(t *testing.T) *incomingResolverTestContext {
|
||||
},
|
||||
}
|
||||
|
||||
cfg := ResolverConfig{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
resolver := &htlcIncomingContestResolver{
|
||||
htlcSuccessResolver: htlcSuccessResolver{
|
||||
ResolverKit: ResolverKit{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
htlcResolution: lnwallet.IncomingHtlcResolution{},
|
||||
payHash: testResHash,
|
||||
contractResolverKit: *newContractResolverKit(cfg),
|
||||
htlcResolution: lnwallet.IncomingHtlcResolution{},
|
||||
payHash: testResHash,
|
||||
},
|
||||
htlcExpiry: testHtlcExpiry,
|
||||
}
|
||||
|
@ -5,6 +5,8 @@ import (
|
||||
"io"
|
||||
|
||||
"github.com/btcsuite/btcutil"
|
||||
"github.com/lightningnetwork/lnd/lnwallet"
|
||||
"github.com/lightningnetwork/lnd/lnwire"
|
||||
)
|
||||
|
||||
// htlcOutgoingContestResolver is a ContractResolver that's able to resolve an
|
||||
@ -18,6 +20,21 @@ type htlcOutgoingContestResolver struct {
|
||||
htlcTimeoutResolver
|
||||
}
|
||||
|
||||
// newOutgoingContestResolver instantiates a new outgoing contested htlc
|
||||
// resolver.
|
||||
func newOutgoingContestResolver(res lnwallet.OutgoingHtlcResolution,
|
||||
broadcastHeight uint32, htlcIndex uint64, htlcAmt lnwire.MilliSatoshi,
|
||||
resCfg ResolverConfig) *htlcOutgoingContestResolver {
|
||||
|
||||
timeout := newTimeoutResolver(
|
||||
res, broadcastHeight, htlcIndex, htlcAmt, resCfg,
|
||||
)
|
||||
|
||||
return &htlcOutgoingContestResolver{
|
||||
htlcTimeoutResolver: *timeout,
|
||||
}
|
||||
}
|
||||
|
||||
// Resolve commences the resolution of this contract. As this contract hasn't
|
||||
// yet timed out, we'll wait for one of two things to happen
|
||||
//
|
||||
@ -130,7 +147,7 @@ func (h *htlcOutgoingContestResolver) Resolve() (ContractResolver, error) {
|
||||
// claimed.
|
||||
return h.claimCleanUp(commitSpend)
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, fmt.Errorf("resolver canceled")
|
||||
}
|
||||
}
|
||||
@ -162,7 +179,7 @@ func (h *htlcOutgoingContestResolver) report() *ContractReport {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcOutgoingContestResolver) Stop() {
|
||||
close(h.Quit)
|
||||
close(h.quit)
|
||||
}
|
||||
|
||||
// IsResolved returns true if the stored state in the resolve is fully
|
||||
@ -181,21 +198,19 @@ func (h *htlcOutgoingContestResolver) Encode(w io.Writer) error {
|
||||
return h.htlcTimeoutResolver.Encode(w)
|
||||
}
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the passed Reader
|
||||
// instance, returning an active ContractResolver instance.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcOutgoingContestResolver) Decode(r io.Reader) error {
|
||||
return h.htlcTimeoutResolver.Decode(r)
|
||||
}
|
||||
// newOutgoingContestResolverFromReader attempts to decode an encoded ContractResolver
|
||||
// from the passed Reader instance, returning an active ContractResolver
|
||||
// instance.
|
||||
func newOutgoingContestResolverFromReader(r io.Reader, resCfg ResolverConfig) (
|
||||
*htlcOutgoingContestResolver, error) {
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully decoded
|
||||
// from its stored format. This struct delivers a generic tool kit that
|
||||
// resolvers need to complete their duty.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcOutgoingContestResolver) AttachResolverKit(r ResolverKit) {
|
||||
h.ResolverKit = r
|
||||
h := &htlcOutgoingContestResolver{}
|
||||
timeoutResolver, err := newTimeoutResolverFromReader(r, resCfg)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
h.htlcTimeoutResolver = *timeoutResolver
|
||||
return h, nil
|
||||
}
|
||||
|
||||
// A compile time assertion to ensure htlcOutgoingContestResolver meets the
|
||||
|
@ -122,16 +122,18 @@ func newOutgoingResolverTestContext(t *testing.T) *outgoingResolverTestContext {
|
||||
},
|
||||
}
|
||||
|
||||
cfg := ResolverConfig{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
resolver := &htlcOutgoingContestResolver{
|
||||
htlcTimeoutResolver: htlcTimeoutResolver{
|
||||
ResolverKit: ResolverKit{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
htlcResolution: outgoingRes,
|
||||
contractResolverKit: *newContractResolverKit(cfg),
|
||||
htlcResolution: outgoingRes,
|
||||
},
|
||||
}
|
||||
|
||||
|
@ -52,7 +52,22 @@ type htlcSuccessResolver struct {
|
||||
// account any fees that may have to be paid if it goes on chain.
|
||||
htlcAmt lnwire.MilliSatoshi
|
||||
|
||||
ResolverKit
|
||||
contractResolverKit
|
||||
}
|
||||
|
||||
// newSuccessResolver instanties a new htlc success resolver.
|
||||
func newSuccessResolver(res lnwallet.IncomingHtlcResolution,
|
||||
broadcastHeight uint32, payHash lntypes.Hash,
|
||||
htlcAmt lnwire.MilliSatoshi,
|
||||
resCfg ResolverConfig) *htlcSuccessResolver {
|
||||
|
||||
return &htlcSuccessResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
htlcResolution: res,
|
||||
broadcastHeight: broadcastHeight,
|
||||
payHash: payHash,
|
||||
htlcAmt: htlcAmt,
|
||||
}
|
||||
}
|
||||
|
||||
// ResolverKey returns an identifier which should be globally unique for this
|
||||
@ -173,7 +188,7 @@ func (h *htlcSuccessResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -238,7 +253,7 @@ func (h *htlcSuccessResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -251,7 +266,7 @@ func (h *htlcSuccessResolver) Resolve() (ContractResolver, error) {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcSuccessResolver) Stop() {
|
||||
close(h.Quit)
|
||||
close(h.quit)
|
||||
}
|
||||
|
||||
// IsResolved returns true if the stored state in the resolve is fully
|
||||
@ -290,41 +305,37 @@ func (h *htlcSuccessResolver) Encode(w io.Writer) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the passed Reader
|
||||
// instance, returning an active ContractResolver instance.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcSuccessResolver) Decode(r io.Reader) error {
|
||||
// newSuccessResolverFromReader attempts to decode an encoded ContractResolver
|
||||
// from the passed Reader instance, returning an active ContractResolver
|
||||
// instance.
|
||||
func newSuccessResolverFromReader(r io.Reader, resCfg ResolverConfig) (
|
||||
*htlcSuccessResolver, error) {
|
||||
|
||||
h := &htlcSuccessResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
}
|
||||
|
||||
// First we'll decode our inner HTLC resolution.
|
||||
if err := decodeIncomingResolution(r, &h.htlcResolution); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Next, we'll read all the fields that are specified to the contract
|
||||
// resolver.
|
||||
if err := binary.Read(r, endian, &h.outputIncubating); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if err := binary.Read(r, endian, &h.resolved); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if err := binary.Read(r, endian, &h.broadcastHeight); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if _, err := io.ReadFull(r, h.payHash[:]); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully decoded
|
||||
// from its stored format. This struct delivers a generic tool kit that
|
||||
// resolvers need to complete their duty.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcSuccessResolver) AttachResolverKit(r ResolverKit) {
|
||||
h.ResolverKit = r
|
||||
return h, nil
|
||||
}
|
||||
|
||||
// A compile time assertion to ensure htlcSuccessResolver meets the
|
||||
|
@ -48,7 +48,22 @@ type htlcTimeoutResolver struct {
|
||||
// account any fees that may have to be paid if it goes on chain.
|
||||
htlcAmt lnwire.MilliSatoshi
|
||||
|
||||
ResolverKit
|
||||
contractResolverKit
|
||||
}
|
||||
|
||||
// newTimeoutResolver instantiates a new timeout htlc resolver.
|
||||
func newTimeoutResolver(res lnwallet.OutgoingHtlcResolution,
|
||||
broadcastHeight uint32, htlcIndex uint64,
|
||||
htlcAmt lnwire.MilliSatoshi,
|
||||
resCfg ResolverConfig) *htlcTimeoutResolver {
|
||||
|
||||
return &htlcTimeoutResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
htlcResolution: res,
|
||||
broadcastHeight: broadcastHeight,
|
||||
htlcIndex: htlcIndex,
|
||||
htlcAmt: htlcAmt,
|
||||
}
|
||||
}
|
||||
|
||||
// ResolverKey returns an identifier which should be globally unique for this
|
||||
@ -274,7 +289,7 @@ func (h *htlcTimeoutResolver) Resolve() (ContractResolver, error) {
|
||||
return errResolverShuttingDown
|
||||
}
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -312,7 +327,7 @@ func (h *htlcTimeoutResolver) Resolve() (ContractResolver, error) {
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
case <-h.Quit:
|
||||
case <-h.quit:
|
||||
return nil, errResolverShuttingDown
|
||||
}
|
||||
|
||||
@ -365,7 +380,7 @@ func (h *htlcTimeoutResolver) Resolve() (ContractResolver, error) {
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcTimeoutResolver) Stop() {
|
||||
close(h.Quit)
|
||||
close(h.quit)
|
||||
}
|
||||
|
||||
// IsResolved returns true if the stored state in the resolve is fully
|
||||
@ -406,43 +421,39 @@ func (h *htlcTimeoutResolver) Encode(w io.Writer) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Decode attempts to decode an encoded ContractResolver from the passed Reader
|
||||
// instance, returning an active ContractResolver instance.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcTimeoutResolver) Decode(r io.Reader) error {
|
||||
// newTimeoutResolverFromReader attempts to decode an encoded ContractResolver
|
||||
// from the passed Reader instance, returning an active ContractResolver
|
||||
// instance.
|
||||
func newTimeoutResolverFromReader(r io.Reader, resCfg ResolverConfig) (
|
||||
*htlcTimeoutResolver, error) {
|
||||
|
||||
h := &htlcTimeoutResolver{
|
||||
contractResolverKit: *newContractResolverKit(resCfg),
|
||||
}
|
||||
|
||||
// First, we'll read out all the mandatory fields of the
|
||||
// OutgoingHtlcResolution that we store.
|
||||
if err := decodeOutgoingResolution(r, &h.htlcResolution); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// With those fields read, we can now read back the fields that are
|
||||
// specific to the resolver itself.
|
||||
if err := binary.Read(r, endian, &h.outputIncubating); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if err := binary.Read(r, endian, &h.resolved); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
if err := binary.Read(r, endian, &h.broadcastHeight); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if err := binary.Read(r, endian, &h.htlcIndex); err != nil {
|
||||
return err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// AttachResolverKit should be called once a resolved is successfully decoded
|
||||
// from its stored format. This struct delivers a generic tool kit that
|
||||
// resolvers need to complete their duty.
|
||||
//
|
||||
// NOTE: Part of the ContractResolver interface.
|
||||
func (h *htlcTimeoutResolver) AttachResolverKit(r ResolverKit) {
|
||||
h.ResolverKit = r
|
||||
return h, nil
|
||||
}
|
||||
|
||||
// A compile time assertion to ensure htlcTimeoutResolver meets the
|
||||
|
@ -237,15 +237,18 @@ func TestHtlcTimeoutResolver(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
resolver := &htlcTimeoutResolver{
|
||||
ResolverKit: ResolverKit{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
cfg := ResolverConfig{
|
||||
ChannelArbitratorConfig: chainCfg,
|
||||
Checkpoint: func(_ ContractResolver) error {
|
||||
checkPointChan <- struct{}{}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
resolver := &htlcTimeoutResolver{
|
||||
contractResolverKit: *newContractResolverKit(
|
||||
cfg,
|
||||
),
|
||||
}
|
||||
resolver.htlcResolution.SweepSignDesc = *fakeSignDesc
|
||||
|
||||
// If the test case needs the remote commitment to be
|
||||
|
Loading…
Reference in New Issue
Block a user