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

How to specify over which path to send PING frames? #144

Closed
mirjak opened this issue Oct 11, 2022 · 14 comments · Fixed by #148
Closed

How to specify over which path to send PING frames? #144

mirjak opened this issue Oct 11, 2022 · 14 comments · Fixed by #148

Comments

@mirjak
Copy link
Collaborator

mirjak commented Oct 11, 2022

Currently we don't mention PING frames in the draft, however, I guess there are use cases where an app wants to send a ping over one specific or both paths. We should probably say something about handling of PING frames if multiple path are available.

@huitema
Copy link
Contributor

huitema commented Oct 11, 2022

We already have the path challenge frame, which provides a way to test continuity of a specific path. I think it is better to leave ping "connection wide", parallel to data frames.

@mirjak
Copy link
Collaborator Author

mirjak commented Oct 11, 2022

That okay as well but we still would need more guidance how to send ping frames when multiple path are available. E.g. try one and if it fails, try the next. or just send a ping on each path...?

@huitema
Copy link
Contributor

huitema commented Oct 11, 2022

It depends whether you want to test continuity on the forward path, the connection, or the return path.

The forward path test is used form example when doing PMTUD or probe time-out. In that case, the Ping frame is sent on the path that the implementation wants to test, and the corresponding ACK will indicate that the packet sent on the specified path has been received. This is exactly as expected, and I don't think it requires clarification.

The connection test is used for example in keep-alive mechanisms. There are many possibilities, because this is only used when the connection is almost idle. Should such connections try to keep many paths alive or just one? I suppose different applications will have different constraints. In any case, once they have decided that, sending Ping frames on the selected path or paths is straightforward.

The return path is different. I don't think it can be tested using Ping, because there is no way to force ACK frames to use a specific return path. If an application want to do that, they have to use Path Challenge.

@qdeconinck
Copy link
Contributor

I tend to agree with Christian. How the application wants to send PING frames on available paths to probe forward path looks more like an API issue than a specification one. And I agree that testing the return path is not easy (beyond PATH_CHALLENGE/PATH_RESPONSE), but in general "forcing" scheduling policies on the other end is not possible (you can only suggest, as with PATH_STATUS frames).

@mirjak
Copy link
Collaborator Author

mirjak commented Oct 12, 2022

Yes, it mainly an API issue. However, I think there is one point we need to address.

This is what RFC9000 says:

With this option, an endpoint could send a PING frame (Section 19.2) periodically, which will cause the peer to restart its idle timeout period. Sending a packet containing a PING frame restarts the idle timeout for this endpoint also if this is the first ack-eliciting packet sent since receiving a packet. Sending a PING frame causes the peer to respond with an acknowledgment, which also restarts the idle timeout for the endpoint.

If you send a PING only one path and don't get a response, you won't reset the timer and might close the connection even though another path might still be alive. I think that would be wrong.

So I think the two options are you either send PINGs on all paths; or you try one path first and if you don't get a reply, reset the timer and try the next one.

@huitema
Copy link
Contributor

huitema commented Oct 12, 2022

@mirjak, you are describing the "keep alive" scenario. Yes, keep alive becomes a bit tricky in multipath, because the client may want to select how many paths it wants to keep alive, and which ones. For example, a client with Wi-Fi and cellular may want to keep the cellular path alive, because it will survive a mobility event. It may want to do that even if it is sending traffic over Wi-Fi. That's a local implementation decision. How they do that, however, is straightforward: send a Ping on the path that you want to keep alive.

I think we should let implementers decide what they want to do. If we do add some text, is should be about keep alive, not about ping. Something like:

## Keep Alive

The QUIC specification defines an optional keep alive process, see {{Section 5.3 of RFC9000}}.
Implementations of the multipath extension should consider whether this keep alive process
should be applied to at least one path, all the paths, no path, or a specific subset of the paths.
Different applications will likely require different strategies. Once the implementation has
decided to keep a specific path alive, it can do so by sending Ping frames on that path before
the idle timeout expires.

@yfmascgy
Copy link
Contributor

