Framebuffer (source code)

= Framebuffer

A \b[framebuffer] is <computer memory> holding an image's <pixel> values in a representation usable by graphics hardware or <software>. A <pixel format> specifies how stored <bits> encode those values. The image's dimensions alone do not determine its complete memory layout: rows can include padding, and different layouts can organize components differently.<The Frame Buffer Device API in the Linux Kernel documentation>[§2, Types and visuals; related Frame Buffer Device introduction, §§0–1]{ref}

For a concrete packed-row model, let the image be three <pixels> wide and two rows high, using four <bytes> per <pixel>. A row's actual pixel data occupies $3\times4=12$ <bytes>. If each row starts 16 <bytes> after the previous one, the <framebuffer stride> is 16 <bytes> and four padding <bytes> separate consecutive pixel rows. Reserving two complete row slots takes $2\times16=32$ <bytes>, although the pixel values themselves occupy only 24 <bytes>.

With zero-based coordinates, base <memory address> $B$, stride $S$ and $b$ <bytes> per <pixel>, the start of a <pixel> in this stipulated layout is
$$
\operatorname{address}(x,y)=B+yS+xb.
$$
Thus $(x,y)=(2,1)$ starts at $B+16+8=B+24$. Replacing $S$ by the packed width12 would instead address the wrong location. This formula assumes packed, byte-addressable rows; it is not a formula for every possible <pixel format>.

The Linux interface makes the distinction explicit: `line_length` reports row length in <bytes>, separately from resolution and `bits_per_pixel`. A program should use the layout supplied by the interface when interpreting a <framebuffer>, rather than infer it from the visible dimensions alone.<The Frame Buffer Device API in the Linux Kernel documentation>[§3, Screen information, fixed line_length and variable resolution/depth fields]{ref}