Commit graph

293 commits

Author SHA1 Message Date
Dor Hen
65b59a9c2d Prepend webrtc ns to StrJoin calls in dcsctp ns
Bug: webrtc:365299886
Change-Id: I4eb87a2b116c3e18b1a84865fab0a22a6084912c
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/361980
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Dor Hen <dorhen@meta.com>
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42980}
2024-09-09 11:16:56 +00:00
Victor Boivie
65b46da1f8 dcsctp: Don't send FORWARD-TSN in its own chunk
This is a rollback of a change list [1] that was an attempt to avoid a
bug in usrsctp[2], but it wasn't very successful. But with the usrsctp
bug fixed, we can revert to the desired state; that we bundle
FORWARD-TSN with other control and data chunks in a SCTP packet.

[1] https://webrtc-review.googlesource.com/c/src/+/229101
[2] https://github.com/sctplab/usrsctp/issues/597

Bug: webrtc:42223134
Change-Id: I2f3b511c91639e6b9516160190600beb0c04b5fa
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/361862
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42976}
2024-09-06 13:29:52 +00:00
Victor Boivie
7929ef578a dcsctp: Add test for stream reset pending
Bug: None
Change-Id: Ida040461dda53b438d88df4a38518f334cadc379
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/361861
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Auto-Submit: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42975}
2024-09-06 13:20:58 +00:00
Florent Castelli
8037fc6ffa Migrate absl::optional to std::optional
Bug: webrtc:342905193
No-Try: True
Change-Id: Icc968be43b8830038ea9a1f5f604307220457807
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/361021
Auto-Submit: Florent Castelli <orphis@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42911}
2024-09-02 12:16:47 +00:00
Victor Boivie
7348f820a9 dcsctp: Re-add lost validating in test case
This was unintentionally removed in change
https://webrtc-review.googlesource.com/c/src/+/359681 due to a dirty
workspace.

Re-adding it.

Bug: None
Change-Id: Icff55b7a656ed9b504b0e10e7aeb947e8df78e85
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/360540
Auto-Submit: Victor Boivie <boivie@webrtc.org>
Commit-Queue: Florent Castelli <orphis@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42846}
2024-08-26 09:22:13 +00:00
Victor Boivie
adb224b3e9 dcsctp: Simplify congestion control algorithm
There was a feature in the retransmission queue to avoid fragmenting
large messages when the congestion window was large. This was a feature
that intended to improve data channel performance under Chrome, where
communication with the network process (over MOJO) was lossy and losing
messages with small fragments could result in unnecessary
retransmissions. But back then, the implementation for fast retransmit
wasn't implemented correctly, so the benchmarking result don't
reproduce any longer.

So just improve the algorithm by removing this code. This aligns it with
the RFC and makes it easier to implement pluggable congestion control
algorithms (that wouldn't want this feature).

Bug: webrtc:42223116
Change-Id: Ifaaa82dac4b8fe2f55418158ae8b3da97199212f
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/359681
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42797}
2024-08-18 15:20:35 +00:00
Dor Hen
1921fa5ea1 Apply include-cleaner to api/test/[^/]*
e.g all files in the api/test folder not including subdirectories

Bug: webrtc:42226242
Change-Id: I18d74a18f8feec41eb252faa9acfffd1d6f45ce4
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/359420
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Commit-Queue: Dor Hen <dorhen@meta.com>
Cr-Commit-Position: refs/heads/main@{#42773}
2024-08-13 15:28:34 +00:00
Victor Boivie
135f781b94 dcsctp: Pack state cookie
The elements in it can be packet better. This saves one byte.

The state cookie is only used from one peer to itself, so there is no
considerations around backwards or forwards compatibility.

Bug: None
Change-Id: I4f9a44f4c825626c7ed84bff52ed3155f5025a69
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/353142
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Florent Castelli <orphis@webrtc.org>
Auto-Submit: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42421}
2024-05-31 13:20:31 +00:00
Victor Boivie
b206ab1f81 dcsctp: Restart heartbeat timer when sending DATA
Before this change, the heartbeat timer was restarted every time a
packet was sent on the socket. On an idle connection, if the peer is
sending heartbeats, just responding to those heartbeats (with a
HEARTBEAT-ACK) would restart the timer, and then this socket wouldn't
do any heartbeating itself because the next hearbeat by the peer would
be received before the timer expires.

This is not according to the specification, where
https://datatracker.ietf.org/doc/html/rfc9260#section-8.3 states that
"A destination transport address is considered "idle" if no new chunk
 that can be used for updating path RTT (usually including first
 transmission DATA, INIT, COOKIE ECHO, or HEARTBEAT chunks, etc.)"

There are already timers running when INIT, and COOKIE-ECHO are sent
and not acked, so the heartbeat shouldn't be sent then. This is further
confirmed in the same section in the RFC which says that "The sending of
HEARTBEAT chunks MAY begin upon reaching the ESTABLISHED state". And
when INIT and COOKIE-ECHO are sent, the connection is not yet
established.

