mirror of
https://github.com/XRPLF/rippled.git
synced 2025-12-06 17:27:55 +00:00
Remove conditionals for fix1528 enabled 14Nov2017
This commit is contained in:
@@ -592,153 +592,103 @@ public:
|
||||
// This is a specialized test engineered to yield ledgers with different
|
||||
// close times even though the peers believe they had close time
|
||||
// consensus on the ledger.
|
||||
ConsensusParms parms;
|
||||
|
||||
for (bool useRoundedCloseTime : {false, true})
|
||||
Sim sim;
|
||||
|
||||
// This requires a group of 4 fast and 2 slow peers to create a
|
||||
// situation in which a subset of peers requires seeing additional
|
||||
// proposals to declare consensus.
|
||||
PeerGroup slow = sim.createGroup(2);
|
||||
PeerGroup fast = sim.createGroup(4);
|
||||
PeerGroup network = fast + slow;
|
||||
|
||||
for (Peer* peer : network)
|
||||
peer->consensusParms = parms;
|
||||
|
||||
// Connected trust graph
|
||||
network.trust(network);
|
||||
|
||||
// Fast and slow network connections
|
||||
fast.connect(
|
||||
fast, date::round<milliseconds>(0.2 * parms.ledgerGRANULARITY));
|
||||
slow.connect(
|
||||
network,
|
||||
date::round<milliseconds>(1.1 * parms.ledgerGRANULARITY));
|
||||
|
||||
// Run to the ledger *prior* to decreasing the resolution
|
||||
sim.run(increaseLedgerTimeResolutionEvery - 2);
|
||||
|
||||
// In order to create the discrepency, we want a case where if
|
||||
// X = effCloseTime(closeTime, resolution, parentCloseTime)
|
||||
// X != effCloseTime(X, resolution, parentCloseTime)
|
||||
//
|
||||
// That is, the effective close time is not a fixed point. This can
|
||||
// happen if X = parentCloseTime + 1, but a subsequent rounding goes
|
||||
// to the next highest multiple of resolution.
|
||||
|
||||
// So we want to find an offset (now + offset) % 30s = 15
|
||||
// (now + offset) % 20s = 15
|
||||
// This way, the next ledger will close and round up Due to the
|
||||
// network delay settings, the round of consensus will take 5s, so
|
||||
// the next ledger's close time will
|
||||
|
||||
NetClock::duration when = network[0]->now().time_since_epoch();
|
||||
|
||||
// Check we are before the 30s to 20s transition
|
||||
NetClock::duration resolution =
|
||||
network[0]->lastClosedLedger.closeTimeResolution();
|
||||
BEAST_EXPECT(resolution == NetClock::duration{30s});
|
||||
|
||||
while (
|
||||
((when % NetClock::duration{30s}) != NetClock::duration{15s}) ||
|
||||
((when % NetClock::duration{20s}) != NetClock::duration{15s}))
|
||||
when += 1s;
|
||||
// Advance the clock without consensus running (IS THIS WHAT
|
||||
// PREVENTS IT IN PRACTICE?)
|
||||
sim.scheduler.step_for(
|
||||
NetClock::time_point{when} - network[0]->now());
|
||||
|
||||
// Run one more ledger with 30s resolution
|
||||
sim.run(1);
|
||||
if (BEAST_EXPECT(sim.synchronized()))
|
||||
{
|
||||
ConsensusParms parms;
|
||||
parms.useRoundedCloseTime = useRoundedCloseTime;
|
||||
|
||||
Sim sim;
|
||||
|
||||
// This requires a group of 4 fast and 2 slow peers to create a
|
||||
// situation in which a subset of peers requires seeing additional
|
||||
// proposals to declare consensus.
|
||||
PeerGroup slow = sim.createGroup(2);
|
||||
PeerGroup fast = sim.createGroup(4);
|
||||
PeerGroup network = fast + slow;
|
||||
|
||||
// close time should be ahead of clock time since we engineered
|
||||
// the close time to round up
|
||||
for (Peer* peer : network)
|
||||
peer->consensusParms = parms;
|
||||
|
||||
// Connected trust graph
|
||||
network.trust(network);
|
||||
|
||||
// Fast and slow network connections
|
||||
fast.connect(
|
||||
fast, date::round<milliseconds>(0.2 * parms.ledgerGRANULARITY));
|
||||
slow.connect(
|
||||
network,
|
||||
date::round<milliseconds>(1.1 * parms.ledgerGRANULARITY));
|
||||
|
||||
// Run to the ledger *prior* to decreasing the resolution
|
||||
sim.run(increaseLedgerTimeResolutionEvery - 2);
|
||||
|
||||
// In order to create the discrepency, we want a case where if
|
||||
// X = effCloseTime(closeTime, resolution, parentCloseTime)
|
||||
// X != effCloseTime(X, resolution, parentCloseTime)
|
||||
//
|
||||
// That is, the effective close time is not a fixed point. This can
|
||||
// happen if X = parentCloseTime + 1, but a subsequent rounding goes
|
||||
// to the next highest multiple of resolution.
|
||||
|
||||
// So we want to find an offset (now + offset) % 30s = 15
|
||||
// (now + offset) % 20s = 15
|
||||
// This way, the next ledger will close and round up Due to the
|
||||
// network delay settings, the round of consensus will take 5s, so
|
||||
// the next ledger's close time will
|
||||
|
||||
NetClock::duration when = network[0]->now().time_since_epoch();
|
||||
|
||||
// Check we are before the 30s to 20s transition
|
||||
NetClock::duration resolution =
|
||||
network[0]->lastClosedLedger.closeTimeResolution();
|
||||
BEAST_EXPECT(resolution == NetClock::duration{30s});
|
||||
|
||||
while (
|
||||
((when % NetClock::duration{30s}) != NetClock::duration{15s}) ||
|
||||
((when % NetClock::duration{20s}) != NetClock::duration{15s}))
|
||||
when += 1s;
|
||||
// Advance the clock without consensus running (IS THIS WHAT
|
||||
// PREVENTS IT IN PRACTICE?)
|
||||
sim.scheduler.step_for(
|
||||
NetClock::time_point{when} - network[0]->now());
|
||||
|
||||
// Run one more ledger with 30s resolution
|
||||
sim.run(1);
|
||||
if (BEAST_EXPECT(sim.synchronized()))
|
||||
{
|
||||
// close time should be ahead of clock time since we engineered
|
||||
// the close time to round up
|
||||
for (Peer* peer : network)
|
||||
{
|
||||
BEAST_EXPECT(
|
||||
peer->lastClosedLedger.closeTime() > peer->now());
|
||||
BEAST_EXPECT(peer->lastClosedLedger.closeAgree());
|
||||
}
|
||||
}
|
||||
|
||||
// All peers submit their own ID as a transaction
|
||||
for (Peer* peer : network)
|
||||
peer->submit(Tx{static_cast<std::uint32_t>(peer->id)});
|
||||
|
||||
// Run 1 more round, this time it will have a decreased
|
||||
// resolution of 20 seconds.
|
||||
|
||||
// The network delays are engineered so that the slow peers
|
||||
// initially have the wrong tx hash, but they see a majority
|
||||
// of agreement from their peers and declare consensus
|
||||
//
|
||||
// The trick is that everyone starts with a raw close time of
|
||||
// 84681s
|
||||
// Which has
|
||||
// effCloseTime(86481s, 20s, 86490s) = 86491s
|
||||
// However, when the slow peers update their position, they change
|
||||
// the close time to 86451s. The fast peers declare consensus with
|
||||
// the 86481s as their position still.
|
||||
//
|
||||
// When accepted the ledger
|
||||
// - fast peers use eff(86481s) -> 86491s as the close time
|
||||
// - slow peers use eff(eff(86481s)) -> eff(86491s) -> 86500s!
|
||||
|
||||
sim.run(1);
|
||||
|
||||
if (parms.useRoundedCloseTime)
|
||||
{
|
||||
BEAST_EXPECT(sim.synchronized());
|
||||
}
|
||||
else
|
||||
{
|
||||
// Not currently synchronized
|
||||
BEAST_EXPECT(!sim.synchronized());
|
||||
|
||||
// All slow peers agreed on LCL
|
||||
BEAST_EXPECT(std::all_of(
|
||||
slow.begin(), slow.end(), [&slow](Peer const* p) {
|
||||
return p->lastClosedLedger.id() ==
|
||||
slow[0]->lastClosedLedger.id();
|
||||
}));
|
||||
|
||||
// All fast peers agreed on LCL
|
||||
BEAST_EXPECT(std::all_of(
|
||||
fast.begin(), fast.end(), [&fast](Peer const* p) {
|
||||
return p->lastClosedLedger.id() ==
|
||||
fast[0]->lastClosedLedger.id();
|
||||
}));
|
||||
|
||||
Ledger const& slowLCL = slow[0]->lastClosedLedger;
|
||||
Ledger const& fastLCL = fast[0]->lastClosedLedger;
|
||||
|
||||
// Agree on parent close and close resolution
|
||||
BEAST_EXPECT(
|
||||
slowLCL.parentCloseTime() == fastLCL.parentCloseTime());
|
||||
BEAST_EXPECT(
|
||||
slowLCL.closeTimeResolution() ==
|
||||
fastLCL.closeTimeResolution());
|
||||
|
||||
// Close times disagree ...
|
||||
BEAST_EXPECT(slowLCL.closeTime() != fastLCL.closeTime());
|
||||
// Effective close times agree! The slow peer already rounded!
|
||||
BEAST_EXPECT(
|
||||
effCloseTime(
|
||||
slowLCL.closeTime(),
|
||||
slowLCL.closeTimeResolution(),
|
||||
slowLCL.parentCloseTime()) ==
|
||||
effCloseTime(
|
||||
fastLCL.closeTime(),
|
||||
fastLCL.closeTimeResolution(),
|
||||
fastLCL.parentCloseTime()));
|
||||
peer->lastClosedLedger.closeTime() > peer->now());
|
||||
BEAST_EXPECT(peer->lastClosedLedger.closeAgree());
|
||||
}
|
||||
}
|
||||
|
||||
// All peers submit their own ID as a transaction
|
||||
for (Peer* peer : network)
|
||||
peer->submit(Tx{static_cast<std::uint32_t>(peer->id)});
|
||||
|
||||
// Run 1 more round, this time it will have a decreased
|
||||
// resolution of 20 seconds.
|
||||
|
||||
// The network delays are engineered so that the slow peers
|
||||
// initially have the wrong tx hash, but they see a majority
|
||||
// of agreement from their peers and declare consensus
|
||||
//
|
||||
// The trick is that everyone starts with a raw close time of
|
||||
// 84681s
|
||||
// Which has
|
||||
// effCloseTime(86481s, 20s, 86490s) = 86491s
|
||||
// However, when the slow peers update their position, they change
|
||||
// the close time to 86451s. The fast peers declare consensus with
|
||||
// the 86481s as their position still.
|
||||
//
|
||||
// When accepted the ledger
|
||||
// - fast peers use eff(86481s) -> 86491s as the close time
|
||||
// - slow peers use eff(eff(86481s)) -> eff(86491s) -> 86500s!
|
||||
|
||||
sim.run(1);
|
||||
|
||||
BEAST_EXPECT(sim.synchronized());
|
||||
}
|
||||
|
||||
void
|
||||
|
||||
Reference in New Issue
Block a user