Mercurial > jwe > octave
changeset 20465:44eb1102f8a8
don't recycle scanf format string if all conversions are done (bug #45808)
* oct-stream.cc, oct-stream.h (scanf_format_elt::special_conversion):
New enum value, no_conversion.
(scanf_format_list::next): If not cycling through the list, return
dummy scanf_format_elt after list has been exhausted.
(octave_base_stream::do_scanf): Only cycle through the format list
more than once if there are conversions to make and the limit on the
number of values to convert has not been reached.
author | John W. Eaton <jwe@octave.org> |
---|---|
date | Wed, 26 Aug 2015 16:05:49 -0400 |
parents | 7fbba8c8efd5 |
children | 16b9ec39ff46 |
files | libinterp/corefcn/oct-stream.cc libinterp/corefcn/oct-stream.h |
diffstat | 2 files changed, 29 insertions(+), 7 deletions(-) [+] |
line wrap: on
line diff
--- a/libinterp/corefcn/oct-stream.cc Wed Aug 26 22:51:59 2015 +0200 +++ b/libinterp/corefcn/oct-stream.cc Wed Aug 26 16:05:49 2015 -0400 @@ -1603,11 +1603,19 @@ if (elt) { - if (! (elt->type == scanf_format_elt::whitespace_conversion - || elt->type == scanf_format_elt::literal_conversion - || elt->type == '%') - && max_conv > 0 && conversion_count == max_conv) + if (elt->type == scanf_format_elt::null + || (! (elt->type == scanf_format_elt::whitespace_conversion + || elt->type == scanf_format_elt::literal_conversion + || elt->type == '%') + && max_conv > 0 && conversion_count == max_conv)) { + // We are done, either because we have reached the end + // of the format string and are not cycling through + // the format again or because we've converted all the + // values that have been requested and the next format + // element is a conversion. Determine final array + // size and exit. + if (all_char_conv && one_elt_size_spec) { final_nr = 1; @@ -1859,7 +1867,16 @@ break; } else - elt = fmt_list.next (nconv > 0); + { + // Cycle through the format list more than once if we have + // some conversions to make and we haven't reached the + // limit on the number of values to convert (possibly + // because there is no specified limit). + + elt = fmt_list.next (nconv > 0 + && (max_conv == 0 + || conversion_count < max_conv)); + } } }
--- a/libinterp/corefcn/oct-stream.h Wed Aug 26 22:51:59 2015 +0200 +++ b/libinterp/corefcn/oct-stream.h Wed Aug 26 16:05:49 2015 -0400 @@ -49,7 +49,8 @@ enum special_conversion { whitespace_conversion = 1, - literal_conversion = 2 + literal_conversion = 2, + null = 3 }; scanf_format_elt (const char *txt = 0, int w = 0, bool d = false, @@ -129,6 +130,9 @@ const scanf_format_elt *next (bool cycle = true) { + static scanf_format_elt dummy + (0, 0, false, scanf_format_elt::null, '\0', ""); + curr_idx++; if (curr_idx >= list.numel ()) @@ -136,8 +140,9 @@ if (cycle) curr_idx = 0; else - return 0; + return &dummy; } + return current (); }