wired
libc-free QUIC/HTTP3 SDK in C for x86_64-linux
Loading...
Searching...
No Matches
srvxdp.h File Reference

AF_XDP driver integration for the HTTP/3 server: opens one AF_XDP socket plus its BPF redirect filter, and drives the resulting rings with the app-facing mmsg_buf shape. More...

#include "app/http3/server/srvxdpbpf/srvxdpbpf.h"
#include "common/bytes/span/span.h"
#include "transport/io/socket/io/udp.h"
#include "transport/io/xdp/xdpmac/xdpmac.h"
#include "transport/io/xdp/xsksetup/xsksetup.h"
#include "transport/io/xdp/xskumem/xskumem.h"

Go to the source code of this file.

Data Structures

struct  wired_srvxdp_cfg
 Caller-supplied configuration for one AF_XDP-backed server socket. More...
struct  wired_srvxdp
 One open AF_XDP driver instance: the socket/rings, the TX frame pool, the learned peer MAC cache, and — when this instance opened its own BPF redirect filter rather than joining a shared one — those BPF objects. More...

Functions

i64 wired_srvxdp_open (wired_srvxdp *x, const wired_srvxdp_cfg *cfg)
 Open one AF_XDP-backed server socket with its own BPF redirect filter: wired_srvxdpbpf_open on cfg->ifindex, then xsksetup_open, then point the map's queue_id slot at the new socket.
i64 wired_srvxdp_open_shared (wired_srvxdp *x, const wired_srvxdp_cfg *cfg, wired_srvxdpbpf *bpf)
 Open one AF_XDP-backed server socket against an already-open shared per-interface BPF object: xsksetup_open, then register the new socket's fd in bpf's cfg->queue_id slot.
i64 wired_srvxdp_rx_burst (wired_srvxdp *x, mmsg_buf *bufs, usz nbufs)
 Drain up to nbufs received datagrams into bufs.
i64 wired_srvxdp_send (wired_srvxdp *x, const sockaddr *dst, wired_span pkt)
 Send one datagram to dst.
void wired_srvxdp_close (wired_srvxdp *x)
 Tear down x: close the owned BPF link/prog/map fds (skipped when x was opened against a shared wired_srvxdpbpf, which the caller owns), then xsksetup_close the socket/rings/UMEM.
void wired_srvxdp_print_stats (i64 fd)
 Read XDP_STATISTICS for fd (xsksetup_stats) and log one line per counter (name + value) via wired_log_str.

Detailed Description

AF_XDP driver integration for the HTTP/3 server: opens one AF_XDP socket plus its BPF redirect filter, and drives the resulting rings with the app-facing mmsg_buf shape.

Delegates every actual mechanism to its lower-layer domain (xsksetup for the syscall plumbing, xdpbpf for the filter program, xdpframe for the wire codec, xdpmac for the reflect cache, xskumem for the TX frame pool): this file is only the driving glue between them.

Function Documentation

◆ wired_srvxdp_close()

void wired_srvxdp_close ( wired_srvxdp * x)

Tear down x: close the owned BPF link/prog/map fds (skipped when x was opened against a shared wired_srvxdpbpf, which the caller owns), then xsksetup_close the socket/rings/UMEM.

Parameters
xdriver instance to close

◆ wired_srvxdp_open()

i64 wired_srvxdp_open ( wired_srvxdp * x,
const wired_srvxdp_cfg * cfg )

Open one AF_XDP-backed server socket with its own BPF redirect filter: wired_srvxdpbpf_open on cfg->ifindex, then xsksetup_open, then point the map's queue_id slot at the new socket.

The TX frame pool is initialized over UMEM frames 64..127 (the RX pool, frames 0..63, is left to the kernel's fill/rx rings). On any failure, everything already built is torn down and a negative errno is returned. For multiple queues on one interface, use wired_srvxdp_open_shared instead: the kernel rejects a second XDP link on the same ifindex with -EBUSY.

Parameters
xzero-initialized output; filled in on success
cfginterface/queue/address/port and bind/attach flags
Returns
0 on success, or a negative errno

◆ wired_srvxdp_open_shared()

i64 wired_srvxdp_open_shared ( wired_srvxdp * x,
const wired_srvxdp_cfg * cfg,
wired_srvxdpbpf * bpf )

Open one AF_XDP-backed server socket against an already-open shared per-interface BPF object: xsksetup_open, then register the new socket's fd in bpf's cfg->queue_id slot.

x keeps no reference to bpf afterwards (x->bpf stays -1/-1/-1, unowned): the caller owns bpf's lifetime and must keep it open while any registered socket is in use. On failure the socket is closed and a negative errno is returned.

Parameters
xzero-initialized output; filled in on success
cfginterface/queue/address/port and bind flags (attach_flags is unused: attachment happened in wired_srvxdpbpf_open)
bpfshared BPF objects for cfg->ifindex (wired_srvxdpbpf_open)
Returns
0 on success, or a negative errno

◆ wired_srvxdp_print_stats()

void wired_srvxdp_print_stats ( i64 fd)

Read XDP_STATISTICS for fd (xsksetup_stats) and log one line per counter (name + value) via wired_log_str.

A no-op (silently returns) if the stats read fails.

Parameters
fdthe XDP socket file descriptor

◆ wired_srvxdp_rx_burst()

i64 wired_srvxdp_rx_burst ( wired_srvxdp * x,
mmsg_buf * bufs,
usz nbufs )

Drain up to nbufs received datagrams into bufs.

First reaps the completion ring (returning any finished TX frames to txpool), then consumes up to nbufs entries from the RX ring: each frame is parsed (xdpframe_parse), its payload copied into bufs[i].buf, its source into bufs[i].src, and the peer's MAC learned into the reflect cache (the first RX frame also seeds x->our_mac). Every consumed RX frame is returned to the fill ring before this call returns.

Parameters
xopen driver instance
bufsarray of nbufs receive slots
nbufsnumber of slots in bufs
Returns
number of datagrams written into bufs (0..nbufs)

◆ wired_srvxdp_send()

i64 wired_srvxdp_send ( wired_srvxdp * x,
const sockaddr * dst,
wired_span pkt )

Send one datagram to dst.

Drops (returns 0, letting QUIC retransmit) when dst's MAC is not yet learned, or when the TX frame pool is exhausted even after one completion-ring reap. On success, builds a complete eth+IPv4+UDP frame around pkt into a TX-pool frame, submits it to the TX ring, and kicks the kernel to service it (a kick failure is ignored: tests exercising this without a real fd expect it to fail).

Parameters
xopen driver instance
dstdestination address
pktthe QUIC datagram to send
Returns
1 sent, 0 dropped