From 6c72a021d75555efbb9ea650d15fa19c4ddcaa23 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Mon, 6 Jan 2014 19:21:16 +0000 Subject: [PATCH] Repotting and big-picture stuff. --- CMakeLists.txt | 2 +- README.md | 8 ++- eth/main.cpp | 14 ++-- libethereum/BlockChain.cpp | 25 ++++++- libethereum/BlockChain.h | 49 +++++++++++++- libethereum/BlockInfo.cpp | 15 ++++- libethereum/BlockInfo.h | 9 ++- libethereum/Common.cpp | 109 ++++++++++++++++--------------- libethereum/Common.h | 42 ++++++++---- libethereum/Exceptions.h | 1 + libethereum/PeerNetwork.cpp | 21 ++++++ libethereum/PeerNetwork.h | 23 ++++++- libethereum/RLP.h | 16 ++--- libethereum/State.cpp | 50 +++++++++++++- libethereum/State.h | 22 ++----- libethereum/TransactionQueue.cpp | 24 +++++++ libethereum/TransactionQueue.h | 45 +++++++++++++ 17 files changed, 372 insertions(+), 103 deletions(-) create mode 100644 libethereum/TransactionQueue.cpp create mode 100644 libethereum/TransactionQueue.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 27bf9d5e2..00af76d2d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -25,5 +25,5 @@ endif () add_subdirectory(libethereum) add_subdirectory(test) -#add_subdirectory(eth) +add_subdirectory(eth) diff --git a/README.md b/README.md index d3ca6b125..e33799b39 100644 --- a/README.md +++ b/README.md @@ -9,14 +9,16 @@ Gav Wood, 2014. secp256k1 implementation: https://github.com/sipa/secp256k1.git Expects secp256k1 directory to be in same path as cpp-ethereum. -(NOTE: secp256k1 requires a development installation of the GMP library and -apparently libcrypto.) +(NOTE: secp256k1 requires a development installation of the GMP library, libssl and +apparently libcrypto++.) A decent C++11 compiler (I use GNU GCC 4.8.1) and a recent version of Boost (I use version 1.53). CMake, version 2.8 or greater. -sudo apt-get install libgmp3-dev libcrypto++-dev libboost-all-dev cmake +On Ubuntu: + + sudo apt-get install libgmp3-dev libcrypto++-dev libssl-dev libboost-all-dev cmake ## Building diff --git a/eth/main.cpp b/eth/main.cpp index cf1b7d63b..309a4853a 100644 --- a/eth/main.cpp +++ b/eth/main.cpp @@ -32,12 +32,10 @@ int main() Address us; // TODO: should be loaded from config file/set at command-line. BlockChain bc; // TODO: Implement - should look for block database. - + TransactionQueue tq; // TODO: Implement. State s(us); // s.restore(); // TODO: Implement - key optimisation. - TransactionQueue tq; // TODO: Implement. - // Synchronise the state according to the block chain - i.e. replay all transactions, in order. Will take a while if the state isn't restored. s.sync(bc, tq); @@ -48,16 +46,24 @@ int main() net.process(); // Synchronise block chain with network. + // Will broadcast any of our (new) transactions and blocks, and collect & add any of their (new) transactions and blocks. net.sync(bc, tq); // Synchronise state to block chain. - // This should remove any transactions on our queue that are included in the block chain. + // This should remove any transactions on our queue that are included within our state. + // It also guarantees that the state reflects the longest (valid!) chain on the block chain. + // This might mean reverting to an earlier state and replaying some blocks, or, (worst-case: + // if there are no checkpoints before our fork) reverting to the genesis block and replaying + // all blocks. s.sync(bc, tq); // Resynchronise state with block chain & trans + // Mine for a while. if (s.mine(100)) { // Mined block bytes b = s.blockData(); + + // Import block. bc.import(b); } } diff --git a/libethereum/BlockChain.cpp b/libethereum/BlockChain.cpp index 0e1fc3d6d..d249f6f88 100644 --- a/libethereum/BlockChain.cpp +++ b/libethereum/BlockChain.cpp @@ -1,3 +1,24 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file BlockChain.cpp + * @author Gav Wood + * @date 2014 + */ + #include "Common.h" #include "BlockChain.h" using namespace std; @@ -11,4 +32,6 @@ BlockChain::~BlockChain() { } - +void BlockChain::import(bytes const& _block) +{ +} diff --git a/libethereum/BlockChain.h b/libethereum/BlockChain.h index bb568a1e8..d79b7c0b8 100644 --- a/libethereum/BlockChain.h +++ b/libethereum/BlockChain.h @@ -1,3 +1,24 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file BlockChain.h + * @author Gav Wood + * @date 2014 + */ + #pragma once #include "Common.h" @@ -5,6 +26,19 @@ namespace eth { +class MappedBlock +{ +public: + MappedBlock() {} + MappedBlock(u256 _hash) {} // TODO: map memory from disk. + ~MappedBlock() {} // TODO: unmap memory from disk + + bytesConstRef data() const { return bytesConstRef(); } + +private: + // TODO: memory mapping. +}; + /** * @brief Models the blockchain database. */ @@ -14,9 +48,22 @@ public: BlockChain(); ~BlockChain(); - void import(bytes const& _block) {} + /// Import block into disk-backed DB + void import(bytes const& _block); + + /// Get the last block of the longest chain. + bytesConstRef lastBlock() const { return bytesConstRef(); } + + /// Get the number of the last block of the longest chain. + u256 lastBlockNumber() const { return Invalid256; } private: + // Get fully populated from disk DB. + mutable std::map> m_numberAndParent; + mutable std::multimap m_children; + + // Gets populated on demand and reduced after a while. + mutable std::map> m_cache; }; } diff --git a/libethereum/BlockInfo.cpp b/libethereum/BlockInfo.cpp index 1ebc5eb58..e7fec94c4 100644 --- a/libethereum/BlockInfo.cpp +++ b/libethereum/BlockInfo.cpp @@ -27,7 +27,12 @@ using namespace std; using namespace eth; -void BlockInfo::populateAndVerify(bytesConstRef _block, u256 _number) +BlockInfo::BlockInfo() +{ + number = Invalid256; +} + +void BlockInfo::populate(bytesConstRef _block, u256 _number) { number = _number; @@ -48,7 +53,13 @@ void BlockInfo::populateAndVerify(bytesConstRef _block, u256 _number) { throw InvalidBlockFormat(); } +} +void BlockInfo::verify(bytesConstRef _block, u256 _number) +{ + populate(_block, _number); + + RLP root(_block); if (sha256Transactions != sha256(root[1].data())) throw InvalidTransactionsHash(); @@ -59,5 +70,5 @@ void BlockInfo::populateAndVerify(bytesConstRef _block, u256 _number) // TODO: check difficulty against timestamp. // TODO: check proof of work. - // TODO: check each transaction. + // TODO: check each transaction - allow any destination for the miner fees, but everything else must be exactly how we would do it. } diff --git a/libethereum/BlockInfo.h b/libethereum/BlockInfo.h index 815079cea..8455114ea 100644 --- a/libethereum/BlockInfo.h +++ b/libethereum/BlockInfo.h @@ -39,7 +39,14 @@ public: u256 nonce; u256 number; - void populateAndVerify(bytesConstRef _block, u256 _number); + BlockInfo(); + + explicit operator bool() { return number != Invalid256; } + + bool operator==(BlockInfo const& _cmp) const { return hash == _cmp.hash && parentHash == _cmp.parentHash && nonce == _cmp.nonce && number == _cmp.number; } + + void populate(bytesConstRef _block, u256 _number); + void verify(bytesConstRef _block, u256 _number); }; } diff --git a/libethereum/Common.cpp b/libethereum/Common.cpp index a33d650e2..471fcd0ce 100644 --- a/libethereum/Common.cpp +++ b/libethereum/Common.cpp @@ -19,62 +19,13 @@ * @date 2014 */ +#include #include "Common.h" +#include "Exceptions.h" #include "rmd160.h" using namespace std; using namespace eth; -/* collect four bytes into one word: */ -#define BYTES_TO_DWORD(strptr) \ - (((uint32_t) *((strptr)+3) << 24) | \ - ((uint32_t) *((strptr)+2) << 16) | \ - ((uint32_t) *((strptr)+1) << 8) | \ - ((uint32_t) *(strptr))) - -u256 eth::ripemd160(bytesConstRef _message) -/* - * returns RMD(message) - * message should be a string terminated by '\0' - */ -{ - static const uint RMDsize = 160; - uint32_t MDbuf[RMDsize/32]; /* contains (A, B, C, D(, E)) */ - static byte hashcode[RMDsize/8]; /* for final hash-value */ - uint32_t X[16]; /* current 16-word chunk */ - unsigned int i; /* counter */ - uint32_t length; /* length in bytes of message */ - uint32_t nbytes; /* # of bytes not yet processed */ - - /* initialize */ - MDinit(MDbuf); - length = _message.size(); - auto message = _message.data(); - - /* process message in 16-word chunks */ - for (nbytes=length; nbytes > 63; nbytes-=64) { - for (i=0; i<16; i++) { - X[i] = BYTES_TO_DWORD(message); - message += 4; - } - compress(MDbuf, X); - } /* length mod 64 bytes left */ - - /* finish: */ - MDfinish(MDbuf, message, length, 0); - - for (i=0; i>2]; /* implicit cast to byte */ - hashcode[i+1] = (MDbuf[i>>2] >> 8); /* extracts the 8 least */ - hashcode[i+2] = (MDbuf[i>>2] >> 16); /* significant bits. */ - hashcode[i+3] = (MDbuf[i>>2] >> 24); - } - - u256 ret = 0; - for (i = 0; i < RMDsize / 8; ++i) - ret = (ret << 8) | hashcode[i]; - return ret; -} - std::string eth::escaped(std::string const& _s, bool _all) { std::string ret; @@ -108,7 +59,6 @@ std::string eth::randomWord() return ret; } - int eth::fromHex(char _i) { if (_i >= '0' && _i <= '9') @@ -144,3 +94,58 @@ bytes eth::toHex(std::string const& _s) } return ret; } + +// ///////////////////////////////////////////////// +// RIPEMD-160 stuff. Leave well alone. +// ///////////////////////////////////////////////// + +/* collect four bytes into one word: */ +#define BYTES_TO_DWORD(strptr) \ + (((uint32_t) *((strptr)+3) << 24) | \ + ((uint32_t) *((strptr)+2) << 16) | \ + ((uint32_t) *((strptr)+1) << 8) | \ + ((uint32_t) *(strptr))) + +u256 eth::ripemd160(bytesConstRef _message) +/* + * returns RMD(message) + * message should be a string terminated by '\0' + */ +{ + static const uint RMDsize = 160; + uint32_t MDbuf[RMDsize/32]; /* contains (A, B, C, D(, E)) */ + static byte hashcode[RMDsize/8]; /* for final hash-value */ + uint32_t X[16]; /* current 16-word chunk */ + unsigned int i; /* counter */ + uint32_t length; /* length in bytes of message */ + uint32_t nbytes; /* # of bytes not yet processed */ + + /* initialize */ + MDinit(MDbuf); + length = _message.size(); + auto message = _message.data(); + + /* process message in 16-word chunks */ + for (nbytes=length; nbytes > 63; nbytes-=64) { + for (i=0; i<16; i++) { + X[i] = BYTES_TO_DWORD(message); + message += 4; + } + compress(MDbuf, X); + } /* length mod 64 bytes left */ + + /* finish: */ + MDfinish(MDbuf, message, length, 0); + + for (i=0; i>2]; /* implicit cast to byte */ + hashcode[i+1] = (MDbuf[i>>2] >> 8); /* extracts the 8 least */ + hashcode[i+2] = (MDbuf[i>>2] >> 16); /* significant bits. */ + hashcode[i+3] = (MDbuf[i>>2] >> 24); + } + + u256 ret = 0; + for (i = 0; i < RMDsize / 8; ++i) + ret = (ret << 8) | hashcode[i]; + return ret; +} diff --git a/libethereum/Common.h b/libethereum/Common.h index b05df6d72..ae28ff883 100644 --- a/libethereum/Common.h +++ b/libethereum/Common.h @@ -26,7 +26,6 @@ #include #include #include -#include #include #include #include @@ -56,11 +55,24 @@ using StringMap = std::map; using u256Map = std::map; using HexMap = std::map; -template std::string toString(_T const& _t) { std::ostringstream o; o << _t; return o.str(); } +static const u256 Invalid256 = ~(u256)0; +static const bytes NullBytes; -inline std::string asString(bytes const& _b) { return std::string((char const*)_b.data(), (char const*)(_b.data() + _b.size())); } +template +std::string toString(_T const& _t) +{ + std::ostringstream o; + o << _t; + return o.str(); +} -template inline std::string asHex(_T const& _data, int _w = 2) +inline std::string asString(bytes const& _b) +{ + return std::string((char const*)_b.data(), (char const*)(_b.data() + _b.size())); +} + +template +std::string asHex(_T const& _data, int _w = 2) { std::ostringstream ret; for (auto i: _data) @@ -68,21 +80,21 @@ template inline std::string asHex(_T const& _data, int _w = 2) return ret.str(); } -template void trimFront(_T& _t, uint _elements) +template +void trimFront(_T& _t, uint _elements) { memmove(_t.data(), _t.data() + _elements, (_t.size() - _elements) * sizeof(_t[0])); _t.resize(_t.size() - _elements); } -template void pushFront(_T& _t, _U _e) +template +void pushFront(_T& _t, _U _e) { _t.push_back(_e); memmove(_t.data() + 1, _t.data(), (_t.size() - 1) * sizeof(_e)); _t[0] = _e; } -class BadHexCharacter: public std::exception {}; - std::string randomWord(); std::string escaped(std::string const& _s, bool _all = true); int fromHex(char _i); @@ -122,7 +134,8 @@ inline std::string toCompactBigEndianString(_T _val) return ret; } -template uint commonPrefix(_T const& _t, _U const& _u) +template +uint commonPrefix(_T const& _t, _U const& _u) { uint s = std::min(_t.size(), _u.size()); for (uint i = 0;; ++i) @@ -145,7 +158,8 @@ inline u160 as160(_T const& _t) return (u160)(_t & ((((_T)1) << 160) - 1)); } -template inline std::vector<_T>& operator+=(std::vector<_T>& _a, std::vector<_T> const& _b) +template +inline std::vector<_T>& operator+=(std::vector<_T>& _a, std::vector<_T> const& _b) { auto s = _a.size(); _a.resize(_a.size() + _b.size()); @@ -153,6 +167,12 @@ template inline std::vector<_T>& operator+=(std::vector<_T>& _a, std: return _a; } -template inline std::vector<_T> operator+(std::vector<_T> const& _a, std::vector<_T> const& _b) { std::vector<_T> ret(_a); return ret += _b; } + +template +inline std::vector<_T> operator+(std::vector<_T> const& _a, std::vector<_T> const& _b) +{ + std::vector<_T> ret(_a); + return ret += _b; +} } diff --git a/libethereum/Exceptions.h b/libethereum/Exceptions.h index 437ac3d32..7678c2bbf 100644 --- a/libethereum/Exceptions.h +++ b/libethereum/Exceptions.h @@ -6,6 +6,7 @@ namespace eth { +class BadHexCharacter: public std::exception {}; class NotEnoughCash: public std::exception {}; class BadInstruction: public std::exception {}; class StackTooSmall: public std::exception { public: StackTooSmall(u256 _req, u256 _got): req(_req), got(_got) {} u256 req; u256 got; }; diff --git a/libethereum/PeerNetwork.cpp b/libethereum/PeerNetwork.cpp index 6f37e4033..91a930bba 100644 --- a/libethereum/PeerNetwork.cpp +++ b/libethereum/PeerNetwork.cpp @@ -1,3 +1,24 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file PeerNetwork.cpp + * @author Gav Wood + * @date 2014 + */ + #include "Common.h" #include "PeerNetwork.h" using namespace std; diff --git a/libethereum/PeerNetwork.h b/libethereum/PeerNetwork.h index 894cc6db5..9ef847b72 100644 --- a/libethereum/PeerNetwork.h +++ b/libethereum/PeerNetwork.h @@ -1,3 +1,24 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file PeerNetwork.h + * @author Gav Wood + * @date 2014 + */ + #pragma once #include "Common.h" @@ -8,8 +29,6 @@ namespace eth class BlockChain; class TransactionQueue; -static const bytes NullBytes; - class PeerNetwork { public: diff --git a/libethereum/RLP.h b/libethereum/RLP.h index 5d103b5fb..891e767d9 100644 --- a/libethereum/RLP.h +++ b/libethereum/RLP.h @@ -75,28 +75,28 @@ public: bool isNull() const { return m_data.size() == 0; } /// Contains a zero-length string or zero-length list. - bool isEmpty() const { return m_data[0] == 0x40 || m_data[0] == 0x80; } + bool isEmpty() const { return !isNull() && (m_data[0] == 0x40 || m_data[0] == 0x80); } /// String value. - bool isString() const { assert(!isNull()); return m_data[0] >= 0x40 && m_data[0] < 0x80; } + bool isString() const { return !isNull() && m_data[0] >= 0x40 && m_data[0] < 0x80; } /// List value. - bool isList() const { assert(!isNull()); return m_data[0] >= 0x80 && m_data[0] < 0xc0; } + bool isList() const { return !isNull() && m_data[0] >= 0x80 && m_data[0] < 0xc0; } /// Integer value. Either isSlimInt(), isFatInt() or isBigInt(). - bool isInt() const { assert(!isNull()); return m_data[0] < 0x40; } + bool isInt() const { return !isNull() && m_data[0] < 0x40; } /// Fits into eth::uint type. Can use toSlimInt() to read (as well as toFatInt() or toBigInt() ). - bool isSlimInt() const { assert(!isNull()); return m_data[0] < 0x20; } + bool isSlimInt() const { return !isNull() && m_data[0] < 0x20; } /// Fits into eth::u256 or eth::bigint type. Use only toFatInt() or toBigInt() to read. - bool isFatInt() const { assert(!isNull()); return m_data[0] >= 0x20 && m_data[0] < 0x38; } + bool isFatInt() const { return !isNull() && m_data[0] >= 0x20 && m_data[0] < 0x38; } /// Fits into eth::u256 type, though might fit into eth::uint type. - bool isFixedInt() const { assert(!isNull()); return m_data[0] < 0x38; } + bool isFixedInt() const { return !isNull() && m_data[0] < 0x38; } /// Fits only into eth::bigint type. Use only toBigInt() to read. - bool isBigInt() const { assert(!isNull()); return m_data[0] >= 0x38 && m_data[0] < 0x40; } + bool isBigInt() const { return !isNull() && m_data[0] >= 0x38 && m_data[0] < 0x40; } /// @returns the number of items in the list, or zero if it isn't a list. uint itemCount() const { return isList() ? items() : 0; } diff --git a/libethereum/State.cpp b/libethereum/State.cpp index 693c45b9b..8ac0151dc 100644 --- a/libethereum/State.cpp +++ b/libethereum/State.cpp @@ -22,6 +22,7 @@ #include #include #include "Trie.h" +#include "BlockChain.h" #include "Instruction.h" #include "Exceptions.h" #include "sha256.h" @@ -40,6 +41,52 @@ u256 const State::c_txFee = 0; State::State(Address _minerAddress): m_minerAddress(_minerAddress) { secp256k1_start(); + // TODO: Initialise current block/previous block, ready for sync. +} + +void State::sync(BlockChain const& _bc, TransactionQueue const& _tq) +{ + BlockInfo bi; + try + { + bi.verify(_bc.lastBlock(), _bc.lastBlockNumber()); + } + catch (...) + { + cerr << "ERROR: Corrupt block-chain! Delete your block-chain DB and restart." << endl; + exit(1); + } + + if (bi == m_currentBlock) + { + // We mined the last block. + // Our state is good - we just need to move on to next. + m_previousBlock = m_currentBlock; + m_current.clear(); + m_transactions.clear(); + m_currentBlock = BlockInfo(); + m_currentBlock.number = m_previousBlock.number + 1; + } + else if (bi == m_previousBlock) + { + // No change since last sync. + // Carry on as we were. + } + else + { + // New blocks available, or we've switched to a different branch. All change. + // TODO: Find most recent state dump and replay what's left. + // (Most recent state dump might end up being genesis.) + } +} + +bool State::mine(uint _msTimeout) const +{ + // TODO: update timestamp according to clock. + // TODO: update difficulty according to timestamp. + // TODO: look for a nonce that makes a good hash. + // ...but don't take longer than _msTimeout ms. + return false; } bool State::isNormalAddress(Address _address) const @@ -97,7 +144,7 @@ bool State::verify(bytes const& _block, uint _number) BlockInfo bi; try { - bi.populateAndVerify(bytesConstRef((bytes*)&_block), _number); + bi.verify(bytesConstRef((bytes*)&_block), _number); } catch (...) { @@ -109,6 +156,7 @@ bool State::verify(bytes const& _block, uint _number) void State::execute(Transaction const& _t, Address _sender) { // Entry point for a contract-originated transaction. + m_transactions.push_back(_t); if (_t.nonce != transactionsFrom(_sender)) throw InvalidNonce(); diff --git a/libethereum/State.h b/libethereum/State.h index f6d8778d2..d725183af 100644 --- a/libethereum/State.h +++ b/libethereum/State.h @@ -26,6 +26,7 @@ #include #include "Common.h" #include "RLP.h" +#include "TransactionQueue.h" #include "Exceptions.h" #include "BlockInfo.h" #include "AddressState.h" @@ -36,19 +37,6 @@ namespace eth class BlockChain; -// TODO: Repot. -/** - * @brief A queue of Transactions, each stored as RLP. - */ -class TransactionQueue -{ -public: - void sync(BlockChain const& _bc) {} - -private: - std::vector m_data; -}; - /** * @brief Model of the current state of the ledger. * Maintains current ledger (m_current) as a fast hash-map. This is hashed only when required (i.e. to create or verify a block). @@ -67,14 +55,14 @@ public: /// Attempt to find valid nonce for block that this state represents. /// @param _msTimeout Timeout before return in milliseconds. /// @returns true if it got lucky. - bool mine(uint _msTimeout = 1000) const { (void)_msTimeout; return false; } + bool mine(uint _msTimeout = 1000) const; /// Get the complete current block, including valid nonce. - bytes blockData() const { return bytes(); } + bytes const& blockData() const { return m_currentBytes; } /// Sync our state with the block chain. /// This basically involves wiping ourselves if we've been superceded and rebuilding from the transaction queue. - void sync(BlockChain const& _bc, TransactionQueue const& _tq) {} + void sync(BlockChain const& _bc, TransactionQueue const& _tq); /// Execute a given transaction. bool execute(bytes const& _rlp) { try { Transaction t(_rlp); execute(t, t.sender()); } catch (...) { return false; } } @@ -117,6 +105,7 @@ private: }; /// Execute a decoded transaction object, given a sender. + /// This will append @a _t to the transaction list and change the state accordingly. void execute(Transaction const& _t, Address _sender); /// Execute a contract transaction. @@ -129,6 +118,7 @@ private: BlockInfo m_previousBlock; ///< The previous block's information. BlockInfo m_currentBlock; ///< The current block's information. + bytes m_currentBytes; ///< The current block. Address m_minerAddress; ///< Our address (i.e. the address to which fees go). diff --git a/libethereum/TransactionQueue.cpp b/libethereum/TransactionQueue.cpp new file mode 100644 index 000000000..340f5802a --- /dev/null +++ b/libethereum/TransactionQueue.cpp @@ -0,0 +1,24 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file TransactionQueue.cpp + * @author Gav Wood + * @date 2014 + */ + +#include "TransactionQueue.h" +using namespace std; +using namespace eth; diff --git a/libethereum/TransactionQueue.h b/libethereum/TransactionQueue.h new file mode 100644 index 000000000..f76709c42 --- /dev/null +++ b/libethereum/TransactionQueue.h @@ -0,0 +1,45 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Foobar is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Foobar. If not, see . +*/ +/** @file TransactionQueue.h + * @author Gav Wood + * @date 2014 + */ + +#pragma once + +#include "Common.h" + +namespace eth +{ + +class BlockChain; + +/** + * @brief A queue of Transactions, each stored as RLP. + */ +class TransactionQueue +{ +public: + void sync(BlockChain const& _bc) {} + +private: + std::vector m_data; +}; + +} + +