preserve the bit stride when resolving an array type.
authorJoel Brobecker <brobecker@adacore.com>
Tue, 31 Mar 2015 14:59:35 +0000 (07:59 -0700)
committerJoel Brobecker <brobecker@adacore.com>
Tue, 5 May 2015 17:42:07 +0000 (10:42 -0700)
Consider the following (Ada) variable...

   A1 : Array_Type := (1 => (I => 0, S => <>),
                       2 => (I => 1, S => "A"),
                       3 => (I => 2, S => "AB"));

... where Array_Type is an array of records whose size is variable:

   subtype Small_Type is Integer range 0 .. 10;
   type Record_Type (I : Small_Type := 0) is record
      S : String (1 .. I);
   end record;
   type Array_Type is array (Integer range <>) of Record_Type;

Trying to print the value of this array currently results in the following
error:

    (gdb) p a1
    Cannot access memory at address 0x61c000

What happens in this case, is that the compiler describes our array
as an array with a specific stride (and bounds being static 1..3):

 <1><749>: Abbrev Number: 10 (DW_TAG_array_type)
    <74a>   DW_AT_name        : (indirect string, offset: 0xb6d): pck__T18s
    <74e>   DW_AT_byte_stride : 16
    <74f>   DW_AT_type        : <0x6ea>
 <2><757>: Abbrev Number: 11 (DW_TAG_subrange_type)
    <758>   DW_AT_type        : <0x75e>
    <75c>   DW_AT_upper_bound : 3

This is because we cannot use, in this case, the size of the record
to determine that stride, since the size of the record depends on
its contents. So the compiler helps us by providing that stride.

The problems start when trying to resolve that type. Because the elements
contained in that array type are dynamic, the array itself is considered
dynamic, and thus we end up creating a resolved version of that array.
And during that resolution, we were not handling the case where the array
had a stride. See gdbtypes.c::resolve_dynamic_array...

  return create_array_type (copy_type (type),
                            elt_type,
                            range_type);

As a result, we created an array whose stride was based on the size
of elt_type, which a record whose size isn't static and irrelevant
regardless.

This patch fixes is by calling create_array_type_with_stride instead.

As it happens, there is another issue for us to be able to print
the value of our array, but those are independent of this patch
and will be handled separately. For now, the patch allows us to
get rid of the first error, and the output is now:

     (gdb) p a1
     $1 = (

gdb/ChangeLog:

* gdbtypes.c (resolve_dynamic_array): Use
create_array_type_with_stride instead of create_array_type.

gdb/ChangeLog
gdb/gdbtypes.c

index c2b5a0511e5d8050e1a595977b4594d87cc58e4e..5c3ca8ff05a5ae66a7395b3b1bba0e6f7a13b94f 100644 (file)
@@ -1,3 +1,8 @@
+2015-05-05  Joel Brobecker  <brobecker@adacore.com>
+
+       * gdbtypes.c (resolve_dynamic_array): Use
+       create_array_type_with_stride instead of create_array_type.
+
 2015-04-30  DJ Delorie  <dj@redhat.com>
 
        * rl78-tdep.c (rl78_analyze_prologue): Pass RL78_ISA_DEFAULT to
index b2e11772dc7bfea6cf97e961e822e1dfec574874..d91b5d542dc48b1915ed07f24b04b89f97107bd3 100644 (file)
@@ -1898,9 +1898,9 @@ resolve_dynamic_array (struct type *type,
   else
     elt_type = TYPE_TARGET_TYPE (type);
 
-  return create_array_type (copy_type (type),
-                           elt_type,
-                           range_type);
+  return create_array_type_with_stride (copy_type (type),
+                                       elt_type, range_type,
+                                       TYPE_FIELD_BITSIZE (type, 0));
 }
 
 /* Resolve dynamic bounds of members of the union TYPE to static