Skip to main content

Module v4l2m2m

Module v4l2m2m 

Source
Expand description

Hardware H.264 through a generic stateful V4L2 M2M encoder: boards whose encoder sits behind the kernel’s own interface rather than a vendor library or a render node, such as a Raspberry Pi 4, RK356x, or i.MX8M. Built everywhere, since the interface is the kernel’s. Hardware H.264 through a generic stateful V4L2 M2M encoder.

Boards that carry an encoder behind the kernel’s own M2M interface publish no render node the VA-API backend can probe and no vendor library the NVENC one can load, so the ladder reaches software on hardware that encodes. A Raspberry Pi 4 is the case at hand (bcm2835-codec), and RK356x and i.MX8M carry the same interface, so the node is discovered by what it offers rather than by the board it sits on.

One host frame becomes one access unit: the frame is copied into the output buffer, queued, and the access unit comes back on the capture queue. The copy is the floor here as it is on Tegra — X11 capture hands over host memory — and it costs 3.81 ms for a 1080p frame on a Pi 4, which is the same speed as a copy between two ordinary allocations: the videobuf2-dma-contig buffer takes a write stream at full memory bandwidth.

Three things about such a device were measured rather than assumed, and each shapes the code:

  1. The output queue takes packed 32-bit color and the firmware converts it, so nothing converts on the CPU. The fourcc names are the opposite way round from the memory a caller holds: AB24 takes the BGRA an X11 capture produces, and BGR4 takes RGBA. Decoding an encoded chart is what settled that; reading the names would have swapped red and blue.
  2. The conversion is BT.601 at full range, and it cannot be steered: a S_FMT asking for REC709 at limited range comes back echoed and changes nothing. The stream also carries no video_signal_type, so what the session declares has to be written into the SPS on the way out, which collect is the place for.
  3. Constant bitrate is not available, and asking for it does not merely fail: the driver hands the firmware a rate control mode it refuses, and the next STREAMON answers ESRCH. A control this session cannot set is therefore a refusal, never a warning — the node has to be closed and reopened to be usable again.

Structs§

Buffer 🔒
Capability 🔒
Control 🔒
FmtDesc 🔒
Format 🔒
FrameSizeEnum 🔒
NodeInfo 🔒
What an encode node offers, read once for the process.
PixFormatMplane 🔒
Plane 🔒
PlaneFormat 🔒
RequestBuffers 🔒
StreamParm 🔒
The union of v4l2_streamparm begins one word in, not two: the frame rate lands in the wrong place if this is laid out like v4l2_format.
V4l2M2mEncoder

Enums§

Color 🔒
What the session has learned about the color its device produces.

Constants§

BITRATE_MODE_VBR 🔒
Variable is the only rate control such a device offers; see the note at the top about what asking for constant does to the session.
CAPTURE_BUFFERS 🔒
CID_BITRATE 🔒
CID_BITRATE_MODE 🔒
CID_FORCE_KEY_FRAME 🔒
CID_GOP_SIZE 🔒
CID_H264_I_PERIOD 🔒
CID_REPEAT_SEQ_HEADER 🔒
FRAME_TIMEOUT_MS 🔒
Long enough for a frame the hardware is slow on, short enough that a stalled node rebuilds the session rather than holding the stream. A 1080p frame takes about 35 ms on a Pi 4.
FRMSIZE_TYPE_DISCRETE 🔒
OUTPUT_BUFFERS 🔒
V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE 🔒
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE 🔒
V4L2_CAP_VIDEO_M2M 🔒
V4L2_CAP_VIDEO_M2M_MPLANE 🔒
V4L2_FIELD_NONE 🔒
V4L2_MEMORY_MMAP 🔒
V4L2_PIX_FMT_BGRA 🔒
Packed 32-bit color. The kernel spells these by channel order in a word and a caller holds bytes, so AB24 is the BGRA of an X11 capture and BGR4 is RGBA.
V4L2_PIX_FMT_H264 🔒
V4L2_PIX_FMT_HEVC 🔒
V4L2_PIX_FMT_RGBA 🔒
V4L2_PIX_FMT_VP8 🔒
V4L2_PIX_FMT_VP9 🔒
VIDIOC_DQBUF 🔒
VIDIOC_ENUM_FMT 🔒
VIDIOC_ENUM_FRAMESIZES 🔒
VIDIOC_QBUF 🔒
VIDIOC_QUERYBUF 🔒
VIDIOC_QUERYCAP 🔒
VIDIOC_REQBUFS 🔒
VIDIOC_STREAMOFF 🔒
VIDIOC_STREAMON 🔒
VIDIOC_S_CTRL 🔒
VIDIOC_S_FMT 🔒
VIDIOC_S_PARM 🔒

Functions§

abi_matches 🔒
The sizes the ioctl numbers above encode, checked once so a layout that drifted is a refusal with a name rather than a scribble through a structure.
available
Whether this machine carries an M2M encode node at all.
coded_fourcc
The capture-queue format for a codec the kernel’s interface names, or None for one it does not. The queues, the controls, and the input format are the same whichever of these a node carries, so the codec is a parameter rather than a second backend.
empty_format 🔒
encodes
Whether a session of this codec and size would come up on it, so the ladder can fall through to software before a session exists rather than after one has failed.
enumerates 🔒
fallback_rates 🔒
The rates to try, in order: what the session asked for, then the ones a device that refuses it is likely to take. A device is asked at its own rate first, so one that can do it is never slowed, and the steps below are the rates video hardware is built around rather than a search.
frame_sizes 🔒
input_format 🔒
The fourcc for the bytes a caller holds. The kernel spells these by channel order in a word, so the name of each is the reverse of the memory it takes, and a session that picks by name rather than by byte order swaps red and blue without failing.
ioctl 🔒 ⚠
known_conversion 🔒
What a device is known to convert RGB with when it declares nothing itself. Only a device whose behavior is on record earns an entry: a Raspberry Pi with firmware older than August 2024 converts to full range BT.601 and writes no video_signal_type, which the driver’s author states in the firmware tracker and a decoded chart confirms. Guessing for a device not on this list would put a claim in the stream that nobody has checked, and a wrong declaration colors a picture worse than an absent one.
node 🔒
The first node that encodes H.264 from packed color, found by asking rather than by name: the number a board gives its encoder is not a contract, and the same interface appears on boards with entirely different numbering.
served
The codecs the node encodes, for the report a caller reads before any session exists.