Blame m4/intl-thread-locale.m4

Packit Service 4684c1
# intl-thread-locale.m4 serial 8
Packit Service 4684c1
dnl Copyright (C) 2015-2020 Free Software Foundation, Inc.
Packit Service 4684c1
dnl This file is free software; the Free Software Foundation
Packit Service 4684c1
dnl gives unlimited permission to copy and/or distribute it,
Packit Service 4684c1
dnl with or without modifications, as long as this notice is preserved.
Packit Service 4684c1
dnl
Packit Service 4684c1
dnl This file can be used in projects which are not available under
Packit Service 4684c1
dnl the GNU General Public License or the GNU Lesser General Public
Packit Service 4684c1
dnl License but which still want to provide support for the GNU gettext
Packit Service 4684c1
dnl functionality.
Packit Service 4684c1
dnl Please note that the actual code of the GNU gettext library is covered
Packit Service 4684c1
dnl by the GNU Lesser General Public License, and the rest of the GNU
Packit Service 4684c1
dnl gettext package is covered by the GNU General Public License.
Packit Service 4684c1
dnl They are *not* in the public domain.
Packit Service 4684c1
Packit Service 4684c1
dnl Check how to retrieve the name of a per-thread locale (POSIX locale_t).
Packit Service 4684c1
dnl Sets gt_nameless_locales.
Packit Service 4684c1
AC_DEFUN([gt_INTL_THREAD_LOCALE_NAME],
Packit Service 4684c1
[
Packit Service 4684c1
  AC_REQUIRE([AC_CANONICAL_HOST])
Packit Service 4684c1
Packit Service 4684c1
  dnl Persuade Solaris <locale.h> to define 'locale_t'.
Packit Service 4684c1
  AC_REQUIRE([AC_USE_SYSTEM_EXTENSIONS])
Packit Service 4684c1
Packit Service 4684c1
  dnl Test whether uselocale() exists and works at all.
Packit Service 4684c1
  gt_FUNC_USELOCALE
Packit Service 4684c1
Packit Service 4684c1
  dnl On OpenBSD >= 6.2, the locale_t type and the uselocale(), newlocale(),
Packit Service 4684c1
  dnl duplocale(), freelocale() functions exist but are effectively useless,
Packit Service 4684c1
  dnl because the locale_t value depends only on the LC_CTYPE category of the
Packit Service 4684c1
  dnl locale and furthermore contains only one bit of information (it
Packit Service 4684c1
  dnl distinguishes the "C" locale from the *.UTF-8 locales). See
Packit Service 4684c1
  dnl <https://cvsweb.openbsd.org/src/lib/libc/locale/newlocale.c?rev=1.1&content-type=text/x-cvsweb-markup>.
Packit Service 4684c1
  dnl In the setlocale() implementation they have thought about the programs
Packit Service 4684c1
  dnl that use the API ("Even though only LC_CTYPE has any effect in the
Packit Service 4684c1
  dnl OpenBSD base system, store complete information about the global locale,
Packit Service 4684c1
  dnl such that third-party software can access it"), but for uselocale()
Packit Service 4684c1
  dnl they did not think about the programs.
Packit Service 4684c1
  dnl In this situation, even the HAVE_NAMELESS_LOCALES support does not work.
Packit Service 4684c1
  dnl So, define HAVE_FAKE_LOCALES and disable all locale_t support.
Packit Service 4684c1
  case "$gt_cv_func_uselocale_works" in
Packit Service 4684c1
    *yes)
Packit Service 4684c1
      AC_CHECK_HEADERS_ONCE([xlocale.h])
Packit Service 4684c1
      AC_CACHE_CHECK([for fake locale system (OpenBSD)],
Packit Service 4684c1
        [gt_cv_locale_fake],
Packit Service 4684c1
        [AC_RUN_IFELSE(
Packit Service 4684c1
           [AC_LANG_SOURCE([[
Packit Service 4684c1
#include <locale.h>
Packit Service 4684c1
#if HAVE_XLOCALE_H
Packit Service 4684c1
# include <xlocale.h>
Packit Service 4684c1
#endif
Packit Service 4684c1
int main ()
Packit Service 4684c1
{
Packit Service 4684c1
  locale_t loc1, loc2;
Packit Service 4684c1
  if (setlocale (LC_ALL, "de_DE.UTF-8") == NULL) return 1;
Packit Service 4684c1
  if (setlocale (LC_ALL, "fr_FR.UTF-8") == NULL) return 1;
Packit Service 4684c1
  loc1 = newlocale (LC_ALL_MASK, "de_DE.UTF-8", (locale_t)0);
Packit Service 4684c1
  loc2 = newlocale (LC_ALL_MASK, "fr_FR.UTF-8", (locale_t)0);
Packit Service 4684c1
  return !(loc1 == loc2);
Packit Service 4684c1
}]])],
Packit Service 4684c1
           [gt_cv_locale_fake=yes],
Packit Service 4684c1
           [gt_cv_locale_fake=no],
Packit Service 4684c1
           [dnl Guess the locale system is fake only on OpenBSD.
Packit Service 4684c1
            case "$host_os" in
Packit Service 4684c1
              openbsd*) gt_cv_locale_fake="guessing yes" ;;
Packit Service 4684c1
              *)        gt_cv_locale_fake="guessing no" ;;
Packit Service 4684c1
            esac
Packit Service 4684c1
           ])
Packit Service 4684c1
        ])
