Skip to main content

packet_dissector/
lib.rs

1//! # packet-dissector
2//!
3//! A Rust crate for zero-copy parsing of layered network packets with
4//! registry-based protocol chaining. Protocol dissectors can be registered
5//! and chained to parse layered packets from L2 through L7.
6//!
7//! ## Features
8//!
9//! - **Zero-copy parsing** — works directly on `&[u8]` slices
10//! - **Extensible** — add new protocols by implementing the [`dissector::Dissector`] trait
11//! - **Layered** — automatic chaining from Ethernet → IP → TCP/UDP → Application
12//! - **Safe Rust** — minimal `unsafe` (lifetime extension in the registry only, with `// SAFETY:` comments)
13//! - **Modular** — enable only the protocols you need via feature flags
14//!
15//! [`DissectorRegistry::default()`](registry::DissectorRegistry::default) registers all
16//! built-in protocol dissectors. See its documentation for the full list.
17//!
18//! ## Quick Start
19//!
20//! ```
21//! use packet_dissector::registry::DissectorRegistry;
22//! use packet_dissector::packet::DissectBuffer;
23//! use packet_dissector::field::FieldValue;
24//!
25//! // Build a registry with all built-in dissectors
26//! let registry = DissectorRegistry::default();
27//!
28//! // An Ethernet + IPv4 + UDP packet (minimal example)
29//! let packet_bytes: &[u8] = &[
30//!     // Ethernet header (14 bytes)
31//!     0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // dst MAC
32//!     0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // src MAC
33//!     0x08, 0x00,                         // EtherType: IPv4
34//!     // IPv4 header (20 bytes)
35//!     0x45, 0x00, 0x00, 0x1c,             // ver, ihl, len=28
36//!     0x00, 0x00, 0x00, 0x00,             // id, flags, frag
37//!     0x40, 0x11, 0x00, 0x00,             // ttl=64, proto=UDP, checksum
38//!     0x0a, 0x00, 0x00, 0x01,             // src: 10.0.0.1
39//!     0x0a, 0x00, 0x00, 0x02,             // dst: 10.0.0.2
40//!     // UDP header (8 bytes)
41//!     0x30, 0x39, 0x00, 0x50,             // src=12345, dst=80
42//!     0x00, 0x08, 0x00, 0x00,             // len=8, checksum
43//! ];
44//!
45//! let mut buf = DissectBuffer::new();
46//! registry.dissect(packet_bytes, &mut buf).unwrap();
47//! assert_eq!(buf.layers().len(), 3); // Ethernet, IPv4, UDP
48//! assert_eq!(buf.layers()[0].name, "Ethernet");
49//! assert_eq!(buf.layers()[1].name, "IPv4");
50//! assert_eq!(buf.layers()[2].name, "UDP");
51//!
52//! // Look up layers by name
53//! let udp = buf.layer_by_name("UDP").unwrap();
54//! let src_port = buf.field_by_name(udp, "src_port").unwrap();
55//! assert_eq!(src_port.value, FieldValue::U16(12345));
56//! ```
57
58#![deny(missing_docs)]
59
60// Re-export core types so users can `use packet_dissector::dissector::Dissector` etc.
61pub use packet_dissector_core::dissector;
62pub use packet_dissector_core::error;
63pub use packet_dissector_core::field;
64pub use packet_dissector_core::packet;
65
66/// Re-exports of built-in protocol dissector crates.
67///
68/// Each protocol is gated behind a feature flag. All are enabled by default.
69pub mod dissectors {
70
71    #[cfg(feature = "ethernet")]
72    pub use packet_dissector_ethernet as ethernet;
73
74    #[cfg(feature = "linux_sll")]
75    pub use packet_dissector_linux_sll as linux_sll;
76
77    #[cfg(feature = "linux_sll2")]
78    pub use packet_dissector_linux_sll2 as linux_sll2;
79
80    #[cfg(feature = "arp")]
81    pub use packet_dissector_arp as arp;
82
83    #[cfg(feature = "lacp")]
84    pub use packet_dissector_lacp as lacp;
85
86    #[cfg(feature = "ipv4")]
87    pub use packet_dissector_ipv4 as ipv4;
88
89    #[cfg(feature = "ipv6")]
90    pub use packet_dissector_ipv6 as ipv6;
91
92    #[cfg(feature = "icmp")]
93    pub use packet_dissector_icmp as icmp;
94
95    #[cfg(feature = "icmpv6")]
96    pub use packet_dissector_icmpv6 as icmpv6;
97
98    #[cfg(feature = "igmp")]
99    pub use packet_dissector_igmp as igmp;
100
101    #[cfg(feature = "tcp")]
102    pub use packet_dissector_tcp as tcp;
103
104    #[cfg(feature = "udp")]
105    pub use packet_dissector_udp as udp;
106
107    #[cfg(feature = "sctp")]
108    pub use packet_dissector_sctp as sctp;
109
110    #[cfg(feature = "dns")]
111    pub use packet_dissector_dns as dns;
112
113    #[cfg(feature = "mdns")]
114    pub use packet_dissector_mdns as mdns;
115
116    #[cfg(feature = "dhcp")]
117    pub use packet_dissector_dhcp as dhcp;
118
119    #[cfg(feature = "dhcpv6")]
120    pub use packet_dissector_dhcpv6 as dhcpv6;
121
122    #[cfg(feature = "srv6")]
123    pub use packet_dissector_srv6 as srv6;
124
125    #[cfg(feature = "gtpv1u")]
126    pub use packet_dissector_gtpv1u as gtpv1u;
127
128    #[cfg(feature = "gtpv2c")]
129    pub use packet_dissector_gtpv2c as gtpv2c;
130
131    #[cfg(feature = "pfcp")]
132    pub use packet_dissector_pfcp as pfcp;
133
134    #[cfg(feature = "http")]
135    pub use packet_dissector_http as http;
136
137    #[cfg(feature = "http2")]
138    pub use packet_dissector_http2 as http2;
139
140    #[cfg(feature = "sip")]
141    pub use packet_dissector_sip as sip;
142
143    #[cfg(feature = "diameter")]
144    pub use packet_dissector_diameter as diameter;
145
146    #[cfg(feature = "nas5g")]
147    pub use packet_dissector_nas5g as nas5g;
148    #[cfg(feature = "ngap")]
149    pub use packet_dissector_ngap as ngap;
150
151    #[cfg(feature = "geneve")]
152    pub use packet_dissector_geneve as geneve;
153
154    #[cfg(feature = "gre")]
155    pub use packet_dissector_gre as gre;
156
157    #[cfg(feature = "mpls")]
158    pub use packet_dissector_mpls as mpls;
159
160    #[cfg(feature = "vxlan")]
161    pub use packet_dissector_vxlan as vxlan;
162
163    #[cfg(feature = "lldp")]
164    pub use packet_dissector_lldp as lldp;
165
166    #[cfg(feature = "stp")]
167    pub use packet_dissector_stp as stp;
168
169    #[cfg(feature = "ntp")]
170    pub use packet_dissector_ntp as ntp;
171
172    #[cfg(feature = "ospf")]
173    pub use packet_dissector_ospf as ospf;
174
175    #[cfg(feature = "vrrp")]
176    pub use packet_dissector_vrrp as vrrp;
177
178    #[cfg(feature = "bfd")]
179    pub use packet_dissector_bfd as bfd;
180
181    #[cfg(feature = "isis")]
182    pub use packet_dissector_isis as isis;
183
184    #[cfg(feature = "bgp")]
185    pub use packet_dissector_bgp as bgp;
186
187    #[cfg(feature = "l2tp")]
188    pub use packet_dissector_l2tp as l2tp;
189
190    #[cfg(feature = "l2tpv3")]
191    pub use packet_dissector_l2tpv3 as l2tpv3;
192
193    #[cfg(feature = "tls")]
194    pub use packet_dissector_tls as tls;
195
196    #[cfg(feature = "ppp")]
197    pub use packet_dissector_ppp as ppp;
198
199    #[cfg(feature = "radius")]
200    pub use packet_dissector_radius as radius;
201
202    #[cfg(feature = "ah")]
203    pub use packet_dissector_ah as ah;
204
205    #[cfg(feature = "esp")]
206    pub use packet_dissector_esp as esp;
207
208    #[cfg(feature = "ike")]
209    pub use packet_dissector_ike as ike;
210
211    #[cfg(feature = "rtp")]
212    pub use packet_dissector_rtp as rtp;
213
214    #[cfg(feature = "quic")]
215    pub use packet_dissector_quic as quic;
216
217    #[cfg(feature = "stun")]
218    pub use packet_dissector_stun as stun;
219}
220
221#[cfg(feature = "tcp")]
222mod tcp_reassembly;
223
224pub mod registry;