• Stars
    star
    148
  • Rank 241,194 (Top 5 %)
  • Language
    Erlang
  • License
    BSD 3-Clause "New...
  • Created over 13 years ago
  • Updated almost 2 years ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Erlang network protocol library

An Erlang network protocol library.

Originally part of epcap: http://github.com/msantos/epcap

EXPORTS

pkt:decapsulate(Data) -> Packet
pkt:decapsulate(Proto, Data) -> Packet

    Types   Data = binary()
            Proto = atom() | integer()
            Packet = [ Header | Payload ]
            Header = #ether{} | #arp{} | #null{} | #linux_cooked{} |
                #ipv4{} | #ipv6{} | #tcp{} | #udp{} | #sctp{} | #icmp{} |
                #icmp6{} | #igmp{} | #gre{} | #llc{} | #vrrp{} | #'802.1q'{} |
                #lldp{} | #mpls{} | #rarp{} | #'802.1x'{}
            Payload = binary()

    Convert network protocols from binary data to a list of Erlang
    records followed by the payload.

    decapsulate/1,2 works on valid packets. If the packet is malformed
    or unsupported, decapsulate/1 will crash.

    decapsulate/1 parses the data as an ethernet frame.

    decapsulate/2 allows specifying the protocol for decoding the
    packet. If the protocol is specified as an integer, the integer
    is treated as a datalink type.

pkt:decode(Data) -> {ok, Packet} | {error, SoFar, {FailedProto, binary()}}
pkt:decode(Proto, Data) -> {ok, Packet} | {error, SoFar, {FailedProto, binary()}}

    Types   Data = binary()
            Proto = FailedProto = atom()
            Packet = {Headers, Payload}
            Headers = [Header]
            Header = #ether{} | #arp{} | #null{} | #linux_cooked{} |
                #ipv4{} | #ipv6{} | #tcp{} | #udp{} | #sctp{} | #icmp{} |
                #icmp6{} | #igmp{} | #gre{} | #llc{} | #vrrp{} | #'802.1q'{} |
                #lldp{} | #mpls{} | #rarp{} | #'802.1x'{}
            SoFar = Headers | []
            Payload = binary()

    Similar to decapsulate/1 but, on error, returns any part of the
    packet that has been successfully converted to Erlang term format.

The following functions create the protocol headers, converting between records and binaries. See include/pkt.hrl for definition of the record types.

