Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
158 changes: 141 additions & 17 deletions docs/porting_guide.rst
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,145 @@
Porting GuideLine
=================

********
Hardware
********

The porting of OpenAMP to a new :doc:`multicore system <../openamp/overview>` requires
configuring the hardware on each core so it aligns with the OpenAMP architecture.

This setup typically includes defining a shared memory region for
:ref:`RPMsg<overview-rpmsg-work-label>` based
:ref:`Interprocessor Communications (IPC)<ipc-work-label>`, with or without interrupts for
asynchronous inter-core notification and defining the firmware execution flow either independently
or with :ref:`Remoteproc<overview-Remoteproc-work-label>` and associated
:ref:`Resource Table<resource-table>`.

Memory and interrupt assignments are critical design choices for any port. For a broader overview, refer to
:doc:`../protocol_details/system_considerations`.


Shared Memory
=============

Shared memory forms the :ref:`physical layer<rpmsg-layers-work-label>` for
:doc:`RPMsg <../docs/rpmsg_design>` protocol.
The specific memory type and layout are implementation dependent, but should be a dedicated
SRAM or DDR region accessible by both cores, with caching disabled.

Memory requirements are generally modest because RPMsg is a control‑oriented protocol
rather than a high‑bandwidth streaming channel. For example, using the Linux RPMsg packet
size of 512 bytes, a 64kB shared memory region can hold roughly 128 messages — sufficient
for most applications. Larger or smaller allocations can be chosen based on system needs.

If the resource table is not embedded in the remote firmware image, additional shared memory
may be required for a dynamic table.

Remoteproc can also use shared memory for optional trace buffers.


Memory Protection
-----------------

Because this is shared memory, appropriate hardware memory protection should be configured
on both processors.

Depending on the memory type, this may involve configuring the Memory Management Unit (MMU),
Memory Protection Unit (MPU), or Input-Output Memory Management Unit (IOMMU) to enforce
correct access permissions.

On systems running an advanced OS — such as Linux on the main
processor — these protections may be applied through OS mechanisms like the device tree or
via the Remoteproc resource table.


Notification
------------

RPMsg uses :ref:`ring buffers<rpmsg-protocol-mac>` in shared memory, so either processor can
poll for incoming messages. However, asynchronous notification via interrupts is recommended.

Most heterogeneous SoCs include a built‑in inter‑core interrupt mechanism, often called a
mailbox. These implementations typically combine shared memory with interrupt signaling and
may be managed through an Inter‑Processor Communication Controller (IPCC).

If no dedicated hardware is available — or it is reserved for other purposes —
software‑generated interrupts can be used instead.


***************
Porting Options
***************

OpenAMP consists of two major components: Remoteproc and RPMsg. These can be ported
independently or together, at either the driver level or the device level.

Driver level ports integrate with an operating system’s existing frameworks,
while device level ports implement the functionality directly on bare metal without
leveraging OS‑provided drivers.

libmetal provides the :ref:`hardware abstraction layer<hardware-abstraction>` for both.

The main porting approaches include:

- Remoteproc on the remote processor only, with the main processor using an existing
Remoteproc implementation (e.g., Linux Remoteproc) and no IPC.

- RPMsg on the remote processor only, with the main processor using an existing RPMsg
stack (e.g., Linux RPMsg) and no remote firmware management.

- Custom device‑level implementation of Remoteproc and/or RPMsg for both processors.


Driver Lifecycle Management via Remoteproc
==========================================

Some systems do not require IPC or use an alternative IPC mechanism. In these cases, only
Remoteproc may be ported (or reused, as on Linux) on both the main and remote processors.

The main processor uses driver level Remoteproc to load, start, stop, and manage remote
firmware.
This approach is useful when the remote firmware must be externally controlled or when
multiple firmware images may be deployed depending on runtime needs.
Thie configuration is common in custom or bare‑metal remote environments.

- Pros: Full remote firmware management
- Cons: No IPC. Larger software footprint

Driver to Remote IPC via RPMsg
==============================

If the remote firmware is static and starts at boot, or if another framework manages
firmware loading, only RPMsg needs to be ported.
In this model, the remote processor runs its firmware autonomously, and the main processor
interacts with it solely through the RPMsg communication channel, without any involvement
in firmware lifecycle control. This approach suits systems where the remote environment is
minimal or bare‑metal, and where the primary requirement is efficient message‑based
IPC rather than external management of the remote core.

- Pros: Lightweight. Provides IPC.
- Cons: No remote firmware management.

Device Level Custom Remoteproc and/or RPMsg
===========================================

In highly customized or bare‑metal only environments, a port of Remoteproc and/or RPMsg may be
required without any driver‑level abstraction.
In this case, one or all of the full Remoteproc and RPMsg mechanism must be implemented
directly on both the main and remote processors, ensuring that each core provides the necessary
firmware lifecycle management, messaging, shared‑memory handling, and notification logic without
relying on OS‑level drivers or frameworks.

- Pros: Lightweight.
- Cons: Highly custom and less portable.


.. _hardware-abstraction:

********************
Hardware Abstraction
********************

