From 3513be550138efef00148289be4a266c21b9ff0b Mon Sep 17 00:00:00 2001 From: Bruno Haible Date: Thu, 23 May 2024 01:10:18 +0200 Subject: [PATCH] iconv: Reject the broken macOS 14.4 iconv implementation. Reported by Daniel Collins at . * m4/iconv.m4 (AM_ICONV_LINK): In the test "for working iconv", test against the macOS 14.4 iconv bug. * doc/posix-functions/iconv.texi: Document the bug. --- ChangeLog | 9 +++++++ doc/posix-functions/iconv.texi | 2 +- m4/iconv.m4 | 43 ++++++++++++++++++++++++++++------ 3 files changed, 46 insertions(+), 8 deletions(-) diff --git a/ChangeLog b/ChangeLog index 098fe742b2..41109e1fac 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,12 @@ +2024-05-22 Bruno Haible + + iconv: Reject the broken macOS 14.4 iconv implementation. + Reported by Daniel Collins at + . + * m4/iconv.m4 (AM_ICONV_LINK): In the test "for working iconv", test + against the macOS 14.4 iconv bug. + * doc/posix-functions/iconv.texi: Document the bug. + 2024-05-22 Bruno Haible stdlib: Handle glibc special invocation conventions correctly. diff --git a/doc/posix-functions/iconv.texi b/doc/posix-functions/iconv.texi index c77b4492dd..29228273aa 100644 --- a/doc/posix-functions/iconv.texi +++ b/doc/posix-functions/iconv.texi @@ -18,7 +18,7 @@ Portability problems handled by Gnulib @itemize @item Failures are not distinguishable from successful returns on some platforms: -AIX 5.1..7.2, Solaris 10. +macOS 14.4, AIX 5.1..7.2, Solaris 10. @item A buffer overrun can occur on some platforms: AIX 6.1..7.1. diff --git a/m4/iconv.m4 b/m4/iconv.m4 index ff5d526113..0cfaeeb7c7 100644 --- a/m4/iconv.m4 +++ b/m4/iconv.m4 @@ -1,5 +1,5 @@ -# iconv.m4 serial 26 -dnl Copyright (C) 2000-2002, 2007-2014, 2016-2023 Free Software Foundation, +# iconv.m4 serial 26.1 +dnl Copyright (C) 2000-2002, 2007-2014, 2016-2024 Free Software Foundation, dnl Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -74,7 +74,7 @@ AC_DEFUN([AM_ICONV_LINK], if test "$am_cv_func_iconv" = yes; then AC_CACHE_CHECK([for working iconv], [am_cv_func_iconv_works], [ dnl This tests against bugs in AIX 5.1, AIX 6.1..7.1, HP-UX 11.11, - dnl Solaris 10. + dnl Solaris 10, macOS 14.4. am_save_LIBS="$LIBS" if test $am_cv_lib_iconv = yes; then LIBS="$LIBS $LIBICONV" @@ -113,6 +113,35 @@ AC_DEFUN([AM_ICONV_LINK], iconv_close (cd_utf8_to_88591); } } + /* Test against macOS 14.4 bug: Failures are not distinguishable from + successful returns. + POSIX:2018 says: "The iconv() function shall ... return the number of + non-identical conversions performed." + But here, the conversion always does transliteration (the suffixes + "//TRANSLIT" and "//IGNORE" have no effect, nor does iconvctl()) and + does not report when it does a non-identical conversion. */ + { + iconv_t cd_utf8_to_88591 = iconv_open ("ISO-8859-1", "UTF-8"); + if (cd_utf8_to_88591 != (iconv_t)(-1)) + { + static ICONV_CONST char input[] = "\305\202"; /* LATIN SMALL LETTER L WITH STROKE */ + char buf[10]; + ICONV_CONST char *inptr = input; + size_t inbytesleft = strlen (input); + char *outptr = buf; + size_t outbytesleft = sizeof (buf); + size_t res = iconv (cd_utf8_to_88591, + &inptr, &inbytesleft, + &outptr, &outbytesleft); + /* Here: + With glibc, GNU libiconv (including macOS up to 13): res == (size_t)-1, errno == EILSEQ. + With musl libc, NetBSD 10, Solaris 11: res == 1. + With macOS 14.4: res == 0, output is "l". */ + if (res == 0) + result |= 2; + iconv_close (cd_utf8_to_88591); + } + } /* Test against Solaris 10 bug: Failures are not distinguishable from successful returns. */ { @@ -129,7 +158,7 @@ AC_DEFUN([AM_ICONV_LINK], &inptr, &inbytesleft, &outptr, &outbytesleft); if (res == 0) - result |= 2; + result |= 4; iconv_close (cd_ascii_to_88591); } } @@ -148,7 +177,7 @@ AC_DEFUN([AM_ICONV_LINK], &inptr, &inbytesleft, &outptr, &outbytesleft); if (res != (size_t)(-1) || outptr - buf > 1 || buf[1] != (char)0xAD) - result |= 4; + result |= 8; iconv_close (cd_88591_to_utf8); } } @@ -168,7 +197,7 @@ AC_DEFUN([AM_ICONV_LINK], &inptr, &inbytesleft, &outptr, &outbytesleft); if ((int)res > 0) - result |= 8; + result |= 16; iconv_close (cd_88591_to_utf8); } } @@ -186,7 +215,7 @@ AC_DEFUN([AM_ICONV_LINK], iconv_t cd4 = iconv_open ("utf8", "eucJP"); if (cd1 == (iconv_t)(-1) && cd2 == (iconv_t)(-1) && cd3 == (iconv_t)(-1) && cd4 == (iconv_t)(-1)) - result |= 16; + result |= 32; if (cd1 != (iconv_t)(-1)) iconv_close (cd1); if (cd2 != (iconv_t)(-1)) -- 2.39.5