1176772Sraj/* 2176772Sraj * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. 3176772Sraj * All rights reserved. 4176772Sraj * 5176772Sraj * Redistribution and use in source and binary forms, with or without 6176772Sraj * modification, are permitted provided that the following conditions 7176772Sraj * are met: 8176772Sraj * 1. Redistributions of source code must retain the above copyright 9176772Sraj * notice, this list of conditions and the following disclaimer. 10176772Sraj * 2. Redistributions in binary form must reproduce the above copyright 11176772Sraj * notice, this list of conditions and the following disclaimer in the 12176772Sraj * documentation and/or other materials provided with the distribution. 13176772Sraj * 3. Neither the name of the project nor the names of its contributors 14176772Sraj * may be used to endorse or promote products derived from this software 15176772Sraj * without specific prior written permission. 16176772Sraj * 17176772Sraj * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 18176772Sraj * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19176772Sraj * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20176772Sraj * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 21176772Sraj * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22176772Sraj * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23176772Sraj * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24176772Sraj * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25176772Sraj * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26176772Sraj * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27176772Sraj * SUCH DAMAGE. 28176772Sraj */ 29176772Sraj 30176772Sraj#include <sys/cdefs.h> 31176772Sraj__FBSDID("$FreeBSD$"); 32176772Sraj 33176772Sraj#include "namespace.h" 34176772Sraj#include <netdb.h> 35176772Sraj#if defined(NLS) 36176772Sraj#include <nl_types.h> 37176772Sraj#include <errno.h> 38176772Sraj#include <limits.h> 39176772Sraj#include <stdlib.h> 40176772Sraj#include <string.h> 41176772Sraj#include "reentrant.h" 42176772Sraj#endif 43176772Sraj#include "un-namespace.h" 44176772Sraj 45176772Sraj/* Entries EAI_ADDRFAMILY (1) and EAI_NODATA (7) are obsoleted, but left */ 46176772Sraj/* for backward compatibility with userland code prior to 2553bis-02 */ 47176772Srajstatic const char *ai_errlist[] = { 48176772Sraj "Success", /* 0 */ 49176772Sraj "Address family for hostname not supported", /* 1 */ 50176772Sraj "Temporary failure in name resolution", /* EAI_AGAIN */ 51176772Sraj "Invalid value for ai_flags", /* EAI_BADFLAGS */ 52176772Sraj "Non-recoverable failure in name resolution", /* EAI_FAIL */ 53176772Sraj "ai_family not supported", /* EAI_FAMILY */ 54176772Sraj "Memory allocation failure", /* EAI_MEMORY */ 55176772Sraj "No address associated with hostname", /* 7 */ 56176772Sraj "hostname nor servname provided, or not known", /* EAI_NONAME */ 57176772Sraj "servname not supported for ai_socktype", /* EAI_SERVICE */ 58176772Sraj "ai_socktype not supported", /* EAI_SOCKTYPE */ 59176772Sraj "System error returned in errno", /* EAI_SYSTEM */ 60176772Sraj "Invalid value for hints", /* EAI_BADHINTS */ 61176772Sraj "Resolved protocol is unknown", /* EAI_PROTOCOL */ 62176772Sraj "Argument buffer overflow" /* EAI_OVERFLOW */ 63176772Sraj}; 64227293Sed 65176772Sraj#if defined(NLS) 66176772Srajstatic char gai_buf[NL_TEXTMAX]; 67176772Srajstatic once_t gai_init_once = ONCE_INITIALIZER; 68176772Srajstatic thread_key_t gai_key; 69176772Srajstatic int gai_keycreated = 0; 70176772Sraj 71176772Srajstatic void 72176772Srajgai_keycreate(void) 73176772Sraj{ 74176772Sraj gai_keycreated = (thr_keycreate(&gai_key, free) == 0); 75176772Sraj} 76176772Sraj#endif 77176772Sraj 78176772Srajconst char * 79176772Srajgai_strerror(int ecode) 80176772Sraj{ 81176772Sraj#if defined(NLS) 82176772Sraj nl_catd catd; 83176772Sraj char *buf; 84176772Sraj 85176772Sraj if (thr_main() != 0) 86176772Sraj buf = gai_buf; 87176772Sraj else { 88176772Sraj if (thr_once(&gai_init_once, gai_keycreate) != 0 || 89176772Sraj !gai_keycreated) 90176772Sraj goto thr_err; 91176772Sraj if ((buf = thr_getspecific(gai_key)) == NULL) { 92176772Sraj if ((buf = malloc(sizeof(gai_buf))) == NULL) 93176772Sraj goto thr_err; 94176772Sraj if (thr_setspecific(gai_key, buf) != 0) { 95176772Sraj free(buf); 96176772Sraj goto thr_err; 97176772Sraj } 98176772Sraj } 99176772Sraj } 100176772Sraj 101176772Sraj catd = catopen("libc", NL_CAT_LOCALE); 102176772Sraj if (ecode > 0 && ecode < EAI_MAX) 103176772Sraj strlcpy(buf, catgets(catd, 3, ecode, ai_errlist[ecode]), 104176772Sraj sizeof(gai_buf)); 105176772Sraj else if (ecode == 0) 106176772Sraj strlcpy(buf, catgets(catd, 3, NL_MSGMAX - 1, "Success"), 107176772Sraj sizeof(gai_buf)); 108176772Sraj else 109176772Sraj strlcpy(buf, catgets(catd, 3, NL_MSGMAX, "Unknown error"), 110176772Sraj sizeof(gai_buf)); 111176772Sraj catclose(catd); 112176772Sraj return buf; 113176772Sraj 114176772Srajthr_err: 115176772Sraj#endif 116176772Sraj if (ecode >= 0 && ecode < EAI_MAX) 117176772Sraj return ai_errlist[ecode]; 118176772Sraj return "Unknown error"; 119176772Sraj} 120176772Sraj