On Wed, May 25, 2011 at 05:37:53PM +0800, Lai Jiangshan wrote:
It make send-key command more friendly for user.
Signed-off-by: Lai Jiangshan <laijs(a)fujitsu.com>
---
include/libvirt/virtkeys.h | 253 ++++++++++++++++++++++++++++++++++++++++++++
tools/virsh.c | 21 ++++
2 files changed, 274 insertions(+), 0 deletions(-)
diff --git a/include/libvirt/virtkeys.h b/include/libvirt/virtkeys.h
index eb07129..7893450 100644
--- a/include/libvirt/virtkeys.h
+++ b/include/libvirt/virtkeys.h
@@ -20,4 +20,257 @@ enum libvirt_keycode_set {
#define MAX_SEND_KEY 16
+#define ITEM_KEYCODE(KEY_XXX) VIRT##KEY_XXX
+#define KEYCODES() \
+ keycode(KEY_ESC, 1)\
+ keycode(KEY_1, 2)\
+ keycode(KEY_2, 3)\
+ keycode(KEY_3, 4)\
+ keycode(KEY_4, 5)\
+ keycode(KEY_5, 6)\
+ keycode(KEY_6, 7)\
+ keycode(KEY_7, 8)\
+ keycode(KEY_8, 9)\
+ keycode(KEY_9, 10)\
+ keycode(KEY_0, 11)\
+ keycode(KEY_MINUS, 12)\
+ keycode(KEY_EQUAL, 13)\
+ keycode(KEY_BACKSPACE, 14)\
+ keycode(KEY_TAB, 15)\
+ keycode(KEY_Q, 16)\
+ keycode(KEY_W, 17)\
+ keycode(KEY_E, 18)\
+ keycode(KEY_R, 19)\
+ keycode(KEY_T, 20)\
+ keycode(KEY_Y, 21)\
+ keycode(KEY_U, 22)\
+ keycode(KEY_I, 23)\
+ keycode(KEY_O, 24)\
+ keycode(KEY_P, 25)\
+ keycode(KEY_LEFTBRACE, 26)\
+ keycode(KEY_RIGHTBRACE, 27)\
+ keycode(KEY_ENTER, 28)\
+ keycode(KEY_LEFTCTRL, 29)\
+ keycode(KEY_A, 30)\
+ keycode(KEY_S, 31)\
+ keycode(KEY_D, 32)\
+ keycode(KEY_F, 33)\
+ keycode(KEY_G, 34)\
+ keycode(KEY_H, 35)\
+ keycode(KEY_J, 36)\
+ keycode(KEY_K, 37)\
+ keycode(KEY_L, 38)\
+ keycode(KEY_SEMICOLON, 39)\
+ keycode(KEY_APOSTROPHE, 40)\
+ keycode(KEY_GRAVE, 41)\
+ keycode(KEY_LEFTSHIFT, 42)\
+ keycode(KEY_BACKSLASH, 43)\
+ keycode(KEY_Z, 44)\
+ keycode(KEY_X, 45)\
+ keycode(KEY_C, 46)\
+ keycode(KEY_V, 47)\
+ keycode(KEY_B, 48)\
+ keycode(KEY_N, 49)\
+ keycode(KEY_M, 50)\
+ keycode(KEY_COMMA, 51)\
+ keycode(KEY_DOT, 52)\
+ keycode(KEY_SLASH, 53)\
+ keycode(KEY_RIGHTSHIFT, 54)\
+ keycode(KEY_KPASTERISK, 55)\
+ keycode(KEY_LEFTALT, 56)\
+ keycode(KEY_SPACE, 57)\
+ keycode(KEY_CAPSLOCK, 58)\
+ keycode(KEY_F1, 59)\
+ keycode(KEY_F2, 60)\
+ keycode(KEY_F3, 61)\
+ keycode(KEY_F4, 62)\
+ keycode(KEY_F5, 63)\
+ keycode(KEY_F6, 64)\
+ keycode(KEY_F7, 65)\
+ keycode(KEY_F8, 66)\
+ keycode(KEY_F9, 67)\
+ keycode(KEY_F10, 68)\
+ keycode(KEY_NUMLOCK, 69)\
+ keycode(KEY_SCROLLLOCK, 70)\
+ keycode(KEY_KP7, 71)\
+ keycode(KEY_KP8, 72)\
+ keycode(KEY_KP9, 73)\
+ keycode(KEY_KPMINUS, 74)\
+ keycode(KEY_KP4, 75)\
+ keycode(KEY_KP5, 76)\
+ keycode(KEY_KP6, 77)\
+ keycode(KEY_KPPLUS, 78)\
+ keycode(KEY_KP1, 79)\
+ keycode(KEY_KP2, 80)\
+ keycode(KEY_KP3, 81)\
+ keycode(KEY_KP0, 82)\
+ keycode(KEY_KPDOT, 83)\
+ keycode(KEY_ZENKAKUHANKAKU, 85)\
+ keycode(KEY_102ND, 86)\
+ keycode(KEY_F11, 87)\
+ keycode(KEY_F12, 88)\
+ keycode(KEY_RO, 89)\
+ keycode(KEY_KATAKANA, 90)\
+ keycode(KEY_HIRAGANA, 91)\
+ keycode(KEY_HENKAN, 92)\
+ keycode(KEY_KATAKANAHIRAGANA, 93)\
+ keycode(KEY_MUHENKAN, 94)\
+ keycode(KEY_KPJPCOMMA, 95)\
+ keycode(KEY_KPENTER, 96)\
+ keycode(KEY_RIGHTCTRL, 97)\
+ keycode(KEY_KPSLASH, 98)\
+ keycode(KEY_SYSRQ, 99)\
+ keycode(KEY_RIGHTALT, 100)\
+ keycode(KEY_LINEFEED, 101)\
+ keycode(KEY_HOME, 102)\
+ keycode(KEY_UP, 103)\
+ keycode(KEY_PAGEUP, 104)\
+ keycode(KEY_LEFT, 105)\
+ keycode(KEY_RIGHT, 106)\
+ keycode(KEY_END, 107)\
+ keycode(KEY_DOWN, 108)\
+ keycode(KEY_PAGEDOWN, 109)\
+ keycode(KEY_INSERT, 110)\
+ keycode(KEY_DELETE, 111)\
+ keycode(KEY_MACRO, 112)\
+ keycode(KEY_MUTE, 113)\
+ keycode(KEY_VOLUMEDOWN, 114)\
+ keycode(KEY_VOLUMEUP, 115)\
+ keycode(KEY_POWER, 116)\
+ keycode(KEY_KPEQUAL, 117)\
+ keycode(KEY_KPPLUSMINUS, 118)\
+ keycode(KEY_PAUSE, 119)\
+ keycode(KEY_SCALE, 120)\
+ keycode(KEY_KPCOMMA, 121)\
+ keycode(KEY_HANGEUL, 122)\
+ keycode(KEY_HANGUEL, 122)\
+ keycode(KEY_HANJA, 123)\
+ keycode(KEY_YEN, 124)\
+ keycode(KEY_LEFTMETA, 125)\
+ keycode(KEY_RIGHTMETA, 126)\
+ keycode(KEY_COMPOSE, 127)\
+ keycode(KEY_STOP, 128)\
+ keycode(KEY_AGAIN, 129)\
+ keycode(KEY_PROPS, 130)\
+ keycode(KEY_UNDO, 131)\
+ keycode(KEY_FRONT, 132)\
+ keycode(KEY_COPY, 133)\
+ keycode(KEY_OPEN, 134)\
+ keycode(KEY_PASTE, 135)\
+ keycode(KEY_FIND, 136)\
+ keycode(KEY_CUT, 137)\
+ keycode(KEY_HELP, 138)\
+ keycode(KEY_MENU, 139)\
+ keycode(KEY_CALC, 140)\
+ keycode(KEY_SETUP, 141)\
+ keycode(KEY_SLEEP, 142)\
+ keycode(KEY_WAKEUP, 143)\
+ keycode(KEY_FILE, 144)\
+ keycode(KEY_SENDFILE, 145)\
+ keycode(KEY_DELETEFILE, 146)\
+ keycode(KEY_XFER, 147)\
+ keycode(KEY_PROG1, 148)\
+ keycode(KEY_PROG2, 149)\
+ keycode(KEY_WWW, 150)\
+ keycode(KEY_MSDOS, 151)\
+ keycode(KEY_COFFEE, 152)\
+ keycode(KEY_SCREENLOCK, 152)\
+ keycode(KEY_DIRECTION, 153)\
+ keycode(KEY_CYCLEWINDOWS, 154)\
+ keycode(KEY_MAIL, 155)\
+ keycode(KEY_BOOKMARKS, 156)\
+ keycode(KEY_COMPUTER, 157)\
+ keycode(KEY_BACK, 158)\
+ keycode(KEY_FORWARD, 159)\
+ keycode(KEY_CLOSECD, 160)\
+ keycode(KEY_EJECTCD, 161)\
+ keycode(KEY_EJECTCLOSECD, 162)\
+ keycode(KEY_NEXTSONG, 163)\
+ keycode(KEY_PLAYPAUSE, 164)\
+ keycode(KEY_PREVIOUSSONG, 165)\
+ keycode(KEY_STOPCD, 166)\
+ keycode(KEY_RECORD, 167)\
+ keycode(KEY_REWIND, 168)\
+ keycode(KEY_PHONE, 169)\
+ keycode(KEY_ISO, 170)\
+ keycode(KEY_CONFIG, 171)\
+ keycode(KEY_HOMEPAGE, 172)\
+ keycode(KEY_REFRESH, 173)\
+ keycode(KEY_EXIT, 174)\
+ keycode(KEY_MOVE, 175)\
+ keycode(KEY_EDIT, 176)\
+ keycode(KEY_SCROLLUP, 177)\
+ keycode(KEY_SCROLLDOWN, 178)\
+ keycode(KEY_KPLEFTPAREN, 179)\
+ keycode(KEY_KPRIGHTPAREN, 180)\
+ keycode(KEY_NEW, 181)\
+ keycode(KEY_REDO, 182)\
+ keycode(KEY_F13, 183)\
+ keycode(KEY_F14, 184)\
+ keycode(KEY_F15, 185)\
+ keycode(KEY_F16, 186)\
+ keycode(KEY_F17, 187)\
+ keycode(KEY_F18, 188)\
+ keycode(KEY_F19, 189)\
+ keycode(KEY_F20, 190)\
+ keycode(KEY_F21, 191)\
+ keycode(KEY_F22, 192)\
+ keycode(KEY_F23, 193)\
+ keycode(KEY_F24, 194)\
+ keycode(KEY_PLAYCD, 200)\
+ keycode(KEY_PAUSECD, 201)\
+ keycode(KEY_PROG3, 202)\
+ keycode(KEY_PROG4, 203)\
+ keycode(KEY_DASHBOARD, 204)\
+ keycode(KEY_SUSPEND, 205)\
+ keycode(KEY_CLOSE, 206)\
+ keycode(KEY_PLAY, 207)\
+ keycode(KEY_FASTFORWARD, 208)\
+ keycode(KEY_BASSBOOST, 209)\
+ keycode(KEY_PRINT, 210)\
+ keycode(KEY_HP, 211)\
+ keycode(KEY_CAMERA, 212)\
+ keycode(KEY_SOUND, 213)\
+ keycode(KEY_QUESTION, 214)\
+ keycode(KEY_EMAIL, 215)\
+ keycode(KEY_CHAT, 216)\
+ keycode(KEY_SEARCH, 217)\
+ keycode(KEY_CONNECT, 218)\
+ keycode(KEY_FINANCE, 219)\
+ keycode(KEY_SPORT, 220)\
+ keycode(KEY_SHOP, 221)\
+ keycode(KEY_ALTERASE, 222)\
+ keycode(KEY_CANCEL, 223)\
+ keycode(KEY_BRIGHTNESSDOWN, 224)\
+ keycode(KEY_BRIGHTNESSUP, 225)\
+ keycode(KEY_MEDIA, 226)\
+ keycode(KEY_SWITCHVIDEOMODE, 227)\
+ keycode(KEY_KBDILLUMTOGGLE, 228)\
+ keycode(KEY_KBDILLUMDOWN, 229)\
+ keycode(KEY_KBDILLUMUP, 230)\
+ keycode(KEY_SEND, 231)\
+ keycode(KEY_REPLY, 232)\
+ keycode(KEY_FORWARDMAIL, 233)\
+ keycode(KEY_SAVE, 234)\
+ keycode(KEY_DOCUMENTS, 235)\
+ keycode(KEY_BATTERY, 236)\
+ keycode(KEY_BLUETOOTH, 237)\
+ keycode(KEY_WLAN, 238)\
+ keycode(KEY_UWB, 239)\
+ keycode(KEY_UNKNOWN, 240)\
+ keycode(KEY_VIDEO_NEXT, 241)\
+ keycode(KEY_VIDEO_PREV, 242)\
+ keycode(KEY_BRIGHTNESS_CYCLE, 243)\
+ keycode(KEY_BRIGHTNESS_ZERO, 244)\
+ keycode(KEY_DISPLAY_OFF, 245)\
+ keycode(KEY_WIMAX, 246)\
+ keycode(KEY_RFKILL, 247)
+
+/* define keycode constants */
+enum {
+#define keycode(KEY_XXX, value) ITEM_KEYCODE(KEY_XXX) = value,
+ KEYCODES()
+#undef keycode
+};
+
#endif
diff --git a/tools/virsh.c b/tools/virsh.c
index 505a821..3bccc08 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -3017,9 +3017,16 @@ cmdInjectNMI(vshControl *ctl, const vshCmd *cmd)
static const vshCmdInfo info_send_key[] = {
{"help", N_("Send keycodes to the guest")},
{"desc", N_("Send keycodes to the guest, the keycodes must be
integers\n"
+ " or the KEY_* strings listed below for the \"linux\"
codeset.\n\n"
" Examples:\n\n"
" virsh # send-key <domain> 37 18 21\n"
" virsh # send-key <domain> --holdtime 1000 0x15 18
0xf\n"
+ " virsh # send-eky <domain> KEY_LEFTCTRL KEY_LEFTALT
KEY_F1\n"
+ "\n"
+ " KEY_XXX strings for the \"linux\" codeset:\n"
+#define keycode(var, value) " " #var " = " #value
"\n"
+ KEYCODES())},
+#undef keycode
{NULL, NULL}
};
@@ -3032,6 +3039,17 @@ static const vshCmdOptDef opts_send_key[] = {
{NULL, 0, 0, NULL}
};
+static int get_linux_keycode(const char *key_name)
+{
+ if (key_name[0] == 'K' && key_name[1] == 'E' &&
key_name[2] == 'Y' &&
+ key_name[3] == '_') {
+#define keycode(var, value) if (STREQ(#var + 4, key_name + 4)) return value;
+ KEYCODES()
+#undef keycode
+ }
+ return -1;
+}
+
static int get_integer_keycode(const char *key_name)
{
long val;
@@ -3092,6 +3110,9 @@ cmdSendKey(vshControl *ctl, const vshCmd *cmd)
goto free_domain;
}
+ if ((keycode = get_linux_keycode(opt->data)) > 0)
+ goto get_keycode;
+
if ((keycode = get_integer_keycode(opt->data)) > 0)
goto get_keycode;
Rather than hardcode two big tables in the source code I would like to
have all these keycode tables automatically generated, from a master
data file in the source tree.
For the GTK-VNC application, I constructed a giant CSV data file which
has mappings for all common keycode sets.
http://git.gnome.org/browse/gtk-vnc/tree/src/keymaps.csv
Copy this csv file into the libvirt source tree.
I also have a script which takes the CSV file and can generate big
tables for mapping between 2 different keycode sets:
http://git.gnome.org/browse/gtk-vnc/tree/src/keymap-gen.pl
You can take that keymap-gen.pl script and extend the code, so that it
can also generate the data for virtkeys.h
Eventually, I'll move the keymaps.csv/keymap-gen.pl into a separate
project, which can be packaged up & shared between libvirt, gtk-vnc
and spice-gtk, so we only have one place to update keycode mappings
Regards,
Daniel
--
|:
http://berrange.com -o-
http://www.flickr.com/photos/dberrange/ :|
|:
http://libvirt.org -o-
http://virt-manager.org :|
|:
http://autobuild.org -o-
http://search.cpan.org/~danberr/ :|
|:
http://entangle-photo.org -o-
http://live.gnome.org/gtk-vnc :|