Documentation
¶
Overview ¶
Package sflow decodes sFlow v5 datagrams per the InMon publicly-published sFlow v5 specification (sflow.org). sFlow is the packet-sampling counterpart to NetFlow (covered by `netflow_v5_decode`): instead of summarising per-flow state, sFlow exports a configurable 1-in-N sample of the packets transiting a device, plus periodic interface counters.
Operationally, sFlow is the dominant monitoring telemetry on every modern datacenter switch — Arista, Cisco Nexus, HP, Juniper QFX, Mellanox, Cumulus — because it scales linearly with link speed regardless of flow churn (whereas NetFlow's per-flow state grows with churn). DDoS-detection, capacity planning, and security-NDR platforms all consume sFlow.
Wrap-vs-native judgement
Native. The sFlow v5 spec is fully public; the wire format is XDR-encoded (network-byte-order, 4-byte aligned). A 32-byte datagram header is followed by N (Sample Type + Length + Data) records, each carrying either a Flow Sample (per-packet) or a Counter Sample (per-interface periodic). No crypto, no compression. Operators paste sFlow bytes (UDP destination port 6343) from a `tcpdump -X udp port 6343` line or a Wireshark Follow-UDP-Stream view and get the documented header + sample breakdown.
What this package covers
**Datagram common header** (variable; 28 or 40 bytes):
bytes 0-3: Version (uint32 BE; must be 5).
bytes 4-7: Agent Address Type (uint32 BE; 1 IPv4, 2 IPv6).
then 4 bytes IPv4 or 16 bytes IPv6 Agent Address.
next 4 bytes: Sub-Agent ID (uint32 BE).
next 4 bytes: Sequence Number (uint32 BE; per-Agent monotonic — gaps signal datagram loss).
next 4 bytes: System Uptime (uint32 BE; ms since agent boot).
next 4 bytes: Sample Count (uint32 BE; number of samples in this datagram).
**Sample walker** — repeated 8-byte header (Sample Type uint32 BE + Sample Length uint32 BE) + sample body. The Sample Type is split into top 12 bits (Enterprise; 0 for standard sFlow) + bottom 20 bits (Format). **4-entry standard sample format table**: 1 Flow Sample, 2 Counter Sample, 3 Expanded Flow Sample, 4 Expanded Counter Sample (Expanded uses uint64 ifIndex fields for bonded interfaces above 2^32 — same body otherwise).
**Flow Sample body** (Format 1):
Sequence Number (uint32 BE).
Source ID: top 8 bits **Source Class** (0 ifIndex, 1 smonVlanDataSource, 2 entPhysicalEntry) + low 24 bits **Source Index** (typically ifIndex of the sampler).
**Sampling Rate** (uint32 BE; 1-in-N).
Sample Pool (uint32 BE; total packets seen so far on this source).
Drops (uint32 BE; cumulative buffer drops).
Input Interface Index (uint32 BE).
Output Interface Index (uint32 BE; high bits encode special meanings — Discarded, Multiple, Unknown — surfaced as a Note when set).
Number of Flow Records (uint32 BE) + N Flow Records.
**Flow Record types** (most common):
**1 Raw Packet Header** — Header Protocol (uint32 BE; **6-entry name table**: 1 Ethernet / 11 802.11 / 12 IPv4 / 13 IPv6 / 21 PPP / 22 PPPoE) + Frame Length on wire (uint32 BE) + Stripped octets (uint32 BE; bytes trimmed from start, typically the L2 framing) + Original Sampled Header Length (uint32 BE) + Header Bytes (capped hex preview).
**2 Ethernet Frame Data** — Length + 6-byte src MAC + 6-byte dst MAC + EtherType.
**3 IPv4 Data** — Length + Protocol (IP proto number) + 4-byte src + 4-byte dst + uint32 src port + uint32 dst port + uint32 TCP flags + uint32 ToS.
**4 IPv6 Data** — same shape but with 16-byte addresses and an IPv6 priority.
**Counter Sample body** (Format 2):
Sequence Number (uint32 BE).
Source ID (same split as Flow Sample).
Number of Counter Records (uint32 BE) + N records.
**Counter Record type 1 (Generic Interface Counters)** — full 88-byte body: ifIndex / ifType / ifSpeed (uint64) / ifDirection / ifStatus / ifInOctets (uint64) / ifInUcastPkts / ifInMulticastPkts / ifInBroadcastPkts / ifInDiscards / ifInErrors / ifInUnknownProtos / ifOutOctets (uint64) / ifOutUcastPkts / ifOutMulticastPkts / ifOutBroadcastPkts / ifOutDiscards / ifOutErrors / ifPromiscuousMode.
What this package does NOT cover (deliberately out of scope)
UDP framing — feed sFlow bytes after the UDP header strip. sFlow runs on UDP destination port 6343.
sFlow v4 and earlier — the wire format changed significantly; v5 has been the standard since 2003.
Per-Counter-Record dissection beyond Generic Interface Counters (Ethernet / Token Ring / 802.11 / VG / VLAN / Processor / Radio counters) — surfaced as raw hex; a future iteration could add them.
Raw Packet Header inner dissection — the captured header bytes are surfaced as hex; the operator feeds them into the appropriate `*_decode` Spec (e.g. `ip_packet_decode`) based on the Header Protocol.
sFlow agent state-machine reasoning (sampling-rate drift, polling-interval skew) — higher-level analysis.
Index ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type CounterRecord ¶
type CounterRecord struct {
RecordType uint32 `json:"record_type"`
Enterprise uint32 `json:"enterprise"`
Format uint32 `json:"format"`
FormatName string `json:"format_name"`
RecordLength uint32 `json:"record_length"`
DataHex string `json:"data_hex,omitempty"`
// Decoded forms populated for known record formats.
GenericInterface *GenericInterfaceCounters `json:"generic_interface_counters,omitempty"`
}
CounterRecord is one (Record Type, Length, Data) entry from a Counter Sample's counters array.
type CounterSampleBody ¶
type CounterSampleBody struct {
SequenceNumber uint32 `json:"sequence_number"`
SourceID uint32 `json:"source_id"`
SourceClass int `json:"source_class"`
SourceClassName string `json:"source_class_name"`
SourceIndex uint32 `json:"source_index"`
NumberOfRecords uint32 `json:"number_of_counter_records"`
CounterRecords []CounterRecord `json:"counter_records,omitempty"`
}
CounterSampleBody is the decoded body of a Counter Sample (Format 2).
type DecodeOpts ¶
type DecodeOpts struct {
// MaxHeaderBytes caps the per-Raw-Packet-Header hex
// preview. Zero shows full header (up to typical
// sampled length of 128 bytes).
MaxHeaderBytes int
}
DecodeOpts tunes the walker for output size.
func DefaultDecodeOpts ¶
func DefaultDecodeOpts() DecodeOpts
DefaultDecodeOpts returns a 128-byte header preview cap.
type EthernetFrame ¶
type EthernetFrame struct {
Length uint32 `json:"length"`
SrcMAC string `json:"src_mac"`
DstMAC string `json:"dst_mac"`
EtherType uint32 `json:"ether_type"`
EtherTypeHex string `json:"ether_type_hex"`
}
EthernetFrame is the decoded body of Flow Record Format 2.
type FlowRecord ¶
type FlowRecord struct {
RecordType uint32 `json:"record_type"`
Enterprise uint32 `json:"enterprise"`
Format uint32 `json:"format"`
FormatName string `json:"format_name"`
RecordLength uint32 `json:"record_length"`
DataHex string `json:"data_hex,omitempty"`
// Decoded forms populated for known record formats.
RawPacketHeader *RawPacketHeader `json:"raw_packet_header,omitempty"`
EthernetFrame *EthernetFrame `json:"ethernet_frame,omitempty"`
IPv4Data *IPv4FlowData `json:"ipv4_data,omitempty"`
}
FlowRecord is one (Record Type, Length, Data) entry from a Flow Sample's flow_records array.
type FlowSampleBody ¶
type FlowSampleBody struct {
SequenceNumber uint32 `json:"sequence_number"`
SourceID uint32 `json:"source_id"`
SourceClass int `json:"source_class"`
SourceClassName string `json:"source_class_name"`
SourceIndex uint32 `json:"source_index"`
SamplingRate uint32 `json:"sampling_rate"`
SamplePool uint32 `json:"sample_pool"`
Drops uint32 `json:"drops"`
InputInterface uint32 `json:"input_interface"`
OutputInterface uint32 `json:"output_interface"`
OutputInterfaceNote string `json:"output_interface_note,omitempty"`
NumberOfRecords uint32 `json:"number_of_flow_records"`
FlowRecords []FlowRecord `json:"flow_records,omitempty"`
}
FlowSampleBody is the decoded body of a Flow Sample (Format 1).
type GenericInterfaceCounters ¶
type GenericInterfaceCounters struct {
IfIndex uint32 `json:"if_index"`
IfType uint32 `json:"if_type"`
IfSpeed uint64 `json:"if_speed"`
IfDirection uint32 `json:"if_direction"`
IfStatus uint32 `json:"if_status"`
IfInOctets uint64 `json:"if_in_octets"`
IfInUcastPkts uint32 `json:"if_in_ucast_pkts"`
IfInMulticastPkts uint32 `json:"if_in_multicast_pkts"`
IfInBroadcastPkts uint32 `json:"if_in_broadcast_pkts"`
IfInDiscards uint32 `json:"if_in_discards"`
IfInErrors uint32 `json:"if_in_errors"`
IfInUnknownProtos uint32 `json:"if_in_unknown_protos"`
IfOutOctets uint64 `json:"if_out_octets"`
IfOutUcastPkts uint32 `json:"if_out_ucast_pkts"`
IfOutMulticastPkts uint32 `json:"if_out_multicast_pkts"`
IfOutBroadcastPkts uint32 `json:"if_out_broadcast_pkts"`
IfOutDiscards uint32 `json:"if_out_discards"`
IfOutErrors uint32 `json:"if_out_errors"`
IfPromiscuousMode uint32 `json:"if_promiscuous_mode"`
}
GenericInterfaceCounters is the decoded body of Counter Record Format 1 (88-byte ifEntry-equivalent body).
type IPv4FlowData ¶
type IPv4FlowData struct {
Length uint32 `json:"length"`
Protocol uint32 `json:"protocol"`
SrcAddress string `json:"src_address"`
DstAddress string `json:"dst_address"`
SrcPort uint32 `json:"src_port"`
DstPort uint32 `json:"dst_port"`
TCPFlags uint32 `json:"tcp_flags"`
TypeOfService uint32 `json:"type_of_service"`
}
IPv4FlowData is the decoded body of Flow Record Format 3.
type RawPacketHeader ¶
type RawPacketHeader struct {
HeaderProtocol uint32 `json:"header_protocol"`
HeaderProtocolName string `json:"header_protocol_name"`
FrameLengthOnWire uint32 `json:"frame_length_on_wire"`
StrippedBytes uint32 `json:"stripped_bytes"`
SampledHeaderLength uint32 `json:"sampled_header_length"`
HeaderBytesShown int `json:"header_bytes_shown,omitempty"`
HeaderHex string `json:"header_hex,omitempty"`
}
RawPacketHeader is the decoded body of Flow Record Format 1.
type Result ¶
type Result struct {
Version uint32 `json:"version"`
AgentAddressType int `json:"agent_address_type"`
AgentAddress string `json:"agent_address"`
SubAgentID uint32 `json:"sub_agent_id"`
SequenceNumber uint32 `json:"sequence_number"`
SystemUptimeMs uint32 `json:"system_uptime_ms"`
SampleCount uint32 `json:"sample_count"`
Samples []Sample `json:"samples"`
TotalBytes int `json:"total_bytes"`
Notes []string `json:"notes,omitempty"`
}
Result is the top-level decoded view of an sFlow v5 datagram.
type Sample ¶
type Sample struct {
SampleType uint32 `json:"sample_type"`
Enterprise uint32 `json:"enterprise"`
Format uint32 `json:"format"`
FormatName string `json:"format_name"`
SampleLength uint32 `json:"sample_length"`
BodyHex string `json:"body_hex,omitempty"`
// Decoded forms populated for known sample formats.
FlowSample *FlowSampleBody `json:"flow_sample,omitempty"`
CounterSample *CounterSampleBody `json:"counter_sample,omitempty"`
}
Sample is one (Sample Type, Length, Data) record from the sample walker.