The `OpenAMP Framework <https://github.com/OpenAMP/open-amp>`_ uses
`libmetal <https://github.com/OpenAMP/libmetal>`_ to provide abstractions that allows for porting
of the OpenAMP Framework to various software environments (operating systems and bare metal
Expand Down Expand Up @@ -132,23 +271,8 @@ Platform Specific Porting to Use Remoteproc to Manage Remote Processor
**********************************************************************

With the platform specific :ref:`remoteproc driver functions<port-remoteproc-driver>`
implemented by the port, the user can use remoteproc APIs to run application on a remote processor.

.. doxygenfunction:: remoteproc_init
:project: openamp_doc_embed

.. doxygenfunction:: remoteproc_remove

.. doxygenfunction:: remoteproc_mmap

.. doxygenfunction:: remoteproc_config

.. doxygenfunction:: remoteproc_start

.. doxygenfunction:: remoteproc_stop

.. doxygenfunction:: remoteproc_shutdown

implemented by the port, the user can use remoteproc APIs to run application on a remote processor,
as detailed in the :ref:`Remote User APIs<remoteproc_config>` section of the Remote Proc Design.

The following code snippet is an example execution.

Expand Down
8 changes: 8 additions & 0 deletions openamp/glossary.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,20 @@ Glossary

AMP, `Asymmentric Multiprocessing <https://en.wikipedia.org/wiki/Asymmetric_multiprocessing>`_
API, Application Interface
DDR (RAM), Double Data Rate (Random Access Memory)
GPL, `GNU General Public License <https://en.wikipedia.org/wiki/GNU_General_Public_License>`_
HAL, Hardware Abstraction Layer
IOMMU, Input-Output Memory Management Unit
IPC, `Inter-Processor Communications <https://en.wikipedia.org/wiki/Inter-process_communication>`_
IPCC, Inter-Processor Communication Controller
LCM, Life-Cycle Management
MMU, Memory Management Unit
MPU, Memory Protection Unit
RAM, Random Access Memory
RPC, :ref:`Remote Procedure Calls (RPC)<overview-proxy-rpc-work-label>`
RTOS, Real Time Operating System
RPMsg, `Remote Processor Messaging <https://en.wikipedia.org/wiki/RPMsg>`_
SMP, `Symmetric Multiprocessing (SMP) <https://en.wikipedia.org/wiki/Symmetric_multiprocessing>`_
SoC, System on Chip
SRAM, Static RAM
Virtio, Virtual Input Output
2 changes: 1 addition & 1 deletion protocol_details/lifecyclemgmt_creation.rst
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ Resource Table Procedure

As an example, please refer to the resource table defined in the bare metal remote echo test
application at
`rsc_table.c <https://github.com/OpenAMP/openamp-system-reference/blob/main/examples/legacy_apps/machine/zynqmp_r5/rsc_table.c>`_.
`rsc_table.c <https://github.com/OpenAMP/openamp-system-reference/blob/main/examples/legacy_apps/machine/xlnx/zynqmp_r5/rsc_table.c>`_.
The resource table contains entries for memory carve-out and virtio device resources. The memory
carve-out entry contains info like firmware ELF image start address and size. The virtio device
resource contains virtio device features, vring addresses, size, and alignment information. The
Expand Down
58 changes: 54 additions & 4 deletions protocol_details/resource_tbl.rst
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ at the offset location of each entry. Directly following the header are the reso
themselves, each of which has a 32 bit type. These in remote context will likely be memory carveouts
for locations of parts of the remote system and virtio device definitions.


+--------------+--------------------------------------------------------------------------------+
| Item | Description |
+==============+================================================================================+
Expand All @@ -30,18 +31,67 @@ for locations of parts of the remote system and virtio device definitions.
| | can correctly extract the information. |
+--------------+--------------------------------------------------------------------------------+

The fw_resource_type's are listed in the
`remoteproc header <https://github.com/OpenAMP/open-amp/blob/main/lib/include/openamp/remoteproc.h>`_.
The resource table is essentially a list of resource definitions, with each entry describing
a specific :ref:`resource structure<resource-structure>`. The Remoteproc framework is
responsible for configuring the appropriate drivers and/or bare‑metal hardware based on
these entries.

The available resource types are defined in the
`Remoteproc Header <https://github.com/OpenAMP/open-amp/blob/main/lib/include/openamp/remoteproc.h>`_
and are described in more detail in the :ref:`resource-types` section below.



Compatibility with Linux kernel
-------------------------------

The resource table should maintain compatibility with that of
`remoteproc <https://www.kernel.org/doc/html/latest/staging/remoteproc.html>`_.
Since Linux is a major full‑stack operating system in the embedded device space,
the resource table should remain compatible with the
`Linux Remoteproc <https://www.kernel.org/doc/html/latest/staging/remoteproc.html>`_
format.

::

Evolution should be done in cooperation with Linux remoteproc community.

Related documentation can be found under the Linux kernel's remoteproc documentation:
`Binary Firmware Structure <https://www.kernel.org/doc/html/latest/staging/remoteproc.html#binary-firmware-structure>`_.


.. _resource-types:

Resource Types
**************

Each of the resources in the :ref:`resource-table` is defined by a type (fw_resource_type) and
its corresponding :ref:`structure<resource-structures>`.

.. doxygenenum:: fw_resource_type
:project: openamp_doc_embed


.. _resource-structures:

Resource Structure Definitions
------------------------------

The following structures correspond to each of the :ref:`resource-types` (fw_resource_type).

.. doxygenstruct:: fw_rsc_carveout
:project: openamp_doc_embed

.. doxygenstruct:: fw_rsc_devmem
:project: openamp_doc_embed

.. doxygenstruct:: fw_rsc_trace
:project: openamp_doc_embed

.. doxygenstruct:: fw_rsc_vdev
:project: openamp_doc_embed


In addition to the predefined :ref:`resource-types` vendors can define their
own with types between RSC_VENDOR_START and RSC_VENDOR_END.

.. doxygenstruct:: fw_rsc_vendor
:project: openamp_doc_embed