Source file src/vendor/golang.org/x/net/quic/packet_parser.go

     1  // Copyright 2023 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 quic
     6  
     7  import (
     8  	"golang.org/x/net/internal/quic/quicwire"
     9  )
    10  
    11  // parseLongHeaderPacket parses a QUIC long header packet.
    12  //
    13  // It does not parse Version Negotiation packets.
    14  //
    15  // On input, pkt contains a long header packet (possibly followed by more packets),
    16  // k the decryption keys for the packet, and pnumMax the largest packet number seen
    17  // in the number space of this packet.
    18  //
    19  // parseLongHeaderPacket returns the parsed packet with protection removed
    20  // and its length in bytes.
    21  //
    22  // It returns an empty packet and -1 if the packet could not be parsed.
    23  func parseLongHeaderPacket(pkt []byte, k fixedKeys, pnumMax packetNumber) (p longPacket, n int) {
    24  	if len(pkt) < 5 || !isLongHeader(pkt[0]) {
    25  		return longPacket{}, -1
    26  	}
    27  
    28  	// Header Form (1) = 1,
    29  	// Fixed Bit (1) = 1,
    30  	// Long Packet Type (2),
    31  	// Type-Specific Bits (4),
    32  	b := pkt
    33  	p.ptype = getPacketType(b)
    34  	if p.ptype == packetTypeInvalid {
    35  		return longPacket{}, -1
    36  	}
    37  	b = b[1:]
    38  	// Version (32),
    39  	p.version, n = quicwire.ConsumeUint32(b)
    40  	if n < 0 {
    41  		return longPacket{}, -1
    42  	}
    43  	b = b[n:]
    44  	if p.version == 0 {
    45  		// Version Negotiation packet; not handled here.
    46  		return longPacket{}, -1
    47  	}
    48  
    49  	// Destination Connection ID Length (8),
    50  	// Destination Connection ID (0..160),
    51  	p.dstConnID, n = quicwire.ConsumeUint8Bytes(b)
    52  	if n < 0 || len(p.dstConnID) > maxConnIDLen {
    53  		return longPacket{}, -1
    54  	}
    55  	b = b[n:]
    56  
    57  	// Source Connection ID Length (8),
    58  	// Source Connection ID (0..160),
    59  	p.srcConnID, n = quicwire.ConsumeUint8Bytes(b)
    60  	if n < 0 || len(p.srcConnID) > maxConnIDLen {
    61  		return longPacket{}, -1
    62  	}
    63  	b = b[n:]
    64  
    65  	switch p.ptype {
    66  	case packetTypeInitial:
    67  		// Token Length (i),
    68  		// Token (..),
    69  		p.extra, n = quicwire.ConsumeVarintBytes(b)
    70  		if n < 0 {
    71  			return longPacket{}, -1
    72  		}
    73  		b = b[n:]
    74  	case packetTypeRetry:
    75  		// Retry Token (..),
    76  		// Retry Integrity Tag (128),
    77  		p.extra = b
    78  		return p, len(pkt)
    79  	}
    80  
    81  	// Length (i),
    82  	payLen, n := quicwire.ConsumeVarint(b)
    83  	if n < 0 {
    84  		return longPacket{}, -1
    85  	}
    86  	b = b[n:]
    87  	if uint64(len(b)) < payLen {
    88  		return longPacket{}, -1
    89  	}
    90  
    91  	// Packet Number (8..32),
    92  	// Packet Payload (..),
    93  	pnumOff := len(pkt) - len(b)
    94  	pkt = pkt[:pnumOff+int(payLen)]
    95  
    96  	if k.isSet() {
    97  		var err error
    98  		p.payload, p.num, err = k.unprotect(pkt, pnumOff, pnumMax)
    99  		if err != nil {
   100  			return longPacket{}, -1
   101  		}
   102  	}
   103  	return p, len(pkt)
   104  }
   105  
   106  // skipLongHeaderPacket returns the length of the long header packet at the start of pkt,
   107  // or -1 if the buffer does not contain a valid packet.
   108  func skipLongHeaderPacket(pkt []byte) int {
   109  	// Header byte, 4 bytes of version.
   110  	n := 5
   111  	if len(pkt) <= n {
   112  		return -1
   113  	}
   114  	// Destination connection ID length, destination connection ID.
   115  	n += 1 + int(pkt[n])
   116  	if len(pkt) <= n {
   117  		return -1
   118  	}
   119  	// Source connection ID length, source connection ID.
   120  	n += 1 + int(pkt[n])
   121  	if len(pkt) <= n {
   122  		return -1
   123  	}
   124  	if getPacketType(pkt) == packetTypeInitial {
   125  		// Token length, token.
   126  		_, nn := quicwire.ConsumeVarintBytes(pkt[n:])
   127  		if nn < 0 {
   128  			return -1
   129  		}
   130  		n += nn
   131  	}
   132  	// Length, packet number, payload.
   133  	_, nn := quicwire.ConsumeVarintBytes(pkt[n:])
   134  	if nn < 0 {
   135  		return -1
   136  	}
   137  	n += nn
   138  	if len(pkt) < n {
   139  		return -1
   140  	}
   141  	return n
   142  }
   143  
   144  // parse1RTTPacket parses a QUIC 1-RTT (short header) packet.
   145  //
   146  // On input, pkt contains a short header packet, k the decryption keys for the packet,
   147  // and pnumMax the largest packet number seen in the number space of this packet.
   148  func parse1RTTPacket(pkt []byte, k *updatingKeyPair, dstConnIDLen int, pnumMax packetNumber) (p shortPacket, err error) {
   149  	pay, pnum, err := k.unprotect(pkt, 1+dstConnIDLen, pnumMax)
   150  	if err != nil {
   151  		return shortPacket{}, err
   152  	}
   153  	p.num = pnum
   154  	p.payload = pay
   155  	return p, nil
   156  }
   157  
   158  // Consume functions return n=-1 on conditions which result in FRAME_ENCODING_ERROR,
   159  // which includes both general parse failures and specific violations of frame
   160  // constraints.
   161  
   162  func consumeAckFrame(frame []byte, f func(rangeIndex int, start, end packetNumber)) (largest packetNumber, ackDelay unscaledAckDelay, ecn ecnCounts, n int) {
   163  	b := frame[1:] // type
   164  
   165  	largestAck, n := quicwire.ConsumeVarint(b)
   166  	if n < 0 {
   167  		return 0, 0, ecnCounts{}, -1
   168  	}
   169  	b = b[n:]
   170  
   171  	v, n := quicwire.ConsumeVarintInt64(b)
   172  	if n < 0 {
   173  		return 0, 0, ecnCounts{}, -1
   174  	}
   175  	b = b[n:]
   176  	ackDelay = unscaledAckDelay(v)
   177  
   178  	ackRangeCount, n := quicwire.ConsumeVarint(b)
   179  	if n < 0 {
   180  		return 0, 0, ecnCounts{}, -1
   181  	}
   182  	b = b[n:]
   183  
   184  	rangeMax := packetNumber(largestAck)
   185  	for i := uint64(0); ; i++ {
   186  		rangeLen, n := quicwire.ConsumeVarint(b)
   187  		if n < 0 {
   188  			return 0, 0, ecnCounts{}, -1
   189  		}
   190  		b = b[n:]
   191  		rangeMin := rangeMax - packetNumber(rangeLen)
   192  		if rangeMin < 0 || rangeMin > rangeMax {
   193  			return 0, 0, ecnCounts{}, -1
   194  		}
   195  		f(int(i), rangeMin, rangeMax+1)
   196  
   197  		if i == ackRangeCount {
   198  			break
   199  		}
   200  
   201  		gap, n := quicwire.ConsumeVarint(b)
   202  		if n < 0 {
   203  			return 0, 0, ecnCounts{}, -1
   204  		}
   205  		b = b[n:]
   206  
   207  		rangeMax = rangeMin - packetNumber(gap) - 2
   208  	}
   209  
   210  	if frame[0] != frameTypeAckECN {
   211  		return packetNumber(largestAck), ackDelay, ecnCounts{}, len(frame) - len(b)
   212  	}
   213  
   214  	ect0Count, n := quicwire.ConsumeVarint(b)
   215  	if n < 0 {
   216  		return 0, 0, ecnCounts{}, -1
   217  	}
   218  	b = b[n:]
   219  	ect1Count, n := quicwire.ConsumeVarint(b)
   220  	if n < 0 {
   221  		return 0, 0, ecnCounts{}, -1
   222  	}
   223  	b = b[n:]
   224  	ecnCECount, n := quicwire.ConsumeVarint(b)
   225  	if n < 0 {
   226  		return 0, 0, ecnCounts{}, -1
   227  	}
   228  	b = b[n:]
   229  
   230  	ecn.t0 = int(ect0Count)
   231  	ecn.t1 = int(ect1Count)
   232  	ecn.ce = int(ecnCECount)
   233  
   234  	return packetNumber(largestAck), ackDelay, ecn, len(frame) - len(b)
   235  }
   236  
   237  func consumeResetStreamFrame(b []byte) (id streamID, code uint64, finalSize int64, n int) {
   238  	n = 1
   239  	idInt, nn := quicwire.ConsumeVarint(b[n:])
   240  	if nn < 0 {
   241  		return 0, 0, 0, -1
   242  	}
   243  	n += nn
   244  	code, nn = quicwire.ConsumeVarint(b[n:])
   245  	if nn < 0 {
   246  		return 0, 0, 0, -1
   247  	}
   248  	n += nn
   249  	v, nn := quicwire.ConsumeVarint(b[n:])
   250  	if nn < 0 {
   251  		return 0, 0, 0, -1
   252  	}
   253  	n += nn
   254  	finalSize = int64(v)
   255  	return streamID(idInt), code, finalSize, n
   256  }
   257  
   258  func consumeStopSendingFrame(b []byte) (id streamID, code uint64, n int) {
   259  	n = 1
   260  	idInt, nn := quicwire.ConsumeVarint(b[n:])
   261  	if nn < 0 {
   262  		return 0, 0, -1
   263  	}
   264  	n += nn
   265  	code, nn = quicwire.ConsumeVarint(b[n:])
   266  	if nn < 0 {
   267  		return 0, 0, -1
   268  	}
   269  	n += nn
   270  	return streamID(idInt), code, n
   271  }
   272  
   273  func consumeCryptoFrame(b []byte) (off int64, data []byte, n int) {
   274  	n = 1
   275  	v, nn := quicwire.ConsumeVarint(b[n:])
   276  	if nn < 0 {
   277  		return 0, nil, -1
   278  	}
   279  	off = int64(v)
   280  	n += nn
   281  	data, nn = quicwire.ConsumeVarintBytes(b[n:])
   282  	if nn < 0 {
   283  		return 0, nil, -1
   284  	}
   285  	n += nn
   286  	return off, data, n
   287  }
   288  
   289  func consumeNewTokenFrame(b []byte) (token []byte, n int) {
   290  	n = 1
   291  	data, nn := quicwire.ConsumeVarintBytes(b[n:])
   292  	if nn < 0 {
   293  		return nil, -1
   294  	}
   295  	if len(data) == 0 {
   296  		return nil, -1
   297  	}
   298  	n += nn
   299  	return data, n
   300  }
   301  
   302  func consumeStreamFrame(b []byte) (id streamID, off int64, fin bool, data []byte, n int) {
   303  	fin = (b[0] & 0x01) != 0
   304  	n = 1
   305  	idInt, nn := quicwire.ConsumeVarint(b[n:])
   306  	if nn < 0 {
   307  		return 0, 0, false, nil, -1
   308  	}
   309  	n += nn
   310  	if b[0]&0x04 != 0 {
   311  		v, nn := quicwire.ConsumeVarint(b[n:])
   312  		if nn < 0 {
   313  			return 0, 0, false, nil, -1
   314  		}
   315  		n += nn
   316  		off = int64(v)
   317  	}
   318  	if b[0]&0x02 != 0 {
   319  		data, nn = quicwire.ConsumeVarintBytes(b[n:])
   320  		if nn < 0 {
   321  			return 0, 0, false, nil, -1
   322  		}
   323  		n += nn
   324  	} else {
   325  		data = b[n:]
   326  		n += len(data)
   327  	}
   328  	if off+int64(len(data)) >= 1<<62 {
   329  		return 0, 0, false, nil, -1
   330  	}
   331  	return streamID(idInt), off, fin, data, n
   332  }
   333  
   334  func consumeMaxDataFrame(b []byte) (max int64, n int) {
   335  	n = 1
   336  	v, nn := quicwire.ConsumeVarint(b[n:])
   337  	if nn < 0 {
   338  		return 0, -1
   339  	}
   340  	n += nn
   341  	return int64(v), n
   342  }
   343  
   344  func consumeMaxStreamDataFrame(b []byte) (id streamID, max int64, n int) {
   345  	n = 1
   346  	v, nn := quicwire.ConsumeVarint(b[n:])
   347  	if nn < 0 {
   348  		return 0, 0, -1
   349  	}
   350  	n += nn
   351  	id = streamID(v)
   352  	v, nn = quicwire.ConsumeVarint(b[n:])
   353  	if nn < 0 {
   354  		return 0, 0, -1
   355  	}
   356  	n += nn
   357  	max = int64(v)
   358  	return id, max, n
   359  }
   360  
   361  func consumeMaxStreamsFrame(b []byte) (typ streamType, max int64, n int) {
   362  	switch b[0] {
   363  	case frameTypeMaxStreamsBidi:
   364  		typ = bidiStream
   365  	case frameTypeMaxStreamsUni:
   366  		typ = uniStream
   367  	default:
   368  		return 0, 0, -1
   369  	}
   370  	n = 1
   371  	v, nn := quicwire.ConsumeVarint(b[n:])
   372  	if nn < 0 {
   373  		return 0, 0, -1
   374  	}
   375  	n += nn
   376  	if v > maxStreamsLimit {
   377  		return 0, 0, -1
   378  	}
   379  	return typ, int64(v), n
   380  }
   381  
   382  func consumeStreamDataBlockedFrame(b []byte) (id streamID, max int64, n int) {
   383  	n = 1
   384  	v, nn := quicwire.ConsumeVarint(b[n:])
   385  	if nn < 0 {
   386  		return 0, 0, -1
   387  	}
   388  	n += nn
   389  	id = streamID(v)
   390  	max, nn = quicwire.ConsumeVarintInt64(b[n:])
   391  	if nn < 0 {
   392  		return 0, 0, -1
   393  	}
   394  	n += nn
   395  	return id, max, n
   396  }
   397  
   398  func consumeDataBlockedFrame(b []byte) (max int64, n int) {
   399  	n = 1
   400  	max, nn := quicwire.ConsumeVarintInt64(b[n:])
   401  	if nn < 0 {
   402  		return 0, -1
   403  	}
   404  	n += nn
   405  	return max, n
   406  }
   407  
   408  func consumeStreamsBlockedFrame(b []byte) (typ streamType, max int64, n int) {
   409  	if b[0] == frameTypeStreamsBlockedBidi {
   410  		typ = bidiStream
   411  	} else {
   412  		typ = uniStream
   413  	}
   414  	n = 1
   415  	max, nn := quicwire.ConsumeVarintInt64(b[n:])
   416  	if nn < 0 {
   417  		return 0, 0, -1
   418  	}
   419  	n += nn
   420  	return typ, max, n
   421  }
   422  
   423  func consumeNewConnectionIDFrame(b []byte) (seq, retire int64, connID []byte, resetToken statelessResetToken, n int) {
   424  	n = 1
   425  	var nn int
   426  	seq, nn = quicwire.ConsumeVarintInt64(b[n:])
   427  	if nn < 0 {
   428  		return 0, 0, nil, statelessResetToken{}, -1
   429  	}
   430  	n += nn
   431  	retire, nn = quicwire.ConsumeVarintInt64(b[n:])
   432  	if nn < 0 {
   433  		return 0, 0, nil, statelessResetToken{}, -1
   434  	}
   435  	n += nn
   436  	if seq < retire {
   437  		return 0, 0, nil, statelessResetToken{}, -1
   438  	}
   439  	connID, nn = quicwire.ConsumeVarintBytes(b[n:])
   440  	if nn < 0 {
   441  		return 0, 0, nil, statelessResetToken{}, -1
   442  	}
   443  	if len(connID) < 1 || len(connID) > 20 {
   444  		return 0, 0, nil, statelessResetToken{}, -1
   445  	}
   446  	n += nn
   447  	if len(b[n:]) < len(resetToken) {
   448  		return 0, 0, nil, statelessResetToken{}, -1
   449  	}
   450  	copy(resetToken[:], b[n:])
   451  	n += len(resetToken)
   452  	return seq, retire, connID, resetToken, n
   453  }
   454  
   455  func consumeRetireConnectionIDFrame(b []byte) (seq int64, n int) {
   456  	n = 1
   457  	var nn int
   458  	seq, nn = quicwire.ConsumeVarintInt64(b[n:])
   459  	if nn < 0 {
   460  		return 0, -1
   461  	}
   462  	n += nn
   463  	return seq, n
   464  }
   465  
   466  func consumePathChallengeFrame(b []byte) (data pathChallengeData, n int) {
   467  	n = 1
   468  	nn := copy(data[:], b[n:])
   469  	if nn != len(data) {
   470  		return data, -1
   471  	}
   472  	n += nn
   473  	return data, n
   474  }
   475  
   476  func consumePathResponseFrame(b []byte) (data pathChallengeData, n int) {
   477  	return consumePathChallengeFrame(b) // identical frame format
   478  }
   479  
   480  func consumeConnectionCloseTransportFrame(b []byte) (code transportError, frameType uint64, reason string, n int) {
   481  	n = 1
   482  	var nn int
   483  	var codeInt uint64
   484  	codeInt, nn = quicwire.ConsumeVarint(b[n:])
   485  	if nn < 0 {
   486  		return 0, 0, "", -1
   487  	}
   488  	code = transportError(codeInt)
   489  	n += nn
   490  	frameType, nn = quicwire.ConsumeVarint(b[n:])
   491  	if nn < 0 {
   492  		return 0, 0, "", -1
   493  	}
   494  	n += nn
   495  	reasonb, nn := quicwire.ConsumeVarintBytes(b[n:])
   496  	if nn < 0 {
   497  		return 0, 0, "", -1
   498  	}
   499  	n += nn
   500  	reason = string(reasonb)
   501  	return code, frameType, reason, n
   502  }
   503  
   504  func consumeConnectionCloseApplicationFrame(b []byte) (code uint64, reason string, n int) {
   505  	n = 1
   506  	var nn int
   507  	code, nn = quicwire.ConsumeVarint(b[n:])
   508  	if nn < 0 {
   509  		return 0, "", -1
   510  	}
   511  	n += nn
   512  	reasonb, nn := quicwire.ConsumeVarintBytes(b[n:])
   513  	if nn < 0 {
   514  		return 0, "", -1
   515  	}
   516  	n += nn
   517  	reason = string(reasonb)
   518  	return code, reason, n
   519  }
   520  

View as plain text