From 46666c845089a109729e705d8cc8bfdca5a184a4 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Sun, 7 Jun 2015 16:15:50 +0900 Subject: [PATCH] Accept alternative nonce. --- eth/main.cpp | 13 +++++++++++++ libethereum/CanonBlockChain.cpp | 26 ++++++++++++++++++++++++-- libethereum/CanonBlockChain.h | 28 +++++++++++++++++----------- libethereum/Client.cpp | 7 +++++-- 4 files changed, 59 insertions(+), 15 deletions(-) diff --git a/eth/main.cpp b/eth/main.cpp index 27e5f4ca0..89b3f058b 100644 --- a/eth/main.cpp +++ b/eth/main.cpp @@ -116,6 +116,7 @@ void help() #endif << " -K,--kill First kill the blockchain." << endl << " -R,--rebuild Rebuild the blockchain from the existing database." << endl + << " --genesis-nonce Set the Genesis Nonce to the given hex nonce." << endl << " -s,--import-secret Import a secret key into the key store and use as the default." << endl << " -S,--import-session-secret Import a secret key into the key store and use as the default for this session only." << endl << " --sign-key
Sign all transactions with the key of the given address." << endl @@ -468,6 +469,18 @@ int main(int argc, char** argv) } else if ((arg == "-d" || arg == "--path" || arg == "--db-path") && i + 1 < argc) dbPath = argv[++i]; + else if (arg == "--genesis-nonce" && i + 1 < argc) + { + try + { + CanonBlockChain::setGenesisNonce(Nonce(argv[++i])); + } + catch (...) + { + cerr << "Bad " << arg << " option: " << argv[i] << endl; + return -1; + } + } /* else if ((arg == "-B" || arg == "--block-fees") && i + 1 < argc) { try diff --git a/libethereum/CanonBlockChain.cpp b/libethereum/CanonBlockChain.cpp index 5dd7dc2ce..4e6d89243 100644 --- a/libethereum/CanonBlockChain.cpp +++ b/libethereum/CanonBlockChain.cpp @@ -72,6 +72,7 @@ std::unordered_map const& dev::eth::genesisState() std::unique_ptr CanonBlockChain::s_genesis; boost::shared_mutex CanonBlockChain::x_genesis; +Nonce CanonBlockChain::s_nonce(u64(42)); bytes CanonBlockChain::createGenesisBlock() { @@ -87,12 +88,33 @@ bytes CanonBlockChain::createGenesisBlock() } block.appendList(15) - << h256() << EmptyListSHA3 << h160() << stateRoot << EmptyTrie << EmptyTrie << LogBloom() << c_genesisDifficulty << 0 << c_genesisGasLimit << 0 << (unsigned)0 << string() << h256() << Nonce(u64(42)); + << h256() << EmptyListSHA3 << h160() << stateRoot << EmptyTrie << EmptyTrie << LogBloom() << c_genesisDifficulty << 0 << c_genesisGasLimit << 0 << (unsigned)0 << string() << h256() << s_nonce; block.appendRaw(RLPEmptyList); block.appendRaw(RLPEmptyList); return block.out(); } -CanonBlockChain::CanonBlockChain(std::string const& _path, WithExisting _we, ProgressCallback const& _pc): BlockChain(CanonBlockChain::createGenesisBlock(), _path, _we, _pc) +CanonBlockChain::CanonBlockChain(std::string const& _path, WithExisting _we, ProgressCallback const& _pc): + BlockChain(createGenesisBlock(), _path, _we, _pc) { } + +void CanonBlockChain::setGenesisNonce(Nonce const& _n) +{ + WriteGuard l(x_genesis); + s_nonce = _n; + s_genesis.reset(); +} + +BlockInfo const& CanonBlockChain::genesis() +{ + UpgradableGuard l(x_genesis); + if (!s_genesis) + { + auto gb = createGenesisBlock(); + UpgradeGuard ul(l); + s_genesis.reset(new BlockInfo); + s_genesis->populate(&gb); + } + return *s_genesis; +} diff --git a/libethereum/CanonBlockChain.h b/libethereum/CanonBlockChain.h index d1d47cd14..d4494c957 100644 --- a/libethereum/CanonBlockChain.h +++ b/libethereum/CanonBlockChain.h @@ -54,21 +54,27 @@ std::unordered_map const& genesisState(); class CanonBlockChain: public BlockChain { public: - CanonBlockChain(WithExisting _we = WithExisting::Trust, ProgressCallback const& _pc = ProgressCallback()): CanonBlockChain(std::string(), _we, _pc) {} - CanonBlockChain(std::string const& _path, WithExisting _we = WithExisting::Trust, ProgressCallback const& _pc = ProgressCallback()); - ~CanonBlockChain() {} + CanonBlockChain(WithExisting _we = WithExisting::Trust, ProgressCallback const& _pc = ProgressCallback()): CanonBlockChain(std::string(), _we, _pc) {} + CanonBlockChain(std::string const& _path, WithExisting _we = WithExisting::Trust, ProgressCallback const& _pc = ProgressCallback()); + ~CanonBlockChain() {} - /// @returns the genesis block header. - static BlockInfo const& genesis() { UpgradableGuard l(x_genesis); if (!s_genesis) { auto gb = createGenesisBlock(); UpgradeGuard ul(l); s_genesis.reset(new BlockInfo); s_genesis->populate(&gb); } return *s_genesis; } + /// @returns the genesis block header. + static BlockInfo const& genesis(); - /// @returns the genesis block as its RLP-encoded byte array. - /// @note This is slow as it's constructed anew each call. Consider genesis() instead. - static bytes createGenesisBlock(); + /// @returns the genesis block as its RLP-encoded byte array. + /// @note This is slow as it's constructed anew each call. Consider genesis() instead. + static bytes createGenesisBlock(); + + /// Alter the value of the genesis block's nonce. + /// @warning Unless you're very careful, make sure you call this right at the start of the + /// program, before anything has had the chance to use this class at all. + static void setGenesisNonce(Nonce const& _n); private: - /// Static genesis info and its lock. - static boost::shared_mutex x_genesis; - static std::unique_ptr s_genesis; + /// Static genesis info and its lock. + static boost::shared_mutex x_genesis; + static std::unique_ptr s_genesis; + static Nonce s_nonce; }; } diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 86b745141..b737f53c9 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -47,8 +47,11 @@ VersionChecker::VersionChecker(string const& _dbPath): (void)protocolVersion; auto minorProtocolVersion = (unsigned)status[1]; auto databaseVersion = (unsigned)status[2]; + h256 ourGenesisHash = CanonBlockChain::genesis().hash(); + auto genesisHash = status.itemCount() > 3 ? (h256)status[3] : ourGenesisHash; + m_action = - databaseVersion != c_databaseVersion ? + databaseVersion != c_databaseVersion || genesisHash != ourGenesisHash ? WithExisting::Kill : minorProtocolVersion != eth::c_minorProtocolVersion ? WithExisting::Verify @@ -73,7 +76,7 @@ void VersionChecker::setOk() { cwarn << "Unhandled exception! Failed to create directory: " << m_path << "\n" << boost::current_exception_diagnostic_information(); } - writeFile(m_path + "/status", rlpList(eth::c_protocolVersion, eth::c_minorProtocolVersion, c_databaseVersion)); + writeFile(m_path + "/status", rlpList(eth::c_protocolVersion, eth::c_minorProtocolVersion, c_databaseVersion, CanonBlockChain::genesis().hash())); } }