Fix the ECN codepoints. Per RFC3168, ECT0 = 0b10, ECT1 = 0b01. Roll flag quic_receive_ecn2 to quic_receive_ecn3 to protect the behavior change.
Protected by FLAGS_quic_restart_flag_quic_receive_ecn3.
PiperOrigin-RevId: 553556652
diff --git a/quiche/quic/core/batch_writer/quic_gso_batch_writer_test.cc b/quiche/quic/core/batch_writer/quic_gso_batch_writer_test.cc
index b21c5e7..35c48c1 100644
--- a/quiche/quic/core/batch_writer/quic_gso_batch_writer_test.cc
+++ b/quiche/quic/core/batch_writer/quic_gso_batch_writer_test.cc
@@ -475,7 +475,7 @@
params.ecn_codepoint = ECN_ECT1;
EXPECT_CALL(mock_syscalls_, Sendmsg(_, _, _))
.WillOnce(Invoke([](int /*sockfd*/, const msghdr* msg, int /*flags*/) {
- const int kEct0 = 0x01;
+ const int kEct0 = 0x02;
EXPECT_EQ(2700u, PacketLength(msg));
msghdr mutable_msg;
memcpy(&mutable_msg, msg, sizeof(*msg));
@@ -521,7 +521,7 @@
params.ecn_codepoint = ECN_ECT1;
EXPECT_CALL(mock_syscalls_, Sendmsg(_, _, _))
.WillOnce(Invoke([](int /*sockfd*/, const msghdr* msg, int /*flags*/) {
- const int kEct0 = 0x01;
+ const int kEct0 = 0x02;
EXPECT_EQ(2700u, PacketLength(msg));
msghdr mutable_msg;
memcpy(&mutable_msg, msg, sizeof(*msg));
diff --git a/quiche/quic/core/http/end_to_end_test.cc b/quiche/quic/core/http/end_to_end_test.cc
index 35b1db0..8f0e186 100644
--- a/quiche/quic/core/http/end_to_end_test.cc
+++ b/quiche/quic/core/http/end_to_end_test.cc
@@ -7246,7 +7246,7 @@
EXPECT_EQ(ecn->ce, 0);
EXPECT_TRUE(client_connection->set_ecn_codepoint(ECN_ECT0));
client_->SendSynchronousRequest("/foo");
- if (!GetQuicRestartFlag(quic_receive_ecn2) ||
+ if (!GetQuicRestartFlag(quic_receive_ecn3) ||
!VersionHasIetfQuicFrames(version_.transport_version)) {
EXPECT_EQ(ecn->ect0, 0);
} else {
@@ -7271,7 +7271,7 @@
EXPECT_EQ(ecn->ce, 0);
EXPECT_TRUE(client_connection->set_ecn_codepoint(ECN_ECT1));
client_->SendSynchronousRequest("/foo");
- if (!GetQuicRestartFlag(quic_receive_ecn2) ||
+ if (!GetQuicRestartFlag(quic_receive_ecn3) ||
!VersionHasIetfQuicFrames(version_.transport_version)) {
EXPECT_EQ(ecn->ect1, 0);
} else {
@@ -7296,7 +7296,7 @@
EXPECT_EQ(ecn->ce, 0);
EXPECT_TRUE(client_connection->set_ecn_codepoint(ECN_CE));
client_->SendSynchronousRequest("/foo");
- if (!GetQuicRestartFlag(quic_receive_ecn2) ||
+ if (!GetQuicRestartFlag(quic_receive_ecn3) ||
!VersionHasIetfQuicFrames(version_.transport_version)) {
EXPECT_EQ(ecn->ce, 0);
} else {
@@ -7325,7 +7325,7 @@
server_thread_->Pause();
EXPECT_EQ(ecn->ect0, 0);
EXPECT_EQ(ecn->ce, 0);
- if (!GetQuicRestartFlag(quic_receive_ecn2) ||
+ if (!GetQuicRestartFlag(quic_receive_ecn3) ||
!VersionHasIetfQuicFrames(version_.transport_version)) {
EXPECT_EQ(ecn->ect1, 0);
} else {
diff --git a/quiche/quic/core/quic_connection_test.cc b/quiche/quic/core/quic_connection_test.cc
index 9fd7756..e394d5c 100644
--- a/quiche/quic/core/quic_connection_test.cc
+++ b/quiche/quic/core/quic_connection_test.cc
@@ -16867,7 +16867,7 @@
QuicConnectionPeer::SendPing(&connection_);
}
QuicConnectionStats stats = connection_.GetStats();
- if (GetQuicRestartFlag(quic_receive_ecn2)) {
+ if (GetQuicRestartFlag(quic_receive_ecn3)) {
ASSERT_TRUE(ack_frame.ecn_counters.has_value());
EXPECT_EQ(ack_frame.ecn_counters->ect0, 1);
EXPECT_EQ(stats.num_ack_frames_sent_with_ecn,
@@ -16883,7 +16883,7 @@
TEST_P(QuicConnectionTest, EcnMarksCoalescedPacket) {
if (!connection_.version().CanSendCoalescedPackets() ||
- !GetQuicRestartFlag(quic_receive_ecn2)) {
+ !GetQuicRestartFlag(quic_receive_ecn3)) {
return;
}
QuicCryptoFrame crypto_frame1{ENCRYPTION_HANDSHAKE, 0, "foo"};
@@ -16935,7 +16935,7 @@
EXPECT_TRUE(ack_frame.ecn_counters.has_value());
EXPECT_EQ(ack_frame.ecn_counters->ect0, 1);
}
- if (GetQuicRestartFlag(quic_receive_ecn2)) {
+ if (GetQuicRestartFlag(quic_receive_ecn3)) {
EXPECT_EQ(stats.num_ecn_marks_received.ect0, 2);
EXPECT_EQ(stats.num_ack_frames_sent_with_ecn,
connection_.version().HasIetfQuicFrames() ? 2 : 0);
@@ -16949,7 +16949,7 @@
TEST_P(QuicConnectionTest, EcnMarksUndecryptableCoalescedPacket) {
if (!connection_.version().CanSendCoalescedPackets() ||
- !GetQuicRestartFlag(quic_receive_ecn2)) {
+ !GetQuicRestartFlag(quic_receive_ecn3)) {
return;
}
// SetFromConfig is always called after construction from InitializeSession.
@@ -17065,10 +17065,10 @@
connection_.SupportsMultiplePacketNumberSpaces() ? 1 : 2);
QuicConnectionStats stats = connection_.GetStats();
EXPECT_EQ(stats.num_ecn_marks_received.ect0,
- GetQuicRestartFlag(quic_receive_ecn2) ? 2 : 0);
+ GetQuicRestartFlag(quic_receive_ecn3) ? 2 : 0);
EXPECT_EQ(stats.num_ecn_marks_received.ect1, 0);
EXPECT_EQ(stats.num_ecn_marks_received.ce,
- GetQuicRestartFlag(quic_receive_ecn2) ? 1 : 0);
+ GetQuicRestartFlag(quic_receive_ecn3) ? 1 : 0);
}
TEST_P(QuicConnectionTest, ReceivedPacketInfoDefaults) {
diff --git a/quiche/quic/core/quic_flags_list.h b/quiche/quic/core/quic_flags_list.h
index 34274d3..d812b0d 100644
--- a/quiche/quic/core/quic_flags_list.h
+++ b/quiche/quic/core/quic_flags_list.h
@@ -91,8 +91,8 @@
QUIC_FLAG(quic_restart_flag_quic_platform_tos_sockopt, false)
// When true, defaults to BBR congestion control instead of Cubic.
QUIC_FLAG(quic_reloadable_flag_quic_default_to_bbr, false)
-// When true, report received ECN markings to the peer.
-QUIC_FLAG(quic_restart_flag_quic_receive_ecn2, false)
+// When true, report received ECN markings to the peer. Replaces quic_receive_ecn2 to use correct codepoints.
+QUIC_FLAG(quic_restart_flag_quic_receive_ecn3, false)
// When true, sends QUIC packets marked ECT(1).
QUIC_FLAG(quic_reloadable_flag_quic_send_ect1, false)
// When true, support RFC9369.
diff --git a/quiche/quic/core/quic_packet_reader.cc b/quiche/quic/core/quic_packet_reader.cc
index 71b723c..1436ab5 100644
--- a/quiche/quic/core/quic_packet_reader.cc
+++ b/quiche/quic/core/quic_packet_reader.cc
@@ -54,8 +54,8 @@
QuicUdpPacketInfoBit::PEER_ADDRESS, QuicUdpPacketInfoBit::V4_SELF_IP,
QuicUdpPacketInfoBit::V6_SELF_IP, QuicUdpPacketInfoBit::RECV_TIMESTAMP,
QuicUdpPacketInfoBit::TTL, QuicUdpPacketInfoBit::GOOGLE_PACKET_HEADER});
- if (GetQuicRestartFlag(quic_receive_ecn2)) {
- QUIC_RESTART_FLAG_COUNT_N(quic_receive_ecn2, 2, 2);
+ if (GetQuicRestartFlag(quic_receive_ecn3)) {
+ QUIC_RESTART_FLAG_COUNT_N(quic_receive_ecn3, 2, 2);
info_bits.Set(QuicUdpPacketInfoBit::ECN);
}
size_t packets_read =
diff --git a/quiche/quic/core/quic_received_packet_manager.cc b/quiche/quic/core/quic_received_packet_manager.cc
index b941e8c..afabb27 100644
--- a/quiche/quic/core/quic_received_packet_manager.cc
+++ b/quiche/quic/core/quic_received_packet_manager.cc
@@ -124,8 +124,8 @@
}
}
- if (GetQuicRestartFlag(quic_receive_ecn2) && ecn != ECN_NOT_ECT) {
- QUIC_RESTART_FLAG_COUNT_N(quic_receive_ecn2, 1, 2);
+ if (GetQuicRestartFlag(quic_receive_ecn3) && ecn != ECN_NOT_ECT) {
+ QUIC_RESTART_FLAG_COUNT_N(quic_receive_ecn3, 1, 2);
if (!ack_frame_.ecn_counters.has_value()) {
ack_frame_.ecn_counters = QuicEcnCounts();
}
diff --git a/quiche/quic/core/quic_received_packet_manager_test.cc b/quiche/quic/core/quic_received_packet_manager_test.cc
index b1d46db..bcb7e65 100644
--- a/quiche/quic/core/quic_received_packet_manager_test.cc
+++ b/quiche/quic/core/quic_received_packet_manager_test.cc
@@ -704,7 +704,7 @@
RecordPacketReceipt(5, QuicTime::Zero(), ECN_ECT1);
RecordPacketReceipt(6, QuicTime::Zero(), ECN_CE);
QuicFrame ack = received_manager_.GetUpdatedAckFrame(QuicTime::Zero());
- if (GetQuicRestartFlag(quic_receive_ecn2)) {
+ if (GetQuicRestartFlag(quic_receive_ecn3)) {
EXPECT_TRUE(ack.ack_frame->ecn_counters.has_value());
EXPECT_EQ(ack.ack_frame->ecn_counters->ect0, 1);
EXPECT_EQ(ack.ack_frame->ecn_counters->ect1, 1);
diff --git a/quiche/quic/core/quic_types.h b/quiche/quic/core/quic_types.h
index ccc0e73..c17bf22 100644
--- a/quiche/quic/core/quic_types.h
+++ b/quiche/quic/core/quic_types.h
@@ -884,12 +884,12 @@
// The NOT-ECT codepoint, indicating the packet sender is not using (or the
// network has disabled) ECN.
ECN_NOT_ECT = 0,
- // The ECT(0) codepoint, indicating the packet sender is using classic ECN
- // (RFC3168).
- ECN_ECT0 = 1,
// The ECT(1) codepoint, indicating the packet sender is using Low Latency,
// Low Loss, Scalable Throughput (L4S) ECN (RFC9330).
- ECN_ECT1 = 2,
+ ECN_ECT1 = 1,
+ // The ECT(0) codepoint, indicating the packet sender is using classic ECN
+ // (RFC3168).
+ ECN_ECT0 = 2,
// The CE ("Congestion Experienced") codepoint, indicating the packet sender
// is using ECN, and a router is experiencing congestion.
ECN_CE = 3,
diff --git a/quiche/quic/core/quic_versions.cc b/quiche/quic/core/quic_versions.cc
index 8fcb1a6..c0fd4fc 100644
--- a/quiche/quic/core/quic_versions.cc
+++ b/quiche/quic/core/quic_versions.cc
@@ -625,7 +625,7 @@
void QuicVersionInitializeSupportForIetfDraft() {
// Enable necessary flags.
- SetQuicRestartFlag(quic_receive_ecn2, true);
+ SetQuicRestartFlag(quic_receive_ecn3, true);
}
void QuicEnableVersion(const ParsedQuicVersion& version) {