github.com/decred/dcrlnd@v0.7.6/channeldb/migration_01_to_11/channel.go (about)

     1  package migration_01_to_11
     2  
     3  import (
     4  	"errors"
     5  	"fmt"
     6  	"io"
     7  	"strconv"
     8  	"strings"
     9  	"sync"
    10  
    11  	"github.com/decred/dcrd/chaincfg/chainhash"
    12  	"github.com/decred/dcrd/dcrec/secp256k1/v4"
    13  	"github.com/decred/dcrd/dcrutil/v4"
    14  	"github.com/decred/dcrd/wire"
    15  	lnwire "github.com/decred/dcrlnd/channeldb/migration/lnwire21"
    16  	"github.com/decred/dcrlnd/keychain"
    17  	"github.com/decred/dcrlnd/shachain"
    18  )
    19  
    20  var (
    21  	// closedChannelBucket stores summarization information concerning
    22  	// previously open, but now closed channels.
    23  	closedChannelBucket = []byte("closed-chan-bucket")
    24  
    25  	// openChanBucket stores all the currently open channels. This bucket
    26  	// has a second, nested bucket which is keyed by a node's ID. Within
    27  	// that node ID bucket, all attributes required to track, update, and
    28  	// close a channel are stored.
    29  	//
    30  	// openChan -> nodeID -> chanPoint
    31  	//
    32  	// TODO(roasbeef): flesh out comment
    33  	openChannelBucket = []byte("open-chan-bucket")
    34  )
    35  
    36  // ChannelType is an enum-like type that describes one of several possible
    37  // channel types. Each open channel is associated with a particular type as the
    38  // channel type may determine how higher level operations are conducted such as
    39  // fee negotiation, channel closing, the format of HTLCs, etc. Structure-wise,
    40  // a ChannelType is a bit field, with each bit denoting a modification from the
    41  // base channel type of single funder.
    42  type ChannelType uint8
    43  
    44  const (
    45  	// NOTE: iota isn't used here for this enum needs to be stable
    46  	// long-term as it will be persisted to the database.
    47  
    48  	// SingleFunderBit represents a channel wherein one party solely funds
    49  	// the entire capacity of the channel.
    50  	SingleFunderBit ChannelType = 0
    51  )
    52  
    53  // ChannelConstraints represents a set of constraints meant to allow a node to
    54  // limit their exposure, enact flow control and ensure that all HTLCs are
    55  // economically relevant. This struct will be mirrored for both sides of the
    56  // channel, as each side will enforce various constraints that MUST be adhered
    57  // to for the life time of the channel. The parameters for each of these
    58  // constraints are static for the duration of the channel, meaning the channel
    59  // must be torn down for them to change.
    60  type ChannelConstraints struct {
    61  	// DustLimit is the threhsold (in atoms) below which any outputs
    62  	// should be trimmed. When an output is trimmed, it isn't materialized
    63  	// as an actual output, but is instead burned to miner's fees.
    64  	DustLimit dcrutil.Amount
    65  
    66  	// ChanReserve is an absolute reservation on the channel for the
    67  	// owner of this set of constraints. This means that the current
    68  	// settled balance for this node CANNOT dip below the reservation
    69  	// amount. This acts as a defense against costless attacks when
    70  	// either side no longer has any skin in the game.
    71  	ChanReserve dcrutil.Amount
    72  
    73  	// MaxPendingAmount is the maximum pending HTLC value that the
    74  	// owner of these constraints can offer the remote node at a
    75  	// particular time.
    76  	MaxPendingAmount lnwire.MilliAtom
    77  
    78  	// MinHTLC is the minimum HTLC value that the owner of these
    79  	// constraints can offer the remote node. If any HTLCs below this
    80  	// amount are offered, then the HTLC will be rejected. This, in
    81  	// tandem with the dust limit allows a node to regulate the
    82  	// smallest HTLC that it deems economically relevant.
    83  	MinHTLC lnwire.MilliAtom
    84  
    85  	// MaxAcceptedHtlcs is the maximum number of HTLCs that the owner of
    86  	// this set of constraints can offer the remote node. This allows each
    87  	// node to limit their over all exposure to HTLCs that may need to be
    88  	// acted upon in the case of a unilateral channel closure or a contract
    89  	// breach.
    90  	MaxAcceptedHtlcs uint16
    91  
    92  	// CsvDelay is the relative time lock delay expressed in blocks. Any
    93  	// settled outputs that pay to the owner of this channel configuration
    94  	// MUST ensure that the delay branch uses this value as the relative
    95  	// time lock. Similarly, any HTLC's offered by this node should use
    96  	// this value as well.
    97  	CsvDelay uint16
    98  }
    99  
   100  // ChannelConfig is a struct that houses the various configuration opens for
   101  // channels. Each side maintains an instance of this configuration file as it
   102  // governs: how the funding and commitment transaction to be created, the
   103  // nature of HTLC's allotted, the keys to be used for delivery, and relative
   104  // time lock parameters.
   105  type ChannelConfig struct {
   106  	// ChannelConstraints is the set of constraints that must be upheld for
   107  	// the duration of the channel for the owner of this channel
   108  	// configuration. Constraints govern a number of flow control related
   109  	// parameters, also including the smallest HTLC that will be accepted
   110  	// by a participant.
   111  	ChannelConstraints
   112  
   113  	// MultiSigKey is the key to be used within the 2-of-2 output script
   114  	// for the owner of this channel config.
   115  	MultiSigKey keychain.KeyDescriptor
   116  
   117  	// RevocationBasePoint is the base public key to be used when deriving
   118  	// revocation keys for the remote node's commitment transaction. This
   119  	// will be combined along with a per commitment secret to derive a
   120  	// unique revocation key for each state.
   121  	RevocationBasePoint keychain.KeyDescriptor
   122  
   123  	// PaymentBasePoint is the base public key to be used when deriving
   124  	// the key used within the non-delayed pay-to-self output on the
   125  	// commitment transaction for a node. This will be combined with a
   126  	// tweak derived from the per-commitment point to ensure unique keys
   127  	// for each commitment transaction.
   128  	PaymentBasePoint keychain.KeyDescriptor
   129  
   130  	// DelayBasePoint is the base public key to be used when deriving the
   131  	// key used within the delayed pay-to-self output on the commitment
   132  	// transaction for a node. This will be combined with a tweak derived
   133  	// from the per-commitment point to ensure unique keys for each
   134  	// commitment transaction.
   135  	DelayBasePoint keychain.KeyDescriptor
   136  
   137  	// HtlcBasePoint is the base public key to be used when deriving the
   138  	// local HTLC key. The derived key (combined with the tweak derived
   139  	// from the per-commitment point) is used within the "to self" clause
   140  	// within any HTLC output scripts.
   141  	HtlcBasePoint keychain.KeyDescriptor
   142  }
   143  
   144  // ChannelCommitment is a snapshot of the commitment state at a particular
   145  // point in the commitment chain. With each state transition, a snapshot of the
   146  // current state along with all non-settled HTLCs are recorded. These snapshots
   147  // detail the state of the _remote_ party's commitment at a particular state
   148  // number.  For ourselves (the local node) we ONLY store our most recent
   149  // (unrevoked) state for safety purposes.
   150  type ChannelCommitment struct {
   151  	// CommitHeight is the update number that this ChannelDelta represents
   152  	// the total number of commitment updates to this point. This can be
   153  	// viewed as sort of a "commitment height" as this number is
   154  	// monotonically increasing.
   155  	CommitHeight uint64
   156  
   157  	// LocalLogIndex is the cumulative log index index of the local node at
   158  	// this point in the commitment chain. This value will be incremented
   159  	// for each _update_ added to the local update log.
   160  	LocalLogIndex uint64
   161  
   162  	// LocalHtlcIndex is the current local running HTLC index. This value
   163  	// will be incremented for each outgoing HTLC the local node offers.
   164  	LocalHtlcIndex uint64
   165  
   166  	// RemoteLogIndex is the cumulative log index index of the remote node
   167  	// at this point in the commitment chain. This value will be
   168  	// incremented for each _update_ added to the remote update log.
   169  	RemoteLogIndex uint64
   170  
   171  	// RemoteHtlcIndex is the current remote running HTLC index. This value
   172  	// will be incremented for each outgoing HTLC the remote node offers.
   173  	RemoteHtlcIndex uint64
   174  
   175  	// LocalBalance is the current available settled balance within the
   176  	// channel directly spendable by us.
   177  	LocalBalance lnwire.MilliAtom
   178  
   179  	// RemoteBalance is the current available settled balance within the
   180  	// channel directly spendable by the remote node.
   181  	RemoteBalance lnwire.MilliAtom
   182  
   183  	// CommitFee is the amount calculated to be paid in fees for the
   184  	// current set of commitment transactions. The fee amount is persisted
   185  	// with the channel in order to allow the fee amount to be removed and
   186  	// recalculated with each channel state update, including updates that
   187  	// happen after a system restart.
   188  	CommitFee dcrutil.Amount
   189  
   190  	// FeePerKB is the min atoms/kilobyte that should be paid within the
   191  	// commitment transaction for the entire duration of the channel's
   192  	// lifetime. This field may be updated during normal operation of the
   193  	// channel as on-chain conditions change.
   194  	//
   195  	// TODO(halseth): make this AtomsPerKByte. Cannot be done atm because
   196  	// this will cause the import cycle lnwallet<->channeldb. Fee
   197  	// estimation stuff should be in its own package.
   198  	FeePerKB dcrutil.Amount
   199  
   200  	// CommitTx is the latest version of the commitment state, broadcast
   201  	// able by us.
   202  	CommitTx *wire.MsgTx
   203  
   204  	// CommitSig is one half of the signature required to fully complete
   205  	// the script for the commitment transaction above. This is the
   206  	// signature signed by the remote party for our version of the
   207  	// commitment transactions.
   208  	CommitSig []byte
   209  
   210  	// Htlcs is the set of HTLC's that are pending at this particular
   211  	// commitment height.
   212  	Htlcs []HTLC
   213  
   214  	// TODO(roasbeef): pending commit pointer?
   215  	//  * lets just walk through
   216  }
   217  
   218  // ChannelStatus is a bit vector used to indicate whether an OpenChannel is in
   219  // the default usable state, or a state where it shouldn't be used.
   220  type ChannelStatus uint8
   221  
   222  var (
   223  	// ChanStatusDefault is the normal state of an open channel.
   224  	ChanStatusDefault ChannelStatus
   225  
   226  	// ChanStatusBorked indicates that the channel has entered an
   227  	// irreconcilable state, triggered by a state desynchronization or
   228  	// channel breach.  Channels in this state should never be added to the
   229  	// htlc switch.
   230  	ChanStatusBorked ChannelStatus = 1
   231  
   232  	// ChanStatusCommitBroadcasted indicates that a commitment for this
   233  	// channel has been broadcasted.
   234  	ChanStatusCommitBroadcasted ChannelStatus = 1 << 1
   235  
   236  	// ChanStatusLocalDataLoss indicates that we have lost channel state
   237  	// for this channel, and broadcasting our latest commitment might be
   238  	// considered a breach.
   239  	//
   240  	// TODO(halseh): actually enforce that we are not force closing such a
   241  	// channel.
   242  	ChanStatusLocalDataLoss ChannelStatus = 1 << 2
   243  
   244  	// ChanStatusRestored is a status flag that signals that the channel
   245  	// has been restored, and doesn't have all the fields a typical channel
   246  	// will have.
   247  	ChanStatusRestored ChannelStatus = 1 << 3
   248  )
   249  
   250  // chanStatusStrings maps a ChannelStatus to a human friendly string that
   251  // describes that status.
   252  var chanStatusStrings = map[ChannelStatus]string{
   253  	ChanStatusDefault:           "ChanStatusDefault",
   254  	ChanStatusBorked:            "ChanStatusBorked",
   255  	ChanStatusCommitBroadcasted: "ChanStatusCommitBroadcasted",
   256  	ChanStatusLocalDataLoss:     "ChanStatusLocalDataLoss",
   257  	ChanStatusRestored:          "ChanStatusRestored",
   258  }
   259  
   260  // orderedChanStatusFlags is an in-order list of all that channel status flags.
   261  var orderedChanStatusFlags = []ChannelStatus{
   262  	ChanStatusDefault,
   263  	ChanStatusBorked,
   264  	ChanStatusCommitBroadcasted,
   265  	ChanStatusLocalDataLoss,
   266  	ChanStatusRestored,
   267  }
   268  
   269  // String returns a human-readable representation of the ChannelStatus.
   270  func (c ChannelStatus) String() string {
   271  	// If no flags are set, then this is the default case.
   272  	if c == 0 {
   273  		return chanStatusStrings[ChanStatusDefault]
   274  	}
   275  
   276  	// Add individual bit flags.
   277  	statusStr := ""
   278  	for _, flag := range orderedChanStatusFlags {
   279  		if c&flag == flag {
   280  			statusStr += chanStatusStrings[flag] + "|"
   281  			c -= flag
   282  		}
   283  	}
   284  
   285  	// Remove anything to the right of the final bar, including it as well.
   286  	statusStr = strings.TrimRight(statusStr, "|")
   287  
   288  	// Add any remaining flags which aren't accounted for as hex.
   289  	if c != 0 {
   290  		statusStr += "|0x" + strconv.FormatUint(uint64(c), 16)
   291  	}
   292  
   293  	// If this was purely an unknown flag, then remove the extra bar at the
   294  	// start of the string.
   295  	statusStr = strings.TrimLeft(statusStr, "|")
   296  
   297  	return statusStr
   298  }
   299  
   300  // OpenChannel encapsulates the persistent and dynamic state of an open channel
   301  // with a remote node. An open channel supports several options for on-disk
   302  // serialization depending on the exact context. Full (upon channel creation)
   303  // state commitments, and partial (due to a commitment update) writes are
   304  // supported. Each partial write due to a state update appends the new update
   305  // to an on-disk log, which can then subsequently be queried in order to
   306  // "time-travel" to a prior state.
   307  type OpenChannel struct {
   308  	// ChanType denotes which type of channel this is.
   309  	ChanType ChannelType
   310  
   311  	// ChainHash is a hash which represents the blockchain that this
   312  	// channel will be opened within. This value is typically the genesis
   313  	// hash. In the case that the original chain went through a contentious
   314  	// hard-fork, then this value will be tweaked using the unique fork
   315  	// point on each branch.
   316  	ChainHash chainhash.Hash
   317  
   318  	// FundingOutpoint is the outpoint of the final funding transaction.
   319  	// This value uniquely and globally identifies the channel within the
   320  	// target blockchain as specified by the chain hash parameter.
   321  	FundingOutpoint wire.OutPoint
   322  
   323  	// ShortChannelID encodes the exact location in the chain in which the
   324  	// channel was initially confirmed. This includes: the block height,
   325  	// transaction index, and the output within the target transaction.
   326  	ShortChannelID lnwire.ShortChannelID
   327  
   328  	// IsPending indicates whether a channel's funding transaction has been
   329  	// confirmed.
   330  	IsPending bool
   331  
   332  	// IsInitiator is a bool which indicates if we were the original
   333  	// initiator for the channel. This value may affect how higher levels
   334  	// negotiate fees, or close the channel.
   335  	IsInitiator bool
   336  
   337  	// FundingBroadcastHeight is the height in which the funding
   338  	// transaction was broadcast. This value can be used by higher level
   339  	// sub-systems to determine if a channel is stale and/or should have
   340  	// been confirmed before a certain height.
   341  	FundingBroadcastHeight uint32
   342  
   343  	// NumConfsRequired is the number of confirmations a channel's funding
   344  	// transaction must have received in order to be considered available
   345  	// for normal transactional use.
   346  	NumConfsRequired uint16
   347  
   348  	// ChannelFlags holds the flags that were sent as part of the
   349  	// open_channel message.
   350  	ChannelFlags lnwire.FundingFlag
   351  
   352  	// IdentityPub is the identity public key of the remote node this
   353  	// channel has been established with.
   354  	IdentityPub *secp256k1.PublicKey
   355  
   356  	// Capacity is the total capacity of this channel.
   357  	Capacity dcrutil.Amount
   358  
   359  	// TotalMAtomsSent is the total number of milli-atoms we've sent
   360  	// within this channel.
   361  	TotalMAtomsSent lnwire.MilliAtom
   362  
   363  	// TotalMAtomsReceived is the total number of milli-atoms we've
   364  	// received within this channel.
   365  	TotalMAtomsReceived lnwire.MilliAtom
   366  
   367  	// LocalChanCfg is the channel configuration for the local node.
   368  	LocalChanCfg ChannelConfig
   369  
   370  	// RemoteChanCfg is the channel configuration for the remote node.
   371  	RemoteChanCfg ChannelConfig
   372  
   373  	// LocalCommitment is the current local commitment state for the local
   374  	// party. This is stored distinct from the state of the remote party
   375  	// as there are certain asymmetric parameters which affect the
   376  	// structure of each commitment.
   377  	LocalCommitment ChannelCommitment
   378  
   379  	// RemoteCommitment is the current remote commitment state for the
   380  	// remote party. This is stored distinct from the state of the local
   381  	// party as there are certain asymmetric parameters which affect the
   382  	// structure of each commitment.
   383  	RemoteCommitment ChannelCommitment
   384  
   385  	// RemoteCurrentRevocation is the current revocation for their
   386  	// commitment transaction. However, since this the derived public key,
   387  	// we don't yet have the private key so we aren't yet able to verify
   388  	// that it's actually in the hash chain.
   389  	RemoteCurrentRevocation *secp256k1.PublicKey
   390  
   391  	// RemoteNextRevocation is the revocation key to be used for the *next*
   392  	// commitment transaction we create for the local node. Within the
   393  	// specification, this value is referred to as the
   394  	// per-commitment-point.
   395  	RemoteNextRevocation *secp256k1.PublicKey
   396  
   397  	// RevocationProducer is used to generate the revocation in such a way
   398  	// that remote side might store it efficiently and have the ability to
   399  	// restore the revocation by index if needed. Current implementation of
   400  	// secret producer is shachain producer.
   401  	RevocationProducer shachain.Producer
   402  
   403  	// RevocationStore is used to efficiently store the revocations for
   404  	// previous channels states sent to us by remote side. Current
   405  	// implementation of secret store is shachain store.
   406  	RevocationStore shachain.Store
   407  
   408  	// FundingTxn is the transaction containing this channel's funding
   409  	// outpoint. Upon restarts, this txn will be rebroadcast if the channel
   410  	// is found to be pending.
   411  	//
   412  	// NOTE: This value will only be populated for single-funder channels
   413  	// for which we are the initiator.
   414  	FundingTxn *wire.MsgTx
   415  
   416  	// TODO(roasbeef): eww
   417  	Db *DB
   418  
   419  	// TODO(roasbeef): just need to store local and remote HTLC's?
   420  
   421  	sync.RWMutex
   422  }
   423  
   424  // ShortChanID returns the current ShortChannelID of this channel.
   425  func (c *OpenChannel) ShortChanID() lnwire.ShortChannelID {
   426  	c.RLock()
   427  	defer c.RUnlock()
   428  
   429  	return c.ShortChannelID
   430  }
   431  
   432  // HTLC is the on-disk representation of a hash time-locked contract. HTLCs are
   433  // contained within ChannelDeltas which encode the current state of the
   434  // commitment between state updates.
   435  //
   436  // TODO(roasbeef): save space by using smaller ints at tail end?
   437  type HTLC struct {
   438  	// Signature is the signature for the second level covenant transaction
   439  	// for this HTLC. The second level transaction is a timeout tx in the
   440  	// case that this is an outgoing HTLC, and a success tx in the case
   441  	// that this is an incoming HTLC.
   442  	//
   443  	// TODO(roasbeef): make [64]byte instead?
   444  	Signature []byte
   445  
   446  	// RHash is the payment hash of the HTLC.
   447  	RHash [32]byte
   448  
   449  	// Amt is the amount of milli-satoshis this HTLC escrows.
   450  	Amt lnwire.MilliAtom
   451  
   452  	// RefundTimeout is the absolute timeout on the HTLC that the sender
   453  	// must wait before reclaiming the funds in limbo.
   454  	RefundTimeout uint32
   455  
   456  	// OutputIndex is the output index for this particular HTLC output
   457  	// within the commitment transaction.
   458  	OutputIndex int32
   459  
   460  	// Incoming denotes whether we're the receiver or the sender of this
   461  	// HTLC.
   462  	Incoming bool
   463  
   464  	// OnionBlob is an opaque blob which is used to complete multi-hop
   465  	// routing.
   466  	OnionBlob []byte
   467  
   468  	// HtlcIndex is the HTLC counter index of this active, outstanding
   469  	// HTLC. This differs from the LogIndex, as the HtlcIndex is only
   470  	// incremented for each offered HTLC, while they LogIndex is
   471  	// incremented for each update (includes settle+fail).
   472  	HtlcIndex uint64
   473  
   474  	// LogIndex is the cumulative log index of this HTLC. This differs
   475  	// from the HtlcIndex as this will be incremented for each new log
   476  	// update added.
   477  	LogIndex uint64
   478  }
   479  
   480  // CircuitKey is used by a channel to uniquely identify the HTLCs it receives
   481  // from the switch, and is used to purge our in-memory state of HTLCs that have
   482  // already been processed by a link. Two list of CircuitKeys are included in
   483  // each CommitDiff to allow a link to determine which in-memory htlcs directed
   484  // the opening and closing of circuits in the switch's circuit map.
   485  type CircuitKey struct {
   486  	// ChanID is the short chanid indicating the HTLC's origin.
   487  	//
   488  	// NOTE: It is fine for this value to be blank, as this indicates a
   489  	// locally-sourced payment.
   490  	ChanID lnwire.ShortChannelID
   491  
   492  	// HtlcID is the unique htlc index predominately assigned by links,
   493  	// though can also be assigned by switch in the case of locally-sourced
   494  	// payments.
   495  	HtlcID uint64
   496  }
   497  
   498  // String returns a string representation of the CircuitKey.
   499  func (k CircuitKey) String() string {
   500  	return fmt.Sprintf("(Chan ID=%s, HTLC ID=%d)", k.ChanID, k.HtlcID)
   501  }
   502  
   503  // ClosureType is an enum like structure that details exactly _how_ a channel
   504  // was closed. Three closure types are currently possible: none, cooperative,
   505  // local force close, remote force close, and (remote) breach.
   506  type ClosureType uint8
   507  
   508  const (
   509  	// RemoteForceClose indicates that the remote peer has unilaterally
   510  	// broadcast their current commitment state on-chain.
   511  	RemoteForceClose ClosureType = 4
   512  )
   513  
   514  // ChannelCloseSummary contains the final state of a channel at the point it
   515  // was closed. Once a channel is closed, all the information pertaining to that
   516  // channel within the openChannelBucket is deleted, and a compact summary is
   517  // put in place instead.
   518  type ChannelCloseSummary struct {
   519  	// ChanPoint is the outpoint for this channel's funding transaction,
   520  	// and is used as a unique identifier for the channel.
   521  	ChanPoint wire.OutPoint
   522  
   523  	// ShortChanID encodes the exact location in the chain in which the
   524  	// channel was initially confirmed. This includes: the block height,
   525  	// transaction index, and the output within the target transaction.
   526  	ShortChanID lnwire.ShortChannelID
   527  
   528  	// ChainHash is the hash of the genesis block that this channel resides
   529  	// within.
   530  	ChainHash chainhash.Hash
   531  
   532  	// ClosingTXID is the txid of the transaction which ultimately closed
   533  	// this channel.
   534  	ClosingTXID chainhash.Hash
   535  
   536  	// RemotePub is the public key of the remote peer that we formerly had
   537  	// a channel with.
   538  	RemotePub *secp256k1.PublicKey
   539  
   540  	// Capacity was the total capacity of the channel.
   541  	Capacity dcrutil.Amount
   542  
   543  	// CloseHeight is the height at which the funding transaction was
   544  	// spent.
   545  	CloseHeight uint32
   546  
   547  	// SettledBalance is our total balance settled balance at the time of
   548  	// channel closure. This _does not_ include the sum of any outputs that
   549  	// have been time-locked as a result of the unilateral channel closure.
   550  	SettledBalance dcrutil.Amount
   551  
   552  	// TimeLockedBalance is the sum of all the time-locked outputs at the
   553  	// time of channel closure. If we triggered the force closure of this
   554  	// channel, then this value will be non-zero if our settled output is
   555  	// above the dust limit. If we were on the receiving side of a channel
   556  	// force closure, then this value will be non-zero if we had any
   557  	// outstanding outgoing HTLC's at the time of channel closure.
   558  	TimeLockedBalance dcrutil.Amount
   559  
   560  	// CloseType details exactly _how_ the channel was closed. Five closure
   561  	// types are possible: cooperative, local force, remote force, breach
   562  	// and funding canceled.
   563  	CloseType ClosureType
   564  
   565  	// IsPending indicates whether this channel is in the 'pending close'
   566  	// state, which means the channel closing transaction has been
   567  	// confirmed, but not yet been fully resolved. In the case of a channel
   568  	// that has been cooperatively closed, it will go straight into the
   569  	// fully resolved state as soon as the closing transaction has been
   570  	// confirmed. However, for channels that have been force closed, they'll
   571  	// stay marked as "pending" until _all_ the pending funds have been
   572  	// swept.
   573  	IsPending bool
   574  
   575  	// RemoteCurrentRevocation is the current revocation for their
   576  	// commitment transaction. However, since this is the derived public key,
   577  	// we don't yet have the private key so we aren't yet able to verify
   578  	// that it's actually in the hash chain.
   579  	RemoteCurrentRevocation *secp256k1.PublicKey
   580  
   581  	// RemoteNextRevocation is the revocation key to be used for the *next*
   582  	// commitment transaction we create for the local node. Within the
   583  	// specification, this value is referred to as the
   584  	// per-commitment-point.
   585  	RemoteNextRevocation *secp256k1.PublicKey
   586  
   587  	// LocalChanCfg is the channel configuration for the local node.
   588  	LocalChanConfig ChannelConfig
   589  
   590  	// LastChanSyncMsg is the ChannelReestablish message for this channel
   591  	// for the state at the point where it was closed.
   592  	LastChanSyncMsg *lnwire.ChannelReestablish
   593  }
   594  
   595  func serializeChannelCloseSummary(w io.Writer, cs *ChannelCloseSummary) error {
   596  	err := WriteElements(w,
   597  		cs.ChanPoint, cs.ShortChanID, cs.ChainHash, cs.ClosingTXID,
   598  		cs.CloseHeight, cs.RemotePub, cs.Capacity, cs.SettledBalance,
   599  		cs.TimeLockedBalance, cs.CloseType, cs.IsPending,
   600  	)
   601  	if err != nil {
   602  		return err
   603  	}
   604  
   605  	// If this is a close channel summary created before the addition of
   606  	// the new fields, then we can exit here.
   607  	if cs.RemoteCurrentRevocation == nil {
   608  		return WriteElements(w, false)
   609  	}
   610  
   611  	// If fields are present, write boolean to indicate this, and continue.
   612  	if err := WriteElements(w, true); err != nil {
   613  		return err
   614  	}
   615  
   616  	if err := WriteElements(w, cs.RemoteCurrentRevocation); err != nil {
   617  		return err
   618  	}
   619  
   620  	if err := writeChanConfig(w, &cs.LocalChanConfig); err != nil {
   621  		return err
   622  	}
   623  
   624  	// The RemoteNextRevocation field is optional, as it's possible for a
   625  	// channel to be closed before we learn of the next unrevoked
   626  	// revocation point for the remote party. Write a boolen indicating
   627  	// whether this field is present or not.
   628  	if err := WriteElements(w, cs.RemoteNextRevocation != nil); err != nil {
   629  		return err
   630  	}
   631  
   632  	// Write the field, if present.
   633  	if cs.RemoteNextRevocation != nil {
   634  		if err = WriteElements(w, cs.RemoteNextRevocation); err != nil {
   635  			return err
   636  		}
   637  	}
   638  
   639  	// Write whether the channel sync message is present.
   640  	if err := WriteElements(w, cs.LastChanSyncMsg != nil); err != nil {
   641  		return err
   642  	}
   643  
   644  	// Write the channel sync message, if present.
   645  	if cs.LastChanSyncMsg != nil {
   646  		if err := WriteElements(w, cs.LastChanSyncMsg); err != nil {
   647  			return err
   648  		}
   649  	}
   650  
   651  	return nil
   652  }
   653  
   654  func deserializeCloseChannelSummary(r io.Reader) (*ChannelCloseSummary, error) {
   655  	c := &ChannelCloseSummary{}
   656  
   657  	err := ReadElements(r,
   658  		&c.ChanPoint, &c.ShortChanID, &c.ChainHash, &c.ClosingTXID,
   659  		&c.CloseHeight, &c.RemotePub, &c.Capacity, &c.SettledBalance,
   660  		&c.TimeLockedBalance, &c.CloseType, &c.IsPending,
   661  	)
   662  	if err != nil {
   663  		return nil, err
   664  	}
   665  
   666  	// We'll now check to see if the channel close summary was encoded with
   667  	// any of the additional optional fields.
   668  	var hasNewFields bool
   669  	err = ReadElements(r, &hasNewFields)
   670  	if err != nil {
   671  		return nil, err
   672  	}
   673  
   674  	// If fields are not present, we can return.
   675  	if !hasNewFields {
   676  		return c, nil
   677  	}
   678  
   679  	// Otherwise read the new fields.
   680  	if err := ReadElements(r, &c.RemoteCurrentRevocation); err != nil {
   681  		return nil, err
   682  	}
   683  
   684  	if err := readChanConfig(r, &c.LocalChanConfig); err != nil {
   685  		return nil, err
   686  	}
   687  
   688  	// Finally, we'll attempt to read the next unrevoked commitment point
   689  	// for the remote party. If we closed the channel before receiving a
   690  	// funding locked message then this might not be present. A boolean
   691  	// indicating whether the field is present will come first.
   692  	var hasRemoteNextRevocation bool
   693  	err = ReadElements(r, &hasRemoteNextRevocation)
   694  	if err != nil {
   695  		return nil, err
   696  	}
   697  
   698  	// If this field was written, read it.
   699  	if hasRemoteNextRevocation {
   700  		err = ReadElements(r, &c.RemoteNextRevocation)
   701  		if err != nil {
   702  			return nil, err
   703  		}
   704  	}
   705  
   706  	// Check if we have a channel sync message to read.
   707  	var hasChanSyncMsg bool
   708  	err = ReadElements(r, &hasChanSyncMsg)
   709  	if err == io.EOF {
   710  		return c, nil
   711  	} else if err != nil {
   712  		return nil, err
   713  	}
   714  
   715  	// If a chan sync message is present, read it.
   716  	if hasChanSyncMsg {
   717  		// We must pass in reference to a lnwire.Message for the codec
   718  		// to support it.
   719  		var msg lnwire.Message
   720  		if err := ReadElements(r, &msg); err != nil {
   721  			return nil, err
   722  		}
   723  
   724  		chanSync, ok := msg.(*lnwire.ChannelReestablish)
   725  		if !ok {
   726  			return nil, errors.New("unable cast db Message to " +
   727  				"ChannelReestablish")
   728  		}
   729  		c.LastChanSyncMsg = chanSync
   730  	}
   731  
   732  	return c, nil
   733  }
   734  
   735  func writeChanConfig(b io.Writer, c *ChannelConfig) error {
   736  	return WriteElements(b,
   737  		c.DustLimit, c.MaxPendingAmount, c.ChanReserve, c.MinHTLC,
   738  		c.MaxAcceptedHtlcs, c.CsvDelay, c.MultiSigKey,
   739  		c.RevocationBasePoint, c.PaymentBasePoint, c.DelayBasePoint,
   740  		c.HtlcBasePoint,
   741  	)
   742  }
   743  
   744  func readChanConfig(b io.Reader, c *ChannelConfig) error {
   745  	return ReadElements(b,
   746  		&c.DustLimit, &c.MaxPendingAmount, &c.ChanReserve,
   747  		&c.MinHTLC, &c.MaxAcceptedHtlcs, &c.CsvDelay,
   748  		&c.MultiSigKey, &c.RevocationBasePoint,
   749  		&c.PaymentBasePoint, &c.DelayBasePoint,
   750  		&c.HtlcBasePoint,
   751  	)
   752  }