xref: /aosp_15_r20/external/pigweed/pw_thread/docs.rst (revision 61c4878ac05f98d0ceed94b57d316916de578985)
1*61c4878aSAndroid Build Coastguard Worker.. _module-pw_thread:
2*61c4878aSAndroid Build Coastguard Worker
3*61c4878aSAndroid Build Coastguard Worker=========
4*61c4878aSAndroid Build Coastguard Workerpw_thread
5*61c4878aSAndroid Build Coastguard Worker=========
6*61c4878aSAndroid Build Coastguard WorkerThe ``pw_thread`` module contains utilities for thread creation and thread
7*61c4878aSAndroid Build Coastguard Workerexecution.
8*61c4878aSAndroid Build Coastguard Worker
9*61c4878aSAndroid Build Coastguard Worker---------------
10*61c4878aSAndroid Build Coastguard WorkerThread Sleeping
11*61c4878aSAndroid Build Coastguard Worker---------------
12*61c4878aSAndroid Build Coastguard WorkerC++
13*61c4878aSAndroid Build Coastguard Worker===
14*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw::this_thread::sleep_for(chrono::SystemClock::duration sleep_duration)
15*61c4878aSAndroid Build Coastguard Worker
16*61c4878aSAndroid Build Coastguard Worker   Blocks the execution of the current thread for at least the specified
17*61c4878aSAndroid Build Coastguard Worker   duration. This function may block for longer due to scheduling or resource
18*61c4878aSAndroid Build Coastguard Worker   contention delays.
19*61c4878aSAndroid Build Coastguard Worker
20*61c4878aSAndroid Build Coastguard Worker   A sleep duration of 0 will at minimum yield, meaning it will provide a hint
21*61c4878aSAndroid Build Coastguard Worker   to the implementation to reschedule the execution of threads, allowing other
22*61c4878aSAndroid Build Coastguard Worker   threads to run.
23*61c4878aSAndroid Build Coastguard Worker
24*61c4878aSAndroid Build Coastguard Worker   **Precondition:** This can only be called from a thread, meaning the
25*61c4878aSAndroid Build Coastguard Worker   scheduler is running.
26*61c4878aSAndroid Build Coastguard Worker
27*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw::this_thread::sleep_until(chrono::SystemClock::time_point wakeup_time)
28*61c4878aSAndroid Build Coastguard Worker
29*61c4878aSAndroid Build Coastguard Worker   Blocks the execution of the current thread until at least the specified
30*61c4878aSAndroid Build Coastguard Worker   time has been reached. This function may block for longer due to scheduling
31*61c4878aSAndroid Build Coastguard Worker   or resource contention delays.
32*61c4878aSAndroid Build Coastguard Worker
33*61c4878aSAndroid Build Coastguard Worker   A sleep deadline in the past up to the current time will at minimum yield
34*61c4878aSAndroid Build Coastguard Worker   meaning it will provide a hint to the implementation to reschedule the
35*61c4878aSAndroid Build Coastguard Worker   execution of threads, allowing other threads to run.
36*61c4878aSAndroid Build Coastguard Worker
37*61c4878aSAndroid Build Coastguard Worker   **Precondition:** This can only be called from a thread, meaning the
38*61c4878aSAndroid Build Coastguard Worker   scheduler is running.
39*61c4878aSAndroid Build Coastguard Worker
40*61c4878aSAndroid Build Coastguard WorkerExamples in C++
41*61c4878aSAndroid Build Coastguard Worker---------------
42*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
43*61c4878aSAndroid Build Coastguard Worker
44*61c4878aSAndroid Build Coastguard Worker   #include <chrono>
45*61c4878aSAndroid Build Coastguard Worker
46*61c4878aSAndroid Build Coastguard Worker   #include "pw_chrono/system_clock.h"
47*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread/sleep.h"
48*61c4878aSAndroid Build Coastguard Worker
49*61c4878aSAndroid Build Coastguard Worker   using std::literals::chrono_literals::ms;
50*61c4878aSAndroid Build Coastguard Worker
51*61c4878aSAndroid Build Coastguard Worker   void FunctionInvokedByThread() {
52*61c4878aSAndroid Build Coastguard Worker     pw::this_thread::sleep_for(42ms);
53*61c4878aSAndroid Build Coastguard Worker   }
54*61c4878aSAndroid Build Coastguard Worker
55*61c4878aSAndroid Build Coastguard Worker   void AnotherFunctionInvokedByThread() {
56*61c4878aSAndroid Build Coastguard Worker     pw::this_thread::sleep_until(pw::chrono::SystemClock::now() + 42ms);
57*61c4878aSAndroid Build Coastguard Worker   }
58*61c4878aSAndroid Build Coastguard Worker
59*61c4878aSAndroid Build Coastguard WorkerC
60*61c4878aSAndroid Build Coastguard Worker=
61*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw_this_thread_SleepFor(pw_chrono_SystemClock_Duration sleep_duration)
62*61c4878aSAndroid Build Coastguard Worker
63*61c4878aSAndroid Build Coastguard Worker   Invokes ``pw::this_thread::sleep_until(sleep_duration)``.
64*61c4878aSAndroid Build Coastguard Worker
65*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw_this_thread_SleepUntil(pw_chrono_SystemClock_TimePoint wakeup_time)
66*61c4878aSAndroid Build Coastguard Worker
67*61c4878aSAndroid Build Coastguard Worker   Invokes ``pw::this_thread::sleep_until(wakeup_time)``.
68*61c4878aSAndroid Build Coastguard Worker
69*61c4878aSAndroid Build Coastguard Worker
70*61c4878aSAndroid Build Coastguard Worker---------------
71*61c4878aSAndroid Build Coastguard WorkerThread Yielding
72*61c4878aSAndroid Build Coastguard Worker---------------
73*61c4878aSAndroid Build Coastguard WorkerC++
74*61c4878aSAndroid Build Coastguard Worker===
75*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw::this_thread::yield() noexcept
76*61c4878aSAndroid Build Coastguard Worker
77*61c4878aSAndroid Build Coastguard Worker   Provides a hint to the implementation to reschedule the execution of threads,
78*61c4878aSAndroid Build Coastguard Worker   allowing other threads to run.
79*61c4878aSAndroid Build Coastguard Worker
80*61c4878aSAndroid Build Coastguard Worker   The exact behavior of this function depends on the implementation, in
81*61c4878aSAndroid Build Coastguard Worker   particular on the mechanics of the OS scheduler in use and the state of the
82*61c4878aSAndroid Build Coastguard Worker   system.
83*61c4878aSAndroid Build Coastguard Worker
84*61c4878aSAndroid Build Coastguard Worker   **Precondition:** This can only be called from a thread, meaning the
85*61c4878aSAndroid Build Coastguard Worker   scheduler is running.
86*61c4878aSAndroid Build Coastguard Worker
87*61c4878aSAndroid Build Coastguard WorkerExample in C++
88*61c4878aSAndroid Build Coastguard Worker---------------
89*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
90*61c4878aSAndroid Build Coastguard Worker
91*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread/yield.h"
92*61c4878aSAndroid Build Coastguard Worker
93*61c4878aSAndroid Build Coastguard Worker   void FunctionInvokedByThread() {
94*61c4878aSAndroid Build Coastguard Worker     pw::this_thread::yield();
95*61c4878aSAndroid Build Coastguard Worker   }
96*61c4878aSAndroid Build Coastguard Worker
97*61c4878aSAndroid Build Coastguard WorkerC
98*61c4878aSAndroid Build Coastguard Worker=
99*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: void pw_this_thread_Yield(void)
100*61c4878aSAndroid Build Coastguard Worker
101*61c4878aSAndroid Build Coastguard Worker   Invokes ``pw::this_thread::yield()``.
102*61c4878aSAndroid Build Coastguard Worker
103*61c4878aSAndroid Build Coastguard Worker---------------------
104*61c4878aSAndroid Build Coastguard WorkerThread Identification
105*61c4878aSAndroid Build Coastguard Worker---------------------
106*61c4878aSAndroid Build Coastguard WorkerThe class :cpp:type:`pw::Thread::id` is a lightweight, trivially copyable class
107*61c4878aSAndroid Build Coastguard Workerthat serves as a unique identifier of Thread objects.
108*61c4878aSAndroid Build Coastguard Worker
109*61c4878aSAndroid Build Coastguard WorkerInstances of this class may also hold the special distinct value that does
110*61c4878aSAndroid Build Coastguard Workernot represent any thread. Once a thread has finished, the value of its
111*61c4878aSAndroid Build Coastguard WorkerThread::id may be reused by another thread.
112*61c4878aSAndroid Build Coastguard Worker
113*61c4878aSAndroid Build Coastguard WorkerThis class is designed for use as key in associative containers, both ordered
114*61c4878aSAndroid Build Coastguard Workerand unordered.
115*61c4878aSAndroid Build Coastguard Worker
116*61c4878aSAndroid Build Coastguard WorkerAlthough the current API is similar to C++11 STL `std::thread::id
117*61c4878aSAndroid Build Coastguard Worker<https://en.cppreference.com/w/cpp/thread/thread/id>`_, it is missing the
118*61c4878aSAndroid Build Coastguard Workerrequired hashing and streaming operators and may diverge further in the future.
119*61c4878aSAndroid Build Coastguard Worker
120*61c4878aSAndroid Build Coastguard WorkerA thread's identification (:cpp:type:`pw::Thread::id`) can be acquired only in
121*61c4878aSAndroid Build Coastguard WorkerC++ in one of two ways:
122*61c4878aSAndroid Build Coastguard Worker
123*61c4878aSAndroid Build Coastguard Worker1) Using the :cpp:type:`pw::Thread` handle's ``pw::Thread::id get_id() const``
124*61c4878aSAndroid Build Coastguard Worker   method.
125*61c4878aSAndroid Build Coastguard Worker2) While executing the thread using
126*61c4878aSAndroid Build Coastguard Worker   ``pw::Thread::id pw::this_thread::get_id() noexcept``.
127*61c4878aSAndroid Build Coastguard Worker
128*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: pw::Thread::id pw::this_thread::get_id() noexcept
129*61c4878aSAndroid Build Coastguard Worker
130*61c4878aSAndroid Build Coastguard Worker   This is thread safe, not IRQ safe. It is implementation defined whether this
131*61c4878aSAndroid Build Coastguard Worker   is safe before the scheduler has started.
132*61c4878aSAndroid Build Coastguard Worker
133*61c4878aSAndroid Build Coastguard Worker
134*61c4878aSAndroid Build Coastguard WorkerExample
135*61c4878aSAndroid Build Coastguard Worker=======
136*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
137*61c4878aSAndroid Build Coastguard Worker
138*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread/thread.h"
139*61c4878aSAndroid Build Coastguard Worker
140*61c4878aSAndroid Build Coastguard Worker   void FunctionInvokedByThread() {
141*61c4878aSAndroid Build Coastguard Worker     const pw::Thread::id my_id = pw::this_thread::get_id();
142*61c4878aSAndroid Build Coastguard Worker   }
143*61c4878aSAndroid Build Coastguard Worker
144*61c4878aSAndroid Build Coastguard Worker.. _module-pw_thread-thread-creation:
145*61c4878aSAndroid Build Coastguard Worker
146*61c4878aSAndroid Build Coastguard Worker---------------
147*61c4878aSAndroid Build Coastguard WorkerThread creation
148*61c4878aSAndroid Build Coastguard Worker---------------
149*61c4878aSAndroid Build Coastguard WorkerThe :cpp:type:`pw::Thread` class can be used to create a thread, allowing
150*61c4878aSAndroid Build Coastguard Workermultiple functions to execute concurrently.
151*61c4878aSAndroid Build Coastguard Worker
152*61c4878aSAndroid Build Coastguard WorkerAPI reference
153*61c4878aSAndroid Build Coastguard Worker=============
154*61c4878aSAndroid Build Coastguard Worker.. doxygentypedef:: pw::Thread
155*61c4878aSAndroid Build Coastguard Worker
156*61c4878aSAndroid Build Coastguard Worker.. doxygenclass:: pw::thread::Thread
157*61c4878aSAndroid Build Coastguard Worker   :members:
158*61c4878aSAndroid Build Coastguard Worker
159*61c4878aSAndroid Build Coastguard Worker.. doxygenclass:: pw::thread::Options
160*61c4878aSAndroid Build Coastguard Worker   :members:
161*61c4878aSAndroid Build Coastguard Worker
162*61c4878aSAndroid Build Coastguard WorkerDifferences from ``std::thread``
163*61c4878aSAndroid Build Coastguard Worker================================
164*61c4878aSAndroid Build Coastguard WorkerThe ``pw::thread:Thread`` API is similar to the C++11 STL `std::thread
165*61c4878aSAndroid Build Coastguard Worker<https://en.cppreference.com/w/cpp/thread/thread>`_ class, meaning the object is
166*61c4878aSAndroid Build Coastguard Workereffectively a thread handle and not an object which contains the thread's
167*61c4878aSAndroid Build Coastguard Workercontext. Unlike ``std::thread``, the API requires ``pw::thread::Options`` as an
168*61c4878aSAndroid Build Coastguard Workerargument. These options are platform-specific, and allow the user to specify
169*61c4878aSAndroid Build Coastguard Workerdetails such as the thread's name, priority, stack size, and where the thread's
170*61c4878aSAndroid Build Coastguard Workermemory will be stored.
171*61c4878aSAndroid Build Coastguard Worker
172*61c4878aSAndroid Build Coastguard WorkerWe recognize that the C++11's STL ``std::thread`` API has some drawbacks where
173*61c4878aSAndroid Build Coastguard Workerit is easy to forget to join or detach the thread handle. Because of this, we
174*61c4878aSAndroid Build Coastguard Workeroffer helper wrappers like the ``pw::thread::DetachedThread``. Soon we will
175*61c4878aSAndroid Build Coastguard Workerextend this by also adding a ``pw::thread::JoiningThread`` helper wrapper which
176*61c4878aSAndroid Build Coastguard Workerwill also have a lighter weight C++20 ``std::jthread`` like cooperative
177*61c4878aSAndroid Build Coastguard Workercancellation contract to make joining safer and easier.
178*61c4878aSAndroid Build Coastguard Worker
179*61c4878aSAndroid Build Coastguard WorkerExecution order
180*61c4878aSAndroid Build Coastguard Worker===============
181*61c4878aSAndroid Build Coastguard WorkerThreads may begin execution immediately upon construction of the associated
182*61c4878aSAndroid Build Coastguard Workerthread object (pending any OS scheduling delays), starting at the top-level
183*61c4878aSAndroid Build Coastguard Workerfunction provided as a constructor argument. The top-level function may
184*61c4878aSAndroid Build Coastguard Workercommunicate its return value by modifying shared variables (which may require
185*61c4878aSAndroid Build Coastguard Workersynchronization, see :ref:`module-pw_sync`)
186*61c4878aSAndroid Build Coastguard Worker
187*61c4878aSAndroid Build Coastguard WorkerThread objects may also be in the state that does not represent any thread
188*61c4878aSAndroid Build Coastguard Worker(after default construction, move from, detach, or join), and a thread of
189*61c4878aSAndroid Build Coastguard Workerexecution may be not associated with any thread objects (after detach).
190*61c4878aSAndroid Build Coastguard Worker
191*61c4878aSAndroid Build Coastguard WorkerNo two Thread objects may represent the same thread of execution; Thread is
192*61c4878aSAndroid Build Coastguard Workernot CopyConstructible or CopyAssignable, although it is MoveConstructible and
193*61c4878aSAndroid Build Coastguard WorkerMoveAssignable.
194*61c4878aSAndroid Build Coastguard Worker
195*61c4878aSAndroid Build Coastguard Worker.. list-table::
196*61c4878aSAndroid Build Coastguard Worker
197*61c4878aSAndroid Build Coastguard Worker  * - *Supported on*
198*61c4878aSAndroid Build Coastguard Worker    - *Backend module*
199*61c4878aSAndroid Build Coastguard Worker  * - FreeRTOS
200*61c4878aSAndroid Build Coastguard Worker    - :ref:`module-pw_thread_freertos`
201*61c4878aSAndroid Build Coastguard Worker  * - ThreadX
202*61c4878aSAndroid Build Coastguard Worker    - :ref:`module-pw_thread_threadx`
203*61c4878aSAndroid Build Coastguard Worker  * - embOS
204*61c4878aSAndroid Build Coastguard Worker    - :ref:`module-pw_thread_embos`
205*61c4878aSAndroid Build Coastguard Worker  * - STL
206*61c4878aSAndroid Build Coastguard Worker    - :ref:`module-pw_thread_stl`
207*61c4878aSAndroid Build Coastguard Worker  * - Zephyr
208*61c4878aSAndroid Build Coastguard Worker    - Planned
209*61c4878aSAndroid Build Coastguard Worker  * - CMSIS-RTOS API v2 & RTX5
210*61c4878aSAndroid Build Coastguard Worker    - Planned
211*61c4878aSAndroid Build Coastguard Worker
212*61c4878aSAndroid Build Coastguard WorkerModule Configuration Options
213*61c4878aSAndroid Build Coastguard Worker============================
214*61c4878aSAndroid Build Coastguard WorkerThe following configurations can be adjusted via compile-time configuration of
215*61c4878aSAndroid Build Coastguard Workerthis module, see the
216*61c4878aSAndroid Build Coastguard Worker:ref:`module documentation <module-structure-compile-time-configuration>` for
217*61c4878aSAndroid Build Coastguard Workermore details.
218*61c4878aSAndroid Build Coastguard Worker
219*61c4878aSAndroid Build Coastguard Worker.. c:macro:: PW_THREAD_CONFIG_LOG_LEVEL
220*61c4878aSAndroid Build Coastguard Worker
221*61c4878aSAndroid Build Coastguard Worker  The log level to use for this module. Logs below this level are omitted.
222*61c4878aSAndroid Build Coastguard Worker
223*61c4878aSAndroid Build Coastguard WorkerOptions
224*61c4878aSAndroid Build Coastguard Worker=======
225*61c4878aSAndroid Build Coastguard WorkerThe ``pw::thread::Options`` contains the parameters or attributes needed for a
226*61c4878aSAndroid Build Coastguard Workerthread to start.
227*61c4878aSAndroid Build Coastguard Worker
228*61c4878aSAndroid Build Coastguard WorkerPigweed does not generalize options, instead we strive to give you full control
229*61c4878aSAndroid Build Coastguard Workerwhere we provide helpers to do this.
230*61c4878aSAndroid Build Coastguard Worker
231*61c4878aSAndroid Build Coastguard WorkerOptions are backend specific and ergo the generic base class cannot be
232*61c4878aSAndroid Build Coastguard Workerdirectly instantiated.
233*61c4878aSAndroid Build Coastguard Worker
234*61c4878aSAndroid Build Coastguard WorkerThe attributes which can be set through the options are backend specific
235*61c4878aSAndroid Build Coastguard Workerbut may contain things like the thread name, priority, scheduling policy,
236*61c4878aSAndroid Build Coastguard Workercore/processor affinity, and/or an optional reference to a pre-allocated
237*61c4878aSAndroid Build Coastguard WorkerContext (the collection of memory allocations needed for a thread to run).
238*61c4878aSAndroid Build Coastguard Worker
239*61c4878aSAndroid Build Coastguard WorkerOptions shall NOT have an attribute to start threads as detached vs joinable.
240*61c4878aSAndroid Build Coastguard WorkerAll :cpp:type:`pw::Thread` instances must be explicitly ``join()``'d or
241*61c4878aSAndroid Build Coastguard Worker``detach()``'d through the run-time Thread API.
242*61c4878aSAndroid Build Coastguard Worker
243*61c4878aSAndroid Build Coastguard WorkerNote that if backends set ``PW_THREAD_JOINING_ENABLED`` to false, backends
244*61c4878aSAndroid Build Coastguard Workermay use native OS specific APIs to create native detached threads because the
245*61c4878aSAndroid Build Coastguard Worker``join()`` API would be compiled out. However, users must still explicitly
246*61c4878aSAndroid Build Coastguard Workerinvoke ``detach()``.
247*61c4878aSAndroid Build Coastguard Worker
248*61c4878aSAndroid Build Coastguard WorkerOptions must not contain any memory needed for a thread to run (TCB,
249*61c4878aSAndroid Build Coastguard Workerstack, etc.). The Options may be deleted or re-used immediately after
250*61c4878aSAndroid Build Coastguard Workerstarting a thread.
251*61c4878aSAndroid Build Coastguard Worker
252*61c4878aSAndroid Build Coastguard WorkerPlease see the thread creation backend documentation for how their Options work.
253*61c4878aSAndroid Build Coastguard Worker
254*61c4878aSAndroid Build Coastguard WorkerPortable Thread Creation
255*61c4878aSAndroid Build Coastguard Worker========================
256*61c4878aSAndroid Build Coastguard WorkerDue to the fact that ``pw::thread::Options`` cannot be created in portable code,
257*61c4878aSAndroid Build Coastguard Workersome extra work must be done in order to permit portable thread creation.
258*61c4878aSAndroid Build Coastguard WorkerNamely, a reference to the portable ``pw::thread::Options`` base class interface
259*61c4878aSAndroid Build Coastguard Workermust be provided through a header or extern which points to an instantiation in
260*61c4878aSAndroid Build Coastguard Workernon-portable code.
261*61c4878aSAndroid Build Coastguard Worker
262*61c4878aSAndroid Build Coastguard WorkerThis can be most easily done through a facade and set of backends. This approach
263*61c4878aSAndroid Build Coastguard Workercan be powerful; enabling multithreaded unit/integration testing which can run
264*61c4878aSAndroid Build Coastguard Workeron both the host and on a device with the device's exact thread options.
265*61c4878aSAndroid Build Coastguard Worker
266*61c4878aSAndroid Build Coastguard WorkerAlternatively, it can also be be injected at build time by instantiating backend
267*61c4878aSAndroid Build Coastguard Workerspecific build rule which share the same common portable source file(s) but
268*61c4878aSAndroid Build Coastguard Workerselect backend specific source files and/or dependencies which provide the
269*61c4878aSAndroid Build Coastguard Workernon-portable option instantiations.
270*61c4878aSAndroid Build Coastguard Worker
271*61c4878aSAndroid Build Coastguard WorkerAs an example, let's say we want to create a thread on the host and on a device
272*61c4878aSAndroid Build Coastguard Workerrunning FreeRTOS. They could use a facade which contains a ``threads.h`` header
273*61c4878aSAndroid Build Coastguard Workerwith the following contents:
274*61c4878aSAndroid Build Coastguard Worker
275*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
276*61c4878aSAndroid Build Coastguard Worker
277*61c4878aSAndroid Build Coastguard Worker   // Contents of my_app/threads.h
278*61c4878aSAndroid Build Coastguard Worker   #pragma once
279*61c4878aSAndroid Build Coastguard Worker
280*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread/thread.h"
281*61c4878aSAndroid Build Coastguard Worker
282*61c4878aSAndroid Build Coastguard Worker   namespace my_app {
283*61c4878aSAndroid Build Coastguard Worker
284*61c4878aSAndroid Build Coastguard Worker   const pw::thread::Options& HellowWorldThreadOptions();
285*61c4878aSAndroid Build Coastguard Worker
286*61c4878aSAndroid Build Coastguard Worker   }  // namespace my_app
287*61c4878aSAndroid Build Coastguard Worker
288*61c4878aSAndroid Build Coastguard WorkerThis could then be backed by two different backend implementations based on
289*61c4878aSAndroid Build Coastguard Workerthe thread backend. For example for the STL the backend's ``stl_threads.cc``
290*61c4878aSAndroid Build Coastguard Workersource file may look something like:
291*61c4878aSAndroid Build Coastguard Worker
292*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
293*61c4878aSAndroid Build Coastguard Worker
294*61c4878aSAndroid Build Coastguard Worker   // Contents of my_app/stl_threads.cc
295*61c4878aSAndroid Build Coastguard Worker   #include "my_app/threads.h"
296*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread_stl/options.h"
297*61c4878aSAndroid Build Coastguard Worker
298*61c4878aSAndroid Build Coastguard Worker   namespace my_app {
299*61c4878aSAndroid Build Coastguard Worker
300*61c4878aSAndroid Build Coastguard Worker   const pw::thread::Options& HelloWorldThreadOptions() {
301*61c4878aSAndroid Build Coastguard Worker     static constexpr auto options = pw::thread::stl::Options();
302*61c4878aSAndroid Build Coastguard Worker     return options;
303*61c4878aSAndroid Build Coastguard Worker   }
304*61c4878aSAndroid Build Coastguard Worker
305*61c4878aSAndroid Build Coastguard Worker   }  // namespace my_app
306*61c4878aSAndroid Build Coastguard Worker
307*61c4878aSAndroid Build Coastguard WorkerWhile for FreeRTOS the backend's ``freertos_threads.cc`` source file may look
308*61c4878aSAndroid Build Coastguard Workersomething like:
309*61c4878aSAndroid Build Coastguard Worker
310*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
311*61c4878aSAndroid Build Coastguard Worker
312*61c4878aSAndroid Build Coastguard Worker   // Contents of my_app/freertos_threads.cc
313*61c4878aSAndroid Build Coastguard Worker   #include "FreeRTOS.h"
314*61c4878aSAndroid Build Coastguard Worker   #include "my_app/threads.h"
315*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread_freertos/context.h"
316*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread_freertos/options.h"
317*61c4878aSAndroid Build Coastguard Worker   #include "task.h"
318*61c4878aSAndroid Build Coastguard Worker
319*61c4878aSAndroid Build Coastguard Worker   namespace my_app {
320*61c4878aSAndroid Build Coastguard Worker
321*61c4878aSAndroid Build Coastguard Worker   StaticContextWithStack<kHelloWorldStackWords> hello_world_thread_context;
322*61c4878aSAndroid Build Coastguard Worker   const pw::thread::Options& HelloWorldThreadOptions() {
323*61c4878aSAndroid Build Coastguard Worker     static constexpr auto options =
324*61c4878aSAndroid Build Coastguard Worker         pw::thread::freertos::Options()
325*61c4878aSAndroid Build Coastguard Worker             .set_name("HelloWorld")
326*61c4878aSAndroid Build Coastguard Worker             .set_static_context(hello_world_thread_context)
327*61c4878aSAndroid Build Coastguard Worker             .set_priority(kHelloWorldThreadPriority);
328*61c4878aSAndroid Build Coastguard Worker     return options;
329*61c4878aSAndroid Build Coastguard Worker   }
330*61c4878aSAndroid Build Coastguard Worker
331*61c4878aSAndroid Build Coastguard Worker   }  // namespace my_app
332*61c4878aSAndroid Build Coastguard Worker
333*61c4878aSAndroid Build Coastguard Worker.. _module-pw_thread-detaching-joining:
334*61c4878aSAndroid Build Coastguard Worker
335*61c4878aSAndroid Build Coastguard WorkerDetaching & Joining
336*61c4878aSAndroid Build Coastguard Worker===================
337*61c4878aSAndroid Build Coastguard WorkerThe ``Thread::detach()`` API is always available, to let you separate the
338*61c4878aSAndroid Build Coastguard Workerthread of execution from the thread object, allowing execution to continue
339*61c4878aSAndroid Build Coastguard Workerindependently.
340*61c4878aSAndroid Build Coastguard Worker
341*61c4878aSAndroid Build Coastguard WorkerThe joining API, more specifically ``Thread::join()``, is conditionally
342*61c4878aSAndroid Build Coastguard Workeravailable depending on the selected backend for thread creation and how it is
343*61c4878aSAndroid Build Coastguard Workerconfigured. The backend is responsible for providing the
344*61c4878aSAndroid Build Coastguard Worker``PW_THREAD_JOINING_ENABLED`` macro through
345*61c4878aSAndroid Build Coastguard Worker``pw_thread_backend/thread_native.h``. This ensures that any users which include
346*61c4878aSAndroid Build Coastguard Worker``pw_thread/thread.h`` can use this macro if needed.
347*61c4878aSAndroid Build Coastguard Worker
348*61c4878aSAndroid Build Coastguard WorkerPlease see the selected thread creation backend documentation for how to
349*61c4878aSAndroid Build Coastguard Workerenable joining if it's not already enabled by default.
350*61c4878aSAndroid Build Coastguard Worker
351*61c4878aSAndroid Build Coastguard Worker.. Warning::
352*61c4878aSAndroid Build Coastguard Worker  A constructed :cpp:type:`pw::Thread` which represents a thread of execution
353*61c4878aSAndroid Build Coastguard Worker  must be EITHER detached or joined, else the destructor will assert!
354*61c4878aSAndroid Build Coastguard Worker
355*61c4878aSAndroid Build Coastguard WorkerDetachedThread
356*61c4878aSAndroid Build Coastguard Worker==============
357*61c4878aSAndroid Build Coastguard WorkerTo make it slightly easier and cleaner to spawn detached threads without having
358*61c4878aSAndroid Build Coastguard Workerto worry about thread handles, a wrapper ``DetachedThread()`` function is
359*61c4878aSAndroid Build Coastguard Workerprovided which creates a ``Thread`` and immediately detaches it. For example
360*61c4878aSAndroid Build Coastguard Workerinstead of:
361*61c4878aSAndroid Build Coastguard Worker
362*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
363*61c4878aSAndroid Build Coastguard Worker
364*61c4878aSAndroid Build Coastguard Worker   Thread(options, foo).detach();
365*61c4878aSAndroid Build Coastguard Worker
366*61c4878aSAndroid Build Coastguard WorkerYou can instead use this helper wrapper to:
367*61c4878aSAndroid Build Coastguard Worker
368*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
369*61c4878aSAndroid Build Coastguard Worker
370*61c4878aSAndroid Build Coastguard Worker   DetachedThread(options, foo);
371*61c4878aSAndroid Build Coastguard Worker
372*61c4878aSAndroid Build Coastguard WorkerThe arguments are directly forwarded to the Thread constructor and ergo exactly
373*61c4878aSAndroid Build Coastguard Workermatch the Thread constuctor arguments for creating a thread of execution.
374*61c4878aSAndroid Build Coastguard Worker
375*61c4878aSAndroid Build Coastguard Worker
376*61c4878aSAndroid Build Coastguard WorkerThread functions and ThreadCore
377*61c4878aSAndroid Build Coastguard Worker===============================
378*61c4878aSAndroid Build Coastguard WorkerThread functions may be provided using either a ``pw::Function<void()>``
379*61c4878aSAndroid Build Coastguard Worker(which may be a lambda or function pointer) or an implementation of the
380*61c4878aSAndroid Build Coastguard Worker``pw::thread::ThreadCore`` interface.
381*61c4878aSAndroid Build Coastguard Worker
382*61c4878aSAndroid Build Coastguard WorkerTo use the ``pw::Function<void()>`` interface, provide a no-argument,
383*61c4878aSAndroid Build Coastguard Workervoid-returning lambda or other callable:
384*61c4878aSAndroid Build Coastguard Worker
385*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
386*61c4878aSAndroid Build Coastguard Worker
387*61c4878aSAndroid Build Coastguard Worker   Thread thread(options, []() {
388*61c4878aSAndroid Build Coastguard Worker     // do some work in a thread.
389*61c4878aSAndroid Build Coastguard Worker   });
390*61c4878aSAndroid Build Coastguard Worker
391*61c4878aSAndroid Build Coastguard WorkerNote that lambdas can capture up to one pointer-sized argument (or more if
392*61c4878aSAndroid Build Coastguard Workerdynamic allocation is enabled). This can be used to call methods on existing
393*61c4878aSAndroid Build Coastguard Workerobjects (though be sure that the objects' lifetime will outlive the thread,
394*61c4878aSAndroid Build Coastguard Workerand note that synchronization may be needed).
395*61c4878aSAndroid Build Coastguard Worker
396*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
397*61c4878aSAndroid Build Coastguard Worker
398*61c4878aSAndroid Build Coastguard Worker   class Foo {
399*61c4878aSAndroid Build Coastguard Worker    public:
400*61c4878aSAndroid Build Coastguard Worker     void DoBar() {}
401*61c4878aSAndroid Build Coastguard Worker   };
402*61c4878aSAndroid Build Coastguard Worker   Foo foo;
403*61c4878aSAndroid Build Coastguard Worker
404*61c4878aSAndroid Build Coastguard Worker   Thread thread(options, [&foo] {
405*61c4878aSAndroid Build Coastguard Worker     foo.DoBar();
406*61c4878aSAndroid Build Coastguard Worker   });
407*61c4878aSAndroid Build Coastguard Worker
408*61c4878aSAndroid Build Coastguard WorkerAlternatively, you can extend the ``ThreadCore`` class in order to use a more
409*61c4878aSAndroid Build Coastguard Workerexplicit construction. For example:
410*61c4878aSAndroid Build Coastguard Worker
411*61c4878aSAndroid Build Coastguard Worker.. code-block:: cpp
412*61c4878aSAndroid Build Coastguard Worker
413*61c4878aSAndroid Build Coastguard Worker   class Foo : public ThreadCore {
414*61c4878aSAndroid Build Coastguard Worker    private:
415*61c4878aSAndroid Build Coastguard Worker     void Run() override {}
416*61c4878aSAndroid Build Coastguard Worker   };
417*61c4878aSAndroid Build Coastguard Worker   Foo foo;
418*61c4878aSAndroid Build Coastguard Worker
419*61c4878aSAndroid Build Coastguard Worker   // Now create the thread, using foo directly.
420*61c4878aSAndroid Build Coastguard Worker   Thread(options, foo).detach();
421*61c4878aSAndroid Build Coastguard Worker
422*61c4878aSAndroid Build Coastguard Worker.. warning::
423*61c4878aSAndroid Build Coastguard Worker
424*61c4878aSAndroid Build Coastguard Worker   Because the thread may start after the :cpp:type:`pw::Thread` creation, an
425*61c4878aSAndroid Build Coastguard Worker   object which implements the ThreadCore MUST meet or exceed the lifetime of
426*61c4878aSAndroid Build Coastguard Worker   its thread of execution!
427*61c4878aSAndroid Build Coastguard Worker
428*61c4878aSAndroid Build Coastguard Worker-------------------------
429*61c4878aSAndroid Build Coastguard WorkerUnit testing with threads
430*61c4878aSAndroid Build Coastguard Worker-------------------------
431*61c4878aSAndroid Build Coastguard Worker.. doxygenclass:: pw::thread::test::TestThreadContext
432*61c4878aSAndroid Build Coastguard Worker   :members:
433*61c4878aSAndroid Build Coastguard Worker
434*61c4878aSAndroid Build Coastguard WorkerAs an example, the STL :cpp:class:`TestThreadContext` backend implementation in
435*61c4878aSAndroid Build Coastguard Worker``test_thread_context_native.h`` is shown below.
436*61c4878aSAndroid Build Coastguard Worker
437*61c4878aSAndroid Build Coastguard Worker.. literalinclude:: ../pw_thread_stl/public/pw_thread_stl/test_thread_context_native.h
438*61c4878aSAndroid Build Coastguard Worker   :language: cpp
439*61c4878aSAndroid Build Coastguard Worker   :lines: 18-36
440*61c4878aSAndroid Build Coastguard Worker
441*61c4878aSAndroid Build Coastguard Worker----------------
442*61c4878aSAndroid Build Coastguard WorkerThread Iteration
443*61c4878aSAndroid Build Coastguard Worker----------------
444*61c4878aSAndroid Build Coastguard WorkerC++
445*61c4878aSAndroid Build Coastguard Worker===
446*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: Status ForEachThread(const ThreadCallback& cb)
447*61c4878aSAndroid Build Coastguard Worker
448*61c4878aSAndroid Build Coastguard Worker   Calls the provided callback for each thread that has not been joined/deleted.
449*61c4878aSAndroid Build Coastguard Worker
450*61c4878aSAndroid Build Coastguard Worker   This function provides a generalized subset of information that a TCB might
451*61c4878aSAndroid Build Coastguard Worker   contain to make it easier to introspect system state. Depending on the RTOS
452*61c4878aSAndroid Build Coastguard Worker   and its configuration, some of these fields may not be populated, so it is
453*61c4878aSAndroid Build Coastguard Worker   important to check that they have values before attempting to access them.
454*61c4878aSAndroid Build Coastguard Worker
455*61c4878aSAndroid Build Coastguard Worker   **Warning:**  The function may disable the scheduler to perform
456*61c4878aSAndroid Build Coastguard Worker   a runtime capture of thread information.
457*61c4878aSAndroid Build Coastguard Worker
458*61c4878aSAndroid Build Coastguard Worker-----------------------
459*61c4878aSAndroid Build Coastguard WorkerThread Snapshot Service
460*61c4878aSAndroid Build Coastguard Worker-----------------------
461*61c4878aSAndroid Build Coastguard Worker``pw_thread`` offers an optional RPC service library
462*61c4878aSAndroid Build Coastguard Worker(``:thread_snapshot_service``) that enables thread info capture of
463*61c4878aSAndroid Build Coastguard Workerrunning threads on a device at runtime via RPC. The service will guide
464*61c4878aSAndroid Build Coastguard Workeroptimization of stack usage by providing an overview of thread information,
465*61c4878aSAndroid Build Coastguard Workerincluding thread name, stack bounds, and peak stack usage.
466*61c4878aSAndroid Build Coastguard Worker
467*61c4878aSAndroid Build Coastguard Worker``ThreadSnapshotService`` currently supports peak stack usage capture for
468*61c4878aSAndroid Build Coastguard Workerall running threads (``ThreadSnapshotService::GetPeakStackUsage()``) as well as
469*61c4878aSAndroid Build Coastguard Workerfor a specific thread, filtering by name
470*61c4878aSAndroid Build Coastguard Worker(``ThreadSnapshotService::GetPeakStackUsage(name=b"/* thread name */")``).
471*61c4878aSAndroid Build Coastguard WorkerThread information capture relies on the thread iteration facade which will
472*61c4878aSAndroid Build Coastguard Worker**momentarily halt your RTOS**, collect information about running threads, and
473*61c4878aSAndroid Build Coastguard Workerreturn this information through the service.
474*61c4878aSAndroid Build Coastguard Worker
475*61c4878aSAndroid Build Coastguard WorkerRPC service setup
476*61c4878aSAndroid Build Coastguard Worker=================
477*61c4878aSAndroid Build Coastguard WorkerTo expose a ``ThreadSnapshotService`` in your application, do the following:
478*61c4878aSAndroid Build Coastguard Worker
479*61c4878aSAndroid Build Coastguard Worker1. Create an instance of ``pw::thread::proto::ThreadSnapshotServiceBuffer``.
480*61c4878aSAndroid Build Coastguard Worker   This template takes the number of expected threads, and uses it to properly
481*61c4878aSAndroid Build Coastguard Worker   size buffers required for a ``ThreadSnapshotService``. If no thread count
482*61c4878aSAndroid Build Coastguard Worker   argument is provided, this defaults to ``PW_THREAD_MAXIMUM_THREADS``.
483*61c4878aSAndroid Build Coastguard Worker2. Register the service with your RPC server.
484*61c4878aSAndroid Build Coastguard Worker
485*61c4878aSAndroid Build Coastguard WorkerFor example:
486*61c4878aSAndroid Build Coastguard Worker
487*61c4878aSAndroid Build Coastguard Worker.. code-block::
488*61c4878aSAndroid Build Coastguard Worker
489*61c4878aSAndroid Build Coastguard Worker   #include "pw_rpc/server.h"
490*61c4878aSAndroid Build Coastguard Worker   #include "pw_thread/thread_snapshot_service.h"
491*61c4878aSAndroid Build Coastguard Worker
492*61c4878aSAndroid Build Coastguard Worker   // Note: You must customize the RPC server setup; see pw_rpc.
493*61c4878aSAndroid Build Coastguard Worker   pw::rpc::Channel channels[] = {
494*61c4878aSAndroid Build Coastguard Worker    pw::rpc::Channel::Create<1>(&uart_output),
495*61c4878aSAndroid Build Coastguard Worker   };
496*61c4878aSAndroid Build Coastguard Worker   Server server(channels);
497*61c4878aSAndroid Build Coastguard Worker
498*61c4878aSAndroid Build Coastguard Worker  // Thread snapshot service builder instance.
499*61c4878aSAndroid Build Coastguard Worker  pw::thread::proto::ThreadSnapshotServiceBuffer</*num threads*/>
500*61c4878aSAndroid Build Coastguard Worker      thread_snapshot_service;
501*61c4878aSAndroid Build Coastguard Worker
502*61c4878aSAndroid Build Coastguard Worker   void RegisterServices() {
503*61c4878aSAndroid Build Coastguard Worker     server.RegisterService(thread_snapshot_service);
504*61c4878aSAndroid Build Coastguard Worker     // Register other services here.
505*61c4878aSAndroid Build Coastguard Worker   }
506*61c4878aSAndroid Build Coastguard Worker
507*61c4878aSAndroid Build Coastguard Worker   void main() {
508*61c4878aSAndroid Build Coastguard Worker     // ... system initialization ...
509*61c4878aSAndroid Build Coastguard Worker
510*61c4878aSAndroid Build Coastguard Worker     RegisterServices();
511*61c4878aSAndroid Build Coastguard Worker
512*61c4878aSAndroid Build Coastguard Worker     // ... start your application ...
513*61c4878aSAndroid Build Coastguard Worker   }
514*61c4878aSAndroid Build Coastguard Worker
515*61c4878aSAndroid Build Coastguard Worker.. c:macro:: PW_THREAD_MAXIMUM_THREADS
516*61c4878aSAndroid Build Coastguard Worker
517*61c4878aSAndroid Build Coastguard Worker  The max number of threads to use by default for thread snapshot service.
518*61c4878aSAndroid Build Coastguard Worker
519*61c4878aSAndroid Build Coastguard Worker.. cpp:function:: constexpr size_t RequiredServiceBufferSize(const size_t num_threads)
520*61c4878aSAndroid Build Coastguard Worker
521*61c4878aSAndroid Build Coastguard Worker  Function provided through the service to calculate buffer sizing. If no
522*61c4878aSAndroid Build Coastguard Worker  argument ``num_threads`` is specified, the function will take ``num_threads``
523*61c4878aSAndroid Build Coastguard Worker  to be ``PW_THREAD_MAXIMUM_THREADS``.
524*61c4878aSAndroid Build Coastguard Worker
525*61c4878aSAndroid Build Coastguard Worker.. attention::
526*61c4878aSAndroid Build Coastguard Worker    Some platforms may only support limited subsets of this service
527*61c4878aSAndroid Build Coastguard Worker    depending on RTOS configuration. **Ensure that your RTOS is configured
528*61c4878aSAndroid Build Coastguard Worker    properly before using this service.** Please see the thread iteration
529*61c4878aSAndroid Build Coastguard Worker    documentation for your backend for more detail on RTOS support.
530*61c4878aSAndroid Build Coastguard Worker
531*61c4878aSAndroid Build Coastguard Worker-----------------------
532*61c4878aSAndroid Build Coastguard Workerpw_snapshot integration
533*61c4878aSAndroid Build Coastguard Worker-----------------------
534*61c4878aSAndroid Build Coastguard Worker``pw_thread`` provides some light, optional integration with pw_snapshot through
535*61c4878aSAndroid Build Coastguard Workerhelper functions for populating a :cpp:type:`pw::Thread` proto. Some of these
536*61c4878aSAndroid Build Coastguard Workerare directly integrated into the RTOS thread backends to simplify the thread
537*61c4878aSAndroid Build Coastguard Workerstate capturing for snapshots.
538*61c4878aSAndroid Build Coastguard Worker
539*61c4878aSAndroid Build Coastguard WorkerSnapshotStack()
540*61c4878aSAndroid Build Coastguard Worker===============
541*61c4878aSAndroid Build Coastguard WorkerThe ``SnapshotStack()`` helper captures stack metadata (stack pointer and
542*61c4878aSAndroid Build Coastguard Workerbounds) into a :cpp:type:`pw::Thread` proto. After the stack bounds are
543*61c4878aSAndroid Build Coastguard Workercaptured, execution is passed off to the thread stack collection callback to
544*61c4878aSAndroid Build Coastguard Workercapture a backtrace or stack dump. Note that this function does NOT capture the
545*61c4878aSAndroid Build Coastguard Workerthread name: that metadata is only required in cases where a stack overflow or
546*61c4878aSAndroid Build Coastguard Workerunderflow is detected.
547*61c4878aSAndroid Build Coastguard Worker
548*61c4878aSAndroid Build Coastguard WorkerPython processor
549*61c4878aSAndroid Build Coastguard Worker================
550*61c4878aSAndroid Build Coastguard WorkerThreads captured as a Thread proto message can be dumped or further analyzed
551*61c4878aSAndroid Build Coastguard Workerusing using ``pw_thread``'s Python module. This is directly integrated into
552*61c4878aSAndroid Build Coastguard Workerpw_snapshot's processor tool to automatically provide rich thread state dumps.
553*61c4878aSAndroid Build Coastguard Worker
554*61c4878aSAndroid Build Coastguard WorkerThe ``ThreadSnapshotAnalyzer`` class may also be used directly to identify the
555*61c4878aSAndroid Build Coastguard Workercurrently running thread and produce symbolized thread dumps.
556*61c4878aSAndroid Build Coastguard Worker
557*61c4878aSAndroid Build Coastguard Worker.. Warning::
558*61c4878aSAndroid Build Coastguard Worker  Snapshot integration is a work-in-progress and may see significant API
559*61c4878aSAndroid Build Coastguard Worker  changes.
560*61c4878aSAndroid Build Coastguard Worker
561*61c4878aSAndroid Build Coastguard Worker
562*61c4878aSAndroid Build Coastguard Worker.. toctree::
563*61c4878aSAndroid Build Coastguard Worker   :hidden:
564*61c4878aSAndroid Build Coastguard Worker   :maxdepth: 1
565*61c4878aSAndroid Build Coastguard Worker
566*61c4878aSAndroid Build Coastguard Worker   Backends <backends>
567