Skip to content

Commit ba1b931

Browse files
Larry RuaneLarryRuane
authored andcommitted
add --sync-from-height command-line option
This causes lightwalletd to discard cached blocks at the given height and beyond. This in turn causes it to re-fetch those blocks from zcashd. It's similar to --redownload, except that option discards all blocks (equivalent to --sync-from-height 0, but the existing --redownload is retained for compatibility). This is mostly intended for testing. It's sometimes useful to force the node to (re)sync some recent blocks, but redownloading all of them takes around an hour.
1 parent dfac020 commit ba1b931

File tree

6 files changed

+29
-17
lines changed

6 files changed

+29
-17
lines changed

cmd/root.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ var rootCmd = &cobra.Command{
5555
GenCertVeryInsecure: viper.GetBool("gen-cert-very-insecure"),
5656
DataDir: viper.GetString("data-dir"),
5757
Redownload: viper.GetBool("redownload"),
58+
SyncFromHeight: viper.GetInt("sync-from-height"),
5859
PingEnable: viper.GetBool("ping-very-insecure"),
5960
Darkside: viper.GetBool("darkside-very-insecure"),
6061
DarksideTimeout: viper.GetUint64("darkside-timeout"),
@@ -239,7 +240,11 @@ func startServer(opts *common.Options) error {
239240
os.Stderr.WriteString(fmt.Sprintf("\n ** Can't create db directory: %s\n\n", dbPath))
240241
os.Exit(1)
241242
}
242-
cache := common.NewBlockCache(dbPath, chainName, saplingHeight, opts.Redownload)
243+
syncFromHeight := opts.SyncFromHeight
244+
if opts.Redownload {
245+
syncFromHeight = 0
246+
}
247+
cache := common.NewBlockCache(dbPath, chainName, saplingHeight, syncFromHeight)
243248
if !opts.Darkside {
244249
go common.BlockIngestor(cache, 0 /*loop forever*/)
245250
} else {
@@ -325,6 +330,7 @@ func init() {
325330
rootCmd.Flags().Bool("no-tls-very-insecure", false, "run without the required TLS certificate, only for debugging, DO NOT use in production")
326331
rootCmd.Flags().Bool("gen-cert-very-insecure", false, "run with self-signed TLS certificate, only for debugging, DO NOT use in production")
327332
rootCmd.Flags().Bool("redownload", false, "re-fetch all blocks from zcashd; reinitialize local cache files")
333+
rootCmd.Flags().Int("sync-from-height", -1, "re-fetch blocks from zcashd start at this height")
328334
rootCmd.Flags().String("data-dir", "/var/lib/lightwalletd", "data directory (such as db)")
329335
rootCmd.Flags().Bool("ping-very-insecure", false, "allow Ping GRPC for testing")
330336
rootCmd.Flags().Bool("darkside-very-insecure", false, "run with GRPC-controllable mock zcashd for integration testing (shuts down after 30 minutes)")
@@ -356,6 +362,8 @@ func init() {
356362
viper.SetDefault("gen-cert-very-insecure", false)
357363
viper.BindPFlag("redownload", rootCmd.Flags().Lookup("redownload"))
358364
viper.SetDefault("redownload", false)
365+
viper.BindPFlag("sync-from-height", rootCmd.Flags().Lookup("sync-from-height"))
366+
viper.SetDefault("sync-from-height", -1)
359367
viper.BindPFlag("data-dir", rootCmd.Flags().Lookup("data-dir"))
360368
viper.SetDefault("data-dir", "/var/lib/lightwalletd")
361369
viper.BindPFlag("ping-very-insecure", rootCmd.Flags().Lookup("ping-very-insecure"))

common/cache.go

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -191,7 +191,8 @@ func (c *BlockCache) Reset(startHeight int) {
191191

192192
// NewBlockCache returns an instance of a block cache object.
193193
// (No locking here, we assume this is single-threaded.)
194-
func NewBlockCache(dbPath string, chainName string, startHeight int, redownload bool) *BlockCache {
194+
// syncFromHeight < 0 means latest (tip) height.
195+
func NewBlockCache(dbPath string, chainName string, startHeight int, syncFromHeight int) *BlockCache {
195196
c := &BlockCache{}
196197
c.firstBlock = startHeight
197198
c.nextBlock = startHeight
@@ -208,18 +209,20 @@ func NewBlockCache(dbPath string, chainName string, startHeight int, redownload
208209
if err != nil {
209210
Log.Fatal("open ", c.lengthsName, " failed: ", err)
210211
}
211-
if redownload {
212-
if err := c.lengthsFile.Truncate(0); err != nil {
213-
Log.Fatal("truncate lengths file failed: ", err)
214-
}
215-
if err := c.blocksFile.Truncate(0); err != nil {
216-
Log.Fatal("truncate blocks file failed: ", err)
217-
}
218-
}
219212
lengths, err := ioutil.ReadFile(c.lengthsName)
220213
if err != nil {
221214
Log.Fatal("read ", c.lengthsName, " failed: ", err)
222215
}
216+
// 4 bytes per lengths[] value (block length)
217+
if syncFromHeight >= 0 {
218+
if syncFromHeight < startHeight {
219+
syncFromHeight = startHeight
220+
}
221+
if (syncFromHeight-startHeight)*4 < len(lengths) {
222+
// discard the entries at and beyond (newer than) the specified height
223+
lengths = lengths[:(syncFromHeight-startHeight)*4]
224+
}
225+
}
223226

224227
// The last entry in starts[] is where to write the next block.
225228
var offset int64

common/cache_test.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ func TestCache(t *testing.T) {
5858

5959
// Pretend Sapling starts at 289460.
6060
os.RemoveAll(unitTestPath)
61-
cache = NewBlockCache(unitTestPath, unitTestChain, 289460, true)
61+
cache = NewBlockCache(unitTestPath, unitTestChain, 289460, 0)
6262

6363
// Initially cache is empty.
6464
if cache.GetLatestHeight() != -1 {
@@ -75,7 +75,7 @@ func TestCache(t *testing.T) {
7575
fillCache(t)
7676

7777
// Simulate a restart to ensure the db files are read correctly.
78-
cache = NewBlockCache(unitTestPath, unitTestChain, 289460, false)
78+
cache = NewBlockCache(unitTestPath, unitTestChain, 289460, -1)
7979

8080
// Should still be 6 blocks.
8181
if cache.nextBlock != 289466 {

common/common.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ type Options struct {
4242
NoTLSVeryInsecure bool `json:"no_tls_very_insecure,omitempty"`
4343
GenCertVeryInsecure bool `json:"gen_cert_very_insecure,omitempty"`
4444
Redownload bool `json:"redownload"`
45+
SyncFromHeight int `json:"sync_from_height"`
4546
DataDir string `json:"data_dir"`
4647
PingEnable bool `json:"ping_enable"`
4748
Darkside bool `json:"darkside"`

common/common_test.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ func TestMain(m *testing.M) {
6262
blockJSON, _ := json.Marshal(scan.Text())
6363
blocks = append(blocks, blockJSON)
6464
}
65-
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, true)
65+
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, 0)
6666

6767
// Setup is done; run all tests.
6868
exitcode := m.Run()
@@ -355,7 +355,7 @@ func TestBlockIngestor(t *testing.T) {
355355
Time.Sleep = sleepStub
356356
Time.Now = nowStub
357357
os.RemoveAll(unitTestPath)
358-
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, false)
358+
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, -1)
359359
BlockIngestor(testcache, 11)
360360
if step != 19 {
361361
t.Error("unexpected final step", step)
@@ -488,7 +488,7 @@ func TestGetBlockRange(t *testing.T) {
488488
testT = t
489489
RawRequest = getblockStub
490490
os.RemoveAll(unitTestPath)
491-
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, true)
491+
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, 0)
492492
blockChan := make(chan *walletrpc.CompactBlock)
493493
errChan := make(chan error)
494494
go GetBlockRange(testcache, blockChan, errChan, 380640, 380642)
@@ -567,7 +567,7 @@ func TestGetBlockRangeReverse(t *testing.T) {
567567
testT = t
568568
RawRequest = getblockStubReverse
569569
os.RemoveAll(unitTestPath)
570-
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, true)
570+
testcache = NewBlockCache(unitTestPath, unitTestChain, 380640, 0)
571571
blockChan := make(chan *walletrpc.CompactBlock)
572572
errChan := make(chan error)
573573

frontend/frontend_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ const (
3636

3737
func testsetup() (walletrpc.CompactTxStreamerServer, *common.BlockCache) {
3838
os.RemoveAll(unitTestPath)
39-
cache := common.NewBlockCache(unitTestPath, unitTestChain, 380640, true)
39+
cache := common.NewBlockCache(unitTestPath, unitTestChain, 380640, 0)
4040
lwd, err := NewLwdStreamer(cache, "main", false /* enablePing */)
4141
if err != nil {
4242
os.Stderr.WriteString(fmt.Sprint("NewLwdStreamer failed:", err))

0 commit comments

Comments
 (0)