aboutsummaryrefslogtreecommitdiffstats
path: root/Documentation/core-api/xarray.rst
diff options
context:
space:
mode:
Diffstat (limited to 'Documentation/core-api/xarray.rst')
-rw-r--r--Documentation/core-api/xarray.rst52
1 files changed, 41 insertions, 11 deletions
diff --git a/Documentation/core-api/xarray.rst b/Documentation/core-api/xarray.rst
index a4e705108f42..dbe96cb5558e 100644
--- a/Documentation/core-api/xarray.rst
+++ b/Documentation/core-api/xarray.rst
@@ -74,7 +74,8 @@ using :c:func:`xa_load`. xa_store will overwrite any entry with the
74new entry and return the previous entry stored at that index. You can 74new entry and return the previous entry stored at that index. You can
75use :c:func:`xa_erase` instead of calling :c:func:`xa_store` with a 75use :c:func:`xa_erase` instead of calling :c:func:`xa_store` with a
76``NULL`` entry. There is no difference between an entry that has never 76``NULL`` entry. There is no difference between an entry that has never
77been stored to and one that has most recently had ``NULL`` stored to it. 77been stored to, one that has been erased and one that has most recently
78had ``NULL`` stored to it.
78 79
79You can conditionally replace an entry at an index by using 80You can conditionally replace an entry at an index by using
80:c:func:`xa_cmpxchg`. Like :c:func:`cmpxchg`, it will only succeed if 81:c:func:`xa_cmpxchg`. Like :c:func:`cmpxchg`, it will only succeed if
@@ -105,23 +106,44 @@ may result in the entry being marked at some, but not all of the other
105indices. Storing into one index may result in the entry retrieved by 106indices. Storing into one index may result in the entry retrieved by
106some, but not all of the other indices changing. 107some, but not all of the other indices changing.
107 108
109Sometimes you need to ensure that a subsequent call to :c:func:`xa_store`
110will not need to allocate memory. The :c:func:`xa_reserve` function
111will store a reserved entry at the indicated index. Users of the normal
112API will see this entry as containing ``NULL``. If you do not need to
113use the reserved entry, you can call :c:func:`xa_release` to remove the
114unused entry. If another user has stored to the entry in the meantime,
115:c:func:`xa_release` will do nothing; if instead you want the entry to
116become ``NULL``, you should use :c:func:`xa_erase`.
117
118If all entries in the array are ``NULL``, the :c:func:`xa_empty` function
119will return ``true``.
120
108Finally, you can remove all entries from an XArray by calling 121Finally, you can remove all entries from an XArray by calling
109:c:func:`xa_destroy`. If the XArray entries are pointers, you may wish 122:c:func:`xa_destroy`. If the XArray entries are pointers, you may wish
110to free the entries first. You can do this by iterating over all present 123to free the entries first. You can do this by iterating over all present
111entries in the XArray using the :c:func:`xa_for_each` iterator. 124entries in the XArray using the :c:func:`xa_for_each` iterator.
112 125
113ID assignment 126Allocating XArrays
114------------- 127------------------
128
129If you use :c:func:`DEFINE_XARRAY_ALLOC` to define the XArray, or
130initialise it by passing ``XA_FLAGS_ALLOC`` to :c:func:`xa_init_flags`,
131the XArray changes to track whether entries are in use or not.
115 132
116You can call :c:func:`xa_alloc` to store the entry at any unused index 133You can call :c:func:`xa_alloc` to store the entry at any unused index
117in the XArray. If you need to modify the array from interrupt context, 134in the XArray. If you need to modify the array from interrupt context,
118you can use :c:func:`xa_alloc_bh` or :c:func:`xa_alloc_irq` to disable 135you can use :c:func:`xa_alloc_bh` or :c:func:`xa_alloc_irq` to disable
119interrupts while allocating the ID. Unlike :c:func:`xa_store`, allocating 136interrupts while allocating the ID.
120a ``NULL`` pointer does not delete an entry. Instead it reserves an 137
121entry like :c:func:`xa_reserve` and you can release it using either 138Using :c:func:`xa_store`, :c:func:`xa_cmpxchg` or :c:func:`xa_insert`
122:c:func:`xa_erase` or :c:func:`xa_release`. To use ID assignment, the 139will mark the entry as being allocated. Unlike a normal XArray, storing
123XArray must be defined with :c:func:`DEFINE_XARRAY_ALLOC`, or initialised 140``NULL`` will mark the entry as being in use, like :c:func:`xa_reserve`.
124by passing ``XA_FLAGS_ALLOC`` to :c:func:`xa_init_flags`, 141To free an entry, use :c:func:`xa_erase` (or :c:func:`xa_release` if
142you only want to free the entry if it's ``NULL``).
143
144You cannot use ``XA_MARK_0`` with an allocating XArray as this mark
145is used to track whether an entry is free or not. The other marks are
146available for your use.
125 147
126Memory allocation 148Memory allocation
127----------------- 149-----------------
@@ -158,6 +180,8 @@ Takes RCU read lock:
158 180
159Takes xa_lock internally: 181Takes xa_lock internally:
160 * :c:func:`xa_store` 182 * :c:func:`xa_store`
183 * :c:func:`xa_store_bh`
184 * :c:func:`xa_store_irq`
161 * :c:func:`xa_insert` 185 * :c:func:`xa_insert`
162 * :c:func:`xa_erase` 186 * :c:func:`xa_erase`
163 * :c:func:`xa_erase_bh` 187 * :c:func:`xa_erase_bh`
@@ -167,6 +191,9 @@ Takes xa_lock internally:
167 * :c:func:`xa_alloc` 191 * :c:func:`xa_alloc`
168 * :c:func:`xa_alloc_bh` 192 * :c:func:`xa_alloc_bh`
169 * :c:func:`xa_alloc_irq` 193 * :c:func:`xa_alloc_irq`
194 * :c:func:`xa_reserve`
195 * :c:func:`xa_reserve_bh`
196 * :c:func:`xa_reserve_irq`
170 * :c:func:`xa_destroy` 197 * :c:func:`xa_destroy`
171 * :c:func:`xa_set_mark` 198 * :c:func:`xa_set_mark`
172 * :c:func:`xa_clear_mark` 199 * :c:func:`xa_clear_mark`
@@ -177,6 +204,7 @@ Assumes xa_lock held on entry:
177 * :c:func:`__xa_erase` 204 * :c:func:`__xa_erase`
178 * :c:func:`__xa_cmpxchg` 205 * :c:func:`__xa_cmpxchg`
179 * :c:func:`__xa_alloc` 206 * :c:func:`__xa_alloc`
207 * :c:func:`__xa_reserve`
180 * :c:func:`__xa_set_mark` 208 * :c:func:`__xa_set_mark`
181 * :c:func:`__xa_clear_mark` 209 * :c:func:`__xa_clear_mark`
182 210
@@ -234,7 +262,8 @@ Sharing the XArray with interrupt context is also possible, either
234using :c:func:`xa_lock_irqsave` in both the interrupt handler and process 262using :c:func:`xa_lock_irqsave` in both the interrupt handler and process
235context, or :c:func:`xa_lock_irq` in process context and :c:func:`xa_lock` 263context, or :c:func:`xa_lock_irq` in process context and :c:func:`xa_lock`
236in the interrupt handler. Some of the more common patterns have helper 264in the interrupt handler. Some of the more common patterns have helper
237functions such as :c:func:`xa_erase_bh` and :c:func:`xa_erase_irq`. 265functions such as :c:func:`xa_store_bh`, :c:func:`xa_store_irq`,
266:c:func:`xa_erase_bh` and :c:func:`xa_erase_irq`.
238 267
239Sometimes you need to protect access to the XArray with a mutex because 268Sometimes you need to protect access to the XArray with a mutex because
240that lock sits above another mutex in the locking hierarchy. That does 269that lock sits above another mutex in the locking hierarchy. That does
@@ -322,7 +351,8 @@ to :c:func:`xas_retry`, and retry the operation if it returns ``true``.
322 - :c:func:`xa_is_zero` 351 - :c:func:`xa_is_zero`
323 - Zero entries appear as ``NULL`` through the Normal API, but occupy 352 - Zero entries appear as ``NULL`` through the Normal API, but occupy
324 an entry in the XArray which can be used to reserve the index for 353 an entry in the XArray which can be used to reserve the index for
325 future use. 354 future use. This is used by allocating XArrays for allocated entries
355 which are ``NULL``.
326 356
327Other internal entries may be added in the future. As far as possible, they 357Other internal entries may be added in the future. As far as possible, they
328will be handled by :c:func:`xas_retry`. 358will be handled by :c:func:`xas_retry`.