I would like to write a c++ function like this:
#include <system_error>
std::errc f() { return std::errc::success; }
But I can't understand how to return a successful value (0 in this case) using std::errc 'enum class' type. The one way i see is to return int:
template <typename E>
constexpr typename std::underlying_type<E>::type to_underlying(E e) {
return static_cast<typename std::underlying_type<E>::type>(e);
}
int f() { is_succ() ? 0 : to_underlying(err); }
But it looks ugly for me. Is where a standard way to return a C-oriented success/error code from a function in a std c++ 0x14?
PS. I'm using MS VC 2015 Patch 2.
You can do it like this:
#include <system_error>
std::errc f() { return std::errc(); }
int main()
{
std::errc x = f();
if (x == std::errc())
{
// success
}
}
std::errc()
(0) is a valid enumeration value even though it does not appear in the enumerator list, which start at 1. It represents success.
For comparison, have a look at std::to_chars, which returns a
struct to_chars_result {
char* ptr;
std::errc ec;
}
You generally don't return a std::errc
value from a function directly. Instead, you return a std::error_code
. For example, your function would be declared like this:
std::error_code f();
You then compare the result of that function against the std::errc values. For example:
std::error_code error = f();
if (error == std::errc::no_such_file_or_directory)
{
// deal with the error
}
std::error_code
is contextually convertible bool. The way you test if a function succeeded is by using the error code in a boolean expression. For example:
std::error_code error = f();
if (error)
{
// the function failed...
}
To return success from such a function, you return a default initialized std::error_code
. For example:
std::error_code f()
{
// do stuff...
return std::error_code{}; // success!
}
This approach works well when you're consuming a C-style API. Your wrapper would construct std::error_code
objects using the integer values returned by the API and a custom std::error_category
that defines how to translate those errors into std::errc
values.
The opposite doesn't work, however. If you're writing a C wrapper for a C++ library, then you have to do things the C way. Define an enum
with your error values and return those values from your C entry points.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With