github.com/NebulousLabs/Sia@v1.3.7/modules/consensus/persist.go (about) 1 package consensus 2 3 import ( 4 "errors" 5 "fmt" 6 "os" 7 "path/filepath" 8 9 "github.com/NebulousLabs/Sia/build" 10 "github.com/NebulousLabs/Sia/modules" 11 "github.com/NebulousLabs/Sia/persist" 12 13 "github.com/coreos/bbolt" 14 ) 15 16 const ( 17 // DatabaseFilename contains the filename of the database that will be used 18 // when managing consensus. 19 DatabaseFilename = modules.ConsensusDir + ".db" 20 logFile = modules.ConsensusDir + ".log" 21 ) 22 23 // loadDB pulls all the blocks that have been saved to disk into memory, using 24 // them to fill out the ConsensusSet. 25 func (cs *ConsensusSet) loadDB() error { 26 // Open the database - a new bolt database will be created if none exists. 27 err := cs.openDB(filepath.Join(cs.persistDir, DatabaseFilename)) 28 if err != nil { 29 return err 30 } 31 32 // Walk through initialization for Sia. 33 return cs.db.Update(func(tx *bolt.Tx) error { 34 // Check if the database has been initialized. 35 err = cs.initDB(tx) 36 if err != nil { 37 return err 38 } 39 40 // Check the initialization of the oak difficulty adjustment fields, and 41 // create them if they do not exist. This is separate from 'initDB' 42 // because older consensus databases will have completed the 'initDB' 43 // process but will not have the oak difficulty adjustment fields, so a 44 // scan will be needed to add and update them. 45 err = cs.initOak(tx) 46 if err != nil { 47 return err 48 } 49 50 // Check that the genesis block is correct - typically only incorrect 51 // in the event of developer binaries vs. release binaires. 52 genesisID, err := getPath(tx, 0) 53 if build.DEBUG && err != nil { 54 panic(err) 55 } 56 if genesisID != cs.blockRoot.Block.ID() { 57 return errors.New("Blockchain has wrong genesis block, exiting.") 58 } 59 return nil 60 }) 61 } 62 63 // initPersist initializes the persistence structures of the consensus set, in 64 // particular loading the database and preparing to manage subscribers. 65 func (cs *ConsensusSet) initPersist() error { 66 // Create the consensus directory. 67 err := os.MkdirAll(cs.persistDir, 0700) 68 if err != nil { 69 return err 70 } 71 72 // Initialize the logger. 73 cs.log, err = persist.NewFileLogger(filepath.Join(cs.persistDir, logFile)) 74 if err != nil { 75 return err 76 } 77 // Set up closing the logger. 78 cs.tg.AfterStop(func() { 79 err := cs.log.Close() 80 if err != nil { 81 // State of the logger is unknown, a println will suffice. 82 fmt.Println("Error shutting down consensus set logger:", err) 83 } 84 }) 85 86 // Try to load an existing database from disk - a new one will be created 87 // if one does not exist. 88 err = cs.loadDB() 89 if err != nil { 90 return err 91 } 92 // Set up the closing of the database. 93 cs.tg.AfterStop(func() { 94 err := cs.db.Close() 95 if err != nil { 96 cs.log.Println("ERROR: Unable to close consensus set database at shutdown:", err) 97 } 98 }) 99 return nil 100 }