Test that DTLS 1.2 rejects renegotiation We do not support renegotiation in DTLS at all. This falls out of us generically rejecting all unexpected handshake records after the handshake, but test this more explicitly. DTLS 1.2 renegotiation is particularly weird because they reset the message sequence number, which actually makes message reassembly ambiguous! One cannot *just* use the sequence number state to distinguish between retransmit of a past message and a new message. We currently assume fragments are renegotiation attempts by default, and special-case Finished as a retransmit. If we were went the other way[*], we should have a test that covers the new messages. [*] Going the other way may be a little tidier if we want to implement crbug.com/383016430. We also currently would break if we ever enabled NPN or Channel ID in DTLS. Change-Id: I9f304d0f7ea356fb67e63e22ee06d1ed0fcaa804 Reviewed-on: https://boringssl-review.googlesource.com/c/boringssl/+/86987 Commit-Queue: Lily Chen <chlily@google.com> Reviewed-by: Lily Chen <chlily@google.com> Auto-Submit: David Benjamin <davidben@google.com>
diff --git a/ssl/test/runner/conn.go b/ssl/test/runner/conn.go index d9a1051..6f11a56 100644 --- a/ssl/test/runner/conn.go +++ b/ssl/test/runner/conn.go
@@ -1741,6 +1741,16 @@ } func (c *Conn) Renegotiate() error { + if c.vers >= VersionTLS13 { + return errors.New("tls: renegotiation requires (D)TLS 1.2 or earlier") + } + + // In DTLS, renegotiation resets the message sequence numbers. + if c.isDTLS { + c.sendHandshakeSeq = 0 + c.recvHandshakeSeq = 0 + } + if !c.isClient { helloReq := new(helloRequestMsg).marshal() if c.config.Bugs.BadHelloRequest != nil {
diff --git a/ssl/test/runner/renegotiation_tests.go b/ssl/test/runner/renegotiation_tests.go index 02dbc19..a0fd152 100644 --- a/ssl/test/runner/renegotiation_tests.go +++ b/ssl/test/runner/renegotiation_tests.go
@@ -543,4 +543,33 @@ "-expect-verify-result", }, }) + + // We do not support renegotiation in DTLS, even if enabled. Currently, + // BoringSSL treats this as an unexpected record. + testCases = append(testCases, testCase{ + protocol: dtls, + testType: clientTest, + name: "Renegotiate-DTLS-Client-Forbidden", + config: Config{ + MaxVersion: VersionTLS12, + }, + renegotiate: 1, + flags: []string{"-renegotiate-freely"}, + shouldFail: true, + expectedError: ":UNEXPECTED_RECORD:", + expectedLocalError: "remote error: unexpected message", + }) + testCases = append(testCases, testCase{ + protocol: dtls, + testType: serverTest, + name: "Renegotiate-DTLS-Server-Forbidden", + config: Config{ + MaxVersion: VersionTLS12, + }, + renegotiate: 1, + flags: []string{"-renegotiate-freely"}, + shouldFail: true, + expectedError: ":UNEXPECTED_RECORD:", + expectedLocalError: "remote error: unexpected message", + }) }