summaryrefslogtreecommitdiffstats
path: root/tty-keys.c
diff options
context:
space:
mode:
Diffstat (limited to 'tty-keys.c')
-rw-r--r--tty-keys.c152
1 files changed, 84 insertions, 68 deletions
diff --git a/tty-keys.c b/tty-keys.c
index a011fcab..d7797a9c 100644
--- a/tty-keys.c
+++ b/tty-keys.c
@@ -257,67 +257,70 @@ static const struct tty_default_key_code tty_default_code_keys[] = {
{ TTYC_KCUB1, KEYC_LEFT },
{ TTYC_KCUF1, KEYC_RIGHT },
- /* Key and modifier capabilities. */
- { TTYC_KDC2, KEYC_DC|KEYC_SHIFT },
- { TTYC_KDC3, KEYC_DC|KEYC_ESCAPE },
- { TTYC_KDC4, KEYC_DC|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KDC5, KEYC_DC|KEYC_CTRL },
- { TTYC_KDC6, KEYC_DC|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KDC7, KEYC_DC|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KDN2, KEYC_DOWN|KEYC_SHIFT },
- { TTYC_KDN3, KEYC_DOWN|KEYC_ESCAPE },
- { TTYC_KDN4, KEYC_DOWN|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KDN5, KEYC_DOWN|KEYC_CTRL },
- { TTYC_KDN6, KEYC_DOWN|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KDN7, KEYC_DOWN|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KEND2, KEYC_END|KEYC_SHIFT },
- { TTYC_KEND3, KEYC_END|KEYC_ESCAPE },
- { TTYC_KEND4, KEYC_END|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KEND5, KEYC_END|KEYC_CTRL },
- { TTYC_KEND6, KEYC_END|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KEND7, KEYC_END|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KHOM2, KEYC_HOME|KEYC_SHIFT },
- { TTYC_KHOM3, KEYC_HOME|KEYC_ESCAPE },
- { TTYC_KHOM4, KEYC_HOME|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KHOM5, KEYC_HOME|KEYC_CTRL },
- { TTYC_KHOM6, KEYC_HOME|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KHOM7, KEYC_HOME|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KIC2, KEYC_IC|KEYC_SHIFT },
- { TTYC_KIC3, KEYC_IC|KEYC_ESCAPE },
- { TTYC_KIC4, KEYC_IC|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KIC5, KEYC_IC|KEYC_CTRL },
- { TTYC_KIC6, KEYC_IC|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KIC7, KEYC_IC|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KLFT2, KEYC_LEFT|KEYC_SHIFT },
- { TTYC_KLFT3, KEYC_LEFT|KEYC_ESCAPE },
- { TTYC_KLFT4, KEYC_LEFT|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KLFT5, KEYC_LEFT|KEYC_CTRL },
- { TTYC_KLFT6, KEYC_LEFT|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KLFT7, KEYC_LEFT|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KNXT2, KEYC_NPAGE|KEYC_SHIFT },
- { TTYC_KNXT3, KEYC_NPAGE|KEYC_ESCAPE },
- { TTYC_KNXT4, KEYC_NPAGE|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KNXT5, KEYC_NPAGE|KEYC_CTRL },
- { TTYC_KNXT6, KEYC_NPAGE|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KNXT7, KEYC_NPAGE|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KPRV2, KEYC_PPAGE|KEYC_SHIFT },
- { TTYC_KPRV3, KEYC_PPAGE|KEYC_ESCAPE },
- { TTYC_KPRV4, KEYC_PPAGE|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KPRV5, KEYC_PPAGE|KEYC_CTRL },
- { TTYC_KPRV6, KEYC_PPAGE|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KPRV7, KEYC_PPAGE|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KRIT2, KEYC_RIGHT|KEYC_SHIFT },
- { TTYC_KRIT3, KEYC_RIGHT|KEYC_ESCAPE },
- { TTYC_KRIT4, KEYC_RIGHT|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KRIT5, KEYC_RIGHT|KEYC_CTRL },
- { TTYC_KRIT6, KEYC_RIGHT|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KRIT7, KEYC_RIGHT|KEYC_ESCAPE|KEYC_CTRL },
- { TTYC_KUP2, KEYC_UP|KEYC_SHIFT },
- { TTYC_KUP3, KEYC_UP|KEYC_ESCAPE },
- { TTYC_KUP4, KEYC_UP|KEYC_SHIFT|KEYC_ESCAPE },
- { TTYC_KUP5, KEYC_UP|KEYC_CTRL },
- { TTYC_KUP6, KEYC_UP|KEYC_SHIFT|KEYC_CTRL },
- { TTYC_KUP7, KEYC_UP|KEYC_ESCAPE|KEYC_CTRL },
+ /*
+ * Key and modifier capabilities. We set the xterm flag to mark that
+ * any leading escape means an escape key press and not the modifier.
+ */
+ { TTYC_KDC2, KEYC_DC|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KDC3, KEYC_DC|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KDC4, KEYC_DC|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KDC5, KEYC_DC|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KDC6, KEYC_DC|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KDC7, KEYC_DC|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KDN2, KEYC_DOWN|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KDN3, KEYC_DOWN|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KDN4, KEYC_DOWN|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KDN5, KEYC_DOWN|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KDN6, KEYC_DOWN|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KDN7, KEYC_DOWN|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KEND2, KEYC_END|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KEND3, KEYC_END|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KEND4, KEYC_END|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KEND5, KEYC_END|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KEND6, KEYC_END|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KEND7, KEYC_END|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KHOM2, KEYC_HOME|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KHOM3, KEYC_HOME|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KHOM4, KEYC_HOME|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KHOM5, KEYC_HOME|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KHOM6, KEYC_HOME|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KHOM7, KEYC_HOME|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KIC2, KEYC_IC|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KIC3, KEYC_IC|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KIC4, KEYC_IC|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KIC5, KEYC_IC|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KIC6, KEYC_IC|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KIC7, KEYC_IC|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KLFT2, KEYC_LEFT|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KLFT3, KEYC_LEFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KLFT4, KEYC_LEFT|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KLFT5, KEYC_LEFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KLFT6, KEYC_LEFT|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KLFT7, KEYC_LEFT|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KNXT2, KEYC_NPAGE|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KNXT3, KEYC_NPAGE|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KNXT4, KEYC_NPAGE|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KNXT5, KEYC_NPAGE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KNXT6, KEYC_NPAGE|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KNXT7, KEYC_NPAGE|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KPRV2, KEYC_PPAGE|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KPRV3, KEYC_PPAGE|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KPRV4, KEYC_PPAGE|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KPRV5, KEYC_PPAGE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KPRV6, KEYC_PPAGE|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KPRV7, KEYC_PPAGE|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KRIT2, KEYC_RIGHT|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KRIT3, KEYC_RIGHT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KRIT4, KEYC_RIGHT|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KRIT5, KEYC_RIGHT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KRIT6, KEYC_RIGHT|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KRIT7, KEYC_RIGHT|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KUP2, KEYC_UP|KEYC_SHIFT|KEYC_XTERM },
+ { TTYC_KUP3, KEYC_UP|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KUP4, KEYC_UP|KEYC_SHIFT|KEYC_ESCAPE|KEYC_XTERM },
+ { TTYC_KUP5, KEYC_UP|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KUP6, KEYC_UP|KEYC_SHIFT|KEYC_CTRL|KEYC_XTERM },
+ { TTYC_KUP7, KEYC_UP|KEYC_ESCAPE|KEYC_CTRL|KEYC_XTERM },
};
/* Add key to tree. */
@@ -476,6 +479,7 @@ tty_keys_next1(struct tty *tty, const char *buf, size_t len, key_code *key,
enum utf8_state more;
u_int i;
wchar_t wc;
+ int n;
log_debug("%s: next key is %zu (%.*s) (expired=%d)", c->name, len,
(int)len, buf, expired);
@@ -493,6 +497,13 @@ tty_keys_next1(struct tty *tty, const char *buf, size_t len, key_code *key,
return (0);
}
+ /* Is this an an xterm(1) key? */
+ n = xterm_keys_find(buf, len, size, key);
+ if (n == 0)
+ return (0);
+ if (n == 1 && !expired)
+ return (1);
+
/* Is this valid UTF-8? */
more = utf8_open(&ud, (u_char)*buf);
if (more == UTF8_MORE) {
@@ -573,6 +584,18 @@ first_key:
/* Look for a key without the escape. */
n = tty_keys_next1(tty, buf + 1, len - 1, &key, &size, expired);
if (n == 0) { /* found */
+ if (key & KEYC_XTERM) {
+ /*
+ * We want the escape key as well as the xterm
+ * key, because the xterm sequence implicitly
+ * includes the escape (so if we see
+ * \033\033[1;3D we know it is an Escape
+ * followed by M-Left, not just M-Left).
+ */
+ key = '\033';
+ size = 1;
+ goto complete_key;
+ }
key |= KEYC_ESCAPE;
size++;
goto complete_key;
@@ -588,13 +611,6 @@ first_key:
if (n == 1)
goto partial_key;
- /* Is this an an xterm(1) key? */
- n = xterm_keys_find(buf, len, &size, &key);
- if (n == 0)
- goto complete_key;
- if (n == 1 && !expired)
- goto partial_key;
-
/*
* At this point, we know the key is not partial (with or without
* escape). So pass it through even if the timer has not expired.