Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Project Manifest

Consortium.toml is the source of truth for the complete system. Paths are resolved relative to the manifest, while hardware names and address ranges are checked against the selected chip database.

A minimal shared-memory system

This i.MX95 fragment follows the current melt-pot reference layout:

[profile]
chip        = "mimx9596xvt"
devkit      = "imx95-19x19-evk"
shared      = "../shared"
deploy_root = "/opt/consortium"

[endpoints]
linux = "./app"
cm7   = "./mcu"

[[ipc.channel]]
name          = "sensor"
doorbell      = "mu7"
pattern       = "memory"
primary       = "linux"
secondary     = "cm7"
party.linux   = { chan = 6, type = "Command" }
party.cm7     = { chan = 7, type = "SensorReading" }
config.memory = { base = 0x00480000, length = 0x4000 }
mtu           = 128

The type under each party is the message sent by that party. Generated Linux code therefore exposes sensor as a transceiver that sends Command and receives SensorReading; the CM7 sees the inverse. Its chan is the doorbell line used for that party’s outgoing direction.

primary and secondary select the shared-memory protocol roles. Current systems use the Linux/A-core as primary and the firmware core as secondary.

Sections

[profile]

FieldRequiredMeaning
chipyesFull part number resolved through the chip database
sharedyesCrate containing IPC and other cross-boundary types
deploy_rootyesOn-target installation prefix used when generating paths; the builder does not write there
devkitnoFull board DTS file stem; falls back to the generic SoC tree
sysrootnoLinux target sysroot; overrides SDK environment variables
kernel_recipenoYocto kernel recipe name used to generate a .bbappend
time_drivernoGenerate the firmware Embassy time driver; defaults to true

The generated time driver uses the reference timer for the family: TIM2 on STM32MP2 or LPIT1 on i.MX9. Set time_driver = false when firmware owns another time base.

[endpoints]

This table maps runtime endpoint names to crate roots. Names must be visible on the selected chip, and every party used by an IPC channel must have a matching endpoint. The conventional application name is linux; controller names include cm33 and cm7 according to the chip.

[[ipc.channel]]

Each entry describes one bidirectional typed channel. The current manifest pattern is memory; the UART transport is available as a crate API but is not lowered from this table yet.

FieldMeaning
nameRust field name under context.ipc_shm
doorbellChip database doorbell, such as ipcc1 or mu7
primary, secondaryEndpoints participating in the descriptor handshake
party.<name>This party’s outgoing doorbell channel and Rust message type
config.memoryPhysical shared region containing the descriptor and slots
mtuMaximum encoded payload size in bytes
codecpostcard by default; prost and rkyv are also supported

Message types must exist in the [profile].shared crate and satisfy the selected codec. The region must be large enough for the descriptor and both directional slots.

[dbg] and [dbg.<core>]

The application processor always hosts debug decoding, so only coprocessor rings are declared:

[dbg]
mode = "auto"

[dbg.cm7]
memory = { base = 0x00484000, length = 0x2000 }
mtu    = 64

auto generates background readers that forward decoded defmt frames to tracing. interface exposes the readers for application-managed polling and decoding.

[dts]

[dts]
mode      = "merge"
linux     = "/path/to/linux"
configfs  = false

merge is the default and emits a full device tree with reserved memory, UIO nodes, and remoteproc fixups. overlay emits a .dtso; it cannot remove existing remoteproc mailbox properties, so use merge mode for those fixups. linux points to a kernel tree whose dt-bindings headers are needed to compile the generated source.

[peripheral.<name>]

[peripheral.lpi2c1]
owner     = "cm7"
secure    = false
clock     = 24000000
frequency = 100000
pin.sda   = "PB0"
pin.scl   = "PB1"

Controller-owned peripherals become typed fields under context.peripherals. The current generated singleton path supports non-secure peripherals; secure = true is rejected. Required clocks, frequencies, pins, and interrupt metadata depend on the driver and chip database.

Optional [tee] and [hmi]

[tee] contains the OP-TEE trusted application’s UUID. [hmi] selects cog or pocket, its display backend, source directory, and build output. Pocket additionally requires an app entry name; it supports wayland and headless today, not drm. The logical viewport defaults to 480 × 272 and can be set under [hmi.logical].

Validation

Manifest parsing does more than syntax checking. A session validates, among other constraints:

  • chip-visible processors, peripherals, and doorbells;
  • doorbell channel bounds and duplicate use;
  • shared and debug region bounds, overlap, and MPU alignment;
  • endpoint presence and peripheral ownership; and
  • HMI engine/backend combinations.

Treat validation failures as contract errors. Fix the manifest or chip data instead of bypassing the generated types with raw addresses.