Skip to content

Commit

Permalink
Merge pull request #12043 from sepalani/strerror
Browse files Browse the repository at this point in the history
Common: Add a strerror_r wrapper
  • Loading branch information
AdmiralCurtiss committed Jul 16, 2023
2 parents 7f40c6f + cbb76c1 commit d867e2b
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 25 deletions.
38 changes: 23 additions & 15 deletions Source/Core/Common/CommonFuncs.cpp
Expand Up @@ -17,27 +17,35 @@ namespace Common
{
constexpr size_t BUFFER_SIZE = 256;

// There are two variants of strerror_r. The XSI version stores the message to the passed-in
// buffer and returns an int (0 on success). The GNU version returns a pointer to the message,
// which might have been stored in the passed-in buffer or might be a static string.
//
// This function might change the errno value.
//
// References:
// https://www.gnu.org/software/gnulib/manual/html_node/strerror_005fr.html
// https://pubs.opengroup.org/onlinepubs/9699919799/functions/strerror_r.html
// https://refspecs.linuxbase.org/LSB_5.0.0/LSB-Core-generic/LSB-Core-generic/baselib-strerror-r.html
const char* StrErrorWrapper(int error, char* buffer, std::size_t length)
{
// We check defines in order to figure out which variant is in use.
#if (defined(__GLIBC__) || __ANDROID_API__ >= 23) && \
(_GNU_SOURCE || (_POSIX_C_SOURCE < 200112L && _XOPEN_SOURCE < 600))
return strerror_r(error, buffer, length);
#else
const int error_code = strerror_r(error, buffer, length);
return error_code == 0 ? buffer : "";
#endif
}

// Wrapper function to get last strerror(errno) string.
// This function might change the error code.
std::string LastStrerrorString()
{
char error_message[BUFFER_SIZE];

// There are two variants of strerror_r. The XSI version stores the message to the passed-in
// buffer and returns an int (0 on success). The GNU version returns a pointer to the message,
// which might have been stored in the passed-in buffer or might be a static string.

// We check defines in order to figure out variant is in use, and we store the returned value
// to a variable so that we'll get a compile-time check that our assumption was correct.

#if (defined(__GLIBC__) || __ANDROID_API__ >= 23) && \
(_GNU_SOURCE || (_POSIX_C_SOURCE < 200112L && _XOPEN_SOURCE < 600))
const char* str = strerror_r(errno, error_message, BUFFER_SIZE);
return std::string(str);
#else
int error_code = strerror_r(errno, error_message, BUFFER_SIZE);
return error_code == 0 ? std::string(error_message) : "";
#endif
return StrErrorWrapper(errno, error_message, BUFFER_SIZE);
}

#ifdef _WIN32
Expand Down
3 changes: 3 additions & 0 deletions Source/Core/Common/CommonFuncs.h
Expand Up @@ -41,6 +41,9 @@ __declspec(dllimport) void __stdcall DebugBreak(void);

namespace Common
{
// strerror_r wrapper to handle XSI and GNU versions.
const char* StrErrorWrapper(int error, char* buffer, std::size_t length);

// Wrapper function to get last strerror(errno) string.
// This function might change the error code.
std::string LastStrerrorString();
Expand Down
12 changes: 2 additions & 10 deletions Source/Core/Common/Network.cpp
Expand Up @@ -19,6 +19,7 @@
#include <fmt/format.h>

#include "Common/BitUtils.h"
#include "Common/CommonFuncs.h"
#include "Common/Random.h"
#include "Common/StringUtil.h"

Expand Down Expand Up @@ -551,23 +552,14 @@ const char* DecodeNetworkError(s32 error_code)
{
thread_local char buffer[1024];

#if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(ANDROID) || \
defined(__APPLE__)
#define IS_BSD_STRERROR
#endif

#ifdef _WIN32
FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS |
FORMAT_MESSAGE_MAX_WIDTH_MASK,
nullptr, error_code, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), buffer,
sizeof(buffer), nullptr);
return buffer;
#elif defined(IS_BSD_STRERROR) || \
((_POSIX_C_SOURCE >= 200112L || _XOPEN_SOURCE >= 600) && !_GNU_SOURCE)
strerror_r(error_code, buffer, sizeof(buffer));
return buffer;
#else
return strerror_r(error_code, buffer, sizeof(buffer));
return Common::StrErrorWrapper(error_code, buffer, sizeof(buffer));
#endif
}

Expand Down

0 comments on commit d867e2b

Please sign in to comment.