ether(Packet) -> {#ether{}, Payload} | binary()
llc(Packet) -> {#llc{}, Payload} | binary()
vrrp(Packet) -> {#vrrp{}, Payload} | binary()
'802.1q'(Packet) -> {#'802.1q'{}, Payload} | binary()
null(Packet) -> {#null{}, Payload} | binary()
linux_cooked(Packet) -> {#linux_cooked{}, Payload} | binary()
gre(Packet) -> {#gre{}, Payload} | binary()
arp(Packet) -> {#arp{}, Payload} | binary()
ipv4(Packet) -> {#ipv4{}, Payload} | binary()
ipv6(Packet) -> {#ipv6{}, Payload} | binary()
tcp(Packet) -> {#tcp{}, Payload} | binary()
sctp(Packet) -> {#sctp{}, Payload} | binary()
udp(Packet) -> {#udp{}, Payload} | binary()
icmp(Packet) -> {#icmp{}, Payload} | binary()
icmp6(Packet) -> {#icmp6{}, Payload} | binary()
igmp(Packet) -> {#igmp{}, Payload} | binary()
mpls(Packet) -> {#mpls{}, Next, Payload}
lldp(Packet) -> {#lldp{}, Payload}
rarp(Packet) -> {#rarp{}, Payload}
'802.1x'(Packet) -> {#'802.1x'{}, Payload}

    Types   Packet = Header | binary()
            Header = #ether{} | #null{} | #linux_cooked{} | #arp{} |
                #ipv4{} | #ipv6{} | #tcp{} | #sctp{} | #udp{} |
                #icmp{} | #icmp6{} | #igmp{} | #gre{} | #llc{} |
                #vrrp{} | #'802.1q'{} | #lldp{} | #mpls{} | #rarp{} | #'802.1x'{}
            Next = ipv4 | ipv6


makesum(Packet) -> integer()

    Types   Packet = IPv4_header | [IPv4_header, Header, Payload]
            IPv4_header = #ipv4{}
            Header = #tcp{} | #udp{}
            Payload = binary()

    Calculate the one's complement checksum of the packet.

    When computing the checksum, the header sum field must be set
    to 0:

        Sum = pkt:makesum([IPv4, TCP#tcp{sum = 0}, Payload]).

    For verifcation, the checksum can be compared to the value in
    the header or:

        0 = pkt:makesum([IPv4, TCP, Payload]).

EXAMPLES

  • decode an ethernet frame, displaying the source and destination of valid packets
Frame = <<224,105,149,59,163,24,0,22,182,181,62,198,8,0,69,0,0,54,2,108,64,
          0,53,6,172,243,173,192,82,195,192,168,213,54,0,80,143,166,75,154,
          212,181,116,33,53,92,128,24,0,126,60,199,0,0,1,1,8,10,92,104,96,
          16,22,69,237,136,137,0>>,

try pkt:decapsulate(Frame) of
    [#ether{}, #ipv4{saddr = Saddr, daddr = Daddr},
        #tcp{sport = Sport, dport = Dport}, _Payload] ->
        {{Saddr, Sport}, {Daddr, Dport}}
catch
    error:_ ->
        ok % ignore invalid packets
end
  • verify the TCP checksum of an ethernet frame
{ok, [#ether{}, IPv4, #tcp{sum = Sum} = TCP, Payload]} = pkt:decode(ether, Frame),

% Re-calculate the checksum and match against the checksum in the header
Sum = pkt:makesum([IPv4, TCP#tcp{sum = 0}, Payload]),

% Or just verify the checksum
0 = pkt:makesum([IPv4, TCP, Payload]).

PADDING OF ETHERNET FRAMES

The minimum size of an ethernet payload is 46 bytes. An ethernet frame containing a TCP/IP packet composed of a 20 byte IPv4 header and 20 byte TCP header and payload will be padded by 6 bytes. To calculate the actual length of the packet, use the length and header length values in the IPv4 header and the offset value in the TCP header:

[#ether{}, #ipv4{len = Len, hl = HL}, #tcp{off = Off}, Payload] = pkt:decapsulate(Frame),
    Size = Len - (HL * 4) - (Off * 4),
    <<Payload:Size/bytes>>.

TODO

  • support RFC 2675 (IPv6 Jumbograms)

  • IPv6 AH and ESP

    • handle alignment differences between IPv4 and IPv6 (IPv4 uses 32 bits, IPv6 uses 64 bits)
  • ICMPv6

    • fix handling of neighbour discovery
    • simplify ICMPv6 header record and add a record for ICMPv6 type or add functions for ICMPv6 variable length payloads
  • IGMP

    • support IGMPv3 variable payloads
  • merge in DLT_IEEE802_11 support from wierl

  • merge in ICMPv6 code from gen_icmp

  • DLTs

    • DLT_SLIP
    • DLT_PPP
    • DLT_RAW
    • DLT_PPP_SERIAL
    • DLT_PPP_ETHER
    • DLT_LOOP

More Repositories

1

procket

Erlang interface to low level socket operations
C
284
star
2

epcap

Erlang packet capture interface using pcap
C
178
star
3

gen_icmp

Erlang interface to ICMP sockets
Erlang
100
star
4

evum

["Linux VM", ["Erlang Process", ["Erlang VM"]]].
Erlang
86
star
5

tunctl

Erlang TUN/TAP interface
Erlang
76
star
6

sods

Socket over DNS tunnel
C
69
star
7

verx

Erlang implementation of the libvirtd remote protocol
Erlang
58
star
8

srly

Native Erlang Unix serial interface
Erlang
54
star
9

alcove

Control plane for system processes
C
47
star
10

prx

an Erlang library for interacting with Unix processes
Erlang
35
star
11

erlang-libvirt

Erlang binding to libvirt virtualization API
Erlang
35
star
12

libkeepalive

LD_PRELOAD library for enabling TCP keepalive socket options
C
32
star
13

emdns

Erlang multicast DNS and DNS-SD (DNS Service Discovery)
Erlang
32
star
14

ewpcap

Portable native Erlang raw socket interface using pcap
Erlang
32
star
15

gen_unix

Erlang Unix socket interface
Erlang
30
star
16

wierl

Erlang interface for manipulating 802.11 wireless devices
Erlang
24
star
17

xmppipe

stdio over XMPP
C
23
star
18

erlxc

Simple, safe erlang interface for managing Linux Containers
Erlang
22
star
19

stk500

Enough of the STK500 protocol in Erlang to control the Arduino boot loader
Erlang
21
star
20

libproxyproto

Proxy protocol v1 and v2 support via an LD_PRELOAD library
C
21
star
21

inert

An Erlang library for notification of events on file descriptors
Erlang
19
star
22

seds

Erlang socket over DNS tunnel server
Erlang
19
star
23

epcap_compile

Compile pcap-filter(7) expressions to BPF programs
Erlang
15
star
24

perc

Erlang interface for controlling Unix processes
Erlang
15
star
25

herp

Erlang user space bridge
Erlang
14
star
26

spoofed

Spoof the Erlang Distribution Protocol!
Erlang
14
star
27

execve

Go package for fexecve(3) and execveat(2)
Go
13
star
28

crypt

Erlang NIF wrapping Unix crypt(3)
Erlang
13
star
29

erpcgen

RPC/XDR protocol compiler (from jungerl)
Erlang
13
star
30

reuseport

SO_REUSEPORT socket load distribution using LD_PRELOAD
C
13
star
31

tuntap

Erlang "Universal TUN/TAP device" driver from Jungerl
C
12
star
32

islet

Simple, safe isolation using Erlang
Erlang
12
star
33

sut

Six (IPv6 in IPv4) Userlspace Tunnel
Erlang
11
star
34

erlang-notify-osd

Erlang NIF interface for sending desktop notifications
Erlang
11
star
35

farp

Poison the ARPs, courtesy of Erlang
Erlang
10
star
36

perv

Media captured from the ether for your viewing pleasure
Erlang
9
star
37

cerck

Password quality checks for Erlang
Erlang
9
star
38

runcron

simple, safe, container-friendly cron alternative
C
8
star
39

spood

The spoofing DNS proxy with a vaguely obscene name
Erlang
8
star
40

totp.c

simple, standalone TOTP without dependencies
C
7
star
41

drench

Makes things go ... down
C
7
star
42

sredird

RFC 2217 network serial port redirector
C
6
star
43

everl

Async socket notifications for Erlang using libev
C
6
star
44

ampule

An elixir library for linux containers
Elixir
6
star
45

libenospace

Process-based disk usage limits
C
6
star
46

runlet

Event stream query and flow control
Elixir
5
star
47

rst

Think of it as peer to peer QoS
C
5
star
48

trep

Selectively stream stdin to stdout/stderr based on regular expressions
C
4
star
49

wat

A simple example of an Erlang NIF for creating mutable variables
C
4
star
50

librlimit

rlimit sandbox for any process
C
4
star
51

pseudocron

sleep(1) using a cron expression
C
3
star
52

libsockfilter

Connection filtering for dynamically linked applications
C
3
star
53

stdio

Reliably reap, restrict and isolate system tasks: Stdio is a control plane for processes
Elixir
3
star
54

cm17a

Erlang X10 Firecracker (CM17A) Interface
Erlang
3
star
55

wwallo

Tag cloud for your geo location
JavaScript
2
star
56

libnoexec

Prevent dynamically linked executables from calling exec(3)
C
2
star
57

embedexe

Run an executable embedded in a Go binary
Go
2
star
58

runlet_sh

Generate runlets from containerized Unix processes
Elixir
2
star
59

collectd-prv

stdout to collectd notification
C
1
star
60

tscat

Timestamp stdin to stdout/stderr
C
1
star
61

runhash-go

runhash: command line interface for distributed node selection
Go
1
star
62

noprivexec

noprivexec: disable setuid privileges
C
1
star
63

pdeathsigexec

signal process when parent exits
C
1
star
64

tcpexec-rs

tcpexec: a minimal, UCSPI inetd
Rust
1
star
65

unixexec

attach stdin/stdout of a command to a Unix socket
C
1
star
66

pipewatch

pipewatch: supervise pipelines of processes
C
1
star
67

fchmodexec

fchmod(2) inherited file descriptors before exec(3)'ing a command
C
1
star
68

prv

pressure relief valve for Unix process pipelines
C
1
star
69

closefrom

close(2) a range of file descriptors before exec(2)
C
1
star
70

xmppipe-go

stdio over XMPP
Go
1
star
71

runlimit

restart intensity limits for supervised Unix processes
C
1
star
72

tcpexec

tcpexec: a minimal, UCSPI inetd
C
1
star
73

logsurfer-

Rules based log file monitoring and alerting tool
C
1
star
74

imappipe

poll IMAP mailbox to stdout
Go
1
star
75

hexlog

Hexdump stdin and/or stdout to stderr
C
1
star
76

runlock

rate limit command invocation based on the last successful run time
C
1
star
77

eventbot

A bot for generating and interacting with event streams using XMPP
Elixir
1
star
78

goreap

User init to supervise and terminate subprocesses
Go
1
star
79

dnsup

Publish an IP address using the Cloudflare API
Go
1
star
80

genlb-ptrace

connect(2) load balancer for Unix processes
C
1
star
81

runlet_net

Miscellaneous network related commands for runlets
Erlang
1
star