Skip to content

Commit ded8ac0

Browse files
authored
GH-622-raw: Merged in master (#696)
* PersistentConfiguration now handles CryptDEs * Temporary commit * All tests apparently passing * Starting to deal with the consequences of removing CryptDE as a static * About two-thirds done. * All unit tests passing * New integration test is passing * Unit, integration, and multinode tests passing * Review issues * Removed two fields from BootstrapperConfig * Formatting * Review issues * Removed unused second parameter to CrashTestDummy constructor * Formatting * Changing the way database passwords are established * Formatting * Trying to find issue with --fake-public-key and chain * Multinode tests and unit tests are working. * Formatting and removing debug logs * Removed unused import * Clippy appeasement * Review issues * Formatting * Switched test from example.com to testingmcafeesites.com * Made running single integration tests easier; added TLS retries to integration test * Formatting * Race in setup_reporter removed * Increased a timeout * Formatting * example.com -> www.example.com * Review issues
1 parent 44b58e4 commit ded8ac0

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

58 files changed

+3067
-1698
lines changed

masq_lib/src/blockchains/chains.rs

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ use crate::constants::{
77
POLYGON_AMOY_FULL_IDENTIFIER, POLYGON_MAINNET_FULL_IDENTIFIER,
88
};
99
use serde_derive::{Deserialize, Serialize};
10+
use std::fmt::{Display, Formatter};
1011

1112
#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq, Serialize, Deserialize)]
1213
pub enum Chain {
@@ -47,6 +48,21 @@ impl From<&str> for Chain {
4748
}
4849
}
4950

51+
impl Display for Chain {
52+
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
53+
let chain_name = match self {
54+
Chain::EthMainnet => ETH_MAINNET_FULL_IDENTIFIER,
55+
Chain::EthRopsten => ETH_ROPSTEN_FULL_IDENTIFIER,
56+
Chain::PolyMainnet => POLYGON_MAINNET_FULL_IDENTIFIER,
57+
Chain::PolyAmoy => POLYGON_AMOY_FULL_IDENTIFIER,
58+
Chain::BaseMainnet => BASE_MAINNET_FULL_IDENTIFIER,
59+
Chain::BaseSepolia => BASE_SEPOLIA_FULL_IDENTIFIER,
60+
Chain::Dev => DEV_CHAIN_FULL_IDENTIFIER,
61+
};
62+
write!(f, "{}", chain_name)
63+
}
64+
}
65+
5066
impl Chain {
5167
pub fn rec(&self) -> &BlockchainRecord {
5268
CHAINS
@@ -158,6 +174,37 @@ mod tests {
158174
})
159175
}
160176

