Skip to content
Closed
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
2 changes: 1 addition & 1 deletion CODEOWNERS
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@
/doc/scripts/ @carlescufi
/doc/guides/bluetooth/ @joerchan @jhedberg @Vudentz
/doc/reference/bluetooth/ @joerchan @jhedberg @Vudentz
/doc/reference/kernel/other/resource_mgmt.rst @pabigot
/doc/reference/resource_management/ @pabigot
/doc/reference/networking/can* @alexanderwachter
/drivers/debug/ @nashif
/drivers/*/*cc13xx_cc26xx* @bwitherspoon
Expand Down
2 changes: 2 additions & 0 deletions doc/reference/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ API Reference
stability.rst
terminology.rst
audio/index.rst
misc/notify.rst
bluetooth/index.rst
kconfig/index.rst
crypto/index.rst
Expand All @@ -22,6 +23,7 @@ API Reference
peripherals/index.rst
power_management/index.rst
random/index.rst
resource_management/index.rst
shell/index.rst
storage/index.rst
usb/index.rst
Expand Down
1 change: 0 additions & 1 deletion doc/reference/kernel/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,6 @@ These pages cover other kernel services.
other/atomic.rst
other/float.rst
other/ring_buffers.rst
other/resource_mgmt.rst
other/cxx_support.rst
other/version.rst
other/fatal.rst
83 changes: 0 additions & 83 deletions doc/reference/kernel/other/resource_mgmt.rst

This file was deleted.

25 changes: 25 additions & 0 deletions doc/reference/misc/notify.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
.. _async_notification:

Asynchronous Notification APIs
##############################

Zephyr APIs often include :ref:`api_term_async` functions where an
operation is initiated and the application needs to be informed when it
completes, and whether it succeeded. Using :cpp:func:`k_poll()` is
often a good method, but some application architectures may be more
suited to a callback notification, and operations like enabling clocks
and power rails may need to be invoked before kernel functions are
available so a busy-wait for completion may be needed.

This API is intended to be embedded within specific subsystems such as
:ref:`resource_mgmt_onoff` and other APIs that support async
transactions. The subsystem wrappers are responsible for extracting
operation-specific data from requests that include a notification
element, and for invoking callbacks with the parameters required by the
API.

API Reference
*************

.. doxygengroup:: sys_notify_apis
:project: Zephyr
204 changes: 204 additions & 0 deletions doc/reference/resource_management/index.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,204 @@
.. _resource_mgmt:

Resource Management
###################

There are various situations where it's necessary to coordinate resource
use at runtime among multiple clients. These include power rails,
clocks, other peripherals, and binary device power management. The
complexity of properly managing multiple consumers of a device in a
multithreaded system, especially when transitions may be asynchronous,
suggests that a shared implementation is desirable.

Zephyr provides managers for several coordination policies. These
managers are embedded into services that use them for specific
functions.

.. contents::
:local:
:depth: 2

.. _resource_mgmt_onoff:

On-Off Manager
**************

An on-off manager supports an arbitrary number of clients of a service
which has a binary state. Example applications are power rails, clocks,
and binary device power management.

The manager has the following properties:

* The stable states are off, on, and error. The service always begins
in the off state. The service may also be in a transition to a given
state.
* The core operations are request (add a dependency) and release (remove
a dependency). The service manages the state based on calls to
functions that initiate these operations.
* The service transitions from off to on when first client request is
received.
* The service transitions from on to off when last client release is
received.
* Each service configuration provides functions that implement the
transition from off to on, from on to off, and optionally from an
error state to off. Transitions that may put a calling thread to
sleep must be flagged in the configuration to support detecting unsafe
invocation from non-thread context.
* All operations are asynchronous, and are initiated by a function call
that references a specific service and is given client notification
data. The function call will succeed or fail. On success, the
operation is guaranteed to be initiated, but whether the operation
itself succeeds or fails is indicated through client notification.
The initiation functions can be invoked from pre-kernel, thread, or
ISR context. In contexts and states where the operation cannot
be started the function will result in an error.
* Requests to turn on may be queued while a transition to off is in
progress: when the service has turned off successfully it will be
immediately turned on again (where context allows) and waiting clients
notified when the start completes.

Requests are reference counted, but not tracked. That means clients are
responsible for recording whether their requests were accepted, and for
initiating a release only if they have previously successfully completed
a request. Improper use of the API can cause an active client to be
shut out, and the manager does not maintain a record of specific clients
that have been granted a request.

Failures in executing a transition are recorded and inhibit further
requests or releases until the manager is reset. Pending requests are
notified (and cancelled) when errors are discovered.

Transition operation completion notifications are provided through the
standard :ref:`async_notification`, supporting these methods:

* Signal: A pointer to a :c:type:`struct k_poll_signal` is provided, and
the signal is raised when the transition completes. The operation
completion code is stored as the signal value.
* Callback: a function pointer is provided by the client along with an
opaque pointer, and on completion of the operation the function is
invoked with the manager, the client data, the manager state, the
operation completion code, and the user-provided pointer.
* Spin-wait: the client is required to check for operation completion
using the :cpp:func:`onoff_client_fetch_result()` function.

Synchronous transition may be implemented by a caller based on its
context, for example by using :cpp:func:`k_poll()` to wait until the
completion is signalled.

.. _resource_mgmt_onoff_monitor:

On-Off Monitor
==============

In the simplest use cases a client of an on-off service will issue
:cpp:func:`onoff_request()` and :cpp:func:`onoff_release()` commands and
rely on the notifications to detect completion of these operations. In
cases where client needs may change, it may be necessary to cancel a
request or release and return to the previous state after a transition
has started. This can be done using :cpp:func:`onoff_cancel()`, which
can be simpler than designing the client to wait until the transition
completes so it can issue a new release or request.

However the asynchronous nature of on-off service transitions makes
reliable use onoff_cancel() difficult. It will return an error
identifying when a transition has already completed, and will
synchronously disable a request that has not been satisfied, but when
cancelling a release it must convert the release operation into a
request operation. The release may complete before the caller has been
informed of the conversion. Similarly it is possible that, due to
cancellation of a request, a service error that occurs during transition
will not be reported.

Clients and other components interested in tracking service state can be
informed of state transitions by registering for state changes using
onoff_monitor_request(). These changes are provided before issuing
completion notifications associated with the new state.

.. _resource_mgmt_onoff_notification:

On-Off Notification
===================

The standard client model for an on-off service is to issue a request
and hold it while the service is in use, then release it on completion.
Service transitions are asynchronous, and there is currently no
mechanism to support cancelling a transition and returning to the
original state. For some use cases where the need for a service is not
under application control the standard sequence of service request, use,
and release may not be easily satisfiable.

An example is functionality that requires both an onoff service (such as
a clock) and an secondary gating signal (such as a connected USB cable).
If the cable is removed before the clock is started then the clock is
not needed anymore, but the client functionality should not be required
to implement the logic to wait for the request to complete and to then
submit a release.

The :cpp:type:`onoff_notifier` infrastructure provides an internal state
machine that reacts immediately to synchronous requests and releases,
coordinating with the underlying onoff service to ensure the client's
latest desired state will be reached as soon as possible. The client
provides a callback that is invoked on relevant state changes, and
synchronously indicates on both request and release whether the desired
state has already been reached.

.. doxygengroup:: resource_mgmt_onoff_apis
:project: Zephyr

.. _resource_mgmt_queued_operation:

Queued Operation Manager
************************

While :ref:`resource_mgmt_onoff` supports a shared resource that must be
available as long as any user still depends on it, the queued operation
manager provides serialized exclusive access to a resource that executes
operations asynchronously. This can be used to support (for example)
ADC sampling for different sensors, or groups of bus transactions.
Clients submit a operation request that is processed when the device
becomes available, with clients being notified of the completion of the
operation though the standard :ref:`async_notification`.

As with the on-off manager, the queued resource manager is a generic
infrastructure tool that should be used by a extending service, such as
an I2C bus controller or an ADC. The manager has the following
characteristics:

* The stable states are idle and processing. The manager always begins
in the idle state.
* The core client operations are submit (add an operation) and cancel
(remove an operation before it starts).
* Ownership of the operation object transitions from the client to the
manager when a queue request is accepted, and is returned to the
client when the manager notifies the client of operation completion.
* The core client event is completion. Manager state changes only as a
side effect from submitting or completing an operation.
* The service transitions from idle to processing when an operation is
submitted.
* The service transitions from processing to idle when notification of
the last operation has completed and there are no queued operations.
* The manager selects the next operation to process when notification of
completion has itself completed. In particular, changes to the set of
pending operations that are made during a completion callback affect
the next operation to execute.
* Each submitted operation includes a priority that orders execution by
first-come-first-served within priority.
* Operations are asynchronous, with completion notification through the
:ref:`async_notification`. The operations and notifications are run
in a context that is service-specific. This may be one or more
dedicated threads, or work queues. Notifications may come from
interrupt handlers. Note that for some services certain operations
may complete before the submit request has returned to its caller.

The generic infrastructure holds the active operation and a queue of
pending operations. A service extension shall provide functions that:

* check that a request is well-formed, i.e. can be added to the queue;
* receive notification that a new operation is to be processed, or that
no operations are available (allowing the service to enter a
power-down mode);
* translate a generic completion callback into a service-specific
callback.

.. doxygengroup:: resource_mgmt_queued_operation_apis
:project: Zephyr
Loading