Fix bugs in 'val and 'pos with range types
authorTom Tromey <tromey@adacore.com>
Tue, 26 May 2020 20:11:08 +0000 (14:11 -0600)
committerTom Tromey <tromey@adacore.com>
Tue, 26 May 2020 20:11:08 +0000 (14:11 -0600)
In Ada, the 'val and 'pos attributes can be used to map from an
enumeration constant to its position in the enum and vice versa.
These operators did not work properly when the type in question was a
subrange of an enum type with "holes".

gdb/ChangeLog
2020-05-26  Tom Tromey  <tromey@adacore.com>

* ada-lang.c (value_val_atr): Handle TYPE_CODE_RANGE.
* gdbtypes.c (discrete_position): Handle TYPE_CODE_RANGE.

gdb/testsuite/ChangeLog
2020-05-26  Tom Tromey  <tromey@adacore.com>

* gdb.ada/arr_acc_idx_w_gap.exp: Add enum subrange tests.
* gdb.ada/arr_acc_idx_w_gap/enum_with_gap.ads (Enum_Subrange): New
type.
* gdb.ada/arr_acc_idx_w_gap/enum_with_gap_main.adb (V): New
variable.

gdb/ChangeLog
gdb/ada-lang.c
gdb/gdbtypes.c
gdb/testsuite/ChangeLog
gdb/testsuite/gdb.ada/arr_acc_idx_w_gap.exp
gdb/testsuite/gdb.ada/arr_acc_idx_w_gap/enum_with_gap.ads
gdb/testsuite/gdb.ada/arr_acc_idx_w_gap/enum_with_gap_main.adb

index 2e21613640caae623a90515f2da2b80448b2c9e1..00d36ab767a18d24eaa5c18e86e8ee872205ee2d 100644 (file)
@@ -1,3 +1,8 @@
+2020-05-26  Tom Tromey  <tromey@adacore.com>
+
+       * ada-lang.c (value_val_atr): Handle TYPE_CODE_RANGE.
+       * gdbtypes.c (discrete_position): Handle TYPE_CODE_RANGE.
+
 2020-05-25  Cristiano De Alti  <cristiano_dealti@hotmail.com>
 
        PR gdb/13519
index 7522917401cf60af5a517baf06d74ff09458ab64..5ffb2d6ac9594244561999c0820269579ec93b44 100644 (file)
@@ -9148,6 +9148,9 @@ value_val_atr (struct type *type, struct value *arg)
   if (!integer_type_p (value_type (arg)))
     error (_("'VAL requires integral argument"));
 
+  if (type->code () == TYPE_CODE_RANGE)
+    type = TYPE_TARGET_TYPE (type);
+
   if (type->code () == TYPE_CODE_ENUM)
     {
       long pos = value_as_long (arg);
index 4fe8d9a8e9cc3b439113427b0694676dd0f76023..2ee69899a935911819e4b49de35e8d21e9f16741 100644 (file)
@@ -1155,6 +1155,9 @@ get_array_bounds (struct type *type, LONGEST *low_bound, LONGEST *high_bound)
 int
 discrete_position (struct type *type, LONGEST val, LONGEST *pos)
 {
+  if (type->code () == TYPE_CODE_RANGE)
+    type = TYPE_TARGET_TYPE (type);
+
   if (type->code () == TYPE_CODE_ENUM)
     {
       int i;
index 50473fc96e89b3ce96e1cc9d1d16103e237981df..0cc377f56e0ebc0084b4cdb30a39ba60e1d3c17b 100644 (file)
@@ -1,3 +1,11 @@
+2020-05-26  Tom Tromey  <tromey@adacore.com>
+
+       * gdb.ada/arr_acc_idx_w_gap.exp: Add enum subrange tests.
+       * gdb.ada/arr_acc_idx_w_gap/enum_with_gap.ads (Enum_Subrange): New
+       type.
+       * gdb.ada/arr_acc_idx_w_gap/enum_with_gap_main.adb (V): New
+       variable.
+
 2020-05-26  Christian Biesinger  <cbiesinger@google.com>
 
        * Makefile.in: Use = instead of == for the test command
index fd7ac44cb0546a2bf55b1d7d68f15d6e3b13dcec..c08070ea53c6e42101b415842bfcdf0088b1cc75 100644 (file)
@@ -53,3 +53,7 @@ gdb_test "print indexed_by_enum(lit2..lit4)" \
          " = \\(lit2 => 43, 42, 41\\)"
 gdb_test "print s(2..4)" \
          " = \"ell\""
+
+gdb_test "print v" " = lit3"
+gdb_test "print enum_subrange'pos(v)" " = 3"
+gdb_test "print enum_subrange'val(3)" " = lit3"
index 6e073e88a498ae57b543a337bab726a9d75d413e..719380077e18c208317e1e773101529d3da6b0b3 100644 (file)
@@ -34,14 +34,16 @@ package Enum_With_Gap is
      );
    for Enum_With_Gaps'size use 16;
 
+   type Enum_Subrange is new Enum_With_Gaps range Lit1 .. Lit3;
+
    type MyWord is range 0 .. 16#FFFF# ;
    for MyWord'Size use 16;
 
    type AR is array (Enum_With_Gaps range <>) of MyWord;
    type AR_Access is access AR;
-   
+
    type String_Access is access String;
-   
+
    procedure Do_Nothing (E : AR_Access);
    procedure Do_Nothing (E : String_Access);
 
index da37dd7d5ec19cae453d0d7de0b50f7f653d2c38..752b883798028dd436e7d9e62a6d6fd010f8d429 100644 (file)
@@ -19,6 +19,7 @@ procedure Enum_With_Gap_Main is
    Indexed_By_Enum : AR_Access :=
      new AR'(LIT1 => 1,  LIT2 => 43, LIT3 => 42, LIT4 => 41);
    S : String_Access := new String'("Hello!");
+   V : Enum_Subrange := LIT3;
 begin
    Do_Nothing (Indexed_By_Enum); --  BREAK
    Do_Nothing (S);