diff options
| author | Kimplul <kimi.h.kuparinen@gmail.com> | 2021-12-01 14:16:16 +0200 |
|---|---|---|
| committer | Kimplul <kimi.h.kuparinen@gmail.com> | 2021-12-01 14:16:16 +0200 |
| commit | 8c4e9e8635fcb84493ff583d0ef00a48a3eb796f (patch) | |
| tree | c0e44cb14ae6d5c65e42c52c99ebbaebe9f3fae6 | |
| parent | 4179def302185641a17ab66c835aca4a69f27825 (diff) | |
| download | hid-tmff2-8c4e9e8635fcb84493ff583d0ef00a48a3eb796f.tar.gz hid-tmff2-8c4e9e8635fcb84493ff583d0ef00a48a3eb796f.zip | |
Detect PS4 mode
FFB seems to be working, buttons are recognised but no input from wheel
rotation or pedals.
| -rw-r--r-- | hid-tmt300rs.c | 36 | ||||
| -rw-r--r-- | hid-tmt300rs.h | 93 |
2 files changed, 116 insertions, 13 deletions
diff --git a/hid-tmt300rs.c b/hid-tmt300rs.c index b08e838..4bd8bc3 100644 --- a/hid-tmt300rs.c +++ b/hid-tmt300rs.c @@ -3,19 +3,23 @@ static int timer_msecs = DEFAULT_TIMER_PERIOD; module_param(timer_msecs, int, 0660); -MODULE_PARM_DESC(timer_msecs, "Timer resolution in msecs"); +MODULE_PARM_DESC(timer_msecs, + "Timer resolution in msecs"); static int spring_level = 30; module_param(spring_level, int, 0); -MODULE_PARM_DESC(spring_level, "Level of spring force (0-100), as per Oversteer standards"); +MODULE_PARM_DESC(spring_level, + "Level of spring force (0-100), as per Oversteer standards"); static int damper_level = 30; module_param(damper_level, int, 0); -MODULE_PARM_DESC(damper_level, "Level of damper force (0-100), as per Oversteer standards"); +MODULE_PARM_DESC(damper_level, + "Level of damper force (0-100), as per Oversteer standards"); static int friction_level = 30; module_param(friction_level, int, 0); -MODULE_PARM_DESC(friction_level, "Level of friction force (0-100), as per Oversteer standards"); +MODULE_PARM_DESC(friction_level, + "Level of friction force (0-100), as per Oversteer standards"); static struct t300rs_device_entry *t300rs_get_device(struct hid_device *hdev) { @@ -41,12 +45,12 @@ static struct t300rs_device_entry *t300rs_get_device(struct hid_device *hdev) static int t300rs_send_int(struct t300rs_device_entry *t300rs) { int i; - for (i = 0; i < T300RS_BUFFER_LENGTH; ++i) + for (i = 0; i < t300rs->buffer_length; ++i) t300rs->ff_field->value[i] = t300rs->send_buffer[i]; hid_hw_request(t300rs->hdev, t300rs->report, HID_REQ_SET_REPORT); - memset(t300rs->send_buffer, 0, T300RS_BUFFER_LENGTH); + memset(t300rs->send_buffer, 0, t300rs->buffer_length); return 0; } @@ -1447,7 +1451,12 @@ static int t300rs_init(struct hid_device *hdev, const signed short *ff_bits) goto states_err; } - t300rs->send_buffer = kzalloc(T300RS_BUFFER_LENGTH, GFP_KERNEL); + if(hdev->product == 0xb66d) + t300rs->buffer_length = T300RS_PS4_BUFFER_LENGTH; + else + t300rs->buffer_length = T300RS_NORM_BUFFER_LENGTH; + + t300rs->send_buffer = kzalloc(t300rs->buffer_length, GFP_KERNEL); if (!t300rs->send_buffer) { ret = -ENOMEM; goto send_err; @@ -1627,12 +1636,19 @@ static void t300rs_remove(struct hid_device *hdev) kfree(drv_data); } -static __u8 *t300rs_report_fixup(struct hid_device *hdev, __u8 *rdesc, unsigned int *rsize) +static __u8 *t300rs_report_fixup(struct hid_device *hdev, __u8 *rdesc, + unsigned int *rsize) { if(hdev->product == 0xb66e) { + /* PS3 normal mode */ rdesc = t300rs_rdesc_nrm_fixed; *rsize = sizeof(t300rs_rdesc_nrm_fixed); - } else { + } else if (hdev->product == 0xb66d){ + /* PS4 normal mode */ + rdesc = t300rs_rdesc_ps4_fixed; + *rsize = sizeof(t300rs_rdesc_ps4_fixed); + } else if (hdev->product == 0xb66f){ + /* PS3 advanced mode */ rdesc = t300rs_rdesc_adv_fixed; *rsize = sizeof(t300rs_rdesc_adv_fixed); } @@ -1645,6 +1661,8 @@ static const struct hid_device_id t300rs_devices[] = { .driver_data = (unsigned long)t300rs_ff_effects}, {HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb66f), .driver_data = (unsigned long)t300rs_ff_effects}, + {HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb66d), + .driver_data = (unsigned long)t300rs_ff_effects}, {} }; MODULE_DEVICE_TABLE(hid, t300rs_devices); diff --git a/hid-tmt300rs.h b/hid-tmt300rs.h index 9ffd87c..3c3a3a9 100644 --- a/hid-tmt300rs.h +++ b/hid-tmt300rs.h @@ -13,7 +13,8 @@ #define USB_VENDOR_ID_THRUSTMASTER 0x044f #define T300RS_MAX_EFFECTS 16 -#define T300RS_BUFFER_LENGTH 63 +#define T300RS_NORM_BUFFER_LENGTH 63 +#define T300RS_PS4_BUFFER_LENGTH 31 /* the wheel seems to only be capable of processing a certain number of * interrupts per second, and if this value is too low the kernel urb buffer(or @@ -126,6 +127,7 @@ struct t300rs_device_entry { spinlock_t lock; unsigned long lock_flags; + u8 buffer_length; u8 *send_buffer; u16 range; @@ -140,7 +142,7 @@ struct t300rs_data { void *device_props; }; -static __u8 t300rs_rdesc_nrm_fixed[] = { +static u8 t300rs_rdesc_nrm_fixed[] = { 0x05, 0x01, /* Usage page (Generic Desktop) */ 0x09, 0x04, /* Usage (Joystick) */ 0xa1, 0x01, /* Collection (Application) */ @@ -205,7 +207,7 @@ static __u8 t300rs_rdesc_nrm_fixed[] = { 0xc0, /* End collection */ }; -static __u8 t300rs_rdesc_adv_fixed[] = { +static u8 t300rs_rdesc_adv_fixed[] = { 0x05, 0x01, /* Usage page (Generic Desktop) */ 0x09, 0x04, /* Usage (Joystick) */ 0xa1, 0x01, /* Collection (Application) */ @@ -243,7 +245,7 @@ static __u8 t300rs_rdesc_adv_fixed[] = { 0x05, 0x01, /* Usage page (Generic Desktop) */ 0x09, 0x39, /* Usage (Hat Switch) */ 0x25, 0x07, /* Logical maximum (7) */ - 0x46, 0x3b, 0x01, /* Physical maximum (315) */ + 0x46, 0x3b, 0x01, /* Physical maximum (315) */ 0x55, 0x00, /* Unit exponent (0) */ 0x65, 0x14, /* Unit (Eng Rot, Angular Pos) */ 0x75, 0x04, /* Report size (4) */ @@ -267,6 +269,89 @@ static __u8 t300rs_rdesc_adv_fixed[] = { 0xc0, /* End collection */ }; +static u8 t300rs_rdesc_ps4_fixed[] = { + 0x05, 0x01, /* Usage page (Generic Desktop) */ + 0x09, 0x05, /* Usage (GamePad) */ + 0xa1, 0x01, /* Collection (Application) */ + 0x85, 0x01, /* Report ID (1) */ + 0x09, 0x30, /* Usage (X) */ + 0x09, 0x31, /* Usage (Y) */ + 0x09, 0x32, /* Usage (Z) */ + 0x09, 0x35, /* Usage (Rz) */ + 0x15, 0x00, /* Logical minimum (0) */ + 0x26, 0xff, 0x00, /* Logical maximum (255) */ + 0x75, 0x08, /* Report size (8) */ + 0x95, 0x04, /* Report count (4) */ + 0x81, 0x02, /* Input (Variable, Absolute) */ + 0x09, 0x39, /* Usage (Hat Switch) */ + 0x15, 0x00, /* Logical minimum (0) */ + 0x25, 0x07, /* Logical maximum (7)*/ + 0x35, 0x00, /* Physical minimum (0) */ + 0x46, 0x3b, 0x01, /* Physical maximum (315) */ + 0x65, 0x14, /* Unit (Eng Rot, Angular Pos) */ + 0x75, 0x04, /* Report size (4) */ + 0x95, 0x01, /* Report count (1) */ + 0x81, 0x42, /* Input (Variable, Absolute, NullState) */ + 0x65, 0x00, /* Input (None) */ + 0x05, 0x09, /* Usage page (Button) */ + 0x19, 0x01, /* Usage minimum (1) */ + 0x29, 0x0e, /* Usage maximum (14) */ + 0x15, 0x00, /* Logical minimum (0) */ + 0x25, 0x01, /* Logical maximum (1) */ + 0x75, 0x01, /* Report size (1) */ + 0x95, 0x0e, /* Report size (14) */ + 0x81, 0x02, /* Input (Variable, Absolute) */ + 0x06, 0x00, 0xff, /* Usage page (Vendor 1) */ + 0x09, 0x20, /* Usage (32) */ + 0x75, 0x06, /* Report size (6) */ + 0x95, 0x01, /* Report count (1) */ + 0x81, 0x02, /* Input (Variable, Absolute) */ + 0x05, 0x01, /* Usage page (Generic Desktop) */ + 0x09, 0x33, /* Usage (Rx) */ + 0x09, 0x34, /* Usage (Ry) */ + 0x15, 0x00, /* Logical minimum (0) */ + 0x26, 0xff, 0x00, /* Logical maximum (255) */ + 0x75, 0x08, /* Report size (8) */ + 0x95, 0x02, /* Report count (2) */ + 0x81, 0x02, /* Input (Variable, Absolute) */ + 0x06, 0x00, 0xff, /* Usage page (Vendor 1) */ + 0x09, 0x21, /* Usage (33) */ + 0x95, 0x36, /* Report count (54) */ + 0x81, 0x02, /* Input (Variable, Absolute) */ + 0x85, 0x60, /* Report ID (5) (change to 0x60?) */ + 0x09, 0x60, /* Usage (34) (change to 0x60?) */ + 0x95, 0x1f, /* Report count (31) () */ + 0x91, 0x02, /* Output (Variable, Absolute) */ + 0x85, 0x03, /* Report ID (3) */ + 0x0a, 0x21, 0x27, /* ??? */ + 0x95, 0x2f, /* Report count (47) */ + 0xb1, 0x02, /* Feature (Data, Var, Abs) */ + 0xc0, /* End collection */ + + /* From here on out no clue */ + 0x06, 0xf0, + 0xff, 0x09, + 0x40, 0xa1, + 0x01, 0x85, + 0xf0, 0x09, + 0x47, 0x95, + 0x3f, 0xb1, + 0x02, 0x85, + 0xf1, 0x09, + 0x48, 0x95, + 0x3f, 0xb1, + 0x02, 0x85, + 0xf2, 0x09, + 0x49, 0x95, + 0x0f, 0xb1, + 0x02, 0x85, + 0xf3, 0x0a, + 0x01, 0x47, + 0x95, 0x07, + 0xb1, 0x02, + 0xc0, +}; + static u8 spring_values[] = { 0xa6, 0x6a, 0xa6, 0x6a, 0xfe, 0xff, 0xfe, 0xff, 0xfe, 0xff, |