I think we should recommend sending out ping frames periodically on all paths for keep alive purpose. Sometimes, if you don't send data on a path for some time, then the path will become a "black hole" for UDP packets, probably due to NAT black hole. But I think we already address it in 4.3.4. Idle Timeout part of the draft with the following text:

"To avoid idle timeout of a path, endpoints can send ack-eliciting packets such as packets containing PING frames (Section 19.2 of [QUIC-TRANSPORT]) on that path to keep it alive. Sending periodic PING frames also helps prevent middlebox timeout, as discussed in Section 10.1.2 of [QUIC-TRANSPORT]."

@mirjak
Copy link
Collaborator Author

mirjak commented Oct 13, 2022

Sounds like we can add some guidance in the implementation section!

@obonaventure
Copy link
Contributor

I agree with Quentin and Christian that the problem is application dependent. We should avoid over specifying things in this section. For example, sending PING frames on all paths does not seem a good suggestion given that a connection may use more than two paths. We could have something like

Keep Alive

The QUIC specification defines an optional keep alive process, see {{Section 5.3 of RFC9000}}.
Implementations of the multipath extension should map this keep alive process to a number of paths.
Some applications may wish to ensure that one path remains active, while others could prefer to have two or more active paths during the connection lifetime. Different applications will likely require different strategies.
Once the implementation has decided which paths to keep alive, it can do so by sending Ping frames on each of these paths before the idle timeout expires. Implementations should jitter their timers to avoid sending Ping frames at the same time over different paths.

@yfmascgy
Copy link
Contributor

Keep Alive

The QUIC specification defines an optional keep alive process, see {{Section 5.3 of RFC9000}}. Implementations of the multipath extension should map this keep alive process to a number of paths. Some applications may wish to ensure that one path remains active, while others could prefer to have two or more active paths during the connection lifetime. Different applications will likely require different strategies. Once the implementation has decided which paths to keep alive, it can do so by sending Ping frames on each of these paths before the idle timeout expires. Implementations should jitter their timers to avoid sending Ping frames at the same time over different paths.

Right now, we have some texts like sending ack-eliciting packets such as PING frames to keep a path alive in Section 4.3.4. But I think we can merge the above text to better clarify this implementation guidance.

@mirjak
Copy link
Collaborator Author

mirjak commented Oct 21, 2022

So for keep alive purposes if you decide to send pings only over one or at least not all open paths, that would mean that you may not get a ping reply on those paths and close the connection even though another path, that you just decide for what every reason to not ping, is still working. That does seem quite right do me?

Also not sure about the recommendation to jitter pings. Ideally paths are distinct (to some extend at least) but even if not a ping frame is quite low load. I guess if you send too many ping frames at ones this could lead to a burst that overflows the short buffers but I guess that would need in most cases at least 10 or more pings. Not sure we need to give this recommendation...?

@mirjak
Copy link
Collaborator Author

mirjak commented Oct 21, 2022

I create a new PR (#148) with the proposed text as a new subsection in the implementation consideration part. However, not sure if this is ready to merge or needs further discussion...

@yfmascgy
Copy link
Contributor

So for keep alive purposes if you decide to send pings only over one or at least not all open paths, that would mean that you may not get a ping reply on those paths and close the connection even though another path, that you just decide for what every reason to not ping, is still working. That does seem quite right do me?

Also not sure about the recommendation to jitter pings. Ideally paths are distinct (to some extend at least) but even if not a ping frame is quite low load. I guess if you send too many ping frames at ones this could lead to a burst that overflows the short buffers but I guess that would need in most cases at least 10 or more pings. Not sure we need to give this recommendation...?

I actually have similar questions. I think to keep it simple, if you want to keep paths alive, just send pings on every path. Sending pings at the same time over different paths should not be problematic as long as you have the frequency control.

@Yanmei-Liu
Copy link
Contributor

We already have some text about how the PING frames influence the paths in Section idle timeout. It mostly depends on implementations. We could simply add:

Different applications MAY require different keep alive strategies. Once the implementation has decided to keep a specific path alive, it can do so by sending Ping frames on that path before the idle timeout expires.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants