rawsend

package
v1.2.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 9, 2026 License: BSD-3-Clause Imports: 7 Imported by: 0

Documentation

Overview

Package rawsend provides high-performance raw IPv4 packet sending primitives that bypass Go's net.IPConn overhead.

Sender wraps a raw socket file descriptor and calls sendto() directly via the syscall package, eliminating net.IPConn.WriteTo's mutex, poll.FD, and error-wrapping overhead (~1µs per packet).

On Linux, NewBatch returns a Batch that accumulates packets and sends them via sendmmsg (loaded through purego, no CGO required), amortising syscall overhead across N packets.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Batch

type Batch struct {
	// contains filtered or unexported fields
}

Batch accumulates raw IPv4 packets and sends them via a single sendmmsg syscall, amortising kernel-transition overhead across batchSize packets.

Loaded via purego (no CGO). NewBatch returns nil when sendmmsg is not available.

func NewBatch

func NewBatch(fd socketFD, batchSize, maxPktLen int) *Batch

NewBatch creates a batch sender that accumulates up to batchSize packets of at most maxPktLen bytes each, sending them all in one sendmmsg syscall. Returns nil if sendmmsg is not available.

func (*Batch) Add

func (b *Batch) Add(pkt []byte, dstIP [4]byte) error

Add copies pkt into the batch and sets the destination IPv4 address. When the batch is full, it is flushed automatically.

func (*Batch) Flush

func (b *Batch) Flush() error

Flush sends all queued packets via sendmmsg. If the kernel performs a partial send (fewer messages than requested), Flush retries the remaining messages. On a mid-batch error (typically ENOBUFS/EAGAIN when the qdisc is full) the still-unsent messages are compacted to the front of the batch and kept queued, so a caller that backs off re-sends them on the next Flush instead of silently dropping up to batchSize-1 probes.

func (*Batch) Len

func (b *Batch) Len() int

Len returns the number of packets currently queued.

type Sender

type Sender struct {
	// contains filtered or unexported fields
}

Sender sends raw IPv4 packets via direct sendto() syscall, bypassing Go's net.IPConn.WriteTo overhead (poll.FD mutex, deadline management, error wrapping).

func NewFromFD

func NewFromFD(fd socketFD, conn *net.IPConn) *Sender

NewFromFD creates a Sender from an already-known file descriptor. conn must be the net.IPConn that owns fd (kept alive to prevent GC).

func NewFromIPConn

func NewFromIPConn(conn *net.IPConn) (*Sender, error)

NewFromIPConn creates a Sender by extracting the raw file descriptor from conn. The conn reference is retained to prevent garbage collection (which would close the fd).

func (*Sender) FD

func (s *Sender) FD() socketFD

FD returns the raw socket file descriptor (or handle on Windows).

func (*Sender) SendTo

func (s *Sender) SendTo(pkt []byte, dstIP [4]byte) error

SendTo transmits pkt to the IPv4 address dstIP using a direct sendto() syscall. The kernel adds the IPv4 header based on the socket's protocol (e.g. IPPROTO_TCP).

SendTo is NOT safe for concurrent use from multiple goroutines because it reuses an internal sockaddr struct without locking.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL