[Spice-devel] [PATCH 3/3] KeyboardInterface: redesign.
Gerd Hoffmann
kraxel at redhat.com
Tue Mar 30 03:10:42 PDT 2010
This is the direction I wanna take with all interfaces: Clearly
separate interface (aka version information and function pointers)
and state information. SpiceKbdInterface defines the interface,
SpiceKbdState maintains state information. Keyboard hasn't much
beside a pointer to SpiceKbdInterface, for other interfaces this
very likely will be different.
All SpiceKbdInterface function pointers carry a opaque value as
first argument. This is the opaque pointer passed to
spice_server_add_interface.
Signed-off-by: Gerd Hoffmann <kraxel at redhat.com>
---
server/reds.c | 67 +++++++++++++++++++++++++++----------------------
server/reds.h | 11 ++++++++
server/vd_interface.h | 17 +++++-------
3 files changed, 55 insertions(+), 40 deletions(-)
diff --git a/server/reds.c b/server/reds.c
index a4563d4..ad1eeee 100644
--- a/server/reds.c
+++ b/server/reds.c
@@ -54,7 +54,7 @@
SpiceCoreInterface *core = NULL;
static MigrationInterface *mig = NULL;
-static KeyboardInterface *keyboard = NULL;
+static SpiceKbdState *keyboard = NULL;
static MouseInterface *mouse = NULL;
static TabletInterface *tablet = NULL;
static VDIPortInterface *vdagent = NULL;
@@ -2120,12 +2120,20 @@ static void activate_modifiers_watch()
core->timer_start(reds->key_modifiers_timer, KEY_MODIFIERS_TTL);
}
-static void push_key_scan(uint8_t scan)
+static void kbd_push_scan(SpiceKbdState *kbd, uint8_t scan)
{
- if (!keyboard) {
+ if (!kbd) {
return;
}
- keyboard->push_scan_freg(keyboard, scan);
+ kbd->ki->push_scan_freg(kbd->base.opaque, scan);
+}
+
+static uint8_t kbd_get_leds(SpiceKbdState *kbd)
+{
+ if (!kbd) {
+ return 0;
+ }
+ return kbd->ki->get_leds(kbd->base.opaque);
}
static void inputs_handle_input(void *opaque, SpiceDataHeader *header)
@@ -2146,7 +2154,7 @@ static void inputs_handle_input(void *opaque, SpiceDataHeader *header)
uint8_t *now = (uint8_t *)&key_down->code;
uint8_t *end = now + sizeof(key_down->code);
for (; now < end && *now; now++) {
- push_key_scan(*now);
+ kbd_push_scan(keyboard, *now);
}
break;
}
@@ -2244,22 +2252,24 @@ static void inputs_handle_input(void *opaque, SpiceDataHeader *header)
}
case SPICE_MSGC_INPUTS_KEY_MODIFIERS: {
SpiceMsgcKeyModifiers *modifiers = (SpiceMsgcKeyModifiers *)buf;
+ uint8_t leds;
+
if (!keyboard) {
break;
}
- uint8_t leds = keyboard->get_leds(keyboard);
+ leds = kbd_get_leds(keyboard);
if ((modifiers->modifiers & SPICE_SCROLL_LOCK_MODIFIER) !=
(leds & SPICE_SCROLL_LOCK_MODIFIER)) {
- push_key_scan(SCROLL_LOCK_SCAN_CODE);
- push_key_scan(SCROLL_LOCK_SCAN_CODE | 0x80);
+ kbd_push_scan(keyboard, SCROLL_LOCK_SCAN_CODE);
+ kbd_push_scan(keyboard, SCROLL_LOCK_SCAN_CODE | 0x80);
}
if ((modifiers->modifiers & SPICE_NUM_LOCK_MODIFIER) != (leds & SPICE_NUM_LOCK_MODIFIER)) {
- push_key_scan(NUM_LOCK_SCAN_CODE);
- push_key_scan(NUM_LOCK_SCAN_CODE | 0x80);
+ kbd_push_scan(keyboard, NUM_LOCK_SCAN_CODE);
+ kbd_push_scan(keyboard, NUM_LOCK_SCAN_CODE | 0x80);
}
if ((modifiers->modifiers & SPICE_CAPS_LOCK_MODIFIER) != (leds & SPICE_CAPS_LOCK_MODIFIER)) {
- push_key_scan(CAPS_LOCK_SCAN_CODE);
- push_key_scan(CAPS_LOCK_SCAN_CODE | 0x80);
+ kbd_push_scan(keyboard, CAPS_LOCK_SCAN_CODE);
+ kbd_push_scan(keyboard, CAPS_LOCK_SCAN_CODE | 0x80);
}
activate_modifiers_watch();
break;
@@ -2284,12 +2294,12 @@ void reds_set_client_mouse_allowed(int is_client_mouse_allowed, int x_res, int y
static void inputs_relase_keys(void)
{
- push_key_scan(0x2a | 0x80); //LSHIFT
- push_key_scan(0x36 | 0x80); //RSHIFT
- push_key_scan(0xe0); push_key_scan(0x1d | 0x80); //RCTRL
- push_key_scan(0x1d | 0x80); //LCTRL
- push_key_scan(0xe0); push_key_scan(0x38 | 0x80); //RALT
- push_key_scan(0x38 | 0x80); //LALT
+ kbd_push_scan(keyboard, 0x2a | 0x80); //LSHIFT
+ kbd_push_scan(keyboard, 0x36 | 0x80); //RSHIFT
+ kbd_push_scan(keyboard, 0xe0); kbd_push_scan(keyboard, 0x1d | 0x80); //RCTRL
+ kbd_push_scan(keyboard, 0x1d | 0x80); //LCTRL
+ kbd_push_scan(keyboard, 0xe0); kbd_push_scan(keyboard, 0x38 | 0x80); //RALT
+ kbd_push_scan(keyboard, 0x38 | 0x80); //LALT
}
static void inputs_event(int fd, int event, void *data)
@@ -2411,7 +2421,7 @@ static void inputs_link(Channel *channel, RedsStreamContext *peer, int migration
header.type = SPICE_MSG_INPUTS_INIT;
header.size = sizeof(SpiceMsgInputsInit);
header.sub_list = 0;
- inputs_init.keyboard_modifiers = keyboard ? keyboard->get_leds(keyboard) : 0;
+ inputs_init.keyboard_modifiers = kbd_get_leds(keyboard);
if (outgoing_write(inputs_state->peer, &inputs_state->out_handler, &header,
sizeof(SpiceDataHeader)) != OUTGOING_OK ||
outgoing_write(inputs_state->peer, &inputs_state->out_handler, &inputs_init,
@@ -3969,7 +3979,7 @@ static void migrate_timout(void *opaque)
static void key_modifiers_sender(void *opaque)
{
- reds_send_keyboard_modifiers(keyboard ? keyboard->get_leds(keyboard) : 0);
+ reds_send_keyboard_modifiers(kbd_get_leds(keyboard));
}
uint32_t reds_get_mm_time()
@@ -4042,23 +4052,20 @@ spice_server_add_interface(SpiceServer *s, SpiceBaseInterface *interface,
ASSERT(reds == s);
- if (strcmp(interface->type, VD_INTERFACE_KEYBOARD) == 0) {
- red_printf("VD_INTERFACE_KEYBOARD");
+ if (strcmp(interface->type, SPICE_INTERFACE_KEYBOARD) == 0) {
+ red_printf("SPICE_INTERFACE_KEYBOARD");
if (keyboard) {
red_printf("already have keyboard");
return NULL;
}
- if (interface->major_version != VD_INTERFACE_KEYBOARD_MAJOR ||
- interface->minor_version < VD_INTERFACE_KEYBOARD_MINOR) {
+ if (interface->major_version != SPICE_INTERFACE_KEYBOARD_MAJOR ||
+ interface->minor_version < SPICE_INTERFACE_KEYBOARD_MINOR) {
red_printf("unsuported keyboard interface");
return NULL;
}
- keyboard = (KeyboardInterface *)interface;
- if (keyboard->register_leds_notifier) {
- if (!keyboard->register_leds_notifier(keyboard, reds_on_keyboard_leds_change, NULL)) {
- red_error("register leds notifier failed");
- }
- }
+ keyboard = spice_malloc0(sizeof(*keyboard));
+ keyboard->ki = container_of(interface, SpiceKbdInterface, base);
+ is = &keyboard->base;
} else if (strcmp(interface->type, VD_INTERFACE_MOUSE) == 0) {
red_printf("VD_INTERFACE_MOUSE");
diff --git a/server/reds.h b/server/reds.h
index a2dadee..b5a4c71 100644
--- a/server/reds.h
+++ b/server/reds.h
@@ -62,6 +62,11 @@ struct SpiceInterfaceState {
void *opaque;
};
+typedef struct SpiceKbdState {
+ SpiceInterfaceState base;
+ SpiceKbdInterface *ki;
+} SpiceKbdState;
+
void reds_desable_mm_timer();
void reds_enable_mm_timer();
void reds_update_mm_timer(uint32_t mm_time);
@@ -76,5 +81,11 @@ extern uint64_t bitrate_per_sec;
#define IS_LOW_BANDWIDTH() (bitrate_per_sec < 10 * 1024 * 1024)
+#ifndef container_of
+#define container_of(ptr, type, member) ({ \
+ const typeof(((type *) 0)->member) *__mptr = (ptr); \
+ (type *) ((char *) __mptr - offsetof(type, member));})
+#endif
+
#endif
diff --git a/server/vd_interface.h b/server/vd_interface.h
index fb40bb0..9784360 100644
--- a/server/vd_interface.h
+++ b/server/vd_interface.h
@@ -192,20 +192,17 @@ struct QXLInterface {
int (*flush_resources)(QXLInterface *qxl);
};
-#define VD_INTERFACE_KEYBOARD "keyboard"
-#define VD_INTERFACE_KEYBOARD_MAJOR 1
-#define VD_INTERFACE_KEYBOARD_MINOR 1
-typedef struct KeyboardInterface KeyboardInterface;
+#define SPICE_INTERFACE_KEYBOARD "keyboard"
+#define SPICE_INTERFACE_KEYBOARD_MAJOR 1
+#define SPICE_INTERFACE_KEYBOARD_MINOR 1
+typedef struct SpiceKbdInterface SpiceKbdInterface;
typedef void (*keyborad_leads_notifier_t)(void *opaque, uint8_t leds);
-struct KeyboardInterface {
+struct SpiceKbdInterface {
SpiceBaseInterface base;
- void (*push_scan_freg)(KeyboardInterface *keyboard, uint8_t frag);
- uint8_t (*get_leds)(KeyboardInterface *keyboard);
- VDObjectRef (*register_leds_notifier)(KeyboardInterface *keyboard,
- keyborad_leads_notifier_t notifier, void *opaque);
- void (*unregister_leds_notifayer)(KeyboardInterface *keyboard, VDObjectRef notifier);
+ void (*push_scan_freg)(void *opaque, uint8_t frag);
+ uint8_t (*get_leds)(void *opaque);
};
#define VD_INTERFACE_MOUSE "mouse"
--
1.6.6.1
More information about the Spice-devel
mailing list