github.com/sberex/go-sberex@v1.8.2-0.20181113200658-ed96ac38f7d7/consensus/misc/dao.go (about) 1 // This file is part of the go-sberex library. The go-sberex library is 2 // free software: you can redistribute it and/or modify it under the terms 3 // of the GNU Lesser General Public License as published by the Free 4 // Software Foundation, either version 3 of the License, or (at your option) 5 // any later version. 6 // 7 // The go-sberex library is distributed in the hope that it will be useful, 8 // but WITHOUT ANY WARRANTY; without even the implied warranty of 9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser 10 // General Public License <http://www.gnu.org/licenses/> for more details. 11 12 package misc 13 14 import ( 15 "bytes" 16 "errors" 17 "math/big" 18 19 "github.com/Sberex/go-sberex/core/state" 20 "github.com/Sberex/go-sberex/core/types" 21 "github.com/Sberex/go-sberex/params" 22 ) 23 24 var ( 25 // ErrBadProDAOExtra is returned if a header doens't support the DAO fork on a 26 // pro-fork client. 27 ErrBadProDAOExtra = errors.New("bad DAO pro-fork extra-data") 28 29 // ErrBadNoDAOExtra is returned if a header does support the DAO fork on a no- 30 // fork client. 31 ErrBadNoDAOExtra = errors.New("bad DAO no-fork extra-data") 32 ) 33 34 // VerifyDAOHeaderExtraData validates the extra-data field of a block header to 35 // ensure it conforms to DAO hard-fork rules. 36 // 37 // DAO hard-fork extension to the header validity: 38 // a) if the node is no-fork, do not accept blocks in the [fork, fork+10) range 39 // with the fork specific extra-data set 40 // b) if the node is pro-fork, require blocks in the specific range to have the 41 // unique extra-data set. 42 func VerifyDAOHeaderExtraData(config *params.ChainConfig, header *types.Header) error { 43 // Short circuit validation if the node doesn't care about the DAO fork 44 if config.DAOForkBlock == nil { 45 return nil 46 } 47 // Make sure the block is within the fork's modified extra-data range 48 limit := new(big.Int).Add(config.DAOForkBlock, params.DAOForkExtraRange) 49 if header.Number.Cmp(config.DAOForkBlock) < 0 || header.Number.Cmp(limit) >= 0 { 50 return nil 51 } 52 // Depending on whether we support or oppose the fork, validate the extra-data contents 53 if config.DAOForkSupport { 54 if !bytes.Equal(header.Extra, params.DAOForkBlockExtra) { 55 return ErrBadProDAOExtra 56 } 57 } else { 58 if bytes.Equal(header.Extra, params.DAOForkBlockExtra) { 59 return ErrBadNoDAOExtra 60 } 61 } 62 // All ok, header has the same extra-data we expect 63 return nil 64 } 65 66 // ApplyDAOHardFork modifies the state database according to the DAO hard-fork 67 // rules, transferring all balances of a set of DAO accounts to a single refund 68 // contract. 69 func ApplyDAOHardFork(statedb *state.StateDB) { 70 // Retrieve the contract to refund balances into 71 if !statedb.Exist(params.DAORefundContract) { 72 statedb.CreateAccount(params.DAORefundContract) 73 } 74 75 // Move every DAO account and extra-balance account funds into the refund contract 76 for _, addr := range params.DAODrainList() { 77 statedb.AddBalance(params.DAORefundContract, statedb.GetBalance(addr)) 78 statedb.SetBalance(addr, new(big.Int)) 79 } 80 }