soft-fp: Use __label__ for all labels within macros.
authorJoseph Myers <joseph@codesourcery.com>
Thu, 22 Jan 2015 22:39:26 +0000 (22:39 +0000)
committerJoseph Myers <joseph@codesourcery.com>
Thu, 22 Jan 2015 22:39:26 +0000 (22:39 +0000)
soft-fp has various macros containing labels and goto statements.
Because label names are function-scoped, this is problematic for using
the same macro more than once within a function, which some
architectures do in the Linux kernel (the soft-fp version there
predates the addition of any of these labels and gotos).  This patch
fixes this by using __label__ to make the labels local to the block
with the __label__ declaration.

Tested for powerpc-nofpu that installed stripped shared libraries are
unchanged by this patch.

* soft-fp/op-common.h (_FP_ADD_INTERNAL): Declare labels with
__label__.
(_FP_FMA): Likewise.
(_FP_TO_INT_ROUND): Likewise.
(_FP_FROM_INT): Likewise.

ChangeLog
soft-fp/op-common.h

index a8cc4e5..ae428c0 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+2015-01-22  Joseph Myers  <joseph@codesourcery.com>
+
+       * soft-fp/op-common.h (_FP_ADD_INTERNAL): Declare labels with
+       __label__.
+       (_FP_FMA): Likewise.
+       (_FP_TO_INT_ROUND): Likewise.
+       (_FP_FROM_INT): Likewise.
+
 2015-01-21  Adhemerval Zanella  <azanella@linux.vnet.ibm.com>
 
        [BZ #16418]
index f92e3b2..6b8b52f 100644 (file)
       if (X##_s == Y##_s)                                              \
        {                                                               \
          /* Addition.  */                                              \
+         __label__ add1, add2, add3, add_done;                         \
          R##_s = X##_s;                                                \
          int _FP_ADD_INTERNAL_ediff = X##_e - Y##_e;                   \
          if (_FP_ADD_INTERNAL_ediff > 0)                               \
       else                                                             \
        {                                                               \
          /* Subtraction.  */                                           \
+         __label__ sub1, sub2, sub3, norm, sub_done;                   \
          int _FP_ADD_INTERNAL_ediff = X##_e - Y##_e;                   \
          if (_FP_ADD_INTERNAL_ediff > 0)                               \
            {                                                           \
 #define _FP_FMA(fs, wc, dwc, R, X, Y, Z)                               \
   do                                                                   \
     {                                                                  \
+      __label__ done_fma;                                              \
       FP_DECL_##fs (_FP_FMA_T);                                                \
       _FP_FMA_T##_s = X##_s ^ Y##_s;                                   \
       _FP_FMA_T##_e = X##_e + Y##_e + 1;                               \
 #define _FP_TO_INT_ROUND(fs, wc, r, X, rsize, rsigned)                 \
   do                                                                   \
     {                                                                  \
+      __label__ _FP_TO_INT_ROUND_done;                                 \
       if (X##_e < _FP_EXPBIAS_##fs)                                    \
        {                                                               \
          int _FP_TO_INT_ROUND_rounds_away = 0;                         \
 #define _FP_FROM_INT(fs, wc, X, r, rsize, rtype)                       \
   do                                                                   \
     {                                                                  \
+      __label__ pack_semiraw;                                          \
       if (r)                                                           \
        {                                                               \
          rtype _FP_FROM_INT_ur;                                        \