From b815b84a5942f591e8a79c731100712558fa41c6 Mon Sep 17 00:00:00 2001 From: Manuel Novoa III Date: Sun, 7 Jul 2002 20:13:41 +0000 Subject: Attempt to clean up the strerror_r situation. --- libc/stdio/old_vfprintf.c | 2 +- libc/stdio/printf.c | 2 +- libc/stdio/stdio.c | 38 +-- libc/string/strerror.c | 133 --------- libc/string/sys_errlist.c | 140 ---------- libc/string/wstring.c | 385 +++++++++++++++++++++++++- libc/sysdeps/linux/common/bits/uClibc_stdio.h | 8 - 7 files changed, 379 insertions(+), 329 deletions(-) delete mode 100644 libc/string/strerror.c delete mode 100644 libc/string/sys_errlist.c (limited to 'libc') diff --git a/libc/stdio/old_vfprintf.c b/libc/stdio/old_vfprintf.c index 945f59a48..8aa9be502 100644 --- a/libc/stdio/old_vfprintf.c +++ b/libc/stdio/old_vfprintf.c @@ -272,7 +272,7 @@ int vfprintf(FILE * __restrict op, register const char * __restrict fmt, if (*fmt == 'm') { flag[FLAG_PLUS] = '\0'; flag[FLAG_0_PAD] = ' '; - p = _stdio_strerror_r(errno, tmp, sizeof(tmp)); + p = _glibc_strerror_r(errno, tmp, sizeof(tmp)); goto print; } #endif diff --git a/libc/stdio/printf.c b/libc/stdio/printf.c index fc6dd87bd..de50ed4e5 100644 --- a/libc/stdio/printf.c +++ b/libc/stdio/printf.c @@ -1220,7 +1220,7 @@ int _do_one_spec(FILE * __restrict stream, register ppfs_t *ppfs, int *count) } #ifdef __STDIO_PRINTF_M_SUPPORT } else if (ppfs->conv_num == CONV_m) { - s = _stdio_strerror_r(errno, buf, sizeof(buf)); + s = _glibc_strerror_r(errno, buf, sizeof(buf)); goto SET_STRING_LEN; #endif } else { diff --git a/libc/stdio/stdio.c b/libc/stdio/stdio.c index a56eff777..1bce679f9 100644 --- a/libc/stdio/stdio.c +++ b/libc/stdio/stdio.c @@ -3218,7 +3218,7 @@ void perror(register const char *s) { char buf[64]; fprintf(stderr, "%s%s%s\n", s, sep, - _stdio_strerror_r(errno, buf, sizeof(buf))); + _glibc_strerror_r(errno, buf, sizeof(buf))); } #endif #else @@ -3228,7 +3228,7 @@ void perror(register const char *s) __STDIO_THREADLOCK(stderr); _stdio_fdout(STDERR_FILENO, s, sep, - _stdio_strerror_r(errno, buf, sizeof(buf))); + _glibc_strerror_r(errno, buf, sizeof(buf))); __STDIO_THREADUNLOCK(stderr); } #endif @@ -3328,37 +3328,3 @@ char *_uintmaxtostr(register char * __restrict bufend, uintmax_t uval, #endif /**********************************************************************/ -#ifdef L__stdio_strerror_r - -/* This is an internal routine, and assumes buf and buflen are set - * appropriately. - * - * WARNING!!! While it is similar to the glibc strerror_r function, - * it is not the same. It is expected that "unknown" error strings - * will fit in the buffer passed. Also, the return value may not - * be == buf, as unknown strings are "right-justified" in the buf - * due to the way _int10stostr works. */ - -static const char unknown[] = "Unknown error"; - -char *_stdio_strerror_r(int err, register char *buf, size_t buflen) -{ - int errsave; - - assert(buflen >= __UIM_BUFLEN_INT + sizeof(unknown)); - - errsave = errno; /* Backup the errno. */ - - if (strerror_r(err, buf, buflen)) { /* Failed! */ - __set_errno(errsave); /* Restore old errno. */ - - buf = _int10tostr(buf+buflen-1, err) - sizeof(unknown); - strcpy(buf, unknown); - buf[sizeof(unknown)-1] = ' '; /* Overwrite the nul. */ - } - - return buf; -} - -#endif -/**********************************************************************/ diff --git a/libc/string/strerror.c b/libc/string/strerror.c deleted file mode 100644 index 80f82de25..000000000 --- a/libc/string/strerror.c +++ /dev/null @@ -1,133 +0,0 @@ -/* Copyright (C) 1991, 1993, 1994 Free Software Foundation, Inc. -This file is part of the GNU C Library. - -The GNU C Library is free software; you can redistribute it and/or -modify it under the terms of the GNU Library General Public License as -published by the Free Software Foundation; either version 2 of the -License, or (at your option) any later version. - -The GNU C 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 -Library General Public License for more details. - -You should have received a copy of the GNU Library General Public -License along with the GNU C Library; see the file COPYING.LIB. If -not, write to the Free Software Foundation, Inc., 675 Mass Ave, -Cambridge, MA 02139, USA. */ - -/* - * Manuel Novoa III Dec 2000 - * - * Converted to use my new (un)signed long (long) to string routines, which - * are smaller than the previous functions and don't require static buffers. - * Removed dependence on strcat in the process. - * - * Also appended a test routine ( -DCHECK_BUF ) to allow a quick check - * on the buffer length when the sys_errorlist is modified. - * - * Added the option WANT_ERRORLIST for low-memory applications to omit the - * error message strings and only output the error number. - * - * Manuel Novoa III Feb 2002 - * - * Change to _int10tostr and fix a bug in end-of-buf arg. - * - * Erik Andersen June 2002 - * - * Added strerror_r (per SuSv3 which differs from glibc) and adapted - * strerror to match. - */ - -#define WANT_ERRORLIST 1 - -#define _STDIO_UTILITY /* For _int10tostr. */ -#include -#include -#include - -int strerror_r(int err, char *retbuf, size_t buflen) -{ -#if WANT_ERRORLIST - if (err < 0 || err >= sys_nerr || sys_errlist[err] == NULL) { - return -EINVAL; - } - if (retbuf==NULL || buflen < 1) { - return -ERANGE; - } - strncpy(retbuf, sys_errlist[err], buflen); - retbuf[buflen-1] = '\0'; - return 0; -#else - char *pos; - static const char unknown_error[] = "Unknown Error: errno"; /* = */ - - if (err < 0 || err >= sys_nerr || sys_errlist[err] == NULL) { - return -EINVAL; - } - /* unknown error -- leave space for the '=' */ - pos = _int10tostr(retbuf+sizeof(retbuf)-1, err) - sizeof(unknown_error); - strcpy(pos, unknown_error); - *(pos + sizeof(unknown_error) - 1) = '='; - return 0; -#endif -} - -/* Return a string descibing the errno code in ERRNUM. - The storage is good only until the next call to strerror. - Writing to the storage causes undefined behavior. */ -char *strerror(int err) -{ -#if WANT_ERRORLIST - static char retbuf[48]; -#else -#if __BUFLEN_INT10TOSTR > 12 -#error currently set up for 32 bit ints max! -#endif - static char retbuf[33]; /* 33 is sufficient for 32 bit ints */ -#endif - - if (strerror_r(err, retbuf, sizeof(retbuf)) != 0) { - return NULL; - } - return(retbuf); -} - -#ifdef CHECK_BUF -/* quick way to check buffer length */ -#include -#include -int main(void) -{ - int max = 0; - int j, retcode; - char *p; -#if WANT_ERRORLIST - int i; -#endif - - retcode = EXIT_SUCCESS; - -#if WANT_ERRORLIST - for ( i=0 ; i < sys_nerr ; i++ ) { - j = strlen(sys_errlist[i])+1; - if (j > max) max = j; - } -#endif - - p = strerror(INT_MIN); - j = retbuf+sizeof(retbuf) - p; - if ( > max) { - max = j; - printf("strerror.c - Test of INT_MIN: <%s> %d\n", p, j); - } - - if (sizeof(retbuf) != max) { - printf("Error: strerror.c - dimension of retbuf should be = %d\n", max); - retcode = EXIT_FAILURE; - } - printf("Passed.\n"); - - return retcode; -} -#endif diff --git a/libc/string/sys_errlist.c b/libc/string/sys_errlist.c deleted file mode 100644 index c92302fce..000000000 --- a/libc/string/sys_errlist.c +++ /dev/null @@ -1,140 +0,0 @@ -#include -#if 0 -#include -#endif - -/* This is a list of all known signal numbers. */ - -const char * const sys_errlist[] = { - "Success", /* 0 */ - "Operation not permitted", /* EPERM */ - "No such file or directory", /* ENOENT */ - "No such process", /* ESRCH */ - "Interrupted system call", /* EINTR */ - "I/O error", /* EIO */ - "No such device or address", /* ENXIO */ - "Arg list too long", /* E2BIG */ - "Exec format error", /* ENOEXEC */ - "Bad file number", /* EBADF */ - "No child processes", /* ECHILD */ - "Try again", /* EAGAIN */ - "Out of memory", /* ENOMEM */ - "Permission denied", /* EACCES */ - "Bad address", /* EFAULT */ - "Block device required", /* ENOTBLK */ - "Device or resource busy", /* EBUSY */ - "File exists", /* EEXIST */ - "Cross-device link", /* EXDEV */ - "No such device", /* ENODEV */ - "Not a directory", /* ENOTDIR */ - "Is a directory", /* EISDIR */ - "Invalid argument", /* EINVAL */ - "File table overflow", /* ENFILE */ - "Too many open files", /* EMFILE */ - "Not a typewriter", /* ENOTTY */ - "Text file busy", /* ETXTBSY */ - "File too large", /* EFBIG */ - "No space left on device", /* ENOSPC */ - "Illegal seek", /* ESPIPE */ - "Read-only file system", /* EROFS */ - "Too many links", /* EMLINK */ - "Broken pipe", /* EPIPE */ - "Math argument out of domain of func", /* EDOM */ - "Math result not representable", /* ERANGE */ - "Resource deadlock would occur", /* EDEADLK */ - "File name too long", /* ENAMETOOLONG */ - "No record locks available", /* ENOLCK */ - "Function not implemented", /* ENOSYS */ - "Directory not empty", /* ENOTEMPTY */ - "Too many symbolic links encountered", /* ELOOP */ - "Operation would block", /* EWOULDBLOCK */ - "No message of desired type", /* ENOMSG */ - "Identifier removed", /* EIDRM */ - "Channel number out of range", /* ECHRNG */ - "Level 2 not synchronized", /* EL2NSYNC */ - "Level 3 halted", /* EL3HLT */ - "Level 3 reset", /* EL3RST */ - "Link number out of range", /* ELNRNG */ - "Protocol driver not attached", /* EUNATCH */ - "No CSI structure available", /* ENOCSI */ - "Level 2 halted", /* EL2HLT */ - "Invalid exchange", /* EBADE */ - "Invalid request descriptor", /* EBADR */ - "Exchange full", /* EXFULL */ - "No anode", /* ENOANO */ - "Invalid request code", /* EBADRQC */ - "Invalid slot", /* EBADSLT */ - "File locking deadlock error", /* EDEADLOCK */ - "Bad font file format", /* EBFONT */ - "Device not a stream", /* ENOSTR */ - "No data available", /* ENODATA */ - "Timer expired", /* ETIME */ - "Out of streams resources", /* ENOSR */ - "Machine is not on the network", /* ENONET */ - "Package not installed", /* ENOPKG */ - "Object is remote", /* EREMOTE */ - "Link has been severed", /* ENOLINK */ - "Advertise error", /* EADV */ - "Srmount error", /* ESRMNT */ - "Communication error on send", /* ECOMM */ - "Protocol error", /* EPROTO */ - "Multihop attempted", /* EMULTIHOP */ - "RFS specific error", /* EDOTDOT */ - "Not a data message", /* EBADMSG */ - "Value too large for defined data type", /* EOVERFLOW */ - "Name not unique on network", /* ENOTUNIQ */ - "File descriptor in bad state", /* EBADFD */ - "Remote address changed", /* EREMCHG */ - "Can not access a needed shared library", /* ELIBACC */ - "Accessing a corrupted shared library", /* ELIBBAD */ - ".lib section in a.out corrupted", /* ELIBSCN */ - "Attempting to link in too many shared libraries", /* ELIBMAX */ - "Cannot exec a shared library directly", /* ELIBEXEC */ - "Illegal byte sequence", /* EILSEQ */ - "Interrupted system call should be restarted", /* ERESTART */ - "Streams pipe error", /* ESTRPIPE */ - "Too many users", /* EUSERS */ - "Socket operation on non-socket", /* ENOTSOCK */ - "Destination address required", /* EDESTADDRREQ */ - "Message too long", /* EMSGSIZE */ - "Protocol wrong type for socket", /* EPROTOTYPE */ - "Protocol not available", /* ENOPROTOOPT */ - "Protocol not supported", /* EPROTONOSUPPORT */ - "Socket type not supported", /* ESOCKTNOSUPPORT */ - "Operation not supported on transport endpoint", /* EOPNOTSUPP */ - "Protocol family not supported", /* EPFNOSUPPORT */ - "Address family not supported by protocol", /* EAFNOSUPPORT */ - "Address already in use", /* EADDRINUSE */ - "Cannot assign requested address", /* EADDRNOTAVAIL */ - "Network is down", /* ENETDOWN */ - "Network is unreachable", /* ENETUNREACH */ - "Network dropped connection because of reset", /* ENETRESET */ - "Software caused connection abort", /* ECONNABORTED */ - "Connection reset by peer", /* ECONNRESET */ - "No buffer space available", /* ENOBUFS */ - "Transport endpoint is already connected", /* EISCONN */ - "Transport endpoint is not connected", /* ENOTCONN */ - "Cannot send after transport endpoint shutdown", /* ESHUTDOWN */ - "Too many references: cannot splice", /* ETOOMANYREFS */ - "Connection timed out", /* ETIMEDOUT */ - "Connection refused", /* ECONNREFUSED */ - "Host is down", /* EHOSTDOWN */ - "No route to host", /* EHOSTUNREACH */ - "Operation already in progress", /* EALREADY */ - "Operation now in progress", /* EINPROGRESS */ - "Stale NFS file handle", /* ESTALE */ - "Structure needs cleaning", /* EUCLEAN */ - "Not a XENIX named type file", /* ENOTNAM */ - "No XENIX semaphores available", /* ENAVAIL */ - "Is a named type file", /* EISNAM */ - "Remote I/O error", /* EREMOTEIO */ - "Quota exceeded", /* EDQUOT */ - "No medium found", /* ENOMEDIUM */ - "Wrong medium type", /* EMEDIUMTYPE */ - NULL -}; - - -#define NR_ERRORS ((sizeof (sys_errlist))/(sizeof(char *))-1) - -const int sys_nerr = NR_ERRORS; diff --git a/libc/string/wstring.c b/libc/string/wstring.c index c78dbce0f..fd9e07d3d 100644 --- a/libc/string/wstring.c +++ b/libc/string/wstring.c @@ -26,12 +26,15 @@ * * ATTENTION! ATTENTION! ATTENTION! ATTENTION! ATTENTION! */ +#define _STDIO_UTILITY #define _GNU_SOURCE #include #include +#include #include #include #include +#include #ifdef WANT_WIDE #include @@ -53,6 +56,291 @@ typedef unsigned char __string_uchar_t; #endif +/**********************************************************************/ +/* NOTE: If we ever do internationalized syserr messages, this will + * have to be changed! */ + +#if _SYS_ERRMSG_MAXLEN < __UIM_BUFLEN_INT + 14 +#define _STRERROR_BUFSIZE (__UIM_BUFLEN_INT + 14) +#else +#define _STRERROR_BUFSIZE _SYS_ERRMSG_MAXLEN +#endif + +#define _SYS_NERR 125 +#define _SYS_ERRMSG_MAXLEN 50 + +extern const char _string_syserrmsgs[]; + +/**********************************************************************/ +#ifdef L__string_syserrmsgs + +const char _string_syserrmsgs[] = { + /* 0: 0, 8 */ "Success\0" + /* 1: 8, 24 */ "Operation not permitted\0" + /* 2: 32, 26 */ "No such file or directory\0" + /* 3: 58, 16 */ "No such process\0" + /* 4: 74, 24 */ "Interrupted system call\0" + /* 5: 98, 19 */ "Input/output error\0" + /* 6: 117, 26 */ "No such device or address\0" + /* 7: 143, 23 */ "Argument list too long\0" + /* 8: 166, 18 */ "Exec format error\0" + /* 9: 184, 20 */ "Bad file descriptor\0" + /* 10: 204, 19 */ "No child processes\0" + /* 11: 223, 33 */ "Resource temporarily unavailable\0" + /* 12: 256, 23 */ "Cannot allocate memory\0" + /* 13: 279, 18 */ "Permission denied\0" + /* 14: 297, 12 */ "Bad address\0" + /* 15: 309, 22 */ "Block device required\0" + /* 16: 331, 24 */ "Device or resource busy\0" + /* 17: 355, 12 */ "File exists\0" + /* 18: 367, 26 */ "Invalid cross-device link\0" + /* 19: 393, 15 */ "No such device\0" + /* 20: 408, 16 */ "Not a directory\0" + /* 21: 424, 15 */ "Is a directory\0" + /* 22: 439, 17 */ "Invalid argument\0" + /* 23: 456, 30 */ "Too many open files in system\0" + /* 24: 486, 20 */ "Too many open files\0" + /* 25: 506, 31 */ "Inappropriate ioctl for device\0" + /* 26: 537, 15 */ "Text file busy\0" + /* 27: 552, 15 */ "File too large\0" + /* 28: 567, 24 */ "No space left on device\0" + /* 29: 591, 13 */ "Illegal seek\0" + /* 30: 604, 22 */ "Read-only file system\0" + /* 31: 626, 15 */ "Too many links\0" + /* 32: 641, 12 */ "Broken pipe\0" + /* 33: 653, 33 */ "Numerical argument out of domain\0" + /* 34: 686, 30 */ "Numerical result out of range\0" + /* 35: 716, 26 */ "Resource deadlock avoided\0" + /* 36: 742, 19 */ "File name too long\0" + /* 37: 761, 19 */ "No locks available\0" + /* 38: 780, 25 */ "Function not implemented\0" + /* 39: 805, 20 */ "Directory not empty\0" + /* 40: 825, 34 */ "Too many levels of symbolic links\0" + /* 41: 859, 1 */ "\0" + /* 42: 860, 27 */ "No message of desired type\0" + /* 43: 887, 19 */ "Identifier removed\0" + /* 44: 906, 28 */ "Channel number out of range\0" + /* 45: 934, 25 */ "Level 2 not synchronized\0" + /* 46: 959, 15 */ "Level 3 halted\0" + /* 47: 974, 14 */ "Level 3 reset\0" + /* 48: 988, 25 */ "Link number out of range\0" + /* 49: 1013, 29 */ "Protocol driver not attached\0" + /* 50: 1042, 27 */ "No CSI structure available\0" + /* 51: 1069, 15 */ "Level 2 halted\0" + /* 52: 1084, 17 */ "Invalid exchange\0" + /* 53: 1101, 27 */ "Invalid request descriptor\0" + /* 54: 1128, 14 */ "Exchange full\0" + /* 55: 1142, 9 */ "No anode\0" + /* 56: 1151, 21 */ "Invalid request code\0" + /* 57: 1172, 13 */ "Invalid slot\0" + /* 58: 1185, 1 */ "\0" + /* 59: 1186, 21 */ "Bad font file format\0" + /* 60: 1207, 20 */ "Device not a stream\0" + /* 61: 1227, 18 */ "No data available\0" + /* 62: 1245, 14 */ "Timer expired\0" + /* 63: 1259, 25 */ "Out of streams resources\0" + /* 64: 1284, 30 */ "Machine is not on the network\0" + /* 65: 1314, 22 */ "Package not installed\0" + /* 66: 1336, 17 */ "Object is remote\0" + /* 67: 1353, 22 */ "Link has been severed\0" + /* 68: 1375, 16 */ "Advertise error\0" + /* 69: 1391, 14 */ "Srmount error\0" + /* 70: 1405, 28 */ "Communication error on send\0" + /* 71: 1433, 15 */ "Protocol error\0" + /* 72: 1448, 19 */ "Multihop attempted\0" + /* 73: 1467, 19 */ "RFS specific error\0" + /* 74: 1486, 12 */ "Bad message\0" + /* 75: 1498, 38 */ "Value too large for defined data type\0" + /* 76: 1536, 27 */ "Name not unique on network\0" + /* 77: 1563, 29 */ "File descriptor in bad state\0" + /* 78: 1592, 23 */ "Remote address changed\0" + /* 79: 1615, 39 */ "Can not access a needed shared library\0" + /* 80: 1654, 37 */ "Accessing a corrupted shared library\0" + /* 81: 1691, 32 */ ".lib section in a.out corrupted\0" + /* 82: 1723, 48 */ "Attempting to link in too many shared libraries\0" + /* 83: 1771, 38 */ "Cannot exec a shared library directly\0" + /* 84: 1809, 50 */ "Invalid or incomplete multibyte or wide character\0" + /* 85: 1859, 44 */ "Interrupted system call should be restarted\0" + /* 86: 1903, 19 */ "Streams pipe error\0" + /* 87: 1922, 15 */ "Too many users\0" + /* 88: 1937, 31 */ "Socket operation on non-socket\0" + /* 89: 1968, 29 */ "Destination address required\0" + /* 90: 1997, 17 */ "Message too long\0" + /* 91: 2014, 31 */ "Protocol wrong type for socket\0" + /* 92: 2045, 23 */ "Protocol not available\0" + /* 93: 2068, 23 */ "Protocol not supported\0" + /* 94: 2091, 26 */ "Socket type not supported\0" + /* 95: 2117, 24 */ "Operation not supported\0" + /* 96: 2141, 30 */ "Protocol family not supported\0" + /* 97: 2171, 41 */ "Address family not supported by protocol\0" + /* 98: 2212, 23 */ "Address already in use\0" + /* 99: 2235, 32 */ "Cannot assign requested address\0" + /* 100: 2267, 16 */ "Network is down\0" + /* 101: 2283, 23 */ "Network is unreachable\0" + /* 102: 2306, 36 */ "Network dropped connection on reset\0" + /* 103: 2342, 33 */ "Software caused connection abort\0" + /* 104: 2375, 25 */ "Connection reset by peer\0" + /* 105: 2400, 26 */ "No buffer space available\0" + /* 106: 2426, 40 */ "Transport endpoint is already connected\0" + /* 107: 2466, 36 */ "Transport endpoint is not connected\0" + /* 108: 2502, 46 */ "Cannot send after transport endpoint shutdown\0" + /* 109: 2548, 35 */ "Too many references: cannot splice\0" + /* 110: 2583, 21 */ "Connection timed out\0" + /* 111: 2604, 19 */ "Connection refused\0" + /* 112: 2623, 13 */ "Host is down\0" + /* 113: 2636, 17 */ "No route to host\0" + /* 114: 2653, 30 */ "Operation already in progress\0" + /* 115: 2683, 26 */ "Operation now in progress\0" + /* 116: 2709, 22 */ "Stale NFS file handle\0" + /* 117: 2731, 25 */ "Structure needs cleaning\0" + /* 118: 2756, 28 */ "Not a XENIX named type file\0" + /* 119: 2784, 30 */ "No XENIX semaphores available\0" + /* 120: 2814, 21 */ "Is a named type file\0" + /* 121: 2835, 17 */ "Remote I/O error\0" + /* 122: 2852, 20 */ "Disk quota exceeded\0" + /* 123: 2872, 16 */ "No medium found\0" + /* 124: 2888, 18 */ "Wrong medium type" +}; + +#endif +/**********************************************************************/ +#ifdef L_sys_errlist + +link_warning(_sys_errlist, "sys_nerr and sys_errlist are obsolete and uClibc support for them (in at least some configurations) will probably be unavailable in the near future.") + +int sys_nerr = _SYS_NERR; + +const char *const sys_errlist[] = { + _string_syserrmsgs + 0, + _string_syserrmsgs + 8, + _string_syserrmsgs + 32, + _string_syserrmsgs + 58, + _string_syserrmsgs + 74, + _string_syserrmsgs + 98, + _string_syserrmsgs + 117, + _string_syserrmsgs + 143, + _string_syserrmsgs + 166, + _string_syserrmsgs + 184, + _string_syserrmsgs + 204, + _string_syserrmsgs + 223, + _string_syserrmsgs + 256, + _string_syserrmsgs + 279, + _string_syserrmsgs + 297, + _string_syserrmsgs + 309, + _string_syserrmsgs + 331, + _string_syserrmsgs + 355, + _string_syserrmsgs + 367, + _string_syserrmsgs + 393, + _string_syserrmsgs + 408, + _string_syserrmsgs + 424, + _string_syserrmsgs + 439, + _string_syserrmsgs + 456, + _string_syserrmsgs + 486, + _string_syserrmsgs + 506, + _string_syserrmsgs + 537, + _string_syserrmsgs + 552, + _string_syserrmsgs + 567, + _string_syserrmsgs + 591, + _string_syserrmsgs + 604, + _string_syserrmsgs + 626, + _string_syserrmsgs + 641, + _string_syserrmsgs + 653, + _string_syserrmsgs + 686, + _string_syserrmsgs + 716, + _string_syserrmsgs + 742, + _string_syserrmsgs + 761, + _string_syserrmsgs + 780, + _string_syserrmsgs + 805, + _string_syserrmsgs + 825, + /* _string_syserrmsgs + 859, */ + NULL, /* glibc compatiblity :-( */ + _string_syserrmsgs + 860, + _string_syserrmsgs + 887, + _string_syserrmsgs + 906, + _string_syserrmsgs + 934, + _string_syserrmsgs + 959, + _string_syserrmsgs + 974, + _string_syserrmsgs + 988, + _string_syserrmsgs + 1013, + _string_syserrmsgs + 1042, + _string_syserrmsgs + 1069, + _string_syserrmsgs + 1084, + _string_syserrmsgs + 1101, + _string_syserrmsgs + 1128, + _string_syserrmsgs + 1142, + _string_syserrmsgs + 1151, + _string_syserrmsgs + 1172, + /* _string_syserrmsgs + 1185, */ + NULL, /* glibc compatiblity :-( */ + _string_syserrmsgs + 1186, + _string_syserrmsgs + 1207, + _string_syserrmsgs + 1227, + _string_syserrmsgs + 1245, + _string_syserrmsgs + 1259, + _string_syserrmsgs + 1284, + _string_syserrmsgs + 1314, + _string_syserrmsgs + 1336, + _string_syserrmsgs + 1353, + _string_syserrmsgs + 1375, + _string_syserrmsgs + 1391, + _string_syserrmsgs + 1405, + _string_syserrmsgs + 1433, + _string_syserrmsgs + 1448, + _string_syserrmsgs + 1467, + _string_syserrmsgs + 1486, + _string_syserrmsgs + 1498, + _string_syserrmsgs + 1536, + _string_syserrmsgs + 1563, + _string_syserrmsgs + 1592, + _string_syserrmsgs + 1615, + _string_syserrmsgs + 1654, + _string_syserrmsgs + 1691, + _string_syserrmsgs + 1723, + _string_syserrmsgs + 1771, + _string_syserrmsgs + 1809, + _string_syserrmsgs + 1859, + _string_syserrmsgs + 1903, + _string_syserrmsgs + 1922, + _string_syserrmsgs + 1937, + _string_syserrmsgs + 1968, + _string_syserrmsgs + 1997, + _string_syserrmsgs + 2014, + _string_syserrmsgs + 2045, + _string_syserrmsgs + 2068, + _string_syserrmsgs + 2091, + _string_syserrmsgs + 2117, + _string_syserrmsgs + 2141, + _string_syserrmsgs + 2171, + _string_syserrmsgs + 2212, + _string_syserrmsgs + 2235, + _string_syserrmsgs + 2267, + _string_syserrmsgs + 2283, + _string_syserrmsgs + 2306, + _string_syserrmsgs + 2342, + _string_syserrmsgs + 2375, + _string_syserrmsgs + 2400, + _string_syserrmsgs + 2426, + _string_syserrmsgs + 2466, + _string_syserrmsgs + 2502, + _string_syserrmsgs + 2548, + _string_syserrmsgs + 2583, + _string_syserrmsgs + 2604, + _string_syserrmsgs + 2623, + _string_syserrmsgs + 2636, + _string_syserrmsgs + 2653, + _string_syserrmsgs + 2683, + _string_syserrmsgs + 2709, + _string_syserrmsgs + 2731, + _string_syserrmsgs + 2756, + _string_syserrmsgs + 2784, + _string_syserrmsgs + 2814, + _string_syserrmsgs + 2835, + _string_syserrmsgs + 2852, + _string_syserrmsgs + 2872, + _string_syserrmsgs + 2888, +}; + +#endif /**********************************************************************/ #ifdef L_wmemcpy #define L_memcpy @@ -255,7 +543,7 @@ Wchar *Wstrncat(Wchar * __restrict s1, register const Wchar * __restrict s2, #ifdef L_memcmp #ifndef L_wmemcmp -weak_alias(memcmp,bcmp) +weak_alias(memcmp,bcmp); #endif int Wmemcmp(const Wvoid *s1, const Wvoid *s2, size_t n) @@ -418,7 +706,7 @@ Wvoid *Wmemchr(const Wvoid *s, Wint c, size_t n) #ifdef L_strchr #ifndef L_wcschr -weak_alias(strchr,index) +weak_alias(strchr,index); #endif Wchar *Wstrchr(register const Wchar *s, Wint c) @@ -492,7 +780,7 @@ Wchar *Wstrpbrk(const Wchar *s1, const Wchar *s2) #ifdef L_strrchr #ifndef L_wcsrchr -weak_alias(strrchr,rindex) +weak_alias(strrchr,rindex); #endif Wchar *Wstrrchr(register const Wchar *s, Wint c) @@ -548,7 +836,7 @@ size_t Wstrspn(const Wchar *s1, const Wchar *s2) /* NOTE: This is the simple-minded O(len(s1) * len(s2)) worst-case approach. */ #ifdef L_wcsstr -weak_alias(wcsstr,wcswcs) +weak_alias(wcsstr,wcswcs); #endif Wchar *Wstrstr(const Wchar *s1, const Wchar *s2) @@ -672,11 +960,6 @@ Wvoid *Wmemset(Wvoid *s, Wint c, size_t n) } #undef np -#endif -/**********************************************************************/ -#ifdef L_strerror -#error implement strerror -/* char *strerror(int errnum); */ #endif /**********************************************************************/ #ifdef L_wcslen @@ -888,10 +1171,92 @@ Wchar *Wstrdup(register const Wchar *s1) return s; } +#endif +/**********************************************************************/ +#ifdef L_strerror + +char *strerror(int errnum) +{ + static char buf[_SYS_ERRMSG_MAXLEN]; + + return (_susv3_strerror_r(errnum, buf, sizeof(buf)) == 0) ? buf : NULL; +} + +#endif +/**********************************************************************/ +/* SUSv3 functions. */ +/**********************************************************************/ +#ifdef L__susv3_strerror_r + +int _susv3_strerror_r(int errnum, char *strerrbuf, size_t buflen) +{ + register char *s; + int i, retval; + char buf[_SYS_ERRMSG_MAXLEN]; + static const char unknown[14] = { + 'U', 'n', 'k', 'n', 'o', 'w', 'n', ' ', 'e', 'r', 'r', 'o', 'r', ' ' + }; + + retval = EINVAL; + + if (((unsigned int) errnum) < _SYS_NERR) { + /* Trade time for space. This function should rarely be called + * so rather than keeping an array of pointers for the different + * messages, just run through the buffer until we find the + * correct string. */ + for (s = (char *) _string_syserrmsgs, i = errnum ; i ; ++s) { + if (!*s) { + --i; + } + } + if (*s) { /* Make sure we have an actual message. */ + retval = 0; + goto GOT_MESG; + } + } + + s = _int10tostr(buf+sizeof(buf)-1, errnum) - sizeof(unknown); + memcpy(s, unknown, sizeof(unknown)); + + GOT_MESG: + if (!strerrbuf) { /* SUSv3 */ + buflen = 0; + } + i = strlen(s) + 1; + if (i > buflen) { + i = buflen; + retval = ERANGE; + } + + if (i) { + memcpy(strerrbuf, s, i); + strerrbuf[i-1] = 0; /* In case buf was too small. */ + } + + if (retval) { + __set_errno(retval); + } + + return retval; +} + #endif /**********************************************************************/ /* GNU extension functions. */ /**********************************************************************/ +#ifdef L__glibc_strerror_r + +weak_alias(_glibc_strerror_r,__strerror_r); + +char *_glibc_strerror_r(int errnum, char *strerrbuf, size_t buflen) +{ + _susv3_strerror_r(errnum, strerrbuf, buflen); + + return strerrbuf; +} + +#endif +/**********************************************************************/ #ifdef L_wmempcpy #define L_mempcpy #define Wmempcpy wmempcpy @@ -903,7 +1268,7 @@ Wchar *Wstrdup(register const Wchar *s1) #ifndef L_wmempcpy /* uClibc's old string implementation did this to cater to some app. */ -weak_alias(mempcpy,__mempcpy) +weak_alias(mempcpy,__mempcpy); #endif Wvoid *Wmempcpy(Wvoid * __restrict s1, const Wvoid * __restrict s2, size_t n) diff --git a/libc/sysdeps/linux/common/bits/uClibc_stdio.h b/libc/sysdeps/linux/common/bits/uClibc_stdio.h index 16a7da876..b8812e7b0 100644 --- a/libc/sysdeps/linux/common/bits/uClibc_stdio.h +++ b/libc/sysdeps/linux/common/bits/uClibc_stdio.h @@ -467,14 +467,6 @@ typedef enum { __UIM_UPPER = 'A' - 10, } __UIM_CASE; -/* WARNING!!! While similar to the glibc strerror_r function, the - * following function is not the same. It expects "unknown" error - * strings will fit in the buffer passed. Also, the return value - * may not be == buf, as unknown strings are "right-justified" in - * the buf due to the way _int10stostr works. */ - -extern char *_stdio_strerror_r(int err, char *buf, size_t buflen); - /* Write a NULL-terminated list of "char *" args to file descriptor fd. * For an example of usage, see __assert.c. */ -- cgit v1.2.3