github.com/pion/dtls/v2@v2.2.12/pkg/protocol/handshake/message_hello_verify_request.go (about)

     1  // SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
     2  // SPDX-License-Identifier: MIT
     3  
     4  package handshake
     5  
     6  import (
     7  	"github.com/pion/dtls/v2/pkg/protocol"
     8  )
     9  
    10  // MessageHelloVerifyRequest is as follows:
    11  //
    12  //	struct {
    13  //	  ProtocolVersion server_version;
    14  //	  opaque cookie<0..2^8-1>;
    15  //	} HelloVerifyRequest;
    16  //
    17  //	The HelloVerifyRequest message type is hello_verify_request(3).
    18  //
    19  //	When the client sends its ClientHello message to the server, the server
    20  //	MAY respond with a HelloVerifyRequest message.  This message contains
    21  //	a stateless cookie generated using the technique of [PHOTURIS].  The
    22  //	client MUST retransmit the ClientHello with the cookie added.
    23  //
    24  //	https://tools.ietf.org/html/rfc6347#section-4.2.1
    25  type MessageHelloVerifyRequest struct {
    26  	Version protocol.Version
    27  	Cookie  []byte
    28  }
    29  
    30  // Type returns the Handshake Type
    31  func (m MessageHelloVerifyRequest) Type() Type {
    32  	return TypeHelloVerifyRequest
    33  }
    34  
    35  // Marshal encodes the Handshake
    36  func (m *MessageHelloVerifyRequest) Marshal() ([]byte, error) {
    37  	if len(m.Cookie) > 255 {
    38  		return nil, errCookieTooLong
    39  	}
    40  
    41  	out := make([]byte, 3+len(m.Cookie))
    42  	out[0] = m.Version.Major
    43  	out[1] = m.Version.Minor
    44  	out[2] = byte(len(m.Cookie))
    45  	copy(out[3:], m.Cookie)
    46  
    47  	return out, nil
    48  }
    49  
    50  // Unmarshal populates the message from encoded data
    51  func (m *MessageHelloVerifyRequest) Unmarshal(data []byte) error {
    52  	if len(data) < 3 {
    53  		return errBufferTooSmall
    54  	}
    55  	m.Version.Major = data[0]
    56  	m.Version.Minor = data[1]
    57  	cookieLength := int(data[2])
    58  	if len(data) < cookieLength+3 {
    59  		return errBufferTooSmall
    60  	}
    61  	m.Cookie = make([]byte, cookieLength)
    62  
    63  	copy(m.Cookie, data[3:3+cookieLength])
    64  	return nil
    65  }