3#include <cuda_runtime.h>
4#include <cuda/std/expected>
11#include <source_location>
29 static_cast<uint32_t
>(location.line()),
30 static_cast<uint32_t
>(location.column()),
65 std::variant<CudaError, InvalidArgumentError, ResourceError>
kind;
71 [[nodiscard]]
const std::string&
message() const noexcept {
73 [](
const auto& error) ->
const std::string& {
return error.message; },
kind
78 return std::get_if<CudaError>(&
kind);
82 return std::get_if<InvalidArgumentError>(&
kind);
86 return std::get_if<ResourceError>(&
kind);
89 [[nodiscard]]
static Error
90 cuda(cudaError_t code, std::source_location location = std::source_location::current()) {
95 std::format(
"{}: {}", site.to_string(), cudaGetErrorString(code)),
118struct [[nodiscard]]
Result : cuda::std::expected<T, Error> {
119 using cuda::std::expected<T,
Error>::expected;
122 return Result(std::move(value));
126 return Result(cuda::std::unexpect, std::move(error));
131struct [[nodiscard]]
Result<void> : cuda::std::expected<void, Error> {
132 using cuda::std::expected<void,
Error>::expected;
139 return Result(cuda::std::unexpect, std::move(error));
146 std::source_location location = std::source_location::current()
148 if (error == cudaSuccess) {
152 std::fputs(err.
message().c_str(), stderr);
153 std::fputc(
'\n', stderr);
161 return std::move(*result);
170 return cuda::std::unexpected<Error>(
Error{error});
176[[nodiscard]]
inline cuda::std::unexpected<Error>
Err(
Error error) {
177 return cuda::std::unexpected<Error>(std::move(error));
186[[nodiscard]]
inline Result<void>
187cuda_try(cudaError_t error, std::source_location location = std::source_location::current()) {
188 if (error == cudaSuccess) {
195template <std::invocable Operation>
197cuda_try(Operation&& operation, std::source_location location = std::source_location::current()) {
198 using Value = std::invoke_result_t<Operation>;
201 if constexpr (std::is_void_v<Value>) {
202 std::forward<Operation>(operation)();
204 }
else if constexpr (std::is_same_v<Value, cudaError_t>) {
205 return cuda_try(std::forward<Operation>(operation)(), location);
207 return Return::ok(std::forward<Operation>(operation)());
209 }
catch (cuda::cuda_error
const& error) {
210 return Return::err(
Error::cuda(
static_cast<cudaError_t
>(error.status()), location));
211 }
catch (std::bad_alloc
const& error) {
225#define CUDDL_TRY(expr) \
227 auto _cuddl_result = (expr); \
228 if (!_cuddl_result) { \
229 return ::cuddl::detail::propagate_error(_cuddl_result.error()); \
231 ::cuddl::detail::try_unwrap_success(_cuddl_result); \
235#define CUDDL_UNWRAP(expr) \
237 auto _cuddl_result = (expr); \
238 if (!_cuddl_result) { \
239 throw std::runtime_error(_cuddl_result.error().message()); \
241 ::cuddl::detail::try_unwrap_success(_cuddl_result); \
245#define CUDDL_CUDA_ABORT(expr) ::cuddl::cuda_abort_on_error((expr))
248#define CUDDL_CUDA_TRY(...) CUDDL_TRY(::cuddl::cuda_try([&] { return (__VA_ARGS__); }))
T try_unwrap_success(Result< T > &result)
cuda::std::unexpected< Error > propagate_error(const Error &error)
Copies error for propagation (avoids moving out of expected::error()).
Batch operations over contiguous device rows.
Result< void > Ok() noexcept
Success return for Result<void>; same as return {}.
void cuda_abort_on_error(cudaError_t error, std::source_location location=std::source_location::current())
Terminates the process when error is not cudaSuccess (for RAII teardown only).
ErrorCategory
Error category for Result failures.
cuda::std::unexpected< Error > Err(Error error)
Failure return; converts to any Result<T> via cuda::std::unexpected.
Result< void > cuda_try(cudaError_t error, std::source_location location=std::source_location::current())
Checks a CUDA runtime call and returns an error on failure.
CUDA failure payload: status code, call site, and formatted message.
Error payload carried in Result on failure.
static Error cuda(cudaError_t code, std::source_location location=std::source_location::current())
const std::string & message() const noexcept
static Error invalid_argument(std::string message)
std::variant< CudaError, InvalidArgumentError, ResourceError > kind
ErrorCategory category() const noexcept
static Error resource(std::string message)
const InvalidArgumentError * as_invalid_argument() const noexcept
const CudaError * as_cuda() const noexcept
const ResourceError * as_resource() const noexcept
Invalid-argument failure payload.
Resource failure payload: allocation, I/O, or capacity errors.
static Result err(Error error)
Fallible API result: cuda::std::expected<T, Error> with cuDDL factories.
static Result err(Error error)
static Result ok(T value)
File, line, and column for a C++ call site or FASTX input position.
static SourceLocation from(std::source_location location)
std::string to_string() const