Packit Service 4684c1
      ;;
Packit Service 4684c1
    *) gt_cv_locale_fake=no ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
  case "$gt_cv_locale_fake" in
Packit Service 4684c1
    *yes)
Packit Service 4684c1
      AC_DEFINE([HAVE_FAKE_LOCALES], [1],
Packit Service 4684c1
        [Define if the locale_t type contains insufficient information, as on OpenBSD.])
Packit Service 4684c1
      ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
Packit Service 4684c1
  case "$gt_cv_func_uselocale_works" in
Packit Service 4684c1
    *yes)
Packit Service 4684c1
      AC_CACHE_CHECK([for Solaris 11.4 locale system],
Packit Service 4684c1
        [gt_cv_locale_solaris114],
Packit Service 4684c1
        [case "$host_os" in
Packit Service 4684c1
           solaris*)
Packit Service 4684c1
             dnl Test whether <locale.h> defines locale_t as a typedef of
Packit Service 4684c1
             dnl 'struct _LC_locale_t **' (whereas Illumos defines it as a
Packit Service 4684c1
             dnl typedef of 'struct _locale *').
Packit Service 4684c1
             dnl Another possible test would be to include <sys/localedef.h>
Packit Service 4684c1
             dnl and test whether it defines the _LC_core_data_locale_t type.
Packit Service 4684c1
             dnl This type was added in Solaris 11.4.
Packit Service 4684c1
             AC_COMPILE_IFELSE(
Packit Service 4684c1
               [AC_LANG_PROGRAM([[
Packit Service 4684c1
                  #include <locale.h>
Packit Service 4684c1
                  struct _LC_locale_t *x;
Packit Service 4684c1
                  locale_t y;
Packit Service 4684c1
                ]],
Packit Service 4684c1
                [[*y = x;]])],
Packit Service 4684c1
               [gt_cv_locale_solaris114=yes],
Packit Service 4684c1
               [gt_cv_locale_solaris114=no])
Packit Service 4684c1
             ;;
Packit Service 4684c1
           *) gt_cv_locale_solaris114=no ;;
Packit Service 4684c1
         esac
Packit Service 4684c1
        ])
Packit Service 4684c1
      ;;
Packit Service 4684c1
    *) gt_cv_locale_solaris114=no ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
  if test $gt_cv_locale_solaris114 = yes; then
Packit Service 4684c1
    AC_DEFINE([HAVE_SOLARIS114_LOCALES], [1],
Packit Service 4684c1
      [Define if the locale_t type is as on Solaris 11.4.])
Packit Service 4684c1
  fi
Packit Service 4684c1
Packit Service 4684c1
  dnl Solaris 12 will maybe provide getlocalename_l.  If it does, it will
Packit Service 4684c1
  dnl improve the implementation of gl_locale_name_thread(), by removing
Packit Service 4684c1
  dnl the use of undocumented structures.
Packit Service 4684c1
  case "$gt_cv_func_uselocale_works" in
Packit Service 4684c1
    *yes)
Packit Service 4684c1
      AC_CHECK_FUNCS([getlocalename_l])
Packit Service 4684c1
      ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
Packit Service 4684c1
  dnl This code is for platforms where the locale_t type does not provide access
