168cd9bedSMike Barcroft /*- 28a16b7a1SPedro F. Giffuni * SPDX-License-Identifier: BSD-3-Clause 38a16b7a1SPedro F. Giffuni * 458f0484fSRodney W. Grimes * Copyright (c) 1988, 1993 558f0484fSRodney W. Grimes * The Regents of the University of California. All rights reserved. 658f0484fSRodney W. Grimes * 758f0484fSRodney W. Grimes * Redistribution and use in source and binary forms, with or without 858f0484fSRodney W. Grimes * modification, are permitted provided that the following conditions 958f0484fSRodney W. Grimes * are met: 1058f0484fSRodney W. Grimes * 1. Redistributions of source code must retain the above copyright 1158f0484fSRodney W. Grimes * notice, this list of conditions and the following disclaimer. 1258f0484fSRodney W. Grimes * 2. Redistributions in binary form must reproduce the above copyright 1358f0484fSRodney W. Grimes * notice, this list of conditions and the following disclaimer in the 1458f0484fSRodney W. Grimes * documentation and/or other materials provided with the distribution. 153fb3b97cSEd Maste * 3. Neither the name of the University nor the names of its contributors 1658f0484fSRodney W. Grimes * may be used to endorse or promote products derived from this software 1758f0484fSRodney W. Grimes * without specific prior written permission. 1858f0484fSRodney W. Grimes * 1958f0484fSRodney W. Grimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 2058f0484fSRodney W. Grimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 2158f0484fSRodney W. Grimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2258f0484fSRodney W. Grimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 2358f0484fSRodney W. Grimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2458f0484fSRodney W. Grimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2558f0484fSRodney W. Grimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2658f0484fSRodney W. Grimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2758f0484fSRodney W. Grimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2858f0484fSRodney W. Grimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2958f0484fSRodney W. Grimes * SUCH DAMAGE. 3058f0484fSRodney W. Grimes */ 3158f0484fSRodney W. Grimes 3258f0484fSRodney W. Grimes #if defined(LIBC_SCCS) && !defined(lint) 3358f0484fSRodney W. Grimes static char sccsid[] = "@(#)strerror.c 8.1 (Berkeley) 6/4/93"; 3458f0484fSRodney W. Grimes #endif /* LIBC_SCCS and not lint */ 35de5fe5d5SDavid E. O'Brien #include <sys/cdefs.h> 36de5fe5d5SDavid E. O'Brien __FBSDID("$FreeBSD$"); 3758f0484fSRodney W. Grimes 38fba5c5faSAlexey Zelkin #if defined(NLS) 39fba5c5faSAlexey Zelkin #include <nl_types.h> 40fba5c5faSAlexey Zelkin #endif 419c324dc0SWes Peters 42fc7c3528SAlexey Zelkin #include <limits.h> 43fba5c5faSAlexey Zelkin #include <errno.h> 44fba5c5faSAlexey Zelkin #include <string.h> 45fba5c5faSAlexey Zelkin #include <stdio.h> 46fba5c5faSAlexey Zelkin 47e73151ebSJilles Tjoelker #include "errlst.h" 48e73151ebSJilles Tjoelker 495a98f074SMike Barcroft /* 50*cd49e866SKonstantin Belousov * Define buffer big enough to contain delimiter (": ", 2 bytes), 51*cd49e866SKonstantin Belousov * 64-bit signed integer converted to ASCII decimal (19 bytes) with 52*cd49e866SKonstantin Belousov * optional leading sign (1 byte), and a trailing NUL. 535a98f074SMike Barcroft */ 54*cd49e866SKonstantin Belousov #define EBUFSIZE (2 + 19 + 1 + 1) 555a98f074SMike Barcroft 5668cd9bedSMike Barcroft /* 5768cd9bedSMike Barcroft * Doing this by hand instead of linking with stdio(3) avoids bloat for 5868cd9bedSMike Barcroft * statically linked binaries. 5968cd9bedSMike Barcroft */ 605a98f074SMike Barcroft static void 61fba5c5faSAlexey Zelkin errstr(int num, char *uprefix, char *buf, size_t len) 629c324dc0SWes Peters { 63e37f8b53SMike Barcroft char *t; 6468cd9bedSMike Barcroft unsigned int uerr; 655a98f074SMike Barcroft char tmp[EBUFSIZE]; 6658f0484fSRodney W. Grimes 67e37f8b53SMike Barcroft t = tmp + sizeof(tmp); 68e37f8b53SMike Barcroft *--t = '\0'; 695a98f074SMike Barcroft uerr = (num >= 0) ? num : -num; 70f61a2edeSWes Peters do { 71e37f8b53SMike Barcroft *--t = "0123456789"[uerr % 10]; 72f61a2edeSWes Peters } while (uerr /= 10); 73f61a2edeSWes Peters if (num < 0) 74e37f8b53SMike Barcroft *--t = '-'; 75fba5c5faSAlexey Zelkin *--t = ' '; 76fba5c5faSAlexey Zelkin *--t = ':'; 77fba5c5faSAlexey Zelkin strlcpy(buf, uprefix, len); 78d0509082SJacques Vidrine strlcat(buf, t, len); 795a98f074SMike Barcroft } 805a98f074SMike Barcroft 815a98f074SMike Barcroft int 825a98f074SMike Barcroft strerror_r(int errnum, char *strerrbuf, size_t buflen) 835a98f074SMike Barcroft { 84fba5c5faSAlexey Zelkin int retval = 0; 85fba5c5faSAlexey Zelkin #if defined(NLS) 86fba5c5faSAlexey Zelkin int saved_errno = errno; 87fba5c5faSAlexey Zelkin nl_catd catd; 88fba5c5faSAlexey Zelkin catd = catopen("libc", NL_CAT_LOCALE); 89fba5c5faSAlexey Zelkin #endif 905a98f074SMike Barcroft 91e73151ebSJilles Tjoelker if (errnum < 0 || errnum >= __hidden_sys_nerr) { 92fba5c5faSAlexey Zelkin errstr(errnum, 93fba5c5faSAlexey Zelkin #if defined(NLS) 94*cd49e866SKonstantin Belousov catgets(catd, 1, 0xffff, __uprefix), 95fba5c5faSAlexey Zelkin #else 96*cd49e866SKonstantin Belousov __uprefix, 97fba5c5faSAlexey Zelkin #endif 98fba5c5faSAlexey Zelkin strerrbuf, buflen); 99fba5c5faSAlexey Zelkin retval = EINVAL; 100fba5c5faSAlexey Zelkin } else { 101fba5c5faSAlexey Zelkin if (strlcpy(strerrbuf, 102fba5c5faSAlexey Zelkin #if defined(NLS) 103e73151ebSJilles Tjoelker catgets(catd, 1, errnum, __hidden_sys_errlist[errnum]), 104fba5c5faSAlexey Zelkin #else 105e73151ebSJilles Tjoelker __hidden_sys_errlist[errnum], 106fba5c5faSAlexey Zelkin #endif 107fba5c5faSAlexey Zelkin buflen) >= buflen) 108fba5c5faSAlexey Zelkin retval = ERANGE; 10968cd9bedSMike Barcroft } 110fba5c5faSAlexey Zelkin 111fba5c5faSAlexey Zelkin #if defined(NLS) 112fba5c5faSAlexey Zelkin catclose(catd); 113fba5c5faSAlexey Zelkin errno = saved_errno; 114fba5c5faSAlexey Zelkin #endif 115fba5c5faSAlexey Zelkin 116fba5c5faSAlexey Zelkin return (retval); 1175a98f074SMike Barcroft } 1185a98f074SMike Barcroft 1195a98f074SMike Barcroft char * 1205a98f074SMike Barcroft strerror(int num) 1215a98f074SMike Barcroft { 122fba5c5faSAlexey Zelkin static char ebuf[NL_TEXTMAX]; 1235a98f074SMike Barcroft 124fba5c5faSAlexey Zelkin if (strerror_r(num, ebuf, sizeof(ebuf)) != 0) 1255a98f074SMike Barcroft errno = EINVAL; 126f61a2edeSWes Peters return (ebuf); 12758f0484fSRodney W. Grimes } 128