From 57e822f146bb471675f2331898cca17d20a5bac6 Mon Sep 17 00:00:00 2001 From: Peter Kokot Date: Thu, 14 Mar 2024 07:42:14 +0100 Subject: [PATCH] Check major, minor and makedev with Autoconf's AC_HEADER_MAJOR The non-standard major(), minor(), and makedev() can be defined as macros. These are usually used together with the Autoconf macro AC_HEADER_MAJOR, which defines the MAJOR_IN_MKDEV if sys/mkdev.h is available, or MAJOR_IN_SYSMACROS if sys/sysmacros.h is available. On Solaris/illumos they are in the sys/mkdev.h header (macro defined to libc implementation) and in sys/sysmacros.h (macro defined with binary operators and bits shifting). On systems with musl and glibc 2.28 or later they are defined in sys/sysmacros.h, in glibc 2.27 and earlier they were in sys/types.h. On BSD-based systems and macOS they are in the sys/types.h. Autoconf 2.70 has fixed the AC_HEADER_MAJOR macro, so it detects the headers properly due to glibc 2.25 throwing deprecation warnings when using the macros from sys/types.h. With Autoconf 2.69 and earlier the ac_cv_header_sys_types_h_makedev cache variable can skip the improper sys/types.h check in the macro. This change syncs the usage within the ext/fileinfo/libmagic bundled library and ext/posix. When sys/mkdev.h header is available, code includes that, otherwise it conditionally includes the sys/sysmacros.h. The ext/posix has additional check whether linker sees the makedev, otherwise it checks if makedev is declared within the given set of headers accoring to the AC_HEADER_MAJOR logic. Previously the AC_CHECK_FUNCS didn't detect it. --- configure.ac | 5 +++++ ext/fileinfo/config.m4 | 2 ++ ext/posix/config.m4 | 16 +++++++++++++--- ext/posix/posix.c | 7 +++---- 4 files changed, 23 insertions(+), 7 deletions(-) diff --git a/configure.ac b/configure.ac index bcf655ed4dc57..d02ad1d8d39a4 100644 --- a/configure.ac +++ b/configure.ac @@ -454,6 +454,11 @@ if test "$GCC" = "yes"; then PHP_BROKEN_GCC_STRLEN_OPT fi +dnl Detect the headers required to use makedev, major, and minor. +dnl Autoconf <= 2.69 didn't check glibc 2.25 deprecated macros in sys/types.h. +m4_version_prereq([2.70],,[ac_cv_header_sys_types_h_makedev=no]) +AC_HEADER_MAJOR + dnl Checks for typedefs, structures, and compiler characteristics. dnl ---------------------------------------------------------------------------- diff --git a/ext/fileinfo/config.m4 b/ext/fileinfo/config.m4 index 8751e1ed7b8f9..a38a205822efd 100644 --- a/ext/fileinfo/config.m4 +++ b/ext/fileinfo/config.m4 @@ -14,6 +14,8 @@ if test "$PHP_FILEINFO" != "no"; then libmagic/readcdf.c libmagic/softmagic.c libmagic/der.c \ libmagic/buffer.c libmagic/is_csv.c" + AC_CHECK_HEADERS([sys/sysmacros.h]) + AC_CHECK_FUNCS([strcasestr],,[ AC_MSG_NOTICE(using libmagic strcasestr implementation) libmagic_sources="$libmagic_sources libmagic/strcasestr.c" diff --git a/ext/posix/config.m4 b/ext/posix/config.m4 index 8d5ad1ce69f8b..9f1091a3c4521 100644 --- a/ext/posix/config.m4 +++ b/ext/posix/config.m4 @@ -8,9 +8,19 @@ if test "$PHP_POSIX" = "yes"; then AC_DEFINE(HAVE_POSIX, 1, [whether to include POSIX-like functions]) PHP_NEW_EXTENSION(posix, posix.c, $ext_shared,, -DZEND_ENABLE_STATIC_TSRMLS_CACHE=1) - AC_CHECK_HEADERS([sys/mkdev.h sys/sysmacros.h]) - - AC_CHECK_FUNCS(seteuid setegid setsid getsid getpgid ctermid mkfifo mknod setrlimit getrlimit getgroups makedev initgroups getgrgid_r eaccess) + AC_CHECK_FUNCS(seteuid setegid setsid getsid getpgid ctermid mkfifo mknod setrlimit getrlimit getgroups initgroups getgrgid_r eaccess) + + dnl Check for makedev. If it's defined as a macro, AC_CHECK_FUNCS won't work. + dnl Required headers are included by the AC_HEADER_MAJOR logic. + AC_CHECK_FUNCS([makedev],, + [AC_CHECK_DECL([makedev], [AC_DEFINE([HAVE_MAKEDEV], [1])],, [ + #include + #ifdef MAJOR_IN_MKDEV + # include + #elif defined(MAJOR_IN_SYSMACROS) + # include + #endif + ])]) dnl Skip pathconf and fpathconf check on musl libc due to limited implementation dnl (first argument is not validated and has different error). diff --git a/ext/posix/posix.c b/ext/posix/posix.c index aa17cc95d8046..f6e028f9a96e3 100644 --- a/ext/posix/posix.c +++ b/ext/posix/posix.c @@ -39,10 +39,9 @@ #include #include #include -#ifdef HAVE_SYS_MKDEV_H +#ifdef MAJOR_IN_MKDEV # include -#endif -#ifdef HAVE_SYS_SYSMACROS_H +#elif defined(MAJOR_IN_SYSMACROS) # include #endif @@ -620,7 +619,7 @@ PHP_FUNCTION(posix_mknod) zend_argument_value_error(3, "cannot be 0 for the POSIX_S_IFCHR and POSIX_S_IFBLK modes"); RETURN_THROWS(); } else { -#if defined(HAVE_MAKEDEV) || defined(makedev) +#ifdef HAVE_MAKEDEV php_dev = makedev(major, minor); #else php_error_docref(NULL, E_WARNING, "Cannot create a block or character device, creating a normal file instead");