From d003e940765e8c8a677619d2d6b9666374399071 Mon Sep 17 00:00:00 2001 From: mutouyun Date: Sun, 30 Oct 2022 15:21:45 +0800 Subject: [PATCH] add: [imp] sys::error object --- include/libimp/system.h | 32 ++++++++++++++++++++++++++++++++ src/libimp/system.cpp | 37 +++++++++++++++++++++++++++++++++++++ test/test_imp_system.cpp | 21 ++++++++++++++------- 3 files changed, 83 insertions(+), 7 deletions(-) diff --git a/include/libimp/system.h b/include/libimp/system.h index ceba407..60d0d37 100644 --- a/include/libimp/system.h +++ b/include/libimp/system.h @@ -7,6 +7,7 @@ #pragma once #include +#include // std::ostream #include #include "libimp/def.h" @@ -32,6 +33,28 @@ LIBIMP_EXPORT std::string error_str(result_code) noexcept; */ LIBIMP_EXPORT std::string error_msg(result_code) noexcept; +/** + * @brief The system error object. + */ +class LIBIMP_EXPORT error { + result_code r_code_; + +public: + explicit error() noexcept; + explicit error(result_code rc) noexcept; + + result_code code() const noexcept; + std::uint64_t value() const noexcept; + explicit operator bool() const noexcept; + + std::string str() const noexcept; + + friend bool operator==(error const &lhs, error const &rhs) noexcept; + friend bool operator!=(error const &lhs, error const &rhs) noexcept; + + friend std::ostream &operator<<(std::ostream &o, error const &e); +}; + /** * @brief Get system configuration information at run time */ @@ -42,3 +65,12 @@ LIBIMP_EXPORT std::int64_t conf(info) noexcept; } // namespace sys LIBIMP_NAMESPACE_END_ + +template <> +struct fmt::formatter<::LIBIMP_::sys::error> + : formatter { + template + auto format(::LIBIMP_::sys::error r, FormatContext &ctx) { + return format_to(ctx.out(), "{}", ::LIBIMP_::sys::error_msg(r.code())); + } +}; diff --git a/src/libimp/system.cpp b/src/libimp/system.cpp index 94e56bc..958d2cd 100644 --- a/src/libimp/system.cpp +++ b/src/libimp/system.cpp @@ -18,5 +18,42 @@ std::string error_msg(result_code code) noexcept { } } +/// @brief The system error object. + +error::error() noexcept + : error(error_code()) {} + +error::error(result_code rc) noexcept + : r_code_(rc) {} + +result_code error::code() const noexcept { + return r_code_; +} + +std::uint64_t error::value() const noexcept { + return r_code_.value(); +} + +error::operator bool() const noexcept { + return !!r_code_; +} + +std::string error::str() const noexcept { + return error_str(r_code_); +} + +bool operator==(error const &lhs, error const &rhs) noexcept { + return lhs.code() == rhs.code(); +} + +bool operator!=(error const &lhs, error const &rhs) noexcept { + return lhs.code() != rhs.code(); +} + +std::ostream &operator<<(std::ostream &o, error const &e) { + o << error_msg(e.code()); + return o; +} + } // namespace sys LIBIMP_NAMESPACE_END_ diff --git a/test/test_imp_system.cpp b/test/test_imp_system.cpp index 7b85fc4..a6a6bcd 100644 --- a/test/test_imp_system.cpp +++ b/test/test_imp_system.cpp @@ -1,5 +1,6 @@  #include +#include #include "gtest/gtest.h" #include "fmt/format.h" @@ -14,8 +15,6 @@ #endif TEST(system, error_code) { - std::cout << fmt::format("{}\n", imp::sys::error_msg(imp::sys::error_code())); - imp::sys::error_code({false, 111}); auto err = imp::sys::error_code(); EXPECT_FALSE(err); @@ -23,20 +22,28 @@ TEST(system, error_code) { imp::sys::error_code({}); EXPECT_TRUE(imp::sys::error_code()); + + imp::sys::error e_obj {err}; + EXPECT_EQ(err.value(), e_obj.value()); + auto e_msg = fmt::format("{}", imp::sys::error_msg(imp::sys::error_code())); + std::stringstream ss; + ss << imp::sys::error{}; + EXPECT_EQ(e_msg, ss.str()); + std::cout << e_msg << "\n"; } TEST(system, error_str) { #if defined(LIBIMP_OS_WIN) - std::u16string u16_ok, u16_err; + std::wstring u16_ok, u16_err; LANGID lId = ::GetSystemDefaultLangID(); switch (lId) { case 0x0804: - u16_ok = u"操作成功完成。\r\n"; - u16_err = u"句柄无效。\r\n"; + u16_ok = L"操作成功完成。\r\n"; + u16_err = L"句柄无效。\r\n"; break; case 0x0409: - u16_ok = u"The operation completed successfully.\r\n"; - u16_err = u"The handle is invalid.\r\n"; + u16_ok = L"The operation completed successfully.\r\n"; + u16_err = L"The handle is invalid.\r\n"; break; default: return;