aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/error.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/error.h')
-rw-r--r--src/error.h316
1 files changed, 123 insertions, 193 deletions
diff --git a/src/error.h b/src/error.h
index a12a76b..16136b9 100644
--- a/src/error.h
+++ b/src/error.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2012-2017 Robin Haberkorn
+ * Copyright (C) 2012-2021 Robin Haberkorn
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -14,205 +14,135 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-
-#ifndef __ERROR_H
-#define __ERROR_H
-
-#include <exception>
-#include <typeinfo>
+#pragma once
#include <glib.h>
-#include <glib/gprintf.h>
#include "sciteco.h"
-#include "memory.h"
#include "string-utils.h"
-namespace SciTECO {
-
-/**
- * Thrown as exception to signify that program
- * should be terminated.
- */
-class Quit : public Object {};
-
-/**
- * Thrown as exception to cause a macro to
- * return or a command-line termination.
+/*
+ * FIXME: Introducing a second error quark might be useful to distinguish
+ * errors that can be cought by SciTECO macros from errors that must always
+ * propagate (TECO_ERROR_QUIT, TECO_ERROR_RETURN).
+ * On the other hand, these error codes will probably soon become obsolete
+ * when the SciTECO call stack no longer corresponds with the C callstack.
*/
-class Return : public Object {
-public:
- guint args;
-
- Return(guint _args = 0) : args(_args) {}
-};
-
-class Error : public Object {
- GSList *frames;
-
-public:
- gchar *description;
- gint pos;
- gint line, column;
-
- class Frame : public Object {
- public:
- gint pos;
- gint line, column;
-
- virtual Frame *copy() const = 0;
- virtual ~Frame() {}
-
- virtual void display(gint nr) = 0;
- };
-
- class QRegFrame : public Frame {
- gchar *name;
-
- public:
- QRegFrame(const gchar *_name)
- : name(g_strdup(_name)) {}
-
- Frame *copy() const;
-
- ~QRegFrame()
- {
- g_free(name);
- }
-
- void display(gint nr);
- };
-
- class FileFrame : public Frame {
- gchar *name;
-
- public:
- FileFrame(const gchar *_name)
- : name(g_strdup(_name)) {}
-
- Frame *copy() const;
-
- ~FileFrame()
- {
- g_free(name);
- }
-
- void display(gint nr);
- };
-
- class EDHookFrame : public Frame {
- gchar *type;
-
- public:
- EDHookFrame(const gchar *_type)
- : type(g_strdup(_type)) {}
-
- Frame *copy() const;
-
- ~EDHookFrame()
- {
- g_free(type);
- }
-
- void display(gint nr);
- };
-
- class ToplevelFrame : public Frame {
- public:
- Frame *copy() const;
-
- void display(gint nr);
- };
-
- Error(const gchar *fmt, ...) G_GNUC_PRINTF(2, 3);
- Error(const Error &inst);
- ~Error();
-
- inline void
- set_coord(const gchar *str, gint _pos)
- {
- pos = _pos;
- String::get_coord(str, pos, line, column);
- }
-
- void add_frame(Frame *frame);
-
- void display_short(void);
- void display_full(void);
-};
+#define TECO_ERROR (g_quark_from_static_string("sciteco-error-quark"))
-class StdError : public Error {
-public:
- StdError(const gchar *type, const std::exception &error)
- : Error("%s: %s", type, error.what()) {}
- StdError(const std::exception &error)
- : Error("%s: %s", typeid(error).name(), error.what()) {}
-};
+typedef enum {
+ /** Default (catch-all) error code */
+ TECO_ERROR_FAILED = 0,
-class GlibError : public Error {
-public:
- /**
- * Construct error for glib's GError.
- * Ownership of the error's resources is passed
- * the GlibError object.
+ /*
+ * FIXME: Subsume all these errors under TECO_ERROR_SYNTAX or TECO_ERROR_FAIL?
+ * They will mainly be different in their error message.
*/
- GlibError(GError *gerror)
- : Error("%s", gerror->message)
- {
- g_error_free(gerror);
- }
-};
-
-class SyntaxError : public Error {
-public:
- SyntaxError(gchar chr)
- : Error("Syntax error \"%c\" (%d)", chr, chr) {}
-};
-
-class ArgExpectedError : public Error {
-public:
- ArgExpectedError(const gchar *cmd)
- : Error("Argument expected for <%s>", cmd) {}
- ArgExpectedError(gchar cmd)
- : Error("Argument expected for <%c>", cmd) {}
-};
-
-class MoveError : public Error {
-public:
- MoveError(const gchar *cmd)
- : Error("Attempt to move pointer off page with <%s>",
- cmd) {}
- MoveError(gchar cmd)
- : Error("Attempt to move pointer off page with <%c>",
- cmd) {}
-};
-
-class RangeError : public Error {
-public:
- RangeError(const gchar *cmd)
- : Error("Invalid range specified for <%s>", cmd) {}
- RangeError(gchar cmd)
- : Error("Invalid range specified for <%c>", cmd) {}
-};
-
-class InvalidQRegError : public Error {
-public:
- InvalidQRegError(const gchar *name, bool local = false)
- : Error("Invalid Q-Register \"%s%s\"",
- local ? "." : "", name) {}
- InvalidQRegError(gchar name, bool local = false)
- : Error("Invalid Q-Register \"%s%c\"",
- local ? "." : "", name) {}
-};
-
-class QRegOpUnsupportedError : public Error {
-public:
- QRegOpUnsupportedError(const gchar *name, bool local = false)
- : Error("Operation unsupported on "
- "Q-Register \"%s%s\"",
- local ? "." : "", name) {}
-};
-
-} /* namespace SciTECO */
-
-#endif
+ TECO_ERROR_SYNTAX,
+ TECO_ERROR_ARGEXPECTED,
+ TECO_ERROR_MOVE,
+ TECO_ERROR_WORDS,
+ TECO_ERROR_RANGE,
+ TECO_ERROR_INVALIDQREG,
+ TECO_ERROR_QREGOPUNSUPPORTED,
+ TECO_ERROR_QREGCONTAINSNULL,
+ TECO_ERROR_MEMLIMIT,
+
+ /** Interrupt current operation */
+ TECO_ERROR_INTERRUPTED,
+
+ /** Thrown to signal command line replacement */
+ TECO_ERROR_CMDLINE = 0x80,
+ /** Thrown as exception to cause a macro to return or a command-line termination. */
+ TECO_ERROR_RETURN,
+ /** Thrown as exception to signify that program should be terminated. */
+ TECO_ERROR_QUIT
+} teco_error_t;
+
+static inline void
+teco_error_syntax_set(GError **error, gchar chr)
+{
+ g_set_error(error, TECO_ERROR, TECO_ERROR_SYNTAX,
+ "Syntax error \"%c\" (%d)", chr, chr);
+}
+
+static inline void
+teco_error_argexpected_set(GError **error, const gchar *cmd)
+{
+ g_set_error(error, TECO_ERROR, TECO_ERROR_ARGEXPECTED,
+ "Argument expected for <%s>", cmd);
+}
+
+static inline void
+teco_error_move_set(GError **error, const gchar *cmd)
+{
+ g_set_error(error, TECO_ERROR, TECO_ERROR_MOVE,
+ "Attempt to move pointer off page with <%s>", cmd);
+}
+
+static inline void
+teco_error_words_set(GError **error, const gchar *cmd)
+{
+ g_set_error(error, TECO_ERROR, TECO_ERROR_MOVE,
+ "Not enough words to delete with <%s>", cmd);
+}
+
+static inline void
+teco_error_range_set(GError **error, const gchar *cmd)
+{
+ g_set_error(error, TECO_ERROR, TECO_ERROR_RANGE,
+ "Invalid range specified for <%s>", cmd);
+}
+
+static inline void
+teco_error_invalidqreg_set(GError **error, const gchar *name, gsize len, gboolean local)
+{
+ g_autofree gchar *name_printable = teco_string_echo(name, len);
+ g_set_error(error, TECO_ERROR, TECO_ERROR_INVALIDQREG,
+ "Invalid %sQ-Register \"%s\"", local ? "local " : "", name_printable);
+}
+
+static inline void
+teco_error_qregopunsupported_set(GError **error, const gchar *name, gsize len, gboolean local)
+{
+ g_autofree gchar *name_printable = teco_string_echo(name, len);
+ g_set_error(error, TECO_ERROR, TECO_ERROR_QREGOPUNSUPPORTED,
+ "Operation unsupported on %sQ-Register \"%s\"", local ? "local " : "", name_printable);
+}
+
+static inline void
+teco_error_qregcontainsnull_set(GError **error, const gchar *name, gsize len, gboolean local)
+{
+ g_autofree gchar *name_printable = teco_string_echo(name, len);
+ g_set_error(error, TECO_ERROR, TECO_ERROR_QREGCONTAINSNULL,
+ "%sQ-Register \"%s\" contains null-byte", local ? "Local " : "", name_printable);
+}
+
+static inline void
+teco_error_interrupted_set(GError **error)
+{
+ g_set_error_literal(error, TECO_ERROR, TECO_ERROR_INTERRUPTED, "Interrupted");
+}
+
+extern guint teco_error_return_args;
+
+static inline void
+teco_error_return_set(GError **error, guint args)
+{
+ teco_error_return_args = args;
+ g_set_error_literal(error, TECO_ERROR, TECO_ERROR_RETURN, "");
+}
+
+extern guint teco_error_pos, teco_error_line, teco_error_column;
+
+void teco_error_set_coord(const gchar *str, guint pos);
+
+void teco_error_display_short(const GError *error);
+void teco_error_display_full(const GError *error);
+
+void teco_error_add_frame_qreg(const gchar *name, gsize len);
+void teco_error_add_frame_file(const gchar *name);
+void teco_error_add_frame_edhook(const gchar *type);
+void teco_error_add_frame_toplevel(void);
+
+void teco_error_clear_frames(void);