forked from Imagelibrary/binutils-gdb
Prefer existing data when evaluating DWARF expression
When evaluating a DWARF expression, the dynamic type resolution code will pass in a buffer of bytes via the property_addr_info. However, the DWARF expression evaluator will then proceed to read memory from the inferior, even when the request could be filled from this buffer. This, in turn, is a problem in some cases; and specifically when trying to handle the Ada scenario of extracting a variable-length value from a packed array. Here, the ordinary DWARF expression cannot be directly evaluated, because the data may appear at some arbitrary bit offset. So, it is unpacked into a staging area and then the expression is evaluated -- using an address of 0. This patch fixes the problem by arranging for the DWARF evaluator, in this case, to prefer passed-in memory when possible. The type of the buffer in the property_addr_info is changed to an array_view so that bounds checking can be done. gdb/ChangeLog 2020-04-24 Tom Tromey <tromey@adacore.com> * ada-lang.c (ada_discrete_type_high_bound, ada_discrete_type_low) (ada_value_primitive_packed_val): Update. * ada-valprint.c (ada_value_print_1): Update. * dwarf2/loc.c (evaluate_for_locexpr_baton): New struct. (dwarf2_locexpr_baton_eval): Take a property_addr_info rather than just an address. Use evaluate_for_locexpr_baton. (dwarf2_evaluate_property): Update. * dwarf2/loc.h (struct property_addr_info) <valaddr>: Now an array_view. * findvar.c (default_read_var_value): Update. * gdbtypes.c (compute_variant_fields_inner) (resolve_dynamic_type_internal): Update. (resolve_dynamic_type): Change type of valaddr parameter. * gdbtypes.h (resolve_dynamic_type): Update. * valarith.c (value_subscripted_rvalue): Update. * value.c (value_from_contents_and_address): Update.
This commit is contained in:
@@ -752,7 +752,7 @@ min_of_type (struct type *t)
|
||||
LONGEST
|
||||
ada_discrete_type_high_bound (struct type *type)
|
||||
{
|
||||
type = resolve_dynamic_type (type, NULL, 0);
|
||||
type = resolve_dynamic_type (type, {}, 0);
|
||||
switch (TYPE_CODE (type))
|
||||
{
|
||||
case TYPE_CODE_RANGE:
|
||||
@@ -773,7 +773,7 @@ ada_discrete_type_high_bound (struct type *type)
|
||||
LONGEST
|
||||
ada_discrete_type_low_bound (struct type *type)
|
||||
{
|
||||
type = resolve_dynamic_type (type, NULL, 0);
|
||||
type = resolve_dynamic_type (type, {}, 0);
|
||||
switch (TYPE_CODE (type))
|
||||
{
|
||||
case TYPE_CODE_RANGE:
|
||||
@@ -2508,7 +2508,7 @@ ada_value_primitive_packed_val (struct value *obj, const gdb_byte *valaddr,
|
||||
staging.data (), staging.size (),
|
||||
is_big_endian, has_negatives (type),
|
||||
is_scalar);
|
||||
type = resolve_dynamic_type (type, staging.data (), 0);
|
||||
type = resolve_dynamic_type (type, staging, 0);
|
||||
if (TYPE_LENGTH (type) < (bit_size + HOST_CHAR_BIT - 1) / HOST_CHAR_BIT)
|
||||
{
|
||||
/* This happens when the length of the object is dynamic,
|
||||
|
||||
Reference in New Issue
Block a user