https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101918
--- Comment #18 from Rimvydas (RJ) <rimvydas.jas at gmail dot com> --- (In reply to Steve Kargl from comment #17) > There is Fortran code in libgfortran that is compiled > by gfortran when the compiler is built. Whether that > code works as intended when someone uses -fdefault-* > or -freal-* family options remains to be seen. Someone in this same PR previously recommended that only -freal-*-real-* options should be used. Now even those are getting flagged as being broken. > REAL(c_float) should map to > C's float. Fortunately, -fdefault-real-8 does not > promote REAL(c_float) (aka REAL(4)) to REAL(8); OTOH > -freal-4-real-8 will do the promotion. This is observed behavior and a main reason why -freal-*-real-* options (including integer ones) are virtually unusable in any bigger project that interfaces to C or even Rust modules. > The IEEE ARITHMETIC module is partially built on-the-fly > when compiling code with some information coming from files > in gcc/libgfortran/ieee. Those files are compiled when > gfortran is built. I don't know if anyone has extensively > tried these options with IEEE modules. We have used IEEE_ARITHMETIC and IEEE_EXCEPTIONS modules, seem to be performing OK, except for handling inexact exceptions, but it is a minor issue. > COMMON, EQUIVALENCE, BOZ, external subprogram, etc are related > because these are affected by mucking around with storage > association and the ABI. These are not an issue if one is using modern portable Fortran code where system and sometimes vendor specific tuning/optimizations/hacks can be more easily implemented in pure C using interface safety provided by ISO_C_BINDING intrinsic module, thus keeping Fortran part of the project portable. However, none of these actually help to get closer to the actual issue in this PR. There are many things that could go wrong in the world, but this PR is about trying to get the bottom of this single issue. The -ftree-dump-original from Comment #8 in bar.f90.005t.original: __attribute__((fn spec (". "))) void bar () { static real(kind=8) b[4] = {[0 ... 3]=1.0e+0}; real(kind=8) h[4]; { struct array02_real(kind=8) parm.0; struct array01_real(kind=8) parm.1; struct array01_real(kind=8) * D.3962; static integer(kind=8) A.2[2] = {2, 2}; struct array01_integer(kind=8) parm.3; struct array01_integer(kind=8) * D.3971; parm.0.span = 8; parm.0.dtype = {.elem_len=8, .rank=2, .type=3}; parm.0.dim[0].lbound = 1; parm.0.dim[0].ubound = 2; parm.0.dim[0].stride = 1; parm.0.dim[1].lbound = 1; parm.0.dim[1].ubound = 2; parm.0.dim[1].stride = 2; parm.0.data = (void *) &h[0]; parm.0.offset = -3; parm.1.span = 8; parm.1.dtype = {.elem_len=8, .rank=1, .type=3}; parm.1.dim[0].lbound = 1; parm.1.dim[0].ubound = 4; parm.1.dim[0].stride = 1; parm.1.data = (void *) &b[0]; parm.1.offset = -1; D.3962 = &parm.1; parm.3.span = 8; parm.3.dtype = {.elem_len=8, .rank=1, .type=1}; parm.3.dim[0].lbound = 1; parm.3.dim[0].ubound = 2; parm.3.dim[0].stride = 1; parm.3.data = (void *) &A.2[0]; parm.3.offset = -1; D.3971 = &parm.3; _gfortran_reshape_r8 (&parm.0, D.3962, D.3971, 0B, 0B); } } The tree dump for foo.f90 is identical + call to bar() and main() ofc. The most puzzling bit is why LTO sees a different information for _gfortran_reshape_r8() runtime intrinsic function?