Packit Service 4684c1
  dnl to the name of each locale category.  This code has the drawback that it
Packit Service 4684c1
  dnl requires the gnulib overrides of 'newlocale', 'duplocale', 'freelocale',
Packit Service 4684c1
  dnl which is a problem for GNU libunistring.  Therefore try hard to avoid
Packit Service 4684c1
  dnl enabling this code!
Packit Service 4684c1
  gt_nameless_locales=no
Packit Service 4684c1
  case "$host_os" in
Packit Service 4684c1
    dnl It's needed on AIX 7.2.
Packit Service 4684c1
    aix*)
Packit Service 4684c1
      gt_nameless_locales=yes
Packit Service 4684c1
      AC_DEFINE([HAVE_NAMELESS_LOCALES], [1],
Packit Service 4684c1
        [Define if the locale_t type does not contain the name of each locale category.])
Packit Service 4684c1
      ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
])
Packit Service 4684c1
Packit Service 4684c1
dnl Tests whether uselocale() exists and is usable.
Packit Service 4684c1
dnl Sets gt_cv_func_uselocale_works. Defines HAVE_WORKING_USELOCALE.
Packit Service 4684c1
AC_DEFUN([gt_FUNC_USELOCALE],
Packit Service 4684c1
[
Packit Service 4684c1
  AC_REQUIRE([AC_CANONICAL_HOST]) dnl for cross-compiles
Packit Service 4684c1
Packit Service 4684c1
  dnl Persuade glibc and Solaris <locale.h> to define 'locale_t'.
Packit Service 4684c1
  AC_REQUIRE([AC_USE_SYSTEM_EXTENSIONS])
Packit Service 4684c1
Packit Service 4684c1
  AC_CHECK_FUNCS_ONCE([uselocale])
Packit Service 4684c1
Packit Service 4684c1
  dnl On AIX 7.2, the uselocale() function is not documented and leads to
Packit Service 4684c1
  dnl crashes in subsequent setlocale() invocations.
Packit Service 4684c1
  dnl In 2019, some versions of z/OS lack the locale_t type and have a broken
Packit Service 4684c1
  dnl uselocale function.
Packit Service 4684c1
  if test $ac_cv_func_uselocale = yes; then
Packit Service 4684c1
    AC_CHECK_HEADERS_ONCE([xlocale.h])
Packit Service 4684c1
    AC_CACHE_CHECK([whether uselocale works],
Packit Service 4684c1
      [gt_cv_func_uselocale_works],
Packit Service 4684c1
      [AC_RUN_IFELSE(
Packit Service 4684c1
         [AC_LANG_SOURCE([[
Packit Service 4684c1
#include <locale.h>
Packit Service 4684c1
#if HAVE_XLOCALE_H
Packit Service 4684c1
# include <xlocale.h>
Packit Service 4684c1
#endif
Packit Service 4684c1
locale_t loc1;
Packit Service 4684c1
int main ()
Packit Service 4684c1
{
Packit Service 4684c1
  uselocale (NULL);
Packit Service 4684c1
  setlocale (LC_ALL, "en_US.UTF-8");
Packit Service 4684c1
  return 0;
Packit Service 4684c1
}]])],
Packit Service 4684c1
         [gt_cv_func_uselocale_works=yes],
Packit Service 4684c1
         [gt_cv_func_uselocale_works=no],
Packit Service 4684c1
         [# Guess no on AIX and z/OS, yes otherwise.
Packit Service 4684c1
          case "$host_os" in
Packit Service 4684c1
            aix* | openedition*) gt_cv_func_uselocale_works="guessing no" ;;
Packit Service 4684c1
            *)                   gt_cv_func_uselocale_works="guessing yes" ;;
Packit Service 4684c1
          esac
Packit Service 4684c1
         ])
Packit Service 4684c1
      ])
Packit Service 4684c1
  else
Packit Service 4684c1
    gt_cv_func_uselocale_works=no
Packit Service 4684c1
  fi
Packit Service 4684c1
  case "$gt_cv_func_uselocale_works" in
Packit Service 4684c1
    *yes)
Packit Service 4684c1
      AC_DEFINE([HAVE_WORKING_USELOCALE], [1],
Packit Service 4684c1
        [Define if the uselocale function exists any may safely be called.])
Packit Service 4684c1
      ;;
Packit Service 4684c1
  esac
Packit Service 4684c1
])