1
0
mirror of https://github.com/facebookincubator/mvfst.git synced 2025-08-05 11:21:09 +03:00

177 Commits

Author SHA1 Message Date
Matt Joras
b74208392c Fix [[maybe_unused]] anti-patterns in QUIC tests
Summary:
Replace `[[maybe_unused]] auto variable = method_call` patterns with proper assertions using `ASSERT_FALSE(method_call.hasError())` for quic::Expected return values. This improves test reliability by actually validating method call success instead of suppressing unused return value warnings.

## Changes Made

### 1. Fixed Anti-Patterns in Tests (84 instances across 5 test files):
- QuicTransportBaseTest.cpp: 74 patterns
- QuicTransportTest.cpp: 5 patterns
- QuicTypedTransportTest.cpp: 3 patterns
- QuicClientTransportLiteTest.cpp: 1 pattern
- QuicClientTransportTest.cpp: 1 pattern

For cleanup scenarios where failure is acceptable (e.g., setting read callback to nullptr), used `(void)method_call` instead of assertions to properly suppress warnings without incorrect success assertions.

### 2. Removed Unhelpful Comments (5 instances):
- QuicStreamAsyncTransport.cpp: Removed comments referencing "original behavior" that provided no actionable context

The logging statements (WARNING/VLOG) already make error handling behavior clear without need for historical commentary.

## Comprehensive Audit Results
Performed comprehensive audit of all `[[maybe_unused]]` usage in fbcode/quic/ (45 total instances):
-  **Self-reference guards**: `[[maybe_unused]] auto self = sharedGuard();` - **LEGITIMATE**
-  **Function parameter suppression**: Intentionally unused parameters - **LEGITIMATE**
-  **Loop variable suppression**: Iteration without using values - **LEGITIMATE**
-  **Static initialization**: Thread-local initialization patterns - **LEGITIMATE**
-  **Third-party code**: Left untouched as required
 ---