This CL changes so that the heartbeat timer is only restarted when any
DATA or I-DATA chunk is sent. This will make both sides send heartbeats
on an idle connection.

Bug: webrtc:343600379
Change-Id: I5ab159b7901e2ec9d37b24aaf845891b60a53c13
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/352841
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42409}
2024-05-30 10:50:30 +00:00
Florent Castelli
99c519b3fd Mass removal of absl_deps in all BUILD.gn files
Bug: webrtc:341803749
Change-Id: Id73844ba8d63b9f2f2c9391d8d8116ad0864c36d
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/351540
Commit-Queue: Florent Castelli <orphis@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42372}
2024-05-23 15:09:46 +00:00
Per K
5566b91356 Reland "Replace usage of link_capacity_kbps with DataRate link_capacity"
This reverts commit ff2dd50fd8.

Reason for revert: Temporary fix for downstream breakage in patch 2

Original change's description:
> Revert "Replace usage of link_capacity_kbps with DataRate link_capacity"
>
> This reverts commit 6186c0226e.
>
> Reason for revert: Breaks downstream project.
>
> Original change's description:
> > Replace usage of link_capacity_kbps with DataRate link_capacity
> >
> > Replace usage of BuiltInNetworkBehaviorConfig.link_capacity_kbps in tests with  DataRate link_capacity.
> >
> > Bug: webrtc:14525
> > Change-Id: Id1c1b8d20eb2be5e9d1461704bb7c37c61c491f0
> > Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350300
> > Reviewed-by: Erik Språng <sprang@webrtc.org>
> > Reviewed-by: Harald Alvestrand <hta@webrtc.org>
> > Commit-Queue: Per Kjellander <perkj@webrtc.org>
> > Reviewed-by: Björn Terelius <terelius@webrtc.org>
> > Cr-Commit-Position: refs/heads/main@{#42306}
>
> Bug: webrtc:14525
> Change-Id: I09ede3e89d065061cb4133bff96dbf242ff70832
> No-Presubmit: true
> No-Tree-Checks: true
> No-Try: true
> Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350621
> Commit-Queue: Mirko Bonadei <mbonadei@webrtc.org>
> Bot-Commit: rubber-stamper@appspot.gserviceaccount.com <rubber-stamper@appspot.gserviceaccount.com>
> Owners-Override: Mirko Bonadei <mbonadei@webrtc.org>
> Cr-Commit-Position: refs/heads/main@{#42309}

Bug: webrtc:14525
Change-Id: Ie35cd97a158d008a80ed007b27d2c6b1a9affff9
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350541
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Reviewed-by: Erik Språng <sprang@webrtc.org>
Commit-Queue: Per Kjellander <perkj@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Reviewed-by: Björn Terelius <terelius@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42320}
2024-05-16 10:39:10 +00:00
Mirko Bonadei
ff2dd50fd8 Revert "Replace usage of link_capacity_kbps with DataRate link_capacity"
This reverts commit 6186c0226e.

Reason for revert: Breaks downstream project.

Original change's description:
> Replace usage of link_capacity_kbps with DataRate link_capacity
>
> Replace usage of BuiltInNetworkBehaviorConfig.link_capacity_kbps in tests with  DataRate link_capacity.
>
> Bug: webrtc:14525
> Change-Id: Id1c1b8d20eb2be5e9d1461704bb7c37c61c491f0
> Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350300
> Reviewed-by: Erik Språng <sprang@webrtc.org>
> Reviewed-by: Harald Alvestrand <hta@webrtc.org>
> Commit-Queue: Per Kjellander <perkj@webrtc.org>
> Reviewed-by: Björn Terelius <terelius@webrtc.org>
> Cr-Commit-Position: refs/heads/main@{#42306}

Bug: webrtc:14525
Change-Id: I09ede3e89d065061cb4133bff96dbf242ff70832
No-Presubmit: true
No-Tree-Checks: true
No-Try: true
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350621
Commit-Queue: Mirko Bonadei <mbonadei@webrtc.org>
Bot-Commit: rubber-stamper@appspot.gserviceaccount.com <rubber-stamper@appspot.gserviceaccount.com>
Owners-Override: Mirko Bonadei <mbonadei@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42309}
2024-05-15 11:09:33 +00:00
Per K
6186c0226e Replace usage of link_capacity_kbps with DataRate link_capacity
Replace usage of BuiltInNetworkBehaviorConfig.link_capacity_kbps in tests with  DataRate link_capacity.

Bug: webrtc:14525
Change-Id: Id1c1b8d20eb2be5e9d1461704bb7c37c61c491f0
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350300
Reviewed-by: Erik Språng <sprang@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Per Kjellander <perkj@webrtc.org>
Reviewed-by: Björn Terelius <terelius@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42306}
2024-05-15 08:44:20 +00:00
Sergey Sukhanov
26a082ce36 Introduce a mode that lets NetworkEmulationManager ignore DTLS handshake sizes.
Bug: b/169531206
Change-Id: I02c19385ff7078944f7509ecc07358b4315f7b08
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/350181
Commit-Queue: Sergey Sukhanov <sergeysu@webrtc.org>
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Reviewed-by: Per Kjellander <perkj@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42261}
2024-05-08 13:20:20 +00:00
Per K
569849e885 Move call/simulated_network to test/network
Old target and call/simulated.h exist but refer to new target in test/network.

