forked from lightningnetwork/lnd
-
Notifications
You must be signed in to change notification settings - Fork 23
/
dcrlnd.go
143 lines (122 loc) · 4.13 KB
/
dcrlnd.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
package dcrlnd
import (
"context"
"crypto/rand"
"errors"
"fmt"
"io"
"time"
"decred.org/dcrwallet/v4/wallet"
"github.com/decred/dcrlnd/chainreg"
"github.com/decred/dcrlnd/lnrpc/initchainsyncrpc"
"github.com/decred/dcrlnd/lnwallet"
"github.com/decred/dcrlnd/lnwallet/dcrwallet"
walletloader "github.com/decred/dcrlnd/lnwallet/dcrwallet/loader"
"github.com/decred/dcrlnd/lnwallet/remotedcrwallet"
"github.com/decred/dcrlnd/signal"
"github.com/decred/slog"
"gopkg.in/macaroon-bakery.v2/bakery"
)
var errShutdownRequested = errors.New("shutdown requested")
var initChainSyncPermissions = map[string][]bakery.Op{
"/initialchainsyncrpc.InitialChainSync/SubscribeChainSync": {{
Entity: "onchain",
Action: "read",
}},
}
// waitForInitialChainSync waits until the initial chain sync is completed
// before returning. It creates a gRPC service to listen to requests to provide
// the sync progress.
func waitForInitialChainSync(activeChainControl *chainreg.ChainControl,
interceptor *signal.Interceptor, svc *initchainsyncrpc.Server) error {
_, bestHeight, err := activeChainControl.ChainIO.GetBestBlock()
if err != nil {
return err
}
ltndLog.Infof("Waiting for chain backend to finish sync, "+
"start_height=%v", bestHeight)
svc.SetChainControl(activeChainControl.Wallet)
// Wait until the initial sync is done.
select {
case <-interceptor.ShutdownChannel():
return errShutdownRequested
case <-activeChainControl.Wallet.InitialSyncChannel():
}
_, bestHeight, err = activeChainControl.ChainIO.GetBestBlock()
if err != nil {
return err
}
ltndLog.Infof("Chain backend is fully synced (end_height=%v)!",
bestHeight)
return nil
}
func noSeedBackupWalletInit(ctx context.Context, cfg *Config, privPass, pubPass []byte) (*wallet.Wallet, error) {
netDir := dcrwallet.NetworkDir(
cfg.Decred.ChainDir, cfg.ActiveNetParams.Params,
)
loader := walletloader.NewLoader(
cfg.ActiveNetParams.Params, netDir, wallet.DefaultGapLimit,
// loaderOpts...,
)
exists, err := loader.WalletExists()
if err != nil {
return nil, err
}
if exists {
return loader.OpenExistingWallet(ctx, pubPass)
}
var seed [32]byte
if _, err := io.ReadFull(rand.Reader, seed[:]); err != nil {
return nil, err
}
return loader.CreateNewWallet(ctx, pubPass, privPass, seed[:],
time.Now().Add(-time.Hour*24))
}
type RemoteWalletBuilder struct {
logger slog.Logger
}
func (rb *RemoteWalletBuilder) BuildChainControl(
partialChainControl *chainreg.PartialChainControl,
walletConfig *chainreg.WalletConfig) (*chainreg.ChainControl, func(), error) {
cfg := partialChainControl.Cfg
// Initialize an RPC syncer for this wallet and use it as
// blockchain IO source.
dcrwConfig := &remotedcrwallet.Config{
PrivatePass: walletConfig.PrivatePass,
NetParams: cfg.ActiveNetParams.Params,
DB: cfg.FullDB,
Conn: partialChainControl.Cfg.WalletUnlockParams.Conn,
AccountNumber: walletConfig.AccountNb,
BlockCache: cfg.BlockCache,
}
walletController, err := remotedcrwallet.New(*dcrwConfig)
if err != nil {
err := fmt.Errorf("unable to create remote wallet "+
"controller: %v\n", err)
return nil, nil, err
}
// Create, and start the lnwallet, which handles the core payment
// channel logic, and exposes control via proxy state machines.
lnWalletConfig := lnwallet.Config{
Database: partialChainControl.Cfg.ChanStateDB,
Notifier: partialChainControl.ChainNotifier,
WalletController: walletController,
Signer: walletController,
FeeEstimator: partialChainControl.FeeEstimator,
SecretKeyRing: walletController,
ChainIO: walletController,
DefaultConstraints: partialChainControl.ChannelConstraints,
NetParams: *partialChainControl.Cfg.ActiveNetParams.Params,
}
// We've created the wallet configuration now, so we can finish
// initializing the main chain control.
activeChainControl, cleanUp, err := chainreg.NewChainControl(
lnWalletConfig, walletController, partialChainControl,
)
if err != nil {
err := fmt.Errorf("unable to create chain control: %v", err)
rb.logger.Error(err)
return nil, nil, err
}
return activeChainControl, cleanUp, nil
}