[v2,03/11,PR,gdb/14441] gdb: valops: add ability to return rvalue reference values from value_ref()
Commit Message
Parameterize value_ref() by the kind of reference type the value of which
is requested. Change all callers to use the new API.
./ChangeLog:
2016-01-19 Artemiy Volkov <artemiyv@acm.org>
* gdb/ada-lang.c (ada_evaluate_subexp): Adhere to the new
value_ref() interface.
* gdb/c-valprint.c (c_value_print): Likewise.
* gdb/infcall.c (value_arg_coerce): Likewise.
* gdb/python/py-value.c (valpy_reference_value): Likewise.
* gdb/valops.c (value_cast): Likewise.
(value_reinterpret_cast): Likewise.
(value_dynamic_cast): Likewise.
(value_ref): Parameterize by kind of return value reference type.
(typecmp): Likewise.
* gdb/value.h: New interface.
---
gdb/ada-lang.c | 2 +-
gdb/c-valprint.c | 9 ++++++---
gdb/infcall.c | 2 +-
gdb/python/py-value.c | 2 +-
gdb/valops.c | 20 ++++++++++++--------
gdb/value.h | 2 +-
6 files changed, 22 insertions(+), 15 deletions(-)
Comments
Just "nits" in this review.
On 01/19/2016 10:53 AM, Artemiy Volkov wrote:
> 2016-01-19 Artemiy Volkov <artemiyv@acm.org>
>
> * gdb/ada-lang.c (ada_evaluate_subexp): Adhere to the new
> value_ref() interface.
> * gdb/c-valprint.c (c_value_print): Likewise.
> * gdb/infcall.c (value_arg_coerce): Likewise.
> * gdb/python/py-value.c (valpy_reference_value): Likewise.
> * gdb/valops.c (value_cast): Likewise.
> (value_reinterpret_cast): Likewise.
> (value_dynamic_cast): Likewise.
> (value_ref): Parameterize by kind of return value reference type.
> (typecmp): Likewise.
Another place that could be simplified, removing "likewise."
> * gdb/value.h: New interface.
This isn't a particularly useful comment. ChangeLogs explain what changed:
* gdb/value.h (value_ref): Add new parameter "refcode".
> diff --git a/gdb/c-valprint.c b/gdb/c-valprint.c
> index 62552ec..e210e99 100644
> --- a/gdb/c-valprint.c
> +++ b/gdb/c-valprint.c
> @@ -602,10 +602,13 @@ c_value_print (struct value *val, struct ui_file *stream,
> else if (options->objectprint
> && (TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_STRUCT))
> {
> - int is_ref = TYPE_CODE (type) == TYPE_CODE_REF;
> + int is_ref = TYPE_REFERENCE (type);
> + enum type_code refcode = TYPE_CODE_UNDEF;
Indentation?
>
> - if (is_ref)
> + if (is_ref) {
> val = value_addr (val);
> + refcode = TYPE_CODE (type);
> + }
>
> /* Pointer to class, check real type of object. */
> fprintf_filtered (stream, "(");
> diff --git a/gdb/valops.c b/gdb/valops.c
> index 1aafb5a..cc01689 100644
> --- a/gdb/valops.c
> +++ b/gdb/valops.c
> @@ -828,7 +829,7 @@ value_dynamic_cast (struct type *type, struct value *arg)
> value_address (tem), tem,
> rtti_type, &result) == 1)
> return value_cast (type,
> - is_ref ? value_ref (result) : value_addr (result));
> + is_ref ? value_ref (result, TYPE_CODE (resolved_type)) : value_addr (result));
>
> if (TYPE_CODE (resolved_type) == TYPE_CODE_PTR)
> return value_zero (type, not_lval);
The two changed lines in the above hunk are too long.
> @@ -1499,16 +1500,19 @@ value_addr (struct value *arg1)
> contents. */
>
> struct value *
> -value_ref (struct value *arg1)
> +value_ref (struct value *arg1, enum type_code refcode)
> {
> struct value *arg2;
> struct type *type = check_typedef (value_type (arg1));
>
> - if (TYPE_CODE (type) == TYPE_CODE_REF)
> + gdb_assert (refcode == TYPE_CODE_REF || refcode == TYPE_CODE_RVALUE_REF);
> +
> + if ((TYPE_CODE (type) == TYPE_CODE_REF || TYPE_CODE (type) == TYPE_CODE_RVALUE_REF)
> + && TYPE_CODE (type) == refcode)
> return arg1;
>
The "if ((TYPE_CODE...)" line is too long.
> arg2 = value_addr (arg1);
> - deprecated_set_value_type (arg2, lookup_lvalue_reference_type (type));
> + deprecated_set_value_type (arg2, lookup_reference_type (type, refcode));
> return arg2;
> }
>
Keith
@@ -10724,7 +10724,7 @@ ada_evaluate_subexp (struct type *expect_type, struct expression *exp,
should return a ref as it should be valid to ask
for its address; so rebuild a ref after coerce. */
arg1 = ada_coerce_ref (arg1);
- return value_ref (arg1);
+ return value_ref (arg1, TYPE_CODE_REF);
}
}
@@ -602,10 +602,13 @@ c_value_print (struct value *val, struct ui_file *stream,
else if (options->objectprint
&& (TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_STRUCT))
{
- int is_ref = TYPE_CODE (type) == TYPE_CODE_REF;
+ int is_ref = TYPE_REFERENCE (type);
+ enum type_code refcode = TYPE_CODE_UNDEF;
- if (is_ref)
+ if (is_ref) {
val = value_addr (val);
+ refcode = TYPE_CODE (type);
+ }
/* Pointer to class, check real type of object. */
fprintf_filtered (stream, "(");
@@ -625,7 +628,7 @@ c_value_print (struct value *val, struct ui_file *stream,
if (is_ref)
{
- val = value_ref (value_ind (val));
+ val = value_ref (value_ind (val), refcode);
type = value_type (val);
}
@@ -169,7 +169,7 @@ value_arg_coerce (struct gdbarch *gdbarch, struct value *arg,
if the value was not previously in memory - in some cases
we should clearly be allowing this, but how? */
new_value = value_cast (TYPE_TARGET_TYPE (type), arg);
- new_value = value_ref (new_value);
+ new_value = value_ref (new_value, TYPE_CODE (type));
return new_value;
}
case TYPE_CODE_INT:
@@ -249,7 +249,7 @@ valpy_reference_value (PyObject *self, PyObject *args)
struct cleanup *cleanup = make_cleanup_value_free_to_mark (value_mark ());
self_val = ((value_object *) self)->value;
- result = value_to_value_object (value_ref (self_val));
+ result = value_to_value_object (value_ref (self_val, TYPE_CODE_REF));
do_cleanups (cleanup);
}
@@ -372,7 +372,7 @@ value_cast (struct type *type, struct value *arg2)
struct type *dereftype = check_typedef (TYPE_TARGET_TYPE (t1));
struct value *val = value_cast (dereftype, arg2);
- return value_ref (val);
+ return value_ref (val, TYPE_CODE (t1));
}
code2 = TYPE_CODE (check_typedef (value_type (arg2)));
@@ -622,7 +622,8 @@ value_reinterpret_cast (struct type *type, struct value *arg)
error (_("Invalid reinterpret_cast"));
if (is_ref)
- result = value_cast (type, value_ref (value_ind (result)));
+ result = value_cast (type, value_ref (value_ind (result),
+ TYPE_CODE (type)));
return result;
}
@@ -816,7 +817,7 @@ value_dynamic_cast (struct type *type, struct value *arg)
arg_type,
&result) == 1)
return value_cast (type,
- is_ref ? value_ref (result) : value_addr (result));
+ is_ref ? value_ref (result, TYPE_CODE (resolved_type)) : value_addr (result));
}
/* The second dynamic check specified in 5.2.7. */
@@ -828,7 +829,7 @@ value_dynamic_cast (struct type *type, struct value *arg)
value_address (tem), tem,
rtti_type, &result) == 1)
return value_cast (type,
- is_ref ? value_ref (result) : value_addr (result));
+ is_ref ? value_ref (result, TYPE_CODE (resolved_type)) : value_addr (result));
if (TYPE_CODE (resolved_type) == TYPE_CODE_PTR)
return value_zero (type, not_lval);
@@ -1499,16 +1500,19 @@ value_addr (struct value *arg1)
contents. */
struct value *
-value_ref (struct value *arg1)
+value_ref (struct value *arg1, enum type_code refcode)
{
struct value *arg2;
struct type *type = check_typedef (value_type (arg1));
- if (TYPE_CODE (type) == TYPE_CODE_REF)
+ gdb_assert (refcode == TYPE_CODE_REF || refcode == TYPE_CODE_RVALUE_REF);
+
+ if ((TYPE_CODE (type) == TYPE_CODE_REF || TYPE_CODE (type) == TYPE_CODE_RVALUE_REF)
+ && TYPE_CODE (type) == refcode)
return arg1;
arg2 = value_addr (arg1);
- deprecated_set_value_type (arg2, lookup_lvalue_reference_type (type));
+ deprecated_set_value_type (arg2, lookup_reference_type (type, refcode));
return arg2;
}
@@ -1715,7 +1719,7 @@ typecmp (int staticp, int varargs, int nargs,
if (TYPE_CODE (tt2) == TYPE_CODE_ARRAY)
t2[i] = value_coerce_array (t2[i]);
else
- t2[i] = value_ref (t2[i]);
+ t2[i] = value_ref (t2[i], TYPE_CODE (tt1));
continue;
}
@@ -725,7 +725,7 @@ extern struct value *value_ind (struct value *arg1);
extern struct value *value_addr (struct value *arg1);
-extern struct value *value_ref (struct value *arg1);
+extern struct value *value_ref (struct value *arg1, enum type_code refcode);
extern struct value *value_assign (struct value *toval,
struct value *fromval);