summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--console/ChangeLog27
-rw-r--r--console/console.h119
-rw-r--r--console/display.c313
3 files changed, 362 insertions, 97 deletions
diff --git a/console/ChangeLog b/console/ChangeLog
index 62b292ad..9e86d139 100644
--- a/console/ChangeLog
+++ b/console/ChangeLog
@@ -1,3 +1,30 @@
+2002-06-18 Marcus Brinkmann <marcus@gnu.org>
+
+ * console.h: Update all CONS_KEY_* macros to match other terminfo
+ definitions (like "linux", "screen", "gnome"). Add CONS_CHAR_*
+ macros for terminal graphic characters.
+
+ * display.c (struct attr): New member ALTCHAR to flag usage of
+ alternate character set.
+ (display_notice_filechange): Make static.
+ (handle_escape_bracket_m): Set ALTCHAR to 0 when resetting.
+ Support new modes 10 and 11 to disable and enable ALTCHAR.
+ (limit_cursor): New function, moved to global scope from ...
+ (handle_escape_bracket): ... here.
+ (linefeed): New function, moved to global scope from ...
+ (display_output_one): ... here.
+ (horizontal_tab): New function.
+ (handle_escape_bracket): Add alias \E[' to \E[G for VT100
+ compatibility. Add capability \E[a (horizontal cursor position
+ relative) for ECMA-48 compatibility. Add capabilities \E[I
+ (horizontal tab) and \E[Z (backward tabulation) for ECMA-48
+ compatibility. Move capabilities \E[s and \E[u to ...
+ (display_output_one): ... here as \E7 and \E8 for VT100
+ compatibility.
+ (altchar_to_ucs4): New function.
+ (display_output_one): Use altchar_to_ucs4 when in altchar mode.
+ Add \EM (reset) capability.
+
2002-06-17 Marcus Brinkmann <marcus@gnu.org>
* console.c (new_node): Adjust size of display node.
diff --git a/console/console.h b/console/console.h
index 771351f5..d1f06492 100644
--- a/console/console.h
+++ b/console/console.h
@@ -94,27 +94,114 @@ struct cons_display
};
-#define CONS_KEY_UP "\e[A" /* Cursor up. */
-#define CONS_KEY_DOWN "\e[B" /* Cursor down. */
-#define CONS_KEY_RIGHT "\e[C" /* Cursor right. */
-#define CONS_KEY_LEFT "\e[D" /* Cursor left. */
-#define CONS_KEY_HOME "\e[H" /* Home key. */
+/* The console server will use the following UCS-4 characters for the
+ specified terminal graphic characters. If the display driver is
+ UCS-4 capabable, it can print them without interpretation. */
+
+/* ACS_BLOCK maps to FULL BLOCK. */
+#define CONS_CHAR_BLOCK ((wchar_t) 0x2588)
+/* ACS_DIAMOND maps to BLACK DIAMOND. */
+#define CONS_CHAR_DIAMOND ((wchar_t) 0x25c6)
+/* ACS_CKBOARD maps to MEDIUM SHADE. */
+#define CONS_CHAR_CKBOARD ((wchar_t) 0x2592)
+/* ACS_BOARD maps to LIGHT SHADE. */
+#define CONS_CHAR_BOARD ((wchar_t) 0x2591)
+/* ACS_BULLET maps to BULLET (Linux maps it to MIDDLE DOT 0x00b7). */
+#define CONS_CHAR_BULLET ((wchar_t) 0x2022)
+/* ACS_STERLING maps to POUND STERLING. */
+#define CONS_CHAR_STERLING ((wchar_t) 0x00a3)
+/* ACS_DEGREE maps to DEGREE SIGN. */
+#define CONS_CHAR_DEGREE ((wchar_t) 0x00b0)
+/* ACS_PLMINUS maps to PLUS-MINUS SIGN. */
+#define CONS_CHAR_PLMINUS ((wchar_t) 0x00b1)
+/* ACS_PI maps to GREEK SMALL LETTER PI. */
+#define CONS_CHAR_PI ((wchar_t) 0x03c0)
+/* ACS_LANTERN maps to BLACK HOURGLASS. XXX Is this appropriate? */
+#define CONS_CHAR_LANTERN ((wchar_t) 0x29d7)
+
+/* ACS_RARROW maps to RIGHTWARDS ARROW. */
+#define CONS_CHAR_RARROW ((wchar_t) 0x2192)
+/* ACS_LARROW maps to LEFTWARDS ARROW. */
+#define CONS_CHAR_LARROW ((wchar_t) 0x2190)
+/* ACS_UARROW maps to UPWARDS ARROW. */
+#define CONS_CHAR_UARROW ((wchar_t) 0x2191)
+/* ACS_DARROW maps to DOWNWARDS ARROW. */
+#define CONS_CHAR_DARROW ((wchar_t) 0x2193)
+
+/* ACS_LRCORNER maps to BOX DRAWINGS LIGHT UP AND LEFT. */
+#define CONS_CHAR_LRCORNER ((wchar_t) 0x2518)
+/* ACS_URCORNER maps to BOX DRAWINGS LIGHT DOWN AND LEFT. */
+#define CONS_CHAR_URCORNER ((wchar_t) 0x2510)
+/* ACS_ULCORNER maps to BOX DRAWINGS LIGHT DOWN AND RIGHT. */
+#define CONS_CHAR_ULCORNER ((wchar_t) 0x250c)
+/* ACS_LLCORNER maps to BOX DRAWINGS LIGHT UP AND RIGHT. */
+#define CONS_CHAR_LLCORNER ((wchar_t) 0x2514)
+/* ACS_PLUS maps to BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL. */
+#define CONS_CHAR_PLUS ((wchar_t) 0x253c)
+/* ACS_HLINE maps to BOX DRAWINGS LIGHT HORIZONTAL. */
+#define CONS_CHAR_HLINE ((wchar_t) 0x2500)
+/* ACS_LTEE maps to BOX DRAWINGS LIGHT VERTICAL AND RIGHT. */
+#define CONS_CHAR_LTEE ((wchar_t) 0x251c)
+/* ACS_RTEE maps to BOX DRAWINGS LIGHT VERTICAL AND LEFT. */
+#define CONS_CHAR_RTEE ((wchar_t) 0x2524)
+/* ACS_BTEE maps to BOX DRAWINGS LIGHT UP AND HORIZONTAL. */
+#define CONS_CHAR_BTEE ((wchar_t) 0x2534)
+/* ACS_TTEE maps to BOX DRAWINGS LIGHT DOWN AND HORIZONTAL. */
+#define CONS_CHAR_TTEE ((wchar_t) 0x252c)
+/* ACS_VLINE maps to BOX DRAWINGS LIGHT VERTICAL. */
+#define CONS_CHAR_VLINE ((wchar_t) 0x2502)
+
+/* ACS_S1 maps to HORIZONTAL SCAN LINE-1. */
+#define CONS_CHAR_S1 ((wchar_t) 0x23ba)
+/* ACS_S3 maps to HORIZONTAL SCAN LINE-3. */
+#define CONS_CHAR_S3 ((wchar_t) 0x23bb)
+/* ACS_S7 maps to HORIZONTAL SCAN LINE-1. */
+#define CONS_CHAR_S7 ((wchar_t) 0x23bc)
+/* ACS_S9 maps to HORIZONTAL SCAN LINE-1. */
+#define CONS_CHAR_S9 ((wchar_t) 0x23bd)
+
+/* ACS_NEQUAL maps to NOT EQUAL TO. */
+#define CONS_CHAR_NEQUAL ((wchar_t) 0x2260)
+/* ACS_LEQUAL maps to LESS-THAN OR EQUAL TO. */
+#define CONS_CHAR_LEQUAL ((wchar_t) 0x2264)
+/* ACS_GEQUAL maps to GREATER-THAN OR EQUAL TO. */
+#define CONS_CHAR_GEQUAL ((wchar_t) 0x2265)
+
+
+
+/* The input driver should emit these escape sequences for special
+ keys which don't represent characters in UTF-8. */
+#define CONS_KEY_UP "\eOA" /* Cursor up. */
+#define CONS_KEY_DOWN "\eOB" /* Cursor down. */
+#define CONS_KEY_RIGHT "\eOC" /* Cursor right. */
+#define CONS_KEY_LEFT "\eOD" /* Cursor left. */
#define CONS_KEY_BACKSPACE "\177" /* Backspace key. */
#define CONS_KEY_F1 "\eOP" /* Function key 1. */
#define CONS_KEY_F2 "\eOQ" /* Function key 2. */
#define CONS_KEY_F3 "\eOR" /* Function key 3. */
#define CONS_KEY_F4 "\eOS" /* Function key 4. */
-#define CONS_KEY_F5 "\eOT" /* Function key 5. */
-#define CONS_KEY_F6 "\eOU" /* Function key 6. */
-#define CONS_KEY_F7 "\eOV" /* Function key 7. */
-#define CONS_KEY_F8 "\eOW" /* Function key 8. */
-#define CONS_KEY_F9 "\eOX" /* Function key 9. */
-#define CONS_KEY_F10 "\eOY" /* Function key 10. */
-#define CONS_KEY_DC "\e[9" /* Delete character. */
-#define CONS_KEY_NPAGE "\e[U" /* Next page. */
-#define CONS_KEY_PPAGE "\e[V" /* Previous page. */
+#define CONS_KEY_F5 "\e[15~" /* Function key 5. */
+#define CONS_KEY_F6 "\e[17~" /* Function key 6. */
+#define CONS_KEY_F7 "\e[18~" /* Function key 7. */
+#define CONS_KEY_F8 "\e[19~" /* Function key 8. */
+#define CONS_KEY_F9 "\e[20~" /* Function key 9. */
+#define CONS_KEY_F10 "\e[21~" /* Function key 10. */
+#define CONS_KEY_F11 "\e[23~" /* Function key 11. */
+#define CONS_KEY_F12 "\e[24~" /* Function key 12. */
+#define CONS_KEY_F13 "\e[25~" /* Function key 13. */
+#define CONS_KEY_F14 "\e[26~" /* Function key 14. */
+#define CONS_KEY_F15 "\e[28~" /* Function key 15. */
+#define CONS_KEY_F16 "\e[29~" /* Function key 16. */
+#define CONS_KEY_F17 "\e[31~" /* Function key 17. */
+#define CONS_KEY_F18 "\e[32~" /* Function key 18. */
+#define CONS_KEY_F19 "\e[33~" /* Function key 19. */
+#define CONS_KEY_F20 "\e[34~" /* Function key 20. */
+#define CONS_KEY_HOME "\e[1~" /* Home key. */
+#define CONS_KEY_IC "\e[2~" /* Insert char mode. */
+#define CONS_KEY_DC "\e[3~" /* Delete character. */
+#define CONS_KEY_END "\e[4~" /* End key. */
+#define CONS_KEY_PPAGE "\e[5~" /* Previous page. */
+#define CONS_KEY_NPAGE "\e[6~" /* Next page. */
#define CONS_KEY_BTAB "\e[Z" /* Back tab key. */
-#define CONS_KEY_IC "\e[@" /* Insert char mode. */
-#define CONS_KEY_END "\e[Y" /* End key. */
#endif /* _HURD_CONSOLE_H */
diff --git a/console/display.c b/console/display.c
index 45190c1e..5528ff98 100644
--- a/console/display.c
+++ b/console/display.c
@@ -123,6 +123,8 @@ struct attr
unsigned int bgcol_def;
unsigned int fgcol_def;
conchar_attr_t current;
+ /* True if in alternate character set (ASCII graphic) mode. */
+ unsigned int altchar;
};
typedef struct attr *attr_t;
@@ -296,7 +298,7 @@ display_notice_changes (display_t display, mach_port_t notify)
}
/* Requires DISPLAY to be locked. */
-void
+static void
display_notice_filechange (display_t display, enum file_changed_type type,
off_t start, off_t end)
{
@@ -391,7 +393,6 @@ display_flush_filechange (display_t display, unsigned int type)
}
}
-
/* Record a change in the matrix ringbuffer. */
static void
display_record_filechange (display_t display, off_t start, off_t end)
@@ -470,7 +471,6 @@ display_record_filechange (display_t display, off_t start, off_t end)
display->changes.end = end;
}
}
-
static void
@@ -737,6 +737,7 @@ handle_esc_bracket_m (attr_t attr, int code)
memset (&attr->current, 0, sizeof (conchar_attr_t));
attr->current.fgcol = attr->fgcol_def;
attr->current.bgcol = attr->bgcol_def;
+ attr->altchar = 0;
break;
case 1:
/* Bold on: <bold>. */
@@ -762,6 +763,14 @@ handle_esc_bracket_m (attr_t attr, int code)
/* Concealed on: <invis>. */
attr->current.concealed = 1;
break;
+ case 10:
+ /* Alternate character set mode off: <rmacs>. */
+ attr->altchar = 0;
+ break;
+ case 11:
+ /* Alternate character set mode on: <smacs>. */
+ attr->altchar = 1;
+ break;
case 22:
/* Normal intensity. */
attr->current.intensity = CONS_ATTR_INTENSITY_NORMAL;
@@ -801,27 +810,71 @@ handle_esc_bracket_m (attr_t attr, int code)
}
}
+static
+void limit_cursor (display_t display)
+{
+ struct cons_display *user = display->user;
+
+ if (user->cursor.col >= user->screen.width)
+ user->cursor.col = user->screen.width - 1;
+ else if (user->cursor.col < 0)
+ user->cursor.col = 0;
+
+ if (user->cursor.row >= user->screen.height)
+ user->cursor.row = user->screen.height - 1;
+ else if (user->cursor.row < 0)
+ user->cursor.row = 0;
+
+ /* XXX Flag cursor change. */
+}
+
+
static void
-handle_esc_bracket (display_t display, char op)
+linefeed (display_t display)
{
struct cons_display *user = display->user;
- parse_t parse = &display->output.parse;
- int i;
- static void limit_cursor (void)
+ if (user->cursor.row < user->screen.height - 1)
{
- if (user->cursor.col >= user->screen.width)
- user->cursor.col = user->screen.width - 1;
- else if (user->cursor.col < 0)
- user->cursor.col = 0;
-
- if (user->cursor.row >= user->screen.height)
- user->cursor.row = user->screen.height - 1;
- else if (user->cursor.row < 0)
- user->cursor.row = 0;
+ user->cursor.row++;
+ /* XXX Flag cursor update. */
+ }
+ else
+ {
+ user->screen.cur_line++;
+ user->screen.cur_line %= user->screen.lines;
- /* XXX Flag cursor change. */
+ screen_fill (display, 0, user->screen.height - 1,
+ user->screen.width - 1, user->screen.height - 1,
+ L' ', display->attr.current);
+ if (user->screen.scr_lines <
+ user->screen.lines - user->screen.height)
+ user->screen.scr_lines++;
+ /* XXX Flag current line change. */
+ /* XXX Possibly flag change of length of scroll back buffer. */
+ }
+}
+
+static void
+horizontal_tab (display_t display)
+{
+ struct cons_display *user = display->user;
+
+ user->cursor.col = (user->cursor.col | 7) + 1;
+ if (user->cursor.col >= user->screen.width)
+ {
+ user->cursor.col = 0;
+ linefeed (display);
}
+ /* XXX Flag cursor update. */
+}
+
+static void
+handle_esc_bracket (display_t display, char op)
+{
+ struct cons_display *user = display->user;
+ parse_t parse = &display->output.parse;
+ int i;
switch (op)
{
@@ -830,18 +883,24 @@ handle_esc_bracket (display_t display, char op)
/* Cursor position: <cup>. */
user->cursor.col = (parse->params[1] ?: 1) - 1;
user->cursor.row = (parse->params[0] ?: 1) - 1;
- limit_cursor ();
+ limit_cursor (display);
break;
case 'G': /* ECMA-48 <CHA>. */
case '`': /* ECMA-48 <HPA>. */
+ case '\'': /* VT100. */
/* Horizontal cursor position: <hpa>. */
user->cursor.col = (parse->params[0] ?: 1) - 1;
- limit_cursor ();
+ limit_cursor (display);
+ break;
+ case 'a': /* ECMA-48 <HPR>. */
+ /* Horizontal cursor position relative. */
+ user->cursor.col += (parse->params[1] ?: 1) - 1;
+ limit_cursor (display);
break;
case 'd': /* ECMA-48 <VPA>. */
- /* Vertical cursor position: <hpa>. */
+ /* Vertical cursor position: <vpa>. */
user->cursor.row = (parse->params[0] ?: 1) - 1;
- limit_cursor ();
+ limit_cursor (display);
break;
case 'F': /* ECMA-48 <CPL>. */
/* Beginning of previous line. */
@@ -851,7 +910,7 @@ handle_esc_bracket (display_t display, char op)
case 'k': /* ECMA-48 <VPB>. */
/* Cursor up: <cuu>, <cuu1>. */
user->cursor.row -= (parse->params[0] ?: 1);
- limit_cursor ();
+ limit_cursor (display);
break;
case 'E': /* ECMA-48 <CNL>. */
/* Beginning of next line. */
@@ -861,29 +920,17 @@ handle_esc_bracket (display_t display, char op)
case 'e': /* ECMA-48 <VPR>. */
/* Cursor down: <cud1>, <cud>. */
user->cursor.row += (parse->params[0] ?: 1);
- limit_cursor ();
+ limit_cursor (display);
break;
case 'C': /* ECMA-48 <CUF>. */
/* Cursor right: <cuf1>, <cuf>. */
user->cursor.col += (parse->params[0] ?: 1);
- limit_cursor ();
+ limit_cursor (display);
break;
case 'D': /* ECMA-48 <CUB>. */
/* Cursor left: <cub>, <cub1>. */
user->cursor.col -= (parse->params[0] ?: 1);
- limit_cursor ();
- break;
- case 's':
- /* Save cursor position: <sc>. */
- display->cursor.saved_x = user->cursor.col;
- display->cursor.saved_y = user->cursor.row;
- break;
- case 'u':
- /* Restore cursor position: <rc>. */
- user->cursor.col = display->cursor.saved_x;
- user->cursor.row = display->cursor.saved_y;
- /* In case the screen was larger before: */
- limit_cursor ();
+ limit_cursor (display);
break;
case 'h':
/* Reset mode. */
@@ -895,11 +942,11 @@ handle_esc_bracket (display_t display, char op)
for (i = 0; i < parse->nparams; i++)
handle_esc_bracket_hl (display, parse->params[i], 1);
break;
- case 'm': /* ECME-48 <SGR>. */
+ case 'm': /* ECMA-48 <SGR>. */
for (i = 0; i < parse->nparams; i++)
handle_esc_bracket_m (&display->attr, parse->params[i]);
break;
- case 'J': /* ECME-48 <ED>. */
+ case 'J': /* ECMA-48 <ED>. */
switch (parse->params[0])
{
case 0:
@@ -922,7 +969,7 @@ handle_esc_bracket (display_t display, char op)
break;
}
break;
- case 'K': /* ECME-48 <EL>. */
+ case 'K': /* ECMA-48 <EL>. */
switch (parse->params[0])
{
case 0:
@@ -945,55 +992,90 @@ handle_esc_bracket (display_t display, char op)
break;
}
break;
- case 'L': /* ECME-48 <IL>. */
+ case 'L': /* ECMA-48 <IL>. */
/* Insert line(s): <il1>, <il>. */
screen_shift_right (display, 0, user->cursor.row,
user->screen.width - 1, user->screen.height - 1,
(parse->params[0] ?: 1) * user->screen.width,
L' ', display->attr.current);
break;
- case 'M': /* ECME-48 <DL>. */
+ case 'M': /* ECMA-48 <DL>. */
/* Delete line(s): <dl1>, <dl>. */
screen_shift_left (display, 0, user->cursor.row,
user->screen.width - 1, user->screen.height - 1,
(parse->params[0] ?: 1) * user->screen.width,
L' ', display->attr.current);
break;
- case '@': /* ECME-48 <ICH>. */
+ case '@': /* ECMA-48 <ICH>. */
/* Insert character(s): <ich1>, <ich>. */
screen_shift_right (display, user->cursor.col, user->cursor.row,
user->screen.width - 1, user->cursor.row,
parse->params[0] ?: 1,
L' ', display->attr.current);
break;
- case 'P': /* ECME-48 <DCH>. */
+ case 'P': /* ECMA-48 <DCH>. */
/* Delete character(s): <dch1>, <dch>. */
screen_shift_left (display, user->cursor.col, user->cursor.row,
user->screen.width - 1, user->cursor.row,
parse->params[0] ?: 1,
L' ', display->attr.current);
break;
- case 'S': /* ECME-48 <SU>. */
+ case 'S': /* ECMA-48 <SU>. */
/* Scroll up: <ind>, <indn>. */
screen_shift_left (display, 0, 0,
user->screen.width - 1, user->screen.height - 1,
(parse->params[0] ?: 1) * user->screen.width,
L' ', display->attr.current);
break;
- case 'T': /* ECME-48 <SD>. */
+ case 'T': /* ECMA-48 <SD>. */
/* Scroll down: <ri>, <rin>. */
screen_shift_right (display, 0, 0,
user->screen.width, user->screen.height,
(parse->params[0] ?: 1) * user->screen.width,
L' ', display->attr.current);
break;
- case 'X': /* ECME-48 <ECH>. */
+ case 'X': /* ECMA-48 <ECH>. */
/* Erase character(s): <ech>. */
screen_fill (display, user->cursor.col, user->cursor.row,
/* XXX limit ? */user->cursor.col + (parse->params[0] ?: 1),
user->cursor.row,
L' ', display->attr.current);
break;
+ case 'I': /* ECMA-48 <CHT>. */
+ /* Horizontal tab. */
+ if (!parse->params[0])
+ parse->params[0] = 1;
+ while (parse->params[0]--)
+ horizontal_tab (display);
+ break;
+ case 'Z': /* ECMA-48 <CBT>. */
+ /* Cursor backward tabulation: <cbt>. */
+ if (parse->params[0] > user->screen.height * (user->screen.width / 8))
+ {
+ user->cursor.col = 0;
+ user->cursor.row = 0;
+ }
+ else
+ {
+ int i = parse->params[0] ?: 1;
+
+ while (i--)
+ {
+ if (user->cursor.col == 0)
+ {
+ if (user->cursor.row == 0)
+ break;
+ else
+ {
+ user->cursor.col = user->screen.width - 1;
+ user->cursor.row--;
+ }
+ }
+ else
+ user->cursor.col--;
+ user->cursor.col &= ~7;
+ }
+ }
}
}
@@ -1035,6 +1117,81 @@ handle_esc_bracket_question (display_t display, char op)
}
}
+static wchar_t
+altchar_to_ucs4 (wchar_t chr)
+{
+ /* Alternative character set frobbing. */
+ switch (chr)
+ {
+ case L'+':
+ return CONS_CHAR_RARROW;
+ case L',':
+ return CONS_CHAR_LARROW;
+ case L'-':
+ return CONS_CHAR_UARROW;
+ case L'.':
+ return CONS_CHAR_DARROW;
+ case L'0':
+ return CONS_CHAR_BLOCK;
+ case L'I':
+ return CONS_CHAR_LANTERN;
+ case L'`':
+ return CONS_CHAR_DIAMOND;
+ case L'a':
+ return CONS_CHAR_CKBOARD;
+ case L'f':
+ return CONS_CHAR_DEGREE;
+ case L'g':
+ return CONS_CHAR_PLMINUS;
+ case L'h':
+ return CONS_CHAR_BOARD;
+ case L'j':
+ return CONS_CHAR_LRCORNER;
+ case L'k':
+ return CONS_CHAR_URCORNER;
+ case L'l':
+ return CONS_CHAR_ULCORNER;
+ case L'm':
+ return CONS_CHAR_LLCORNER;
+ case L'n':
+ return CONS_CHAR_PLUS;
+ case L'o':
+ return CONS_CHAR_S1;
+ case L'p':
+ return CONS_CHAR_S3;
+ case L'q':
+ return CONS_CHAR_HLINE;
+ case L'r':
+ return CONS_CHAR_S7;
+ case L's':
+ return CONS_CHAR_S9;
+ case L't':
+ return CONS_CHAR_LTEE;
+ case L'u':
+ return CONS_CHAR_RTEE;
+ case L'v':
+ return CONS_CHAR_BTEE;
+ case L'w':
+ return CONS_CHAR_TTEE;
+ case L'x':
+ return CONS_CHAR_VLINE;
+ case L'y':
+ return CONS_CHAR_LEQUAL;
+ case L'z':
+ return CONS_CHAR_GEQUAL;
+ case L'{':
+ return CONS_CHAR_PI;
+ case L'|':
+ return CONS_CHAR_NEQUAL;
+ case L'}':
+ return CONS_CHAR_STERLING;
+ case L'~':
+ return CONS_CHAR_BULLET;
+ default:
+ return chr;
+ }
+}
+
/* Display must be locked. */
static void
display_output_one (display_t display, wchar_t chr)
@@ -1042,29 +1199,6 @@ display_output_one (display_t display, wchar_t chr)
struct cons_display *user = display->user;
parse_t parse = &display->output.parse;
- void linefeed (void)
- {
- if (user->cursor.row < user->screen.height - 1)
- {
- user->cursor.row++;
- /* XXX Flag cursor update. */
- }
- else
- {
- user->screen.cur_line++;
- user->screen.cur_line %= user->screen.lines;
-
- screen_fill (display, 0, user->screen.height - 1,
- user->screen.width - 1, user->screen.height - 1,
- L' ', display->attr.current);
- if (user->screen.scr_lines <
- user->screen.lines - user->screen.height)
- user->screen.scr_lines++;
- /* XXX Flag current line change. */
- /* XXX Possibly flag change of length of scroll back buffer. */
- }
- }
-
switch (parse->state)
{
case STATE_NORMAL:
@@ -1080,7 +1214,7 @@ display_output_one (display_t display, wchar_t chr)
break;
case L'\n':
/* Line feed. */
- linefeed ();
+ linefeed (display);
break;
case L'\b':
/* Backspace. */
@@ -1100,13 +1234,7 @@ display_output_one (display_t display, wchar_t chr)
break;
case L'\t':
/* Horizontal tab: <ht> */
- user->cursor.col = (user->cursor.col | 7) + 1;
- if (user->cursor.col >= user->screen.width)
- {
- user->cursor.col = 0;
- linefeed ();
- }
- /* XXX Flag cursor update. */
+ horizontal_tab (display);
break;
case L'\033':
parse->state = STATE_ESC;
@@ -1119,7 +1247,9 @@ display_output_one (display_t display, wchar_t chr)
int line = (user->screen.cur_line + user->cursor.row)
% user->screen.lines;
int idx = line * user->screen.width + user->cursor.col;
- user->_matrix[idx].chr = chr;
+
+ user->_matrix[idx].chr = display->attr.altchar
+ ? altchar_to_ucs4 (chr) : chr;
user->_matrix[idx].attr = display->attr.current;
display_record_filechange (display, idx, idx);
@@ -1127,7 +1257,7 @@ display_output_one (display_t display, wchar_t chr)
if (user->cursor.col == user->screen.width)
{
user->cursor.col = 0;
- linefeed ();
+ linefeed (display);
}
}
break;
@@ -1140,6 +1270,13 @@ display_output_one (display_t display, wchar_t chr)
case L'[':
parse->state = STATE_ESC_BRACKET_INIT;
break;
+ case L'M': /* ECMA-48 <RIS>. */
+ /* Reset: <rs2>. */
+ * (uint32_t *) &display->attr.current = 0;
+ display->attr.current.bgcol = display->attr.bgcol_def;
+ display->attr.current.fgcol = display->attr.fgcol_def;
+ display->attr.altchar = 0;
+ /* Fall through. */
case L'c':
/* Clear screen and home cursor: <clear>. */
screen_fill (display, 0, 0,
@@ -1152,7 +1289,19 @@ display_output_one (display_t display, wchar_t chr)
case L'E': /* ECMA-48 <NEL>. */
/* Newline. */
user->cursor.col = 0;
- linefeed ();
+ linefeed (display);
+ break;
+ case L'7': /* VT100: Save cursor and attributes. */
+ /* Save cursor position: <sc>. */
+ display->cursor.saved_x = user->cursor.col;
+ display->cursor.saved_y = user->cursor.row;
+ break;
+ case L'8': /* VT100: Restore cursor and attributes. */
+ /* Restore cursor position: <rc>. */
+ user->cursor.col = display->cursor.saved_x;
+ user->cursor.row = display->cursor.saved_y;
+ /* In case the screen was larger before: */
+ limit_cursor (display);
break;
default:
/* Unsupported escape sequence. */
@@ -1244,6 +1393,7 @@ display_output_some (display_t display, char **buffer, size_t *length)
display_flush_filechange (display, ~0);
return err;
}
+
void
display_init (void)
@@ -1258,6 +1408,7 @@ display_init (void)
(any_t)pager_bucket));
}
+
/* Create a new virtual console display, with the system encoding
being ENCODING. */
error_t