Bug: webrtc:14525
Change-Id: Ida04cef17913f2f829d7e925ae454dc40d5e8240
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/349264
Commit-Queue: Per Kjellander <perkj@webrtc.org>
Reviewed-by: Björn Terelius <terelius@webrtc.org>
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Owners-Override: Per Kjellander <perkj@webrtc.org>
Reviewed-by: Erik Språng <sprang@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42191}
2024-04-29 09:55:06 +00:00
Victor Boivie
b5f2442275 dcsctp: Remove dead code
This was only used for handover state, and not updated at all after
https://webrtc-review.googlesource.com/c/src/+/322623.

Bug: None
Change-Id: I5005902486d1fae76badd9f196e0e3525fe573de
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/349163
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42175}
2024-04-25 12:39:48 +00:00
Victor Boivie
28d07ddbfd dcsctp: Compute RTO with higher precision
Since the code measuring the RTT has been converted to using TimeDelta
which internally stores the duration in microseconds, from DurationMs
which uses milliseconds, the RTO calculation can use the higher
precision to calculate lower non-zero durations on really fast networks
such within a data center.

Before this CL, which is from the initial drop of dcSCTP, the RTO
calculation was done using the algorithm from the paper "V. Jacobson:
Congestion avoidance and control", but now we're using the original
algorith from https://tools.ietf.org/html/rfc4960#section-6.3.1, which
comes from https://datatracker.ietf.org/doc/html/rfc6298#section-2.

Two issues were found and corrected:
 1. The min RTT variance that is specified in the config file was
    previously incorrectly divided by 8. That was not its intention,
    but we're keeping that behaviour as other clients have actually
    measured a good value to put there. This represents "G" in
    the "basic algorithm" above, and since that is multiplied with K,
    which is four, the default value of 220 wouldn't make sense if it
    wasn't scaled down, as that would make the RTO easily saturate to
    the RTO_max (800ms).
 2. The previous algorithm had large round-off errors (probably because
    the code used milliseconds), which makes fairly big changes to the
    calculated RTO in some situations.

Bug: webrtc:15593
Change-Id: I95a3e137c2bbbe7bf8b99c016381e9e63fd01d87
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/349000
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#42170}
2024-04-25 07:53:24 +00:00
Victor Boivie
de276cf049 dcsctp: Remove initial TSN from reassembly queue
With a previous refactoring, which made the data tracker responsible for
ensuring that the reassembly queue doesn't see any duplicate received
chunks, it no longer needs to know the initial peer's TSN. Removing.

Bug: None
Change-Id: I0e2aef1de0293f1860b46dee0089757c9c300aea
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/345701
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41997}
2024-04-04 19:19:47 +00:00
Victor Boivie
0b83b2cbb4 dcsctp: Remove unreferenced reassembly_streams.cc
This code was moved to ReassemblyQueue::AddReassembledMessage, the build
file was updated to remove the source file, but the source file was
never actually deleted. Dead code.

Bug: None
Change-Id: Iafb9bb276ff870398a76737ceb16ffc50a91738e
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/345620
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41994}
2024-04-04 10:44:11 +00:00
Victor Boivie
2fc097ea83 Reapply "dcsctp: Add per-stream-limit, refactor limits."
Keeping the old setting for the total queue size
limit, which avoids breaking a downstream.

This reverts commit 47ce449afa
and relands commit 4c990e2e56.

Bug: chromium:40072842
Change-Id: I1e7d14b5d0026232d1fc9277172b6947b8be3490
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/343120
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41907}
2024-03-15 13:27:37 +00:00
Björn Terelius
47ce449afa Revert "dcsctp: Add per-stream-limit, refactor limits."
This reverts commit 4c990e2e56.

Reason for revert: Breaks downstream build.

