mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-11-11 14:38:29 +01:00
Replace non-threadsafe strerror
Log the name of the error as well as the error code if a network problem happens. This makes network troubleshooting more convenient. Use thread-safe strerror_r and the WIN32 equivalent FormatMessage.
This commit is contained in:
@@ -361,7 +361,7 @@ bool static ConnectSocketDirectly(const CService &addrConnect, SOCKET& hSocketRe
|
||||
}
|
||||
if (nRet == SOCKET_ERROR)
|
||||
{
|
||||
LogPrintf("select() for %s failed: %i\n", addrConnect.ToString(), WSAGetLastError());
|
||||
LogPrintf("select() for %s failed: %s\n", addrConnect.ToString(), NetworkErrorString(WSAGetLastError()));
|
||||
closesocket(hSocket);
|
||||
return false;
|
||||
}
|
||||
@@ -372,13 +372,13 @@ bool static ConnectSocketDirectly(const CService &addrConnect, SOCKET& hSocketRe
|
||||
if (getsockopt(hSocket, SOL_SOCKET, SO_ERROR, &nRet, &nRetSize) == SOCKET_ERROR)
|
||||
#endif
|
||||
{
|
||||
LogPrintf("getsockopt() for %s failed: %i\n", addrConnect.ToString(), WSAGetLastError());
|
||||
LogPrintf("getsockopt() for %s failed: %s\n", addrConnect.ToString(), NetworkErrorString(WSAGetLastError()));
|
||||
closesocket(hSocket);
|
||||
return false;
|
||||
}
|
||||
if (nRet != 0)
|
||||
{
|
||||
LogPrintf("connect() to %s failed after select(): %s\n", addrConnect.ToString(), strerror(nRet));
|
||||
LogPrintf("connect() to %s failed after select(): %s\n", addrConnect.ToString(), NetworkErrorString(nRet));
|
||||
closesocket(hSocket);
|
||||
return false;
|
||||
}
|
||||
@@ -389,7 +389,7 @@ bool static ConnectSocketDirectly(const CService &addrConnect, SOCKET& hSocketRe
|
||||
else
|
||||
#endif
|
||||
{
|
||||
LogPrintf("connect() to %s failed: %i\n", addrConnect.ToString(), WSAGetLastError());
|
||||
LogPrintf("connect() to %s failed: %s\n", addrConnect.ToString(), NetworkErrorString(WSAGetLastError()));
|
||||
closesocket(hSocket);
|
||||
return false;
|
||||
}
|
||||
@@ -1237,3 +1237,36 @@ bool operator!=(const CSubNet& a, const CSubNet& b)
|
||||
{
|
||||
return !(a==b);
|
||||
}
|
||||
|
||||
#ifdef WIN32
|
||||
std::string NetworkErrorString(int err)
|
||||
{
|
||||
char buf[256];
|
||||
buf[0] = 0;
|
||||
if(FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS | FORMAT_MESSAGE_MAX_WIDTH_MASK,
|
||||
NULL, err, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
|
||||
buf, sizeof(buf), NULL))
|
||||
{
|
||||
return strprintf("%s (%d)", buf, err);
|
||||
}
|
||||
else
|
||||
{
|
||||
return strprintf("Unknown error (%d)", err);
|
||||
}
|
||||
}
|
||||
#else
|
||||
std::string NetworkErrorString(int err)
|
||||
{
|
||||
char buf[256];
|
||||
const char *s = buf;
|
||||
buf[0] = 0;
|
||||
/* Too bad there are two incompatible implementations of the
|
||||
* thread-safe strerror. */
|
||||
#ifdef STRERROR_R_CHAR_P /* GNU variant can return a pointer outside the passed buffer */
|
||||
s = strerror_r(err, buf, sizeof(buf));
|
||||
#else /* POSIX variant always returns message in buffer */
|
||||
(void) strerror_r(err, buf, sizeof(buf));
|
||||
#endif
|
||||
return strprintf("%s (%d)", s, err);
|
||||
}
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user