Subject: [tsvwg] Re: DTLS in SCTP: my concern and proposal
From: [email-masked]
To: Claudio Porfiri <claudio.porfiri=[email-masked]>
Cc: tsvwg <[email-masked]>
Date: Tue, 18 Mar 2025 09:22:08 +0100
List-Id: Transport Area Working Group <tsvwg.ietf.org>

> On 17. Mar 2025, at 14:18, Claudio Porfiri <claudio.porfiri=[email-masked]> wrote:
> 
> Dear all, Michael,
> Even though I think that you depicted pretty well a possible adoption of DTLS in SCTP,
> the original intent for DTLS in SCTP was to protect all SCTP traffic including Control-Chunks, in my
Hi Claudio,

I am just describing the solution specified in
https://datatracker.ietf.org/doc/draft-westerlund-tsvwg-sctp-dtls-chunk/
in a different way. But it is a the same solution.
> opinion this makes an even harder challenge for keeping the Record Protection Operator
> and Chunk Protection Operator aligned.
Not sure what you are saying here.
Conceptually, the proposal in the ID above uses a record protection operator and
a chunk protection operator, which has identical state and identical code.
Do we agree on this?
> That intent will also challenge your proposal, I don't see an easy solution using two separate
> Instantiation of DTLS.
There are is only a singe instance of DTLS. It is just split. The record layer
is handled in the kernel, all the rest is done in userland.
My proposal then comes down to using different keys and different replay protection arrays
for both protection operators.
> 
> May you consider a different architecture, where all the DTLS work is done in a User-space sidecar
> working as helper function and interfacing DTLS library? That would be a proof-of-concept
> as long as no better alternative exist.
Unfortunately, I don't get, what you are suggesting. Can you elaborate?
Are you suggesting to avoid doing the record layer in the kernel? Why?
This is already done for kernel TLS.

