1 /* packet-gquic.c
2  * Routines for (Google) Quick UDP Internet Connections dissection
3  * Copyright 2013, Alexis La Goutte <alexis.lagoutte at gmail dot com>
4  *
5  * Wireshark - Network traffic analyzer
6  * By Gerald Combs <gerald@wireshark.org>
7  * Copyright 1998 Gerald Combs
8  *
9  * SPDX-License-Identifier: GPL-2.0-or-later
10  */
11 
12 /*
13 QUIC Wire Layout Specification : https://docs.google.com/document/d/1WJvyZflAO2pq77yOLbp9NsGjC1CHetAXV8I0fQe-B_U/
14 
15 QUIC Crypto : https://docs.google.com/document/d/1g5nIXAIkN_Y-7XJW5K45IblHd_L2f5LTaDUDwvZ5L6g/
16 
17 QUIC source code in Chromium : https://code.google.com/p/chromium/codesearch#chromium/src/net/quic/quic_utils.h&sq=package:chromium
18 
19 */
20 #include "config.h"
21 
22 #include <epan/packet.h>
23 #include <epan/prefs.h>
24 #include <epan/expert.h>
25 #include <epan/conversation.h>
26 #include <epan/dissectors/packet-http2.h>
27 #include <epan/dissectors/packet-quic.h>
28 #include <wsutil/strtoi.h>
29 
30 void proto_register_gquic(void);
31 void proto_reg_handoff_gquic(void);
32 
33 static dissector_handle_t gquic_handle;
34 static dissector_handle_t tls13_handshake_handle;
35 static dissector_handle_t quic_handle;
36 
37 static int proto_gquic = -1;
38 static int hf_gquic_header_form = -1;
39 static int hf_gquic_fixed_bit = -1;
40 static int hf_gquic_long_packet_type = -1;
41 static int hf_gquic_long_reserved = -1;
42 static int hf_gquic_packet_number_length = -1;
43 static int hf_gquic_dcil = -1;
44 static int hf_gquic_scil = -1;
45 static int hf_gquic_puflags = -1;
46 static int hf_gquic_puflags_vrsn = -1;
47 static int hf_gquic_puflags_rst = -1;
48 static int hf_gquic_puflags_dnonce = -1;
49 static int hf_gquic_puflags_cid = -1;
50 static int hf_gquic_puflags_cid_old = -1;
51 static int hf_gquic_puflags_pkn = -1;
52 static int hf_gquic_puflags_mpth = -1;
53 static int hf_gquic_puflags_rsv = -1;
54 static int hf_gquic_cid = -1;
55 static int hf_gquic_version = -1;
56 static int hf_gquic_diversification_nonce = -1;
57 static int hf_gquic_packet_number = -1;
58 static int hf_gquic_prflags = -1;
59 static int hf_gquic_prflags_entropy = -1;
60 static int hf_gquic_prflags_fecg = -1;
61 static int hf_gquic_prflags_fec = -1;
62 static int hf_gquic_prflags_rsv = -1;
63 static int hf_gquic_message_authentication_hash = -1;
64 static int hf_gquic_frame = -1;
65 static int hf_gquic_frame_type = -1;
66 static int hf_gquic_frame_type_padding_length = -1;
67 static int hf_gquic_frame_type_padding = -1;
68 static int hf_gquic_frame_type_rsts_stream_id = -1;
69 static int hf_gquic_frame_type_rsts_byte_offset = -1;
70 static int hf_gquic_frame_type_rsts_error_code = -1;
71 static int hf_gquic_frame_type_cc_error_code = -1;
72 static int hf_gquic_frame_type_cc_reason_phrase_length = -1;
73 static int hf_gquic_frame_type_cc_reason_phrase = -1;
74 static int hf_gquic_frame_type_goaway_error_code = -1;
75 static int hf_gquic_frame_type_goaway_last_good_stream_id = -1;
76 static int hf_gquic_frame_type_goaway_reason_phrase_length = -1;
77 static int hf_gquic_frame_type_goaway_reason_phrase = -1;
78 static int hf_gquic_frame_type_wu_stream_id = -1;
79 static int hf_gquic_frame_type_wu_byte_offset = -1;
80 static int hf_gquic_frame_type_blocked_stream_id = -1;
81 static int hf_gquic_frame_type_sw_send_entropy = -1;
82 static int hf_gquic_frame_type_sw_least_unacked_delta = -1;
83 static int hf_gquic_crypto_offset = -1;
84 static int hf_gquic_crypto_length = -1;
85 static int hf_gquic_crypto_crypto_data = -1;
86 static int hf_gquic_frame_type_stream = -1;
87 static int hf_gquic_frame_type_stream_f = -1;
88 static int hf_gquic_frame_type_stream_d = -1;
89 static int hf_gquic_frame_type_stream_ooo = -1;
90 static int hf_gquic_frame_type_stream_ss = -1;
91 /* ACK */
92 static int hf_gquic_frame_type_ack = -1;
93 static int hf_gquic_frame_type_ack_n = -1;
94 static int hf_gquic_frame_type_ack_u = -1;
95 static int hf_gquic_frame_type_ack_t = -1;
96 static int hf_gquic_frame_type_ack_ll = -1;
97 static int hf_gquic_frame_type_ack_mm = -1;
98 /* ACK Before Q034 */
99 static int hf_gquic_frame_type_ack_received_entropy = -1;
100 static int hf_gquic_frame_type_ack_largest_observed = -1;
101 static int hf_gquic_frame_type_ack_ack_delay_time = -1;
102 static int hf_gquic_frame_type_ack_num_timestamp = -1;
103 static int hf_gquic_frame_type_ack_delta_largest_observed = -1;
104 static int hf_gquic_frame_type_ack_first_timestamp = -1;
105 static int hf_gquic_frame_type_ack_time_since_previous_timestamp = -1;
106 static int hf_gquic_frame_type_ack_num_ranges = -1;
107 static int hf_gquic_frame_type_ack_missing_packet = -1;
108 static int hf_gquic_frame_type_ack_range_length = -1;
109 static int hf_gquic_frame_type_ack_num_revived = -1;
110 static int hf_gquic_frame_type_ack_revived_packet = -1;
111 /* ACK After Q034 */
112 static int hf_gquic_frame_type_ack_largest_acked = -1;
113 static int hf_gquic_frame_type_ack_largest_acked_delta_time = -1;
114 static int hf_gquic_frame_type_ack_num_blocks = -1;
115 static int hf_gquic_frame_type_ack_first_ack_block_length = -1;
116 static int hf_gquic_frame_type_ack_gap_to_next_block = -1;
117 static int hf_gquic_frame_type_ack_ack_block_length = -1;
118 static int hf_gquic_frame_type_ack_delta_largest_acked = -1;
119 static int hf_gquic_frame_type_ack_time_since_largest_acked = -1;
120 static int hf_gquic_stream_id = -1;
121 static int hf_gquic_offset = -1;
122 static int hf_gquic_data_len = -1;
123 static int hf_gquic_tag = -1;
124 static int hf_gquic_tags = -1;
125 static int hf_gquic_tag_number = -1;
126 static int hf_gquic_tag_value = -1;
127 static int hf_gquic_tag_type = -1;
128 static int hf_gquic_tag_offset_end = -1;
129 static int hf_gquic_tag_length = -1;
130 static int hf_gquic_tag_sni = -1;
131 static int hf_gquic_tag_pad = -1;
132 static int hf_gquic_tag_ver = -1;
133 static int hf_gquic_tag_ccs = -1;
134 static int hf_gquic_tag_pdmd = -1;
135 static int hf_gquic_tag_uaid = -1;
136 static int hf_gquic_tag_stk = -1;
137 static int hf_gquic_tag_sno = -1;
138 static int hf_gquic_tag_prof = -1;
139 static int hf_gquic_tag_scfg = -1;
140 static int hf_gquic_tag_scfg_number = -1;
141 static int hf_gquic_tag_rrej = -1;
142 static int hf_gquic_tag_crt = -1;
143 static int hf_gquic_tag_aead = -1;
144 static int hf_gquic_tag_scid = -1;
145 static int hf_gquic_tag_pubs = -1;
146 static int hf_gquic_tag_kexs = -1;
147 static int hf_gquic_tag_obit = -1;
148 static int hf_gquic_tag_expy = -1;
149 static int hf_gquic_tag_nonc = -1;
150 static int hf_gquic_tag_mspc = -1;
151 static int hf_gquic_tag_tcid = -1;
152 static int hf_gquic_tag_srbf = -1;
153 static int hf_gquic_tag_icsl = -1;
154 static int hf_gquic_tag_scls = -1;
155 static int hf_gquic_tag_copt = -1;
156 static int hf_gquic_tag_ccrt = -1;
157 static int hf_gquic_tag_irtt = -1;
158 static int hf_gquic_tag_cfcw = -1;
159 static int hf_gquic_tag_sfcw = -1;
160 static int hf_gquic_tag_cetv = -1;
161 static int hf_gquic_tag_xlct = -1;
162 static int hf_gquic_tag_nonp = -1;
163 static int hf_gquic_tag_csct = -1;
164 static int hf_gquic_tag_ctim = -1;
165 static int hf_gquic_tag_mids = -1;
166 static int hf_gquic_tag_fhol = -1;
167 static int hf_gquic_tag_sttl = -1;
168 static int hf_gquic_tag_smhl = -1;
169 static int hf_gquic_tag_tbkp = -1;
170 static int hf_gquic_tag_mad0 = -1;
171 static int hf_gquic_tag_qlve = -1;
172 static int hf_gquic_tag_cgst = -1;
173 static int hf_gquic_tag_epid = -1;
174 static int hf_gquic_tag_srst = -1;
175 
176 /* Public Reset Tags */
177 static int hf_gquic_tag_rnon = -1;
178 static int hf_gquic_tag_rseq = -1;
179 static int hf_gquic_tag_cadr_addr_type = -1;
180 static int hf_gquic_tag_cadr_addr_ipv4 = -1;
181 static int hf_gquic_tag_cadr_addr_ipv6 = -1;
182 static int hf_gquic_tag_cadr_addr = -1;
183 static int hf_gquic_tag_cadr_port = -1;
184 
185 static int hf_gquic_tag_unknown = -1;
186 
187 static int hf_gquic_padding = -1;
188 static int hf_gquic_stream_data = -1;
189 static int hf_gquic_payload = -1;
190 
191 #define QUIC_PORT_RANGE "80,443"
192 static gboolean g_gquic_debug = FALSE;
193 
194 static gint ett_gquic = -1;
195 static gint ett_gquic_puflags = -1;
196 static gint ett_gquic_prflags = -1;
197 static gint ett_gquic_ft = -1;
198 static gint ett_gquic_ftflags = -1;
199 static gint ett_gquic_tag_value = -1;
200 
201 static expert_field ei_gquic_tag_undecoded = EI_INIT;
202 static expert_field ei_gquic_tag_length = EI_INIT;
203 static expert_field ei_gquic_tag_unknown = EI_INIT;
204 static expert_field ei_gquic_version_invalid = EI_INIT;
205 static expert_field ei_gquic_invalid_parameter = EI_INIT;
206 static expert_field ei_gquic_length_invalid = EI_INIT;
207 
208 static const value_string gquic_short_long_header_vals[] = {
209     { 0, "Short Header" },
210     { 1, "Long Header" },
211     { 0, NULL }
212 };
213 static const value_string gquic_long_packet_type_vals[] = {
214     { 0, "Initial" },
215     { 2, "Handshake" },
216     { 1, "0-RTT" },
217     { 0, NULL }
218 };
219 static const value_string gquic_packet_number_lengths[] = {
220     { 0, "1 bytes" },
221     { 1, "2 bytes" },
222     { 2, "3 bytes" },
223     { 3, "4 bytes" },
224     { 0, NULL }
225 };
226 static const value_string quic_cid_lengths[] = {
227     { 0, "0 bytes" },
228     { 5, "8 bytes" },
229     { 0, NULL }
230 };
231 
232 #define GQUIC_MIN_LENGTH 3
233 #define GQUIC_MAGIC2 0x513032
234 #define GQUIC_MAGIC3 0x513033
235 #define GQUIC_MAGIC4 0x513034
236 
237 #define GQUIC_VERSION_Q046 0x51303436
238 
239 /**************************************************************************/
240 /*                      Public Flags                                      */
241 /**************************************************************************/
242 #define PUFLAGS_VRSN    0x01
243 #define PUFLAGS_RST     0x02
244 #define PUFLAGS_DNONCE  0x04
245 #define PUFLAGS_CID     0x08
246 #define PUFLAGS_CID_OLD 0x0C
247 #define PUFLAGS_PKN     0x30
248 #define PUFLAGS_MPTH    0x40
249 #define PUFLAGS_RSV     0x80
250 
251 static const true_false_string puflags_cid_tfs = {
252     "8 Bytes",
253     "0 Byte"
254 };
255 
256 static const value_string puflags_cid_old_vals[] = {
257     { 0, "0 Byte" },
258     { 1, "1 Bytes" },
259     { 2, "4 Bytes" },
260     { 3, "8 Bytes" },
261     { 0, NULL }
262 };
263 
264 static const value_string puflags_pkn_vals[] = {
265     { 0, "1 Byte" },
266     { 1, "2 Bytes" },
267     { 2, "4 Bytes" },
268     { 3, "6 Bytes" },
269     { 0, NULL }
270 };
271 
272 /**************************************************************************/
273 /*                      Private Flags                                     */
274 /**************************************************************************/
275 #define PRFLAGS_ENTROPY 0x01
276 #define PRFLAGS_FECG    0x02
277 #define PRFLAGS_FEC     0x04
278 #define PRFLAGS_RSV     0xF8
279 
280 
281 /**************************************************************************/
282 /*                      Frame Type Regular                                */
283 /**************************************************************************/
284 #define FT_PADDING          0x00
285 #define FT_RST_STREAM       0x01
286 #define FT_CONNECTION_CLOSE 0x02
287 #define FT_GOAWAY           0x03
288 #define FT_WINDOW_UPDATE    0x04
289 #define FT_BLOCKED          0x05
290 #define FT_STOP_WAITING     0x06
291 #define FT_PING             0x07
292 /* CRYPTO is not a real GQUIC frame, but a QUIC one. Since some GQUIC flows
293  * have this kind of frame, try handling it like all the others */
294 #define FT_CRYPTO           0x08
295 
296 /**************************************************************************/
297 /*                      Frame Type Special                                */
298 /**************************************************************************/
299 #define FTFLAGS_SPECIAL     0xE0
300 
301 #define FTFLAGS_STREAM      0x80
302 #define FTFLAGS_STREAM_F    0x40
303 #define FTFLAGS_STREAM_D    0x20
304 #define FTFLAGS_STREAM_OOO  0x1C
305 #define FTFLAGS_STREAM_SS   0x03
306 
307 #define FTFLAGS_ACK         0x40
308 #define FTFLAGS_ACK_N       0x20
309 #define FTFLAGS_ACK_U       0x10
310 #define FTFLAGS_ACK_T       0x10
311 #define FTFLAGS_ACK_LL      0x0C
312 #define FTFLAGS_ACK_MM      0x03
313 
314 static const range_string frame_type_vals[] = {
315   { 0,0,         "PADDING" },
316   { 1,1,         "RST_STREAM" },
317   { 2,2,         "CONNECTION_CLOSE" },
318   { 3,3,         "GOAWAY" },
319   { 4,4,         "WINDOW_UPDATE" },
320   { 5,5,         "BLOCKED" },
321   { 6,6,         "STOP_WAITING" },
322   { 7,7,         "PING" },
323   { 8,8,         "CRYPTO" },
324   { 9,31,        "Unknown" },
325   { 32,63,       "CONGESTION_FEEDBACK (Special Frame Type)" },
326   { 64,127,      "ACK (Special Frame Type)" },
327   { 128,256,     "STREAM (Special Frame Type)" },
328   { 0,0, NULL }
329 };
330 
331 static const value_string len_offset_vals[] = {
332     { 0, "0 Byte" },
333     { 1, "2 Bytes" },
334     { 2, "3 Bytes" },
335     { 3, "4 Bytes" },
336     { 4, "5 Bytes" },
337     { 5, "6 Bytes" },
338     { 6, "7 Bytes" },
339     { 7, "8 Bytes" },
340     { 0, NULL }
341 };
342 
343 static const value_string len_stream_vals[] = {
344     { 0, "1 Byte" },
345     { 1, "2 Bytes" },
346     { 2, "3 Bytes" },
347     { 3, "4 Bytes" },
348     { 0, NULL }
349 };
350 
351 static const true_false_string len_data_vals = {
352     "2 Bytes",
353     "0 Byte"
354 };
355 
356 static const value_string len_largest_observed_vals[] = {
357     { 0, "1 Byte" },
358     { 1, "2 Bytes" },
359     { 2, "4 Bytes" },
360     { 3, "6 Bytes" },
361     { 0, NULL }
362 };
363 
364 static const value_string len_missing_packet_vals[] = {
365     { 0, "1 Byte" },
366     { 1, "2 Bytes" },
367     { 2, "4 Bytes" },
368     { 3, "6 Bytes" },
369     { 0, NULL }
370 };
371 
372 
373 /**************************************************************************/
374 /*                      Message tag                                       */
375 /**************************************************************************/
376 
377 #define MTAG_CHLO 0x43484C4F
378 #define MTAG_SHLO 0x53484C4F
379 #define MTAG_REJ  0x52454A00
380 #define MTAG_PRST 0x50525354
381 
382 static const value_string message_tag_vals[] = {
383     { MTAG_CHLO, "Client Hello" },
384     { MTAG_SHLO, "Server Hello" },
385     { MTAG_REJ, "Rejection" },
386     { MTAG_PRST, "Public Reset" },
387     { 0, NULL }
388 };
389 
390 /**************************************************************************/
391 /*                      Tag                                               */
392 /**************************************************************************/
393 /* See https://chromium.googlesource.com/chromium/src.git/+/master/net/third_party/quic/core/crypto/crypto_protocol.h */
394 
395 #define TAG_PAD  0x50414400
396 #define TAG_SNI  0x534E4900
397 #define TAG_VER  0x56455200
398 #define TAG_CCS  0x43435300
399 #define TAG_UAID 0x55414944
400 #define TAG_PDMD 0x50444d44
401 #define TAG_STK  0x53544b00
402 #define TAG_SNO  0x534E4F00
403 #define TAG_PROF 0x50524F46
404 #define TAG_SCFG 0x53434647
405 #define TAG_RREJ 0x5252454A
406 #define TAG_CRT  0x435254FF
407 #define TAG_AEAD 0x41454144
408 #define TAG_SCID 0x53434944
409 #define TAG_PUBS 0x50554253
410 #define TAG_KEXS 0x4B455853
411 #define TAG_OBIT 0x4F424954
412 #define TAG_EXPY 0x45585059
413 #define TAG_NONC 0x4E4F4E43
414 #define TAG_MSPC 0x4D535043
415 #define TAG_TCID 0x54434944
416 #define TAG_SRBF 0x53524246
417 #define TAG_ICSL 0x4943534C
418 #define TAG_SCLS 0x53434C53
419 #define TAG_COPT 0x434F5054
420 #define TAG_CCRT 0x43435254
421 #define TAG_IRTT 0x49525454
422 #define TAG_CFCW 0x43464357
423 #define TAG_SFCW 0x53464357
424 #define TAG_CETV 0x43455456
425 #define TAG_XLCT 0x584C4354
426 #define TAG_NONP 0x4E4F4E50
427 #define TAG_CSCT 0x43534354
428 #define TAG_CTIM 0x4354494D
429 #define TAG_MIDS 0x4D494453
430 #define TAG_FHOL 0x46484F4C
431 #define TAG_STTL 0x5354544C
432 #define TAG_SMHL 0x534D484C
433 #define TAG_TBKP 0x54424B50
434 #define TAG_MAD0 0x4d414400
435 #define TAG_QLVE 0x514C5645
436 #define TAG_CGST 0x43475354
437 #define TAG_EPID 0x45504944
438 #define TAG_SRST 0x53525354
439 
440 /* Public Reset Tag */
441 #define TAG_RNON 0x524E4F4E
442 #define TAG_RSEQ 0x52534551
443 #define TAG_CADR 0x43414452
444 
445 static const value_string tag_vals[] = {
446     { TAG_PAD, "Padding" },
447     { TAG_SNI, "Server Name Indication" },
448     { TAG_VER, "Version" },
449     { TAG_CCS, "Common Certificate Sets" },
450     { TAG_UAID, "Client's User Agent ID" },
451     { TAG_PDMD, "Proof Demand" },
452     { TAG_STK, "Source Address Token" },
453     { TAG_SNO, "Server nonce" },
454     { TAG_PROF, "Proof (Signature)" },
455     { TAG_SCFG, "Server Config" },
456     { TAG_RREJ, "Reasons for server sending" },
457     { TAG_CRT, "Certificate chain" },
458     { TAG_AEAD, "Authenticated encryption algorithms" },
459     { TAG_SCID, "Server config ID" },
460     { TAG_PUBS, "Public value" },
461     { TAG_KEXS, "Key exchange algorithms" },
462     { TAG_OBIT, "Server Orbit" },
463     { TAG_EXPY, "Expiry" },
464     { TAG_NONC, "Client Nonce" },
465     { TAG_MSPC, "Max streams per connection" },
466     { TAG_TCID, "Connection ID truncation" },
467     { TAG_SRBF, "Socket receive buffer" },
468     { TAG_ICSL, "Idle connection state" },
469     { TAG_SCLS, "Silently close on timeout" },
470     { TAG_COPT, "Connection options" },
471     { TAG_CCRT, "Cached certificates" },
472     { TAG_IRTT, "Estimated initial RTT" },
473     { TAG_CFCW, "Initial session/connection" },
474     { TAG_SFCW, "Initial stream flow control" },
475     { TAG_CETV, "Client encrypted tag-value" },
476     { TAG_XLCT, "Expected leaf certificate" },
477     { TAG_NONP, "Client Proof Nonce" },
478     { TAG_CSCT, "Signed cert timestamp (RFC6962) of leaf cert" },
479     { TAG_CTIM, "Client Timestamp" },
480     { TAG_MIDS, "Max incoming dynamic streams" },
481     { TAG_FHOL, "Force Head Of Line blocking" },
482     { TAG_STTL, "Server Config TTL" },
483     { TAG_SMHL, "Support Max Header List (size)" },
484     { TAG_TBKP, "Token Binding Key Params" },
485     { TAG_MAD0, "Max Ack Delay (IETF QUIC)" },
486     { TAG_QLVE, "Legacy Version Encapsulation" },
487     { TAG_CGST, "Congestion Control Feedback Type" },
488     { TAG_EPID, "Endpoint Identifier" },
489     { TAG_SRST, "Stateless Reset Token" },
490 
491     { TAG_RNON, "Public Reset Nonce Proof" },
492     { TAG_RSEQ, "Rejected Packet Number" },
493     { TAG_CADR, "Client Address" },
494     { 0, NULL }
495 };
496 
497 
498 /**************************************************************************/
499 /*                      AEAD Tag                                          */
500 /**************************************************************************/
501 
502 #define AEAD_AESG  0x41455347
503 #define AEAD_S20P  0x53323050
504 #define AEAD_CC12  0x43433132
505 
506 static const value_string tag_aead_vals[] = {
507     { AEAD_AESG, "AES-GCM with a 12-byte tag and IV" },
508     { AEAD_S20P, "Salsa20 with Poly1305" },
509     { AEAD_CC12, "Salsa20 with Poly1305" },
510     { 0, NULL }
511 };
512 
513 /**************************************************************************/
514 /*                      KEXS Tag                                          */
515 /**************************************************************************/
516 
517 #define KEXS_C255  0x43323535
518 #define KEXS_P256  0x50323536
519 
520 static const value_string tag_kexs_vals[] = {
521     { KEXS_C255, "Curve25519" },
522     { KEXS_P256, "P-256" },
523     { 0, NULL }
524 };
525 
526 /**************************************************************************/
527 /*                      Client Address Type                               */
528 /**************************************************************************/
529 
530 static const value_string cadr_type_vals[] = {
531     { 2, "IPv4" },
532     { 10, "IPv6" },
533     { 0, NULL }
534 };
535 
536 /**************************************************************************/
537 /*                      Error Code                                        */
538 /**************************************************************************/
539 /* See https://chromium.googlesource.com/chromium/src.git/+/master/net/third_party/quic/core/quic_error_codes.h */
540 
541 enum QuicErrorCode {
542     QUIC_NO_ERROR = 0,
543     /* Connection has reached an invalid state. */
544     QUIC_INTERNAL_ERROR = 1,
545     /* There were data frames after the a fin or reset. */
546     QUIC_STREAM_DATA_AFTER_TERMINATION = 2,
547     /* Control frame is malformed. */
548     QUIC_INVALID_PACKET_HEADER = 3,
549     /* Frame data is malformed. */
550     QUIC_INVALID_FRAME_DATA = 4,
551     /* The packet contained no payload. */
552     QUIC_MISSING_PAYLOAD = 48,
553     /* FEC data is malformed. */
554     QUIC_INVALID_FEC_DATA = 5,
555     /* STREAM frame data is malformed. */
556     QUIC_INVALID_STREAM_DATA = 46,
557     /* STREAM frame data overlaps with buffered data. */
558     QUIC_OVERLAPPING_STREAM_DATA = 87,
559     /* STREAM frame data is not encrypted. */
560     QUIC_UNENCRYPTED_STREAM_DATA = 61,
561     /* Attempt to send unencrypted STREAM frame. */
562     QUIC_ATTEMPT_TO_SEND_UNENCRYPTED_STREAM_DATA = 88,
563     /* Received a frame which is likely the result of memory corruption. */
564     QUIC_MAYBE_CORRUPTED_MEMORY = 89,
565     /* FEC frame data is not encrypted. */
566     QUIC_UNENCRYPTED_FEC_DATA = 77,
567     /* RST_STREAM frame data is malformed. */
568     QUIC_INVALID_RST_STREAM_DATA = 6,
569     /* CONNECTION_CLOSE frame data is malformed. */
570     QUIC_INVALID_CONNECTION_CLOSE_DATA = 7,
571     /* GOAWAY frame data is malformed. */
572     QUIC_INVALID_GOAWAY_DATA = 8,
573     /* WINDOW_UPDATE frame data is malformed. */
574     QUIC_INVALID_WINDOW_UPDATE_DATA = 57,
575     /* BLOCKED frame data is malformed. */
576     QUIC_INVALID_BLOCKED_DATA = 58,
577     /* STOP_WAITING frame data is malformed. */
578     QUIC_INVALID_STOP_WAITING_DATA = 60,
579     /* PATH_CLOSE frame data is malformed. */
580     QUIC_INVALID_PATH_CLOSE_DATA = 78,
581     /* ACK frame data is malformed. */
582     QUIC_INVALID_ACK_DATA = 9,
583     /* deprecated: */
584     QUIC_INVALID_CONGESTION_FEEDBACK_DATA = 47,
585     /* Version negotiation packet is malformed. */
586     QUIC_INVALID_VERSION_NEGOTIATION_PACKET = 10,
587     /* Public RST packet is malformed. */
588     QUIC_INVALID_PUBLIC_RST_PACKET = 11,
589     /* There was an error decrypting. */
590     QUIC_DECRYPTION_FAILURE = 12,
591     /* There was an error encrypting. */
592     QUIC_ENCRYPTION_FAILURE = 13,
593     /* The packet exceeded kMaxPacketSize. */
594     QUIC_PACKET_TOO_LARGE = 14,
595     /* Data was sent for a stream which did not exist. */
596     QUIC_PACKET_FOR_NONEXISTENT_STREAM = 15,
597     /* The peer is going away.   May be a client or server. */
598     QUIC_PEER_GOING_AWAY = 16,
599     /* A stream ID was invalid. */
600     QUIC_INVALID_STREAM_ID = 17,
601     /* A priority was invalid. */
602     QUIC_INVALID_PRIORITY = 49,
603     /* Too many streams already open. */
604     QUIC_TOO_MANY_OPEN_STREAMS = 18,
605     /* The peer created too many available streams. */
606     QUIC_TOO_MANY_AVAILABLE_STREAMS = 76,
607     /* The peer must send a FIN/RST for each stream, and has not been doing so. */
608     QUIC_TOO_MANY_UNFINISHED_STREAMS = 66,
609     /* Received public reset for this connection. */
610     QUIC_PUBLIC_RESET = 19,
611     /* Invalid protocol version. */
612     QUIC_INVALID_VERSION = 20,
613     /* deprecated: */
614     QUIC_STREAM_RST_BEFORE_HEADERS_DECOMPRESSED = 21,
615     /* The Header ID for a stream was too far from the previous. */
616     QUIC_INVALID_HEADER_ID = 22,
617     /* Negotiable parameter received during handshake had invalid value. */
618     QUIC_INVALID_NEGOTIATED_VALUE = 23,
619     /* There was an error decompressing data. */
620     QUIC_DECOMPRESSION_FAILURE = 24,
621     /* We hit our prenegotiated (or default) timeout */
622     QUIC_CONNECTION_TIMED_OUT = 25,
623     /* We hit our overall connection timeout */
624     QUIC_CONNECTION_OVERALL_TIMED_OUT = 67,
625     /* There was an error encountered migrating addresses */
626     QUIC_ERROR_MIGRATING_ADDRESS = 26,
627     /* There was an error encountered migrating port only. */
628     QUIC_ERROR_MIGRATING_PORT = 86,
629     /* There was an error while writing to the socket. */
630     QUIC_PACKET_WRITE_ERROR = 27,
631     /* There was an error while reading from the socket. */
632     QUIC_PACKET_READ_ERROR = 51,
633     /* We received a STREAM_FRAME with no data and no fin flag set. */
634     QUIC_INVALID_STREAM_FRAME = 50,
635     /* We received invalid data on the headers stream. */
636     QUIC_INVALID_HEADERS_STREAM_DATA = 56,
637     /* Invalid data on the headers stream received because of decompression failure. */
638     QUIC_HEADERS_STREAM_DATA_DECOMPRESS_FAILURE = 97,
639     /* The peer received too much data, violating flow control. */
640     QUIC_FLOW_CONTROL_RECEIVED_TOO_MUCH_DATA = 59,
641     /* The peer sent too much data, violating flow control. */
642     QUIC_FLOW_CONTROL_SENT_TOO_MUCH_DATA = 63,
643     /* The peer received an invalid flow control window. */
644     QUIC_FLOW_CONTROL_INVALID_WINDOW = 64,
645     /* The connection has been IP pooled into an existing connection. */
646     QUIC_CONNECTION_IP_POOLED = 62,
647     /* The connection has too many outstanding sent packets. */
648     QUIC_TOO_MANY_OUTSTANDING_SENT_PACKETS = 68,
649     /* The connection has too many outstanding received packets. */
650     QUIC_TOO_MANY_OUTSTANDING_RECEIVED_PACKETS = 69,
651     /* The quic connection job to load server config is cancelled. */
652     QUIC_CONNECTION_CANCELLED = 70,
653     /* Disabled QUIC because of high packet loss rate. */
654     QUIC_BAD_PACKET_LOSS_RATE = 71,
655     /* Disabled QUIC because of too many PUBLIC_RESETs post handshake. */
656     QUIC_PUBLIC_RESETS_POST_HANDSHAKE = 73,
657     /* Disabled QUIC because of too many timeouts with streams open. */
658     QUIC_TIMEOUTS_WITH_OPEN_STREAMS = 74,
659     /* Closed because we failed to serialize a packet. */
660     QUIC_FAILED_TO_SERIALIZE_PACKET = 75,
661     /* QUIC timed out after too many RTOs. */
662     QUIC_TOO_MANY_RTOS = 85,
663 
664     /* Crypto errors. */
665     /* Handshake failed. */
666     QUIC_HANDSHAKE_FAILED = 28,
667     /* Handshake message contained out of order tags. */
668     QUIC_CRYPTO_TAGS_OUT_OF_ORDER = 29,
669     /* Handshake message contained too many entries. */
670     QUIC_CRYPTO_TOO_MANY_ENTRIES = 30,
671     /* Handshake message contained an invalid value length. */
672     QUIC_CRYPTO_INVALID_VALUE_LENGTH = 31,
673     /* A crypto message was received after the handshake was complete. */
674     QUIC_CRYPTO_MESSAGE_AFTER_HANDSHAKE_COMPLETE = 32,
675     /* A crypto message was received with an illegal message tag. */
676     QUIC_INVALID_CRYPTO_MESSAGE_TYPE = 33,
677     /* A crypto message was received with an illegal parameter. */
678     QUIC_INVALID_CRYPTO_MESSAGE_PARAMETER = 34,
679     /* An invalid channel id signature was supplied. */
680     QUIC_INVALID_CHANNEL_ID_SIGNATURE = 52,
681     /* A crypto message was received with a mandatory parameter missing. */
682     QUIC_CRYPTO_MESSAGE_PARAMETER_NOT_FOUND = 35,
683     /* A crypto message was received with a parameter that has no overlap
684        with the local parameter. */
685     QUIC_CRYPTO_MESSAGE_PARAMETER_NO_OVERLAP = 36,
686     /* A crypto message was received that contained a parameter with too few
687        values. */
688     QUIC_CRYPTO_MESSAGE_INDEX_NOT_FOUND = 37,
689     /* A demand for an unsupport proof type was received. */
690     QUIC_UNSUPPORTED_PROOF_DEMAND = 94,
691     /* An internal error occurred in crypto processing. */
692     QUIC_CRYPTO_INTERNAL_ERROR = 38,
693     /* A crypto handshake message specified an unsupported version. */
694     QUIC_CRYPTO_VERSION_NOT_SUPPORTED = 39,
695     /* A crypto handshake message resulted in a stateless reject. */
696     QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT = 72,
697     /* There was no intersection between the crypto primitives supported by the
698        peer and ourselves. */
699     QUIC_CRYPTO_NO_SUPPORT = 40,
700     /* The server rejected our client hello messages too many times. */
701     QUIC_CRYPTO_TOO_MANY_REJECTS = 41,
702     /* The client rejected the server's certificate chain or signature. */
703     QUIC_PROOF_INVALID = 42,
704     /* A crypto message was received with a duplicate tag. */
705     QUIC_CRYPTO_DUPLICATE_TAG = 43,
706     /* A crypto message was received with the wrong encryption level (i.e. it
707        should have been encrypted but was not. ) */
708     QUIC_CRYPTO_ENCRYPTION_LEVEL_INCORRECT = 44,
709     /* The server config for a server has expired. */
710     QUIC_CRYPTO_SERVER_CONFIG_EXPIRED = 45,
711     /* We failed to setup the symmetric keys for a connection. */
712     QUIC_CRYPTO_SYMMETRIC_KEY_SETUP_FAILED = 53,
713     /* A handshake message arrived, but we are still validating the
714        previous handshake message. */
715     QUIC_CRYPTO_MESSAGE_WHILE_VALIDATING_CLIENT_HELLO = 54,
716     /* A server config update arrived before the handshake is complete. */
717     QUIC_CRYPTO_UPDATE_BEFORE_HANDSHAKE_COMPLETE = 65,
718     /* CHLO cannot fit in one packet. */
719     QUIC_CRYPTO_CHLO_TOO_LARGE = 90,
720     /* This connection involved a version negotiation which appears to have been
721        tampered with. */
722     QUIC_VERSION_NEGOTIATION_MISMATCH = 55,
723 
724     /* Multipath is not enabled, but a packet with multipath flag on is received. */
725     QUIC_BAD_MULTIPATH_FLAG = 79,
726     /* A path is supposed to exist but does not. */
727     QUIC_MULTIPATH_PATH_DOES_NOT_EXIST = 91,
728     /* A path is supposed to be active but is not. */
729     QUIC_MULTIPATH_PATH_NOT_ACTIVE = 92,
730 
731     /* IP address changed causing connection close. */
732     QUIC_IP_ADDRESS_CHANGED = 80,
733 
734     /* Connection migration errors. */
735     /* Network changed, but connection had no migratable streams. */
736     QUIC_CONNECTION_MIGRATION_NO_MIGRATABLE_STREAMS = 81,
737     /* Connection changed networks too many times. */
738     QUIC_CONNECTION_MIGRATION_TOO_MANY_CHANGES = 82,
739     /* Connection migration was attempted, but there was no new network to migrate to. */
740     QUIC_CONNECTION_MIGRATION_NO_NEW_NETWORK = 83,
741     /* Network changed, but connection had one or more non-migratable streams. */
742     QUIC_CONNECTION_MIGRATION_NON_MIGRATABLE_STREAM = 84,
743     /* Network changed, but connection migration was disabled by config. */
744     QUIC_CONNECTION_MIGRATION_DISABLED_BY_CONFIG = 99,
745     /* Network changed, but error was encountered on the alternative network. */
746     QUIC_CONNECTION_MIGRATION_INTERNAL_ERROR = 100,
747 
748     /* Stream frames arrived too discontiguously so that stream sequencer buffer maintains too many gaps. */
749     QUIC_TOO_MANY_FRAME_GAPS = 93,
750 
751     /* Sequencer buffer get into weird state where continuing read/write will lead
752        to crash. */
753     QUIC_STREAM_SEQUENCER_INVALID_STATE = 95,
754     /* Connection closed because of server hits max number of sessions allowed. */
755     QUIC_TOO_MANY_SESSIONS_ON_SERVER = 96,
756 
757     /* Receive a RST_STREAM with offset larger than kMaxStreamLength. */
758     QUIC_STREAM_LENGTH_OVERFLOW = 98,
759 
760     /* No error. Used as bound while iterating. */
761     QUIC_LAST_ERROR = 101
762 };
763 
764 
765 static const value_string error_code_vals[] = {
766     { QUIC_NO_ERROR, "There was no error" },
767     { QUIC_INTERNAL_ERROR, "Connection has reached an invalid state" },
768     { QUIC_STREAM_DATA_AFTER_TERMINATION, "There were data frames after the a fin or reset" },
769     { QUIC_INVALID_PACKET_HEADER, "Control frame is malformed" },
770     { QUIC_INVALID_FRAME_DATA, "Frame data is malformed" },
771     { QUIC_INVALID_FEC_DATA, "FEC data is malformed" },
772     { QUIC_INVALID_RST_STREAM_DATA, "RST_STREAM frame data is malformed" },
773     { QUIC_INVALID_CONNECTION_CLOSE_DATA, "CONNECTION_CLOSE frame data is malformed" },
774     { QUIC_INVALID_GOAWAY_DATA, "GOAWAY frame data is malformed" },
775     { QUIC_INVALID_ACK_DATA, "ACK frame data is malformed" },
776     { QUIC_INVALID_VERSION_NEGOTIATION_PACKET, "Version negotiation packet is malformed" },
777     { QUIC_INVALID_PUBLIC_RST_PACKET, "Public RST packet is malformed" },
778     { QUIC_DECRYPTION_FAILURE, "There was an error decrypting" },
779     { QUIC_ENCRYPTION_FAILURE, "There was an error encrypting" },
780     { QUIC_PACKET_TOO_LARGE, "The packet exceeded kMaxPacketSize" },
781     { QUIC_PACKET_FOR_NONEXISTENT_STREAM, "Data was sent for a stream which did not exist" },
782     { QUIC_PEER_GOING_AWAY, "The peer is going away. May be a client or server" },
783     { QUIC_INVALID_STREAM_ID, "A stream ID was invalid" },
784     { QUIC_TOO_MANY_OPEN_STREAMS, "Too many streams already open" },
785     { QUIC_PUBLIC_RESET, "Received public reset for this connection" },
786     { QUIC_INVALID_VERSION, "Invalid protocol version" },
787     { QUIC_STREAM_RST_BEFORE_HEADERS_DECOMPRESSED, "Stream RST before Headers decompressed (Deprecated)" },
788     { QUIC_INVALID_HEADER_ID, "The Header ID for a stream was too far from the previous" },
789     { QUIC_INVALID_NEGOTIATED_VALUE, "Negotiable parameter received during handshake had invalid value" },
790     { QUIC_DECOMPRESSION_FAILURE, "There was an error decompressing data" },
791     { QUIC_CONNECTION_TIMED_OUT, "We hit our prenegotiated (or default) timeout" },
792     { QUIC_ERROR_MIGRATING_ADDRESS, "There was an error encountered migrating addresses" },
793     { QUIC_PACKET_WRITE_ERROR, "There was an error while writing to the socket" },
794     { QUIC_HANDSHAKE_FAILED, "Handshake failed" },
795     { QUIC_CRYPTO_TAGS_OUT_OF_ORDER, "Handshake message contained out of order tags" },
796     { QUIC_CRYPTO_TOO_MANY_ENTRIES, "Handshake message contained too many entries" },
797     { QUIC_CRYPTO_INVALID_VALUE_LENGTH, "Handshake message contained an invalid value length" },
798     { QUIC_CRYPTO_MESSAGE_AFTER_HANDSHAKE_COMPLETE, "A crypto message was received after the handshake was complete" },
799     { QUIC_INVALID_CRYPTO_MESSAGE_TYPE, "A crypto message was received with an illegal message tag" },
800     { QUIC_INVALID_CRYPTO_MESSAGE_PARAMETER, "A crypto message was received with an illegal parameter" },
801     { QUIC_CRYPTO_MESSAGE_PARAMETER_NOT_FOUND, "A crypto message was received with a mandatory parameter missing" },
802     { QUIC_CRYPTO_MESSAGE_PARAMETER_NO_OVERLAP, "A crypto message was received with a parameter that has no overlap with the local parameter" },
803     { QUIC_CRYPTO_MESSAGE_INDEX_NOT_FOUND, "A crypto message was received that contained a parameter with too few values" },
804     { QUIC_CRYPTO_INTERNAL_ERROR, "An internal error occurred in crypto processing" },
805     { QUIC_CRYPTO_VERSION_NOT_SUPPORTED, "A crypto handshake message specified an unsupported version" },
806 
807     { QUIC_CRYPTO_NO_SUPPORT, "There was no intersection between the crypto primitives supported by the peer and ourselves" },
808     { QUIC_CRYPTO_TOO_MANY_REJECTS, "The server rejected our client hello messages too many times" },
809     { QUIC_PROOF_INVALID, "The client rejected the server's certificate chain or signature" },
810     { QUIC_CRYPTO_DUPLICATE_TAG, "A crypto message was received with a duplicate tag" },
811     { QUIC_CRYPTO_ENCRYPTION_LEVEL_INCORRECT, "A crypto message was received with the wrong encryption level (i.e. it should have been encrypted but was not" },
812     { QUIC_CRYPTO_SERVER_CONFIG_EXPIRED, "The server config for a server has expired" },
813     { QUIC_INVALID_STREAM_DATA, "STREAM frame data is malformed" },
814     { QUIC_INVALID_CONGESTION_FEEDBACK_DATA, "Invalid congestion Feedback data (Deprecated)" },
815     { QUIC_MISSING_PAYLOAD, "The packet contained no payload" },
816     { QUIC_INVALID_PRIORITY, "A priority was invalid" },
817     { QUIC_INVALID_STREAM_FRAME, "We received a STREAM_FRAME with no data and no fin flag set" },
818     { QUIC_PACKET_READ_ERROR, "There was an error while reading from the socket" },
819     { QUIC_INVALID_CHANNEL_ID_SIGNATURE, "An invalid channel id signature was supplied" },
820     { QUIC_CRYPTO_SYMMETRIC_KEY_SETUP_FAILED, "We failed to setup the symmetric keys for a connection" },
821     { QUIC_CRYPTO_MESSAGE_WHILE_VALIDATING_CLIENT_HELLO, "A handshake message arrived, but we are still validating the previous handshake message" },
822     { QUIC_VERSION_NEGOTIATION_MISMATCH, "This connection involved a version negotiation which appears to have been tampered with" },
823     { QUIC_INVALID_HEADERS_STREAM_DATA, "We received invalid data on the headers stream" },
824     { QUIC_INVALID_WINDOW_UPDATE_DATA, "WINDOW_UPDATE frame data is malformed" },
825     { QUIC_INVALID_BLOCKED_DATA, "BLOCKED frame data is malformed" },
826 
827     { QUIC_FLOW_CONTROL_RECEIVED_TOO_MUCH_DATA, "The peer received too much data, violating flow control" },
828     { QUIC_INVALID_STOP_WAITING_DATA, "STOP_WAITING frame data is malformed" },
829     { QUIC_UNENCRYPTED_STREAM_DATA, "STREAM frame data is not encrypted" },
830     { QUIC_CONNECTION_IP_POOLED, "The connection has been IP pooled into an existing connection" },
831     { QUIC_FLOW_CONTROL_SENT_TOO_MUCH_DATA, "The peer sent too much data, violating flow control" },
832     { QUIC_FLOW_CONTROL_INVALID_WINDOW, "The peer received an invalid flow control window" },
833     { QUIC_CRYPTO_UPDATE_BEFORE_HANDSHAKE_COMPLETE, "A server config update arrived before the handshake is complete" },
834     { QUIC_TOO_MANY_UNFINISHED_STREAMS, "The peer must send a FIN/RST for each stream, and has not been doing so" },
835     { QUIC_CONNECTION_OVERALL_TIMED_OUT, "We hit our overall connection timeout" },
836     { QUIC_TOO_MANY_OUTSTANDING_SENT_PACKETS, "The connection has too many outstanding sent packets" },
837     { QUIC_TOO_MANY_OUTSTANDING_RECEIVED_PACKETS, "The connection has too many outstanding received packets" },
838     { QUIC_CONNECTION_CANCELLED, "The quic connection job to load server config is cancelled" },
839     { QUIC_BAD_PACKET_LOSS_RATE, "Disabled QUIC because of high packet loss rate" },
840     { QUIC_CRYPTO_HANDSHAKE_STATELESS_REJECT, "A crypto handshake message resulted in a stateless reject" },
841     { QUIC_PUBLIC_RESETS_POST_HANDSHAKE, "Disabled QUIC because of too many PUBLIC_RESETs post handshake" },
842     { QUIC_TIMEOUTS_WITH_OPEN_STREAMS, "Disabled QUIC because of too many timeouts with streams open" },
843     { QUIC_FAILED_TO_SERIALIZE_PACKET, "Closed because we failed to serialize a packet" },
844     { QUIC_TOO_MANY_AVAILABLE_STREAMS, "The peer created too many available streams" },
845     { QUIC_UNENCRYPTED_FEC_DATA, "FEC frame data is not encrypted" },
846     { QUIC_INVALID_PATH_CLOSE_DATA, "PATH_CLOSE frame data is malformed" },
847     { QUIC_BAD_MULTIPATH_FLAG, "Multipath is not enabled, but a packet with multipath flag on is received" },
848     { QUIC_IP_ADDRESS_CHANGED, "IP address changed causing connection close" },
849     { QUIC_CONNECTION_MIGRATION_NO_MIGRATABLE_STREAMS, "Network changed, but connection had no migratable stream" },
850     { QUIC_CONNECTION_MIGRATION_TOO_MANY_CHANGES, "Connection changed networks too many times" },
851     { QUIC_CONNECTION_MIGRATION_NO_NEW_NETWORK, "Connection migration was attempted, but there was no new network to migrate to" },
852     { QUIC_CONNECTION_MIGRATION_NON_MIGRATABLE_STREAM, "Network changed, but connection had one or more non-migratable streams" },
853     { QUIC_TOO_MANY_RTOS, "QUIC timed out after too many RTOs" },
854     { QUIC_ERROR_MIGRATING_PORT, "There was an error encountered migrating port only" },
855     { QUIC_OVERLAPPING_STREAM_DATA, "STREAM frame data overlaps with buffered data" },
856     { QUIC_ATTEMPT_TO_SEND_UNENCRYPTED_STREAM_DATA, "Attempt to send unencrypted STREAM frame" },
857     { QUIC_MAYBE_CORRUPTED_MEMORY, "Received a frame which is likely the result of memory corruption" },
858     { QUIC_CRYPTO_CHLO_TOO_LARGE, "CHLO cannot fit in one packet" },
859     { QUIC_MULTIPATH_PATH_DOES_NOT_EXIST, "A path is supposed to exist but does not" },
860     { QUIC_MULTIPATH_PATH_NOT_ACTIVE, "A path is supposed to be active but is not" },
861     { QUIC_TOO_MANY_FRAME_GAPS, "Stream frames arrived too discontiguously so that stream sequencer buffer maintains too many gaps" },
862     { QUIC_UNSUPPORTED_PROOF_DEMAND, "A demand for an unsupport proof type was received" },
863     { QUIC_STREAM_SEQUENCER_INVALID_STATE, "Sequencer buffer get into weird state where continuing read/write will lead to crash" },
864     { QUIC_TOO_MANY_SESSIONS_ON_SERVER, "Connection closed because of server hits max number of sessions allowed" },
865     { QUIC_HEADERS_STREAM_DATA_DECOMPRESS_FAILURE, "Invalid data on the headers stream received because of decompression failure" },
866     { QUIC_STREAM_LENGTH_OVERFLOW, "Receive a RST_STREAM with offset larger than kMaxStreamLength" },
867     { QUIC_CONNECTION_MIGRATION_DISABLED_BY_CONFIG, "Network changed, but connection migration was disabled by config" },
868     { QUIC_CONNECTION_MIGRATION_INTERNAL_ERROR, "Network changed, but error was encountered on the alternative network" },
869     { QUIC_LAST_ERROR, "No error. Used as bound while iterating" },
870     { 0, NULL }
871 };
872 
873 static value_string_ext error_code_vals_ext = VALUE_STRING_EXT_INIT(error_code_vals);
874 
875 /**************************************************************************/
876 /*                      RST Stream Error Code                             */
877 /**************************************************************************/
878 /* See https://chromium.googlesource.com/chromium/src.git/+/master/net/third_party/quic/core/quic_error_codes.h (enum QuicRstStreamErrorCode) */
879 
880 enum QuicRstStreamErrorCode {
881   /* Complete response has been sent, sending a RST to ask the other endpoint to stop sending request data without discarding the response. */
882 
883   QUIC_STREAM_NO_ERROR = 0,
884   /* There was some error which halted stream processing.*/
885   QUIC_ERROR_PROCESSING_STREAM,
886   /* We got two fin or reset offsets which did not match.*/
887   QUIC_MULTIPLE_TERMINATION_OFFSETS,
888   /* We got bad payload and can not respond to it at the protocol level. */
889   QUIC_BAD_APPLICATION_PAYLOAD,
890   /* Stream closed due to connection error. No reset frame is sent when this happens. */
891   QUIC_STREAM_CONNECTION_ERROR,
892   /* GoAway frame sent. No more stream can be created. */
893   QUIC_STREAM_PEER_GOING_AWAY,
894   /* The stream has been cancelled. */
895   QUIC_STREAM_CANCELLED,
896   /* Closing stream locally, sending a RST to allow for proper flow control accounting. Sent in response to a RST from the peer. */
897   QUIC_RST_ACKNOWLEDGEMENT,
898   /* Receiver refused to create the stream (because its limit on open streams has been reached).  The sender should retry the request later (using another stream). */
899   QUIC_REFUSED_STREAM,
900   /* Invalid URL in PUSH_PROMISE request header. */
901   QUIC_INVALID_PROMISE_URL,
902   /* Server is not authoritative for this URL. */
903   QUIC_UNAUTHORIZED_PROMISE_URL,
904   /* Can't have more than one active PUSH_PROMISE per URL. */
905   QUIC_DUPLICATE_PROMISE_URL,
906   /* Vary check failed. */
907   QUIC_PROMISE_VARY_MISMATCH,
908   /* Only GET and HEAD methods allowed. */
909   QUIC_INVALID_PROMISE_METHOD,
910   /* The push stream is unclaimed and timed out. */
911   QUIC_PUSH_STREAM_TIMED_OUT,
912   /* Received headers were too large. */
913   QUIC_HEADERS_TOO_LARGE,
914   /* The data is not likely arrive in time. */
915   QUIC_STREAM_TTL_EXPIRED,
916   /* No error. Used as bound while iterating. */
917   QUIC_STREAM_LAST_ERROR,
918 };
919 
920 static const value_string rststream_error_code_vals[] = {
921     { QUIC_STREAM_NO_ERROR, "Complete response has been sent, sending a RST to ask the other endpoint to stop sending request data without discarding the response." },
922     { QUIC_ERROR_PROCESSING_STREAM, "There was some error which halted stream processing" },
923     { QUIC_MULTIPLE_TERMINATION_OFFSETS, "We got two fin or reset offsets which did not match" },
924     { QUIC_BAD_APPLICATION_PAYLOAD, "We got bad payload and can not respond to it at the protocol level" },
925     { QUIC_STREAM_CONNECTION_ERROR, "Stream closed due to connection error. No reset frame is sent when this happens" },
926     { QUIC_STREAM_PEER_GOING_AWAY, "GoAway frame sent. No more stream can be created" },
927     { QUIC_STREAM_CANCELLED, "The stream has been cancelled" },
928     { QUIC_RST_ACKNOWLEDGEMENT, "Closing stream locally, sending a RST to allow for proper flow control accounting. Sent in response to a RST from the peer" },
929     { QUIC_REFUSED_STREAM, "Receiver refused to create the stream (because its limit on open streams has been reached). The sender should retry the request later (using another stream)" },
930     { QUIC_INVALID_PROMISE_URL, "Invalid URL in PUSH_PROMISE request header" },
931     { QUIC_UNAUTHORIZED_PROMISE_URL, "Server is not authoritative for this URL" },
932     { QUIC_DUPLICATE_PROMISE_URL, "Can't have more than one active PUSH_PROMISE per URL" },
933     { QUIC_PROMISE_VARY_MISMATCH, "Vary check failed" },
934     { QUIC_INVALID_PROMISE_METHOD, "Only GET and HEAD methods allowed" },
935     { QUIC_PUSH_STREAM_TIMED_OUT, "The push stream is unclaimed and timed out" },
936     { QUIC_HEADERS_TOO_LARGE, "Received headers were too large" },
937     { QUIC_STREAM_TTL_EXPIRED, "The data is not likely arrive in time" },
938     { QUIC_STREAM_LAST_ERROR, "No error. Used as bound while iterating" },
939     { 0, NULL }
940 };
941 static value_string_ext rststream_error_code_vals_ext = VALUE_STRING_EXT_INIT(rststream_error_code_vals);
942 
943 /**************************************************************************/
944 /*                      Handshake Failure Reason                          */
945 /**************************************************************************/
946 /* See https://chromium.googlesource.com/chromium/src.git/+/master/net/third_party/quic/core/crypto/crypto_handshake.h */
947 
948 enum HandshakeFailureReason {
949     HANDSHAKE_OK = 0,
950 
951     /* Failure reasons for an invalid client nonce in CHLO. */
952 
953     /* The default error value for nonce verification failures from strike register (covers old strike registers and unknown failures). */
954     CLIENT_NONCE_UNKNOWN_FAILURE = 1,
955     /* Client nonce had incorrect length. */
956     CLIENT_NONCE_INVALID_FAILURE = 2,
957     /* Client nonce is not unique. */
958     CLIENT_NONCE_NOT_UNIQUE_FAILURE = 3,
959     /* Client orbit is invalid or incorrect. */
960     CLIENT_NONCE_INVALID_ORBIT_FAILURE = 4,
961     /* Client nonce's timestamp is not in the strike register's valid time range. */
962     CLIENT_NONCE_INVALID_TIME_FAILURE = 5,
963     /* Strike register's RPC call timed out, client nonce couldn't be verified. */
964     CLIENT_NONCE_STRIKE_REGISTER_TIMEOUT = 6,
965     /* Strike register is down, client nonce couldn't be verified. */
966     CLIENT_NONCE_STRIKE_REGISTER_FAILURE = 7,
967 
968     /* Failure reasons for an invalid server nonce in CHLO. */
969 
970     /* Unbox of server nonce failed. */
971     SERVER_NONCE_DECRYPTION_FAILURE = 8,
972     /* Decrypted server nonce had incorrect length. */
973     SERVER_NONCE_INVALID_FAILURE = 9,
974     /* Server nonce is not unique. */
975     SERVER_NONCE_NOT_UNIQUE_FAILURE = 10,
976     /* Server nonce's timestamp is not in the strike register's valid time range. */
977     SERVER_NONCE_INVALID_TIME_FAILURE = 11,
978     /* The server requires handshake confirmation. */
979     SERVER_NONCE_REQUIRED_FAILURE = 20,
980 
981     /* Failure reasons for an invalid server config in CHLO. */
982 
983     /* Missing Server config id (kSCID) tag. */
984     SERVER_CONFIG_INCHOATE_HELLO_FAILURE = 12,
985     /* Couldn't find the Server config id (kSCID). */
986     SERVER_CONFIG_UNKNOWN_CONFIG_FAILURE = 13,
987 
988     /* Failure reasons for an invalid source-address token. */
989 
990     /* Missing Source-address token (kSourceAddressTokenTag) tag. */
991     SOURCE_ADDRESS_TOKEN_INVALID_FAILURE = 14,
992     /* Unbox of Source-address token failed. */
993     SOURCE_ADDRESS_TOKEN_DECRYPTION_FAILURE = 15,
994     /* Couldn't parse the unbox'ed Source-address token. */
995     SOURCE_ADDRESS_TOKEN_PARSE_FAILURE = 16,
996     /* Source-address token is for a different IP address. */
997     SOURCE_ADDRESS_TOKEN_DIFFERENT_IP_ADDRESS_FAILURE = 17,
998     /* The source-address token has a timestamp in the future. */
999     SOURCE_ADDRESS_TOKEN_CLOCK_SKEW_FAILURE = 18,
1000     /* The source-address token has expired. */
1001     SOURCE_ADDRESS_TOKEN_EXPIRED_FAILURE = 19,
1002 
1003     /* The expected leaf certificate hash could not be validated. */
1004     INVALID_EXPECTED_LEAF_CERTIFICATE = 21,
1005 
1006     MAX_FAILURE_REASON = 22
1007 };
1008 
1009 static const value_string handshake_failure_reason_vals[] = {
1010     { HANDSHAKE_OK, "Handshake OK" },
1011     { CLIENT_NONCE_UNKNOWN_FAILURE, "The default error value for nonce verification failures from strike register (covers old strike registers and unknown failures)" },
1012     { CLIENT_NONCE_INVALID_FAILURE, "Client nonce had incorrect length" },
1013     { CLIENT_NONCE_NOT_UNIQUE_FAILURE, "Client nonce is not unique" },
1014     { CLIENT_NONCE_INVALID_ORBIT_FAILURE, "Client orbit is invalid or incorrect" },
1015     { CLIENT_NONCE_INVALID_TIME_FAILURE, "Client nonce's timestamp is not in the strike register's valid time range" },
1016     { CLIENT_NONCE_STRIKE_REGISTER_TIMEOUT, "Strike register's RPC call timed out, client nonce couldn't be verified" },
1017     { CLIENT_NONCE_STRIKE_REGISTER_FAILURE, "Strike register is down, client nonce couldn't be verified" },
1018     { SERVER_NONCE_DECRYPTION_FAILURE, "Unbox of server nonce failed" },
1019     { SERVER_NONCE_INVALID_FAILURE, "Decrypted server nonce had incorrect length" },
1020     { SERVER_NONCE_NOT_UNIQUE_FAILURE, "Server nonce is not unique" },
1021     { SERVER_NONCE_INVALID_TIME_FAILURE, "Server nonce's timestamp is not in the strike register's valid time range" },
1022     { SERVER_CONFIG_INCHOATE_HELLO_FAILURE, "Missing Server config id (kSCID) tag" },
1023     { SERVER_CONFIG_UNKNOWN_CONFIG_FAILURE, "Couldn't find the Server config id (kSCID)" },
1024     { SOURCE_ADDRESS_TOKEN_INVALID_FAILURE, "Missing Source-address token (kSourceAddressTokenTag) tag" },
1025     { SOURCE_ADDRESS_TOKEN_DECRYPTION_FAILURE, "Unbox of Source-address token failed" },
1026     { SOURCE_ADDRESS_TOKEN_PARSE_FAILURE, "Couldn't parse the unbox'ed Source-address token" },
1027     { SOURCE_ADDRESS_TOKEN_DIFFERENT_IP_ADDRESS_FAILURE, "Source-address token is for a different IP address" },
1028     { SOURCE_ADDRESS_TOKEN_CLOCK_SKEW_FAILURE, "The source-address token has a timestamp in the future" },
1029     { SOURCE_ADDRESS_TOKEN_EXPIRED_FAILURE, "The source-address token has expired" },
1030     { SERVER_NONCE_REQUIRED_FAILURE, "The server requires handshake confirmation" },
1031     { INVALID_EXPECTED_LEAF_CERTIFICATE, "The expected leaf certificate hash could not be validated" },
1032     { 0, NULL }
1033 };
1034 static value_string_ext handshake_failure_reason_vals_ext = VALUE_STRING_EXT_INIT(handshake_failure_reason_vals);
1035 
1036 
get_len_offset(guint8 frame_type)1037 static guint32 get_len_offset(guint8 frame_type){
1038 
1039     switch((frame_type & FTFLAGS_STREAM_OOO) >> 2){
1040         case 0:
1041             return 0;
1042         break;
1043         case 1:
1044             return 2;
1045         break;
1046         case 2:
1047             return 3;
1048         break;
1049         case 3:
1050             return 4;
1051         break;
1052         case 4:
1053             return 5;
1054         break;
1055         case 5:
1056             return 6;
1057         break;
1058         case 6:
1059             return 7;
1060         break;
1061         case 7:
1062             return 8;
1063         break;
1064         default:
1065         break;
1066     }
1067     return 0;
1068 }
get_len_stream(guint8 frame_type)1069 static guint32 get_len_stream(guint8 frame_type){
1070 
1071     switch(frame_type & FTFLAGS_STREAM_SS){
1072         case 0:
1073             return 1;
1074         break;
1075         case 1:
1076             return 2;
1077         break;
1078         case 2:
1079             return 3;
1080         break;
1081         case 3:
1082             return 4;
1083         break;
1084         default:
1085         break;
1086     }
1087     return 1;
1088 }
1089 
get_len_largest_observed(guint8 frame_type)1090 static guint32 get_len_largest_observed(guint8 frame_type){
1091 
1092     switch((frame_type & FTFLAGS_ACK_LL) >> 2){
1093         case 0:
1094             return 1;
1095         break;
1096         case 1:
1097             return 2;
1098         break;
1099         case 2:
1100             return 4;
1101         break;
1102         case 3:
1103             return 6;
1104         break;
1105         default:
1106         break;
1107     }
1108     return 1;
1109 }
get_len_missing_packet(guint8 frame_type)1110 static guint32 get_len_missing_packet(guint8 frame_type){
1111 
1112     switch(frame_type & FTFLAGS_ACK_MM){
1113         case 0:
1114             return 1;
1115         break;
1116         case 1:
1117             return 2;
1118         break;
1119         case 2:
1120             return 4;
1121         break;
1122         case 3:
1123             return 6;
1124         break;
1125         default:
1126         break;
1127     }
1128     return 1;
1129 }
1130 
get_len_packet_number(guint8 puflags)1131 static guint32 get_len_packet_number(guint8 puflags){
1132 
1133     switch((puflags & PUFLAGS_PKN) >> 4){
1134         case 0:
1135             return 1;
1136         break;
1137         case 1:
1138             return 2;
1139         break;
1140         case 2:
1141             return 4;
1142         break;
1143         case 3:
1144             return 6;
1145         break;
1146         default:
1147         break;
1148     }
1149     return 6;
1150 }
1151 
1152 static
is_gquic_unencrypt(tvbuff_t * tvb,packet_info * pinfo,guint offset,guint16 len_pkn,gquic_info_data_t * gquic_info)1153 gboolean is_gquic_unencrypt(tvbuff_t *tvb, packet_info *pinfo, guint offset, guint16 len_pkn, gquic_info_data_t *gquic_info){
1154     guint8 frame_type;
1155     guint8 num_ranges, num_revived, num_blocks = 0, num_timestamp;
1156     guint32 len_stream = 0, len_offset = 0, len_data = 0, len_largest_observed = 1, len_missing_packet = 1;
1157     guint32 message_tag;
1158 
1159 
1160     if(tvb_captured_length_remaining(tvb, offset) <= 13){
1161         return FALSE;
1162     }
1163     /* Message Authentication Hash */
1164     offset += 12;
1165 
1166     if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer Private Flags after Q034 */
1167         /* Private Flags */
1168         offset += 1;
1169     }
1170 
1171     while(tvb_reported_length_remaining(tvb, offset) > 0){
1172 
1173         if (tvb_captured_length_remaining(tvb, offset) <= 1){
1174             return FALSE;
1175         }
1176         /* Frame type */
1177         frame_type = tvb_get_guint8(tvb, offset);
1178         if((frame_type & FTFLAGS_SPECIAL) == 0){
1179             offset += 1;
1180             switch(frame_type){
1181                 case FT_PADDING:
1182                     return FALSE; /* Pad on rest of packet.. */
1183                 break;
1184                 case FT_RST_STREAM:
1185                     /* Stream ID */
1186                     offset += 4;
1187                     /* Byte Offset */
1188                     offset += 8;
1189                     /* Error Code */
1190                     offset += 4;
1191                 break;
1192                 case FT_CONNECTION_CLOSE:{
1193                     guint16 len_reason;
1194 
1195                     /* Error Code */
1196                     offset += 4;
1197                     /* Reason Phrase Length */
1198                     if (tvb_captured_length_remaining(tvb, offset) <= 2){
1199                         return FALSE;
1200                     }
1201                     len_reason = tvb_get_guint16(tvb, offset, gquic_info->encoding);
1202                     offset += 2;
1203                     /* Reason Phrase */
1204                     /* If length remaining == len_reason, it is Connection Close */
1205                     if (tvb_captured_length_remaining(tvb, offset) == len_reason){
1206                         return TRUE;
1207                     }
1208                     }
1209                 break;
1210                 case FT_GOAWAY:{
1211                     guint16 len_reason;
1212 
1213                     /* Error Code */
1214                     offset += 4;
1215                     /* Last Good Stream ID */
1216                     offset += 4;
1217                     /* Reason Phrase Length */
1218                     if (tvb_captured_length_remaining(tvb, offset) <= 2){
1219                         return FALSE;
1220                     }
1221                     len_reason = tvb_get_guint16(tvb, offset, gquic_info->encoding);
1222                     offset += 2;
1223                     /* Reason Phrase */
1224                     offset += len_reason;
1225                     }
1226                 break;
1227                 case FT_WINDOW_UPDATE:
1228                     /* Stream ID */
1229                     offset += 4;
1230                     /* Byte Offset */
1231                     offset += 8;
1232                 break;
1233                 case FT_BLOCKED:
1234                     /* Stream ID */
1235                     offset += 4;
1236                 break;
1237                 case FT_STOP_WAITING:
1238                     if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer Entropy after Q034 */
1239                         /* Send Entropy */
1240                         offset += 1;
1241                     }
1242                     /* Least Unacked Delta */
1243                     offset += len_pkn;
1244                 break;
1245                 case FT_PING: /* No Payload */
1246                 default: /* No default */
1247                 break;
1248             }
1249         } else {
1250             /* Special Frame Type */
1251             if(frame_type & FTFLAGS_STREAM){ /* Stream */
1252 
1253                 if(frame_type & FTFLAGS_STREAM_D){
1254                     len_data = 2;
1255                 }
1256                 len_offset = get_len_offset(frame_type);
1257                 len_stream = get_len_stream(frame_type);
1258 
1259                 /* Frame Type */
1260                 offset += 1;
1261 
1262                 /* Stream */
1263                 offset += len_stream;
1264 
1265                 /* Offset */
1266                 offset += len_offset;
1267 
1268                 /* Data length */
1269                 offset += len_data;
1270 
1271                 if (tvb_captured_length_remaining(tvb, offset) <= 4){
1272                     return FALSE;
1273                 }
1274 
1275                 /* Check if the Message Tag is CHLO (Client Hello) or SHLO (Server Hello) or REJ (Rejection) */
1276                 message_tag = tvb_get_ntohl(tvb, offset);
1277                 if (message_tag == MTAG_CHLO|| message_tag == MTAG_SHLO || message_tag == MTAG_REJ) {
1278                     if(message_tag == MTAG_CHLO && pinfo->srcport != 443) { /* Found */
1279                         gquic_info->server_port = pinfo->destport;
1280                     }
1281                     return TRUE;
1282                 }
1283 
1284 
1285             } else if (frame_type & FTFLAGS_ACK) {
1286             /* ACK Flags */
1287 
1288                 len_largest_observed = get_len_largest_observed(frame_type);
1289                 len_missing_packet = get_len_missing_packet(frame_type);
1290 
1291                 /* Frame Type */
1292                 offset += 1;
1293 
1294                 if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer Entropy after Q034 */
1295                     /* Received Entropy */
1296                     offset += 1;
1297 
1298                     /* Largest Observed */
1299                     offset += len_largest_observed;
1300 
1301                     /* Ack Delay Time */
1302                     offset += 2;
1303 
1304                     /* Num Timestamp */
1305                     if (tvb_captured_length_remaining(tvb, offset) <= 1){
1306                         return FALSE;
1307                     }
1308                     num_timestamp = tvb_get_guint8(tvb, offset);
1309                     offset += 1;
1310 
1311                     if(num_timestamp > 0){
1312                         /* Delta Largest Observed */
1313                         offset += 1;
1314 
1315                         /* First Timestamp */
1316                         offset += 4;
1317 
1318                         /* Num Timestamp (-1)x (Delta Largest Observed + Time Since Previous Timestamp) */
1319                         offset += (num_timestamp - 1)*(1+2);
1320                     }
1321 
1322                     if(frame_type & FTFLAGS_ACK_N){
1323                         /* Num Ranges */
1324                         if (tvb_captured_length_remaining(tvb, offset) <= 1){
1325                             return FALSE;
1326                         }
1327                         num_ranges = tvb_get_guint8(tvb, offset);
1328                         offset += 1;
1329 
1330                         /* Num Range x (Missing Packet + Range Length) */
1331                         offset += num_ranges*(len_missing_packet+1);
1332 
1333                         /* Num Revived */
1334                         if (tvb_captured_length_remaining(tvb, offset) <= 1){
1335                             return FALSE;
1336                         }
1337                         num_revived = tvb_get_guint8(tvb, offset);
1338                         offset += 1;
1339 
1340                         /* Num Revived x Length Largest Observed */
1341                         offset += num_revived*len_largest_observed;
1342 
1343                     }
1344                 } else {
1345 
1346                     /* Largest Acked */
1347                     offset += len_largest_observed;
1348 
1349                     /* Largest Acked Delta Time*/
1350                     offset += 2;
1351 
1352                     /* Ack Block */
1353                     if(frame_type & FTFLAGS_ACK_N){
1354                         if (tvb_captured_length_remaining(tvb, offset) <= 1){
1355                             return FALSE;
1356                         }
1357                         num_blocks = tvb_get_guint8(tvb, offset);
1358                         offset += 1;
1359                     }
1360 
1361                     /* First Ack Block Length */
1362                     offset += len_missing_packet;
1363                     if(num_blocks){
1364                         offset += (num_blocks)*(1 + len_missing_packet);
1365                     }
1366 
1367                     /* Timestamp */
1368                     if (tvb_captured_length_remaining(tvb, offset) <= 1){
1369                         return FALSE;
1370                     }
1371                     num_timestamp = tvb_get_guint8(tvb, offset);
1372                     offset += 1;
1373 
1374                     if(num_timestamp > 0){
1375 
1376                         /* Delta Largest Acked */
1377                         offset += 1;
1378 
1379                         /* Time Since Largest Acked */
1380                         offset += 4;
1381 
1382                         /* Num Timestamp x (Delta Largest Acked + Time Since Previous Timestamp) */
1383                         offset += (num_timestamp - 1)*(1+2);
1384                     }
1385 
1386                 }
1387             } else { /* Other Special Frame type */
1388                 offset += 1;
1389             }
1390         }
1391     }
1392 
1393     return FALSE;
1394 
1395 }
1396 
1397 static guint32
dissect_gquic_tag(tvbuff_t * tvb,packet_info * pinfo,proto_tree * gquic_tree,guint offset,guint32 tag_number)1398 dissect_gquic_tag(tvbuff_t *tvb, packet_info *pinfo, proto_tree *gquic_tree, guint offset, guint32 tag_number){
1399     guint32 tag_offset_start = offset + tag_number*4*2;
1400     guint32 tag_offset = 0, total_tag_len = 0;
1401     gint32 tag_len;
1402 
1403     while(tag_number){
1404         proto_tree *tag_tree, *ti_len, *ti_tag, *ti_type;
1405         guint32 offset_end, tag, num_iter;
1406         const guint8* tag_str;
1407 
1408         ti_tag = proto_tree_add_item(gquic_tree, hf_gquic_tags, tvb, offset, 8, ENC_NA);
1409         tag_tree = proto_item_add_subtree(ti_tag, ett_gquic_tag_value);
1410         ti_type = proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_type, tvb, offset, 4, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1411         tag = tvb_get_ntohl(tvb, offset);
1412         proto_item_append_text(ti_type, " (%s)", val_to_str(tag, tag_vals, "Unknown"));
1413         proto_item_append_text(ti_tag, ": %s (%s)", tag_str, val_to_str(tag, tag_vals, "Unknown"));
1414         offset += 4;
1415 
1416         proto_tree_add_item(tag_tree, hf_gquic_tag_offset_end, tvb, offset, 4, ENC_LITTLE_ENDIAN);
1417         offset_end = tvb_get_guint32(tvb, offset, ENC_LITTLE_ENDIAN);
1418 
1419         tag_len = offset_end - tag_offset;
1420         ti_len = proto_tree_add_uint(tag_tree, hf_gquic_tag_length, tvb, offset, 4, tag_len);
1421         proto_item_append_text(ti_tag, " (l=%u)", tag_len);
1422         proto_item_set_generated(ti_len);
1423         offset += 4;
1424 
1425         /* Fix issue with CRT.. (Fragmentation ?) */
1426         if( tag_len > tvb_reported_length_remaining(tvb, tag_offset_start + tag_offset)){
1427             tag_len = tvb_reported_length_remaining(tvb, tag_offset_start + tag_offset);
1428             offset_end = tag_offset + tag_len;
1429             expert_add_info(pinfo, ti_len, &ei_gquic_tag_length);
1430         }
1431 
1432         total_tag_len += tag_len;
1433 
1434         proto_tree_add_item(tag_tree, hf_gquic_tag_value, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1435 
1436         switch(tag){
1437             case TAG_PAD:
1438                 proto_tree_add_item(tag_tree, hf_gquic_tag_pad, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1439                 tag_offset += tag_len;
1440             break;
1441             case TAG_SNI:
1442                 proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_sni, tvb, tag_offset_start + tag_offset, tag_len, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1443                 proto_item_append_text(ti_tag, ": %s", tag_str);
1444                 tag_offset += tag_len;
1445             break;
1446             case TAG_VER:
1447                 num_iter = 1;
1448                 while(offset_end - tag_offset >= 4){
1449                     proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_ver, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1450                     proto_item_append_text(ti_tag, "%s %s", num_iter == 1 ? ":" : ",", tag_str);
1451                     tag_offset += 4;
1452                     num_iter++;
1453                 }
1454             break;
1455             case TAG_CCS:
1456                 while(offset_end - tag_offset >= 8){
1457                     proto_tree_add_item(tag_tree, hf_gquic_tag_ccs, tvb, tag_offset_start + tag_offset, 8, ENC_NA);
1458                     tag_offset += 8;
1459                 }
1460             break;
1461             case TAG_PDMD:
1462                 proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_pdmd, tvb, tag_offset_start + tag_offset, tag_len, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1463                 proto_item_append_text(ti_tag, ": %s", tag_str);
1464                 tag_offset += tag_len;
1465             break;
1466             case TAG_UAID:
1467                 proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_uaid, tvb, tag_offset_start + tag_offset, tag_len, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1468                 proto_item_append_text(ti_tag, ": %s", tag_str);
1469                 tag_offset += tag_len;
1470             break;
1471             case TAG_STK:
1472                 proto_tree_add_item(tag_tree, hf_gquic_tag_stk, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1473                 tag_offset += tag_len;
1474             break;
1475             case TAG_SNO:
1476                 proto_tree_add_item(tag_tree, hf_gquic_tag_sno, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1477                 tag_offset += tag_len;
1478             break;
1479             case TAG_PROF:
1480                 proto_tree_add_item(tag_tree, hf_gquic_tag_prof, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1481                 tag_offset += tag_len;
1482             break;
1483             case TAG_SCFG:{
1484                 guint32 scfg_tag_number;
1485 
1486                 proto_tree_add_item(tag_tree, hf_gquic_tag_scfg, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA);
1487                 tag_offset += 4;
1488                 proto_tree_add_item(tag_tree, hf_gquic_tag_scfg_number, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1489                 scfg_tag_number = tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN);
1490                 tag_offset += 4;
1491 
1492                 dissect_gquic_tag(tvb, pinfo, tag_tree, tag_offset_start + tag_offset, scfg_tag_number);
1493                 tag_offset += tag_len - 4 - 4;
1494                 }
1495             break;
1496             case TAG_RREJ:
1497                 while(offset_end - tag_offset >= 4){
1498                     proto_tree_add_item(tag_tree, hf_gquic_tag_rrej, tvb, tag_offset_start + tag_offset, 4,  ENC_LITTLE_ENDIAN);
1499                     proto_item_append_text(ti_tag, ", Code %s", val_to_str_ext(tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN), &handshake_failure_reason_vals_ext, "Unknown"));
1500                     tag_offset += 4;
1501                 }
1502             break;
1503             case TAG_CRT:
1504                 proto_tree_add_item(tag_tree, hf_gquic_tag_crt, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1505                 tag_offset += tag_len;
1506             break;
1507             case TAG_AEAD:
1508                 while(offset_end - tag_offset >= 4){
1509                     proto_tree *ti_aead;
1510                     ti_aead = proto_tree_add_item(tag_tree, hf_gquic_tag_aead, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA);
1511                     proto_item_append_text(ti_aead, " (%s)", val_to_str(tvb_get_ntohl(tvb, tag_offset_start + tag_offset), tag_aead_vals, "Unknown"));
1512                     proto_item_append_text(ti_tag, ", %s", val_to_str(tvb_get_ntohl(tvb, tag_offset_start + tag_offset), tag_aead_vals, "Unknown"));
1513                     tag_offset += 4;
1514                 }
1515             break;
1516             case TAG_SCID:
1517                 proto_tree_add_item(tag_tree, hf_gquic_tag_scid, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1518                 tag_offset += tag_len;
1519             break;
1520             case TAG_PUBS:
1521                 /*TODO FIX: 24 Length + Pubs key?.. ! */
1522                 proto_tree_add_item(tag_tree, hf_gquic_tag_pubs, tvb, tag_offset_start + tag_offset, 2, ENC_LITTLE_ENDIAN);
1523                 tag_offset += 2;
1524                 while(offset_end - tag_offset >= 3){
1525                     proto_tree_add_item(tag_tree, hf_gquic_tag_pubs, tvb, tag_offset_start + tag_offset, 3, ENC_LITTLE_ENDIAN);
1526                     tag_offset += 3;
1527                 }
1528             break;
1529             case TAG_KEXS:
1530                 while(offset_end - tag_offset >= 4){
1531                     proto_tree *ti_kexs;
1532                     ti_kexs = proto_tree_add_item(tag_tree, hf_gquic_tag_kexs, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA);
1533                     proto_item_append_text(ti_kexs, " (%s)", val_to_str(tvb_get_ntohl(tvb, tag_offset_start + tag_offset), tag_kexs_vals, "Unknown"));
1534                     proto_item_append_text(ti_tag, ", %s", val_to_str(tvb_get_ntohl(tvb, tag_offset_start + tag_offset), tag_kexs_vals, "Unknown"));
1535                     tag_offset += 4;
1536                 }
1537             break;
1538             case TAG_OBIT:
1539                 proto_tree_add_item(tag_tree, hf_gquic_tag_obit, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1540                 tag_offset += tag_len;
1541             break;
1542             case TAG_EXPY:
1543                 proto_tree_add_item(tag_tree, hf_gquic_tag_expy, tvb, tag_offset_start + tag_offset, 8, ENC_LITTLE_ENDIAN);
1544                 tag_offset += 8;
1545             break;
1546             case TAG_NONC:
1547                 /*TODO: Enhance display: 32 bytes consisting of 4 bytes of timestamp (big-endian, UNIX epoch seconds), 8 bytes of server orbit and 20 bytes of random data. */
1548                 proto_tree_add_item(tag_tree, hf_gquic_tag_nonc, tvb, tag_offset_start + tag_offset, 32, ENC_NA);
1549                 tag_offset += 32;
1550             break;
1551             case TAG_MSPC:
1552                 proto_tree_add_item(tag_tree, hf_gquic_tag_mspc, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1553                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1554                 tag_offset += 4;
1555             break;
1556             case TAG_TCID:
1557                 proto_tree_add_item(tag_tree, hf_gquic_tag_tcid, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1558                 tag_offset += 4;
1559             break;
1560             case TAG_SRBF:
1561                 proto_tree_add_item(tag_tree, hf_gquic_tag_srbf, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1562                 tag_offset += 4;
1563             break;
1564             case TAG_ICSL:
1565                 proto_tree_add_item(tag_tree, hf_gquic_tag_icsl, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1566                 tag_offset += 4;
1567             break;
1568             case TAG_SCLS:
1569                 proto_tree_add_item(tag_tree, hf_gquic_tag_scls, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1570                 tag_offset += 4;
1571             break;
1572             case TAG_COPT:
1573                 while(offset_end - tag_offset >= 4){
1574                     proto_tree_add_item(tag_tree, hf_gquic_tag_copt, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA);
1575                     tag_offset += 4;
1576                 }
1577             break;
1578             case TAG_CCRT:
1579                 proto_tree_add_item(tag_tree, hf_gquic_tag_ccrt, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1580                 tag_offset += tag_len;
1581             break;
1582             case TAG_IRTT:
1583                 proto_tree_add_item(tag_tree, hf_gquic_tag_irtt, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1584                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1585                 tag_offset += 4;
1586             break;
1587             case TAG_CFCW:
1588                 proto_tree_add_item(tag_tree, hf_gquic_tag_cfcw, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1589                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1590                 tag_offset += 4;
1591             break;
1592             case TAG_SFCW:
1593                 proto_tree_add_item(tag_tree, hf_gquic_tag_sfcw, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1594                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1595                 tag_offset += 4;
1596             break;
1597             case TAG_CETV:
1598                 proto_tree_add_item(tag_tree, hf_gquic_tag_cetv, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1599                 tag_offset += tag_len;
1600             break;
1601             case TAG_XLCT:
1602                 proto_tree_add_item(tag_tree, hf_gquic_tag_xlct, tvb, tag_offset_start + tag_offset, 8, ENC_NA);
1603                 tag_offset += 8;
1604             break;
1605             case TAG_NONP:
1606                 proto_tree_add_item(tag_tree, hf_gquic_tag_nonp, tvb, tag_offset_start + tag_offset, 32, ENC_NA);
1607                 tag_offset += 32;
1608             break;
1609             case TAG_CSCT:
1610                 proto_tree_add_item(tag_tree, hf_gquic_tag_csct, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1611                 tag_offset += tag_len;
1612             break;
1613             case TAG_CTIM:
1614                 proto_tree_add_item(tag_tree, hf_gquic_tag_ctim, tvb, tag_offset_start + tag_offset, 8, ENC_LITTLE_ENDIAN|ENC_TIME_SECS_NSECS);
1615                 tag_offset += 8;
1616             break;
1617             case TAG_RNON: /* Public Reset Tag */
1618                 proto_tree_add_item(tag_tree, hf_gquic_tag_rnon, tvb, tag_offset_start + tag_offset, 8, ENC_LITTLE_ENDIAN);
1619                 tag_offset += 8;
1620             break;
1621             case TAG_RSEQ: /* Public Reset Tag */
1622                 proto_tree_add_item(tag_tree, hf_gquic_tag_rseq, tvb, tag_offset_start + tag_offset, 8, ENC_LITTLE_ENDIAN);
1623                 tag_offset += 8;
1624             break;
1625             case TAG_CADR: /* Public Reset Tag */{
1626                 guint32 addr_type;
1627                 proto_tree_add_item_ret_uint(tag_tree, hf_gquic_tag_cadr_addr_type, tvb, tag_offset_start + tag_offset, 2, ENC_LITTLE_ENDIAN, &addr_type);
1628                 tag_offset += 2;
1629                 switch(addr_type){
1630                     case 2: /* IPv4 */
1631                     proto_tree_add_item(tag_tree, hf_gquic_tag_cadr_addr_ipv4, tvb, tag_offset_start + tag_offset, 4, ENC_NA);
1632                     tag_offset += 4;
1633                     break;
1634                     case 10: /* IPv6 */
1635                     proto_tree_add_item(tag_tree, hf_gquic_tag_cadr_addr_ipv6, tvb, tag_offset_start + tag_offset, 16, ENC_NA);
1636                     tag_offset += 16;
1637                     break;
1638                     default: /* Unknown */
1639                     proto_tree_add_item(tag_tree, hf_gquic_tag_cadr_addr, tvb, tag_offset_start + tag_offset, tag_len - 2 - 2, ENC_NA);
1640                     tag_offset += tag_len + 2 + 2 ;
1641                     break;
1642                 }
1643                 proto_tree_add_item(tag_tree, hf_gquic_tag_cadr_port, tvb, tag_offset_start + tag_offset, 2, ENC_LITTLE_ENDIAN);
1644                 tag_offset += 2;
1645             }
1646             break;
1647             case TAG_MIDS:
1648                 proto_tree_add_item(tag_tree, hf_gquic_tag_mids, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1649                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1650                 tag_offset += 4;
1651             break;
1652             case TAG_FHOL:
1653                 proto_tree_add_item(tag_tree, hf_gquic_tag_fhol, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1654                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1655                 tag_offset += 4;
1656             break;
1657             case TAG_STTL:
1658                 proto_tree_add_item(tag_tree, hf_gquic_tag_sttl, tvb, tag_offset_start + tag_offset, 8, ENC_LITTLE_ENDIAN);
1659                 tag_offset += 8;
1660             break;
1661             case TAG_SMHL:
1662                 proto_tree_add_item(tag_tree, hf_gquic_tag_smhl, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1663                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1664                 tag_offset += 4;
1665             break;
1666             case TAG_TBKP:
1667                 proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_tbkp, tvb, tag_offset_start + tag_offset, 4, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1668                 proto_item_append_text(ti_tag, ": %s", tag_str);
1669                 tag_offset += 4;
1670             break;
1671             case TAG_MAD0:
1672                 proto_tree_add_item(tag_tree, hf_gquic_tag_mad0, tvb, tag_offset_start + tag_offset, 4, ENC_LITTLE_ENDIAN);
1673                 proto_item_append_text(ti_tag, ": %u", tvb_get_guint32(tvb, tag_offset_start + tag_offset, ENC_LITTLE_ENDIAN));
1674                 tag_offset += 4;
1675             break;
1676             case TAG_QLVE:
1677             {
1678                 proto_tree_add_item(tag_tree, hf_gquic_tag_qlve, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1679 
1680                 /* Newest GQUIC versions (usually Q050) encapsulate their first flight in Q043 packets.
1681 		 * (Q050 is handled by QUIC dissector) */
1682                 tvbuff_t *next_tvb = tvb_new_subset_length(tvb, tag_offset_start + tag_offset, tag_len);
1683                 call_dissector_with_data(quic_handle, next_tvb, pinfo, tag_tree, NULL);
1684 
1685                 tag_offset += tag_len;
1686             }
1687             break;
1688             case TAG_CGST:
1689                 proto_tree_add_item(tag_tree, hf_gquic_tag_cgst, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1690                 tag_offset += tag_len;
1691             break;
1692             case TAG_EPID:
1693                 proto_tree_add_item_ret_string(tag_tree, hf_gquic_tag_epid, tvb, tag_offset_start + tag_offset, tag_len, ENC_ASCII|ENC_NA, pinfo->pool, &tag_str);
1694                 proto_item_append_text(ti_tag, ": %s", tag_str);
1695                 tag_offset += tag_len;
1696             break;
1697             case TAG_SRST:
1698                 proto_tree_add_item(tag_tree, hf_gquic_tag_srst, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1699                 tag_offset += tag_len;
1700             break;
1701             default:
1702                 proto_tree_add_item(tag_tree, hf_gquic_tag_unknown, tvb, tag_offset_start + tag_offset, tag_len, ENC_NA);
1703                 expert_add_info_format(pinfo, ti_tag, &ei_gquic_tag_undecoded,
1704                                  "Dissector for (Google) QUIC Tag"
1705                                  " %s (%s) code not implemented, Contact"
1706                                  " Wireshark developers if you want this supported", tvb_get_string_enc(pinfo->pool, tvb, offset-8, 4, ENC_ASCII|ENC_NA), val_to_str(tag, tag_vals, "Unknown"));
1707                 tag_offset += tag_len;
1708             break;
1709         }
1710         if(tag_offset != offset_end){
1711             /* Wrong Tag len... */
1712             proto_tree_add_expert(tag_tree, pinfo, &ei_gquic_tag_unknown, tvb, tag_offset_start + tag_offset, tag_len);
1713             tag_offset = offset_end;
1714         }
1715 
1716         tag_number--;
1717     }
1718 
1719     if (offset + total_tag_len <= offset) {
1720         expert_add_info_format(pinfo, gquic_tree, &ei_gquic_length_invalid,
1721                                 "Invalid total tag length: %u", total_tag_len);
1722         return offset + tvb_reported_length_remaining(tvb, offset);
1723     }
1724     return offset + total_tag_len;
1725 
1726 }
1727 
1728 guint32
dissect_gquic_tags(tvbuff_t * tvb,packet_info * pinfo,proto_tree * ft_tree,guint offset)1729 dissect_gquic_tags(tvbuff_t *tvb, packet_info *pinfo, proto_tree *ft_tree, guint offset){
1730     guint32 tag_number;
1731 
1732     proto_tree_add_item(ft_tree, hf_gquic_tag_number, tvb, offset, 2, ENC_LITTLE_ENDIAN);
1733     tag_number = tvb_get_guint16(tvb, offset, ENC_LITTLE_ENDIAN);
1734     offset += 2;
1735 
1736     proto_tree_add_item(ft_tree, hf_gquic_padding, tvb, offset, 2, ENC_NA);
1737     offset += 2;
1738 
1739     offset = dissect_gquic_tag(tvb, pinfo, ft_tree, offset, tag_number);
1740 
1741     return offset;
1742 }
1743 
1744 int
dissect_gquic_frame_type(tvbuff_t * tvb,packet_info * pinfo,proto_tree * gquic_tree,guint offset,guint8 len_pkn,gquic_info_data_t * gquic_info)1745 dissect_gquic_frame_type(tvbuff_t *tvb, packet_info *pinfo, proto_tree *gquic_tree, guint offset, guint8 len_pkn, gquic_info_data_t *gquic_info){
1746     proto_item *ti, *ti_ft, *ti_ftflags /*, *expert_ti*/;
1747     proto_tree *ft_tree, *ftflags_tree;
1748     guint8 frame_type;
1749     guint8 num_ranges, num_revived, num_blocks = 0, num_timestamp;
1750     guint32 len_stream = 0, len_offset = 0, len_data = 0, len_largest_observed = 1, len_missing_packet = 1;
1751 
1752     ti_ft = proto_tree_add_item(gquic_tree, hf_gquic_frame, tvb, offset, 1, ENC_NA);
1753     ft_tree = proto_item_add_subtree(ti_ft, ett_gquic_ft);
1754 
1755     /* Frame type */
1756     ti_ftflags = proto_tree_add_item(ft_tree, hf_gquic_frame_type, tvb, offset, 1, ENC_NA);
1757     frame_type = tvb_get_guint8(tvb, offset);
1758     proto_item_set_text(ti_ft, "%s", rval_to_str(frame_type, frame_type_vals, "Unknown"));
1759 
1760     if((frame_type & FTFLAGS_SPECIAL) == 0 && frame_type != FT_CRYPTO){ /* Regular Stream Flags */
1761         offset += 1;
1762         switch(frame_type){
1763             case FT_PADDING:{
1764                 proto_item *ti_pad_len;
1765                 guint32 pad_len = tvb_reported_length_remaining(tvb, offset);
1766 
1767                 ti_pad_len = proto_tree_add_uint(ft_tree, hf_gquic_frame_type_padding_length, tvb, offset, 0, pad_len);
1768                 proto_item_set_generated(ti_pad_len);
1769                 proto_item_append_text(ti_ft, " Length: %u", pad_len);
1770                 if(pad_len > 0) /* Avoid Malformed Exception with pad_len == 0 */
1771 		    proto_tree_add_item(ft_tree, hf_gquic_frame_type_padding, tvb, offset, -1, ENC_NA);
1772                 offset += pad_len;
1773                 }
1774             break;
1775             case FT_RST_STREAM:{
1776                 guint32 stream_id, error_code;
1777                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_rsts_stream_id, tvb, offset, 4, gquic_info->encoding, &stream_id);
1778                 offset += 4;
1779                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_rsts_byte_offset, tvb, offset, 8, gquic_info->encoding);
1780                 offset += 8;
1781                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_rsts_error_code, tvb, offset, 4, gquic_info->encoding, &error_code);
1782                 offset += 4;
1783                 proto_item_append_text(ti_ft, " Stream ID: %u, Error code: %s", stream_id, val_to_str_ext(error_code, &rststream_error_code_vals_ext, "Unknown (%d)"));
1784                 col_set_str(pinfo->cinfo, COL_INFO, "RST STREAM");
1785                 }
1786             break;
1787             case FT_CONNECTION_CLOSE:{
1788                 guint16 len_reason;
1789                 guint32 error_code;
1790 
1791                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_cc_error_code, tvb, offset, 4, gquic_info->encoding, &error_code);
1792                 offset += 4;
1793                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_cc_reason_phrase_length, tvb, offset, 2, gquic_info->encoding);
1794                 len_reason = tvb_get_guint16(tvb, offset, gquic_info->encoding);
1795                 offset += 2;
1796                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_cc_reason_phrase, tvb, offset, len_reason, ENC_ASCII|ENC_NA);
1797                 offset += len_reason;
1798                 proto_item_append_text(ti_ft, " Error code: %s", val_to_str_ext(error_code, &error_code_vals_ext, "Unknown (%d)"));
1799                 col_set_str(pinfo->cinfo, COL_INFO, "Connection Close");
1800                 }
1801             break;
1802             case FT_GOAWAY:{
1803                 guint16 len_reason;
1804                 guint32 error_code, last_good_stream_id;
1805 
1806                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_goaway_error_code, tvb, offset, 4, gquic_info->encoding, &error_code);
1807                 offset += 4;
1808                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_goaway_last_good_stream_id, tvb, offset, 4, gquic_info->encoding, &last_good_stream_id);
1809                 offset += 4;
1810                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_goaway_reason_phrase_length, tvb, offset, 2, gquic_info->encoding);
1811                 len_reason = tvb_get_guint16(tvb, offset, gquic_info->encoding);
1812                 offset += 2;
1813                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_goaway_reason_phrase, tvb, offset, len_reason, ENC_ASCII|ENC_NA);
1814                 offset += len_reason;
1815                 proto_item_append_text(ti_ft, " Stream ID: %u, Error code: %s", last_good_stream_id, val_to_str_ext(error_code, &error_code_vals_ext, "Unknown (%d)"));
1816                 col_set_str(pinfo->cinfo, COL_INFO, "GOAWAY");
1817                 }
1818             break;
1819             case FT_WINDOW_UPDATE:{
1820                 guint32 stream_id;
1821 
1822                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_wu_stream_id, tvb, offset, 4, gquic_info->encoding, &stream_id);
1823                 offset += 4;
1824                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_wu_byte_offset, tvb, offset, 8, gquic_info->encoding);
1825                 offset += 8;
1826                 proto_item_append_text(ti_ft, " Stream ID: %u", stream_id);
1827                 }
1828             break;
1829             case FT_BLOCKED:{
1830                 guint32 stream_id;
1831 
1832                 proto_tree_add_item_ret_uint(ft_tree, hf_gquic_frame_type_blocked_stream_id, tvb, offset, 4, gquic_info->encoding, &stream_id);
1833                 offset += 4;
1834                 proto_item_append_text(ti_ft, " Stream ID: %u", stream_id);
1835                 }
1836             break;
1837             case FT_STOP_WAITING:{
1838                 guint8 send_entropy;
1839                 if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer Entropy after Q034 */
1840                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_sw_send_entropy, tvb, offset, 1, ENC_NA);
1841                     send_entropy = tvb_get_guint8(tvb, offset);
1842                     proto_item_append_text(ti_ft, " Send Entropy: %u", send_entropy);
1843                     offset += 1;
1844                 }
1845                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_sw_least_unacked_delta, tvb, offset, len_pkn, gquic_info->encoding);
1846                 offset += len_pkn;
1847 
1848                 }
1849             break;
1850             case FT_PING: /* No Payload */
1851             default: /* No default */
1852             break;
1853         }
1854     }
1855     else { /* Special Frame Types */
1856         guint32 stream_id, message_tag;
1857         const guint8* message_tag_str;
1858         proto_item *ti_stream;
1859 
1860         ftflags_tree = proto_item_add_subtree(ti_ftflags, ett_gquic_ftflags);
1861         proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_stream , tvb, offset, 1, ENC_NA);
1862 
1863         if(frame_type == FT_CRYPTO) {
1864             guint64 crypto_offset, crypto_length;
1865             gint32 lenvar;
1866 
1867             DISSECTOR_ASSERT(gquic_info->version_valid && gquic_info->version >= 50);
1868 
1869             col_append_fstr(pinfo->cinfo, COL_INFO, ", CRYPTO");
1870             offset += 1;
1871             proto_tree_add_item_ret_varint(ft_tree, hf_gquic_crypto_offset, tvb, offset, -1, ENC_VARINT_QUIC, &crypto_offset, &lenvar);
1872             offset += lenvar;
1873             proto_tree_add_item_ret_varint(ft_tree, hf_gquic_crypto_length, tvb, offset, -1, ENC_VARINT_QUIC, &crypto_length, &lenvar);
1874             offset += lenvar;
1875             proto_tree_add_item(ft_tree, hf_gquic_crypto_crypto_data, tvb, offset, (guint32)crypto_length, ENC_NA);
1876 
1877             if (gquic_info->version == 50) {
1878 	        message_tag = tvb_get_ntohl(tvb, offset);
1879                 ti = proto_tree_add_item_ret_string(ft_tree, hf_gquic_tag, tvb, offset, 4, ENC_ASCII|ENC_NA, pinfo->pool, &message_tag_str);
1880                 proto_item_append_text(ti, " (%s)", val_to_str(message_tag, message_tag_vals, "Unknown Tag"));
1881                 col_add_fstr(pinfo->cinfo, COL_INFO, "%s", val_to_str(message_tag, message_tag_vals, "Unknown"));
1882                 offset += 4;
1883 
1884                 offset = dissect_gquic_tags(tvb, pinfo, ft_tree, offset);
1885 	    } else { /* T050 and T051 */
1886                 tvbuff_t *next_tvb = tvb_new_subset_length(tvb, offset, (int)crypto_length);
1887                 col_set_writable(pinfo->cinfo, -1, FALSE);
1888                 call_dissector_with_data(tls13_handshake_handle, next_tvb, pinfo, ft_tree, GUINT_TO_POINTER(crypto_offset));
1889                 col_set_writable(pinfo->cinfo, -1, TRUE);
1890                 offset += (guint32)crypto_length;
1891 	    }
1892 
1893 	} else if(frame_type & FTFLAGS_STREAM){ /* Stream Flags */
1894             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_stream_f, tvb, offset, 1, ENC_NA);
1895             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_stream_d, tvb, offset, 1, ENC_NA);
1896             if(frame_type & FTFLAGS_STREAM_D){
1897                 len_data = 2;
1898             }
1899             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_stream_ooo, tvb, offset, 1, ENC_NA);
1900 
1901             len_offset = get_len_offset(frame_type);
1902 
1903             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_stream_ss, tvb, offset, 1, ENC_NA);
1904             len_stream = get_len_stream(frame_type);
1905             offset += 1;
1906 
1907             ti_stream = proto_tree_add_item_ret_uint(ft_tree, hf_gquic_stream_id, tvb, offset, len_stream, gquic_info->encoding, &stream_id);
1908             offset += len_stream;
1909 
1910             proto_item_append_text(ti_ft, " Stream ID: %u", stream_id);
1911 
1912             if(len_offset) {
1913                 proto_tree_add_item(ft_tree, hf_gquic_offset, tvb, offset, len_offset, gquic_info->encoding);
1914                 offset += len_offset;
1915             }
1916 
1917             if(len_data) {
1918                 proto_tree_add_item(ft_tree, hf_gquic_data_len, tvb, offset, len_data, gquic_info->encoding);
1919                 offset += len_data;
1920             }
1921 
1922             /* Check if there is some reserved streams (Chapiter 6.1 of draft-shade-gquic-http2-mapping-00) */
1923 
1924             switch(stream_id) {
1925                 case 1: { /* Reserved (G)QUIC (handshake, crypto, config updates...) */
1926                     message_tag = tvb_get_ntohl(tvb, offset);
1927                     ti = proto_tree_add_item_ret_string(ft_tree, hf_gquic_tag, tvb, offset, 4, ENC_ASCII|ENC_NA, pinfo->pool, &message_tag_str);
1928 
1929                     proto_item_append_text(ti_stream, " (Reserved for (G)QUIC handshake, crypto, config updates...)");
1930                     proto_item_append_text(ti, " (%s)", val_to_str(message_tag, message_tag_vals, "Unknown Tag"));
1931                     proto_item_append_text(ti_ft, ", Type: %s (%s)", message_tag_str, val_to_str(message_tag, message_tag_vals, "Unknown Tag"));
1932                     col_add_fstr(pinfo->cinfo, COL_INFO, "%s", val_to_str(message_tag, message_tag_vals, "Unknown"));
1933                     offset += 4;
1934 
1935                     offset = dissect_gquic_tags(tvb, pinfo, ft_tree, offset);
1936                 break;
1937                 }
1938                 case 3: { /* Reserved H2 HEADERS (or PUSH_PROMISE..) */
1939                     tvbuff_t* tvb_h2;
1940 
1941                     proto_item_append_text(ti_stream, " (Reserved for H2 HEADERS)");
1942 
1943                     col_add_str(pinfo->cinfo, COL_INFO, "H2");
1944 
1945                     tvb_h2 = tvb_new_subset_remaining(tvb, offset);
1946 
1947                     offset += dissect_http2_pdu(tvb_h2, pinfo, ft_tree, NULL);
1948                 }
1949                 break;
1950                 default: { /* Data... */
1951                     int data_len = tvb_reported_length_remaining(tvb, offset);
1952 
1953                     col_add_str(pinfo->cinfo, COL_INFO, "DATA");
1954 
1955                     proto_tree_add_item(ft_tree, hf_gquic_stream_data, tvb, offset, data_len, ENC_NA);
1956                     offset += data_len;
1957                 }
1958                 break;
1959             }
1960         } else if (frame_type & FTFLAGS_ACK) {     /* ACK Flags */
1961 
1962             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack, tvb, offset, 1, ENC_NA);
1963 
1964             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack_n, tvb, offset, 1, ENC_NA);
1965 
1966             if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer NACK after Q034 */
1967                 proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack_t, tvb, offset, 1, ENC_NA);
1968             } else {
1969                 proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack_u, tvb, offset, 1, ENC_NA);
1970             }
1971             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack_ll, tvb, offset, 1, ENC_NA);
1972 
1973             len_largest_observed = get_len_largest_observed(frame_type);
1974 
1975             proto_tree_add_item(ftflags_tree, hf_gquic_frame_type_ack_mm, tvb, offset, 1, ENC_NA);
1976             len_missing_packet = get_len_missing_packet(frame_type);
1977             offset += 1;
1978 
1979             if(gquic_info->version_valid && gquic_info->version < 34){ /* Big change after Q034 */
1980                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_received_entropy, tvb, offset, 1, ENC_NA);
1981                 offset += 1;
1982 
1983                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_largest_observed, tvb, offset, len_largest_observed, gquic_info->encoding);
1984                 offset += len_largest_observed;
1985 
1986                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_ack_delay_time, tvb, offset, 2, gquic_info->encoding);
1987                 offset += 2;
1988 
1989                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_num_timestamp, tvb, offset, 1, ENC_NA);
1990                 num_timestamp = tvb_get_guint8(tvb, offset);
1991                 offset += 1;
1992 
1993                 if(num_timestamp){
1994 
1995                     /* Delta Largest Observed */
1996                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_delta_largest_observed, tvb, offset, 1, ENC_NA);
1997                     offset += 1;
1998 
1999                     /* First Timestamp */
2000                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_first_timestamp, tvb, offset, 4, gquic_info->encoding);
2001                     offset += 4;
2002 
2003                     num_timestamp -= 1;
2004                     /* Num Timestamp (-1) x (Delta Largest Observed + Time Since Previous Timestamp) */
2005                     while(num_timestamp){
2006                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_delta_largest_observed, tvb, offset, 1, ENC_NA);
2007                         offset += 1;
2008 
2009                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_time_since_previous_timestamp, tvb, offset, 2, gquic_info->encoding);
2010                         offset += 2;
2011 
2012                         num_timestamp--;
2013                     }
2014                 }
2015 
2016                 if(frame_type & FTFLAGS_ACK_N){
2017                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_num_ranges, tvb, offset, 1, ENC_NA);
2018                     num_ranges = tvb_get_guint8(tvb, offset);
2019                     offset += 1;
2020                     while(num_ranges){
2021 
2022                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_missing_packet, tvb, offset, len_missing_packet, gquic_info->encoding);
2023                         offset += len_missing_packet;
2024 
2025                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_range_length, tvb, offset, 1, ENC_NA);
2026                         offset += 1;
2027                         num_ranges--;
2028                     }
2029 
2030                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_num_revived, tvb, offset, 1, ENC_NA);
2031                     num_revived = tvb_get_guint8(tvb, offset);
2032                     offset += 1;
2033                     while(num_revived){
2034 
2035                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_revived_packet, tvb, offset, len_largest_observed, gquic_info->encoding);
2036                         offset += len_largest_observed;
2037                         num_revived--;
2038 
2039                     }
2040 
2041                 }
2042 
2043             } else {
2044 
2045                 /* Largest Acked */
2046                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_largest_acked, tvb, offset, len_largest_observed, gquic_info->encoding);
2047                 offset += len_largest_observed;
2048 
2049                 /* Largest Acked Delta Time*/
2050                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_largest_acked_delta_time, tvb, offset, 2, gquic_info->encoding);
2051                 offset += 2;
2052 
2053                 /* Ack Block */
2054                 if(frame_type & FTFLAGS_ACK_N){
2055                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_num_blocks, tvb, offset, 1, ENC_NA);
2056                     num_blocks = tvb_get_guint8(tvb, offset);
2057                     offset += 1;
2058                 }
2059 
2060                 /* First Ack Block Length */
2061                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_first_ack_block_length, tvb, offset, len_missing_packet, gquic_info->encoding);
2062                 offset += len_missing_packet;
2063 
2064                 while(num_blocks){
2065                     /* Gap to next block */
2066                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_gap_to_next_block, tvb, offset, 1, ENC_NA);
2067                     offset += 1;
2068 
2069                     /* Ack Block Length */
2070                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_ack_block_length, tvb, offset, len_missing_packet, gquic_info->encoding);
2071                     offset += len_missing_packet;
2072 
2073                     num_blocks--;
2074                 }
2075 
2076                 /* Timestamp */
2077                 proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_num_timestamp, tvb, offset, 1, ENC_NA);
2078                 num_timestamp = tvb_get_guint8(tvb, offset);
2079                 offset += 1;
2080 
2081                 if(num_timestamp){
2082 
2083                     /* Delta Largest Acked */
2084                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_delta_largest_acked, tvb, offset, 1, ENC_NA);
2085                     offset += 1;
2086 
2087                     /* Time Since Largest Acked */
2088                     proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_time_since_largest_acked, tvb, offset, 4, gquic_info->encoding);
2089                     offset += 4;
2090 
2091                     num_timestamp -= 1;
2092                     /* Num Timestamp x (Delta Largest Acked + Time Since Previous Timestamp) */
2093                     while(num_timestamp){
2094                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_delta_largest_acked, tvb, offset, 1, ENC_NA);
2095                         offset += 1;
2096 
2097                         proto_tree_add_item(ft_tree, hf_gquic_frame_type_ack_time_since_previous_timestamp, tvb, offset, 2, gquic_info->encoding);
2098                         offset += 2;
2099 
2100                         num_timestamp--;
2101                     }
2102                 }
2103 
2104             }
2105 
2106         } else { /* Other ...*/
2107             offset += 1;
2108         }
2109     }
2110     return offset;
2111 
2112 }
2113 
2114 static int
dissect_gquic_unencrypt(tvbuff_t * tvb,packet_info * pinfo,proto_tree * gquic_tree,guint offset,guint8 len_pkn,gquic_info_data_t * gquic_info)2115 dissect_gquic_unencrypt(tvbuff_t *tvb, packet_info *pinfo, proto_tree *gquic_tree, guint offset, guint8 len_pkn, gquic_info_data_t *gquic_info){
2116     proto_item *ti_prflags;
2117     proto_tree *prflags_tree;
2118 
2119     /* Message Authentication Hash */
2120     proto_tree_add_item(gquic_tree, hf_gquic_message_authentication_hash, tvb, offset, 12, ENC_NA);
2121     offset += 12;
2122 
2123     if(gquic_info->version_valid && gquic_info->version < 34){ /* No longer Private Flags after Q034 */
2124         /* Private Flags */
2125         ti_prflags = proto_tree_add_item(gquic_tree, hf_gquic_prflags, tvb, offset, 1, ENC_NA);
2126         prflags_tree = proto_item_add_subtree(ti_prflags, ett_gquic_prflags);
2127         proto_tree_add_item(prflags_tree, hf_gquic_prflags_entropy, tvb, offset, 1, ENC_NA);
2128         proto_tree_add_item(prflags_tree, hf_gquic_prflags_fecg, tvb, offset, 1, ENC_NA);
2129         proto_tree_add_item(prflags_tree, hf_gquic_prflags_fec, tvb, offset, 1, ENC_NA);
2130         proto_tree_add_item(prflags_tree, hf_gquic_prflags_rsv, tvb, offset, 1, ENC_NA);
2131         offset += 1;
2132     }
2133 
2134     while(tvb_reported_length_remaining(tvb, offset) > 0){
2135         offset = dissect_gquic_frame_type(tvb, pinfo, gquic_tree, offset, len_pkn, gquic_info);
2136     }
2137 
2138     return offset;
2139 
2140 }
2141 
2142 static int
dissect_gquic_common(tvbuff_t * tvb,packet_info * pinfo,proto_tree * tree,void * data _U_)2143 dissect_gquic_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
2144         void *data _U_)
2145 {
2146     proto_item *ti, *ti_puflags; /*, *expert_ti*/
2147     proto_tree *gquic_tree, *puflags_tree;
2148     guint offset = 0;
2149     guint8 puflags, len_cid = 0, len_pkn;
2150     guint64 cid = 0, pkn;
2151     conversation_t  *conv;
2152     gquic_info_data_t  *gquic_info;
2153 
2154     if (tvb_captured_length(tvb) < GQUIC_MIN_LENGTH)
2155         return 0;
2156 
2157 
2158     /* get conversation, create if necessary*/
2159     conv = find_or_create_conversation(pinfo);
2160 
2161     /* get associated state information, create if necessary */
2162     gquic_info = (gquic_info_data_t *)conversation_get_proto_data(conv, proto_gquic);
2163 
2164     if (!gquic_info) {
2165         gquic_info = wmem_new(wmem_file_scope(), gquic_info_data_t);
2166         gquic_info->version = 0;
2167         gquic_info->encoding = ENC_LITTLE_ENDIAN;
2168         gquic_info->version_valid = TRUE;
2169         gquic_info->server_port = 443;
2170         conversation_add_proto_data(conv, proto_gquic, gquic_info);
2171     }
2172 
2173     col_set_str(pinfo->cinfo, COL_PROTOCOL, "GQUIC");
2174 
2175     ti = proto_tree_add_item(tree, proto_gquic, tvb, 0, -1, ENC_NA);
2176     gquic_tree = proto_item_add_subtree(ti, ett_gquic);
2177 
2178     /* Public Flags */
2179     puflags = tvb_get_guint8(tvb, offset);
2180 
2181     /* Get len of CID */
2182     if(puflags & PUFLAGS_CID){
2183         len_cid = 8;
2184     }
2185     /* check and get (and store) version */
2186     if(puflags & PUFLAGS_VRSN){
2187         gquic_info->version_valid = ws_strtou8(tvb_get_string_enc(pinfo->pool, tvb,
2188             offset + 1 + len_cid + 1, 3, ENC_ASCII), NULL, &gquic_info->version);
2189         if (!gquic_info->version_valid)
2190             expert_add_info(pinfo, gquic_tree, &ei_gquic_version_invalid);
2191     }
2192 
2193     if(gquic_info->version >= 39){ /* After Q039, Integers and floating numbers are written in big endian*/
2194         gquic_info->encoding = ENC_BIG_ENDIAN;
2195     }
2196     ti_puflags = proto_tree_add_item(gquic_tree, hf_gquic_puflags, tvb, offset, 1, ENC_NA);
2197     puflags_tree = proto_item_add_subtree(ti_puflags, ett_gquic_puflags);
2198     proto_tree_add_item(puflags_tree, hf_gquic_puflags_vrsn, tvb, offset, 1, ENC_NA);
2199     proto_tree_add_item(puflags_tree, hf_gquic_puflags_rst, tvb, offset, 1, ENC_NA);
2200     if (gquic_info->version_valid) {
2201         if(gquic_info->version < 33){
2202             proto_tree_add_item(puflags_tree, hf_gquic_puflags_cid_old, tvb, offset, 1, ENC_NA);
2203         } else {
2204             proto_tree_add_item(puflags_tree, hf_gquic_puflags_dnonce, tvb, offset, 1, ENC_NA);
2205             proto_tree_add_item(puflags_tree, hf_gquic_puflags_cid, tvb, offset, 1, ENC_NA);
2206         }
2207     }
2208     proto_tree_add_item(puflags_tree, hf_gquic_puflags_pkn, tvb, offset, 1, ENC_NA);
2209     proto_tree_add_item(puflags_tree, hf_gquic_puflags_mpth, tvb, offset, 1, ENC_NA);
2210     proto_tree_add_item(puflags_tree, hf_gquic_puflags_rsv, tvb, offset, 1, ENC_NA);
2211     offset += 1;
2212 
2213     /* CID */
2214     if (len_cid) {
2215         cid = tvb_get_guint64(tvb, offset, gquic_info->encoding);
2216         proto_tree_add_item(gquic_tree, hf_gquic_cid, tvb, offset, len_cid, gquic_info->encoding);
2217         offset += len_cid;
2218     }
2219 
2220     /* Version */
2221     if(puflags & PUFLAGS_VRSN){
2222         if(pinfo->srcport == gquic_info->server_port){ /* Version Negotiation Packet */
2223             while(tvb_reported_length_remaining(tvb, offset) > 0){
2224                 proto_tree_add_item(gquic_tree, hf_gquic_version, tvb, offset, 4, ENC_ASCII|ENC_NA);
2225                 offset += 4;
2226             }
2227             col_add_fstr(pinfo->cinfo, COL_INFO, "Version Negotiation, CID: %" G_GINT64_MODIFIER "u", cid);
2228             return offset;
2229         }
2230         else{
2231             proto_tree_add_item(gquic_tree, hf_gquic_version, tvb, offset, 4, ENC_ASCII|ENC_NA);
2232             offset += 4;
2233         }
2234     }
2235 
2236     /* Public Reset Packet */
2237     if(puflags & PUFLAGS_RST){
2238         guint32 tag_number, message_tag;
2239 
2240         ti = proto_tree_add_item(gquic_tree, hf_gquic_tag, tvb, offset, 4, ENC_ASCII|ENC_NA);
2241         message_tag = tvb_get_ntohl(tvb, offset);
2242         proto_item_append_text(ti, " (%s)", val_to_str(message_tag, message_tag_vals, "Unknown Tag"));
2243         offset += 4;
2244 
2245         proto_tree_add_item(gquic_tree, hf_gquic_tag_number, tvb, offset, 2, ENC_LITTLE_ENDIAN);
2246         tag_number = tvb_get_guint16(tvb, offset, ENC_LITTLE_ENDIAN);
2247         offset += 2;
2248 
2249         proto_tree_add_item(gquic_tree, hf_gquic_padding, tvb, offset, 2, ENC_NA);
2250         offset += 2;
2251 
2252         offset = dissect_gquic_tag(tvb, pinfo, gquic_tree, offset, tag_number);
2253 
2254         col_add_fstr(pinfo->cinfo, COL_INFO, "Public Reset, CID: %" G_GINT64_MODIFIER "u", cid);
2255 
2256         return offset;
2257     }
2258 
2259     /* Diversification Nonce */
2260     if(gquic_info->version_valid && (puflags & PUFLAGS_DNONCE) && (gquic_info->version >= 33)){
2261         if(pinfo->srcport == gquic_info->server_port){ /* Diversification nonce is only present from server to client */
2262             proto_tree_add_item(gquic_tree, hf_gquic_diversification_nonce, tvb, offset, 32, ENC_NA);
2263             offset += 32;
2264         }
2265     }
2266 
2267     /* Packet Number */
2268 
2269     /* Get len of packet number */
2270     len_pkn = get_len_packet_number(puflags);
2271     proto_tree_add_item_ret_uint64(gquic_tree, hf_gquic_packet_number, tvb, offset, len_pkn, gquic_info->encoding, &pkn);
2272     offset += len_pkn;
2273 
2274     /* Unencrypt Message (Handshake or Connection Close...) */
2275     if (is_gquic_unencrypt(tvb, pinfo, offset, len_pkn, gquic_info) || g_gquic_debug){
2276         offset = dissect_gquic_unencrypt(tvb, pinfo, gquic_tree, offset, len_pkn, gquic_info);
2277     }else {     /* Payload... (encrypted... TODO FIX !) */
2278         col_add_str(pinfo->cinfo, COL_INFO, "Payload (Encrypted)");
2279         proto_tree_add_item(gquic_tree, hf_gquic_payload, tvb, offset, -1, ENC_NA);
2280 
2281     }
2282 
2283     col_append_fstr(pinfo->cinfo, COL_INFO, ", PKN: %" G_GINT64_MODIFIER "u", pkn);
2284 
2285     if(cid){
2286         col_append_fstr(pinfo->cinfo, COL_INFO, ", CID: %" G_GINT64_MODIFIER "u", cid);
2287     }
2288 
2289 
2290     return offset;
2291 }
2292 
2293 static int
dissect_gquic_q046(tvbuff_t * tvb,packet_info * pinfo,proto_tree * tree,void * data _U_)2294 dissect_gquic_q046(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
2295         void *data _U_)
2296 {
2297     proto_item *ti, *ti_firstbyte; /*, *expert_ti*/
2298     proto_tree *gquic_tree, *firstbyte_tree;
2299     guint offset = 0;
2300     guint8 first_byte, len_cid, cil, len_pkn;
2301     guint64 cid = 0, pkn = 0;
2302     conversation_t  *conv;
2303     gquic_info_data_t  *gquic_info;
2304 
2305     /* get conversation, create if necessary*/
2306     conv = find_or_create_conversation(pinfo);
2307 
2308     /* get associated state information, create if necessary */
2309     gquic_info = (gquic_info_data_t *)conversation_get_proto_data(conv, proto_gquic);
2310 
2311     if (!gquic_info) {
2312         gquic_info = wmem_new(wmem_file_scope(), gquic_info_data_t);
2313         gquic_info->version = 0;
2314         gquic_info->encoding = ENC_BIG_ENDIAN;
2315         gquic_info->version_valid = TRUE;
2316         gquic_info->server_port = 443;
2317         conversation_add_proto_data(conv, proto_gquic, gquic_info);
2318     }
2319 
2320     col_set_str(pinfo->cinfo, COL_PROTOCOL, "GQUIC");
2321 
2322     ti = proto_tree_add_item(tree, proto_gquic, tvb, 0, -1, ENC_NA);
2323     gquic_tree = proto_item_add_subtree(ti, ett_gquic);
2324 
2325     /* First byte */
2326     first_byte = tvb_get_guint8(tvb, offset);
2327     len_pkn = (first_byte & 0x03) + 1;
2328 
2329     ti_firstbyte = proto_tree_add_item(gquic_tree, hf_gquic_puflags, tvb, offset, 1, ENC_NA);
2330     firstbyte_tree = proto_item_add_subtree(ti_firstbyte, ett_gquic_puflags);
2331     proto_tree_add_item(firstbyte_tree, hf_gquic_header_form, tvb, offset, 1, ENC_NA);
2332     proto_tree_add_item(firstbyte_tree, hf_gquic_fixed_bit, tvb, offset, 1, ENC_NA);
2333 
2334     if((first_byte & PUFLAGS_MPTH) && (first_byte & PUFLAGS_RSV)) {
2335         /* Long Header. We handle only Q046 */
2336 
2337 	gquic_info->version_valid = ws_strtou8(tvb_get_string_enc(pinfo->pool, tvb,
2338             offset + 2, 3, ENC_ASCII), NULL, &gquic_info->version);
2339         if (!gquic_info->version_valid) {
2340             expert_add_info(pinfo, gquic_tree, &ei_gquic_version_invalid);
2341         }
2342 
2343 	cil = tvb_get_guint8(tvb, offset + 5);
2344 	if(pinfo->srcport == gquic_info->server_port) { /* Server to client */
2345 	    len_cid = (cil & 0x0F) + 3;
2346 	} else {
2347 	    len_cid = ((cil & 0xF0) >> 4) + 3;
2348 	}
2349 	if (len_cid != 8) {
2350             expert_add_info(pinfo, gquic_tree, &ei_gquic_invalid_parameter);
2351         }
2352 
2353         proto_tree_add_item(firstbyte_tree, hf_gquic_long_packet_type, tvb, offset, 1, ENC_NA);
2354         proto_tree_add_item(firstbyte_tree, hf_gquic_long_reserved, tvb, offset, 1, ENC_NA);
2355         proto_tree_add_item(firstbyte_tree, hf_gquic_packet_number_length, tvb, offset, 1, ENC_NA);
2356         offset += 1;
2357 
2358         proto_tree_add_item(gquic_tree, hf_gquic_version, tvb, offset, 4, ENC_ASCII|ENC_NA);
2359         offset += 4;
2360 
2361         proto_tree_add_item(gquic_tree, hf_gquic_dcil, tvb, offset, 1, ENC_NA);
2362         proto_tree_add_item(gquic_tree, hf_gquic_scil, tvb, offset, 1, ENC_NA);
2363         offset += 1;
2364 
2365         /* CID */
2366         if (len_cid > 0) {
2367             cid = tvb_get_guint64(tvb, offset, gquic_info->encoding);
2368             proto_tree_add_item(gquic_tree, hf_gquic_cid, tvb, offset, len_cid, gquic_info->encoding);
2369         }
2370         offset += len_cid;
2371 
2372     } else {
2373         /* Short Header. We handle only Q046 */
2374 
2375         proto_tree_add_uint(firstbyte_tree, hf_gquic_packet_number_length, tvb, offset, 1, first_byte);
2376 
2377         offset += 1;
2378 
2379         if(pinfo->srcport == gquic_info->server_port) { /* Server to client */
2380             len_cid = 0;
2381         } else {
2382             len_cid = 8;
2383             cid = tvb_get_guint64(tvb, offset, gquic_info->encoding);
2384             proto_tree_add_item(gquic_tree, hf_gquic_cid, tvb, offset, len_cid, gquic_info->encoding);
2385         }
2386         offset += len_cid;
2387     }
2388 
2389     /* Packet Number */
2390     proto_tree_add_item_ret_uint64(gquic_tree, hf_gquic_packet_number, tvb, offset, len_pkn, gquic_info->encoding, &pkn);
2391     offset += len_pkn;
2392 
2393     /* Unencrypt Message (Handshake or Connection Close...) */
2394     if (is_gquic_unencrypt(tvb, pinfo, offset, len_pkn, gquic_info) || g_gquic_debug){
2395         offset = dissect_gquic_unencrypt(tvb, pinfo, gquic_tree, offset, len_pkn, gquic_info);
2396     }else {     /* Payload... (encrypted... TODO FIX !) */
2397         col_add_str(pinfo->cinfo, COL_INFO, "Payload (Encrypted)");
2398         proto_tree_add_item(gquic_tree, hf_gquic_payload, tvb, offset, -1, ENC_NA);
2399 
2400     }
2401 
2402     col_append_fstr(pinfo->cinfo, COL_INFO, ", PKN: %" G_GINT64_MODIFIER "u", pkn);
2403 
2404     if(cid){
2405         col_append_fstr(pinfo->cinfo, COL_INFO, ", CID: %" G_GINT64_MODIFIER "u", cid);
2406     }
2407 
2408     return offset;
2409 }
2410 
2411 static int
dissect_gquic(tvbuff_t * tvb,packet_info * pinfo,proto_tree * tree,void * data _U_)2412 dissect_gquic(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
2413               void *data _U_)
2414 {
2415     guint8 flags;
2416 
2417     flags = tvb_get_guint8(tvb, 0);
2418     if((flags & PUFLAGS_RSV) == 0 && (flags & PUFLAGS_MPTH) == 0)
2419         return dissect_gquic_common(tvb, pinfo, tree, NULL);
2420     return dissect_gquic_q046(tvb, pinfo, tree, NULL);
2421 }
2422 
dissect_gquic_heur(tvbuff_t * tvb,packet_info * pinfo,proto_tree * tree,void * data)2423 static gboolean dissect_gquic_heur(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
2424 {
2425 
2426     conversation_t *conversation = NULL;
2427     int offset = 0;
2428     guint8 flags;
2429     guint32 version;
2430 
2431     if (tvb_captured_length(tvb) < 1) {
2432         return FALSE;
2433     }
2434     flags = tvb_get_guint8(tvb, offset);
2435     offset += 1;
2436 
2437     if((flags & PUFLAGS_RSV) == 0 && (flags & PUFLAGS_MPTH) == 0) {
2438         /* It may be <= Q043 */
2439 
2440         /* Verify packet size  (Flag (1 byte) + Connection ID (8 bytes) + Version (4 bytes)) */
2441         if (tvb_captured_length(tvb) < 13) {
2442             return FALSE;
2443         }
2444 
2445         /* Check if flags version is set */
2446         if((flags & PUFLAGS_VRSN) == 0) {
2447             return FALSE;
2448         }
2449 
2450         /* Connection ID is always set to "long" (8bytes) too */
2451         if((flags & PUFLAGS_CID) == 0){
2452             return FALSE;
2453         }
2454         offset += 8;
2455 
2456         /* Check if version start with Q02... (0x51 0x30 0x32), Q03... (0x51 0x30 0x33) or Q04... (0x51 0x30 0x34) */
2457         version = tvb_get_ntoh24(tvb, offset);
2458         if ( version == GQUIC_MAGIC2 || version == GQUIC_MAGIC3 || version == GQUIC_MAGIC4) {
2459             conversation = find_or_create_conversation(pinfo);
2460             conversation_set_dissector(conversation, gquic_handle);
2461             dissect_gquic(tvb, pinfo, tree, data);
2462             return TRUE;
2463         }
2464     } else if((flags & PUFLAGS_MPTH) && (flags & PUFLAGS_RSV)) {
2465         /* It may be > Q043, Long Header. We handle only Q046 */
2466 
2467         /* Verify packet size  (Flag (1 byte) + Version (4) + DCIL/SCIL (1) + Dest Connection ID (8 bytes)) */
2468         if (tvb_captured_length(tvb) < 14) {
2469             return FALSE;
2470         }
2471 
2472         version = tvb_get_ntohl(tvb, offset);
2473         if (version != GQUIC_VERSION_Q046) {
2474             return FALSE;
2475         }
2476 
2477         conversation = find_or_create_conversation(pinfo);
2478         conversation_set_dissector(conversation, gquic_handle);
2479         dissect_gquic(tvb, pinfo, tree, data);
2480         return TRUE;
2481     }
2482 
2483     return FALSE;
2484 }
2485 
2486 void
proto_register_gquic(void)2487 proto_register_gquic(void)
2488 {
2489     module_t *gquic_module;
2490 
2491     static hf_register_info hf[] = {
2492         /* Long/Short header for Q046 */
2493         { &hf_gquic_header_form,
2494           { "Header Form", "gquic.header_form",
2495             FT_UINT8, BASE_DEC, VALS(gquic_short_long_header_vals), 0x80,
2496             "The most significant bit (0x80) of the first octet is set to 1 for long headers and 0 for short headers.", HFILL }
2497         },
2498         { &hf_gquic_fixed_bit,
2499           { "Fixed Bit", "gquic.fixed_bit",
2500             FT_BOOLEAN, 8, NULL, 0x40,
2501             "Must be 1", HFILL }
2502         },
2503         { &hf_gquic_long_packet_type,
2504           { "Packet Type", "gquic.long.packet_type",
2505             FT_UINT8, BASE_DEC, VALS(gquic_long_packet_type_vals), 0x30,
2506             "Long Header Packet Type", HFILL }
2507         },
2508         { &hf_gquic_long_reserved,
2509           { "Reserved", "gquic.long.reserved",
2510             FT_UINT8, BASE_DEC, NULL, 0x0c,
2511             "Reserved bits", HFILL }
2512         },
2513         { &hf_gquic_packet_number_length,
2514           { "Packet Number Length", "gquic.packet_number_length",
2515             FT_UINT8, BASE_DEC, VALS(gquic_packet_number_lengths), 0x03,
2516             "Packet Number field length", HFILL }
2517 	},
2518         { &hf_gquic_dcil,
2519           { "Destination Connection ID Length", "gquic.dcil",
2520             FT_UINT8, BASE_DEC, VALS(quic_cid_lengths), 0xF0,
2521             NULL, HFILL }
2522         },
2523         { &hf_gquic_scil,
2524           { "Source Connection ID Length", "gquic.scil",
2525             FT_UINT8, BASE_DEC, VALS(quic_cid_lengths), 0x0F,
2526             NULL, HFILL }
2527         },
2528 
2529         /* Public header for < Q046 */
2530         { &hf_gquic_puflags,
2531             { "Public Flags", "gquic.puflags",
2532               FT_UINT8, BASE_HEX, NULL, 0x0,
2533               "Specifying per-packet public flags", HFILL }
2534         },
2535         { &hf_gquic_puflags_vrsn,
2536             { "Version", "gquic.puflags.version",
2537               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PUFLAGS_VRSN,
2538               "Signifies that this packet also contains the version of the (Google)QUIC protocol", HFILL }
2539         },
2540         { &hf_gquic_puflags_rst,
2541             { "Reset", "gquic.puflags.reset",
2542               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PUFLAGS_RST,
2543               "Signifies that this packet is a public reset packet", HFILL }
2544         },
2545         { &hf_gquic_puflags_dnonce,
2546             { "Diversification nonce", "gquic.puflags.nonce",
2547               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PUFLAGS_DNONCE,
2548               "Indicates the presence of a 32 byte diversification nonce", HFILL }
2549         },
2550         { &hf_gquic_puflags_cid,
2551             { "CID Length", "gquic.puflags.cid",
2552               FT_BOOLEAN, 8, TFS(&puflags_cid_tfs), PUFLAGS_CID,
2553               "Indicates the full 8 byte Connection ID is present", HFILL }
2554         },
2555         { &hf_gquic_puflags_cid_old,
2556             { "CID Length", "gquic.puflags.cid.old",
2557               FT_UINT8, BASE_HEX, VALS(puflags_cid_old_vals), PUFLAGS_CID_OLD,
2558               "Signifies the Length of CID", HFILL }
2559         },
2560         { &hf_gquic_puflags_pkn,
2561             { "Packet Number Length", "gquic.puflags.pkn",
2562               FT_UINT8, BASE_HEX, VALS(puflags_pkn_vals), PUFLAGS_PKN,
2563               "Signifies the Length of packet number", HFILL }
2564         },
2565         { &hf_gquic_puflags_mpth,
2566             { "Multipath", "gquic.puflags.mpth",
2567               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PUFLAGS_MPTH,
2568               "Reserved for multipath use", HFILL }
2569         },
2570         { &hf_gquic_puflags_rsv,
2571             { "Reserved", "gquic.puflags.rsv",
2572               FT_UINT8, BASE_HEX, NULL, PUFLAGS_RSV,
2573               "Must be Zero", HFILL }
2574         },
2575         { &hf_gquic_cid,
2576             { "CID", "gquic.cid",
2577               FT_UINT64, BASE_DEC, NULL, 0x0,
2578               "Connection ID 64 bit pseudo random number", HFILL }
2579         },
2580         { &hf_gquic_version,
2581             { "Version", "gquic.version",
2582               FT_STRING, BASE_NONE, NULL, 0x0,
2583               "32 bit opaque tag that represents the version of the (Google)QUIC", HFILL }
2584         },
2585         { &hf_gquic_diversification_nonce,
2586             { "Diversification nonce", "gquic.diversification_nonce",
2587               FT_BYTES, BASE_NONE, NULL, 0x0,
2588               NULL, HFILL }
2589         },
2590         { &hf_gquic_packet_number,
2591             { "Packet Number", "gquic.packet_number",
2592               FT_UINT64, BASE_DEC, NULL, 0x0,
2593               "The lower 8, 16, 32, or 48 bits of the packet number", HFILL }
2594         },
2595 
2596         { &hf_gquic_prflags,
2597             { "Private Flags", "gquic.prflags",
2598               FT_UINT8, BASE_HEX, NULL, 0x0,
2599               "Specifying per-packet Private flags", HFILL }
2600         },
2601 
2602         { &hf_gquic_prflags_entropy,
2603             { "Entropy", "gquic.prflags.entropy",
2604               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PRFLAGS_ENTROPY,
2605               "For data packets, signifies that this packet contains the 1 bit of entropy, for fec packets, contains the xor of the entropy of protected packets", HFILL }
2606         },
2607         { &hf_gquic_prflags_fecg,
2608             { "FEC Group", "gquic.prflags.fecg",
2609               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PRFLAGS_FECG,
2610               "Indicates whether the fec byte is present.", HFILL }
2611         },
2612         { &hf_gquic_prflags_fec,
2613             { "FEC", "gquic.prflags.fec",
2614               FT_BOOLEAN, 8, TFS(&tfs_yes_no), PRFLAGS_FEC,
2615               "Signifies that this packet represents an FEC packet", HFILL }
2616         },
2617         { &hf_gquic_prflags_rsv,
2618             { "Reserved", "gquic.prflags.rsv",
2619               FT_UINT8, BASE_HEX, NULL, PRFLAGS_RSV,
2620               "Must be Zero", HFILL }
2621         },
2622 
2623         { &hf_gquic_message_authentication_hash,
2624             { "Message Authentication Hash", "gquic.message_authentication_hash",
2625               FT_BYTES, BASE_NONE, NULL, 0x0,
2626               "The hash is an FNV1a-128 hash, serialized in little endian order", HFILL }
2627         },
2628         { &hf_gquic_frame,
2629             { "Frame", "gquic.frame",
2630               FT_NONE, BASE_NONE, NULL, 0x0,
2631               NULL, HFILL }
2632         },
2633         { &hf_gquic_frame_type,
2634             { "Frame Type", "gquic.frame_type",
2635               FT_UINT8 ,BASE_RANGE_STRING | BASE_HEX, RVALS(frame_type_vals), 0x0,
2636               NULL, HFILL }
2637         },
2638         { &hf_gquic_frame_type_padding_length,
2639             { "Padding Length", "gquic.frame_type.padding.length",
2640               FT_UINT32, BASE_DEC, NULL, 0x0,
2641               NULL, HFILL }
2642         },
2643         { &hf_gquic_frame_type_padding,
2644             { "Padding", "gquic.frame_type.padding",
2645               FT_BYTES, BASE_NONE, NULL, 0x0,
2646               "Must be zero", HFILL }
2647         },
2648         { &hf_gquic_frame_type_rsts_stream_id,
2649             { "Stream ID", "gquic.frame_type.rsts.stream_id",
2650               FT_UINT32, BASE_DEC, NULL, 0x0,
2651               "Stream ID of the stream being terminated", HFILL }
2652         },
2653         { &hf_gquic_frame_type_rsts_byte_offset,
2654             { "Byte offset", "gquic.frame_type.rsts.byte_offset",
2655               FT_UINT64, BASE_DEC, NULL, 0x0,
2656               "Indicating the absolute byte offset of the end of data for this stream", HFILL }
2657         },
2658         { &hf_gquic_frame_type_rsts_error_code,
2659             { "Error code", "gquic.frame_type.rsts.error_code",
2660               FT_UINT32, BASE_DEC|BASE_EXT_STRING, &rststream_error_code_vals_ext, 0x0,
2661               "Indicates why the stream is being closed", HFILL }
2662         },
2663         { &hf_gquic_frame_type_cc_error_code,
2664             { "Error code", "gquic.frame_type.cc.error_code",
2665               FT_UINT32, BASE_DEC|BASE_EXT_STRING, &error_code_vals_ext, 0x0,
2666               "Indicates the reason for closing this connection", HFILL }
2667         },
2668         { &hf_gquic_frame_type_cc_reason_phrase_length,
2669             { "Reason phrase Length", "gquic.frame_type.cc.reason_phrase.length",
2670               FT_UINT16, BASE_DEC, NULL, 0x0,
2671               "Specifying the length of the reason phrase", HFILL }
2672         },
2673         { &hf_gquic_frame_type_cc_reason_phrase,
2674             { "Reason phrase", "gquic.frame_type.cc.reason_phrase",
2675               FT_STRING, BASE_NONE, NULL, 0x0,
2676               "An optional human-readable explanation for why the connection was closed", HFILL }
2677         },
2678         { &hf_gquic_frame_type_goaway_error_code,
2679             { "Error code", "gquic.frame_type.goaway.error_code",
2680               FT_UINT32, BASE_DEC|BASE_EXT_STRING, &error_code_vals_ext, 0x0,
2681               "Indicates the reason for closing this connection", HFILL }
2682         },
2683         { &hf_gquic_frame_type_goaway_last_good_stream_id,
2684             { "Last Good Stream ID", "gquic.frame_type.goaway.last_good_stream_id",
2685               FT_UINT32, BASE_DEC, NULL, 0x0,
2686               "last Stream ID which was accepted by the sender of the GOAWAY message", HFILL }
2687         },
2688         { &hf_gquic_frame_type_goaway_reason_phrase_length,
2689             { "Reason phrase Length", "gquic.frame_type.goaway.reason_phrase.length",
2690               FT_UINT16, BASE_DEC, NULL, 0x0,
2691               "Specifying the length of the reason phrase", HFILL }
2692         },
2693         { &hf_gquic_frame_type_goaway_reason_phrase,
2694             { "Reason phrase", "gquic.frame_type.goaway.reason_phrase",
2695               FT_STRING, BASE_NONE, NULL, 0x0,
2696               "An optional human-readable explanation for why the connection was closed", HFILL }
2697         },
2698         { &hf_gquic_frame_type_wu_stream_id,
2699             { "Stream ID", "gquic.frame_type.wu.stream_id",
2700               FT_UINT32, BASE_DEC, NULL, 0x0,
2701               "ID of the stream whose flow control windows is begin updated, or 0 to specify the connection-level flow control window", HFILL }
2702         },
2703         { &hf_gquic_frame_type_wu_byte_offset,
2704             { "Byte offset", "gquic.frame_type.wu.byte_offset",
2705               FT_UINT64, BASE_DEC, NULL, 0x0,
2706               "Indicating the absolute byte offset of data which can be sent on the given stream", HFILL }
2707         },
2708         { &hf_gquic_frame_type_blocked_stream_id,
2709             { "Stream ID", "gquic.frame_type.blocked.stream_id",
2710               FT_UINT32, BASE_DEC, NULL, 0x0,
2711               "Indicating the stream which is flow control blocked", HFILL }
2712         },
2713         { &hf_gquic_frame_type_sw_send_entropy,
2714             { "Send Entropy", "gquic.frame_type.sw.send_entropy",
2715               FT_UINT8, BASE_DEC, NULL, 0x0,
2716               "Specifying the cumulative hash of entropy in all sent packets up to the packet with packet number one less than the least unacked packet", HFILL }
2717         },
2718         { &hf_gquic_frame_type_sw_least_unacked_delta,
2719             { "Least unacked delta", "gquic.frame_type.sw.least_unacked_delta",
2720               FT_UINT64, BASE_DEC, NULL, 0x0,
2721               "A variable length packet number delta with the same length as the packet header's packet number", HFILL }
2722         },
2723         { &hf_gquic_crypto_offset,
2724             { "Offset", "gquic.crypto.offset",
2725               FT_UINT64, BASE_DEC, NULL, 0x0,
2726               "Byte offset into the stream", HFILL }
2727         },
2728         { &hf_gquic_crypto_length,
2729             { "Length", "gquic.crypto.length",
2730               FT_UINT64, BASE_DEC, NULL, 0x0,
2731               "Length of the Crypto Data field", HFILL }
2732         },
2733         { &hf_gquic_crypto_crypto_data,
2734             { "Crypto Data", "gquic.crypto.crypto_data",
2735               FT_NONE, BASE_NONE, NULL, 0x0,
2736               "The cryptographic message data", HFILL }
2737         },
2738         { &hf_gquic_frame_type_stream,
2739             { "Stream", "gquic.frame_type.stream",
2740               FT_BOOLEAN, 8, NULL, FTFLAGS_STREAM,
2741               NULL, HFILL }
2742         },
2743         { &hf_gquic_frame_type_stream_f,
2744             { "FIN", "gquic.frame_type.stream.f",
2745               FT_BOOLEAN, 8, NULL, FTFLAGS_STREAM_F,
2746               NULL, HFILL }
2747         },
2748         { &hf_gquic_frame_type_stream_d,
2749             { "Data Length", "gquic.frame_type.stream.d",
2750               FT_BOOLEAN, 8, TFS(&len_data_vals), FTFLAGS_STREAM_D,
2751               NULL, HFILL }
2752         },
2753         { &hf_gquic_frame_type_stream_ooo,
2754             { "Offset Length", "gquic.frame_type.stream.ooo",
2755               FT_UINT8, BASE_DEC, VALS(len_offset_vals), FTFLAGS_STREAM_OOO,
2756               NULL, HFILL }
2757         },
2758         { &hf_gquic_frame_type_stream_ss,
2759             { "Stream Length", "gquic.frame_type.stream.ss",
2760               FT_UINT8, BASE_DEC, VALS(len_stream_vals), FTFLAGS_STREAM_SS,
2761               NULL, HFILL }
2762         },
2763         { &hf_gquic_frame_type_ack,
2764             { "ACK", "gquic.frame_type.ack",
2765               FT_BOOLEAN, 8, NULL, FTFLAGS_ACK,
2766               NULL, HFILL }
2767         },
2768         { &hf_gquic_frame_type_ack_n,
2769             { "NACK", "gquic.frame_type.ack.n",
2770               FT_BOOLEAN, 8, NULL, FTFLAGS_ACK_N,
2771               NULL, HFILL }
2772         },
2773         { &hf_gquic_frame_type_ack_u,
2774             { "Unused", "gquic.frame_type.ack.u",
2775               FT_BOOLEAN, 8, NULL, FTFLAGS_ACK_U,
2776               NULL, HFILL }
2777         },
2778         { &hf_gquic_frame_type_ack_t,
2779             { "Truncated", "gquic.frame_type.ack.t",
2780               FT_BOOLEAN, 8, NULL, FTFLAGS_ACK_T,
2781               NULL, HFILL }
2782         },
2783         { &hf_gquic_frame_type_ack_ll,
2784             { "Largest Observed Length", "gquic.frame_type.ack.ll",
2785               FT_UINT8, BASE_DEC, VALS(len_largest_observed_vals), FTFLAGS_ACK_LL,
2786               "Length of the Largest Observed field as 1, 2, 4, or 6 bytes long", HFILL }
2787         },
2788         { &hf_gquic_frame_type_ack_mm,
2789             { "Missing Packet Length", "gquic.frame_type.ack.mm",
2790               FT_UINT8, BASE_DEC, VALS(len_missing_packet_vals), FTFLAGS_ACK_MM,
2791               "Length of the Missing Packet Number Delta field as 1, 2, 4, or 6 bytes long", HFILL }
2792         },
2793         /* ACK before Q034 */
2794         { &hf_gquic_frame_type_ack_received_entropy,
2795             { "Received Entropy", "gquic.frame_type.ack.received_entropy",
2796               FT_UINT8, BASE_DEC, NULL, 0x0,
2797               "Specifying the cumulative hash of entropy in all received packets up to the largest observed packet", HFILL }
2798         },
2799         { &hf_gquic_frame_type_ack_largest_observed,
2800             { "Largest Observed", "gquic.frame_type.ack.largest_observed",
2801               FT_UINT64, BASE_DEC, NULL, 0x0,
2802               "Representing the largest packet number the peer has observed", HFILL }
2803         },
2804         { &hf_gquic_frame_type_ack_ack_delay_time,
2805             { "Ack Delay time", "gquic.frame_type.ack.ack_delay_time",
2806               FT_UINT16, BASE_DEC, NULL, 0x0,
2807               "Specifying the time elapsed in microseconds from when largest observed was received until this Ack frame was sent", HFILL }
2808         },
2809         { &hf_gquic_frame_type_ack_num_timestamp,
2810             { "Num Timestamp", "gquic.frame_type.ack.num_timestamp",
2811               FT_UINT8, BASE_DEC, NULL, 0x0,
2812               "Specifying the number of TCP timestamps that are included in this frame", HFILL }
2813         },
2814         { &hf_gquic_frame_type_ack_delta_largest_observed,
2815             { "Delta Largest Observed", "gquic.frame_type.ack.delta_largest_observed",
2816               FT_UINT8, BASE_DEC, NULL, 0x0,
2817               "Specifying the packet number delta from the first timestamp to the largest observed", HFILL }
2818         },
2819         { &hf_gquic_frame_type_ack_first_timestamp,
2820             { "First Timestamp", "gquic.frame_type.ack.first_timestamp",
2821               FT_UINT32, BASE_DEC, NULL, 0x0,
2822               "Specifying the time delta in microseconds, from the beginning of the connection of the arrival of the packet specified by Largest Observed minus Delta Largest Observed", HFILL }
2823         },
2824         { &hf_gquic_frame_type_ack_time_since_previous_timestamp,
2825             { "Time since Previous timestamp", "gquic.frame_type.ack.time_since_previous_timestamp",
2826               FT_UINT16, BASE_DEC, NULL, 0x0,
2827               "This is the time delta from the previous timestamp", HFILL }
2828         },
2829         { &hf_gquic_frame_type_ack_num_ranges,
2830             { "Num Ranges", "gquic.frame_type.ack.num_ranges",
2831               FT_UINT8, BASE_DEC, NULL, 0x0,
2832               "Specifying the number of missing packet ranges between largest observed and least unacked", HFILL }
2833         },
2834         { &hf_gquic_frame_type_ack_missing_packet,
2835             { "Missing Packet Packet Number Delta", "gquic.frame_type.ack.missing_packet",
2836               FT_UINT64, BASE_DEC, NULL, 0x0,
2837               NULL, HFILL }
2838         },
2839         { &hf_gquic_frame_type_ack_range_length,
2840             { "Range Length", "gquic.frame_type.ack.range_length",
2841               FT_UINT8, BASE_DEC, NULL, 0x0,
2842               "Specifying one less than the number of sequential nacks in the range", HFILL }
2843         },
2844         { &hf_gquic_frame_type_ack_num_revived,
2845             { "Num Revived", "gquic.frame_type.ack.num_revived",
2846               FT_UINT8, BASE_DEC, NULL, 0x0,
2847               "Specifying the number of revived packets, recovered via FEC", HFILL }
2848         },
2849         { &hf_gquic_frame_type_ack_revived_packet,
2850             { "Revived Packet Packet Number", "gquic.frame_type.ack.revived_packet",
2851               FT_UINT64, BASE_DEC, NULL, 0x0,
2852               "Representing a packet the peer has revived via FEC", HFILL }
2853         },
2854         /* ACK after Q034 */
2855         { &hf_gquic_frame_type_ack_largest_acked,
2856             { "Largest Acked", "gquic.frame_type.ack.largest_acked",
2857               FT_UINT64, BASE_DEC, NULL, 0x0,
2858               "Representing the largest packet number the peer has observed", HFILL }
2859         },
2860         { &hf_gquic_frame_type_ack_largest_acked_delta_time,
2861             { "Largest Acked Delta Time", "gquic.frame_type.ack.largest_acked_delta_time",
2862               FT_UINT16, BASE_DEC, NULL, 0x0,
2863               "Specifying the time elapsed in microseconds from when largest acked was received until this Ack frame was sent", HFILL }
2864         },
2865         { &hf_gquic_frame_type_ack_num_blocks,
2866             { "Num blocks", "gquic.frame_type.ack.num_blocks",
2867               FT_UINT8, BASE_DEC, NULL, 0x0,
2868               "Specifying one less than the number of ack blocks", HFILL }
2869         },
2870         { &hf_gquic_frame_type_ack_first_ack_block_length,
2871             { "First Ack block length", "gquic.frame_type.ack.first_ack_block_length",
2872               FT_UINT64, BASE_DEC, NULL, 0x0,
2873               NULL, HFILL }
2874         },
2875         { &hf_gquic_frame_type_ack_gap_to_next_block,
2876             { "Gap to next block", "gquic.frame_type.ack.gap_to_next_block",
2877               FT_UINT8, BASE_DEC, NULL, 0x0,
2878               "Specifying the number of packets between ack blocks", HFILL }
2879         },
2880         { &hf_gquic_frame_type_ack_ack_block_length,
2881             { "Ack block length", "gquic.frame_type.ack.ack_block_length",
2882               FT_UINT64, BASE_DEC, NULL, 0x0,
2883               NULL, HFILL }
2884         },
2885         { &hf_gquic_frame_type_ack_delta_largest_acked,
2886             { "Delta Largest Observed", "gquic.frame_type.ack.delta_largest_acked",
2887               FT_UINT8, BASE_DEC, NULL, 0x0,
2888               "Specifying the packet number delta from the first timestamp to the largest observed", HFILL }
2889         },
2890         { &hf_gquic_frame_type_ack_time_since_largest_acked,
2891             { "Time Since Largest Acked", "gquic.frame_type.ack.time_since_largest_acked",
2892               FT_UINT32, BASE_DEC, NULL, 0x0,
2893               "Specifying the time delta in microseconds, from the beginning of the connection of the arrival of the packet specified by Largest Observed minus Delta Largest Observed", HFILL }
2894         },
2895 
2896 
2897 
2898         { &hf_gquic_stream_id,
2899             { "Stream ID", "gquic.stream_id",
2900               FT_UINT32, BASE_DEC, NULL, 0x0,
2901               NULL, HFILL }
2902         },
2903         { &hf_gquic_offset,
2904             { "Offset", "gquic.offset",
2905               FT_UINT64, BASE_DEC, NULL, 0x0,
2906               NULL, HFILL }
2907         },
2908         { &hf_gquic_data_len,
2909             { "Data Length", "gquic.data_len",
2910               FT_UINT32, BASE_DEC, NULL, 0x0,
2911               NULL, HFILL }
2912         },
2913         { &hf_gquic_tag,
2914             { "Tag", "gquic.tag",
2915               FT_STRING, BASE_NONE, NULL, 0x0,
2916               NULL, HFILL }
2917         },
2918         { &hf_gquic_tag_number,
2919             { "Tag Number", "gquic.tag_number",
2920               FT_UINT16, BASE_DEC, NULL, 0x0,
2921               NULL, HFILL }
2922         },
2923         { &hf_gquic_tags,
2924             { "Tag/value", "gquic.tags",
2925               FT_NONE, BASE_NONE, NULL, 0x0,
2926               NULL, HFILL }
2927         },
2928         { &hf_gquic_tag_type,
2929             { "Tag Type", "gquic.tag_type",
2930               FT_STRING, BASE_NONE, NULL, 0x0,
2931               NULL, HFILL }
2932         },
2933         { &hf_gquic_tag_offset_end,
2934             { "Tag offset end", "gquic.tag_offset_end",
2935               FT_UINT32, BASE_DEC, NULL, 0x0,
2936               NULL, HFILL }
2937         },
2938         { &hf_gquic_tag_length,
2939             { "Tag length", "gquic.tag_offset_length",
2940               FT_UINT32, BASE_DEC, NULL, 0x0,
2941               NULL, HFILL }
2942         },
2943         { &hf_gquic_tag_value,
2944             { "Tag/value", "gquic.tag_value",
2945               FT_BYTES, BASE_NONE, NULL, 0x0,
2946               NULL, HFILL }
2947         },
2948         { &hf_gquic_tag_sni,
2949             { "Server Name Indication", "gquic.tag.sni",
2950               FT_STRING, BASE_NONE, NULL, 0x0,
2951               "The fully qualified DNS name of the server, canonicalised to lowercase with no trailing period", HFILL }
2952         },
2953         { &hf_gquic_tag_pad,
2954             { "Padding", "gquic.tag.pad",
2955               FT_BYTES, BASE_NONE, NULL, 0x0,
2956               "Pad.....", HFILL }
2957         },
2958         { &hf_gquic_tag_ver,
2959             { "Version", "gquic.tag.version",
2960               FT_STRING, BASE_NONE, NULL, 0x0,
2961               "Version of gquic supported", HFILL }
2962         },
2963         { &hf_gquic_tag_pdmd,
2964             { "Proof demand", "gquic.tag.pdmd",
2965               FT_STRING, BASE_NONE, NULL, 0x0,
2966               "a list of tags describing the types of proof acceptable to the client, in preference order", HFILL }
2967         },
2968         { &hf_gquic_tag_ccs,
2969             { "Common certificate sets", "gquic.tag.ccs",
2970               FT_UINT64, BASE_HEX, NULL, 0x0,
2971               "A series of 64-bit, FNV-1a hashes of sets of common certificates that the client possesses", HFILL }
2972         },
2973         { &hf_gquic_tag_uaid,
2974             { "Client's User Agent ID", "gquic.tag.uaid",
2975               FT_STRING, BASE_NONE, NULL, 0x0,
2976               NULL, HFILL }
2977         },
2978         { &hf_gquic_tag_stk,
2979             { "Source-address token", "gquic.tag.stk",
2980               FT_BYTES, BASE_NONE, NULL, 0x0,
2981               NULL, HFILL }
2982         },
2983         { &hf_gquic_tag_sno,
2984             { "Server nonce", "gquic.tag.sno",
2985               FT_BYTES, BASE_NONE, NULL, 0x0,
2986               NULL, HFILL }
2987         },
2988         { &hf_gquic_tag_prof,
2989             { "Proof (Signature)", "gquic.tag.prof",
2990               FT_BYTES, BASE_NONE, NULL, 0x0,
2991               NULL, HFILL }
2992         },
2993         { &hf_gquic_tag_scfg,
2994             { "Server Config Tag", "gquic.tag.scfg",
2995               FT_STRING, BASE_NONE, NULL, 0x0,
2996               NULL, HFILL }
2997         },
2998         { &hf_gquic_tag_scfg_number,
2999             { "Number Server Config Tag", "gquic.tag.scfg.number",
3000               FT_UINT32, BASE_DEC, NULL, 0x0,
3001               NULL, HFILL }
3002         },
3003         { &hf_gquic_tag_rrej,
3004             { "Reasons for server sending", "gquic.tag.rrej",
3005               FT_UINT32, BASE_DEC|BASE_EXT_STRING, &handshake_failure_reason_vals_ext, 0x0,
3006               NULL, HFILL }
3007         },
3008         { &hf_gquic_tag_crt,
3009             { "Certificate chain", "gquic.tag.crt",
3010               FT_BYTES, BASE_NONE, NULL, 0x0,
3011               NULL, HFILL }
3012         },
3013         { &hf_gquic_tag_aead,
3014             { "Authenticated encryption algorithms", "gquic.tag.aead",
3015               FT_STRING, BASE_NONE, NULL, 0x0,
3016               "A list of tags, in preference order, specifying the AEAD primitives supported by the server", HFILL }
3017         },
3018         { &hf_gquic_tag_scid,
3019             { "Server Config ID", "gquic.tag.scid",
3020               FT_BYTES, BASE_NONE, NULL, 0x0,
3021               "An opaque, 16-byte identifier for this server config", HFILL }
3022         },
3023         { &hf_gquic_tag_pubs,
3024             { "Public value", "gquic.tag.pubs",
3025               FT_UINT24, BASE_DEC_HEX, NULL, 0x0,
3026               "A list of public values, 24-bit, little-endian length prefixed", HFILL }
3027         },
3028         { &hf_gquic_tag_kexs,
3029             { "Key exchange algorithms", "gquic.tag.kexs",
3030               FT_STRING, BASE_NONE, NULL, 0x0,
3031               "A list of tags, in preference order, specifying the key exchange algorithms that the server supports", HFILL }
3032         },
3033         { &hf_gquic_tag_obit,
3034             { "Server orbit", "gquic.tag.obit",
3035               FT_BYTES, BASE_NONE, NULL, 0x0,
3036               NULL, HFILL }
3037         },
3038         { &hf_gquic_tag_expy,
3039             { "Expiry", "gquic.tag.expy",
3040               FT_UINT64, BASE_DEC, NULL, 0x0,
3041               "a 64-bit expiry time for the server config in UNIX epoch seconds", HFILL }
3042         },
3043         { &hf_gquic_tag_nonc,
3044             { "Client nonce", "gquic.tag.nonc",
3045               FT_BYTES, BASE_NONE, NULL, 0x0,
3046               "32 bytes consisting of 4 bytes of timestamp (big-endian, UNIX epoch seconds), 8 bytes of server orbit and 20 bytes of random data", HFILL }
3047         },
3048         { &hf_gquic_tag_mspc,
3049             { "Max streams per connection", "gquic.tag.mspc",
3050               FT_UINT32, BASE_DEC, NULL, 0x0,
3051               NULL, HFILL }
3052         },
3053         { &hf_gquic_tag_tcid,
3054             { "Connection ID truncation", "gquic.tag.tcid",
3055               FT_UINT32, BASE_DEC_HEX, NULL, 0x0,
3056               NULL, HFILL }
3057         },
3058         { &hf_gquic_tag_srbf,
3059             { "Socket receive buffer", "gquic.tag.srbf",
3060               FT_UINT32, BASE_DEC_HEX, NULL, 0x0,
3061               NULL, HFILL }
3062         },
3063         { &hf_gquic_tag_icsl,
3064             { "Idle connection state", "gquic.tag.icsl",
3065               FT_UINT32, BASE_DEC_HEX, NULL, 0x0,
3066               NULL, HFILL }
3067         },
3068         { &hf_gquic_tag_scls,
3069             { "Silently close on timeout", "gquic.tag.scls",
3070               FT_UINT32, BASE_DEC_HEX, NULL, 0x0,
3071               NULL, HFILL }
3072         },
3073         { &hf_gquic_tag_copt,
3074             { "Connection options", "gquic.tag.copt",
3075               FT_STRING, BASE_NONE, NULL, 0x0,
3076               NULL, HFILL }
3077         },
3078         { &hf_gquic_tag_ccrt,
3079             { "Cached certificates", "gquic.tag.ccrt",
3080               FT_BYTES, BASE_NONE, NULL, 0x0,
3081               NULL, HFILL }
3082         },
3083         { &hf_gquic_tag_irtt,
3084             { "Estimated initial RTT", "gquic.tag.irtt",
3085               FT_UINT32, BASE_DEC, NULL, 0x0,
3086               "in us", HFILL }
3087         },
3088         { &hf_gquic_tag_cfcw,
3089             { "Initial session/connection", "gquic.tag.cfcw",
3090               FT_UINT32, BASE_DEC, NULL, 0x0,
3091               NULL, HFILL }
3092         },
3093         { &hf_gquic_tag_sfcw,
3094             { "Initial stream flow control", "gquic.tag.sfcw",
3095               FT_UINT32, BASE_DEC, NULL, 0x0,
3096               NULL, HFILL }
3097         },
3098         { &hf_gquic_tag_cetv,
3099             { "Client encrypted tag-value", "gquic.tag.cetv",
3100               FT_BYTES, BASE_NONE, NULL, 0x0,
3101               NULL, HFILL }
3102         },
3103         { &hf_gquic_tag_xlct,
3104             { "Expected leaf certificate", "gquic.tag.xlct",
3105               FT_BYTES, BASE_NONE, NULL, 0x0,
3106               NULL, HFILL }
3107         },
3108         { &hf_gquic_tag_nonp,
3109             { "Client Proof nonce", "gquic.tag.nonp",
3110               FT_BYTES, BASE_NONE, NULL, 0x0,
3111               NULL, HFILL }
3112         },
3113         { &hf_gquic_tag_csct,
3114             { "Signed cert timestamp", "gquic.tag.csct",
3115               FT_BYTES, BASE_NONE, NULL, 0x0,
3116               NULL, HFILL }
3117         },
3118         { &hf_gquic_tag_ctim,
3119             { "Client Timestamp", "gquic.tag.ctim",
3120               FT_ABSOLUTE_TIME, ABSOLUTE_TIME_UTC, NULL, 0x0,
3121               NULL, HFILL }
3122         },
3123         { &hf_gquic_tag_rnon,
3124             { "Public reset nonce proof", "gquic.tag.rnon",
3125               FT_UINT64, BASE_DEC, NULL, 0x0,
3126               NULL, HFILL }
3127         },
3128         { &hf_gquic_tag_rseq,
3129             { "Rejected Packet Number", "gquic.tag.rseq",
3130               FT_UINT64, BASE_DEC, NULL, 0x0,
3131               "a 64-bit packet number", HFILL }
3132         },
3133         { &hf_gquic_tag_cadr_addr_type,
3134             { "Client IP Address Type", "gquic.tag.caddr.addr.type",
3135               FT_UINT16, BASE_DEC, VALS(cadr_type_vals), 0x0,
3136               NULL, HFILL }
3137         },
3138         { &hf_gquic_tag_cadr_addr_ipv4,
3139             { "Client IP Address", "gquic.tag.caddr.addr.ipv4",
3140               FT_IPv4, BASE_NONE, NULL, 0x0,
3141               NULL, HFILL }
3142         },
3143         { &hf_gquic_tag_cadr_addr_ipv6,
3144             { "Client IP Address", "gquic.tag.caddr.addr.ipv6",
3145               FT_IPv6, BASE_NONE, NULL, 0x0,
3146               NULL, HFILL }
3147         },
3148         { &hf_gquic_tag_cadr_addr,
3149             { "Client IP Address", "gquic.tag.caddr.addr",
3150               FT_BYTES, BASE_NONE, NULL, 0x0,
3151               NULL, HFILL }
3152         },
3153         { &hf_gquic_tag_cadr_port,
3154             { "Client Port (Source)", "gquic.tag.caddr.port",
3155               FT_UINT16, BASE_DEC, NULL, 0x0,
3156               NULL, HFILL }
3157         },
3158         { &hf_gquic_tag_mids,
3159             { "Max incoming dynamic streams", "gquic.tag.mids",
3160               FT_UINT32, BASE_DEC, NULL, 0x0,
3161               NULL, HFILL }
3162         },
3163         { &hf_gquic_tag_fhol,
3164             { "Force Head Of Line blocking", "gquic.tag.fhol",
3165               FT_UINT32, BASE_DEC, NULL, 0x0,
3166               NULL, HFILL }
3167         },
3168         { &hf_gquic_tag_sttl,
3169             { "Server Config TTL", "gquic.tag.sttl",
3170               FT_UINT64, BASE_DEC, NULL, 0x0,
3171               NULL, HFILL }
3172         },
3173         { &hf_gquic_tag_smhl,
3174             { "Support Max Header List (size)", "gquic.tag.smhl",
3175               FT_UINT64, BASE_DEC, NULL, 0x0,
3176               NULL, HFILL }
3177         },
3178         { &hf_gquic_tag_tbkp,
3179             { "Token Binding Key Params.", "gquic.tag.tbkp",
3180               FT_STRING, BASE_NONE, NULL, 0x0,
3181               NULL, HFILL }
3182         },
3183         { &hf_gquic_tag_mad0,
3184             { "Max Ack Delay", "gquic.tag.mad0",
3185               FT_UINT32, BASE_DEC, NULL, 0x0,
3186               NULL, HFILL }
3187         },
3188         { &hf_gquic_tag_qlve,
3189             { "Legacy Version Encapsulation", "gquic.tag.qlve",
3190               FT_BYTES, BASE_NONE, NULL, 0x0,
3191               NULL, HFILL }
3192         },
3193         { &hf_gquic_tag_cgst,
3194             { "Congestion Control Feedback Type", "gquic.tag.cgst",
3195               FT_BYTES, BASE_NONE, NULL, 0x0,
3196               NULL, HFILL }
3197         },
3198         { &hf_gquic_tag_epid,
3199             { "Endpoint identifier", "gquic.tag.epid",
3200               FT_STRING, BASE_NONE, NULL, 0x0,
3201               NULL, HFILL }
3202         },
3203         { &hf_gquic_tag_srst,
3204             { "Stateless Reset Token", "gquic.tag.srst",
3205               FT_BYTES, BASE_NONE, NULL, 0x0,
3206               NULL, HFILL }
3207         },
3208 
3209         { &hf_gquic_tag_unknown,
3210             { "Unknown tag", "gquic.tag.unknown",
3211               FT_BYTES, BASE_NONE, NULL, 0x0,
3212               NULL, HFILL }
3213         },
3214         { &hf_gquic_padding,
3215             { "Padding", "gquic.padding",
3216               FT_BYTES, BASE_NONE, NULL, 0x0,
3217               NULL, HFILL }
3218         },
3219         { &hf_gquic_stream_data,
3220             { "Stream Data", "gquic.stream_data",
3221               FT_BYTES, BASE_NONE, NULL, 0x0,
3222               NULL, HFILL }
3223         },
3224         { &hf_gquic_payload,
3225             { "Payload", "gquic.payload",
3226               FT_BYTES, BASE_NONE, NULL, 0x0,
3227               "(Google) QUIC Payload..", HFILL }
3228         },
3229     };
3230 
3231 
3232     static gint *ett[] = {
3233         &ett_gquic,
3234         &ett_gquic_puflags,
3235         &ett_gquic_prflags,
3236         &ett_gquic_ft,
3237         &ett_gquic_ftflags,
3238         &ett_gquic_tag_value
3239     };
3240 
3241     static ei_register_info ei[] = {
3242         { &ei_gquic_tag_undecoded, { "gquic.tag.undecoded", PI_UNDECODED, PI_NOTE, "Dissector for (Google)QUIC Tag code not implemented, Contact Wireshark developers if you want this supported", EXPFILL }},
3243         { &ei_gquic_tag_length, { "gquic.tag.length.truncated", PI_MALFORMED, PI_NOTE, "Truncated Tag Length...", EXPFILL }},
3244         { &ei_gquic_tag_unknown, { "gquic.tag.unknown.data", PI_UNDECODED, PI_NOTE, "Unknown Data", EXPFILL }},
3245         { &ei_gquic_version_invalid, { "gquic.version.invalid", PI_MALFORMED, PI_ERROR, "Invalid Version", EXPFILL }},
3246         { &ei_gquic_invalid_parameter, { "gquic.invalid.parameter", PI_MALFORMED, PI_ERROR, "Invalid Parameter", EXPFILL }},
3247         { &ei_gquic_length_invalid, { "gquic.length.invalid", PI_PROTOCOL, PI_WARN, "Invalid Length", EXPFILL }}
3248     };
3249 
3250     expert_module_t *expert_gquic;
3251 
3252     proto_gquic = proto_register_protocol("GQUIC (Google Quick UDP Internet Connections)", "GQUIC", "gquic");
3253 
3254     proto_register_field_array(proto_gquic, hf, array_length(hf));
3255     proto_register_subtree_array(ett, array_length(ett));
3256 
3257     gquic_module = prefs_register_protocol(proto_gquic, NULL);
3258 
3259     prefs_register_bool_preference(gquic_module, "debug.quic",
3260                        "Force decode of all (Google) QUIC Payload",
3261                        "Help for debug...",
3262                        &g_gquic_debug);
3263 
3264     expert_gquic = expert_register_protocol(proto_gquic);
3265     expert_register_field_array(expert_gquic, ei, array_length(ei));
3266 
3267     gquic_handle = register_dissector("gquic", dissect_gquic, proto_gquic);
3268 }
3269 
3270 void
proto_reg_handoff_gquic(void)3271 proto_reg_handoff_gquic(void)
3272 {
3273     tls13_handshake_handle = find_dissector("tls13-handshake");
3274     quic_handle = find_dissector("quic");
3275     dissector_add_uint_range_with_preference("udp.port", "", gquic_handle);
3276     heur_dissector_add("udp", dissect_gquic_heur, "Google QUIC", "gquic", proto_gquic, HEURISTIC_ENABLE);
3277 }
3278 
3279 
3280 /*
3281  * Editor modelines  -  https://www.wireshark.org/tools/modelines.html
3282  *
3283  * Local variables:
3284  * c-basic-offset: 4
3285  * tab-width: 8
3286  * indent-tabs-mode: nil
3287  * End:
3288  *
3289  * vi: set shiftwidth=4 tabstop=8 expandtab:
3290  * :indentSize=4:tabSize=8:noTabs=true:
3291  */
3292