Original change's description:
> dcsctp: Add per-stream-limit, refactor limits.
>
> The limits have been moved out from the Send Queue as they were enforced
> outside the queue anyway (in the socket). That was a preparation for
> adding even more limits; There is now also a per-stream limit, allowing
> individual streams to have one (global) limit, and the entire socket to
> have another limit.
>
> These limits are very small in the default options. In Chrome, the limit
> is 16MB per stream, so expect the defaults to be updated when the
> additional buffering outside dcSCTP is removed.
>
> Bug: chromium:41221056
> Change-Id: I9f835be05d349cbfce3e9235d34b5ea0e2fe87d1
> Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/342481
> Reviewed-by: Florent Castelli <orphis@webrtc.org>
> Commit-Queue: Victor Boivie <boivie@webrtc.org>
> Cr-Commit-Position: refs/heads/main@{#41895}

Bug: chromium:41221056
Change-Id: Icd57fbfca87d6b512cfc7f7682ae709000c2bcad
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/343080
Commit-Queue: Björn Terelius <terelius@webrtc.org>
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Bot-Commit: rubber-stamper@appspot.gserviceaccount.com <rubber-stamper@appspot.gserviceaccount.com>
Cr-Commit-Position: refs/heads/main@{#41901}
2024-03-14 16:47:45 +00:00
Victor Boivie
4c990e2e56 dcsctp: Add per-stream-limit, refactor limits.
The limits have been moved out from the Send Queue as they were enforced
outside the queue anyway (in the socket). That was a preparation for
adding even more limits; There is now also a per-stream limit, allowing
individual streams to have one (global) limit, and the entire socket to
have another limit.

These limits are very small in the default options. In Chrome, the limit
is 16MB per stream, so expect the defaults to be updated when the
additional buffering outside dcSCTP is removed.

Bug: chromium:41221056
Change-Id: I9f835be05d349cbfce3e9235d34b5ea0e2fe87d1
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/342481
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41895}
2024-03-13 11:13:56 +00:00
Victor Boivie
2bfb5db548 dcsctp: Update zero checksum option to v-06 draft
https://datatracker.ietf.org/doc/draft-ietf-tsvwg-sctp-zero-checksum/06/

The previous implementation was for version 00, and since then changes
have been made. The chunk that is used to negotiate this capability has
now grown to include an additional property - the sender's alternate
error detection method.

Bug: webrtc:14997
Change-Id: I78043d187b79f40bbadbcba02eae6eedf54f30f9
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/336380
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41759}
2024-02-19 10:25:17 +00:00
Tal Benesh
e126e45403 Fixing unspecified evaluation order of std:move(), to avoid future issues.
This will be done by splitting the use of variables values prior to performing std:move

Bug: webrtc:15771
Change-Id: Ia88e733c3a4edf729e440295ae271d3cd9926ec5
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/334461
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Commit-Queue: Harald Alvestrand <hta@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41532}
2024-01-16 08:53:28 +00:00
Victor Boivie
6791c9d17e dcsctp: Relax thread sequence checker
The DcSctpSocket is thread compatible. As long as you serialize accesses
to it - either by calling it from the same thread, or using some kind of
concurrency primitive (e.g. mutex) to avoid calling the API methods from
different threads concurrently, it's fine.

Using the sequence checker, we can verify that the socket is called from
the thread it was created on, or from the same task queue. This provided
a more strict verification, as it didn't allow e.g. creating a socket on
one thread, and then handing it to a different thread where it was used.
Nor did it allow having multiple threads use it, protecting any calls to
it using an external mutex.

One can avoid these checks using webrtc::CurrentTaskQueueSetter to allow
the sequence checker to believe it's running where it's not running, but
this is a hack.

This CL removes the sequence checker in the socket, to simplify using it
in environments that don't use task queues for synchronization. Since it
is still kept in dcsctp::TaskQueueTimeoutFactory, it's still used in all
environments where the task queue is used (e.g. Chrome).

This makes it easier to use dcSCTP without WebRTC.

Bug: None
Change-Id: I2674d7cd902bad45ed3d0816c908ecf3ee971727
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/333801
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41482}
2024-01-09 11:50:44 +00:00
Daniel Collins
c9d44b3fb9 Add SendMany method to dcsctp socket
Bug: webrtc:15724
Change-Id: Ib1689cd46395e2315803714ef50c009580fd71bb
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/331021
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41397}
2023-12-15 21:35:14 +00:00
Daniel Collins
d093d0db7f Change CallbackDeferrer to pre-reserve the deferred vector.
The push_back pattern results in frequent vector growth which has performance overhead. This is .5% of our server's CPU