Best regards
Michael
> 
> Best regards,
> Claudio.
> 
> -----Original Message-----
> From: [email-masked] <[email-masked]>
> Sent: Sunday, March 16, 2025 8:04 AM
> To: tsvwg <[email-masked]>
> Subject: [tsvwg] DTLS in SCTP: my concern and proposal
> 
> Dear all,
> 
> This email was originally sent to the members of the former design team.
> It was suggested to send it also the TSVWG mailing list.
> I covers only technical aspects.
> 
> You all know that we had three alternate solutions. Last IETF there was the
> consensus to go for a fourth solution, which is a compromise.
> Part of the compromise was that we do the protection at the packet
> level, not at the payload level.
> So the starting point of a discussing was
> https://datatracker.ietf.org/doc/draft-westerlund-tsvwg-sctp-dtls-chunk/
> 
> I suggested some modifications, but they seem to be unacceptable to the
> authors of the ID. So I am seeking out to you all for further input for
> this discussion, since there is an agreement that we need to move forward.
> 
> Here is a figure describing the architecture, which I'll use in this email.
> 
>  +---------------+ +------------------------------+
>  |      ULP      | |           DTLS 1.3           |
>  |               | |   +---------------------+    |
>  |               | | +-+    Key Management   +--+ |
>  |               | | | +---------------------+  | |
>  |               | | |     +---+ +---+          | |
>  |               | | |     | H | |   |          | |
>  |               | | |     | a | |   |          | |
>  |               | | | k   | n | | A |        k | |
>  |               | | | e   | d | | l |        e | |
>  |               | | | y   | s | | e |   ...  y | |
>  |               | | | s   | h | | r |        s | |
>  |               | | |     | a | | t |          | |
>  |               | | |     | k | |   |          | |
>  |               | | |     | e | |   |          | |
>  |               | | |     +-+-+ +-+-+          | |
>  |               | | |       |     |            | |
>  |               | | |       +-----+---...      | |
>  |               | | | ContentType |            | |
>  |               | | |  +----------+----------+ | |
>  |               | | +->|        Record       | | |
>  |               | |    | Protection Operator | | |
>  +               | |    +----------+----------+ | |
>  +-------+-------+ +----------------------------+-+
>          |                          |           |
>          +--+-----------------------+           | keys
>        PPID |                                   V
>  +----------------------------------------------+-+
>  |                    +---------------------+   | |
>  |        SCTP        |         Chunk       |<--+ |
>  |                    | Protection Operator |     |
>  |                    +---------------------+     |
>  +------------------------------------------------+
> 
> The figure is not perfect and it does intentionally not show
> kernel/userland boundaries.
> 
> The Record Protection Operator transform an DTLSInnerPlaintext, which
> contains a message (handshake, alert, ...) and a ContentType and
> computes the DTLSCiphertext, which contains the unified_hdr and
> the encrypted_record and vice versa.
> 
> The Chunk Protection Operator transforms an DTLSInnerPlaintext, which
> contains a message (list of SCTP chunks) and uses application_data
> as the ContentType and computes the DTLSCiphertext, which contains
> the unified_hdr and the encrypted_record and vice versa.
> The DTLSCiphertext is the chunk value of the DTLS chunk.
> 
> From a functional point of view, the Record Protection Operator and
> the Record Protection Operator are very similar. Both also provide
> replay protection.
> 
> The proposal from Ericsson is that the Record Protection Operator and
> the Record Protection Operator are identical. This means they share
> the same code and the same state.
> Since sharing the state is hard, a solution is to have only one
> protection layer which does both. This is simple to implement,
> if SCTP and DTLS are both implemented in user space or kernel space.
> However, doing full DTLS in kernel space is not acceptable for FreeBSD
> or Linux kernel developers at the moment.
> But this is not necessary. For a kernel SCTP implementation using the
> socket APU one can do the following:
> 
>  +---------------+ +------------------------------+
>  |      ULP      | |           DTLS 1.3           |
>  |               | |   +---------------------+    |
>  |               | |   +    Key Management   +--+ |
>  |               | |   +---------------------+  | |
>  |               | |       +---+ +---+          | |
>  |               | |       | H | |   |          | |
>  |               | |       | a | |   |          | |
>  |               | |       | n | | A |        k | |
>  |               | |       | d | | l |        e | |
>  |               | |       | s | | e |   ...  y | |
>  |               | |       | h | | r |        s | |
>  |               | |       | a | | t |          | |
>  |               | |       | k | |   |          | |
>  |               | |       | e | |   |          | |
>  |               | |       +-+-+ +-+-+          | |
>  |               | |         |     |            | |
>  |               | |         +-----+---...      | |
>  |               | |               |            | |
>  +-------+-------+ +----------------------------+-+
>          |                         |            |
>          +--+----------------------+            | keys
>        cmsg |        cmsg_data=ContentType      V
>  +----------------------------------------------+-+
>  |                    +---------------------+   | |
>  |        SCTP        |    Chunk/Record     |<--+ |
>  |                    | Protection Operator |     |
>  |                    +---------------------+     |
>  +------------------------------------------------+
> 
> So when the DTLS stack sends a message needing to be protected,
> it calls sendmsg() with the message (handshake, alert, ...) and
> a cmsg providing the ContentType. Then the kernel know that
> the Record Protection Operator should be applied to the message
> before putting it into the send buffer.
> If packet level protection is enabled, the SCTP stack will use
> the Chunk Protection Operator to construct the DTLS chunk just
> before sending the SCTP packet.
> 
> If a packet is received and contains a DTLS chunk, the Chunk
> Protection Operator will decrypt the chunks and performs the
> replay protection.
> When a user message is put into the receive buffer, the PPID
> is inspected to figure out, if the Record Protection Operator
> needs to be applied. If that is the case, the content type
> will be provided as a cmsg.
> 
> So the proposal of Ericsson an be implemented also for SCTP kernel
> stacks.
> What is needed is:
> * a DTLS implementation which provides the DTLSInnerPlaintext.
> This looks similar to what TLS implementation might do for QUIC,
> but this time it is DTLS, not TLS.
> * an implementation of the DTLS record layer in the kernel
> I think we all agree up to here. If not, please let me know.
> 
> Here is my concern:
> 
> In my view, Record Protection Operator and Chunk Protection Operator
> are conceptually different things. I agree that they are functionally
> very similar. In particular I would have no problem is using the same
> code. But sharing the state between these two operators it what concerns
> me. I have fixed a couple of security issues where sharing the state
> between unrelated/independent functions was the root cause.
> Let me illustrate this by an example.
> Since DTLS messages are transmitted via SCTP reliably, it makes no
> sense to me to retransmit them at the DTLS layer.
> If both protection operators share the same state, they perform the
> replay protection the same data (most likely an array and the sequence
> number of the left edge). Let us assume the replay window is W.
> Now the sender sends a key_update and uses sequence number S.
> Assume this SCTP packet containing this message is lost.
> If the SCTP sender sends a lot more packets and they all
> arrive at the receiver and the retransmission is W packets later,
> the Chunk Protection Operator will process the packet successfully,
> but the Record Protection Operator will drop the valid packet.
> This should not happen.
> This is an example, and we can fix it. But it keeps the door open for
> attacks/problems related to this state sharing (including side channel
> attacks).
> 
> Here is my proposal:
> 
>  +---------------+ +------------------------------+
>  |      ULP      | |           DTLS 1.3           |
>  |               | |   +---------------------+    |
>  |               | | +>+    Key Exporter     +--+ |
>  |               | | | +---------------------+  | |
>  |               | | | +---------------------+  | |
>  |               | | +-+    Key Management   +  | |
>  |               | | | +---------------------+  | |
>  |               | | |     +---+ +---+          | |
>  |               | | |     | H | |   |          | |
>  |               | | |     | a | |   |          | |
>  |               | | | k   | n | | A |        k | |
>  |               | | | e   | d | | l |        e | |
>  |               | | | y   | s | | e |   ...  y | |
>  |               | | | s   | h | | r |        s | |
>  |               | | |     | a | | t |          | |
>  |               | | |     | k | |   |          | |
>  |               | | |     | e | |   |          | |
>  |               | | |     +-+-+ +-+-+          | |
>  |               | | |       |     |            | |
>  |               | | |       +-----+---...      | |
>  |               | | | ContentType |            | |
>  |               | | |  +----------+----------+ | |
>  |               | | +->|        Record       | | |
>  |               | |    | Protection Operator | | |
>  +               | |    +----------+----------+ | |
>  +-------+-------+ +----------------------------+-+
>          |                          |           |
>          +--+-----------------------+           | keys
>        PPID |                                   V
>  +----------------------------------------------+-+
>  |                    +---------------------+   | |
>  |        SCTP        |         Chunk       |<--+ |
>  |                    | Protection Operator |     |
>  |                    +---------------------+     |
>  +------------------------------------------------+
> 
> Let the Chunk Protection Operator use keys from the Key Exporter
> and its own replay protection (its own sequence number and array).
> 
> As the solution above, an implementation of the DTLS record layer
> is needed in the SCTP stack.
> However, the DTLS stack does not need any modifications. One could
> even use a TLS 1.3 implementation, since SCTP can provide a reliable
> in-sequence transmission.
> This solution also avoids that the SCTP stack looks into the PPID,
> which is needed by the first solution. The SCTP stack is not intended
> to look into the SCTP stack.
> 
> I have also two comments about the DTLS chunk:
> 1. I am not sure we need more than one DTLS connection in general.
>  I do understand that the key management proposed by Ericsson needs
>  it. So the R and DCI bits might be specified in that ID.
>  But this depends how we specify (multiple versions of) key management
> 2. I think we can optimize the chunk layout:
>  One could use the chunk flags to encode the flags needed for the unified_hdr.
>  I think there is not use for the length field in the unified_hdr, so the L
>  bit can go away. We could make the sequence number part of the chunk value
>  with a fixed size. So the S bit can go away. Not sure, if the Connection ID
>  is really needed.
> But the first one is something to move around in specifications, the second
> one is an optimization.
> 
> It would be great, if you can share any opinions or suggestions or questions.
> If there are other people you know that can provide input in the discussion,
> please forward the mail to them.
> 
> Best regards
> Michael
> 
> 
> 
> 
> 
>