diff --git a/lib/libc/include/libc_private.h b/lib/libc/include/libc_private.h --- a/lib/libc/include/libc_private.h +++ b/lib/libc/include/libc_private.h @@ -374,5 +374,7 @@ struct _xlocale; struct __nl_cat_d *__catopen_l(const char *name, int type, struct _xlocale *locale); +int __strerror_rl(int errnum, char *strerrbuf, size_t buflen, + struct _xlocale *locale); #endif /* _LIBC_PRIVATE_H_ */ diff --git a/lib/libc/stdio/vfprintf.c b/lib/libc/stdio/vfprintf.c --- a/lib/libc/stdio/vfprintf.c +++ b/lib/libc/stdio/vfprintf.c @@ -312,6 +312,8 @@ int width; /* width from format (%8d), or 0 */ int prec; /* precision from format; <0 for N/A */ int saved_errno; + int error; + char errnomsg[NL_TEXTMAX]; char sign; /* sign prefix (' ', '+', '-', or \0) */ struct grouping_state gs; /* thousands' grouping info */ @@ -829,7 +831,9 @@ break; #endif /* !NO_FLOATING_POINT */ case 'm': - cp = strerror(saved_errno); + error = strerror_rl(saved_errno, errnomsg, + sizeof(errnomsg), locale); + cp = error == 0 ? errnomsg : ""; size = (prec >= 0) ? strnlen(cp, prec) : strlen(cp); sign = '\0'; break; diff --git a/lib/libc/stdio/xprintf_errno.c b/lib/libc/stdio/xprintf_errno.c --- a/lib/libc/stdio/xprintf_errno.c +++ b/lib/libc/stdio/xprintf_errno.c @@ -38,7 +38,8 @@ #include "printf.h" int -__printf_arginfo_errno(const struct printf_info *pi __unused, size_t n, int *argt) +__printf_arginfo_errno(const struct printf_info *pi __unused, size_t n, + int *argt) { assert(n >= 1); @@ -47,17 +48,19 @@ } int -__printf_render_errno(struct __printf_io *io, const struct printf_info *pi __unused, const void *const *arg) +__printf_render_errno(struct __printf_io *io, const struct printf_info *pi + __unused, const void *const *arg) { int ret, error; char buf[64]; + char errnomsg[NL_TEXTMAX]; const char *p; ret = 0; error = *((const int *)arg[0]); if (error >= 0 && error < __hidden_sys_nerr) { - p = strerror(error); - return (__printf_out(io, pi, p, strlen(p))); + strerror_r(error, errnomsg, sizeof(errnomsg)); + return (__printf_out(io, pi, errnomsg, strlen(errnomsg))); } sprintf(buf, "errno=%d/0x%x", error, error); ret += __printf_out(io, pi, buf, strlen(buf)); diff --git a/lib/libc/string/strerror.c b/lib/libc/string/strerror.c --- a/lib/libc/string/strerror.c +++ b/lib/libc/string/strerror.c @@ -74,8 +74,8 @@ strlcat(buf, t, len); } -static int -strerror_rl(int errnum, char *strerrbuf, size_t buflen, locale_t locale) +int +__strerror_rl(int errnum, char *strerrbuf, size_t buflen, locale_t locale) { int retval = 0; #if defined(NLS) @@ -116,7 +116,7 @@ int strerror_r(int errnum, char *strerrbuf, size_t buflen) { - return (strerror_rl(errnum, strerrbuf, buflen, __get_locale())); + return (__strerror_rl(errnum, strerrbuf, buflen, __get_locale())); } char * @@ -124,7 +124,7 @@ { static _Thread_local char ebuf[NL_TEXTMAX]; - if (strerror_rl(num, ebuf, sizeof(ebuf), locale) != 0) + if (__strerror_rl(num, ebuf, sizeof(ebuf), locale) != 0) errno = EINVAL; return (ebuf); } @@ -134,7 +134,7 @@ { static char ebuf[NL_TEXTMAX]; - if (strerror_rl(num, ebuf, sizeof(ebuf), __get_locale()) != 0) + if (__strerror_rl(num, ebuf, sizeof(ebuf), __get_locale()) != 0) errno = EINVAL; return (ebuf); }