Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Anchor commitments 2024 #9264

Draft
wants to merge 19 commits into
base: master
Choose a base branch
from
Draft

Anchor commitments 2024 #9264

wants to merge 19 commits into from

Conversation

ecdsa
Copy link
Member

@ecdsa ecdsa commented Oct 20, 2024

this was rebased in july 2024 from #7509
I guess it needs to be rebased again :-)

Here are my personal notes regarding this rebase:

  • some tests are broken (REDEEMED state reached too early in test_breach)
  • we should use password in memory (daemon unlock command)
  • if no password in memory (non-android GUI): maybe warn user?
  • stop LN support for watching-only and hardware wallets

bitromortac and others added 19 commits June 21, 2024 09:30
* add anchor ln features
* peer.use_anchors is added
* channel.has_anchors is added
* in order to be able to sweep to_remote in an onchain backup scenario
  we need to retain the private key for the payment_basepoint
* to facilitate the above, we open a channel derived from a static
  secret (tied to the wallet seed), the static_payment_key combined with
the funding pubkey (multisig_key), which we can restore from the channel
closing transaction
* changes the htlc outputs' witness script to have a csv lock of 1
* send signatures for remote ctx with ANYONECANPAY|SINGLE
* refactor htlc weight (useful for zero-fee-htlc)
* to_remote has now an additional csv lock of 1
* anchor outputs are added if to_local/remote outputs are present
* funder balance is reduced to accomodate anchors
* sweep to_remote output, as this is now a p2wsh (previously internal
  wallet address)
* sweep htlc outputs with new scripts
* add a method for backups to sweep to_remote
* to_remote sweeping needs the payment_basepoint's private key
  to sign the sweep transaction
* we restore the private key from our funding multisig pubkey
  (pubished with the closing transaction) and a static payment key secret
* lower the final balance of the backup regtest, which is due to additional
  sweep transactions
* testing of anchor channels is controlled via TEST_ANCHOR_CHANNELS
* rewrite tests in test_lnchannel.py
* tests are kept variable via TEST_ANCHOR_CHANNELS
* sets the weight of htlc transactions to zero, thereby putting a zero
  fee for the htlc transactions
* add inputs to htlc-tx for fee bumping
* switches feature flags
* disable anchor test vectors, which are now partially invalid
* in test_lnutil, patch htlc weight to pass original anchor commitment
  test vectors
* activate tests for both commitment types
naming scheme: tx(s)_our/their_ctx/htlctx_output-description

function names are shortened to whether a single (tx) or several sweep
transactions (txs) are generated
Due to anchor channel's sighash.SINGLE and sighash.ANYONECANPAY,
several HTLC-transactions can be combined. This means we must watch for
revoked outputs in the HTLC transaction not only at index 0 but at any
index. Also, any input can now contain preimages which we have to
extract.
Due to malleability of HTLC-transactions, we can't send presigned
justice transactions for the second-stage HTLC transactions, which is
why we now send first-stage justice transactions for anchor channels.
# generate justice transactions
gen_tx = lambda: tx_sweep_htlctx_output(
sweep_address=sweep_address,
output_idx=output_idx,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh wow, amazing that the linter caught this!

./electrum/lnsweep.py:244:24: B023 Function definition does not bind loop variable 'output_idx'.
            output_idx=output_idx,
                       ^
1     B023 Function definition does not bind loop variable 'output_idx'.

Comment on lines 868 to 875
addr = None
assert self.is_static_remotekey_enabled()
our_payment_pubkey = self.config[LOCAL].payment_basepoint.pubkey
addr = make_commitment_output_to_remote_address(our_payment_pubkey)
if self.lnworker:
assert self.lnworker.wallet.is_mine(addr)
addr = make_commitment_output_to_remote_address(our_payment_pubkey, has_anchors=self.has_anchors())
# this assert fails with anchor output channels
#if self.lnworker:
# assert self.lnworker.wallet.is_mine(addr)
return addr
Copy link
Member

@SomberNight SomberNight Oct 20, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Something weird happened in a rebase here.
The original branch looks like this: https://github.com/bitromortac/electrum/blob/5cb97c077c799aa6ebd06492645b9c4f738f85f8/electrum/lnchannel.py#L325
which looks okay.

However this new implementation is not good. There is a reason that assert is there, and it failing signals a problem.
The sweep_address() method is supposed to return a wallet address that we can send coins to as part of closing this channel. It is called from a lot of places, e.g. code that is trying to sweep HTLCs will send coins here, or even the mutual close will send our coins here. Clearly we don't want the mutual close to send coins to a CSV-locked non-wallet address :)

I've tried to clarify this method in dd140df

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants