// SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>// SPDX-License-Identifier: MITpackage recordlayerimport ()// DTLS fixed size record layer header when Connection IDs are not in-use.// ---------------------------------// | Type | Version | Epoch |// ---------------------------------// | Epoch | Sequence Number |// ---------------------------------// | Sequence Number | Length |// ---------------------------------// | Length | Fragment... |// ---------------------------------// fixedHeaderLenIdx is the index at which the record layer content length is// specified in a fixed length header (i.e. one that does not include a// Connection ID).const fixedHeaderLenIdx = 11// RecordLayer which handles all data transport.// The record layer is assumed to sit directly on top of some// reliable transport such as TCP. The record layer can carry four types of content://// 1. Handshake messages—used for algorithm negotiation and key establishment.// 2. ChangeCipherSpec messages—really part of the handshake but technically a separate kind of message.// 3. Alert messages—used to signal that errors have occurred// 4. Application layer data//// The DTLS record layer is extremely similar to that of TLS 1.1. The// only change is the inclusion of an explicit sequence number in the// record. This sequence number allows the recipient to correctly// verify the TLS MAC.//// https://tools.ietf.org/html/rfc4347#section-4.1typeRecordLayerstruct { Header Header Content protocol.Content}// Marshal encodes the RecordLayer to binary.func ( *RecordLayer) () ([]byte, error) { , := .Content.Marshal()if != nil {returnnil, } .Header.ContentLen = uint16(len()) //nolint:gosec // G115 .Header.ContentType = .Content.ContentType() , := .Header.Marshal()if != nil {returnnil, }returnappend(, ...), nil}// Unmarshal populates the RecordLayer from binary.func ( *RecordLayer) ( []byte) error {if := .Header.Unmarshal(); != nil {return }switch .Header.ContentType {caseprotocol.ContentTypeChangeCipherSpec: .Content = &protocol.ChangeCipherSpec{}caseprotocol.ContentTypeAlert: .Content = &alert.Alert{}caseprotocol.ContentTypeHandshake: .Content = &handshake.Handshake{}caseprotocol.ContentTypeApplicationData: .Content = &protocol.ApplicationData{}default:returnerrInvalidContentType }return .Content.Unmarshal([.Header.Size()+len(.Header.ConnectionID):])}// UnpackDatagram extracts all RecordLayer messages from a single datagram.// Note that as with TLS, multiple handshake messages may be placed in// the same DTLS record, provided that there is room and that they are// part of the same flight. Thus, there are two acceptable ways to pack// two DTLS messages into the same datagram: in the same record or in// separate records.// https://tools.ietf.org/html/rfc6347#section-4.2.3func ( []byte) ([][]byte, error) { := [][]byte{}for := 0; len() != ; {iflen()- <= FixedHeaderSize {returnnil, ErrInvalidPacketLength } := (FixedHeaderSize + int(binary.BigEndian.Uint16([+11:])))if + > len() {returnnil, ErrInvalidPacketLength } = append(, [:+]) += }return , nil}// ContentAwareUnpackDatagram is the same as UnpackDatagram but considers the// presence of a connection identifier if the record is of content type// tls12_cid.func ( []byte, int) ([][]byte, error) { := [][]byte{}for := 0; len() != ; { := FixedHeaderSize := fixedHeaderLenIdxifprotocol.ContentType([]) == protocol.ContentTypeConnectionID { += += }iflen()- <= {returnnil, ErrInvalidPacketLength } := ( + int(binary.BigEndian.Uint16([+:])))if + > len() {returnnil, ErrInvalidPacketLength } = append(, [:+]) += }return , nil}
The pages are generated with Goldsv0.8.2. (GOOS=linux GOARCH=amd64)
Golds is a Go 101 project developed by Tapir Liu.
PR and bug reports are welcome and can be submitted to the issue list.
Please follow @zigo_101 (reachable from the left QR code) to get the latest news of Golds.