diff options
author | Tom Tromey <tromey@adacore.com> | 2021-06-18 13:08:33 -0600 |
---|---|---|
committer | Tom Tromey <tromey@adacore.com> | 2021-07-16 08:23:47 -0600 |
commit | cc9d6997a5b23d0c8e1960f6c0b5f5cdf456d4e9 (patch) | |
tree | 98b8274e28e753f9ba06b8c17975fabba46199ac | |
parent | 05a1dd47cc9b6fcc8ec112bd0b68b36567ccbb39 (diff) | |
download | gdb-cc9d6997a5b23d0c8e1960f6c0b5f5cdf456d4e9.zip gdb-cc9d6997a5b23d0c8e1960f6c0b5f5cdf456d4e9.tar.gz gdb-cc9d6997a5b23d0c8e1960f6c0b5f5cdf456d4e9.tar.bz2 |
Fix array stride bug
Investigation of using the Python API with an Ada program showed that
an array of dynamic types was not being handled properly. I tracked
this down to an oddity of how array strides are handled.
In gdb, an array stride can be attached to the range type, via the
range_bounds object. However, the stride can also be put into the
array's first field. From create_range_type_with_stride:
else if (bit_stride > 0)
TYPE_FIELD_BITSIZE (result_type, 0) = bit_stride;
It's hard to be sure why this is done, but I would guess a combination
of historical reasons plus a desire (mentioned in a comment somewhere)
to avoid modifying the range type.
This patch fixes the problem by changing type::bit_stride to
understand this convention. It also fixes one spot that reproduces
this logic.
Regression tested on x86-64 Fedora 32.
-rw-r--r-- | gdb/gdbtypes.c | 8 | ||||
-rw-r--r-- | gdb/gdbtypes.h | 2 | ||||
-rw-r--r-- | gdb/testsuite/gdb.ada/array_of_variant.exp | 17 |
3 files changed, 20 insertions, 7 deletions
diff --git a/gdb/gdbtypes.c b/gdb/gdbtypes.c index dbc82f0..1a26171 100644 --- a/gdb/gdbtypes.c +++ b/gdb/gdbtypes.c @@ -1280,13 +1280,7 @@ update_static_array_size (struct type *type) int stride; struct type *element_type; - /* If the array itself doesn't provide a stride value then take - whatever stride the range provides. Don't update BIT_STRIDE as - we don't want to place the stride value from the range into this - arrays bit size field. */ - stride = TYPE_FIELD_BITSIZE (type, 0); - if (stride == 0) - stride = range_type->bit_stride (); + stride = type->bit_stride (); if (!get_discrete_bounds (range_type, &low_bound, &high_bound)) low_bound = high_bound = 0; diff --git a/gdb/gdbtypes.h b/gdb/gdbtypes.h index 0cc00e7..d754f2f 100644 --- a/gdb/gdbtypes.h +++ b/gdb/gdbtypes.h @@ -1029,6 +1029,8 @@ struct type ULONGEST bit_stride () const { + if (this->code () == TYPE_CODE_ARRAY && this->field (0).bitsize != 0) + return this->field (0).bitsize; return this->bounds ()->bit_stride (); } diff --git a/gdb/testsuite/gdb.ada/array_of_variant.exp b/gdb/testsuite/gdb.ada/array_of_variant.exp index dfcbe75..d93ad47 100644 --- a/gdb/testsuite/gdb.ada/array_of_variant.exp +++ b/gdb/testsuite/gdb.ada/array_of_variant.exp @@ -14,6 +14,7 @@ # along with this program. If not, see <http://www.gnu.org/licenses/>. load_lib "ada.exp" +load_lib "gdb-python.exp" if { [skip_ada_tests] } { return -1 } @@ -49,4 +50,20 @@ foreach_with_prefix scenario {all minimal} { gdb_test "print objects(2 .. 2)" \ [string_to_regexp " = (2 => $v2)"] \ "print second array slice" + + # This is only supported for the DWARF encoding. + if {$scenario == "minimal" && ![skip_python_tests]} { + gdb_test_no_output \ + "python o = gdb.parse_and_eval('objects')" \ + "fetch value for python" + gdb_test "python print(o)" \ + [string_to_regexp "($v1, $v2)"] \ + "python print array" + gdb_test "python print(o\[1\])" \ + [string_to_regexp "$v1"] \ + "python print first array element" + gdb_test "python print(o\[2\])" \ + [string_to_regexp "$v2"] \ + "python print second array element" + } } |