Skip to content

Commit

Permalink
Add vmmap RPC and EVM hash indexes (#2018)
Browse files Browse the repository at this point in the history
* Add send to try block

* Fix Linux builds

* Fix eth_* RPC casing

* Ignore *.bin from persistent state

* Use a single-use context when context == 0

* Panic when wrong input format

* Change to_eth_case fallback to lowercase casing

* Use owner address as Eth miner address

* Fix test build on Linux

* Get updated owner for EVM miner if changed

* Fix make.sh git hook, unsafe complaints

* Fix commiting the test path

* Update pkg_name with correct one

* Switch to pre-commit hook to pre-push

* Fix to_eth_case for non eth_* RPCs

* Add Eth_Accounts RPC (#1916)

* Add Eth_Accounts RPC

* Return only Eth addresses in eth_accounts RPC

* Resolve issues with RPC and address behaviour (#1919)

* Simpler impl with #[rpc(server) macro

* Clippy cleanup

* Revert test changes

* Cargo fmt

* Quick fix

* Add latest fork to getblockchaininfo

* Bump regtest grpc ports to avoid conflict with devnet

* Update RPC

* Skip IsMine for destination address

* Write Eth address on creation

---------

Co-authored-by: jouzo <jdesclercs@gmail.com>
Co-authored-by: Shoham Chakraborty <shhmchk@gmail.com>

* Reset fork height

* Devnet hard fork at 1,586,750

* Fix eth_call output

* Run individual Python tests via make.sh

* Fix hex import

* For mocknet use operator key as miner address

* Cleanup RPC/gRPC server codegen (#1922)

* Cleanup RPC/gRPC server codegen

* Fix warnings

* Additional cleanup and prettyplease types output

* add hashrate RPC (#1921)

* Restore load evm state on startup

* Add mc_getState RPC call to debug EVMState + cleanup

* Fix eth_hashrate

* Add mock eth_gasPrice RPC

* Add back eth_accounts logic for RPC (#1923)

* Add few example debug call

* Add evm balances to gettokenbalances (#1924)

* WIP add EVM balances to gettokenbalances

* Correct variable name

* Add feature_evm to runnable tests

* Remove combined log from test_py

* Convert WEI to Sats

* Do not try and restore inputs on an EVM TX

* Add used_gas to TxResponse

* Resolve datadir through FFI (#1925)

* Resolve datadir through FFI

* Fix format

* Create evm dir

* Fix EVM TX sending and receiving

* Check nonce in EVM TX

* Clean up rust double builds, respect debug builds

* Add cargo.toml workaround undefined symbols

* Disable unviable tests

* Cleanup

* fmt

* Implement evm RPC into test framework (#1926)

* Remove script test case that uses OP_SHA3 opcode

* Modification of test framework to connect to evm RPC, and to correctly handle evm RPC to the correct jsonrpc port on defid node

* Fix bug to not remove evm directory after initializing chain

* Fix rpc_help functional test to include evm component. Fix rust lib env_logger to direct logs to stdout instead of the default stderr.

* Create eth_rpc port and url utility functions, included chain initialization of ethrpcport inside datadir

* Revert args in test-py

* Add EVM JSON RPC port into chain param (#1929)

* New port in chain params for eth-json-rpc. includes pipeline to read new arg ethrpcport when starting node.

* Using ..50 for GRPC and ..51 for ETH JRPC

* Fix port numbers

* Update lib/ain-grpc/src/lib.rs

* Update make.sh

* Update make.sh

---------

Co-authored-by: Bushstar <bushsolo@gmail.com>
Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>

* Clean up builds.rs, separate ffi impls and stub tests

* Cleanup warnings, fmt

* evm: Rename finalize_block (#1928)

* Rename finalize_block

* Revert "Rename finalize_block"

This reverts commit efdfbc3.

* Rename FFI call

* Fixes to CI build workflows for dev, staging and production pipelines into feature/evm (#1906)

* Enable aarch64-apple-darwin builds (#1893) (#1894)

* Build pipeline for building on arm64 macOS host architecture. Included CI build workflow for building the arm64 binaries

* Rename to aarch64-apple-darwin to resolve build dependency bug

* Amended markdown documentation

(cherry picked from commit 29e10be)

* CI workflow fixes for dev, staging and production pipelines

* Fix naming bug

* Removed publishing to dockerhub pipeline in build staging workflow, and renamed "mac" to "osx"

* Added workflow to push arm build image into Dockerhub. Rename docker tag convention to differentiate arm and x64 build images.

* Fix docker tags

* Reverting changes to pushing only linux-x64 into dockerhub registry.

* Include image layer to install rust dependencies

* Install protobuf-compiler pkg dep

* bug fixes

* Fix bug in pkg_local_ensure_osx_sysroot function that does not exit out of entered dir if the package exists. Include new gnu-tar support for macos in platform_init function to support tar --transform on macos

* Install target toolchains in dockerfiles

* Fix target toolchain for linux-arm docker build

* Resolve rustc toolchain bug

* Removed optional label in proto3 syntax to fix build error

* Fix _tar func in make.sh to pass all args to gnu-tar, and fix docker release build workflow to only push x64 linux to docker registry.

* Re-order build targets to select major dev envs first.

* Fix merge errors

* Revert to feature/evm branch version

* Reverting eth.proto version to feature/evm version
t Please enter the commit message for your changes. Lines starting

* Debug fail tx

* Add exit_reason to validate_raw_tx Err

* Get block difficulty and chain work of block via CPP FFI (#1931)

* FFI: Get block difficulty and chain work of block

* Pass difficulty to finalise_block

* Do not store total_difficulty

* Move start servers to AppInitMain (#1930)

* Add EVM functional tests (#1932)

* Cleanup RPC error

* Initial functional test of EVM rpc

* Metachain JSON-RPC CLI (#1934)

* Cleanup RPC error

* Initial functional test of EVM rpc

* Metachain JSON-RPC CLI

* Format output

* Fix help message

* Move default target into build-dir

* Add missing size field to RpcBlock (#1935)

* Fix rust release build detection, build rs change detect, move types out of source (#1936)

* Cleanup make.sh

* Use gcc for depends

* Add debug-env

* Revert the rust, proto change in dockerfiles (#1937)

* fix build and make.sh script

* Update make.sh

---------

Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>

* evm: Transaction receipts (#1927)

* Minor make.sh cleanups

* Mark items that needs fixing

* Add git tree dirty check on hook

* Add 0x to block size

* Set block gas limit

* Resolve make check errors (#1939)

* eth_getpendingtransactions (#1933)

* WIP eth_getpendingtransactions

* Update for base branch and fmt

* Complete eth_pendingTransactions impl

* rustfmt rpc.rs

* Move code to impls.rs

* Fix errors on git push

* Resolve compile errors after merge

* Test EVM Tx showing in EVM block

* Corrections

* Cargo fmt

* Use helper functions

* evm: Update get_contract_address to return H160 (#1942)

* Change get_contract_address to return H160

* Update test

* Remove todo note

* Add beneficiary, logs_bloom and gas_used to block (#1945)

* Add deprecated mining stubs (#1943)

* fix(lib/ain-cpp-imports): conditionally specific stdlib (#1948)

* conditionally target lib based on diff os

* fmt

* use macro for conditinal compilation

* Add lab project scaffolds  (#1938)

* Add scaffold for grpc-v2

* Add flatten serde checks

* Use Request/Response convention to avoid confusion with `Result` types

* Add missing doc for RPCs

* Add 0x to block size

* Set block gas limit

* Resolve make check errors (#1939)

* eth_getpendingtransactions (#1933)

* WIP eth_getpendingtransactions

* Update for base branch and fmt

* Complete eth_pendingTransactions impl

* rustfmt rpc.rs

* Move code to impls.rs

* Fix errors on git push

* Resolve compile errors after merge

* Test EVM Tx showing in EVM block

* Corrections

* Cargo fmt

* Use helper functions

* Use untagged enums

* Cleanup, add servers

* Cleanup mod

* Add part of missing doc for proto messages

* Add missing doc for proto messages

* evm: Update get_contract_address to return H160 (#1942)

* Change get_contract_address to return H160

* Update test

* Remove todo note

* Add beneficiary, logs_bloom and gas_used to block (#1945)

* Add deprecated mining stubs (#1943)

* fix(lib/ain-cpp-imports): conditionally specific stdlib (#1948)

* conditionally target lib based on diff os

* fmt

* use macro for conditinal compilation

* Cleanup gitignore

* Add lab crates

* Enable rust build

* cargo fmt

---------

Co-authored-by: DrPing <drping974@proton.me>
Co-authored-by: Bushstar <bushsolo@gmail.com>
Co-authored-by: Shoham Chakraborty <shhmchk@gmail.com>
Co-authored-by: Jouzo <15011228+Jouzo@users.noreply.github.com>
Co-authored-by: canonbrother <w.canonbrother@gmail.com>

* Use protobuf-src instead of external dep

* Remove protoc lib includes

* Resolve depends build issues

* Consolidate persistent state to BlockchainDataHandler struct (#1944)

* Consolidate persistent state to BlockchainDataHandler struct

* Update cache after cache miss

* Get receipts root before creating block

* Update deps, add protobuf-src into runtime deps

* Fix protobuf-src compilation

* Use self contained rust toolchain

* CI workflow for EVM RPC testing (#1821)

* Add workflow for testing evm rpc

* Add test workflow for EVM RPCs

* Rename EVM RPC Test

* Rename tests

* Rename workflow job

* Fix typo on environment var on CI

* Rename tag 'test/rpc_evm' to 'evm'

* Set NODE_URL to point devnet

* estimateGas and gasPrice RPC implementations (#1940)

* estimateGas and gasPrice rpc and ffi

* Remove protoc lib includes

* Resolve depends build issues

* Consolidate persistent state to BlockchainDataHandler struct (#1944)

* Consolidate persistent state to BlockchainDataHandler struct

* Update cache after cache miss

* Get receipts root before creating block

* Update deps, add protobuf-src into runtime deps

* Fix protobuf-src compilation

* Use self contained rust toolchain

* CI workflow for EVM RPC testing (#1821)

* Add workflow for testing evm rpc

* Add test workflow for EVM RPCs

* Rename EVM RPC Test

* Rename tests

* Rename workflow job

* Fix typo on environment var on CI

* Rename tag 'test/rpc_evm' to 'evm'

* Set NODE_URL to point devnet

---------

Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>
Co-authored-by: Jouzo <15011228+Jouzo@users.noreply.github.com>
Co-authored-by: dCorral <55594560+dcorral@users.noreply.github.com>
Co-authored-by: canonbrother <w.canonbrother@gmail.com>

* CPP changes from master

* Restore updated test

* Fix exposed ports, env path variables (#1962)

* Remove unwrap

* Proto documentation (#1970)

* Add partial doc example for proto messages

* Add remaning doc example for proto messages

* Replace line comment by block comment

* Update doc proto messages

* Update doc proto messages

* Update doc proto messages

* Update doc proto messages

* Update doc proto messages

* Fix doc error

* Add more examples to proto messages doc and fix formating

* fix feature evm rpc tests (#1972)

* EVM State Trie (#1973)

* Debug send_raw_transaction and return RPC error when could not publish eth tx via cpp_imports (#1975)

* Add query by blockNumber RPC changes to metachain-cli (#1977)

* Remove EVMState tests

* Add latest RPC changes to CLI

* Handle full_transactions flag in getBlock* RPCs (#1976)

* Handle full_transactions flag in getBlock* RPCs

* Few RPCs type fixes

* Remove EVM block update after creation (#1978)

* Add debug log and fix NoSuchAccount error

* Don't mutate block after creation

* Refactor and rename transferbalance to transferdomain (#1966)

* Refactor transferbalance

* Rename transfer types, use intiger in rpc for type, adapt test.

* EVM RPC improvements (#1979)

* Takes eth_call input as Bytes

* Add dump_db debug RPC call

* Add clang-15 to Ubuntu build instructions

* Fix eth json RPC issue when running DFI in containerized environment (#1967)

* Change ip to 0.0.0.0

* Fix rust log output in init_runtime

* Include arg to pass address:port to bind eth rpc server

* Include pipeline to bind gRPC address to gRPC server

* Remove passing default ipv6 address to eth rpc and grpc servers

* Include rust export to pass command line args into init function, and
refactor to create init_evm_runtime function

* Fix init_evm_runtime to be called after base chain params is
initialized

* Fix clippy linter warnings

* Fix safety lint warning

* Shift unsafe init function into ain-exports lib, wraps ain-grpc init

* Fix lint

* Rebroadcast and restore failed transactions to mempool (#1965)

* Rebroadcast failed TXs

* Takes native tx as input and use it to return fail txs

* Update CPP FFI calls so code compiles

* Return failed EvmIn/Out native tx hashes

* WIP miner remove failed TXs. ConnectBlock revert failed TXs.

* Update tests for new RPC name

* Rename TransferBalance

* Miner remove coinbase fees for failed TXs

* Revert failed TransferDomain in ConnectBlock

---------

Co-authored-by: jouzo <jdesclercs@gmail.com>

* Trickle down block timestamp to EVM (#1980)

* Merge branch 'master' into feature/evm

* Clean up after merge

* Remove unused include

* lint: correct and include RPC argument names

* lint: Update guards

* lint: remove func with locale dep

* lint: resolve Python errors

* Pay gas to miner (#1981)

* Move .vsdb to evm subfolder

* Build cleanup, enable CI, fix logs (#1982)

* Clean up build, separate rust toolchain

* Windows build fixes

* Cleanup builds, add protoc, noarch dockerfile

* lint: correct and include RPC argument names

* lint: Update guards

* lint: remove func with locale dep

* lint: resolve Python errors

* Use c style header for c compile set

* Delegate tests to makefile

* Refactor lints and run through makefile

* fmt

* Remove clang builds from CI

* Fix stable builds, fmt

* Fix build dep

* Update deps, patch vsdb, use our open forked versions

---------

Co-authored-by: Peter Bushnell <bushsolo@gmail.com>

* Add package hashes

* Fix default input

* Add cross compile deps

* Add second seed node

* Add seeders as pnSeeds

* Add transferdomain type to conversion table

* Update to static IP

* Change default builds to debug, fix fmt checks

* Fix warnings

* Add debug in validate raw tx

* Get private key for Eth address (#1983)

* evm: Fix receipts log output (#1985)

* Fix receipts result output

* Formatting

* Return hex encoded index

* Make logIndex index across block instead of transaction

* Formatting

* Track cumulative gas usage

* Use enumerate

* Fix build and warnings

* Coinbase placeholder Eth block hash (#1986)

* Coinbase placeholder Eth block hash

* cargo fmt

* Filter out TransferDomain TXs (#1988)

* Add vinicity to EVM execution and update on each TX (#1987)

* Remove receipt clones (#1989)

* Restore check account balance on EvmOut RPC call (#1990)

* evm: fix gas estimates (#1992)

* Do not modify gas usage in estimate_gas

* Set default gas limit to maximum

* Fix warnings

* Fix formatting

* fix cross build target os

* Fix debug format

* Downgrade block_number RPC log level to trace

* Add missing import

* Fix failing EVM tests (#1995)

* Fix EVM tests

* Change to 0x for explorer compatibility

* Remove setting of gas

* chore(test): add `eth_sendRawTransaction` test (#1998)

* add eth_sendRawTransaction test

* rm print

* move test to clean set up

* Set correct Eth block hash in coinbase TX (#1993)

* Read-only state root

* Set correct Eth block hash in coinbase TX

* Match fee to eth block

---------

Co-authored-by: jouzo <jdesclercs@gmail.com>

* feat(lib): add rpc `eth_sendTransaction` (#1984)

* getprivkey

* getprivkey from GetWallets

* add rpc eth_sendtx

* fix cross build target os

* Change default builds to debug, fix fmt checks

* fix getchainid

* rm ffi::getprivkey, use ffi::getethprivkey

* use h160.asfixedbytes

* should use encoded signed tx

* add eth_sendTransaction test

---------

Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>

* Fix serialisation error

* Return correct data encoding

* Split up RPC namespaces (#2006)

* RPC: call and estimateGas at specific block height (#2005)

Co-authored-by: Shoham Chakraborty <shhmchk@gmail.com>

* Add RPC to get equivalent eth address from BTC address

* Bump evm version and use shanghai config (#2009)

* Document ain-rs-exports FFI calls. (#2004)

Co-authored-by: Shoham Chakraborty <shhmchk@gmail.com>

* Check pointer is valid (#2008)

* evm: Allow failed tx in `eth_sendRawTransaction` (#2003)

* Do not validate EVM TX

* Do not skip TX validation

---------

Co-authored-by: Jouzo <15011228+Jouzo@users.noreply.github.com>

* Fix warning (#2010)

Co-authored-by: jouzo <jdesclercs@gmail.com>

* Rollback latest EVM block (#2002)

* Rename to prevalidate_raw_tx

* Fix mapping EVM to DVM addresses

* Add type parameter for evmmap RPC

* Don't panic when restoring old code_map structure

* Fix RPC names

* Return reason for failure (#2012)

Co-authored-by: Peter Bushnell <bushsolo@gmail.com>

* add mapping for dfi tx to evm tx (not working)

* fix(evm): fix eth block type `nonce` & `extra_data` (#2015)

* change extra_data type Vec to Bytes

* change block nonce type U256 to H64

* fix req

* Rename DFI to DVM for evmmap RPC

* Remove unsed code in evmmap RPC

* Fix evmmap RPC for tx from DVM to EVM

* CI workflow for EVM test suites (#2017)

* Include feature evm test suites into CI workflow

* Fix indentation

* Include workflow trigger when PR is made into feature/evm branch

* Fix dependency bug

* Fix superuser privileges

* fix indentation and filepath

* Separate build stage and rpc tests into different jobs

* Fix bug for running test suite

* Debug log

* add fixtures.sh

* on trigger push & target tag evm

* pump required flags for defid cmd

* Remove debug logs

* clean

* path correction & some refined

* pretty print defid

* add foundation member fixtures

* revert pretty print defid

* fix defid

* pre-note contract addr

---------

Co-authored-by: canonbrother <w.canonbrother@gmail.com>

* Fix default gas in eth_call

* Adding block map indexes

* Change block hash arg names for clarity

* Fix bug for variable naming

* state check for eth_getBlockByNumber == eth_getBlockByHash

* Add RPC to convert block from EVM and DVM (not working)

* Fix bug to use unique instance of customview

* fix(evm): diff signer on tx2 and tx3 (#2022)

* log

* map access_list correctly

* chore(py): impr `eth_sendtx` and `eth_sendrawtx` test (#2013)

* wip

* log

* map access_list correctly

* rm pdb

* fix sendrawtx test

* refine note

* Fix publishEthTransaction catch error type

* Include method to remove block index, update to rollback pipeline

* test: fix intermittent updatemasternode test failure (#1996)

* test: add eth port to bind test (#1994)

* test: add eth port to bind test

* update loopback bind test

* lint: fix incorrectly identified dead code

* lint: remove whitespace

* lint: add expected export to first line of script

* Fix evmmaptype to enum class, return JSON error for invalid evmmap RPC

* lint: set bash before export

* Reorder cases

* Add ox prefix when mapping dvm to evm address

* lint: comment unused vars in script

* Refactor mapping order

* Refactor get block hash from custom db to return Res type

* Fix bugs

* Fix indexing of EVM/DVM block

* Refactor to use ResVal for evmmap db

* Return Eth addresses with EIP-55 checksum applied (#2024)

* Return Eth addresses with EIP-55 checksum applied

* Update src/key_io.cpp

* Fix formatting in added comments

---------

Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>

* fix eth checksum addr (#2028)

* test: test checksum address

* evm: Support contracts in functional tests (#2023)

* Add contract compilation and interaction to Python tests

* Fix path

* Clean up test

* Change function name

* Refactor to EVMProvider and KeyPair

* Move files to test_framework

* Add EVMProvider to TestNode

* Add static from_node method to KeyPair

* Add static from_file method to EVMContract

* Add static from_node method to EVMProvider

* Remove web3 checksum

* refactor(workflows): move `./scripts/fixtures.sh` to `.github` (#2030)

* move scripts/fixtures.sh to .github

* update bob addr to checksum addr

* Add evmmap function for transaction

* Include EVM mnview in rollback. Convert miner fee to Sats. (#1999)

* Convert miner fee to Sats

* Move evm_finalize to ProcessDefi and include mnview changes in rollback

* Fix error message

* Remove debug lines

* Rename evmmap RPC into xvmmap

* Move EVM state changes to outside Connect/DisconnectBlock (#2032)

* Demo work in progress code

* Add iter method to keep transaction in queue instead of draining

* Remove print from test

* Rename iter to get_cloned_vec

* Use get_cloned_vec

* Update code after merge

---------

Co-authored-by: jouzo <jdesclercs@gmail.com>

* Fix logic for xvmmap RPC

* Feature guard evm_finalize

* lint: add known local deps

* Remove free string and require for file evm.cpp

* test: use arg for gas price

* test: set utf8 encoding on open

* Remove SPV calls

* Remove useless code for validation and fix import

* Add web3 test dependencies (#2033)

* Install solc from make.sh

* Add pkg_install_solc to ci_setup_deps

* Install web3.py in make.sh

* Restore ProcessEVMQueue

* Make VMDomain class enum

* Move tx mapping logic

* Fix non void function not returning anything

* Fix non void function not returning anything

* Add logxvmindexes RPC

* Fix crash when getting block and tx

* Add test for xvmmap

* Fix merge from master to feature/evmmap

* Add setBlockHash indexes

* Fix test xvmmap

* Replace pcustomcsview by mnview

* Replace call from pustomcsview to a cache

* Remove unused function

* Add lock before calling pcustomcsview

* Remove previous commit that was deleted

* Refactor

* Minor cleanup

* Fix vmmap RPC

* Throw errro instead of returning string when unknown type in vmmap

* Add more test cases for vmmap

* Fix logic for vmmap RPC

* Fix logic vmmap RPC

* Add comments

* Format comments

* Add more TODO comments

* Format comments

* Fix lints

---------

Co-authored-by: Bushstar <bushsolo@gmail.com>
Co-authored-by: Mihailo Milenkovic <mihailo.milenkovic84@gmail.com>
Co-authored-by: jouzo <jdesclercs@gmail.com>
Co-authored-by: Prasanna Loganathar <pvl@prasannavl.com>
Co-authored-by: Shoham Chakraborty <shhmchk@gmail.com>
Co-authored-by: Jouzo <15011228+Jouzo@users.noreply.github.com>
Co-authored-by: Niven <sieniven@gmail.com>
Co-authored-by: canonbrother <w.canonbrother@gmail.com>
Co-authored-by: dCorral <55594560+dcorral@users.noreply.github.com>
  • Loading branch information
10 people committed Jun 19, 2023
1 parent 9859bec commit fc4a54b
Show file tree
Hide file tree
Showing 10 changed files with 262 additions and 4 deletions.
1 change: 1 addition & 0 deletions src/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -397,6 +397,7 @@ libdefi_server_a_SOURCES = \
masternodes/accountshistory.cpp \
masternodes/anchors.cpp \
masternodes/auctionhistory.cpp \
masternodes/evm.cpp \
masternodes/govvariables/attributes.cpp \
masternodes/govvariables/icx_takerfee_per_btc.cpp \
masternodes/govvariables/loan_daily_reward.cpp \
Expand Down
4 changes: 4 additions & 0 deletions src/masternodes/errors.h
Original file line number Diff line number Diff line change
Expand Up @@ -441,6 +441,10 @@ class DeFiErrors {
static Res TransferDomainInvalidDestinationDomain() {
return Res::Err("Invalid domain set for \"dst\" argument");
}

static Res DatabaseRWFailure(const std::string key) {
return Res::Err("DB r/w failure: %s", key);
}
};

#endif // DEFI_MASTERNODES_ERRORS_H
Expand Down
44 changes: 44 additions & 0 deletions src/masternodes/evm.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
#include <masternodes/evm.h>
#include <masternodes/errors.h>
#include <masternodes/res.h>
#include <uint256.h>

Res CVMDomainMapView::SetVMDomainMapBlockHash(uint8_t type, uint256 blockHashKey, uint256 blockHash)
{
return WriteBy<VMDomainBlockHash>(std::pair(type, blockHashKey), blockHash) ? Res::Ok() : DeFiErrors::DatabaseRWFailure(blockHashKey.GetHex());
}

ResVal<uint256> CVMDomainMapView::GetVMDomainMapBlockHash(uint8_t type, uint256 blockHashKey) const
{
uint256 blockHash;
if (ReadBy<VMDomainBlockHash>(std::pair(type, blockHashKey), blockHash))
return ResVal<uint256>(blockHash, Res::Ok());
return DeFiErrors::DatabaseRWFailure(blockHashKey.GetHex());
}

Res CVMDomainMapView::SetVMDomainMapTxHash(uint8_t type, uint256 txHashKey, uint256 txHash)
{
return WriteBy<VMDomainTxHash>(std::pair(type, txHashKey), txHash) ? Res::Ok() : DeFiErrors::DatabaseRWFailure(txHashKey.GetHex());
}

ResVal<uint256> CVMDomainMapView::GetVMDomainMapTxHash(uint8_t type, uint256 txHashKey) const
{
uint256 txHash;
if (ReadBy<VMDomainTxHash>(std::pair(type, txHashKey), txHash))
return ResVal<uint256>(txHash, Res::Ok());
return DeFiErrors::DatabaseRWFailure(txHashKey.GetHex());
}

void CVMDomainMapView::ForEachVMDomainMapBlockIndexes(std::function<bool(const std::pair<uint8_t, uint256> &, const uint256 &)> callback) {
ForEach<VMDomainBlockHash, std::pair<uint8_t, uint256>, uint256>(
[&callback](const std::pair<uint8_t, uint256> &key, uint256 val) {
return callback(key, val);
});
}

void CVMDomainMapView::ForEachVMDomainMapTxIndexes(std::function<bool(const std::pair<uint8_t, uint256> &, const uint256 &)> callback) {
ForEach<VMDomainTxHash, std::pair<uint8_t, uint256>, uint256>(
[&callback](const std::pair<uint8_t, uint256> &key, uint256 val) {
return callback(key, val);
});
}
24 changes: 24 additions & 0 deletions src/masternodes/evm.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,4 +26,28 @@ struct CEvmTxMessage {
}
};

enum VMDomainMapType : uint8_t {
DVMToEVM = 0x01,
EVMToDVM = 0x02,
};

class CVMDomainMapView : public virtual CStorageView {
public:
Res SetVMDomainMapBlockHash(uint8_t type, uint256 blockHashKey, uint256 blockHash);
ResVal<uint256> GetVMDomainMapBlockHash(uint8_t type, uint256 blockHashKey) const;
void ForEachVMDomainMapBlockIndexes(std::function<bool(const std::pair<uint8_t, uint256> &, const uint256 &)> callback);

Res SetVMDomainMapTxHash(uint8_t type, uint256 txHashKey, uint256 txHash);
ResVal<uint256> GetVMDomainMapTxHash(uint8_t type, uint256 txHashKey) const;
void ForEachVMDomainMapTxIndexes(std::function<bool(const std::pair<uint8_t, uint256> &, const uint256 &)> callback);

struct VMDomainBlockHash {
static constexpr uint8_t prefix() { return 'N'; }
};

struct VMDomainTxHash {
static constexpr uint8_t prefix() { return 'e'; }
};
};

#endif // DEFI_MASTERNODES_EVM_H
6 changes: 4 additions & 2 deletions src/masternodes/masternodes.h
Original file line number Diff line number Diff line change
Expand Up @@ -445,7 +445,8 @@ class CCustomCSView : public CMasternodesView,
public CLoanView,
public CVaultView,
public CSettingsView,
public CProposalView {
public CProposalView,
public CVMDomainMapView {
// clang-format off
void CheckPrefixes()
{
Expand Down Expand Up @@ -477,7 +478,8 @@ class CCustomCSView : public CMasternodesView,
LoanInterestV3ByVault,
CVaultView :: VaultKey, OwnerVaultKey, CollateralKey, AuctionBatchKey, AuctionHeightKey, AuctionBidKey,
CSettingsView :: KVSettings,
CProposalView :: ByType, ByCycle, ByMnVote, ByStatus
CProposalView :: ByType, ByCycle, ByMnVote, ByStatus,
CVMDomainMapView :: VMDomainBlockHash, VMDomainTxHash
>();
}
// clang-format on
Expand Down
6 changes: 6 additions & 0 deletions src/masternodes/mn_checks.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3875,6 +3875,12 @@ class CCustomTxApplyVisitor : public CCustomTxVisitor {

gasUsed = hashAndGas.used_gas;

std::vector<unsigned char> evmTxHashBytes;
sha3(obj.evmTx, evmTxHashBytes);
auto txHash = tx.GetHash();
auto evmTxHash = uint256(evmTxHashBytes);
mnview.SetVMDomainMapTxHash(VMDomainMapType::DVMToEVM, txHash, evmTxHash);
mnview.SetVMDomainMapTxHash(VMDomainMapType::EVMToDVM, evmTxHash, txHash);
return Res::Ok();
}

Expand Down
138 changes: 137 additions & 1 deletion src/masternodes/rpc_evm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,24 @@
#include <key_io.h>
#include <util/strencodings.h>

enum class VMDomainRPCMapType {
Auto,
AddressDVMToEVM,
AddressEVMToDVM,
TxHashDVMToEVM,
TxHashEVMToEVM,
BlockHashDVMToEVM,
BlockHashEVMToDVM
};

static int VMDomainRPCMapTypeCount = 7;

enum class VMDomainIndexType {
BlockHash,
TxHash
};


UniValue evmtx(const JSONRPCRequest& request) {
auto pwallet = GetWallet(request);

Expand Down Expand Up @@ -122,11 +140,129 @@ UniValue evmtx(const JSONRPCRequest& request) {
return send(MakeTransactionRef(std::move(rawTx)), optAuthTx)->GetHash().ToString();
}


UniValue vmmap(const JSONRPCRequest& request) {
auto pwallet = GetWallet(request);
RPCHelpMan{"vmmap",
"Give the equivalent of an address, blockhash or transaction from EVM to DVM\n",
{
{"hash", RPCArg::Type::STR, RPCArg::Optional::NO, "DVM address, EVM blockhash, EVM transaction"},
{"type", RPCArg::Type::NUM, RPCArg::Optional::NO, "Type of mapping: 1 - DFI Address to EVM, 2 - EVM to DFI Address, 3 - DFI Tx to EVM, 4 - EVM Tx to DFI, 5 - DFI Block to EVM, 6 - EVM Block to DFI"}
},
RPCResult{
"\"hash\" (string) The hex-encoded string for address, block or transaction\n"
},
RPCExamples{
HelpExampleCli("vmmap", R"('"<hex>"' 1)")
},
}.Check(request);
const std::string hash = request.params[0].get_str();

if (request.params[1].get_int() >= VMDomainRPCMapTypeCount) {
throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Invalid parameters, argument \"type\" must be less than %d.", VMDomainRPCMapTypeCount));
}
const auto type = static_cast<VMDomainRPCMapType>(request.params[1].get_int());
switch (type) {
case VMDomainRPCMapType::AddressDVMToEVM: {
const CPubKey key = AddrToPubKey(pwallet, hash);
return EncodeDestination(WitnessV16EthHash(key.GetID()));
}
case VMDomainRPCMapType::AddressEVMToDVM: {
const CPubKey key = AddrToPubKey(pwallet, hash);
return EncodeDestination(PKHash(key.GetID()));
}
default:
break;
}

LOCK(cs_main);

ResVal res = ResVal<uint256>(uint256{}, Res::Ok());
switch (type) {
case VMDomainRPCMapType::TxHashDVMToEVM: {
res = pcustomcsview->GetVMDomainMapTxHash(VMDomainMapType::DVMToEVM, uint256S(hash));
break;
}
case VMDomainRPCMapType::TxHashEVMToEVM: {
res = pcustomcsview->GetVMDomainMapTxHash(VMDomainMapType::EVMToDVM, uint256S(hash));
break;
}
case VMDomainRPCMapType::BlockHashDVMToEVM: {
res = pcustomcsview->GetVMDomainMapBlockHash(VMDomainMapType::DVMToEVM, uint256S(hash));
break;
}
case VMDomainRPCMapType::BlockHashEVMToDVM: {
res = pcustomcsview->GetVMDomainMapBlockHash(VMDomainMapType::EVMToDVM, uint256S(hash));
break;
}
default: {
throw JSONRPCError(RPC_INVALID_PARAMETER, "Unknown map type");
}
}
if (!res) {
throw JSONRPCError(RPC_INVALID_REQUEST, res.msg);
} else {
return res.val->ToString();
}
}

UniValue logvmmaps(const JSONRPCRequest& request) {
RPCHelpMan{
"logvmmaps",
"\nLogs all block or tx indexes for debugging.\n",
{
{"type", RPCArg::Type::NUM, RPCArg::Optional::NO, "Type of log: 0 - Blocks, 1 - Txs"}
},
RPCResult{
"{...} (array) Json object with account balances if rpcresult is enabled."
"This is for debugging purposes only.\n"},
RPCExamples{
HelpExampleCli("logvmmaps", R"('"<hex>"' 1)")},
}.Check(request);

LOCK(cs_main);

size_t count{};
UniValue result{UniValue::VOBJ};
UniValue indexesJson{UniValue::VOBJ};
const auto type = static_cast<VMDomainIndexType>(request.params[0].get_int());
// TODO: For now, we iterate through the whole list. But this is just a debugging RPC.
// But there's no need to iterate the whole list, we can start at where we need to and
// return false, once we hit the limit and stop the iter.
switch (type) {
case VMDomainIndexType::BlockHash: {
pcustomcsview->ForEachVMDomainMapBlockIndexes([&](const std::pair<uint8_t, uint256> &index, uint256 blockHash) {
if (index.first == VMDomainMapType::DVMToEVM) {
indexesJson.pushKV(index.second.GetHex(), blockHash.GetHex());
++count;
}
return true;
});
}
case VMDomainIndexType::TxHash: {
pcustomcsview->ForEachVMDomainMapTxIndexes([&](const std::pair<uint8_t, uint256> &index, uint256 txHash) {
if (index.first == VMDomainMapType::DVMToEVM) {
indexesJson.pushKV(index.second.GetHex(), txHash.GetHex());
++count;
}
return true;
});
}
}

result.pushKV("indexes", indexesJson);
result.pushKV("count", static_cast<uint64_t>(count));
return result;
}


static const CRPCCommand commands[] =
{
// category name actor (function) params
// --------------- ---------------------- --------------------- ----------
{"evm", "evmtx", &evmtx, {"from", "nonce", "gasPrice", "gasLimit", "to", "value", "data"}},
{"evm", "evmtx", &evmtx, {"from", "nonce", "gasPrice", "gasLimit", "to", "value", "data"}},
{"evm", "vmmap", &vmmap, {"hash", "type"}},
{"evm", "logvmmaps", &logvmmaps, {"type"}},
};

void RegisterEVMRPCCommands(CRPCTable& tableRPC) {
Expand Down
5 changes: 5 additions & 0 deletions src/masternodes/validation.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2428,6 +2428,11 @@ static void ProcessEVMQueue(const CBlock &block, const CBlockIndex *pindex, CCus
}

const auto blockResult = evm_finalize(evmContext, false, block.nBits, beneficiary, block.GetBlockTime());
auto evmBlockHash = std::vector<uint8_t>(blockResult.block_hash.begin(), blockResult.block_hash.end());
std::reverse(evmBlockHash.begin(), evmBlockHash.end());

cache.SetVMDomainMapBlockHash(VMDomainMapType::DVMToEVM, block.GetHash(), uint256(evmBlockHash));
cache.SetVMDomainMapBlockHash(VMDomainMapType::EVMToDVM, uint256(evmBlockHash), block.GetHash());

if (!blockResult.failed_transactions.empty()) {
std::vector<std::string> failedTransactions;
Expand Down
2 changes: 2 additions & 0 deletions src/rpc/client.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -365,6 +365,8 @@ static const CRPCConvertParam vRPCConvertParams[] =
{ "evmtx", 2, "gasPrice" },
{ "evmtx", 3, "gasLimit" },
{ "evmtx", 5, "value" },
{ "vmmap", 1, "type"},
{ "logvmmaps", 0, "type"},
};
// clang-format on

Expand Down
36 changes: 35 additions & 1 deletion test/functional/feature_evm_rpc.py
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,39 @@ def test_block(self):
block = self.nodes[0].eth_getBlockByHash(latest_block['hash'])
assert_equal(block, latest_block)

def test_vmmap(self):
# TODO: This PR isn't ready just yet without proper tests.
# Current tests are very basic. Need to add proper tests.
# Merging for now, for faster feedback loop. But this is a key to-do.
# Check if xvmmap is working for addresses
eth_address = '0x2E04dbc946c6473DFd318d3bE2BE36E5dfbdACDC'
address = self.nodes[0].vmmap(eth_address, 2)
assert_equal(eth_address, self.nodes[0].vmmap(address, 1))

# Check that vmmap is failing on wrong input
eth_address = '0x0000000000000000000000000000000000000000'
assert_raises_rpc_error(-5, "0x0000000000000000000000000000000000000000 does not refer to a key", self.nodes[0].vmmap, eth_address, 2)
assert_raises_rpc_error(-5, "Invalid address: test", self.nodes[0].vmmap, 'test', 1)

#Check if xvmmap is working for Txs
list_tx = self.nodes[0].logvmmaps(1)
dvm_tx = list(list_tx['indexes'].keys())[0]
evm_tx = self.nodes[0].vmmap(dvm_tx, 3)
assert_equal(dvm_tx, self.nodes[0].vmmap(evm_tx, 4))

# Check vmmap fail on wrong tx
evm_tx = '0x0000000000000000000000000000000000000000000000000000000000000000'
assert_raises_rpc_error(-32600, "DB r/w failure: 0000000000000000000000000000000000000000000000000000000000000000", self.nodes[0].vmmap, evm_tx, 4)

# Check if xvmmap is working for Blocks
latest_block = self.nodes[0].eth_getBlockByNumber("latest", False)
dvm_block = self.nodes[0].vmmap(latest_block['hash'], 6)
assert_equal(latest_block['hash'], "0x" + self.nodes[0].vmmap(dvm_block, 5))

# Check vmmap fail on wrong block
evm_block = '0x0000000000000000000000000000000000000000000000000000000000000000'
assert_raises_rpc_error(-32600, "DB r/w failure: 0000000000000000000000000000000000000000000000000000000000000000", self.nodes[0].vmmap, evm_block, 6)

def run_test(self):
self.setup()

Expand All @@ -163,11 +196,12 @@ def run_test(self):
self.test_accounts()

self.nodes[0].transferdomain([{"src": {"address":self.address, "amount":"100@DFI", "domain": 2}, "dst":{"address":self.ethAddress, "amount":"100@DFI", "domain": 3}}])
self.nodes[0].generate(1)
self.nodes[0].generate(2)

self.test_address_state(self.ethAddress) # TODO test smart contract

self.test_block()
self.test_vmmap()


if __name__ == '__main__':
Expand Down

0 comments on commit fc4a54b

Please sign in to comment.