diff options
author | Tom Tromey <tromey@adacore.com> | 2023-10-04 12:58:32 -0600 |
---|---|---|
committer | Tom Tromey <tromey@adacore.com> | 2023-10-16 09:27:28 -0600 |
commit | 138c7d2661044d80dddc0445616aada039af1a95 (patch) | |
tree | 181bb22124066287be3b60f4047f7c1e7c335b48 | |
parent | fd00374fc73e990b2a1b97a1bab431e0466f5efc (diff) | |
download | gdb-138c7d2661044d80dddc0445616aada039af1a95.zip gdb-138c7d2661044d80dddc0445616aada039af1a95.tar.gz gdb-138c7d2661044d80dddc0445616aada039af1a95.tar.bz2 |
Fix register-setting response from DAP
Andry noticed that given a DAP setExpression request, where the
expression to set is a register, DAP will return the wrong value -- it
will return the old value, not the updated one.
This happens because gdb.Value.assign (which was recently added for
DAP) does not update the value.
In this patch, I chose to have the assign method update the Value
in-place. It's also possible to have it return a new value, but this
didn't seem very useful to me.
-rw-r--r-- | gdb/python/py-value.c | 8 | ||||
-rw-r--r-- | gdb/testsuite/gdb.dap/scopes.exp | 25 |
2 files changed, 29 insertions, 4 deletions
diff --git a/gdb/python/py-value.c b/gdb/python/py-value.c index 245de68..0bf1d6e 100644 --- a/gdb/python/py-value.c +++ b/gdb/python/py-value.c @@ -905,7 +905,13 @@ valpy_assign (PyObject *self_obj, PyObject *args) try { value_object *self = (value_object *) self_obj; - value_assign (self->value, val); + value *new_value = value_assign (self->value, val); + /* value_as_address returns a new value with the same location + as the old one. Ensure that this gdb.Value is updated to + reflect the new value. */ + new_value->incref (); + self->value->decref (); + self->value = new_value; } catch (const gdb_exception &except) { diff --git a/gdb/testsuite/gdb.dap/scopes.exp b/gdb/testsuite/gdb.dap/scopes.exp index 003557c..db815d2 100644 --- a/gdb/testsuite/gdb.dap/scopes.exp +++ b/gdb/testsuite/gdb.dap/scopes.exp @@ -125,8 +125,27 @@ gdb_assert {[llength $deivals] == 2} "dei has two members" set num [dict get $reg_scope variablesReference] # The request succeeding is sufficient. -dap_check_request_and_response "fetch first register" \ - "variables" \ - [format {o variablesReference [i %d] count [i 1]} $num] +set val [dap_check_request_and_response "fetch first register" \ + "variables" \ + [format {o variablesReference [i %d] count [i 1]} $num]] + +# Try setting the value to something else. +set val [dict get [lindex $val 0] body variables] +set name [dict get [lindex $val 0] name] +set val [dict get [lindex $val 0] value] +# Just make sure it is different from the original value. +set val [expr {$val ^ 7}] + +# setVariable isn't implemented yet, so use the register name. Note +# that we sneak the "$" into the name, written in a slightly funny way +# to work around apparent TON limitations. +set response [dap_check_request_and_response "set first register" \ + setExpression \ + [format {o expression [s \$%s] value [s %d] frameId [i %d]} \ + $name $val $frame_id]] +set response [lindex $response 0] + +gdb_assert {[dict get $response body value] == $val} \ + "setting register yields updated value" dap_shutdown |