github.com/devops-filetransfer/sshego@v7.0.4+incompatible/_vendor/golang.org/x/crypto/cryptobyte/string.go (about)

     1  // Copyright 2017 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  // Package cryptobyte implements building and parsing of byte strings for
     6  // DER-encoded ASN.1 and TLS messages. See the examples for the Builder and
     7  // String types to get started.
     8  package cryptobyte // import "golang.org/x/crypto/cryptobyte"
     9  
    10  // String represents a string of bytes. It provides methods for parsing
    11  // fixed-length and length-prefixed values from it.
    12  type String []byte
    13  
    14  // read advances a String by n bytes and returns them. If less than n bytes
    15  // remain, it returns nil.
    16  func (s *String) read(n int) []byte {
    17  	if len(*s) < n {
    18  		return nil
    19  	}
    20  	v := (*s)[:n]
    21  	*s = (*s)[n:]
    22  	return v
    23  }
    24  
    25  // Skip advances the String by n byte and reports whether it was successful.
    26  func (s *String) Skip(n int) bool {
    27  	return s.read(n) != nil
    28  }
    29  
    30  // ReadUint8 decodes an 8-bit value into out and advances over it. It
    31  // returns true on success and false on error.
    32  func (s *String) ReadUint8(out *uint8) bool {
    33  	v := s.read(1)
    34  	if v == nil {
    35  		return false
    36  	}
    37  	*out = uint8(v[0])
    38  	return true
    39  }
    40  
    41  // ReadUint16 decodes a big-endian, 16-bit value into out and advances over it.
    42  // It returns true on success and false on error.
    43  func (s *String) ReadUint16(out *uint16) bool {
    44  	v := s.read(2)
    45  	if v == nil {
    46  		return false
    47  	}
    48  	*out = uint16(v[0])<<8 | uint16(v[1])
    49  	return true
    50  }
    51  
    52  // ReadUint24 decodes a big-endian, 24-bit value into out and advances over it.
    53  // It returns true on success and false on error.
    54  func (s *String) ReadUint24(out *uint32) bool {
    55  	v := s.read(3)
    56  	if v == nil {
    57  		return false
    58  	}
    59  	*out = uint32(v[0])<<16 | uint32(v[1])<<8 | uint32(v[2])
    60  	return true
    61  }
    62  
    63  // ReadUint32 decodes a big-endian, 32-bit value into out and advances over it.
    64  // It returns true on success and false on error.
    65  func (s *String) ReadUint32(out *uint32) bool {
    66  	v := s.read(4)
    67  	if v == nil {
    68  		return false
    69  	}
    70  	*out = uint32(v[0])<<24 | uint32(v[1])<<16 | uint32(v[2])<<8 | uint32(v[3])
    71  	return true
    72  }
    73  
    74  func (s *String) readUnsigned(out *uint32, length int) bool {
    75  	v := s.read(length)
    76  	if v == nil {
    77  		return false
    78  	}
    79  	var result uint32
    80  	for i := 0; i < length; i++ {
    81  		result <<= 8
    82  		result |= uint32(v[i])
    83  	}
    84  	*out = result
    85  	return true
    86  }
    87  
    88  func (s *String) readLengthPrefixed(lenLen int, outChild *String) bool {
    89  	lenBytes := s.read(lenLen)
    90  	if lenBytes == nil {
    91  		return false
    92  	}
    93  	var length uint32
    94  	for _, b := range lenBytes {
    95  		length = length << 8
    96  		length = length | uint32(b)
    97  	}
    98  	if int(length) < 0 {
    99  		// This currently cannot overflow because we read uint24 at most, but check
   100  		// anyway in case that changes in the future.
   101  		return false
   102  	}
   103  	v := s.read(int(length))
   104  	if v == nil {
   105  		return false
   106  	}
   107  	*outChild = v
   108  	return true
   109  }
   110  
   111  // ReadUint8LengthPrefixed reads the content of an 8-bit length-prefixed value
   112  // into out and advances over it. It returns true on success and false on
   113  // error.
   114  func (s *String) ReadUint8LengthPrefixed(out *String) bool {
   115  	return s.readLengthPrefixed(1, out)
   116  }
   117  
   118  // ReadUint16LengthPrefixed reads the content of a big-endian, 16-bit
   119  // length-prefixed value into out and advances over it. It returns true on
   120  // success and false on error.
   121  func (s *String) ReadUint16LengthPrefixed(out *String) bool {
   122  	return s.readLengthPrefixed(2, out)
   123  }
   124  
   125  // ReadUint24LengthPrefixed reads the content of a big-endian, 24-bit
   126  // length-prefixed value into out and advances over it. It returns true on
   127  // success and false on error.
   128  func (s *String) ReadUint24LengthPrefixed(out *String) bool {
   129  	return s.readLengthPrefixed(3, out)
   130  }
   131  
   132  // ReadBytes reads n bytes into out and advances over them. It returns true on
   133  // success and false and error.
   134  func (s *String) ReadBytes(out *[]byte, n int) bool {
   135  	v := s.read(n)
   136  	if v == nil {
   137  		return false
   138  	}
   139  	*out = v
   140  	return true
   141  }
   142  
   143  // CopyBytes copies len(out) bytes into out and advances over them. It returns
   144  // true on success and false on error.
   145  func (s *String) CopyBytes(out []byte) bool {
   146  	n := len(out)
   147  	v := s.read(n)
   148  	if v == nil {
   149  		return false
   150  	}
   151  	return copy(out, v) == n
   152  }
   153  
   154  // Empty reports whether the string does not contain any bytes.
   155  func (s String) Empty() bool {
   156  	return len(s) == 0
   157  }