core, cmd/geth: recover by number

This commit is contained in:
Jeffrey Wilcke 2015-07-01 00:52:44 +02:00
parent be935bff84
commit 29ab1fa8a5
2 changed files with 34 additions and 2 deletions

View File

@ -39,6 +39,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/eth" "github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/logger" "github.com/ethereum/go-ethereum/logger"
"github.com/ethereum/go-ethereum/logger/glog"
"github.com/ethereum/go-ethereum/metrics" "github.com/ethereum/go-ethereum/metrics"
"github.com/ethereum/go-ethereum/rpc/codec" "github.com/ethereum/go-ethereum/rpc/codec"
"github.com/ethereum/go-ethereum/rpc/comms" "github.com/ethereum/go-ethereum/rpc/comms"
@ -68,6 +69,15 @@ func init() {
app.Action = run app.Action = run
app.HideVersion = true // we have a command to print the version app.HideVersion = true // we have a command to print the version
app.Commands = []cli.Command{ app.Commands = []cli.Command{
{
Action: blockRecovery,
Name: "recover",
Usage: "attempts to recover a corrupted database by setting a new block head by number",
Description: `
The recover commands will attempt to read out the last
block based on that.
`,
},
blocktestCommand, blocktestCommand,
importCommand, importCommand,
exportCommand, exportCommand,
@ -439,6 +449,20 @@ func unlockAccount(ctx *cli.Context, am *accounts.Manager, account string) (pass
return return
} }
func blockRecovery(ctx *cli.Context) {
num := ctx.Args().First()
if len(ctx.Args()) < 1 {
glog.Fatal("recover requires block number")
}
cfg := utils.MakeEthConfig(ClientIdentifier, nodeNameVersion, ctx)
ethereum, err := eth.New(cfg)
if err != nil {
utils.Fatalf("%v", err)
}
ethereum.ChainManager().Recover(common.String2Big(num).Uint64())
}
func startEth(ctx *cli.Context, eth *eth.Ethereum) { func startEth(ctx *cli.Context, eth *eth.Ethereum) {
// Start Ethereum itself // Start Ethereum itself

View File

@ -238,6 +238,16 @@ func (self *ChainManager) setTransState(statedb *state.StateDB) {
self.transState = statedb self.transState = statedb
} }
func (bc *ChainManager) Recover(num uint64) {
block := bc.GetBlockByNumber(num)
if block != nil {
bc.insert(block)
glog.Infof("Recovery succesful. New HEAD %x\n", block.Hash())
} else {
glog.Fatalln("Recovery failed")
}
}
func (bc *ChainManager) recover() bool { func (bc *ChainManager) recover() bool {
data, _ := bc.blockDb.Get([]byte("checkpoint")) data, _ := bc.blockDb.Get([]byte("checkpoint"))
if len(data) != 0 { if len(data) != 0 {
@ -261,8 +271,6 @@ func (bc *ChainManager) setLastState() {
if len(data) != 0 { if len(data) != 0 {
block := bc.GetBlock(common.BytesToHash(data)) block := bc.GetBlock(common.BytesToHash(data))
if block != nil { if block != nil {
bc.blockDb.Put([]byte("checkpoint"), block.Hash().Bytes())
bc.currentBlock = block bc.currentBlock = block
bc.lastBlockHash = block.Hash() bc.lastBlockHash = block.Hash()
} else { } else {