trans.c (Attribute_to_gnu): Add kludge to avoid generating an overflow for -1.
authorEric Botcazou <ebotcazou@adacore.com>
Sun, 26 May 2013 10:02:33 +0000 (10:02 +0000)
committerEric Botcazou <ebotcazou@gcc.gnu.org>
Sun, 26 May 2013 10:02:33 +0000 (10:02 +0000)
* gcc-interface/trans.c (Attribute_to_gnu) <Attr_Last_Bit>: Add kludge
to avoid generating an overflow for -1.

From-SVN: r199339

gcc/ada/ChangeLog
gcc/ada/gcc-interface/trans.c
gcc/testsuite/ChangeLog
gcc/testsuite/gnat.dg/specs/last_bit.ads [new file with mode: 0644]

index 9eac544c9559ff2006cc7d789cdddc96014f7ae4..8cd13769ddd8c4d6a9a8dee5bf471e1d9c0387f0 100644 (file)
@@ -1,3 +1,8 @@
+2013-05-26  Eric Botcazou  <ebotcazou@adacore.com>
+
+       * gcc-interface/trans.c (Attribute_to_gnu) <Attr_Last_Bit>: Add kludge
+       to avoid generating an overflow for -1.
+
 2013-05-26  Eric Botcazou  <ebotcazou@adacore.com>
 
        * gcc-interface/gigi.h (create_type_decl): Adjust prototype.
index 13767e9dd9bc609a32c936d300b6dbe00cb10b69..4b71568b8ba956d2fe34d6ccf25912bf3baa90c5 100644 (file)
@@ -2080,14 +2080,19 @@ Attribute_to_gnu (Node_Id gnat_node, tree *gnu_result_type_p, int attribute)
            gnu_result = bitsize_int (bitpos % BITS_PER_UNIT);
            gnu_result = size_binop (PLUS_EXPR, gnu_result,
                                     TYPE_SIZE (TREE_TYPE (gnu_prefix)));
-           gnu_result = size_binop (MINUS_EXPR, gnu_result,
-                                    bitsize_one_node);
+           /* ??? Avoid a large unsigned result that will overflow when
+              converted to the signed universal_integer.  */
+           if (integer_zerop (gnu_result))
+             gnu_result = integer_minus_one_node;
+           else
+             gnu_result
+               = size_binop (MINUS_EXPR, gnu_result, bitsize_one_node);
            break;
 
          case Attr_Bit_Position:
            gnu_result = gnu_field_bitpos;
            break;
-               }
+         }
 
        /* If this has a PLACEHOLDER_EXPR, qualify it by the object we are
           handling.  */
index b6bb1b7ed3aeca40256b7b75c9130fb5a9a92e11..5cb426f8542bc44bde970124bfd985bcfb8b24ea 100644 (file)
@@ -1,3 +1,7 @@
+2013-05-26  Eric Botcazou  <ebotcazou@adacore.com>
+
+       * gnat.dg/specs/last_bit.ads: New test.
+
 2013-05-26  Eric Botcazou  <ebotcazou@adacore.com>
 
        * gnat.dg/specs/machine_attribute.ads: New test.
diff --git a/gcc/testsuite/gnat.dg/specs/last_bit.ads b/gcc/testsuite/gnat.dg/specs/last_bit.ads
new file mode 100644 (file)
index 0000000..ecfc254
--- /dev/null
@@ -0,0 +1,19 @@
+-- { dg-do compile }
+
+package Last_Bit is
+
+   Max_Components : constant := 100;
+   type Count_Type is new Natural range 0 .. Max_Components;
+   subtype Index_Type is Count_Type range 1 .. Count_Type'Last;
+   
+   type List_Type is array (Index_Type range <>) of Integer;
+
+   type Record_Type (Count : Count_Type := 0) is record
+      List : List_Type (1 .. Count);
+   end record;
+
+   Null_Record : Record_Type (Count => 0);
+
+   List_Last_Bit : Integer := Null_Record.List'Last_Bit;
+
+end Last_Bit;