From patchwork Thu Mar 24 07:56:16 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Gerd Hoffmann X-Patchwork-Id: 8658711 Return-Path: X-Original-To: patchwork-qemu-devel@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork2.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.136]) by patchwork2.web.kernel.org (Postfix) with ESMTP id D2643C0553 for ; Thu, 24 Mar 2016 07:57:59 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id 04739202FF for ; Thu, 24 Mar 2016 07:57:59 +0000 (UTC) Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id F2386202E9 for ; Thu, 24 Mar 2016 07:57:57 +0000 (UTC) Received: from localhost ([::1]:48238 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aj09V-0008Gz-FW for patchwork-qemu-devel@patchwork.kernel.org; Thu, 24 Mar 2016 03:57:57 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:45311) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aj084-0005hG-V4 for qemu-devel@nongnu.org; Thu, 24 Mar 2016 03:56:30 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1aj080-0002bt-Dh for qemu-devel@nongnu.org; Thu, 24 Mar 2016 03:56:28 -0400 Received: from mx1.redhat.com ([209.132.183.28]:48208) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aj080-0002bD-5k for qemu-devel@nongnu.org; Thu, 24 Mar 2016 03:56:24 -0400 Received: from int-mx09.intmail.prod.int.phx2.redhat.com (int-mx09.intmail.prod.int.phx2.redhat.com [10.5.11.22]) by mx1.redhat.com (Postfix) with ESMTPS id BA9046314A for ; Thu, 24 Mar 2016 07:56:23 +0000 (UTC) Received: from nilsson.home.kraxel.org (ovpn-116-29.ams2.redhat.com [10.36.116.29]) by int-mx09.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id u2O7uL7J025113; Thu, 24 Mar 2016 03:56:22 -0400 Received: by nilsson.home.kraxel.org (Postfix, from userid 500) id 9534981873; Thu, 24 Mar 2016 08:56:20 +0100 (CET) From: Gerd Hoffmann To: qemu-devel@nongnu.org Date: Thu, 24 Mar 2016 08:56:16 +0100 Message-Id: <1458806178-31096-2-git-send-email-kraxel@redhat.com> In-Reply-To: <1458806178-31096-1-git-send-email-kraxel@redhat.com> References: <1458806178-31096-1-git-send-email-kraxel@redhat.com> X-Scanned-By: MIMEDefang 2.68 on 10.5.11.22 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.38]); Thu, 24 Mar 2016 07:56:23 +0000 (UTC) X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.132.183.28 Cc: Paolo Bonzini , Gerd Hoffmann Subject: [Qemu-devel] [PULL 1/3] input-linux: switch over to -object X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org X-Spam-Status: No, score=-6.9 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_HI, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP This patches makes input-linux use -object instead of a new command line switch. So, instead of the switch ... -input-linux /dev/input/event$nr ... you must create an object this way: -object input-linux,id=$name,evdev=/dev/input/event$nr Bonus is that you can hot-add and hot-remove them via monitor now. Suggested-by: Paolo Bonzini Signed-off-by: Gerd Hoffmann Reviewed-by: Paolo Bonzini Message-id: 1457681901-30916-1-git-send-email-kraxel@redhat.com --- qemu-options.hx | 9 ---- ui/input-linux.c | 158 +++++++++++++++++++++++++++++++++++++++++++------------ vl.c | 10 ---- 3 files changed, 123 insertions(+), 54 deletions(-) diff --git a/qemu-options.hx b/qemu-options.hx index 732ed8c..b98fa3e 100644 --- a/qemu-options.hx +++ b/qemu-options.hx @@ -1226,15 +1226,6 @@ STEXI Set the initial graphical resolution and depth (PPC, SPARC only). ETEXI -DEF("input-linux", 1, QEMU_OPTION_input_linux, - "-input-linux \n" - " Use input device.\n", QEMU_ARCH_ALL) -STEXI -@item -input-linux @var{dev} -@findex -input-linux -Use input device. -ETEXI - DEF("vnc", HAS_ARG, QEMU_OPTION_vnc , "-vnc display start a VNC server on display\n", QEMU_ARCH_ALL) STEXI diff --git a/ui/input-linux.c b/ui/input-linux.c index 2cf5d49..59d9348 100644 --- a/ui/input-linux.c +++ b/ui/input-linux.c @@ -10,6 +10,7 @@ #include "qemu/sockets.h" #include "sysemu/sysemu.h" #include "ui/input.h" +#include "qom/object_interfaces.h" #include #include "standard-headers/linux/input.h" @@ -127,10 +128,21 @@ static int qemu_input_linux_to_qcode(unsigned int lnx) return linux_to_qcode[lnx]; } +#define TYPE_INPUT_LINUX "input-linux" +#define INPUT_LINUX(obj) \ + OBJECT_CHECK(InputLinux, (obj), TYPE_INPUT_LINUX) +#define INPUT_LINUX_GET_CLASS(obj) \ + OBJECT_GET_CLASS(InputLinuxClass, (obj), TYPE_INPUT_LINUX) +#define INPUT_LINUX_CLASS(klass) \ + OBJECT_CLASS_CHECK(InputLinuxClass, (klass), TYPE_INPUT_LINUX) + typedef struct InputLinux InputLinux; +typedef struct InputLinuxClass InputLinuxClass; struct InputLinux { - const char *evdev; + Object parent; + + char *evdev; int fd; bool repeat; bool grab_request; @@ -139,9 +151,14 @@ struct InputLinux { bool keydown[KEY_CNT]; int keycount; int wheel; + bool initialized; QTAILQ_ENTRY(InputLinux) next; }; +struct InputLinuxClass { + ObjectClass parent_class; +}; + static QTAILQ_HEAD(, InputLinux) inputs = QTAILQ_HEAD_INITIALIZER(inputs); static void input_linux_toggle_grab(InputLinux *il) @@ -309,25 +326,21 @@ static void input_linux_event_mouse(void *opaque) } } -int input_linux_init(void *opaque, QemuOpts *opts, Error **errp) +static void input_linux_complete(UserCreatable *uc, Error **errp) { - InputLinux *il = g_new0(InputLinux, 1); + InputLinux *il = INPUT_LINUX(uc); uint32_t evtmap; int rc, ver; - il->evdev = qemu_opt_get(opts, "evdev"); - il->grab_all = qemu_opt_get_bool(opts, "grab-all", false); - il->repeat = qemu_opt_get_bool(opts, "repeat", false); - if (!il->evdev) { error_setg(errp, "no input device specified"); - goto err_free; + return; } il->fd = open(il->evdev, O_RDWR); if (il->fd < 0) { error_setg_file_open(errp, errno, il->evdev); - goto err_free; + return; } qemu_set_nonblock(il->fd); @@ -356,36 +369,111 @@ int input_linux_init(void *opaque, QemuOpts *opts, Error **errp) } input_linux_toggle_grab(il); QTAILQ_INSERT_TAIL(&inputs, il, next); - return 0; + il->initialized = true; + return; err_close: close(il->fd); -err_free: - g_free(il); - return -1; -} - -static QemuOptsList qemu_input_linux_opts = { - .name = "input-linux", - .head = QTAILQ_HEAD_INITIALIZER(qemu_input_linux_opts.head), - .implied_opt_name = "evdev", - .desc = { - { - .name = "evdev", - .type = QEMU_OPT_STRING, - },{ - .name = "grab-all", - .type = QEMU_OPT_BOOL, - },{ - .name = "repeat", - .type = QEMU_OPT_BOOL, - }, - { /* end of list */ } - }, + return; +} + +static void input_linux_instance_finalize(Object *obj) +{ + InputLinux *il = INPUT_LINUX(obj); + + if (il->initialized) { + QTAILQ_REMOVE(&inputs, il, next); + close(il->fd); + } + g_free(il->evdev); +} + +static char *input_linux_get_evdev(Object *obj, Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + return g_strdup(il->evdev); +} + +static void input_linux_set_evdev(Object *obj, const char *value, + Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + if (il->evdev) { + error_setg(errp, "evdev property already set"); + return; + } + il->evdev = g_strdup(value); +} + +static bool input_linux_get_grab_all(Object *obj, Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + return il->grab_all; +} + +static void input_linux_set_grab_all(Object *obj, bool value, + Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + il->grab_all = value; +} + +static bool input_linux_get_repeat(Object *obj, Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + return il->repeat; +} + +static void input_linux_set_repeat(Object *obj, bool value, + Error **errp) +{ + InputLinux *il = INPUT_LINUX(obj); + + il->repeat = value; +} + +static void input_linux_instance_init(Object *obj) +{ + object_property_add_str(obj, "evdev", + input_linux_get_evdev, + input_linux_set_evdev, NULL); + object_property_add_bool(obj, "grab_all", + input_linux_get_grab_all, + input_linux_set_grab_all, NULL); + object_property_add_bool(obj, "repeat", + input_linux_get_repeat, + input_linux_set_repeat, NULL); +} + +static void input_linux_class_init(ObjectClass *oc, void *data) +{ + UserCreatableClass *ucc = USER_CREATABLE_CLASS(oc); + + ucc->complete = input_linux_complete; +} + +static const TypeInfo input_linux_info = { + .name = TYPE_INPUT_LINUX, + .parent = TYPE_OBJECT, + .class_size = sizeof(InputLinuxClass), + .class_init = input_linux_class_init, + .instance_size = sizeof(InputLinux), + .instance_init = input_linux_instance_init, + .instance_finalize = input_linux_instance_finalize, + .interfaces = (InterfaceInfo[]) { + { TYPE_USER_CREATABLE }, + { } + } }; -static void input_linux_register_config(void) +static void register_types(void) { - qemu_add_opts(&qemu_input_linux_opts); + type_register_static(&input_linux_info); } -opts_init(input_linux_register_config); + +type_init(register_types); diff --git a/vl.c b/vl.c index 40ed4d0..ca49e75 100644 --- a/vl.c +++ b/vl.c @@ -3729,12 +3729,6 @@ int main(int argc, char **argv, char **envp) #endif break; } - case QEMU_OPTION_input_linux: - if (!qemu_opts_parse_noisily(qemu_find_opts("input-linux"), - optarg, true)) { - exit(1); - } - break; case QEMU_OPTION_no_acpi: acpi_enabled = 0; break; @@ -4598,10 +4592,6 @@ int main(int argc, char **argv, char **envp) qemu_spice_display_init(); } #endif -#ifdef CONFIG_LINUX - qemu_opts_foreach(qemu_find_opts("input-linux"), - input_linux_init, NULL, &error_fatal); -#endif if (foreach_device_config(DEV_GDB, gdbserver_start) < 0) { exit(1);