diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2016-07-24 20:14:37 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2016-07-24 20:14:37 -0400 |
commit | 721413aff218118548b84b18cb5b49660e6e2940 (patch) | |
tree | 967b1c535645a25c19e948d0b9fdf096f93b253e /drivers/tty/vt | |
parent | 25a0dc4be86fc0d8c7e81bb5f8be8427022bf15f (diff) | |
parent | 67417f9c262e2cd4b706eba3e1fd879d0bebc6d8 (diff) |
Merge tag 'tty-4.8-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty
Pull tty/serial driver updates from Greg KH:
"Here is the big tty and serial driver update for 4.8-rc1.
Lots of good cleanups from Jiri on a number of vt and other tty
related things, and the normal driver updates. Full details are in
the shortlog.
All of these have been in linux-next for a while with no reported
issues"
* tag 'tty-4.8-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty: (90 commits)
tty/serial: atmel: enforce tasklet init and termination sequences
serial: sh-sci: Stop transfers in sci_shutdown()
serial: 8250_ingenic: drop #if conditional surrounding earlycon code
serial: 8250_mtk: drop !defined(MODULE) conditional
serial: 8250_uniphier: drop !defined(MODULE) conditional
earlycon: mark earlycon code as __used iif the caller is built-in
tty/serial/8250: use mctrl_gpio helpers
serial: mctrl_gpio: enable API usage only for initialized mctrl_gpios struct
serial: mctrl_gpio: add modem control read routine
tty/serial/8250: make UART_MCR register access consistent
serial: 8250_mid: Read RX buffer on RX DMA timeout for DNV
serial: 8250_dma: Export serial8250_rx_dma_flush()
dmaengine: hsu: Export hsu_dma_get_status()
tty: serial: 8250: add CON_CONSDEV to flags
tty: serial: samsung: add byte-order aware bit functions
tty: serial: samsung: fixup accessors for endian
serial: sirf: make fifo functions static
serial: mps2-uart: make driver explicitly non-modular
serial: mvebu-uart: free the IRQ in ->shutdown()
serial/bcm63xx_uart: use correct alias naming
...
Diffstat (limited to 'drivers/tty/vt')
-rw-r--r-- | drivers/tty/vt/consolemap.c | 13 | ||||
-rw-r--r-- | drivers/tty/vt/keyboard.c | 16 | ||||
-rw-r--r-- | drivers/tty/vt/vt.c | 431 | ||||
-rw-r--r-- | drivers/tty/vt/vt_ioctl.c | 8 |
4 files changed, 221 insertions, 247 deletions
diff --git a/drivers/tty/vt/consolemap.c b/drivers/tty/vt/consolemap.c index c8c91f0476a2..9d7ab7b66a8a 100644 --- a/drivers/tty/vt/consolemap.c +++ b/drivers/tty/vt/consolemap.c | |||
@@ -499,9 +499,8 @@ con_insert_unipair(struct uni_pagedir *p, u_short unicode, u_short fontpos) | |||
499 | return 0; | 499 | return 0; |
500 | } | 500 | } |
501 | 501 | ||
502 | /* ui is a leftover from using a hashtable, but might be used again | 502 | /* Caller must hold the lock */ |
503 | Caller must hold the lock */ | 503 | static int con_do_clear_unimap(struct vc_data *vc) |
504 | static int con_do_clear_unimap(struct vc_data *vc, struct unimapinit *ui) | ||
505 | { | 504 | { |
506 | struct uni_pagedir *p, *q; | 505 | struct uni_pagedir *p, *q; |
507 | 506 | ||
@@ -524,11 +523,11 @@ static int con_do_clear_unimap(struct vc_data *vc, struct unimapinit *ui) | |||
524 | return 0; | 523 | return 0; |
525 | } | 524 | } |
526 | 525 | ||
527 | int con_clear_unimap(struct vc_data *vc, struct unimapinit *ui) | 526 | int con_clear_unimap(struct vc_data *vc) |
528 | { | 527 | { |
529 | int ret; | 528 | int ret; |
530 | console_lock(); | 529 | console_lock(); |
531 | ret = con_do_clear_unimap(vc, ui); | 530 | ret = con_do_clear_unimap(vc); |
532 | console_unlock(); | 531 | console_unlock(); |
533 | return ret; | 532 | return ret; |
534 | } | 533 | } |
@@ -556,7 +555,7 @@ int con_set_unimap(struct vc_data *vc, ushort ct, struct unipair __user *list) | |||
556 | int j, k; | 555 | int j, k; |
557 | u16 **p1, *p2, l; | 556 | u16 **p1, *p2, l; |
558 | 557 | ||
559 | err1 = con_do_clear_unimap(vc, NULL); | 558 | err1 = con_do_clear_unimap(vc); |
560 | if (err1) { | 559 | if (err1) { |
561 | console_unlock(); | 560 | console_unlock(); |
562 | return err1; | 561 | return err1; |
@@ -677,7 +676,7 @@ int con_set_default_unimap(struct vc_data *vc) | |||
677 | 676 | ||
678 | /* The default font is always 256 characters */ | 677 | /* The default font is always 256 characters */ |
679 | 678 | ||
680 | err = con_do_clear_unimap(vc, NULL); | 679 | err = con_do_clear_unimap(vc); |
681 | if (err) | 680 | if (err) |
682 | return err; | 681 | return err; |
683 | 682 | ||
diff --git a/drivers/tty/vt/keyboard.c b/drivers/tty/vt/keyboard.c index 1e93a37e27f0..0f8caae4267d 100644 --- a/drivers/tty/vt/keyboard.c +++ b/drivers/tty/vt/keyboard.c | |||
@@ -567,7 +567,7 @@ static void fn_scroll_forw(struct vc_data *vc) | |||
567 | 567 | ||
568 | static void fn_scroll_back(struct vc_data *vc) | 568 | static void fn_scroll_back(struct vc_data *vc) |
569 | { | 569 | { |
570 | scrollback(vc, 0); | 570 | scrollback(vc); |
571 | } | 571 | } |
572 | 572 | ||
573 | static void fn_show_mem(struct vc_data *vc) | 573 | static void fn_show_mem(struct vc_data *vc) |
@@ -1733,16 +1733,10 @@ int vt_do_diacrit(unsigned int cmd, void __user *udp, int perm) | |||
1733 | return -EINVAL; | 1733 | return -EINVAL; |
1734 | 1734 | ||
1735 | if (ct) { | 1735 | if (ct) { |
1736 | buf = kmalloc(ct * sizeof(struct kbdiacruc), | 1736 | buf = memdup_user(a->kbdiacruc, |
1737 | GFP_KERNEL); | 1737 | ct * sizeof(struct kbdiacruc)); |
1738 | if (buf == NULL) | 1738 | if (IS_ERR(buf)) |
1739 | return -ENOMEM; | 1739 | return PTR_ERR(buf); |
1740 | |||
1741 | if (copy_from_user(buf, a->kbdiacruc, | ||
1742 | ct * sizeof(struct kbdiacruc))) { | ||
1743 | kfree(buf); | ||
1744 | return -EFAULT; | ||
1745 | } | ||
1746 | } | 1740 | } |
1747 | spin_lock_irqsave(&kbd_event_lock, flags); | 1741 | spin_lock_irqsave(&kbd_event_lock, flags); |
1748 | if (ct) | 1742 | if (ct) |
diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c index 5b0fe97c46ca..2705ca960e92 100644 --- a/drivers/tty/vt/vt.c +++ b/drivers/tty/vt/vt.c | |||
@@ -277,13 +277,15 @@ static void notify_update(struct vc_data *vc) | |||
277 | * Low-Level Functions | 277 | * Low-Level Functions |
278 | */ | 278 | */ |
279 | 279 | ||
280 | #define IS_FG(vc) ((vc)->vc_num == fg_console) | 280 | static inline bool con_is_fg(const struct vc_data *vc) |
281 | { | ||
282 | return vc->vc_num == fg_console; | ||
283 | } | ||
281 | 284 | ||
282 | #ifdef VT_BUF_VRAM_ONLY | 285 | static inline bool con_should_update(const struct vc_data *vc) |
283 | #define DO_UPDATE(vc) 0 | 286 | { |
284 | #else | 287 | return con_is_visible(vc) && !console_blanked; |
285 | #define DO_UPDATE(vc) (CON_IS_VISIBLE(vc) && !console_blanked) | 288 | } |
286 | #endif | ||
287 | 289 | ||
288 | static inline unsigned short *screenpos(struct vc_data *vc, int offset, int viewed) | 290 | static inline unsigned short *screenpos(struct vc_data *vc, int offset, int viewed) |
289 | { | 291 | { |
@@ -321,7 +323,7 @@ static void scrup(struct vc_data *vc, unsigned int t, unsigned int b, int nr) | |||
321 | nr = b - t - 1; | 323 | nr = b - t - 1; |
322 | if (b > vc->vc_rows || t >= b || nr < 1) | 324 | if (b > vc->vc_rows || t >= b || nr < 1) |
323 | return; | 325 | return; |
324 | if (CON_IS_VISIBLE(vc) && vc->vc_sw->con_scroll(vc, t, b, SM_UP, nr)) | 326 | if (con_is_visible(vc) && vc->vc_sw->con_scroll(vc, t, b, SM_UP, nr)) |
325 | return; | 327 | return; |
326 | d = (unsigned short *)(vc->vc_origin + vc->vc_size_row * t); | 328 | d = (unsigned short *)(vc->vc_origin + vc->vc_size_row * t); |
327 | s = (unsigned short *)(vc->vc_origin + vc->vc_size_row * (t + nr)); | 329 | s = (unsigned short *)(vc->vc_origin + vc->vc_size_row * (t + nr)); |
@@ -339,7 +341,7 @@ static void scrdown(struct vc_data *vc, unsigned int t, unsigned int b, int nr) | |||
339 | nr = b - t - 1; | 341 | nr = b - t - 1; |
340 | if (b > vc->vc_rows || t >= b || nr < 1) | 342 | if (b > vc->vc_rows || t >= b || nr < 1) |
341 | return; | 343 | return; |
342 | if (CON_IS_VISIBLE(vc) && vc->vc_sw->con_scroll(vc, t, b, SM_DOWN, nr)) | 344 | if (con_is_visible(vc) && vc->vc_sw->con_scroll(vc, t, b, SM_DOWN, nr)) |
343 | return; | 345 | return; |
344 | s = (unsigned short *)(vc->vc_origin + vc->vc_size_row * t); | 346 | s = (unsigned short *)(vc->vc_origin + vc->vc_size_row * t); |
345 | step = vc->vc_cols * nr; | 347 | step = vc->vc_cols * nr; |
@@ -349,7 +351,6 @@ static void scrdown(struct vc_data *vc, unsigned int t, unsigned int b, int nr) | |||
349 | 351 | ||
350 | static void do_update_region(struct vc_data *vc, unsigned long start, int count) | 352 | static void do_update_region(struct vc_data *vc, unsigned long start, int count) |
351 | { | 353 | { |
352 | #ifndef VT_BUF_VRAM_ONLY | ||
353 | unsigned int xx, yy, offset; | 354 | unsigned int xx, yy, offset; |
354 | u16 *p; | 355 | u16 *p; |
355 | 356 | ||
@@ -390,14 +391,13 @@ static void do_update_region(struct vc_data *vc, unsigned long start, int count) | |||
390 | start = vc->vc_sw->con_getxy(vc, start, NULL, NULL); | 391 | start = vc->vc_sw->con_getxy(vc, start, NULL, NULL); |
391 | } | 392 | } |
392 | } | 393 | } |
393 | #endif | ||
394 | } | 394 | } |
395 | 395 | ||
396 | void update_region(struct vc_data *vc, unsigned long start, int count) | 396 | void update_region(struct vc_data *vc, unsigned long start, int count) |
397 | { | 397 | { |
398 | WARN_CONSOLE_UNLOCKED(); | 398 | WARN_CONSOLE_UNLOCKED(); |
399 | 399 | ||
400 | if (DO_UPDATE(vc)) { | 400 | if (con_should_update(vc)) { |
401 | hide_cursor(vc); | 401 | hide_cursor(vc); |
402 | do_update_region(vc, start, count); | 402 | do_update_region(vc, start, count); |
403 | set_cursor(vc); | 403 | set_cursor(vc); |
@@ -413,7 +413,6 @@ static u8 build_attr(struct vc_data *vc, u8 _color, u8 _intensity, u8 _blink, | |||
413 | return vc->vc_sw->con_build_attr(vc, _color, _intensity, | 413 | return vc->vc_sw->con_build_attr(vc, _color, _intensity, |
414 | _blink, _underline, _reverse, _italic); | 414 | _blink, _underline, _reverse, _italic); |
415 | 415 | ||
416 | #ifndef VT_BUF_VRAM_ONLY | ||
417 | /* | 416 | /* |
418 | * ++roman: I completely changed the attribute format for monochrome | 417 | * ++roman: I completely changed the attribute format for monochrome |
419 | * mode (!can_do_color). The formerly used MDA (monochrome display | 418 | * mode (!can_do_color). The formerly used MDA (monochrome display |
@@ -448,9 +447,6 @@ static u8 build_attr(struct vc_data *vc, u8 _color, u8 _intensity, u8 _blink, | |||
448 | a <<= 1; | 447 | a <<= 1; |
449 | return a; | 448 | return a; |
450 | } | 449 | } |
451 | #else | ||
452 | return 0; | ||
453 | #endif | ||
454 | } | 450 | } |
455 | 451 | ||
456 | static void update_attr(struct vc_data *vc) | 452 | static void update_attr(struct vc_data *vc) |
@@ -470,10 +466,9 @@ void invert_screen(struct vc_data *vc, int offset, int count, int viewed) | |||
470 | 466 | ||
471 | count /= 2; | 467 | count /= 2; |
472 | p = screenpos(vc, offset, viewed); | 468 | p = screenpos(vc, offset, viewed); |
473 | if (vc->vc_sw->con_invert_region) | 469 | if (vc->vc_sw->con_invert_region) { |
474 | vc->vc_sw->con_invert_region(vc, p, count); | 470 | vc->vc_sw->con_invert_region(vc, p, count); |
475 | #ifndef VT_BUF_VRAM_ONLY | 471 | } else { |
476 | else { | ||
477 | u16 *q = p; | 472 | u16 *q = p; |
478 | int cnt = count; | 473 | int cnt = count; |
479 | u16 a; | 474 | u16 a; |
@@ -501,8 +496,8 @@ void invert_screen(struct vc_data *vc, int offset, int count, int viewed) | |||
501 | } | 496 | } |
502 | } | 497 | } |
503 | } | 498 | } |
504 | #endif | 499 | |
505 | if (DO_UPDATE(vc)) | 500 | if (con_should_update(vc)) |
506 | do_update_region(vc, (unsigned long) p, count); | 501 | do_update_region(vc, (unsigned long) p, count); |
507 | notify_update(vc); | 502 | notify_update(vc); |
508 | } | 503 | } |
@@ -519,7 +514,7 @@ void complement_pos(struct vc_data *vc, int offset) | |||
519 | if (old_offset != -1 && old_offset >= 0 && | 514 | if (old_offset != -1 && old_offset >= 0 && |
520 | old_offset < vc->vc_screenbuf_size) { | 515 | old_offset < vc->vc_screenbuf_size) { |
521 | scr_writew(old, screenpos(vc, old_offset, 1)); | 516 | scr_writew(old, screenpos(vc, old_offset, 1)); |
522 | if (DO_UPDATE(vc)) | 517 | if (con_should_update(vc)) |
523 | vc->vc_sw->con_putc(vc, old, oldy, oldx); | 518 | vc->vc_sw->con_putc(vc, old, oldy, oldx); |
524 | notify_update(vc); | 519 | notify_update(vc); |
525 | } | 520 | } |
@@ -534,7 +529,7 @@ void complement_pos(struct vc_data *vc, int offset) | |||
534 | old = scr_readw(p); | 529 | old = scr_readw(p); |
535 | new = old ^ vc->vc_complement_mask; | 530 | new = old ^ vc->vc_complement_mask; |
536 | scr_writew(new, p); | 531 | scr_writew(new, p); |
537 | if (DO_UPDATE(vc)) { | 532 | if (con_should_update(vc)) { |
538 | oldx = (offset >> 1) % vc->vc_cols; | 533 | oldx = (offset >> 1) % vc->vc_cols; |
539 | oldy = (offset >> 1) / vc->vc_cols; | 534 | oldy = (offset >> 1) / vc->vc_cols; |
540 | vc->vc_sw->con_putc(vc, new, oldy, oldx); | 535 | vc->vc_sw->con_putc(vc, new, oldy, oldx); |
@@ -550,7 +545,7 @@ static void insert_char(struct vc_data *vc, unsigned int nr) | |||
550 | scr_memmovew(p + nr, p, (vc->vc_cols - vc->vc_x - nr) * 2); | 545 | scr_memmovew(p + nr, p, (vc->vc_cols - vc->vc_x - nr) * 2); |
551 | scr_memsetw(p, vc->vc_video_erase_char, nr * 2); | 546 | scr_memsetw(p, vc->vc_video_erase_char, nr * 2); |
552 | vc->vc_need_wrap = 0; | 547 | vc->vc_need_wrap = 0; |
553 | if (DO_UPDATE(vc)) | 548 | if (con_should_update(vc)) |
554 | do_update_region(vc, (unsigned long) p, | 549 | do_update_region(vc, (unsigned long) p, |
555 | vc->vc_cols - vc->vc_x); | 550 | vc->vc_cols - vc->vc_x); |
556 | } | 551 | } |
@@ -563,7 +558,7 @@ static void delete_char(struct vc_data *vc, unsigned int nr) | |||
563 | scr_memsetw(p + vc->vc_cols - vc->vc_x - nr, vc->vc_video_erase_char, | 558 | scr_memsetw(p + vc->vc_cols - vc->vc_x - nr, vc->vc_video_erase_char, |
564 | nr * 2); | 559 | nr * 2); |
565 | vc->vc_need_wrap = 0; | 560 | vc->vc_need_wrap = 0; |
566 | if (DO_UPDATE(vc)) | 561 | if (con_should_update(vc)) |
567 | do_update_region(vc, (unsigned long) p, | 562 | do_update_region(vc, (unsigned long) p, |
568 | vc->vc_cols - vc->vc_x); | 563 | vc->vc_cols - vc->vc_x); |
569 | } | 564 | } |
@@ -583,7 +578,7 @@ static void add_softcursor(struct vc_data *vc) | |||
583 | if ((type & 0x20) && ((softcursor_original & 0x7000) == (i & 0x7000))) i ^= 0x7000; | 578 | if ((type & 0x20) && ((softcursor_original & 0x7000) == (i & 0x7000))) i ^= 0x7000; |
584 | if ((type & 0x40) && ((i & 0x700) == ((i & 0x7000) >> 4))) i ^= 0x0700; | 579 | if ((type & 0x40) && ((i & 0x700) == ((i & 0x7000) >> 4))) i ^= 0x0700; |
585 | scr_writew(i, (u16 *) vc->vc_pos); | 580 | scr_writew(i, (u16 *) vc->vc_pos); |
586 | if (DO_UPDATE(vc)) | 581 | if (con_should_update(vc)) |
587 | vc->vc_sw->con_putc(vc, i, vc->vc_y, vc->vc_x); | 582 | vc->vc_sw->con_putc(vc, i, vc->vc_y, vc->vc_x); |
588 | } | 583 | } |
589 | 584 | ||
@@ -591,7 +586,7 @@ static void hide_softcursor(struct vc_data *vc) | |||
591 | { | 586 | { |
592 | if (softcursor_original != -1) { | 587 | if (softcursor_original != -1) { |
593 | scr_writew(softcursor_original, (u16 *)vc->vc_pos); | 588 | scr_writew(softcursor_original, (u16 *)vc->vc_pos); |
594 | if (DO_UPDATE(vc)) | 589 | if (con_should_update(vc)) |
595 | vc->vc_sw->con_putc(vc, softcursor_original, | 590 | vc->vc_sw->con_putc(vc, softcursor_original, |
596 | vc->vc_y, vc->vc_x); | 591 | vc->vc_y, vc->vc_x); |
597 | softcursor_original = -1; | 592 | softcursor_original = -1; |
@@ -608,8 +603,7 @@ static void hide_cursor(struct vc_data *vc) | |||
608 | 603 | ||
609 | static void set_cursor(struct vc_data *vc) | 604 | static void set_cursor(struct vc_data *vc) |
610 | { | 605 | { |
611 | if (!IS_FG(vc) || console_blanked || | 606 | if (!con_is_fg(vc) || console_blanked || vc->vc_mode == KD_GRAPHICS) |
612 | vc->vc_mode == KD_GRAPHICS) | ||
613 | return; | 607 | return; |
614 | if (vc->vc_deccm) { | 608 | if (vc->vc_deccm) { |
615 | if (vc == sel_cons) | 609 | if (vc == sel_cons) |
@@ -625,7 +619,7 @@ static void set_origin(struct vc_data *vc) | |||
625 | { | 619 | { |
626 | WARN_CONSOLE_UNLOCKED(); | 620 | WARN_CONSOLE_UNLOCKED(); |
627 | 621 | ||
628 | if (!CON_IS_VISIBLE(vc) || | 622 | if (!con_is_visible(vc) || |
629 | !vc->vc_sw->con_set_origin || | 623 | !vc->vc_sw->con_set_origin || |
630 | !vc->vc_sw->con_set_origin(vc)) | 624 | !vc->vc_sw->con_set_origin(vc)) |
631 | vc->vc_origin = (unsigned long)vc->vc_screenbuf; | 625 | vc->vc_origin = (unsigned long)vc->vc_screenbuf; |
@@ -673,12 +667,12 @@ void redraw_screen(struct vc_data *vc, int is_switch) | |||
673 | struct vc_data *old_vc = vc_cons[fg_console].d; | 667 | struct vc_data *old_vc = vc_cons[fg_console].d; |
674 | if (old_vc == vc) | 668 | if (old_vc == vc) |
675 | return; | 669 | return; |
676 | if (!CON_IS_VISIBLE(vc)) | 670 | if (!con_is_visible(vc)) |
677 | redraw = 1; | 671 | redraw = 1; |
678 | *vc->vc_display_fg = vc; | 672 | *vc->vc_display_fg = vc; |
679 | fg_console = vc->vc_num; | 673 | fg_console = vc->vc_num; |
680 | hide_cursor(old_vc); | 674 | hide_cursor(old_vc); |
681 | if (!CON_IS_VISIBLE(old_vc)) { | 675 | if (!con_is_visible(old_vc)) { |
682 | save_screen(old_vc); | 676 | save_screen(old_vc); |
683 | set_origin(old_vc); | 677 | set_origin(old_vc); |
684 | } | 678 | } |
@@ -954,7 +948,7 @@ static int vc_do_resize(struct tty_struct *tty, struct vc_data *vc, | |||
954 | tty_do_resize(tty, &ws); | 948 | tty_do_resize(tty, &ws); |
955 | } | 949 | } |
956 | 950 | ||
957 | if (CON_IS_VISIBLE(vc)) | 951 | if (con_is_visible(vc)) |
958 | update_screen(vc); | 952 | update_screen(vc); |
959 | vt_event_post(VT_EVENT_RESIZE, vc->vc_num, vc->vc_num); | 953 | vt_event_post(VT_EVENT_RESIZE, vc->vc_num, vc->vc_num); |
960 | return err; | 954 | return err; |
@@ -1103,11 +1097,9 @@ static void gotoxay(struct vc_data *vc, int new_x, int new_y) | |||
1103 | gotoxy(vc, new_x, vc->vc_decom ? (vc->vc_top + new_y) : new_y); | 1097 | gotoxy(vc, new_x, vc->vc_decom ? (vc->vc_top + new_y) : new_y); |
1104 | } | 1098 | } |
1105 | 1099 | ||
1106 | void scrollback(struct vc_data *vc, int lines) | 1100 | void scrollback(struct vc_data *vc) |
1107 | { | 1101 | { |
1108 | if (!lines) | 1102 | scrolldelta(-(vc->vc_rows / 2)); |
1109 | lines = vc->vc_rows / 2; | ||
1110 | scrolldelta(-lines); | ||
1111 | } | 1103 | } |
1112 | 1104 | ||
1113 | void scrollfront(struct vc_data *vc, int lines) | 1105 | void scrollfront(struct vc_data *vc, int lines) |
@@ -1186,7 +1178,7 @@ static void csi_J(struct vc_data *vc, int vpar) | |||
1186 | scr_memsetw(vc->vc_screenbuf, vc->vc_video_erase_char, | 1178 | scr_memsetw(vc->vc_screenbuf, vc->vc_video_erase_char, |
1187 | vc->vc_screenbuf_size >> 1); | 1179 | vc->vc_screenbuf_size >> 1); |
1188 | set_origin(vc); | 1180 | set_origin(vc); |
1189 | if (CON_IS_VISIBLE(vc)) | 1181 | if (con_is_visible(vc)) |
1190 | update_screen(vc); | 1182 | update_screen(vc); |
1191 | /* fall through */ | 1183 | /* fall through */ |
1192 | case 2: /* erase whole display */ | 1184 | case 2: /* erase whole display */ |
@@ -1197,7 +1189,7 @@ static void csi_J(struct vc_data *vc, int vpar) | |||
1197 | return; | 1189 | return; |
1198 | } | 1190 | } |
1199 | scr_memsetw(start, vc->vc_video_erase_char, 2 * count); | 1191 | scr_memsetw(start, vc->vc_video_erase_char, 2 * count); |
1200 | if (DO_UPDATE(vc)) | 1192 | if (con_should_update(vc)) |
1201 | do_update_region(vc, (unsigned long) start, count); | 1193 | do_update_region(vc, (unsigned long) start, count); |
1202 | vc->vc_need_wrap = 0; | 1194 | vc->vc_need_wrap = 0; |
1203 | } | 1195 | } |
@@ -1225,7 +1217,7 @@ static void csi_K(struct vc_data *vc, int vpar) | |||
1225 | } | 1217 | } |
1226 | scr_memsetw(start, vc->vc_video_erase_char, 2 * count); | 1218 | scr_memsetw(start, vc->vc_video_erase_char, 2 * count); |
1227 | vc->vc_need_wrap = 0; | 1219 | vc->vc_need_wrap = 0; |
1228 | if (DO_UPDATE(vc)) | 1220 | if (con_should_update(vc)) |
1229 | do_update_region(vc, (unsigned long) start, count); | 1221 | do_update_region(vc, (unsigned long) start, count); |
1230 | } | 1222 | } |
1231 | 1223 | ||
@@ -1238,7 +1230,7 @@ static void csi_X(struct vc_data *vc, int vpar) /* erase the following vpar posi | |||
1238 | count = (vpar > vc->vc_cols - vc->vc_x) ? (vc->vc_cols - vc->vc_x) : vpar; | 1230 | count = (vpar > vc->vc_cols - vc->vc_x) ? (vc->vc_cols - vc->vc_x) : vpar; |
1239 | 1231 | ||
1240 | scr_memsetw((unsigned short *)vc->vc_pos, vc->vc_video_erase_char, 2 * count); | 1232 | scr_memsetw((unsigned short *)vc->vc_pos, vc->vc_video_erase_char, 2 * count); |
1241 | if (DO_UPDATE(vc)) | 1233 | if (con_should_update(vc)) |
1242 | vc->vc_sw->con_clear(vc, vc->vc_y, vc->vc_x, 1, count); | 1234 | vc->vc_sw->con_clear(vc, vc->vc_y, vc->vc_x, 1, count); |
1243 | vc->vc_need_wrap = 0; | 1235 | vc->vc_need_wrap = 0; |
1244 | } | 1236 | } |
@@ -1255,48 +1247,87 @@ static void default_attr(struct vc_data *vc) | |||
1255 | 1247 | ||
1256 | struct rgb { u8 r; u8 g; u8 b; }; | 1248 | struct rgb { u8 r; u8 g; u8 b; }; |
1257 | 1249 | ||
1258 | static struct rgb rgb_from_256(int i) | 1250 | static void rgb_from_256(int i, struct rgb *c) |
1259 | { | 1251 | { |
1260 | struct rgb c; | ||
1261 | if (i < 8) { /* Standard colours. */ | 1252 | if (i < 8) { /* Standard colours. */ |
1262 | c.r = i&1 ? 0xaa : 0x00; | 1253 | c->r = i&1 ? 0xaa : 0x00; |
1263 | c.g = i&2 ? 0xaa : 0x00; | 1254 | c->g = i&2 ? 0xaa : 0x00; |
1264 | c.b = i&4 ? 0xaa : 0x00; | 1255 | c->b = i&4 ? 0xaa : 0x00; |
1265 | } else if (i < 16) { | 1256 | } else if (i < 16) { |
1266 | c.r = i&1 ? 0xff : 0x55; | 1257 | c->r = i&1 ? 0xff : 0x55; |
1267 | c.g = i&2 ? 0xff : 0x55; | 1258 | c->g = i&2 ? 0xff : 0x55; |
1268 | c.b = i&4 ? 0xff : 0x55; | 1259 | c->b = i&4 ? 0xff : 0x55; |
1269 | } else if (i < 232) { /* 6x6x6 colour cube. */ | 1260 | } else if (i < 232) { /* 6x6x6 colour cube. */ |
1270 | c.r = (i - 16) / 36 * 85 / 2; | 1261 | c->r = (i - 16) / 36 * 85 / 2; |
1271 | c.g = (i - 16) / 6 % 6 * 85 / 2; | 1262 | c->g = (i - 16) / 6 % 6 * 85 / 2; |
1272 | c.b = (i - 16) % 6 * 85 / 2; | 1263 | c->b = (i - 16) % 6 * 85 / 2; |
1273 | } else /* Grayscale ramp. */ | 1264 | } else /* Grayscale ramp. */ |
1274 | c.r = c.g = c.b = i * 10 - 2312; | 1265 | c->r = c->g = c->b = i * 10 - 2312; |
1275 | return c; | ||
1276 | } | 1266 | } |
1277 | 1267 | ||
1278 | static void rgb_foreground(struct vc_data *vc, struct rgb c) | 1268 | static void rgb_foreground(struct vc_data *vc, const struct rgb *c) |
1279 | { | 1269 | { |
1280 | u8 hue, max = c.r; | 1270 | u8 hue = 0, max = max3(c->r, c->g, c->b); |
1281 | if (c.g > max) | 1271 | |
1282 | max = c.g; | 1272 | if (c->r > max / 2) |
1283 | if (c.b > max) | 1273 | hue |= 4; |
1284 | max = c.b; | 1274 | if (c->g > max / 2) |
1285 | hue = (c.r > max/2 ? 4 : 0) | 1275 | hue |= 2; |
1286 | | (c.g > max/2 ? 2 : 0) | 1276 | if (c->b > max / 2) |
1287 | | (c.b > max/2 ? 1 : 0); | 1277 | hue |= 1; |
1288 | if (hue == 7 && max <= 0x55) | 1278 | |
1289 | hue = 0, vc->vc_intensity = 2; | 1279 | if (hue == 7 && max <= 0x55) { |
1280 | hue = 0; | ||
1281 | vc->vc_intensity = 2; | ||
1282 | } else if (max > 0xaa) | ||
1283 | vc->vc_intensity = 2; | ||
1290 | else | 1284 | else |
1291 | vc->vc_intensity = (max > 0xaa) + 1; | 1285 | vc->vc_intensity = 1; |
1286 | |||
1292 | vc->vc_color = (vc->vc_color & 0xf0) | hue; | 1287 | vc->vc_color = (vc->vc_color & 0xf0) | hue; |
1293 | } | 1288 | } |
1294 | 1289 | ||
1295 | static void rgb_background(struct vc_data *vc, struct rgb c) | 1290 | static void rgb_background(struct vc_data *vc, const struct rgb *c) |
1296 | { | 1291 | { |
1297 | /* For backgrounds, err on the dark side. */ | 1292 | /* For backgrounds, err on the dark side. */ |
1298 | vc->vc_color = (vc->vc_color & 0x0f) | 1293 | vc->vc_color = (vc->vc_color & 0x0f) |
1299 | | (c.r&0x80) >> 1 | (c.g&0x80) >> 2 | (c.b&0x80) >> 3; | 1294 | | (c->r&0x80) >> 1 | (c->g&0x80) >> 2 | (c->b&0x80) >> 3; |
1295 | } | ||
1296 | |||
1297 | /* | ||
1298 | * ITU T.416 Higher colour modes. They break the usual properties of SGR codes | ||
1299 | * and thus need to be detected and ignored by hand. Strictly speaking, that | ||
1300 | * standard also wants : rather than ; as separators, contrary to ECMA-48, but | ||
1301 | * no one produces such codes and almost no one accepts them. | ||
1302 | * | ||
1303 | * Subcommands 3 (CMY) and 4 (CMYK) are so insane there's no point in | ||
1304 | * supporting them. | ||
1305 | */ | ||
1306 | static int vc_t416_color(struct vc_data *vc, int i, | ||
1307 | void(*set_color)(struct vc_data *vc, const struct rgb *c)) | ||
1308 | { | ||
1309 | struct rgb c; | ||
1310 | |||
1311 | i++; | ||
1312 | if (i > vc->vc_npar) | ||
1313 | return i; | ||
1314 | |||
1315 | if (vc->vc_par[i] == 5 && i < vc->vc_npar) { | ||
1316 | /* 256 colours -- ubiquitous */ | ||
1317 | i++; | ||
1318 | rgb_from_256(vc->vc_par[i], &c); | ||
1319 | } else if (vc->vc_par[i] == 2 && i <= vc->vc_npar + 3) { | ||
1320 | /* 24 bit -- extremely rare */ | ||
1321 | c.r = vc->vc_par[i + 1]; | ||
1322 | c.g = vc->vc_par[i + 2]; | ||
1323 | c.b = vc->vc_par[i + 3]; | ||
1324 | i += 3; | ||
1325 | } else | ||
1326 | return i; | ||
1327 | |||
1328 | set_color(vc, &c); | ||
1329 | |||
1330 | return i; | ||
1300 | } | 1331 | } |
1301 | 1332 | ||
1302 | /* console_lock is held */ | 1333 | /* console_lock is held */ |
@@ -1306,135 +1337,91 @@ static void csi_m(struct vc_data *vc) | |||
1306 | 1337 | ||
1307 | for (i = 0; i <= vc->vc_npar; i++) | 1338 | for (i = 0; i <= vc->vc_npar; i++) |
1308 | switch (vc->vc_par[i]) { | 1339 | switch (vc->vc_par[i]) { |
1309 | case 0: /* all attributes off */ | 1340 | case 0: /* all attributes off */ |
1310 | default_attr(vc); | 1341 | default_attr(vc); |
1311 | break; | 1342 | break; |
1312 | case 1: | 1343 | case 1: |
1313 | vc->vc_intensity = 2; | 1344 | vc->vc_intensity = 2; |
1314 | break; | 1345 | break; |
1315 | case 2: | 1346 | case 2: |
1316 | vc->vc_intensity = 0; | 1347 | vc->vc_intensity = 0; |
1317 | break; | 1348 | break; |
1318 | case 3: | 1349 | case 3: |
1319 | vc->vc_italic = 1; | 1350 | vc->vc_italic = 1; |
1320 | break; | 1351 | break; |
1321 | case 4: | 1352 | case 4: |
1322 | vc->vc_underline = 1; | 1353 | vc->vc_underline = 1; |
1323 | break; | 1354 | break; |
1324 | case 5: | 1355 | case 5: |
1325 | vc->vc_blink = 1; | 1356 | vc->vc_blink = 1; |
1326 | break; | 1357 | break; |
1327 | case 7: | 1358 | case 7: |
1328 | vc->vc_reverse = 1; | 1359 | vc->vc_reverse = 1; |
1329 | break; | 1360 | break; |
1330 | case 10: /* ANSI X3.64-1979 (SCO-ish?) | 1361 | case 10: /* ANSI X3.64-1979 (SCO-ish?) |
1331 | * Select primary font, don't display | 1362 | * Select primary font, don't display control chars if |
1332 | * control chars if defined, don't set | 1363 | * defined, don't set bit 8 on output. |
1333 | * bit 8 on output. | 1364 | */ |
1334 | */ | 1365 | vc->vc_translate = set_translate(vc->vc_charset == 0 |
1335 | vc->vc_translate = set_translate(vc->vc_charset == 0 | 1366 | ? vc->vc_G0_charset |
1336 | ? vc->vc_G0_charset | 1367 | : vc->vc_G1_charset, vc); |
1337 | : vc->vc_G1_charset, vc); | 1368 | vc->vc_disp_ctrl = 0; |
1338 | vc->vc_disp_ctrl = 0; | 1369 | vc->vc_toggle_meta = 0; |
1339 | vc->vc_toggle_meta = 0; | 1370 | break; |
1340 | break; | 1371 | case 11: /* ANSI X3.64-1979 (SCO-ish?) |
1341 | case 11: /* ANSI X3.64-1979 (SCO-ish?) | 1372 | * Select first alternate font, lets chars < 32 be |
1342 | * Select first alternate font, lets | 1373 | * displayed as ROM chars. |
1343 | * chars < 32 be displayed as ROM chars. | 1374 | */ |
1344 | */ | 1375 | vc->vc_translate = set_translate(IBMPC_MAP, vc); |
1345 | vc->vc_translate = set_translate(IBMPC_MAP, vc); | 1376 | vc->vc_disp_ctrl = 1; |
1346 | vc->vc_disp_ctrl = 1; | 1377 | vc->vc_toggle_meta = 0; |
1347 | vc->vc_toggle_meta = 0; | 1378 | break; |
1348 | break; | 1379 | case 12: /* ANSI X3.64-1979 (SCO-ish?) |
1349 | case 12: /* ANSI X3.64-1979 (SCO-ish?) | 1380 | * Select second alternate font, toggle high bit |
1350 | * Select second alternate font, toggle | 1381 | * before displaying as ROM char. |
1351 | * high bit before displaying as ROM char. | 1382 | */ |
1352 | */ | 1383 | vc->vc_translate = set_translate(IBMPC_MAP, vc); |
1353 | vc->vc_translate = set_translate(IBMPC_MAP, vc); | 1384 | vc->vc_disp_ctrl = 1; |
1354 | vc->vc_disp_ctrl = 1; | 1385 | vc->vc_toggle_meta = 1; |
1355 | vc->vc_toggle_meta = 1; | 1386 | break; |
1356 | break; | 1387 | case 21: |
1357 | case 21: | 1388 | case 22: |
1358 | case 22: | 1389 | vc->vc_intensity = 1; |
1359 | vc->vc_intensity = 1; | 1390 | break; |
1360 | break; | 1391 | case 23: |
1361 | case 23: | 1392 | vc->vc_italic = 0; |
1362 | vc->vc_italic = 0; | 1393 | break; |
1363 | break; | 1394 | case 24: |
1364 | case 24: | 1395 | vc->vc_underline = 0; |
1365 | vc->vc_underline = 0; | 1396 | break; |
1366 | break; | 1397 | case 25: |
1367 | case 25: | 1398 | vc->vc_blink = 0; |
1368 | vc->vc_blink = 0; | 1399 | break; |
1369 | break; | 1400 | case 27: |
1370 | case 27: | 1401 | vc->vc_reverse = 0; |
1371 | vc->vc_reverse = 0; | 1402 | break; |
1372 | break; | 1403 | case 38: |
1373 | case 38: /* ITU T.416 | 1404 | i = vc_t416_color(vc, i, rgb_foreground); |
1374 | * Higher colour modes. | 1405 | break; |
1375 | * They break the usual properties of SGR codes | 1406 | case 48: |
1376 | * and thus need to be detected and ignored by | 1407 | i = vc_t416_color(vc, i, rgb_background); |
1377 | * hand. Strictly speaking, that standard also | 1408 | break; |
1378 | * wants : rather than ; as separators, contrary | 1409 | case 39: |
1379 | * to ECMA-48, but no one produces such codes | 1410 | vc->vc_color = (vc->vc_def_color & 0x0f) | |
1380 | * and almost no one accepts them. | 1411 | (vc->vc_color & 0xf0); |
1381 | */ | 1412 | break; |
1382 | i++; | 1413 | case 49: |
1383 | if (i > vc->vc_npar) | 1414 | vc->vc_color = (vc->vc_def_color & 0xf0) | |
1384 | break; | 1415 | (vc->vc_color & 0x0f); |
1385 | if (vc->vc_par[i] == 5 && /* 256 colours */ | 1416 | break; |
1386 | i < vc->vc_npar) { /* ubiquitous */ | 1417 | default: |
1387 | i++; | 1418 | if (vc->vc_par[i] >= 30 && vc->vc_par[i] <= 37) |
1388 | rgb_foreground(vc, | 1419 | vc->vc_color = color_table[vc->vc_par[i] - 30] |
1389 | rgb_from_256(vc->vc_par[i])); | 1420 | | (vc->vc_color & 0xf0); |
1390 | } else if (vc->vc_par[i] == 2 && /* 24 bit */ | 1421 | else if (vc->vc_par[i] >= 40 && vc->vc_par[i] <= 47) |
1391 | i <= vc->vc_npar + 3) {/* extremely rare */ | 1422 | vc->vc_color = (color_table[vc->vc_par[i] - 40] << 4) |
1392 | struct rgb c = { | 1423 | | (vc->vc_color & 0x0f); |
1393 | .r = vc->vc_par[i + 1], | 1424 | break; |
1394 | .g = vc->vc_par[i + 2], | ||
1395 | .b = vc->vc_par[i + 3], | ||
1396 | }; | ||
1397 | rgb_foreground(vc, c); | ||
1398 | i += 3; | ||
1399 | } | ||
1400 | /* Subcommands 3 (CMY) and 4 (CMYK) are so insane | ||
1401 | * there's no point in supporting them. | ||
1402 | */ | ||
1403 | break; | ||
1404 | case 48: | ||
1405 | i++; | ||
1406 | if (i > vc->vc_npar) | ||
1407 | break; | ||
1408 | if (vc->vc_par[i] == 5 && /* 256 colours */ | ||
1409 | i < vc->vc_npar) { | ||
1410 | i++; | ||
1411 | rgb_background(vc, | ||
1412 | rgb_from_256(vc->vc_par[i])); | ||
1413 | } else if (vc->vc_par[i] == 2 && /* 24 bit */ | ||
1414 | i <= vc->vc_npar + 3) { | ||
1415 | struct rgb c = { | ||
1416 | .r = vc->vc_par[i + 1], | ||
1417 | .g = vc->vc_par[i + 2], | ||
1418 | .b = vc->vc_par[i + 3], | ||
1419 | }; | ||
1420 | rgb_background(vc, c); | ||
1421 | i += 3; | ||
1422 | } | ||
1423 | break; | ||
1424 | case 39: | ||
1425 | vc->vc_color = (vc->vc_def_color & 0x0f) | (vc->vc_color & 0xf0); | ||
1426 | break; | ||
1427 | case 49: | ||
1428 | vc->vc_color = (vc->vc_def_color & 0xf0) | (vc->vc_color & 0x0f); | ||
1429 | break; | ||
1430 | default: | ||
1431 | if (vc->vc_par[i] >= 30 && vc->vc_par[i] <= 37) | ||
1432 | vc->vc_color = color_table[vc->vc_par[i] - 30] | ||
1433 | | (vc->vc_color & 0xf0); | ||
1434 | else if (vc->vc_par[i] >= 40 && vc->vc_par[i] <= 47) | ||
1435 | vc->vc_color = (color_table[vc->vc_par[i] - 40] << 4) | ||
1436 | | (vc->vc_color & 0x0f); | ||
1437 | break; | ||
1438 | } | 1425 | } |
1439 | update_attr(vc); | 1426 | update_attr(vc); |
1440 | } | 1427 | } |
@@ -1496,7 +1483,6 @@ static void set_mode(struct vc_data *vc, int on_off) | |||
1496 | clr_kbd(vc, decckm); | 1483 | clr_kbd(vc, decckm); |
1497 | break; | 1484 | break; |
1498 | case 3: /* 80/132 mode switch unimplemented */ | 1485 | case 3: /* 80/132 mode switch unimplemented */ |
1499 | vc->vc_deccolm = on_off; | ||
1500 | #if 0 | 1486 | #if 0 |
1501 | vc_resize(deccolm ? 132 : 80, vc->vc_rows); | 1487 | vc_resize(deccolm ? 132 : 80, vc->vc_rows); |
1502 | /* this alone does not suffice; some user mode | 1488 | /* this alone does not suffice; some user mode |
@@ -2178,18 +2164,20 @@ static int is_double_width(uint32_t ucs) | |||
2178 | return bisearch(ucs, double_width, ARRAY_SIZE(double_width) - 1); | 2164 | return bisearch(ucs, double_width, ARRAY_SIZE(double_width) - 1); |
2179 | } | 2165 | } |
2180 | 2166 | ||
2167 | static void con_flush(struct vc_data *vc, unsigned long draw_from, | ||
2168 | unsigned long draw_to, int *draw_x) | ||
2169 | { | ||
2170 | if (*draw_x < 0) | ||
2171 | return; | ||
2172 | |||
2173 | vc->vc_sw->con_putcs(vc, (u16 *)draw_from, | ||
2174 | (u16 *)draw_to - (u16 *)draw_from, vc->vc_y, *draw_x); | ||
2175 | *draw_x = -1; | ||
2176 | } | ||
2177 | |||
2181 | /* acquires console_lock */ | 2178 | /* acquires console_lock */ |
2182 | static int do_con_write(struct tty_struct *tty, const unsigned char *buf, int count) | 2179 | static int do_con_write(struct tty_struct *tty, const unsigned char *buf, int count) |
2183 | { | 2180 | { |
2184 | #ifdef VT_BUF_VRAM_ONLY | ||
2185 | #define FLUSH do { } while(0); | ||
2186 | #else | ||
2187 | #define FLUSH if (draw_x >= 0) { \ | ||
2188 | vc->vc_sw->con_putcs(vc, (u16 *)draw_from, (u16 *)draw_to - (u16 *)draw_from, vc->vc_y, draw_x); \ | ||
2189 | draw_x = -1; \ | ||
2190 | } | ||
2191 | #endif | ||
2192 | |||
2193 | int c, tc, ok, n = 0, draw_x = -1; | 2181 | int c, tc, ok, n = 0, draw_x = -1; |
2194 | unsigned int currcons; | 2182 | unsigned int currcons; |
2195 | unsigned long draw_from = 0, draw_to = 0; | 2183 | unsigned long draw_from = 0, draw_to = 0; |
@@ -2226,7 +2214,7 @@ static int do_con_write(struct tty_struct *tty, const unsigned char *buf, int co | |||
2226 | charmask = himask ? 0x1ff : 0xff; | 2214 | charmask = himask ? 0x1ff : 0xff; |
2227 | 2215 | ||
2228 | /* undraw cursor first */ | 2216 | /* undraw cursor first */ |
2229 | if (IS_FG(vc)) | 2217 | if (con_is_fg(vc)) |
2230 | hide_cursor(vc); | 2218 | hide_cursor(vc); |
2231 | 2219 | ||
2232 | param.vc = vc; | 2220 | param.vc = vc; |
@@ -2381,12 +2369,13 @@ rescan_last_byte: | |||
2381 | } else { | 2369 | } else { |
2382 | vc_attr = ((vc->vc_attr) & 0x88) | (((vc->vc_attr) & 0x70) >> 4) | (((vc->vc_attr) & 0x07) << 4); | 2370 | vc_attr = ((vc->vc_attr) & 0x88) | (((vc->vc_attr) & 0x70) >> 4) | (((vc->vc_attr) & 0x07) << 4); |
2383 | } | 2371 | } |
2384 | FLUSH | 2372 | con_flush(vc, draw_from, draw_to, &draw_x); |
2385 | } | 2373 | } |
2386 | 2374 | ||
2387 | while (1) { | 2375 | while (1) { |
2388 | if (vc->vc_need_wrap || vc->vc_decim) | 2376 | if (vc->vc_need_wrap || vc->vc_decim) |
2389 | FLUSH | 2377 | con_flush(vc, draw_from, draw_to, |
2378 | &draw_x); | ||
2390 | if (vc->vc_need_wrap) { | 2379 | if (vc->vc_need_wrap) { |
2391 | cr(vc); | 2380 | cr(vc); |
2392 | lf(vc); | 2381 | lf(vc); |
@@ -2397,7 +2386,7 @@ rescan_last_byte: | |||
2397 | ((vc_attr << 8) & ~himask) + ((tc & 0x100) ? himask : 0) + (tc & 0xff) : | 2386 | ((vc_attr << 8) & ~himask) + ((tc & 0x100) ? himask : 0) + (tc & 0xff) : |
2398 | (vc_attr << 8) + tc, | 2387 | (vc_attr << 8) + tc, |
2399 | (u16 *) vc->vc_pos); | 2388 | (u16 *) vc->vc_pos); |
2400 | if (DO_UPDATE(vc) && draw_x < 0) { | 2389 | if (con_should_update(vc) && draw_x < 0) { |
2401 | draw_x = vc->vc_x; | 2390 | draw_x = vc->vc_x; |
2402 | draw_from = vc->vc_pos; | 2391 | draw_from = vc->vc_pos; |
2403 | } | 2392 | } |
@@ -2416,9 +2405,8 @@ rescan_last_byte: | |||
2416 | } | 2405 | } |
2417 | notify_write(vc, c); | 2406 | notify_write(vc, c); |
2418 | 2407 | ||
2419 | if (inverse) { | 2408 | if (inverse) |
2420 | FLUSH | 2409 | con_flush(vc, draw_from, draw_to, &draw_x); |
2421 | } | ||
2422 | 2410 | ||
2423 | if (rescan) { | 2411 | if (rescan) { |
2424 | rescan = 0; | 2412 | rescan = 0; |
@@ -2429,15 +2417,14 @@ rescan_last_byte: | |||
2429 | } | 2417 | } |
2430 | continue; | 2418 | continue; |
2431 | } | 2419 | } |
2432 | FLUSH | 2420 | con_flush(vc, draw_from, draw_to, &draw_x); |
2433 | do_con_trol(tty, vc, orig); | 2421 | do_con_trol(tty, vc, orig); |
2434 | } | 2422 | } |
2435 | FLUSH | 2423 | con_flush(vc, draw_from, draw_to, &draw_x); |
2436 | console_conditional_schedule(); | 2424 | console_conditional_schedule(); |
2437 | console_unlock(); | 2425 | console_unlock(); |
2438 | notify_update(vc); | 2426 | notify_update(vc); |
2439 | return n; | 2427 | return n; |
2440 | #undef FLUSH | ||
2441 | } | 2428 | } |
2442 | 2429 | ||
2443 | /* | 2430 | /* |
@@ -2471,7 +2458,7 @@ static void console_callback(struct work_struct *ignored) | |||
2471 | if (scrollback_delta) { | 2458 | if (scrollback_delta) { |
2472 | struct vc_data *vc = vc_cons[fg_console].d; | 2459 | struct vc_data *vc = vc_cons[fg_console].d; |
2473 | clear_selection(); | 2460 | clear_selection(); |
2474 | if (vc->vc_mode == KD_TEXT) | 2461 | if (vc->vc_mode == KD_TEXT && vc->vc_sw->con_scrolldelta) |
2475 | vc->vc_sw->con_scrolldelta(vc, scrollback_delta); | 2462 | vc->vc_sw->con_scrolldelta(vc, scrollback_delta); |
2476 | scrollback_delta = 0; | 2463 | scrollback_delta = 0; |
2477 | } | 2464 | } |
@@ -2583,7 +2570,7 @@ static void vt_console_print(struct console *co, const char *b, unsigned count) | |||
2583 | goto quit; | 2570 | goto quit; |
2584 | 2571 | ||
2585 | /* undraw cursor first */ | 2572 | /* undraw cursor first */ |
2586 | if (IS_FG(vc)) | 2573 | if (con_is_fg(vc)) |
2587 | hide_cursor(vc); | 2574 | hide_cursor(vc); |
2588 | 2575 | ||
2589 | start = (ushort *)vc->vc_pos; | 2576 | start = (ushort *)vc->vc_pos; |
@@ -2594,7 +2581,7 @@ static void vt_console_print(struct console *co, const char *b, unsigned count) | |||
2594 | c = *b++; | 2581 | c = *b++; |
2595 | if (c == 10 || c == 13 || c == 8 || vc->vc_need_wrap) { | 2582 | if (c == 10 || c == 13 || c == 8 || vc->vc_need_wrap) { |
2596 | if (cnt > 0) { | 2583 | if (cnt > 0) { |
2597 | if (CON_IS_VISIBLE(vc)) | 2584 | if (con_is_visible(vc)) |
2598 | vc->vc_sw->con_putcs(vc, start, cnt, vc->vc_y, vc->vc_x); | 2585 | vc->vc_sw->con_putcs(vc, start, cnt, vc->vc_y, vc->vc_x); |
2599 | vc->vc_x += cnt; | 2586 | vc->vc_x += cnt; |
2600 | if (vc->vc_need_wrap) | 2587 | if (vc->vc_need_wrap) |
@@ -2626,7 +2613,7 @@ static void vt_console_print(struct console *co, const char *b, unsigned count) | |||
2626 | myx++; | 2613 | myx++; |
2627 | } | 2614 | } |
2628 | if (cnt > 0) { | 2615 | if (cnt > 0) { |
2629 | if (CON_IS_VISIBLE(vc)) | 2616 | if (con_is_visible(vc)) |
2630 | vc->vc_sw->con_putcs(vc, start, cnt, vc->vc_y, vc->vc_x); | 2617 | vc->vc_sw->con_putcs(vc, start, cnt, vc->vc_y, vc->vc_x); |
2631 | vc->vc_x += cnt; | 2618 | vc->vc_x += cnt; |
2632 | if (vc->vc_x == vc->vc_cols) { | 2619 | if (vc->vc_x == vc->vc_cols) { |
@@ -3173,7 +3160,7 @@ static int do_bind_con_driver(const struct consw *csw, int first, int last, | |||
3173 | 3160 | ||
3174 | j = i; | 3161 | j = i; |
3175 | 3162 | ||
3176 | if (CON_IS_VISIBLE(vc)) { | 3163 | if (con_is_visible(vc)) { |
3177 | k = i; | 3164 | k = i; |
3178 | save_screen(vc); | 3165 | save_screen(vc); |
3179 | } | 3166 | } |
@@ -3981,7 +3968,7 @@ static void set_palette(struct vc_data *vc) | |||
3981 | { | 3968 | { |
3982 | WARN_CONSOLE_UNLOCKED(); | 3969 | WARN_CONSOLE_UNLOCKED(); |
3983 | 3970 | ||
3984 | if (vc->vc_mode != KD_GRAPHICS) | 3971 | if (vc->vc_mode != KD_GRAPHICS && vc->vc_sw->con_set_palette) |
3985 | vc->vc_sw->con_set_palette(vc, color_table); | 3972 | vc->vc_sw->con_set_palette(vc, color_table); |
3986 | } | 3973 | } |
3987 | 3974 | ||
diff --git a/drivers/tty/vt/vt_ioctl.c b/drivers/tty/vt/vt_ioctl.c index 97d5a74558a3..f62c598810ff 100644 --- a/drivers/tty/vt/vt_ioctl.c +++ b/drivers/tty/vt/vt_ioctl.c | |||
@@ -1006,16 +1006,10 @@ int vt_ioctl(struct tty_struct *tty, | |||
1006 | break; | 1006 | break; |
1007 | 1007 | ||
1008 | case PIO_UNIMAPCLR: | 1008 | case PIO_UNIMAPCLR: |
1009 | { struct unimapinit ui; | ||
1010 | if (!perm) | 1009 | if (!perm) |
1011 | return -EPERM; | 1010 | return -EPERM; |
1012 | ret = copy_from_user(&ui, up, sizeof(struct unimapinit)); | 1011 | con_clear_unimap(vc); |
1013 | if (ret) | ||
1014 | ret = -EFAULT; | ||
1015 | else | ||
1016 | con_clear_unimap(vc, &ui); | ||
1017 | break; | 1012 | break; |
1018 | } | ||
1019 | 1013 | ||
1020 | case PIO_UNIMAP: | 1014 | case PIO_UNIMAP: |
1021 | case GIO_UNIMAP: | 1015 | case GIO_UNIMAP: |