Commit 64f5a135a7fee4e95efa08861698373b30a23bb0
1 parent
a817d936
signed fixes - VNC console switch (initial patch by Andrzej Zaborowski)
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@2137 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
1 changed file
with
94 additions
and
11 deletions
vnc.c
... | ... | @@ -81,6 +81,8 @@ struct VncState |
81 | 81 | |
82 | 82 | VncReadEvent *read_handler; |
83 | 83 | size_t read_handler_expect; |
84 | + /* input */ | |
85 | + uint8_t modifiers_state[256]; | |
84 | 86 | }; |
85 | 87 | |
86 | 88 | /* TODO |
... | ... | @@ -622,7 +624,7 @@ static void vnc_write_u32(VncState *vs, uint32_t value) |
622 | 624 | |
623 | 625 | static void vnc_write_u16(VncState *vs, uint16_t value) |
624 | 626 | { |
625 | - char buf[2]; | |
627 | + uint8_t buf[2]; | |
626 | 628 | |
627 | 629 | buf[0] = (value >> 8) & 0xFF; |
628 | 630 | buf[1] = value & 0xFF; |
... | ... | @@ -641,23 +643,23 @@ static void vnc_flush(VncState *vs) |
641 | 643 | vnc_client_write(vs); |
642 | 644 | } |
643 | 645 | |
644 | -static uint8_t read_u8(char *data, size_t offset) | |
646 | +static uint8_t read_u8(uint8_t *data, size_t offset) | |
645 | 647 | { |
646 | 648 | return data[offset]; |
647 | 649 | } |
648 | 650 | |
649 | -static uint16_t read_u16(char *data, size_t offset) | |
651 | +static uint16_t read_u16(uint8_t *data, size_t offset) | |
650 | 652 | { |
651 | 653 | return ((data[offset] & 0xFF) << 8) | (data[offset + 1] & 0xFF); |
652 | 654 | } |
653 | 655 | |
654 | -static int32_t read_s32(char *data, size_t offset) | |
656 | +static int32_t read_s32(uint8_t *data, size_t offset) | |
655 | 657 | { |
656 | 658 | return (int32_t)((data[offset] << 24) | (data[offset + 1] << 16) | |
657 | 659 | (data[offset + 2] << 8) | data[offset + 3]); |
658 | 660 | } |
659 | 661 | |
660 | -static uint32_t read_u32(char *data, size_t offset) | |
662 | +static uint32_t read_u32(uint8_t *data, size_t offset) | |
661 | 663 | { |
662 | 664 | return ((data[offset] << 24) | (data[offset + 1] << 16) | |
663 | 665 | (data[offset + 2] << 8) | data[offset + 3]); |
... | ... | @@ -699,18 +701,99 @@ static void pointer_event(VncState *vs, int button_mask, int x, int y) |
699 | 701 | } |
700 | 702 | } |
701 | 703 | |
704 | +static void reset_keys(VncState *vs) | |
705 | +{ | |
706 | + int i; | |
707 | + for(i = 0; i < 256; i++) { | |
708 | + if (vs->modifiers_state[i]) { | |
709 | + if (i & 0x80) | |
710 | + kbd_put_keycode(0xe0); | |
711 | + kbd_put_keycode(i | 0x80); | |
712 | + vs->modifiers_state[i] = 0; | |
713 | + } | |
714 | + } | |
715 | +} | |
716 | + | |
702 | 717 | static void do_key_event(VncState *vs, int down, uint32_t sym) |
703 | 718 | { |
704 | 719 | int keycode; |
705 | 720 | |
706 | 721 | keycode = keysym2scancode(vs->kbd_layout, sym & 0xFFFF); |
722 | + | |
723 | + /* QEMU console switch */ | |
724 | + switch(keycode) { | |
725 | + case 0x2a: /* Left Shift */ | |
726 | + case 0x36: /* Right Shift */ | |
727 | + case 0x1d: /* Left CTRL */ | |
728 | + case 0x9d: /* Right CTRL */ | |
729 | + case 0x38: /* Left ALT */ | |
730 | + case 0xb8: /* Right ALT */ | |
731 | + if (down) | |
732 | + vs->modifiers_state[keycode] = 1; | |
733 | + else | |
734 | + vs->modifiers_state[keycode] = 0; | |
735 | + break; | |
736 | + case 0x02 ... 0x0a: /* '1' to '9' keys */ | |
737 | + if (down && vs->modifiers_state[0x1d] && vs->modifiers_state[0x38]) { | |
738 | + /* Reset the modifiers sent to the current console */ | |
739 | + reset_keys(vs); | |
740 | + console_select(keycode - 0x02); | |
741 | + return; | |
742 | + } | |
743 | + break; | |
744 | + } | |
707 | 745 | |
708 | - if (keycode & 0x80) | |
709 | - kbd_put_keycode(0xe0); | |
710 | - if (down) | |
711 | - kbd_put_keycode(keycode & 0x7f); | |
712 | - else | |
713 | - kbd_put_keycode(keycode | 0x80); | |
746 | + if (is_graphic_console()) { | |
747 | + if (keycode & 0x80) | |
748 | + kbd_put_keycode(0xe0); | |
749 | + if (down) | |
750 | + kbd_put_keycode(keycode & 0x7f); | |
751 | + else | |
752 | + kbd_put_keycode(keycode | 0x80); | |
753 | + } else { | |
754 | + /* QEMU console emulation */ | |
755 | + if (down) { | |
756 | + switch (keycode) { | |
757 | + case 0x2a: /* Left Shift */ | |
758 | + case 0x36: /* Right Shift */ | |
759 | + case 0x1d: /* Left CTRL */ | |
760 | + case 0x9d: /* Right CTRL */ | |
761 | + case 0x38: /* Left ALT */ | |
762 | + case 0xb8: /* Right ALT */ | |
763 | + break; | |
764 | + case 0xc8: | |
765 | + kbd_put_keysym(QEMU_KEY_UP); | |
766 | + break; | |
767 | + case 0xd0: | |
768 | + kbd_put_keysym(QEMU_KEY_DOWN); | |
769 | + break; | |
770 | + case 0xcb: | |
771 | + kbd_put_keysym(QEMU_KEY_LEFT); | |
772 | + break; | |
773 | + case 0xcd: | |
774 | + kbd_put_keysym(QEMU_KEY_RIGHT); | |
775 | + break; | |
776 | + case 0xd3: | |
777 | + kbd_put_keysym(QEMU_KEY_DELETE); | |
778 | + break; | |
779 | + case 0xc7: | |
780 | + kbd_put_keysym(QEMU_KEY_HOME); | |
781 | + break; | |
782 | + case 0xcf: | |
783 | + kbd_put_keysym(QEMU_KEY_END); | |
784 | + break; | |
785 | + case 0xc9: | |
786 | + kbd_put_keysym(QEMU_KEY_PAGEUP); | |
787 | + break; | |
788 | + case 0xd1: | |
789 | + kbd_put_keysym(QEMU_KEY_PAGEDOWN); | |
790 | + break; | |
791 | + default: | |
792 | + kbd_put_keysym(sym); | |
793 | + break; | |
794 | + } | |
795 | + } | |
796 | + } | |
714 | 797 | } |
715 | 798 | |
716 | 799 | static void key_event(VncState *vs, int down, uint32_t sym) | ... | ... |