diff --git a/retesteth/session/ToolBackend/ToolChain.cpp b/retesteth/session/ToolBackend/ToolChain.cpp index c2249f58d..cd6d42a86 100644 --- a/retesteth/session/ToolBackend/ToolChain.cpp +++ b/retesteth/session/ToolBackend/ToolChain.cpp @@ -183,7 +183,8 @@ ToolResponse ToolChain::mineBlockOnTool(EthereumBlockState const& _block, SealEn if (tr.getCContent().gasLimit().asU256() <= c_maxGasLimit) // tool fails on limits here. txs.addArrayObject(tr.getCContent().asDataObject(ExportOrder::ToolStyle)); else - ETH_WARNING("Retesteth rejecting tx with gasLimit > 64 bits for tool"); + ETH_WARNING( + "Retesteth rejecting tx with gasLimit > 64 bits for tool" + TestOutputHelper::get().testInfo().errorDebug()); } writeFile(txsPath.string(), txs.asJson()); diff --git a/retesteth/testStructures/types/Ethereum/Transaction.cpp b/retesteth/testStructures/types/Ethereum/Transaction.cpp index 4a435f46e..268a3a39a 100644 --- a/retesteth/testStructures/types/Ethereum/Transaction.cpp +++ b/retesteth/testStructures/types/Ethereum/Transaction.cpp @@ -49,6 +49,7 @@ void Transaction::fromDataObject(DataObject const& _data) throw test::UpwardsException("Incorrect transaction `v` value: " + m_v.getCContent().asString()); m_r = spVALUE(new VALUE(_data.atKey("r"))); m_s = spVALUE(new VALUE(_data.atKey("s"))); + rebuildRLP(); } requireJsonFields(_data, "Transaction " + _data.getKey(), { @@ -109,7 +110,6 @@ Transaction::Transaction(BYTES const& _rlp) fromRLP(rlp); } - void Transaction::streamHeader(dev::RLPStream& _s) const { _s << nonce().asU256(); @@ -141,32 +141,21 @@ void Transaction::buildVRS(VALUE const& _secret) assignV(spVALUE(new VALUE(v))); assignR(spVALUE(new VALUE(r))); assignS(spVALUE(new VALUE(s))); + rebuildRLP(); } void Transaction::assignV(spVALUE const _v) { m_v = _v; } void Transaction::assignR(spVALUE const _r) { m_r = _r; } void Transaction::assignS(spVALUE const _s) { m_s = _s; } -BYTES const Transaction::getSignedRLP() const +BYTES const& Transaction::getSignedRLP() const { - dev::RLPStream sWithSignature; - sWithSignature.appendList(9); - streamHeader(sWithSignature); - sWithSignature << v().asU256().convert_to(); - sWithSignature << r().asU256(); - sWithSignature << s().asU256(); - return BYTES(dev::toHexPrefixed(sWithSignature.out())); + return m_signedRLPdata.getCContent(); } -dev::RLPStream const Transaction::asRLPStream() const +dev::RLPStream const& Transaction::asRLPStream() const { - dev::RLPStream out; - out.appendList(9); - streamHeader(out); - out << v().asU256().convert_to(); - out << r().asU256(); - out << s().asU256(); - return out; + return m_outRlpStream; } const DataObject Transaction::asDataObject(ExportOrder _order) const @@ -202,9 +191,22 @@ const DataObject Transaction::asDataObject(ExportOrder _order) const return out; } -FH32 Transaction::hash() const +FH32 const& Transaction::hash() const { - return FH32("0x" + dev::toString(dev::sha3(asRLPStream().out()))); + return m_hash.getCContent(); +} + +void Transaction::rebuildRLP() +{ + dev::RLPStream out; + out.appendList(9); + streamHeader(out); + out << v().asU256().convert_to(); + out << r().asU256(); + out << s().asU256(); + m_outRlpStream = out; + m_signedRLPdata = spBYTES(new BYTES(dev::toHexPrefixed(out.out()))); + m_hash = spFH32(new FH32("0x" + dev::toString(dev::sha3(out.out())))); } } // namespace teststruct diff --git a/retesteth/testStructures/types/Ethereum/Transaction.h b/retesteth/testStructures/types/Ethereum/Transaction.h index 5e3dc1327..5981c6efe 100644 --- a/retesteth/testStructures/types/Ethereum/Transaction.h +++ b/retesteth/testStructures/types/Ethereum/Transaction.h @@ -36,11 +36,11 @@ struct Transaction : GCP_SPointerBase VALUE const& v() const { return m_v.getCContent(); } VALUE const& r() const { return m_r.getCContent(); } VALUE const& s() const { return m_s.getCContent(); } - virtual FH32 hash() const; + FH32 const& hash() const; virtual TransactionType type() const { return TransactionType::LEGACY; } - virtual BYTES const getSignedRLP() const; - virtual dev::RLPStream const asRLPStream() const; + BYTES const& getSignedRLP() const; + dev::RLPStream const& asRLPStream() const; virtual DataObject const asDataObject(ExportOrder _order = ExportOrder::Default) const; virtual ~Transaction(){}; @@ -76,6 +76,12 @@ struct Transaction : GCP_SPointerBase void assignV(spVALUE const); void assignR(spVALUE const); void assignS(spVALUE const); + + // Optimization + spFH32 m_hash; + dev::RLPStream m_outRlpStream; + spBYTES m_signedRLPdata; + virtual void rebuildRLP(); }; typedef GCP_SPointer spTransaction; diff --git a/retesteth/testStructures/types/Ethereum/TransactionAccessList.cpp b/retesteth/testStructures/types/Ethereum/TransactionAccessList.cpp index c78aa8cdb..5ac2381a6 100644 --- a/retesteth/testStructures/types/Ethereum/TransactionAccessList.cpp +++ b/retesteth/testStructures/types/Ethereum/TransactionAccessList.cpp @@ -18,6 +18,8 @@ TransactionAccessList::TransactionAccessList(DataObject const& _data, string con m_accessList = spAccessList(new AccessList(_data.atKey("accessList"))); if (_data.count("secretKey")) buildVRS(VALUE(_data.atKey("secretKey"))); // Build without v + 27 + else + rebuildRLP(); } TransactionAccessList::TransactionAccessList(dev::RLP const& _rlp) @@ -82,6 +84,7 @@ void TransactionAccessList::buildVRS(VALUE const& _secret) assignV(spVALUE(new VALUE(v))); assignR(spVALUE(new VALUE(r))); assignS(spVALUE(new VALUE(s))); + rebuildRLP(); } void TransactionAccessList::streamHeader(dev::RLPStream& _s) const @@ -106,31 +109,6 @@ void TransactionAccessList::streamHeader(dev::RLPStream& _s) const _s.appendRaw(accessList.out()); } -BYTES const TransactionAccessList::getSignedRLP() const -{ - return BYTES("0x" + dev::toHex(asRLPStream().out())); -} - -dev::RLPStream const TransactionAccessList::asRLPStream() const -{ - // RLP(01 + tr.rlp) - dev::RLPStream wrapper; - dev::RLPStream out; - out.appendList(11); - streamHeader(out); - out << v().asU256().convert_to(); - out << r().asU256(); - out << s().asU256(); - - // Alter output with prefixed 01 byte + tr.rlp - dev::bytes outa = out.out(); - outa.insert(outa.begin(), dev::byte(1)); - - // Encode bytearray into rlp - wrapper << outa; - return wrapper; -} - DataObject const TransactionAccessList::asDataObject(ExportOrder _order) const { DataObject out = Transaction::asDataObject(_order); @@ -146,9 +124,10 @@ DataObject const TransactionAccessList::asDataObject(ExportOrder _order) const return out; } -FH32 TransactionAccessList::hash() const +void TransactionAccessList::rebuildRLP() { - // HASH (01 + tr.rlp) + // RLP(01 + tr.rlp) + dev::RLPStream wrapper; dev::RLPStream out; out.appendList(11); streamHeader(out); @@ -156,9 +135,15 @@ FH32 TransactionAccessList::hash() const out << r().asU256(); out << s().asU256(); - dev::bytes trRLP = out.out(); - trRLP.insert(trRLP.begin(), dev::byte(1)); - return FH32("0x" + dev::toString(dev::sha3(trRLP))); + // Alter output with prefixed 01 byte + tr.rlp + dev::bytes outa = out.out(); + outa.insert(outa.begin(), dev::byte(1)); + + // Encode bytearray into rlp + wrapper << outa; + m_outRlpStream = wrapper; + m_signedRLPdata = spBYTES(new BYTES(dev::toHexPrefixed(m_outRlpStream.out()))); + m_hash = spFH32(new FH32("0x" + dev::toString(dev::sha3(outa)))); } diff --git a/retesteth/testStructures/types/Ethereum/TransactionAccessList.h b/retesteth/testStructures/types/Ethereum/TransactionAccessList.h index 7611d9992..82320a1bc 100644 --- a/retesteth/testStructures/types/Ethereum/TransactionAccessList.h +++ b/retesteth/testStructures/types/Ethereum/TransactionAccessList.h @@ -13,19 +13,16 @@ struct TransactionAccessList : Transaction TransactionAccessList(BYTES const&); TransactionAccessList(dev::RLP const&); - BYTES const getSignedRLP() const override; - dev::RLPStream const asRLPStream() const override; DataObject const asDataObject(ExportOrder _order = ExportOrder::Default) const override; - - FH32 hash() const override; TransactionType type() const override { return TransactionType::ACCESSLIST; } private: - // void fromDataObject(DataObject const&) override; void fromRLP(dev::RLP const&) override; void buildVRS(VALUE const& _secret) override; void streamHeader(dev::RLPStream& _stream) const override; + + void rebuildRLP() override; spAccessList m_accessList; };