Misc fixes in error handling.

This commit is contained in:
Vincent Richard 2016-03-25 21:50:35 +01:00
parent fed1469ade
commit 08a3ba2ba1
3 changed files with 65 additions and 17 deletions

View File

@ -978,6 +978,8 @@ CHECK_SYMBOL_EXISTS(SYS_gettid sys/syscall.h VMIME_HAVE_SYSCALL_GETTID)
CHECK_SYMBOL_EXISTS(SO_KEEPALIVE sys/socket.h VMIME_HAVE_SO_KEEPALIVE)
CHECK_SYMBOL_EXISTS(strerror_r string.h VMIME_HAVE_STRERROR_R)
FIND_PACKAGE(Threads)
IF(VMIME_BUILD_SHARED_LIBRARY)

View File

@ -84,6 +84,7 @@ typedef unsigned @VMIME_64BIT_TYPE@ vmime_uint64;
#cmakedefine01 VMIME_HAVE_GMTIME_R
#cmakedefine01 VMIME_HAVE_LOCALTIME_S
#cmakedefine01 VMIME_HAVE_LOCALTIME_R
#cmakedefine01 VMIME_HAVE_STRERROR_R
#cmakedefine01 VMIME_HAVE_MLANG
#cmakedefine01 VMIME_HAVE_SO_KEEPALIVE
#cmakedefine01 VMIME_SHARED_PTR_USE_CXX

View File

@ -421,10 +421,28 @@ void posixSocket::resolve(struct ::addrinfo** addrInfo, const vmime::string& add
}
}
else if (gaiError != EAI_AGAIN)
{
if (gaiError == EAI_SYSTEM)
{
if (errno != 0)
{
try
{
throwSocketError(errno);
}
catch (exceptions::socket_exception& e)
{
throw vmime::exceptions::connection_error
("Error while connecting socket.", e);
}
}
}
else
{
throw vmime::exceptions::connection_error
("gai_suspend() failed: " + std::string(gai_strerror(gaiError)));
}
}
// Check for timeout
if (m_timeoutHandler && m_timeoutHandler->isTimeOut())
@ -797,7 +815,7 @@ size_t posixSocket::sendRawNonBlocking(const byte_t* buffer, const size_t count)
void posixSocket::throwSocketError(const int err)
{
string msg;
const char* msg = NULL;
switch (err)
{
@ -815,20 +833,47 @@ void posixSocket::throwSocketError(const int err)
case EMSGSIZE: msg = "EMSGSIZE: message cannot be sent atomically"; break;
case ENOBUFS: msg = "ENOBUFS: output queue is full"; break;
case ENOMEM: msg = "ENOMEM: out of memory"; break;
case EPIPE:
case EPIPE: msg = "EPIPE: broken pipe"; break;
case ENOTCONN: msg = "ENOTCONN: not connected"; break;
case ECONNREFUSED: msg = "ECONNREFUSED: connection refused"; break;
default:
std::ostringstream oss;
oss << ::strerror(err);
msg = oss.str();
break;
}
if (msg)
{
throw exceptions::socket_exception(msg);
}
else
{
// Use strerror() to get string describing error number
#if VMIME_HAVE_STRERROR_R
char errbuf[512];
#if (_POSIX_C_SOURCE >= 200112L || _XOPEN_SOURCE >= 600) && ! _GNU_SOURCE
// XSI-compliant strerror_r()
strerror_r(err, errbuf, sizeof(errbuf));
throw exceptions::socket_exception(errbuf);
#else
// GNU-specific strerror_r()
const std::string strmsg(strerror_r(err, errbuf, sizeof(errbuf)));
throw exceptions::socket_exception(strmsg);
#endif
#else // !VMIME_HAVE_STRERROR_R
const std::string strmsg(strerror(err));
throw exceptions::socket_exception(strmsg);
#endif // VMIME_HAVE_STRERROR_R
}
}
unsigned int posixSocket::getStatus() const