Packet analysis for .NET 10: read network and automotive captures, dissect them into typed fields, filter them
with Wireshark-style expressions, and export them to formats for tools, spreadsheets, and SQL. Use it as a
library, or from the command line with ni.
dotnet tool install -g NetworkInspector.CLI
ni export capture.pcapng -o packets.duckdb # every packet, every field, queryable with SQL- Enterprise and automotive traffic in one stack. Ethernet, IP, TCP/UDP, DNS, DHCP, HTTP/1.x, HTTP/2, TLS, WebSocket and CAN, CAN FD, CAN XL, LIN, FlexRay, SOME/IP, and JSON-configured signal decoding.
- Capture formats both worlds use. PCAP, PCAPNG, Vector BLF, and Vector ASC in and out, with round trips that keep interface metadata and bus details (CAN DLC 9–15, LIN protected id).
- Fast. Millions of frames per second from memory-mapped files and streams, allocation-aware parsing with packet recycling, skip-parse modes, and Roaring-bitmap presence indexes for filtering huge captures.
- Analytics built in. Export to JSON, CSV, Text, PBF, Parquet, or a single DuckDB file with a field catalog and native types; record selected fields into columnar RAM caches while parsing.
- Wireshark-style filters, compiled.
tcp.port in {80, 443} && !tls, checked against the stack at compile time with "did you mean" hints, plus subtree scopes and edge detection across packets. - Live sessions for applications. Multi-source, multi-listener sessions with per-listener filters, background value caches, and hot protocol-stack swaps.
- Verified against Wireshark. More than 5,000 tests; dissectors, readers, writers, and the frame builder are
cross-validated against
tshark4.6. - Modular. Take only what you need: values, parser, readers, writers, filters, sessions, or the CLI.
dotnet tool install -g NetworkInspector.CLI
ni convert capture.blf -o capture.pcapng # Vector BLF -> Wireshark
ni export capture.pcapng -o packets.json # parsed packets as JSON
ni export capture.pcapng -o dns.json --filter "udp.port == 53" # only DNS
ni export capture.pcapng -o out -f parquet # Parquet dataset for pandas, Polars, SparkMore: CLI README.
dotnet add package NetworkInspector.Sources
dotnet add package NetworkInspector.Protocols
dotnet add package NetworkInspector.FilterRead a capture, parse every frame, and print the DNS packets:
using NetworkInspector.Core;
using NetworkInspector.Core.Ids;
using NetworkInspector.Core.Settings;
using NetworkInspector.Filter;
using NetworkInspector.Filter.Errors;
using NetworkInspector.Protocols;
using NetworkInspector.Sources.Pcapng;
// One registry for the stack and the source.
FrameInterfaceRegistry registry = new();
StackBuilder builder = new(new SettingsManager(), registry);
builder.RegisterStandardProtocols();
using Stack stack = builder.Build();
if (!Filter.TryCompile("udp.port == 53", stack, out Filter? dns, out FilterError? error))
{
throw new InvalidOperationException(error.ToString());
}
using PcapngSource source = PcapngSource.Open("capture.pcapng"); // PCAPNG and legacy PCAP
source.Start(registry.RegisterSource(source), registry);
ParseOptions options = new();
int nextId = 0; // first-parse ids are dense: 0, 1, 2, ...
while (source.NextFrame() is { } frame)
{
if (!Packet.TryParse(new PacketId(nextId), stack, frame, in options, out Packet? packet, out ParseFailure failure)
|| packet is null)
{
Console.Error.WriteLine($"frame {frame.Id.Value}: {failure}");
continue;
}
nextId++;
if (dns.TryIsMatch(packet, out bool matched, out _) && matched)
{
Console.WriteLine($"#{packet.Id.Value} {frame.Timestamp} {packet.Info}");
}
}Next steps: walk the field tree (Core), write the packets to a file (Exporters), or run the same pipeline on background threads with listeners (Sessions).
| Package | Version | Downloads | Purpose |
|---|---|---|---|
| NetworkInspector.Core | Parser engine, field tree, index, value cache | ||
| NetworkInspector.Protocols | Built-in dissectors | ||
| NetworkInspector.Sources | Read PCAP, PCAPNG, BLF, ASC | ||
| NetworkInspector.Exporters | Write capture and analysis formats | ||
| NetworkInspector.Exporters.DuckDb | Write a DuckDB database | ||
| NetworkInspector.Filter | Compiled display filters | ||
| NetworkInspector.Sessions | Multi-threaded capture sessions | ||
| NetworkInspector.FrameBuilder | Build wire frames from typed layers | ||
| NetworkInspector.Values | MAC, IP, EUI-64, UUID, timestamp values | ||
| NetworkInspector.CLI | ni command-line tool |
The source generator (NetworkInspector.Generators) ships inside
NetworkInspector.Core. Packages pull in their own dependencies: Sources, Exporters, and Filter bring Core;
Core brings Values.
| Goal | Packages |
|---|---|
| Convert or export captures without code | NetworkInspector.CLI (tool) |
| Parse frames you already have | Core + Protocols |
| Read capture files | Sources (+ Protocols to parse) |
| Write captures or analysis files | Exporters (+ Exporters.DuckDb for DuckDB) |
| Filter packets | Filter (+ Protocols) |
| Build an analysis application with live views | Sessions + Protocols |
| Generate test traffic | FrameBuilder (+ Exporters to save it) |
| Typed addresses and timestamps only | Values |
| Write your own dissector | Core + Protocols (Protocol guide) |
| Layer | Protocols |
|---|---|
| Link | Ethernet II, VLAN (802.1Q, 802.1ad), LLC/SNAP, Linux SLL, Linux SLL2 |
| Network | IPv4, IPv6 (with fragment reassembly), ARP, ICMPv4, ICMPv6 |
| Transport | TCP (stream reassembly and analysis), UDP |
| Application | DNS, DHCPv4, DHCPv6, HTTP/1.x, HTTP/2, TLS, DTLS, WebSocket, JSON, Text |
| Automotive | CAN (classic, FD, XL), LIN, FlexRay, SOME/IP (SD, TP), PDU Transport, signal messages |
Details and configuration: Protocols README.
| Format | Read | Write | Kind |
|---|---|---|---|
| PCAPNG | ✅ | ✅ | frames |
| PCAP (legacy) | ✅ | — | frames |
| Vector BLF | ✅ | ✅ | frames |
| Vector ASC | ✅ | ✅ | frames |
| JSON, CSV, Text | — | ✅ | packets |
| PBF (NetworkInspector binary) | — | ✅ | packets |
| Apache Parquet | — | ✅ | packets |
| DuckDB | — | ✅ | packets |
Measured with the NetworkInspector.Profiling scenarios on 50 000 PCAPNG frames (64 KiB frame slabs):
| Read path | Frames per second |
|---|---|
| Stream source, frames dropped | 7.55 M |
| Memory-mapped file, frames dropped | 3.72 M |
| Stream source, frames held | 3.45 M |
| Memory-mapped file, frames held | 2.40 M |
The parser recycles packets, decodes lazily, and can skip the field tree entirely when only values, indexes, or
filter verdicts are needed. Run NetworkInspector.Profiling to measure parse, filter, export, and session
throughput on your hardware.
- More than 5,000 tests (TUnit on Microsoft.Testing.Platform), including round trips through every capture format.
- Dissectors, capture readers and writers, and frame-builder output are cross-validated against
tshark4.6. - Warnings are errors; .NET analyzers and a style checker run on every build.
- Untrusted-input hardening: bounded lengths, counts, and nesting; decompression-bomb limits; process-seeded connection hashing; linear-time regular expressions where possible.
- Build a protocol stack once and reuse it; construction is single-threaded. First parses run in packet-id order; re-parses may run concurrently.
- Exporters and filters are single-threaded per instance.
Sessionis thread-safe. Package READMEs state the rules for each type. - Dispose stacks, sources, exporters, and sessions to release memory maps and files promptly.
- No live capture from network interfaces; inputs are capture files, streams, and in-memory frames.
- NativeAOT and trimming are not supported.
- Spoofing: Treat captures as untrusted input and check their provenance where it matters.
- Tampering: Expect malformed records; use tolerant processing and inspect the reported errors.
- Repudiation: Keep source metadata and command settings when results must be reproducible.
- Information disclosure: Captures and exports can contain credentials and personal data; control access.
- Denial of service: Use split, count, size, and cancellation limits on large or unknown inputs.
- Elevation of privilege: Run processing with least-privilege file-system and process rights.
Requires the .NET SDK 10.0.100 or newer (see global.json). Windows, Linux, and macOS on x64 and
ARM64.
dotnet build NetworkInspector.slnx -c Release
dotnet test NetworkInspector.slnx -c ReleaseThe cross-validation tests need tshark 4.6.x (part of Wireshark) on PATH:
| Platform | Install |
|---|---|
| Windows | Wireshark installer (includes tshark) or choco install wireshark |
| Ubuntu / Debian | sudo add-apt-repository ppa:wireshark-dev/wireshark && sudo apt-get install tshark |
| macOS | brew install wireshark |
Without Wireshark, set NETWORKINSPECTOR_ALLOW_MISSING_TSHARK=1 to skip the tests that opt into
TsharkAvailability.ShouldSkip(); all other tests still run. Do not set it in CI or release runs, so
cross-validation evidence is never discarded silently.
NetworkInspector.Core bundles NetworkInspector.Generators in its analyzer assets, and the library packages
carry ZeroAlloc (including its generator) transitively, so consumers need no extra references.