This source file includes following definitions.
- wsemul_vt100_init
- wsemul_vt100_cnattach
- wsemul_vt100_attach
- wsemul_vt100_detach
- wsemul_vt100_resetop
- wsemul_vt100_reset
- wsemul_vt100_nextline
- wsemul_vt100_output_normal
- wsemul_vt100_output_c0c1
- wsemul_vt100_output_esc
- wsemul_vt100_output_scs94
- wsemul_vt100_output_scs94_percent
- wsemul_vt100_output_scs96
- wsemul_vt100_output_scs96_percent
- wsemul_vt100_output_esc_spc
- wsemul_vt100_output_string
- wsemul_vt100_output_string_esc
- wsemul_vt100_output_dcs
- wsemul_vt100_output_dcs_dollar
- wsemul_vt100_output_esc_hash
- wsemul_vt100_output_csi
- wsemul_vt100_output
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30 #ifndef SMALL_KERNEL
31 #define JUMP_SCROLL
32 #endif
33
34 #include <sys/param.h>
35 #include <sys/systm.h>
36 #include <sys/time.h>
37 #include <sys/malloc.h>
38 #include <sys/fcntl.h>
39
40 #include <dev/wscons/wsconsio.h>
41 #include <dev/wscons/wsdisplayvar.h>
42 #include <dev/wscons/wsemulvar.h>
43 #include <dev/wscons/wsemul_vt100var.h>
44 #include <dev/wscons/ascii.h>
45
46 void *wsemul_vt100_cnattach(const struct wsscreen_descr *, void *,
47 int, int, long);
48 void *wsemul_vt100_attach(int console, const struct wsscreen_descr *,
49 void *, int, int, void *, long);
50 void wsemul_vt100_output(void *cookie, const u_char *data, u_int count,
51 int);
52 void wsemul_vt100_detach(void *cookie, u_int *crowp, u_int *ccolp);
53 void wsemul_vt100_resetop(void *, enum wsemul_resetops);
54
55 const struct wsemul_ops wsemul_vt100_ops = {
56 "vt100",
57 wsemul_vt100_cnattach,
58 wsemul_vt100_attach,
59 wsemul_vt100_output,
60 wsemul_vt100_translate,
61 wsemul_vt100_detach,
62 wsemul_vt100_resetop
63 };
64
65 struct wsemul_vt100_emuldata wsemul_vt100_console_emuldata;
66
67 void wsemul_vt100_init(struct wsemul_vt100_emuldata *,
68 const struct wsscreen_descr *, void *, int, int,
69 long);
70
71 void wsemul_vt100_output_normal(struct wsemul_vt100_emuldata *, u_char,
72 int);
73 void wsemul_vt100_output_c0c1(struct wsemul_vt100_emuldata *, u_char,
74 int);
75 void wsemul_vt100_nextline(struct wsemul_vt100_emuldata *);
76 typedef u_int vt100_handler(struct wsemul_vt100_emuldata *, u_char);
77 vt100_handler
78 wsemul_vt100_output_esc,
79 wsemul_vt100_output_csi,
80 wsemul_vt100_output_scs94,
81 wsemul_vt100_output_scs94_percent,
82 wsemul_vt100_output_scs96,
83 wsemul_vt100_output_scs96_percent,
84 wsemul_vt100_output_esc_hash,
85 wsemul_vt100_output_esc_spc,
86 wsemul_vt100_output_string,
87 wsemul_vt100_output_string_esc,
88 wsemul_vt100_output_dcs,
89 wsemul_vt100_output_dcs_dollar;
90
91 #define VT100_EMUL_STATE_NORMAL 0
92 #define VT100_EMUL_STATE_ESC 1
93 #define VT100_EMUL_STATE_CSI 2
94 #define VT100_EMUL_STATE_SCS94 3
95 #define VT100_EMUL_STATE_SCS94_PERCENT 4
96 #define VT100_EMUL_STATE_SCS96 5
97 #define VT100_EMUL_STATE_SCS96_PERCENT 6
98 #define VT100_EMUL_STATE_ESC_HASH 7
99 #define VT100_EMUL_STATE_ESC_SPC 8
100 #define VT100_EMUL_STATE_STRING 9
101 #define VT100_EMUL_STATE_STRING_ESC 10
102 #define VT100_EMUL_STATE_DCS 11
103 #define VT100_EMUL_STATE_DCS_DOLLAR 12
104
105 vt100_handler *vt100_output[] = {
106 wsemul_vt100_output_esc,
107 wsemul_vt100_output_csi,
108 wsemul_vt100_output_scs94,
109 wsemul_vt100_output_scs94_percent,
110 wsemul_vt100_output_scs96,
111 wsemul_vt100_output_scs96_percent,
112 wsemul_vt100_output_esc_hash,
113 wsemul_vt100_output_esc_spc,
114 wsemul_vt100_output_string,
115 wsemul_vt100_output_string_esc,
116 wsemul_vt100_output_dcs,
117 wsemul_vt100_output_dcs_dollar,
118 };
119
120 void
121 wsemul_vt100_init(edp, type, cookie, ccol, crow, defattr)
122 struct wsemul_vt100_emuldata *edp;
123 const struct wsscreen_descr *type;
124 void *cookie;
125 int ccol, crow;
126 long defattr;
127 {
128 edp->emulops = type->textops;
129 edp->emulcookie = cookie;
130 edp->scrcapabilities = type->capabilities;
131 edp->nrows = type->nrows;
132 edp->ncols = type->ncols;
133 edp->crow = crow;
134 edp->ccol = ccol;
135 edp->defattr = defattr;
136 }
137
138 void *
139 wsemul_vt100_cnattach(type, cookie, ccol, crow, defattr)
140 const struct wsscreen_descr *type;
141 void *cookie;
142 int ccol, crow;
143 long defattr;
144 {
145 struct wsemul_vt100_emuldata *edp;
146 int res;
147
148 edp = &wsemul_vt100_console_emuldata;
149 wsemul_vt100_init(edp, type, cookie, ccol, crow, defattr);
150 #ifdef DIAGNOSTIC
151 edp->console = 1;
152 #endif
153 edp->cbcookie = NULL;
154
155 #ifndef WS_KERNEL_FG
156 #define WS_KERNEL_FG WSCOL_WHITE
157 #endif
158 #ifndef WS_KERNEL_BG
159 #define WS_KERNEL_BG WSCOL_BLUE
160 #endif
161 #ifndef WS_KERNEL_COLATTR
162 #define WS_KERNEL_COLATTR 0
163 #endif
164 #ifndef WS_KERNEL_MONOATTR
165 #define WS_KERNEL_MONOATTR 0
166 #endif
167 if (type->capabilities & WSSCREEN_WSCOLORS)
168 res = (*edp->emulops->alloc_attr)(cookie,
169 WS_KERNEL_FG, WS_KERNEL_BG,
170 WS_KERNEL_COLATTR | WSATTR_WSCOLORS,
171 &edp->kernattr);
172 else
173 res = (*edp->emulops->alloc_attr)(cookie, 0, 0,
174 WS_KERNEL_MONOATTR,
175 &edp->kernattr);
176 if (res)
177 edp->kernattr = defattr;
178
179 edp->tabs = NULL;
180 edp->dblwid = NULL;
181 edp->dw = 0;
182 edp->dcsarg = 0;
183 edp->isolatin1tab = edp->decgraphtab = edp->dectechtab = NULL;
184 edp->nrctab = NULL;
185 wsemul_vt100_reset(edp);
186 return (edp);
187 }
188
189 void *
190 wsemul_vt100_attach(console, type, cookie, ccol, crow, cbcookie, defattr)
191 int console;
192 const struct wsscreen_descr *type;
193 void *cookie;
194 int ccol, crow;
195 void *cbcookie;
196 long defattr;
197 {
198 struct wsemul_vt100_emuldata *edp;
199
200 if (console) {
201 edp = &wsemul_vt100_console_emuldata;
202 #ifdef DIAGNOSTIC
203 KASSERT(edp->console == 1);
204 #endif
205 } else {
206 edp = malloc(sizeof *edp, M_DEVBUF, M_NOWAIT);
207 if (edp == NULL)
208 return (NULL);
209 wsemul_vt100_init(edp, type, cookie, ccol, crow, defattr);
210 #ifdef DIAGNOSTIC
211 edp->console = 0;
212 #endif
213 }
214 edp->cbcookie = cbcookie;
215
216 edp->tabs = malloc(edp->ncols, M_DEVBUF, M_NOWAIT);
217 edp->dblwid = malloc(edp->nrows, M_DEVBUF, M_NOWAIT);
218 if (edp->dblwid != NULL)
219 memset(edp->dblwid, 0, edp->nrows);
220 edp->dw = 0;
221 edp->dcsarg = malloc(DCS_MAXLEN, M_DEVBUF, M_NOWAIT);
222 edp->isolatin1tab = malloc(128 * sizeof(int), M_DEVBUF, M_NOWAIT);
223 edp->decgraphtab = malloc(128 * sizeof(int), M_DEVBUF, M_NOWAIT);
224 edp->dectechtab = malloc(128 * sizeof(int), M_DEVBUF, M_NOWAIT);
225 edp->nrctab = malloc(128 * sizeof(int), M_DEVBUF, M_NOWAIT);
226 vt100_initchartables(edp);
227 wsemul_vt100_reset(edp);
228 return (edp);
229 }
230
231 void
232 wsemul_vt100_detach(cookie, crowp, ccolp)
233 void *cookie;
234 u_int *crowp, *ccolp;
235 {
236 struct wsemul_vt100_emuldata *edp = cookie;
237
238 *crowp = edp->crow;
239 *ccolp = edp->ccol;
240 #define f(ptr) if (ptr) {free(ptr, M_DEVBUF); ptr = NULL;}
241 f(edp->tabs)
242 f(edp->dblwid)
243 f(edp->dcsarg)
244 f(edp->isolatin1tab)
245 f(edp->decgraphtab)
246 f(edp->dectechtab)
247 f(edp->nrctab)
248 #undef f
249 if (edp != &wsemul_vt100_console_emuldata)
250 free(edp, M_DEVBUF);
251 }
252
253 void
254 wsemul_vt100_resetop(cookie, op)
255 void *cookie;
256 enum wsemul_resetops op;
257 {
258 struct wsemul_vt100_emuldata *edp = cookie;
259
260 switch (op) {
261 case WSEMUL_RESET:
262 wsemul_vt100_reset(edp);
263 break;
264 case WSEMUL_SYNCFONT:
265 vt100_initchartables(edp);
266 break;
267 case WSEMUL_CLEARSCREEN:
268 wsemul_vt100_ed(edp, 2);
269 edp->ccol = edp->crow = 0;
270 (*edp->emulops->cursor)(edp->emulcookie,
271 edp->flags & VTFL_CURSORON, 0, 0);
272 break;
273 default:
274 break;
275 }
276 }
277
278 void
279 wsemul_vt100_reset(edp)
280 struct wsemul_vt100_emuldata *edp;
281 {
282 int i;
283
284 edp->state = VT100_EMUL_STATE_NORMAL;
285 edp->flags = VTFL_DECAWM | VTFL_CURSORON;
286 edp->bkgdattr = edp->curattr = edp->defattr;
287 edp->attrflags = 0;
288 edp->fgcol = WSCOL_WHITE;
289 edp->bgcol = WSCOL_BLACK;
290 edp->scrreg_startrow = 0;
291 edp->scrreg_nrows = edp->nrows;
292 if (edp->tabs) {
293 memset(edp->tabs, 0, edp->ncols);
294 for (i = 8; i < edp->ncols; i += 8)
295 edp->tabs[i] = 1;
296 }
297 edp->dcspos = 0;
298 edp->dcstype = 0;
299 edp->chartab_G[0] = NULL;
300 edp->chartab_G[1] = edp->nrctab;
301 edp->chartab_G[2] = edp->isolatin1tab;
302 edp->chartab_G[3] = edp->isolatin1tab;
303 edp->chartab0 = 0;
304 edp->chartab1 = 2;
305 edp->sschartab = 0;
306 }
307
308
309
310
311
312
313 void
314 wsemul_vt100_nextline(struct wsemul_vt100_emuldata *edp)
315 {
316 if (ROWS_BELOW == 0) {
317
318 wsemul_vt100_scrollup(edp, 1);
319 } else {
320 if ((edp->crow+1) < edp->nrows)
321
322 edp->crow++;
323 CHECK_DW;
324 }
325 }
326
327
328
329
330
331 void
332 wsemul_vt100_output_normal(edp, c, kernel)
333 struct wsemul_vt100_emuldata *edp;
334 u_char c;
335 int kernel;
336 {
337 u_int *ct, dc;
338
339 if ((edp->flags & (VTFL_LASTCHAR | VTFL_DECAWM)) ==
340 (VTFL_LASTCHAR | VTFL_DECAWM)) {
341 wsemul_vt100_nextline(edp);
342 edp->ccol = 0;
343 edp->flags &= ~VTFL_LASTCHAR;
344 }
345
346 if (c & 0x80) {
347 c &= 0x7f;
348 ct = edp->chartab_G[edp->chartab1];
349 } else {
350 if (edp->sschartab) {
351 ct = edp->chartab_G[edp->sschartab];
352 edp->sschartab = 0;
353 } else
354 ct = edp->chartab_G[edp->chartab0];
355 }
356 dc = (ct ? ct[c] : c);
357
358 if ((edp->flags & VTFL_INSERTMODE) && COLS_LEFT)
359 COPYCOLS(edp->ccol, edp->ccol + 1, COLS_LEFT);
360
361 (*edp->emulops->putchar)(edp->emulcookie, edp->crow,
362 edp->ccol << edp->dw, dc,
363 kernel ? edp->kernattr : edp->curattr);
364
365 if (COLS_LEFT)
366 edp->ccol++;
367 else
368 edp->flags |= VTFL_LASTCHAR;
369 }
370
371 void
372 wsemul_vt100_output_c0c1(edp, c, kernel)
373 struct wsemul_vt100_emuldata *edp;
374 u_char c;
375 int kernel;
376 {
377 u_int n;
378
379 switch (c) {
380 case ASCII_NUL:
381 default:
382
383 break;
384 case ASCII_BEL:
385 wsdisplay_emulbell(edp->cbcookie);
386 break;
387 case ASCII_BS:
388 if (edp->ccol > 0) {
389 edp->ccol--;
390 edp->flags &= ~VTFL_LASTCHAR;
391 }
392 break;
393 case ASCII_CR:
394 edp->ccol = 0;
395 edp->flags &= ~VTFL_LASTCHAR;
396 break;
397 case ASCII_HT:
398 if (edp->tabs) {
399 if (!COLS_LEFT)
400 break;
401 for (n = edp->ccol + 1; n < NCOLS - 1; n++)
402 if (edp->tabs[n])
403 break;
404 } else {
405 n = edp->ccol + min(8 - (edp->ccol & 7), COLS_LEFT);
406 }
407 edp->ccol = n;
408 break;
409 case ASCII_SO:
410 edp->chartab0 = 1;
411 break;
412 case ASCII_SI:
413 edp->chartab0 = 0;
414 break;
415 case ASCII_ESC:
416 if (kernel) {
417 printf("wsemul_vt100_output_c0c1: ESC in kernel "
418 "output ignored\n");
419 break;
420 }
421
422 if (edp->state == VT100_EMUL_STATE_STRING) {
423
424 edp->state = VT100_EMUL_STATE_STRING_ESC;
425 } else {
426
427 edp->state = VT100_EMUL_STATE_ESC;
428 }
429 break;
430 #if 0
431 case CSI:
432
433 edp->nargs = 0;
434 memset(edp->args, 0, sizeof (edp->args));
435 edp->modif1 = edp->modif2 = '\0';
436 edp->state = VT100_EMUL_STATE_CSI;
437 break;
438 case DCS:
439
440 edp->nargs = 0;
441 memset(edp->args, 0, sizeof (edp->args));
442 edp->state = VT100_EMUL_STATE_DCS;
443 break;
444 case ST:
445
446 wsemul_vt100_handle_dcs(edp);
447 return (VT100_EMUL_STATE_NORMAL);
448 #endif
449 case ASCII_LF:
450 case ASCII_VT:
451 case ASCII_FF:
452 wsemul_vt100_nextline(edp);
453 break;
454 }
455 }
456
457 u_int
458 wsemul_vt100_output_esc(edp, c)
459 struct wsemul_vt100_emuldata *edp;
460 u_char c;
461 {
462 u_int newstate = VT100_EMUL_STATE_NORMAL;
463 int i;
464
465 switch (c) {
466 case '[':
467 edp->nargs = 0;
468 memset(edp->args, 0, sizeof (edp->args));
469 edp->modif1 = edp->modif2 = '\0';
470 newstate = VT100_EMUL_STATE_CSI;
471 break;
472 case '7':
473 edp->flags |= VTFL_SAVEDCURS;
474 edp->savedcursor_row = edp->crow;
475 edp->savedcursor_col = edp->ccol;
476 edp->savedattr = edp->curattr;
477 edp->savedbkgdattr = edp->bkgdattr;
478 edp->savedattrflags = edp->attrflags;
479 edp->savedfgcol = edp->fgcol;
480 edp->savedbgcol = edp->bgcol;
481 for (i = 0; i < 4; i++)
482 edp->savedchartab_G[i] = edp->chartab_G[i];
483 edp->savedchartab0 = edp->chartab0;
484 edp->savedchartab1 = edp->chartab1;
485 break;
486 case '8':
487 if ((edp->flags & VTFL_SAVEDCURS) == 0)
488 break;
489 edp->crow = edp->savedcursor_row;
490 edp->ccol = edp->savedcursor_col;
491 edp->curattr = edp->savedattr;
492 edp->bkgdattr = edp->savedbkgdattr;
493 edp->attrflags = edp->savedattrflags;
494 edp->fgcol = edp->savedfgcol;
495 edp->bgcol = edp->savedbgcol;
496 for (i = 0; i < 4; i++)
497 edp->chartab_G[i] = edp->savedchartab_G[i];
498 edp->chartab0 = edp->savedchartab0;
499 edp->chartab1 = edp->savedchartab1;
500 break;
501 case '=':
502 edp->flags |= VTFL_APPLKEYPAD;
503 break;
504 case '>':
505 edp->flags &= ~VTFL_APPLKEYPAD;
506 break;
507 case 'E':
508 edp->ccol = 0;
509
510 case 'D':
511 wsemul_vt100_nextline(edp);
512 break;
513 case 'H':
514 if (edp->tabs != NULL)
515 edp->tabs[edp->ccol] = 1;
516 break;
517 case '~':
518 edp->chartab1 = 1;
519 break;
520 case 'n':
521 edp->chartab0 = 2;
522 break;
523 case '}':
524 edp->chartab1 = 2;
525 break;
526 case 'o':
527 edp->chartab0 = 3;
528 break;
529 case '|':
530 edp->chartab1 = 3;
531 break;
532 case 'N':
533 edp->sschartab = 2;
534 break;
535 case 'O':
536 edp->sschartab = 3;
537 break;
538 case 'M':
539 if (ROWS_ABOVE > 0) {
540 edp->crow--;
541 CHECK_DW;
542 break;
543 }
544 wsemul_vt100_scrolldown(edp, 1);
545 break;
546 case 'P':
547 edp->nargs = 0;
548 memset(edp->args, 0, sizeof (edp->args));
549 newstate = VT100_EMUL_STATE_DCS;
550 break;
551 case 'c':
552 wsemul_vt100_reset(edp);
553 wsemul_vt100_ed(edp, 2);
554 edp->ccol = edp->crow = 0;
555 break;
556 case '(': case ')': case '*': case '+':
557 edp->designating = c - '(';
558 newstate = VT100_EMUL_STATE_SCS94;
559 break;
560 case '-': case '.': case '/':
561 edp->designating = c - '-' + 1;
562 newstate = VT100_EMUL_STATE_SCS96;
563 break;
564 case '#':
565 newstate = VT100_EMUL_STATE_ESC_HASH;
566 break;
567 case ' ':
568 newstate = VT100_EMUL_STATE_ESC_SPC;
569 break;
570 case ']':
571 case '^':
572 case '_':
573
574 newstate = VT100_EMUL_STATE_STRING;
575 break;
576 case '<':
577 break;
578 default:
579 #ifdef VT100_PRINTUNKNOWN
580 printf("ESC%c unknown\n", c);
581 #endif
582 break;
583 }
584
585 return (newstate);
586 }
587
588 u_int
589 wsemul_vt100_output_scs94(edp, c)
590 struct wsemul_vt100_emuldata *edp;
591 u_char c;
592 {
593 u_int newstate = VT100_EMUL_STATE_NORMAL;
594
595 switch (c) {
596 case '%':
597 newstate = VT100_EMUL_STATE_SCS94_PERCENT;
598 break;
599 case 'A':
600 edp->chartab_G[edp->designating] = edp->nrctab;
601 break;
602 case 'B':
603 edp->chartab_G[edp->designating] = 0;
604 break;
605 case '<':
606
607 edp->chartab_G[edp->designating] = edp->isolatin1tab;
608 break;
609 case '0':
610 edp->chartab_G[edp->designating] = edp->decgraphtab;
611 break;
612 case '>':
613 edp->chartab_G[edp->designating] = edp->dectechtab;
614 break;
615 default:
616 #ifdef VT100_PRINTUNKNOWN
617 printf("ESC%c%c unknown\n", edp->designating + '(', c);
618 #endif
619 break;
620 }
621 return (newstate);
622 }
623
624 u_int
625 wsemul_vt100_output_scs94_percent(edp, c)
626 struct wsemul_vt100_emuldata *edp;
627 u_char c;
628 {
629 switch (c) {
630 case '5':
631
632 edp->chartab_G[edp->designating] = edp->isolatin1tab;
633 break;
634 default:
635 #ifdef VT100_PRINTUNKNOWN
636 printf("ESC%c%%%c unknown\n", edp->designating + '(', c);
637 #endif
638 break;
639 }
640 return (VT100_EMUL_STATE_NORMAL);
641 }
642
643 u_int
644 wsemul_vt100_output_scs96(edp, c)
645 struct wsemul_vt100_emuldata *edp;
646 u_char c;
647 {
648 u_int newstate = VT100_EMUL_STATE_NORMAL;
649 int nrc;
650
651 switch (c) {
652 case '%':
653 newstate = VT100_EMUL_STATE_SCS96_PERCENT;
654 break;
655 case 'A':
656 edp->chartab_G[edp->designating] = edp->isolatin1tab;
657 break;
658 case '4':
659 nrc = 1;
660 goto setnrc;
661 case '5': case 'C':
662 nrc = 2;
663 goto setnrc;
664 case 'R':
665 nrc = 3;
666 goto setnrc;
667 case 'Q':
668 nrc = 4;
669 goto setnrc;
670 case 'K':
671 nrc = 5;
672 goto setnrc;
673 case 'Y':
674 nrc = 6;
675 goto setnrc;
676 case 'E': case '6':
677 nrc = 7;
678 goto setnrc;
679 case 'Z':
680 nrc = 9;
681 goto setnrc;
682 case '7': case 'H':
683 nrc = 10;
684 goto setnrc;
685 case '=':
686 nrc = 11;
687 setnrc:
688 if (vt100_setnrc(edp, nrc) == 0)
689 break;
690
691 default:
692 #ifdef VT100_PRINTUNKNOWN
693 printf("ESC%c%c unknown\n", edp->designating + '-' - 1, c);
694 #endif
695 break;
696 }
697 return (newstate);
698 }
699
700 u_int
701 wsemul_vt100_output_scs96_percent(edp, c)
702 struct wsemul_vt100_emuldata *edp;
703 u_char c;
704 {
705 switch (c) {
706 case '6':
707 if (vt100_setnrc(edp, 8) == 0)
708 break;
709
710 default:
711 #ifdef VT100_PRINTUNKNOWN
712 printf("ESC%c%%%c unknown\n", edp->designating + '-' - 1, c);
713 #endif
714 break;
715 }
716 return (VT100_EMUL_STATE_NORMAL);
717 }
718
719 u_int
720 wsemul_vt100_output_esc_spc(edp, c)
721 struct wsemul_vt100_emuldata *edp;
722 u_char c;
723 {
724 switch (c) {
725 case 'F':
726 case 'G':
727 #ifdef VT100_PRINTNOTIMPL
728 printf("ESC<SPC>%c ignored\n", c);
729 #endif
730 break;
731 default:
732 #ifdef VT100_PRINTUNKNOWN
733 printf("ESC<SPC>%c unknown\n", c);
734 #endif
735 break;
736 }
737 return (VT100_EMUL_STATE_NORMAL);
738 }
739
740 u_int
741 wsemul_vt100_output_string(edp, c)
742 struct wsemul_vt100_emuldata *edp;
743 u_char c;
744 {
745 if (edp->dcstype && edp->dcspos < DCS_MAXLEN)
746 edp->dcsarg[edp->dcspos++] = c;
747 return (VT100_EMUL_STATE_STRING);
748 }
749
750 u_int
751 wsemul_vt100_output_string_esc(edp, c)
752 struct wsemul_vt100_emuldata *edp;
753 u_char c;
754 {
755 if (c == '\\') {
756 wsemul_vt100_handle_dcs(edp);
757 return (VT100_EMUL_STATE_NORMAL);
758 } else
759 return (VT100_EMUL_STATE_STRING);
760 }
761
762 u_int
763 wsemul_vt100_output_dcs(edp, c)
764 struct wsemul_vt100_emuldata *edp;
765 u_char c;
766 {
767 u_int newstate = VT100_EMUL_STATE_DCS;
768
769 switch (c) {
770 case '0': case '1': case '2': case '3': case '4':
771 case '5': case '6': case '7': case '8': case '9':
772
773 if (edp->nargs > VT100_EMUL_NARGS - 1)
774 break;
775 edp->args[edp->nargs] = (edp->args[edp->nargs] * 10) +
776 (c - '0');
777 break;
778 case ';':
779 edp->nargs++;
780 break;
781 default:
782 edp->nargs++;
783 if (edp->nargs > VT100_EMUL_NARGS) {
784 #ifdef VT100_DEBUG
785 printf("vt100: too many arguments\n");
786 #endif
787 edp->nargs = VT100_EMUL_NARGS;
788 }
789 newstate = VT100_EMUL_STATE_STRING;
790 switch (c) {
791 case '$':
792 newstate = VT100_EMUL_STATE_DCS_DOLLAR;
793 break;
794 case '{':
795 case '!':
796
797 case '|':
798 #ifdef VT100_PRINTNOTIMPL
799 printf("DCS%c ignored\n", c);
800 #endif
801 break;
802 default:
803 #ifdef VT100_PRINTUNKNOWN
804 printf("DCS%c (%d, %d) unknown\n", c, ARG(0), ARG(1));
805 #endif
806 break;
807 }
808 }
809
810 return (newstate);
811 }
812
813 u_int
814 wsemul_vt100_output_dcs_dollar(edp, c)
815 struct wsemul_vt100_emuldata *edp;
816 u_char c;
817 {
818 switch (c) {
819 case 'p':
820 case 'q':
821 #ifdef VT100_PRINTNOTIMPL
822 printf("DCS$%c ignored\n", c);
823 #endif
824 break;
825 case 't':
826 switch (ARG(0)) {
827 case 0:
828 break;
829 case 1:
830 #ifdef VT100_PRINTNOTIMPL
831 printf("DCS1$t ignored\n");
832 #endif
833 break;
834 case 2:
835 edp->dcspos = 0;
836 edp->dcstype = DCSTYPE_TABRESTORE;
837 break;
838 default:
839 #ifdef VT100_PRINTUNKNOWN
840 printf("DCS%d$t unknown\n", ARG(0));
841 #endif
842 break;
843 }
844 break;
845 default:
846 #ifdef VT100_PRINTUNKNOWN
847 printf("DCS$%c (%d, %d) unknown\n", c, ARG(0), ARG(1));
848 #endif
849 break;
850 }
851 return (VT100_EMUL_STATE_STRING);
852 }
853
854 u_int
855 wsemul_vt100_output_esc_hash(edp, c)
856 struct wsemul_vt100_emuldata *edp;
857 u_char c;
858 {
859 int i;
860
861 switch (c) {
862 case '5':
863 if (edp->dblwid != NULL && edp->dw != 0) {
864 for (i = 0; i < edp->ncols / 2; i++)
865 (*edp->emulops->copycols)(edp->emulcookie,
866 edp->crow,
867 2 * i, i, 1);
868 (*edp->emulops->erasecols)(edp->emulcookie, edp->crow,
869 i, edp->ncols - i,
870 edp->bkgdattr);
871 edp->dblwid[edp->crow] = 0;
872 edp->dw = 0;
873 }
874 break;
875 case '6':
876 case '3':
877 case '4':
878 if (edp->dblwid != NULL && edp->dw == 0) {
879 for (i = edp->ncols / 2 - 1; i >= 0; i--)
880 (*edp->emulops->copycols)(edp->emulcookie,
881 edp->crow,
882 i, 2 * i, 1);
883 for (i = 0; i < edp->ncols / 2; i++)
884 (*edp->emulops->erasecols)(edp->emulcookie,
885 edp->crow,
886 2 * i + 1, 1,
887 edp->bkgdattr);
888 edp->dblwid[edp->crow] = 1;
889 edp->dw = 1;
890 if (edp->ccol > (edp->ncols >> 1) - 1)
891 edp->ccol = (edp->ncols >> 1) - 1;
892 }
893 break;
894 case '8': {
895 int i, j;
896 for (i = 0; i < edp->nrows; i++)
897 for (j = 0; j < edp->ncols; j++)
898 (*edp->emulops->putchar)(edp->emulcookie, i, j,
899 'E', edp->curattr);
900 }
901 edp->ccol = 0;
902 edp->crow = 0;
903 break;
904 default:
905 #ifdef VT100_PRINTUNKNOWN
906 printf("ESC#%c unknown\n", c);
907 #endif
908 break;
909 }
910 return (VT100_EMUL_STATE_NORMAL);
911 }
912
913 u_int
914 wsemul_vt100_output_csi(edp, c)
915 struct wsemul_vt100_emuldata *edp;
916 u_char c;
917 {
918 u_int newstate = VT100_EMUL_STATE_CSI;
919
920 switch (c) {
921 case '0': case '1': case '2': case '3': case '4':
922 case '5': case '6': case '7': case '8': case '9':
923
924 if (edp->nargs > VT100_EMUL_NARGS - 1)
925 break;
926 edp->args[edp->nargs] = (edp->args[edp->nargs] * 10) +
927 (c - '0');
928 break;
929 case ';':
930 edp->nargs++;
931 break;
932 case '?':
933 case '>':
934 edp->modif1 = c;
935 break;
936 case '!':
937 case '"':
938 case '$':
939 case '&':
940 edp->modif2 = c;
941 break;
942 default:
943 edp->nargs++;
944 if (edp->nargs > VT100_EMUL_NARGS) {
945 #ifdef VT100_DEBUG
946 printf("vt100: too many arguments\n");
947 #endif
948 edp->nargs = VT100_EMUL_NARGS;
949 }
950 wsemul_vt100_handle_csi(edp, c);
951 newstate = VT100_EMUL_STATE_NORMAL;
952 break;
953 }
954 return (newstate);
955 }
956
957 void
958 wsemul_vt100_output(cookie, data, count, kernel)
959 void *cookie;
960 const u_char *data;
961 u_int count;
962 int kernel;
963 {
964 struct wsemul_vt100_emuldata *edp = cookie;
965 #ifdef JUMP_SCROLL
966 const u_char *eot;
967 u_char curchar;
968 u_int cnt, pos, lines;
969 #endif
970
971 #ifdef DIAGNOSTIC
972 if (kernel && !edp->console)
973 panic("wsemul_vt100_output: kernel output, not console");
974 #endif
975
976 if (edp->flags & VTFL_CURSORON)
977 (*edp->emulops->cursor)(edp->emulcookie, 0,
978 edp->crow, edp->ccol << edp->dw);
979
980 for (; count > 0; data++, count--) {
981 #ifdef JUMP_SCROLL
982
983
984
985
986 if ((edp->state == VT100_EMUL_STATE_NORMAL || kernel) &&
987 ROWS_BELOW == 0) {
988 lines = 0;
989 pos = edp->ccol;
990 for (eot = data, cnt = count; cnt != 0; eot++, cnt--) {
991 curchar = *eot;
992
993
994
995
996
997
998 if (curchar == ASCII_ESC)
999 break;
1000
1001 if (ISSET(edp->flags, VTFL_DECAWM))
1002 switch (curchar) {
1003 case ASCII_BS:
1004 if (pos > 0)
1005 pos--;
1006 break;
1007 case ASCII_CR:
1008 pos = 0;
1009 break;
1010 case ASCII_HT:
1011 if (edp->tabs) {
1012 pos++;
1013 while (pos < NCOLS - 1 &&
1014 edp->tabs[pos] == 0)
1015 pos++;
1016 } else {
1017 pos = (pos + 7) & ~7;
1018 if (pos >= NCOLS)
1019 pos = NCOLS - 1;
1020 }
1021 break;
1022 default:
1023 if ((curchar & 0x7f) < 0x20)
1024 break;
1025 if (pos++ >= NCOLS) {
1026 pos = 0;
1027 curchar = ASCII_LF;
1028 }
1029 break;
1030 }
1031
1032 if (curchar == ASCII_LF ||
1033 curchar == ASCII_VT ||
1034 curchar == ASCII_FF) {
1035 if (++lines >= edp->scrreg_nrows - 1)
1036 break;
1037 }
1038 }
1039
1040 if (lines > 1) {
1041 wsemul_vt100_scrollup(edp, lines);
1042 edp->crow -= lines;
1043 }
1044 }
1045 #endif
1046
1047 if ((*data & 0x7f) < 0x20) {
1048 wsemul_vt100_output_c0c1(edp, *data, kernel);
1049 continue;
1050 }
1051
1052 if (edp->state == VT100_EMUL_STATE_NORMAL || kernel) {
1053 wsemul_vt100_output_normal(edp, *data, kernel);
1054 continue;
1055 }
1056 #ifdef DIAGNOSTIC
1057 if (edp->state > sizeof(vt100_output) / sizeof(vt100_output[0]))
1058 panic("wsemul_vt100: invalid state %d", edp->state);
1059 #endif
1060 edp->state = vt100_output[edp->state - 1](edp, *data);
1061 }
1062
1063 if (edp->flags & VTFL_CURSORON)
1064 (*edp->emulops->cursor)(edp->emulcookie, 1,
1065 edp->crow, edp->ccol << edp->dw);
1066 }