summaryrefslogtreecommitdiffstats
path: root/Documentation/driver-api/reset.rst
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--Documentation/driver-api/reset.rst221
1 files changed, 221 insertions, 0 deletions
diff --git a/Documentation/driver-api/reset.rst b/Documentation/driver-api/reset.rst
new file mode 100644
index 000000000..84e03d703
--- /dev/null
+++ b/Documentation/driver-api/reset.rst
@@ -0,0 +1,221 @@
+.. SPDX-License-Identifier: GPL-2.0-only
+
+====================
+Reset controller API
+====================
+
+Introduction
+============
+
+Reset controllers are central units that control the reset signals to multiple
+peripherals.
+The reset controller API is split into two parts:
+the `consumer driver interface <#consumer-driver-interface>`__ (`API reference
+<#reset-consumer-api>`__), which allows peripheral drivers to request control
+over their reset input signals, and the `reset controller driver interface
+<#reset-controller-driver-interface>`__ (`API reference
+<#reset-controller-driver-api>`__), which is used by drivers for reset
+controller devices to register their reset controls to provide them to the
+consumers.
+
+While some reset controller hardware units also implement system restart
+functionality, restart handlers are out of scope for the reset controller API.
+
+Glossary
+--------
+
+The reset controller API uses these terms with a specific meaning:
+
+Reset line
+
+ Physical reset line carrying a reset signal from a reset controller
+ hardware unit to a peripheral module.
+
+Reset control
+
+ Control method that determines the state of one or multiple reset lines.
+ Most commonly this is a single bit in reset controller register space that
+ either allows direct control over the physical state of the reset line, or
+ is self-clearing and can be used to trigger a predetermined pulse on the
+ reset line.
+ In more complicated reset controls, a single trigger action can launch a
+ carefully timed sequence of pulses on multiple reset lines.
+
+Reset controller
+
+ A hardware module that provides a number of reset controls to control a
+ number of reset lines.
+
+Reset consumer
+
+ Peripheral module or external IC that is put into reset by the signal on a
+ reset line.
+
+Consumer driver interface
+=========================
+
+This interface provides an API that is similar to the kernel clock framework.
+Consumer drivers use get and put operations to acquire and release reset
+controls.
+Functions are provided to assert and deassert the controlled reset lines,
+trigger reset pulses, or to query reset line status.
+
+When requesting reset controls, consumers can use symbolic names for their
+reset inputs, which are mapped to an actual reset control on an existing reset
+controller device by the core.
+
+A stub version of this API is provided when the reset controller framework is
+not in use in order to minimize the need to use ifdefs.
+
+Shared and exclusive resets
+---------------------------
+
+The reset controller API provides either reference counted deassertion and
+assertion or direct, exclusive control.
+The distinction between shared and exclusive reset controls is made at the time
+the reset control is requested, either via devm_reset_control_get_shared() or
+via devm_reset_control_get_exclusive().
+This choice determines the behavior of the API calls made with the reset
+control.
+
+Shared resets behave similarly to clocks in the kernel clock framework.
+They provide reference counted deassertion, where only the first deassert,
+which increments the deassertion reference count to one, and the last assert
+which decrements the deassertion reference count back to zero, have a physical
+effect on the reset line.
+
+Exclusive resets on the other hand guarantee direct control.
+That is, an assert causes the reset line to be asserted immediately, and a
+deassert causes the reset line to be deasserted immediately.
+
+Assertion and deassertion
+-------------------------
+
+Consumer drivers use the reset_control_assert() and reset_control_deassert()
+functions to assert and deassert reset lines.
+For shared reset controls, calls to the two functions must be balanced.
+
+Note that since multiple consumers may be using a shared reset control, there
+is no guarantee that calling reset_control_assert() on a shared reset control
+will actually cause the reset line to be asserted.
+Consumer drivers using shared reset controls should assume that the reset line
+may be kept deasserted at all times.
+The API only guarantees that the reset line can not be asserted as long as any
+consumer has requested it to be deasserted.
+
+Triggering
+----------
+
+Consumer drivers use reset_control_reset() to trigger a reset pulse on a
+self-deasserting reset control.
+In general, these resets can not be shared between multiple consumers, since
+requesting a pulse from any consumer driver will reset all connected
+peripherals.
+
+The reset controller API allows requesting self-deasserting reset controls as
+shared, but for those only the first trigger request causes an actual pulse to
+be issued on the reset line.
+All further calls to this function have no effect until all consumers have
+called reset_control_rearm().
+For shared reset controls, calls to the two functions must be balanced.
+This allows devices that only require an initial reset at any point before the
+driver is probed or resumed to share a pulsed reset line.
+
+Querying
+--------
+
+Only some reset controllers support querying the current status of a reset
+line, via reset_control_status().
+If supported, this function returns a positive non-zero value if the given
+reset line is asserted.
+The reset_control_status() function does not accept a
+`reset control array <#reset-control-arrays>`__ handle as its input parameter.
+
+Optional resets
+---------------
+
+Often peripherals require a reset line on some platforms but not on others.
+For this, reset controls can be requested as optional using
+devm_reset_control_get_optional_exclusive() or
+devm_reset_control_get_optional_shared().
+These functions return a NULL pointer instead of an error when the requested
+reset control is not specified in the device tree.
+Passing a NULL pointer to the reset_control functions causes them to return
+quietly without an error.
+
+Reset control arrays
+--------------------
+
+Some drivers need to assert a bunch of reset lines in no particular order.
+devm_reset_control_array_get() returns an opaque reset control handle that can
+be used to assert, deassert, or trigger all specified reset controls at once.
+The reset control API does not guarantee the order in which the individual
+controls therein are handled.
+
+Reset controller driver interface
+=================================
+
+Drivers for reset controller modules provide the functionality necessary to
+assert or deassert reset signals, to trigger a reset pulse on a reset line, or
+to query its current state.
+All functions are optional.
+
+Initialization
+--------------
+
+Drivers fill a struct :c:type:`reset_controller_dev` and register it with
+reset_controller_register() in their probe function.
+The actual functionality is implemented in callback functions via a struct
+:c:type:`reset_control_ops`.
+
+API reference
+=============
+
+The reset controller API is documented here in two parts:
+the `reset consumer API <#reset-consumer-api>`__ and the `reset controller
+driver API <#reset-controller-driver-api>`__.
+
+Reset consumer API
+------------------
+
+Reset consumers can control a reset line using an opaque reset control handle,
+which can be obtained from devm_reset_control_get_exclusive() or
+devm_reset_control_get_shared().
+Given the reset control, consumers can call reset_control_assert() and
+reset_control_deassert(), trigger a reset pulse using reset_control_reset(), or
+query the reset line status using reset_control_status().
+
+.. kernel-doc:: include/linux/reset.h
+ :internal:
+
+.. kernel-doc:: drivers/reset/core.c
+ :functions: reset_control_reset
+ reset_control_assert
+ reset_control_deassert
+ reset_control_status
+ reset_control_acquire
+ reset_control_release
+ reset_control_rearm
+ reset_control_put
+ of_reset_control_get_count
+ of_reset_control_array_get
+ devm_reset_control_array_get
+ reset_control_get_count
+
+Reset controller driver API
+---------------------------
+
+Reset controller drivers are supposed to implement the necessary functions in
+a static constant structure :c:type:`reset_control_ops`, allocate and fill out
+a struct :c:type:`reset_controller_dev`, and register it using
+devm_reset_controller_register().
+
+.. kernel-doc:: include/linux/reset-controller.h
+ :internal:
+
+.. kernel-doc:: drivers/reset/core.c
+ :functions: of_reset_simple_xlate
+ reset_controller_register
+ reset_controller_unregister
+ devm_reset_controller_register
+ reset_controller_add_lookup