diff mbox series

Add support for abs info in vhost-user-input

Message ID 20240322102421.2158139-1-christian.poetzsch@kernkonzept.com
State New
Headers show
Series Add support for abs info in vhost-user-input | expand

Commit Message

Christian Pötzsch March 22, 2024, 10:24 a.m. UTC
Absolute input device did not work, cause VIRTIO_INPUT_CFG_ABS_INFO is
missing. Fetch this info when available and provide it to any virtio
client.

This is basically the same code as in hw/input/virtio-input-host.c, just
modified to work here.

Signed-off-by: Christian Pötzsch <christian.poetzsch@kernkonzept.com>
---
 contrib/vhost-user-input/main.c | 46 +++++++++++++++++++++++++++++++--
 1 file changed, 44 insertions(+), 2 deletions(-)

Comments

Christian Pötzsch April 26, 2024, 8:06 a.m. UTC | #1
Ping. Anyone interested?

Thanks
Chris

On 3/22/24 11:24, Christian Pötzsch wrote:
> Absolute input device did not work, cause VIRTIO_INPUT_CFG_ABS_INFO is
> missing. Fetch this info when available and provide it to any virtio
> client.
> 
> This is basically the same code as in hw/input/virtio-input-host.c, just
> modified to work here.
> 
> Signed-off-by: Christian Pötzsch <christian.poetzsch@kernkonzept.com>
> ---
>   contrib/vhost-user-input/main.c | 46 +++++++++++++++++++++++++++++++--
>   1 file changed, 44 insertions(+), 2 deletions(-)
> 
> diff --git a/contrib/vhost-user-input/main.c b/contrib/vhost-user-input/main.c
> index 081230da54..9506e34d04 100644
> --- a/contrib/vhost-user-input/main.c
> +++ b/contrib/vhost-user-input/main.c
> @@ -272,6 +272,32 @@ vi_bits_config(VuInput *vi, int type, int count)
>       g_array_append_val(vi->config, bits);
>   }
>   
> +static void
> +vi_input_abs_config(VuInput *vi, int axis)
> +{
> +    virtio_input_config config;
> +    struct input_absinfo absinfo;
> +    int rc;
> +
> +    rc = ioctl(vi->evdevfd, EVIOCGABS(axis), &absinfo);
> +    if (rc < 0) {
> +        return;
> +    }
> +
> +    memset(&config, 0, sizeof(config));
> +    config.select = VIRTIO_INPUT_CFG_ABS_INFO;
> +    config.subsel = axis;
> +    config.size   = sizeof(struct input_absinfo);
> +
> +    config.u.abs.min  = cpu_to_le32(absinfo.minimum);
> +    config.u.abs.max  = cpu_to_le32(absinfo.maximum);
> +    config.u.abs.fuzz = cpu_to_le32(absinfo.fuzz);
> +    config.u.abs.flat = cpu_to_le32(absinfo.flat);
> +    config.u.abs.res  = cpu_to_le32(absinfo.resolution);
> +
> +    g_array_append_val(vi->config, config);
> +}
> +
>   static char *opt_evdev;
>   static int opt_fdnum = -1;
>   static char *opt_socket_path;
> @@ -297,11 +323,12 @@ main(int argc, char *argv[])
>   {
>       GMainLoop *loop = NULL;
>       VuInput vi = { 0, };
> -    int rc, ver, fd;
> -    virtio_input_config id;
> +    int rc, ver, fd, i, axis;
> +    virtio_input_config id, *abs;
>       struct input_id ids;
>       GError *error = NULL;
>       GOptionContext *context;
> +    uint8_t byte;
>   
>       context = g_option_context_new(NULL);
>       g_option_context_add_main_entries(context, entries, NULL);
> @@ -375,6 +402,21 @@ main(int argc, char *argv[])
>       vi_bits_config(&vi, EV_ABS, ABS_CNT);
>       vi_bits_config(&vi, EV_MSC, MSC_CNT);
>       vi_bits_config(&vi, EV_SW,  SW_CNT);
> +
> +    abs = vi_find_config(&vi, VIRTIO_INPUT_CFG_EV_BITS, EV_ABS);
> +    if (abs) {
> +        for (i = 0; i < abs->size; i++) {
> +            byte = abs->u.bitmap[i];
> +            axis = 8 * i;
> +            while (byte) {
> +                if (byte & 1) {
> +                    vi_input_abs_config(&vi, axis);
> +                }
> +                axis++;
> +                byte >>= 1;
> +            }
> +        }
> +    }
>       g_debug("config length: %u", vi.config->len);
>   
>       if (opt_socket_path) {
diff mbox series

Patch

diff --git a/contrib/vhost-user-input/main.c b/contrib/vhost-user-input/main.c
index 081230da54..9506e34d04 100644
--- a/contrib/vhost-user-input/main.c
+++ b/contrib/vhost-user-input/main.c
@@ -272,6 +272,32 @@  vi_bits_config(VuInput *vi, int type, int count)
     g_array_append_val(vi->config, bits);
 }
 
+static void
+vi_input_abs_config(VuInput *vi, int axis)
+{
+    virtio_input_config config;
+    struct input_absinfo absinfo;
+    int rc;
+
+    rc = ioctl(vi->evdevfd, EVIOCGABS(axis), &absinfo);
+    if (rc < 0) {
+        return;
+    }
+
+    memset(&config, 0, sizeof(config));
+    config.select = VIRTIO_INPUT_CFG_ABS_INFO;
+    config.subsel = axis;
+    config.size   = sizeof(struct input_absinfo);
+
+    config.u.abs.min  = cpu_to_le32(absinfo.minimum);
+    config.u.abs.max  = cpu_to_le32(absinfo.maximum);
+    config.u.abs.fuzz = cpu_to_le32(absinfo.fuzz);
+    config.u.abs.flat = cpu_to_le32(absinfo.flat);
+    config.u.abs.res  = cpu_to_le32(absinfo.resolution);
+
+    g_array_append_val(vi->config, config);
+}
+
 static char *opt_evdev;
 static int opt_fdnum = -1;
 static char *opt_socket_path;
@@ -297,11 +323,12 @@  main(int argc, char *argv[])
 {
     GMainLoop *loop = NULL;
     VuInput vi = { 0, };
-    int rc, ver, fd;
-    virtio_input_config id;
+    int rc, ver, fd, i, axis;
+    virtio_input_config id, *abs;
     struct input_id ids;
     GError *error = NULL;
     GOptionContext *context;
+    uint8_t byte;
 
     context = g_option_context_new(NULL);
     g_option_context_add_main_entries(context, entries, NULL);
@@ -375,6 +402,21 @@  main(int argc, char *argv[])
     vi_bits_config(&vi, EV_ABS, ABS_CNT);
     vi_bits_config(&vi, EV_MSC, MSC_CNT);
     vi_bits_config(&vi, EV_SW,  SW_CNT);
+
+    abs = vi_find_config(&vi, VIRTIO_INPUT_CFG_EV_BITS, EV_ABS);
+    if (abs) {
+        for (i = 0; i < abs->size; i++) {
+            byte = abs->u.bitmap[i];
+            axis = 8 * i;
+            while (byte) {
+                if (byte & 1) {
+                    vi_input_abs_config(&vi, axis);
+                }
+                axis++;
+                byte >>= 1;
+            }
+        }
+    }
     g_debug("config length: %u", vi.config->len);
 
     if (opt_socket_path) {