aboutsummaryrefslogtreecommitdiffhomepage
path: root/cmdline.cpp
diff options
context:
space:
mode:
authorRobin Haberkorn <robin.haberkorn@googlemail.com>2012-11-17 01:08:28 +0100
committerRobin Haberkorn <robin.haberkorn@googlemail.com>2012-11-17 01:08:28 +0100
commit3c12d015023a48bf6c48dea4ae1a60045b2c9c04 (patch)
tree0f8107ecb96af97fd9bb4ba7b2b1f56311951548 /cmdline.cpp
parent39a5feaf8c080de9e35350b079f47f3914f8b77d (diff)
downloadsciteco-3c12d015023a48bf6c48dea4ae1a60045b2c9c04.tar.gz
fixed behaviour on runtime errors: the character resulting in the error is not accepted and all side-effects up to the exception must be reversed
if more than one character is inserted (e.g. via <TAB>), insertion stops at the offending character
Diffstat (limited to 'cmdline.cpp')
-rw-r--r--cmdline.cpp25
1 files changed, 19 insertions, 6 deletions
diff --git a/cmdline.cpp b/cmdline.cpp
index 5018054..8fc9dc6 100644
--- a/cmdline.cpp
+++ b/cmdline.cpp
@@ -27,8 +27,8 @@ bool quit_requested = false;
void
cmdline_keypress(gchar key)
{
+ gchar *cmdline_p;
const gchar *insert;
- gint old_cmdline_len = 0;
gchar *echo;
/*
@@ -46,21 +46,34 @@ cmdline_keypress(gchar key)
* Parse/execute characters
*/
if (cmdline) {
- old_cmdline_len = strlen(cmdline);
- cmdline = (gchar *)g_realloc(cmdline, old_cmdline_len +
- strlen(insert) + 1);
+ gint len = strlen(cmdline);
+ cmdline = (gchar *)g_realloc(cmdline, len + strlen(insert) + 1);
+ cmdline_p = cmdline + len;
} else {
cmdline = (gchar *)g_malloc(strlen(insert) + 1);
*cmdline = '\0';
+ cmdline_p = cmdline;
}
+ /*
+ * Execute one insertion character, extending cmdline, at a time so
+ * undo tokens get emitted for the corresponding characters.
+ */
for (const gchar *p = insert; *p; p++) {
- strcat(cmdline, (gchar[]){*p, '\0'});
+ *cmdline_p++ = *p;
+ *cmdline_p = '\0';
try {
macro_execute(cmdline);
} catch (...) {
- cmdline[old_cmdline_len] = '\0';
+ /*
+ * Undo tokens may have been emitted (or had to be)
+ * before the exception is thrown. They must be
+ * executed so as if the character had never been
+ * inserted.
+ */
+ undo.pop(cmdline_p - cmdline);
+ cmdline_p[-1] = '\0';
break;
}
}