mirror of
https://github.com/refraction-networking/uquic.git
synced 2025-04-03 20:27:35 +03:00
feed ECN feedback into the congestion controller
This commit is contained in:
parent
797e275293
commit
d6ac6300a4
5 changed files with 251 additions and 6 deletions
|
@ -1429,4 +1429,151 @@ var _ = Describe("SentPacketHandler", func() {
|
|||
Expect(handler.rttStats.SmoothedRTT()).To(BeZero())
|
||||
})
|
||||
})
|
||||
|
||||
Context("ECN handling", func() {
|
||||
var ecnHandler *MockECNHandler
|
||||
var cong *mocks.MockSendAlgorithmWithDebugInfos
|
||||
|
||||
JustBeforeEach(func() {
|
||||
cong = mocks.NewMockSendAlgorithmWithDebugInfos(mockCtrl)
|
||||
cong.EXPECT().OnPacketSent(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).AnyTimes()
|
||||
cong.EXPECT().OnPacketAcked(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).AnyTimes()
|
||||
cong.EXPECT().MaybeExitSlowStart().AnyTimes()
|
||||
ecnHandler = NewMockECNHandler(mockCtrl)
|
||||
lostPackets = nil
|
||||
rttStats := utils.NewRTTStats()
|
||||
rttStats.UpdateRTT(time.Hour, 0, time.Now())
|
||||
handler = newSentPacketHandler(42, protocol.InitialPacketSizeIPv4, rttStats, false, false, perspective, nil, utils.DefaultLogger)
|
||||
handler.ecnTracker = ecnHandler
|
||||
handler.congestion = cong
|
||||
})
|
||||
|
||||
It("informs about sent packets", func() {
|
||||
// Check that only 1-RTT packets are reported
|
||||
handler.SentPacket(time.Now(), 100, -1, nil, nil, protocol.EncryptionInitial, protocol.ECT1, 1200, false)
|
||||
handler.SentPacket(time.Now(), 101, -1, nil, nil, protocol.EncryptionHandshake, protocol.ECT0, 1200, false)
|
||||
handler.SentPacket(time.Now(), 102, -1, nil, nil, protocol.Encryption0RTT, protocol.ECNCE, 1200, false)
|
||||
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(103), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), 103, -1, nil, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
})
|
||||
|
||||
It("informs about sent packets", func() {
|
||||
// Check that only 1-RTT packets are reported
|
||||
handler.SentPacket(time.Now(), 100, -1, nil, nil, protocol.EncryptionInitial, protocol.ECT1, 1200, false)
|
||||
handler.SentPacket(time.Now(), 101, -1, nil, nil, protocol.EncryptionHandshake, protocol.ECT0, 1200, false)
|
||||
handler.SentPacket(time.Now(), 102, -1, nil, nil, protocol.Encryption0RTT, protocol.ECNCE, 1200, false)
|
||||
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(103), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), 103, -1, nil, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
})
|
||||
|
||||
It("informs about lost packets", func() {
|
||||
for i := 10; i < 20; i++ {
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(i), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), protocol.PacketNumber(i), -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
}
|
||||
cong.EXPECT().OnCongestionEvent(gomock.Any(), gomock.Any(), gomock.Any()).Times(3)
|
||||
ecnHandler.EXPECT().LostPacket(protocol.PacketNumber(10))
|
||||
ecnHandler.EXPECT().LostPacket(protocol.PacketNumber(11))
|
||||
ecnHandler.EXPECT().LostPacket(protocol.PacketNumber(12))
|
||||
ecnHandler.EXPECT().HandleNewlyAcked(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any())
|
||||
_, err := handler.ReceivedAck(&wire.AckFrame{AckRanges: []wire.AckRange{{Largest: 16, Smallest: 13}}}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("processes ACKs", func() {
|
||||
// Check that we only care about 1-RTT packets.
|
||||
handler.SentPacket(time.Now(), 100, -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.EncryptionInitial, protocol.ECT1, 1200, false)
|
||||
_, err := handler.ReceivedAck(&wire.AckFrame{AckRanges: []wire.AckRange{{Largest: 100, Smallest: 100}}}, protocol.EncryptionInitial, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
for i := 10; i < 20; i++ {
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(i), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), protocol.PacketNumber(i), -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
}
|
||||
ecnHandler.EXPECT().HandleNewlyAcked(gomock.Any(), int64(1), int64(2), int64(3)).DoAndReturn(func(packets []*packet, _, _, _ int64) bool {
|
||||
Expect(packets).To(HaveLen(5))
|
||||
Expect(packets[0].PacketNumber).To(Equal(protocol.PacketNumber(10)))
|
||||
Expect(packets[1].PacketNumber).To(Equal(protocol.PacketNumber(11)))
|
||||
Expect(packets[2].PacketNumber).To(Equal(protocol.PacketNumber(12)))
|
||||
Expect(packets[3].PacketNumber).To(Equal(protocol.PacketNumber(14)))
|
||||
Expect(packets[4].PacketNumber).To(Equal(protocol.PacketNumber(15)))
|
||||
return false
|
||||
})
|
||||
_, err = handler.ReceivedAck(&wire.AckFrame{
|
||||
AckRanges: []wire.AckRange{
|
||||
{Largest: 15, Smallest: 14},
|
||||
{Largest: 12, Smallest: 10},
|
||||
},
|
||||
ECT0: 1,
|
||||
ECT1: 2,
|
||||
ECNCE: 3,
|
||||
}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("ignores reordered ACKs", func() {
|
||||
for i := 10; i < 20; i++ {
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(i), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), protocol.PacketNumber(i), -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
}
|
||||
ecnHandler.EXPECT().HandleNewlyAcked(gomock.Any(), int64(1), int64(2), int64(3)).DoAndReturn(func(packets []*packet, _, _, _ int64) bool {
|
||||
Expect(packets).To(HaveLen(2))
|
||||
Expect(packets[0].PacketNumber).To(Equal(protocol.PacketNumber(11)))
|
||||
Expect(packets[1].PacketNumber).To(Equal(protocol.PacketNumber(12)))
|
||||
return false
|
||||
})
|
||||
_, err := handler.ReceivedAck(&wire.AckFrame{
|
||||
AckRanges: []wire.AckRange{{Largest: 12, Smallest: 11}},
|
||||
ECT0: 1,
|
||||
ECT1: 2,
|
||||
ECNCE: 3,
|
||||
}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
// acknowledge packet 10 now, but don't increase the largest acked
|
||||
_, err = handler.ReceivedAck(&wire.AckFrame{
|
||||
AckRanges: []wire.AckRange{{Largest: 12, Smallest: 10}},
|
||||
ECT0: 1,
|
||||
ECNCE: 3,
|
||||
}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("ignores ACKs that don't increase the largest acked", func() {
|
||||
for i := 10; i < 20; i++ {
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(i), protocol.ECT1)
|
||||
handler.SentPacket(time.Now(), protocol.PacketNumber(i), -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.Encryption1RTT, protocol.ECT1, 1200, false)
|
||||
}
|
||||
ecnHandler.EXPECT().HandleNewlyAcked(gomock.Any(), int64(1), int64(2), int64(3)).DoAndReturn(func(packets []*packet, _, _, _ int64) bool {
|
||||
Expect(packets).To(HaveLen(1))
|
||||
Expect(packets[0].PacketNumber).To(Equal(protocol.PacketNumber(11)))
|
||||
return false
|
||||
})
|
||||
_, err := handler.ReceivedAck(&wire.AckFrame{
|
||||
AckRanges: []wire.AckRange{{Largest: 11, Smallest: 11}},
|
||||
ECT0: 1,
|
||||
ECT1: 2,
|
||||
ECNCE: 3,
|
||||
}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
_, err = handler.ReceivedAck(&wire.AckFrame{
|
||||
AckRanges: []wire.AckRange{{Largest: 11, Smallest: 10}},
|
||||
ECT0: 1,
|
||||
ECNCE: 3,
|
||||
}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("informs the congestion controller about CE events", func() {
|
||||
for i := 10; i < 20; i++ {
|
||||
ecnHandler.EXPECT().SentPacket(protocol.PacketNumber(i), protocol.ECT0)
|
||||
handler.SentPacket(time.Now(), protocol.PacketNumber(i), -1, []StreamFrame{{Frame: &streamFrame}}, nil, protocol.Encryption1RTT, protocol.ECT0, 1200, false)
|
||||
}
|
||||
ecnHandler.EXPECT().HandleNewlyAcked(gomock.Any(), int64(0), int64(0), int64(0)).Return(true)
|
||||
cong.EXPECT().OnCongestionEvent(protocol.PacketNumber(15), gomock.Any(), gomock.Any())
|
||||
_, err := handler.ReceivedAck(&wire.AckFrame{AckRanges: []wire.AckRange{{Largest: 15, Smallest: 10}}}, protocol.Encryption1RTT, time.Now())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
})
|
||||
})
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue