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) | ... | ... |