diff options
Diffstat (limited to '3rdparty/openpgm-svn-r1085/pgm/error.c')
-rw-r--r-- | 3rdparty/openpgm-svn-r1085/pgm/error.c | 518 |
1 files changed, 518 insertions, 0 deletions
diff --git a/3rdparty/openpgm-svn-r1085/pgm/error.c b/3rdparty/openpgm-svn-r1085/pgm/error.c new file mode 100644 index 0000000..3f3fe30 --- /dev/null +++ b/3rdparty/openpgm-svn-r1085/pgm/error.c @@ -0,0 +1,518 @@ +/* vim:ts=8:sts=8:sw=4:noai:noexpandtab + * + * portable error reporting. + * + * Copyright (c) 2010 Miru Limited. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#ifndef _WIN32 +# include <netdb.h> +#endif +#include <impl/i18n.h> +#include <impl/framework.h> + + +//#define ERROR_DEBUG + + +#define ERROR_OVERWRITTEN_WARNING "pgm_error_t set over the top of a previous pgm_error_t or uninitialized memory.\n" \ + "This indicates a bug. You must ensure an error is NULL before it's set.\n" \ + "The overwriting error message was: %s" + +static pgm_error_t* pgm_error_new_valist (const int, const int, const char*, va_list) PGM_GNUC_PRINTF(3, 0); +static void pgm_error_add_prefix (char**restrict, const char*restrict, va_list) PGM_GNUC_PRINTF(2, 0); + + +static +pgm_error_t* +pgm_error_new_valist ( + const int error_domain, + const int error_code, + const char* format, + va_list args + ) +{ + pgm_error_t *error = pgm_new (pgm_error_t, 1); + error->domain = error_domain; + error->code = error_code; + error->message = pgm_strdup_vprintf (format, args); + return error; +} + +void +pgm_error_free ( + pgm_error_t* error + ) +{ + pgm_return_if_fail (error != NULL); + pgm_free (error->message); + pgm_free (error); +} + +void +pgm_set_error ( + pgm_error_t** restrict err, + const int error_domain, + const int error_code, + const char* restrict format, + ... + ) +{ + pgm_error_t *new; + va_list args; + + if (NULL == err) + return; + + va_start (args, format); + new = pgm_error_new_valist (error_domain, error_code, format, args); + va_end (args); + + if (NULL == *err) + *err = new; + else + pgm_warn (_(ERROR_OVERWRITTEN_WARNING), new->message); +} + +void +pgm_propagate_error ( + pgm_error_t** restrict dest, + pgm_error_t* restrict src + ) +{ + pgm_return_if_fail (src != NULL); + + if (NULL == dest) { + if (src) + pgm_error_free (src); + return; + } else { + if (NULL != *dest) { + pgm_warn (_(ERROR_OVERWRITTEN_WARNING), src->message); + } else { + *dest = src; + } + } +} + +void +pgm_clear_error ( + pgm_error_t** err + ) +{ + if (err && *err) { + pgm_error_free (*err); + *err = NULL; + } +} + +static +void +pgm_error_add_prefix ( + char** restrict string, + const char* restrict format, + va_list ap + ) +{ + char* prefix = pgm_strdup_vprintf (format, ap); + char* oldstring = *string; + *string = pgm_strconcat (prefix, oldstring, NULL); + pgm_free (oldstring); + pgm_free (prefix); +} + +void +pgm_prefix_error ( + pgm_error_t** restrict err, + const char* restrict format, + ... + ) +{ + if (err && *err) { + va_list ap; + va_start (ap, format); + pgm_error_add_prefix (&(*err)->message, format, ap); + va_end (ap); + } +} + +/* error from libc. + */ + +int +pgm_error_from_errno ( + const int from_errno + ) +{ + switch (from_errno) { +#ifdef EAFNOSUPPORT + case EAFNOSUPPORT: + return PGM_ERROR_AFNOSUPPORT; + break; +#endif + +#ifdef EAGAIN + case EAGAIN: + return PGM_ERROR_AGAIN; + break; +#endif + +#ifdef EBADF + case EBADF: + return PGM_ERROR_BADF; + break; +#endif + +#ifdef ECONNRESET + case ECONNRESET: + return PGM_ERROR_CONNRESET; + break; +#endif + +#ifdef EFAULT + case EFAULT: + return PGM_ERROR_FAULT; + break; +#endif + +#ifdef EINTR + case EINTR: + return PGM_ERROR_INTR; + break; +#endif + +#ifdef EINVAL + case EINVAL: + return PGM_ERROR_INVAL; + break; +#endif + +#ifdef EMFILE + case EMFILE: + return PGM_ERROR_MFILE; + break; +#endif + +#ifdef ENFILE + case ENFILE: + return PGM_ERROR_NFILE; + break; +#endif + +#ifdef ENODEV + case ENODEV: + return PGM_ERROR_NODEV; + break; +#endif + +#ifdef ENOENT + case ENOENT: + return PGM_ERROR_NOENT; + break; +#endif + +#ifdef ENOMEM + case ENOMEM: + return PGM_ERROR_NOMEM; + break; +#endif + +#ifdef ENONET + case ENONET: + return PGM_ERROR_NONET; + break; +#endif + +#ifdef ENOPROTOOPT + case ENOPROTOOPT: + return PGM_ERROR_NOPROTOOPT; + break; +#endif + +#ifdef ENOTUNIQ + case ENOTUNIQ: + return PGM_ERROR_NOTUNIQ; + break; +#endif + +#ifdef ENXIO + case ENXIO: + return PGM_ERROR_NXIO; + break; +#endif + +#ifdef EPERM + case EPERM: + return PGM_ERROR_PERM; + break; +#endif + +#ifdef EPROTO + case EPROTO: + return PGM_ERROR_PROTO; + break; +#endif + +#ifdef ERANGE + case ERANGE: + return PGM_ERROR_RANGE; + break; +#endif + +#ifdef EXDEV + case EXDEV: + return PGM_ERROR_XDEV; + break; +#endif + + default : + return PGM_ERROR_FAILED; + break; + } +} + +/* h_errno from gethostbyname. + */ + +int +pgm_error_from_h_errno ( + const int from_h_errno + ) +{ + switch (from_h_errno) { +#ifdef HOST_NOT_FOUND + case HOST_NOT_FOUND: + return PGM_ERROR_NONAME; + break; +#endif + +#ifdef TRY_AGAIN + case TRY_AGAIN: + return PGM_ERROR_AGAIN; + break; +#endif + +#ifdef NO_RECOVERY + case NO_RECOVERY: + return PGM_ERROR_FAIL; + break; +#endif + +#ifdef NO_DATA + case NO_DATA: + return PGM_ERROR_NODATA; + break; +#endif + + default: + return PGM_ERROR_FAILED; + break; + } +} + +/* errno must be preserved before calling to catch correct error + * status with EAI_SYSTEM. + */ + +int +pgm_error_from_eai_errno ( + const int from_eai_errno, +#ifdef EAI_SYSTEM + const int from_errno +#else + PGM_GNUC_UNUSED const int from_errno +#endif + ) +{ + switch (from_eai_errno) { +#ifdef EAI_ADDRFAMILY + case EAI_ADDRFAMILY: + return PGM_ERROR_ADDRFAMILY; + break; +#endif + +#ifdef EAI_AGAIN + case EAI_AGAIN: + return PGM_ERROR_AGAIN; + break; +#endif + +#ifdef EAI_BADFLAGS + case EAI_BADFLAGS: + return PGM_ERROR_INVAL; + break; +#endif + +#ifdef EAI_FAIL + case EAI_FAIL: + return PGM_ERROR_FAIL; + break; +#endif + +#ifdef EAI_FAMILY + case EAI_FAMILY: + return PGM_ERROR_AFNOSUPPORT; + break; +#endif + +#ifdef EAI_MEMORY + case EAI_MEMORY: + return PGM_ERROR_NOMEM; + break; +#endif + +#ifdef EAI_NODATA + case EAI_NODATA: + return PGM_ERROR_NODATA; + break; +#endif + +#if defined(EAI_NONAME) && EAI_NONAME != EAI_NODATA + case EAI_NONAME: + return PGM_ERROR_NONAME; + break; +#endif + +#ifdef EAI_SERVICE + case EAI_SERVICE: + return PGM_ERROR_SERVICE; + break; +#endif + +#ifdef EAI_SOCKTYPE + case EAI_SOCKTYPE: + return PGM_ERROR_SOCKTNOSUPPORT; + break; +#endif + +#ifdef EAI_SYSTEM + case EAI_SYSTEM: + return pgm_error_from_errno (from_errno); + break; +#endif + + default : + return PGM_ERROR_FAILED; + break; + } +} + +/* from WSAGetLastError() + */ + +int +pgm_error_from_wsa_errno ( + const int from_wsa_errno + ) +{ + switch (from_wsa_errno) { +#ifdef WSAEINVAL + case WSAEINVAL: + return PGM_ERROR_INVAL; + break; +#endif +#ifdef WSAEMFILE + case WSAEMFILE: + return PGM_ERROR_MFILE; + break; +#endif +#ifdef WSA_NOT_ENOUGH_MEMORY + case WSA_NOT_ENOUGH_MEMORY: + return PGM_ERROR_NOMEM; + break; +#endif +#ifdef WSAENOPROTOOPT + case WSAENOPROTOOPT: + return PGM_ERROR_NOPROTOOPT; + break; +#endif +#ifdef WSAECONNRESET + case WSAECONNRESET: + return PGM_ERROR_CONNRESET; + break; +#endif + + default : + return PGM_ERROR_FAILED; + break; + } +} + +/* from Last-Error codes, i.e. Windows non-WinSock and non-DOS errors. + */ + +int +pgm_error_from_win_errno ( + const int from_win_errno + ) +{ + switch (from_win_errno) { +#ifdef ERROR_ADDRESS_NOT_ASSOCIATED + case ERROR_ADDRESS_NOT_ASSOCIATED: + return PGM_ERROR_NODATA; + break; +#endif + +#ifdef ERROR_BUFFER_OVERFLOW + case ERROR_BUFFER_OVERFLOW: + return PGM_ERROR_NOBUFS; + break; +#endif + +#ifdef ERROR_INVALID_DATA + case ERROR_INVALID_DATA: + return PGM_ERROR_BADE; + break; +#endif + +#ifdef ERROR_INSUFFICIENT_BUFFER + case ERROR_INSUFFICIENT_BUFFER: + return PGM_ERROR_NOMEM; + break; +#endif + +#ifdef ERROR_INVALID_PARAMETER + case ERROR_INVALID_PARAMETER: + return PGM_ERROR_INVAL; + break; +#endif + +#ifdef ERROR_NOT_ENOUGH_MEMORY + case ERROR_NOT_ENOUGH_MEMORY: + return PGM_ERROR_NOMEM; + break; +#endif + +#ifdef ERROR_NO_DATA + case ERROR_NO_DATA: + return PGM_ERROR_NODATA; + break; +#endif + +#ifdef ERROR_NOT_SUPPORTED + case ERROR_NOT_SUPPORTED: + return PGM_ERROR_NOSYS; + break; +#endif + + default : + return PGM_ERROR_FAILED; + break; + } +} + +/* eof */ |