|
| 1 | +diff --git a/m4/ax_c_float_words_bigendian.m4 b/m4/ax_c_float_words_bigendian.m4 |
| 2 | +index 216b90d8..52036844 100644 |
| 3 | +--- a/m4/ax_c_float_words_bigendian.m4 |
| 4 | ++++ b/m4/ax_c_float_words_bigendian.m4 |
| 5 | +@@ -27,32 +27,81 @@ |
| 6 | + # If neither value is found, the user is instructed to specify the |
| 7 | + # ordering. |
| 8 | + # |
| 9 | ++# Early versions of this macro (i.e., before serial 12) would not work |
| 10 | ++# when interprocedural optimization (via link-time optimization) was |
| 11 | ++# enabled. This would happen when, say, the GCC/clang "-flto" flag, or the |
| 12 | ++# ICC "-ipo" flag was used, for example. The problem was that under |
| 13 | ++# these conditions, the compiler did not allocate for and write the special |
| 14 | ++# float value in the data segment of the object file, since doing so might |
| 15 | ++# not prove optimal once more context was available. Thus, the special value |
| 16 | ++# (in platform-dependent binary form) could not be found in the object file, |
| 17 | ++# and the macro would fail. |
| 18 | ++# |
| 19 | ++# The solution to the above problem was to: |
| 20 | ++# |
| 21 | ++# 1) Compile and link a whole test program rather than just compile an |
| 22 | ++# object file. This ensures that we reach the point where even an |
| 23 | ++# interprocedural optimizing compiler writes values to the data segment. |
| 24 | ++# |
| 25 | ++# 2) Add code that requires the compiler to write the special value to |
| 26 | ++# the data segment, as opposed to "optimizing away" the variable's |
| 27 | ++# allocation. This could be done via compiler keywords or options, but |
| 28 | ++# it's tricky to make this work for all versions of all compilers with |
| 29 | ++# all optimization settings. The chosen solution was to make the exit |
| 30 | ++# code of the test program depend on the storing of the special value |
| 31 | ++# in memory (in the data segment). Because the exit code can be |
| 32 | ++# verified, any compiler that aspires to be correct will produce a |
| 33 | ++# program binary that contains the value, which the macro can then find. |
| 34 | ++# |
| 35 | ++# How does the exit code depend on the special value residing in memory? |
| 36 | ++# Memory, unlike variables and registers, can be addressed indirectly at run |
| 37 | ++# time. The exit code of this test program is a result of indirectly reading |
| 38 | ++# and writing to the memory region where the special value is supposed to |
| 39 | ++# reside. The actual memory addresses used and the values to be written are |
| 40 | ++# derived from the the program input ("argv") and are therefore not known at |
| 41 | ++# compile or link time. The compiler has no choice but to defer the |
| 42 | ++# computation to run time, and to prepare by allocating and populating the |
| 43 | ++# data segment with the special value. For further details, refer to the |
| 44 | ++# source code of the test program. |
| 45 | ++# |
| 46 | ++# Note that the test program is never meant to be run. It only exists to host |
| 47 | ++# a double float value in a given platform's binary format. Thus, error |
| 48 | ++# handling is not included. |
| 49 | ++# |
| 50 | + # LICENSE |
| 51 | + # |
| 52 | +-# Copyright (c) 2008 Daniel Amelang <[email protected]> |
| 53 | ++# Copyright (c) 2008, 2023 Daniel Amelang <[email protected]> |
| 54 | + # |
| 55 | + # Copying and distribution of this file, with or without modification, are |
| 56 | + # permitted in any medium without royalty provided the copyright notice |
| 57 | + # and this notice are preserved. This file is offered as-is, without any |
| 58 | + # warranty. |
| 59 | + |
| 60 | +-#serial 11 |
| 61 | ++#serial 12 |
| 62 | + |
| 63 | + AC_DEFUN([AX_C_FLOAT_WORDS_BIGENDIAN], |
| 64 | + [AC_CACHE_CHECK(whether float word ordering is bigendian, |
| 65 | + ax_cv_c_float_words_bigendian, [ |
| 66 | + |
| 67 | + ax_cv_c_float_words_bigendian=unknown |
| 68 | +-AC_COMPILE_IFELSE([AC_LANG_SOURCE([[ |
| 69 | ++AC_LINK_IFELSE([AC_LANG_SOURCE([[ |
| 70 | ++ |
| 71 | ++#include <stdlib.h> |
| 72 | ++ |
| 73 | ++static double m[] = {9.090423496703681e+223, 0.0}; |
| 74 | + |
| 75 | +-double d = 90904234967036810337470478905505011476211692735615632014797120844053488865816695273723469097858056257517020191247487429516932130503560650002327564517570778480236724525140520121371739201496540132640109977779420565776568942592.0; |
| 76 | ++int main (int argc, char *argv[]) |
| 77 | ++{ |
| 78 | ++ m[atoi (argv[1])] += atof (argv[2]); |
| 79 | ++ return m[atoi (argv[3])] > 0.0; |
| 80 | ++} |
| 81 | + |
| 82 | + ]])], [ |
| 83 | + |
| 84 | +-if grep noonsees conftest.$ac_objext >/dev/null ; then |
| 85 | ++if grep noonsees conftest$EXEEXT >/dev/null ; then |
| 86 | + ax_cv_c_float_words_bigendian=yes |
| 87 | + fi |
| 88 | +-if grep seesnoon conftest.$ac_objext >/dev/null ; then |
| 89 | ++if grep seesnoon conftest$EXEEXT >/dev/null ; then |
| 90 | + if test "$ax_cv_c_float_words_bigendian" = unknown; then |
| 91 | + ax_cv_c_float_words_bigendian=no |
| 92 | + else |
0 commit comments