https://gcc.gnu.org/bugzilla/show_bug.cgi?id=97791

            Bug ID: 97791
           Summary: GNU attributes for long double could be improved on
                    PowerPC
           Product: gcc
           Version: 11.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: target
          Assignee: unassigned at gcc dot gnu.org
          Reporter: meissner at gcc dot gnu.org
  Target Milestone: ---

The long double gnu attributes on PowerPC are not quite correct.

If you have a function that returns __float128 when the ABI is IBM extended
double, it still sets gnu attribute #4 to 5 (i.e. h/w float, IBM 128-bit long
double).

Similarly if you have a function that returns __ibm128 when the ABI is IEEE
extended double, it still sets gnu attribute #4 to 13 (i.e. h/w float, IEEE
128-bit long double).

This is due to code in rs6000-call.c that treats any __float128 or __ibm128
function return or argument as passing long double.  Instead, it should only
set the attribute if the type used is long double.

Due to decisions made previously, where __ibm128 uses the long double type if
the default long double is IBM extended and __float128 uses the long double
type if the default long double is IEEE 128-bit, the gnu attribute will mirror
the long double type.  But if you use the non-default type, it should not
trigger setting the long double type.

Similarly if you just use a variable of the right type, even if it isn't the
official long double type, it will set the long double flag.  This is due to
code in rs6000_emit_move that checks the mode.  The rs6000_emit_move code is
too late to make this distinction, since it just has modes, and it does not
have access to the type node.

Similar issues exist if the default long double is set to 64 bits.

A simple fix is just to remove the code in rs6000_emit_move.  A more complete
fix would be insert a gimple pass that sees if the long double type was ever
used.

Reply via email to