summaryrefslogtreecommitdiff
path: root/src/hal.zig
blob: c62ea2b9cfc56210704d7ccc3a61d5966a88b1b7 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
//! ESP32-P4 hardware abstraction, on top of ESP-IDF's register macros and nothing else.
//!
//! The register *numbers* come from `@import("regs")`, which is `zig translate-c` over ESP-IDF's
//! own `*_reg.h` headers, so no address, shift or mask in this file is a re-derivation of IDF's -
//! they are IDF's, as evaluated by clang. What this file adds is the part macros cannot express:
//! the sequences. Clock-gate before reset, reset before configure, configure before enable; divider
//! arithmetic; which bits must move together in one store.
//!
//! Scope is low-level hardware. Video encode, image signal processing, 2D blitting and the display
//! and camera serial interfaces are deliberately absent; so is anything needing an OS.
//!
//! Every peripheral here is checked against ESP-IDF's own `*_ll.h` implementation of the same
//! operation, in one image, on the die - see `examples/differ.zig` and `tools/differ.zig`.

const std = @import("std");
const regs = @import("regs");
const mmio = @import("mmio");

pub const Reg = mmio.Reg;
pub const Field = mmio.Field;

comptime {
    // The register set is per-silicon-revision, and the two sets share macro *names* while
    // disagreeing on 61 values: AHB_DMA_INFIFO_CNT_CH0 is bits [7:2] under hw_ver1 and [14:8] under
    // hw_ver3. A module built from the wrong set is therefore silently wrong rather than absent, so
    // the build stamps which one it used and this refuses to compile against anything else. This
    // board is a rev v1.3 die, which is what hw_ver1 describes.
    if (regs.ZIG_P4_HW_VER != 1) @compileError(
        "this HAL targets the pre-v3 ESP32-P4 register set (hw_ver1); rebuild with -Didf-hw-ver=1",
    );
}

pub const gpio = @import("hal/gpio.zig");
pub const rwdt = @import("hal/rwdt.zig");
pub const clkrst = @import("hal/clkrst.zig");
pub const intr = @import("hal/intr.zig");
pub const systimer = @import("hal/systimer.zig");
pub const timg = @import("hal/timg.zig");
pub const ledc = @import("hal/ledc.zig");
pub const uart = @import("hal/uart.zig");
pub const i2c = @import("hal/i2c.zig");
pub const sdmmc = @import("hal/sdmmc.zig");

// Force semantic analysis of every peripheral's decls, not just the ones a test happens to call:
// a wrong `Field.of` pair is a compile error, and an unanalysed function never raises it.
//
// `std.testing.refAllDeclsRecursive` was what this said, and Zig 0.16 does not have it - only
// `refAllDecls` survives (`/usr/lib/zig/std/testing.zig:1213`). Nothing noticed, because no test
// step in build.zig uses this file as a root: `zig build test` roots are tools/image_test.zig,
// src/mmio.zig and the five src/net + src/io files, and `hal` reaches them only as an imported
// *module*, whose tests a test binary does not run. So every `test` in src/hal/*.zig is currently
// compiled by nothing. One line in build.zig's root list fixes that; see this slice's report.
test {
    std.testing.refAllDecls(@This());
}