package extension
import "encoding/binary"
type TypeValue uint16
const (
ServerNameTypeValue TypeValue = 0
SupportedEllipticCurvesTypeValue TypeValue = 10
SupportedPointFormatsTypeValue TypeValue = 11
SupportedSignatureAlgorithmsTypeValue TypeValue = 13
UseSRTPTypeValue TypeValue = 14
ALPNTypeValue TypeValue = 16
UseExtendedMasterSecretTypeValue TypeValue = 23
ConnectionIDTypeValue TypeValue = 54
RenegotiationInfoTypeValue TypeValue = 65281
)
type Extension interface {
Marshal () ([]byte , error )
Unmarshal (data []byte ) error
TypeValue () TypeValue
}
func Unmarshal (buf []byte ) ([]Extension , error ) {
switch {
case len (buf ) == 0 :
return []Extension {}, nil
case len (buf ) < 2 :
return nil , errBufferTooSmall
}
declaredLen := binary .BigEndian .Uint16 (buf )
if len (buf )-2 != int (declaredLen ) {
return nil , errLengthMismatch
}
extensions := []Extension {}
unmarshalAndAppend := func (data []byte , e Extension ) error {
err := e .Unmarshal (data )
if err != nil {
return err
}
extensions = append (extensions , e )
return nil
}
for offset := 2 ; offset < len (buf ); {
if len (buf ) < (offset + 2 ) {
return nil , errBufferTooSmall
}
var err error
switch TypeValue (binary .BigEndian .Uint16 (buf [offset :])) {
case ServerNameTypeValue :
err = unmarshalAndAppend (buf [offset :], &ServerName {})
case SupportedEllipticCurvesTypeValue :
err = unmarshalAndAppend (buf [offset :], &SupportedEllipticCurves {})
case SupportedPointFormatsTypeValue :
err = unmarshalAndAppend (buf [offset :], &SupportedPointFormats {})
case SupportedSignatureAlgorithmsTypeValue :
err = unmarshalAndAppend (buf [offset :], &SupportedSignatureAlgorithms {})
case UseSRTPTypeValue :
err = unmarshalAndAppend (buf [offset :], &UseSRTP {})
case ALPNTypeValue :
err = unmarshalAndAppend (buf [offset :], &ALPN {})
case UseExtendedMasterSecretTypeValue :
err = unmarshalAndAppend (buf [offset :], &UseExtendedMasterSecret {})
case RenegotiationInfoTypeValue :
err = unmarshalAndAppend (buf [offset :], &RenegotiationInfo {})
case ConnectionIDTypeValue :
err = unmarshalAndAppend (buf [offset :], &ConnectionID {})
default :
}
if err != nil {
return nil , err
}
if len (buf ) < (offset + 4 ) {
return nil , errBufferTooSmall
}
extensionLength := binary .BigEndian .Uint16 (buf [offset +2 :])
offset += (4 + int (extensionLength ))
}
return extensions , nil
}
func Marshal (e []Extension ) ([]byte , error ) {
extensions := []byte {}
for _ , e := range e {
raw , err := e .Marshal ()
if err != nil {
return nil , err
}
extensions = append (extensions , raw ...)
}
out := []byte {0x00 , 0x00 }
binary .BigEndian .PutUint16 (out , uint16 (len (extensions )))
return append (out , extensions ...), nil
}
The pages are generated with Golds v0.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 .