Qemu support for multiple keyboard devices - v2
cover Qemu support for multiple keyboard devices - v2
* After Anthony patches, and Luiz comments
Qemu support for multiple keyboard devices:
Patch #1 adding keyboard is done to list instead of "last added keyboard
wins", when removing keyboard via device_del - next keyboard selected.
Patch #2 adding 2 new monitor command to handle keyboard list:
'info keyboard' - show all keyboards and mark the current one 'keyboard_set' - set active keyboard by index as display in
'info keyboard'
Shahar Havivi (2):
Support for multiple keyboard devices
Added monitor commands: 'keyboard_set' and 'info keybaord'
console.h | 16 ++++- hw/adb.c | 2 +- hw/escc.c | 3 +- hw/musicpal.c | 2 +- hw/nseries.c | 4 +- hw/palm.c | 2 +- hw/ps2.c | 2 +- hw/pxa2xx_keypad.c | 2 +- hw/spitz.c | 2 +- hw/stellaris_input.c | 2 +- hw/syborg_keyboard.c | 2 +- hw/usb-hid.c | 10 ++- hw/xenfb.c | 4 +- input.c | 194 +++++++++++++++++++++++++++++++++++++++++++++++--- monitor.c | 8 ++ qemu-monitor.hx | 17 +++++ qerror.c | 8 ++ 17 files changed, 253 insertions(+), 27 deletions(-)
PATCH 1/2 Support for multiple keyboard devices
Currently you get segfault when trying to remove keyboard (device_del monitor command) because no keyboard handling is done.
This patch add QEMUPutKbdEntry structure, handling each keyboard entry. Adding a keyboard add to the list, removing keyboard select the previous keyboard in list.
--- console.h | 12 ++++++- hw/adb.c | 2 +- hw/escc.c | 3 +- hw/musicpal.c | 2 +- hw/nseries.c | 4 +- hw/palm.c | 2 +- hw/ps2.c | 2 +- hw/pxa2xx_keypad.c | 2 +- hw/spitz.c | 2 +- hw/stellaris_input.c | 2 +- hw/syborg_keyboard.c | 2 +- hw/usb-hid.c | 10 ++++-- hw/xenfb.c | 4 +- input.c | 90 ++++++++++++++++++++++++++++++++++++++++++++----- 14 files changed, 112 insertions(+), 27 deletions(-)
console.h +11 -1
@@ -41,7 +41,17 @@ typedef struct QEMUPutLEDEntry {QTAILQ_ENTRY (QEMUPutLEDEntry) next; } QEMUPutLEDEntry; -void qemu_add_kbd_event_handler (QEMUPutKBDEvent *func,void *opaque); +typedef struct QEMUPutKbdEntry { +char *qemu_put_kbd_name; +QEMUPutKBDEvent *qemu_put_kbd_event; +void *qemu_put_kbd_event_opaque; +struct QEMUPutKbdEntry *next; +}QEMUPutKbdEntry ; + +QEMUPutKbdEntry *qemu_add_kbd_event_handler (QEMUPutKBDEvent *func, +void *opaque, +const char *name); +void qemu_remove_kbd_event_handler (QEMUPutKbdEntry *entry);QEMUPutMouseEntry *qemu_add_mouse_event_handler (QEMUPutMouseEvent *func,void *opaque,int absolute,const char *name);
hw/adb.c +1 -1
@@ -304,7 +304,7 @@ void adb_kbd_init(ADBBusState *bus) s =qemu_mallocz (sizeof (KBDState)); d =adb_register_device (bus,ADB_KEYBOARD , adb_kbd_request, adb_kbd_reset, s); -qemu_add_kbd_event_handler (adb_kbd_put_keycode, d); +qemu_add_kbd_event_handler (adb_kbd_put_keycode, d,"adb" );register_savevm ("adb_kbd" ,-1 ,1 , adb_kbd_save, adb_kbd_load, s); }
hw/escc.c +2 -1
@@ -919,7 +919,8 @@ static int escc_init1(SysBusDevice *dev) "QEMU Sun Mouse"); }if (s->chn[1 ].type == kbd) { -qemu_add_kbd_event_handler (sunkbd_event, &s->chn[1 ]); +qemu_add_kbd_event_handler (sunkbd_event, &s->chn[1 ], +"QEMU Sun Keyboard" ); }return 0 ;
hw/musicpal.c +1 -1
@@ -1447,7 +1447,7 @@ static int musicpal_key_init(SysBusDevice *dev)qdev_init_gpio_out (&dev->qdev, s->out,ARRAY_SIZE (s->out)); -qemu_add_kbd_event_handler (musicpal_key_event, s); +qemu_add_kbd_event_handler (musicpal_key_event, s,"Musicpal" );return 0 ; }
hw/nseries.c +2 -2
@@ -262,7 +262,7 @@ static void n800_tsc_kbd_setup(struct n800_s *s)if (n800_keys[i] >=0 ) s->keymap[n800_keys[i]] = i; -qemu_add_kbd_event_handler (n800_key_event, s); +qemu_add_kbd_event_handler (n800_key_event, s,"Nokia n800" );tsc210x_set_transform (s->ts.chip, &n800_pointercal); }
@@ -371,7 +371,7 @@ static void n810_kbd_setup(struct n800_s *s)if (n810_keys[i] >0 ) s->keymap[n810_keys[i]] = i; -qemu_add_kbd_event_handler (n810_key_event, s); +qemu_add_kbd_event_handler (n810_key_event, s,"Nokia n810" );/* Attach the LM8322 keyboard to the I2C bus, * should happen in n8x0_i2c_setup and s->kbd be initialised here. */
hw/palm.c +1 -1
@@ -228,7 +228,7 @@ static void palmte_init(ram_addr_t ram_size,palmte_microwire_setup (cpu); -qemu_add_kbd_event_handler (palmte_button_event, cpu); +qemu_add_kbd_event_handler (palmte_button_event, cpu,"Palm Keyboard" );palmte_gpio_setup (cpu);
hw/ps2.c +1 -1
@@ -596,7 +596,7 @@ void *ps2_kbd_init(void (*update_irq)(void *, int), void *update_arg) s->common.update_arg = update_arg; s->scancode_set =2 ;vmstate_register (0 , &vmstate_ps2_keyboard, s); -qemu_add_kbd_event_handler (ps2_put_keycode, s); +qemu_add_kbd_event_handler (ps2_put_keycode, s,"QEMU PS/2 Keyboard" );qemu_register_reset (ps2_kbd_reset, s);return s; }
hw/pxa2xx_keypad.c +1 -1
@@ -332,5 +332,5 @@ void pxa27x_register_keypad(PXA2xxKeyPadState *kp, struct keymap *map, } kp->map = map; -qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) pxa27x_keyboard_event, kp); +qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) pxa27x_keyboard_event, kp,"PXA keypad" ); }
hw/spitz.c +1 -1
@@ -506,7 +506,7 @@ static void spitz_keyboard_register(PXA2xxState *cpu)pxa2xx_gpio_out_set (cpu->gpio, spitz_gpio_key_strobe[i], s->strobe[i]);spitz_keyboard_pre_map (s); -qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) spitz_keyboard_handler, s); +qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) spitz_keyboard_handler, s,"Spitz keyboard" );register_savevm ("spitz_keyboard" ,0 ,0 , spitz_keyboard_save, spitz_keyboard_load, s);
hw/stellaris_input.c +1 -1
@@ -85,7 +85,7 @@ void stellaris_gamepad_init(int n, qemu_irq *irq, const int *keycode) s->buttons[i].keycode = keycode[i]; } s->num_buttons = n; -qemu_add_kbd_event_handler (stellaris_gamepad_put_key, s); +qemu_add_kbd_event_handler (stellaris_gamepad_put_key, s,"Stellaris Gamepad" );register_savevm ("stellaris_gamepad" ,-1 ,1 , stellaris_gamepad_save, stellaris_gamepad_load, s); }
hw/syborg_keyboard.c +1 -1
@@ -218,7 +218,7 @@ static int syborg_keyboard_init(SysBusDevice *dev) } s->key_fifo =qemu_mallocz (s->fifo_size *sizeof (s->key_fifo[0 ])); -qemu_add_kbd_event_handler (syborg_keyboard_event, s); +qemu_add_kbd_event_handler (syborg_keyboard_event, s,"Syborg Keyboard" );register_savevm ("syborg_keyboard" ,-1 ,1 , syborg_keyboard_save, syborg_keyboard_load, s);
hw/usb-hid.c +7 -3
@@ -55,6 +55,7 @@ typedef struct USBKeyboardState {uint8_t leds;uint8_t key[16 ];int keys; +QEMUPutKbdEntry *eh_entry; } USBKeyboardState; typedef struct USBHIDState {
@@ -633,7 +634,8 @@ static void usb_keyboard_handle_reset(USBDevice *dev) {USBHIDState *s = (USBHIDState *)dev; -qemu_add_kbd_event_handler (usb_keyboard_event, s); + s->kbd.eh_entry =qemu_add_kbd_event_handler (usb_keyboard_event, s, + dev->product_desc); s->protocol =1 ; }
@@ -854,9 +856,11 @@ static void usb_hid_handle_destroy(USBDevice *dev) {USBHIDState *s = (USBHIDState *)dev; -if (s->kind !=USB_KEYBOARD ) +if (s->kind !=USB_KEYBOARD ) {qemu_remove_mouse_event_handler (s->ptr.eh_entry); -/* TODO: else */ + }else { +qemu_remove_kbd_event_handler (s->kbd.eh_entry); + } }static int usb_hid_initfn (USBDevice *dev,int kind)
hw/xenfb.c +2 -2
@@ -373,7 +373,7 @@ static int input_connect(struct XenDevice *xendev)if (rc !=0 )return rc; -qemu_add_kbd_event_handler (xenfb_key_event, in); +qemu_add_kbd_event_handler (xenfb_key_event, in,"Xen Keyboard" ); in->qmouse =qemu_add_mouse_event_handler (xenfb_mouse_event, in, in->abs_pointer_wanted,"Xen PVFB Mouse" );
@@ -388,7 +388,7 @@ static void input_disconnect(struct XenDevice *xendev)qemu_remove_mouse_event_handler (in->qmouse); in->qmouse =NULL ; } -qemu_add_kbd_event_handler (NULL ,NULL ); +qemu_add_kbd_event_handler (NULL ,NULL ,NULL );common_unbind (&in->c); }
input.c +80 -10
114 lines not on this page · raw message
Signature · 1 line
1.6.3.3
Re: [Qemu-devel] [PATCH 1/2] Support for multiple keyboard devices
Quoted 48 lines · Shahar Havivi
Currently you get segfault when trying to remove keyboard (
device_delmonitor command) because no keyboard handling is done.This patch add QEMUPutKbdEntry structure, handling each keyboard entry. Adding a keyboard add to the list, removing keyboard select the previous keyboard in list.
Signed-off-by Shahar Havivi <[email protected]>--- console.h | 12 ++++++- hw/adb.c | 2 +- hw/escc.c | 3 +- hw/musicpal.c | 2 +- hw/nseries.c | 4 +- hw/palm.c | 2 +- hw/ps2.c | 2 +- hw/pxa2xx_keypad.c | 2 +- hw/spitz.c | 2 +- hw/stellaris_input.c | 2 +- hw/syborg_keyboard.c | 2 +- hw/usb-hid.c | 10 ++++-- hw/xenfb.c | 4 +- input.c | 90 ++++++++++++++++++++++++++++++++++++++++++++----- 14 files changed, 112 insertions(+), 27 deletions(-)console.h +11
-1@@ -41,7 +41,17 @@ typedef struct QEMUPutLEDEntry {QTAILQ_ENTRY (QEMUPutLEDEntry) next; } QEMUPutLEDEntry; -void qemu_add_kbd_event_handler (QEMUPutKBDEvent *func,void *opaque); +typedef struct QEMUPutKbdEntry { +char *qemu_put_kbd_name; +QEMUPutKBDEvent *qemu_put_kbd_event; +void *qemu_put_kbd_event_opaque; +struct QEMUPutKbdEntry *next; +}QEMUPutKbdEntry ; + +QEMUPutKbdEntry *qemu_add_kbd_event_handler (QEMUPutKBDEvent *func, +void *opaque, +const char *name); +void qemu_remove_kbd_event_handler (QEMUPutKbdEntry *entry);QEMUPutMouseEntry *qemu_add_mouse_event_handler (QEMUPutMouseEvent *func,void *opaque,int absolute,const char *name);
[...]
Quoted 37 lines
input.c +8
-8@@ -28,20 +28,14 @@#include "console.h" #include "qjson.h" -static QEMUPutKBDEvent *qemu_put_kbd_event; -static void *qemu_put_kbd_event_opaque; +static QEMUPutKbdEntry *qemu_put_kbd_event_head; +static QEMUPutKbdEntry *qemu_put_kbd_event_current; static QTAILQ_HEAD(, QEMUPutLEDEntry) led_handlers = QTAILQ_HEAD_INITIALIZER(led_handlers); static QTAILQ_HEAD(, QEMUPutMouseEntry) mouse_handlers =QTAILQ_HEAD_INITIALIZER (mouse_handlers);static NotifierList mouse_mode_notifiers =NOTIFIER_LIST_INITIALIZER (mouse_mode_notifiers); -void qemu_add_kbd_event_handler (QEMUPutKBDEvent *func,void *opaque) -{ - qemu_put_kbd_event_opaque = opaque; - qemu_put_kbd_event = func; -} -static void check_mode_change (void ) {static int current_is_absolute, current_has_absolute;@@ -60,6 +54,81 @@ static void check_mode_change(void) current_has_absolute = has_absolute; } +QEMUPutKbdEntry *qemu_add_kbd_event_handler (QEMUPutKBDEvent *func, +void *opaque, +const char *name) +{ +QEMUPutKbdEntry *s, *cursor; +
input.c static void check_mode_change(void) · line 72
Quoted 10 lines
input.c +10
-0+ cursor = qemu_put_kbd_event_head; +while (cursor) { +if (cursor->qemu_put_kbd_event == func && + cursor->qemu_put_kbd_event_opaque == opaque) { + + qemu_put_kbd_event_current = cursor; +return cursor; + } + cursor = cursor->next; + }
You're chasing list pointers. Why not use a suitable list type from qemu-queue.h?
Quoted 47 lines
input.c +47
-0+ + s =qemu_mallocz (sizeof (QEMUPutKbdEntry)); + + s->qemu_put_kbd_event_opaque = opaque; + s->qemu_put_kbd_event = func; + s->qemu_put_kbd_name =qemu_strdup (name); + s->next =NULL ; + +if (!qemu_put_kbd_event_head) { + qemu_put_kbd_event_head = s; + qemu_put_kbd_event_current = s; +return s; + } + + cursor = qemu_put_kbd_event_head; +while (cursor->next) { + cursor = cursor->next; + } + + cursor->next = s; + qemu_put_kbd_event_current = s; + +return s; +} + +void qemu_remove_kbd_event_handler (QEMUPutKbdEntry *entry) +{ +QEMUPutKbdEntry *prev =NULL , *cursor; + +if (!qemu_put_kbd_event_head || !entry) { +return ; + } + + cursor = qemu_put_kbd_event_head; +while (cursor && cursor != entry) { + prev = cursor; + cursor = cursor->next; + } + +if (cursor ==NULL ) { +return ; + }else if (prev ==NULL ) { + qemu_put_kbd_event_head = cursor->next; +if (qemu_put_kbd_event_current == entry) { + qemu_put_kbd_event_current = cursor->next; + } +qemu_free (entry);
input.c static void check_mode_change(void) · line 129
Quoted 10 lines
input.c +10
-0+return ; + } + + prev->next = entry->next; + +if (qemu_put_kbd_event_current == entry) { + qemu_put_kbd_event_current = prev; + } + +qemu_free (entry);
More list pointer chasing.
Quoted 16 lines
input.c +5
-2+} +QEMUPutMouseEntry *qemu_add_mouse_event_handler (QEMUPutMouseEvent *func,void *opaque,int absolute,const char *name)@@ -123,8 +192,9 @@ void qemu_remove_led_event_handler(QEMUPutLEDEntry *entry)void kbd_put_keycode (int keycode) { -if (qemu_put_kbd_event) { -qemu_put_kbd_event (qemu_put_kbd_event_opaque, keycode); +if (qemu_put_kbd_event_current) { + qemu_put_kbd_event_current->qemu_put_kbd_event ( + qemu_put_kbd_event_current->qemu_put_kbd_event_opaque, keycode); } }
Re: [Qemu-devel] [PATCH 1/2] Support for multiple keyboard devices
Quoted 11 lines · Markus Armbruster
Quoted 11 lines
(quoted diff) +11
-0+QEMUPutKbdEntry *qemu_add_kbd_event_handler(QEMUPutKBDEvent *func, + void *opaque, + const char *name) +{ + QEMUPutKbdEntry *s, *cursor; + + cursor = qemu_put_kbd_event_head; + while (cursor) { + if (cursor->qemu_put_kbd_event == func && + cursor->qemu_put_kbd_event_opaque == opaque) { +
Quoted 9 lines
Review
Quoted 5 lines
(quoted diff) +5
-0+ qemu_put_kbd_event_current = cursor; + return cursor; + } + cursor = cursor->next; + }You're chasing list pointers. Why not use a suitable list type from
qemu-queue.h?
Change keyboard list to qemu tail queue.
--- console.h | 12 ++++++++++- hw/adb.c | 2 +- hw/escc.c | 3 +- hw/musicpal.c | 2 +- hw/nseries.c | 4 +- hw/palm.c | 2 +- hw/ps2.c | 2 +- hw/pxa2xx_keypad.c | 2 +- hw/spitz.c | 2 +- hw/stellaris_input.c | 2 +- hw/syborg_keyboard.c | 2 +- hw/usb-hid.c | 10 ++++++-- hw/xenfb.c | 4 +- input.c | 51 ++++++++++++++++++++++++++++++++++++++++--------- 14 files changed, 73 insertions(+), 27 deletions(-)
console.h +11 -1
@@ -41,7 +41,17 @@ typedef struct QEMUPutLEDEntry {QTAILQ_ENTRY (QEMUPutLEDEntry) next; } QEMUPutLEDEntry; -void qemu_add_kbd_event_handler (QEMUPutKBDEvent *func,void *opaque); +typedef struct QEMUPutKbdEntry { +char *qemu_put_kbd_name; +QEMUPutKBDEvent *qemu_put_kbd_event; +void *qemu_put_kbd_event_opaque; +QTAILQ_ENTRY (QEMUPutKbdEntry) entry; +}QEMUPutKbdEntry ; + +QEMUPutKbdEntry *qemu_add_kbd_event_handler (QEMUPutKBDEvent *func, +void *opaque, +const char *name); +void qemu_remove_kbd_event_handler (QEMUPutKbdEntry *entry);QEMUPutMouseEntry *qemu_add_mouse_event_handler (QEMUPutMouseEvent *func,void *opaque,int absolute,const char *name);
hw/adb.c +1 -1
@@ -304,7 +304,7 @@ void adb_kbd_init(ADBBusState *bus) s =qemu_mallocz (sizeof (KBDState)); d =adb_register_device (bus,ADB_KEYBOARD , adb_kbd_request, adb_kbd_reset, s); -qemu_add_kbd_event_handler (adb_kbd_put_keycode, d); +qemu_add_kbd_event_handler (adb_kbd_put_keycode, d,"adb" );register_savevm ("adb_kbd" ,-1 ,1 , adb_kbd_save, adb_kbd_load, s); }
hw/escc.c +2 -1
@@ -919,7 +919,8 @@ static int escc_init1(SysBusDevice *dev) "QEMU Sun Mouse"); }if (s->chn[1 ].type == kbd) { -qemu_add_kbd_event_handler (sunkbd_event, &s->chn[1 ]); +qemu_add_kbd_event_handler (sunkbd_event, &s->chn[1 ], +"QEMU Sun Keyboard" ); }return 0 ;
hw/musicpal.c +1 -1
@@ -1447,7 +1447,7 @@ static int musicpal_key_init(SysBusDevice *dev)qdev_init_gpio_out (&dev->qdev, s->out,ARRAY_SIZE (s->out)); -qemu_add_kbd_event_handler (musicpal_key_event, s); +qemu_add_kbd_event_handler (musicpal_key_event, s,"Musicpal" );return 0 ; }
hw/nseries.c +2 -2
@@ -262,7 +262,7 @@ static void n800_tsc_kbd_setup(struct n800_s *s)if (n800_keys[i] >=0 ) s->keymap[n800_keys[i]] = i; -qemu_add_kbd_event_handler (n800_key_event, s); +qemu_add_kbd_event_handler (n800_key_event, s,"Nokia n800" );tsc210x_set_transform (s->ts.chip, &n800_pointercal); }
@@ -371,7 +371,7 @@ static void n810_kbd_setup(struct n800_s *s)if (n810_keys[i] >0 ) s->keymap[n810_keys[i]] = i; -qemu_add_kbd_event_handler (n810_key_event, s); +qemu_add_kbd_event_handler (n810_key_event, s,"Nokia n810" );/* Attach the LM8322 keyboard to the I2C bus, * should happen in n8x0_i2c_setup and s->kbd be initialised here. */
hw/palm.c +1 -1
@@ -228,7 +228,7 @@ static void palmte_init(ram_addr_t ram_size,palmte_microwire_setup (cpu); -qemu_add_kbd_event_handler (palmte_button_event, cpu); +qemu_add_kbd_event_handler (palmte_button_event, cpu,"Palm Keyboard" );palmte_gpio_setup (cpu);
hw/ps2.c +1 -1
@@ -596,7 +596,7 @@ void *ps2_kbd_init(void (*update_irq)(void *, int), void *update_arg) s->common.update_arg = update_arg; s->scancode_set =2 ;vmstate_register (0 , &vmstate_ps2_keyboard, s); -qemu_add_kbd_event_handler (ps2_put_keycode, s); +qemu_add_kbd_event_handler (ps2_put_keycode, s,"QEMU PS/2 Keyboard" );qemu_register_reset (ps2_kbd_reset, s);return s; }
hw/pxa2xx_keypad.c +1 -1
@@ -332,5 +332,5 @@ void pxa27x_register_keypad(PXA2xxKeyPadState *kp, struct keymap *map, } kp->map = map; -qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) pxa27x_keyboard_event, kp); +qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) pxa27x_keyboard_event, kp,"PXA keypad" ); }
hw/spitz.c +1 -1
@@ -506,7 +506,7 @@ static void spitz_keyboard_register(PXA2xxState *cpu)pxa2xx_gpio_out_set (cpu->gpio, spitz_gpio_key_strobe[i], s->strobe[i]);spitz_keyboard_pre_map (s); -qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) spitz_keyboard_handler, s); +qemu_add_kbd_event_handler ((QEMUPutKBDEvent *) spitz_keyboard_handler, s,"Spitz keyboard" );register_savevm ("spitz_keyboard" ,0 ,0 , spitz_keyboard_save, spitz_keyboard_load, s);
hw/stellaris_input.c +1 -1
@@ -85,7 +85,7 @@ void stellaris_gamepad_init(int n, qemu_irq *irq, const int *keycode) s->buttons[i].keycode = keycode[i]; } s->num_buttons = n; -qemu_add_kbd_event_handler (stellaris_gamepad_put_key, s); +qemu_add_kbd_event_handler (stellaris_gamepad_put_key, s,"Stellaris Gamepad" );register_savevm ("stellaris_gamepad" ,-1 ,1 , stellaris_gamepad_save, stellaris_gamepad_load, s); }
hw/syborg_keyboard.c +1 -1
@@ -218,7 +218,7 @@ static int syborg_keyboard_init(SysBusDevice *dev) } s->key_fifo =qemu_mallocz (s->fifo_size *sizeof (s->key_fifo[0 ])); -qemu_add_kbd_event_handler (syborg_keyboard_event, s); +qemu_add_kbd_event_handler (syborg_keyboard_event, s,"Syborg Keyboard" );register_savevm ("syborg_keyboard" ,-1 ,1 , syborg_keyboard_save, syborg_keyboard_load, s);
hw/usb-hid.c +7 -3
@@ -55,6 +55,7 @@ typedef struct USBKeyboardState {uint8_t leds;uint8_t key[16 ];int keys; +QEMUPutKbdEntry *eh_entry; } USBKeyboardState; typedef struct USBHIDState {
@@ -633,7 +634,8 @@ static void usb_keyboard_handle_reset(USBDevice *dev) {USBHIDState *s = (USBHIDState *)dev; -qemu_add_kbd_event_handler (usb_keyboard_event, s); + s->kbd.eh_entry =qemu_add_kbd_event_handler (usb_keyboard_event, s, + dev->product_desc); s->protocol =1 ; }
@@ -854,9 +856,11 @@ static void usb_hid_handle_destroy(USBDevice *dev) {USBHIDState *s = (USBHIDState *)dev; -if (s->kind !=USB_KEYBOARD ) +if (s->kind !=USB_KEYBOARD ) {qemu_remove_mouse_event_handler (s->ptr.eh_entry); -/* TODO: else */ + }else { +qemu_remove_kbd_event_handler (s->kbd.eh_entry); + } }static int usb_hid_initfn (USBDevice *dev,int kind)
hw/xenfb.c +2 -2
@@ -373,7 +373,7 @@ static int input_connect(struct XenDevice *xendev)if (rc !=0 )return rc; -qemu_add_kbd_event_handler (xenfb_key_event, in); +qemu_add_kbd_event_handler (xenfb_key_event, in,"Xen Keyboard" ); in->qmouse =qemu_add_mouse_event_handler (xenfb_mouse_event, in, in->abs_pointer_wanted,"Xen PVFB Mouse" );
@@ -388,7 +388,7 @@ static void input_disconnect(struct XenDevice *xendev)qemu_remove_mouse_event_handler (in->qmouse); in->qmouse =NULL ; } -qemu_add_kbd_event_handler (NULL ,NULL ); +qemu_add_kbd_event_handler (NULL ,NULL ,NULL );common_unbind (&in->c); }
input.c +41 -10
75 lines not on this page · raw message
Signature · 1 line
1.6.3.3
PATCH 2/2 Added monitor commands: 'keyboard_set' and 'info keybaord'
In reply to Shahar HaviviTwo new monitor commands: adding ability to handle which keyboard qemu will use and to see which keyboard are currently available.
$ info keyboard $ keyboard_set <index>
--- console.h | 4 ++ input.c | 104 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ monitor.c | 8 ++++ qemu-monitor.hx | 17 +++++++++ qerror.c | 8 ++++ 5 files changed, 141 insertions(+), 0 deletions(-)
console.h +4 -0
@@ -85,6 +85,10 @@ void do_info_mice_print(Monitor *mon, const QObject *data);void do_info_mice (Monitor *mon,QObject **ret_data);void do_mouse_set (Monitor *mon,const QDict *qdict); +void do_info_keyboard_print (Monitor *mon,const QObject *data); +void do_info_keyboard (Monitor *mon,QObject **ret_data); +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data); +/* keysym is a unicode code except for special keys (see QEMU_KEY_xxx constants) */ #define QEMU_KEY_ESC1 (c) ((c) | 0xe100)
input.c +104 -0
107 lines not on this page · raw message
monitor.c +8 -0
@@ -2783,6 +2783,14 @@ static const mon_cmd_t info_cmds[] = { .mhandler.info_new = do_info_mice, }, { + .name = "keyboard", + .args_type = "", + .params = "", + .help = "show which guest keyboard is receiving events", + .user_print = do_info_keyboard_print, + .mhandler.info_new = do_info_keyboard, + }, + { .name = "vnc", .args_type = "", .params = "",
qemu-monitor.hx +17 -0
@@ -659,6 +659,23 @@ info mice @end example ETEXI + { + .name = "keyboard_set", + .args_type = "index:i", + .params = "index", + .help = "set which keyboard device receives events", + .mhandler.cmd_new = do_keyboard_set, + }, + +STEXI +@item keyboard_set @var{index} +@findex keyboard_set +Set which keyboard device receives events at given @var{index}, index +can be obtained with +@example +info keyboard +@end example +ETEXI #ifdef HAS_AUDIO { .name = "wavcapture",
qerror.c +8 -0
@@ -172,6 +172,14 @@ static const QErrorStringTable qerror_table[] = { .error_fmt = QERR_VNC_SERVER_FAILED, .desc = "Could not start VNC server on %(target)", }, + { + .error_fmt = QERR_DEVICE_NOT_FOUND, + .desc = "No keyboard device found", + }, + { + .error_fmt = QERR_INVALID_PARAMETER, + .desc = "Invalid index '%(name)' for keyboard device", + }, {} };
Signature · 1 line
1.6.3.3
Re: [Qemu-devel] [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
Quoted 95 lines · Shahar Havivi
Two new monitor commands: adding ability to handle which keyboard qemu will use and to see which keyboard are currently available.
$ info keyboard $ keyboard_set <index>Signed-off-by Shahar Havivi <[email protected]>--- console.h | 4 ++ input.c | 104 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ monitor.c | 8 ++++ qemu-monitor.hx | 17 +++++++++ qerror.c | 8 ++++ 5 files changed, 141 insertions(+), 0 deletions(-)console.h +4
-0@@ -85,6 +85,10 @@ void do_info_mice_print(Monitor *mon, const QObject *data);void do_info_mice (Monitor *mon,QObject **ret_data);void do_mouse_set (Monitor *mon,const QDict *qdict); +void do_info_keyboard_print (Monitor *mon,const QObject *data); +void do_info_keyboard (Monitor *mon,QObject **ret_data); +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data); +/* keysym is a unicode code except for special keys (see QEMU_KEY_xxx constants) */ #define QEMU_KEY_ESC1 (c) ((c) | 0xe100)input.c +57
-0@@ -368,3 +368,107 @@ void qemu_remove_mouse_mode_change_notifier(Notifier *notify) {notifier_list_remove (&mouse_mode_notifiers, notify); } + +static void info_keyboard_iter (QObject *data,void *opaque) +{ +QDict *kbd; +Monitor *mon = opaque; + + kbd =qobject_to_qdict (data); +monitor_printf (mon,"%c Keyboard #%" PRId64": %s\n" , + (qdict_get_bool (kbd,"current" ) ?'*' :' ' ), +qdict_get_int (kbd,"index" ),qdict_get_str (kbd,"name" )); +} + +void do_info_keyboard_print (Monitor *mon,const QObject *data) +{ +QList *kbd_list; + + kbd_list =qobject_to_qlist (data); +if (qlist_empty (kbd_list)) { +monitor_printf (mon,"No keyboard devices connected\n" ); +return ; + } + +qlist_iter (kbd_list, info_keyboard_iter, mon); +} + +/* +* do_info_keyboard(): Show VM keyboard information +* +* Each keyboard is represented by a QDict, the returned QObject is +* a QList of all keyboards. +* +* The keyboard QDict contains the following: +* +* - "name": keyboard's name +* - "index": keyboard's index +* - "current": true if this keyboard is receiving events, false otherwise +* +* Example: +* +* [ { "name": "QEMU USB Keyboard", "index": 0, "current": false }, +* { "name": "QEMU PS/2 Keyboard", "index": 1, "current": true } ] +*/ +void do_info_keyboard (Monitor *mon,QObject **ret_data) +{ +QEMUPutKbdEntry *cursor; +QList *kbd_list; +int index =0 ; + + kbd_list =qlist_new (); + +if (!qemu_put_kbd_event_head) { + goto out; + } + + cursor = qemu_put_kbd_event_head; +while (cursor !=NULL ) { +QObject *obj;
input.c void qemu_remove_mouse_mode_change_notifier(Notifier *notify) · line 437
Quoted 10 lines
input.c +10
-0+ obj =qobject_from_jsonf ("{ 'name': %s, 'index': %d, 'current': %i }" , + cursor->qemu_put_kbd_name, + index, cursor == qemu_put_kbd_event_current); +qlist_append_obj (kbd_list, obj); + index++; + cursor = cursor->next; + } +out: + *ret_data =QOBJECT (kbd_list); +}
Keyboard indexes change when keyboards other than the last one get removed. Hmm.
Quoted 27 lines
input.c +27
-0+ +/* +* do_keyboard_set(): Set active keyboard +* +* Argument qdict contains +* - "index": the keyboard index to set +* +* Example: +* +* { "index": "0" } +*/ +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data) +{ +QEMUPutKbdEntry *cursor; +int i =0 ; +int index =qdict_get_int (qdict,"index" ); + +if (!qemu_put_kbd_event_head) { +qerror_report (QERR_DEVICE_NOT_FOUND ,"keyboard" ); +return -1 ; + } + + cursor = qemu_put_kbd_event_head; +while (cursor !=NULL && index != i) { + i++; + cursor = cursor->next; + }
input.c void qemu_remove_mouse_mode_change_notifier(Notifier *notify) · line 474
Quoted 10 lines
input.c +10
-0+ +if (cursor !=NULL ) { + qemu_put_kbd_event_current = cursor; + } +else { +qerror_report (QERR_INVALID_PARAMETER ,"index" ); +return -1 ; + } +return 0 ; +}
Since the index is not a stable identifier of keyboards, and we support multiple monitors, you're prone to remove the wrong keyboard.
Monitor#1 Monitor#2
"info keyboard" to find the index
unplug a keyboard, invalidating index
keyboard_set <index>
I think it's best to use a stable ID, like we do in other places. We commonly let the user specify it, e.g. as id=ID in -netdev, -device and elswhere.
Quoted 55 lines
monitor.c +8
-0@@ -2783,6 +2783,14 @@ static const mon_cmd_t info_cmds[] = { .mhandler.info_new = do_info_mice, }, { + .name = "keyboard", + .args_type = "", + .params = "", + .help = "show which guest keyboard is receiving events", + .user_print = do_info_keyboard_print, + .mhandler.info_new = do_info_keyboard, + }, + { .name = "vnc", .args_type = "", .params = "",qemu-monitor.hx +17
-0@@ -659,6 +659,23 @@ info mice @end example ETEXI + { + .name = "keyboard_set", + .args_type = "index:i", + .params = "index", + .help = "set which keyboard device receives events", + .mhandler.cmd_new = do_keyboard_set, + }, + +STEXI +@item keyboard_set @var{index} +@findex keyboard_set +Set which keyboard device receives events at given @var{index}, index +can be obtained with +@example +info keyboard +@end example +ETEXI #ifdef HAS_AUDIO { .name = "wavcapture",qerror.c +0
-0@@ -172,6 +172,14 @@ static const QErrorStringTable qerror_table[] = { .error_fmt = QERR_VNC_SERVER_FAILED, .desc = "Could not start VNC server on %(target)", },
qerror.c static const QErrorStringTable qerror_table[] = { · line 184
Quoted 10 lines
qerror.c +8
-0+ { + .error_fmt = QERR_DEVICE_NOT_FOUND, + .desc = "No keyboard device found", + }, + { + .error_fmt = QERR_INVALID_PARAMETER, + .desc = "Invalid index '%(name)' for keyboard device", + }, {} };
I'm afraid you're breaking all other uses of these errors here.
Re: [Qemu-devel] [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
Quoted 165 lines · Markus Armbruster
Date: Fri, 26 Mar 2010 10:57:58 +0100
From: Markus Armbruster <[email protected]>
To: Shahar Havivi <[email protected]>
Cc: [email protected]
Subject: Re: [Qemu-devel] [PATCH 2/2] Added monitor commands:
'keyboard_set' and 'info keybaord'Quoted 95 lines · Shahar Havivi
Two new monitor commands: adding ability to handle which keyboard qemu will use and to see which keyboard are currently available.
$ info keyboard $ keyboard_set <index>Signed-off-by Shahar Havivi <[email protected]>--- console.h | 4 ++ input.c | 104 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ monitor.c | 8 ++++ qemu-monitor.hx | 17 +++++++++ qerror.c | 8 ++++ 5 files changed, 141 insertions(+), 0 deletions(-)console.h +4
-0@@ -85,6 +85,10 @@ void do_info_mice_print(Monitor *mon, const QObject *data);void do_info_mice (Monitor *mon,QObject **ret_data);void do_mouse_set (Monitor *mon,const QDict *qdict); +void do_info_keyboard_print (Monitor *mon,const QObject *data); +void do_info_keyboard (Monitor *mon,QObject **ret_data); +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data); +/* keysym is a unicode code except for special keys (see QEMU_KEY_xxx constants) */ #define QEMU_KEY_ESC1 (c) ((c) | 0xe100)input.c +57
-0@@ -368,3 +368,107 @@ void qemu_remove_mouse_mode_change_notifier(Notifier *notify) {notifier_list_remove (&mouse_mode_notifiers, notify); } + +static void info_keyboard_iter (QObject *data,void *opaque) +{ +QDict *kbd; +Monitor *mon = opaque; + + kbd =qobject_to_qdict (data); +monitor_printf (mon,"%c Keyboard #%" PRId64": %s\n" , + (qdict_get_bool (kbd,"current" ) ?'*' :' ' ), +qdict_get_int (kbd,"index" ),qdict_get_str (kbd,"name" )); +} + +void do_info_keyboard_print (Monitor *mon,const QObject *data) +{ +QList *kbd_list; + + kbd_list =qobject_to_qlist (data); +if (qlist_empty (kbd_list)) { +monitor_printf (mon,"No keyboard devices connected\n" ); +return ; + } + +qlist_iter (kbd_list, info_keyboard_iter, mon); +} + +/* +* do_info_keyboard(): Show VM keyboard information +* +* Each keyboard is represented by a QDict, the returned QObject is +* a QList of all keyboards. +* +* The keyboard QDict contains the following: +* +* - "name": keyboard's name +* - "index": keyboard's index +* - "current": true if this keyboard is receiving events, false otherwise +* +* Example: +* +* [ { "name": "QEMU USB Keyboard", "index": 0, "current": false }, +* { "name": "QEMU PS/2 Keyboard", "index": 1, "current": true } ] +*/ +void do_info_keyboard (Monitor *mon,QObject **ret_data) +{ +QEMUPutKbdEntry *cursor; +QList *kbd_list; +int index =0 ; + + kbd_list =qlist_new (); + +if (!qemu_put_kbd_event_head) { + goto out; + } + + cursor = qemu_put_kbd_event_head; +while (cursor !=NULL ) { +QObject *obj;input.c void qemu_remove_mouse_mode_change_notifier(Notifier *notify) · line 437
Quoted 10 lines
input.c +10
-0+ obj =qobject_from_jsonf ("{ 'name': %s, 'index': %d, 'current': %i }" , + cursor->qemu_put_kbd_name, + index, cursor == qemu_put_kbd_event_current); +qlist_append_obj (kbd_list, obj); + index++; + cursor = cursor->next; + } +out: + *ret_data =QOBJECT (kbd_list); +}Keyboard indexes change when keyboards other than the last one get removed. Hmm.
Quoted 27 lines
input.c +27
-0+ +/* +* do_keyboard_set(): Set active keyboard +* +* Argument qdict contains +* - "index": the keyboard index to set +* +* Example: +* +* { "index": "0" } +*/ +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data) +{ +QEMUPutKbdEntry *cursor; +int i =0 ; +int index =qdict_get_int (qdict,"index" ); + +if (!qemu_put_kbd_event_head) { +qerror_report (QERR_DEVICE_NOT_FOUND ,"keyboard" ); +return -1 ; + } + + cursor = qemu_put_kbd_event_head; +while (cursor !=NULL && index != i) { + i++; + cursor = cursor->next; + }input.c void qemu_remove_mouse_mode_change_notifier(Notifier *notify) · line 474
Quoted 10 lines
input.c +10
-0+ +if (cursor !=NULL ) { + qemu_put_kbd_event_current = cursor; + } +else { +qerror_report (QERR_INVALID_PARAMETER ,"index" ); +return -1 ; + } +return 0 ; +}Since the index is not a stable identifier of keyboards, and we support multiple monitors, you're prone to remove the wrong keyboard.
Monitor#1 Monitor#2
"info keyboard" to find the index
unplug a keyboard, invalidating index
keyboard_set<index>
Quoted 3 lines
I think it's best to use a stable ID, like we do in other places. We commonly let the user specify it, e.g. as id=ID in -netdev, -device and elswhere.
What do we do when user not specify id for device?
Quoted 60 lines
Quoted 60 lines
monitor.c +8
-0@@ -2783,6 +2783,14 @@ static const mon_cmd_t info_cmds[] = { .mhandler.info_new = do_info_mice, }, { + .name = "keyboard", + .args_type = "", + .params = "", + .help = "show which guest keyboard is receiving events", + .user_print = do_info_keyboard_print, + .mhandler.info_new = do_info_keyboard, + }, + { .name = "vnc", .args_type = "", .params = "",qemu-monitor.hx +17
-0@@ -659,6 +659,23 @@ info mice @end example ETEXI + { + .name = "keyboard_set", + .args_type = "index:i", + .params = "index", + .help = "set which keyboard device receives events", + .mhandler.cmd_new = do_keyboard_set, + }, + +STEXI +@item keyboard_set @var{index} +@findex keyboard_set +Set which keyboard device receives events at given @var{index}, index +can be obtained with +@example +info keyboard +@end example +ETEXI #ifdef HAS_AUDIO { .name = "wavcapture",qerror.c +4
-0@@ -172,6 +172,14 @@ static const QErrorStringTable qerror_table[] = { .error_fmt = QERR_VNC_SERVER_FAILED, .desc = "Could not start VNC server on %(target)", }, + { + .error_fmt = QERR_DEVICE_NOT_FOUND, + .desc = "No keyboard device found", + },
Quoted 8 lines
qerror.c static const QErrorStringTable qerror_table[] = { · line 184
Quoted 6 lines
qerror.c +4
-0+ { + .error_fmt = QERR_INVALID_PARAMETER, + .desc = "Invalid index '%(name)' for keyboard device", + }, {} };I'm afraid you're breaking all other uses of these errors here.
you right, my bad - this errors where not meant to be in this patch.
Re: [Qemu-devel] [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
Quoted 1 line · Shahar Havivi
On Fri, Mar 26, 2010 at 10:57:58AM +0100, Markus Armbruster wrote:
[...]
Quoted 9 lines
Quoted 9 lines
Since the index is not a stable identifier of keyboards, and we support multiple monitors, you're prone to remove the wrong keyboard.
Monitor#1 Monitor#2
"info keyboard" to find the index
unplug a keyboard, invalidating index
keyboard_set<index>
Quoted 4 lines
Quoted 3 lines
I think it's best to use a stable ID, like we do in other places. We commonly let the user specify it, e.g. as id=ID in -netdev, -device and elswhere.
What do we do when user not specify id for device?
Two obvious options: make one up (problem: clashes), or stipulate "if you want to keyboard_set this keyboard, you must specify an id for it".
[...]
Re: [Qemu-devel] [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
Quoted 23 lines · Markus Armbruster
Date: Wed, 31 Mar 2010 17:10:22 +0200
From: Markus Armbruster <[email protected]>
To: Shahar Havivi <[email protected]>
Cc: [email protected]
Subject: Re: [Qemu-devel] [PATCH 2/2] Added monitor commands:
'keyboard_set' and 'info keybaord'Quoted 1 line · Shahar Havivi
On Fri, Mar 26, 2010 at 10:57:58AM +0100, Markus Armbruster wrote:
[...]
Quoted 12 lines
Quoted 12 lines
Since the index is not a stable identifier of keyboards, and we support multiple monitors, you're prone to remove the wrong keyboard.
Monitor#1 Monitor#2
"info keyboard" to find the index
unplug a keyboard, invalidating index
keyboard_set<index>I think it's best to use a stable ID, like we do in other places. We commonly let the user specify it, e.g. as id=ID in -netdev, -device and elswhere.
Quoted 6 lines
Quoted 1 line
What do we do when user not specify id for device?
Two obvious options: make one up (problem: clashes), or stipulate "if you want to
keyboard_setthis keyboard, you must specify an id for it".[...]
How about static auto incremented id like the mouse does?
[Qemu-devel] Re: [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
In reply to Markus ArmbrusterQuoted 13 lines · Markus Armbruster
Quoted 1 line · Shahar Havivi
On Fri, Mar 26, 2010 at 10:57:58AM +0100, Markus Armbruster wrote:
[...]
Quoted 9 lines
Quoted 9 lines
Since the index is not a stable identifier of keyboards, and we support multiple monitors, you're prone to remove the wrong keyboard.
Monitor#1 Monitor#2
"info keyboard" to find the index
unplug a keyboard, invalidating index
keyboard_set<index>
Quoted 7 lines
Quoted 4 lines
Quoted 3 lines
I think it's best to use a stable ID, like we do in other places. We commonly let the user specify it, e.g. as id=ID in -netdev, -device and elswhere.
What do we do when user not specify id for device?
Two obvious options: make one up (problem: clashes), or stipulate "if you want to
keyboard_setthis keyboard, you must specify an id for it".
Second one is simpler, so .....
O:-)
Later, Juan.
Re: [Qemu-devel] [PATCH 2/2] Added monitor commands: 'keyboard_set' and 'info keybaord'
In reply to Markus ArmbrusterFix to Markus comments.
--- console.h | 6 +++ input.c | 119 ++++++++++++++++++++++++++++++++++++++++++++++++++---- monitor.c | 8 ++++ qemu-monitor.hx | 17 ++++++++ 4 files changed, 141 insertions(+), 9 deletions(-)
console.h +6 -0
@@ -45,6 +45,8 @@ typedef struct QEMUPutKbdEntry {char *qemu_put_kbd_name;QEMUPutKBDEvent *qemu_put_kbd_event;void *qemu_put_kbd_event_opaque; +int index; +QTAILQ_ENTRY (QEMUPutKbdEntry) entry; } QEMUPutKbdEntry;
@@ -85,6 +87,10 @@ void do_info_mice_print(Monitor *mon, const QObject *data);void do_info_mice (Monitor *mon,QObject **ret_data);void do_mouse_set (Monitor *mon,const QDict *qdict); +void do_info_keyboard_print (Monitor *mon,const QObject *data); +void do_info_keyboard (Monitor *mon,QObject **ret_data); +int do_keyboard_set (Monitor *mon,const QDict *qdict,QObject **ret_data); +/* keysym is a unicode code except for special keys (see QEMU_KEY_xxx constants) */ #define QEMU_KEY_ESC1 (c) ((c) | 0xe100)
input.c +110 -9
160 lines not on this page · raw message
monitor.c +8 -0
@@ -2783,6 +2783,14 @@ static const mon_cmd_t info_cmds[] = { .mhandler.info_new = do_info_mice, }, { + .name = "keyboard", + .args_type = "", + .params = "", + .help = "show which guest keyboard is receiving events", + .user_print = do_info_keyboard_print, + .mhandler.info_new = do_info_keyboard, + }, + { .name = "vnc", .args_type = "", .params = "",
qemu-monitor.hx +17 -0
@@ -659,6 +659,23 @@ info mice @end example ETEXI + { + .name = "keyboard_set", + .args_type = "index:i", + .params = "index", + .help = "set which keyboard device receives events", + .mhandler.cmd_new = do_keyboard_set, + }, + +STEXI +@item keyboard_set @var{index} +@findex keyboard_set +Set which keyboard device receives events at given @var{index}, index +can be obtained with +@example +info keyboard +@end example +ETEXI #ifdef HAS_AUDIO { .name = "wavcapture",
Signature · 1 line
1.6.3.3