# HG changeset patch # User John W. Eaton # Date 1594165220 14400 # Node ID 5f4e8dddf05fb8277be57ca79324588e516ee395 # Parent 3e60f505f03819256e3258504a7e1046b3ea60bf# Parent ea5a632b255347234cf71ddc239666249252b01c maint: merge stable to default. diff -r 3e60f505f038 -r 5f4e8dddf05f libinterp/parse-tree/pt-assign.cc --- a/libinterp/parse-tree/pt-assign.cc Tue Jul 07 13:15:45 2020 -0400 +++ b/libinterp/parse-tree/pt-assign.cc Tue Jul 07 19:40:20 2020 -0400 @@ -350,14 +350,34 @@ } /* -%!function varargout = f () +%!function varargout = f1 () %! varargout{1} = nargout; %!endfunction %! %!test -%! [a, ~] = f (); +%! [a, ~] = f1 (); %! assert (a, 2); %!test -%! [a, ~, ~, ~, ~] = f (); +%! [a, ~, ~, ~, ~] = f1 (); %! assert (a, 5); + +%!function [x, y] = f2 () +%! y = 1; +%!endfunction +%! +%!test +%! [~, y] = f2 (); +%! assert (y, 1); + +%!function [x, y, varargout] = f3 () +%! y = 1; +%! varargout = {2, 3}; +%!endfunction +%! +%!test +%! [~, y, a, b] = f3 (); +%! assert ([y, a, b], [1, 2, 3]); +%!test +%! [~, y, ~, b] = f3 (); +%! assert ([y, b], [1, 3]); */ diff -r 3e60f505f038 -r 5f4e8dddf05f libinterp/parse-tree/pt-eval.cc --- a/libinterp/parse-tree/pt-eval.cc Tue Jul 07 13:15:45 2020 -0400 +++ b/libinterp/parse-tree/pt-eval.cc Tue Jul 07 19:40:20 2020 -0400 @@ -1788,7 +1788,8 @@ octave_value_list tree_evaluator::convert_return_list_to_const_vector - (tree_parameter_list *ret_list, int nargout, const Cell& varargout) + (tree_parameter_list *ret_list, int nargout, const Matrix& ignored_outputs, + const Cell& varargout) { octave_idx_type vlen = varargout.numel (); int len = ret_list->length (); @@ -1796,35 +1797,59 @@ // Special case. Will do a shallow copy. if (len == 0) return varargout; - else if (nargout <= len) - { - octave_value_list retval (nargout); - - int i = 0; - - for (tree_decl_elt *elt : *ret_list) - { - if (is_defined (elt->ident ())) - retval(i) = evaluate (elt); - - i++; - } - - return retval; - } else { - octave_value_list retval (len + vlen); - int i = 0; - - for (tree_decl_elt *elt : *ret_list) - retval(i++) = evaluate (elt); - - for (octave_idx_type j = 0; j < vlen; j++) - retval(i++) = varargout(j); - - return retval; + int k = 0; + int num_ignored = ignored_outputs.numel (); + int ignored = num_ignored > 0 ? ignored_outputs(k) - 1 : -1; + + if (nargout <= len) + { + int nout = nargout > 0 ? nargout : 1; + octave_value_list retval (nout); + + for (tree_decl_elt *elt : *ret_list) + { + if (nargout == 0 && ! is_defined (elt->ident ())) + break; + + if (ignored >= 0 && i == ignored) + { + i++; + k++; + ignored = k < num_ignored ? ignored_outputs(k) - 1 : -1; + } + else + retval(i++) = evaluate (elt); + + if (i == nout) + break; + } + + return retval; + } + else + { + octave_value_list retval (len + vlen); + + for (tree_decl_elt *elt : *ret_list) + { + if (ignored >= 0 && i == ignored) + { + i++; + k++; + ignored = k < num_ignored ? ignored_outputs(k) - 1 : -1; + } + else + retval(i++) = evaluate (elt); + } + + for (octave_idx_type j = 0; j < vlen; j++) + retval(i++) = varargout(j); + + return retval; + } } } @@ -2769,7 +2794,9 @@ if (m_call_stack.size () >= static_cast (m_max_recursion_depth)) error ("max_recursion_depth exceeded"); - bind_auto_fcn_vars (xargs.name_tags (), args.length (), + Matrix ignored_outputs = ignored_fcn_outputs (); + + bind_auto_fcn_vars (xargs.name_tags (), ignored_outputs, args.length (), nargout, user_function.takes_varargs (), user_function.all_va_args (args)); @@ -2851,6 +2878,7 @@ } retval = convert_return_list_to_const_vector (ret_list, nargout, + ignored_outputs, varargout); } @@ -4168,12 +4196,13 @@ } void tree_evaluator::bind_auto_fcn_vars (const string_vector& arg_names, + const Matrix& ignored_outputs, int nargin, int nargout, bool takes_varargs, const octave_value_list& va_args) { set_auto_fcn_var (stack_frame::ARG_NAMES, Cell (arg_names)); - set_auto_fcn_var (stack_frame::IGNORED, ignored_fcn_outputs ()); + set_auto_fcn_var (stack_frame::IGNORED, ignored_outputs); set_auto_fcn_var (stack_frame::NARGIN, nargin); set_auto_fcn_var (stack_frame::NARGOUT, nargout); set_auto_fcn_var (stack_frame::SAVED_WARNING_STATES, octave_value ()); diff -r 3e60f505f038 -r 5f4e8dddf05f libinterp/parse-tree/pt-eval.h --- a/libinterp/parse-tree/pt-eval.h Tue Jul 07 13:15:45 2020 -0400 +++ b/libinterp/parse-tree/pt-eval.h Tue Jul 07 19:40:20 2020 -0400 @@ -363,7 +363,8 @@ octave_value_list convert_return_list_to_const_vector - (tree_parameter_list *ret_list, int nargout, const Cell& varargout); + (tree_parameter_list *ret_list, int nargout, + const Matrix& ignored_outputs, const Cell& varargout); bool eval_decl_elt (tree_decl_elt *elt); @@ -741,7 +742,8 @@ bool quit_loop_now (void); - void bind_auto_fcn_vars (const string_vector& arg_names, int nargin, + void bind_auto_fcn_vars (const string_vector& arg_names, + const Matrix& ignored_outputs, int nargin, int nargout, bool takes_varargs, const octave_value_list& va_args);