Implement very bad state machine to match a subset of ANSI escape codes.
This commit is contained in:
parent
dd3281aba0
commit
f00ab71fb5
|
@ -38,6 +38,14 @@ i386_init(void)
|
|||
// Test the stack backtrace function (lab 1 only)
|
||||
test_backtrace(5);
|
||||
|
||||
// Test ANSI color escape codes
|
||||
cprintf("\33[31m" "C"
|
||||
"\33[33m" "o"
|
||||
"\33[32m" "l"
|
||||
"\33[36m" "o"
|
||||
"\33[34m" "r"
|
||||
"\33[0m" " Works!" "\n");
|
||||
|
||||
// Drop into the kernel monitor.
|
||||
while (1)
|
||||
monitor(NULL);
|
||||
|
|
|
@ -79,6 +79,54 @@ getint(va_list *ap, int lflag)
|
|||
// Main function to format and print a string.
|
||||
void printfmt(void (*putch)(int, void*), void *putdat, const char *fmt, ...);
|
||||
|
||||
struct AttrState {
|
||||
uint8_t cattrs;
|
||||
uint8_t attrs;
|
||||
enum {
|
||||
NORMAL,
|
||||
ESC,
|
||||
BRACKET,
|
||||
COLOR_FG,
|
||||
COLOR
|
||||
} state;
|
||||
};
|
||||
|
||||
void
|
||||
putchw(void (*putch)(int, void*), int c, void* data, struct AttrState* s) {
|
||||
switch(s->state) {
|
||||
case NORMAL:
|
||||
if(c != 27) putch(c | (s->cattrs << 8), data);
|
||||
else s->state = ESC;
|
||||
return;
|
||||
case ESC:
|
||||
s->state = (c == '[') ? BRACKET : NORMAL;
|
||||
return;
|
||||
case BRACKET:
|
||||
if(c == '3') {
|
||||
s->state = COLOR_FG;
|
||||
} else if(c == '0') {
|
||||
s->state = COLOR;
|
||||
s->attrs = 0;
|
||||
} else {
|
||||
s->state = NORMAL;
|
||||
}
|
||||
return;
|
||||
case COLOR_FG:
|
||||
if(c >= '0' && c <= '9') {
|
||||
s->attrs = (s->attrs & ~(0x07)) | (c - '0');
|
||||
c |= ((c - '0') << 8);
|
||||
s->state = COLOR;
|
||||
} else {
|
||||
s->state = NORMAL;
|
||||
}
|
||||
return;
|
||||
case COLOR:
|
||||
s->state = (c == ';') ? BRACKET : NORMAL;
|
||||
if(c == 'm') s->cattrs = s->attrs;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
vprintfmt(void (*putch)(int, void*), void *putdat, const char *fmt, va_list ap)
|
||||
{
|
||||
|
@ -87,12 +135,17 @@ vprintfmt(void (*putch)(int, void*), void *putdat, const char *fmt, va_list ap)
|
|||
unsigned long long num;
|
||||
int base, lflag, width, precision, altflag;
|
||||
char padc;
|
||||
struct AttrState attst;
|
||||
|
||||
attst.state = NORMAL;
|
||||
attst.cattrs = 0;
|
||||
attst.attrs = 0;
|
||||
|
||||
while (1) {
|
||||
while ((ch = *(unsigned char *) fmt++) != '%') {
|
||||
if (ch == '\0')
|
||||
return;
|
||||
putch(ch, putdat);
|
||||
putchw(putch, ch, putdat, &attst);
|
||||
}
|
||||
|
||||
// Process a %-escape sequence
|
||||
|
|
Loading…
Reference in New Issue
Block a user