From: Vicki Pfau <vi@endrift.com>
To: Dmitry Torokhov <dmitry.torokhov@gmail.com>, linux-input@vger.kernel.org
Cc: Vicki Pfau <vi@endrift.com>
Subject: [PATCH v3 04/10] Input: xbox_gip - Add HID relaying
Date: Mon, 9 Mar 2026 22:19:58 -0700 [thread overview]
Message-ID: <20260310052017.1289494-5-vi@endrift.com> (raw)
In-Reply-To: <20260310052017.1289494-1-vi@endrift.com>
GIP allows tunneling of HID packets, with the HID descriptor embedded in
the GIP metadata exchanged during the initial handshake. This patch creates
a hid_device for this HID descriptor if found, as well as relaying the HID
packets.
Signed-off-by: Vicki Pfau <vi@endrift.com>
---
drivers/input/joystick/gip/gip-core.c | 95 ++++++++++++++++++++++++++-
drivers/input/joystick/gip/gip.h | 2 +
2 files changed, 94 insertions(+), 3 deletions(-)
diff --git a/drivers/input/joystick/gip/gip-core.c b/drivers/input/joystick/gip/gip-core.c
index 223668ca2b2a9..7355737b29d19 100644
--- a/drivers/input/joystick/gip/gip-core.c
+++ b/drivers/input/joystick/gip/gip-core.c
@@ -547,6 +547,54 @@ int gip_send_vendor_message(struct gip_attachment *attachment,
bytes, num_bytes);
}
+static int gip_hid_ll_parse(struct hid_device *hdev)
+{
+ struct gip_attachment *attachment = hdev->driver_data;
+
+ return hid_parse_report(hdev,
+ attachment->metadata.device.hid_descriptor,
+ attachment->metadata.device.hid_descriptor_size);
+}
+
+static int gip_hid_ll_start(struct hid_device *hdev)
+{
+ return 0;
+}
+
+static void gip_hid_ll_stop(struct hid_device *hdev)
+{
+}
+
+static int gip_hid_ll_open(struct hid_device *hdev)
+{
+ return 0;
+}
+
+static void gip_hid_ll_close(struct hid_device *hdev)
+{
+}
+
+static int gip_hid_ll_raw_request(struct hid_device *hdev,
+ unsigned char reportnum, uint8_t *buf, size_t count,
+ unsigned char report_type, int reqtype)
+{
+ /*
+ * TODO: Based on the metadata, output reports appear to be possible,
+ * but the chatpad doesn't have the LEDs it claims to support, so
+ * it's not clear how to test we're sending them properly.
+ */
+ return 0;
+}
+
+static const struct hid_ll_driver gip_hid_ll_driver = {
+ .parse = gip_hid_ll_parse,
+ .start = gip_hid_ll_start,
+ .stop = gip_hid_ll_stop,
+ .open = gip_hid_ll_open,
+ .close = gip_hid_ll_close,
+ .raw_request = gip_hid_ll_raw_request,
+};
+
static void gip_metadata_free(struct device *dev, struct gip_metadata *metadata)
{
devm_kfree(dev, metadata->device.audio_formats);
@@ -1350,8 +1398,36 @@ static int gip_send_init_sequence(struct gip_attachment *attachment)
if (rc)
return rc;
}
+ rc = 0;
- return 0;
+ if (attachment->metadata.device.hid_descriptor) {
+ struct hid_device *hdev = hid_allocate_device();
+
+ if (IS_ERR(hdev))
+ return PTR_ERR(hdev);
+
+ hdev->ll_driver = &gip_hid_ll_driver;
+ hdev->bus = BUS_USB;
+ hdev->vendor = attachment->vendor_id;
+ hdev->product = attachment->product_id;
+ hdev->dev.parent = GIP_DEV(attachment);
+ hdev->driver_data = attachment;
+ if (attachment->name)
+ strscpy(hdev->name, attachment->name);
+ else
+ strscpy(hdev->name, "Xbox Chatpad");
+ strscpy(hdev->phys, attachment->phys);
+ rc = hid_add_device(hdev);
+ if (rc) {
+ dev_err(GIP_DEV(attachment), "HID device add failed: %d\n", rc);
+ hid_destroy_device(hdev);
+ } else {
+ rcu_assign_pointer(attachment->hdev, hdev);
+ synchronize_rcu();
+ }
+ }
+
+ return rc;
}
static void gip_fragment_timeout(struct work_struct *work)
@@ -1784,9 +1860,16 @@ static int gip_handle_command_firmware(struct gip_attachment *attachment,
static int gip_handle_command_hid_report(struct gip_attachment *attachment,
const struct gip_header *header, uint8_t *bytes, int num_bytes)
{
- dev_warn(GIP_DEV(attachment), "Unimplemented HID report message\n");
+ struct hid_device *hdev;
- return -ENOTSUPP;
+ guard(rcu)();
+ hdev = rcu_dereference(attachment->hdev);
+ if (hdev)
+ return hid_input_report(hdev, HID_INPUT_REPORT, bytes, num_bytes, true);
+
+ dev_warn(GIP_DEV(attachment), "Got HID report with no HID descriptor\n");
+
+ return -EINVAL;
}
static int gip_handle_command_extended(struct gip_attachment *attachment,
@@ -2501,6 +2584,7 @@ static int gip_shutdown(struct gip_device *device)
for (i = 0; i < MAX_ATTACHMENTS; i++) {
struct gip_attachment *attachment = device->attachments[i];
struct input_dev *input;
+ struct hid_device *hdev;
if (!attachment)
continue;
@@ -2511,14 +2595,19 @@ static int gip_shutdown(struct gip_device *device)
rcu_read_lock();
input = rcu_dereference(attachment->input);
+ hdev = rcu_dereference(attachment->hdev);
rcu_read_unlock();
rcu_assign_pointer(attachment->input, NULL);
+ rcu_assign_pointer(attachment->hdev, NULL);
synchronize_rcu();
}
if (input)
input_unregister_device(input);
+
+ if (hdev)
+ hid_destroy_device(hdev);
}
return 0;
diff --git a/drivers/input/joystick/gip/gip.h b/drivers/input/joystick/gip/gip.h
index 63b4929b14e7f..c9d1c4f16c760 100644
--- a/drivers/input/joystick/gip/gip.h
+++ b/drivers/input/joystick/gip/gip.h
@@ -12,6 +12,7 @@
#ifndef _GIP_H
#define _GIP_H
+#include <linux/hid.h>
#ifdef CONFIG_JOYSTICK_XBOX_GIP_LEDS
#include <linux/led-class-multicolor.h>
#endif
@@ -221,6 +222,7 @@ struct gip_attachment {
int extra_axes;
bool dpad_as_buttons;
+ struct hid_device __rcu *hdev;
};
struct gip_urb {
--
2.53.0
next prev parent reply other threads:[~2026-03-10 5:20 UTC|newest]
Thread overview: 13+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-03-10 5:19 [PATCH v3 00/10] Input: xbox_gip - Add new driver for Xbox GIP Vicki Pfau
2026-03-10 5:19 ` [PATCH v3 01/10] " Vicki Pfau
2026-03-11 0:41 ` Vicki Pfau
2026-03-10 5:19 ` [PATCH v3 02/10] Input: xpad - Remove Xbox One support Vicki Pfau
2026-03-10 5:19 ` [PATCH v3 03/10] Input: xbox_gip - Add controllable LED support Vicki Pfau
2026-03-10 5:19 ` Vicki Pfau [this message]
2026-03-10 5:19 ` [PATCH v3 05/10] Input: xbox_gip - Add battery support Vicki Pfau
2026-03-10 5:20 ` [PATCH v3 06/10] Input: xbox_gip - Add arcade stick support Vicki Pfau
2026-03-10 5:20 ` [PATCH v3 07/10] Input: Add ABS_CLUTCH, HANDBRAKE, and SHIFTER Vicki Pfau
2026-03-10 5:20 ` [PATCH v3 08/10] HID: Map more automobile simulation inputs Vicki Pfau
2026-03-10 5:20 ` [PATCH v3 09/10] Input: xbox_gip - Add wheel support Vicki Pfau
2026-03-10 5:20 ` [PATCH v3 10/10] Input: xbox_gip - Add flight stick support Vicki Pfau
2026-03-10 5:23 ` Vicki Pfau
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260310052017.1289494-5-vi@endrift.com \
--to=vi@endrift.com \
--cc=dmitry.torokhov@gmail.com \
--cc=linux-input@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox