Skip to content

Commit

Permalink
staticaddr: dest addr and fee rate for withdrawals
Browse files Browse the repository at this point in the history
  • Loading branch information
hieblmi committed Nov 29, 2024
1 parent 0d30733 commit fb9562b
Show file tree
Hide file tree
Showing 3 changed files with 73 additions and 28 deletions.
26 changes: 21 additions & 5 deletions cmd/loop/staticaddr.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,3 @@
//go:build staticaddr
// +build staticaddr

package main

import (
Expand Down Expand Up @@ -145,6 +142,18 @@ var withdrawalCommand = cli.Command{
Name: "all",
Usage: "withdraws all static address deposits.",
},
cli.StringFlag{
Name: "addr",
Usage: "the optional address that the withdrawn " +
"funds should be sent to, if let blank the " +
"funds will go to lnd's wallet",
},
cli.Int64Flag{
Name: "sat_per_vbyte",
Usage: "(optional) a manual fee expressed in " +
"sat/vbyte that should be used when crafting " +
"the transaction",
},
},
Action: withdraw,
}
Expand All @@ -165,6 +174,7 @@ func withdraw(ctx *cli.Context) error {
isUtxoSelected = ctx.IsSet("utxo")
outpoints []*looprpc.OutPoint
ctxb = context.Background()
destAddr string
)

switch {
Expand All @@ -183,10 +193,16 @@ func withdraw(ctx *cli.Context) error {
return fmt.Errorf("unknown withdrawal request")
}

if ctx.IsSet("addr") {
destAddr = ctx.String("addr")
}

resp, err := client.WithdrawDeposits(ctxb,
&looprpc.WithdrawDepositsRequest{
Outpoints: outpoints,
All: isAllSelected,
Outpoints: outpoints,
All: isAllSelected,
DestAddr: destAddr,
SatPerVbyte: int64(ctx.Uint64("sat_per_vbyte")),
})
if err != nil {
return err
Expand Down
2 changes: 1 addition & 1 deletion loopd/swapclient_server.go
Original file line number Diff line number Diff line change
Expand Up @@ -1447,7 +1447,7 @@ func (s *swapClientServer) WithdrawDeposits(ctx context.Context,
}

txhash, pkScript, err := s.withdrawalManager.DeliverWithdrawalRequest(
ctx, outpoints,
ctx, outpoints, req.DestAddr, req.SatPerVbyte,
)
if err != nil {
return nil, err
Expand Down
73 changes: 51 additions & 22 deletions staticaddr/withdraw/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -71,8 +71,10 @@ type ManagerConfig struct {
// newWithdrawalRequest is used to send withdrawal request to the manager main
// loop.
type newWithdrawalRequest struct {
outpoints []wire.OutPoint
respChan chan *newWithdrawalResponse
outpoints []wire.OutPoint
respChan chan *newWithdrawalResponse
destAddr string
satPerVbyte int64
}

// newWithdrawalResponse is used to return withdrawal info and error to the
Expand Down Expand Up @@ -156,7 +158,8 @@ func (m *Manager) Run(ctx context.Context, currentHeight uint32) error {

case request := <-m.newWithdrawalRequestChan:
txHash, pkScript, err = m.WithdrawDeposits(
ctx, request.outpoints,
ctx, request.outpoints, request.destAddr,
request.satPerVbyte,
)
if err != nil {
log.Errorf("Error withdrawing deposits: %v",
Expand Down Expand Up @@ -258,7 +261,8 @@ func (m *Manager) WaitInitComplete() {

// WithdrawDeposits starts a deposits withdrawal flow.
func (m *Manager) WithdrawDeposits(ctx context.Context,
outpoints []wire.OutPoint) (string, string, error) {
outpoints []wire.OutPoint, destAddr string, satPerVbyte int64) (string,
string, error) {

if len(outpoints) == 0 {
return "", "", fmt.Errorf("no outpoints selected to " +
Expand All @@ -274,17 +278,32 @@ func (m *Manager) WithdrawDeposits(ctx context.Context,
return "", "", ErrWithdrawingInactiveDeposits
}

// Generate the withdrawal address from our local lnd wallet.
withdrawalAddress, err := m.cfg.WalletKit.NextAddr(
ctx, lnwallet.DefaultAccountName,
walletrpc.AddressType_TAPROOT_PUBKEY, false,
var (
withdrawalAddress btcutil.Address
err error
)
if err != nil {
return "", "", err

// Check if the user provided an address to withdraw to. If not, we'll
// generate a new address for them.
if destAddr != "" {
withdrawalAddress, err = btcutil.DecodeAddress(
destAddr, m.cfg.ChainParams,
)
if err != nil {
return "", "", err
}
} else {
withdrawalAddress, err = m.cfg.WalletKit.NextAddr(
ctx, lnwallet.DefaultAccountName,
walletrpc.AddressType_TAPROOT_PUBKEY, false,
)
if err != nil {
return "", "", err
}
}

finalizedTx, err := m.createFinalizedWithdrawalTx(
ctx, deposits, withdrawalAddress,
ctx, deposits, withdrawalAddress, satPerVbyte,
)
if err != nil {
return "", "", err
Expand Down Expand Up @@ -335,8 +354,8 @@ func (m *Manager) WithdrawDeposits(ctx context.Context,
}

func (m *Manager) createFinalizedWithdrawalTx(ctx context.Context,
deposits []*deposit.Deposit, withdrawalAddress btcutil.Address) (
*wire.MsgTx, error) {
deposits []*deposit.Deposit, withdrawalAddress btcutil.Address,
satPerVbyte int64) (*wire.MsgTx, error) {

// Create a musig2 session for each deposit.
withdrawalSessions, clientNonces, err := m.createMusig2Sessions(
Expand All @@ -346,12 +365,19 @@ func (m *Manager) createFinalizedWithdrawalTx(ctx context.Context,
return nil, err
}

// Get the fee rate for the withdrawal sweep.
withdrawalSweepFeeRate, err := m.cfg.WalletKit.EstimateFeeRate(
ctx, defaultConfTarget,
)
if err != nil {
return nil, err
var withdrawalSweepFeeRate chainfee.SatPerKWeight
if satPerVbyte == 0 {
// Get the fee rate for the withdrawal sweep.
withdrawalSweepFeeRate, err = m.cfg.WalletKit.EstimateFeeRate(
ctx, defaultConfTarget,
)
if err != nil {
return nil, err
}
} else {
withdrawalSweepFeeRate = chainfee.SatPerKVByte(
satPerVbyte * 1000,
).FeePerKWeight()
}

outpoints := toOutpoints(deposits)
Expand Down Expand Up @@ -788,11 +814,14 @@ func (m *Manager) republishWithdrawals(ctx context.Context) error {
// DeliverWithdrawalRequest forwards a withdrawal request to the manager main
// loop.
func (m *Manager) DeliverWithdrawalRequest(ctx context.Context,
outpoints []wire.OutPoint) (string, string, error) {
outpoints []wire.OutPoint, destAddr string, satPerVbyte int64) (string,
string, error) {

request := newWithdrawalRequest{
outpoints: outpoints,
respChan: make(chan *newWithdrawalResponse),
outpoints: outpoints,
destAddr: destAddr,
satPerVbyte: satPerVbyte,
respChan: make(chan *newWithdrawalResponse),
}

// Send the new loop-in request to the manager run loop.
Expand Down

0 comments on commit fb9562b

Please sign in to comment.