1pub mod builder;
15pub mod frames;
16pub mod headers;
17pub mod varint;
18
19pub use builder::{QuicBuilder, QuicInitialBuilder};
20pub use frames::{FrameType, QuicFrame, parse_frames};
21pub use headers::{QuicLongHeader, QuicPacketType, QuicShortHeader, packet_type};
22pub use varint::{decode as varint_decode, encode as varint_encode};
23
24use crate::layer::field::{FieldDesc, FieldError, FieldType, FieldValue};
25use crate::layer::{Layer, LayerIndex, LayerKind};
26
27pub const QUIC_MIN_HEADER_LEN: usize = 1;
29
30pub static QUIC_FIELDS: &[FieldDesc] = &[
37 FieldDesc::new("header_form", 0, 1, FieldType::U8),
38 FieldDesc::new("fixed_bit", 0, 1, FieldType::U8),
39 FieldDesc::new("packet_type", 0, 1, FieldType::U8),
40 FieldDesc::new("long_packet_type", 0, 1, FieldType::U8),
41 FieldDesc::new("packet_number_len", 0, 1, FieldType::U8),
42 FieldDesc::new("version", 1, 4, FieldType::U32),
43 FieldDesc::new("dst_conn_id_len", 5, 1, FieldType::U8),
45 FieldDesc::new("src_conn_id_len", 5, 1, FieldType::U8),
46 FieldDesc::new("dst_conn_id", 6, 0, FieldType::Bytes),
47 FieldDesc::new("src_conn_id", 6, 0, FieldType::Bytes),
48 FieldDesc::new("length", 6, 8, FieldType::U64),
49 FieldDesc::new("packet_number", 6, 4, FieldType::U32),
50];
51
52#[derive(Debug, Clone)]
58pub struct QuicLayer {
59 pub index: LayerIndex,
60}
61
62impl QuicLayer {
63 pub fn new(start: usize, end: usize) -> Self {
65 Self {
66 index: LayerIndex::new(LayerKind::Quic, start, end),
67 }
68 }
69
70 pub fn from_index(index: LayerIndex) -> Self {
72 Self { index }
73 }
74
75 pub fn is_long_header(&self, buf: &[u8]) -> bool {
81 let slice = self.index.slice(buf);
82 !slice.is_empty() && slice[0] & 0x80 != 0
83 }
84
85 pub fn packet_type(&self, buf: &[u8]) -> Option<QuicPacketType> {
87 let slice = self.index.slice(buf);
88 if slice.is_empty() {
89 return None;
90 }
91 let first = slice[0];
92 let version = if slice.len() >= 5 {
93 u32::from_be_bytes([slice[1], slice[2], slice[3], slice[4]])
94 } else {
95 0
96 };
97 Some(headers::packet_type(first, version))
98 }
99
100 pub fn version(&self, buf: &[u8]) -> Option<u32> {
103 if !self.is_long_header(buf) {
104 return None;
105 }
106 let slice = self.index.slice(buf);
107 if slice.len() < 5 {
108 return None;
109 }
110 Some(u32::from_be_bytes([slice[1], slice[2], slice[3], slice[4]]))
111 }
112
113 pub fn summary(&self, buf: &[u8]) -> String {
115 match self.packet_type(buf) {
116 Some(pt) => format!("QUIC {}", pt.name()),
117 None => "QUIC".to_string(),
118 }
119 }
120
121 pub fn header_len(&self, buf: &[u8]) -> usize {
127 let slice = self.index.slice(buf);
128 if slice.is_empty() {
129 return QUIC_MIN_HEADER_LEN;
130 }
131
132 if self.is_long_header(buf) {
133 match QuicLongHeader::parse(slice) {
134 Some(hdr) => hdr.header_len,
135 None => QUIC_MIN_HEADER_LEN,
136 }
137 } else {
138 QUIC_MIN_HEADER_LEN
140 }
141 }
142
143 pub fn field_names() -> &'static [&'static str] {
145 &[
146 "header_form",
147 "fixed_bit",
148 "packet_type",
149 "long_packet_type",
150 "packet_number_len",
151 "version",
152 "dst_conn_id_len",
153 "src_conn_id_len",
154 "dst_conn_id",
155 "src_conn_id",
156 "length",
157 "packet_number",
158 ]
159 }
160
161 pub fn get_field(&self, buf: &[u8], name: &str) -> Option<Result<FieldValue, FieldError>> {
163 let slice = self.index.slice(buf);
164 match name {
165 "header_form" => {
166 if slice.is_empty() {
167 return Some(Err(FieldError::BufferTooShort {
168 offset: self.index.start,
169 need: 1,
170 have: 0,
171 }));
172 }
173 let v = (slice[0] >> 7) & 0x01;
174 Some(Ok(FieldValue::U8(v)))
175 }
176 "fixed_bit" => {
177 if slice.is_empty() {
178 return Some(Err(FieldError::BufferTooShort {
179 offset: self.index.start,
180 need: 1,
181 have: 0,
182 }));
183 }
184 let v = (slice[0] >> 6) & 0x01;
185 Some(Ok(FieldValue::U8(v)))
186 }
187 "packet_type" => {
188 if slice.is_empty() {
189 return Some(Err(FieldError::BufferTooShort {
190 offset: self.index.start,
191 need: 1,
192 have: 0,
193 }));
194 }
195 let v = if slice[0] & 0x80 != 0 {
197 (slice[0] & 0x30) >> 4
198 } else {
199 0
200 };
201 Some(Ok(FieldValue::U8(v)))
202 }
203 "version" => {
204 if slice.len() < 5 {
205 return Some(Err(FieldError::BufferTooShort {
206 offset: self.index.start + 1,
207 need: 4,
208 have: slice.len().saturating_sub(1),
209 }));
210 }
211 let v = u32::from_be_bytes([slice[1], slice[2], slice[3], slice[4]]);
212 Some(Ok(FieldValue::U32(v)))
213 }
214 "long_packet_type" => {
215 if slice.is_empty() {
216 return Some(Err(FieldError::BufferTooShort {
217 offset: self.index.start,
218 need: 1,
219 have: 0,
220 }));
221 }
222 let v = (slice[0] & 0x30) >> 4;
224 Some(Ok(FieldValue::U8(v)))
225 }
226 "packet_number_len" => {
227 if slice.is_empty() {
228 return Some(Err(FieldError::BufferTooShort {
229 offset: self.index.start,
230 need: 1,
231 have: 0,
232 }));
233 }
234 let v = slice[0] & 0x03;
236 Some(Ok(FieldValue::U8(v)))
237 }
238 "dst_conn_id_len" => {
239 if slice.len() < 6 {
240 return Some(Err(FieldError::BufferTooShort {
241 offset: self.index.start + 5,
242 need: 1,
243 have: slice.len().saturating_sub(5),
244 }));
245 }
246 if slice[0] & 0x80 == 0 {
247 return Some(Ok(FieldValue::U8(0)));
249 }
250 Some(Ok(FieldValue::U8(slice[5])))
251 }
252 "src_conn_id_len" => {
253 if slice[0] & 0x80 == 0 {
254 return Some(Ok(FieldValue::U8(0)));
256 }
257 match QuicLongHeader::parse(slice) {
258 Some(hdr) => Some(Ok(FieldValue::U8(hdr.src_conn_id.len() as u8))),
259 None => Some(Err(FieldError::BufferTooShort {
260 offset: self.index.start,
261 need: 7,
262 have: slice.len(),
263 })),
264 }
265 }
266 "dst_conn_id" => {
267 if slice[0] & 0x80 == 0 {
268 return Some(Ok(FieldValue::Bytes(vec![])));
270 }
271 match QuicLongHeader::parse(slice) {
272 Some(hdr) => Some(Ok(FieldValue::Bytes(hdr.dst_conn_id))),
273 None => Some(Err(FieldError::BufferTooShort {
274 offset: self.index.start,
275 need: 7,
276 have: slice.len(),
277 })),
278 }
279 }
280 "src_conn_id" => {
281 if slice[0] & 0x80 == 0 {
282 return Some(Ok(FieldValue::Bytes(vec![])));
284 }
285 match QuicLongHeader::parse(slice) {
286 Some(hdr) => Some(Ok(FieldValue::Bytes(hdr.src_conn_id))),
287 None => Some(Err(FieldError::BufferTooShort {
288 offset: self.index.start,
289 need: 7,
290 have: slice.len(),
291 })),
292 }
293 }
294 "length" | "packet_number" => {
295 if slice[0] & 0x80 == 0 {
296 return None;
298 }
299 let hdr = match QuicLongHeader::parse(slice) {
300 Some(h) => h,
301 None => {
302 return Some(Err(FieldError::BufferTooShort {
303 offset: self.index.start,
304 need: 7,
305 have: slice.len(),
306 }));
307 }
308 };
309 let mut pos = hdr.header_len; if hdr.packet_type == headers::QuicPacketType::Initial {
313 match varint::decode(&slice[pos..]) {
314 Some((token_len, token_varint_bytes)) => {
315 pos += token_varint_bytes + token_len as usize;
316 }
317 None => {
318 return Some(Err(FieldError::BufferTooShort {
319 offset: self.index.start + pos,
320 need: 1,
321 have: slice.len().saturating_sub(pos),
322 }));
323 }
324 }
325 }
326
327 let (length_val, length_varint_bytes) = match varint::decode(&slice[pos..]) {
329 Some(v) => v,
330 None => {
331 return Some(Err(FieldError::BufferTooShort {
332 offset: self.index.start + pos,
333 need: 1,
334 have: slice.len().saturating_sub(pos),
335 }));
336 }
337 };
338
339 if name == "length" {
340 return Some(Ok(FieldValue::U64(length_val)));
341 }
342
343 pos += length_varint_bytes;
345 let pn_len = (slice[0] & 0x03) as usize + 1;
346 if pos + pn_len > slice.len() {
347 return Some(Err(FieldError::BufferTooShort {
348 offset: self.index.start + pos,
349 need: pn_len,
350 have: slice.len().saturating_sub(pos),
351 }));
352 }
353 let pn_bytes = &slice[pos..pos + pn_len];
354 let pn: u32 = match pn_len {
355 1 => pn_bytes[0] as u32,
356 2 => u16::from_be_bytes([pn_bytes[0], pn_bytes[1]]) as u32,
357 3 => {
358 ((pn_bytes[0] as u32) << 16)
359 | ((pn_bytes[1] as u32) << 8)
360 | (pn_bytes[2] as u32)
361 }
362 4 => u32::from_be_bytes([pn_bytes[0], pn_bytes[1], pn_bytes[2], pn_bytes[3]]),
363 _ => unreachable!(),
364 };
365 Some(Ok(FieldValue::U32(pn)))
366 }
367 _ => None,
368 }
369 }
370
371 pub fn set_field(
373 &self,
374 buf: &mut [u8],
375 name: &str,
376 value: FieldValue,
377 ) -> Option<Result<(), FieldError>> {
378 let start = self.index.start;
379 match name {
380 "header_form" => {
381 let v = match value {
382 FieldValue::U8(v) => v,
383 other => {
384 return Some(Err(FieldError::InvalidValue(format!(
385 "header_form: expected U8, got {:?}",
386 other
387 ))));
388 }
389 };
390 if buf.len() <= start {
391 return Some(Err(FieldError::BufferTooShort {
392 offset: start,
393 need: 1,
394 have: 0,
395 }));
396 }
397 if v != 0 {
398 buf[start] |= 0x80;
399 } else {
400 buf[start] &= !0x80;
401 }
402 Some(Ok(()))
403 }
404 "fixed_bit" => {
405 let v = match value {
406 FieldValue::U8(v) => v,
407 other => {
408 return Some(Err(FieldError::InvalidValue(format!(
409 "fixed_bit: expected U8, got {:?}",
410 other
411 ))));
412 }
413 };
414 if buf.len() <= start {
415 return Some(Err(FieldError::BufferTooShort {
416 offset: start,
417 need: 1,
418 have: 0,
419 }));
420 }
421 if v != 0 {
422 buf[start] |= 0x40;
423 } else {
424 buf[start] &= !0x40;
425 }
426 Some(Ok(()))
427 }
428 "packet_type" => {
429 let v = match value {
430 FieldValue::U8(v) => v,
431 other => {
432 return Some(Err(FieldError::InvalidValue(format!(
433 "packet_type: expected U8, got {:?}",
434 other
435 ))));
436 }
437 };
438 if buf.len() <= start {
439 return Some(Err(FieldError::BufferTooShort {
440 offset: start,
441 need: 1,
442 have: 0,
443 }));
444 }
445 buf[start] = (buf[start] & !0x30) | ((v & 0x03) << 4);
447 Some(Ok(()))
448 }
449 "version" => {
450 let v = match value {
451 FieldValue::U32(v) => v,
452 other => {
453 return Some(Err(FieldError::InvalidValue(format!(
454 "version: expected U32, got {:?}",
455 other
456 ))));
457 }
458 };
459 if buf.len() < start + 5 {
460 return Some(Err(FieldError::BufferTooShort {
461 offset: start + 1,
462 need: 4,
463 have: buf.len().saturating_sub(start + 1),
464 }));
465 }
466 buf[start + 1..start + 5].copy_from_slice(&v.to_be_bytes());
467 Some(Ok(()))
468 }
469 _ => None,
470 }
471 }
472}
473
474impl Layer for QuicLayer {
475 fn kind(&self) -> LayerKind {
476 LayerKind::Quic
477 }
478
479 fn summary(&self, data: &[u8]) -> String {
480 self.summary(data)
481 }
482
483 fn header_len(&self, data: &[u8]) -> usize {
484 self.header_len(data)
485 }
486
487 fn field_names(&self) -> &'static [&'static str] {
488 QuicLayer::field_names()
489 }
490
491 fn hashret(&self, _data: &[u8]) -> Vec<u8> {
492 vec![]
493 }
494}
495
496#[cfg(test)]
497mod tests {
498 use super::*;
499
500 fn from_hex(s: &str) -> Vec<u8> {
502 (0..s.len())
503 .step_by(2)
504 .map(|i| u8::from_str_radix(&s[i..i + 2], 16).unwrap())
505 .collect()
506 }
507
508 fn make_initial_buf() -> Vec<u8> {
509 QuicBuilder::initial()
510 .version(1)
511 .dst_conn_id(vec![0x01, 0x02])
512 .src_conn_id(vec![])
513 .payload(vec![])
514 .build()
515 }
516
517 #[test]
518 fn test_quic_layer_new() {
519 let buf = make_initial_buf();
520 let layer = QuicLayer::new(0, buf.len());
521 assert!(layer.is_long_header(&buf));
522 assert_eq!(layer.packet_type(&buf), Some(QuicPacketType::Initial));
523 assert_eq!(layer.version(&buf), Some(1));
524 }
525
526 #[test]
527 fn test_summary_initial() {
528 let buf = make_initial_buf();
529 let layer = QuicLayer::new(0, buf.len());
530 let s = layer.summary(&buf);
531 assert!(s.contains("Initial"), "summary: {}", s);
532 }
533
534 #[test]
535 fn test_get_field_header_form() {
536 let buf = make_initial_buf();
537 let layer = QuicLayer::new(0, buf.len());
538 let val = layer.get_field(&buf, "header_form").unwrap().unwrap();
539 assert_eq!(val, FieldValue::U8(1));
540 }
541
542 #[test]
543 fn test_get_field_fixed_bit() {
544 let buf = make_initial_buf();
545 let layer = QuicLayer::new(0, buf.len());
546 let val = layer.get_field(&buf, "fixed_bit").unwrap().unwrap();
547 assert_eq!(val, FieldValue::U8(1));
548 }
549
550 #[test]
551 fn test_get_field_packet_type() {
552 let buf = make_initial_buf();
553 let layer = QuicLayer::new(0, buf.len());
554 let val = layer.get_field(&buf, "packet_type").unwrap().unwrap();
555 assert_eq!(val, FieldValue::U8(0));
557 }
558
559 #[test]
560 fn test_get_field_version() {
561 let buf = make_initial_buf();
562 let layer = QuicLayer::new(0, buf.len());
563 let val = layer.get_field(&buf, "version").unwrap().unwrap();
564 assert_eq!(val, FieldValue::U32(1));
565 }
566
567 #[test]
568 fn test_get_field_unknown() {
569 let buf = make_initial_buf();
570 let layer = QuicLayer::new(0, buf.len());
571 assert!(layer.get_field(&buf, "nonexistent").is_none());
572 }
573
574 #[test]
575 fn test_set_field_version() {
576 let mut buf = make_initial_buf();
577 let layer = QuicLayer::new(0, buf.len());
578 layer
579 .set_field(&mut buf, "version", FieldValue::U32(2))
580 .unwrap()
581 .unwrap();
582 assert_eq!(layer.version(&buf), Some(2));
583 }
584
585 #[test]
586 fn test_one_rtt_is_short_header() {
587 let buf = QuicBuilder::one_rtt().payload(vec![0x01]).build();
588 let layer = QuicLayer::new(0, buf.len());
589 assert!(!layer.is_long_header(&buf));
590 assert_eq!(layer.packet_type(&buf), Some(QuicPacketType::OneRtt));
591 assert_eq!(layer.version(&buf), None);
592 }
593
594 #[test]
595 fn test_layer_kind() {
596 let buf = make_initial_buf();
597 let layer = QuicLayer::new(0, buf.len());
598 assert_eq!(layer.kind(), LayerKind::Quic);
599 }
600
601 #[test]
602 fn test_header_len_long() {
603 let buf = make_initial_buf();
604 let layer = QuicLayer::new(0, buf.len());
605 let h = layer.header_len(&buf);
608 assert!(h >= 6, "header_len={}", h);
609 }
610
611 #[test]
616 fn test_get_field_long_packet_type_initial() {
617 let buf = make_initial_buf();
618 let layer = QuicLayer::new(0, buf.len());
619 let val = layer.get_field(&buf, "long_packet_type").unwrap().unwrap();
620 assert_eq!(val, FieldValue::U8(0)); }
622
623 #[test]
624 fn test_get_field_long_packet_type_handshake() {
625 let buf = QuicBuilder::handshake().dst_conn_id(vec![0x01]).build();
626 let layer = QuicLayer::new(0, buf.len());
627 let val = layer.get_field(&buf, "long_packet_type").unwrap().unwrap();
628 assert_eq!(val, FieldValue::U8(2)); }
630
631 #[test]
632 fn test_get_field_packet_number_len_zero() {
633 let buf = make_initial_buf();
635 let layer = QuicLayer::new(0, buf.len());
636 let val = layer.get_field(&buf, "packet_number_len").unwrap().unwrap();
637 assert_eq!(val, FieldValue::U8(0));
638 }
639
640 #[test]
641 fn test_get_field_packet_number_len_one() {
642 let buf = QuicBuilder::initial().packet_number(0xFFFF).build();
644 let layer = QuicLayer::new(0, buf.len());
645 let val = layer.get_field(&buf, "packet_number_len").unwrap().unwrap();
646 assert_eq!(val, FieldValue::U8(1));
647 }
648
649 #[test]
650 fn test_get_field_dst_conn_id_len() {
651 let buf = make_initial_buf();
652 let layer = QuicLayer::new(0, buf.len());
653 let val = layer.get_field(&buf, "dst_conn_id_len").unwrap().unwrap();
654 assert_eq!(val, FieldValue::U8(2)); }
656
657 #[test]
658 fn test_get_field_src_conn_id_len_zero() {
659 let buf = make_initial_buf();
660 let layer = QuicLayer::new(0, buf.len());
661 let val = layer.get_field(&buf, "src_conn_id_len").unwrap().unwrap();
662 assert_eq!(val, FieldValue::U8(0)); }
664
665 #[test]
666 fn test_get_field_src_conn_id_len_nonzero() {
667 let buf = QuicBuilder::initial()
668 .dst_conn_id(vec![0xAA])
669 .src_conn_id(vec![0xBB, 0xCC])
670 .build();
671 let layer = QuicLayer::new(0, buf.len());
672 let val = layer.get_field(&buf, "src_conn_id_len").unwrap().unwrap();
673 assert_eq!(val, FieldValue::U8(2));
674 }
675
676 #[test]
677 fn test_get_field_dst_conn_id() {
678 let dcid = vec![0x01, 0x02];
679 let buf = QuicBuilder::initial().dst_conn_id(dcid.clone()).build();
680 let layer = QuicLayer::new(0, buf.len());
681 let val = layer.get_field(&buf, "dst_conn_id").unwrap().unwrap();
682 assert_eq!(val, FieldValue::Bytes(dcid));
683 }
684
685 #[test]
686 fn test_get_field_src_conn_id() {
687 let scid = vec![0xAA, 0xBB];
688 let buf = QuicBuilder::initial().src_conn_id(scid.clone()).build();
689 let layer = QuicLayer::new(0, buf.len());
690 let val = layer.get_field(&buf, "src_conn_id").unwrap().unwrap();
691 assert_eq!(val, FieldValue::Bytes(scid));
692 }
693
694 #[test]
695 fn test_get_field_length_initial() {
696 let buf = QuicBuilder::initial()
698 .dst_conn_id(vec![0x01])
699 .payload(vec![])
700 .build();
701 let layer = QuicLayer::new(0, buf.len());
702 let val = layer.get_field(&buf, "length").unwrap().unwrap();
703 assert_eq!(val, FieldValue::U64(1)); }
705
706 #[test]
707 fn test_get_field_packet_number_initial_zero() {
708 let buf = QuicBuilder::initial()
709 .dst_conn_id(vec![0x01])
710 .packet_number(0)
711 .build();
712 let layer = QuicLayer::new(0, buf.len());
713 let val = layer.get_field(&buf, "packet_number").unwrap().unwrap();
714 assert_eq!(val, FieldValue::U32(0));
715 }
716
717 #[test]
718 fn test_get_field_packet_number_initial_255() {
719 let buf = QuicBuilder::initial()
720 .dst_conn_id(vec![0x01])
721 .packet_number(0xFF)
722 .build();
723 let layer = QuicLayer::new(0, buf.len());
724 let val = layer.get_field(&buf, "packet_number").unwrap().unwrap();
725 assert_eq!(val, FieldValue::U32(0xFF));
726 }
727
728 #[test]
729 fn test_get_field_packet_number_initial_65535() {
730 let buf = QuicBuilder::initial()
731 .dst_conn_id(vec![0x01])
732 .packet_number(0xFFFF)
733 .build();
734 let layer = QuicLayer::new(0, buf.len());
735 let val = layer.get_field(&buf, "packet_number").unwrap().unwrap();
736 assert_eq!(val, FieldValue::U32(0xFFFF));
737 }
738
739 #[test]
740 fn test_get_field_packet_number_handshake() {
741 let buf = QuicBuilder::handshake()
742 .dst_conn_id(vec![0x01])
743 .packet_number(1)
744 .build();
745 let layer = QuicLayer::new(0, buf.len());
746 let val = layer.get_field(&buf, "packet_number").unwrap().unwrap();
747 assert_eq!(val, FieldValue::U32(1));
748 }
749
750 #[test]
751 fn test_uts_client_initial_fields() {
752 let data = from_hex(
754 "c00000000108000102030405060705635f636964004103001c36a7ed78716be9711ba498b7ed868443bb2e0c514d4d848eadcc7a00d25ce9f9afa483978088de836be68c0b32a24595d7813ea5414a9199329a6d9f7f760dd8bb249bf3f53d9a77fbb7b395b8d66d7879a51fe59ef9601f79998eb3568e1fdc789f640acab3858a82ef2930fa5ce14b5b9ea0bdb29f4572da85aa3def39b7efafffa074b9267070d50b5d07842e49bba3bc787ff295d6ae3b514305f102afe5a047b3fb4c99eb92a274d244d60492c0e2e6e212cef0f9e3f62efd0955e71c768aa6bb3cd80bbb3755c8b7ebee32712f40f2245119487021b4b84e1565e3ca31967ac8604d4032170dec280aeefa095d08b3b7241ef6646a6c86e5c62ce08be099",
755 );
756 let layer = QuicLayer::new(0, data.len());
757
758 let dcid = layer.get_field(&data, "dst_conn_id").unwrap().unwrap();
759 assert_eq!(
760 dcid,
761 FieldValue::Bytes(vec![0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07])
762 );
763
764 let scid = layer.get_field(&data, "src_conn_id").unwrap().unwrap();
765 assert_eq!(scid, FieldValue::Bytes(b"c_cid".to_vec()));
766
767 let lpt = layer.get_field(&data, "long_packet_type").unwrap().unwrap();
768 assert_eq!(lpt, FieldValue::U8(0)); let version = layer.get_field(&data, "version").unwrap().unwrap();
771 assert_eq!(version, FieldValue::U32(1));
772
773 let length = layer.get_field(&data, "length").unwrap().unwrap();
774 assert_eq!(length, FieldValue::U64(259));
775
776 let pn = layer.get_field(&data, "packet_number").unwrap().unwrap();
777 assert_eq!(pn, FieldValue::U32(0));
778 }
779
780 #[test]
781 fn test_uts_server_handshake_fields() {
782 let data = from_hex(
784 "e00000000105635f63696405735f63696440cf014420f919681c3f0f102a30f5e647a3399abf54bc8e80453134996ba33099056242f3b8e662bbfce42f3ef2b6ba87159147489f8479e849284e983fd905320a62fc7d67e9587797096ca60101d0b2685d8747811178133ad9172b7ff8ea83fd81a814bae27b953a97d57ebff4b4710dba8df82a6b49d7d7fa3d8179cbdb8683d4bfa832645401e5a56a76535f71c6fb3e616c241bb1f43bc147c296f591402997ed49aa0c55e31721d03e14114af2dc458ae03944de5126fe08d66a6ef3ba2ed1025f98fea6d6024998184687dc06",
785 );
786 let layer = QuicLayer::new(0, data.len());
787
788 let lpt = layer.get_field(&data, "long_packet_type").unwrap().unwrap();
789 assert_eq!(lpt, FieldValue::U8(2)); let dcid = layer.get_field(&data, "dst_conn_id").unwrap().unwrap();
792 assert_eq!(dcid, FieldValue::Bytes(b"c_cid".to_vec()));
793
794 let scid = layer.get_field(&data, "src_conn_id").unwrap().unwrap();
795 assert_eq!(scid, FieldValue::Bytes(b"s_cid".to_vec()));
796
797 let pn = layer.get_field(&data, "packet_number").unwrap().unwrap();
798 assert_eq!(pn, FieldValue::U32(1));
799 }
800
801 #[test]
802 fn test_uts_build_packet_fields() {
803 let data: &[u8] = b"\xc0\x00\x00\x00\x01\x0fp\xa2\x8e@\x96\xc5}\xd0\xff\xb6\xc3\xd8\x1b\xcaR\x03\xf7\x10Q\x00\x00\xff";
805 let layer = QuicLayer::new(0, data.len());
806
807 let dcil = layer.get_field(data, "dst_conn_id_len").unwrap().unwrap();
808 assert_eq!(dcil, FieldValue::U8(15));
809
810 let scil = layer.get_field(data, "src_conn_id_len").unwrap().unwrap();
811 assert_eq!(scil, FieldValue::U8(3));
812
813 let pnl = layer.get_field(data, "packet_number_len").unwrap().unwrap();
814 assert_eq!(pnl, FieldValue::U8(0)); let pn = layer.get_field(data, "packet_number").unwrap().unwrap();
817 assert_eq!(pn, FieldValue::U32(0xFF));
818 }
819}