Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] Add Multipath support #4724

Draft
wants to merge 25 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
3ca34bb
Add active migration support.
masa-koz Mar 28, 2024
cb3545e
fix nits
masa-koz Mar 30, 2024
ac71d73
move the codes into the separate functions.
masa-koz Mar 30, 2024
5ca2a72
Merge branch 'microsoft:main' into add_active_migration
masa-koz Mar 31, 2024
a339913
Change the ConnID and reset Congestion Control.
masa-koz Apr 6, 2024
2bed382
Merge branch 'main' into add_active_migration
masa-koz Dec 18, 2024
257f270
Merge branch 'add_active_migration' of https://github.com/masa-koz/ms…
masa-koz Dec 18, 2024
c6f7e3d
Defer sending a path challange if there is no unused ConnID
masa-koz Dec 18, 2024
ac1f616
Release bindings and assert non-null for retired paths in connection …
masa-koz Dec 18, 2024
2b3c6fd
Accept adding local address before connection start
masa-koz Dec 18, 2024
9e287a7
Add support for multiple local addresses in connection tests
masa-koz Dec 18, 2024
5da50d7
Replace all the existing source connection IDs if we find the collisi…
masa-koz Dec 18, 2024
d1d69a3
run ./scripts/update-sidecar.ps1
masa-koz Dec 21, 2024
12c1579
Fix missing newline at end of file in quic_gtest.h
masa-koz Dec 21, 2024
f2c9629
Define local address management parameters only when preview features…
masa-koz Dec 21, 2024
b85b832
Improve local address handling in path tests with retry logic for add…
masa-koz Dec 21, 2024
f04be9c
Add support for multipath by introducing path ID management structure…
masa-koz Dec 21, 2024
82ddc1c
Merge branch 'main' into masa-koz/multipath
masa-koz Dec 31, 2024
bf1a2f7
Refactor congestion control code to remove unused connection referenc…
masa-koz Dec 31, 2024
6103189
Refactor multipath handling to use negotiated state
masa-koz Dec 31, 2024
24d468e
Add support for path status management and new frame types for multip…
masa-koz Jan 3, 2025
f5ba851
Merge branch 'main' into masa-koz/multipath
masa-koz Jan 4, 2025
c1dd089
Implement Debug trait for Addr and add new connection event structure…
masa-koz Jan 4, 2025
8f9acca
Add VersionSettings and PathStatus structures for preview API support
masa-koz Jan 4, 2025
62d3d9b
Add set_multipath_enabled method to Settings for preview API support
masa-koz Jan 4, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions scripts/clog.inputs
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@
../src/core/packet_space.c
../src/core/registration.c
../src/core/send.c
../src/core/pathid_set.c
../src/core/pathid.c
../src/core/path.c
../src/core/settings.c
../src/core/connection.c
Expand Down Expand Up @@ -82,6 +84,7 @@
../src/bin/static/empty.c
../src/core/operation.h
../src/core/stream.h
../src/core/pathid.h
../src/core/connection.h
../src/test/lib/TestHelpers.h
../src/test/lib/TestStream.cpp
Expand Down
2 changes: 2 additions & 0 deletions src/core/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ set(SOURCES
packet.c
packet_builder.c
packet_space.c
pathid_set.c
pathid.c
path.c
range.c
recv_buffer.c
Expand Down
4 changes: 4 additions & 0 deletions src/core/ack_tracker.c
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,7 @@ QuicAckTrackerAckFrameEncode(
_Inout_ QUIC_PACKET_BUILDER* Builder
)
{
QUIC_PACKET_SPACE* PacketSpace = QuicAckTrackerGetPacketSpace(Tracker);
CXPLAT_DBG_ASSERT(QuicAckTrackerHasPacketsToAck(Tracker));

const uint64_t Timestamp = CxPlatTimeUs64();
Expand All @@ -310,6 +311,9 @@ QuicAckTrackerAckFrameEncode(
}

if (!QuicAckFrameEncode(
PacketSpace->Connection->State.MultipathNegotiated &&
Builder->EncryptLevel == QUIC_ENCRYPT_LEVEL_1_RTT,
PacketSpace->PathID->ID,
&Tracker->PacketNumbersToAck,
AckDelay,
Tracker->NonZeroRecvECN ?
Expand Down
67 changes: 39 additions & 28 deletions src/core/bbr.c
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ BbrCongestionControlGetCongestionWindow(
)
{
const QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_CONNECTION* Connection = QuicCongestionControlGetPathID(Cc)->Connection;

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
Expand Down Expand Up @@ -279,16 +279,16 @@ BbrCongestionControlIsAppLimited(
_IRQL_requires_max_(DISPATCH_LEVEL)
void
QuicConnLogBbr(
_In_ QUIC_CONNECTION* const Connection
_In_ QUIC_PATHID* const PathID
)
{
QUIC_CONGESTION_CONTROL* Cc = &Connection->CongestionControl;
QUIC_CONGESTION_CONTROL* Cc = &PathID->CongestionControl;
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

QuicTraceEvent(
ConnBbr,
"[conn][%p] BBR: State=%u RState=%u CongestionWindow=%u BytesInFlight=%u BytesInFlightMax=%u MinRttEst=%lu EstBw=%lu AppLimited=%u",
Connection,
PathID->Connection,
Bbr->BbrState,
Bbr->RecoveryState,
BbrCongestionControlGetCongestionWindow(Cc),
Expand All @@ -307,7 +307,8 @@ BbrCongestionControlIndicateConnectionEvent(
)
{
const QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;
const QUIC_PATH* Path = &Connection->Paths[0];
const QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
const QUIC_PATH* Path = PathID->Path;
QUIC_CONNECTION_EVENT Event;
Event.Type = QUIC_CONNECTION_EVENT_NETWORK_STATISTICS;
Event.NETWORK_STATISTICS.BytesInFlight = Bbr->BytesInFlight;
Expand Down Expand Up @@ -345,8 +346,9 @@ BbrCongestionControlLogOutFlowStatus(
_In_ const QUIC_CONGESTION_CONTROL* Cc
)
{
const QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
const QUIC_PATH* Path = &Connection->Paths[0];
const QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
const QUIC_CONNECTION* Connection = PathID->Connection;
const QUIC_PATH* Path = PathID->Path;
const QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

QuicTraceEvent(
Expand All @@ -373,8 +375,9 @@ BbrCongestionControlUpdateBlockedState(
_In_ BOOLEAN PreviousCanSendState
)
{
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QuicConnLogOutFlowStats(Connection);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;
QuicConnLogOutFlowStats(PathID);

if (PreviousCanSendState != BbrCongestionControlCanSend(Cc)) {
if (PreviousCanSendState) {
Expand Down Expand Up @@ -436,7 +439,7 @@ BbrCongestionControlOnDataSent(
Bbr->BytesInFlight += NumRetransmittableBytes;
if (Bbr->BytesInFlightMax < Bbr->BytesInFlight) {
Bbr->BytesInFlightMax = Bbr->BytesInFlight;
QuicSendBufferConnectionAdjust(QuicCongestionControlGetConnection(Cc));
QuicSendBufferConnectionAdjust(QuicCongestionControlGetPathID(Cc)->Connection);
}

if (Bbr->Exemptions > 0) {
Expand Down Expand Up @@ -471,10 +474,10 @@ BbrCongestionControlUpdateRecoveryWindow(
)
{
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
QuicPathGetDatagramPayloadSize(PathID->Path);

CXPLAT_DBG_ASSERT(Bbr->RecoveryState != RECOVERY_STATE_NOT_RECOVERY);

Expand All @@ -500,13 +503,13 @@ BbrCongestionControlHandleAckInProbeRtt(
)
{
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);

Bbr->BandwidthFilter.AppLimited = TRUE;
Bbr->BandwidthFilter.AppLimitedExitTarget = LargestSentPacketNumber;

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
QuicPathGetDatagramPayloadSize(PathID->Path);

if (!Bbr->ProbeRttEndTimeValid &&
Bbr->BytesInFlight < BbrCongestionControlGetCongestionWindow(Cc) + DatagramPayloadLength) {
Expand Down Expand Up @@ -608,7 +611,8 @@ BbrCongestionControlGetSendAllowance(
_In_ BOOLEAN TimeSinceLastSendValid
)
{
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

uint64_t BandwidthEst = BbrCongestionControlGetBandwidth(Cc);
Expand Down Expand Up @@ -693,7 +697,8 @@ BbrCongestionControlSetSendQuantum(
)
{
QUIC_CONGESTION_CONTROL_BBR *Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

uint64_t Bandwidth = BbrCongestionControlGetBandwidth(Cc);

Expand All @@ -720,7 +725,8 @@ BbrCongestionControlUpdateCongestionWindow(
)
{
QUIC_CONGESTION_CONTROL_BBR *Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

if (Bbr->BbrState == BBR_STATE_PROBE_RTT) {
return;
Expand Down Expand Up @@ -751,7 +757,7 @@ BbrCongestionControlUpdateCongestionWindow(

Bbr->CongestionWindow = CXPLAT_MAX(CongestionWindow, MinCongestionWindow);

QuicConnLogBbr(QuicCongestionControlGetConnection(Cc));
QuicConnLogBbr(PathID);
}

_IRQL_requires_max_(DISPATCH_LEVEL)
Expand All @@ -764,7 +770,8 @@ BbrCongestionControlOnDataAcknowledged(
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

BOOLEAN PreviousCanSendState = BbrCongestionControlCanSend(Cc);
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

if (AckEvent->IsImplicit) {
BbrCongestionControlUpdateCongestionWindow(
Expand Down Expand Up @@ -897,7 +904,8 @@ BbrCongestionControlOnDataLost(
)
{
QUIC_CONGESTION_CONTROL_BBR *Bbr = &Cc->Bbr;
QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
Expand Down Expand Up @@ -948,7 +956,7 @@ BbrCongestionControlOnDataLost(
}

BbrCongestionControlUpdateBlockedState(Cc, PreviousCanSendState);
QuicConnLogBbr(QuicCongestionControlGetConnection(Cc));
QuicConnLogBbr(PathID);
}

_IRQL_requires_max_(DISPATCH_LEVEL)
Expand All @@ -969,8 +977,9 @@ BbrCongestionControlSetAppLimited(
{
QUIC_CONGESTION_CONTROL_BBR *Bbr = &Cc->Bbr;

QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
uint64_t LargestSentPacketNumber = Connection->LossDetection.LargestSentPacketNumber;
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;
uint64_t LargestSentPacketNumber = Connection->Paths[0].PathID->LossDetection.LargestSentPacketNumber;

if (Bbr->BytesInFlight > BbrCongestionControlGetCongestionWindow(Cc)) {
return;
Expand All @@ -989,7 +998,8 @@ BbrCongestionControlReset(
{
QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
Expand Down Expand Up @@ -1046,7 +1056,7 @@ BbrCongestionControlReset(
Bbr->BandwidthFilter.AppLimitedExitTarget = 0;

BbrCongestionControlLogOutFlowStatus(Cc);
QuicConnLogBbr(Connection);
QuicConnLogBbr(PathID);
}


Expand Down Expand Up @@ -1081,7 +1091,8 @@ BbrCongestionControlInitialize(

QUIC_CONGESTION_CONTROL_BBR* Bbr = &Cc->Bbr;

QUIC_CONNECTION* Connection = QuicCongestionControlGetConnection(Cc);
QUIC_PATHID* PathID = QuicCongestionControlGetPathID(Cc);
QUIC_CONNECTION* Connection = PathID->Connection;

const uint16_t DatagramPayloadLength =
QuicPathGetDatagramPayloadSize(&Connection->Paths[0]);
Expand Down Expand Up @@ -1141,6 +1152,6 @@ BbrCongestionControlInitialize(
.AppLimitedExitTarget = 0,
};

QuicConnLogOutFlowStats(Connection);
QuicConnLogBbr(Connection);
QuicConnLogOutFlowStats(PathID);
QuicConnLogBbr(PathID);
}
Loading