Bug: webrtc:15723
Change-Id: Ic151c81a4b49a7d48a354b75f62694bc6f9a1ee4
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/331440
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Commit-Queue: Daniel Collins <dpcollins@google.com>
Cr-Commit-Position: refs/heads/main@{#41388}
2023-12-14 21:08:58 +00:00
Daniel Collins
042e57deea Add a fastpath for message reassembly that avoids map insertion
Change-Id: I50204915f4857f22e091fb9d88b4111e40d64227
Bug: webrtc:15724
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/331340
Commit-Queue: Daniel Collins <dpcollins@google.com>
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41379}
2023-12-13 16:46:50 +00:00
Victor Boivie
161d2c8452 dcsctp: Fix not using iteraters after NackItem
OutstandingData::NackItem nacks a chunk, and if that chunk reaches its
partial reliability critera, it will abandon the entire message. If that
message hasn't been sent in full, a placeholder "end" message is
inserted (see https://crbug.com/webrtc/12812). And when the message is
inserted, any iterators may be invalidated (if e.g. std::deque would
want to grow the deque).

So ensure that there are no iterators used after having called NackItem.
By changing the interface of NackItem, and not passing an Item, but just
the TSN, this is encouraged. NackAll was rewritten as a two-pass
algorithm to first collect TSNs, then iterating that list, looking up
the items in the second pass (constant complexity).

Bug: chromium:1510364
Change-Id: I5156b6d6a683184f290e71c98f16bc68ea2a562f
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/331320
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Sam Zackrisson <saza@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41374}
2023-12-13 14:21:12 +00:00
Daniel Collins
f418f48702 Change CallbackDeferrer to use a variant and callback pointer instead of std::function
This should substantially reduce the overhead due to deferred callbacks in profiles.

Bug: webrtc:15723
Change-Id: I4c52beb91eb08c9b0ac2d1ce9a4e11839aa35e38
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/331020
Reviewed-by: Victor Boivie <boivie@webrtc.org>
Commit-Queue: Daniel Collins <dpcollins@google.com>
Cr-Commit-Position: refs/heads/main@{#41363}
2023-12-12 13:15:12 +00:00
Victor Boivie
63e273ad4b dcsctp: Persist all state in state cookie
In the example below, the association is being established between peer
A and Z, and A is the initiating party.

Before this CL, when an association was about to be established, Z would
after having received the INIT chunk, persist state in the socket about
which verification tag and initial TSN that was picked. These would be
re-generated on every incoming INIT (that's fine), but when A had
extracted the cookie from INIT_ACK and sent a reply (COOKIE_ECHO) with
the state cookie, that could fail validation when it's received by Z, if
the sent cookie was not the most recent one or if the COOKIE_ECHO had a
verification tag coming not from the most recent INIT_ACK, because Z had
replaced the state in the socket with the one generated when the second
INIT_ACK chunk was generated - state it used for validation of future
received data.

In other words:
A -> INIT 1
<timeout>
A -> INIT 2 (retransmission of INIT 1)
INIT 1 -> Z - sends INIT_ACK 1 with verification_tag=1, initial_tsn=1,
              cookie 1 (and records these to socket state)
INIT 2 -> Z - sends INIT_ACK 2 with verification_tag=2, initial_tsn=2,
              cookie 2 (replaces socket state with the new data)
INIT_ACK 1 -> A -> sends COOKIE_ECHO with verification_tag=1, cookie 1
COOKIE_ECHO (cookie 1) -> Z <FAILS, as the state isn't as expected>.

The solution is really to do what RFC4960 says, to not maintain any
state as the receiving peer until COOKIE_ECHO has been received. This
was initially not done because the underlying reason why this is
important in SCTP is to avoid denial of service, and this is why SCTP
has the four-way handshake. But for Data Channels - SCTP over DTLS -
this attack vector isn't available. So the implementation was
"simplified" by keeping socket state instead of encoding it in the
state cookie, but that obviously had downsides.

So with this CL, the non-initiating peer in connection establishment
doesn't keep any socket state, and puts all that state in the state
cookie instead. This allows any COOKIE_ECHO to be received by Z.

Bug: webrtc:15712
Change-Id: I596c7330ce27292612d3c9f86b21c712f6f4e408
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/330440
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41340}
2023-12-08 10:54:42 +00:00
Victor Boivie
9a2e32b9f2 dcsctp: Rename outstanding bytes to unacked bytes
And the same for outstanding items, which become unacked items. The old
names were unfortunate - especially since they were managed by a class
called OutstandingData.

To make this less complicated, these variables have been renamed to
something that is easier to understand; "Unacked bytes/items". Simply
what has been sent but hasn't been acked or nacked yet. So likely what's
in-flight, but could possibly be lost and not found to be lost yet.

Bug: None
Change-Id: I877d7f2cac5d164bf2f9f66cb32ae1f6d850ad2c
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/329761
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41313}
2023-12-04 19:10:17 +00:00
Victor Boivie
9abc4865a4 dcsctp: Use std::deque for outstanding_data
A std::map is a fairly inefficient data structure. Accessing an item
is O(log(N)), but as every item is a separate allocation, iterating it
and searching for items is not very kind to the data caches.

As the outstanding data is a contiguous list (no gaps) where you only
append to the end and remove from the front, use a std::deque instead.

