|
ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
|
IT8951 geometry, pixel-format, waveform-map and config validation. More...
#include <stddef.h>#include <stdint.h>#include "ra8_attributes.h"#include "ra8_check.h"#include "ra8_epaper.h"#include "ra8_err.h"Go to the source code of this file.
Enumerations | |
| enum | ra8_epaper_geom_const_t : uint16_t { k_ra8_epaper_geom_bits_per_byte = 8U , k_ra8_epaper_geom_panel_max_dim = 4096U } |
| Packing arithmetic constants (no magic numbers). More... | |
| enum | ra8_epaper_bpp_t : uint8_t { k_ra8_epaper_bpp_1 = 1U , k_ra8_epaper_bpp_2 = 2U , k_ra8_epaper_bpp_4 = 4U , k_ra8_epaper_bpp_8 = 8U } |
| Bit depth of each ra8_epaper_pixel_format_t. More... | |
| enum | ra8_epaper_lut_mode_t : uint8_t { k_ra8_epaper_lut_init = 0U , k_ra8_epaper_lut_du = 1U , k_ra8_epaper_lut_gc16 = 2U , k_ra8_epaper_lut_a2_m641 = 4U , k_ra8_epaper_lut_a2_gen = 6U } |
| Waveform LUT mode numbers the vendor documents. More... | |
Functions | |
| uint8_t | ra8_epaper_bits_per_pixel (ra8_epaper_pixel_format_t pf) |
| Bits per pixel carried by a ra8_epaper_pixel_format_t. | |
| ra8_err_t | ra8_epaper_image_bytes (const ra8_epaper_area_t *area, ra8_epaper_pixel_format_t pf, size_t *out_bytes) |
| Bytes a packed source buffer needs for area at depth pf. | |
| bool | ra8_epaper_area_is_aligned (const ra8_epaper_area_t *area, ra8_epaper_pixel_format_t pf) |
| Report whether area satisfies the depth's X/width alignment. | |
| ra8_err_t | ra8_epaper_align_area (ra8_epaper_area_t *area, ra8_epaper_pixel_format_t pf, uint16_t panel_width) |
| Grow area outward onto the alignment grid its depth requires. | |
| ra8_err_t | ra8_epaper_waveform_cfg_for_lut (const char *lut_version, ra8_epaper_waveform_cfg_t *out_cfg) |
| Fill a waveform map from a controller-reported LUT version. | |
| static ra8_err_t | internal_ra8_epaper_validate_waveform (const ra8_epaper_waveform_cfg_t *wf) |
| Validate the caller's waveform map against the LUT mode range. | |
| ra8_err_t | ra8_epaper_validate_cfg (const ra8_epaper_cfg_t *cfg) |
| Validate a panel descriptor without touching any hardware. | |
| bool | ra8_epaper_geometry_agrees (const ra8_epaper_dev_info_t *info, const ra8_epaper_cfg_t *cfg) |
| Report whether reported panel geometry matches the descriptor. | |
Variables | |
| static const char *const | s_tag = "EPAPER" |
| Logging tag used by the null-argument guards in this TU. | |
| static const char *const | s_lut_m641 = "M641" |
| LUT-version token identifying the 6 inch / 6 inch HD waveform set. | |
IT8951 geometry, pixel-format, waveform-map and config validation.
The pure half of the IT8951 driver, split out of ra8_epaper.c so neither translation unit exceeds the repository's file-size cap. These functions touch no bus, no GPIO and no driver state – they are total functions over their arguments, which is why they can be called (and tested) before ra8_epaper_init has ever run.
Three IT8951 facts are encoded here, and each one is a defect the driver previously had:
ra8_epaper_validate_cfg lives here for the same reason: it is a total function over a descriptor, checking exactly the geometry and waveform-map facts above, so it can reject a bad board descriptor before any bus exists to talk to.
Definition in file ra8_epaper_geom.c.
| enum ra8_epaper_bpp_t : uint8_t |
Bit depth of each ra8_epaper_pixel_format_t.
| Enumerator | |
|---|---|
| k_ra8_epaper_bpp_1 | |
| k_ra8_epaper_bpp_2 | |
| k_ra8_epaper_bpp_4 | |
| k_ra8_epaper_bpp_8 | |
Definition at line 68 of file ra8_epaper_geom.c.
| enum ra8_epaper_geom_const_t : uint16_t |
Packing arithmetic constants (no magic numbers).
| Enumerator | |
|---|---|
| k_ra8_epaper_geom_bits_per_byte | Row-packing denominator. |
| k_ra8_epaper_geom_panel_max_dim | Sanity ceiling on cfg dims. |
Definition at line 59 of file ra8_epaper_geom.c.
| enum ra8_epaper_lut_mode_t : uint8_t |
Waveform LUT mode numbers the vendor documents.
INIT / DU / GC16 are stable across every Waveshare IT8951 panel. A2 is the one that moves: mode 4 on the M641 LUT (6 inch, 6 inch HD) and mode 6 on the vendor's generic default for the larger panels.
Definition at line 84 of file ra8_epaper_geom.c.
|
staticnodiscard |
Validate the caller's waveform map against the LUT mode range.
A zero-initialised map would silently refresh every mode as INIT, so DU / GC16 / A2 are additionally required to be non-zero. That single rule is what stops a board descriptor inheriting another panel's numbering by omission.
| [in] | wf | Caller-supplied waveform map; non-NULL. |
Definition at line 225 of file ra8_epaper_geom.c.
References ra8_epaper_waveform_cfg_t::a2, ra8_epaper_waveform_cfg_t::du, ra8_epaper_waveform_cfg_t::gc16, ra8_epaper_waveform_cfg_t::init, k_ra8_epaper_wf_mode_max, k_ra8_err_invalid_arg, and k_ra8_ok.
Referenced by ra8_epaper_validate_cfg().
|
nodiscard |
Grow area outward onto the alignment grid its depth requires.
Rounds x down and the right edge up to the next multiple of k_ra8_epaper_align_1bpp_px, then clamps the right edge to panel_width. Growing outward (never inward) guarantees the caller's requested rectangle stays wholly covered, so the refresh is a superset of what was asked for rather than a silently cropped subset. A no-op for depths other than 1 bpp.
| [in,out] | area | Rectangle to align in place; non-NULL. |
| [in] | pf | Pixel depth the rectangle will be sent at. |
| [in] | panel_width | Panel width in pixels used as the clamp; must be non-zero and itself a multiple of k_ra8_epaper_align_1bpp_px when pf is 1 bpp, otherwise the clamp could reintroduce a misaligned right edge. |
| k_ra8_ok | *area is aligned and within the panel. |
| k_ra8_err_null_ptr | area is NULL. |
| k_ra8_err_invalid_arg | panel_width is zero, area steps outside it, or the clamp cannot produce an aligned width. |
Definition at line 152 of file ra8_epaper_geom.c.
References k_ra8_epaper_align_1bpp_px, k_ra8_epaper_pf_1bpp, k_ra8_err_invalid_arg, k_ra8_ok, RA8_CHECK_NULL_PTR, s_tag, ra8_epaper_area_t::width, and ra8_epaper_area_t::x.
|
nodiscard |
Report whether area satisfies the depth's X/width alignment.
Only 1 bpp constrains geometry: the controller's bi-level LUT reads the update window in 4-byte units, so x and width must both be multiples of k_ra8_epaper_align_1bpp_px (32 pixels). Every other depth is unconstrained and always reports aligned.
| [in] | area | Rectangle to test; non-NULL. |
| [in] | pf | Pixel depth the rectangle will be transferred at. |
| true | pf is not 1 bpp, or both x and width sit on the 32-pixel grid. |
| false | pf is 1 bpp and x or width is misaligned. |
Definition at line 138 of file ra8_epaper_geom.c.
References k_ra8_epaper_align_1bpp_px, k_ra8_epaper_pf_1bpp, ra8_epaper_area_t::width, and ra8_epaper_area_t::x.
Referenced by internal_ra8_epaper_validate_load().
|
nodiscard |
Bits per pixel carried by a ra8_epaper_pixel_format_t.
Pure lookup used to size transfers. Kept public because the PAL and the host tests both need the packing arithmetic to agree with the driver's.
| [in] | pf | Pixel format selector. |
| 1 | For k_ra8_epaper_pf_1bpp. |
| 2 | For k_ra8_epaper_pf_2bpp. |
| 4 | For k_ra8_epaper_pf_4bpp. |
| 8 | For k_ra8_epaper_pf_8bpp and any out-of-range input (8 bpp is the widest format, so an unknown selector can only over-estimate the buffer a caller must supply – it can never under-run one). |
Definition at line 106 of file ra8_epaper_geom.c.
References k_ra8_epaper_bpp_1, k_ra8_epaper_bpp_2, k_ra8_epaper_bpp_4, k_ra8_epaper_bpp_8, k_ra8_epaper_pf_1bpp, k_ra8_epaper_pf_2bpp, k_ra8_epaper_pf_4bpp, and k_ra8_epaper_pf_8bpp.
Referenced by ra8_epaper_image_bytes().
|
nodiscard |
Report whether reported panel geometry matches the descriptor.
ra8_epaper_init cross-checks the geometry the controller reports in its GET_DEV_INFO block against the descriptor it was handed, and warns rather than fails on a mismatch. Both halves of that are deliberate: a controller that has not finished loading its waveform answers the first read with zeroes, and an application may legitimately drive a sub-window of a larger panel, so a mismatch is information rather than an error.
Split out of ra8_epaper_init so the comparison is a pure function that host tests can vary directly. Inside init it could only be reached through a real GET_DEV_INFO exchange, whose reported dimensions the test bus cannot steer to a value that is also a legal descriptor size – which left the "agrees" case untestable.
| [in] | info | Decoded device block; NULL is treated as disagreement. |
| [in] | cfg | Descriptor to compare against; NULL likewise. |
Definition at line 250 of file ra8_epaper_geom.c.
References ra8_epaper_cfg_t::panel_height, ra8_epaper_dev_info_t::panel_height, ra8_epaper_cfg_t::panel_width, and ra8_epaper_dev_info_t::panel_width.
Referenced by ra8_epaper_init().
|
nodiscard |
Bytes a packed source buffer needs for area at depth pf.
Rows are packed independently and each starts on a byte boundary, so the size is ceil(width * bpp / 8) * height. This is the exact value ra8_epaper_load_image requires in buf_len.
| [in] | area | Rectangle to be transferred; non-NULL. |
| [in] | pf | Source pixel depth. |
| [out] | out_bytes | Receives the required byte count; non-NULL. |
| k_ra8_ok | *out_bytes holds the size. |
| k_ra8_err_null_ptr | area or out_bytes is NULL. |
| k_ra8_err_invalid_size | area has a zero dimension. |
Definition at line 121 of file ra8_epaper_geom.c.
References ra8_epaper_area_t::height, k_ra8_epaper_geom_bits_per_byte, k_ra8_err_invalid_size, k_ra8_ok, RA8_CHECK_NULL_PTR, ra8_epaper_bits_per_pixel(), s_tag, and ra8_epaper_area_t::width.
Referenced by internal_eink_load_rect(), and internal_ra8_epaper_validate_load().
|
nodiscard |
Validate a panel descriptor without touching any hardware.
ra8_epaper_init calls this before it drives a single pin, so a bad descriptor is rejected with no bus traffic and no reset pulse. It is public because it is a total function over the descriptor: a board bring-up can check its own ra8_epaper_cfg_t before a controller is even attached.
Beyond range-checking the geometry, this rejects a zero-initialised waveform map. That check is load-bearing: mode 0 is INIT on every documented LUT, so a descriptor that forgot to fill the map would refresh every mode as a full INIT flash rather than fail, and a missing A2 would look like a merely slow panel instead of a misconfigured one.
| [in] | cfg | Descriptor to check; non-NULL. |
| k_ra8_ok | Every field is in range and usable. |
| k_ra8_err_null_ptr | cfg is NULL. |
| k_ra8_err_invalid_arg | A field is out of range, the bus seam is unbound, or the waveform map is unset. |
Definition at line 239 of file ra8_epaper_geom.c.
References ra8_epaper_cfg_t::bus, internal_ra8_epaper_validate_waveform(), k_ra8_epaper_geom_panel_max_dim, k_ra8_err_invalid_arg, ra8_epaper_cfg_t::panel_height, ra8_epaper_cfg_t::panel_width, RA8_CHECK_NULL_PTR, s_tag, ra8_epaper_cfg_t::waveform, and ra8_spi_bus_ops_t::xfer8.
Referenced by ra8_epaper_init().
|
nodiscard |
Fill a waveform map from a controller-reported LUT version.
The waveform mode numbering is a property of the firmware LUT the IT8951 loaded, which GET_DEV_INFO reports as a version string. The M641 LUT – the 6 inch and 6 inch HD panels, including the Waveshare 1448x1072 HAT – places A2 at mode 4; the vendor's generic default for the larger 7.8 / 9.7 / 10.3 inch panels is mode 6. INIT (0), DU (1) and GC16 (2) are stable across both.
The match is a prefix match on the leading M641 token, because the reported string carries a build suffix that varies between controller firmware revisions.
| [in] | lut_version | NUL-terminated LUT version string as reported in ra8_epaper_dev_info_t; non-NULL. |
| [out] | out_cfg | Receives the waveform map; non-NULL. |
| k_ra8_ok | *out_cfg populated (M641 or generic). |
| k_ra8_err_null_ptr | lut_version or out_cfg is NULL. |
Definition at line 182 of file ra8_epaper_geom.c.
References ra8_epaper_waveform_cfg_t::a2, ra8_epaper_waveform_cfg_t::du, ra8_epaper_waveform_cfg_t::gc16, ra8_epaper_waveform_cfg_t::init, k_ra8_epaper_lut_a2_gen, k_ra8_epaper_lut_a2_m641, k_ra8_epaper_lut_du, k_ra8_epaper_lut_gc16, k_ra8_epaper_lut_init, k_ra8_ok, RA8_CHECK_NULL_PTR, s_lut_m641, and s_tag.
Referenced by ep_bringup_panel_bus().
|
static |
LUT-version token identifying the 6 inch / 6 inch HD waveform set.
Matched as a prefix because the controller appends a build suffix that varies between firmware revisions.
Definition at line 104 of file ra8_epaper_geom.c.
Referenced by ra8_epaper_waveform_cfg_for_lut().
|
static |
Logging tag used by the null-argument guards in this TU.
Definition at line 53 of file ra8_epaper_geom.c.