summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom Gundersen <teg@jklm.no>2014-10-04 23:48:22 +0200
committerTom Gundersen <teg@jklm.no>2014-10-05 01:24:57 +0200
commita6a94db23a2a43ef46ee2450aaa4d81b084a4937 (patch)
treed17b6057d4fc12ed3c74b55ba6434718eab73196
parent498572a75f8261fd12caf84c04f53f754b2bbe24 (diff)
sd-terminal: save cursor settings per-page rather than per-screenterminal
This is how xterm works: <http://invisible-island.net/xterm/xterm.log.html#xterm_90>.
-rw-r--r--src/libsystemd-terminal/term-internal.h41
-rw-r--r--src/libsystemd-terminal/term-screen.c74
2 files changed, 64 insertions, 51 deletions
diff --git a/src/libsystemd-terminal/term-internal.h b/src/libsystemd-terminal/term-internal.h
index f0f4432c8..c5e0be6b7 100644
--- a/src/libsystemd-terminal/term-internal.h
+++ b/src/libsystemd-terminal/term-internal.h
@@ -600,6 +600,17 @@ enum {
TERM_CONFORMANCE_LEVEL_CNT,
};
+struct term_cursor {
+ unsigned int cursor_x;
+ unsigned int cursor_y;
+ term_attr attr;
+ term_charset **gl;
+ term_charset **gr;
+ term_charset **glt;
+ term_charset **grt;
+ unsigned int flags;
+};
+
struct term_screen {
unsigned long ref;
term_age_t age;
@@ -621,32 +632,26 @@ struct term_screen {
term_screen_cmd_fn cmd_fn;
void *cmd_fn_data;
- unsigned int flags;
unsigned int conformance_level;
+ term_attr default_attr;
+
+ term_charset *g0;
+ term_charset *g1;
+ term_charset *g2;
+ term_charset *g3;
+
unsigned int cursor_x;
unsigned int cursor_y;
term_attr attr;
- term_attr default_attr;
-
term_charset **gl;
term_charset **gr;
term_charset **glt;
term_charset **grt;
- term_charset *g0;
- term_charset *g1;
- term_charset *g2;
- term_charset *g3;
+ unsigned int flags;
- char *answerback;
+ struct term_cursor *saved;
+ struct term_cursor saved_main;
+ struct term_cursor saved_alt;
- struct {
- unsigned int cursor_x;
- unsigned int cursor_y;
- term_attr attr;
- term_charset **gl;
- term_charset **gr;
- term_charset **glt;
- term_charset **grt;
- unsigned int flags;
- } saved;
+ char *answerback;
};
diff --git a/src/libsystemd-terminal/term-screen.c b/src/libsystemd-terminal/term-screen.c
index ec6c14d98..3aeb6ed39 100644
--- a/src/libsystemd-terminal/term-screen.c
+++ b/src/libsystemd-terminal/term-screen.c
@@ -77,11 +77,13 @@ int term_screen_new(term_screen **out, term_screen_write_fn write_fn, void *writ
screen->g2 = &term_unicode_lower;
screen->g3 = &term_unicode_upper;
- screen->saved.cursor_x = 0;
- screen->saved.cursor_y = 0;
- screen->saved.attr = screen->attr;
- screen->saved.gl = screen->gl;
- screen->saved.gr = screen->gr;
+ screen->saved_main.cursor_x = 0;
+ screen->saved_main.cursor_y = 0;
+ screen->saved_main.attr = screen->attr;
+ screen->saved_main.gl = screen->gl;
+ screen->saved_main.gr = screen->gr;
+
+ screen->saved_alt = screen->saved_main;
r = term_page_new(&screen->page_main);
if (r < 0)
@@ -101,6 +103,7 @@ int term_screen_new(term_screen **out, term_screen_write_fn write_fn, void *writ
screen->page = screen->page_main;
screen->history = screen->history_main;
+ screen->saved = &screen->saved_main;
*out = screen;
screen = NULL;
@@ -374,6 +377,11 @@ static int screen_DECSC(term_screen *screen, const term_seq *seq);
static int screen_DECRC(term_screen *screen, const term_seq *seq);
static inline void screen_clear_alt(term_screen *screen) {
+ zero(screen->saved_alt);
+ screen->saved_main.attr = screen->attr;
+ screen->saved_main.gl = screen->gl;
+ screen->saved_main.gr = screen->gr;
+
term_page_set_scroll_region(screen->page_alt, 0, screen->page->height);
term_page_erase(screen->page_alt, 0, 0, screen->page->width, screen->page->height, &screen->attr, screen->age, false);
}
@@ -460,24 +468,23 @@ static void screen_mode_change(term_screen *screen, unsigned int mode, bool dec,
case 1048:
if (dec) {
if (set)
- screen_DECSC(screen, seq);
+ screen_DECSC(screen, NULL);
else
- screen_DECRC(screen, seq);
+ screen_DECRC(screen, NULL);
}
break;
case 1049:
if (dec) {
- /* TODO: should DEC{S,R}C be done per-page, rather than per-screen? */
if (set) {
- screen_DECSC(screen, seq);
+ screen_DECSC(screen, NULL);
screen_clear_alt(screen);
}
screen_set_alt(screen, set);
if (!set)
- screen_DECRC(screen, seq);
+ screen_DECRC(screen, NULL);
}
break;
@@ -1312,14 +1319,14 @@ int screen_DECRC(term_screen *screen, const term_seq *seq) {
* state for the main display and the status line.
*/
- screen->attr = screen->saved.attr;
- screen->gl = screen->saved.gl;
- screen->gr = screen->saved.gr;
- screen->glt = screen->saved.glt;
- screen->grt = screen->saved.grt;
- set_reset(screen, TERM_FLAG_AUTO_WRAP, screen->saved.flags & TERM_FLAG_AUTO_WRAP);
- set_reset(screen, TERM_FLAG_ORIGIN_MODE, screen->saved.flags & TERM_FLAG_ORIGIN_MODE);
- screen_cursor_set(screen, screen->saved.cursor_x, screen->saved.cursor_y);
+ screen->attr = screen->saved->attr;
+ screen->gl = screen->saved->gl;
+ screen->gr = screen->saved->gr;
+ screen->glt = screen->saved->glt;
+ screen->grt = screen->saved->grt;
+ set_reset(screen, TERM_FLAG_AUTO_WRAP, screen->saved->flags & TERM_FLAG_AUTO_WRAP);
+ set_reset(screen, TERM_FLAG_ORIGIN_MODE, screen->saved->flags & TERM_FLAG_ORIGIN_MODE);
+ screen_cursor_set(screen, screen->saved->cursor_x, screen->saved->cursor_y);
return 0;
}
@@ -1526,14 +1533,14 @@ int screen_DECSC(term_screen *screen, const term_seq *seq) {
* * Any single shift 2 (SS2) or single shift 3 (SS3) functions sent
*/
- screen->saved.cursor_x = screen->cursor_x;
- screen->saved.cursor_y = screen->cursor_y;
- screen->saved.attr = screen->attr;
- screen->saved.gl = screen->gl;
- screen->saved.gr = screen->gr;
- screen->saved.glt = screen->glt;
- screen->saved.grt = screen->grt;
- screen->saved.flags = screen->flags & (TERM_FLAG_AUTO_WRAP
+ screen->saved->cursor_x = screen->cursor_x;
+ screen->saved->cursor_y = screen->cursor_y;
+ screen->saved->attr = screen->attr;
+ screen->saved->gl = screen->gl;
+ screen->saved->gr = screen->gr;
+ screen->saved->glt = screen->glt;
+ screen->saved->grt = screen->grt;
+ screen->saved->flags = screen->flags & (TERM_FLAG_AUTO_WRAP
| TERM_FLAG_ORIGIN_MODE);
return 0;
@@ -4208,17 +4215,18 @@ void term_screen_soft_reset(term_screen *screen) {
screen->page = screen->page_main;
screen->history = screen->history_main;
+ screen->saved = &screen->saved_main;
screen->flags = TERM_FLAG_7BIT_MODE;
screen->conformance_level = TERM_CONFORMANCE_LEVEL_VT400;
screen->attr = screen->default_attr;
- screen->saved.cursor_x = 0;
- screen->saved.cursor_y = 0;
- screen->saved.attr = screen->attr;
- screen->saved.gl = screen->gl;
- screen->saved.gr = screen->gr;
- screen->saved.glt = NULL;
- screen->saved.grt = NULL;
+ zero(screen->saved_main);
+ screen->saved_main.attr = screen->attr;
+ screen->saved_main.gl = screen->gl;
+ screen->saved_main.gr = screen->gr;
+
+ screen->saved_alt = screen->saved_main;
+
screen->flags = 0;
for (i = 0; i < screen->page->width; i += 8)