177+
#[test]
178+
fn display_is_properly_implemented() {
179+
let chains = [
180+
Chain::EthMainnet,
181+
Chain::EthRopsten,
182+
Chain::PolyMainnet,
183+
Chain::PolyAmoy,
184+
Chain::BaseMainnet,
185+
Chain::BaseSepolia,
186+
Chain::Dev,
187+
];
188+
189+
let strings = chains
190+
.iter()
191+
.map(|chain| chain.to_string())
192+
.collect::<Vec<_>>();
193+
194+
assert_eq!(
195+
strings,
196+
vec![
197+
ETH_MAINNET_FULL_IDENTIFIER.to_string(),
198+
ETH_ROPSTEN_FULL_IDENTIFIER.to_string(),
199+
POLYGON_MAINNET_FULL_IDENTIFIER.to_string(),
200+
POLYGON_AMOY_FULL_IDENTIFIER.to_string(),
201+
BASE_MAINNET_FULL_IDENTIFIER.to_string(),
202+
BASE_SEPOLIA_FULL_IDENTIFIER.to_string(),
203+
DEV_CHAIN_FULL_IDENTIFIER.to_string(),
204+
]
205+
);
206+
}
207+
161208
fn assert_mainnet_exist() {
162209
assert!(CHAINS
163210
.iter()

masq_lib/src/constants.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use crate::data_version::DataVersion;
55
use const_format::concatcp;
66

77
pub const DEFAULT_CHAIN: Chain = Chain::PolyMainnet;
8-
pub const CURRENT_SCHEMA_VERSION: usize = 10;
8+
pub const CURRENT_SCHEMA_VERSION: usize = 11;
99

1010
pub const HIGHEST_RANDOM_CLANDESTINE_PORT: u16 = 9999;
1111
pub const HTTP_PORT: u16 = 80;

masq_lib/src/test_utils/environment_guard.rs

Lines changed: 42 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@
33
use lazy_static::lazy_static;
44
use std::ffi::OsString;
55
use std::sync::{Mutex, MutexGuard};
6+
use std::thread::ThreadId;
67

78
lazy_static! {
89
static ref ENVIRONMENT_GUARD_MUTEX: Mutex<()> = Mutex::new(());
10+
static ref ENVIRONMENT_GUARD_THREAD_ID: Mutex<Option<ThreadId>> = Mutex::new(None);
911
static ref CLAP_GUARD_MUTEX: Mutex<()> = Mutex::new(());
1012
static ref LOGFILE_NAME_GUARD_MUTEX: Mutex<()> = Mutex::new(());
1113
}
@@ -17,10 +19,9 @@ pub struct ConcurrencyPreventer<'a> {
1719
impl<'a> ConcurrencyPreventer<'a> {
1820
pub fn new(mutex: &'a Mutex<()>) -> ConcurrencyPreventer<'a> {
1921
ConcurrencyPreventer {
20-
_lock: match mutex.lock() {
21-
Ok(guard) => guard,
22-
Err(poisoned) => poisoned.into_inner(),
23-
},
22+
_lock: mutex
23+
.lock()
24+
.unwrap_or_else(|poisoned| poisoned.into_inner()),
2425
}
2526
}
2627
}
@@ -43,16 +44,50 @@ impl<'a> Drop for EnvironmentGuard<'a> {
4344
self.environment
4445
.iter()
4546
.for_each(|(name, value)| std::env::set_var(name, value));
47+
let mut thread_id_guard = ENVIRONMENT_GUARD_THREAD_ID
48+
.lock()
49+
.unwrap_or_else(|e| e.into_inner());
50+
*thread_id_guard = None; // Clear the thread ID guard
4651
}
4752
}
4853

4954
impl<'a> EnvironmentGuard<'a> {
5055
pub fn new() -> EnvironmentGuard<'a> {
51-
EnvironmentGuard {
52-
_preventer: ConcurrencyPreventer::new(&ENVIRONMENT_GUARD_MUTEX),
53-
environment: std::env::vars_os().collect(),
56+
// TODO: Consider a #[cfg(not(test))] line here to panic if production code tries this
57+
loop {
58+
{
59+
let mut thread_id_guard = Self::thread_id_guard();
60+
let current_thread_id = std::thread::current().id();
61+
match *thread_id_guard {
62+
Some(id) => {
63+
if id == current_thread_id {
64+
panic!(
65+
"Thread {:?} is trying to claim multiple EnvironmentGuards",
66+
current_thread_id
67+
);
68+
}
69+
}
70+
None => {
71+
// Set thread ID, claim environment guard, release thread ID lock
72+
*thread_id_guard = Some(current_thread_id);
73+
return EnvironmentGuard {
74+
_preventer: ConcurrencyPreventer::new(&ENVIRONMENT_GUARD_MUTEX),
75+
environment: std::env::vars_os().collect(),
76+
};
77+
}
78+
}
79+
}
80+
// Somebody else has the EnvironmentGuard. We've released the thread ID lock; now
81+
// wait for a little while and try again.
82+
std::thread::sleep(std::time::Duration::from_millis(10));
5483
}
5584
}
85+
86+
pub fn thread_id_guard() -> MutexGuard<'a, Option<ThreadId>> {
87+
ENVIRONMENT_GUARD_THREAD_ID
88+
.lock()
89+
.unwrap_or_else(|poisoned| poisoned.into_inner())
90+
}
5691
}
5792

5893
impl<'a> Default for EnvironmentGuard<'a> {

multinode_integration_tests/src/masq_node_server.rs

Lines changed: 18 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -2,23 +2,24 @@
22

33
use crate::masq_node_cluster::DockerHostSocketAddr;
44
use crate::utils;
5-
use std::io;
5+
use crossbeam_channel::{unbounded, Receiver, Sender};
66
use std::net::{Shutdown, SocketAddr, TcpListener, TcpStream};
77
use std::time::Duration;
8+
use std::{io, thread};
89

910
pub struct MASQNodeServer {
11+
docker_host_addr: Option<DockerHostSocketAddr>,
1012
local_addr: SocketAddr,
11-
listener: TcpListener,
1213
stream_opt: Option<TcpStream>,
1314
}
1415

1516
impl MASQNodeServer {
1617
pub fn new(port: u16) -> MASQNodeServer {
17-
let socket_addr = DockerHostSocketAddr::new(port);
18-
let listener = TcpListener::bind(socket_addr).unwrap();
18+
let dummy_listener = TcpListener::bind(DockerHostSocketAddr::new(port)).unwrap();
19+
let local_addr = dummy_listener.local_addr().unwrap();
1920
MASQNodeServer {
20-
local_addr: listener.local_addr().unwrap(),
21-
listener,
21+
docker_host_addr: Some(DockerHostSocketAddr::new(port)),
22+
local_addr,
2223
stream_opt: None,
2324
}
2425
}
@@ -37,10 +38,17 @@ impl MASQNodeServer {
3738
pub fn wait_for_chunk(&mut self, duration: Duration) -> Result<Vec<u8>, io::Error> {
3839
match &mut self.stream_opt {
3940
None => {
40-
let (stream, _) = self.listener.accept().unwrap();
41-
stream
42-
.set_read_timeout(Some(Duration::from_millis(250)))
43-
.unwrap();
41+
let (tx, rx): (Sender<TcpStream>, Receiver<TcpStream>) = unbounded();
42+
let local_addr = self.docker_host_addr.take().unwrap();
43+
let listener = TcpListener::bind(local_addr).unwrap();
44+
thread::spawn(move || {
45+
let (stream, _) = listener.accept().unwrap();
46+
stream
47+
.set_read_timeout(Some(Duration::from_millis(250)))
48+
.unwrap();
49+
tx.send(stream).unwrap();
50+
});
51+
let stream = rx.recv_timeout(duration).unwrap();
4452
self.stream_opt = Some(stream);
4553
self.wait_for_chunk(duration)
4654
}

multinode_integration_tests/tests/bookkeeping_test.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,6 +112,7 @@ pub fn start_real_node(cluster: &mut MASQNodeCluster, neighbor: NodeReference) -
112112
let index = cluster.next_index();
113113
cluster.start_real_node(
114114
NodeStartupConfigBuilder::standard()
115+
.db_password(None)
115116
.neighbor(neighbor)
116117
.earning_wallet_info(make_earning_wallet_info(&index.to_string()))
117118
.chain(cluster.chain)

multinode_integration_tests/tests/communication_failure_test.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -236,6 +236,7 @@ fn dns_resolution_failure_with_real_nodes() {
236236
let mut cluster = MASQNodeCluster::start().unwrap();
237237
let first_node = cluster.start_real_node(
238238
NodeStartupConfigBuilder::standard()
239+
.db_password(None)
239240
.consuming_wallet_info(make_consuming_wallet_info("first_node"))
240241
.chain(cluster.chain)
241242
.build(),
@@ -244,6 +245,7 @@ fn dns_resolution_failure_with_real_nodes() {
244245
.map(|_| {
245246
cluster.start_real_node(
246247
NodeStartupConfigBuilder::standard()
248+
.db_password(None)
247249
.neighbor(first_node.node_reference())
248250
.chain(cluster.chain)
249251
.build(),
@@ -280,13 +282,15 @@ fn dns_resolution_failure_for_wildcard_ip_with_real_nodes() {
280282
let mut cluster = MASQNodeCluster::start().unwrap();
281283
let exit_node = cluster.start_real_node(
282284
NodeStartupConfigBuilder::standard()
285+
.db_password(None)
283286
.chain(cluster.chain)
284287
.consuming_wallet_info(make_consuming_wallet_info("exit_node"))
285288
.dns_servers(vec![dns_server_that_fails])
286289
.build(),
287290
);
288291
let originating_node = cluster.start_real_node(
289292
NodeStartupConfigBuilder::standard()
293+
.db_password(None)
290294
.neighbor(exit_node.node_reference())
291295
.consuming_wallet_info(make_consuming_wallet_info("originating_node"))
292296
.chain(cluster.chain)

multinode_integration_tests/tests/connection_progress_test.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,15 @@ fn connection_progress_is_properly_broadcast() {
1818
let ui_port = find_free_port();
1919
let mut cluster = MASQNodeCluster::start().unwrap();
2020
// Set up small preexisting network that is much too small to route
21-
let relay_2 = cluster.start_real_node(NodeStartupConfigBuilder::standard().build());
21+
let relay_2 = cluster.start_real_node(
22+
NodeStartupConfigBuilder::standard()
23+
.db_password(Some("relay_2"))
24+
.build(),
25+
);
2226
let relay_1 = cluster.start_real_node(
2327
NodeStartupConfigBuilder::standard()
2428
.neighbor(relay_2.node_reference())
29+
.db_password(Some("relay_1"))
2530
.build(),
2631
);
2732
// Set up Node from which we will get connection-progress information
@@ -32,6 +37,7 @@ fn connection_progress_is_properly_broadcast() {
3237
"0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF".to_string(),
3338
))
3439
.neighbor(relay_1.node_reference())
40+
.db_password(Some("subject"))
3541
.ui_port(ui_port)
3642
.build(),
3743
);
@@ -40,10 +46,11 @@ fn connection_progress_is_properly_broadcast() {
4046
// Hook up enough new Nodes to make the subject fully connected
4147
let _additional_nodes = (0..3)
4248
.into_iter()
43-
.map(|_| {
49+
.map(|i| {
4450
cluster.start_real_node(
4551
NodeStartupConfigBuilder::standard()
4652
.neighbor(relay_2.node_reference())
53+
.db_password(Some(format!("additional_{}", i).as_str()))
4754
.build(),
4855
)
4956
})

multinode_integration_tests/tests/self_test.rs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
// Copyright (c) 2019, MASQ (https://masq.ai) and/or its affiliates. All rights reserved.
22

3+
use masq_lib::test_utils::utils::TEST_DEFAULT_CHAIN;
34
use multinode_integration_tests_lib::command::Command;
45
use multinode_integration_tests_lib::main::CONTROL_STREAM_PORT;
56
use multinode_integration_tests_lib::masq_cores_client::MASQCoresClient;
@@ -10,11 +11,12 @@ use multinode_integration_tests_lib::masq_node_cluster::MASQNodeCluster;
1011
use multinode_integration_tests_lib::masq_real_node::NodeStartupConfigBuilder;
1112
use node_lib::json_masquerader::JsonMasquerader;
1213
use node_lib::sub_lib::cryptde::PublicKey;
14+
use node_lib::sub_lib::cryptde_null::CryptDENull;
1315
use node_lib::sub_lib::dispatcher::Component;
1416
use node_lib::sub_lib::hopper::IncipientCoresPackage;
1517
use node_lib::sub_lib::route::Route;
1618
use node_lib::sub_lib::route::RouteSegment;
17-
use node_lib::test_utils::{main_cryptde, make_meaningless_message_type, make_paying_wallet};
19+
use node_lib::test_utils::{make_meaningless_message_type, make_paying_wallet};
1820
use std::collections::HashSet;
1921
use std::io::ErrorKind;
2022
use std::net::IpAddr;
@@ -108,7 +110,7 @@ fn one_mock_node_talks_to_another() {
108110
cluster.start_mock_node_with_public_key(vec![5551], &PublicKey::new(&[2, 3, 4, 5]));
109111
let mock_node_1 = cluster.get_mock_node_by_name("mock_node_1").unwrap();
110112
let mock_node_2 = cluster.get_mock_node_by_name("mock_node_2").unwrap();
111-
let cryptde = main_cryptde();
113+
let cryptde = CryptDENull::new(TEST_DEFAULT_CHAIN);
112114
let route = Route::one_way(
113115
RouteSegment::new(
114116
vec![
@@ -117,13 +119,13 @@ fn one_mock_node_talks_to_another() {
117119
],
118120
Component::Hopper,
119121
),
120-
cryptde,
122+
&cryptde,
121123
Some(make_paying_wallet(b"consuming")),
122124
Some(cluster.chain.rec().contract),
123125
)
124126
.unwrap();
125127
let incipient_cores_package = IncipientCoresPackage::new(
126-
cryptde,
128+
&cryptde,
127129
route,
128130
make_meaningless_message_type(),
129131
&mock_node_2.main_public_key(),

node/ci/integration_tests.sh

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,12 @@ case "$OSTYPE" in
1515
Darwin | darwin*)
1616
echo "macOS"
1717
[[ $GITHUB_ACTIONS -eq true ]] && sudo launchctl limit maxfiles 524288 524288 && ulimit -Sn 524288 && sudo launchctl limit maxfiles
18-
sudo --preserve-env ci/run_integration_tests.sh "$TOOLCHAIN_HOME"
18+
sudo --preserve-env ci/run_integration_tests.sh
1919
;;
2020
linux-gnu)
2121
echo "Linux"
2222
[[ $GITHUB_ACTIONS -eq true ]] && sudo --preserve-env ci/free-port-53.sh
23-
sudo --preserve-env ci/run_integration_tests.sh "$TOOLCHAIN_HOME"
23+
sudo --preserve-env ci/run_integration_tests.sh
2424
;;
2525
*)
2626
exit 1

node/ci/run_integration_tests.sh

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,19 @@ export RUST_BACKTRACE=full
88
export RUSTFLAGS="-D warnings -Anon-snake-case"
99
umask 000
1010

11-
pushd "$CI_DIR/.."
12-
cargo test --release --no-fail-fast -- --nocapture --test-threads=1 _integration
11+
if [ "$1" == "" ]; then
12+
TEST_NAME_FRAGMENT="_integration"
13+
else
14+
if [[ "$USER" != "root" ]]; then
15+
echo "run_integration_tests.sh must be run as root"
16+
exit 1
17+
fi
18+
TEST_NAME_FRAGMENT="$1"
19+
fi
20+
21+
pushd "$CI_DIR/.." || { echo "Failed to pushd $CI_DIR/.."; exit 1; }
22+
cargo test --release --no-fail-fast -- --nocapture --test-threads=1 "$TEST_NAME_FRAGMENT"
1323
BUILD_RESULT=$?
1424
chmod -R 777 target
15-
popd
25+
popd || { echo "Failed to popd"; exit 1; }
1626
exit "$BUILD_RESULT"

0 commit comments

Comments
 (0)