Bug: webrtc:15699
Co-authored-by: Daniel Collins <dpcollins@google.com>
Change-Id: I1f5fe97d06204c75b2b9553856af24e50f2ce715
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/329422
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41310}
2023-12-04 15:10:15 +00:00
Victor Boivie
032805068c dcsctp: Calculate next_tsn
Before this CL, the next_tsn was stored as a variable, but that was
not needed as it can be calculated from the higest outstanding TSN. The
next TSN is simply the value after the highest outstanding TSN.

The highest outstanding TSN calculation could be simplified as well,
as the outstanding_data_ is contiguous list of TSNs counted from
last_cumulative_tsn_ack_.

Bug: None
Change-Id: Iafe188683427b5f2959d5ce2b19b5943d4760791
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/329421
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41303}
2023-12-04 10:10:47 +00:00
Victor Boivie
b506d68f2a dcsctp: Remove deprecated delivery checks
With https://webrtc-review.googlesource.com/c/src/+/321603, the
responsibility to not ingest duplicate received chunks was moved from
the reassembly queue to the data tracker. But in that CL, we couldn't
remove updating the internal variables in the reassembly queue, because
those were included in the handover state. Now that time has passed,
we can remove this code altogether as nothing was ever reading from
these variables - only writing to them.

Bug: webrtc:14600
Change-Id: Icf958c75f74974be6cad7cd827cf49b3ab2f5412
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/329300
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41291}
2023-11-30 17:27:52 +00:00
Sergey Silkin
ebc4d3edd5 Move StrJoin to rtc_base/strings
A similar function was defined in rtc_base/openssl_adapter. Moving it from net/dcsctp/common/ to rtc_base/strings/. I'm planning to use StrJoin in a video codec test (a follow-up change).

Bug: webrtc:14852
Change-Id: Ie657c03e7f9fb52c189c127af6f66ec505b512ae
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/327322
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Commit-Queue: Sergey Silkin <ssilkin@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41166}
2023-11-15 12:10:28 +00:00
Victor Boivie
82cbbcc179 dcsctp: Convert use of TimeMs to webrtc::Timestamp
While this is a fairly big CL, it's fairly straightforward. It replaces
uses of TimeMs with webrtc::Timestamp, and additionally does some
cleanup of DurationMs to webrtc::TimeDelta that are now easier to do.

Bug: webrtc:15593
Change-Id: Id0e3edcba0533e0e8df3358b1778b6995c344243
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/326560
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41138}
2023-11-12 21:12:29 +00:00
Victor Boivie
2d43ab8508 dcsctp: Add Now() callback
This callback is identical to TimeMillis, but returns a
webrtc::Timestamp instead of a TimeMs.

When all callers have migrated to Now() (and all dcsctp code),
TimeMillis will be removed.

Bug: webrtc:15593
Change-Id: I608387607537f29989736af5bf98c7f184f52ebc
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/326500
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41127}
2023-11-10 15:23:13 +00:00
Victor Boivie
4397482d71 dcsctp: Convert timers to rtc::TimeDelta
With this, the code base should be mostly converted from using
DurationMs to rtc::TimeDelta, and the work can continue to replace
TimeMs with rtc::Timestamp.

Bug: webrtc:15593
Change-Id: I083fee6eccb173efc0232bb8d46e2554a5fbee5b
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/326161
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41101}
2023-11-07 21:42:15 +00:00
Victor Boivie
be04c98d64 dcsctp: Migrate non-Timer related to rtc::TimeDelta
This does the bulk of the remaining refactoring, except timers since
they are an even bigger part - but more isolated.

Bug: webrtc:15593
Change-Id: I7afa349e2119be7592797ee6b3b198e6de4f697a
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/326160
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41090}
2023-11-06 19:55:22 +00:00
Victor Boivie
37f5172f6e dcsctp: Use TimeDelta in RetransmissionTimeout
It's still doing the calculations in milliseconds, which will be updated
in follow-up CLs.

Bug: webrtc:15593
Change-Id: I7fb93d4687d58f409db182db40db720d82feb3dd
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325524
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41074}
2023-11-03 11:56:18 +00:00
Harald Alvestrand
78f905e5cc Move some users to use webrtc::RefCountInterface
Bug: webrtc:15622
Change-Id: I2d4c20c726af1a052e161b7689a73d1e5e3eb191
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325526
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Commit-Queue: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41067}
2023-11-02 14:45:57 +00:00
Victor Boivie
b78e6a9305 dcsctp: Use TimeDelta in TX path
This commit replaces the internal use of DurationMs, with millisecond
precision, to webrtc::TimeDelta, which uses microsecond precision.

This is just a refactoring. The only change to the public API is
convenience methods to convert between DurationMs and webrtc::TimeDelta.

Bug: webrtc:15593
Change-Id: Ida861bf585c716be5f898d0e7ef98da2c15268b7
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325402
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41062}
2023-11-01 16:17:13 +00:00
Victor Boivie
51b93a5417 dcsctp: Simplify interface for unchanged timeout
When a timer expires, it can optionally return a new expiration value.
Clearly, that value can't be zero, as that would make it expire
immediately again.

