19 #include <ripple/basics/random.h>
20 #include <ripple/beast/unit_test.h>
21 #include <ripple/overlay/Message.h>
22 #include <ripple/overlay/Peer.h>
23 #include <ripple/overlay/Slot.h>
24 #include <ripple/protocol/SecretKey.h>
25 #include <ripple.pb.h>
26 #include <test/jtx/Env.h>
28 #include <boost/optional.hpp>
29 #include <boost/thread.hpp>
67 onMessage(protocol::TMSquelch
const& squelch) = 0;
69 send(protocol::TMSquelch
const& squelch)
119 boost::optional<std::size_t>
177 inline static const bool is_steady =
false;
188 now_ += randDuration(min, max);
223 updateSlotAndSquelch(
228 protocol::MessageType type = protocol::mtVALIDATION) = 0;
249 : validator_(validator), peer_(peer), latency_(latency), up_(
true)
251 auto sp = peer_.lock();
260 auto sp = peer_.lock();
262 auto peer = std::dynamic_pointer_cast<PeerPartial>(sp);
263 peer->onMessage(m, f);
278 auto p = peer_.lock();
285 auto p = peer_.lock();
306 protocol::TMValidation v;
307 v.set_validation(
"validation");
308 message_ = std::make_shared<Message>(v, protocol::mtVALIDATION, pkey_);
361 for (
auto id : peers)
363 assert(links_.find(
id) != links_.end());
364 f(*links_[
id], message_);
415 auto it = links_.find(
id);
416 assert(it != links_.end());
417 it->second->up(
true);
423 auto it = links_.find(
id);
424 assert(it != links_.end());
425 it->second->up(
false);
468 overlay_.updateSlotAndSquelch({}, *
validator, id(), f);
475 auto validator = squelch.validatorpubkey();
477 squelch_.squelch(key, squelch.squelch(), squelch.squelchduration());
505 slots_.deleteIdlePeers();
511 auto res = slots_.inState(
validator, state);
512 return res ? *res : 0;
521 protocol::MessageType type = protocol::mtVALIDATION)
override
524 slots_.updateSlotAndSquelch(key,
validator,
id, type);
531 slots_.deletePeer(
id,
true);
538 slots_.deleteIdlePeers();
546 if (peersCache_.empty() || !useCache)
548 peer = std::make_shared<PeerSim>(*
this);
553 auto it = peersCache_.begin();
556 peersCache_.erase(it);
565 auto it = peers_.find(
id);
566 assert(it != peers_.end());
576 while (!peers_.empty())
577 deletePeer(peers_.begin()->first);
578 while (!peersCache_.empty())
590 for (
auto& [
id, _] : peers_)
597 deletePeer(maxId,
false);
617 auto selected = slots_.getSelected(
validator);
618 return selected.find(peer) != selected.end();
624 auto selected = slots_.getSelected(
validator);
625 assert(selected.size());
626 return *selected.begin();
644 return peers_.size();
654 if (
auto it = peers_.find(
id); it != peers_.end())
655 squelch_(
validator, it->second, squelchDuration);
660 if (
auto it = peers_.find(
id); it != peers_.end())
684 auto peer = overlay_.addPeer();
685 for (
auto& v : validators_)
705 auto peer = overlay_.addPeer();
706 for (
auto& v : validators_)
714 auto id = overlay_.deleteLastPeer();
726 while (overlay_.getNumPeers() >
MAX_PEERS)
733 assert(v < validators_.size());
734 return validators_[v];
747 std::find_if(validators_.begin(), validators_.end(), [&](
auto& v) {
748 return v.id() == validatorId;
750 assert(it != validators_.end());
764 protocol::TMSquelch squelch;
765 squelch.set_squelch(
false);
766 for (
auto& v : validators_)
769 squelch.clear_validatorpubkey();
770 squelch.set_validatorpubkey(key.
data(), key.
size());
772 std::dynamic_pointer_cast<PeerSim>(l.
getPeer())->send(squelch);
783 auto size = max - min;
799 bool resetClock =
true)
807 overlay_.resetPeers();
810 for (
int m = 0; m < nMessages; ++m)
814 validators_[v].for_links(link);
823 for (
auto& v : validators_)
825 if (overlay_.isSelected(v,
id))
838 for (
auto& v : validators_)
840 if (!overlay_.isSelected(v, peer))
842 auto peers = overlay_.getPeers(v);
843 for (
auto& [_, v] : peers)
846 if (std::get<squelch::PeerState>(v) ==
868 auto peers = network_.overlay().getPeers(network_.validator(
validator));
870 <<
"num peers " << (int)network_.overlay().getNumPeers()
872 for (
auto& [k, v] : peers)
873 std::cout << k <<
":" << (int)std::get<squelch::PeerState>(v)
885 protocol::TMSquelch squelch;
887 squelch.set_squelch(res);
890 squelch.set_squelchduration(*
duration);
891 auto sp = peerPtr.
lock();
893 std::dynamic_pointer_cast<PeerSim>(sp)->send(squelch);
908 bool isSelected_ =
false;
913 bool handled_ =
false;
923 {LinkDown, {}}, {PeerDisconnected, {}}};
931 bool squelched =
false;
940 auto p = sendSquelch(key, peerPtr,
duration);
947 auto selected = network_.overlay().getSelected(
validator);
948 str <<
" selected: ";
949 for (
auto s : selected)
953 << (double)squelch::epoch<milliseconds>(now).count() /
955 <<
" random, squelched, validator: " <<
validator.id()
958 network_.overlay().isCountingState(
validator);
960 countingState ==
false &&
966 if (events[EventType::LinkDown].state_ == State::Off)
969 events[event].cnt_++;
970 events[event].validator_ =
validator.id();
972 events[event].peer_ = link.
peerId();
973 events[event].state_ = State::On;
974 events[event].time_ = now;
975 if (event == EventType::LinkDown)
979 events[event].isSelected_ =
980 network_.overlay().isSelected(
984 events[event].isSelected_ =
985 network_.isSelected(link.
peerId());
988 if (r == (
int)EventType::LinkDown ||
989 r == (
int)EventType::PeerDisconnected)
995 if (events[EventType::PeerDisconnected].state_ == State::On)
997 auto&
event = events[EventType::PeerDisconnected];
998 bool allCounting = network_.allCounting(event.peer_);
999 network_.overlay().deletePeer(
1002 if (event.isSelected_)
1003 sendSquelch(v, peerPtr, {});
1004 event.handled_ =
true;
1012 (
event.isSelected_ ==
false && !
event.handled_) ||
1013 (event.isSelected_ ==
true &&
1014 (event.handled_ || allCounting));
1015 BEAST_EXPECT(handled);
1016 event.state_ = State::Off;
1017 event.isSelected_ =
false;
1018 event.handledCnt_ += handled;
1019 event.handled_ =
false;
1020 network_.onDisconnectPeer(event.peer_);
1023 auto&
event = events[EventType::LinkDown];
1035 bool mustHandle =
false;
1036 if (event.state_ == State::On)
1039 network_.overlay().isSelected(event.key_, event.peer_);
1040 auto peers = network_.overlay().getPeers(event.key_);
1041 auto d = squelch::epoch<milliseconds>(now).count() -
1042 std::get<3>(peers[event.peer_]);
1043 mustHandle =
event.isSelected_ &&
1045 network_.overlay().inState(
1047 peers.find(event.peer_) != peers.end();
1049 network_.overlay().deleteIdlePeers(
1051 event.handled_ =
true;
1052 if (mustHandle && v == event.key_)
1054 event.state_ = State::WaitReset;
1055 sendSquelch(validator, ptr, {});
1059 (
event.handled_ &&
event.state_ == State::WaitReset) ||
1060 (!event.handled_ && !mustHandle);
1061 BEAST_EXPECT(handled);
1063 if (event.state_ == State::WaitReset ||
1064 (event.state_ == State::On &&
1068 event.state_ == State::WaitReset || !
event.handled_;
1069 BEAST_EXPECT(handled);
1070 event.state_ = State::Off;
1071 event.isSelected_ =
false;
1072 event.handledCnt_ += handled;
1073 event.handled_ =
false;
1074 network_.enableLink(event.validator_, event.peer_,
true);
1078 auto& down = events[EventType::LinkDown];
1079 auto& disconnected = events[EventType::PeerDisconnected];
1081 BEAST_EXPECT(down.handledCnt_ >= down.cnt_ - 1);
1083 BEAST_EXPECT(disconnected.cnt_ == disconnected.handledCnt_);
1085 std::cout <<
"link down count: " << down.cnt_ <<
"/"
1087 <<
" peer disconnect count: " << disconnected.cnt_ <<
"/"
1088 << disconnected.handledCnt_;
1094 auto countingState = network_.overlay().isCountingState(
validator);
1095 BEAST_EXPECT(countingState == isCountingState);
1096 return countingState == isCountingState;
1114 doTest(
"Initial Round", log, [
this](
bool log) {
1115 BEAST_EXPECT(propagateAndSquelch(log));
1125 doTest(
"Peer Unsquelched Too Soon", log, [
this](
bool log) {
1126 BEAST_EXPECT(propagateNoSquelch(log, 1,
false,
false,
false));
1137 doTest(
"Peer Unsquelched", log, [
this](
bool log) {
1138 BEAST_EXPECT(propagateNoSquelch(log, 2,
true,
true,
false));
1156 sendSquelch(key, peerPtr,
duration);
1169 auto selected = network_.overlay().getSelected(network_.validator(0));
1171 BEAST_EXPECT(n == 1);
1172 auto res = checkCounting(network_.validator(0),
false);
1174 return n == 1 && res;
1184 bool resetClock =
true)
1186 bool squelched =
false;
1195 BEAST_EXPECT(
false);
1202 auto res = checkCounting(network_.validator(0), countingState);
1203 return !squelched && res;
1212 doTest(
"New Peer", log, [
this](
bool log) {
1213 BEAST_EXPECT(propagateAndSquelch(log,
true,
false));
1215 BEAST_EXPECT(propagateNoSquelch(log, 1,
true,
false,
false));
1224 doTest(
"Selected Peer Disconnects", log, [
this](
bool log) {
1226 BEAST_EXPECT(propagateAndSquelch(log,
true,
false));
1227 auto id = network_.overlay().getSelectedPeer(network_.validator(0));
1229 network_.overlay().deletePeer(
1235 BEAST_EXPECT(checkCounting(network_.validator(0),
true));
1244 doTest(
"Selected Peer Stops Relaying", log, [
this](
bool log) {
1246 BEAST_EXPECT(propagateAndSquelch(log,
true,
false));
1249 network_.overlay().deleteIdlePeers(
1253 auto peers = network_.overlay().getPeers(network_.validator(0));
1256 BEAST_EXPECT(checkCounting(network_.validator(0),
true));
1265 doTest(
"Squelched Peer Disconnects", log, [
this](
bool log) {
1267 BEAST_EXPECT(propagateAndSquelch(log,
true,
false));
1268 auto peers = network_.overlay().getPeers(network_.validator(0));
1269 auto it =
std::find_if(peers.begin(), peers.end(), [&](
auto it) {
1270 return std::get<squelch::PeerState>(it.second) ==
1271 squelch::PeerState::Squelched;
1273 assert(it != peers.end());
1275 network_.overlay().deletePeer(
1279 BEAST_EXPECT(unsquelched == 0);
1280 BEAST_EXPECT(checkCounting(network_.validator(0),
false));
1287 doTest(
"Config Test", log, [&](
bool log) {
1302 toLoad = (R
"rippleConfig(
1314 toLoad = R
"rippleConfig(
1329 doTest(
"Duplicate Message", log, [&](
bool log) {
1333 for (
int i = 0; i < nMessages; i++)
1336 network_.overlay().updateSlotAndSquelch(
1338 network_.validator(0),
1342 auto peers = network_.overlay().getPeers(network_.validator(0));
1345 BEAST_EXPECT(std::get<1>(peers[0]) == (nMessages - 1));
1348 network_.overlay().updateSlotAndSquelch(
1350 network_.validator(0),
1354 peers = network_.overlay().getPeers(network_.validator(0));
1355 BEAST_EXPECT(std::get<1>(peers[0]) == (nMessages - 1));
1358 network_.overlay().updateSlotAndSquelch(
1360 network_.validator(0),
1363 peers = network_.overlay().getPeers(network_.validator(0));
1365 BEAST_EXPECT(std::get<1>(peers[0]) == nMessages);
1382 testInitialRound(log);
1383 testPeerUnsquelchedTooSoon(log);
1384 testPeerUnsquelched(log);
1386 testSquelchedPeerDisconnects(log);
1387 testSelectedPeerDisconnects(log);
1388 testSelectedPeerStopsRelaying(log);
1389 testInternalHashRouter(log);
1398 doTest(
"Random Test", log, [&](
bool log) { random(log); });
1410 BEAST_DEFINE_TESTSUITE_MANUAL(reduce_relay_simulate, ripple_data,
ripple);