Skip to content

Commit

Permalink
Completes PR mit-dci#138, adds additional contemperary features
Browse files Browse the repository at this point in the history
Signed-off-by: Michael Maurer <[email protected]>
  • Loading branch information
maurermi committed Feb 17, 2023
1 parent 5f2781d commit 6814f91
Show file tree
Hide file tree
Showing 36 changed files with 2,239 additions and 26 deletions.
1 change: 0 additions & 1 deletion .dockerignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
build
run
benchmarks
plots
.vscode
.deps
Expand Down
5 changes: 4 additions & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,11 @@ find_library(LEVELDB_LIBRARY leveldb REQUIRED)
find_library(NURAFT_LIBRARY nuraft REQUIRED)
find_library(GTEST_LIBRARY gtest REQUIRED)
find_library(GTEST_MAIN_LIBRARY gtest_main REQUIRED)
find_package(benchmark REQUIRED)

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-rtti")

include_directories(3rdparty 3rdparty/secp256k1/include /usr/local/include /opt/homebrew/include)
include_directories(3rdparty 3rdparty/secp256k1/include /usr/lib /usr/local/lib /usr/local/include /opt/homebrew/include)

if(CMAKE_BUILD_TYPE STREQUAL "Debug")
add_compile_options(-fprofile-arcs -ftest-coverage)
Expand Down Expand Up @@ -74,5 +75,7 @@ endif()