To simplify the interface, and make it easier to migrate to
rtc::TimeDelta, change it from an optional value to an always-present
value that - if zero - means that the expiration time should be
unchanged.

This is just an internal refactoring, and not part of any external
interface.

Bug: webrtc:15593
Change-Id: I6e7010d2dbe774ccb260e14fd6b9861c319e2411
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325281
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41045}
2023-10-31 09:44:39 +00:00
Victor Boivie
f3e9db9e17 dcsctp: Use InfiniteDuration for no max duration
Before this change, a timer could have an optional max duration. Either
that value was present, and that limited the max duration of the timer,
or it was absl::nullopt, which represented "no limit".

To simplify the interface, this CL makes that value "not optional" by
having it always present. The previous "no limit" is now represented by
DurationMs::InfiniteDuration.

This is just a refactoring of internal interfaces - public interfaces
are left untouched.

Bug: webrtc:15593
Change-Id: I80df1d9b2f4d208411ce6cb5045db0a57865e3b4
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325280
Reviewed-by: Florent Castelli <orphis@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#41040}
2023-10-30 13:43:07 +00:00
Victor Boivie
b847a43488 dcsctp: Reset synchronously with incoming request
When a sender has requested a stream to be reset, and the last sender
assigned TSN hasn't been received yet, the receiver will enter deferred
reset mode, where it will store any data chunks received after that
given TSN, and replay those later, when the stream has been reset.

Before this CL, leaving deferred mode was done as soon as the sender's
last assigned TSN was received. That's actually not how the RFC
describes the process[1], but was done that way to properly handle some
sequences of RE-CONFIG and FORWARD-TSN. But after having read the RFCs
again, and realizing that whenever RFC6525 mention "any data arriving",
this also applies to any FORWARD-TSN[2] - it's better to reset streams
synchronously with the incoming requests, and defer not just DATA past
the sender last assigned TSN, but also any FORWARD-TSN after that TSN.

This mostly simplifies the code and is mostly a refactoring, but most
importantly aligns it with how the resetting procedure is explained in
the RFC. It also fixes two bugs:

 * It defers FORWARD-TSN *as well as* DATA chunks with a TSN later
   than the sender's last assigned TSN - see test case. The old
   implementation tried to handle that by exiting the deferred reset
   processing as soon as it reached the sender's last assigned TSN, but
   it didn't manage to do that in all cases.
 * It only defers DATA chunks for streams that are to be reset, not
   all DATA chunks with a TSN > sender's last assigned TSN. This was
   missed in the old implementation, but as it's now implemented
   strictly according to the RFC, this was now done.

[1] https://datatracker.ietf.org/doc/html/rfc6525#section-5.2.2
[2] RFC6525 cover stream resetting, and RFC3758 cover FORWARD-TSN, and
    the combination of these is not covered in the RFCs.

Bug: webrtc:14600
Change-Id: Ief878b755291b9c923aa6fb4317b0f5c00231df4
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/322623
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#40889}
2023-10-09 09:47:57 +00:00
Victor Boivie
9cf825ded9 dcsctp: Abandon correct message on stream reset
Before this CL, a message was identified by the triple (stream_id,
is_unordered, MID) (and yes, the MID is always present in the send
queue, even when interleaved message is not enabled.). So when a chunk
was abandoned due to e.g. having reached the retransmission limit, all
other chunks for that message in the retransmission queue, and all
unsent chunks in the send queue were discarded as well.

This works well, except for the fact that resetting a stream will result
in the MID being set to zero again, which can result in two different
messages having the same identifying triple. And due to the
implementation, both messages would get abandoned.

In WebRTC, an entire data channels is either reliable or unreliable, and
for a message to be abandoned, the channel must be unreliable. So this
means that in the case of stream resets - meaning that a channel was
closed and then reopened, an abandoned message from the old (now closed)
channel would result in abandoning another message sent on the re-opened
data channel.

This CL introduces a new internal property on messages while in the
retransmission and send queue; The "outgoing message id". It's a
monotonically increasing identifier - shared among all streams - that is
never reset to zero in the event of a stream reset. And now a message is
actually only identified by the outgoing message id, but often used
together with the stream identifier, as all data in the send queue is
partitioned by stream. This identifier is 32 bits wide, allowing at most
four billion messages to be in-flight, which is not a limitation, as the
TSN is also 32 bits wide.

