mirror of
https://fuchsia.googlesource.com/third_party/pigweed.googlesource.com/pigweed/pigweed
synced 2024-09-18 21:00:07 +00:00
pw_async2: Move PW_CO_TRY functions
Change-Id: I9d35803370e5294bcd411e2124db99a01e17a544 Reviewed-on: https://pigweed-review.googlesource.com/c/pigweed/pigweed/+/209911 Commit-Queue: Taylor Cramer <cramertj@google.com> Lint: Lint 🤖 <android-build-ayeaye@system.gserviceaccount.com> Reviewed-by: Wyatt Hepler <hepler@google.com>
This commit is contained in:
parent
d1841fd3dd
commit
dcbe39839b
|
@ -243,6 +243,7 @@ _doxygen_input_files = [ # keep-sorted: start
|
||||||
"$dir_pw_spi/public/pw_spi/chip_selector.h",
|
"$dir_pw_spi/public/pw_spi/chip_selector.h",
|
||||||
"$dir_pw_spi/public/pw_spi/chip_selector_digital_out.h",
|
"$dir_pw_spi/public/pw_spi/chip_selector_digital_out.h",
|
||||||
"$dir_pw_status/public/pw_status/status.h",
|
"$dir_pw_status/public/pw_status/status.h",
|
||||||
|
"$dir_pw_status/public/pw_status/try.h",
|
||||||
"$dir_pw_stream/public/pw_stream/stream.h",
|
"$dir_pw_stream/public/pw_stream/stream.h",
|
||||||
"$dir_pw_stream_uart_linux/public/pw_stream_uart_linux/stream.h",
|
"$dir_pw_stream_uart_linux/public/pw_stream_uart_linux/stream.h",
|
||||||
"$dir_pw_string/public/pw_string/format.h",
|
"$dir_pw_string/public/pw_string/format.h",
|
||||||
|
|
|
@ -16,10 +16,10 @@ pw_async2
|
||||||
like other tasks, and can easily plug into an existing ``pw_async2``
|
like other tasks, and can easily plug into an existing ``pw_async2``
|
||||||
systems.
|
systems.
|
||||||
|
|
||||||
:cpp:type:`pw::async2::Task` is Pigweed's async primitive. ``Task`` objects
|
:cpp:class:`pw::async2::Task` is Pigweed's async primitive. ``Task`` objects
|
||||||
are cooperatively-scheduled "threads" which yield to the ``Dispatcher``
|
are cooperatively-scheduled "threads" which yield to the
|
||||||
when waiting. When the ``Task`` is able to make progress, the ``Dispatcher``
|
:cpp:class:`pw::async2::Dispatcher` when waiting. When the ``Task`` is able to make
|
||||||
will run it again. For example:
|
progress, the ``Dispatcher`` will run it again. For example:
|
||||||
|
|
||||||
.. code-block:: cpp
|
.. code-block:: cpp
|
||||||
|
|
||||||
|
@ -82,8 +82,8 @@ will run it again. For example:
|
||||||
std::optional<SendFuture> send_future_ = std::nullopt;
|
std::optional<SendFuture> send_future_ = std::nullopt;
|
||||||
};
|
};
|
||||||
|
|
||||||
Tasks can then be run on a ``Dispatcher`` using the ``Dispatcher::Post``
|
Tasks can then be run on a :cpp:class:`pw::async2::Dispatcher` using the
|
||||||
method:
|
:cpp:func:`pw::async2::Dispatcher::Post` method:
|
||||||
|
|
||||||
.. code-block:: cpp
|
.. code-block:: cpp
|
||||||
|
|
||||||
|
@ -108,6 +108,18 @@ C++20 users can also define tasks using coroutines!
|
||||||
:start-after: [pw_async2-examples-coro-injection]
|
:start-after: [pw_async2-examples-coro-injection]
|
||||||
:end-before: [pw_async2-examples-coro-injection]
|
:end-before: [pw_async2-examples-coro-injection]
|
||||||
|
|
||||||
|
Any value with a ``Poll<T> Pend(Context&)`` method can be passed to
|
||||||
|
``co_await``, which will return with a ``T`` when the result is ready.
|
||||||
|
|
||||||
|
To return from a coroutine, ``co_return <expression>`` must be used instead of
|
||||||
|
the usual ``return <expression>`` syntax. Because of this, the
|
||||||
|
:c:macro:`PW_TRY` and :c:macro:`PW_TRY_ASSIGN` macros are not usable within
|
||||||
|
coroutines. :c:macro:`PW_CO_TRY` and :c:macro:`PW_CO_TRY_ASSIGN` should be
|
||||||
|
used instead.
|
||||||
|
|
||||||
|
For a more detailed explanation of Pigweed's coroutine support, see the
|
||||||
|
documentation on the :cpp:class:`pw::async2::Coro<T>` type.
|
||||||
|
|
||||||
-----------------
|
-----------------
|
||||||
C++ API reference
|
C++ API reference
|
||||||
-----------------
|
-----------------
|
||||||
|
@ -137,6 +149,9 @@ C++ API reference
|
||||||
.. doxygenclass:: pw::async2::Coro
|
.. doxygenclass:: pw::async2::Coro
|
||||||
:members:
|
:members:
|
||||||
|
|
||||||
|
.. doxygenclass:: pw::async2::CoroContext
|
||||||
|
:members:
|
||||||
|
|
||||||
-------------
|
-------------
|
||||||
C++ Utilities
|
C++ Utilities
|
||||||
-------------
|
-------------
|
||||||
|
|
|
@ -496,32 +496,3 @@ Coro<T> CoroPromiseType<T>::get_return_object_on_allocation_failure() {
|
||||||
|
|
||||||
} // namespace internal
|
} // namespace internal
|
||||||
} // namespace pw::async2
|
} // namespace pw::async2
|
||||||
|
|
||||||
/// Like `PW_TRY`, but using `co_return` instead of early `return`.
|
|
||||||
///
|
|
||||||
/// This is necessary because only `co_return` can be used inside of a
|
|
||||||
/// coroutine, and there is no way to detect whether particular code is running
|
|
||||||
/// within a coroutine or not.
|
|
||||||
#define PW_CO_TRY(expr) _PW_CO_TRY(_PW_TRY_UNIQUE(__LINE__), expr)
|
|
||||||
|
|
||||||
#define _PW_CO_TRY(result, expr) \
|
|
||||||
do { \
|
|
||||||
if (auto result = (expr); !result.ok()) { \
|
|
||||||
co_return ::pw::internal::ConvertToStatus(result); \
|
|
||||||
} \
|
|
||||||
} while (0)
|
|
||||||
|
|
||||||
/// Like `PW_TRY_ASSIGN`, but using `co_return` instead of early `return`.
|
|
||||||
///
|
|
||||||
/// This is necessary because only `co_return` can be used inside of a
|
|
||||||
/// coroutine, and there is no way to detect whether particular code is running
|
|
||||||
/// within a coroutine or not.
|
|
||||||
#define PW_CO_TRY_ASSIGN(assignment_lhs, expression) \
|
|
||||||
_PW_CO_TRY_ASSIGN(_PW_TRY_UNIQUE(__LINE__), assignment_lhs, expression)
|
|
||||||
|
|
||||||
#define _PW_CO_TRY_ASSIGN(result, lhs, expr) \
|
|
||||||
auto result = (expr); \
|
|
||||||
if (!result.ok()) { \
|
|
||||||
co_return ::pw::internal::ConvertToStatus(result); \
|
|
||||||
} \
|
|
||||||
lhs = ::pw::internal::ConvertToValue(result);
|
|
||||||
|
|
|
@ -20,6 +20,8 @@
|
||||||
|
|
||||||
// Macros for cleanly working with Status or StatusWithSize objects in functions
|
// Macros for cleanly working with Status or StatusWithSize objects in functions
|
||||||
// that return Status.
|
// that return Status.
|
||||||
|
|
||||||
|
/// Returns early if \a expr is a non-OK `Status` or `Result`.
|
||||||
#define PW_TRY(expr) _PW_TRY(_PW_TRY_UNIQUE(__LINE__), expr)
|
#define PW_TRY(expr) _PW_TRY(_PW_TRY_UNIQUE(__LINE__), expr)
|
||||||
|
|
||||||
#define _PW_TRY(result, expr) \
|
#define _PW_TRY(result, expr) \
|
||||||
|
@ -29,8 +31,10 @@
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define PW_TRY_ASSIGN(assignment_lhs, expression) \
|
/// Returns early if \a expression is a non-OK `Result`.
|
||||||
_PW_TRY_ASSIGN(_PW_TRY_UNIQUE(__LINE__), assignment_lhs, expression)
|
/// If \a expression is okay, assigns the inner value to \a lhs.
|
||||||
|
#define PW_TRY_ASSIGN(lhs, expression) \
|
||||||
|
_PW_TRY_ASSIGN(_PW_TRY_UNIQUE(__LINE__), lhs, expression)
|
||||||
|
|
||||||
#define _PW_TRY_ASSIGN(result, lhs, expr) \
|
#define _PW_TRY_ASSIGN(result, lhs, expr) \
|
||||||
auto result = (expr); \
|
auto result = (expr); \
|
||||||
|
@ -39,8 +43,9 @@
|
||||||
} \
|
} \
|
||||||
lhs = ::pw::internal::ConvertToValue(result);
|
lhs = ::pw::internal::ConvertToValue(result);
|
||||||
|
|
||||||
// Macro for cleanly working with Status or StatusWithSize objects in functions
|
/// Returns early if \a expr is a non-OK `Status` or `StatusWithSize`.
|
||||||
// that return StatusWithSize.
|
///
|
||||||
|
/// This is designed for use in functions that return a `StatusWithSize`.
|
||||||
#define PW_TRY_WITH_SIZE(expr) _PW_TRY_WITH_SIZE(_PW_TRY_UNIQUE(__LINE__), expr)
|
#define PW_TRY_WITH_SIZE(expr) _PW_TRY_WITH_SIZE(_PW_TRY_UNIQUE(__LINE__), expr)
|
||||||
|
|
||||||
#define _PW_TRY_WITH_SIZE(result, expr) \
|
#define _PW_TRY_WITH_SIZE(result, expr) \
|
||||||
|
@ -53,6 +58,35 @@
|
||||||
#define _PW_TRY_UNIQUE(line) _PW_TRY_UNIQUE_EXPANDED(line)
|
#define _PW_TRY_UNIQUE(line) _PW_TRY_UNIQUE_EXPANDED(line)
|
||||||
#define _PW_TRY_UNIQUE_EXPANDED(line) _pw_try_unique_name_##line
|
#define _PW_TRY_UNIQUE_EXPANDED(line) _pw_try_unique_name_##line
|
||||||
|
|
||||||
|
/// Like `PW_TRY`, but using `co_return` instead of early `return`.
|
||||||
|
///
|
||||||
|
/// This is necessary because only `co_return` can be used inside of a
|
||||||
|
/// coroutine, and there is no way to detect whether particular code is running
|
||||||
|
/// within a coroutine or not.
|
||||||
|
#define PW_CO_TRY(expr) _PW_CO_TRY(_PW_TRY_UNIQUE(__LINE__), expr)
|
||||||
|
|
||||||
|
#define _PW_CO_TRY(result, expr) \
|
||||||
|
do { \
|
||||||
|
if (auto result = (expr); !result.ok()) { \
|
||||||
|
co_return ::pw::internal::ConvertToStatus(result); \
|
||||||
|
} \
|
||||||
|
} while (0)
|
||||||
|
|
||||||
|
/// Like `PW_TRY_ASSIGN`, but using `co_return` instead of early `return`.
|
||||||
|
///
|
||||||
|
/// This is necessary because only `co_return` can be used inside of a
|
||||||
|
/// coroutine, and there is no way to detect whether particular code is running
|
||||||
|
/// within a coroutine or not.
|
||||||
|
#define PW_CO_TRY_ASSIGN(lhs, expression) \
|
||||||
|
_PW_CO_TRY_ASSIGN(_PW_TRY_UNIQUE(__LINE__), lhs, expression)
|
||||||
|
|
||||||
|
#define _PW_CO_TRY_ASSIGN(result, lhs, expr) \
|
||||||
|
auto result = (expr); \
|
||||||
|
if (!result.ok()) { \
|
||||||
|
co_return ::pw::internal::ConvertToStatus(result); \
|
||||||
|
} \
|
||||||
|
lhs = ::pw::internal::ConvertToValue(result);
|
||||||
|
|
||||||
namespace pw::internal {
|
namespace pw::internal {
|
||||||
|
|
||||||
constexpr Status ConvertToStatus(Status status) { return status; }
|
constexpr Status ConvertToStatus(Status status) { return status; }
|
||||||
|
|
|
@ -373,6 +373,12 @@ C++ API
|
||||||
``PW_STATUS_``. For example, ``PW_STATUS_DATA_LOSS`` corresponds with
|
``PW_STATUS_``. For example, ``PW_STATUS_DATA_LOSS`` corresponds with
|
||||||
:c:enumerator:`DATA_LOSS`.
|
:c:enumerator:`DATA_LOSS`.
|
||||||
|
|
||||||
|
.. doxygendefine:: PW_TRY
|
||||||
|
.. doxygendefine:: PW_TRY_ASSIGN
|
||||||
|
.. doxygendefine:: PW_TRY_WITH_SIZE
|
||||||
|
.. doxygendefine:: PW_CO_TRY
|
||||||
|
.. doxygendefine:: PW_CO_TRY_ASSIGN
|
||||||
|
|
||||||
Unused result warnings
|
Unused result warnings
|
||||||
----------------------
|
----------------------
|
||||||
If the ``PW_STATUS_CFG_CHECK_IF_USED`` option is enabled, ``pw::Status`` objects
|
If the ``PW_STATUS_CFG_CHECK_IF_USED`` option is enabled, ``pw::Status`` objects
|
||||||
|
|
Loading…
Reference in New Issue
Block a user