> Generated by [Confucius Code Assist (CCA)](https://www.internalfb.com/wiki/Confucius/Analect/Shared_Analects/Confucius_Code_Assist_(CCA)/)
[Session](https://www.internalfb.com/confucius?session_id=7be75dc0-61d5-11f0-8f26-27b21c240401&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=7be75dc0-61d5-11f0-8f26-27b21c240401&tab=Trace)

Reviewed By: knekritz

Differential Revision: D78385516

fbshipit-source-id: 98c8989a147ed639be4582be3460b146aaa1075f
2025-07-16 14:23:39 -07:00
Matt Joras
4601c4bdae Migrate folly::Expected to quic::Expected
Summary:
This migrates the quic code to use quic::Expected instead of folly::Expected. quic::Expected is a vendored wrapper for expected-lite, which itself matches std::expected. std::expected is not available to us, but once it is, we would be able to further simplify to the std version.

This migration is almost entirely mechanical.
 ---
> Generated by [Confucius Code Assist (CCA)](https://www.internalfb.com/wiki/Confucius/Analect/Shared_Analects/Confucius_Code_Assist_(CCA)/)
[Session](https://www.internalfb.com/confucius?session_id=7044a18e-4d22-11f0-afeb-97de80927172&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=7044a18e-4d22-11f0-afeb-97de80927172&tab=Trace)
 ---
> Generated by [RACER](https://www.internalfb.com/wiki/RACER_(Risk-Aware_Code_Editing_and_Refactoring)/), powered by [Confucius](https://www.internalfb.com/wiki/Confucius/Analect/Shared_Analects/Confucius_Code_Assist_(CCA)/)
[Session](https://www.internalfb.com/confucius?session_id=1fea6620-4d30-11f0-a206-ad0241db9ec9&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=1fea6620-4d30-11f0-a206-ad0241db9ec9&tab=Trace)
[Session](https://www.internalfb.com/confucius?session_id=2bdbabba-505a-11f0-a21b-fb3d40195e00&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=2bdbabba-505a-11f0-a21b-fb3d40195e00&tab=Trace)
[Session](https://www.internalfb.com/confucius?session_id=eb689fd2-5114-11f0-ade8-99c0fe2f80f2&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=eb689fd2-5114-11f0-ade8-99c0fe2f80f2&tab=Trace)
[Session](https://www.internalfb.com/confucius?session_id=9bc2dcec-51f8-11f0-8604-7bc1f5225a86&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=9bc2dcec-51f8-11f0-8604-7bc1f5225a86&tab=Trace)
[Session](https://www.internalfb.com/confucius?session_id=46b187ea-5cdd-11f0-9bab-7b6b886e8a09&tab=Chat), [Trace](https://www.internalfb.com/confucius?session_id=46b187ea-5cdd-11f0-9bab-7b6b886e8a09&tab=Trace)

Reviewed By: kvtsoy

Differential Revision: D76488955

fbshipit-source-id: 92b9cbeac85a28722a6180464b47d84696b1e81b
2025-07-10 15:57:07 -07:00
Matt Joras
bf71d17f2c Remove throws from CryptoFactory
Summary: Continuing the theme, removing them from the CryptoFactory and translating to Expected.

Reviewed By: kvtsoy, jbeshay

Differential Revision: D74676120

fbshipit-source-id: 715b497e68a4e3004811038cba479c443d5398fd
2025-05-16 14:19:45 -07:00
Matt Joras
159994752d Remove exceptions from ConnectionId
Summary: This primarily involved making the constructors private and changing the callers of the factory functions. The crashing factory is only expected to be used by tests.

Reviewed By: kvtsoy

Differential Revision: D74347638

fbshipit-source-id: 4c0dd7fabaa233c8a3460c359462a22642d26f5b
2025-05-09 18:25:33 -07:00
Matt Joras
9a9dcca57c Mostly remove folly::Optional
Summary:
This is an API break, but it should mostly be a manageable one. We want to be able to compile mvfst internally without exceptions, and folly::Optional is one dependency that makes this challenging. Additionally, we already have an imported secondary optional type for performance/struct size reasons, tiny-optional.

This second optional interface is mostly compatible in an API sense (including the use of std::nullopt) with std::optional. Thus our approach is to remove the dependency on folly::Optional, and offer a quic::Optional instead.

The next diff will properly vendor tiny-optional so that quic::Optional is an independent version of it.

Reviewed By: sharmafb, kvtsoy

Differential Revision: D74133131

fbshipit-source-id: 715f8bb5043ba3bb876cacfe54236887e0686b30
2025-05-07 23:01:49 -07:00
Matt Joras
089bf581a7 Remove throws from socket layer
Summary: More in the theme of returning Expected instead of throwing. For the folly case, we keep the try/catches in there and translate to Expected. For Libev, we convert directly to Expected.

Reviewed By: kvtsoy

Differential Revision: D73217128

fbshipit-source-id: d00a978f24e3b29a77a8ac99a19765ae49f64df8
2025-04-19 15:20:15 -07:00
Alan Frindell
1e1c7defef Use new priority queue implementation
Summary:
This adds the new priority queue implementation and a TransportSetting that controls whether it should be used or not.  The default is still the old priority queue, so this diff should not introduce any functional changes in production code.

One key difference is that with the new queue, streams with new data that become connection flow control blocked are *removed* from the queue, and added back once more flow control comes.  I think this will make the scheduler slightly more efficient at writing low-priority loss streams when there's high-pri data and no connection flow control, since it doesn't need to skip over those streams when building the packet.

If this diff regresses build size, D72476484 should get it back.

Reviewed By: mjoras

Differential Revision: D72476486

fbshipit-source-id: 9665cf3f66dcdbfd57d2199d5c832529a68cfac0
2025-04-17 08:43:19 -07:00
Alan Frindell
444a0f261b Use new PriorityQueue interface
Summary:
Migrating mvfst priority API to be abstract, based on new classes is quic/priority.  For now, it requires applications use `HTTPPriorityQueue::Priority`, to be compatible with the hardcoded `deprecated::PriorityQueue` implementation and apps cannot yet change the queue impl.  Eventually the application will have full control of the queue.

There are minor functional changes in this diff:

1. Priority QLog types changed from int/bool to string
2. Any PAUSED stream has priority `u=7,i` if paused streams are disabled (previously explicitly settable to any priority)

Reviewed By: jbeshay

Differential Revision: D68696110

fbshipit-source-id: 5a4721b08248ac75d725f51b5cb3e5d5de206d86
2025-04-09 13:54:27 -07:00
Matt Joras
67ce39cfdd Remove exception throwing from the stream manager and flow control.
Summary: I started with the QuicStreamManager, but it turns out that the path from the manager up to the close path touches a LOT, and so this is a big diff. The strategy is basically the same everywhere, add a folly::Expected and check it on every function and enforce that with [[nodiscard]]

Reviewed By: kvtsoy

Differential Revision: D72347215

fbshipit-source-id: 452868b541754d2ecab646d6c3cbd6aacf317d7f
2025-04-07 23:45:33 -07:00
Matt Joras
d153b04ec4 Add SeparateDefinitionBlocks to clang-format
Summary: As in title.

Reviewed By: kvtsoy

Differential Revision: D72543602

fbshipit-source-id: 6190b7fa541b1535eab565bac3da159c85781c0e
2025-04-07 13:20:35 -07:00
Aman Sharma
07f91b0698 Move ByteEventCallback to QuicCallbacks.h
Summary:
The purpose of this is so that we can import this header from the WebTransport implementation and use the `ByteEventCallback` directly instead of creating a wrapper, thereby saving an allocation.

There's no functional change in this commit, it's just moving things around.

Relevant files:
* quic/api/QuicCallbacks.h
* quic/api/QuicSocketLite.h

Reviewed By: hanidamlaj

Differential Revision: D70000563

fbshipit-source-id: 9523cc788f50b4ba218be33e84f7d5b4f44a73c2
2025-02-25 17:58:37 -08:00
Nicholas Ormrod
484898f61b facebook-unused-include-check in fbcode/quic
Summary:
Remove headers flagged by facebook-unused-include-check over fbcode.quic.

+ format and autodeps

This is a codemod. It was automatically generated and will be landed once it is approved and tests are passing in sandcastle.
You have been added as a reviewer by Sentinel or Butterfly.

Autodiff project: uiq
Autodiff partition: fbcode.quic
Autodiff bookmark: ad.uiq.fbcode.quic

Reviewed By: hanidamlaj

Differential Revision: D69864370

fbshipit-source-id: fb8f85599e1e12429f00dc2817dfc5ecf55bc482
2025-02-20 10:03:44 -08:00
Aman Sharma
6800a7511e API for reliable resets
Reviewed By: jbeshay

Differential Revision: D67360862

fbshipit-source-id: 163f030b866a5ba6fa89f8b97bb15875f8bbf2a0
2025-01-28 12:37:29 -08:00
Aman Sharma
29f6071b75 Make a checkpoint function for reliable resets
Summary: I'm making a `checkpoint` function in the QUIC API. This is to be used in conjunction with reliable resets. When we send data on a stream and want to mark which offset will constitute the reliable size in a future call to resetStreamReliably, we call this function. This function can potentially be called multiple times on a stream to advance the offset, but it is an error to call it after sending a reset.

Reviewed By: jbeshay

Differential Revision: D68592906

fbshipit-source-id: e301385a04dffdb9f23daa805ee74c574e4393c2
2025-01-28 10:52:55 -08:00
Joseph Beshay
5fa7816bfd Enable controlling the pacer in the static cwnd controller
Summary: The StaticCwnd congestion controller is useful for the transport with a constant cwnd. This change allows it to control the pacer to make it easier to test the transport and pacer performance at a fixed cwnd + fixed pace.

Reviewed By: sharmafb

Differential Revision: D67925271

fbshipit-source-id: 27eba6b33f05f82e052129aed0324afab9c8ab42
2025-01-13 10:43:56 -08:00
Matt Joras
058f5db28c Don't special case stream frames for opportunistic ACKing
Summary: This was added to not bundle ACKs with stream frames. Don't special case those and also disabling opportunistic ACKing for all write reasons.

Reviewed By: jbeshay

Differential Revision: D66514392

fbshipit-source-id: f2657a5c06ea8ae37b8c8eacd04c5a3b8ac75390
2024-11-26 19:54:04 -08:00
Aman Sharma
3f27fdebd9 Rename offset in RstStreamFrame to finalSize
Summary: This will make it easier to distinguish between the `finalSize` and the `reliableSize` when we implement reliable resets

Reviewed By: hanidamlaj

Differential Revision: D64836474

fbshipit-source-id: d811d64a2538d4d1acba1ea10a7790d5905f02a4
2024-11-14 11:36:01 -08:00
Crystal Jin
95898ef8b7 Fall back to evb timer if no pacer timer set
Reviewed By: kvtsoy

Differential Revision: D65848549

fbshipit-source-id: 38c1e9b8c820dbe2848cb132d7e49079c45eb67d
2024-11-13 16:57:21 -08:00
Crystal Jin
a5fd828b90 Move setPacingFunction to when pacer is set
Reviewed By: hanidamlaj

Differential Revision: D65845962

fbshipit-source-id: 9d14e9845c6232b9825c20c7c67e2f49ac2fed73
2024-11-13 10:39:16 -08:00
Nicholas Ormrod
37cf3495d8 namespace-concat in fbcode/quic
Summary:
Concatenate adjacent namespaces + format

This is a codemod. It was automatically generated and will be landed once it is approved and tests are passing in sandcastle.
You have been added as a reviewer by Sentinel or Butterfly.

Autodiff project: nc
Autodiff partition: fbcode.quic
Autodiff bookmark: ad.nc.fbcode.quic

Reviewed By: hanidamlaj

Differential Revision: D65365244

fbshipit-source-id: 0bbaa7684d03caf8fc8eff3439a0865940398220
2024-11-01 18:34:56 -07:00
Aman Sharma
2369ecb69b Use iovec instead of IOBuf in QuicAsyncUDPSocket::write and QuicAsyncUDPSocket::writeGSO
Summary: See title

Reviewed By: mjoras

Differential Revision: D61048705

fbshipit-source-id: 60dc63cc67f63be6f0ac6cbe0e766172a8c79d7c
2024-10-02 15:13:23 -07:00
Aman Sharma
8e650ed585 Rename PacketEvent -> ClonedPacketIdentifier [take 2]
Summary: This is my second attempt at D61871891. This time, I ran `xplat/cross_plat_devx/somerge_maps/compute_merge_maps.py`, which generated quic/somerge_defs.bzl

Reviewed By: kvtsoy

Differential Revision: D61975459

fbshipit-source-id: bec62acb2b400f4a102574e8c882927f41b9330e
2024-08-30 12:18:20 -07:00
Marshall Mann-Wood
457ae5b1ac Revert D61871891: Rename PacketEvent -> ClonedPacketIdentifier
Differential Revision:
D61871891

Original commit changeset: f9c626d900c8

Original Phabricator Diff: D61871891

fbshipit-source-id: afe88d4b7a2ca62b16e122d9f087df3caf3e0f41
2024-08-28 16:13:54 -07:00
Aman Sharma
6f13f404b0 Rename PacketEvent -> ClonedPacketIdentifier
Summary: `PacketEvent` is a very inaccurate and misleading name. We're basically using this as an identifier for cloned packets, so `ClonedPacketIdentifier` is a much better.

Reviewed By: kvtsoy

Differential Revision: D61871891

fbshipit-source-id: f9c626d900c8b7ab7e231c9bad4c1629384ebb77
2024-08-28 14:26:30 -07:00
Aman Sharma
bc386475e5 Integrate RangeChain into write path of QUIC stack
Summary: See title

Reviewed By: mjoras

Differential Revision: D58216871

fbshipit-source-id: 9afc08946a676ec967c998416a6470d4884af550
2024-08-15 05:46:08 -07:00
Aman Sharma
55bf4a2d27 Move DSR-related APIs to QuicServerTransport
Reviewed By: mjoras

Differential Revision: D59768195

fbshipit-source-id: 8f0780019e5cd9bc3a3863fe30140b8da160c0bc
2024-07-31 10:48:06 -07:00
Matt Joras
aefc9e369b Introduce quic::Optional
Summary:
The idea here is to make it so we can swap out the type we are using for optionality. In the near term we are going to try swapping towards one that more aggressively tries to save size.

For now there is no functional change and this is just a big aliasing diff.

Reviewed By: sharmafb

Differential Revision: D57633896

fbshipit-source-id: 6eae5953d47395b390016e59cf9d639f3b6c8cfe
2024-06-11 11:02:02 -07:00
Joseph Beshay
3b8782b4b2 Wire the EcnL4STracker to the QuicTransport when L4S is validated
Summary: As title.

Reviewed By: mjoras

Differential Revision: D56449545

fbshipit-source-id: daea00bb179b7f555e9386de5e4ee490be904f4a
2024-05-24 17:16:40 -07:00
Joseph Beshay
eb778e8f5d Validate ECN/L4S feedback
Summary:
This adds validation to verify that packets sent with an ECT(0/1) marks, are being echoed correctly by the client without any interference in the network path. If validation succeeds, the transport can use the ECN feedback in the congestion controller. If it fails, packet marking is disabled.

Ideally, the number of marks echoed by the peer in ACK_ECN frames should be equal to the number of packets sent with marks. However, that is not achievable with the current design due to the following restrictions:

- To be able to track the number of marks accurately, the sending transport needs to match incoming acks with the outstanding packets they are acking. However,  the sending transport's list of outstanding packets only tracks retransmittable packets. Therefore, acks containing marks that refer to non-retranmittable packets cannot be verified.
- If the client is using GRO, we have one header for the whole batch. So echoed marking can be inflated.

To work around these limitations, the validation logic checks that:
- At least 10 retransmittable packets were sent with marks in the AppData packet number space.
- The number of echoed marks is greater than the number of retransmittable AppData packets sent with marks.
- The number of echoed marks is less than the total number of packets sent.
- No unexpected marks show up. I.e. No ECT0 when sending ECT1 or vv.

Reviewed By: kvtsoy

Differential Revision: D55618562

fbshipit-source-id: 8bc44b4f1b64725f51f63bb86d6c4bd573338e83
2024-05-15 11:51:15 -07:00
Joseph Beshay
3eef6d0e55 Add ToS field to ReceivedUdpPacket
Summary: Adds new field `tosValue` to  ReceivedUdpPacket so it is accessible in the rest of the read path.

Reviewed By: kvtsoy

Differential Revision: D54912161

fbshipit-source-id: ea4714fa2374d38e915fc850387e1094d1fb8adf
2024-05-15 11:51:15 -07:00
Joseph Beshay
993fe05231 Support for sending packets with DSCP, ECT(0) and ECT(1) marking
Summary:
Adds new transport settings for enabling quic sockets to read or write the tos/tclass field in the IP headers.

The new transport settings are: readEcnOnIngress, enableEcnOnEgress, useL4sEcn. All are defaulted to false.

readEcnOnIngress=true --> enabled reading the ToS field from incoming packets.

enableEcnOnEgress=false --> does not set marking
enableEcnOnEgress=true, useL4sEcn=false --> sets marking to ECT0
enableEcnOnEgress=true, useL4sEcn=true --> sets marking to ECT1

The next changes handle these packets in the rest of the stack.

Reviewed By: mjoras, kvtsoy

Differential Revision: D54877773

fbshipit-source-id: af6aefc714e2678f488d027583cf666200748782
2024-05-09 11:05:32 -07:00
Konstantin Tsoy
acfe58c9a8 Do not emit blocked frames more than once
Summary: Until a flow control update arrives

Reviewed By: mjoras

Differential Revision: D55528849

fbshipit-source-id: 904543f3d04aae1cbbceb34f5723039dc5fb94e2
2024-04-04 16:11:54 -07:00
Joseph Beshay
e8eff25a13 Fix QuicTransportTest
Summary: An unused folly timer fd keeps the event base active causing the tests to timeout. This fixes it.

Differential Revision: D52647419

fbshipit-source-id: 57e699e9b34c9fd6d86cb6e0cb1705066f09e1c9
2024-01-09 19:49:55 -08:00
Joseph Beshay
96b65104dc Move QuicEventBase and QuicTimer callback operations back to the Callbacks themselves.
Summary:
This moves all the loop and timer callback operations back to the callbacks instead of relying the QuicEventBase to perform them. I.e. it's now Callback::cancelCallback() instead of QuicEventBase::cancelCallback(&callback).

To simplify the design, the lifetime of LoopCallbackWrapper and TimerCallbackWrapper has been changed. Previously these wrappers lasted for one iteration of the loop or the timer callback. In the new design the wrapper is created the first time the callback is scheduled and is only destroyed when the callback is destroyed. This significantly simplifies the lifetime management of the wrapper and the code overall.

While transitioning LibevQuicEventBase to this new design, this change also consolidates the QuicTimer functionality in the LibevQuicEventBase itself.

Reviewed By: hanidamlaj, mjoras

Differential Revision: D52217879

fbshipit-source-id: da7b95d592650ddc112813fdc3b9f5010d32e7fb
2024-01-03 12:38:20 -08:00
Matt Joras
cc927374d7 Optional writable bytes backpressure
Summary: Add backpressure based on CCA's writable bytes (cwnd), which can be useful for the app to use as backpressure. This also takes into account stream bytes currently buffered.

Differential Revision: D52098629

fbshipit-source-id: c672e73bab01eb301a67c9b8a95225780000cbd6
2023-12-15 21:58:10 -08:00
Joseph Beshay
ead139adef Move all mvfst use-cases to the new Eventbase, Timer, and Socket interfaces
Summary:
This is the major transition that updates mvfst code to use the new interfaces. The new Folly implementations of the interfaces maintain all the existing behavior of folly types so this should not introduce any functional change. The core changes are:
- Update the BatchWriters to use the new interfaces.
- Update the FunctionLooper to use the new interfaces.
- Change QuicServerTransport to take the folly types and wrap them in the new types for use in the QuicTransportBase.

The rest of the diff is for updating all the existing uses of the QuicTrasnport to initialize the necessary types and pass them to the QUIC transport instead of directly passing folly types.

Reviewed By: mjoras

Differential Revision: D51413481

fbshipit-source-id: 5ed607e12b9a52b96148ad9b4f8f43899655d936
2023-12-14 00:24:12 -08:00
Brandon Schlinker
a1445434b0 Cleanup and modularize receive path, improve timestamp support [5/x]
Summary:
This diff changes `QuicAsyncUDPSocketWrapper` so that it is an abstraction layer that inherits from `QuicAsyncUDPSocketType`, instead of simply being a container with aliases.
- Key changes in `QuicAsyncUDPSocketWrapper.h`, the rest of the updates switch us from using `QuicAsyncUDPSocketType` to `QuicAsyncUDPSocketWrapper`.
- It's difficult to mock the UDP socket today given that we expose the entire `folly::AsyncUDPSocket` type to the higher layers of the QUIC stack. This complicates testing and emulation because any mock / fake has to implement low level primitives like `recvmmsg`, and because the `folly::AsyncUDPSocket` interface can change over time.
- Pure virtual functions will be defined in `QuicAsyncUDPSocketWrapper` in a follow up diff to start creating an interface between the higher layers of the mvfst QUIC stack and the UDP socket, and this interface will abstract away lower layer details such as `cmsgs` and `io_vec`, and instead focus on populating higher layer structures such as `NetworkData` and `ReceivedPacket` (D48714615). This will make it easier for us to mock or fake the UDP socket.

This diff relies on changes to `folly::MockAsyncUDPSocket` introduced in D48717389.

--

This diff is part of a larger stack focused on the following:

- **Cleaning up client and server UDP packet receive paths while improving testability.** We currently have multiple receive paths for client and server. Capabilities vary significantly and there are few tests. For instance:
  - The server receive path supports socket RX timestamps, abet incorrectly in that it does not store timestamp per packet. In comparison, the client receive path does not currently support socket RX timestamps, although the code in `QuicClientTransport::recvmsg` and `QuicClientTransport::recvmmsg` makes reference to socket RX timestamps, making it confusing to understand the capabilities available when tracing through the code. This complicates the tests in `QuicTypedTransportTests`, as we have to disable test logic that depends on socket RX timestamps for client tests.
  - The client currently has three receive paths, and none of them are well tested.

- **Modularize and abstract components in the receive path.** This will make it easier to mock/fake the UDP socket and network layers.
  - `QuicClientTransport` and `QuicServerTransport` currently contain UDP socket handling logic that operates over lower layer primitives such `cmsg` and `io_vec` (see `QuicClientTransport::recvmmsg` and `...::recvmsg` as examples).
  - Because this UDP socket handling logic is inside of the mvfst transport implementations, it is difficult to test this logic in isolation and mock/fake the underlying socket and network layers. For instance, injecting a user space network emulator that operates at the socket layer would require faking `folly::AsyncUDPSocket`, which is non-trivial given that `AsyncUDPSocket` does not abstract away intricacies arising from the aforementioned lower layer primitives.
  - By shifting this logic into an intermediate layer between the transport and the underlying UDP socket, it will be easier to mock out the UDP socket layer when testing functionality at higher layers, and inject fake components when we want to emulate the network between a mvfst client and server. It will also be easier for us to have unit tests focused on testing interactions between the UDP socket implementation and this intermediate layer.

- **Improving receive path timestamping.** We only record a single timestamp per `NetworkData` at the moment, but (1) it is possible for a `NetworkData` to have multiple packets, each with their own timestamps, and (2) we should be able to record both userspace and socket timestamps.

Reviewed By: jbeshay, hanidamlaj

Differential Revision: D48717388

fbshipit-source-id: 4f34182a69ab1e619e454da19e357a6a2ee2b9ab
2023-09-21 07:57:58 -07:00
Konstantin Tsoy
264bf20d9a Update flow control settings names to reflect that these are indeed flow
Summary: Update flow control settings names to reflect that these are indeed flow control

Reviewed By: jbeshay

Differential Revision: D48137685

fbshipit-source-id: a48372e21cdd529480e25785a9bd5de456427ef3
2023-08-18 10:21:24 -07:00
Christian Clauss
b8396fc119 Fix typos discovered by codespell
Summary:
`codespell --ignore-words-list=arithmetics,atleast,crate,crated,deriver,ect,hel,onl,startin,whats --skip="*.lock"`
* https://pypi.org/project/codespell

X-link: https://github.com/facebookincubator/mvfst/pull/307

Reviewed By: hanidamlaj, lnicco

Differential Revision: D47809078

Pulled By: kvtsoy

fbshipit-source-id: 566557f2389746db541ff265a5dec8d6404b3701
2023-07-26 17:10:41 -07:00
Konstantin Tsoy
73edee8252 Back out "Fix typos discovered by codespell"
Summary:
Original commit changeset: 337824bc37bc

Original Phabricator Diff: D47722462

Reviewed By: jbeshay, terrelln, lnicco

Differential Revision: D47801753

fbshipit-source-id: 795ffcccbc2223608e2a707ec2e5bcc7dd974eb3
2023-07-26 12:49:13 -07:00
Facebook Community Bot
9d89b66485 Re-sync with internal repository 2023-07-25 09:45:22 -07:00
Joseph Beshay
931abc64af Separate transport settings for pacing tick and the pacing timer resolution
Summary:
The pacingTimerTickInterval transport setting conflates two options: the minimum interval a pacer can use, and the resolution of the underlying timer. This means that a higher value leads to lower timer resolution and less pacing accuracy.

This change adds a separate parameter for the timer resolution to ensure that a larger pacing tick does not degrade the pacer accuracy.

Reviewed By: mjoras

Differential Revision: D46564066

fbshipit-source-id: 0d0e54077b80da03e6e6c9baaab49a4c969966b6
2023-06-20 15:18:38 -07:00
Matt Joras
3c5a34ee11 Put opportunistic ACKing behind TransportSetting
Summary:
This has been a default behavior for us for a long time. Basically, we will always include ACK frames in a burst if there's new packets to ACK.

This is overall probably fine and is flexible to peer behavior such that the peer can get away with basically never sending anything ACK-eliciting.

However it is not without its issues. In particular, for DSR it means that we write an excessive amount of pure ACK packets since they cannot be coalesced with a DSR burst.

Make this behavior optional, such that we only include ACK frames in non-probing schedulers when we are only writing stream data.

Reviewed By: kvtsoy

Differential Revision: D39479149

fbshipit-source-id: 6e92d45311a3fb23750c93483b94e97dd3fdce26
2023-06-15 13:15:08 -07:00
Matt Joras
35a2d34843 Use a single queue for scheduling DSR and non-DSR streams.
Summary:
The write loop functions for DSR or non-DSR are segmented today. As such, so are the schedulers. Mirroring this, we also currently store the DSR and non-DSR streams in separate write queues. This makes it impossible to effectively balance between the two without potential priority inversions or starvation.

Combining them into a single queue eliminates this possibility, but is not entirely straightforward.

The main difficulty comes from the schedulers. The `StreamFrameScheduler` for non-DSR data essentially loops over the control stream queue and the normal write queue looking for the next stream to write to a given packet. When the queues are segmented things are nice and easy. When they are combined, we have to deal with the potential that the non-DSR scheduler will hit a stream with only DSR data. Simply bailing isn't quite correct, since it will just cause an empty write loop. To fix that we need check, after we are finished writing a packet, if the next scheduled stream only has DSR data. If it does, we need to ensure `hasPendingData()` returns false.

The same needs to be done in reverse for the DSR stream scheduler.

The last major compication is that we need another loop which wraps the two individual write loop functions, and calls both functions until the packet limit is exhausted or there's no more data to write. This is to handle the case where there are, for example, two active streams with the same incremental priority, and one is DSR and the other is not. In this case each write loop we want to write `packetLimit` packets, flip flopping between DSR and non DSR packets.

This kind of round robining is pathologically bad for DSR, and a future diff will experiment with changing the round robin behavior such that we write a minimum number of packets per stream before moving on to the next stream.

This change also contains some other refactors, such as eliminating `updateLossStreams` from the stream manager.

(Note: this ignores all push blocking failures!)

Reviewed By: kvtsoy

Differential Revision: D46249067

fbshipit-source-id: 56a37c02fef51908c1336266ed40ac6d99bd14d4
2023-06-01 14:11:31 -07:00
Paul Farcasanu
e56d4bd7f6 refactor setStreamPriority to accept Priority struct
Summary:
## Context
Context: see summary for D43854603.

## In this diff
In this diff, make way for easily adding new elements to Priority struct.

Reviewed By: afrind

Differential Revision: D43882907

fbshipit-source-id: f74f6ec41162a970dcd666bfa5192676f968d740
2023-03-28 16:00:38 -07:00
Hani Damlaj
104b9848bc fix connection migration deadlock
Summary: Currently, we can enter a deadlock situation where a client rx's a PathChallenge frame, but the packet containing its respective PathResposne frame is lost/delayed. Clients should re-tx the PathResponse frame upon PTO/loss.

Reviewed By: jbeshay

Differential Revision: D43718357

fbshipit-source-id: 26b4bc64dbf48417558eda02744f321f1cb73148
2023-03-17 20:36:56 -07:00
Konstantin Tsoy
424ab5c8c1 Remove useless func argument
Summary: Remove useless func argument

Reviewed By: jbeshay

Differential Revision: D42647239

fbshipit-source-id: d27b26391971ca31f8bf727e3648d1a0dbf124be
2023-01-24 14:53:27 -08:00
Matt Joras
3e57e82400 When using ACK_FREQUENCY, disable SRTT/4 heuristic.
Summary: We always use an SRTT/4 ACKing heuristic for the ACK delay. This has generally been a useful heuristic, but when using ACK_FREQUENCY we should defer to using the delay by the peer.

Reviewed By: jbeshay

Differential Revision: D40272530

fbshipit-source-id: c7a44e53233c97d0c96bc6f936a7318cf4676aba
2022-10-11 18:15:24 -07:00
Matt Joras
6c0d60d589 Don't allow DSR EOF to come via writeChain.
Summary: We were previously allowing this, but I don't think it's actually a useful semantic. The application should commit to writing the EOF via writeBufferMeta.

Reviewed By: shodoco

Differential Revision: D40245316

fbshipit-source-id: 22492755f45a04223246306b91bfda10be02f8eb
2022-10-10 21:45:12 -07:00
Brandon Schlinker
5b8e0de5bd Improve transport close handling and observability
Summary:
The current `close` observer event marks when `closeImpl` is called. However, the actual close of the socket may be delayed for some time while the socket drains. I've changed the existing event to `closeStarted` and added a new event `closing` that marks the close of the underlying `AsyncUDPSocket`.

Adding the `closeStarted` event required two other changes which are difficult to separate from this diff:
- When a transport is destroyed, `QuicTransportBase` was calling `closeImpl` and also closing the UDP socket. However, because the `folly::ObserverContainer` used to store observers is maintained in classes that derive from `QuicTransportBase`, the observers are gone by the time the UDP socket is closed in the base class destructor. Thus, the UDP socket should be closed by the derived classes in their respective destructors. This requirement is inline with the existing code: `closeImpl` is called by all derived classes in their destructors. Made this change and added `DCHECK` statements in the `QuicTransportBase` destructor to ensure that derived classes cleanup after themselves.
- Writing tests with draining enabled and disabled required being able to set the transport settings. However, all of the existing `QuicTypedTransportTest` test cases were designed to operate after the connection was accepted (for the server impls) or established (for client impls), and transport settings cannot be updated at this state. Resolving this required adding new test classes in which the accept/connect operation is delayed until requested by the test.

Reviewed By: mjoras

Differential Revision: D39249604

fbshipit-source-id: 0ebf8b719c4d3b01d4f9509cf2b9a4fc72c2e737
2022-09-10 10:39:11 -07:00