GNU Octave 11.1.0
A high-level interpreted language, primarily intended for numerical computations, mostly compatible with Matlab
 
Loading...
Searching...
No Matches
error.cc
Go to the documentation of this file.
1////////////////////////////////////////////////////////////////////////
2//
3// Copyright (C) 1993-2026 The Octave Project Developers
4//
5// See the file COPYRIGHT.md in the top-level directory of this
6// distribution or <https://octave.org/copyright/>.
7//
8// This file is part of Octave.
9//
10// Octave is free software: you can redistribute it and/or modify it
11// under the terms of the GNU General Public License as published by
12// the Free Software Foundation, either version 3 of the License, or
13// (at your option) any later version.
14//
15// Octave is distributed in the hope that it will be useful, but
16// WITHOUT ANY WARRANTY; without even the implied warranty of
17// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18// GNU General Public License for more details.
19//
20// You should have received a copy of the GNU General Public License
21// along with Octave; see the file COPYING. If not, see
22// <https://www.gnu.org/licenses/>.
23//
24////////////////////////////////////////////////////////////////////////
25
26#if defined (HAVE_CONFIG_H)
27# include "config.h"
28#endif
29
30#include <cstdarg>
31#include <cstdlib>
32#include <cstring>
33
34#include <algorithm>
35#include <iomanip>
36#include <iostream>
37#include <sstream>
38#include <string>
39
40#include "quit.h"
41
42#include "bp-table.h"
43#include "builtin-defun-decls.h"
44#include "defun.h"
45#include "error.h"
46#include "event-manager.h"
47#include "input.h"
48#include "interpreter-private.h"
49#include "interpreter.h"
50#include "oct-map.h"
51#include "octave.h"
52#include "ov-usr-fcn.h"
53#include "ov.h"
54#include "ovl.h"
55#include "pager.h"
56#include "pt-eval.h"
57#include "unwind-prot.h"
58#include "utils.h"
59#include "variables.h"
60
61static std::string
62format_message (const char *fmt, va_list args)
63{
64 if (! fmt)
65 return "";
66
67 std::ostringstream output_buf;
68
69 octave::vformat (output_buf, fmt, args);
70
71 return output_buf.str ();
72}
73
74OCTAVE_NORETURN
75static void
76error_1 (octave::execution_exception& ee, const char *id, const char *fmt,
77 va_list args)
78{
79 octave::error_system& es = octave::__get_error_system__ ();
80
81 es.error_1 (ee, id, fmt, args);
82}
83
84OCTAVE_NORETURN
85static void
86error_1 (const char *id, const char *fmt, va_list args)
87{
88 octave::error_system& es = octave::__get_error_system__ ();
89
90 es.error_1 (id, fmt, args);
91}
92
93static int
94check_state (const std::string& state)
95{
96 // -1: not found
97 // 0: found, "off"
98 // 1: found, "on"
99 // 2: found, "error"
100
101 if (state == "off")
102 return 0;
103 else if (state == "on")
104 return 1;
105 else if (state == "error")
106 return 2;
107 else
108 return -1;
109}
110
111static void
112vwarning (const char *id, const char *fmt, va_list args)
113{
114 octave::error_system& es = octave::__get_error_system__ ();
115
116 es.vwarning (id, fmt, args);
117}
118
119static void
120defun_usage_message (const char *fmt, ...)
121{
122 va_list args;
123 va_start (args, fmt);
124 error_1 ("", fmt, args);
125 va_end (args);
126}
127
128typedef void (*error_fcn)(const char *, const char *, ...);
129
130static std::string
131handle_message (error_fcn f, const char *id, const char *msg,
132 const octave_value_list& args, bool have_fmt)
133{
134 std::string retval;
135
136 std::string tmpstr;
137
138 if (args.length () > 0)
139 {
140 octave_value arg;
141
142 if (have_fmt)
143 {
144 octave_value_list tmp = octave::Fsprintf (args, 1);
145 arg = tmp(0);
146 }
147 else
148 arg = args(0);
149
150 if (arg.is_defined ())
151 {
152 if (arg.isempty ())
153 return retval;
154 else if (arg.is_string ())
155 {
156 tmpstr = arg.string_value (); // 2-stage assignment required
157 msg = tmpstr.c_str (); // in order to generate pointer
158 // to valid memory.
159 }
160 }
161 }
162
163 // Ugh.
164
165 std::size_t len = strlen (msg);
166
167 if (len > 0)
168 {
169 if (msg[len - 1] == '\n')
170 {
171 if (len > 1)
172 {
173 std::string tmp_msg (msg, len - 1);
174 f (id, "%s\n", tmp_msg.c_str ());
175 retval = tmp_msg;
176 }
177 }
178 else
179 {
180 f (id, "%s", msg);
181 retval = msg;
182 }
183 }
184
185 return retval;
186}
187
188// Determine whether the first argument to error or warning function
189// should be handled as the message identifier or as the format string.
190
191static bool
192maybe_extract_message_id (const std::string& caller,
193 const octave_value_list& args,
194 octave_value_list& nargs,
195 std::string& id)
196{
197 nargs = args;
198 id = "";
199
200 int nargin = args.length ();
201
202 bool have_fmt = nargin > 1;
203
204 if (nargin > 0)
205 {
206 std::string arg1 = args(0).xstring_value ("%s: MESSAGE must be a string",
207 caller.c_str ());
208
209 // For compatibility with Matlab, an identifier must contain ':',
210 // but not at the beginning or the end, and it must not contain '%'
211 // (even if it is not a valid conversion operator) or whitespace.
212
213 if (arg1.find_first_of ("% \f\n\r\t\v") == std::string::npos
214 && arg1.find (':') != std::string::npos
215 && arg1[0] != ':'
216 && arg1.back () != ':')
217 {
218 if (nargin > 1)
219 {
220 id = arg1;
221
222 nargs.resize (nargin-1);
223
224 for (int i = 1; i < nargin; i++)
225 nargs(i-1) = args(i);
226 }
227 else
228 nargs(0) = "call to " + caller
229 + " with message identifier '" + arg1
230 + "' requires message";
231 }
232 }
233
234 return have_fmt;
235}
236
238
240init_warning_options (const std::string& state)
241{
242 octave_scalar_map initw;
243
244 initw.setfield ("identifier", "all");
245 initw.setfield ("state", state);
246
247 return initw;
248}
249
250static octave_map
251init_error_stack (interpreter& interp)
252{
253 tree_evaluator& tw = interp.get_evaluator ();
254
255 return tw.empty_backtrace ();
256}
257
259 : m_interpreter (interp),
260 m_debug_on_error (false),
261 m_debug_on_caught (false),
262 m_debug_on_warning (false),
263 m_discard_warning_messages (false),
264 m_beep_on_error (false),
265 m_backtrace_on_warning (true),
266 m_verbose_warning (false),
267 m_quiet_warning (false),
268 m_warning_options (init_warning_options ("on")),
269 m_last_error_message (),
270 m_last_warning_message (),
271 m_last_warning_id (),
272 m_last_error_id (),
273 m_last_error_stack (init_error_stack (interp))
274{
276}
277
280{
281 return set_internal_variable (m_debug_on_error, args, nargout,
282 "debug_on_error");
283}
284
287{
288 return set_internal_variable (m_debug_on_caught, args, nargout,
289 "debug_on_caught");
290}
291
294{
295 return set_internal_variable (m_debug_on_warning, args, nargout,
296 "debug_on_warning");
297}
298
301 int nargout)
302{
303 return set_internal_variable (m_discard_warning_messages, args, nargout,
304 "discard_warning_messages");
305}
306
309{
310 return set_internal_variable (m_beep_on_error, args, nargout,
311 "beep_on_error");
312}
313
316 int nargout)
317{
318 return set_internal_variable (m_backtrace_on_warning, args, nargout,
319 "backtrace_on_warning");
320}
321
324{
325 return set_internal_variable (m_verbose_warning, args, nargout,
326 "verbose_warning");
327}
328
331{
332 return set_internal_variable (m_quiet_warning, args, nargout,
333 "quiet_warning");
334}
335
338{
339 return set_internal_variable (m_last_error_message, args, nargout,
340 "last_error_message");
341}
342
345 int nargout)
346{
347 return set_internal_variable (m_last_warning_message, args, nargout,
348 "last_warning_message");
349}
350
353{
354 return set_internal_variable (m_last_warning_id, args, nargout,
355 "last_warning_id");
356}
357
360{
361 return set_internal_variable (m_last_error_id, args, nargout,
362 "last_error_id");
363}
364
365// Use static fields for the best efficiency.
366// NOTE: C++0x will allow these two to be merged into one.
367static const char *bt_fieldnames[] =
368{ "file", "name", "line", "column", nullptr };
369
370static const octave_fields bt_fields (bt_fieldnames);
371
373error_system::make_stack_map (const std::list<frame_info>& frames)
374{
375 std::size_t nframes = frames.size ();
376
377 octave_map retval (dim_vector (nframes, 1), bt_fields);
378
379 Cell& file = retval.contents (0);
380 Cell& name = retval.contents (1);
381 Cell& line = retval.contents (2);
382 Cell& column = retval.contents (3);
383
384 octave_idx_type k = 0;
385
386 for (const auto& frm : frames)
387 {
388 file(k) = frm.file_name ();
389 name(k) = frm.fcn_name ();
390 line(k) = frm.line ();
391 column(k) = frm.column ();
392
393 k++;
394 }
395
396 return retval;
397}
398
399static std::list<frame_info>
400make_stack_frame_list_intern (const octave_map& stack)
401{
402 std::list<frame_info> frames;
403
404 Cell file = stack.contents ("file");
405 Cell name = stack.contents ("name");
406 Cell line = stack.contents ("line");
407 Cell column = stack.contents ("column");
408
409 octave_idx_type nel = name.numel ();
410
411 for (octave_idx_type i = 0; i < nel; i++)
412 frames.push_back (frame_info (file(i).string_value (),
413 name(i).string_value (),
414 line(i).int_value (),
415 column(i).int_value ()));
416
417 return frames;
418}
419
420std::list<frame_info>
422 const std::string& who)
423{
424 if (! (stack.contains ("file") && stack.contains ("name")
425 && stack.contains ("line")))
426 error ("%s: STACK struct must contain the fields 'file', 'name', and 'line'",
427 who.c_str ());
428
429 if (! stack.contains ("column"))
430 {
431 octave_map stack1 (stack); // copy before modification
432 stack1.setfield ("column", Cell (octave_value (-1)));
433 return make_stack_frame_list_intern (stack1);
434 }
435 else
436 return make_stack_frame_list_intern (stack);
437}
438
439// For given warning ID, return 0 if warnings are disabled, 1 if
440// enabled, and 2 if the given ID should be an error instead of a
441// warning.
442
443int
444error_system::warning_enabled (const std::string& id)
445{
446 int retval = 0;
447
448 int all_state = -1;
449 int id_state = -1;
450
451 octave_map opts = warning_options ();
452
453 octave_idx_type nel = opts.numel ();
454
455 if (nel > 0)
456 {
457 Cell identifier = opts.contents ("identifier");
458 Cell state = opts.contents ("state");
459
460 bool all_found = false;
461 bool id_found = false;
462
463 for (octave_idx_type i = 0; i < nel; i++)
464 {
465 octave_value ov = identifier(i);
466 std::string ovs = ov.string_value ();
467
468 if (! all_found && ovs == "all")
469 {
470 all_state = check_state (state(i).string_value ());
471
472 if (all_state >= 0)
473 all_found = true;
474 }
475
476 if (! id_found && ovs == id)
477 {
478 id_state = check_state (state(i).string_value ());
479
480 if (id_state >= 0)
481 id_found = true;
482 }
483
484 if (all_found && id_found)
485 break;
486 }
487 }
488
489 // If "all" is not present, assume warnings are enabled.
490 if (all_state == -1)
491 all_state = 1;
492
493 if (all_state == 0)
494 {
495 if (id_state >= 0)
496 retval = id_state;
497 }
498 else if (all_state == 1)
499 {
500 if (id_state == 0 || id_state == 2)
501 retval = id_state;
502 else
503 retval = all_state;
504 }
505 else if (all_state == 2)
506 {
507 if (id_state == 0)
508 retval= id_state;
509 else
510 retval = all_state;
511 }
512
513 return retval;
514}
515
516void
517error_system::vusage (const char *id, const char *fmt, va_list args)
518{
519 std::string str_id = id ? id : "";
520 std::string message = format_message (fmt, args);
521
522 throw_error ("usage", str_id, message);
523}
524
525void
526error_system::vwarning (const char *name, const char *id,
527 const char *fmt, va_list args)
528{
529 int warn_opt = warning_enabled (id);
530
531 if (warn_opt == 2)
532 {
533 // Handle this warning as an error. ERROR_1 won't return.
534 error_1 (id, fmt, args);
535 }
536
537 std::string base_msg = format_message (fmt, args);
538 std::string msg_string;
539
540 if (name)
541 msg_string = std::string (name) + ": ";
542
543 msg_string += base_msg;
544
545 // Set LAST_WARNING_MESSAGE independent on whether the WARN_OPT is 0 unless
546 // warnings are quiet. In that case, only set LAST_WARNING_MESSAGE if the
547 // warning is not disabled. Quiet warnings are used, e.g., for the "warning"
548 // mode of the "test" function.
549 if (! quiet_warning () || warn_opt != 0)
550 {
551 last_warning_id (id);
552 last_warning_message (base_msg);
553 }
554
555 // If WARN_OPT is 0, then the warning is disabled.
556 if (discard_warning_messages () || warn_opt == 0)
557 return;
558
559 bool fmt_suppresses_backtrace = false;
560 std::size_t fmt_len = (fmt ? strlen (fmt) : 0);
561 fmt_suppresses_backtrace = (fmt_len > 0 && fmt[fmt_len-1] == '\n');
562
563 if (! fmt_suppresses_backtrace)
564 msg_string += '\n';
565
566 tree_evaluator& tw = m_interpreter.get_evaluator ();
567
568 bool in_user_code = tw.in_user_code ();
569
570 flush_stdout ();
571
572 if (! quiet_warning ())
573 {
574 octave_diary << msg_string;
575 std::cerr << msg_string;
576
577 if (! fmt_suppresses_backtrace && in_user_code
580 {
581 std::string bt_msg = tw.backtrace_message ();
582
583 if (! bt_msg.empty ())
584 bt_msg = "warning: called from\n" + bt_msg;
585
586 octave_diary << bt_msg << std::endl;
587 std::cerr << bt_msg << std::endl;
588 }
589 }
590
591 bp_table& bptab = tw.get_bp_table ();
592
593 if ((m_interpreter.interactive ()
595 && debug_on_warning () && in_user_code && bptab.debug_on_warn (id))
596 {
597 unwind_protect_var<bool> restore_var (m_debug_on_warning, false);
598
599 tw.enter_debugger ();
600 }
601}
602
603void
605 const char *fmt, va_list args)
606{
607 ee.set_identifier (id);
608 ee.set_message (format_message (fmt, args));
609
610 throw_error (ee);
611}
612
613void
614error_system::error_1 (const char *id, const char *fmt,
615 va_list args)
616{
617 std::string message = format_message (fmt, args);
618
619 std::list<frame_info> stack_info;
620
621 throw_error ("error", id, message);
622}
623
624void
625error_system::vwarning (const char *id, const char *fmt, va_list args)
626{
627 // OK, this probably seems strange now, but there is a version of
628 // vwarning that takes the "name" of the warning as an argument,
629 // possibly because "usage" was previously handled as a warning?
630 // For consistent behavior, that function will deal with all the
631 // ON/OFF/ERROR warning state options.
632 vwarning ("warning", id, fmt, args);
633}
634
635void
636error_system::rethrow_error (const std::string& id,
637 const std::string& msg,
638 const octave_map& stack)
639{
640 std::list<frame_info> stack_info;
641
642 execution_exception ee ("error", id, msg, stack_info);
643
644 if (! stack.isempty ())
645 ee.set_stack_info (make_stack_frame_list (stack, "rethrow"));
646
647 throw_error (ee);
648}
649
650void
651error_system::vpanic (const char *fmt, va_list args)
652{
653 // Earlier versions of Octave printed a message directly to std::cerr
654 // and called abort. That might be acceptable behavior for some
655 // programs but for an interactive application like Octave, aborting
656 // the entire program when an internal programming error has been
657 // detected seems unnecessary and certainly provides a much worse user
658 // experience than simply generating an ordinary error message and
659 // attempting to return to the command prompt.
660
661 ::verror (fmt, args);
662}
663
664void
665error_system::panic (const char *fmt, ...)
666{
667 va_list args;
668 va_start (args, fmt);
669 vpanic (fmt, args);
670 va_end (args);
671}
672
674error_system::warning_query (const std::string& id_arg)
675{
676 octave_scalar_map retval;
677
678 std::string id = id_arg;
679
680 if (id == "last")
681 id = last_warning_id ();
682
683 octave_map opts = warning_options ();
684
685 Cell ident = opts.contents ("identifier");
686 Cell state = opts.contents ("state");
687
688 octave_idx_type nel = ident.numel ();
689
690 panic_if (nel == 0);
691
692 bool found = false;
693
694 std::string val;
695
696 for (octave_idx_type i = 0; i < nel; i++)
697 {
698 if (ident(i).string_value () == id)
699 {
700 val = state(i).string_value ();
701 found = true;
702 break;
703 }
704 }
705
706 if (! found)
707 {
708 for (octave_idx_type i = 0; i < nel; i++)
709 {
710 if (ident(i).string_value () == "all")
711 {
712 val = state(i).string_value ();
713 found = true;
714 break;
715 }
716 }
717 }
718
719 // The warning state "all" is always supposed to remain in the list,
720 // so we should always find a state, either explicitly or by using the
721 // state for "all".
722 panic_unless (found);
723
724 retval.assign ("identifier", id);
725 retval.assign ("state", val);
726
727 return retval;
728}
729
730std::string
732{
733 std::string retval = "on";
734
735 octave_map opts = warning_options ();
736
737 Cell ident = opts.contents ("identifier");
738 Cell state = opts.contents ("state");
739
740 octave_idx_type nel = ident.numel ();
741
742 for (octave_idx_type i = 0; i < nel; i++)
743 {
744 if (ident(i).string_value () == "all")
745 {
746 retval = state(i).string_value ();
747 break;
748 }
749 }
750
751 return retval;
752}
753
754void
756{
757 octave_map opts = warning_options ();
758
759 Cell ident = opts.contents ("identifier");
760 Cell state = opts.contents ("state");
761
762 octave_idx_type nel = ident.numel ();
763
764 std::string all_state = default_warning_state ();
765
766 if (all_state == "on")
767 os << "By default, warnings are enabled.";
768 else if (all_state == "off")
769 os << "By default, warnings are disabled.";
770 else if (all_state == "error")
771 os << "By default, warnings are treated as errors.";
772 else
773 error ("unexpected default warning state '%s' - please report this bug", all_state.c_str ());
774
775 if (nel > 1)
776 {
777 os << "\n";
778 os << "Non-default warning states are:\n\n";
779 os << " State Warning ID\n";
780 }
781
782 // The state for "all" is always supposed to be first in the list.
783
784 for (octave_idx_type i = 1; i < nel; i++)
785 {
786 std::string tid = ident(i).string_value ();
787 std::string tst = state(i).string_value ();
788
789 os << std::setw (7) << tst << " " << tid << "\n";
790 }
791
792 os << std::endl;
793}
794
795void
796error_system::set_warning_option (const std::string& state,
797 const std::string& ident)
798{
799 std::string all_state = default_warning_state ();
800
801 if (state != "on" && state != "off" && state != "error")
802 error ("invalid warning state: %s", state.c_str ());
803
804 octave_map opts = warning_options ();
805
806 Cell tid = opts.contents ("identifier");
807 Cell tst = opts.contents ("state");
808
809 octave_idx_type nel = tid.numel ();
810
811 for (octave_idx_type i = 0; i < nel; i++)
812 {
813 if (tid(i).string_value () == ident)
814 {
815 // We found it in the current list of options. If the state
816 // for "all" is same as arg1, we can simply remove the item
817 // from the list.
818
819 if (state == all_state && ident != "all")
820 {
821 for (i = i + 1; i < nel; i++)
822 {
823 tid(i-1) = tid(i);
824 tst(i-1) = tst(i);
825 }
826
827 tid.resize (dim_vector (1, nel-1));
828 tst.resize (dim_vector (1, nel-1));
829 }
830 else
831 tst(i) = state;
832
833 opts.clear ();
834
835 opts.assign ("identifier", tid);
836 opts.assign ("state", tst);
837
838 warning_options (opts);
839
840 return;
841 }
842 }
843
844 // The option wasn't already in the list. Append it.
845
846 tid.resize (dim_vector (1, nel+1));
847 tst.resize (dim_vector (1, nel+1));
848
849 tid(nel) = ident;
850 tst(nel) = state;
851
852 opts.clear ();
853
854 opts.assign ("identifier", tid);
855 opts.assign ("state", tst);
856
857 warning_options (opts);
858}
859
860void
861error_system::disable_warning (const std::string& id)
862{
863 set_warning_option ("off", id);
864}
865
866void
868{
869 warning_options (init_warning_options ("on"));
870
871 // Most people will want to have the following disabled.
872
873 disable_warning ("Octave:array-as-logical");
874 disable_warning ("Octave:array-to-scalar");
875 disable_warning ("Octave:array-to-vector");
876 disable_warning ("Octave:imag-to-real");
877 disable_warning ("Octave:language-extension");
878 disable_warning ("Octave:missing-semicolon");
879 disable_warning ("Octave:neg-dim-as-zero");
880 disable_warning ("Octave:separator-insert");
881 disable_warning ("Octave:single-quote-string");
882 disable_warning ("Octave:str-to-num");
883 disable_warning ("Octave:mixed-string-concat");
884 disable_warning ("Octave:variable-switch-label");
885}
886
887void
889{
890 frame.protect_var (m_debug_on_error);
891 m_debug_on_error = false;
892
893 frame.protect_var (m_debug_on_warning);
894 m_debug_on_warning = false;
895
896 // Leave debug_on_caught as it was, so errors in try/catch are still
897 // caught.
898}
899
900void
901error_system::throw_error (const std::string& err_type,
902 const std::string& id,
903 const std::string& message,
904 const std::list<frame_info>& stack_info_arg)
905{
906 std::list<frame_info> stack_info = stack_info_arg;
907
908 if (stack_info.empty ())
909 {
910 tree_evaluator& tw = m_interpreter.get_evaluator ();
911
912 stack_info = tw.backtrace_info ();
913
914 // Print the error message only if it is different from the
915 // previous one; makes the output more concise and readable.
916
917 stack_info.unique ();
918 }
919
920 execution_exception ex (err_type, id, message, stack_info);
921
922 throw_error (ex);
923}
924
925void
927{
928 throw ex;
929}
930
931void
933{
934 last_error_id (ee.identifier ());
935 std::string message = ee.message ();
936 std::string xmsg
937 = (message.size () > 0 && message.back () == '\n'
938 ? message.substr (0, message.size () - 1) : message);
939 last_error_message (xmsg);
940 last_error_stack (make_stack_map (ee.stack_info ()));
941}
942
943void
945{
946 // FIXME: How should we handle beep_on_error?
947
948 ee.display (octave_diary);
949
950 // FIXME: Handle display using an event manager message so that the
951 // GUI or other client can receive error messages without needing to
952 // capture them from std::cerr or some other stream.
953
954 event_manager& evmgr = m_interpreter.get_event_manager ();
955
956 evmgr.display_exception (ee, m_beep_on_error);
957}
958
959OCTAVE_END_NAMESPACE(octave)
960
961void
962vmessage (const char *name, const char *fmt, va_list args)
963{
964 std::string message;
965
966 if (name)
967 message = std::string (name) + ": ";
968
969 message += format_message (fmt, args);
970
971 octave_diary << message << std::endl;
972 std::cerr << message << std::endl;
973}
974
975void
976message (const char *name, const char *fmt, ...)
977{
978 va_list args;
979 va_start (args, fmt);
980 vmessage (name, fmt, args);
981 va_end (args);
982}
983
984void
985vusage_with_id (const char *id, const char *fmt, va_list args)
986{
987 octave::error_system& es = octave::__get_error_system__ ();
988
989 es.vusage (id, fmt, args);
990}
991
992void
993usage_with_id (const char *id, const char *fmt, ...)
994{
995 va_list args;
996 va_start (args, fmt);
997 vusage_with_id (id, fmt, args);
998 va_end (args);
999}
1000
1001void
1002verror (const char *fmt, va_list args)
1003{
1004 error_1 ("", fmt, args);
1005}
1006
1007void
1008error (const char *fmt, ...)
1009{
1010 va_list args;
1011 va_start (args, fmt);
1012 verror (fmt, args);
1013 va_end (args);
1014}
1015
1016void
1017verror (octave::execution_exception& ee, const char *fmt, va_list args)
1018{
1019 error_1 (ee, "", fmt, args);
1020}
1021
1022void
1023error (octave::execution_exception& ee, const char *fmt, ...)
1024{
1025 va_list args;
1026 va_start (args, fmt);
1027 verror (ee, fmt, args);
1028 va_end (args);
1029}
1030
1031void
1032verror_with_cfn (const char *fmt, va_list args)
1033{
1034 error_1 ("", fmt, args);
1035}
1036
1037void
1038error_with_cfn (const char *fmt, ...)
1039{
1040 va_list args;
1041 va_start (args, fmt);
1042 verror_with_cfn (fmt, args);
1043 va_end (args);
1044}
1045
1046void
1047verror_with_id (const char *id, const char *fmt, va_list args)
1048{
1049 error_1 (id, fmt, args);
1050}
1051
1052void
1053error_with_id (const char *id, const char *fmt, ...)
1054{
1055 va_list args;
1056 va_start (args, fmt);
1057 verror_with_id (id, fmt, args);
1058 va_end (args);
1059}
1060
1061void
1062verror_with_id_cfn (const char *id, const char *fmt, va_list args)
1063{
1064 error_1 (id, fmt, args);
1065}
1066
1067void
1068error_with_id_cfn (const char *id, const char *fmt, ...)
1069{
1070 va_list args;
1071 va_start (args, fmt);
1072 verror_with_id_cfn (id, fmt, args);
1073 va_end (args);
1074}
1075
1076void
1077vwarning (const char *fmt, va_list args)
1078{
1079 vwarning ("", fmt, args);
1080}
1081
1082void
1083warning (const char *fmt, ...)
1084{
1085 va_list args;
1086 va_start (args, fmt);
1087 vwarning (fmt, args);
1088 va_end (args);
1089}
1090
1091void
1092vwarning_with_id (const char *id, const char *fmt, va_list args)
1093{
1094 vwarning (id, fmt, args);
1095}
1096
1097void
1098warning_with_id (const char *id, const char *fmt, ...)
1099{
1100 va_list args;
1101 va_start (args, fmt);
1102 vwarning (id, fmt, args);
1103 va_end (args);
1104}
1105
1106void
1107vparse_error (const char *fmt, va_list args)
1108{
1109 error_1 ("", fmt, args);
1110}
1111
1112void
1113parse_error (const char *fmt, ...)
1114{
1115 va_list args;
1116 va_start (args, fmt);
1117 vparse_error (fmt, args);
1118 va_end (args);
1119}
1120
1121void
1122vparse_error_with_id (const char *id, const char *fmt, va_list args)
1123{
1124 error_1 (id, fmt, args);
1125}
1126
1127void
1128parse_error_with_id (const char *id, const char *fmt, ...)
1129{
1130 va_list args;
1131 va_start (args, fmt);
1132 vparse_error_with_id (id, fmt, args);
1133 va_end (args);
1134}
1135
1137
1138void
1139defun_usage_message (const std::string& msg)
1140{
1141 ::defun_usage_message ("%s", msg.c_str ());
1142}
1143
1144DEFMETHOD (rethrow, interp, args, ,
1145 doc: /* -*- texinfo -*-
1146@deftypefn {} {} rethrow (@var{err})
1147Reissue a previous error as defined by @var{err}.
1148
1149@var{err} is a structure that must contain at least the @qcode{"message"}
1150and @qcode{"identifier"} fields. @var{err} can also contain a field
1151@qcode{"stack"} that gives information on the assumed location of the
1152error. Typically @var{err} is returned from @code{lasterror}.
1153@seealso{lasterror, lasterr, error}
1154@end deftypefn */)
1155{
1156 if (args.length () != 1)
1157 print_usage ();
1158
1159 const octave_scalar_map err = args(0).scalar_map_value ();
1160
1161 if (! (err.contains ("message") && err.contains ("identifier")))
1162 error ("rethrow: ERR struct must contain the fields 'message' and 'identifier'");
1163
1164 std::string msg = err.contents ("message").string_value ();
1165 std::string id = err.contents ("identifier").string_value ();
1166
1167 octave_map err_stack = init_error_stack (interp);
1168
1169 if (err.contains ("stack"))
1170 err_stack = err.contents ("stack").xmap_value ("ERR.STACK must be a struct");
1171
1172 error_system& es = interp.get_error_system ();
1173
1174 es.rethrow_error (id, msg, err_stack);
1175
1176 return ovl ();
1177}
1178
1179DEFMETHOD (error, interp, args, ,
1180 doc: /* -*- texinfo -*-
1181@deftypefn {} {} error (@var{msg})
1182@deftypefnx {} {} error (@var{template}, @dots{})
1183@deftypefnx {} {} error (@var{id}, @var{template}, @dots{})
1184@deftypefnx {} {} error (@var{errstruct})
1185Display an error message and stop m-file execution.
1186
1187The input @var{msg} is a simple string to which the text @samp{error: } is
1188prepended. The resulting message is printed on the @code{stderr} stream.
1189Alternatively, the first input may be a template string @var{template} which
1190uses the same rules as the @code{printf} family of functions
1191(@pxref{Formatted Output}). Formatting is only done for single-quoted
1192character vectors if there are additional arguments following the template
1193string. If there are no additional arguments, the template string is used
1194literally (i.e., without interpreting any escape sequences in single-quoted
1195character vectors).
1196
1197The optional @var{id} argument allows programmers to tag an error
1198with a specific identifier so that users can later retrieve it (using
1199@code{lasterr} or @code{lasterror}) and know the origin of the error.
1200The identifier must contain at least one colon character (@qcode{':'})
1201and must not contain any whitespace characters. It should be a string of
1202the form @qcode{"NAMESPACE:ERROR-NAME"}@. Octave's own errors use the
1203@qcode{"Octave"} namespace (@pxref{XREFerror_ids,,@code{error_ids}}).
1204For example:
1205
1206@example
1207@group
1208error ("MyNameSpace:wrong-type-argument",
1209 "fcn_name: argument should be numeric");
1210@end group
1211@end example
1212
1213Calling @code{error} also sets Octave's internal error state such that
1214control will return to the top level without evaluating any further
1215commands. This is useful for aborting from functions or scripts.
1216
1217If the error message does not end with a newline character, Octave will
1218print a traceback of all the function calls leading to the error. For
1219example, given the following function definitions:
1220
1221@example
1222@group
1223function f () g (); end
1224function g () h (); end
1225function h () nargin == 1 || error ("nargin != 1"); end
1226@end group
1227@end example
1228
1229@noindent
1230calling the function @code{f} will result in a list of messages that
1231can help you to quickly find the exact location of the error:
1232
1233@example
1234@group
1235f ()
1236error: nargin != 1
1237error: called from:
1238error: h at line 1, column 27
1239error: g at line 1, column 15
1240error: f at line 1, column 15
1241@end group
1242@end example
1243
1244If the error message ends in a newline character, Octave will print the
1245message but will not display any traceback messages as it returns
1246control to the top level. For example, modifying the error message
1247in the previous example to end in a newline causes Octave to only print
1248a single message:
1249
1250@example
1251@group
1252function h () nargin == 1 || error ("nargin != 1\n"); end
1253f ()
1254error: nargin != 1
1255@end group
1256@end example
1257
1258A null string ("") input to @code{error} will be ignored and the code
1259will continue running as if the statement were a NOP@. This is for
1260compatibility with @sc{matlab}. It also makes it possible to write code
1261such as
1262
1263@example
1264@group
1265err_msg = "";
1266if (CONDITION 1)
1267 err_msg = "CONDITION 1 found";
1268elseif (CONDITION2)
1269 err_msg = "CONDITION 2 found";
1270@dots{}
1271endif
1272error (err_msg);
1273@end group
1274@end example
1275
1276@noindent
1277which will only stop execution if an error has been found.
1278
1279The function may also be called with an error structure such as that returned
1280from @code{lasterror}. The @var{errstruct} argument must contain fields
1281@code{message}, @code{identifier}, and @code{stack}. The first two fields are
1282strings with the meanings discussed above. The @code{stack} field must be a
1283structure or structure array with fields @code{file}, @code{name}, and
1284@code{line}.
1285
1286Implementation Note: For compatibility with @sc{matlab}, escape
1287sequences in @var{template} (e.g., @qcode{"@backslashchar{}n"} =>
1288newline) are processed regardless of whether @var{template} has been defined
1289with single quotes, as long as there are two or more input arguments. To
1290disable escape sequence expansion use a second backslash before the sequence
1291(e.g., @qcode{"@backslashchar{}@backslashchar{}n"}) or use the
1292@code{regexptranslate} function.
1293@seealso{warning, lasterror}
1294@end deftypefn */)
1295{
1296 int nargin = args.length ();
1297
1298 if (nargin == 0)
1299 print_usage ();
1300
1301 octave_value retval;
1302
1303 std::string id;
1304 std::string message;
1305 std::list<frame_info> stack_info;
1306
1307 bool have_fmt = false;
1308
1309 if (nargin == 1 && args(0).isstruct ())
1310 {
1311 // empty struct is not an error. return and resume calling function.
1312 if (args(0).isempty ())
1313 return retval;
1314
1315 octave_scalar_map m = args(0).xscalar_map_value ("ERRSTRUCT must be a scalar structure with fields 'message' and 'identifier'");
1316
1317 // empty struct is not an error. return and resume calling function.
1318 if (m.nfields () == 0)
1319 return retval;
1320
1321 if (! m.contains ("message"))
1322 error_with_id ("Octave:invalid-input-arg",
1323 "error: ERRSTRUCT must have field 'message'");
1324 else
1325 {
1326 octave_value c = m.getfield ("message");
1327
1328 if (! c.isempty ())
1329 message = c.xstring_value ("error: MESSAGE must be a string");
1330 }
1331
1332 if (! m.contains ("identifier"))
1333 error_with_id ("Octave:invalid-input-arg",
1334 "error: ERRSTRUCT must have field 'identifier'");
1335 else
1336 {
1337 octave_value c = m.getfield ("identifier");
1338
1339 if (! c.isempty ())
1340 id = c.xstring_value ("error: IDENTIFIER must be a string");
1341 }
1342
1343 if (m.contains ("stack"))
1344 {
1345 octave_value c = m.getfield ("stack");
1346
1347 if (! c.isempty ())
1348 {
1349 octave_map stack = c.xmap_value ("error: STACK must be a structure");
1350 stack_info = error_system::make_stack_frame_list (stack,
1351 "error");
1352 }
1353 }
1354 }
1355 else
1356 {
1357 octave_value_list nargs = args;
1358
1359 have_fmt = maybe_extract_message_id ("error", args, nargs, id);
1360
1361 if (nargs.length () == 0)
1362 message = "unspecified error";
1363 else
1364 {
1365 octave_value arg;
1366
1367 if (have_fmt)
1368 {
1369 octave_value_list tmp = Fsprintf (nargs, 1);
1370 arg = tmp(0);
1371 }
1372 else
1373 arg = nargs(0);
1374
1375 if (arg.is_defined ())
1376 {
1377 if (arg.isempty ())
1378 message = "";
1379 else if (arg.is_string ())
1380 message = arg.string_value ();
1381 }
1382 }
1383 }
1384
1385 if (message.empty ())
1386 return retval;
1387
1388 error_system& es = interp.get_error_system ();
1389
1390 es.throw_error ("error", id, message, stack_info);
1391
1392 return retval;
1393}
1394
1395/*
1396%!error <error message 1>
1397%! error ('error message 1');
1398
1399%!error <error message 2>
1400%! error ('my:error_id_2', 'error message 2');
1401
1402%!error id=my:error_id_3
1403%! error ('my:error_id_3', 'error message 3');
1404
1405%!error <error message 4>
1406%! serr.message = 'error message 4';
1407%! serr.identifier = 'my:error_id_4';
1408%! error (serr);
1409
1410%!error id=my:error_id_5
1411%! serr.message = 'error message 5';
1412%! serr.identifier = 'my:error_id_5';
1413%! error (serr);
1414
1415## bug #67143
1416%!error <error message 6>
1417%! serr.identifier = 'my:error_id_6';
1418%! serr.message = 'error message 6';
1419%! serr.stack = struct ('file', 'myfile', 'name', 'myfcn', 'line', 0);
1420%! error (serr);
1421
1422%!error id=my:error_id_7
1423%! serr.identifier = 'my:error_id_7';
1424%! serr.message = 'error message 7';
1425%! serr.stack = struct ('file', 'myfile', 'name', 'myfcn', 'line', 0, ...
1426%! 'column', 0);
1427%! error (serr);
1428
1429## Test input validation
1430############################################################
1431%!error <Invalid call> error ()
1432
1433%!error <ERRSTRUCT must be a scalar structure>
1434%! serr(1).message = 'msg1';
1435%! serr(1).identifier = 'id1';
1436%! serr(2).message = 'msg2';
1437%! serr(2).identifier = 'id2';
1438%! error (serr);
1439
1440%!error <ERRSTRUCT must have field 'message'>
1441%! serr.identifier = 'id';
1442%! error (serr);
1443
1444%!error <MESSAGE must be a string>
1445%! serr.message = {1};
1446%! error (serr);
1447
1448%!error <ERRSTRUCT must have field 'identifier'>
1449%! serr.message = 'msg';
1450%! error (serr);
1451
1452%!error <IDENTIFIER must be a string>
1453%! serr.message = 'msg';
1454%! serr.identifier = {1};
1455%! error (serr);
1456
1457%!error <STACK must be a structure>
1458%! serr.message = 'msg';
1459%! serr.identifier = 'id';
1460%! serr.stack = 5;
1461%! error (serr);
1462
1463%!error <STACK struct must contain the fields 'file'>
1464%! serr.message = 'msg';
1465%! serr.identifier = 'id';
1466%! serr.stack = struct ('name', 'myfcn', 'line', 0);
1467%! error (serr);
1468
1469%!error <STACK struct must contain the fields .* 'name'>
1470%! serr.message = 'msg';
1471%! serr.identifier = 'id';
1472%! serr.stack = struct ('file', 'myfile', 'line', 0);
1473%! error (serr);
1474
1475%!error <STACK struct must contain the fields .* 'line'>
1476%! serr.message = 'msg';
1477%! serr.identifier = 'id';
1478%! serr.stack = struct ('file', 'myfile', 'name', 'myfcn');
1479%! error (serr);
1480
1481%!error <MESSAGE must be a string> error ({1});
1482
1483*/
1484
1485DEFMETHOD (warning, interp, args, nargout,
1486 doc: /* -*- texinfo -*-
1487@deftypefn {} {} warning (@var{template}, @dots{})
1488@deftypefnx {} {} warning (@var{id}, @var{template}, @dots{})
1489@deftypefnx {} {} warning ("on", @var{id})
1490@deftypefnx {} {} warning ("off", @var{id})
1491@deftypefnx {} {} warning ("error", @var{id})
1492@deftypefnx {} {} warning ("query", @var{id})
1493@deftypefnx {} {} warning (@var{state}, @var{id}, "local")
1494@deftypefnx {} {} warning (@var{warning_struct})
1495@deftypefnx {} {@var{warning_struct} =} warning (@dots{})
1496@deftypefnx {} {} warning (@var{state}, @var{mode})
1497
1498Display a warning message or control the behavior of Octave's warning system.
1499
1500The first call form uses a template @var{template} and optional additional
1501arguments to display a message on the @code{stderr} stream. The message is
1502formatted using the same rules as the @code{printf} family of functions
1503(@pxref{Formatted Output}) and prefixed by the character string
1504@w{@samp{warning: }}. You should use this function when you want to notify the
1505user of an unusual condition, but only when it makes sense for your program to
1506go on. For example:
1507
1508@example
1509@group
1510warning ("foo: maybe something wrong here");
1511@end group
1512@end example
1513
1514If the warning message does not end with a newline character, Octave will
1515print a traceback of all the function calls leading to the warning. If the
1516warning message does end in a newline character, Octave will suppress the
1517traceback messages as it returns control to the top level. For more details
1518and examples, @pxref{XREFerror,,@code{error}}.
1519
1520The optional warning identifier @var{id} allows users to enable or disable
1521warnings tagged by this identifier. A message identifier is a string of the
1522form @qcode{"NAMESPACE:WARNING-NAME"}. Octave's own warnings use the
1523@qcode{"Octave"} namespace (@pxref{XREFwarning_ids,,@code{warning_ids}}). For
1524example:
1525
1526@example
1527@group
1528warning ("MyNameSpace:check-something",
1529 "foo: maybe something wrong here");
1530@end group
1531@end example
1532
1533The second call form is meant to change and/or query the state of warnings.
1534The first input argument must be a string @var{state} (@qcode{"on"},
1535@qcode{"off"}, @qcode{"error"}, or @qcode{"query"}) followed by an optional
1536warning identifier @var{id} or @qcode{"all"} (default).
1537
1538The optional output argument @var{warning_struct} is a structure or structure
1539array with fields @qcode{"state"} and @qcode{"identifier"}. The @var{state}
1540argument may have the following values:
1541
1542@table @asis
1543@item @qcode{"on"}|@qcode{"off"}:
1544Enable or disable the display of warnings identified by @var{id} and optionally
1545return their previous state @var{stout}.
1546
1547@item @qcode{"error"}:
1548Turn warnings identified by @var{id} into errors and optionally return their
1549previous state @var{stout}.
1550
1551@item @qcode{"query"}:
1552Return the current state of warnings identified by @var{id}.
1553@end table
1554
1555A structure or structure array @var{warning_struct}, with fields
1556@qcode{"state"} and @qcode{"identifier"}, may be given as an input to achieve
1557equivalent results. The following example shows how to temporarily disable a
1558warning and then restore its original state:
1559
1560@example
1561@group
1562loglog (-1:10);
1563## Disable the previous warning and save its original state
1564[~, id] = lastwarn ();
1565warnstate = warning ("off", id);
1566loglog (-1:10);
1567## Restore its original state
1568warning (warnstate);
1569@end group
1570@end example
1571
1572If a final argument @qcode{"local"} is provided then the warning state will be
1573set temporarily until the end of the current function. Changes to warning
1574states that are set locally affect the current function and all functions
1575called from the current scope. The previous warning state is restored on
1576return from the current function. The @qcode{"local"} option is ignored if
1577used in the top-level workspace.
1578
1579With no input argument @code{warning ()} is equivalent to
1580@code{warning ("query", "all")} except that in the absence of an output
1581argument, the state of warnings is displayed on @code{stderr}.
1582
1583The level of verbosity of the warning system may also be controlled by two
1584modes @var{mode}:
1585
1586@table @asis
1587@item @qcode{"backtrace"}:
1588enable/disable the display of the stack trace after the warning message
1589
1590@item @qcode{"verbose"}:
1591enable/disable the display of additional information after the warning message
1592@end table
1593
1594In this case the @var{state} argument may only be @qcode{"on"} or
1595@qcode{"off"}.
1596
1597Implementation Note: For compatibility with @sc{matlab}, escape sequences in
1598@var{template} (e.g., @qcode{"@backslashchar{}n"} => newline) are processed
1599regardless of whether @var{template} has been defined with single quotes, as
1600long as there are two or more input arguments. To disable escape sequence
1601expansion use a second backslash before the sequence (e.g.,
1602@qcode{"@backslashchar{}@backslashchar{}n"}) or use the
1603@code{regexptranslate} function.
1604@seealso{warning_ids, lastwarn, error}
1605@end deftypefn */)
1606{
1607 octave_value retval;
1608
1609 int nargin = args.length ();
1610 bool done = false;
1611
1612 error_system& es = interp.get_error_system ();
1613
1614 if (nargin > 0 && args.all_strings_p ())
1615 {
1616 string_vector argv = args.make_argv ("warning");
1617
1618 std::string arg1 = argv[1];
1619 std::transform (arg1.begin (), arg1.end (), arg1.begin (), tolower);
1620 std::string arg2 = "all";
1621 std::string arg2_lc = "all";
1622
1623 if (nargin >= 2)
1624 {
1625 arg2 = argv[2];
1626 arg2_lc = arg2;
1627 std::transform (arg2_lc.begin (), arg2_lc.end (), arg2_lc.begin (),
1628 tolower);
1629 }
1630
1631 if (arg1 == "on" || arg1 == "off" || arg1 == "error")
1632 {
1633 // Prepare output structure
1634 octave_map old_warning_options;
1635 if (arg2_lc == "all")
1636 old_warning_options = es.warning_options ();
1637 else
1638 old_warning_options = octave_map (es.warning_query (arg2));
1639
1640 if (nargin == 3)
1641 {
1642 std::string arg3_lc = argv[3];
1643 std::transform (arg3_lc.begin (), arg3_lc.end (),
1644 arg3_lc.begin (), tolower);
1645 if (arg3_lc == "local" && ! interp.at_top_level ())
1646 {
1647 octave_scalar_map val = es.warning_query (arg2);
1648
1649 octave_value curr_state = val.contents ("state");
1650
1651 // FIXME: this might be better with a dictionary object.
1652 tree_evaluator& tw = interp.get_evaluator ();
1653
1654 octave_value curr_warning_states
1656
1657 octave_map m;
1658
1659 if (curr_warning_states.is_defined ())
1660 m = curr_warning_states.map_value ();
1661 else
1662 {
1663 string_vector fields (2);
1664
1665 fields(0) = "identifier";
1666 fields(1) = "state";
1667
1668 m = octave_map (dim_vector (0, 1), fields);
1669 }
1670
1671 Cell ids = m.contents ("identifier");
1672 Cell states = m.contents ("state");
1673
1674 octave_idx_type nel = states.numel ();
1675 bool found = false;
1677 for (i = 0; i < nel; i++)
1678 {
1679 std::string id = ids(i).string_value ();
1680
1681 if (id == arg2)
1682 {
1683 states(i) = curr_state;
1684 found = true;
1685 break;
1686 }
1687 }
1688
1689 if (! found)
1690 {
1691 m.resize (dim_vector (nel+1, 1));
1692
1693 ids.resize (dim_vector (nel+1, 1));
1694 states.resize (dim_vector (nel+1, 1));
1695
1696 ids(nel) = arg2;
1697 states(nel) = curr_state;
1698 }
1699
1700 m.contents ("identifier") = ids;
1701 m.contents ("state") = states;
1702
1704
1705 // Now ignore the "local" argument,
1706 // and continue to handle the current setting.
1707 nargin--;
1708 }
1709 }
1710
1711 if ((nargin == 1
1712 && (arg1 == "on" || arg1 == "off" || arg1 == "error"))
1713 || (nargin >= 2 && arg2_lc == "all"))
1714 {
1715 // If "all" is given implicitly or explicitly as ID.
1716 if (arg1 == "error")
1717 error (R"(warning: cannot specify "all" warning ID with state "error")");
1718
1719 octave_map tmp;
1720
1721 Cell id (1, 1);
1722 Cell st (1, 1);
1723
1724 id(0) = "all";
1725 st(0) = arg1;
1726
1727 tmp.assign ("identifier", id);
1728 tmp.assign ("state", st);
1729
1730 es.warning_options (tmp);
1731
1732 done = true;
1733 }
1734 else if (arg2_lc == "backtrace")
1735 {
1736 if (arg1 != "error")
1737 {
1738 es.backtrace_on_warning (arg1 == "on");
1739 done = true;
1740 }
1741 }
1742 else if (arg2_lc == "debug")
1743 {
1744 if (arg1 != "error")
1745 {
1746 es.debug_on_warning (arg1 == "on");
1747 done = true;
1748 }
1749 }
1750 else if (arg2_lc == "verbose")
1751 {
1752 if (arg1 != "error")
1753 {
1754 es.verbose_warning (arg1 == "on");
1755 done = true;
1756 }
1757 }
1758 else if (arg2_lc == "quiet")
1759 {
1760 if (arg1 != "error")
1761 {
1762 es.quiet_warning (arg1 == "on");
1763 done = true;
1764 }
1765 }
1766 else
1767 {
1768 if (arg2_lc == "last")
1769 arg2 = es.last_warning_id ();
1770
1771 es.set_warning_option (arg1, arg2);
1772
1773 done = true;
1774 }
1775
1776 if (done && nargout > 0)
1777 retval = old_warning_options;
1778 }
1779 else if (arg1 == "query")
1780 {
1781 if (arg2_lc == "all")
1782 {
1783 if (nargout > 0)
1784 retval = es.warning_options ();
1785 else
1787 }
1788 else if (arg2_lc == "backtrace" || arg2_lc == "debug"
1789 || arg2_lc == "verbose" || arg2_lc == "quiet")
1790 {
1791 if (nargout > 0)
1792 {
1794 tmp.assign ("identifier", arg2_lc);
1795 if (arg2_lc == "backtrace")
1796 tmp.assign ("state", es.backtrace_on_warning () ? "on" : "off");
1797 else if (arg2_lc == "debug")
1798 tmp.assign ("state", es.debug_on_warning () ? "on" : "off");
1799 else if (arg2_lc == "verbose")
1800 tmp.assign ("state", es.verbose_warning () ? "on" : "off");
1801 else
1802 tmp.assign ("state", es.quiet_warning () ? "on" : "off");
1803
1804 retval = tmp;
1805 }
1806 else
1807 {
1808 if (arg2_lc == "backtrace")
1809 octave_stdout << R"("backtrace" warning state is ")" <<
1810 (es.backtrace_on_warning () ? "on" : "off") <<
1811 "\"\n";
1812 else if (arg2_lc == "debug")
1813 octave_stdout << R"("debug" warning state is ")" <<
1814 (es.debug_on_warning () ? "on" : "off") <<
1815 "\"\n";
1816 else if (arg2_lc == "verbose")
1817 octave_stdout << R"("verbose" warning state is ")" <<
1818 (es.verbose_warning () ? "on" : "off") <<
1819 "\"\n";
1820 else
1821 octave_stdout << R"("quiet" warning state is ")" <<
1822 (es.quiet_warning () ? "on" : "off") <<
1823 "\"\n";
1824 }
1825 }
1826 else
1827 {
1828 if (nargout > 0)
1829 retval = es.warning_query (arg2);
1830 else
1831 {
1832 octave_scalar_map tmp = es.warning_query (arg2);
1833
1834 octave_stdout << '"' << arg2 << R"(" warning state is ")" <<
1835 tmp.getfield ("state").string_value () <<
1836 "\"\n";
1837 }
1838 }
1839
1840 done = true;
1841 }
1842 }
1843 else if (nargin == 0)
1844 {
1845 if (nargout > 0)
1846 retval = es.warning_options ();
1847 else
1849
1850 done = true;
1851 }
1852 else if (nargin == 1)
1853 {
1854 octave_value arg = args(0);
1855
1856 octave_map old_warning_options;
1857
1858 if (arg.isstruct ())
1859 {
1860 octave_map m = arg.map_value ();
1861
1862 if (! m.contains ("identifier") || ! m.contains ("state"))
1863 error ("warning: STATE structure must have fields 'identifier' and 'state'");
1864
1865 // Simply step through the struct elements one at a time.
1866
1867 Cell ident = m.contents ("identifier");
1868 Cell state = m.contents ("state");
1869
1870 octave_idx_type nel = ident.numel ();
1871
1872 // Prepare output structure
1873 old_warning_options = octave_map (m);
1874 Cell oldstate (state);
1875
1876 for (octave_idx_type i = 0; i < nel; i++)
1877 {
1878 std::string tid = ident(i).string_value ();
1879 oldstate(i) = es.warning_query (tid).getfield ("state");
1880 }
1881 old_warning_options.setfield ("state", oldstate);
1882
1883 // Set new values
1884 for (octave_idx_type i = 0; i < nel; i++)
1885 {
1886 std::string tst = state(i).string_value ();
1887 std::string tid = ident(i).string_value ();
1888
1889 es.set_warning_option (tst, tid);
1890 }
1891
1892 done = true;
1893
1894 if (nargout > 0)
1895 retval = old_warning_options;
1896 }
1897 }
1898
1899 if (! done)
1900 {
1901 octave_value_list nargs = args;
1902
1903 std::string id;
1904
1905 bool have_fmt = maybe_extract_message_id ("warning", args, nargs, id);
1906
1907 std::string prev_msg = es.last_warning_message ();
1908
1909 std::string curr_msg = handle_message (warning_with_id, id.c_str (),
1910 "unspecified warning", nargs,
1911 have_fmt);
1912
1913 if (nargout > 0)
1914 retval = prev_msg;
1915 }
1916
1917 return retval;
1918}
1919
1920/*
1921
1922%!test <*51997>
1923%! id = "Octave:logical-conversion";
1924%! current = warning ("query", id);
1925%! current_all = warning ();
1926%! previous = warning (current_all);
1927%! assert (previous, current_all);
1928%! previous = warning (current);
1929%! assert (previous, current);
1930%! previous = warning (current.state, id);
1931%! assert (previous, current);
1932
1933%!test <*57290>
1934%! warning ("oN", "Octave:test-57290-ID");
1935%! warnst = warning ("QUery", "Octave:test-57290-ID");
1936%! assert (warnst.state, "on");
1937%! assert (warnst.identifier, "Octave:test-57290-ID");
1938%! warning ("OFF", "Octave:test-57290-ID");
1939%! warnst = warning ("QUery", "ALL");
1940%! idx = strcmp ({warnst.identifier}, "Octave:test-57290-ID");
1941%! assert (warnst(idx).state, "off");
1942
1943%!error <cannot specify "all" warning ID> warning ("error")
1944
1945*/
1946
1948set_warning_state (const std::string& id, const std::string& state)
1949{
1950 octave_value_list args (2);
1951
1952 args(0) = state;
1953 args(1) = id;
1954
1955 interpreter& interp = __get_interpreter__ ();
1956
1957 return Fwarning (interp, args, 1);
1958}
1959
1962{
1963 interpreter& interp = __get_interpreter__ ();
1964
1965 return Fwarning (interp, args, 1);
1966}
1967
1968int
1969warning_enabled (const std::string& id)
1970{
1972
1973 return es.warning_enabled (id);
1974}
1975
1976void
1977disable_warning (const std::string& id)
1978{
1980
1981 es.disable_warning (id);
1982}
1983
1984DEFMETHOD (lasterror, interp, args, ,
1985 doc: /* -*- texinfo -*-
1986@deftypefn {} {@var{lasterr} =} lasterror ()
1987@deftypefnx {} {} lasterror (@var{err})
1988@deftypefnx {} {} lasterror ("reset")
1989Query or set the last error message structure.
1990
1991When called without arguments, return a structure containing the last error
1992message and other information related to this error. The elements of the
1993structure are:
1994
1995@table @code
1996@item message
1997The text of the last error message
1998
1999@item identifier
2000The message identifier of this error message
2001
2002@item stack
2003A structure containing information on where the message occurred. This may
2004be an empty structure if the information cannot be obtained. The fields of
2005the structure are:
2006
2007@table @code
2008@item file
2009The name of the file where the error occurred
2010
2011@item name
2012The name of function in which the error occurred
2013
2014@item line
2015The line number at which the error occurred
2016
2017@item column
2018An optional field with the column number at which the error occurred
2019@end table
2020@end table
2021
2022The last error structure may be set by passing a scalar structure,
2023@var{err}, as input. Any fields of @var{err} that match those above are
2024set while any unspecified fields are initialized with default values.
2025
2026If @code{lasterror} is called with the argument @qcode{"reset"}, all
2027fields are set to their default values.
2028@seealso{lasterr, error, lastwarn}
2029@end deftypefn */)
2030{
2031 int nargin = args.length ();
2032
2033 if (nargin > 1)
2034 print_usage ();
2035
2036 error_system& es = interp.get_error_system ();
2037
2039
2040 err.assign ("message", es.last_error_message ());
2041 err.assign ("identifier", es.last_error_id ());
2042
2043 err.assign ("stack", octave_value (es.last_error_stack ()));
2044
2045 if (nargin == 1)
2046 {
2047 tree_evaluator& tw = interp.get_evaluator ();
2048
2049 if (args(0).is_string ())
2050 {
2051 if (args(0).string_value () != "reset")
2052 error ("lasterror: unrecognized string argument");
2053
2054 es.last_error_message ("");
2055 es.last_error_id ("");
2056
2058 }
2059 else if (args(0).isstruct ())
2060 {
2061 octave_scalar_map new_err = args(0).scalar_map_value ();
2062 octave_scalar_map new_err_stack;
2063 std::string new_error_message;
2064 std::string new_error_id;
2065 std::string new_error_file;
2066 std::string new_error_name;
2067 int new_error_line = -1;
2068 int new_error_column = -1;
2069 bool initialize_stack = false;
2070
2071 if (new_err.contains ("message"))
2072 {
2073 const std::string tmp
2074 = new_err.getfield ("message").string_value ();
2075 new_error_message = tmp;
2076 }
2077
2078 if (new_err.contains ("identifier"))
2079 {
2080 const std::string tmp
2081 = new_err.getfield ("identifier").string_value ();
2082 new_error_id = tmp;
2083 }
2084
2085 if (new_err.contains ("stack"))
2086 {
2087 if (new_err.getfield ("stack").isempty ())
2088 initialize_stack = true;
2089 else
2090 {
2091 new_err_stack
2092 = new_err.getfield ("stack").scalar_map_value ();
2093
2094 if (new_err_stack.contains ("file"))
2095 {
2096 const std::string tmp
2097 = new_err_stack.getfield ("file").string_value ();
2098 new_error_file = tmp;
2099 }
2100
2101 if (new_err_stack.contains ("name"))
2102 {
2103 const std::string tmp
2104 = new_err_stack.getfield ("name").string_value ();
2105 new_error_name = tmp;
2106 }
2107
2108 if (new_err_stack.contains ("line"))
2109 {
2110 const int tmp
2111 = new_err_stack.getfield ("line").nint_value ();
2112 new_error_line = tmp;
2113 }
2114
2115 if (new_err_stack.contains ("column"))
2116 {
2117 const int tmp
2118 = new_err_stack.getfield ("column").nint_value ();
2119 new_error_column = tmp;
2120 }
2121 }
2122 }
2123
2124 es.last_error_message (new_error_message);
2125 es.last_error_id (new_error_id);
2126
2127 if (initialize_stack)
2129 else if (new_err.contains ("stack"))
2130 {
2131 new_err_stack.setfield ("file", new_error_file);
2132 new_err_stack.setfield ("name", new_error_name);
2133 new_err_stack.setfield ("line", new_error_line);
2134 new_err_stack.setfield ("column", new_error_column);
2135
2136 es.last_error_stack (new_err_stack);
2137 }
2138 else
2139 es.last_error_stack (tw.backtrace ());
2140 }
2141 else
2142 error ("lasterror: argument must be a structure or a string");
2143 }
2144
2145 return ovl (err);
2146}
2147
2148/*
2149## Test lasterror with empty error state
2150%!test
2151%! lasterror ("reset");
2152%! x = lasterror ();
2153%! assert (x.identifier, "");
2154%! assert (x.message, "");
2155%! assert (isempty (x.stack));
2156%! lasterror (x);
2157%! y = lasterror ();
2158%! assert (y, x);
2159*/
2160
2161DEFMETHOD (lasterr, interp, args, nargout,
2162 doc: /* -*- texinfo -*-
2163@deftypefn {} {[@var{msg}, @var{msgid}] =} lasterr ()
2164@deftypefnx {} {} lasterr (@var{msg})
2165@deftypefnx {} {} lasterr (@var{msg}, @var{msgid})
2166Query or set the last error message.
2167
2168When called without input arguments, return the last error message and
2169message identifier.
2170
2171With one argument, set the last error message to @var{msg}.
2172
2173With two arguments, also set the last message identifier.
2174@seealso{lasterror, error, lastwarn}
2175@end deftypefn */)
2176{
2177 int nargin = args.length ();
2178
2179 if (nargin > 2)
2180 print_usage ();
2181
2182 error_system& es = interp.get_error_system ();
2183
2184 string_vector argv = args.make_argv ("lasterr");
2185
2186 std::string prev_error_id = es.last_error_id ();
2187 std::string prev_error_message = es.last_error_message ();
2188
2189 if (nargin == 2)
2190 {
2191 es.last_error_id (argv[2]);
2192 es.last_error_message (argv[1]);
2193 }
2194 else if (nargin == 1)
2195 {
2196 es.last_error_id ("");
2197 es.last_error_message (argv[1]);
2198 }
2199
2200 if (nargin == 0 || nargout > 0)
2201 return ovl (prev_error_message, prev_error_id);
2202 else
2203 return ovl ();
2204}
2205
2206DEFMETHOD (lastwarn, interp, args, nargout,
2207 doc: /* -*- texinfo -*-
2208@deftypefn {} {[@var{msg}, @var{msgid}] =} lastwarn ()
2209@deftypefnx {} {} lastwarn (@var{msg})
2210@deftypefnx {} {} lastwarn (@var{msg}, @var{msgid})
2211Query or set the last warning message.
2212
2213When called without input arguments, return the last warning message and
2214message identifier.
2215
2216With one argument, set the last warning message to @var{msg}.
2217
2218With two arguments, also set the last message identifier to @var{msgid}.
2219@seealso{warning, lasterror, lasterr}
2220@end deftypefn */)
2221{
2222 int nargin = args.length ();
2223
2224 if (nargin > 2)
2225 print_usage ();
2226
2227 error_system& es = interp.get_error_system ();
2228
2229 string_vector argv = args.make_argv ("lastwarn");
2230
2231 std::string prev_warning_id = es.last_warning_id ();
2232 std::string prev_warning_message = es.last_warning_message ();
2233
2234 if (nargin == 2)
2235 {
2236 es.last_warning_id (argv[2]);
2237 es.last_warning_message (argv[1]);
2238 }
2239 else if (nargin == 1)
2240 {
2241 es.last_warning_id ("");
2242 es.last_warning_message (argv[1]);
2243 }
2244
2245 if (nargin == 0 || nargout > 0)
2246 return ovl (prev_warning_message, prev_warning_id);
2247 else
2248 return ovl ();
2249}
2250
2251DEFMETHOD (beep_on_error, interp, args, nargout,
2252 doc: /* -*- texinfo -*-
2253@deftypefn {} {@var{val} =} beep_on_error ()
2254@deftypefnx {} {@var{old_val} =} beep_on_error (@var{new_val})
2255@deftypefnx {} {@var{old_val} =} beep_on_error (@var{new_val}, "local")
2256Query or set the internal variable that controls whether Octave will try
2257to ring the terminal bell before printing an error message.
2258
2259When called from inside a function with the @qcode{"local"} option, the
2260variable is changed locally for the function and any subroutines it calls.
2261The original variable value is restored when exiting the function.
2262@end deftypefn */)
2263{
2264 error_system& es = interp.get_error_system ();
2265
2266 return es.beep_on_error (args, nargout);
2267}
2268
2269DEFMETHOD (debug_on_error, interp, args, nargout,
2270 doc: /* -*- texinfo -*-
2271@deftypefn {} {@var{val} =} debug_on_error ()
2272@deftypefnx {} {@var{old_val} =} debug_on_error (@var{new_val})
2273@deftypefnx {} {@var{old_val} =} debug_on_error (@var{new_val}, "local")
2274Query or set the internal variable that controls whether Octave will try
2275to enter the debugger when an error is encountered.
2276
2277This will also inhibit printing of the normal traceback message (you will
2278only see the top-level error message).
2279
2280When called from inside a function with the @qcode{"local"} option, the
2281variable is changed locally for the function and any subroutines it calls.
2282The original variable value is restored when exiting the function.
2283@seealso{debug_on_warning, debug_on_interrupt}
2284@end deftypefn */)
2285{
2286 error_system& es = interp.get_error_system ();
2287
2288 return es.debug_on_error (args, nargout);
2289}
2290
2291DEFMETHOD (debug_on_warning, interp, args, nargout,
2292 doc: /* -*- texinfo -*-
2293@deftypefn {} {@var{val} =} debug_on_warning ()
2294@deftypefnx {} {@var{old_val} =} debug_on_warning (@var{new_val})
2295@deftypefnx {} {@var{old_val} =} debug_on_warning (@var{new_val}, "local")
2296Query or set the internal variable that controls whether Octave will try
2297to enter the debugger when a warning is encountered.
2298
2299When called from inside a function with the @qcode{"local"} option, the
2300variable is changed locally for the function and any subroutines it calls.
2301The original variable value is restored when exiting the function.
2302@seealso{debug_on_error, debug_on_interrupt}
2303@end deftypefn */)
2304{
2305 error_system& es = interp.get_error_system ();
2306
2307 return es.debug_on_warning (args, nargout);
2308}
2309
2310void
2312{
2314
2315 es.interpreter_try (frame);
2316}
2317
2318OCTAVE_END_NAMESPACE(octave)
void resize(const dim_vector &dv, const T &rfv)
Size of the specified dimension.
octave_idx_type numel() const
Number of elements in the array.
Definition Array-base.h:440
Definition Cell.h:41
Cell column(octave_idx_type i) const
Definition Cell.cc:303
void protect_var(T &var)
static bool forced_interactive()
Definition octave.cc:342
bool debug_on_warn(const std::string &id)
Definition bp-table.h:154
Vector representing the dimensions (size) of an Array.
Definition dim-vector.h:92
error_system(interpreter &interp)
Definition error.cc:258
octave_value beep_on_error(const octave_value_list &args, int nargout)
Definition error.cc:308
std::string last_error_message() const
Definition error.h:195
void interpreter_try(unwind_protect &frame)
Definition error.cc:888
void display_warning_options(std::ostream &os)
Definition error.cc:755
static std::list< frame_info > make_stack_frame_list(const octave_map &stack, const std::string &who="error")
Definition error.cc:421
std::string last_warning_id() const
Definition error.h:226
octave_value last_error_id(const octave_value_list &args, int nargout)
Definition error.cc:359
bool debug_on_error() const
Definition error.h:64
OCTAVE_NORETURN void error_1(execution_exception &ee, const char *id, const char *fmt, va_list args)
Definition error.cc:604
OCTAVE_NORETURN void vpanic(const char *fmt, va_list args)
Definition error.cc:651
bool debug_on_warning() const
Definition error.h:92
octave_value quiet_warning(const octave_value_list &args, int nargout)
Definition error.cc:330
void verror(bool save_last_error, std::ostream &os, const char *name, const char *id, const char *fmt, va_list args, bool with_cfn=false)
void set_warning_option(const std::string &state, const std::string &id)
Definition error.cc:796
bool beep_on_error() const
Definition error.h:126
OCTAVE_NORETURN void rethrow_error(const std::string &id, const std::string &msg, const octave_map &stack)
Definition error.cc:636
bool verbose_warning() const
Definition error.h:154
octave_scalar_map warning_query(const std::string &id_arg)
Definition error.cc:674
octave_value backtrace_on_warning(const octave_value_list &args, int nargout)
Definition error.cc:315
octave_value last_warning_message(const octave_value_list &args, int nargout)
Definition error.cc:344
OCTAVE_NORETURN void throw_error(const std::string &err_type, const std::string &id, const std::string &message, const std::list< frame_info > &stack_info=std::list< frame_info >())
Definition error.cc:901
octave_map last_error_stack() const
Definition error.h:254
int warning_enabled(const std::string &id)
For given warning ID, return 0 if warnings are disabled, 1 if enabled, and 2 if the given ID should b...
Definition error.cc:444
std::string last_warning_message() const
Definition error.h:210
static octave_map make_stack_map(const std::list< frame_info > &frames)
Definition error.cc:373
OCTAVE_NORETURN void vusage(const char *id, const char *fmt, va_list args)
Definition error.cc:517
octave_value debug_on_warning(const octave_value_list &args, int nargout)
Definition error.cc:293
octave_value verbose_warning(const octave_value_list &args, int nargout)
Definition error.cc:323
bool discard_warning_messages() const
Definition error.h:109
octave_map warning_options() const
Definition error.h:177
void disable_warning(const std::string &id)
Definition error.cc:861
void initialize_default_warning_state()
Definition error.cc:867
void vwarning(const char *name, const char *id, const char *fmt, va_list args)
Definition error.cc:526
octave_value last_warning_id(const octave_value_list &args, int nargout)
Definition error.cc:352
bool debug_on_caught() const
Definition error.h:78
std::string last_error_id() const
Definition error.h:240
void save_exception(const execution_exception &ee)
Definition error.cc:932
octave_value debug_on_error(const octave_value_list &args, int nargout)
Definition error.cc:279
bool quiet_warning() const
Definition error.h:168
octave_value last_error_message(const octave_value_list &args, int nargout)
Definition error.cc:337
bool backtrace_on_warning() const
Definition error.h:140
std::string default_warning_state()
Definition error.cc:731
void display_exception(const execution_exception &ee) const
Definition error.cc:944
OCTAVE_NORETURN void panic(const char *fmt,...)
Definition error.cc:665
Provides threadsafe access to octave.
bool display_exception(const execution_exception &ee, bool beep=false)
error_system & get_error_system()
bool at_top_level() const
bool interactive() const
tree_evaluator & get_evaluator()
event_manager & get_event_manager()
void resize(const dim_vector &dv, bool fill=false)
Definition oct-map.cc:574
void clear()
Definition oct-map.h:361
const Cell & contents(const_iterator p) const
Definition oct-map.h:310
void setfield(const std::string &key, const Cell &val)
Definition oct-map.cc:282
octave_idx_type numel() const
Definition oct-map.h:368
bool contains(const std::string &name) const
Definition oct-map.h:329
void assign(const std::string &k, const Cell &val)
Definition oct-map.h:344
bool isempty() const
Definition oct-map.h:370
const octave_value & contents(const_iterator p) const
Definition oct-map.h:197
bool contains(const std::string &name) const
Definition oct-map.h:216
void setfield(const std::string &key, const octave_value &val)
Definition oct-map.cc:190
void assign(const std::string &k, const octave_value &val)
Definition oct-map.h:230
octave_idx_type nfields() const
Definition oct-map.h:210
octave_value getfield(const std::string &key) const
Definition oct-map.cc:183
void resize(octave_idx_type n, const octave_value &rfv=octave_value())
Definition ovl.h:115
bool all_strings_p() const
Definition ovl.cc:176
string_vector make_argv(const std::string &="") const
Definition ovl.cc:227
octave_idx_type length() const
Definition ovl.h:111
octave_map xmap_value(const char *fmt,...) const
octave_scalar_map scalar_map_value() const
bool is_string() const
Definition ov.h:635
bool is_defined() const
Definition ov.h:590
bool isempty() const
Definition ov.h:599
octave_map map_value() const
std::string string_value(bool force=false) const
Definition ov.h:981
int nint_value(bool frc_str_conv=false) const
Definition ov.h:820
std::string xstring_value(const char *fmt,...) const
bool isstruct() const
Definition ov.h:647
octave_map empty_backtrace() const
Definition pt-eval.cc:2716
octave_value get_auto_fcn_var(stack_frame::auto_var_type avt) const
Definition pt-eval.cc:2247
bool in_user_code() const
Definition pt-eval.cc:3136
octave_map backtrace(octave_idx_type &curr_user_frame, bool print_subfn=true) const
Definition pt-eval.cc:2703
bp_table & get_bp_table()
Definition pt-eval.h:430
std::string backtrace_message() const
Definition pt-eval.cc:2722
std::list< frame_info > backtrace_info(octave_idx_type &curr_user_frame, bool print_subfn=true) const
Definition pt-eval.cc:2690
void set_auto_fcn_var(stack_frame::auto_var_type avt, const octave_value &val=octave_value())
Definition pt-eval.cc:2228
void enter_debugger(const std::string &prompt="debug> ")
Definition pt-eval.cc:1405
OCTAVE_BEGIN_NAMESPACE(octave) static octave_value daspk_fcn
void print_usage()
Definition defun-int.h:72
#define DEFMETHOD(name, interp_name, args_name, nargout_name, doc)
Macro to define a builtin method.
Definition defun.h:111
void interpreter_try(unwind_protect &frame)
Definition error.cc:2311
void error_with_id(const char *id, const char *fmt,...)
Definition error.cc:1053
void(* error_fcn)(const char *, const char *,...)
Definition error.cc:128
void usage_with_id(const char *id, const char *fmt,...)
Definition error.cc:993
void warning(const char *fmt,...)
Definition error.cc:1083
void warning_with_id(const char *id, const char *fmt,...)
Definition error.cc:1098
void verror_with_id_cfn(const char *id, const char *fmt, va_list args)
Definition error.cc:1062
void parse_error_with_id(const char *id, const char *fmt,...)
Definition error.cc:1128
octave_value_list Fwarning(octave::interpreter &interp, const octave_value_list &args, int nargout)
Definition error.cc:1605
void error_with_id_cfn(const char *id, const char *fmt,...)
Definition error.cc:1068
void vwarning_with_id(const char *id, const char *fmt, va_list args)
Definition error.cc:1092
void verror(const char *fmt, va_list args)
Definition error.cc:1002
void verror_with_id(const char *id, const char *fmt, va_list args)
Definition error.cc:1047
void vusage_with_id(const char *id, const char *fmt, va_list args)
Definition error.cc:985
void verror_with_cfn(const char *fmt, va_list args)
Definition error.cc:1032
void error_with_cfn(const char *fmt,...)
Definition error.cc:1038
void vparse_error_with_id(const char *id, const char *fmt, va_list args)
Definition error.cc:1122
void parse_error(const char *fmt,...)
Definition error.cc:1113
void error(const char *fmt,...)
Definition error.cc:1008
void vparse_error(const char *fmt, va_list args)
Definition error.cc:1107
void message(const char *name, const char *fmt,...)
Definition error.cc:976
octave_value_list set_warning_state(const std::string &id, const std::string &state)
Definition error.cc:1948
void vmessage(const char *name, const char *fmt, va_list args)
Definition error.cc:962
void disable_warning(const std::string &id)
Definition error.cc:1977
int warning_enabled(const std::string &id)
Definition error.cc:1969
OCTAVE_NORETURN void error(const char *fmt,...)
Definition error.cc:1008
void message(const char *name, const char *fmt,...)
Definition error.cc:976
octave_value_list Fsprintf(const octave_value_list &args, int)
Definition file-io.cc:1004
error_system & __get_error_system__()
interpreter & __get_interpreter__()
T::size_type strlen(const typename T::value_type *str)
Definition oct-string.cc:95
octave_value_list ovl(const OV_Args &... args)
Construct an octave_value_list with less typing.
Definition ovl.h:217
void flush_stdout()
Definition pager.cc:268
#define octave_stdout
Definition pager.h:301
#define octave_diary
Definition pager.h:303
#define panic_if(cond)
Definition panic.h:57
#define panic_unless(cond)
Definition panic.h:59
F77_RET_T const F77_DBLE const F77_DBLE * f
octave_value set_internal_variable(bool &var, const octave_value_list &args, int nargout, const char *nm)
Definition variables.cc:583
F77_RET_T len
Definition xerbla.cc:61