mirror of
https://github.com/zephyrproject-rtos/zephyr
synced 2025-08-27 07:05:21 +00:00
Remove thread from memory domain API (k_mem_domain_remove_thread())has only one argument which is thread ID as per the implementation whereas documentation says there has to be two arguments, memory domain and thread ID.Memory domain argument is not required as a thread belongs to single memory domain at any point in time. Also memory domain initialisation function (k_mem_domain_init()) should accept only 3 arguments i.e, memory domain name, number of parts and array of pointers to the memory domain, instead of 4. Signed-off-by: Spoorthi K <spoorthi.k@intel.com>
191 lines
6.0 KiB
ReStructuredText
191 lines
6.0 KiB
ReStructuredText
.. _memory_domain:
|
|
|
|
Memory Domain
|
|
#############
|
|
|
|
The memory domain APIs are used by unprivileged threads to share data to
|
|
the threads in the same memory domain and protect sensitive data from threads
|
|
outside their domain. Memory domains are not only used for improving security,
|
|
but are also useful for debugging (unexpected access would cause an exception).
|
|
|
|
An alternative to using memory domains is the
|
|
:option:`CONFIG_APPLICATION_MEMORY` option, which will grant access to user
|
|
threads at boot to all global memory defined in object files that are not
|
|
part of the core kernel. This is useful for very simple applications which
|
|
will allow all threads to use global data defined within the application, but
|
|
each thread's stack is still protected from other user threads and there is
|
|
no access to private kernel data structures.
|
|
|
|
Since architectures generally have constraints on how many partitions can be
|
|
defined, and the size/alignment of each partition, users may need to group
|
|
related data together using linker sections.
|
|
|
|
.. contents::
|
|
:local:
|
|
:depth: 2
|
|
|
|
Concepts
|
|
********
|
|
|
|
A memory domain contains some number of memory partitions.
|
|
A memory partition is a memory region (might be RAM, peripheral registers,
|
|
or flash, for example) with specific attributes (access permission, e.g.
|
|
privileged read/write, unprivileged read-only, or execute never).
|
|
Memory partitions are defined by a set of underlying MPU regions
|
|
or MMU tables. A thread belongs to a single memory domain at
|
|
any point in time but a memory domain may contain multiple threads.
|
|
Threads in the same memory domain have the same access permissions
|
|
to the memory partitions belonging to the memory domain. New threads
|
|
will inherit any memory domain configuration from the parent thread.
|
|
|
|
Implementation
|
|
**************
|
|
|
|
Create a Memory Domain
|
|
======================
|
|
|
|
A memory domain is defined using a variable of type
|
|
:c:type:`struct k_mem_domain`. It must then be initialized by calling
|
|
:cpp:func:`k_mem_domain_init()`.
|
|
|
|
The following code defines and initializes an empty memory domain.
|
|
|
|
.. code-block:: c
|
|
|
|
struct k_mem_domain app0_domain;
|
|
|
|
k_mem_domain_init(&app0_domain, 0, NULL);
|
|
|
|
Add Memory Partitions into a Memory Domain
|
|
==========================================
|
|
|
|
There are two ways to add memory partitions into a memory domain.
|
|
|
|
This first code sample shows how to add memory partitions while creating
|
|
a memory domain.
|
|
|
|
.. code-block:: c
|
|
|
|
/* the start address of the MPU region needs to align with its size */
|
|
u8_t __aligned(32) app0_buf[32];
|
|
u8_t __aligned(32) app1_buf[32];
|
|
|
|
K_MEM_PARTITION_DEFINE(app0_part0, app0_buf, sizeof(app0_buf),
|
|
K_MEM_PARTITION_P_RW_U_RW);
|
|
|
|
K_MEM_PARTITION_DEFINE(app0_part1, app1_buf, sizeof(app1_buf),
|
|
K_MEM_PARTITION_P_RW_U_RO);
|
|
|
|
struct k_mem_partition *app0_parts[] = {
|
|
app0_part0,
|
|
app0_part1
|
|
};
|
|
|
|
k_mem_domain_init(&app0_domain, ARRAY_SIZE(app0_parts), app0_parts);
|
|
|
|
This second code sample shows how to add memory partitions into an initialized
|
|
memory domain one by one.
|
|
|
|
.. code-block:: c
|
|
|
|
/* the start address of the MPU region needs to align with its size */
|
|
u8_t __aligned(32) app0_buf[32];
|
|
u8_t __aligned(32) app1_buf[32];
|
|
|
|
K_MEM_PARTITION_DEFINE(app0_part0, app0_buf, sizeof(app0_buf),
|
|
K_MEM_PARTITION_P_RW_U_RW);
|
|
|
|
K_MEM_PARTITION_DEFINE(app0_part1, app1_buf, sizeof(app1_buf),
|
|
K_MEM_PARTITION_P_RW_U_RO);
|
|
|
|
k_mem_domain_add_partition(&app0_domain, &app0_part0);
|
|
k_mem_domain_add_partition(&app0_domain, &app0_part1);
|
|
|
|
.. note::
|
|
The maximum number of memory partitions is limited by the maximum
|
|
number of MPU regions or the maximum number of MMU tables.
|
|
|
|
Add Threads into a Memory Domain
|
|
================================
|
|
|
|
Adding threads into a memory domain grants threads permission to access
|
|
the memory partitions in the memory domain.
|
|
|
|
The following code shows how to add threads into a memory domain.
|
|
|
|
.. code-block:: c
|
|
|
|
k_mem_domain_add_thread(&app0_domain, app_thread_id);
|
|
|
|
Remove a Memory Partition from a Memory Domain
|
|
==============================================
|
|
|
|
The following code shows how to remove a memory partition from a memory
|
|
domain.
|
|
|
|
.. code-block:: c
|
|
|
|
k_mem_domain_remove_partition(&app0_domain, &app0_part1);
|
|
|
|
The k_mem_domain_remove_partition() API finds the memory partition
|
|
that matches the given parameter and removes that partition from the
|
|
memory domain.
|
|
|
|
Remove a Thread from the Memory Domain
|
|
======================================
|
|
|
|
The following code shows how to remove a thread from the memory domain.
|
|
|
|
.. code-block:: c
|
|
|
|
k_mem_domain_remove_thread(app_thread_id);
|
|
|
|
Destroy a Memory Domain
|
|
=======================
|
|
|
|
The following code shows how to destroy a memory domain.
|
|
|
|
.. code-block:: c
|
|
|
|
k_mem_domain_destroy(&app0_domain);
|
|
|
|
Available Partition Attributes
|
|
==============================
|
|
|
|
When defining a partition, we need to set access permission attributes
|
|
to the partition. Since the access control of memory partitions relies on
|
|
either an MPU or MMU, the available partition attributes would be architecture
|
|
dependent.
|
|
|
|
The complete list of available partition attributes for a specific architecture
|
|
is found in the architecture-specific include file
|
|
``include/arch/<arch name>/arch.h``, (for example, ``include/arch/arm/arch.h``.)
|
|
Some examples of partition attributes are:
|
|
|
|
.. code-block:: c
|
|
|
|
/* Denote partition is privileged read/write, unprivileged read/write */
|
|
K_MEM_PARTITION_P_RW_U_RW
|
|
/* Denote partition is privileged read/write, unprivileged read-only */
|
|
K_MEM_PARTITION_P_RW_U_RO
|
|
|
|
Configuration Options
|
|
*********************
|
|
|
|
Related configuration options:
|
|
|
|
* :option:`CONFIG_MAX_DOMAIN_PARTITIONS`
|
|
|
|
APIs
|
|
****
|
|
|
|
The following memory domain APIs are provided by :file:`kernel.h`:
|
|
|
|
* :c:macro:`K_MEM_PARTITION_DEFINE`
|
|
* :cpp:func:`k_mem_domain_init()`
|
|
* :cpp:func:`k_mem_domain_destroy()`
|
|
* :cpp:func:`k_mem_domain_add_partition()`
|
|
* :cpp:func:`k_mem_domain_remove_partition()`
|
|
* :cpp:func:`k_mem_domain_add_thread()`
|
|
* :cpp:func:`k_mem_domain_remove_thread()`
|