diff options
author | Doug Evans <dje@google.com> | 2017-03-15 15:44:45 -0700 |
---|---|---|
committer | Doug Evans <dje@google.com> | 2017-03-16 09:31:29 -0700 |
commit | a7c0469f992721b30665ba92f4f2f74d29032a84 (patch) | |
tree | a969a42f1d28f0d33360ecbdb053d947974182d3 /gdb/guile/scm-value.c | |
parent | 34b433203b5f56149c27a8dfea21a921392cb158 (diff) | |
download | gdb-a7c0469f992721b30665ba92f4f2f74d29032a84.zip gdb-a7c0469f992721b30665ba92f4f2f74d29032a84.tar.gz gdb-a7c0469f992721b30665ba92f4f2f74d29032a84.tar.bz2 |
Copy lazy string handling fixes from Python.
This patch keeps the Scheme side of lazy string handling in sync
with the python size, bringing over fixes for
PRs python/17728, python/18439, python/18779.
gdb/ChangeLog:
* guile/scm-lazy-string.c (lazy_string_smob): Clarify use of LENGTH
member. Change type of TYPE member to SCM. All uses updated.
(lsscm_make_lazy_string_smob): Add assert.
(lsscm_make_lazy_string): Flag bad length values.
(lsscm_elt_type): New function.
(gdbscm_lazy_string_to_value): Rewrite to use
lsscm_safe_lazy_string_to_value.
(lsscm_safe_lazy_string_to_value): Fix handling of TYPE_CODE_PTR.
* guile/scm-value.c (gdbscm_value_to_lazy_string): Flag bad length
values. Fix TYPE_CODE_PTR. Handle TYPE_CODE_ARRAY. Handle typedefs
in incoming type.
* guile/guile-internal.h (tyscm_scm_to_type): Declare.
* guile/scm-type.c (tyscm_scm_to_type): New function.
gdb/testsuite/ChangeLog:
* gdb.guile/scm-value.c (main) Delete locals sptr, sn.
* gdb.guile/scm-lazy-string.c: New file.
* gdb.guile/scm-value.exp: Move lazy string tests to ...
* gdb.guile/scm-lazy-string.exp: ... here, new file. Add more tests
for pointer, array, typedef lazy strings.
Diffstat (limited to 'gdb/guile/scm-value.c')
-rw-r--r-- | gdb/guile/scm-value.c | 65 |
1 files changed, 59 insertions, 6 deletions
diff --git a/gdb/guile/scm-value.c b/gdb/guile/scm-value.c index ebccfb6..f81a90c 100644 --- a/gdb/guile/scm-value.c +++ b/gdb/guile/scm-value.c @@ -1173,8 +1173,10 @@ gdbscm_value_to_string (SCM self, SCM rest) Return a Scheme object representing a lazy_string_object type. A lazy string is a pointer to a string with an optional encoding and length. If ENCODING is not given, the target's charset is used. - If LENGTH is provided then the length parameter is set to LENGTH, otherwise - length will be set to -1 (first null of appropriate with). + If LENGTH is provided then the length parameter is set to LENGTH. + Otherwise if the value is an array of known length then the array's length + is used. Otherwise the length will be set to -1 (meaning first null of + appropriate with). LENGTH must be a Scheme integer, it can't be a <gdb:value> integer. */ static SCM @@ -1198,18 +1200,69 @@ gdbscm_value_to_lazy_string (SCM self, SCM rest) &encoding_arg_pos, &encoding, &length_arg_pos, &length); + if (length < -1) + { + gdbscm_out_of_range_error (FUNC_NAME, length_arg_pos, + scm_from_int (length), + _("invalid length")); + } + cleanups = make_cleanup (xfree, encoding); TRY { struct cleanup *inner_cleanup = make_cleanup_value_free_to_mark (value_mark ()); + struct type *type, *realtype; + CORE_ADDR addr; - if (TYPE_CODE (value_type (value)) == TYPE_CODE_PTR) - value = value_ind (value); + type = value_type (value); + realtype = check_typedef (type); + + switch (TYPE_CODE (realtype)) + { + case TYPE_CODE_ARRAY: + { + LONGEST array_length = -1; + LONGEST low_bound, high_bound; + + /* PR 20786: There's no way to specify an array of length zero. + Record a length of [0,-1] which is how Ada does it. Anything + we do is broken, but this one possible solution. */ + if (get_array_bounds (realtype, &low_bound, &high_bound)) + array_length = high_bound - low_bound + 1; + if (length == -1) + length = array_length; + else if (array_length == -1) + { + type = lookup_array_range_type (TYPE_TARGET_TYPE (realtype), + 0, length - 1); + } + else if (length != array_length) + { + /* We need to create a new array type with the + specified length. */ + if (length > array_length) + error (_("length is larger than array size")); + type = lookup_array_range_type (TYPE_TARGET_TYPE (type), + low_bound, + low_bound + length - 1); + } + addr = value_address (value); + break; + } + case TYPE_CODE_PTR: + /* If a length is specified we defer creating an array of the + specified width until we need to. */ + addr = value_as_address (value); + break; + default: + /* Should flag an error here. PR 20769. */ + addr = value_address (value); + break; + } - result = lsscm_make_lazy_string (value_address (value), length, - encoding, value_type (value)); + result = lsscm_make_lazy_string (addr, length, encoding, type); do_cleanups (inner_cleanup); } |