add_subdirectory(src)
add_subdirectory(tests)
add_subdirectory(benchmarks)
add_subdirectory(tools/config_generator)
add_subdirectory(tools/bench)
add_subdirectory(tools/shard-seeder)
22 changes: 11 additions & 11 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -160,38 +160,38 @@ You can find the images [in the Github Container Registry](https://github.com/mi
## Setup test wallets and test them

The following commands are all performed from within the second container we started in the previous step.
In each of the below commands, you should pass `atomizer-compose.cfg` instead of `2pc-compose.cfg` if you started the atomizer architecture.
In each of the below commands, you should pass `config/general/atomizer-compose.cfg` instead of `config/general/2pc-compose.cfg` if you started the atomizer architecture.

* Mint new coins (e.g., 10 new UTXOs each with a value of 5 atomic units of currency)
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool0.dat wallet0.dat mint 10 5
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool0.dat wallet0.dat mint 10 5
[2021-08-17 15:11:57.686] [WARN ] Existing wallet file not found
[2021-08-17 15:11:57.686] [WARN ] Existing mempool not found
4bc23da407c3a8110145c5b6c38199c8ec3b0e35ea66bbfd78f0ed65304ce6fa
```

If using the atomizer architecture, you'll need to sync the wallet after:
```terminal
# ./build/src/uhs/client/client-cli atomizer-compose.cfg mempool0.dat wallet0.dat sync
# ./build/src/uhs/client/client-cli config/general/atomizer-compose.cfg mempool0.dat wallet0.dat sync
```

* Inspect the balance of a wallet
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool0.dat wallet0.dat info
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool0.dat wallet0.dat info
Balance: $0.50, UTXOs: 10, pending TXs: 0
```

* Make a new wallet
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool1.dat wallet1.dat newaddress
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool1.dat wallet1.dat newaddress
[2021-08-17 15:13:16.148] [WARN ] Existing wallet file not found
[2021-08-17 15:13:16.148] [WARN ] Existing mempool not found
usd1qrw038lx5n4wxx3yvuwdndpr7gnm347d6pn37uywgudzq90w7fsuk52kd5u
```

* Send currency from the first wallet to the second wallet created in the previous step (e.g., 30 atomic units of currency)
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool0.dat wallet0.dat send 30 usd1qrw038lx5n4wxx3yvuwdndpr7gnm347d6pn37uywgudzq90w7fsuk52kd5u
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool0.dat wallet0.dat send 30 usd1qrw038lx5n4wxx3yvuwdndpr7gnm347d6pn37uywgudzq90w7fsuk52kd5u
tx_id:
cc1f7dc708be5b07e23e125cf0674002ff8546a9342928114bc97031d8b96e75
Data for recipient importinput:
Expand All @@ -201,20 +201,20 @@ In each of the below commands, you should pass `atomizer-compose.cfg` instead of

If using the atomizer architecture, you'll need to sync the sending wallet after:
```terminal
# ./build/src/uhs/client/client-cli atomizer-compose.cfg mempool0.dat wallet0.dat sync
# ./build/src/uhs/client/client-cli config/general/atomizer-compose.cfg mempool0.dat wallet0.dat sync
```

* Check that the currency is no longer available in the sending wallet
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool0.dat wallet0.dat info
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool0.dat wallet0.dat info
Balance: $0.20, UTXOs: 4, pending TXs: 0
```

* Import coins to the receiving wallet using the string after `importinput` from the currency transfer step above
```terminal
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool1.dat wallet1.dat importinput cc1f7dc708be5b07e23e125cf0674002ff8546a9342928114bc97031d8b96e750000000000000000d0e4f689b550f623e9370edae235de50417860be0f2f8e924eca9f402fcefeaa1e00000000000000
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool1.dat wallet1.dat sync
# ./build/src/uhs/client/client-cli 2pc-compose.cfg mempool1.dat wallet1.dat info
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool1.dat wallet1.dat importinput cc1f7dc708be5b07e23e125cf0674002ff8546a9342928114bc97031d8b96e750000000000000000d0e4f689b550f623e9370edae235de50417860be0f2f8e924eca9f402fcefeaa1e00000000000000
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool1.dat wallet1.dat sync
# ./build/src/uhs/client/client-cli config/general/2pc-compose.cfg mempool1.dat wallet1.dat info
Balance: $0.30, UTXOs: 1, pending TXs: 0
```

Expand Down
26 changes: 26 additions & 0 deletions benchmarks/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
project(benchmarks)

include_directories(. ../src ../tools/watchtower ../3rdparty ../3rdparty/secp256k1/include)
set(SECP256K1_LIBRARY $<TARGET_FILE:secp256k1>)

add_executable(run_benchmarks low_level.cpp
transactions.cpp
uhs_leveldb.cpp
uhs_set.cpp
)

target_compile_options(run_benchmarks PRIVATE -ftest-coverage -fprofile-arcs)
target_link_options(run_benchmarks PRIVATE --coverage)
target_link_libraries(run_benchmarks ${GTEST_LIBRARY}
${GTEST_MAIN_LIBRARY}
benchmark::benchmark
util
shard
locking_shard
transaction
common
serialization
crypto
secp256k1
${LEVELDB_LIBRARY}
${CMAKE_THREAD_LIBS_INIT})
180 changes: 180 additions & 0 deletions benchmarks/low_level.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,180 @@
// Copyright (c) 2021 MIT Digital Currency Initiative,
// Federal Reserve Bank of Boston
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.

// Note: Contains call to BENCHMARK_MAIN

#include "uhs/transaction/messages.hpp"
#include "uhs/transaction/transaction.hpp"
#include "uhs/transaction/validation.hpp"
#include "uhs/transaction/wallet.hpp"
#include "util/serialization/istream_serializer.hpp"
#include "util/serialization/ostream_serializer.hpp"

#include <benchmark/benchmark.h>
#include <filesystem>
#include <gtest/gtest.h>

class low_level : public ::benchmark::Fixture {
protected:
void SetUp(const ::benchmark::State&) override {
auto mint_tx1 = wallet1.mint_new_coins(100, 2);
wallet1.confirm_transaction(mint_tx1);

m_of.open(m_BENCHMARK_File);

counter = 1;
}

void TearDown(const ::benchmark::State&) override {
m_if.close();
m_of.close();
std::filesystem::remove_all(m_BENCHMARK_File);
};

cbdc::transaction::wallet wallet1;
cbdc::transaction::wallet wallet2;

cbdc::transaction::full_tx m_valid_tx{};
cbdc::transaction::full_tx m_valid_tx_multi_inp{};

// for serialization
std::ifstream m_if;
std::ofstream m_of;

cbdc::istream_serializer m_is{m_if};
cbdc::ostream_serializer m_os{m_of};

static constexpr auto m_BENCHMARK_File = "serial_BENCHMARK_File.dat";

// used to ensure that transaction validation timing
// uses unique N values for N->1 transactions
int counter = 1;
};

// serialize full tx
BENCHMARK_F(low_level, serialize_tx)(benchmark::State& state) {
m_valid_tx = wallet1.send_to(2, wallet2.generate_key(), true).value();
for(auto _ : state) {
m_os << m_valid_tx;
}
m_of.close();
}

// serialize compact tx
BENCHMARK_F(low_level, serialize_compact_tx)(benchmark::State& state) {
// serialize 1-1 tx
m_valid_tx = wallet1.send_to(2, wallet2.generate_key(), true).value();
auto cp_tx = cbdc::transaction::compact_tx(m_valid_tx);
for(auto _ : state) {
m_os << cp_tx;
}
m_of.close();
}

// deserialize full tx
BENCHMARK_F(low_level, deserialize_tx)(benchmark::State& state) {
// serialize 1-1 tx
auto read_tx = cbdc::transaction::full_tx();
m_valid_tx = wallet1.send_to(2, wallet2.generate_key(), true).value();
for(auto _ : state) {
state.PauseTiming();
m_os.reset();
m_os << m_valid_tx;
m_of.close();
m_if.open(m_BENCHMARK_File);

read_tx = cbdc::transaction::full_tx();
m_is.reset();
state.ResumeTiming();
m_is >> read_tx;
state.PauseTiming();
ASSERT_EQ(read_tx, m_valid_tx);
}

m_if.close();
}

// deserialize compact tx
BENCHMARK_F(low_level, deserialize_compact_tx)(benchmark::State& state) {
// serialize 1-1 tx
auto read_tx = cbdc::transaction::full_tx();
auto read_cp = cbdc::transaction::compact_tx(read_tx);

m_valid_tx = wallet1.send_to(2, wallet2.generate_key(), true).value();
auto cp_tx = cbdc::transaction::compact_tx(m_valid_tx);
for(auto _ : state) {
state.PauseTiming();
m_os.reset();
m_os << cp_tx;
m_of.close();
m_if.open(m_BENCHMARK_File);

read_cp = cbdc::transaction::compact_tx(read_tx);
m_is.reset();
state.ResumeTiming();
m_is >> read_cp;
state.PauseTiming();
ASSERT_EQ(cp_tx, read_cp);
}

m_if.close();
}

// wallet sign tx
BENCHMARK_F(low_level, sign_tx)(benchmark::State& state) {
// sign 1-1 tx
for(auto _ : state) {
state.PauseTiming();
m_valid_tx = wallet1.send_to(2, wallet1.generate_key(), true).value();

state.ResumeTiming();
wallet1.sign(m_valid_tx);
state.PauseTiming();

wallet1.confirm_transaction(m_valid_tx);
}
}

// tx validiation
BENCHMARK_F(low_level, valid_tx)(benchmark::State& state) {
// validate n-1 tx
auto err = cbdc::transaction::validation::check_tx(m_valid_tx);
for(auto _ : state) {
m_valid_tx = wallet1.mint_new_coins(counter, 1);
wallet1.confirm_transaction(m_valid_tx);
m_valid_tx
= wallet1.send_to(counter, wallet2.generate_key(), true).value();
state.ResumeTiming();
err = cbdc::transaction::validation::check_tx(m_valid_tx);
state.PauseTiming();
counter++;
}
}

// test quick-failing validation
BENCHMARK_F(low_level, no_inputs)(benchmark::State& state) {
m_valid_tx.m_inputs.clear();
auto err = cbdc::transaction::validation::check_tx(m_valid_tx);
for(auto _ : state) {
err = cbdc::transaction::validation::check_tx(m_valid_tx);
}
}

// calculate uhs id
BENCHMARK_F(low_level, calculate_uhs_id)(benchmark::State& state) {
m_valid_tx = wallet1.send_to(2, wallet2.generate_key(), true).value();
auto cp_tx = cbdc::transaction::compact_tx(m_valid_tx);
auto engine = std::default_random_engine();
for(auto _ : state) {
state.PauseTiming();
uint64_t i = (uint64_t)engine();
state.ResumeTiming();
cbdc::transaction::uhs_id_from_output(cp_tx.m_id,
i,
m_valid_tx.m_outputs[0]);
}
}

BENCHMARK_MAIN();
Loading

0 comments on commit 6814f91

Please sign in to comment.