github.com/Hyperledger-TWGC/tjfoc-gm@v1.4.0/gmtls/gm_handshake_messages.go (about)

     1  // Copyright 2009 The Go Authors. All rights reserved.
     2  // Copyright 2009 The Go Authors. All rights reserved.
     3  // Use of this source code is governed by a BSD-style
     4  // license that can be found in the LICENSE file.
     5  
     6  package gmtls
     7  
     8  import "bytes"
     9  
    10  type certificateRequestMsgGM struct {
    11  	raw []byte
    12  
    13  	certificateTypes             []byte
    14  	certificateAuthorities       [][]byte
    15  }
    16  
    17  func (m *certificateRequestMsgGM) equal(i interface{}) bool {
    18  	m1, ok := i.(*certificateRequestMsgGM)
    19  	if !ok {
    20  		return false
    21  	}
    22  
    23  	return bytes.Equal(m.raw, m1.raw) &&
    24  		bytes.Equal(m.certificateTypes, m1.certificateTypes) &&
    25  		eqByteSlices(m.certificateAuthorities, m1.certificateAuthorities)
    26  }
    27  
    28  func (m *certificateRequestMsgGM) marshal() (x []byte) {
    29  	if m.raw != nil {
    30  		return m.raw
    31  	}
    32  
    33  	// See https://tools.ietf.org/html/rfc4346#section-7.4.4
    34  	length := 1 + len(m.certificateTypes) + 2
    35  	casLength := 0
    36  	for _, ca := range m.certificateAuthorities {
    37  		casLength += 2 + len(ca)
    38  	}
    39  	length += casLength
    40  
    41  	x = make([]byte, 4+length)
    42  	x[0] = typeCertificateRequest
    43  	x[1] = uint8(length >> 16)
    44  	x[2] = uint8(length >> 8)
    45  	x[3] = uint8(length)
    46  
    47  	x[4] = uint8(len(m.certificateTypes))
    48  
    49  	copy(x[5:], m.certificateTypes)
    50  	y := x[5+len(m.certificateTypes):]
    51  
    52  	y[0] = uint8(casLength >> 8)
    53  	y[1] = uint8(casLength)
    54  	y = y[2:]
    55  	for _, ca := range m.certificateAuthorities {
    56  		y[0] = uint8(len(ca) >> 8)
    57  		y[1] = uint8(len(ca))
    58  		y = y[2:]
    59  		copy(y, ca)
    60  		y = y[len(ca):]
    61  	}
    62  
    63  	m.raw = x
    64  	return
    65  }
    66  
    67  func (m *certificateRequestMsgGM) unmarshal(data []byte) bool {
    68  	m.raw = data
    69  
    70  	if len(data) < 5 {
    71  		return false
    72  	}
    73  
    74  	length := uint32(data[1])<<16 | uint32(data[2])<<8 | uint32(data[3])
    75  	if uint32(len(data))-4 != length {
    76  		return false
    77  	}
    78  
    79  	numCertTypes := int(data[4])
    80  	data = data[5:]
    81  	if numCertTypes == 0 || len(data) <= numCertTypes {
    82  		return false
    83  	}
    84  
    85  	m.certificateTypes = make([]byte, numCertTypes)
    86  	if copy(m.certificateTypes, data) != numCertTypes {
    87  		return false
    88  	}
    89  
    90  	data = data[numCertTypes:]
    91  
    92  	if len(data) < 2 {
    93  		return false
    94  	}
    95  	casLength := uint16(data[0])<<8 | uint16(data[1])
    96  	data = data[2:]
    97  	if len(data) < int(casLength) {
    98  		return false
    99  	}
   100  	cas := make([]byte, casLength)
   101  	copy(cas, data)
   102  	data = data[casLength:]
   103  
   104  	m.certificateAuthorities = nil
   105  	for len(cas) > 0 {
   106  		if len(cas) < 2 {
   107  			return false
   108  		}
   109  		caLen := uint16(cas[0])<<8 | uint16(cas[1])
   110  		cas = cas[2:]
   111  
   112  		if len(cas) < int(caLen) {
   113  			return false
   114  		}
   115  
   116  		m.certificateAuthorities = append(m.certificateAuthorities, cas[:caLen])
   117  		cas = cas[caLen:]
   118  	}
   119  
   120  	return len(data) == 0
   121  }
   122