use of co.rsk.metrics.profilers.Metric in project rskj by rsksmart.
the class TransactionExecutor method go.
private void go() {
// TODO: transaction call for pre-compiled contracts
if (vm == null) {
cacheTrack.commit();
return;
}
logger.trace("Go transaction {} {}", toBI(tx.getNonce()), tx.getHash());
// Set the deleted accounts in the block in the remote case there is a CREATE2 creating a deleted account
Metric metric = profiler.start(Profiler.PROFILING_TYPE.VM_EXECUTE);
try {
// Charge basic cost of the transaction
program.spendGas(tx.transactionCost(constants, activations), "TRANSACTION COST");
vm.play(program);
result = program.getResult();
gasLeftover = GasCost.subtract(GasCost.toGas(tx.getGasLimit()), program.getResult().getGasUsed());
if (tx.isContractCreation() && !result.isRevert()) {
createContract();
}
if (result.getException() != null || result.isRevert()) {
result.clearFieldsOnException();
cacheTrack.rollback();
if (result.getException() != null) {
throw result.getException();
} else {
execError("REVERT opcode executed");
}
}
} catch (Exception e) {
cacheTrack.rollback();
gasLeftover = 0;
execError(e);
result.setException(e);
profiler.stop(metric);
return;
}
cacheTrack.commit();
profiler.stop(metric);
}
use of co.rsk.metrics.profilers.Metric in project rskj by rsksmart.
the class TransactionExecutor method call.
private void call() {
logger.trace("Call transaction {} {}", toBI(tx.getNonce()), tx.getHash());
RskAddress targetAddress = tx.getReceiveAddress();
// DataWord(targetAddress)) can fail with exception:
// java.lang.RuntimeException: Data word can't exceed 32 bytes:
// if targetAddress size is greater than 32 bytes.
// But init() will detect this earlier
precompiledContract = precompiledContracts.getContractForAddress(activations, DataWord.valueOf(targetAddress.getBytes()));
this.subtraces = new ArrayList<>();
if (precompiledContract != null) {
Metric metric = profiler.start(Profiler.PROFILING_TYPE.PRECOMPILED_CONTRACT_INIT);
precompiledContract.init(tx, executionBlock, track, blockStore, receiptStore, result.getLogInfoList());
profiler.stop(metric);
metric = profiler.start(Profiler.PROFILING_TYPE.PRECOMPILED_CONTRACT_EXECUTE);
long requiredGas = precompiledContract.getGasForData(tx.getData());
long txGasLimit = GasCost.toGas(tx.getGasLimit());
long gasUsed = GasCost.add(requiredGas, basicTxCost);
if (!localCall && !enoughGas(txGasLimit, requiredGas, gasUsed)) {
// no refund no endowment
execError(String.format("Out of Gas calling precompiled contract at block %d " + "for address 0x%s. required: %s, used: %s, left: %s ", executionBlock.getNumber(), targetAddress.toString(), requiredGas, gasUsed, gasLeftover));
gasLeftover = 0;
profiler.stop(metric);
return;
}
gasLeftover = activations.isActive(ConsensusRule.RSKIP136) ? GasCost.subtract(txGasLimit, gasUsed) : txGasLimit - gasUsed;
// FIXME: save return for vm trace
try {
byte[] out = precompiledContract.execute(tx.getData());
this.subtraces = precompiledContract.getSubtraces();
result.setHReturn(out);
if (!track.isExist(targetAddress)) {
track.createAccount(targetAddress);
track.setupContract(targetAddress);
} else if (!track.isContract(targetAddress)) {
track.setupContract(targetAddress);
}
} catch (VMException | RuntimeException e) {
result.setException(e);
}
result.spendGas(gasUsed);
profiler.stop(metric);
} else {
byte[] code = track.getCode(targetAddress);
// Code can be null
if (isEmpty(code)) {
gasLeftover = GasCost.subtract(GasCost.toGas(tx.getGasLimit()), basicTxCost);
result.spendGas(basicTxCost);
} else {
ProgramInvoke programInvoke = programInvokeFactory.createProgramInvoke(tx, txindex, executionBlock, cacheTrack, blockStore);
this.vm = new VM(vmConfig, precompiledContracts);
this.program = new Program(vmConfig, precompiledContracts, blockFactory, activations, code, programInvoke, tx, deletedAccounts);
}
}
if (result.getException() == null) {
Coin endowment = tx.getValue();
cacheTrack.transfer(tx.getSender(), targetAddress, endowment);
}
}
use of co.rsk.metrics.profilers.Metric in project rskj by rsksmart.
the class LevelDbDataSource method put.
@Override
public byte[] put(byte[] key, byte[] value) {
Objects.requireNonNull(key);
Objects.requireNonNull(value);
Metric metric = profiler.start(Profiler.PROFILING_TYPE.DB_WRITE);
resetDbLock.readLock().lock();
try {
if (logger.isTraceEnabled()) {
logger.trace("~> LevelDbDataSource.put(): {}, key: {}, return length: {}", name, ByteUtil.toHexString(key), value.length);
}
db.put(key, value);
if (logger.isTraceEnabled()) {
logger.trace("<~ LevelDbDataSource.put(): {}, key: {}, return length: {}", name, ByteUtil.toHexString(key), value.length);
}
return value;
} finally {
resetDbLock.readLock().unlock();
profiler.stop(metric);
}
}
use of co.rsk.metrics.profilers.Metric in project rskj by rsksmart.
the class LevelDbDataSource method close.
@Override
public void close() {
Metric metric = profiler.start(Profiler.PROFILING_TYPE.LEVEL_DB_CLOSE);
resetDbLock.writeLock().lock();
try {
if (!isAlive()) {
return;
}
try {
logger.debug("Close db: {}", name);
db.close();
alive = false;
} catch (IOException e) {
logger.error("Failed to find the db file on the close: {} ", name);
panicProcessor.panic("leveldb", String.format("Failed to find the db file on the close: %s", name));
}
} finally {
resetDbLock.writeLock().unlock();
profiler.stop(metric);
}
}
use of co.rsk.metrics.profilers.Metric in project rskj by rsksmart.
the class LevelDbDataSource method delete.
@Override
public void delete(byte[] key) {
Metric metric = profiler.start(Profiler.PROFILING_TYPE.DB_WRITE);
resetDbLock.readLock().lock();
try {
if (logger.isTraceEnabled()) {
logger.trace("~> LevelDbDataSource.delete(): {}, key: {}", name, ByteUtil.toHexString(key));
}
db.delete(key);
if (logger.isTraceEnabled()) {
logger.trace("<~ LevelDbDataSource.delete(): {}, key: {}", name, ByteUtil.toHexString(key));
}
} finally {
resetDbLock.readLock().unlock();
profiler.stop(metric);
}
}
Aggregations