Avoid global lookup when decoding XA type.
This patch enhances GDB to take advantage of a recent change in the GNAT encoding regarding XA types. A detailed description of the logic has been added at the start of ada_fixup_array_indexes_type to give the context behind this enhancement. 2010-05-17 Joel Brobecker <brobecker@adacore.com> * ada-lang.c (to_fixed_range_type): The the raw index type as argument instead of the raw type name. Remove orig_type parameter. Update calls throughout. (ada_fixup_array_indexes_type): New function. (ada_array_bound_from_type): Add call to ada_fixup_array_indexes_type. * ada-lang.h (ada_fixup_array_indexes_type): Add declaration. * ada-typeprint.c (print_range_type): Renames print_range_type_named. Remove name parameter. (print_array_type): Add call to ada_fixup_array_indexes_type. Update calls to print_range_type. (ada_print_type): Update calls to print_range_type.
This commit is contained in:
parent
3872d37d18
commit
28c85d6c4b
4 changed files with 100 additions and 28 deletions
|
@ -165,8 +165,7 @@ static struct type *to_fixed_variant_branch_type (struct type *,
|
|||
|
||||
static struct type *to_fixed_array_type (struct type *, struct value *, int);
|
||||
|
||||
static struct type *to_fixed_range_type (char *, struct value *,
|
||||
struct type *);
|
||||
static struct type *to_fixed_range_type (struct type *, struct value *);
|
||||
|
||||
static struct type *to_static_fixed_type (struct type *);
|
||||
static struct type *static_unwrap_type (struct type *type);
|
||||
|
@ -1204,6 +1203,61 @@ ada_match_name (const char *sym_name, const char *name, int wild)
|
|||
|
||||
/* Arrays */
|
||||
|
||||
/* Assuming that INDEX_DESC_TYPE is an ___XA structure, a structure
|
||||
generated by the GNAT compiler to describe the index type used
|
||||
for each dimension of an array, check whether it follows the latest
|
||||
known encoding. If not, fix it up to conform to the latest encoding.
|
||||
Otherwise, do nothing. This function also does nothing if
|
||||
INDEX_DESC_TYPE is NULL.
|
||||
|
||||
The GNAT encoding used to describle the array index type evolved a bit.
|
||||
Initially, the information would be provided through the name of each
|
||||
field of the structure type only, while the type of these fields was
|
||||
described as unspecified and irrelevant. The debugger was then expected
|
||||
to perform a global type lookup using the name of that field in order
|
||||
to get access to the full index type description. Because these global
|
||||
lookups can be very expensive, the encoding was later enhanced to make
|
||||
the global lookup unnecessary by defining the field type as being
|
||||
the full index type description.
|
||||
|
||||
The purpose of this routine is to allow us to support older versions
|
||||
of the compiler by detecting the use of the older encoding, and by
|
||||
fixing up the INDEX_DESC_TYPE to follow the new one (at this point,
|
||||
we essentially replace each field's meaningless type by the associated
|
||||
index subtype). */
|
||||
|
||||
void
|
||||
ada_fixup_array_indexes_type (struct type *index_desc_type)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (index_desc_type == NULL)
|
||||
return;
|
||||
gdb_assert (TYPE_NFIELDS (index_desc_type) > 0);
|
||||
|
||||
/* Check if INDEX_DESC_TYPE follows the older encoding (it is sufficient
|
||||
to check one field only, no need to check them all). If not, return
|
||||
now.
|
||||
|
||||
If our INDEX_DESC_TYPE was generated using the older encoding,
|
||||
the field type should be a meaningless integer type whose name
|
||||
is not equal to the field name. */
|
||||
if (TYPE_NAME (TYPE_FIELD_TYPE (index_desc_type, 0)) != NULL
|
||||
&& strcmp (TYPE_NAME (TYPE_FIELD_TYPE (index_desc_type, 0)),
|
||||
TYPE_FIELD_NAME (index_desc_type, 0)) == 0)
|
||||
return;
|
||||
|
||||
/* Fixup each field of INDEX_DESC_TYPE. */
|
||||
for (i = 0; i < TYPE_NFIELDS (index_desc_type); i++)
|
||||
{
|
||||
char *name = TYPE_FIELD_NAME (index_desc_type, i);
|
||||
struct type *raw_type = ada_check_typedef (ada_find_any_type (name));
|
||||
|
||||
if (raw_type)
|
||||
TYPE_FIELD_TYPE (index_desc_type, i) = raw_type;
|
||||
}
|
||||
}
|
||||
|
||||
/* Names of MAX_ADA_DIMENS bounds in P_BOUNDS fields of array descriptors. */
|
||||
|
||||
static char *bound_name[] = {
|
||||
|
@ -2530,9 +2584,10 @@ ada_array_bound_from_type (struct type * arr_type, int n, int which)
|
|||
elt_type = TYPE_TARGET_TYPE (type);
|
||||
|
||||
index_type_desc = ada_find_parallel_type (type, "___XA");
|
||||
ada_fixup_array_indexes_type (index_type_desc);
|
||||
if (index_type_desc != NULL)
|
||||
index_type = to_fixed_range_type (TYPE_FIELD_NAME (index_type_desc, n - 1),
|
||||
NULL, TYPE_INDEX_TYPE (elt_type));
|
||||
index_type = to_fixed_range_type (TYPE_FIELD_TYPE (index_type_desc, n - 1),
|
||||
NULL);
|
||||
else
|
||||
index_type = TYPE_INDEX_TYPE (elt_type);
|
||||
|
||||
|
@ -7150,6 +7205,7 @@ to_fixed_array_type (struct type *type0, struct value *dval,
|
|||
type0 = decode_constrained_packed_array_type (type0);
|
||||
|
||||
index_type_desc = ada_find_parallel_type (type0, "___XA");
|
||||
ada_fixup_array_indexes_type (index_type_desc);
|
||||
if (index_type_desc == NULL)
|
||||
{
|
||||
struct type *elt_type0 = ada_check_typedef (TYPE_TARGET_TYPE (type0));
|
||||
|
@ -7202,8 +7258,7 @@ to_fixed_array_type (struct type *type0, struct value *dval,
|
|||
for (i = TYPE_NFIELDS (index_type_desc) - 1; i >= 0; i -= 1)
|
||||
{
|
||||
struct type *range_type =
|
||||
to_fixed_range_type (TYPE_FIELD_NAME (index_type_desc, i),
|
||||
dval, TYPE_INDEX_TYPE (elt_type0));
|
||||
to_fixed_range_type (TYPE_FIELD_TYPE (index_type_desc, i), dval);
|
||||
result = create_array_type (alloc_type_copy (elt_type0),
|
||||
result, range_type);
|
||||
elt_type0 = TYPE_TARGET_TYPE (elt_type0);
|
||||
|
@ -9182,7 +9237,7 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
|
|||
char *name = ada_type_name (type_arg);
|
||||
range_type = NULL;
|
||||
if (name != NULL && TYPE_CODE (type_arg) != TYPE_CODE_ENUM)
|
||||
range_type = to_fixed_range_type (name, NULL, type_arg);
|
||||
range_type = to_fixed_range_type (type_arg, NULL);
|
||||
if (range_type == NULL)
|
||||
range_type = type_arg;
|
||||
switch (op)
|
||||
|
@ -9704,21 +9759,21 @@ get_int_var_value (char *name, int *flag)
|
|||
in NAME, the base type given in the named range type. */
|
||||
|
||||
static struct type *
|
||||
to_fixed_range_type (char *name, struct value *dval, struct type *orig_type)
|
||||
to_fixed_range_type (struct type *raw_type, struct value *dval)
|
||||
{
|
||||
struct type *raw_type = ada_find_any_type (name);
|
||||
char *name;
|
||||
struct type *base_type;
|
||||
char *subtype_info;
|
||||
|
||||
/* Fall back to the original type if symbol lookup failed. */
|
||||
if (raw_type == NULL)
|
||||
raw_type = orig_type;
|
||||
gdb_assert (raw_type != NULL);
|
||||
gdb_assert (TYPE_NAME (raw_type) != NULL);
|
||||
|
||||
if (TYPE_CODE (raw_type) == TYPE_CODE_RANGE)
|
||||
base_type = TYPE_TARGET_TYPE (raw_type);
|
||||
else
|
||||
base_type = raw_type;
|
||||
|
||||
name = TYPE_NAME (raw_type);
|
||||
subtype_info = strstr (name, "___XD");
|
||||
if (subtype_info == NULL)
|
||||
{
|
||||
|
@ -9727,7 +9782,7 @@ to_fixed_range_type (char *name, struct value *dval, struct type *orig_type)
|
|||
if (L < INT_MIN || U > INT_MAX)
|
||||
return raw_type;
|
||||
else
|
||||
return create_range_type (alloc_type_copy (orig_type), raw_type,
|
||||
return create_range_type (alloc_type_copy (raw_type), raw_type,
|
||||
ada_discrete_type_low_bound (raw_type),
|
||||
ada_discrete_type_high_bound (raw_type));
|
||||
}
|
||||
|
@ -9790,7 +9845,7 @@ to_fixed_range_type (char *name, struct value *dval, struct type *orig_type)
|
|||
}
|
||||
}
|
||||
|
||||
type = create_range_type (alloc_type_copy (orig_type), base_type, L, U);
|
||||
type = create_range_type (alloc_type_copy (raw_type), base_type, L, U);
|
||||
TYPE_NAME (type) = name;
|
||||
return type;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue