U-Boot dtoc: A Second Node Can Change the First Node’s Generated Platform Data

Adding a second device node can change the generated C representation
used by an existing node even when the first node’s source text is
untouched. In U-Boot v2025.01’s of-platdata generator, nodes sharing a
generated structure contribute to a common set of fields and property
widths.

That matters when a driver accesses generated members directly. A
property that previously appeared scalar can become an array, and
shorter values can acquire zero padding. Review the generated structure
across all its contributing nodes rather than treating one node as an
independent C interface.

Understand the compilation
boundary

The of-platdata
guide
describes converting devicetree data into C for constrained
SPL/TPL builds. The driver consumes members of a generated structure
instead of looking up arbitrary property names at runtime.

The guide also warns that property types are inferred heuristically.
A DT byte sequence does not carry a complete C type declaration, so the
generated representation is not a substitute for the device binding’s
meaning. Keep this mechanism separate from U-Boot proper’s ordinary
runtime devicetree access.

Follow structure-wide
widening

In the platform-data
generator
, scan_structs() collects fields under each
generated structure name. When another node uses that structure, its
fields are merged and existing properties are widened as necessary. A
later pass widens each node’s present properties to the shared
representation.

The property
implementation
shows the relevant array behavior. When the wider
property is a list, a scalar is promoted to a list. A shorter list is
extended with the type’s empty value; for integer cells, that value is
zero.

For a hypothetical integer property, node A containing one cell and
node B containing two cells can therefore share a two-element C member.
Node A’s value is represented with a padded second element. This example
assumes both nodes resolve to the same generated structure; compatible
strings, driver selection and aliases must be checked rather than
guessed.

Nodes contributing to one generated structure determine shared field widths; a longer list can promote and zero-pad a shorter node’s representation.

Padding does not
preserve the original count

A zero in the generated tail is not proof that the source node
explicitly supplied zero. It can be padding introduced to satisfy the
shared array width. A driver that needs the original logical count must
obtain that information through a deliberately supported contract, not
infer it by scanning for zero unless the binding makes that
interpretation valid.

This matters for arrays where zero is a legitimate entry. Treating
the first zero as a terminator can silently truncate an explicit value.
Treating every slot in the widest array as supplied can instead consume
padding as configuration. Choose the interpretation from the actual
binding and generator behavior together.

Field presence has a related limitation. The generator emits a static
structure initializer from the properties present on that node. A field
contributed by another node can be omitted from this initializer and
receive C’s zero initialization. Conversely, if no contributing node
supplies a property, there may be no generated member to access at all.
Neither case recreates a general runtime “property exists” query.

Review a multi-node
generated fixture

For a proposed build fixture, compare one node with a scalar value,
two nodes with different list lengths, and a node that omits a field
supplied by its peer. Preserve the generated header and each
platform-data initializer, then inspect the driver’s member accesses
against them.

Check the actual SPL/TPL input tree after filtering. A node absent
from that input cannot contribute to the structure, even if it exists in
another phase’s tree. Regeneration after a board-description change can
therefore alter the interface seen by the driver.

No dtoc generation or target build was executed here. The acceptance
artifact is a mapping from contributing source nodes to generated
fields, widths and values. It should explain both real values and
introduced padding before the driver interprets the resulting C
data.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *