catchunks: Implement CUBIC window adaptation
Also increase the RTT estimator multiplier k to 8.
Change-Id: I68c5096ac0da854f071bab5f7519b1c144f20ca1
refs: #4861
diff --git a/tests/chunks/pipeline-interests-adaptive.t.cpp b/tests/chunks/pipeline-interests-aimd.t.cpp
similarity index 97%
rename from tests/chunks/pipeline-interests-adaptive.t.cpp
rename to tests/chunks/pipeline-interests-aimd.t.cpp
index 1cc4f04..57022a6 100644
--- a/tests/chunks/pipeline-interests-adaptive.t.cpp
+++ b/tests/chunks/pipeline-interests-aimd.t.cpp
@@ -25,7 +25,7 @@
* @author Klaus Schneider
*/
-#include "tools/chunks/catchunks/pipeline-interests-adaptive.hpp"
+#include "tools/chunks/catchunks/pipeline-interests-aimd.hpp"
#include "tools/chunks/catchunks/options.hpp"
#include "pipeline-interests-fixture.hpp"
@@ -36,10 +36,10 @@
using namespace ndn::tests;
-class PipelineInterestAdaptiveFixture : public PipelineInterestsFixture
+class PipelineInterestAimdFixture : public PipelineInterestsFixture
{
public:
- PipelineInterestAdaptiveFixture()
+ PipelineInterestAimdFixture()
: opt(makePipelineOptions())
, rttEstimator(makeRttEstimatorOptions())
{
@@ -49,7 +49,7 @@
void
createPipeline()
{
- auto pline = make_unique<PipelineInterestsAdaptive>(face, rttEstimator, opt);
+ auto pline = make_unique<PipelineInterestsAimd>(face, rttEstimator, opt);
pipeline = pline.get();
setPipeline(std::move(pline));
}
@@ -90,10 +90,10 @@
static constexpr double MARGIN = 0.01;
};
-constexpr double PipelineInterestAdaptiveFixture::MARGIN;
+constexpr double PipelineInterestAimdFixture::MARGIN;
BOOST_AUTO_TEST_SUITE(Chunks)
-BOOST_FIXTURE_TEST_SUITE(TestPipelineInterestsAdaptive, PipelineInterestAdaptiveFixture)
+BOOST_FIXTURE_TEST_SUITE(TestPipelineInterestsAimd, PipelineInterestAimdFixture)
BOOST_AUTO_TEST_CASE(SlowStart)
{
@@ -608,7 +608,7 @@
}
-BOOST_AUTO_TEST_SUITE_END() // TestPipelineInterestsAdaptive
+BOOST_AUTO_TEST_SUITE_END() // TestPipelineInterestsAimd
BOOST_AUTO_TEST_SUITE_END() // Chunks
} // namespace tests
diff --git a/tests/chunks/pipeline-interests-adaptive.t.cpp b/tests/chunks/pipeline-interests-cubic.t.cpp
similarity index 86%
copy from tests/chunks/pipeline-interests-adaptive.t.cpp
copy to tests/chunks/pipeline-interests-cubic.t.cpp
index 1cc4f04..b42728b 100644
--- a/tests/chunks/pipeline-interests-adaptive.t.cpp
+++ b/tests/chunks/pipeline-interests-cubic.t.cpp
@@ -25,7 +25,7 @@
* @author Klaus Schneider
*/
-#include "tools/chunks/catchunks/pipeline-interests-adaptive.hpp"
+#include "tools/chunks/catchunks/pipeline-interests-cubic.hpp"
#include "tools/chunks/catchunks/options.hpp"
#include "pipeline-interests-fixture.hpp"
@@ -36,10 +36,10 @@
using namespace ndn::tests;
-class PipelineInterestAdaptiveFixture : public PipelineInterestsFixture
+class PipelineInterestCubicFixture : public PipelineInterestsFixture
{
public:
- PipelineInterestAdaptiveFixture()
+ PipelineInterestCubicFixture()
: opt(makePipelineOptions())
, rttEstimator(makeRttEstimatorOptions())
{
@@ -49,16 +49,16 @@
void
createPipeline()
{
- auto pline = make_unique<PipelineInterestsAdaptive>(face, rttEstimator, opt);
+ auto pline = make_unique<PipelineInterestsCubic>(face, rttEstimator, opt);
pipeline = pline.get();
setPipeline(std::move(pline));
}
private:
- static PipelineInterestsAdaptive::Options
+ static PipelineInterestsCubic::Options
makePipelineOptions()
{
- PipelineInterestsAdaptive::Options pipelineOptions;
+ PipelineInterestsCubic::Options pipelineOptions;
pipelineOptions.isQuiet = true;
pipelineOptions.isVerbose = false;
pipelineOptions.disableCwa = false;
@@ -68,6 +68,8 @@
pipelineOptions.aiStep = 1.0;
pipelineOptions.mdCoef = 0.5;
pipelineOptions.initSsthresh = std::numeric_limits<int>::max();
+ pipelineOptions.cubicBeta = 0.7;
+ pipelineOptions.enableFastConv = false;
return pipelineOptions;
}
@@ -77,28 +79,27 @@
RttEstimator::Options rttOptions;
rttOptions.alpha = 0.125;
rttOptions.beta = 0.25;
- rttOptions.k = 4;
+ rttOptions.k = 8;
rttOptions.minRto = Milliseconds(200);
rttOptions.maxRto = Milliseconds(4000);
return rttOptions;
}
protected:
- PipelineInterestsAdaptive::Options opt;
+ PipelineInterestsCubic::Options opt;
RttEstimator rttEstimator;
- PipelineInterestsAdaptive* pipeline;
+ PipelineInterestsCubic* pipeline;
static constexpr double MARGIN = 0.01;
};
-constexpr double PipelineInterestAdaptiveFixture::MARGIN;
+constexpr double PipelineInterestCubicFixture::MARGIN;
BOOST_AUTO_TEST_SUITE(Chunks)
-BOOST_FIXTURE_TEST_SUITE(TestPipelineInterestsAdaptive, PipelineInterestAdaptiveFixture)
+BOOST_FIXTURE_TEST_SUITE(TestPipelineInterestsCubic, PipelineInterestCubicFixture)
BOOST_AUTO_TEST_CASE(SlowStart)
{
nDataSegments = 4;
- pipeline->m_ssthresh = 8.0;
BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
double preCwnd = pipeline->m_cwnd;
@@ -116,39 +117,10 @@
BOOST_CHECK_EQUAL(pipeline->m_nReceived, nDataSegments - 1);
}
-BOOST_AUTO_TEST_CASE(CongestionAvoidance)
-{
- nDataSegments = 7;
- pipeline->m_ssthresh = 4.0;
- BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
-
- double preCwnd = pipeline->m_cwnd;
- run(name);
- advanceClocks(io, time::nanoseconds(1));
- BOOST_CHECK_EQUAL(face.sentInterests.size(), 1);
-
- for (uint64_t i = 0; i < pipeline->m_ssthresh; ++i) { // slow start
- face.receive(*makeDataWithSegment(i));
- advanceClocks(io, time::nanoseconds(1));
- preCwnd = pipeline->m_cwnd;
- }
-
- BOOST_CHECK_CLOSE(preCwnd, 4.25, MARGIN);
-
- for (uint64_t i = pipeline->m_ssthresh; i < nDataSegments - 1; ++i) { // congestion avoidance
- face.receive(*makeDataWithSegment(i));
- advanceClocks(io, time::nanoseconds(1));
- BOOST_CHECK_CLOSE(pipeline->m_cwnd - preCwnd, opt.aiStep / floor(pipeline->m_cwnd), MARGIN);
- preCwnd = pipeline->m_cwnd;
- }
-
- BOOST_CHECK_EQUAL(pipeline->m_nReceived, nDataSegments - 1);
-}
BOOST_AUTO_TEST_CASE(Timeout)
{
nDataSegments = 8;
- pipeline->m_ssthresh = 4.0;
BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
run(name);
@@ -176,7 +148,7 @@
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 5);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.5, MARGIN);
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 6.0, MARGIN);
BOOST_CHECK_EQUAL(face.sentInterests.size(), nDataSegments); // all the segment requests have been sent
BOOST_CHECK_EQUAL(pipeline->m_nTimeouts, 0);
@@ -189,20 +161,20 @@
// timeout segment 3 & 6
advanceClocks(io, time::milliseconds(150));
BOOST_CHECK_EQUAL(pipeline->m_nTimeouts, 2);
- BOOST_CHECK_EQUAL(pipeline->m_nRetransmitted, 1);
+ BOOST_CHECK_EQUAL(pipeline->m_nRetransmitted, 2);
BOOST_CHECK_EQUAL(pipeline->m_nLossDecr, 1);
BOOST_CHECK_EQUAL(pipeline->m_nSkippedRetx, 0);
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 5);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.25, MARGIN); // window size drop to 1/2 of previous size
- BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 1);
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.2, MARGIN); // window size drop to 0.7x of previous size
+ BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 0);
// receive segment 6, retransmit 3
face.receive(*makeDataWithSegment(6));
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 6);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.75, MARGIN); // congestion avoidance
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.2, MARGIN); // congestion avoidance
BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 0);
BOOST_CHECK_EQUAL(pipeline->m_retxCount[3], 1);
@@ -216,7 +188,6 @@
BOOST_AUTO_TEST_CASE(CongestionMarksWithCwa)
{
nDataSegments = 7;
- pipeline->m_ssthresh = 4.0;
BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
run(name);
@@ -230,14 +201,14 @@
}
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 5);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.5, MARGIN);
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 6.0, MARGIN);
// receive segment 5 with congestion mark
face.receive(*makeDataWithSegmentAndCongMark(5));
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 6);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.25, MARGIN); // window size drops to 1/2 of previous size
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.2, MARGIN); // window size drops to 1/2 of previous size
BOOST_CHECK_EQUAL(face.sentInterests.size(), nDataSegments); // all interests have been sent
// receive the last segment with congestion mark
@@ -245,7 +216,7 @@
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, nDataSegments);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.25, MARGIN); // conservative window adaption (window size should not decrease)
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.2, MARGIN); // conservative window adaption (window size should not decrease)
BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 0);
// make sure no interest is retransmitted for marked data packets
@@ -262,7 +233,6 @@
createPipeline();
nDataSegments = 7;
- pipeline->m_ssthresh = 4.0;
BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
run(name);
@@ -276,14 +246,14 @@
}
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 5);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.5, MARGIN);
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 6.0, MARGIN);
// receive segment 5 with congestion mark
face.receive(*makeDataWithSegmentAndCongMark(5));
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 6);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.25, MARGIN); // window size drops to 1/2 of previous size
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.2, MARGIN); // window size drops to 1/2 of previous size
BOOST_CHECK_EQUAL(face.sentInterests.size(), nDataSegments); // all interests have been sent
// receive the last segment with congestion mark
@@ -291,7 +261,7 @@
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, nDataSegments);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, PipelineInterestsAdaptive::MIN_SSTHRESH,
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 2.94,
MARGIN); // window size should decrease, as cwa is disabled
BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 0);
@@ -309,7 +279,6 @@
createPipeline();
nDataSegments = 7;
- pipeline->m_ssthresh = 4.0;
BOOST_REQUIRE_CLOSE(pipeline->m_cwnd, 1, MARGIN);
run(name);
@@ -323,7 +292,7 @@
}
BOOST_CHECK_EQUAL(pipeline->m_nReceived, 6);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 4.75, MARGIN);
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 7.0, MARGIN);
BOOST_CHECK_EQUAL(face.sentInterests.size(), nDataSegments); // all interests have been sent
// receive the last segment with congestion mark
@@ -331,7 +300,7 @@
advanceClocks(io, time::nanoseconds(1));
BOOST_CHECK_EQUAL(pipeline->m_nReceived, nDataSegments);
- BOOST_CHECK_CLOSE(pipeline->m_cwnd, 5.0, MARGIN); // window size increases
+ BOOST_CHECK_CLOSE(pipeline->m_cwnd, 8.0, MARGIN); // window size increases
BOOST_CHECK_EQUAL(pipeline->m_retxQueue.size(), 0);
// make sure no interest is retransmitted for marked data packet
@@ -608,7 +577,7 @@
}
-BOOST_AUTO_TEST_SUITE_END() // TestPipelineInterestsAdaptive
+BOOST_AUTO_TEST_SUITE_END() // TestPipelineInterestsCubic
BOOST_AUTO_TEST_SUITE_END() // Chunks
} // namespace tests