ExShark is an Elixir wrapper for tshark (Wireshark's command-line interface) that enables packet capture and analysis using Wireshark's powerful dissectors.
- π Live packet capture with streaming support
- π¦ PCAP file analysis
- π Lazy packet loading for memory efficiency
- β‘ Async packet processing
- π Full access to Wireshark dissectors
- π Rich packet information including raw data access
- π§ͺ Comprehensive test suite
- Ensure you have Wireshark/tshark installed on your system:
# Ubuntu/Debian
sudo apt-get install tshark
# macOS
brew install wireshark
- Add
exshark
to your dependencies inmix.exs
:
def deps do
[
{:exshark, "~> 0.1.0"},
{:jason, "~> 1.2"}
]
end
- Install dependencies:
mix deps.get
# Read all packets from a PCAP file
packets = ExShark.read_file("capture.pcap")
# Access packet information
first_packet = Enum.at(packets, 0)
IO.puts "Protocol: #{first_packet.highest_layer}"
# Access protocol fields (multiple methods available)
source_ip = ExShark.Packet.get_field(first_packet, {:ip, :src})
# OR
source_ip = ExShark.PacketAccess.get(first_packet, {:ip, :src})
# Start a live capture
ExShark.capture(interface: "eth0", filter: "tcp port 80")
|> Stream.each(fn packet ->
IO.puts "Captured: #{packet.highest_layer}"
# Access source and destination addresses
src = ExShark.Packet.get_field(packet, {:eth, :src})
dst = ExShark.Packet.get_field(packet, {:eth, :dst})
IO.puts "#{src} -> #{dst}"
end)
|> Stream.run()
# Start a lazy capture
{:ok, capture} = ExShark.LazyCapture.start_link("large_capture.pcap")
# Load specific packets on demand
packet = ExShark.LazyCapture.get_packet(capture, 1000)
IO.puts "Packet #{packet.frame_info.number}: #{packet.highest_layer}"
callback = fn packet ->
protocol = packet.highest_layer
src = ExShark.Packet.get_field(packet, {:ip, :src})
dst = ExShark.Packet.get_field(packet, {:ip, :dst})
IO.puts "Processing #{protocol} packet: #{src} -> #{dst}"
{:ok, nil}
end
ExShark.AsyncCapture.apply_on_packets("capture.pcap", callback, timeout: 5000)
There are multiple ways to access packet fields:
# Using the Packet module (recommended)
src_ip = ExShark.Packet.get_field(packet, {:ip, :src})
dst_ip = ExShark.Packet.get_field(packet, {:ip, :dst})
# Using the PacketAccess protocol directly
src_port = ExShark.PacketAccess.get(packet, {:tcp, :srcport})
# Accessing frame info directly
IO.puts "Protocol Stack: #{packet.frame_info.protocols}"
# Getting entire protocol layer
layer = ExShark.Packet.get_layer(packet, :tcp)
# Access raw packet data
packet = ExShark.read_file("capture.pcap") |> Enum.at(0)
layer = ExShark.Packet.get_layer(packet, :tcp)
# Enable raw mode for hex/binary data
raw_layer = %{layer | raw_mode: true}
raw_payload = ExShark.Packet.Layer.get_field(raw_layer, :payload)
Full documentation can be found at https://hexdocs.pm/tshark_ex.
- Elixir 1.14 or later
- Erlang/OTP 25 or later
- tshark/Wireshark
mix test
mix coveralls
mix test test/exshark/async_capture_test.exs
- Fork the repository
- Create your feature branch (
git checkout -b feature/amazing-feature
) - Commit your changes (
git commit -m 'Add some amazing feature'
) - Push to the branch (
git push origin feature/amazing-feature
) - Open a Pull Request
This project is licensed under the MIT License - see the LICENSE file for details.
If you have any questions or run into issues, please open an issue on GitHub.