doc: guides: dts improvements
People seem to miss the troubleshooting page a lot, since nobody ever mentions that they tried its steps and they didn't work. Promote it to a top level page to make it easier to see. Add cross-references between the two to keep them well linked together. Add a couple of extra links to the bindings related HOWTO while we are here, now that the bindings docs are a bit better off than they were when this content was originally written. Signed-off-by: Martí Bolívar <marti.bolivar@nordicsemi.no>
This commit is contained in:
parent
574746e7dc
commit
7e7f4201df
|
@ -5,6 +5,8 @@ Devicetree HOWTOs
|
|||
|
||||
This page has step-by-step advice for getting things done with devicetree.
|
||||
|
||||
.. tip:: See :ref:`dt-trouble` for troubleshooting advice.
|
||||
|
||||
.. _get-devicetree-outputs:
|
||||
|
||||
Get your devicetree and generated header
|
||||
|
@ -153,8 +155,9 @@ creating the device, or the device's initialization function failed.
|
|||
Find a devicetree binding
|
||||
*************************
|
||||
|
||||
Devicetree binding YAML files document what you can do with the nodes they
|
||||
describe, so it's critical to be able to find them for the nodes you are using.
|
||||
:ref:`dt-bindings` are YAML files which declare what you can do with the nodes
|
||||
they describe, so it's critical to be able to find them for the nodes you are
|
||||
using.
|
||||
|
||||
If you don't have them already, :ref:`get-devicetree-outputs`. To find a node's
|
||||
binding, open the generated header file, which starts with a list of nodes in a
|
||||
|
@ -597,130 +600,3 @@ supporting a devicetree alias to specify the hardware specific portions, as is
|
|||
done in the :ref:`blinky-sample`. The application can then be configured in
|
||||
:ref:`BOARD.dts <devicetree-in-out-files>` files or via :ref:`devicetree
|
||||
overlays <use-dt-overlays>`.
|
||||
|
||||
.. _dt-trouble:
|
||||
|
||||
Troubleshoot devicetree issues
|
||||
******************************
|
||||
|
||||
Here are some tips for fixing misbehaving devicetree code.
|
||||
|
||||
Try again with a pristine build directory
|
||||
=========================================
|
||||
|
||||
See :ref:`west-building-pristine` for examples, or just delete the build
|
||||
directory completely and retry.
|
||||
|
||||
This is general advice which is especially applicable to debugging devicetree
|
||||
issues, because the outputs are created at CMake configuration time, and are
|
||||
not always regenerated when one of their inputs changes.
|
||||
|
||||
Make sure <devicetree.h> is included
|
||||
====================================
|
||||
|
||||
Unlike Kconfig symbols, the :file:`devicetree.h` header must be included
|
||||
explicitly.
|
||||
|
||||
Many Zephyr header files rely on information from devicetree, so including some
|
||||
other API may transitively include :file:`devicetree.h`, but that's not
|
||||
guaranteed.
|
||||
|
||||
.. _dt-use-the-right-names:
|
||||
|
||||
Make sure you're using the right names
|
||||
======================================
|
||||
|
||||
Remember that:
|
||||
|
||||
- In C/C++, devicetree names must be lowercased and special characters must be
|
||||
converted to underscores. Zephyr's generated devicetree header has DTS names
|
||||
converted in this way into the C tokens used by the preprocessor-based
|
||||
``<devicetree.h>`` API.
|
||||
- In overlays, use devicetree node and property names the same way they
|
||||
would appear in any DTS file. Zephyr overlays are just DTS fragments.
|
||||
|
||||
For example, if you're trying to **get** the ``clock-frequency`` property of a
|
||||
node with path ``/soc/i2c@12340000`` in a C/C++ file:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
/*
|
||||
* foo.c: lowercase-and-underscores names
|
||||
*/
|
||||
|
||||
/* Don't do this: */
|
||||
#define MY_CLOCK_FREQ DT_PROP(DT_PATH(soc, i2c@1234000), clock-frequency)
|
||||
/* ^ ^
|
||||
* @ should be _ - should be _ */
|
||||
|
||||
/* Do this instead: */
|
||||
#define MY_CLOCK_FREQ DT_PROP(DT_PATH(soc, i2c_1234000), clock_frequency)
|
||||
/* ^ ^ */
|
||||
|
||||
And if you're trying to **set** that property in a devicetree overlay:
|
||||
|
||||
.. code-block:: none
|
||||
|
||||
/*
|
||||
* foo.overlay: DTS names with special characters, etc.
|
||||
*/
|
||||
|
||||
/* Don't do this; you'll get devicetree errors. */
|
||||
&{/soc/i2c_12340000/} {
|
||||
clock_frequency = <115200>;
|
||||
};
|
||||
|
||||
/* Do this instead. Overlays are just DTS fragments. */
|
||||
&{/soc/i2c@12340000/} {
|
||||
clock-frequency = <115200>;
|
||||
};
|
||||
|
||||
Validate properties
|
||||
===================
|
||||
|
||||
If you're getting a compile error reading a node property, check your node
|
||||
identifier and property. For example, if you get a build error on a line that
|
||||
looks like this:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
int baud_rate = DT_PROP(DT_NODELABEL(my_serial), current_speed);
|
||||
|
||||
Try checking the node by adding this to the file and recompiling:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
#if !DT_NODE_EXISTS(DT_NODELABEL(my_serial))
|
||||
#error "whoops"
|
||||
#endif
|
||||
|
||||
If you see the "whoops" error message when you rebuild, the node identifier
|
||||
isn't referring to a valid node. :ref:`get-devicetree-outputs` and debug from
|
||||
there.
|
||||
|
||||
Some hints for what to check next if you don't see the "whoops" error message:
|
||||
|
||||
- did you :ref:`dt-use-the-right-names`?
|
||||
- does the :ref:`property exist <dt-checking-property-exists>`?
|
||||
- does the node have a :ref:`matching binding <dt-bindings>`?
|
||||
|
||||
.. _missing-dt-binding:
|
||||
|
||||
Check for missing bindings
|
||||
==========================
|
||||
|
||||
If the build fails to :ref:`dts-find-binding` for a node, then either the
|
||||
node's ``compatible`` property is not defined, or its value has no matching
|
||||
binding. If the property is set, check for typos in its name. In a devicetree
|
||||
source file, ``compatible`` should look like ``"vnd,some-device"`` --
|
||||
:ref:`dt-use-the-right-names`.
|
||||
|
||||
If your binding file is not under :file:`zephyr/dts`, you may need to set
|
||||
:ref:`DTS_ROOT <dts_root>`.
|
||||
|
||||
Errors with DT_INST_() APIs
|
||||
===========================
|
||||
|
||||
If you're using an API like :c:func:`DT_INST_PROP`, you must define
|
||||
``DT_DRV_COMPAT`` to the lowercase-and-underscores version of the compatible
|
||||
you are interested in. See :ref:`dt-create-devices-inst`.
|
||||
|
|
|
@ -14,4 +14,5 @@ See :ref:`devicetree` for reference material.
|
|||
bindings.rst
|
||||
api-usage.rst
|
||||
howtos.rst
|
||||
troubleshooting.rst
|
||||
dt-vs-kconfig.rst
|
||||
|
|
134
doc/guides/dts/troubleshooting.rst
Normal file
134
doc/guides/dts/troubleshooting.rst
Normal file
|
@ -0,0 +1,134 @@
|
|||
.. _dt-trouble:
|
||||
|
||||
Troubleshooting devicetree
|
||||
##########################
|
||||
|
||||
Here are some tips for fixing misbehaving devicetree related code.
|
||||
|
||||
See :ref:`dt-howtos` for other "HOWTO" style information.
|
||||
|
||||
Try again with a pristine build directory
|
||||
*****************************************
|
||||
|
||||
.. important:: Try this first, before doing anything else.
|
||||
|
||||
See :ref:`west-building-pristine` for examples, or just delete the build
|
||||
directory completely and retry.
|
||||
|
||||
This is general advice which is especially applicable to debugging devicetree
|
||||
issues, because the outputs are created during the CMake configuration phase,
|
||||
and are not always regenerated when one of their inputs changes.
|
||||
|
||||
Make sure <devicetree.h> is included
|
||||
************************************
|
||||
|
||||
Unlike Kconfig symbols, the :file:`devicetree.h` header must be included
|
||||
explicitly.
|
||||
|
||||
Many Zephyr header files rely on information from devicetree, so including some
|
||||
other API may transitively include :file:`devicetree.h`, but that's not
|
||||
guaranteed.
|
||||
|
||||
.. _dt-use-the-right-names:
|
||||
|
||||
Make sure you're using the right names
|
||||
**************************************
|
||||
|
||||
Remember that:
|
||||
|
||||
- In C/C++, devicetree names must be lowercased and special characters must be
|
||||
converted to underscores. Zephyr's generated devicetree header has DTS names
|
||||
converted in this way into the C tokens used by the preprocessor-based
|
||||
``<devicetree.h>`` API.
|
||||
- In overlays, use devicetree node and property names the same way they
|
||||
would appear in any DTS file. Zephyr overlays are just DTS fragments.
|
||||
|
||||
For example, if you're trying to **get** the ``clock-frequency`` property of a
|
||||
node with path ``/soc/i2c@12340000`` in a C/C++ file:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
/*
|
||||
* foo.c: lowercase-and-underscores names
|
||||
*/
|
||||
|
||||
/* Don't do this: */
|
||||
#define MY_CLOCK_FREQ DT_PROP(DT_PATH(soc, i2c@1234000), clock-frequency)
|
||||
/* ^ ^
|
||||
* @ should be _ - should be _ */
|
||||
|
||||
/* Do this instead: */
|
||||
#define MY_CLOCK_FREQ DT_PROP(DT_PATH(soc, i2c_1234000), clock_frequency)
|
||||
/* ^ ^ */
|
||||
|
||||
And if you're trying to **set** that property in a devicetree overlay:
|
||||
|
||||
.. code-block:: none
|
||||
|
||||
/*
|
||||
* foo.overlay: DTS names with special characters, etc.
|
||||
*/
|
||||
|
||||
/* Don't do this; you'll get devicetree errors. */
|
||||
&{/soc/i2c_12340000/} {
|
||||
clock_frequency = <115200>;
|
||||
};
|
||||
|
||||
/* Do this instead. Overlays are just DTS fragments. */
|
||||
&{/soc/i2c@12340000/} {
|
||||
clock-frequency = <115200>;
|
||||
};
|
||||
|
||||
Validate properties
|
||||
*******************
|
||||
|
||||
If you're getting a compile error reading a node property, check your node
|
||||
identifier and property. For example, if you get a build error on a line that
|
||||
looks like this:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
int baud_rate = DT_PROP(DT_NODELABEL(my_serial), current_speed);
|
||||
|
||||
Try checking the node by adding this to the file and recompiling:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
#if !DT_NODE_EXISTS(DT_NODELABEL(my_serial))
|
||||
#error "whoops"
|
||||
#endif
|
||||
|
||||
If you see the "whoops" error message when you rebuild, the node identifier
|
||||
isn't referring to a valid node. :ref:`get-devicetree-outputs` and debug from
|
||||
there.
|
||||
|
||||
Some hints for what to check next if you don't see the "whoops" error message:
|
||||
|
||||
- did you :ref:`dt-use-the-right-names`?
|
||||
- does the :ref:`property exist <dt-checking-property-exists>`?
|
||||
- does the node have a :ref:`matching binding <dt-bindings>`?
|
||||
- does the binding define the property?
|
||||
|
||||
.. _missing-dt-binding:
|
||||
|
||||
Check for missing bindings
|
||||
**************************
|
||||
|
||||
See :ref:`dt-bindings` for information about bindings, and
|
||||
:ref:`devicetree_binding_index` for information on bindings built into Zephyr.
|
||||
|
||||
If the build fails to :ref:`dts-find-binding` for a node, then either the
|
||||
node's ``compatible`` property is not defined, or its value has no matching
|
||||
binding. If the property is set, check for typos in its name. In a devicetree
|
||||
source file, ``compatible`` should look like ``"vnd,some-device"`` --
|
||||
:ref:`dt-use-the-right-names`.
|
||||
|
||||
If your binding file is not under :file:`zephyr/dts`, you may need to set
|
||||
:ref:`DTS_ROOT <dts_root>`; see :ref:`dt-where-bindings-are-located`.
|
||||
|
||||
Errors with DT_INST_() APIs
|
||||
***************************
|
||||
|
||||
If you're using an API like :c:func:`DT_INST_PROP`, you must define
|
||||
``DT_DRV_COMPAT`` to the lowercase-and-underscores version of the compatible
|
||||
you are interested in. See :ref:`dt-create-devices-inst`.
|
Loading…
Reference in a new issue