From fffbcb21034420450aecd7468d520c90568d6834 Mon Sep 17 00:00:00 2001 From: Bruno Haible Date: Thu, 2 Mar 2023 20:52:16 +0100 Subject: [PATCH] mkfifoat: Fix crash on macOS 12. * m4/gnulib-common.m4 (gl_PREPARE_CHECK_FUNCS_MACOS, gl_CHECK_FUNCS_MACOS): New macros. * m4/mkfifoat.m4 (gl_FUNC_MKFIFOAT): Test for mknodat and mkfifoat using gl_CHECK_FUNCS_MACOS instead of AC_CHECK_FUNCS_ONCE. --- ChangeLog | 8 +++ m4/gnulib-common.m4 | 123 +++++++++++++++++++++++++++++++++++++++++++- m4/mkfifoat.m4 | 7 +-- 3 files changed, 134 insertions(+), 4 deletions(-) diff --git a/ChangeLog b/ChangeLog index 74eabffda2..657c1a2b2b 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +2023-02-10 Bruno Haible + + mkfifoat: Fix crash on macOS 12. + * m4/gnulib-common.m4 (gl_PREPARE_CHECK_FUNCS_MACOS, + gl_CHECK_FUNCS_MACOS): New macros. + * m4/mkfifoat.m4 (gl_FUNC_MKFIFOAT): Test for mknodat and mkfifoat using + gl_CHECK_FUNCS_MACOS instead of AC_CHECK_FUNCS_ONCE. + 2023-02-10 Bruno Haible chown, lchown, fchownat tests: Avoid test failure on macOS 12. diff --git a/m4/gnulib-common.m4 b/m4/gnulib-common.m4 index 99ec9bc7c3..260870bee4 100644 --- a/m4/gnulib-common.m4 +++ b/m4/gnulib-common.m4 @@ -1,4 +1,4 @@ -# gnulib-common.m4 serial 73.5 +# gnulib-common.m4 serial 73.6 dnl Copyright (C) 2007-2023 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -1084,6 +1084,127 @@ AC_DEFUN([gl_CONDITIONAL_HEADER], m4_popdef([gl_header_name]) ]) +dnl Preparations for gl_CHECK_FUNCS_MACOS. +AC_DEFUN([gl_PREPARE_CHECK_FUNCS_MACOS], +[ + AC_REQUIRE([AC_CANONICAL_HOST]) + AC_REQUIRE([gl_COMPILER_CLANG]) + AC_CACHE_CHECK([for compiler option needed when checking for future declarations], + [gl_cv_compiler_check_future_option], + [case "$host_os" in + dnl This is only needed on macOS. + darwin*) + if test $gl_cv_compiler_clang = yes; then + dnl Test whether the compiler supports the option + dnl '-Werror=unguarded-availability-new'. + save_ac_compile="$ac_compile" + ac_compile="$ac_compile -Werror=unguarded-availability-new" + AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[]],[[]])], + [gl_cv_compiler_check_future_option='-Werror=unguarded-availability-new'], + [gl_cv_compiler_check_future_option=none]) + ac_compile="$save_ac_compile" + else + gl_cv_compiler_check_future_option=none + fi + ;; + *) gl_cv_compiler_check_future_option=none ;; + esac + ]) +]) + +dnl gl_CHECK_FUNCS_MACOS([func], [[#include ]]) +dnl is like AC_CHECK_FUNCS([func]), taking into account a portability problem +dnl on macOS. +dnl +dnl When code is compiled on macOS, it is in the context of a certain minimum +dnl macOS version, that can be set through the option '-mmacosx-version-min='. +dnl In other words, you don't compile for a specific version of macOS. You +dnl compile for all versions of macOS, onwards from the given version. +dnl Thus, the question "does the OS have the function func" has three possible +dnl answers: +dnl - yes, in all versions starting from the given version, +dnl - no, in no version, +dnl - not in the given version, but in a later version of macOS. +dnl +dnl In detail, this works as follows: +dnl If func was added to, say, macOS version 13, then the libc has the +dnl symbol func always, whereas the header file declares func +dnl conditionally with a special availability attribute: +dnl ... func (...) __attribute__((availability(macos,introduced=13.0))); +dnl Thus, when compiling with "clang mmacosx-version-min=13", there is no +dnl warning about the use of func, and the resulting binary +dnl - runs fine on macOS 13, +dnl - aborts with a dyld "Symbol not found" message on macOS 12. +dnl Whereas, when compiling with "clang mmacosx-version-min=12", there is a +dnl warning: 'func' is only available on macOS 13.0 or newer +dnl [-Wunguarded-availability-new], +dnl and the resulting binary +dnl - runs fine on macOS 13, +dnl - crashes with a SIGSEGV (signal 11) on macOS 12. +dnl +dnl This macro sets two variables: +dnl - gl_cv_onwards_func_ to yes / no / "future OS version" +dnl - ac_cv_func_ to yes / no / no +dnl The first variable allows to distinguish all three cases. +dnl The second variable is set, so that an invocation +dnl gl_CHECK_FUNCS_MACOS([func], [[#include ]]) +dnl can be used as a drop-in replacement for +dnl AC_CHECK_FUNCS([func]). +AC_DEFUN([gl_CHECK_FUNCS_MACOS], +[ + AC_REQUIRE([AC_CANONICAL_HOST]) + AC_REQUIRE([gl_PREPARE_CHECK_FUNCS_MACOS]) + AC_CACHE_CHECK([for [$1]], + [[gl_cv_onwards_func_][$1]], + [gl_SILENT([ + case "$host_os" in + darwin*) + if test "x$gl_cv_compiler_check_future_option" != "xnone"; then + dnl Use a compile test, not a link test. + save_ac_compile="$ac_compile" + ac_compile="$ac_compile $gl_cv_compiler_check_future_option" + save_ac_compile_for_check_decl="$ac_compile_for_check_decl" + ac_compile_for_check_decl="$ac_compile_for_check_decl $gl_cv_compiler_check_future_option" + unset [ac_cv_have_decl_][$1] + AC_CHECK_DECL([$1], , , [$2]) + ac_compile="$save_ac_compile" + ac_compile_for_check_decl="$save_ac_compile_for_check_decl" + [ac_cv_func_][$1]="$[ac_cv_have_decl_][$1]" + if test $[ac_cv_func_][$1] = yes; then + [gl_cv_onwards_func_][$1]=yes + else + unset [ac_cv_have_decl_][$1] + AC_CHECK_DECL([$1], , , [$2]) + if test $[ac_cv_have_decl_][$1] = yes; then + [gl_cv_onwards_func_][$1]='future OS version' + else + [gl_cv_onwards_func_][$1]=no + fi + fi + else + AC_CHECK_FUNC([$1]) + [gl_cv_onwards_func_][$1]=$[ac_cv_func_][$1] + fi + ;; + *) + AC_CHECK_FUNC([$1]) + [gl_cv_onwards_func_][$1]=$[ac_cv_func_][$1] + ;; + esac + ]) + ]) + case "$[gl_cv_onwards_func_][$1]" in + future*) [ac_cv_func_][$1]=no ;; + *) [ac_cv_func_][$1]=$[gl_cv_onwards_func_][$1] ;; + esac + if test $[ac_cv_func_][$1] = yes; then + AC_DEFINE([HAVE_]m4_translit([[$1]], + [abcdefghijklmnopqrstuvwxyz], + [ABCDEFGHIJKLMNOPQRSTUVWXYZ]), + [1], [Define to 1 if you have the `$1' function.]) + fi +]) + dnl Expands to some code for use in .c programs that, on native Windows, defines dnl the Microsoft deprecated alias function names to the underscore-prefixed dnl actual function names. With this macro, these function names are available diff --git a/m4/mkfifoat.m4 b/m4/mkfifoat.m4 index d7ce2126c9..9246abf3a8 100644 --- a/m4/mkfifoat.m4 +++ b/m4/mkfifoat.m4 @@ -1,7 +1,7 @@ -# serial 5 +# serial 5.1 # See if we need to provide mkfifoat/mknodat replacement. -dnl Copyright (C) 2009-2022 Free Software Foundation, Inc. +dnl Copyright (C) 2009-2023 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, dnl with or without modifications, as long as this notice is preserved. @@ -18,7 +18,8 @@ AC_DEFUN([gl_FUNC_MKFIFOAT], AC_REQUIRE([gl_FUNC_OPENAT]) - AC_CHECK_FUNCS_ONCE([mkfifoat mknodat]) + gl_CHECK_FUNCS_MACOS([mknodat], [[#include ]]) + gl_CHECK_FUNCS_MACOS([mkfifoat], [[#include ]]) if test $ac_cv_func_mkfifoat = yes; then dnl Check for AIX 7.2 bug with trailing slash. AC_CACHE_CHECK([whether mkfifoat rejects trailing slashes], -- 2.39.5