diff --git a/Zend/Zend.m4 b/Zend/Zend.m4 index 41da8344bf1f..66c3d256e996 100644 --- a/Zend/Zend.m4 +++ b/Zend/Zend.m4 @@ -331,6 +331,22 @@ AS_VAR_IF([php_cv_have_global_register_vars], [yes], ]) AC_MSG_CHECKING([whether to enable global register variables support]) AC_MSG_RESULT([$ZEND_GCC_GLOBAL_REGS]) + +dnl GCC doesn't propagate -ffixed-* from LTO objects. Reserve the VM registers +dnl before LTO code gen to avoid "global register variable follows a function definition" +AS_VAR_IF([ZEND_GCC_GLOBAL_REGS], [yes], [ + zend_lto=no + for zend_flag in $CC $CFLAGS $LDFLAGS; do + AS_CASE([$zend_flag], [-flto|-flto=*], [zend_lto=yes], [-fno-lto], [zend_lto=no]) + done + AS_VAR_IF([zend_lto], [yes], [ + AS_CASE([$host_cpu], + [i386], [AS_VAR_APPEND([LDFLAGS], [" -ffixed-esi -ffixed-edi"])], + [x86_64], [AS_VAR_APPEND([LDFLAGS], [" -ffixed-r14 -ffixed-r15"])], + [aarch64*], [AS_VAR_APPEND([LDFLAGS], [" -ffixed-x27 -ffixed-x28"])], + [AC_MSG_ERROR([Cannot reserve VM registers for LTO, disable lto or use --disable-gcc-global-regs])]) + ]) +]) ]) dnl diff --git a/build/ltmain.sh b/build/ltmain.sh index 3e6a3db3a5a1..c299766165bc 100755 --- a/build/ltmain.sh +++ b/build/ltmain.sh @@ -7705,6 +7705,7 @@ func_mode_link () # -tp=* Portland pgcc target processor selection # --sysroot=* for sysroot support # -O*, -g*, -flto*, -fwhopr*, -fuse-linker-plugin GCC link-time optimization + # -ffixed-*, -fno-lto GCC LTO register reservations and cancellation # -specs=* GCC specs files # -stdlib=* select c++ std lib with clang # -fdiagnostics-color* simply affects output @@ -7725,6 +7726,7 @@ func_mode_link () -64|-mips[0-9]|-r[0-9][0-9]*|-xarch=*|-xtarget=*|+DA*|+DD*|-q*|-m*| \ -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*|-tp=*|--sysroot=*| \ -O*|-g*|-flto*|-fwhopr*|-fuse-linker-plugin|-fstack-protector*|-no-canonical-prefixes| \ + -ffixed-*|-fno-lto| \ -stdlib=*|-rtlib=*|--unwindlib=*| \ -specs=*|-fsanitize=*|-fno-sanitize*|-shared-libsan|-static-libsan| \ -ffile-prefix-map=*|-fdebug-prefix-map=*|-fmacro-prefix-map=*|-fprofile-prefix-map=*| \