result.c

Go to the documentation of this file.
00001 /*
00002  * Copyright (C) 2004, 2005, 2007, 2008, 2012, 2014, 2015  Internet Systems Consortium, Inc. ("ISC")
00003  * Copyright (C) 1998-2001, 2003  Internet Software Consortium.
00004  *
00005  * Permission to use, copy, modify, and/or distribute this software for any
00006  * purpose with or without fee is hereby granted, provided that the above
00007  * copyright notice and this permission notice appear in all copies.
00008  *
00009  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
00010  * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
00011  * AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
00012  * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
00013  * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
00014  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
00015  * PERFORMANCE OF THIS SOFTWARE.
00016  */
00017 
00018 /* $Id$ */
00019 
00020 /*! \file */
00021 
00022 #include <config.h>
00023 
00024 #include <stddef.h>
00025 #include <stdlib.h>
00026 
00027 #include <isc/lib.h>
00028 #include <isc/msgs.h>
00029 #include <isc/mutex.h>
00030 #include <isc/once.h>
00031 #include <isc/resultclass.h>
00032 #include <isc/util.h>
00033 
00034 typedef struct resulttable {
00035         unsigned int                            base;
00036         unsigned int                            last;
00037         const char **                           text;
00038         isc_msgcat_t *                          msgcat;
00039         int                                     set;
00040         ISC_LINK(struct resulttable)            link;
00041 } resulttable;
00042 
00043 static const char *description[ISC_R_NRESULTS] = {
00044         "success",                              /*%< 0 */
00045         "out of memory",                        /*%< 1 */
00046         "timed out",                            /*%< 2 */
00047         "no available threads",                 /*%< 3 */
00048         "address not available",                /*%< 4 */
00049         "address in use",                       /*%< 5 */
00050         "permission denied",                    /*%< 6 */
00051         "no pending connections",               /*%< 7 */
00052         "network unreachable",                  /*%< 8 */
00053         "host unreachable",                     /*%< 9 */
00054         "network down",                         /*%< 10 */
00055         "host down",                            /*%< 11 */
00056         "connection refused",                   /*%< 12 */
00057         "not enough free resources",            /*%< 13 */
00058         "end of file",                          /*%< 14 */
00059         "socket already bound",                 /*%< 15 */
00060         "reload",                               /*%< 16 */
00061         "lock busy",                            /*%< 17 */
00062         "already exists",                       /*%< 18 */
00063         "ran out of space",                     /*%< 19 */
00064         "operation canceled",                   /*%< 20 */
00065         "socket is not bound",                  /*%< 21 */
00066         "shutting down",                        /*%< 22 */
00067         "not found",                            /*%< 23 */
00068         "unexpected end of input",              /*%< 24 */
00069         "failure",                              /*%< 25 */
00070         "I/O error",                            /*%< 26 */
00071         "not implemented",                      /*%< 27 */
00072         "unbalanced parentheses",               /*%< 28 */
00073         "no more",                              /*%< 29 */
00074         "invalid file",                         /*%< 30 */
00075         "bad base64 encoding",                  /*%< 31 */
00076         "unexpected token",                     /*%< 32 */
00077         "quota reached",                        /*%< 33 */
00078         "unexpected error",                     /*%< 34 */
00079         "already running",                      /*%< 35 */
00080         "ignore",                               /*%< 36 */
00081         "address mask not contiguous",          /*%< 37 */
00082         "file not found",                       /*%< 38 */
00083         "file already exists",                  /*%< 39 */
00084         "socket is not connected",              /*%< 40 */
00085         "out of range",                         /*%< 41 */
00086         "out of entropy",                       /*%< 42 */
00087         "invalid use of multicast address",     /*%< 43 */
00088         "not a file",                           /*%< 44 */
00089         "not a directory",                      /*%< 45 */
00090         "queue is full",                        /*%< 46 */
00091         "address family mismatch",              /*%< 47 */
00092         "address family not supported",         /*%< 48 */
00093         "bad hex encoding",                     /*%< 49 */
00094         "too many open files",                  /*%< 50 */
00095         "not blocking",                         /*%< 51 */
00096         "unbalanced quotes",                    /*%< 52 */
00097         "operation in progress",                /*%< 53 */
00098         "connection reset",                     /*%< 54 */
00099         "soft quota reached",                   /*%< 55 */
00100         "not a valid number",                   /*%< 56 */
00101         "disabled",                             /*%< 57 */
00102         "max size",                             /*%< 58 */
00103         "invalid address format",               /*%< 59 */
00104         "bad base32 encoding",                  /*%< 60 */
00105         "unset",                                /*%< 61 */
00106         "multiple",                             /*%< 62 */
00107 };
00108 
00109 #define ISC_RESULT_RESULTSET                    2
00110 #define ISC_RESULT_UNAVAILABLESET               3
00111 
00112 static isc_once_t                               once = ISC_ONCE_INIT;
00113 static ISC_LIST(resulttable)                    tables;
00114 static isc_mutex_t                              lock;
00115 
00116 static isc_result_t
00117 register_table(unsigned int base, unsigned int nresults, const char **text,
00118                isc_msgcat_t *msgcat, int set)
00119 {
00120         resulttable *table;
00121 
00122         REQUIRE(base % ISC_RESULTCLASS_SIZE == 0);
00123         REQUIRE(nresults <= ISC_RESULTCLASS_SIZE);
00124         REQUIRE(text != NULL);
00125 
00126         /*
00127          * We use malloc() here because we we want to be able to use
00128          * isc_result_totext() even if there is no memory context.
00129          */
00130         table = malloc(sizeof(*table));
00131         if (table == NULL)
00132                 return (ISC_R_NOMEMORY);
00133         table->base = base;
00134         table->last = base + nresults - 1;
00135         table->text = text;
00136         table->msgcat = msgcat;
00137         table->set = set;
00138         ISC_LINK_INIT(table, link);
00139 
00140         LOCK(&lock);
00141 
00142         ISC_LIST_APPEND(tables, table, link);
00143 
00144         UNLOCK(&lock);
00145 
00146         return (ISC_R_SUCCESS);
00147 }
00148 
00149 static void
00150 initialize_action(void) {
00151         isc_result_t result;
00152 
00153         RUNTIME_CHECK(isc_mutex_init(&lock) == ISC_R_SUCCESS);
00154         ISC_LIST_INIT(tables);
00155 
00156         result = register_table(ISC_RESULTCLASS_ISC, ISC_R_NRESULTS,
00157                                 description, isc_msgcat, ISC_RESULT_RESULTSET);
00158         if (result != ISC_R_SUCCESS)
00159                 UNEXPECTED_ERROR(__FILE__, __LINE__,
00160                                  "register_table() %s: %u",
00161                                  isc_msgcat_get(isc_msgcat, ISC_MSGSET_GENERAL,
00162                                                 ISC_MSG_FAILED, "failed"),
00163                                  result);
00164 }
00165 
00166 static void
00167 initialize(void) {
00168         isc_lib_initmsgcat();
00169         RUNTIME_CHECK(isc_once_do(&once, initialize_action) == ISC_R_SUCCESS);
00170 }
00171 
00172 const char *
00173 isc_result_totext(isc_result_t result) {
00174         resulttable *table;
00175         const char *text, *default_text;
00176         int index;
00177 
00178         initialize();
00179 
00180         LOCK(&lock);
00181 
00182         text = NULL;
00183         for (table = ISC_LIST_HEAD(tables);
00184              table != NULL;
00185              table = ISC_LIST_NEXT(table, link)) {
00186                 if (result >= table->base && result <= table->last) {
00187                         index = (int)(result - table->base);
00188                         default_text = table->text[index];
00189                         /*
00190                          * Note: we use 'index + 1' as the message number
00191                          * instead of index because isc_msgcat_get() requires
00192                          * the message number to be > 0.
00193                          */
00194                         text = isc_msgcat_get(table->msgcat, table->set,
00195                                               index + 1, default_text);
00196                         break;
00197                 }
00198         }
00199         if (text == NULL)
00200                 text = isc_msgcat_get(isc_msgcat, ISC_RESULT_UNAVAILABLESET,
00201                                       1, "(result code text not available)");
00202 
00203         UNLOCK(&lock);
00204 
00205         return (text);
00206 }
00207 
00208 isc_result_t
00209 isc_result_register(unsigned int base, unsigned int nresults,
00210                     const char **text, isc_msgcat_t *msgcat, int set)
00211 {
00212         initialize();
00213 
00214         return (register_table(base, nresults, text, msgcat, set));
00215 }

Generated on Tue Apr 28 17:41:05 2015 by Doxygen 1.5.4 for BIND9 Internals 9.11.0pre-alpha