Bug: webrtc:14600
Change-Id: I33c23fb0e4bde95327b15d1999e76aa43f5fa7db
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/322603
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#40881}
2023-10-06 10:48:33 +00:00
Victor Boivie
ee0270b67c dcsctp: Rename message_id to mid
MID is a RFC8260 property on an I-DATA chunk, replacing the SSN property
on the DATA chunk in non-interleaved message. The MID stands for
"Message Identifier", and it was frequently named "message_id" in the
source code, but sometimes "mid". To be consistent and using the same
terminology as is most common in the RFC, use "mid" everywhere.

This was triggered by the need to introduce yet another "message
identifier" - but for now, this is just a refacotring CL.

Bug: None
Change-Id: I9cca898d9f3a2f162d6f2e4508ec1b4bc8d7308f
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/322500
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#40876}
2023-10-05 18:48:21 +00:00
Victor Boivie
a55746808e dcsctp: Only process meaningful FORWARD-TSN
Similar to change I602a8552a9a4c853684fcf105309ec3d8073f2c2, which
ensured that only new DATA chunks would be processed by the reassembly
queue by utilizing the data tracker, the same is done for FORWARD-TSN
chunks.

By having the data tracker gate keeping what is provided to the
reassembly queue, the reassembly queue can be simplified as well, which
is an added bonus, by removing last_assembled_tsn_watermark_ and
reassembled_messages_ as those were protecting the queue from
re-delivering messages it had already delivered, but as now the data
tracker would ensure that it wouldn't re-process DATA/FORWARD-TSNs, that
would have the same effect. In this CL, we will still update those
variables and save to the handover state, but not actually read from
them, and then when this change has been rolled out on the servers, I
can remove the variables as well.

The core change is to move validation from ReassemblyQueue::Handle
to DataTracker::HandleForwardTsn.

Some tests have been moved/replicated into data_tracker_test.cc to
ensure that it catches the issues that the reassembly queue did earlier.

Bug: webrtc:14600
Change-Id: I75c1d5911185d594f73c8b1e6bcf776e88f5b7c7
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/321603
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#40856}
2023-10-02 16:05:11 +00:00
Victor Boivie
a93f581705 dcsctp: Don't generate FORWARD-TSN across stream resets
This was a fun bug which proved to be challenging to find a good
solution for. The issue comes from the combination of partial
reliability and stream resetting, which are covered in different RFCs,
and where they don't refer to each other...

Stream resetting (RFC 6525) is used in WebRTC for closing a Data
Channel, and is done by signaling to the receiver that the stream
sequence number (SSN) should be set to zero (0) at some time. Partial
reliability (RFC 3758) - and expiring messages that will not be
retransmitted - is done by signaling that the SSN should be set to a
certain value at a certain TSN, as the messages up until the provided
SSN are not to be expected to be sent again.

As these two functionalities both work by signaling to the receiver
what the next expected SSN should be, they need to do it correctly not
to overwrite each others' intent. And here was the bug. An example
scenario where this caused issues, where we are Z (the receiver),
getting packets from the sender (A):

 5  A->Z          DATA (TSN=30, B, SID=2, SSN=0)
 6          Z->A  SACK (Ack=30)
 7  A->Z          DATA (TSN=31, E, SID=2, SSN=0)
 8  A->Z          RE_CONFIG (REQ=30, TSN=31, SID=2)
 9          Z->A  RE_CONFIG (RESP=30, Performed)
10          Z->A  SACK (Ack=31)
11  A->Z          DATA (TSN=32, SID=1)
12  A->Z          FORWARD_TSN (TSN=32, SID=2, SSN=0)

Let's assume that the path Z->A had packet loss and A never really
received our responses (#6, #9, #10) in time.

At #5, Z receives a DATA fragment, which it acks, and at #7 the end of
that message. The stream is then reset (#8) which it signals that it
was performed (#9) and acked (#10), and data on another stream (2) was
received (#11). Since A hasn't received any ACKS yet, and those chunks
on SID=2 all expired, A sends a FORWARD-TSN saying that "Skip to TSN=32,
and don't expect SID=2, SSN=0". That makes the receiver expect the SSN
on SID=2 to be SSN=1 next time at TSN=32.

But that's not good at all - A reset the stream at #8 and will want to
send the next message on SID=2 using SSN=0 - not 1. The FORWARD-TSN
clearly can't have a TSN that is beyond the stream reset TSN for that
stream.

This is just one example - combining stream resetting and partial
reliability, together with a lossy network, and different variants of
this can occur, which results in the receiver possibly not delivering
packets because it expects a different SSN than the one the sender is
later using.

So this CL adds "breakpoints" to how far a FORWARD-TSN can stretch. It
will simply not cross any Stream Reset last assigned TSNs, and only when
a receiver has acked that all TSNs up till the Stream Reset last
assigned TSN has been received, it will proceed expiring chunks after
that.

Bug: webrtc:14600
Change-Id: Ibae8c9308f5dfe8d734377d42cce653e69e95731
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/321600
Commit-Queue: Victor Boivie <boivie@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#40829}
2023-09-28 11:31:02 +00:00