From 48562de51c21142d3ec9ef1736d7c3db503e4db3 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 8 Sep 2022 22:21:23 -0300 Subject: [PATCH 01/18] Adding cache support --- rskj-core/src/main/java/co/rsk/RskContext.java | 2 +- .../BlockTxsFieldsValidationRule.java | 9 ++++++++- .../rsk/validators/BlockTxsValidationRule.java | 2 +- .../java/org/ethereum/core/Transaction.java | 18 +++++++++++++----- .../co/rsk/core/bc/BlockValidatorBuilder.java | 3 ++- .../org/ethereum/core/TransactionTest.java | 6 ++++-- 6 files changed, 29 insertions(+), 11 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index dc4c49a1f7d..c3909586bbf 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -1101,7 +1101,7 @@ public synchronized BlockParentDependantValidationRule getBlockParentDependantVa if (blockParentDependantValidationRule == null) { Constants commonConstants = getRskSystemProperties().getNetworkConstants(); blockParentDependantValidationRule = new BlockParentCompositeRule( - new BlockTxsFieldsValidationRule(), + new BlockTxsFieldsValidationRule(getBlockTxSignatureCache()), new BlockTxsValidationRule(getRepositoryLocator(), getBlockTxSignatureCache()), new PrevMinGasPriceRule(), new BlockParentNumberRule(), diff --git a/rskj-core/src/main/java/co/rsk/validators/BlockTxsFieldsValidationRule.java b/rskj-core/src/main/java/co/rsk/validators/BlockTxsFieldsValidationRule.java index 736b5d8554c..9d4656b03d7 100644 --- a/rskj-core/src/main/java/co/rsk/validators/BlockTxsFieldsValidationRule.java +++ b/rskj-core/src/main/java/co/rsk/validators/BlockTxsFieldsValidationRule.java @@ -19,6 +19,7 @@ package co.rsk.validators; import org.ethereum.core.Block; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -31,6 +32,12 @@ public class BlockTxsFieldsValidationRule implements BlockParentDependantValidationRule { private static final Logger logger = LoggerFactory.getLogger("blockvalidator"); + private final SignatureCache signatureCache; + + public BlockTxsFieldsValidationRule(SignatureCache signatureCache) { + this.signatureCache = signatureCache; + } + @Override public boolean isValid(Block block, Block parent) { if (block == null) { @@ -41,7 +48,7 @@ public boolean isValid(Block block, Block parent) { List txs = block.getTransactionsList(); for (Transaction tx : txs) { try { - tx.verify(); + tx.verify(signatureCache); } catch (RuntimeException e) { logger.warn("Unable to verify transaction", e); return false; diff --git a/rskj-core/src/main/java/co/rsk/validators/BlockTxsValidationRule.java b/rskj-core/src/main/java/co/rsk/validators/BlockTxsValidationRule.java index 16ec790f0ca..bf2cb042ae6 100644 --- a/rskj-core/src/main/java/co/rsk/validators/BlockTxsValidationRule.java +++ b/rskj-core/src/main/java/co/rsk/validators/BlockTxsValidationRule.java @@ -74,7 +74,7 @@ public boolean isValid(Block block, Block parent) { for (Transaction tx : txs) { try { - tx.verify(); + tx.verify(signatureCache); } catch (RuntimeException e) { logger.warn("Unable to verify transaction", e); return false; diff --git a/rskj-core/src/main/java/org/ethereum/core/Transaction.java b/rskj-core/src/main/java/org/ethereum/core/Transaction.java index 36096fd7bfa..9de6cbcbcc9 100644 --- a/rskj-core/src/main/java/org/ethereum/core/Transaction.java +++ b/rskj-core/src/main/java/org/ethereum/core/Transaction.java @@ -208,11 +208,11 @@ public long transactionCost(Constants constants, ActivationConfig.ForBlock activ return (this.isContractCreation() ? GasCost.TRANSACTION_CREATE_CONTRACT : GasCost.TRANSACTION) + zeroVals * GasCost.TX_ZERO_DATA + nonZeroes * GasCost.TX_NO_ZERO_DATA; } - public void verify() { - validate(); + public void verify(SignatureCache signatureCache) { + validate(signatureCache); } - private void validate() { + private void validate(SignatureCache signatureCache) { if (getNonce().length > DATAWORD_LENGTH) { throw new RuntimeException("Nonce is not valid"); } @@ -235,7 +235,8 @@ private void validate() { if (BigIntegers.asUnsignedByteArray(signature.getS()).length > DATAWORD_LENGTH) { throw new RuntimeException("Signature S is not valid"); } - if (getSender().getBytes() != null && getSender().getBytes().length != Constants.getMaxAddressByteLength()) { + RskAddress senderAddress = getSender(signatureCache); + if (senderAddress.getBytes() != null && senderAddress.getBytes().length != Constants.getMaxAddressByteLength()) { throw new RuntimeException("Sender is not valid"); } } @@ -371,12 +372,19 @@ public ECKey getKey() { return key; } + /** + * Returns sender's Address + *

+ * Usage of this method should be avoided in favor of getSender(SignatureCache signatureCache) + * as it tries to get the data from the cache first, improving performance. + * + * @return RskAddress the sender's Address + */ public synchronized RskAddress getSender() { if (sender != null) { return sender; } - Metric metric = profiler.start(Profiler.PROFILING_TYPE.KEY_RECOV_FROM_SIG); try { ECKey key = Secp256k1.getInstance().signatureToKey(getRawHash().getBytes(), getSignature()); diff --git a/rskj-core/src/test/java/co/rsk/core/bc/BlockValidatorBuilder.java b/rskj-core/src/test/java/co/rsk/core/bc/BlockValidatorBuilder.java index 06cd21f4fd2..fd0b881a61c 100644 --- a/rskj-core/src/test/java/co/rsk/core/bc/BlockValidatorBuilder.java +++ b/rskj-core/src/test/java/co/rsk/core/bc/BlockValidatorBuilder.java @@ -71,7 +71,8 @@ public BlockValidatorBuilder() { } public BlockValidatorBuilder addBlockTxsFieldsValidationRule() { - this.blockTxsFieldsValidationRule = new BlockTxsFieldsValidationRule(); + this.blockTxsFieldsValidationRule = new BlockTxsFieldsValidationRule( + new BlockTxSignatureCache(new ReceivedTxSignatureCache())); return this; } diff --git a/rskj-core/src/test/java/org/ethereum/core/TransactionTest.java b/rskj-core/src/test/java/org/ethereum/core/TransactionTest.java index bf045a0564b..555038fb408 100644 --- a/rskj-core/src/test/java/org/ethereum/core/TransactionTest.java +++ b/rskj-core/src/test/java/org/ethereum/core/TransactionTest.java @@ -750,6 +750,7 @@ void verifyTx_noSignature() { ECKey ecKey = ECKey.fromPrivate(privKey); byte[] gasPrice = Hex.decode("09184e72a000"); byte[] gas = Hex.decode("4255"); + SignatureCache signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); Transaction tx = Transaction.builder() .gasPrice(gasPrice) @@ -758,7 +759,7 @@ void verifyTx_noSignature() { .value(value) .build(); try { - tx.verify(); + tx.verify(signatureCache); } catch (Exception e) { fail(e.getMessage()); } @@ -772,6 +773,7 @@ void verifyTx_withSignature() { ECKey ecKey = ECKey.fromPrivate(privKey); byte[] gasPrice = Hex.decode("09184e72a000"); byte[] gas = Hex.decode("4255"); + SignatureCache signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); Transaction tx = Transaction.builder() .gasPrice(gasPrice) @@ -781,7 +783,7 @@ void verifyTx_withSignature() { .build(); tx.sign(senderPrivKey); try { - tx.verify(); + tx.verify(signatureCache); } catch (Exception e) { fail(e.getMessage()); } From 264468de9b87ac1391e1de7fcedc887ba245592c Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 15 Sep 2022 10:38:17 -0300 Subject: [PATCH 02/18] Adding signature cache to Mining Module --- .../src/main/java/co/rsk/RskContext.java | 2 +- .../java/co/rsk/core/bc/PendingState.java | 20 +++---- .../co/rsk/core/bc/TransactionPoolImpl.java | 3 +- .../src/main/java/co/rsk/mine/MinerUtils.java | 13 +++-- .../java/org/ethereum/core/Transaction.java | 6 +- .../ethereum/core/TransactionExecutor.java | 24 ++++---- .../src/test/java/co/rsk/TestHelpers/Tx.java | 8 +-- .../java/co/rsk/mine/MainNetMinerTest.java | 28 ++++++--- .../java/co/rsk/mine/MinerManagerTest.java | 8 +-- .../java/co/rsk/mine/MinerServerTest.java | 33 ++++------- .../test/java/co/rsk/mine/MinerUtilsTest.java | 57 +++++++++---------- .../co/rsk/mine/TransactionModuleTest.java | 3 +- .../ethereum/rpc/Web3ImplSnapshotTest.java | 9 +-- 13 files changed, 105 insertions(+), 109 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index c3909586bbf..cd9144b54f9 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -1766,7 +1766,7 @@ private BlockToMineBuilder getBlockToMineBuilder() { getBlockFactory(), getBlockExecutor(), new MinimumGasPriceCalculator(Coin.valueOf(getMiningConfig().getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(getBlockTxSignatureCache()) ); } diff --git a/rskj-core/src/main/java/co/rsk/core/bc/PendingState.java b/rskj-core/src/main/java/co/rsk/core/bc/PendingState.java index 0c794416701..d4ff4529751 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/PendingState.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/PendingState.java @@ -15,17 +15,13 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.core.bc; import co.rsk.core.Coin; import co.rsk.core.RskAddress; import co.rsk.crypto.Keccak256; import co.rsk.db.RepositorySnapshot; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionExecutor; -import org.ethereum.core.TransactionSet; +import org.ethereum.core.*; import org.ethereum.util.ByteUtil; import org.ethereum.vm.DataWord; import org.slf4j.Logger; @@ -46,12 +42,13 @@ public class PendingState implements AccountInformationProvider { private final TransactionExecutorFactory transactionExecutorFactory; private final TransactionSet pendingTransactions; private boolean executed = false; + private final SignatureCache signatureCache; - - public PendingState(RepositorySnapshot repository, TransactionSet pendingTransactions, TransactionExecutorFactory transactionExecutorFactory) { + public PendingState(RepositorySnapshot repository, TransactionSet pendingTransactions, TransactionExecutorFactory transactionExecutorFactory, SignatureCache signatureCache) { this.pendingRepository = repository.startTracking(); this.pendingTransactions = pendingTransactions; this.transactionExecutorFactory = transactionExecutorFactory; + this.signatureCache = signatureCache; } @Override @@ -117,13 +114,13 @@ public BigInteger getNonce(RskAddress addr) { // Note that this sort doesn't return the best solution, it is an approximation algorithm to find approximate // solution. (No trivial solution) - public static List sortByPriceTakingIntoAccountSenderAndNonce(List transactions) { + public static List sortByPriceTakingIntoAccountSenderAndNonce(List transactions, SignatureCache signatureCache) { //Priority heap, and list of transactions are ordered by descending gas price. Comparator gasPriceComparator = reverseOrder(Comparator.comparing(Transaction::getGasPrice)); //First create a map to separate txs by each sender. - Map> senderTxs = transactions.stream().collect(Collectors.groupingBy(Transaction::getSender)); + Map> senderTxs = transactions.stream().collect(Collectors.groupingBy(transaction -> transaction.getSender(signatureCache))); //For each sender, order all txs by nonce and then by hash, //finally we order by price in cases where nonce are equal, and then by hash to disambiguate @@ -151,7 +148,7 @@ public static List sortByPriceTakingIntoAccountSenderAndNonce(List< while (txsCount > 0) { Transaction nextTxToAdd = candidateTxs.remove(); sortedTxs.add(nextTxToAdd); - List txs = senderTxs.get(nextTxToAdd.getSender()); + List txs = senderTxs.get(nextTxToAdd.getSender(signatureCache)); if (!txs.isEmpty()) { Transaction tx = txs.remove(0); candidateTxs.add(tx); @@ -172,8 +169,7 @@ private T postExecutionReturn(PostExecutionAction action) { } private void executeTransactions(Repository currentRepository, List pendingTransactions) { - - PendingState.sortByPriceTakingIntoAccountSenderAndNonce(pendingTransactions) + PendingState.sortByPriceTakingIntoAccountSenderAndNonce(pendingTransactions, signatureCache) .forEach(pendingTransaction -> executeTransaction(currentRepository, pendingTransaction)); } diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index d3e93159a52..a895eb50ca9 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.core.bc; import co.rsk.config.RskSystemProperties; @@ -158,7 +157,7 @@ public PendingState getPendingState() { private PendingState getPendingState(RepositorySnapshot currentRepository) { removeObsoleteTransactions(this.outdatedThreshold, this.outdatedTimeout); - return new PendingState(currentRepository, new TransactionSet(pendingTransactions), (repository, tx) -> transactionExecutorFactory.newInstance(tx, 0, bestBlock.getCoinbase(), repository, createFakePendingBlock(bestBlock), 0)); + return new PendingState(currentRepository, new TransactionSet(pendingTransactions), (repository, tx) -> transactionExecutorFactory.newInstance(tx, 0, bestBlock.getCoinbase(), repository, createFakePendingBlock(bestBlock), 0), signatureCache); } private RepositorySnapshot getCurrentRepository() { diff --git a/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java b/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java index ca2248f8b54..5cda826f833 100644 --- a/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java +++ b/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import co.rsk.bitcoinj.core.BtcTransaction; @@ -32,6 +31,7 @@ import org.bouncycastle.util.Arrays; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.core.TransactionPool; import org.slf4j.Logger; @@ -48,9 +48,14 @@ import java.util.function.Function; public class MinerUtils { - private static final Logger logger = LoggerFactory.getLogger("minerserver"); + private final SignatureCache signatureCache; + + public MinerUtils(SignatureCache signatureCache) { + this.signatureCache = signatureCache; + } + public static co.rsk.bitcoinj.core.BtcTransaction getBitcoinMergedMiningCoinbaseTransaction(co.rsk.bitcoinj.core.NetworkParameters params, MinerWork work) { return getBitcoinMergedMiningCoinbaseTransaction(params, HexUtils.stringHexToByteArray(work.getBlockHashForMergedMining())); } @@ -167,7 +172,7 @@ public List getAllTransactions(TransactionPool tr List txs = transactionPool.getPendingTransactions(); - return PendingState.sortByPriceTakingIntoAccountSenderAndNonce(txs); + return PendingState.sortByPriceTakingIntoAccountSenderAndNonce(txs, signatureCache); } public List filterTransactions(List txsToRemove, List txs, Map accountNonces, RepositorySnapshot originalRepo, Coin minGasPrice, boolean isRskip252Enabled) { @@ -177,7 +182,7 @@ public List filterTransactions(List Keccak256 hash = tx.getHash(); Coin txValue = tx.getValue(); BigInteger txNonce = new BigInteger(1, tx.getNonce()); - RskAddress txSender = tx.getSender(); + RskAddress txSender = tx.getSender(signatureCache); logger.debug("Examining tx={} sender: {} value: {} nonce: {}", hash, txSender, txValue, txNonce); BigInteger expectedNonce; diff --git a/rskj-core/src/main/java/org/ethereum/core/Transaction.java b/rskj-core/src/main/java/org/ethereum/core/Transaction.java index 9de6cbcbcc9..956a313f917 100644 --- a/rskj-core/src/main/java/org/ethereum/core/Transaction.java +++ b/rskj-core/src/main/java/org/ethereum/core/Transaction.java @@ -407,7 +407,11 @@ public synchronized RskAddress getSender(SignatureCache signatureCache) { sender = signatureCache.getSender(this); - return sender; + if (sender != null) { + return sender; + } + + return getSender(); } public byte getChainId() { diff --git a/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java b/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java index fc0e3426b6f..916fedb2370 100644 --- a/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java +++ b/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java @@ -16,7 +16,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.core; import co.rsk.config.VmConfig; @@ -176,7 +175,7 @@ private boolean init() { totalCost = totalCost.add(txGasCost); } - Coin senderBalance = track.getBalance(tx.getSender()); + Coin senderBalance = track.getBalance(tx.getSender(signatureCache)); if (!isCovers(senderBalance, totalCost)) { @@ -229,7 +228,7 @@ private boolean nonceIsValid() { if (isNotEqual(reqNonce, txNonce)) { if (logger.isWarnEnabled()) { - logger.warn("Invalid nonce: sender {}, required: {} , tx.nonce: {}, tx {}", tx.getSender(), reqNonce, txNonce, tx.getHash()); + logger.warn("Invalid nonce: sender {}, required: {} , tx.nonce: {}, tx {}", tx.getSender(signatureCache), reqNonce, txNonce, tx.getHash()); logger.warn("Transaction Data: {}", tx); logger.warn("Tx Included in the following block: {}", this.executionBlock.getShortDescr()); } @@ -270,11 +269,11 @@ private void execute() { if (!localCall) { - track.increaseNonce(tx.getSender()); + track.increaseNonce(tx.getSender(signatureCache)); long txGasLimit = GasCost.toGas(tx.getGasLimit()); Coin txGasCost = tx.getGasPrice().multiply(BigInteger.valueOf(txGasLimit)); - track.addBalance(tx.getSender(), txGasCost.negate()); + track.addBalance(tx.getSender(signatureCache), txGasCost.negate()); logger.trace("Paying: txGasCost: [{}], gasPrice: [{}], gasLimit: [{}]", txGasCost, tx.getGasPrice(), txGasLimit); } @@ -362,7 +361,7 @@ private void call() { if (result.getException() == null) { Coin endowment = tx.getValue(); - cacheTrack.transfer(tx.getSender(), targetAddress, endowment); + cacheTrack.transfer(tx.getSender(signatureCache), targetAddress, endowment); } } @@ -392,7 +391,7 @@ private void create() { } Coin endowment = tx.getValue(); - cacheTrack.transfer(tx.getSender(), newContractAddress, endowment); + cacheTrack.transfer(tx.getSender(signatureCache), newContractAddress, endowment); } private void execError(Throwable err) { @@ -520,8 +519,9 @@ private void finalization() { TransactionExecutionSummary summary = buildTransactionExecutionSummary(summaryBuilder, gasRefund); // Refund for gas leftover - track.addBalance(tx.getSender(), summary.getLeftover().add(summary.getRefund())); - logger.trace("Pay total refund to sender: [{}], refund val: [{}]", tx.getSender(), summary.getRefund()); + RskAddress txSender = tx.getSender(signatureCache); + track.addBalance(txSender, summary.getLeftover().add(summary.getRefund())); + logger.trace("Pay total refund to sender: [{}], refund val: [{}]", txSender, summary.getRefund()); // Transfer fees to miner Coin summaryFee = summary.getFee(); @@ -576,7 +576,9 @@ private void localCallFinalization() { TransactionExecutionSummary summary = buildTransactionExecutionSummary(summaryBuilder, gasRefund); - logger.trace("Pay total refund to sender: [{}], refund val: [{}]", tx.getSender(), summary.getRefund()); + if (logger.isTraceEnabled()) { + logger.trace("Pay total refund to sender: [{}], refund val: [{}]", tx.getSender(signatureCache), summary.getRefund()); + } // Transfer fees to miner this.paidFees = summary.getFee(); @@ -634,7 +636,7 @@ public void extractTrace(ProgramTraceProcessor programTraceProcessor) { programTraceProcessor.processProgramTrace(trace, tx.getHash()); } else { - TransferInvoke invoke = new TransferInvoke(DataWord.valueOf(tx.getSender().getBytes()), DataWord.valueOf(tx.getReceiveAddress().getBytes()), 0L, DataWord.valueOf(tx.getValue().getBytes())); + TransferInvoke invoke = new TransferInvoke(DataWord.valueOf(tx.getSender(signatureCache).getBytes()), DataWord.valueOf(tx.getReceiveAddress().getBytes()), 0L, DataWord.valueOf(tx.getValue().getBytes())); SummarizedProgramTrace trace = new SummarizedProgramTrace(invoke); diff --git a/rskj-core/src/test/java/co/rsk/TestHelpers/Tx.java b/rskj-core/src/test/java/co/rsk/TestHelpers/Tx.java index 87b79e07909..dc51a6d88a9 100644 --- a/rskj-core/src/test/java/co/rsk/TestHelpers/Tx.java +++ b/rskj-core/src/test/java/co/rsk/TestHelpers/Tx.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.TestHelpers; import co.rsk.config.RskSystemProperties; @@ -32,7 +31,6 @@ import static org.mockito.Mockito.any; - public class Tx { public static Transaction create( @@ -60,11 +58,11 @@ public static Transaction create( r.nextBytes(returnReceiveAddressBytes); RskAddress returnReceiveAddress = new RskAddress(returnReceiveAddressBytes); - Mockito.when(transaction.getSender()).thenReturn(returnSender); + Mockito.when(transaction.getSender(any())).thenReturn(returnSender); Mockito.when(transaction.getHash()).thenReturn(new Keccak256(TestUtils.randomBytes(32))); Mockito.when(transaction.acceptTransactionSignature(config.getNetworkConstants().getChainId())).thenReturn(Boolean.TRUE); Mockito.when(transaction.getReceiveAddress()).thenReturn(returnReceiveAddress); - ArrayList bytes = new ArrayList(); + ArrayList bytes = new ArrayList<>(); long amount = 21000; if (data != 0) { data /= 2; @@ -78,7 +76,7 @@ public static Transaction create( } } int n = bytes.size(); - byte b[] = new byte[n]; + byte[] b = new byte[n]; for (int i = 0; i < n; i++) { b[i] = bytes.get(i); } diff --git a/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java b/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java index d91523e757e..3206848620b 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java @@ -1,3 +1,20 @@ +/* + * This file is part of RskJ + * Copyright (C) 2019 RSK Labs Ltd. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package co.rsk.mine; import co.rsk.bitcoinj.core.NetworkParameters; @@ -19,10 +36,7 @@ import co.rsk.validators.ProofOfWorkRule; import org.ethereum.config.Constants; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Genesis; -import org.ethereum.core.ImportResult; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.core.genesis.GenesisLoader; import org.ethereum.db.BlockStore; import org.ethereum.facade.EthereumImpl; @@ -31,11 +45,9 @@ import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; -import org.junit.jupiter.api.io.TempDir; import org.mockito.Mockito; import java.math.BigInteger; -import java.nio.file.Path; import java.time.Clock; import static org.mockito.Mockito.spy; @@ -222,7 +234,7 @@ private BlockToMineBuilder blockToMineBuilder() { blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) ); } -} +} \ No newline at end of file diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java index 9df38b2dfa6..a2e69bc07d6 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import co.rsk.config.ConfigUtils; @@ -31,10 +30,7 @@ import co.rsk.validators.BlockValidationRule; import co.rsk.validators.ProofOfWorkRule; import org.awaitility.Awaitility; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Blockchain; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.db.BlockStore; import org.ethereum.rpc.Simples.SimpleEthereum; import org.ethereum.util.BuildInfo; @@ -291,7 +287,7 @@ private MinerServerImpl getMinerServer() { blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) // TODO -> should it be ReceivedTxSignatureCache? See Miner Server Test for reference ), clock, blockFactory, diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java index 3d69b87e7e9..b2da89000bc 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import static org.hamcrest.CoreMatchers.instanceOf; @@ -34,7 +33,6 @@ import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; - import java.math.BigInteger; import java.nio.ByteBuffer; import java.time.Clock; @@ -43,18 +41,9 @@ import java.util.Collections; import java.util.List; +import co.rsk.core.RskAddress; import org.ethereum.TestUtils; -import org.ethereum.core.Account; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.BlockTxSignatureCache; -import org.ethereum.core.Blockchain; -import org.ethereum.core.Genesis; -import org.ethereum.core.ImportResult; -import org.ethereum.core.ReceivedTxSignatureCache; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.db.BlockStore; import org.ethereum.facade.Ethereum; import org.ethereum.facade.EthereumImpl; @@ -101,7 +90,6 @@ import co.rsk.validators.BlockUnclesValidationRule; import co.rsk.validators.ProofOfWorkRule; - /** * Created by adrian.eidelman on 3/16/2016. */ @@ -118,7 +106,6 @@ public abstract class MinerServerTest { private BlockExecutor blockExecutor; private MinimumGasPriceCalculator minimumGasPriceCalculator; private MinerUtils minerUtils; - private ReceivedTxSignatureCache signatureCache; private Repository repository; private CompositeEthereumListener compositeEthereumListener; private RskTestFactory rskTestContext; @@ -137,7 +124,7 @@ protected RepositoryLocator buildRepositoryLocator() { blockStore = rskTestContext.getBlockStore(); standardBlockchain = rskTestContext.getBlockchain(); repository = repositoryLocator.startTrackingAt(standardBlockchain.getBestBlock().getHeader()); - signatureCache = spy(rskTestContext.getReceivedTxSignatureCache()); + ReceivedTxSignatureCache signatureCache = spy(rskTestContext.getReceivedTxSignatureCache()); compositeEthereumListener = rskTestContext.getCompositeEthereumListener(); transactionPool = new TransactionPoolImpl( rskTestContext.getRskSystemProperties(), @@ -157,7 +144,7 @@ protected RepositoryLocator buildRepositoryLocator() { blockFactory = rskTestContext.getBlockFactory(); blockExecutor = rskTestContext.getBlockExecutor(); minimumGasPriceCalculator = new MinimumGasPriceCalculator(Coin.ZERO); - minerUtils = new MinerUtils(); + minerUtils = new MinerUtils(signatureCache); } @Test @@ -168,15 +155,19 @@ void buildBlockToMineCheckThatLastTransactionIsForREMASC() { when(tx1.getHash()).thenReturn(new Keccak256(s1)); when(tx1.getEncoded()).thenReturn(new byte[32]); + // IMPORTANT: tx1 is a mock, each mock has a random sender set at creation time (Tx.java) + // There's no need of passing a cache here since getSender method is stubbed to always + // return the sender, and we only need to use its value when stubbing track methods. + RskAddress tx1Sender = tx1.getSender(null); + Repository repository = repositoryLocator.startTrackingAt(blockStore.getBestBlock().getHeader()); Repository track = mock(Repository.class); - BlockTxSignatureCache blockTxSignatureCache = mock(BlockTxSignatureCache.class); + Mockito.doReturn(repository.getRoot()).when(track).getRoot(); Mockito.doReturn(repository.getTrie()).when(track).getTrie(); - when(track.getNonce(tx1.getSender())).thenReturn(BigInteger.ZERO); - when(track.getNonce(tx1.getSender(blockTxSignatureCache))).thenReturn(BigInteger.ZERO); + when(track.getNonce(tx1Sender)).thenReturn(BigInteger.ZERO); when(track.getNonce(RemascTransaction.REMASC_ADDRESS)).thenReturn(BigInteger.ZERO); - when(track.getBalance(tx1.getSender())).thenReturn(Coin.valueOf(4200000L)); + when(track.getBalance(tx1Sender)).thenReturn(Coin.valueOf(4200000L)); when(track.getBalance(RemascTransaction.REMASC_ADDRESS)).thenReturn(Coin.valueOf(4200000L)); Mockito.doReturn(track).when(repositoryLocator).startTrackingAt(any()); Mockito.doReturn(track).when(track).startTracking(); diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java index fb5696a8db9..b1a41b1c23e 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import co.rsk.TestHelpers.Tx; @@ -23,9 +22,7 @@ import co.rsk.core.Coin; import co.rsk.core.RskAddress; import co.rsk.crypto.Keccak256; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.util.ByteUtil; import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.BeforeEach; @@ -35,6 +32,8 @@ import java.math.BigInteger; import java.util.*; +import static org.mockito.ArgumentMatchers.any; + class MinerUtilsTest { private static final Coin ONE_COIN = Coin.valueOf(1L); @@ -44,7 +43,7 @@ class MinerUtilsTest { @BeforeEach void setup() { - minerUtils = new MinerUtils(); + minerUtils = new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } @Test @@ -68,8 +67,8 @@ void getAllTransactionsTest() { Mockito.when(tx2.getNonce()).thenReturn(ByteUtil.cloneBytes(BigInteger.TEN.toByteArray())); Mockito.when(tx1.getGasPrice()).thenReturn(Coin.valueOf(1)); Mockito.when(tx2.getGasPrice()).thenReturn(Coin.valueOf(1)); - Mockito.when(tx1.getSender()).thenReturn(new RskAddress(addressBytes)); - Mockito.when(tx2.getSender()).thenReturn(new RskAddress(addressBytes)); + Mockito.when(tx1.getSender(any())).thenReturn(new RskAddress(addressBytes)); // TODO -> Discuss this + Mockito.when(tx2.getSender(any())).thenReturn(new RskAddress(addressBytes)); // TODO -> Discuss this List txs = new LinkedList<>(); @@ -89,9 +88,9 @@ void validTransactionRepositoryNonceTest() { //Mockito.when(tx.checkGasPrice(Mockito.any(BigInteger.class))).thenReturn(true); List txs = new LinkedList<>(); txs.add(tx); - Map accountNounces = new HashMap(); + Map accountNounces = new HashMap<>(); Repository repository = Mockito.mock(Repository.class); - Mockito.when(repository.getNonce(tx.getSender())).thenReturn(BigInteger.valueOf(0)); + Mockito.when(repository.getNonce(tx.getSender(null))).thenReturn(BigInteger.valueOf(0)); List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true); Assertions.assertEquals(1, res.size()); @@ -103,8 +102,8 @@ void validTransactionAccWrapNonceTest() { //Mockito.when(tx.checkGasPrice(Mockito.any(BigInteger.class))).thenReturn(true); List txs = new LinkedList<>(); txs.add(tx); - Map accountNounces = new HashMap(); - accountNounces.put(tx.getSender(), BigInteger.valueOf(0)); + Map accountNounces = new HashMap<>(); + accountNounces.put(tx.getSender(null), BigInteger.valueOf(0)); Repository repository = Mockito.mock(Repository.class); List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true); @@ -116,8 +115,8 @@ void invalidNonceTransactionTest() { Transaction tx = Tx.create(config, 0, 50000, 2, 0, 0, 0); List txs = new LinkedList<>(); txs.add(tx); - Map accountNounces = new HashMap(); - accountNounces.put(tx.getSender(), BigInteger.valueOf(0)); + Map accountNounces = new HashMap<>(); + accountNounces.put(tx.getSender(null), BigInteger.valueOf(0)); Repository repository = Mockito.mock(Repository.class); List txsToRemove = new LinkedList<>(); @@ -131,7 +130,7 @@ void invalidGasPriceTransactionTest() { Transaction tx = Tx.create(config, 0, 50000, 1, 0, 0, 0); List txs = new LinkedList<>(); txs.add(tx); - Map accountNounces = new HashMap(); + Map accountNounces = new HashMap<>(); byte[] addressBytes = ByteUtil.leftPadBytes(BigInteger.valueOf(new Random(0).nextLong()).toByteArray(), 20); accountNounces.put(new RskAddress(addressBytes), BigInteger.valueOf(0)); Repository repository = Mockito.mock(Repository.class); @@ -149,7 +148,7 @@ void harmfulTransactionTest() { List txs = new LinkedList<>(); txs.add(tx); Mockito.when(tx.getGasPrice()).thenReturn(null); - Map accountNounces = new HashMap(); + Map accountNounces = new HashMap<>(); byte[] addressBytes = ByteUtil.leftPadBytes(BigInteger.valueOf(new Random(0).nextLong()).toByteArray(), 20); accountNounces.put(new RskAddress(addressBytes), BigInteger.valueOf(0)); Repository repository = Mockito.mock(Repository.class); @@ -173,8 +172,8 @@ void filterTransactions_whenRskip252DisabledThenTxIncludedRegardlessGasPrice() { txs.add(txLessGasPriceThanCap); txs.add(txMoreGasPriceThanCap); Map accountNounces = new HashMap<>(); - accountNounces.put(txLessGasPriceThanCap.getSender(), BigInteger.ZERO); - accountNounces.put(txMoreGasPriceThanCap.getSender(), BigInteger.ZERO); + accountNounces.put(txLessGasPriceThanCap.getSender(null), BigInteger.ZERO); + accountNounces.put(txMoreGasPriceThanCap.getSender(null), BigInteger.ZERO); Repository repository = Mockito.mock(Repository.class); LinkedList txsToRemove = new LinkedList<>(); @@ -196,8 +195,8 @@ void filterTransactions_whenRskip252EnabledThenTxWithMoreGasPriceThanCapExcluded txs.add(txLessGasPriceThanCap); txs.add(txMoreGasPriceThanCap); Map accountNounces = new HashMap<>(); - accountNounces.put(txLessGasPriceThanCap.getSender(), BigInteger.ZERO); - accountNounces.put(txMoreGasPriceThanCap.getSender(), BigInteger.ZERO); + accountNounces.put(txLessGasPriceThanCap.getSender(null), BigInteger.ZERO); + accountNounces.put(txMoreGasPriceThanCap.getSender(null), BigInteger.ZERO); Repository repository = Mockito.mock(Repository.class); LinkedList txsToRemove = new LinkedList<>(); @@ -224,19 +223,19 @@ void getAllTransactionsCheckOrderTest() { byte[] nonce2 = ByteUtil.cloneBytes(BigInteger.valueOf(2).toByteArray()); byte[] addressBytes = ByteUtil.leftPadBytes(BigInteger.valueOf(new Random(0).nextLong()).toByteArray(), 20); - Mockito.when(tx0.getSender()).thenReturn(new RskAddress(addressBytes)); + Mockito.when(tx0.getSender(any())).thenReturn(new RskAddress(addressBytes)); Mockito.when(tx0.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce0)); Mockito.when(tx0.getGasPrice()).thenReturn(Coin.valueOf(10)); - Mockito.when(tx1.getSender()).thenReturn(new RskAddress(addressBytes)); + Mockito.when(tx1.getSender(any())).thenReturn(new RskAddress(addressBytes)); Mockito.when(tx1.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce0)); Mockito.when(tx1.getGasPrice()).thenReturn(Coin.valueOf(1)); - Mockito.when(tx2.getSender()).thenReturn(new RskAddress(addressBytes)); + Mockito.when(tx2.getSender(any())).thenReturn(new RskAddress(addressBytes)); Mockito.when(tx2.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce1)); Mockito.when(tx2.getGasPrice()).thenReturn(Coin.valueOf(10)); - Mockito.when(tx3.getSender()).thenReturn(new RskAddress(addressBytes)); + Mockito.when(tx3.getSender(any())).thenReturn(new RskAddress(addressBytes)); Mockito.when(tx3.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce2)); Mockito.when(tx3.getGasPrice()).thenReturn(Coin.valueOf(100)); @@ -278,15 +277,15 @@ void getAllTransactionsCheckOrderTest() { Transaction tx6 = Mockito.mock(Transaction.class); byte[] addressBytes2 = ByteUtil.leftPadBytes(BigInteger.valueOf(new Random(100).nextLong()).toByteArray(), 20); - Mockito.when(tx4.getSender()).thenReturn(new RskAddress(addressBytes2)); + Mockito.when(tx4.getSender(any())).thenReturn(new RskAddress(addressBytes2)); Mockito.when(tx4.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce0)); Mockito.when(tx4.getGasPrice()).thenReturn(Coin.valueOf(50)); - Mockito.when(tx5.getSender()).thenReturn(new RskAddress(addressBytes2)); + Mockito.when(tx5.getSender(any())).thenReturn(new RskAddress(addressBytes2)); Mockito.when(tx5.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce1)); Mockito.when(tx5.getGasPrice()).thenReturn(Coin.valueOf(1000)); - Mockito.when(tx6.getSender()).thenReturn(new RskAddress(addressBytes2)); + Mockito.when(tx6.getSender(any())).thenReturn(new RskAddress(addressBytes2)); Mockito.when(tx6.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce2)); Mockito.when(tx6.getGasPrice()).thenReturn(Coin.valueOf(1)); @@ -312,15 +311,15 @@ void getAllTransactionsCheckOrderTest() { Transaction tx9 = Mockito.mock(Transaction.class); byte[] addressBytes3 = ByteUtil.leftPadBytes(BigInteger.valueOf(new Random(1000).nextLong()).toByteArray(), 20); - Mockito.when(tx7.getSender()).thenReturn(new RskAddress(addressBytes3)); + Mockito.when(tx7.getSender(any())).thenReturn(new RskAddress(addressBytes3)); Mockito.when(tx7.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce0)); Mockito.when(tx7.getGasPrice()).thenReturn(Coin.valueOf(500)); - Mockito.when(tx8.getSender()).thenReturn(new RskAddress(addressBytes3)); + Mockito.when(tx8.getSender(any())).thenReturn(new RskAddress(addressBytes3)); Mockito.when(tx8.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce1)); Mockito.when(tx8.getGasPrice()).thenReturn(Coin.valueOf(500)); - Mockito.when(tx9.getSender()).thenReturn(new RskAddress(addressBytes3)); + Mockito.when(tx9.getSender(any())).thenReturn(new RskAddress(addressBytes3)); Mockito.when(tx9.getNonce()).thenReturn(ByteUtil.cloneBytes(nonce2)); Mockito.when(tx9.getGasPrice()).thenReturn(Coin.valueOf(2000)); diff --git a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java index 450bb7c18a9..b1303bb2e04 100644 --- a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import co.rsk.config.ConfigUtils; @@ -608,7 +607,7 @@ private Web3Impl internalCreateEnvironment(Blockchain blockchain, blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) ), minerClock, blockFactory, diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java index 3ccc84b9b89..9345ac6d378 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc; import co.rsk.blockchain.utils.BlockGenerator; @@ -38,9 +37,7 @@ import co.rsk.rpc.modules.txpool.TxPoolModuleImpl; import co.rsk.validators.BlockValidationRule; import co.rsk.validators.ProofOfWorkRule; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Blockchain; +import org.ethereum.core.*; import org.ethereum.rpc.Simples.SimpleEthereum; import org.ethereum.util.BuildInfo; import org.ethereum.util.RskTestFactory; @@ -51,8 +48,6 @@ import java.time.Clock; import java.util.List; -import static org.mockito.Mockito.mock; - /** * Created by ajlopez on 15/04/2017. */ @@ -233,7 +228,7 @@ private MinerServer getMinerServerForTest(SimpleEthereum ethereum, MinerClock cl blockFactory, factory.getBlockExecutor(), new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) ), clock, blockFactory, From 895cfe6fcba2d6027da9b666ac2392c631f07cc2 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 15 Sep 2022 14:14:20 -0300 Subject: [PATCH 03/18] Adding signature cache to TransactionPoolImpl --- .../main/java/co/rsk/core/bc/TransactionPoolImpl.java | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index a895eb50ca9..9fa841b56aa 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -214,7 +214,7 @@ public synchronized List addTransactions(final List tx private Optional getQueuedSuccessor(Transaction tx) { BigInteger next = tx.getNonceAsInteger().add(BigInteger.ONE); - List txsaccount = this.queuedTransactions.getTransactionsWithSender(tx.getSender()); + List txsaccount = this.queuedTransactions.getTransactionsWithSender(tx.getSender(signatureCache)); if (txsaccount == null) { return Optional.empty(); @@ -242,7 +242,7 @@ private TransactionPoolAddResult internalAddTransaction(final Transaction tx) { Keccak256 hash = tx.getHash(); logger.trace("add transaction {} {}", toBI(tx.getNonce()), tx.getHash()); - Optional replacedTx = pendingTransactions.getTransactionsWithSender(tx.getSender()).stream().filter(t -> t.getNonceAsInteger().equals(tx.getNonceAsInteger())).findFirst(); + Optional replacedTx = pendingTransactions.getTransactionsWithSender(tx.getSender(signatureCache)).stream().filter(t -> t.getNonceAsInteger().equals(tx.getNonceAsInteger())).findFirst(); if (replacedTx.isPresent() && !isBumpingGasPriceForSameNonceTx(tx, replacedTx.get())) { return TransactionPoolAddResult.withError("gas price not enough to bump transaction"); } @@ -252,7 +252,7 @@ private TransactionPoolAddResult internalAddTransaction(final Transaction tx) { final long timestampSeconds = this.getCurrentTimeInSeconds(); transactionTimes.put(hash, timestampSeconds); - BigInteger currentNonce = getPendingState(currentRepository).getNonce(tx.getSender()); + BigInteger currentNonce = getPendingState(currentRepository).getNonce(tx.getSender(signatureCache)); BigInteger txNonce = tx.getNonceAsInteger(); if (txNonce.compareTo(currentNonce) > 0) { this.addQueuedTransaction(tx); @@ -463,7 +463,7 @@ private TransactionValidationResult shouldAcceptTx(Transaction tx, RepositorySna * @return whether the sender balance is enough to pay for all pending transactions + newTx */ private boolean senderCanPayPendingTransactionsAndNewTx(Transaction newTx, RepositorySnapshot currentRepository) { - List transactions = pendingTransactions.getTransactionsWithSender(newTx.getSender()); + List transactions = pendingTransactions.getTransactionsWithSender(newTx.getSender(signatureCache)); Coin accumTxCost = Coin.ZERO; for (Transaction t : transactions) { @@ -471,7 +471,7 @@ private boolean senderCanPayPendingTransactionsAndNewTx(Transaction newTx, Repos } Coin costWithNewTx = accumTxCost.add(getTxBaseCost(newTx)); - return costWithNewTx.compareTo(currentRepository.getBalance(newTx.getSender())) <= 0; + return costWithNewTx.compareTo(currentRepository.getBalance(newTx.getSender(signatureCache))) <= 0; } private Coin getTxBaseCost(Transaction tx) { From a4077c2219f97b78226231dd938d548c48c89a0f Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 15 Sep 2022 14:30:25 -0300 Subject: [PATCH 04/18] Adding signature cache to TxPendingValidator --- .../src/main/java/co/rsk/core/bc/TransactionPoolImpl.java | 6 ++++-- .../main/java/co/rsk/net/handler/TxPendingValidator.java | 5 +++-- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index 9fa841b56aa..f978ac40dea 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -19,6 +19,7 @@ import co.rsk.config.RskSystemProperties; import co.rsk.core.Coin; +import co.rsk.core.RskAddress; import co.rsk.core.TransactionExecutorFactory; import co.rsk.crypto.Keccak256; import co.rsk.db.RepositoryLocator; @@ -453,8 +454,9 @@ private Block createFakePendingBlock(Block best) { } private TransactionValidationResult shouldAcceptTx(Transaction tx, RepositorySnapshot currentRepository) { - AccountState state = currentRepository.getAccountState(tx.getSender(signatureCache)); - return validator.isValid(tx, bestBlock, state); + RskAddress txSender = tx.getSender(signatureCache); + AccountState state = currentRepository.getAccountState(txSender); + return validator.isValid(tx, bestBlock, state, txSender); // TODO -> Discuss this, sender is only for logging purposes } /** diff --git a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java index c01e9b8bb4f..6f922d8e558 100644 --- a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java +++ b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java @@ -19,6 +19,7 @@ package co.rsk.net.handler; import co.rsk.core.Coin; +import co.rsk.core.RskAddress; import co.rsk.net.TransactionValidationResult; import co.rsk.net.handler.txvalidator.*; import org.bouncycastle.util.BigIntegers; @@ -65,14 +66,14 @@ public TxPendingValidator(Constants constants, ActivationConfig activationConfig validatorSteps.add(new TxValidatorMaximumGasPriceValidator(activationConfig)); } - public TransactionValidationResult isValid(Transaction tx, Block executionBlock, @Nullable AccountState state) { + public TransactionValidationResult isValid(Transaction tx, Block executionBlock, @Nullable AccountState state, RskAddress sender) { BigInteger blockGasLimit = BigIntegers.fromUnsignedByteArray(executionBlock.getGasLimit()); Coin minimumGasPrice = executionBlock.getMinimumGasPrice(); long bestBlockNumber = executionBlock.getNumber(); long basicTxCost = tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber)); if (state == null && basicTxCost != 0) { - logger.trace("[tx={}, sender={}] account doesn't exist", tx.getHash(), tx.getSender()); + logger.trace("[tx={}, sender={}] account doesn't exist", tx.getHash(), sender); return TransactionValidationResult.withError("the sender account doesn't exist"); } From 10fcc4fe11fc0d63bfde91ce909ef78aad170472 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 15 Sep 2022 18:18:17 -0300 Subject: [PATCH 05/18] Adding signature cache to TxQuota --- rskj-core/src/main/java/co/rsk/RskContext.java | 2 +- .../co/rsk/net/handler/quota/TxQuotaChecker.java | 13 ++++++++----- .../quota/TxQuotaCheckerIntegrationTest.java | 3 +-- .../java/co/rsk/net/handler/quota/TxQuotaTest.java | 1 - 4 files changed, 10 insertions(+), 9 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index cd9144b54f9..75aeea4727d 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -402,7 +402,7 @@ public TxQuotaChecker getTxQuotaChecker() { checkIfNotClosed(); if (this.txQuotaChecker == null) { - this.txQuotaChecker = new TxQuotaChecker(System::currentTimeMillis); + this.txQuotaChecker = new TxQuotaChecker(System::currentTimeMillis, getBlockTxSignatureCache()); } return txQuotaChecker; } diff --git a/rskj-core/src/main/java/co/rsk/net/handler/quota/TxQuotaChecker.java b/rskj-core/src/main/java/co/rsk/net/handler/quota/TxQuotaChecker.java index 581c3791587..bff9690850d 100644 --- a/rskj-core/src/main/java/co/rsk/net/handler/quota/TxQuotaChecker.java +++ b/rskj-core/src/main/java/co/rsk/net/handler/quota/TxQuotaChecker.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.net.handler.quota; import co.rsk.core.RskAddress; @@ -24,6 +23,7 @@ import co.rsk.util.MaxSizeHashMap; import co.rsk.util.TimeProvider; import org.ethereum.core.Block; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.listener.GasPriceTracker; import org.slf4j.Logger; @@ -55,10 +55,13 @@ public class TxQuotaChecker { private final TimeProvider timeProvider; - public TxQuotaChecker(TimeProvider timeProvider) { + private final SignatureCache signatureCache; + + public TxQuotaChecker(TimeProvider timeProvider, SignatureCache signatureCache) { this.accountQuotas = new MaxSizeHashMap<>(MAX_QUOTAS_SIZE, true); this.timeProvider = timeProvider; this.lastBlockGasLimit = UNKNOWN_LAST_BLOCK_GAS_LIMIT; + this.signatureCache = signatureCache; } /** @@ -118,7 +121,7 @@ private void updateReceiverQuotaIfRequired(Transaction newTx, CurrentContext cur } private boolean isFirstTxFromSender(Transaction newTx, CurrentContext currentContext) { - RskAddress senderAddress = newTx.getSender(); + RskAddress senderAddress = newTx.getSender(signatureCache); TxQuota quotaForSender = this.accountQuotas.get(senderAddress); long accountNonce = currentContext.state.getNonce(senderAddress).longValue(); @@ -176,7 +179,7 @@ private TxQuota updateQuota(Transaction newTx, boolean isTxSource, CurrentContex long maxGasPerSecond = getMaxGasPerSecond(blockGasLimit.longValue()); long maxQuota = getMaxQuota(maxGasPerSecond); - RskAddress address = isTxSource ? newTx.getSender() : newTx.getReceiveAddress(); + RskAddress address = isTxSource ? newTx.getSender(signatureCache) : newTx.getReceiveAddress(); TxQuota quotaForAddress = this.accountQuotas.get(address); if (quotaForAddress == null) { @@ -206,7 +209,7 @@ private long getMaxQuota(long maxGasPerSecond) { } private double calculateConsumedVirtualGas(Transaction newTx, @Nullable Transaction replacedTx, CurrentContext currentContext) { - long accountNonce = currentContext.state.getNonce(newTx.getSender()).longValue(); + long accountNonce = currentContext.state.getNonce(newTx.getSender(signatureCache)).longValue(); long blockGasLimit = currentContext.bestBlock.getGasLimitAsInteger().longValue(); long blockMinGasPrice = currentContext.bestBlock.getMinimumGasPrice().asBigInteger().longValue(); diff --git a/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaCheckerIntegrationTest.java b/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaCheckerIntegrationTest.java index 389207fc25b..c5216ec746e 100644 --- a/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaCheckerIntegrationTest.java +++ b/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaCheckerIntegrationTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.net.handler.quota; import co.rsk.core.Coin; @@ -112,7 +111,7 @@ void setUp() { timeProvider = mock(TimeProvider.class); - quotaChecker = new TxQuotaChecker(timeProvider); + quotaChecker = new TxQuotaChecker(timeProvider, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); // 3 items to facilitate testing TestUtils.setInternalState(quotaChecker, "accountQuotas", new MaxSizeHashMap<>(3, true)); diff --git a/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaTest.java b/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaTest.java index 54b5bc6dd5b..b18df2ae260 100644 --- a/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaTest.java +++ b/rskj-core/src/test/java/co/rsk/net/handler/quota/TxQuotaTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.net.handler.quota; import co.rsk.core.RskAddress; From 6183c66f080f94abf26bb4a0b7a4b7a947d0ff3e Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Tue, 20 Sep 2022 21:45:37 -0300 Subject: [PATCH 06/18] Adding signature cache to Trace module related classes --- .../src/main/java/co/rsk/RskContext.java | 3 +- .../rpc/modules/trace/TraceModuleImpl.java | 10 +++- .../modules/trace/TraceModuleImplTest.java | 56 +++++++++---------- 3 files changed, 35 insertions(+), 34 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index 75aeea4727d..aeae7f45879 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -815,7 +815,8 @@ public synchronized TraceModule getTraceModule() { getBlockStore(), getReceiptStore(), getBlockExecutor(), - getExecutionBlockRetriever() + getExecutionBlockRetriever(), + getBlockTxSignatureCache() ); } diff --git a/rskj-core/src/main/java/co/rsk/rpc/modules/trace/TraceModuleImpl.java b/rskj-core/src/main/java/co/rsk/rpc/modules/trace/TraceModuleImpl.java index 02b800781cc..2f0789f8c6f 100644 --- a/rskj-core/src/main/java/co/rsk/rpc/modules/trace/TraceModuleImpl.java +++ b/rskj-core/src/main/java/co/rsk/rpc/modules/trace/TraceModuleImpl.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.rpc.modules.trace; import co.rsk.config.VmConfig; @@ -27,6 +26,7 @@ import com.fasterxml.jackson.databind.ObjectMapper; import org.ethereum.core.Block; import org.ethereum.core.Blockchain; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.core.TransactionReceipt; import org.ethereum.db.BlockStore; @@ -63,17 +63,21 @@ public class TraceModuleImpl implements TraceModule { private final BlockExecutor blockExecutor; private final ExecutionBlockRetriever executionBlockRetriever; + private final SignatureCache signatureCache; + public TraceModuleImpl( Blockchain blockchain, BlockStore blockStore, ReceiptStore receiptStore, BlockExecutor blockExecutor, - ExecutionBlockRetriever executionBlockRetriever) { + ExecutionBlockRetriever executionBlockRetriever, + SignatureCache signatureCache) { this.blockchain = blockchain; this.blockStore = blockStore; this.receiptStore = receiptStore; this.blockExecutor = blockExecutor; this.executionBlockRetriever = executionBlockRetriever; + this.signatureCache = signatureCache; } @Override @@ -232,7 +236,7 @@ private List buildBlockTraces(Block block, TraceFilterRequest if (traceFilterRequest.getFromAddress() != null && !traceFilterRequest.getFromAddress().isEmpty()) { List addresses = traceFilterRequest.getFromAddressAsRskAddresses(); - txStream = txStream.filter(tx -> tx.getSender().getBytes().length > 0 && addresses.contains(tx.getSender())); + txStream = txStream.filter(tx -> tx.getSender(signatureCache).getBytes().length > 0 && addresses.contains(tx.getSender(signatureCache))); } if (traceFilterRequest.getToAddress() != null && !traceFilterRequest.getToAddress().isEmpty()) { diff --git a/rskj-core/src/test/java/co/rsk/rpc/modules/trace/TraceModuleImplTest.java b/rskj-core/src/test/java/co/rsk/rpc/modules/trace/TraceModuleImplTest.java index abe91426011..c9d856f626e 100644 --- a/rskj-core/src/test/java/co/rsk/rpc/modules/trace/TraceModuleImplTest.java +++ b/rskj-core/src/test/java/co/rsk/rpc/modules/trace/TraceModuleImplTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.rpc.modules.trace; import co.rsk.config.GasLimitConfig; @@ -35,10 +34,7 @@ import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.node.ArrayNode; import com.fasterxml.jackson.databind.node.ObjectNode; -import org.ethereum.core.Account; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.datasource.HashMapDB; import org.ethereum.db.ReceiptStore; import org.ethereum.db.ReceiptStoreImpl; @@ -60,7 +56,7 @@ void retrieveUnknownTransactionAsNull() throws Exception { ReceiptStore receiptStore = new ReceiptStoreImpl(new HashMapDB()); World world = new World(receiptStore); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction("0x00"); @@ -72,7 +68,7 @@ void retrieveUnknownBlockAsNull() throws Exception { ReceiptStore receiptStore = new ReceiptStoreImpl(new HashMapDB()); World world = new World(receiptStore); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceBlock("0x0001020300010203000102030001020300010203000102030001020300010203"); @@ -85,7 +81,7 @@ void retrievePendingBlock() throws Exception { World world = executeMultiContract(receiptStore); ExecutionBlockRetriever executionBlockRetriever = createExecutionBlockRetriever(world); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), executionBlockRetriever); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), executionBlockRetriever, world.getBlockTxSignatureCache()); world.getTransactionPool().addTransaction(createSampleTransaction()); @@ -110,7 +106,7 @@ void retrieveSimpleContractCreationTrace() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -144,7 +140,7 @@ void retrieveEmptyContractCreationTrace() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -200,7 +196,7 @@ void getASingleTrace() throws Exception { ReceiptStore receiptStore = new ReceiptStoreImpl(new HashMapDB()); World world = executeMultiContract(receiptStore); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); String transactionHash = "0x64cbd00a73bad9df13ee188931c84555a5662057e6381b3476bdc20ab3c09ef3"; JsonNode result = traceModule.traceGet(transactionHash, Stream.of("0x0").collect(Collectors.toList())); @@ -213,7 +209,7 @@ void getASingleTrace() throws Exception { private static void retrieveEmptyBlockTrace(World world, ReceiptStore receiptStore, String blkname) throws Exception { Block block = world.getBlockByName(blkname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceBlock(block == null ? blkname : block.getHash().toJsonString()); @@ -228,7 +224,7 @@ private static void retrieveEmptyBlockTrace(World world, ReceiptStore receiptSto private static void retrieveNestedContractCreationBlockTrace(World world, ReceiptStore receiptStore, String blkname) throws Exception { Block block = world.getBlockByName(blkname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceBlock(block == null ? blkname : block.getHash().toJsonString()); @@ -260,7 +256,7 @@ private static void retrieveNestedContractCreationBlockTrace(World world, Receip private static void retrieveNestedContractCreationTrace(World world, ReceiptStore receiptStore, String txname) throws Exception { Transaction transaction = world.getTransactionByName(txname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -284,7 +280,7 @@ private static void retrieveNestedContractCreationTrace(World world, ReceiptStor private static void retrieveNestedContractInvocationTrace(World world, ReceiptStore receiptStore, String txname) throws Exception { Transaction transaction = world.getTransactionByName(txname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -308,7 +304,7 @@ private static void retrieveNestedContractInvocationTrace(World world, ReceiptSt private static void retrieveNestedRevertedInvocationTrace(World world, ReceiptStore receiptStore, String txname) throws Exception { Transaction transaction = world.getTransactionByName(txname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -332,7 +328,7 @@ private static void retrieveNestedRevertedInvocationTrace(World world, ReceiptSt private static void retrieveSuicideInvocationTrace(World world, ReceiptStore receiptStore, String txname) throws Exception { Transaction transaction = world.getTransactionByName(txname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -359,7 +355,7 @@ private static void retrieveSuicideInvocationTrace(World world, ReceiptStore rec private static void retrieveSuicideInvocationBlockTrace(World world, ReceiptStore receiptStore, String blkname) throws Exception { Block block = world.getBlockByName(blkname); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceBlock(block == null ? blkname : block.getHash().toJsonString()); @@ -384,7 +380,7 @@ private static void retrieveSuicideInvocationBlockTrace(World world, ReceiptStor } private static void retrieveTraceFilterEmpty(World world, ReceiptStore receiptStore) throws Exception { - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); TraceFilterRequest traceFilterRequest = new TraceFilterRequest(); @@ -404,7 +400,7 @@ private static void retrieveTraceFilterEmpty(World world, ReceiptStore receiptSt private static void retrieveTraceFilterPending(World world, ReceiptStore receiptStore) throws Exception { ExecutionBlockRetriever executionBlockRetriever = createExecutionBlockRetriever(world); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), executionBlockRetriever); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), executionBlockRetriever, world.getBlockTxSignatureCache()); world.getTransactionPool().addTransaction(createSampleTransaction()); @@ -457,7 +453,7 @@ private static ExecutionBlockRetriever createExecutionBlockRetriever(World world new BlockFactory(rskSystemProperties.getActivationConfig()), world.getBlockExecutor(), new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils() + new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) ); return new ExecutionBlockRetriever(world.getBlockChain(), builder, mock(CompositeEthereumListener.class)); @@ -476,7 +472,7 @@ private static Transaction createSampleTransaction() { } private static void retrieveTraceFilter1Record(World world, ReceiptStore receiptStore) throws Exception { - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); TraceFilterRequest traceFilterRequest = new TraceFilterRequest(); @@ -503,7 +499,7 @@ private static void retrieveTraceFilter1Record(World world, ReceiptStore receipt } private static void retrieveTraceFilter3Records(World world, ReceiptStore receiptStore) throws Exception { - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); TraceFilterRequest traceFilterRequest = new TraceFilterRequest(); @@ -540,7 +536,7 @@ private static void retrieveTraceFilter3Records(World world, ReceiptStore receip } private static void retrieveTraceFilterNext3RecordsAndOnly1Remains(World world, ReceiptStore receiptStore) throws Exception { - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); TraceFilterRequest traceFilterRequest = new TraceFilterRequest(); @@ -566,7 +562,7 @@ private static void retrieveTraceFilterNext3RecordsAndOnly1Remains(World world, } private static void retrieveTraceFilterByAddress(World world, ReceiptStore receiptStore) throws Exception { - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); TraceFilterRequest traceFilterRequest = new TraceFilterRequest(); @@ -600,7 +596,7 @@ void retrieveSimpleContractInvocationTrace() throws Exception { Transaction transaction = world.getTransactionByName("tx02"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -629,7 +625,7 @@ void retrieveSimpleAccountTransfer() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -664,7 +660,7 @@ void executeContractWithCall() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -702,7 +698,7 @@ void executeContractWithDelegateCall() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); @@ -734,7 +730,7 @@ void executeContractWithCreate2() throws Exception { Transaction transaction = world.getTransactionByName("tx01"); - TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null); + TraceModuleImpl traceModule = new TraceModuleImpl(world.getBlockChain(), world.getBlockStore(), receiptStore, world.getBlockExecutor(), null, world.getBlockTxSignatureCache()); JsonNode result = traceModule.traceTransaction(transaction.getHash().toJsonString()); From 3a2b311657ea3a2b64145eac6dff09e8b17c802e Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Tue, 20 Sep 2022 22:08:15 -0300 Subject: [PATCH 07/18] Adding signature cache to Tx Pool module related classes --- .../src/main/java/co/rsk/RskContext.java | 2 +- .../rpc/modules/txpool/TxPoolModuleImpl.java | 22 +++++++++---------- .../co/rsk/mine/TransactionModuleTest.java | 2 +- .../modules/txpool/TxPoolModuleImplTest.java | 14 ++++++------ .../org/ethereum/rpc/Web3ImplLogsTest.java | 13 +++++------ .../org/ethereum/rpc/Web3ImplScoringTest.java | 3 ++- .../ethereum/rpc/Web3ImplSnapshotTest.java | 2 +- .../java/org/ethereum/rpc/Web3ImplTest.java | 16 ++++++++++---- 8 files changed, 40 insertions(+), 34 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index aeae7f45879..07576f22c2c 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -837,7 +837,7 @@ public synchronized TxPoolModule getTxPoolModule() { checkIfNotClosed(); if (txPoolModule == null) { - txPoolModule = new TxPoolModuleImpl(getTransactionPool()); + txPoolModule = new TxPoolModuleImpl(getTransactionPool(), getReceivedTxSignatureCache()); } return txPoolModule; diff --git a/rskj-core/src/main/java/co/rsk/rpc/modules/txpool/TxPoolModuleImpl.java b/rskj-core/src/main/java/co/rsk/rpc/modules/txpool/TxPoolModuleImpl.java index 5f46ca1b9e3..28ddbe4ba7e 100644 --- a/rskj-core/src/main/java/co/rsk/rpc/modules/txpool/TxPoolModuleImpl.java +++ b/rskj-core/src/main/java/co/rsk/rpc/modules/txpool/TxPoolModuleImpl.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.rpc.modules.txpool; import java.math.BigInteger; @@ -25,6 +24,7 @@ import java.util.Map; import java.util.function.Function; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.core.TransactionPool; @@ -43,9 +43,12 @@ public class TxPoolModuleImpl implements TxPoolModule { private final JsonNodeFactory jsonNodeFactory; private final TransactionPool transactionPool; - public TxPoolModuleImpl(TransactionPool transactionPool) { + private final SignatureCache signatureCache; + + public TxPoolModuleImpl(TransactionPool transactionPool, SignatureCache signatureCache) { this.transactionPool = transactionPool; jsonNodeFactory = JsonNodeFactory.instance; + this.signatureCache = signatureCache; } /** @@ -62,8 +65,7 @@ public JsonNode content() { Map>> queuedGrouped = groupTransactions(transactionPool.getQueuedTransactions()); contentProps.put(PENDING, serializeTransactions(pendingGrouped, this::fullSerializer)); contentProps.put(QUEUED, serializeTransactions(queuedGrouped, this::fullSerializer)); - JsonNode node = jsonNodeFactory.objectNode().setAll(contentProps); - return node; + return jsonNodeFactory.objectNode().setAll(contentProps); } private JsonNode serializeTransactions( @@ -91,7 +93,7 @@ private JsonNode fullSerializer(Transaction tx) { txNode.putNull("blockNumber"); txNode.putNull("transactionIndex"); - txNode.put("from", HexUtils.toJsonHex(tx.getSender().getBytes())); + txNode.put("from", HexUtils.toJsonHex(tx.getSender(signatureCache).getBytes())); txNode.put("gas", HexUtils.toQuantityJsonHex(tx.getGasLimitAsInteger())); txNode.put("gasPrice", HexUtils.toJsonHex(tx.getGasPrice().getBytes())); txNode.put("hash", HexUtils.toJsonHex(tx.getHash().toHexString())); @@ -115,10 +117,10 @@ private JsonNode summarySerializer(Transaction tx) { private Map>> groupTransactions(List transactions) { Map>> groupedTransactions = new HashMap<>(); for (Transaction tx : transactions){ - Map> txsBySender = groupedTransactions.get(tx.getSender()); + Map> txsBySender = groupedTransactions.get(tx.getSender(signatureCache)); if (txsBySender == null){ txsBySender = new HashMap<>(); - groupedTransactions.put(tx.getSender(), txsBySender); + groupedTransactions.put(tx.getSender(signatureCache), txsBySender); } List txsByNonce = txsBySender.get(tx.getNonceAsInteger()); if (txsByNonce == null){ @@ -146,8 +148,7 @@ public JsonNode inspect() { Map>> queuedGrouped = groupTransactions(transactionPool.getQueuedTransactions()); contentProps.put(PENDING, serializeTransactions(pendingGrouped, this::summarySerializer)); contentProps.put(QUEUED, serializeTransactions(queuedGrouped, this::summarySerializer)); - JsonNode node = jsonNodeFactory.objectNode().setAll(contentProps); - return node; + return jsonNodeFactory.objectNode().setAll(contentProps); } /** @@ -162,7 +163,6 @@ public JsonNode status() { Map txProps = new HashMap<>(); txProps.put(PENDING, jsonNodeFactory.numberNode(transactionPool.getPendingTransactions().size())); txProps.put(QUEUED, jsonNodeFactory.numberNode(transactionPool.getQueuedTransactions().size())); - JsonNode node = jsonNodeFactory.objectNode().setAll(txProps); - return node; + return jsonNodeFactory.objectNode().setAll(txProps); } } \ No newline at end of file diff --git a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java index b1303bb2e04..1709950ba7e 100644 --- a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java @@ -642,7 +642,7 @@ repositoryLocator, new EthModuleWalletEnabled(wallet), transactionModule, config.getActivationConfig()), config.getGasEstimationCap() ); - TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool); + TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool, new ReceivedTxSignatureCache()); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); ChannelManager channelManager = new SimpleChannelManager(); diff --git a/rskj-core/src/test/java/co/rsk/rpc/modules/txpool/TxPoolModuleImplTest.java b/rskj-core/src/test/java/co/rsk/rpc/modules/txpool/TxPoolModuleImplTest.java index de72d2f3f84..9e014cee660 100644 --- a/rskj-core/src/test/java/co/rsk/rpc/modules/txpool/TxPoolModuleImplTest.java +++ b/rskj-core/src/test/java/co/rsk/rpc/modules/txpool/TxPoolModuleImplTest.java @@ -27,9 +27,7 @@ import java.util.List; import java.util.Map; -import org.ethereum.core.Account; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.rpc.Web3Mocks; import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.BeforeEach; @@ -48,12 +46,14 @@ class TxPoolModuleImplTest { private TxPoolModule txPoolModule; private TransactionPool transactionPool; private Map accountMap; + private SignatureCache signatureCache; @BeforeEach - void setup(){ + void setup() { + signatureCache = new ReceivedTxSignatureCache(); transactionPool = Web3Mocks.getMockTransactionPool(); - txPoolModule = new TxPoolModuleImpl(transactionPool); - accountMap = new HashMap(); + txPoolModule = new TxPoolModuleImpl(transactionPool, signatureCache); + accountMap = new HashMap<>(); } private Transaction createSampleTransaction() { @@ -433,4 +433,4 @@ private void assertFullTransaction(Transaction tx, JsonNode transactionNode) { private void assertSummaryTransaction(Transaction tx, JsonNode summaryNode) { Assertions.assertEquals(tx.getReceiveAddress().toString() + ": " + tx.getValue().toString() + " wei + " + tx.getGasLimitAsInteger().toString() + " x " + tx.getGasPrice().toString() + " gas", summaryNode.asText()); } -} +} \ No newline at end of file diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java index 466abd6676f..ca0632f76ec 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java @@ -27,13 +27,7 @@ import java.util.ArrayList; import java.util.List; -import org.ethereum.core.Account; -import org.ethereum.core.Block; -import org.ethereum.core.Blockchain; -import org.ethereum.core.CallTransaction; -import org.ethereum.core.ImportResult; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionPool; +import org.ethereum.core.*; import org.ethereum.datasource.HashMapDB; import org.ethereum.db.BlockStore; import org.ethereum.db.ReceiptStore; @@ -119,6 +113,8 @@ class Web3ImplLogsTest { private TrieStore trieStore; private BlockStore blockStore; + private SignatureCache signatureCache; + //20965255 getValue() //371303c0 inc() @@ -134,6 +130,7 @@ void setUp() { eth = factory.getRsk(); receiptStore = factory.getReceiptStore(); web3 = createWeb3(); + signatureCache = new ReceivedTxSignatureCache(); } @Test @@ -1074,7 +1071,7 @@ null, new EthModuleWalletEnabled(wallet), null, null, config.getNetworkConstants().getBridgeConstants(), config.getActivationConfig()), config.getGasEstimationCap() ); - TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool); + TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool, signatureCache); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); return new Web3RskImpl( eth, diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java index 917d43b16ba..ef6e2f0c1db 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java @@ -38,6 +38,7 @@ import co.rsk.scoring.*; import co.rsk.test.World; import org.ethereum.TestUtils; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.rpc.Simples.SimpleEthereum; import org.ethereum.rpc.exception.RskJsonRpcRequestException; import org.ethereum.util.ByteUtil; @@ -410,7 +411,7 @@ null, new EthModuleWalletEnabled(wallet), null, null, config.getNetworkConstants().getBridgeConstants(), config.getActivationConfig()), config.getGasEstimationCap() ); - TxPoolModule tpm = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool()); + TxPoolModule tpm = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool(), new ReceivedTxSignatureCache()); DebugModule dm = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); return new Web3RskImpl( rsk, diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java index 9345ac6d378..f4bdb099859 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java @@ -167,7 +167,7 @@ private Web3Impl createWeb3(SimpleEthereum ethereum) { ) ); PersonalModule pm = new PersonalModuleWalletDisabled(); - TxPoolModule tpm = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool()); + TxPoolModule tpm = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool(), new ReceivedTxSignatureCache()); DebugModule dm = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); ethereum.blockchain = blockchain; diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java index 46848363cfb..5468a253bbf 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java @@ -84,6 +84,7 @@ import org.ethereum.vm.program.invoke.ProgramInvokeFactoryImpl; import org.hamcrest.MatcherAssert; import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.mockito.MockedStatic; import org.mockito.Mockito; @@ -112,6 +113,13 @@ class Web3ImplTest { private Wallet wallet; + private SignatureCache signatureCache; + + @BeforeEach + public void setup() { + signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); + } + @Test void web3_clientVersion() { Web3 web3 = createWeb3(); @@ -646,7 +654,7 @@ void eth_mining() { RskSystemProperties mockProperties = Web3Mocks.getMockProperties(); MinerClient minerClient = new SimpleMinerClient(); PersonalModule personalModule = new PersonalModuleWalletDisabled(); - TxPoolModule txPoolModule = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool()); + TxPoolModule txPoolModule = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool(), signatureCache); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); Web3 web3 = new Web3Impl( ethMock, @@ -2348,7 +2356,7 @@ null, new EthModuleWalletEnabled(wallet), null, null, config.getNetworkConstants().getBridgeConstants(), config.getActivationConfig()), config.getGasEstimationCap() ); - TxPoolModule txPoolModule = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool()); + TxPoolModule txPoolModule = new TxPoolModuleImpl(Web3Mocks.getMockTransactionPool(), signatureCache); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); MinerClient minerClient = new SimpleMinerClient(); ChannelManager channelManager = new SimpleChannelManager(); @@ -2458,7 +2466,7 @@ private Web3Impl createWeb3( null, config.getNetworkConstants().getBridgeConstants(), config.getActivationConfig()), config.getGasEstimationCap() ); - TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool); + TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool, signatureCache); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); RskModule rskModule = new RskModuleImpl(blockchain, blockStore, receiptStore, retriever); MinerClient minerClient = new SimpleMinerClient(); @@ -2518,7 +2526,7 @@ private Web3Impl createWeb3CallNoReturn( new BridgeSupportFactory( null, config.getNetworkConstants().getBridgeConstants(), config.getActivationConfig()), config.getGasEstimationCap()); - TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool); + TxPoolModule txPoolModule = new TxPoolModuleImpl(transactionPool, signatureCache); DebugModule debugModule = new DebugModuleImpl(null, null, Web3Mocks.getMockMessageHandler(), null, null); RskModule rskModule = new RskModuleImpl(blockchain, blockStore, receiptStore, retriever); MinerClient minerClient = new SimpleMinerClient(); From 555a296467504186405235473ff261559e84eb1c Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Wed, 21 Sep 2022 11:51:10 -0300 Subject: [PATCH 08/18] Updating MinerUtils --- .../src/main/java/co/rsk/RskContext.java | 3 +- .../java/co/rsk/mine/BlockToMineBuilder.java | 10 +++++-- .../src/main/java/co/rsk/mine/MinerUtils.java | 10 ++----- .../co/rsk/mine/BlockToMineBuilderTest.java | 11 ++++---- .../java/co/rsk/mine/MainNetMinerTest.java | 3 +- .../java/co/rsk/mine/MinerManagerTest.java | 3 +- .../java/co/rsk/mine/MinerServerTest.java | 11 +++++--- .../test/java/co/rsk/mine/MinerUtilsTest.java | 28 ++++++++++--------- .../co/rsk/mine/TransactionModuleTest.java | 3 +- .../ethereum/rpc/Web3ImplSnapshotTest.java | 3 +- 10 files changed, 46 insertions(+), 39 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index 07576f22c2c..7fc39edee90 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -1767,7 +1767,8 @@ private BlockToMineBuilder getBlockToMineBuilder() { getBlockFactory(), getBlockExecutor(), new MinimumGasPriceCalculator(Coin.valueOf(getMiningConfig().getMinGasPriceTarget())), - new MinerUtils(getBlockTxSignatureCache()) + new MinerUtils(), + getBlockTxSignatureCache() ); } diff --git a/rskj-core/src/main/java/co/rsk/mine/BlockToMineBuilder.java b/rskj-core/src/main/java/co/rsk/mine/BlockToMineBuilder.java index d887562334a..42b895dd20c 100644 --- a/rskj-core/src/main/java/co/rsk/mine/BlockToMineBuilder.java +++ b/rskj-core/src/main/java/co/rsk/mine/BlockToMineBuilder.java @@ -71,6 +71,8 @@ public class BlockToMineBuilder { private final ForkDetectionDataCalculator forkDetectionDataCalculator; + private final SignatureCache signatureCache; + public BlockToMineBuilder( ActivationConfig activationConfig, MiningConfig miningConfig, @@ -85,7 +87,8 @@ public BlockToMineBuilder( BlockFactory blockFactory, BlockExecutor blockExecutor, MinimumGasPriceCalculator minimumGasPriceCalculator, - MinerUtils minerUtils) { + MinerUtils minerUtils, + SignatureCache signatureCache) { this.activationConfig = Objects.requireNonNull(activationConfig); this.miningConfig = Objects.requireNonNull(miningConfig); this.repositoryLocator = Objects.requireNonNull(repositoryLocator); @@ -100,6 +103,7 @@ public BlockToMineBuilder( this.executor = blockExecutor; this.minimumGasPriceCalculator = minimumGasPriceCalculator; this.minerUtils = minerUtils; + this.signatureCache = signatureCache; } /** @@ -157,7 +161,7 @@ private List getUnclesHeaders(BlockHeader newBlockParentHeader) { private List getTransactions(List txsToRemove, BlockHeader parentHeader, Coin minGasPrice) { logger.debug("getting transactions from pending state"); - List txs = minerUtils.getAllTransactions(transactionPool); + List txs = minerUtils.getAllTransactions(transactionPool, signatureCache); logger.debug("{} transaction(s) collected from pending state", txs.size()); final long blockNumber = parentHeader.getNumber() + 1; @@ -170,7 +174,7 @@ private List getTransactions(List txsToRemove, BlockHe final boolean isRskip252Enabled = activationConfig.isActive(ConsensusRule.RSKIP252, blockNumber); - return minerUtils.filterTransactions(txsToRemove, txs, accountNonces, originalRepo, minGasPrice, isRskip252Enabled); + return minerUtils.filterTransactions(txsToRemove, txs, accountNonces, originalRepo, minGasPrice, isRskip252Enabled, signatureCache); } private void removePendingTransactions(List transactions) { diff --git a/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java b/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java index 5cda826f833..30f7fd0be8e 100644 --- a/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java +++ b/rskj-core/src/main/java/co/rsk/mine/MinerUtils.java @@ -50,12 +50,6 @@ public class MinerUtils { private static final Logger logger = LoggerFactory.getLogger("minerserver"); - private final SignatureCache signatureCache; - - public MinerUtils(SignatureCache signatureCache) { - this.signatureCache = signatureCache; - } - public static co.rsk.bitcoinj.core.BtcTransaction getBitcoinMergedMiningCoinbaseTransaction(co.rsk.bitcoinj.core.NetworkParameters params, MinerWork work) { return getBitcoinMergedMiningCoinbaseTransaction(params, HexUtils.stringHexToByteArray(work.getBlockHashForMergedMining())); } @@ -168,14 +162,14 @@ public static byte[] buildMerkleProof( } } - public List getAllTransactions(TransactionPool transactionPool) { + public List getAllTransactions(TransactionPool transactionPool, SignatureCache signatureCache) { List txs = transactionPool.getPendingTransactions(); return PendingState.sortByPriceTakingIntoAccountSenderAndNonce(txs, signatureCache); } - public List filterTransactions(List txsToRemove, List txs, Map accountNonces, RepositorySnapshot originalRepo, Coin minGasPrice, boolean isRskip252Enabled) { + public List filterTransactions(List txsToRemove, List txs, Map accountNonces, RepositorySnapshot originalRepo, Coin minGasPrice, boolean isRskip252Enabled, SignatureCache signatureCache) { List txsResult = new ArrayList<>(); for (org.ethereum.core.Transaction tx : txs) { try { diff --git a/rskj-core/src/test/java/co/rsk/mine/BlockToMineBuilderTest.java b/rskj-core/src/test/java/co/rsk/mine/BlockToMineBuilderTest.java index 99d523cf7d4..a381fb9e08c 100644 --- a/rskj-core/src/test/java/co/rsk/mine/BlockToMineBuilderTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/BlockToMineBuilderTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.mine; import co.rsk.config.GasLimitConfig; @@ -28,7 +27,6 @@ import co.rsk.core.bc.FamilyUtils; import co.rsk.crypto.Keccak256; import co.rsk.db.RepositoryLocator; -import co.rsk.db.StateRootHandler; import co.rsk.validators.BlockValidationRule; import org.ethereum.TestUtils; import org.ethereum.config.Constants; @@ -68,11 +66,11 @@ void setUp() { validationRules = mock(BlockValidationRule.class); RepositoryLocator repositoryLocator = mock(RepositoryLocator.class); - StateRootHandler stateRootHandler = mock(StateRootHandler.class); MiningConfig miningConfig = mock(MiningConfig.class); DifficultyCalculator difficultyCalculator = mock(DifficultyCalculator.class); MinimumGasPriceCalculator minimumGasPriceCalculator = mock(MinimumGasPriceCalculator.class); MinerUtils minerUtils = mock(MinerUtils.class); + SignatureCache signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); activationConfig = mock(ActivationConfig.class); blockExecutor = mock(BlockExecutor.class); @@ -90,15 +88,16 @@ void setUp() { new BlockFactory(activationConfig), blockExecutor, minimumGasPriceCalculator, - minerUtils + minerUtils, + signatureCache ); BlockDifficulty blockDifficulty = mock(BlockDifficulty.class); Repository snapshot = mock(Repository.class); GasLimitConfig gasLimitConfig = new GasLimitConfig(0,0,false); - when(minerUtils.getAllTransactions(any())).thenReturn(new ArrayList<>()); - when(minerUtils.filterTransactions(any(), any(), any(), any(), any(), anyBoolean())).thenReturn(new ArrayList<>()); + when(minerUtils.getAllTransactions(any(), any())).thenReturn(new ArrayList<>()); + when(minerUtils.filterTransactions(any(), any(), any(), any(), any(), anyBoolean(), any())).thenReturn(new ArrayList<>()); when(repositoryLocator.snapshotAt(any())).thenReturn(snapshot); when(minimumGasPriceCalculator.calculate(any())).thenReturn(mock(Coin.class)); when(miningConfig.getGasLimit()).thenReturn(gasLimitConfig); diff --git a/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java b/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java index 3206848620b..27e95284af2 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MainNetMinerTest.java @@ -234,7 +234,8 @@ private BlockToMineBuilder blockToMineBuilder() { blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) + new MinerUtils(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); } } \ No newline at end of file diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java index a2e69bc07d6..527736e0976 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerManagerTest.java @@ -287,7 +287,8 @@ private MinerServerImpl getMinerServer() { blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) // TODO -> should it be ReceivedTxSignatureCache? See Miner Server Test for reference + new MinerUtils(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) // TODO -> should it be ReceivedTxSignatureCache? See Miner Server Test for reference ), clock, blockFactory, diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java index b2da89000bc..af1f8351d3d 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerServerTest.java @@ -108,6 +108,7 @@ public abstract class MinerServerTest { private MinerUtils minerUtils; private Repository repository; private CompositeEthereumListener compositeEthereumListener; + private SignatureCache signatureCache; private RskTestFactory rskTestContext; protected void setUp(TestSystemProperties config) { @@ -124,7 +125,7 @@ protected RepositoryLocator buildRepositoryLocator() { blockStore = rskTestContext.getBlockStore(); standardBlockchain = rskTestContext.getBlockchain(); repository = repositoryLocator.startTrackingAt(standardBlockchain.getBestBlock().getHeader()); - ReceivedTxSignatureCache signatureCache = spy(rskTestContext.getReceivedTxSignatureCache()); + signatureCache = spy(rskTestContext.getReceivedTxSignatureCache()); compositeEthereumListener = rskTestContext.getCompositeEthereumListener(); transactionPool = new TransactionPoolImpl( rskTestContext.getRskSystemProperties(), @@ -144,7 +145,7 @@ protected RepositoryLocator buildRepositoryLocator() { blockFactory = rskTestContext.getBlockFactory(); blockExecutor = rskTestContext.getBlockExecutor(); minimumGasPriceCalculator = new MinimumGasPriceCalculator(Coin.ZERO); - minerUtils = new MinerUtils(signatureCache); + minerUtils = new MinerUtils(); } @Test @@ -865,7 +866,8 @@ private MinerServer makeMinerServer(Ethereum ethereum, BlockProcessor blockProce blockFactory, blockExecutor, minimumGasPriceCalculator, - minerUtils + minerUtils, + signatureCache ), clock, blockFactory, @@ -897,7 +899,8 @@ private MinerServer makeMinerServer(Ethereum ethereum, BlockUnclesValidationRule blockFactory, blockExecutor, minimumGasPriceCalculator, - minerUtils + minerUtils, + signatureCache ), clock, blockFactory, diff --git a/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java b/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java index b1a41b1c23e..16482a1231a 100644 --- a/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/MinerUtilsTest.java @@ -40,10 +40,12 @@ class MinerUtilsTest { private final TestSystemProperties config = new TestSystemProperties(); private MinerUtils minerUtils; + private SignatureCache signatureCache; @BeforeEach void setup() { - minerUtils = new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())); + signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); + minerUtils = new MinerUtils(); } @Test @@ -77,7 +79,7 @@ void getAllTransactionsTest() { Mockito.when(transactionPool.getPendingTransactions()).thenReturn(txs); - List res = minerUtils.getAllTransactions(transactionPool); + List res = minerUtils.getAllTransactions(transactionPool, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertEquals(2, res.size()); } @@ -92,7 +94,7 @@ void validTransactionRepositoryNonceTest() { Repository repository = Mockito.mock(Repository.class); Mockito.when(repository.getNonce(tx.getSender(null))).thenReturn(BigInteger.valueOf(0)); - List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true); + List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true, signatureCache); Assertions.assertEquals(1, res.size()); } @@ -106,7 +108,7 @@ void validTransactionAccWrapNonceTest() { accountNounces.put(tx.getSender(null), BigInteger.valueOf(0)); Repository repository = Mockito.mock(Repository.class); - List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true); + List res = minerUtils.filterTransactions(new LinkedList<>(), txs, accountNounces, repository, ONE_COIN, true, signatureCache); Assertions.assertEquals(1, res.size()); } @@ -120,7 +122,7 @@ void invalidNonceTransactionTest() { Repository repository = Mockito.mock(Repository.class); List txsToRemove = new LinkedList<>(); - List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, ONE_COIN, true); + List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, ONE_COIN, true, signatureCache); Assertions.assertEquals(0, res.size()); Assertions.assertEquals(0, txsToRemove.size()); } @@ -137,7 +139,7 @@ void invalidGasPriceTransactionTest() { Coin minGasPrice = Coin.valueOf(2L); LinkedList txsToRemove = new LinkedList<>(); - List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true); + List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true, signatureCache); Assertions.assertEquals(0, res.size()); Assertions.assertEquals(1, txsToRemove.size()); } @@ -155,7 +157,7 @@ void harmfulTransactionTest() { Coin minGasPrice = Coin.valueOf(2L); LinkedList txsToRemove = new LinkedList<>(); - List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true); + List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true, signatureCache); Assertions.assertEquals(0, res.size()); Assertions.assertEquals(1, txsToRemove.size()); } @@ -177,7 +179,7 @@ void filterTransactions_whenRskip252DisabledThenTxIncludedRegardlessGasPrice() { Repository repository = Mockito.mock(Repository.class); LinkedList txsToRemove = new LinkedList<>(); - List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, false); + List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, false, signatureCache); Assertions.assertEquals(2, res.size()); Assertions.assertEquals(0, txsToRemove.size()); @@ -200,7 +202,7 @@ void filterTransactions_whenRskip252EnabledThenTxWithMoreGasPriceThanCapExcluded Repository repository = Mockito.mock(Repository.class); LinkedList txsToRemove = new LinkedList<>(); - List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true); + List res = minerUtils.filterTransactions(txsToRemove, txs, accountNounces, repository, minGasPrice, true, signatureCache); Assertions.assertEquals(1, res.size()); Assertions.assertEquals(txLessGasPriceThanCap, res.get(0)); @@ -247,7 +249,7 @@ void getAllTransactionsCheckOrderTest() { Mockito.when(transactionPool.getPendingTransactions()).thenReturn(txs); - List res = minerUtils.getAllTransactions(transactionPool); + List res = minerUtils.getAllTransactions(transactionPool, signatureCache); Assertions.assertEquals(2, res.size()); Assertions.assertEquals(res.get(0).getGasPrice(), Coin.valueOf(10)); @@ -261,7 +263,7 @@ void getAllTransactionsCheckOrderTest() { Mockito.when(transactionPool.getPendingTransactions()).thenReturn(txs); - res = minerUtils.getAllTransactions(transactionPool); + res = minerUtils.getAllTransactions(transactionPool, signatureCache); Assertions.assertEquals(3, res.size()); Assertions.assertEquals(res.get(0).getNonce(), tx1.getNonce()); @@ -296,7 +298,7 @@ void getAllTransactionsCheckOrderTest() { Mockito.when(transactionPool.getPendingTransactions()).thenReturn(txs); - res = minerUtils.getAllTransactions(transactionPool); + res = minerUtils.getAllTransactions(transactionPool, signatureCache); Assertions.assertEquals(6, res.size()); Assertions.assertEquals(res.get(0).getGasPrice(), Coin.valueOf(50)); @@ -329,7 +331,7 @@ void getAllTransactionsCheckOrderTest() { Mockito.when(transactionPool.getPendingTransactions()).thenReturn(txs); - res = minerUtils.getAllTransactions(transactionPool); + res = minerUtils.getAllTransactions(transactionPool, signatureCache); Assertions.assertEquals(9, res.size()); Assertions.assertEquals(res.get(0).getGasPrice(), Coin.valueOf(500)); diff --git a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java index 1709950ba7e..a6f0060a297 100644 --- a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java @@ -607,7 +607,8 @@ private Web3Impl internalCreateEnvironment(Blockchain blockchain, blockFactory, blockExecutor, new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) + new MinerUtils(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ), minerClock, blockFactory, diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java index f4bdb099859..2314d125954 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java @@ -228,7 +228,8 @@ private MinerServer getMinerServerForTest(SimpleEthereum ethereum, MinerClock cl blockFactory, factory.getBlockExecutor(), new MinimumGasPriceCalculator(Coin.valueOf(miningConfig.getMinGasPriceTarget())), - new MinerUtils(new BlockTxSignatureCache(new ReceivedTxSignatureCache())) + new MinerUtils(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ), clock, blockFactory, From ad3d0f553ab7cb6da79305ba5f1f70d8c296d6af Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Wed, 21 Sep 2022 13:07:53 -0300 Subject: [PATCH 09/18] Updating TxPendingValidator --- .../java/co/rsk/core/bc/TransactionPoolImpl.java | 7 ++----- .../java/co/rsk/net/handler/TxPendingValidator.java | 12 +++++++----- 2 files changed, 9 insertions(+), 10 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index f978ac40dea..0dd33e643e2 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -19,7 +19,6 @@ import co.rsk.config.RskSystemProperties; import co.rsk.core.Coin; -import co.rsk.core.RskAddress; import co.rsk.core.TransactionExecutorFactory; import co.rsk.crypto.Keccak256; import co.rsk.db.RepositoryLocator; @@ -95,7 +94,7 @@ public TransactionPoolImpl(RskSystemProperties config, RepositoryLocator reposit this.quotaChecker = txQuotaChecker; this.gasPriceTracker = gasPriceTracker; - this.validator = new TxPendingValidator(config.getNetworkConstants(), config.getActivationConfig(), config.getNumOfAccountSlots()); + this.validator = new TxPendingValidator(config.getNetworkConstants(), config.getActivationConfig(), config.getNumOfAccountSlots(), signatureCache); if (this.outdatedTimeout > 0) { this.cleanerTimer = Executors.newSingleThreadScheduledExecutor(r -> new Thread(r, "TransactionPoolCleanerTimer")); @@ -454,9 +453,7 @@ private Block createFakePendingBlock(Block best) { } private TransactionValidationResult shouldAcceptTx(Transaction tx, RepositorySnapshot currentRepository) { - RskAddress txSender = tx.getSender(signatureCache); - AccountState state = currentRepository.getAccountState(txSender); - return validator.isValid(tx, bestBlock, state, txSender); // TODO -> Discuss this, sender is only for logging purposes + return validator.isValid(tx, bestBlock, currentRepository.getAccountState(tx.getSender(signatureCache))); } /** diff --git a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java index 6f922d8e558..1a67e859865 100644 --- a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java +++ b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java @@ -15,11 +15,9 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.net.handler; import co.rsk.core.Coin; -import co.rsk.core.RskAddress; import co.rsk.net.TransactionValidationResult; import co.rsk.net.handler.txvalidator.*; import org.bouncycastle.util.BigIntegers; @@ -27,6 +25,7 @@ import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.core.AccountState; import org.ethereum.core.Block; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -51,9 +50,12 @@ public class TxPendingValidator { private final Constants constants; private final ActivationConfig activationConfig; - public TxPendingValidator(Constants constants, ActivationConfig activationConfig, int accountSlots) { + private final SignatureCache signatureCache; + + public TxPendingValidator(Constants constants, ActivationConfig activationConfig, int accountSlots, SignatureCache signatureCache) { this.constants = constants; this.activationConfig = activationConfig; + this.signatureCache = signatureCache; validatorSteps.add(new TxNotNullValidator()); validatorSteps.add(new TxValidatorNotRemascTxValidator()); @@ -66,14 +68,14 @@ public TxPendingValidator(Constants constants, ActivationConfig activationConfig validatorSteps.add(new TxValidatorMaximumGasPriceValidator(activationConfig)); } - public TransactionValidationResult isValid(Transaction tx, Block executionBlock, @Nullable AccountState state, RskAddress sender) { + public TransactionValidationResult isValid(Transaction tx, Block executionBlock, @Nullable AccountState state) { BigInteger blockGasLimit = BigIntegers.fromUnsignedByteArray(executionBlock.getGasLimit()); Coin minimumGasPrice = executionBlock.getMinimumGasPrice(); long bestBlockNumber = executionBlock.getNumber(); long basicTxCost = tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber)); if (state == null && basicTxCost != 0) { - logger.trace("[tx={}, sender={}] account doesn't exist", tx.getHash(), sender); + logger.trace("[tx={}, sender={}] account doesn't exist", tx.getHash(), tx.getSender(signatureCache)); return TransactionValidationResult.withError("the sender account doesn't exist"); } From fecacc0ac9e18ca44871ab218c5e1ee1fc417836 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 22 Sep 2022 21:43:16 -0300 Subject: [PATCH 10/18] Adding signature cache to transaction set --- .../co/rsk/core/bc/TransactionPoolImpl.java | 9 ++++--- .../org/ethereum/core/TransactionSet.java | 18 +++++++------ .../org/ethereum/core/TransactionSetTest.java | 27 ++++++++++++------- 3 files changed, 33 insertions(+), 21 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index 0dd33e643e2..047cf2ef547 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -51,8 +51,8 @@ public class TransactionPoolImpl implements TransactionPool { private static final Logger logger = LoggerFactory.getLogger("txpool"); - private final TransactionSet pendingTransactions = new TransactionSet(); - private final TransactionSet queuedTransactions = new TransactionSet(); + private final TransactionSet pendingTransactions; + private final TransactionSet queuedTransactions; private final Map transactionBlocks = new HashMap<>(); private final Map transactionTimes = new HashMap<>(); @@ -94,6 +94,9 @@ public TransactionPoolImpl(RskSystemProperties config, RepositoryLocator reposit this.quotaChecker = txQuotaChecker; this.gasPriceTracker = gasPriceTracker; + pendingTransactions = new TransactionSet(this.signatureCache); + queuedTransactions = new TransactionSet(this.signatureCache); + this.validator = new TxPendingValidator(config.getNetworkConstants(), config.getActivationConfig(), config.getNumOfAccountSlots(), signatureCache); if (this.outdatedTimeout > 0) { @@ -157,7 +160,7 @@ public PendingState getPendingState() { private PendingState getPendingState(RepositorySnapshot currentRepository) { removeObsoleteTransactions(this.outdatedThreshold, this.outdatedTimeout); - return new PendingState(currentRepository, new TransactionSet(pendingTransactions), (repository, tx) -> transactionExecutorFactory.newInstance(tx, 0, bestBlock.getCoinbase(), repository, createFakePendingBlock(bestBlock), 0), signatureCache); + return new PendingState(currentRepository, new TransactionSet(pendingTransactions, signatureCache), (repository, tx) -> transactionExecutorFactory.newInstance(tx, 0, bestBlock.getCoinbase(), repository, createFakePendingBlock(bestBlock), 0), signatureCache); } private RepositorySnapshot getCurrentRepository() { diff --git a/rskj-core/src/main/java/org/ethereum/core/TransactionSet.java b/rskj-core/src/main/java/org/ethereum/core/TransactionSet.java index 913ac95024b..ed367e935d0 100644 --- a/rskj-core/src/main/java/org/ethereum/core/TransactionSet.java +++ b/rskj-core/src/main/java/org/ethereum/core/TransactionSet.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.core; import co.rsk.core.RskAddress; @@ -28,17 +27,20 @@ public class TransactionSet { private final Map transactionsByHash; private final Map> transactionsByAddress; - public TransactionSet() { - this(new HashMap<>(), new HashMap<>()); + private final SignatureCache signatureCache; + + public TransactionSet(SignatureCache signatureCache) { + this(new HashMap<>(), new HashMap<>(), signatureCache); } - public TransactionSet(TransactionSet transactionSet) { - this(new HashMap<>(transactionSet.transactionsByHash), new HashMap<>(transactionSet.transactionsByAddress)); + public TransactionSet(TransactionSet transactionSet, SignatureCache signatureCache) { + this(new HashMap<>(transactionSet.transactionsByHash), new HashMap<>(transactionSet.transactionsByAddress), signatureCache); } - public TransactionSet(Map transactionsByHash, Map> transactionsByAddress) { + public TransactionSet(Map transactionsByHash, Map> transactionsByAddress, SignatureCache signatureCache) { this.transactionsByHash = transactionsByHash; this.transactionsByAddress = transactionsByAddress; + this.signatureCache = signatureCache; } public void addTransaction(Transaction transaction) { @@ -50,7 +52,7 @@ public void addTransaction(Transaction transaction) { this.transactionsByHash.put(txhash, transaction); - RskAddress senderAddress = transaction.getSender(); + RskAddress senderAddress = transaction.getSender(signatureCache); List txs = this.transactionsByAddress.get(senderAddress); @@ -85,7 +87,7 @@ public void removeTransactionByHash(Keccak256 hash) { this.transactionsByHash.remove(hash); - RskAddress senderAddress = transaction.getSender(); + RskAddress senderAddress = transaction.getSender(signatureCache); List txs = this.transactionsByAddress.get(senderAddress); if (txs != null) { diff --git a/rskj-core/src/test/java/org/ethereum/core/TransactionSetTest.java b/rskj-core/src/test/java/org/ethereum/core/TransactionSetTest.java index ee2b979e1f8..902bcdacabd 100644 --- a/rskj-core/src/test/java/org/ethereum/core/TransactionSetTest.java +++ b/rskj-core/src/test/java/org/ethereum/core/TransactionSetTest.java @@ -15,11 +15,11 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.core; import co.rsk.core.RskAddress; import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import java.util.List; @@ -30,9 +30,16 @@ * Created by ajlopez on 28/02/2018. */ class TransactionSetTest { + + private SignatureCache signatureCache; + + @BeforeEach + public void setup() { + signatureCache = new BlockTxSignatureCache(new ReceivedTxSignatureCache()); + } @Test void getEmptyTransactionList() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); List result = txset.getTransactions(); @@ -42,7 +49,7 @@ void getEmptyTransactionList() { @Test void transactionIsNotInEmptySet() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction = createSampleTransaction(); Assertions.assertFalse(txset.hasTransaction(transaction)); @@ -54,7 +61,7 @@ void transactionIsNotInEmptySet() { @Test void hasTransaction() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction1 = createSampleTransaction(10); Transaction transaction2 = createSampleTransaction(20); Transaction transaction3 = createSampleTransaction(30); @@ -69,7 +76,7 @@ void hasTransaction() { @Test void addAndRemoveTransactions() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction1 = createSampleTransaction(1, 2, 100, 0); Transaction transaction2 = createSampleTransaction(2, 3, 200, 0); @@ -95,7 +102,7 @@ void addAndRemoveTransactions() { @Test void addTransactionAndGetListWithOneTransaction() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction tx = createSampleTransaction(); txset.addTransaction(tx); @@ -110,7 +117,7 @@ void addTransactionAndGetListWithOneTransaction() { @Test void addtTransactionTwiceAndGetListWithOneTransaction() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction = createSampleTransaction(); txset.addTransaction(transaction); @@ -126,7 +133,7 @@ void addtTransactionTwiceAndGetListWithOneTransaction() { @Test void getEmptyTransactionListByUnknownSender() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); List result = txset.getTransactionsWithSender(new RskAddress(new byte[20])); @@ -136,7 +143,7 @@ void getEmptyTransactionListByUnknownSender() { @Test void addTransactionAndGetListBySenderWithOneTransaction() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction = createSampleTransaction(); txset.addTransaction(transaction); @@ -151,7 +158,7 @@ void addTransactionAndGetListBySenderWithOneTransaction() { @Test void addTransactionTwiceAndGetListBySenderWithOneTransaction() { - TransactionSet txset = new TransactionSet(); + TransactionSet txset = new TransactionSet(signatureCache); Transaction transaction = createSampleTransaction(); txset.addTransaction(transaction); From 72dbb542a56af08ac91b401c9ffb26e324b88a60 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Thu, 22 Sep 2022 22:19:09 -0300 Subject: [PATCH 11/18] Updating DTOs --- .../src/main/java/co/rsk/RskContext.java | 3 +- .../src/main/java/co/rsk/rpc/Web3RskImpl.java | 7 ++-- .../main/java/org/ethereum/rpc/Web3Impl.java | 25 +++++++------- .../org/ethereum/rpc/dto/BlockResultDTO.java | 34 +++++++++---------- .../rpc/dto/TransactionReceiptDTO.java | 6 ++-- .../rpc/dto/TransactionResultDTO.java | 15 ++++---- .../co/rsk/mine/TransactionModuleTest.java | 1 + .../java/co/rsk/rpc/Web3EthModuleTest.java | 6 ++-- .../test/java/co/rsk/rpc/Web3ImplRpcTest.java | 2 +- .../org/ethereum/rpc/Web3ImplLogsTest.java | 1 + .../org/ethereum/rpc/Web3ImplScoringTest.java | 1 + .../ethereum/rpc/Web3ImplSnapshotTest.java | 1 + .../java/org/ethereum/rpc/Web3ImplTest.java | 11 ++++-- .../org/ethereum/rpc/Web3ImplUnitTest.java | 8 ++--- .../ethereum/rpc/dto/BlockResultDTOTest.java | 23 ++++++------- .../rpc/dto/TransactionReceiptDTOTest.java | 23 ++++++------- .../rpc/dto/TransactionResultDTOTest.java | 17 ++++------ 17 files changed, 93 insertions(+), 91 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index 7fc39edee90..499f3ca54e0 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -1289,7 +1289,8 @@ protected synchronized Web3 buildWeb3() { getBuildInfo(), getBlocksBloomStore(), getWeb3InformationRetriever(), - getSyncProcessor()); + getSyncProcessor(), + getBlockTxSignatureCache()); } protected synchronized Web3InformationRetriever getWeb3InformationRetriever() { diff --git a/rskj-core/src/main/java/co/rsk/rpc/Web3RskImpl.java b/rskj-core/src/main/java/co/rsk/rpc/Web3RskImpl.java index b3836be9cba..7984f5b15e5 100644 --- a/rskj-core/src/main/java/co/rsk/rpc/Web3RskImpl.java +++ b/rskj-core/src/main/java/co/rsk/rpc/Web3RskImpl.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.rpc; import co.rsk.config.RskSystemProperties; @@ -40,6 +39,7 @@ import org.ethereum.core.Block; import org.ethereum.core.BlockHeader; import org.ethereum.core.Blockchain; +import org.ethereum.core.SignatureCache; import org.ethereum.crypto.HashUtil; import org.ethereum.db.BlockStore; import org.ethereum.db.ReceiptStore; @@ -96,11 +96,12 @@ public Web3RskImpl( BuildInfo buildInfo, BlocksBloomStore blocksBloomStore, Web3InformationRetriever retriever, - SyncProcessor syncProcessor) { + SyncProcessor syncProcessor, + SignatureCache signatureCache) { super(eth, blockchain, blockStore, receiptStore, properties, minerClient, minerServer, personalModule, ethModule, evmModule, txPoolModule, mnrModule, debugModule, traceModule, rskModule, channelManager, peerScoringManager, peerServer, nodeBlockProcessor, - hashRateCalculator, configCapabilities, buildInfo, blocksBloomStore, retriever, syncProcessor); + hashRateCalculator, configCapabilities, buildInfo, blocksBloomStore, retriever, syncProcessor, signatureCache); this.networkStateExporter = networkStateExporter; this.blockStore = blockStore; diff --git a/rskj-core/src/main/java/org/ethereum/rpc/Web3Impl.java b/rskj-core/src/main/java/org/ethereum/rpc/Web3Impl.java index 43fc5432101..f9cdb5ce2db 100644 --- a/rskj-core/src/main/java/org/ethereum/rpc/Web3Impl.java +++ b/rskj-core/src/main/java/org/ethereum/rpc/Web3Impl.java @@ -15,10 +15,8 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc; - import static co.rsk.util.HexUtils.jsonHexToInt; import static co.rsk.util.HexUtils.jsonHexToLong; import static co.rsk.util.HexUtils.stringHexToBigInteger; @@ -46,10 +44,7 @@ import java.util.function.UnaryOperator; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Block; -import org.ethereum.core.BlockHeader; -import org.ethereum.core.Blockchain; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.HashUtil; import org.ethereum.db.BlockInformation; import org.ethereum.db.BlockStore; @@ -135,6 +130,8 @@ public class Web3Impl implements Web3 { private final RskModule rskModule; private final SyncProcessor syncProcessor; + private final SignatureCache signatureCache; + private Ethereum eth; protected Web3Impl( @@ -162,7 +159,8 @@ protected Web3Impl( BuildInfo buildInfo, BlocksBloomStore blocksBloomStore, Web3InformationRetriever web3InformationRetriever, - SyncProcessor syncProcessor) { + SyncProcessor syncProcessor, + SignatureCache signatureCache) { this.eth = eth; this.blockchain = blockchain; this.blockStore = blockStore; @@ -188,6 +186,7 @@ protected Web3Impl( this.blocksBloomStore = blocksBloomStore; this.web3InformationRetriever = web3InformationRetriever; this.syncProcessor = syncProcessor; + this.signatureCache = signatureCache; personalModule.init(); } @@ -637,7 +636,7 @@ public BlockInformationResult getBlockInformationResult(BlockInformation blockIn } public BlockResultDTO getBlockResult(Block b, boolean fullTx) { - return BlockResultDTO.fromBlock(b, fullTx, this.blockStore, config.skipRemasc(), config.rpcZeroSignatureIfRemasc()); + return BlockResultDTO.fromBlock(b, fullTx, this.blockStore, config.skipRemasc(), config.rpcZeroSignatureIfRemasc(), signatureCache); } public BlockInformationResult[] eth_getBlocksByNumber(String number) { @@ -705,7 +704,7 @@ public TransactionResultDTO eth_getTransactionByHash(String transactionHash) { for (Transaction tx : txs) { if (tx.getHash().equals(txHash)) { - return s = new TransactionResultDTO(null, null, tx, config.rpcZeroSignatureIfRemasc()); + return s = new TransactionResultDTO(null, null, tx, config.rpcZeroSignatureIfRemasc(), signatureCache); } } } else { @@ -722,7 +721,7 @@ public TransactionResultDTO eth_getTransactionByHash(String transactionHash) { return null; } - return s = new TransactionResultDTO(block, txInfo.getIndex(), txInfo.getReceipt().getTransaction(), config.rpcZeroSignatureIfRemasc()); + return s = new TransactionResultDTO(block, txInfo.getIndex(), txInfo.getReceipt().getTransaction(), config.rpcZeroSignatureIfRemasc(), signatureCache); } finally { logger.debug("eth_getTransactionByHash({}): {}", transactionHash, s); } @@ -746,7 +745,7 @@ public TransactionResultDTO eth_getTransactionByBlockHashAndIndex(String blockHa Transaction tx = b.getTransactionsList().get(idx); - return s = new TransactionResultDTO(b, idx, tx, config.rpcZeroSignatureIfRemasc()); + return s = new TransactionResultDTO(b, idx, tx, config.rpcZeroSignatureIfRemasc(), signatureCache); } finally { if (logger.isDebugEnabled()) { logger.debug("eth_getTransactionByBlockHashAndIndex({}, {}): {}", blockHash, index, s); @@ -769,7 +768,7 @@ public TransactionResultDTO eth_getTransactionByBlockNumberAndIndex(String bnOrI return null; } - s = new TransactionResultDTO(block.get(), idx, txs.get(idx), config.rpcZeroSignatureIfRemasc()); + s = new TransactionResultDTO(block.get(), idx, txs.get(idx), config.rpcZeroSignatureIfRemasc(), signatureCache); return s; } finally { if (logger.isDebugEnabled()) { @@ -794,7 +793,7 @@ public TransactionReceiptDTO eth_getTransactionReceipt(String transactionHash) { Transaction tx = block.getTransactionsList().get(txInfo.getIndex()); txInfo.setTransaction(tx); - return new TransactionReceiptDTO(block, txInfo); + return new TransactionReceiptDTO(block, txInfo, signatureCache); } @Override diff --git a/rskj-core/src/main/java/org/ethereum/rpc/dto/BlockResultDTO.java b/rskj-core/src/main/java/org/ethereum/rpc/dto/BlockResultDTO.java index e6f33497eda..1acf8aaad7f 100644 --- a/rskj-core/src/main/java/org/ethereum/rpc/dto/BlockResultDTO.java +++ b/rskj-core/src/main/java/org/ethereum/rpc/dto/BlockResultDTO.java @@ -15,18 +15,9 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; -import co.rsk.core.BlockDifficulty; -import co.rsk.core.Coin; -import co.rsk.core.RskAddress; -import co.rsk.crypto.Keccak256; -import co.rsk.util.HexUtils; -import org.ethereum.core.Block; -import org.ethereum.core.BlockHeader; -import org.ethereum.core.Transaction; -import org.ethereum.db.BlockStore; +import static org.ethereum.crypto.HashUtil.EMPTY_TRIE_HASH; import java.util.ArrayList; import java.util.Collections; @@ -35,8 +26,17 @@ import java.util.stream.Collectors; import java.util.stream.IntStream; -import static org.ethereum.crypto.HashUtil.EMPTY_TRIE_HASH; +import org.ethereum.core.Block; +import org.ethereum.core.BlockHeader; +import org.ethereum.core.SignatureCache; +import org.ethereum.core.Transaction; +import org.ethereum.db.BlockStore; +import co.rsk.core.BlockDifficulty; +import co.rsk.core.Coin; +import co.rsk.core.RskAddress; +import co.rsk.crypto.Keccak256; +import co.rsk.util.HexUtils; public class BlockResultDTO { private final String number; // QUANTITY - the block number. null when its pending block. @@ -122,7 +122,7 @@ private BlockResultDTO( this.paidFees = paidFees != null ? HexUtils.toQuantityJsonHex(paidFees.getBytes()) : null; } - public static BlockResultDTO fromBlock(Block b, boolean fullTx, BlockStore blockStore, boolean skipRemasc, boolean zeroSignatureIfRemasc) { + public static BlockResultDTO fromBlock(Block b, boolean fullTx, BlockStore blockStore, boolean skipRemasc, boolean zeroSignatureIfRemasc, SignatureCache signatureCache) { if (b == null) { return null; } @@ -135,7 +135,7 @@ public static BlockResultDTO fromBlock(Block b, boolean fullTx, BlockStore block List blockTransactions = b.getTransactionsList(); // For full tx will present as TransactionResultDTO otherwise just as transaction hash List transactions = IntStream.range(0, blockTransactions.size()) - .mapToObj(txIndex -> toTransactionResult(txIndex, b, fullTx, skipRemasc, zeroSignatureIfRemasc)) + .mapToObj(txIndex -> toTransactionResult(txIndex, b, fullTx, skipRemasc, zeroSignatureIfRemasc, signatureCache)) .filter(Objects::nonNull) .collect(Collectors.toList()); @@ -181,15 +181,15 @@ public static BlockResultDTO fromBlock(Block b, boolean fullTx, BlockStore block ); } - private static Object toTransactionResult(int transactionIndex, Block block, boolean fullTx, boolean skipRemasc, boolean zeroSignatureIfRemasc) { + private static Object toTransactionResult(int transactionIndex, Block block, boolean fullTx, boolean skipRemasc, boolean zeroSignatureIfRemasc, SignatureCache signatureCache) { Transaction transaction = block.getTransactionsList().get(transactionIndex); if(skipRemasc && transaction.isRemascTransaction(transactionIndex, block.getTransactionsList().size())) { return null; } - + if(fullTx) { - return new TransactionResultDTO(block, transactionIndex, transaction, zeroSignatureIfRemasc); + return new TransactionResultDTO(block, transactionIndex, transaction, zeroSignatureIfRemasc, signatureCache); } return transaction.getHash().toJsonString(); @@ -290,4 +290,4 @@ public String getHashForMergedMining() { public String getPaidFees() { return paidFees; } -} +} \ No newline at end of file diff --git a/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionReceiptDTO.java b/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionReceiptDTO.java index d26262fe4fc..e1873dc184c 100644 --- a/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionReceiptDTO.java +++ b/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionReceiptDTO.java @@ -15,10 +15,10 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; import org.ethereum.core.Block; +import org.ethereum.core.SignatureCache; import org.ethereum.core.TransactionReceipt; import org.ethereum.db.TransactionInfo; import org.ethereum.rpc.LogFilterElement; @@ -44,7 +44,7 @@ public class TransactionReceiptDTO { private String status; // either 1 (success) or 0 (failure) private String logsBloom; // Bloom filter for light clients to quickly retrieve related logs. - public TransactionReceiptDTO(Block block, TransactionInfo txInfo) { + public TransactionReceiptDTO(Block block, TransactionInfo txInfo, SignatureCache signatureCache) { TransactionReceipt receipt = txInfo.getReceipt(); status = HexUtils.toQuantityJsonHex(txInfo.getReceipt().getStatus()); @@ -57,7 +57,7 @@ public TransactionReceiptDTO(Block block, TransactionInfo txInfo) { } cumulativeGasUsed = HexUtils.toQuantityJsonHex(receipt.getCumulativeGas()); - from = receipt.getTransaction().getSender().toJsonString(); + from = receipt.getTransaction().getSender(signatureCache).toJsonString(); gasUsed = HexUtils.toQuantityJsonHex(receipt.getGasUsed()); logs = new LogFilterElement[receipt.getLogInfoList().size()]; diff --git a/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionResultDTO.java b/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionResultDTO.java index c86003493f9..9f7ab3e886f 100644 --- a/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionResultDTO.java +++ b/rskj-core/src/main/java/org/ethereum/rpc/dto/TransactionResultDTO.java @@ -15,16 +15,17 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; -import co.rsk.core.Coin; -import co.rsk.remasc.RemascTransaction; -import co.rsk.util.HexUtils; import org.ethereum.core.Block; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.crypto.signature.ECDSASignature; +import co.rsk.core.Coin; +import co.rsk.remasc.RemascTransaction; +import co.rsk.util.HexUtils; + /** * Created by Ruben on 8/1/2016. */ @@ -47,7 +48,7 @@ public class TransactionResultDTO { private String r; private String s; - public TransactionResultDTO(Block b, Integer index, Transaction tx, boolean zeroSignatureIfRemasc) { + public TransactionResultDTO(Block b, Integer index, Transaction tx, boolean zeroSignatureIfRemasc, SignatureCache signatureCache) { hash = tx.getHash().toJsonString(); nonce = HexUtils.toQuantityJsonHex(tx.getNonce()); @@ -56,7 +57,7 @@ public TransactionResultDTO(Block b, Integer index, Transaction tx, boolean zero blockNumber = b != null ? HexUtils.toQuantityJsonHex(b.getNumber()) : null; transactionIndex = index != null ? HexUtils.toQuantityJsonHex(index) : null; - from = tx.getSender().toJsonString(); + from = tx.getSender(signatureCache).toJsonString(); to = tx.getReceiveAddress().toJsonString(); gas = HexUtils.toQuantityJsonHex(tx.getGasLimit()); @@ -141,4 +142,4 @@ public String getS() { return s; } -} +} \ No newline at end of file diff --git a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java index a6f0060a297..e39631bd5c5 100644 --- a/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java +++ b/rskj-core/src/test/java/co/rsk/mine/TransactionModuleTest.java @@ -672,6 +672,7 @@ repositoryLocator, new EthModuleWalletEnabled(wallet), transactionModule, null, null, null, + null, null); } diff --git a/rskj-core/src/test/java/co/rsk/rpc/Web3EthModuleTest.java b/rskj-core/src/test/java/co/rsk/rpc/Web3EthModuleTest.java index 021a862719f..e91284aebb7 100644 --- a/rskj-core/src/test/java/co/rsk/rpc/Web3EthModuleTest.java +++ b/rskj-core/src/test/java/co/rsk/rpc/Web3EthModuleTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.rpc; import co.rsk.config.RskSystemProperties; @@ -34,7 +33,9 @@ import co.rsk.rpc.modules.rsk.RskModule; import co.rsk.rpc.modules.txpool.TxPoolModule; import co.rsk.scoring.PeerScoringManager; +import org.ethereum.core.BlockTxSignatureCache; import org.ethereum.core.Blockchain; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.db.BlockStore; import org.ethereum.db.ReceiptStore; import org.ethereum.facade.Ethereum; @@ -79,7 +80,8 @@ null, mock(RskModule.class), mock(BuildInfo.class), mock(BlocksBloomStore.class), mock(Web3InformationRetriever.class), - mock(SyncProcessor.class)); + mock(SyncProcessor.class), + new BlockTxSignatureCache(new ReceivedTxSignatureCache())); assertThat(web3.eth_chainId(), is("0x21")); } diff --git a/rskj-core/src/test/java/co/rsk/rpc/Web3ImplRpcTest.java b/rskj-core/src/test/java/co/rsk/rpc/Web3ImplRpcTest.java index 38121611e13..d28d6566aff 100644 --- a/rskj-core/src/test/java/co/rsk/rpc/Web3ImplRpcTest.java +++ b/rskj-core/src/test/java/co/rsk/rpc/Web3ImplRpcTest.java @@ -48,7 +48,7 @@ void getRpcModules() { null, null, null, null, null, null, null, null, null, null, null, null, null, - null, null, null, null, null, null, null); + null, null, null, null, null, null, null, null); Map result = web3.rpc_modules(); diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java index ca0632f76ec..268f2ff77fd 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplLogsTest.java @@ -1098,6 +1098,7 @@ null, new EthModuleWalletEnabled(wallet), null, null, new BlocksBloomStore(2, 0, new HashMapDB()), mock(Web3InformationRetriever.class), + null, null); } diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java index ef6e2f0c1db..88e114fd142 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplScoringTest.java @@ -438,6 +438,7 @@ null, new EthModuleWalletEnabled(wallet), null, null, null, null, + null, null); } diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java index 2314d125954..6708c7c75de 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplSnapshotTest.java @@ -196,6 +196,7 @@ private Web3Impl createWeb3(SimpleEthereum ethereum) { null, null, null, + null, null); } diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java index 5468a253bbf..bcf847a81d5 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplTest.java @@ -680,7 +680,8 @@ void eth_mining() { null, null, mock(Web3InformationRetriever.class), - null); + null, + signatureCache); assertFalse(web3.eth_mining(), "Node is not mining"); try { @@ -1892,7 +1893,8 @@ void eth_coinbase() { null, null, mock(Web3InformationRetriever.class), - null); + null, + signatureCache); assertEquals("0x" + originalCoinbase, web3.eth_coinbase()); verify(minerServerMock, times(1)).getCoinbaseAddress(); @@ -2389,6 +2391,7 @@ null, new EthModuleWalletEnabled(wallet), null, blockchain, mock(RepositoryLocator.class), mock(ExecutionBlockRetriever.class)), + null, null); } @@ -2497,7 +2500,8 @@ private Web3Impl createWeb3( new BuildInfo("test", "test"), null, retriever, - syncProcessor + syncProcessor, + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); } @@ -2557,6 +2561,7 @@ private Web3Impl createWeb3CallNoReturn( new BuildInfo("test", "test"), null, retriever, + null, null); } diff --git a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplUnitTest.java b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplUnitTest.java index a6d334c781d..752d0d05d5f 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplUnitTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/Web3ImplUnitTest.java @@ -17,10 +17,7 @@ import java.util.Optional; import org.ethereum.TestUtils; -import org.ethereum.core.Block; -import org.ethereum.core.BlockHeader; -import org.ethereum.core.Blockchain; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.db.BlockStore; import org.ethereum.db.ReceiptStore; import org.ethereum.facade.Ethereum; @@ -92,7 +89,8 @@ void setup() { mock(BuildInfo.class), mock(BlocksBloomStore.class), retriever, - null); + null, + new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } @Test diff --git a/rskj-core/src/test/java/org/ethereum/rpc/dto/BlockResultDTOTest.java b/rskj-core/src/test/java/org/ethereum/rpc/dto/BlockResultDTOTest.java index 1aa3bb6bbc0..fbe71730cef 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/dto/BlockResultDTOTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/dto/BlockResultDTOTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; import co.rsk.core.BlockDifficulty; @@ -24,9 +23,7 @@ import co.rsk.test.builders.BlockBuilder; import co.rsk.test.builders.TransactionBuilder; import co.rsk.util.HexUtils; -import org.ethereum.core.Block; -import org.ethereum.core.Blockchain; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.core.genesis.GenesisLoader; import org.ethereum.db.BlockStore; import org.ethereum.util.RskTestFactory; @@ -47,14 +44,14 @@ class BlockResultDTOTest { - private static final String HEX_ZERO = "0x0"; - private Block block; private BlockStore blockStore; - public static final Transaction TRANSACTION = new TransactionBuilder().buildRandomTransaction(); // todo(fedejinich) currently RemascTx(blockNumber) has a bug, thats why I initialize this way public static final RemascTransaction REMASC_TRANSACTION = new RemascTransaction(new RemascTransaction(1).getEncoded()); + public static final Transaction TRANSACTION = new TransactionBuilder().buildRandomTransaction(); + + private static final String HEX_ZERO = "0x0"; @BeforeEach void setup() { @@ -65,7 +62,7 @@ void setup() { @Test void getBlockResultDTOWithRemascAndTransactionHashes() { - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, false, false); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, false, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); List transactionHashes = transactionHashesByBlock(blockResultDTO); Assertions.assertNotNull(blockResultDTO); @@ -76,7 +73,7 @@ void getBlockResultDTOWithRemascAndTransactionHashes() { @Test void getBlockResultDTOWithoutRemascAndTransactionHashes() { - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, true, false); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, true, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); List transactionHashes = transactionHashesByBlock(blockResultDTO); Assertions.assertNotNull(blockResultDTO); @@ -88,7 +85,7 @@ void getBlockResultDTOWithoutRemascAndTransactionHashes() { @Test void getBlockResultDTOWithoutRemasc_emptyTransactions() { Block block = buildBlockWithTransactions(Arrays.asList(REMASC_TRANSACTION)); - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, true, false); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, false, blockStore, true, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertEquals(HexUtils.toUnformattedJsonHex(EMPTY_TRIE_HASH), blockResultDTO.getTransactionsRoot()); @@ -99,7 +96,7 @@ void getBlockResultDTOWithoutRemasc_emptyTransactions() { @Test void getBlockResultDTOWithNullSignatureRemascAndFullTransactions() { - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, false, false); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, false, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNotNull(blockResultDTO); Assertions.assertEquals(2, blockResultDTO.getTransactions().size()); @@ -116,7 +113,7 @@ void getBlockResultDTOWithNullSignatureRemascAndFullTransactions() { @Test void getBlockResultDTOWithWithZeroSignatureRemascAndFullTransactions() { - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, false, true); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, false, true, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNotNull(blockResultDTO); Assertions.assertEquals(2, blockResultDTO.getTransactions().size()); @@ -132,7 +129,7 @@ void getBlockResultDTOWithWithZeroSignatureRemascAndFullTransactions() { @Test void getBlockResultDTOWithoutRemascAndFullTransactions() { - BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, true, false); + BlockResultDTO blockResultDTO = BlockResultDTO.fromBlock(block, true, blockStore, true, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); List transactionResultsHashes = transactionResultsByBlock(blockResultDTO).stream().map(e -> e.getHash()).collect(Collectors.toList()); diff --git a/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionReceiptDTOTest.java b/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionReceiptDTOTest.java index 804f8d97771..ba72288225e 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionReceiptDTOTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionReceiptDTOTest.java @@ -15,15 +15,11 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; import co.rsk.core.RskAddress; import co.rsk.crypto.Keccak256; -import org.ethereum.core.Block; -import org.ethereum.core.Bloom; -import org.ethereum.core.Transaction; -import org.ethereum.core.TransactionReceipt; +import org.ethereum.core.*; import org.ethereum.db.TransactionInfo; import org.ethereum.util.ByteUtil; import org.junit.jupiter.api.Test; @@ -32,6 +28,7 @@ import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; +import static org.mockito.ArgumentMatchers.any; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; @@ -48,7 +45,7 @@ void testOkStatusField() { Transaction transaction = mock(Transaction.class); when(transaction.getHash()).thenReturn(hash); - when(transaction.getSender()).thenReturn(rskAddress); + when(transaction.getSender(any())).thenReturn(rskAddress); when(transaction.getReceiveAddress()).thenReturn(rskAddress); TransactionReceipt txReceipt = mock(TransactionReceipt.class); @@ -59,7 +56,7 @@ void testOkStatusField() { TransactionInfo txInfo = new TransactionInfo(txReceipt, hash.getBytes(), 0); - TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo); + TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); String actualStatus = transactionReceiptDTO.getStatus(); @@ -78,7 +75,7 @@ void testErrorStatusField() { Transaction transaction = mock(Transaction.class); when(transaction.getHash()).thenReturn(hash); - when(transaction.getSender()).thenReturn(rskAddress); + when(transaction.getSender(any())).thenReturn(rskAddress); when(transaction.getReceiveAddress()).thenReturn(rskAddress); TransactionReceipt txReceipt = mock(TransactionReceipt.class); @@ -89,7 +86,7 @@ void testErrorStatusField() { TransactionInfo txInfo = new TransactionInfo(txReceipt, hash.getBytes(), 0); - TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo); + TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); String actualStatus = transactionReceiptDTO.getStatus(); @@ -108,7 +105,7 @@ void testErrorStatusFieldUsingEmptyByteArray() { Transaction transaction = mock(Transaction.class); when(transaction.getHash()).thenReturn(hash); - when(transaction.getSender()).thenReturn(rskAddress); + when(transaction.getSender(any())).thenReturn(rskAddress); when(transaction.getReceiveAddress()).thenReturn(rskAddress); TransactionReceipt txReceipt = mock(TransactionReceipt.class); @@ -119,7 +116,7 @@ void testErrorStatusFieldUsingEmptyByteArray() { TransactionInfo txInfo = new TransactionInfo(txReceipt, hash.getBytes(), 0); - TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo); + TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); String actualStatus = transactionReceiptDTO.getStatus(); @@ -138,7 +135,7 @@ void testErrorStatusFieldUsingNullByteArray() { Transaction transaction = mock(Transaction.class); when(transaction.getHash()).thenReturn(hash); - when(transaction.getSender()).thenReturn(rskAddress); + when(transaction.getSender(any())).thenReturn(rskAddress); when(transaction.getReceiveAddress()).thenReturn(rskAddress); TransactionReceipt txReceipt = mock(TransactionReceipt.class); @@ -149,7 +146,7 @@ void testErrorStatusFieldUsingNullByteArray() { TransactionInfo txInfo = new TransactionInfo(txReceipt, hash.getBytes(), 0); - TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo); + TransactionReceiptDTO transactionReceiptDTO = new TransactionReceiptDTO(block, txInfo, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); String actualStatus = transactionReceiptDTO.getStatus(); diff --git a/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionResultDTOTest.java b/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionResultDTOTest.java index 5c527409269..d76421ad38a 100644 --- a/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionResultDTOTest.java +++ b/rskj-core/src/test/java/org/ethereum/rpc/dto/TransactionResultDTOTest.java @@ -15,15 +15,12 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.rpc.dto; import co.rsk.config.TestSystemProperties; import co.rsk.core.RskAddress; import co.rsk.remasc.RemascTransaction; -import org.ethereum.core.Block; -import org.ethereum.core.CallTransaction; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; @@ -45,7 +42,7 @@ class TransactionResultDTOTest { void remascAddressSerialization() { RemascTransaction remascTransaction = new RemascTransaction(new Random().nextLong()); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, false); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); assertThat(dto.getFrom(), is("0x0000000000000000000000000000000000000000")); assertThat(dto.getR(), is(nullValue())); assertThat(dto.getS(), is(nullValue())); @@ -61,7 +58,7 @@ void signedTransactionWithChainIdSerialization() { originalTransaction.sign(new byte[]{}); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNotNull(dto.getR()); Assertions.assertNotNull(dto.getS()); @@ -81,7 +78,7 @@ void transactionWithZeroNonce() { originalTransaction.sign(new byte[]{}); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNotNull(dto.getNonce()); Assertions.assertEquals("0x0", dto.getNonce()); @@ -96,7 +93,7 @@ void transactionWithOneNonceWithoutLeadingZeroes() { originalTransaction.sign(new byte[]{}); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, originalTransaction, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNotNull(dto.getNonce()); Assertions.assertEquals("0x1", dto.getNonce()); @@ -105,7 +102,7 @@ void transactionWithOneNonceWithoutLeadingZeroes() { @Test void transactionRemascHasSignatureNullWhenFlagIsFalse() { RemascTransaction remascTransaction = new RemascTransaction(new Random().nextLong()); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, false); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, false, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertNull(dto.getV()); Assertions.assertNull(dto.getR()); Assertions.assertNull(dto.getS()); @@ -114,7 +111,7 @@ void transactionRemascHasSignatureNullWhenFlagIsFalse() { @Test void transactionRemascHasSignatureZeroWhenFlagIsTrue() { RemascTransaction remascTransaction = new RemascTransaction(new Random().nextLong()); - TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, true); + TransactionResultDTO dto = new TransactionResultDTO(mock(Block.class), 42, remascTransaction, true, new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Assertions.assertEquals(HEX_ZERO, dto.getV()); Assertions.assertEquals(HEX_ZERO, dto.getR()); Assertions.assertEquals(HEX_ZERO, dto.getS()); From 9fcf45e3e3a77fb03b7527f7f30374dadfcaf9b6 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Fri, 23 Sep 2022 14:29:45 -0300 Subject: [PATCH 12/18] Adding signature cache to VM --- .../java/org/ethereum/core/Transaction.java | 1 - .../ethereum/core/TransactionExecutor.java | 8 ++--- .../vm/program/InternalTransaction.java | 13 ++++--- .../java/org/ethereum/vm/program/Program.java | 19 +++++----- .../ethereum/vm/program/ProgramResult.java | 8 +++-- .../program/invoke/ProgramInvokeFactory.java | 5 +-- .../invoke/ProgramInvokeFactoryImpl.java | 8 ++--- .../test/java/co/rsk/pcc/AltBN128Test.java | 4 ++- .../co/rsk/peg/BridgeSupportFlyoverTest.java | 35 +++++++++++++++++++ .../rsk/peg/BridgeSupportReleaseBtcTest.java | 24 ++++++++++--- .../rsk/peg/BridgeSupportTestIntegration.java | 9 ++--- .../co/rsk/peg/BridgeTestIntegration.java | 12 ++----- .../test/java/co/rsk/peg/BridgeUtilsTest.java | 2 +- .../BridgePerformanceTestCase.java | 2 +- .../src/test/java/co/rsk/vm/Create2Test.java | 10 ++---- .../test/java/co/rsk/vm/ExtCodeHashTest.java | 25 ++++++++++--- .../test/java/co/rsk/vm/VMExecutionTest.java | 11 +++--- .../java/co/rsk/vm/VMPerformanceTest.java | 9 ++--- .../vm/VMSpecificOpcodesPerformanceTest.java | 23 +++++++++--- .../TestProgramInvokeFactory.java | 12 +++---- .../ethereum/jsontestsuite/TestRunner.java | 2 +- .../org/ethereum/vm/ProgramMemoryTest.java | 5 ++- .../java/org/ethereum/vm/VMComplexTest.java | 6 ++-- .../java/org/ethereum/vm/VMCustomTest.java | 4 ++- .../src/test/java/org/ethereum/vm/VMTest.java | 7 ++-- .../vm/program/ProgramResultTest.java | 33 ++++++++++++++--- .../org/ethereum/vm/program/ProgramTest.java | 8 ++--- 27 files changed, 202 insertions(+), 103 deletions(-) diff --git a/rskj-core/src/main/java/org/ethereum/core/Transaction.java b/rskj-core/src/main/java/org/ethereum/core/Transaction.java index 956a313f917..5bc59f43671 100644 --- a/rskj-core/src/main/java/org/ethereum/core/Transaction.java +++ b/rskj-core/src/main/java/org/ethereum/core/Transaction.java @@ -16,7 +16,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.core; import co.rsk.core.Coin; diff --git a/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java b/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java index 916fedb2370..c12728d49b7 100644 --- a/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java +++ b/rskj-core/src/main/java/org/ethereum/core/TransactionExecutor.java @@ -352,10 +352,10 @@ private void call() { result.spendGas(basicTxCost); } else { ProgramInvoke programInvoke = - programInvokeFactory.createProgramInvoke(tx, txindex, executionBlock, cacheTrack, blockStore); + programInvokeFactory.createProgramInvoke(tx, txindex, executionBlock, cacheTrack, blockStore, signatureCache); this.vm = new VM(vmConfig, precompiledContracts); - this.program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, programInvoke, tx, deletedAccounts); + this.program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, programInvoke, tx, deletedAccounts, signatureCache); } } @@ -375,10 +375,10 @@ private void create() { // storage. It doesn't even call setupContract() to setup a storage root } else { cacheTrack.setupContract(newContractAddress); - ProgramInvoke programInvoke = programInvokeFactory.createProgramInvoke(tx, txindex, executionBlock, cacheTrack, blockStore); + ProgramInvoke programInvoke = programInvokeFactory.createProgramInvoke(tx, txindex, executionBlock, cacheTrack, blockStore, signatureCache); this.vm = new VM(vmConfig, precompiledContracts); - this.program = new Program(vmConfig, precompiledContracts, blockFactory, activations, tx.getData(), programInvoke, tx, deletedAccounts); + this.program = new Program(vmConfig, precompiledContracts, blockFactory, activations, tx.getData(), programInvoke, tx, deletedAccounts, signatureCache); // reset storage if the contract with the same address already exists // TCK test case only - normally this is near-impossible situation in the real network diff --git a/rskj-core/src/main/java/org/ethereum/vm/program/InternalTransaction.java b/rskj-core/src/main/java/org/ethereum/vm/program/InternalTransaction.java index e0f299debce..b2a4fa2e614 100644 --- a/rskj-core/src/main/java/org/ethereum/vm/program/InternalTransaction.java +++ b/rskj-core/src/main/java/org/ethereum/vm/program/InternalTransaction.java @@ -16,9 +16,9 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.vm.program; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.crypto.ECKey; import org.ethereum.util.ByteUtil; @@ -34,10 +34,12 @@ public class InternalTransaction extends Transaction { private final int deep; private final int index; private final String note; + private final SignatureCache signatureCache; + private boolean rejected = false; public InternalTransaction(byte[] originHash, byte[] parentHash, int deep, int index, byte[] nonce, DataWord gasPrice, DataWord gasLimit, - byte[] sendAddress, byte[] receiveAddress, byte[] value, byte[] data, String note) { + byte[] sendAddress, byte[] receiveAddress, byte[] value, byte[] data, String note, SignatureCache signatureCache) { super(nonce, getData(gasPrice), getData(gasLimit), receiveAddress, nullToEmpty(value), nullToEmpty(data)); @@ -47,11 +49,12 @@ public InternalTransaction(byte[] originHash, byte[] parentHash, int deep, int i this.index = index; this.sender = RLP.parseRskAddress(sendAddress); this.note = note; + this.signatureCache = signatureCache; } public InternalTransaction(byte[] parentHash, int deep, int index, byte[] nonce, DataWord gasPrice, DataWord gasLimit, - byte[] sendAddress, byte[] receiveAddress, byte[] value, byte[] data, String note) { - this(parentHash, parentHash, deep, index, nonce, gasPrice, gasLimit, sendAddress, receiveAddress, value, data, note); + byte[] sendAddress, byte[] receiveAddress, byte[] value, byte[] data, String note, SignatureCache signatureCache) { + this(parentHash, parentHash, deep, index, nonce, gasPrice, gasLimit, sendAddress, receiveAddress, value, data, note, signatureCache); } private static byte[] getData(DataWord gasPrice) { @@ -94,7 +97,7 @@ public byte[] getEncoded() { } else { nonce = RLP.encodeElement(nonce); } - byte[] senderAddress = RLP.encodeElement(getSender().getBytes()); + byte[] senderAddress = RLP.encodeElement(getSender(signatureCache).getBytes()); byte[] receiveAddress = RLP.encodeElement(getReceiveAddress().getBytes()); byte[] value = RLP.encodeCoin(getValue()); byte[] gasPrice = RLP.encodeCoin(getGasPrice()); diff --git a/rskj-core/src/main/java/org/ethereum/vm/program/Program.java b/rskj-core/src/main/java/org/ethereum/vm/program/Program.java index 2e88a1280e4..9a2ec121b15 100644 --- a/rskj-core/src/main/java/org/ethereum/vm/program/Program.java +++ b/rskj-core/src/main/java/org/ethereum/vm/program/Program.java @@ -16,7 +16,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.vm.program; import co.rsk.config.VmConfig; @@ -34,10 +33,7 @@ import org.ethereum.config.Constants; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.HashUtil; import org.ethereum.util.ByteUtil; import org.ethereum.util.FastByteComparisons; @@ -115,6 +111,8 @@ public class Program { private final Set deletedAccountsInBlock; + private final SignatureCache signatureCache; + public Program( VmConfig config, PrecompiledContracts precompiledContracts, @@ -123,7 +121,8 @@ public Program( byte[] ops, ProgramInvoke programInvoke, Transaction transaction, - Set deletedAccounts) { + Set deletedAccounts, + SignatureCache signatureCache) { this.config = config; this.precompiledContracts = precompiledContracts; this.blockFactory = blockFactory; @@ -150,6 +149,7 @@ public Program( this.stack.ensureCapacity(1024); // faster? this.storage = setupProgramListener(new Storage(programInvoke)); this.deletedAccountsInBlock = new HashSet<>(deletedAccounts); + this.signatureCache = signatureCache; precompile(); traceListener = new ProgramTraceListener(config); @@ -201,7 +201,8 @@ private InternalTransaction addInternalTx(byte[] nonce, DataWord gasLimit, RskAd receiveAddress.getBytes(), value.getBytes(), data, - note); + note, + signatureCache); } private T setupProgramListener(T traceListenerAware) { @@ -600,7 +601,7 @@ private ProgramResult getProgramResult(RskAddress senderAddress, byte[] nonce, D if (!isEmpty(programCode)) { VM vm = new VM(config, precompiledContracts); - Program program = new Program(config, precompiledContracts, blockFactory, activations, programCode, programInvoke, internalTx, deletedAccountsInBlock); + Program program = new Program(config, precompiledContracts, blockFactory, activations, programCode, programInvoke, internalTx, deletedAccountsInBlock, signatureCache); vm.play(program); programResult = program.getResult(); @@ -825,7 +826,7 @@ private boolean executeCode( msg.getType() == MsgType.STATICCALL || isStaticCall(), byTestingSuite()); VM vm = new VM(config, precompiledContracts); - Program program = new Program(config, precompiledContracts, blockFactory, activations, programCode, programInvoke, internalTx, deletedAccountsInBlock); + Program program = new Program(config, precompiledContracts, blockFactory, activations, programCode, programInvoke, internalTx, deletedAccountsInBlock, signatureCache); vm.play(program); childResult = program.getResult(); diff --git a/rskj-core/src/main/java/org/ethereum/vm/program/ProgramResult.java b/rskj-core/src/main/java/org/ethereum/vm/program/ProgramResult.java index 7f54299d5fc..f329eb4fc30 100644 --- a/rskj-core/src/main/java/org/ethereum/vm/program/ProgramResult.java +++ b/rskj-core/src/main/java/org/ethereum/vm/program/ProgramResult.java @@ -16,9 +16,9 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.vm.program; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.vm.CallCreate; import org.ethereum.vm.DataWord; @@ -215,7 +215,8 @@ public InternalTransaction addInternalTransaction( byte[] receiveAddress, byte[] value, byte[] data, - String note + String note, + SignatureCache signatureCache ) { byte[] parentHash = parentTransaction.getHash().getBytes(); byte[] originHash = parentHash; @@ -234,7 +235,8 @@ public InternalTransaction addInternalTransaction( receiveAddress, value, data, - note + note, + signatureCache ); getInternalTransactions().add(transaction); return transaction; diff --git a/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactory.java b/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactory.java index b0df955dd05..63befefe62e 100644 --- a/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactory.java +++ b/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactory.java @@ -16,12 +16,12 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.vm.program.invoke; import co.rsk.core.Coin; import org.ethereum.core.Block; import org.ethereum.core.Repository; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.db.BlockStore; import org.ethereum.vm.DataWord; @@ -34,7 +34,8 @@ public interface ProgramInvokeFactory { ProgramInvoke createProgramInvoke(Transaction tx, int txindex, Block block, - Repository repository, BlockStore blockStore); + Repository repository, BlockStore blockStore, + SignatureCache signatureCache); ProgramInvoke createProgramInvoke(Program program, DataWord toAddress, DataWord callerAddress, DataWord inValue, long inGas, diff --git a/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactoryImpl.java b/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactoryImpl.java index 824cecb34a3..cd07c765f07 100644 --- a/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactoryImpl.java +++ b/rskj-core/src/main/java/org/ethereum/vm/program/invoke/ProgramInvokeFactoryImpl.java @@ -16,13 +16,13 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.vm.program.invoke; import co.rsk.core.Coin; import co.rsk.core.RskAddress; import org.ethereum.core.Block; import org.ethereum.core.Repository; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.db.BlockStore; import org.ethereum.util.ByteUtil; @@ -46,7 +46,7 @@ public class ProgramInvokeFactoryImpl implements ProgramInvokeFactory { // Invocation by the wire tx @Override public ProgramInvoke createProgramInvoke(Transaction tx, int txindex, Block block, Repository repository, - BlockStore blockStore) { + BlockStore blockStore, SignatureCache signatureCache) { /*** ADDRESS op ***/ // YP: Get address of currently executing account. @@ -54,11 +54,11 @@ public ProgramInvoke createProgramInvoke(Transaction tx, int txindex, Block bloc /*** ORIGIN op ***/ // YP: This is the sender of original transaction; it is never a contract. - byte[] origin = tx.getSender().getBytes(); + byte[] origin = tx.getSender(signatureCache).getBytes(); /*** CALLER op ***/ // YP: This is the address of the account that is directly responsible for this execution. - byte[] caller = tx.getSender().getBytes(); + byte[] caller = tx.getSender(signatureCache).getBytes(); /*** BALANCE op ***/ Coin balance = repository.getBalance(addr); diff --git a/rskj-core/src/test/java/co/rsk/pcc/AltBN128Test.java b/rskj-core/src/test/java/co/rsk/pcc/AltBN128Test.java index 1d5e932cb8e..96e19e7d565 100644 --- a/rskj-core/src/test/java/co/rsk/pcc/AltBN128Test.java +++ b/rskj-core/src/test/java/co/rsk/pcc/AltBN128Test.java @@ -30,6 +30,8 @@ import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; import org.ethereum.core.BlockFactory; +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.util.ByteUtil; import org.ethereum.vm.DataWord; import org.ethereum.vm.PrecompiledContracts; @@ -796,7 +798,7 @@ private Program executeCode(String code) { byte[] compiledCode = compiler.compile(code); VM vm = new VM(vmConfig, precompiledContracts); Program program = new Program(vmConfig, precompiledContracts, blockFactory, - activations, compiledCode, invoke, null, new HashSet<>()); + activations, compiledCode, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); vm.play(program); diff --git a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportFlyoverTest.java b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportFlyoverTest.java index 976402d13fc..a238bac93b3 100644 --- a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportFlyoverTest.java +++ b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportFlyoverTest.java @@ -1,3 +1,20 @@ +/* + * This file is part of RskJ + * Copyright (C) 2017 RSK Labs Ltd. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package co.rsk.peg; import co.rsk.bitcoinj.core.Address; @@ -179,6 +196,7 @@ private BigInteger sendFundsToActiveFederation( null, null, null, + null, null ); @@ -321,6 +339,7 @@ private BigInteger sendFundsToRetiringFederation( null, null, null, + null, null ); @@ -472,6 +491,7 @@ private BigInteger sendFundsToActiveAndRetiringFederation( null, null, null, + null, null ); @@ -635,6 +655,7 @@ private BigInteger sendFundsToAnyAddress( null, null, null, + null, null ); @@ -764,6 +785,7 @@ private BigInteger sendFundsSurpassesLockingCapToAnyAddress( null, null, null, + null, null ); @@ -1680,6 +1702,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_with_witness_already_saved_in_ null, null, null, + null, null ); @@ -1873,6 +1896,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_with_witness_surpassing_lockin null, null, null, + null, null ); @@ -2066,6 +2090,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_with_witness_surpassing_lockin null, null, null, + null, null ); @@ -2245,6 +2270,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_without_witness_surpassing_loc null, null, null, + null, null ); @@ -2411,6 +2437,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_without_witness_surpassing_loc null, null, null, + null, null ); @@ -2583,6 +2610,7 @@ void registerFlyoverBtcTransaction_failed_when_tx_without_witness_already_saved_ null, null, null, + null, null ); @@ -2687,6 +2715,7 @@ void registerFlyoverBtcTransaction_sender_is_not_lbc() null, null, null, + null, null ); @@ -2737,6 +2766,7 @@ void registerFlyoverBtcTransaction_validationsForRegisterBtcTransaction_returns_ null, null, null, + null, null ); @@ -2801,6 +2831,7 @@ void registerFlyoverBtcTransaction_amount_sent_is_0() null, null, null, + null, null ); @@ -2884,6 +2915,7 @@ void registerFlyoverBtcTransaction_surpasses_locking_cap_and_shouldTransfer_is_t null, null, null, + null, null ); @@ -2969,6 +3001,7 @@ void registerFlyoverBtcTransaction_surpasses_locking_cap_and_shouldTransfer_is_f null, null, null, + null, null ); @@ -3058,6 +3091,7 @@ void registerFlyoverBtcTransaction_surpasses_locking_cap_and_tries_to_register_a null, null, null, + null, null ); @@ -3158,6 +3192,7 @@ void registerFlyoverBtcTransaction_OK() null, null, null, + null, null ); diff --git a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportReleaseBtcTest.java b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportReleaseBtcTest.java index fda581b4ccf..01517dca307 100644 --- a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportReleaseBtcTest.java +++ b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportReleaseBtcTest.java @@ -1,3 +1,20 @@ +/* + * This file is part of RskJ + * Copyright (C) 2017 RSK Labs Ltd. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package co.rsk.peg; import co.rsk.bitcoinj.core.*; @@ -17,10 +34,7 @@ import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Block; -import org.ethereum.core.CallTransaction; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.ECKey; import org.ethereum.crypto.HashUtil; import org.ethereum.db.MutableRepository; @@ -1190,7 +1204,7 @@ private Transaction buildReleaseRskTx_fromContract(Coin coin) { return new InternalTransaction(releaseTx.getHash().getBytes(), 400, 0, NONCE.toByteArray(), DataWord.valueOf(GAS_PRICE.intValue()), DataWord.valueOf(GAS_LIMIT.intValue()), SENDER.getAddress(), PrecompiledContracts.BRIDGE_ADDR.getBytes(), co.rsk.core.Coin.fromBitcoin(Coin.COIN).getBytes(), - Hex.decode(DATA), ""); + Hex.decode(DATA), "", new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } private Transaction buildUpdateTx() { diff --git a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportTestIntegration.java b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportTestIntegration.java index eea4dd31686..da0fa8e4561 100644 --- a/rskj-core/src/test/java/co/rsk/peg/BridgeSupportTestIntegration.java +++ b/rskj-core/src/test/java/co/rsk/peg/BridgeSupportTestIntegration.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import co.rsk.bitcoinj.core.*; @@ -52,10 +51,7 @@ import org.ethereum.config.Constants; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; -import org.ethereum.core.Block; -import org.ethereum.core.Genesis; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.ECKey; import org.ethereum.crypto.HashUtil; import org.ethereum.db.MutableRepository; @@ -994,7 +990,8 @@ void releaseBtcFromContract() throws AddressFormatException, IOException { Hex.decode(TO_ADDRESS), BigIntegers.asUnsignedByteArray(AMOUNT), Hex.decode(DATA), - "" + "", + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); track.saveCode(tx.getSender(), new byte[]{0x1}); diff --git a/rskj-core/src/test/java/co/rsk/peg/BridgeTestIntegration.java b/rskj-core/src/test/java/co/rsk/peg/BridgeTestIntegration.java index 2f79559cbba..15688b4cfb0 100644 --- a/rskj-core/src/test/java/co/rsk/peg/BridgeTestIntegration.java +++ b/rskj-core/src/test/java/co/rsk/peg/BridgeTestIntegration.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import static co.rsk.bitcoinj.core.Utils.uint32ToByteStreamLE; @@ -58,12 +57,7 @@ import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.CallTransaction; -import org.ethereum.core.Genesis; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.ECKey; import org.ethereum.crypto.HashUtil; import org.ethereum.datasource.HashMapDB; @@ -2886,7 +2880,7 @@ void testCallFromContract_beforeOrchid() { when(tx.getHash()).thenReturn(new Keccak256("001122334455667788990011223344556677889900112233445566778899aabb")); // Run the program on the VM - Program program = new Program(config.getVmConfig(), precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, tx, new HashSet<>()); + Program program = new Program(config.getVmConfig(), precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, tx, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); Exception ex = Assertions.assertThrows(NullPointerException.class, () -> { for (int i = 0; i < numOps; i++) { vm.step(program); @@ -2931,7 +2925,7 @@ void testCallFromContract_afterOrchid() { when(tx.getHash()).thenReturn(new Keccak256("001122334455667788990011223344556677889900112233445566778899aabb")); // Run the program on the VM - Program program = new Program(config.getVmConfig(), precompiledContracts, blockFactory, activationConfig.forBlock(0), code, invoke, tx, new HashSet<>()); + Program program = new Program(config.getVmConfig(), precompiledContracts, blockFactory, activationConfig.forBlock(0), code, invoke, tx, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); try { for (int i = 0; i < numOps; i++) { vm.step(program); diff --git a/rskj-core/src/test/java/co/rsk/peg/BridgeUtilsTest.java b/rskj-core/src/test/java/co/rsk/peg/BridgeUtilsTest.java index bfe116f577b..acc21ba0e8e 100644 --- a/rskj-core/src/test/java/co/rsk/peg/BridgeUtilsTest.java +++ b/rskj-core/src/test/java/co/rsk/peg/BridgeUtilsTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import co.rsk.bitcoinj.core.*; @@ -2068,6 +2067,7 @@ void testIsContractTx() { null, null, null, + null, null )) ); diff --git a/rskj-core/src/test/java/co/rsk/peg/performance/BridgePerformanceTestCase.java b/rskj-core/src/test/java/co/rsk/peg/performance/BridgePerformanceTestCase.java index 0f1c97dc2b5..7daf0ed3591 100644 --- a/rskj-core/src/test/java/co/rsk/peg/performance/BridgePerformanceTestCase.java +++ b/rskj-core/src/test/java/co/rsk/peg/performance/BridgePerformanceTestCase.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg.performance; import co.rsk.bitcoinj.core.*; @@ -99,6 +98,7 @@ public static TxBuilder getTxBuilderWithInternalTransaction(RskAddress sender){ null, null, null, + null, null ); return internalTx; diff --git a/rskj-core/src/test/java/co/rsk/vm/Create2Test.java b/rskj-core/src/test/java/co/rsk/vm/Create2Test.java index 8abe86ddb65..a1f01f97b5d 100644 --- a/rskj-core/src/test/java/co/rsk/vm/Create2Test.java +++ b/rskj-core/src/test/java/co/rsk/vm/Create2Test.java @@ -1,5 +1,3 @@ -package co.rsk.vm; - /* * This file is part of RskJ * Copyright (C) 2017 RSK Labs Ltd. @@ -17,6 +15,7 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ +package co.rsk.vm; import co.rsk.config.TestSystemProperties; import co.rsk.config.VmConfig; @@ -29,9 +28,7 @@ import co.rsk.test.builders.TransactionBuilder; import org.bouncycastle.util.Arrays; import org.ethereum.config.blockchain.upgrades.ActivationConfig; -import org.ethereum.core.Account; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.util.ByteUtil; import org.ethereum.crypto.Keccak256Helper; import org.ethereum.vm.DataWord; @@ -51,7 +48,6 @@ import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; - /** * Created by Sebastian Sicardi on 22/05/2019. */ @@ -412,7 +408,7 @@ private Program executeCode(String stringCode) { byte[] code = compiler.compile(stringCode); VM vm = new VM(vmConfig,precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); while (!program.isStopped()){ vm.step(program); diff --git a/rskj-core/src/test/java/co/rsk/vm/ExtCodeHashTest.java b/rskj-core/src/test/java/co/rsk/vm/ExtCodeHashTest.java index 3a0eb2ad661..8db0fd993e9 100644 --- a/rskj-core/src/test/java/co/rsk/vm/ExtCodeHashTest.java +++ b/rskj-core/src/test/java/co/rsk/vm/ExtCodeHashTest.java @@ -1,3 +1,20 @@ +/* + * This file is part of RskJ + * Copyright (C) 2017 RSK Labs Ltd. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package co.rsk.vm; import co.rsk.config.TestSystemProperties; @@ -7,9 +24,7 @@ import co.rsk.test.builders.AccountBuilder; import co.rsk.test.builders.TransactionBuilder; import org.ethereum.config.blockchain.upgrades.ActivationConfig; -import org.ethereum.core.Account; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.crypto.Keccak256Helper; import org.ethereum.util.ByteUtil; import org.ethereum.vm.DataWord; @@ -93,7 +108,7 @@ void testDoEXTCODEHASHWithoutArguments() { byte[] code = compiler.compile(stringCode); VM vm = new VM(vmConfig, precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); try { while (!program.isStopped()) { vm.step(program); @@ -111,7 +126,7 @@ private void executeExtCodeHash(String destAddress, int gasExpected, byte[] code byte[] code = compiler.compile(stringCode); VM vm = new VM(vmConfig, precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, activationConfig, code, invoke, transaction, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); while (!program.isStopped()) { vm.step(program); diff --git a/rskj-core/src/test/java/co/rsk/vm/VMExecutionTest.java b/rskj-core/src/test/java/co/rsk/vm/VMExecutionTest.java index f1bfa547bb9..548b4a6a2ab 100644 --- a/rskj-core/src/test/java/co/rsk/vm/VMExecutionTest.java +++ b/rskj-core/src/test/java/co/rsk/vm/VMExecutionTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.vm; import co.rsk.config.TestSystemProperties; @@ -25,6 +24,8 @@ import org.ethereum.config.Constants; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.core.BlockFactory; +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.crypto.HashUtil; import org.ethereum.util.ByteUtil; import org.ethereum.vm.*; @@ -607,7 +608,7 @@ void invalidTooFarJump() { @Test void dupnArgumentIsNotJumpdest() { byte[] code = compiler.compile("JUMPDEST DUPN 0x5b 0x5b"); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, null, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); BitSet jumpdestSet = program.getJumpdestSet(); @@ -622,7 +623,7 @@ void dupnArgumentIsNotJumpdest() { @Test void swapnArgumentIsNotJumpdest() { byte[] code = compiler.compile("JUMPDEST SWAPN 0x5b 0x5b"); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, null, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); BitSet jumpdestSet = program.getJumpdestSet(); @@ -871,7 +872,7 @@ private Program executeCodeWithActivationConfig(String code, int nsteps, Activat private Program executeCodeWithActivationConfig(byte[] code, int nsteps, ActivationConfig.ForBlock activations) { VM vm = new VM(vmConfig, precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke,null, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke,null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); for (int k = 0; k < nsteps; k++) { vm.step(program); @@ -886,7 +887,7 @@ private Program playCodeWithActivationConfig(String code, ActivationConfig.ForBl private Program playCodeWithActivationConfig(byte[] code, ActivationConfig.ForBlock activations) { VM vm = new VM(vmConfig, precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke,null, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke,null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); vm.play(program); diff --git a/rskj-core/src/test/java/co/rsk/vm/VMPerformanceTest.java b/rskj-core/src/test/java/co/rsk/vm/VMPerformanceTest.java index 17ac6c70be0..e0db1898cce 100644 --- a/rskj-core/src/test/java/co/rsk/vm/VMPerformanceTest.java +++ b/rskj-core/src/test/java/co/rsk/vm/VMPerformanceTest.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.vm; import co.rsk.config.TestSystemProperties; @@ -25,6 +24,8 @@ import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; import org.ethereum.core.BlockFactory; +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.util.ByteUtil; import org.ethereum.vm.DataWord; import org.ethereum.vm.OpCode; @@ -264,7 +265,7 @@ public long measureProgram(String opcode, byte[] code, int insCount, int divisor byte[] newCode = getClonedCode(code,cloneCount); - program = new Program(vmConfig, precompiledContracts, blockFactory, activations, newCode, invoke, null, new HashSet<>()); + program = new Program(vmConfig, precompiledContracts, blockFactory, activations, newCode, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); int sa = program.getStartAddr(); long myLoops = maxLoops / cloneCount; @@ -492,7 +493,7 @@ function fib() returns (uint r) { ------------------------------------------------------------------------------------------------------------------------------------------------------*/ byte[] code = Arrays.copyOfRange(codePlusPrefix,16,codePlusPrefix.length); - program =new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke, null, new HashSet<>()); + program =new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); //String s_expected_1 = "000000000000000000000000000000000000000000000000000000033FFC1244"; // 55 //String s_expected_1 = "00000000000000000000000000000000000000000000000000000002EE333961";// 50 @@ -603,7 +604,7 @@ void testFibonacciLongTime() { -----------------------------------------------------------------------------*/ void testRunTime(byte[] code, String s_expected) { - program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke, null, new HashSet<>()); + program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); System.out.println("-----------------------------------------------------------------------------"); System.out.println("Starting test...."); startMeasure(); diff --git a/rskj-core/src/test/java/co/rsk/vm/VMSpecificOpcodesPerformanceTest.java b/rskj-core/src/test/java/co/rsk/vm/VMSpecificOpcodesPerformanceTest.java index 6746193bdb4..f354bfbcedf 100644 --- a/rskj-core/src/test/java/co/rsk/vm/VMSpecificOpcodesPerformanceTest.java +++ b/rskj-core/src/test/java/co/rsk/vm/VMSpecificOpcodesPerformanceTest.java @@ -1,3 +1,20 @@ +/* + * This file is part of RskJ + * Copyright (C) 2017 RSK Labs Ltd. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package co.rsk.vm; import co.rsk.config.TestSystemProperties; @@ -11,9 +28,7 @@ import org.apache.commons.lang3.StringUtils; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Account; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.vm.PrecompiledContracts; import org.ethereum.vm.VM; import org.ethereum.vm.program.Program; @@ -183,7 +198,7 @@ void printResults(Stopwatch stopWatch, int gasCostPerCALLLoop) { } private Program getProgram(byte[] code, Transaction transaction) { - return new Program(vmConfig, precompiledContracts, blockFactory, getBlockchainConfig(), code, invoke, transaction, new HashSet<>()); + return new Program(vmConfig, precompiledContracts, blockFactory, getBlockchainConfig(), code, invoke, transaction, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } private byte[] compile(String code) { diff --git a/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestProgramInvokeFactory.java b/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestProgramInvokeFactory.java index 73510a8dce2..e19db998bad 100644 --- a/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestProgramInvokeFactory.java +++ b/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestProgramInvokeFactory.java @@ -16,13 +16,13 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package org.ethereum.jsontestsuite; import co.rsk.core.Coin; import co.rsk.core.RskAddress; import org.ethereum.core.Block; import org.ethereum.core.Repository; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.db.BlockStore; import org.ethereum.util.ByteUtil; @@ -46,8 +46,8 @@ public TestProgramInvokeFactory(Env env) { @Override - public ProgramInvoke createProgramInvoke(Transaction tx, int txindex, Block block, Repository repository, BlockStore blockStore) { - return generalInvoke(tx, txindex, repository, blockStore); + public ProgramInvoke createProgramInvoke(Transaction tx, int txindex, Block block, Repository repository, BlockStore blockStore, SignatureCache signatureCache) { + return generalInvoke(tx, txindex, repository, blockStore, signatureCache); } @Override @@ -59,7 +59,7 @@ public ProgramInvoke createProgramInvoke(Program program, DataWord toAddress, Da return null; } - private ProgramInvoke generalInvoke(Transaction tx, int txindex, Repository repository, BlockStore blockStore) { + private ProgramInvoke generalInvoke(Transaction tx, int txindex, Repository repository, BlockStore blockStore, SignatureCache signatureCache) { /*** ADDRESS op ***/ // YP: Get address of currently executing account. @@ -67,11 +67,11 @@ private ProgramInvoke generalInvoke(Transaction tx, int txindex, Repository repo /*** ORIGIN op ***/ // YP: This is the sender of original transaction; it is never a contract. - RskAddress origin = tx.getSender(); + RskAddress origin = tx.getSender(signatureCache); /*** CALLER op ***/ // YP: This is the address of the account that is directly responsible for this execution. - RskAddress caller = tx.getSender(); + RskAddress caller = tx.getSender(signatureCache); /*** BALANCE op ***/ Coin balance = repository.getBalance(addr); diff --git a/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestRunner.java b/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestRunner.java index 0b53e529f04..163f850211c 100644 --- a/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestRunner.java +++ b/rskj-core/src/test/java/org/ethereum/jsontestsuite/TestRunner.java @@ -282,7 +282,7 @@ public List runTestCase(TestCase testCase) { /* 3. Create Program - exec.code */ /* 4. run VM */ VM vm = new VM(vmConfig, precompiledContracts); - Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), exec.getCode(), programInvoke, null, new HashSet<>()); + Program program = new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), exec.getCode(), programInvoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); boolean vmDidThrowAnEception = false; Exception e = null; ThreadMXBean thread; diff --git a/rskj-core/src/test/java/org/ethereum/vm/ProgramMemoryTest.java b/rskj-core/src/test/java/org/ethereum/vm/ProgramMemoryTest.java index d22837d9d70..5baee30f601 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/ProgramMemoryTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/ProgramMemoryTest.java @@ -22,6 +22,8 @@ import co.rsk.config.TestSystemProperties; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.core.BlockFactory; +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.util.ByteUtil; import org.ethereum.vm.program.Program; import org.ethereum.vm.program.invoke.ProgramInvokeMockImpl; @@ -48,7 +50,8 @@ void createProgram() { program = new Program(config.getVmConfig(), new PrecompiledContracts(config, null), new BlockFactory(config.getActivationConfig()), mock(ActivationConfig.ForBlock.class), - ByteUtil.EMPTY_BYTE_ARRAY, pi, null, new HashSet<>()); + ByteUtil.EMPTY_BYTE_ARRAY, pi, null, new HashSet<>(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } @Test diff --git a/rskj-core/src/test/java/org/ethereum/vm/VMComplexTest.java b/rskj-core/src/test/java/org/ethereum/vm/VMComplexTest.java index 8c5be74d289..da8f30a89fd 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/VMComplexTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/VMComplexTest.java @@ -25,9 +25,7 @@ import co.rsk.core.RskAddress; import org.bouncycastle.util.encoders.Hex; import org.ethereum.config.blockchain.upgrades.ActivationConfig; -import org.ethereum.core.AccountState; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Repository; +import org.ethereum.core.*; import org.ethereum.crypto.HashUtil; import org.ethereum.vm.program.Program; import org.ethereum.vm.program.invoke.ProgramInvoke; @@ -696,6 +694,6 @@ private VM getSubject() { } private Program getProgram(byte[] code, ProgramInvoke pi) { - return new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, pi, null, new HashSet<>()); + return new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), code, pi, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } } diff --git a/rskj-core/src/test/java/org/ethereum/vm/VMCustomTest.java b/rskj-core/src/test/java/org/ethereum/vm/VMCustomTest.java index 454fca28fb4..54d585f752c 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/VMCustomTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/VMCustomTest.java @@ -26,6 +26,8 @@ import org.bouncycastle.util.encoders.Hex; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.core.BlockFactory; +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.util.ByteUtil; import org.ethereum.vm.program.Program; import org.ethereum.vm.program.Program.OutOfGasException; @@ -532,7 +534,7 @@ private VM getSubject() { } private Program getProgram(String ops) { - return new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), Hex.decode(ops), invoke, null, new HashSet<>()); + return new Program(vmConfig, precompiledContracts, blockFactory, mock(ActivationConfig.ForBlock.class), Hex.decode(ops), invoke, null, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } } diff --git a/rskj-core/src/test/java/org/ethereum/vm/VMTest.java b/rskj-core/src/test/java/org/ethereum/vm/VMTest.java index 7c7224cb044..c23cab5365e 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/VMTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/VMTest.java @@ -30,10 +30,7 @@ import org.bouncycastle.util.encoders.Hex; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Account; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.util.ByteUtil; import org.ethereum.util.Utils; import org.ethereum.vm.program.Program; @@ -3393,7 +3390,7 @@ private Program getProgram(byte[] code, Transaction transaction) { } private Program getProgram(byte[] code, Transaction transaction, boolean preFixStaticCall) { - return new Program(vmConfig, precompiledContracts, blockFactory, getBlockchainConfig(preFixStaticCall), code, invoke, transaction, new HashSet<>()); + return new Program(vmConfig, precompiledContracts, blockFactory, getBlockchainConfig(preFixStaticCall), code, invoke, transaction, new HashSet<>(), new BlockTxSignatureCache(new ReceivedTxSignatureCache())); } private byte[] compile(String code) { diff --git a/rskj-core/src/test/java/org/ethereum/vm/program/ProgramResultTest.java b/rskj-core/src/test/java/org/ethereum/vm/program/ProgramResultTest.java index 4290d330378..da0403c34ea 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/program/ProgramResultTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/program/ProgramResultTest.java @@ -1,7 +1,28 @@ +/* + * This file is part of RskJ + * Copyright (C) 2017 RSK Labs Ltd. + * (derived from ethereumJ library, Copyright (c) 2016 ) + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program 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 Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + */ package org.ethereum.vm.program; import co.rsk.config.TestSystemProperties; import java.math.BigInteger; + +import org.ethereum.core.BlockTxSignatureCache; +import org.ethereum.core.ReceivedTxSignatureCache; import org.ethereum.core.Transaction; import org.ethereum.crypto.ECKey; import org.ethereum.vm.DataWord; @@ -27,7 +48,8 @@ void add_internal_tx_one_level_Ok() { new ECKey().getAddress(), new byte[] {}, new byte[] {}, - "" + "", + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); Assertions.assertArrayEquals(originTx.getHash().getBytes(), internalTx.getOriginHash()); @@ -48,7 +70,8 @@ void add_interenal_tx_two_levels_Ok() { new ECKey().getAddress(), new byte[] {}, new byte[] {}, - "" + "", + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); InternalTransaction internalTx2 = programResult.addInternalTransaction( internalTx1, @@ -60,7 +83,8 @@ void add_interenal_tx_two_levels_Ok() { new ECKey().getAddress(), new byte[] {}, new byte[] {}, - "" + "", + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); Assertions.assertArrayEquals(originTx.getHash().getBytes(), internalTx2.getOriginHash()); @@ -84,7 +108,8 @@ void add_interenal_tx_many_levels_Ok() { new ECKey().getAddress(), new byte[] {}, new byte[] {}, - "" + "", + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); } InternalTransaction result = (InternalTransaction)internalTxN; diff --git a/rskj-core/src/test/java/org/ethereum/vm/program/ProgramTest.java b/rskj-core/src/test/java/org/ethereum/vm/program/ProgramTest.java index f6cbc3c55be..75bf6205d89 100644 --- a/rskj-core/src/test/java/org/ethereum/vm/program/ProgramTest.java +++ b/rskj-core/src/test/java/org/ethereum/vm/program/ProgramTest.java @@ -24,10 +24,7 @@ import com.google.common.collect.Sets; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ActivationConfigsForTest; -import org.ethereum.core.Block; -import org.ethereum.core.BlockFactory; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.vm.DataWord; import org.ethereum.vm.MessageCall; import org.ethereum.vm.PrecompiledContracts; @@ -111,7 +108,8 @@ void setup() { null, programInvoke, transaction, - Sets.newHashSet() + Sets.newHashSet(), + new BlockTxSignatureCache(new ReceivedTxSignatureCache()) ); program.getResult().spendGas(TOTAL_GAS); } From 1328fac06b9df68dedec51784826f84c329561e0 Mon Sep 17 00:00:00 2001 From: Nazaret Garcia Date: Fri, 30 Sep 2022 10:43:44 -0300 Subject: [PATCH 13/18] Adding signature cache to peg related files --- .../src/main/java/co/rsk/RskContext.java | 7 +- .../co/rsk/core/bc/TransactionPoolImpl.java | 2 +- .../rsk/net/handler/TxPendingValidator.java | 4 +- ...TxValidatorIntrinsicGasLimitValidator.java | 10 +- .../co/rsk/peg/AddressBasedAuthorizer.java | 6 +- .../src/main/java/co/rsk/peg/Bridge.java | 21 +- .../main/java/co/rsk/peg/BridgeSupport.java | 32 +- .../java/co/rsk/peg/BridgeSupportFactory.java | 15 +- .../src/main/java/co/rsk/peg/BridgeUtils.java | 28 +- .../rsk/peg/utils/BridgeEventLoggerImpl.java | 10 +- .../peg/utils/BrigeEventLoggerLegacyImpl.java | 25 +- .../java/co/rsk/remasc/RemascTransaction.java | 6 +- .../java/org/ethereum/core/Transaction.java | 4 +- .../ethereum/core/TransactionExecutor.java | 6 +- .../org/ethereum/vm/PrecompiledContracts.java | 19 +- .../src/test/java/co/rsk/TestHelpers/Tx.java | 5 +- .../java/co/rsk/core/CallContractTest.java | 6 +- .../java/co/rsk/core/TransactionTest.java | 5 +- .../co/rsk/core/bc/BlockExecutorTest.java | 9 +- .../java/co/rsk/mine/MinerServerTest.java | 2 +- .../test/java/co/rsk/mine/MinerUtilsTest.java | 38 +- .../co/rsk/mine/TransactionModuleTest.java | 9 +- .../java/co/rsk/net/SyncProcessorTest.java | 6 +- .../quota/TxVirtualGasCalculatorTest.java | 4 - ...lidatorIntrinsicGasLimitValidatorTest.java | 7 +- .../test/java/co/rsk/pcc/AltBN128Test.java | 5 +- .../blockheader/BlockHeaderContractTest.java | 9 +- .../rsk/peg/AddressBasedAuthorizerTest.java | 12 +- .../test/java/co/rsk/peg/BridgeCostsTest.java | 21 +- .../rsk/peg/BridgeRSKIP220NewMethodsTest.java | 8 +- .../co/rsk/peg/BridgeSupportFlyoverTest.java | 29 +- .../BridgeSupportRSKIP220NewMethodsTest.java | 9 +- .../rsk/peg/BridgeSupportReleaseBtcTest.java | 31 +- .../java/co/rsk/peg/BridgeSupportTest.java | 222 ++++++---- .../rsk/peg/BridgeSupportTestIntegration.java | 44 +- .../src/test/java/co/rsk/peg/BridgeTest.java | 32 +- .../co/rsk/peg/BridgeTestIntegration.java | 414 ++++++++++-------- .../test/java/co/rsk/peg/BridgeUtilsTest.java | 8 +- .../java/co/rsk/peg/RskForksBridgeTest.java | 2 +- .../BridgePerformanceTestCase.java | 10 +- .../peg/utils/BridgeEventLoggerImplTest.java | 20 +- .../BridgeEventLoggerLegacyImplTest.java | 9 +- .../remasc/RemascProcessMinerFeesTest.java | 6 +- .../rsk/remasc/RemascStorageProviderTest.java | 6 +- .../java/co/rsk/remasc/RemascTestRunner.java | 4 +- .../co/rsk/rpc/modules/eth/EthModuleTest.java | 11 +- .../src/test/java/co/rsk/test/World.java | 7 +- .../co/rsk/test/builders/BlockBuilder.java | 2 +- .../rsk/test/builders/BlockChainBuilder.java | 7 +- .../test/builders/BridgeSupportBuilder.java | 13 +- .../BlockTxsValidationRuleTest.java | 12 +- .../src/test/java/co/rsk/vm/Create2Test.java | 4 +- .../test/java/co/rsk/vm/ExtCodeHashTest.java | 3 +- .../src/test/java/co/rsk/vm/MinerHelper.java | 6 +- .../test/java/co/rsk/vm/VMExecutionTest.java | 2 +- .../java/co/rsk/vm/VMPerformanceTest.java | 10 +- .../vm/VMSpecificOpcodesPerformanceTest.java | 2 +- .../PrecompiledContractAddressTests.java | 5 +- .../precompiles/PrecompiledContractTest.java | 4 +- .../core/TransactionExecutorTest.java | 23 +- .../org/ethereum/core/TransactionTest.java | 16 +- .../ethereum/jsontestsuite/TestRunner.java | 3 +- .../runners/StateTestRunner.java | 10 +- .../org/ethereum/rpc/Web3ImplLogsTest.java | 2 +- .../org/ethereum/rpc/Web3ImplScoringTest.java | 3 +- .../java/org/ethereum/rpc/Web3ImplTest.java | 27 +- .../rpc/dto/TransactionReceiptDTOTest.java | 8 +- .../org/ethereum/util/EthModuleTestUtils.java | 2 +- .../ethereum/vm/PrecompiledContractTest.java | 4 +- .../org/ethereum/vm/ProgramMemoryTest.java | 2 +- .../java/org/ethereum/vm/VMComplexTest.java | 3 +- .../java/org/ethereum/vm/VMCustomTest.java | 2 +- .../src/test/java/org/ethereum/vm/VMTest.java | 3 +- .../vm/program/NestedContractsTest.java | 4 +- .../org/ethereum/vm/program/ProgramTest.java | 2 +- 75 files changed, 834 insertions(+), 555 deletions(-) diff --git a/rskj-core/src/main/java/co/rsk/RskContext.java b/rskj-core/src/main/java/co/rsk/RskContext.java index 499f3ca54e0..c8a5fcbe65e 100644 --- a/rskj-core/src/main/java/co/rsk/RskContext.java +++ b/rskj-core/src/main/java/co/rsk/RskContext.java @@ -485,7 +485,10 @@ public synchronized PrecompiledContracts getPrecompiledContracts() { checkIfNotClosed(); if (precompiledContracts == null) { - precompiledContracts = new PrecompiledContracts(getRskSystemProperties(), getBridgeSupportFactory()); + precompiledContracts = new PrecompiledContracts( + getRskSystemProperties(), + getBridgeSupportFactory(), + getBlockTxSignatureCache()); } return precompiledContracts; @@ -497,7 +500,7 @@ public synchronized BridgeSupportFactory getBridgeSupportFactory() { if (bridgeSupportFactory == null) { bridgeSupportFactory = new BridgeSupportFactory(getBtcBlockStoreFactory(), getRskSystemProperties().getNetworkConstants().getBridgeConstants(), - getRskSystemProperties().getActivationConfig()); + getRskSystemProperties().getActivationConfig(), getBlockTxSignatureCache()); } return bridgeSupportFactory; diff --git a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java index 047cf2ef547..1b784dd62fc 100644 --- a/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java +++ b/rskj-core/src/main/java/co/rsk/core/bc/TransactionPoolImpl.java @@ -487,7 +487,7 @@ private Coin getTxBaseCost(Transaction tx) { } private long getTransactionCost(Transaction tx, long number) { - return tx.transactionCost(config.getNetworkConstants(), config.getActivationConfig().forBlock(number)); + return tx.transactionCost(config.getNetworkConstants(), config.getActivationConfig().forBlock(number), signatureCache); } } diff --git a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java index 1a67e859865..d7dd18ff540 100644 --- a/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java +++ b/rskj-core/src/main/java/co/rsk/net/handler/TxPendingValidator.java @@ -64,7 +64,7 @@ public TxPendingValidator(Constants constants, ActivationConfig activationConfig validatorSteps.add(new TxValidatorNonceRangeValidator(accountSlots)); validatorSteps.add(new TxValidatorAccountBalanceValidator()); validatorSteps.add(new TxValidatorMinimuGasPriceValidator()); - validatorSteps.add(new TxValidatorIntrinsicGasLimitValidator(constants, activationConfig)); + validatorSteps.add(new TxValidatorIntrinsicGasLimitValidator(constants, activationConfig, signatureCache)); validatorSteps.add(new TxValidatorMaximumGasPriceValidator(activationConfig)); } @@ -72,7 +72,7 @@ public TransactionValidationResult isValid(Transaction tx, Block executionBlock, BigInteger blockGasLimit = BigIntegers.fromUnsignedByteArray(executionBlock.getGasLimit()); Coin minimumGasPrice = executionBlock.getMinimumGasPrice(); long bestBlockNumber = executionBlock.getNumber(); - long basicTxCost = tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber)); + long basicTxCost = tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber), signatureCache); if (state == null && basicTxCost != 0) { logger.trace("[tx={}, sender={}] account doesn't exist", tx.getHash(), tx.getSender(signatureCache)); diff --git a/rskj-core/src/main/java/co/rsk/net/handler/txvalidator/TxValidatorIntrinsicGasLimitValidator.java b/rskj-core/src/main/java/co/rsk/net/handler/txvalidator/TxValidatorIntrinsicGasLimitValidator.java index eab810cc340..6ac70394496 100644 --- a/rskj-core/src/main/java/co/rsk/net/handler/txvalidator/TxValidatorIntrinsicGasLimitValidator.java +++ b/rskj-core/src/main/java/co/rsk/net/handler/txvalidator/TxValidatorIntrinsicGasLimitValidator.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.net.handler.txvalidator; import co.rsk.core.Coin; @@ -35,15 +34,20 @@ public class TxValidatorIntrinsicGasLimitValidator implements TxValidatorStep { private final Constants constants; private final ActivationConfig activationConfig; + private final SignatureCache signatureCache; - public TxValidatorIntrinsicGasLimitValidator(Constants constants, ActivationConfig activationConfig) { + public TxValidatorIntrinsicGasLimitValidator( + Constants constants, + ActivationConfig activationConfig, + SignatureCache signatureCache) { this.constants = constants; this.activationConfig = activationConfig; + this.signatureCache = signatureCache; } @Override public TransactionValidationResult validate(Transaction tx, @Nullable AccountState state, BigInteger gasLimit, Coin minimumGasPrice, long bestBlockNumber, boolean isFreeTx) { - if (BigInteger.valueOf(tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber))).compareTo(tx.getGasLimitAsInteger()) <= 0) { + if (BigInteger.valueOf(tx.transactionCost(constants, activationConfig.forBlock(bestBlockNumber), signatureCache)).compareTo(tx.getGasLimitAsInteger()) <= 0) { return TransactionValidationResult.ok(); } diff --git a/rskj-core/src/main/java/co/rsk/peg/AddressBasedAuthorizer.java b/rskj-core/src/main/java/co/rsk/peg/AddressBasedAuthorizer.java index 4d6e537c14e..3ef1101b0ce 100644 --- a/rskj-core/src/main/java/co/rsk/peg/AddressBasedAuthorizer.java +++ b/rskj-core/src/main/java/co/rsk/peg/AddressBasedAuthorizer.java @@ -15,10 +15,10 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import co.rsk.core.RskAddress; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.crypto.ECKey; @@ -48,8 +48,8 @@ public boolean isAuthorized(RskAddress sender) { .anyMatch(address -> Arrays.equals(address, sender.getBytes())); } - public boolean isAuthorized(Transaction tx) { - return isAuthorized(tx.getSender()); + public boolean isAuthorized(Transaction tx, SignatureCache signatureCache) { + return isAuthorized(tx.getSender(signatureCache)); } public int getNumberOfAuthorizedKeys() { diff --git a/rskj-core/src/main/java/co/rsk/peg/Bridge.java b/rskj-core/src/main/java/co/rsk/peg/Bridge.java index ba7cd5003fa..26cfa216238 100644 --- a/rskj-core/src/main/java/co/rsk/peg/Bridge.java +++ b/rskj-core/src/main/java/co/rsk/peg/Bridge.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import co.rsk.bitcoinj.core.*; @@ -35,10 +34,7 @@ import org.ethereum.config.Constants; import org.ethereum.config.blockchain.upgrades.ActivationConfig; import org.ethereum.config.blockchain.upgrades.ConsensusRule; -import org.ethereum.core.Block; -import org.ethereum.core.CallTransaction; -import org.ethereum.core.Repository; -import org.ethereum.core.Transaction; +import org.ethereum.core.*; import org.ethereum.db.BlockStore; import org.ethereum.db.ReceiptStore; import org.ethereum.util.ByteUtil; @@ -228,20 +224,23 @@ public class Bridge extends PrecompiledContracts.PrecompiledContract { private final BiFunction, Integer, MerkleBranch> merkleBranchFactory; + private final SignatureCache signatureCache; + public Bridge(RskAddress contractAddress, Constants constants, ActivationConfig activationConfig, - BridgeSupportFactory bridgeSupportFactory) { - this(contractAddress, constants, activationConfig, bridgeSupportFactory, MerkleBranch::new); + BridgeSupportFactory bridgeSupportFactory, SignatureCache signatureCache) { + this(contractAddress, constants, activationConfig, bridgeSupportFactory, MerkleBranch::new, signatureCache); } @VisibleForTesting Bridge(RskAddress contractAddress, Constants constants, ActivationConfig activationConfig, - BridgeSupportFactory bridgeSupportFactory, BiFunction, Integer, MerkleBranch> merkleBranchFactory) { + BridgeSupportFactory bridgeSupportFactory, BiFunction, Integer, MerkleBranch> merkleBranchFactory, SignatureCache signatureCache) { this.bridgeSupportFactory = bridgeSupportFactory; this.contractAddress = contractAddress; this.constants = constants; this.bridgeConstants = constants.getBridgeConstants(); this.activationConfig = activationConfig; this.merkleBranchFactory = merkleBranchFactory; + this.signatureCache = signatureCache; } @Override @@ -251,7 +250,7 @@ public long getGasForData(byte[] data) { throw new NullPointerException(); } - if (BridgeUtils.isFreeBridgeTx(rskTx, constants, activations)) { + if (BridgeUtils.isFreeBridgeTx(rskTx, constants, activations, signatureCache)) { return 0; } @@ -1235,8 +1234,8 @@ public static BridgeMethods.BridgeMethodExecutor activeAndRetiringFederationOnly return (self, args) -> { Federation retiringFederation = self.bridgeSupport.getRetiringFederation(); - if (!BridgeUtils.isFromFederateMember(self.rskTx, self.bridgeSupport.getActiveFederation()) - && (retiringFederation == null || !BridgeUtils.isFromFederateMember(self.rskTx, retiringFederation))) { + if (!BridgeUtils.isFromFederateMember(self.rskTx, self.bridgeSupport.getActiveFederation(), self.signatureCache) + && (retiringFederation == null || !BridgeUtils.isFromFederateMember(self.rskTx, retiringFederation, self.signatureCache))) { String errorMessage = String.format("Sender is not part of the active or retiring federations, so he is not enabled to call the function '%s'",funcName); logger.warn(errorMessage); throw new VMException(errorMessage); diff --git a/rskj-core/src/main/java/co/rsk/peg/BridgeSupport.java b/rskj-core/src/main/java/co/rsk/peg/BridgeSupport.java index 71ef75c2e3d..2dd547c919d 100644 --- a/rskj-core/src/main/java/co/rsk/peg/BridgeSupport.java +++ b/rskj-core/src/main/java/co/rsk/peg/BridgeSupport.java @@ -15,7 +15,6 @@ * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ - package co.rsk.peg; import co.rsk.bitcoinj.core.Address; @@ -87,6 +86,7 @@ import org.ethereum.config.blockchain.upgrades.ConsensusRule; import org.ethereum.core.Block; import org.ethereum.core.Repository; +import org.ethereum.core.SignatureCache; import org.ethereum.core.Transaction; import org.ethereum.crypto.ECKey; import org.ethereum.crypto.HashUtil; @@ -172,6 +172,8 @@ public class BridgeSupport { private final org.ethereum.core.Block rskExecutionBlock; private final ActivationConfig.ForBlock activations; + private final SignatureCache signatureCache; + protected enum TxType { PEGIN, PEGOUT, @@ -190,7 +192,8 @@ public BridgeSupport( Context btcContext, FederationSupport federationSupport, BtcBlockStoreWithCache.Factory btcBlockStoreFactory, - ActivationConfig.ForBlock activations) { + ActivationConfig.ForBlock activations, + SignatureCache signatureCache) { this.rskRepository = repository; this.provider = provider; this.rskExecutionBlock = executionBlock; @@ -202,6 +205,7 @@ public BridgeSupport( this.federationSupport = federationSupport; this.btcBlockStoreFactory = btcBlockStoreFactory; this.activations = activations; + this.signatureCache = signatureCache; } public List getSubtraces() { @@ -774,7 +778,7 @@ private void saveNewUTXOs(BtcTransaction btcTx) throws IOException { */ public void releaseBtc(Transaction rskTx) throws IOException { Coin value = rskTx.getValue().toBitcoin(); - final RskAddress senderAddress = rskTx.getSender(); + final RskAddress senderAddress = rskTx.getSender(signatureCache); //as we can't send btc from contracts we want to send them back to the senderAddressStr if (BridgeUtils.isContractTx(rskTx)) { logger.trace("Contract {} tried to release funds. Release is just allowed from standard accounts.", rskTx); @@ -864,7 +868,7 @@ private void requestRelease(Address destinationAddress, Coin value, Transaction if (activations.isActive(ConsensusRule.RSKIP185)) { refundAndEmitRejectEvent( value, - rskTx.getSender(), + rskTx.getSender(signatureCache), optionalRejectedPegoutReason.get() ); } @@ -876,7 +880,7 @@ private void requestRelease(Address destinationAddress, Coin value, Transaction } if (activations.isActive(ConsensusRule.RSKIP185)) { - eventLogger.logReleaseBtcRequestReceived(rskTx.getSender().toHexString(), destinationAddress, value); + eventLogger.logReleaseBtcRequestReceived(rskTx.getSender(signatureCache).toHexString(), destinationAddress, value); } logger.info("releaseBtc successful to {}. Tx {}. Value {}.", destinationAddress, rskTx, value); } @@ -2104,7 +2108,7 @@ public Integer voteFederationChange(Transaction tx, ABICallSpec callSpec) throws AddressBasedAuthorizer authorizer = bridgeConstants.getFederationChangeAuthorizer(); // Must be authorized to vote (checking for signature) - if (!authorizer.isAuthorized(tx)) { + if (!authorizer.isAuthorized(tx, signatureCache)) { return FEDERATION_CHANGE_GENERIC_ERROR_CODE; } @@ -2124,7 +2128,7 @@ public Integer voteFederationChange(Transaction tx, ABICallSpec callSpec) throws ABICallElection election = provider.getFederationElection(authorizer); // Register the vote. It is expected to succeed, since all previous checks succeeded - if (!election.vote(callSpec, tx.getSender())) { + if (!election.vote(callSpec, tx.getSender(signatureCache))) { logger.warn("Unexpected federation change vote failure"); return FEDERATION_CHANGE_GENERIC_ERROR_CODE; } @@ -2369,7 +2373,7 @@ private Integer addLockWhitelistAddress(Transaction tx, LockWhitelistEntry entry private boolean isLockWhitelistChangeAuthorized(Transaction tx) { AddressBasedAuthorizer authorizer = bridgeConstants.getLockWhitelistChangeAuthorizer(); - return authorizer.isAuthorized(tx); + return authorizer.isAuthorized(tx, signatureCache); } /** @@ -2421,7 +2425,7 @@ public Coin getMinimumPeginTxValue() { */ public Integer voteFeePerKbChange(Transaction tx, Coin feePerKb) { AddressBasedAuthorizer authorizer = bridgeConstants.getFeePerKbChangeAuthorizer(); - if (!authorizer.isAuthorized(tx)) { + if (!authorizer.isAuthorized(tx, signatureCache)) { return FEE_PER_KB_GENERIC_ERROR_CODE; } @@ -2435,7 +2439,7 @@ public Integer voteFeePerKbChange(Transaction tx, Coin feePerKb) { ABICallElection feePerKbElection = provider.getFeePerKbElection(authorizer); ABICallSpec feeVote = new ABICallSpec("setFeePerKb", new byte[][]{BridgeSerializationUtils.serializeCoin(feePerKb)}); - boolean successfulVote = feePerKbElection.vote(feeVote, tx.getSender()); + boolean successfulVote = feePerKbElection.vote(feeVote, tx.getSender(signatureCache)); if (!successfulVote) { return -1; } @@ -2517,8 +2521,8 @@ public Optional