···11+ HID I/O Transport Drivers22+ ===========================33+44+The HID subsystem is independent of the underlying transport driver. Initially,55+only USB was supported, but other specifications adopted the HID design and66+provided new transport drivers. The kernel includes at least support for USB,77+Bluetooth, I2C and user-space I/O drivers.88+99+1) HID Bus1010+==========1111+1212+The HID subsystem is designed as a bus. Any I/O subsystem may provide HID1313+devices and register them with the HID bus. HID core then loads generic device1414+drivers on top of it. The transport drivers are responsible of raw data1515+transport and device setup/management. HID core is responsible of1616+report-parsing, report interpretation and the user-space API. Device specifics1717+and quirks are handled by all layers depending on the quirk.1818+1919+ +-----------+ +-----------+ +-----------+ +-----------+2020+ | Device #1 | | Device #i | | Device #j | | Device #k |2121+ +-----------+ +-----------+ +-----------+ +-----------+2222+ \\ // \\ //2323+ +------------+ +------------+2424+ | I/O Driver | | I/O Driver |2525+ +------------+ +------------+2626+ || ||2727+ +------------------+ +------------------+2828+ | Transport Driver | | Transport Driver |2929+ +------------------+ +------------------+3030+ \___ ___/3131+ \ /3232+ +----------------+3333+ | HID Core |3434+ +----------------+3535+ / | | \3636+ / | | \3737+ ____________/ | | \_________________3838+ / | | \3939+ / | | \4040+ +----------------+ +-----------+ +------------------+ +------------------+4141+ | Generic Driver | | MT Driver | | Custom Driver #1 | | Custom Driver #2 |4242+ +----------------+ +-----------+ +------------------+ +------------------+4343+4444+Example Drivers:4545+ I/O: USB, I2C, Bluetooth-l2cap4646+ Transport: USB-HID, I2C-HID, BT-HIDP4747+4848+Everything below "HID Core" is simplified in this graph as it is only of4949+interest to HID device drivers. Transport drivers do not need to know the5050+specifics.5151+5252+1.1) Device Setup5353+-----------------5454+5555+I/O drivers normally provide hotplug detection or device enumeration APIs to the5656+transport drivers. Transport drivers use this to find any suitable HID device.5757+They allocate HID device objects and register them with HID core. Transport5858+drivers are not required to register themselves with HID core. HID core is never5959+aware of which transport drivers are available and is not interested in it. It6060+is only interested in devices.6161+6262+Transport drivers attach a constant "struct hid_ll_driver" object with each6363+device. Once a device is registered with HID core, the callbacks provided via6464+this struct are used by HID core to communicate with the device.6565+6666+Transport drivers are responsible of detecting device failures and unplugging.6767+HID core will operate a device as long as it is registered regardless of any6868+device failures. Once transport drivers detect unplug or failure events, they6969+must unregister the device from HID core and HID core will stop using the7070+provided callbacks.7171+7272+1.2) Transport Driver Requirements7373+----------------------------------7474+7575+The terms "asynchronous" and "synchronous" in this document describe the7676+transmission behavior regarding acknowledgements. An asynchronous channel must7777+not perform any synchronous operations like waiting for acknowledgements or7878+verifications. Generally, HID calls operating on asynchronous channels must be7979+running in atomic-context just fine.8080+On the other hand, synchronous channels can be implemented by the transport8181+driver in whatever way they like. They might just be the same as asynchronous8282+channels, but they can also provide acknowledgement reports, automatic8383+retransmission on failure, etc. in a blocking manner. If such functionality is8484+required on asynchronous channels, a transport-driver must implement that via8585+its own worker threads.8686+8787+HID core requires transport drivers to follow a given design. A Transport8888+driver must provide two bi-directional I/O channels to each HID device. These8989+channels must not necessarily be bi-directional in the hardware itself. A9090+transport driver might just provide 4 uni-directional channels. Or it might9191+multiplex all four on a single physical channel. However, in this document we9292+will describe them as two bi-directional channels as they have several9393+properties in common.9494+9595+ - Interrupt Channel (intr): The intr channel is used for asynchronous data9696+ reports. No management commands or data acknowledgements are sent on this9797+ channel. Any unrequested incoming or outgoing data report must be sent on9898+ this channel and is never acknowledged by the remote side. Devices usually9999+ send their input events on this channel. Outgoing events are normally100100+ not send via intr, except if high throughput is required.101101+ - Control Channel (ctrl): The ctrl channel is used for synchronous requests and102102+ device management. Unrequested data input events must not be sent on this103103+ channel and are normally ignored. Instead, devices only send management104104+ events or answers to host requests on this channel.105105+ The control-channel is used for direct blocking queries to the device106106+ independent of any events on the intr-channel.107107+ Outgoing reports are usually sent on the ctrl channel via synchronous108108+ SET_REPORT requests.109109+110110+Communication between devices and HID core is mostly done via HID reports. A111111+report can be of one of three types:112112+113113+ - INPUT Report: Input reports provide data from device to host. This114114+ data may include button events, axis events, battery status or more. This115115+ data is generated by the device and sent to the host with or without116116+ requiring explicit requests. Devices can choose to send data continuously or117117+ only on change.118118+ - OUTPUT Report: Output reports change device states. They are sent from host119119+ to device and may include LED requests, rumble requests or more. Output120120+ reports are never sent from device to host, but a host can retrieve their121121+ current state.122122+ Hosts may choose to send output reports either continuously or only on123123+ change.124124+ - FEATURE Report: Feature reports are used for specific static device features125125+ and never reported spontaneously. A host can read and/or write them to access126126+ data like battery-state or device-settings.127127+ Feature reports are never sent without requests. A host must explicitly set128128+ or retrieve a feature report. This also means, feature reports are never sent129129+ on the intr channel as this channel is asynchronous.130130+131131+INPUT and OUTPUT reports can be sent as pure data reports on the intr channel.132132+For INPUT reports this is the usual operational mode. But for OUTPUT reports,133133+this is rarely done as OUTPUT reports are normally quite scarce. But devices are134134+free to make excessive use of asynchronous OUTPUT reports (for instance, custom135135+HID audio speakers make great use of it).136136+137137+Plain reports must not be sent on the ctrl channel, though. Instead, the ctrl138138+channel provides synchronous GET/SET_REPORT requests. Plain reports are only139139+allowed on the intr channel and are the only means of data there.140140+141141+ - GET_REPORT: A GET_REPORT request has a report ID as payload and is sent142142+ from host to device. The device must answer with a data report for the143143+ requested report ID on the ctrl channel as a synchronous acknowledgement.144144+ Only one GET_REPORT request can be pending for each device. This restriction145145+ is enforced by HID core as several transport drivers don't allow multiple146146+ simultaneous GET_REPORT requests.147147+ Note that data reports which are sent as answer to a GET_REPORT request are148148+ not handled as generic device events. That is, if a device does not operate149149+ in continuous data reporting mode, an answer to GET_REPORT does not replace150150+ the raw data report on the intr channel on state change.151151+ GET_REPORT is only used by custom HID device drivers to query device state.152152+ Normally, HID core caches any device state so this request is not necessary153153+ on devices that follow the HID specs except during device initialization to154154+ retrieve the current state.155155+ GET_REPORT requests can be sent for any of the 3 report types and shall156156+ return the current report state of the device. However, OUTPUT reports as157157+ payload may be blocked by the underlying transport driver if the158158+ specification does not allow them.159159+ - SET_REPORT: A SET_REPORT request has a report ID plus data as payload. It is160160+ sent from host to device and a device must update it's current report state161161+ according to the given data. Any of the 3 report types can be used. However,162162+ INPUT reports as payload might be blocked by the underlying transport driver163163+ if the specification does not allow them.164164+ A device must answer with a synchronous acknowledgement. However, HID core165165+ does not require transport drivers to forward this acknowledgement to HID166166+ core.167167+ Same as for GET_REPORT, only one SET_REPORT can be pending at a time. This168168+ restriction is enforced by HID core as some transport drivers do not support169169+ multiple synchronous SET_REPORT requests.170170+171171+Other ctrl-channel requests are supported by USB-HID but are not available172172+(or deprecated) in most other transport level specifications:173173+174174+ - GET/SET_IDLE: Only used by USB-HID and I2C-HID.175175+ - GET/SET_PROTOCOL: Not used by HID core.176176+ - RESET: Used by I2C-HID, not hooked up in HID core.177177+ - SET_POWER: Used by I2C-HID, not hooked up in HID core.178178+179179+2) HID API180180+==========181181+182182+2.1) Initialization183183+-------------------184184+185185+Transport drivers normally use the following procedure to register a new device186186+with HID core:187187+188188+ struct hid_device *hid;189189+ int ret;190190+191191+ hid = hid_allocate_device();192192+ if (IS_ERR(hid)) {193193+ ret = PTR_ERR(hid);194194+ goto err_<...>;195195+ }196196+197197+ strlcpy(hid->name, <device-name-src>, 127);198198+ strlcpy(hid->phys, <device-phys-src>, 63);199199+ strlcpy(hid->uniq, <device-uniq-src>, 63);200200+201201+ hid->ll_driver = &custom_ll_driver;202202+ hid->bus = <device-bus>;203203+ hid->vendor = <device-vendor>;204204+ hid->product = <device-product>;205205+ hid->version = <device-version>;206206+ hid->country = <device-country>;207207+ hid->dev.parent = <pointer-to-parent-device>;208208+ hid->driver_data = <transport-driver-data-field>;209209+210210+ ret = hid_add_device(hid);211211+ if (ret)212212+ goto err_<...>;213213+214214+Once hid_add_device() is entered, HID core might use the callbacks provided in215215+"custom_ll_driver". Note that fields like "country" can be ignored by underlying216216+transport-drivers if not supported.217217+218218+To unregister a device, use:219219+220220+ hid_destroy_device(hid);221221+222222+Once hid_destroy_device() returns, HID core will no longer make use of any223223+driver callbacks.224224+225225+2.2) hid_ll_driver operations226226+-----------------------------227227+228228+The available HID callbacks are:229229+ - int (*start) (struct hid_device *hdev)230230+ Called from HID device drivers once they want to use the device. Transport231231+ drivers can choose to setup their device in this callback. However, normally232232+ devices are already set up before transport drivers register them to HID core233233+ so this is mostly only used by USB-HID.234234+235235+ - void (*stop) (struct hid_device *hdev)236236+ Called from HID device drivers once they are done with a device. Transport237237+ drivers can free any buffers and deinitialize the device. But note that238238+ ->start() might be called again if another HID device driver is loaded on the239239+ device.240240+ Transport drivers are free to ignore it and deinitialize devices after they241241+ destroyed them via hid_destroy_device().242242+243243+ - int (*open) (struct hid_device *hdev)244244+ Called from HID device drivers once they are interested in data reports.245245+ Usually, while user-space didn't open any input API/etc., device drivers are246246+ not interested in device data and transport drivers can put devices asleep.247247+ However, once ->open() is called, transport drivers must be ready for I/O.248248+ ->open() calls are nested for each client that opens the HID device.249249+250250+ - void (*close) (struct hid_device *hdev)251251+ Called from HID device drivers after ->open() was called but they are no252252+ longer interested in device reports. (Usually if user-space closed any input253253+ devices of the driver).254254+ Transport drivers can put devices asleep and terminate any I/O of all255255+ ->open() calls have been followed by a ->close() call. However, ->start() may256256+ be called again if the device driver is interested in input reports again.257257+258258+ - int (*parse) (struct hid_device *hdev)259259+ Called once during device setup after ->start() has been called. Transport260260+ drivers must read the HID report-descriptor from the device and tell HID core261261+ about it via hid_parse_report().262262+263263+ - int (*power) (struct hid_device *hdev, int level)264264+ Called by HID core to give PM hints to transport drivers. Usually this is265265+ analogical to the ->open() and ->close() hints and redundant.266266+267267+ - void (*request) (struct hid_device *hdev, struct hid_report *report,268268+ int reqtype)269269+ Send an HID request on the ctrl channel. "report" contains the report that270270+ should be sent and "reqtype" the request type. Request-type can be271271+ HID_REQ_SET_REPORT or HID_REQ_GET_REPORT.272272+ This callback is optional. If not provided, HID core will assemble a raw273273+ report following the HID specs and send it via the ->raw_request() callback.274274+ The transport driver is free to implement this asynchronously.275275+276276+ - int (*wait) (struct hid_device *hdev)277277+ Used by HID core before calling ->request() again. A transport driver can use278278+ it to wait for any pending requests to complete if only one request is279279+ allowed at a time.280280+281281+ - int (*raw_request) (struct hid_device *hdev, unsigned char reportnum,282282+ __u8 *buf, size_t count, unsigned char rtype,283283+ int reqtype)284284+ Same as ->request() but provides the report as raw buffer. This request shall285285+ be synchronous. A transport driver must not use ->wait() to complete such286286+ requests. This request is mandatory and hid core will reject the device if287287+ it is missing.288288+289289+ - int (*output_report) (struct hid_device *hdev, __u8 *buf, size_t len)290290+ Send raw output report via intr channel. Used by some HID device drivers291291+ which require high throughput for outgoing requests on the intr channel. This292292+ must not cause SET_REPORT calls! This must be implemented as asynchronous293293+ output report on the intr channel!294294+295295+ - int (*idle) (struct hid_device *hdev, int report, int idle, int reqtype)296296+ Perform SET/GET_IDLE request. Only used by USB-HID, do not implement!297297+298298+2.3) Data Path299299+--------------300300+301301+Transport drivers are responsible of reading data from I/O devices. They must302302+handle any I/O-related state-tracking themselves. HID core does not implement303303+protocol handshakes or other management commands which can be required by the304304+given HID transport specification.305305+306306+Every raw data packet read from a device must be fed into HID core via307307+hid_input_report(). You must specify the channel-type (intr or ctrl) and report308308+type (input/output/feature). Under normal conditions, only input reports are309309+provided via this API.310310+311311+Responses to GET_REPORT requests via ->request() must also be provided via this312312+API. Responses to ->raw_request() are synchronous and must be intercepted by the313313+transport driver and not passed to hid_input_report().314314+Acknowledgements to SET_REPORT requests are not of interest to HID core.315315+316316+----------------------------------------------------317317+Written 2013, David Herrmann <dh.herrmann@gmail.com>
+15-4
drivers/hid/Kconfig
···175175 multimedia keyboard, but will lack support for the musical keyboard176176 and some additional multimedia keys.177177178178+config HID_CP2112179179+ tristate "Silicon Labs CP2112 HID USB-to-SMBus Bridge support"180180+ depends on USB_HID && I2C && GPIOLIB181181+ ---help---182182+ Support for Silicon Labs CP2112 HID USB to SMBus Master Bridge.183183+ This is a HID device driver which registers as an i2c adapter184184+ and gpiochip to expose these functions of the CP2112. The185185+ customizable USB descriptor fields are exposed as sysfs attributes.186186+178187config HID_CYPRESS179188 tristate "Cypress mouse and barcode readers" if EXPERT180189 depends on HID···617608 Support for Samsung InfraRed remote control or keyboards.618609619610config HID_SONY620620- tristate "Sony PS2/3 accessories"611611+ tristate "Sony PS2/3/4 accessories"621612 depends on USB_HID622613 depends on NEW_LEDS623614 depends on LEDS_CLASS615615+ select POWER_SUPPLY624616 ---help---625617 Support for626618627619 * Sony PS3 6-axis controllers620620+ * Sony PS4 DualShock 4 controllers628621 * Buzz controllers629622 * Sony PS3 Blue-ray Disk Remote Control (Bluetooth)630623 * Logitech Harmony adapter for Sony Playstation 3 (Bluetooth)631624632625config SONY_FF633633- bool "Sony PS2/3 accessories force feedback support"626626+ bool "Sony PS2/3/4 accessories force feedback support" 634627 depends on HID_SONY635628 select INPUT_FF_MEMLESS636629 ---help---637637- Say Y here if you have a Sony PS2/3 accessory and want to enable force638638- feedback support for it.630630+ Say Y here if you have a Sony PS2/3/4 accessory and want to enable631631+ force feedback support for it.639632640633config HID_SPEEDLINK641634 tristate "Speedlink VAD Cezanne mouse support"
···12481248}12491249EXPORT_SYMBOL_GPL(hid_output_report);1250125012511251+static int hid_report_len(struct hid_report *report)12521252+{12531253+ return ((report->size - 1) >> 3) + 1 + (report->id > 0) + 7;12541254+}12551255+12511256/*12521257 * Allocator for buffer that is going to be passed to hid_output_report()12531258 */···12631258 * of implement() working on 8 byte chunks12641259 */1265126012661266- int len = ((report->size - 1) >> 3) + 1 + (report->id > 0) + 7;12611261+ int len = hid_report_len(report);1267126212681263 return kmalloc(len, flags);12691264}···1318131313191314 return report;13201315}13161316+13171317+/*13181318+ * Implement a generic .request() callback, using .raw_request()13191319+ * DO NOT USE in hid drivers directly, but through hid_hw_request instead.13201320+ */13211321+void __hid_request(struct hid_device *hid, struct hid_report *report,13221322+ int reqtype)13231323+{13241324+ char *buf;13251325+ int ret;13261326+ int len;13271327+13281328+ buf = hid_alloc_report_buf(report, GFP_KERNEL);13291329+ if (!buf)13301330+ return;13311331+13321332+ len = hid_report_len(report);13331333+13341334+ if (reqtype == HID_REQ_SET_REPORT)13351335+ hid_output_report(report, buf);13361336+13371337+ ret = hid->ll_driver->raw_request(hid, report->id, buf, len,13381338+ report->type, reqtype);13391339+ if (ret < 0) {13401340+ dbg_hid("unable to complete request: %d\n", ret);13411341+ goto out;13421342+ }13431343+13441344+ if (reqtype == HID_REQ_GET_REPORT)13451345+ hid_input_report(hid, report->type, buf, ret, 0);13461346+13471347+out:13481348+ kfree(buf);13491349+}13501350+EXPORT_SYMBOL_GPL(__hid_request);1321135113221352int hid_report_raw_event(struct hid_device *hid, int type, u8 *data, int size,13231353 int interrupt)···17331693 { HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_WIRELESS2) },17341694 { HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_AK1D) },17351695 { HID_USB_DEVICE(USB_VENDOR_ID_CREATIVELABS, USB_DEVICE_ID_PRODIKEYS_PCMIDI) },16961696+ { HID_USB_DEVICE(USB_VENDOR_ID_CYGNAL, USB_DEVICE_ID_CYGNAL_CP2112) },17361697 { HID_USB_DEVICE(USB_VENDOR_ID_CYPRESS, USB_DEVICE_ID_CYPRESS_BARCODE_1) },17371698 { HID_USB_DEVICE(USB_VENDOR_ID_CYPRESS, USB_DEVICE_ID_CYPRESS_BARCODE_2) },17381699 { HID_USB_DEVICE(USB_VENDOR_ID_CYPRESS, USB_DEVICE_ID_CYPRESS_BARCODE_3) },···24712430 * wait for coming driver */24722431 if (hid_ignore(hdev))24732432 return -ENODEV;24332433+24342434+ /*24352435+ * Check for the mandatory transport channel.24362436+ */24372437+ if (!hdev->ll_driver->raw_request) {24382438+ hid_err(hdev, "transport driver missing .raw_request()\n");24392439+ return -EINVAL;24402440+ }2474244124752442 /*24762443 * Read the device report descriptor once and use as template
+1073
drivers/hid/hid-cp2112.c
···11+/*22+ * hid-cp2112.c - Silicon Labs HID USB to SMBus master bridge33+ * Copyright (c) 2013,2014 Uplogix, Inc.44+ * David Barksdale <dbarksdale@uplogix.com>55+ *66+ * This program is free software; you can redistribute it and/or modify it77+ * under the terms and conditions of the GNU General Public License,88+ * version 2, as published by the Free Software Foundation.99+ *1010+ * This program is distributed in the hope it will be useful, but WITHOUT1111+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or1212+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for1313+ * more details.1414+ */1515+1616+/*1717+ * The Silicon Labs CP2112 chip is a USB HID device which provides an1818+ * SMBus controller for talking to slave devices and 8 GPIO pins. The1919+ * host communicates with the CP2112 via raw HID reports.2020+ *2121+ * Data Sheet:2222+ * http://www.silabs.com/Support%20Documents/TechnicalDocs/CP2112.pdf2323+ * Programming Interface Specification:2424+ * http://www.silabs.com/Support%20Documents/TechnicalDocs/AN495.pdf2525+ */2626+2727+#include <linux/gpio.h>2828+#include <linux/hid.h>2929+#include <linux/i2c.h>3030+#include <linux/module.h>3131+#include <linux/nls.h>3232+#include <linux/usb/ch9.h>3333+#include "hid-ids.h"3434+3535+enum {3636+ CP2112_GPIO_CONFIG = 0x02,3737+ CP2112_GPIO_GET = 0x03,3838+ CP2112_GPIO_SET = 0x04,3939+ CP2112_GET_VERSION_INFO = 0x05,4040+ CP2112_SMBUS_CONFIG = 0x06,4141+ CP2112_DATA_READ_REQUEST = 0x10,4242+ CP2112_DATA_WRITE_READ_REQUEST = 0x11,4343+ CP2112_DATA_READ_FORCE_SEND = 0x12,4444+ CP2112_DATA_READ_RESPONSE = 0x13,4545+ CP2112_DATA_WRITE_REQUEST = 0x14,4646+ CP2112_TRANSFER_STATUS_REQUEST = 0x15,4747+ CP2112_TRANSFER_STATUS_RESPONSE = 0x16,4848+ CP2112_CANCEL_TRANSFER = 0x17,4949+ CP2112_LOCK_BYTE = 0x20,5050+ CP2112_USB_CONFIG = 0x21,5151+ CP2112_MANUFACTURER_STRING = 0x22,5252+ CP2112_PRODUCT_STRING = 0x23,5353+ CP2112_SERIAL_STRING = 0x24,5454+};5555+5656+enum {5757+ STATUS0_IDLE = 0x00,5858+ STATUS0_BUSY = 0x01,5959+ STATUS0_COMPLETE = 0x02,6060+ STATUS0_ERROR = 0x03,6161+};6262+6363+enum {6464+ STATUS1_TIMEOUT_NACK = 0x00,6565+ STATUS1_TIMEOUT_BUS = 0x01,6666+ STATUS1_ARBITRATION_LOST = 0x02,6767+ STATUS1_READ_INCOMPLETE = 0x03,6868+ STATUS1_WRITE_INCOMPLETE = 0x04,6969+ STATUS1_SUCCESS = 0x05,7070+};7171+7272+struct cp2112_smbus_config_report {7373+ u8 report; /* CP2112_SMBUS_CONFIG */7474+ __be32 clock_speed; /* Hz */7575+ u8 device_address; /* Stored in the upper 7 bits */7676+ u8 auto_send_read; /* 1 = enabled, 0 = disabled */7777+ __be16 write_timeout; /* ms, 0 = no timeout */7878+ __be16 read_timeout; /* ms, 0 = no timeout */7979+ u8 scl_low_timeout; /* 1 = enabled, 0 = disabled */8080+ __be16 retry_time; /* # of retries, 0 = no limit */8181+} __packed;8282+8383+struct cp2112_usb_config_report {8484+ u8 report; /* CP2112_USB_CONFIG */8585+ __le16 vid; /* Vendor ID */8686+ __le16 pid; /* Product ID */8787+ u8 max_power; /* Power requested in 2mA units */8888+ u8 power_mode; /* 0x00 = bus powered8989+ 0x01 = self powered & regulator off9090+ 0x02 = self powered & regulator on */9191+ u8 release_major;9292+ u8 release_minor;9393+ u8 mask; /* What fields to program */9494+} __packed;9595+9696+struct cp2112_read_req_report {9797+ u8 report; /* CP2112_DATA_READ_REQUEST */9898+ u8 slave_address;9999+ __be16 length;100100+} __packed;101101+102102+struct cp2112_write_read_req_report {103103+ u8 report; /* CP2112_DATA_WRITE_READ_REQUEST */104104+ u8 slave_address;105105+ __be16 length;106106+ u8 target_address_length;107107+ u8 target_address[16];108108+} __packed;109109+110110+struct cp2112_write_req_report {111111+ u8 report; /* CP2112_DATA_WRITE_REQUEST */112112+ u8 slave_address;113113+ u8 length;114114+ u8 data[61];115115+} __packed;116116+117117+struct cp2112_force_read_report {118118+ u8 report; /* CP2112_DATA_READ_FORCE_SEND */119119+ __be16 length;120120+} __packed;121121+122122+struct cp2112_xfer_status_report {123123+ u8 report; /* CP2112_TRANSFER_STATUS_RESPONSE */124124+ u8 status0; /* STATUS0_* */125125+ u8 status1; /* STATUS1_* */126126+ __be16 retries;127127+ __be16 length;128128+} __packed;129129+130130+struct cp2112_string_report {131131+ u8 dummy; /* force .string to be aligned */132132+ u8 report; /* CP2112_*_STRING */133133+ u8 length; /* length in bytes of everyting after .report */134134+ u8 type; /* USB_DT_STRING */135135+ wchar_t string[30]; /* UTF16_LITTLE_ENDIAN string */136136+} __packed;137137+138138+/* Number of times to request transfer status before giving up waiting for a139139+ transfer to complete. This may need to be changed if SMBUS clock, retries,140140+ or read/write/scl_low timeout settings are changed. */141141+static const int XFER_STATUS_RETRIES = 10;142142+143143+/* Time in ms to wait for a CP2112_DATA_READ_RESPONSE or144144+ CP2112_TRANSFER_STATUS_RESPONSE. */145145+static const int RESPONSE_TIMEOUT = 50;146146+147147+static const struct hid_device_id cp2112_devices[] = {148148+ { HID_USB_DEVICE(USB_VENDOR_ID_CYGNAL, USB_DEVICE_ID_CYGNAL_CP2112) },149149+ { }150150+};151151+MODULE_DEVICE_TABLE(hid, cp2112_devices);152152+153153+struct cp2112_device {154154+ struct i2c_adapter adap;155155+ struct hid_device *hdev;156156+ wait_queue_head_t wait;157157+ u8 read_data[61];158158+ u8 read_length;159159+ int xfer_status;160160+ atomic_t read_avail;161161+ atomic_t xfer_avail;162162+ struct gpio_chip gc;163163+};164164+165165+static int gpio_push_pull = 0xFF;166166+module_param(gpio_push_pull, int, S_IRUGO | S_IWUSR);167167+MODULE_PARM_DESC(gpio_push_pull, "GPIO push-pull configuration bitmask");168168+169169+static int cp2112_gpio_direction_input(struct gpio_chip *chip, unsigned offset)170170+{171171+ struct cp2112_device *dev = container_of(chip, struct cp2112_device,172172+ gc);173173+ struct hid_device *hdev = dev->hdev;174174+ u8 buf[5];175175+ int ret;176176+177177+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_CONFIG, buf,178178+ sizeof(buf), HID_FEATURE_REPORT,179179+ HID_REQ_GET_REPORT);180180+ if (ret != sizeof(buf)) {181181+ hid_err(hdev, "error requesting GPIO config: %d\n", ret);182182+ return ret;183183+ }184184+185185+ buf[1] &= ~(1 << offset);186186+ buf[2] = gpio_push_pull;187187+188188+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_CONFIG, buf, sizeof(buf),189189+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);190190+ if (ret < 0) {191191+ hid_err(hdev, "error setting GPIO config: %d\n", ret);192192+ return ret;193193+ }194194+195195+ return 0;196196+}197197+198198+static void cp2112_gpio_set(struct gpio_chip *chip, unsigned offset, int value)199199+{200200+ struct cp2112_device *dev = container_of(chip, struct cp2112_device,201201+ gc);202202+ struct hid_device *hdev = dev->hdev;203203+ u8 buf[3];204204+ int ret;205205+206206+ buf[0] = CP2112_GPIO_SET;207207+ buf[1] = value ? 0xff : 0;208208+ buf[2] = 1 << offset;209209+210210+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_SET, buf, sizeof(buf),211211+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);212212+ if (ret < 0)213213+ hid_err(hdev, "error setting GPIO values: %d\n", ret);214214+}215215+216216+static int cp2112_gpio_get(struct gpio_chip *chip, unsigned offset)217217+{218218+ struct cp2112_device *dev = container_of(chip, struct cp2112_device,219219+ gc);220220+ struct hid_device *hdev = dev->hdev;221221+ u8 buf[2];222222+ int ret;223223+224224+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_GET, buf, sizeof(buf),225225+ HID_FEATURE_REPORT, HID_REQ_GET_REPORT);226226+ if (ret != sizeof(buf)) {227227+ hid_err(hdev, "error requesting GPIO values: %d\n", ret);228228+ return ret;229229+ }230230+231231+ return (buf[1] >> offset) & 1;232232+}233233+234234+static int cp2112_gpio_direction_output(struct gpio_chip *chip,235235+ unsigned offset, int value)236236+{237237+ struct cp2112_device *dev = container_of(chip, struct cp2112_device,238238+ gc);239239+ struct hid_device *hdev = dev->hdev;240240+ u8 buf[5];241241+ int ret;242242+243243+ cp2112_gpio_set(chip, offset, value);244244+245245+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_CONFIG, buf,246246+ sizeof(buf), HID_FEATURE_REPORT,247247+ HID_REQ_GET_REPORT);248248+ if (ret != sizeof(buf)) {249249+ hid_err(hdev, "error requesting GPIO config: %d\n", ret);250250+ return ret;251251+ }252252+253253+ buf[1] |= 1 << offset;254254+ buf[2] = gpio_push_pull;255255+256256+ ret = hid_hw_raw_request(hdev, CP2112_GPIO_CONFIG, buf, sizeof(buf),257257+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);258258+ if (ret < 0) {259259+ hid_err(hdev, "error setting GPIO config: %d\n", ret);260260+ return ret;261261+ }262262+263263+ return 0;264264+}265265+266266+static int cp2112_hid_get(struct hid_device *hdev, unsigned char report_number,267267+ u8 *data, size_t count, unsigned char report_type)268268+{269269+ u8 *buf;270270+ int ret;271271+272272+ buf = kmalloc(count, GFP_KERNEL);273273+ if (!buf)274274+ return -ENOMEM;275275+276276+ ret = hid_hw_raw_request(hdev, report_number, buf, count,277277+ report_type, HID_REQ_GET_REPORT);278278+ memcpy(data, buf, count);279279+ kfree(buf);280280+ return ret;281281+}282282+283283+static int cp2112_hid_output(struct hid_device *hdev, u8 *data, size_t count,284284+ unsigned char report_type)285285+{286286+ u8 *buf;287287+ int ret;288288+289289+ buf = kmemdup(data, count, GFP_KERNEL);290290+ if (!buf)291291+ return -ENOMEM;292292+293293+ if (report_type == HID_OUTPUT_REPORT)294294+ ret = hid_hw_output_report(hdev, buf, count);295295+ else296296+ ret = hid_hw_raw_request(hdev, buf[0], buf, count, report_type,297297+ HID_REQ_SET_REPORT);298298+299299+ kfree(buf);300300+ return ret;301301+}302302+303303+static int cp2112_wait(struct cp2112_device *dev, atomic_t *avail)304304+{305305+ int ret = 0;306306+307307+ /* We have sent either a CP2112_TRANSFER_STATUS_REQUEST or a308308+ * CP2112_DATA_READ_FORCE_SEND and we are waiting for the response to309309+ * come in cp2112_raw_event or timeout. There will only be one of these310310+ * in flight at any one time. The timeout is extremely large and is a311311+ * last resort if the CP2112 has died. If we do timeout we don't expect312312+ * to receive the response which would cause data races, it's not like313313+ * we can do anything about it anyway.314314+ */315315+ ret = wait_event_interruptible_timeout(dev->wait,316316+ atomic_read(avail), msecs_to_jiffies(RESPONSE_TIMEOUT));317317+ if (-ERESTARTSYS == ret)318318+ return ret;319319+ if (!ret)320320+ return -ETIMEDOUT;321321+322322+ atomic_set(avail, 0);323323+ return 0;324324+}325325+326326+static int cp2112_xfer_status(struct cp2112_device *dev)327327+{328328+ struct hid_device *hdev = dev->hdev;329329+ u8 buf[2];330330+ int ret;331331+332332+ buf[0] = CP2112_TRANSFER_STATUS_REQUEST;333333+ buf[1] = 0x01;334334+ atomic_set(&dev->xfer_avail, 0);335335+336336+ ret = cp2112_hid_output(hdev, buf, 2, HID_OUTPUT_REPORT);337337+ if (ret < 0) {338338+ hid_warn(hdev, "Error requesting status: %d\n", ret);339339+ return ret;340340+ }341341+342342+ ret = cp2112_wait(dev, &dev->xfer_avail);343343+ if (ret)344344+ return ret;345345+346346+ return dev->xfer_status;347347+}348348+349349+static int cp2112_read(struct cp2112_device *dev, u8 *data, size_t size)350350+{351351+ struct hid_device *hdev = dev->hdev;352352+ struct cp2112_force_read_report report;353353+ int ret;354354+355355+ report.report = CP2112_DATA_READ_FORCE_SEND;356356+ report.length = cpu_to_be16(size);357357+358358+ atomic_set(&dev->read_avail, 0);359359+360360+ ret = cp2112_hid_output(hdev, &report.report, sizeof(report),361361+ HID_OUTPUT_REPORT);362362+ if (ret < 0) {363363+ hid_warn(hdev, "Error requesting data: %d\n", ret);364364+ return ret;365365+ }366366+367367+ ret = cp2112_wait(dev, &dev->read_avail);368368+ if (ret)369369+ return ret;370370+371371+ hid_dbg(hdev, "read %d of %zd bytes requested\n",372372+ dev->read_length, size);373373+374374+ if (size > dev->read_length)375375+ size = dev->read_length;376376+377377+ memcpy(data, dev->read_data, size);378378+ return dev->read_length;379379+}380380+381381+static int cp2112_read_req(void *buf, u8 slave_address, u16 length)382382+{383383+ struct cp2112_read_req_report *report = buf;384384+385385+ if (length < 1 || length > 512)386386+ return -EINVAL;387387+388388+ report->report = CP2112_DATA_READ_REQUEST;389389+ report->slave_address = slave_address << 1;390390+ report->length = cpu_to_be16(length);391391+ return sizeof(*report);392392+}393393+394394+static int cp2112_write_read_req(void *buf, u8 slave_address, u16 length,395395+ u8 command, u8 *data, u8 data_length)396396+{397397+ struct cp2112_write_read_req_report *report = buf;398398+399399+ if (length < 1 || length > 512400400+ || data_length > sizeof(report->target_address) - 1)401401+ return -EINVAL;402402+403403+ report->report = CP2112_DATA_WRITE_READ_REQUEST;404404+ report->slave_address = slave_address << 1;405405+ report->length = cpu_to_be16(length);406406+ report->target_address_length = data_length + 1;407407+ report->target_address[0] = command;408408+ memcpy(&report->target_address[1], data, data_length);409409+ return data_length + 6;410410+}411411+412412+static int cp2112_write_req(void *buf, u8 slave_address, u8 command, u8 *data,413413+ u8 data_length)414414+{415415+ struct cp2112_write_req_report *report = buf;416416+417417+ if (data_length > sizeof(report->data) - 1)418418+ return -EINVAL;419419+420420+ report->report = CP2112_DATA_WRITE_REQUEST;421421+ report->slave_address = slave_address << 1;422422+ report->length = data_length + 1;423423+ report->data[0] = command;424424+ memcpy(&report->data[1], data, data_length);425425+ return data_length + 4;426426+}427427+428428+static int cp2112_xfer(struct i2c_adapter *adap, u16 addr,429429+ unsigned short flags, char read_write, u8 command,430430+ int size, union i2c_smbus_data *data)431431+{432432+ struct cp2112_device *dev = (struct cp2112_device *)adap->algo_data;433433+ struct hid_device *hdev = dev->hdev;434434+ u8 buf[64];435435+ __be16 word;436436+ ssize_t count;437437+ size_t read_length = 0;438438+ unsigned int retries;439439+ int ret;440440+441441+ hid_dbg(hdev, "%s addr 0x%x flags 0x%x cmd 0x%x size %d\n",442442+ read_write == I2C_SMBUS_WRITE ? "write" : "read",443443+ addr, flags, command, size);444444+445445+ switch (size) {446446+ case I2C_SMBUS_BYTE:447447+ read_length = 1;448448+449449+ if (I2C_SMBUS_READ == read_write)450450+ count = cp2112_read_req(buf, addr, read_length);451451+ else452452+ count = cp2112_write_req(buf, addr, data->byte, NULL,453453+ 0);454454+ break;455455+ case I2C_SMBUS_BYTE_DATA:456456+ read_length = 1;457457+458458+ if (I2C_SMBUS_READ == read_write)459459+ count = cp2112_write_read_req(buf, addr, read_length,460460+ command, NULL, 0);461461+ else462462+ count = cp2112_write_req(buf, addr, command,463463+ &data->byte, 1);464464+ break;465465+ case I2C_SMBUS_WORD_DATA:466466+ read_length = 2;467467+ word = cpu_to_be16(data->word);468468+469469+ if (I2C_SMBUS_READ == read_write)470470+ count = cp2112_write_read_req(buf, addr, read_length,471471+ command, NULL, 0);472472+ else473473+ count = cp2112_write_req(buf, addr, command,474474+ (u8 *)&word, 2);475475+ break;476476+ case I2C_SMBUS_PROC_CALL:477477+ size = I2C_SMBUS_WORD_DATA;478478+ read_write = I2C_SMBUS_READ;479479+ read_length = 2;480480+ word = cpu_to_be16(data->word);481481+482482+ count = cp2112_write_read_req(buf, addr, read_length, command,483483+ (u8 *)&word, 2);484484+ break;485485+ case I2C_SMBUS_I2C_BLOCK_DATA:486486+ size = I2C_SMBUS_BLOCK_DATA;487487+ /* fallthrough */488488+ case I2C_SMBUS_BLOCK_DATA:489489+ if (I2C_SMBUS_READ == read_write) {490490+ count = cp2112_write_read_req(buf, addr,491491+ I2C_SMBUS_BLOCK_MAX,492492+ command, NULL, 0);493493+ } else {494494+ count = cp2112_write_req(buf, addr, command,495495+ data->block,496496+ data->block[0] + 1);497497+ }498498+ break;499499+ case I2C_SMBUS_BLOCK_PROC_CALL:500500+ size = I2C_SMBUS_BLOCK_DATA;501501+ read_write = I2C_SMBUS_READ;502502+503503+ count = cp2112_write_read_req(buf, addr, I2C_SMBUS_BLOCK_MAX,504504+ command, data->block,505505+ data->block[0] + 1);506506+ break;507507+ default:508508+ hid_warn(hdev, "Unsupported transaction %d\n", size);509509+ return -EOPNOTSUPP;510510+ }511511+512512+ if (count < 0)513513+ return count;514514+515515+ ret = hid_hw_power(hdev, PM_HINT_FULLON);516516+ if (ret < 0) {517517+ hid_err(hdev, "power management error: %d\n", ret);518518+ return ret;519519+ }520520+521521+ ret = cp2112_hid_output(hdev, buf, count, HID_OUTPUT_REPORT);522522+ if (ret < 0) {523523+ hid_warn(hdev, "Error starting transaction: %d\n", ret);524524+ goto power_normal;525525+ }526526+527527+ for (retries = 0; retries < XFER_STATUS_RETRIES; ++retries) {528528+ ret = cp2112_xfer_status(dev);529529+ if (-EBUSY == ret)530530+ continue;531531+ if (ret < 0)532532+ goto power_normal;533533+ break;534534+ }535535+536536+ if (XFER_STATUS_RETRIES <= retries) {537537+ hid_warn(hdev, "Transfer timed out, cancelling.\n");538538+ buf[0] = CP2112_CANCEL_TRANSFER;539539+ buf[1] = 0x01;540540+541541+ ret = cp2112_hid_output(hdev, buf, 2, HID_OUTPUT_REPORT);542542+ if (ret < 0)543543+ hid_warn(hdev, "Error cancelling transaction: %d\n",544544+ ret);545545+546546+ ret = -ETIMEDOUT;547547+ goto power_normal;548548+ }549549+550550+ if (I2C_SMBUS_WRITE == read_write) {551551+ ret = 0;552552+ goto power_normal;553553+ }554554+555555+ if (I2C_SMBUS_BLOCK_DATA == size)556556+ read_length = ret;557557+558558+ ret = cp2112_read(dev, buf, read_length);559559+ if (ret < 0)560560+ goto power_normal;561561+ if (ret != read_length) {562562+ hid_warn(hdev, "short read: %d < %zd\n", ret, read_length);563563+ ret = -EIO;564564+ goto power_normal;565565+ }566566+567567+ switch (size) {568568+ case I2C_SMBUS_BYTE:569569+ case I2C_SMBUS_BYTE_DATA:570570+ data->byte = buf[0];571571+ break;572572+ case I2C_SMBUS_WORD_DATA:573573+ data->word = be16_to_cpup((__be16 *)buf);574574+ break;575575+ case I2C_SMBUS_BLOCK_DATA:576576+ if (read_length > I2C_SMBUS_BLOCK_MAX) {577577+ ret = -EPROTO;578578+ goto power_normal;579579+ }580580+581581+ memcpy(data->block, buf, read_length);582582+ break;583583+ }584584+585585+ ret = 0;586586+power_normal:587587+ hid_hw_power(hdev, PM_HINT_NORMAL);588588+ hid_dbg(hdev, "transfer finished: %d\n", ret);589589+ return ret;590590+}591591+592592+static u32 cp2112_functionality(struct i2c_adapter *adap)593593+{594594+ return I2C_FUNC_SMBUS_BYTE |595595+ I2C_FUNC_SMBUS_BYTE_DATA |596596+ I2C_FUNC_SMBUS_WORD_DATA |597597+ I2C_FUNC_SMBUS_BLOCK_DATA |598598+ I2C_FUNC_SMBUS_I2C_BLOCK |599599+ I2C_FUNC_SMBUS_PROC_CALL |600600+ I2C_FUNC_SMBUS_BLOCK_PROC_CALL;601601+}602602+603603+static const struct i2c_algorithm smbus_algorithm = {604604+ .smbus_xfer = cp2112_xfer,605605+ .functionality = cp2112_functionality,606606+};607607+608608+static int cp2112_get_usb_config(struct hid_device *hdev,609609+ struct cp2112_usb_config_report *cfg)610610+{611611+ int ret;612612+613613+ ret = cp2112_hid_get(hdev, CP2112_USB_CONFIG, (u8 *)cfg, sizeof(*cfg),614614+ HID_FEATURE_REPORT);615615+ if (ret != sizeof(*cfg)) {616616+ hid_err(hdev, "error reading usb config: %d\n", ret);617617+ if (ret < 0)618618+ return ret;619619+ return -EIO;620620+ }621621+622622+ return 0;623623+}624624+625625+static int cp2112_set_usb_config(struct hid_device *hdev,626626+ struct cp2112_usb_config_report *cfg)627627+{628628+ int ret;629629+630630+ BUG_ON(cfg->report != CP2112_USB_CONFIG);631631+632632+ ret = cp2112_hid_output(hdev, (u8 *)cfg, sizeof(*cfg),633633+ HID_FEATURE_REPORT);634634+ if (ret != sizeof(*cfg)) {635635+ hid_err(hdev, "error writing usb config: %d\n", ret);636636+ if (ret < 0)637637+ return ret;638638+ return -EIO;639639+ }640640+641641+ return 0;642642+}643643+644644+static void chmod_sysfs_attrs(struct hid_device *hdev);645645+646646+#define CP2112_CONFIG_ATTR(name, store, format, ...) \647647+static ssize_t name##_store(struct device *kdev, \648648+ struct device_attribute *attr, const char *buf, \649649+ size_t count) \650650+{ \651651+ struct hid_device *hdev = container_of(kdev, struct hid_device, dev); \652652+ struct cp2112_usb_config_report cfg; \653653+ int ret = cp2112_get_usb_config(hdev, &cfg); \654654+ if (ret) \655655+ return ret; \656656+ store; \657657+ ret = cp2112_set_usb_config(hdev, &cfg); \658658+ if (ret) \659659+ return ret; \660660+ chmod_sysfs_attrs(hdev); \661661+ return count; \662662+} \663663+static ssize_t name##_show(struct device *kdev, \664664+ struct device_attribute *attr, char *buf) \665665+{ \666666+ struct hid_device *hdev = container_of(kdev, struct hid_device, dev); \667667+ struct cp2112_usb_config_report cfg; \668668+ int ret = cp2112_get_usb_config(hdev, &cfg); \669669+ if (ret) \670670+ return ret; \671671+ return scnprintf(buf, PAGE_SIZE, format, ##__VA_ARGS__); \672672+} \673673+static DEVICE_ATTR_RW(name);674674+675675+CP2112_CONFIG_ATTR(vendor_id, ({676676+ u16 vid;677677+678678+ if (sscanf(buf, "%hi", &vid) != 1)679679+ return -EINVAL;680680+681681+ cfg.vid = cpu_to_le16(vid);682682+ cfg.mask = 0x01;683683+}), "0x%04x\n", le16_to_cpu(cfg.vid));684684+685685+CP2112_CONFIG_ATTR(product_id, ({686686+ u16 pid;687687+688688+ if (sscanf(buf, "%hi", &pid) != 1)689689+ return -EINVAL;690690+691691+ cfg.pid = cpu_to_le16(pid);692692+ cfg.mask = 0x02;693693+}), "0x%04x\n", le16_to_cpu(cfg.pid));694694+695695+CP2112_CONFIG_ATTR(max_power, ({696696+ int mA;697697+698698+ if (sscanf(buf, "%i", &mA) != 1)699699+ return -EINVAL;700700+701701+ cfg.max_power = (mA + 1) / 2;702702+ cfg.mask = 0x04;703703+}), "%u mA\n", cfg.max_power * 2);704704+705705+CP2112_CONFIG_ATTR(power_mode, ({706706+ if (sscanf(buf, "%hhi", &cfg.power_mode) != 1)707707+ return -EINVAL;708708+709709+ cfg.mask = 0x08;710710+}), "%u\n", cfg.power_mode);711711+712712+CP2112_CONFIG_ATTR(release_version, ({713713+ if (sscanf(buf, "%hhi.%hhi", &cfg.release_major, &cfg.release_minor)714714+ != 2)715715+ return -EINVAL;716716+717717+ cfg.mask = 0x10;718718+}), "%u.%u\n", cfg.release_major, cfg.release_minor);719719+720720+#undef CP2112_CONFIG_ATTR721721+722722+struct cp2112_pstring_attribute {723723+ struct device_attribute attr;724724+ unsigned char report;725725+};726726+727727+static ssize_t pstr_store(struct device *kdev,728728+ struct device_attribute *kattr, const char *buf,729729+ size_t count)730730+{731731+ struct hid_device *hdev = container_of(kdev, struct hid_device, dev);732732+ struct cp2112_pstring_attribute *attr =733733+ container_of(kattr, struct cp2112_pstring_attribute, attr);734734+ struct cp2112_string_report report;735735+ int ret;736736+737737+ memset(&report, 0, sizeof(report));738738+739739+ ret = utf8s_to_utf16s(buf, count, UTF16_LITTLE_ENDIAN,740740+ report.string, ARRAY_SIZE(report.string));741741+ report.report = attr->report;742742+ report.length = ret * sizeof(report.string[0]) + 2;743743+ report.type = USB_DT_STRING;744744+745745+ ret = cp2112_hid_output(hdev, &report.report, report.length + 1,746746+ HID_FEATURE_REPORT);747747+ if (ret != report.length + 1) {748748+ hid_err(hdev, "error writing %s string: %d\n", kattr->attr.name,749749+ ret);750750+ if (ret < 0)751751+ return ret;752752+ return -EIO;753753+ }754754+755755+ chmod_sysfs_attrs(hdev);756756+ return count;757757+}758758+759759+static ssize_t pstr_show(struct device *kdev,760760+ struct device_attribute *kattr, char *buf)761761+{762762+ struct hid_device *hdev = container_of(kdev, struct hid_device, dev);763763+ struct cp2112_pstring_attribute *attr =764764+ container_of(kattr, struct cp2112_pstring_attribute, attr);765765+ struct cp2112_string_report report;766766+ u8 length;767767+ int ret;768768+769769+ ret = cp2112_hid_get(hdev, attr->report, &report.report,770770+ sizeof(report) - 1, HID_FEATURE_REPORT);771771+ if (ret < 3) {772772+ hid_err(hdev, "error reading %s string: %d\n", kattr->attr.name,773773+ ret);774774+ if (ret < 0)775775+ return ret;776776+ return -EIO;777777+ }778778+779779+ if (report.length < 2) {780780+ hid_err(hdev, "invalid %s string length: %d\n",781781+ kattr->attr.name, report.length);782782+ return -EIO;783783+ }784784+785785+ length = report.length > ret - 1 ? ret - 1 : report.length;786786+ length = (length - 2) / sizeof(report.string[0]);787787+ ret = utf16s_to_utf8s(report.string, length, UTF16_LITTLE_ENDIAN, buf,788788+ PAGE_SIZE - 1);789789+ buf[ret++] = '\n';790790+ return ret;791791+}792792+793793+#define CP2112_PSTR_ATTR(name, _report) \794794+static struct cp2112_pstring_attribute dev_attr_##name = { \795795+ .attr = __ATTR(name, (S_IWUSR | S_IRUGO), pstr_show, pstr_store), \796796+ .report = _report, \797797+};798798+799799+CP2112_PSTR_ATTR(manufacturer, CP2112_MANUFACTURER_STRING);800800+CP2112_PSTR_ATTR(product, CP2112_PRODUCT_STRING);801801+CP2112_PSTR_ATTR(serial, CP2112_SERIAL_STRING);802802+803803+#undef CP2112_PSTR_ATTR804804+805805+static const struct attribute_group cp2112_attr_group = {806806+ .attrs = (struct attribute *[]){807807+ &dev_attr_vendor_id.attr,808808+ &dev_attr_product_id.attr,809809+ &dev_attr_max_power.attr,810810+ &dev_attr_power_mode.attr,811811+ &dev_attr_release_version.attr,812812+ &dev_attr_manufacturer.attr.attr,813813+ &dev_attr_product.attr.attr,814814+ &dev_attr_serial.attr.attr,815815+ NULL816816+ }817817+};818818+819819+/* Chmoding our sysfs attributes is simply a way to expose which fields in the820820+ * PROM have already been programmed. We do not depend on this preventing821821+ * writing to these attributes since the CP2112 will simply ignore writes to822822+ * already-programmed fields. This is why there is no sense in fixing this823823+ * racy behaviour.824824+ */825825+static void chmod_sysfs_attrs(struct hid_device *hdev)826826+{827827+ struct attribute **attr;828828+ u8 buf[2];829829+ int ret;830830+831831+ ret = cp2112_hid_get(hdev, CP2112_LOCK_BYTE, buf, sizeof(buf),832832+ HID_FEATURE_REPORT);833833+ if (ret != sizeof(buf)) {834834+ hid_err(hdev, "error reading lock byte: %d\n", ret);835835+ return;836836+ }837837+838838+ for (attr = cp2112_attr_group.attrs; *attr; ++attr) {839839+ umode_t mode = (buf[1] & 1) ? S_IWUSR | S_IRUGO : S_IRUGO;840840+ ret = sysfs_chmod_file(&hdev->dev.kobj, *attr, mode);841841+ if (ret < 0)842842+ hid_err(hdev, "error chmoding sysfs file %s\n",843843+ (*attr)->name);844844+ buf[1] >>= 1;845845+ }846846+}847847+848848+static int cp2112_probe(struct hid_device *hdev, const struct hid_device_id *id)849849+{850850+ struct cp2112_device *dev;851851+ u8 buf[3];852852+ struct cp2112_smbus_config_report config;853853+ int ret;854854+855855+ ret = hid_parse(hdev);856856+ if (ret) {857857+ hid_err(hdev, "parse failed\n");858858+ return ret;859859+ }860860+861861+ ret = hid_hw_start(hdev, HID_CONNECT_HIDRAW);862862+ if (ret) {863863+ hid_err(hdev, "hw start failed\n");864864+ return ret;865865+ }866866+867867+ ret = hid_hw_open(hdev);868868+ if (ret) {869869+ hid_err(hdev, "hw open failed\n");870870+ goto err_hid_stop;871871+ }872872+873873+ ret = hid_hw_power(hdev, PM_HINT_FULLON);874874+ if (ret < 0) {875875+ hid_err(hdev, "power management error: %d\n", ret);876876+ goto err_hid_close;877877+ }878878+879879+ ret = cp2112_hid_get(hdev, CP2112_GET_VERSION_INFO, buf, sizeof(buf),880880+ HID_FEATURE_REPORT);881881+ if (ret != sizeof(buf)) {882882+ hid_err(hdev, "error requesting version\n");883883+ if (ret >= 0)884884+ ret = -EIO;885885+ goto err_power_normal;886886+ }887887+888888+ hid_info(hdev, "Part Number: 0x%02X Device Version: 0x%02X\n",889889+ buf[1], buf[2]);890890+891891+ ret = cp2112_hid_get(hdev, CP2112_SMBUS_CONFIG, (u8 *)&config,892892+ sizeof(config), HID_FEATURE_REPORT);893893+ if (ret != sizeof(config)) {894894+ hid_err(hdev, "error requesting SMBus config\n");895895+ if (ret >= 0)896896+ ret = -EIO;897897+ goto err_power_normal;898898+ }899899+900900+ config.retry_time = cpu_to_be16(1);901901+902902+ ret = cp2112_hid_output(hdev, (u8 *)&config, sizeof(config),903903+ HID_FEATURE_REPORT);904904+ if (ret != sizeof(config)) {905905+ hid_err(hdev, "error setting SMBus config\n");906906+ if (ret >= 0)907907+ ret = -EIO;908908+ goto err_power_normal;909909+ }910910+911911+ dev = kzalloc(sizeof(*dev), GFP_KERNEL);912912+ if (!dev) {913913+ ret = -ENOMEM;914914+ goto err_power_normal;915915+ }916916+917917+ hid_set_drvdata(hdev, (void *)dev);918918+ dev->hdev = hdev;919919+ dev->adap.owner = THIS_MODULE;920920+ dev->adap.class = I2C_CLASS_HWMON;921921+ dev->adap.algo = &smbus_algorithm;922922+ dev->adap.algo_data = dev;923923+ dev->adap.dev.parent = &hdev->dev;924924+ snprintf(dev->adap.name, sizeof(dev->adap.name),925925+ "CP2112 SMBus Bridge on hiddev%d", hdev->minor);926926+ init_waitqueue_head(&dev->wait);927927+928928+ hid_device_io_start(hdev);929929+ ret = i2c_add_adapter(&dev->adap);930930+ hid_device_io_stop(hdev);931931+932932+ if (ret) {933933+ hid_err(hdev, "error registering i2c adapter\n");934934+ goto err_free_dev;935935+ }936936+937937+ hid_dbg(hdev, "adapter registered\n");938938+939939+ dev->gc.label = "cp2112_gpio";940940+ dev->gc.direction_input = cp2112_gpio_direction_input;941941+ dev->gc.direction_output = cp2112_gpio_direction_output;942942+ dev->gc.set = cp2112_gpio_set;943943+ dev->gc.get = cp2112_gpio_get;944944+ dev->gc.base = -1;945945+ dev->gc.ngpio = 8;946946+ dev->gc.can_sleep = 1;947947+ dev->gc.dev = &hdev->dev;948948+949949+ ret = gpiochip_add(&dev->gc);950950+ if (ret < 0) {951951+ hid_err(hdev, "error registering gpio chip\n");952952+ goto err_free_i2c;953953+ }954954+955955+ ret = sysfs_create_group(&hdev->dev.kobj, &cp2112_attr_group);956956+ if (ret < 0) {957957+ hid_err(hdev, "error creating sysfs attrs\n");958958+ goto err_gpiochip_remove;959959+ }960960+961961+ chmod_sysfs_attrs(hdev);962962+ hid_hw_power(hdev, PM_HINT_NORMAL);963963+964964+ return ret;965965+966966+err_gpiochip_remove:967967+ if (gpiochip_remove(&dev->gc) < 0)968968+ hid_err(hdev, "error removing gpio chip\n");969969+err_free_i2c:970970+ i2c_del_adapter(&dev->adap);971971+err_free_dev:972972+ kfree(dev);973973+err_power_normal:974974+ hid_hw_power(hdev, PM_HINT_NORMAL);975975+err_hid_close:976976+ hid_hw_close(hdev);977977+err_hid_stop:978978+ hid_hw_stop(hdev);979979+ return ret;980980+}981981+982982+static void cp2112_remove(struct hid_device *hdev)983983+{984984+ struct cp2112_device *dev = hid_get_drvdata(hdev);985985+986986+ sysfs_remove_group(&hdev->dev.kobj, &cp2112_attr_group);987987+ if (gpiochip_remove(&dev->gc))988988+ hid_err(hdev, "unable to remove gpio chip\n");989989+ i2c_del_adapter(&dev->adap);990990+ /* i2c_del_adapter has finished removing all i2c devices from our991991+ * adapter. Well behaved devices should no longer call our cp2112_xfer992992+ * and should have waited for any pending calls to finish. It has also993993+ * waited for device_unregister(&adap->dev) to complete. Therefore we994994+ * can safely free our struct cp2112_device.995995+ */996996+ hid_hw_close(hdev);997997+ hid_hw_stop(hdev);998998+ kfree(dev);999999+}10001000+10011001+static int cp2112_raw_event(struct hid_device *hdev, struct hid_report *report,10021002+ u8 *data, int size)10031003+{10041004+ struct cp2112_device *dev = hid_get_drvdata(hdev);10051005+ struct cp2112_xfer_status_report *xfer = (void *)data;10061006+10071007+ switch (data[0]) {10081008+ case CP2112_TRANSFER_STATUS_RESPONSE:10091009+ hid_dbg(hdev, "xfer status: %02x %02x %04x %04x\n",10101010+ xfer->status0, xfer->status1,10111011+ be16_to_cpu(xfer->retries), be16_to_cpu(xfer->length));10121012+10131013+ switch (xfer->status0) {10141014+ case STATUS0_IDLE:10151015+ dev->xfer_status = -EAGAIN;10161016+ break;10171017+ case STATUS0_BUSY:10181018+ dev->xfer_status = -EBUSY;10191019+ break;10201020+ case STATUS0_COMPLETE:10211021+ dev->xfer_status = be16_to_cpu(xfer->length);10221022+ break;10231023+ case STATUS0_ERROR:10241024+ switch (xfer->status1) {10251025+ case STATUS1_TIMEOUT_NACK:10261026+ case STATUS1_TIMEOUT_BUS:10271027+ dev->xfer_status = -ETIMEDOUT;10281028+ break;10291029+ default:10301030+ dev->xfer_status = -EIO;10311031+ break;10321032+ }10331033+ break;10341034+ default:10351035+ dev->xfer_status = -EINVAL;10361036+ break;10371037+ }10381038+10391039+ atomic_set(&dev->xfer_avail, 1);10401040+ break;10411041+ case CP2112_DATA_READ_RESPONSE:10421042+ hid_dbg(hdev, "read response: %02x %02x\n", data[1], data[2]);10431043+10441044+ dev->read_length = data[2];10451045+ if (dev->read_length > sizeof(dev->read_data))10461046+ dev->read_length = sizeof(dev->read_data);10471047+10481048+ memcpy(dev->read_data, &data[3], dev->read_length);10491049+ atomic_set(&dev->read_avail, 1);10501050+ break;10511051+ default:10521052+ hid_err(hdev, "unknown report\n");10531053+10541054+ return 0;10551055+ }10561056+10571057+ wake_up_interruptible(&dev->wait);10581058+ return 1;10591059+}10601060+10611061+static struct hid_driver cp2112_driver = {10621062+ .name = "cp2112",10631063+ .id_table = cp2112_devices,10641064+ .probe = cp2112_probe,10651065+ .remove = cp2112_remove,10661066+ .raw_event = cp2112_raw_event,10671067+};10681068+10691069+module_hid_driver(cp2112_driver);10701070+MODULE_DESCRIPTION("Silicon Labs HID USB to SMBus master bridge");10711071+MODULE_AUTHOR("David Barksdale <dbarksdale@uplogix.com>");10721072+MODULE_LICENSE("GPL");10731073+
···538538 * but there seems to be no other way of switching the mode.539539 * Thus the super-ugly hacky success check below.540540 */541541- ret = hdev->hid_output_raw_report(hdev, feature, sizeof(feature),542542- HID_FEATURE_REPORT);541541+ ret = hid_hw_raw_request(hdev, feature[0], feature, sizeof(feature),542542+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);543543 if (ret != -EIO && ret != sizeof(feature)) {544544 hid_err(hdev, "unable to request touch data (%d)\n", ret);545545 goto err_stop_hw;
+704-96
drivers/hid/hid-sony.c
···1717 * any later version.1818 */19192020-/* NOTE: in order for the Sony PS3 BD Remote Control to be found by2020+/*2121+ * NOTE: in order for the Sony PS3 BD Remote Control to be found by2122 * a Bluetooth host, the key combination Start+Enter has to be kept pressed2223 * for about 7 seconds with the Bluetooth Host Controller in discovering mode.2324 *···2928#include <linux/hid.h>3029#include <linux/module.h>3130#include <linux/slab.h>3232-#include <linux/usb.h>3331#include <linux/leds.h>3232+#include <linux/power_supply.h>3333+#include <linux/spinlock.h>3434+#include <linux/list.h>3535+#include <linux/input/mt.h>34363537#include "hid-ids.h"3638···4541#define DUALSHOCK4_CONTROLLER_USB BIT(5)4642#define DUALSHOCK4_CONTROLLER_BT BIT(6)47434848-#define SONY_LED_SUPPORT (SIXAXIS_CONTROLLER_USB | BUZZ_CONTROLLER | DUALSHOCK4_CONTROLLER_USB)4949-#define SONY_FF_SUPPORT (SIXAXIS_CONTROLLER_USB | DUALSHOCK4_CONTROLLER_USB)4444+#define SIXAXIS_CONTROLLER (SIXAXIS_CONTROLLER_USB | SIXAXIS_CONTROLLER_BT)4545+#define DUALSHOCK4_CONTROLLER (DUALSHOCK4_CONTROLLER_USB |\4646+ DUALSHOCK4_CONTROLLER_BT)4747+#define SONY_LED_SUPPORT (SIXAXIS_CONTROLLER | BUZZ_CONTROLLER |\4848+ DUALSHOCK4_CONTROLLER)4949+#define SONY_BATTERY_SUPPORT (SIXAXIS_CONTROLLER | DUALSHOCK4_CONTROLLER)5050+#define SONY_FF_SUPPORT (SIXAXIS_CONTROLLER | DUALSHOCK4_CONTROLLER)50515152#define MAX_LEDS 45253···8374 0xb1, 0x02, 0xc0, 0xc0,8475};85768686-/* The default descriptor doesn't provide mapping for the accelerometers7777+/*7878+ * The default descriptor doesn't provide mapping for the accelerometers8779 * or orientation sensors. This fixed descriptor maps the accelerometers8880 * to usage values 0x40, 0x41 and 0x42 and maps the orientation sensors8981 * to usage values 0x43, 0x44 and 0x45.···343333 0xC0 /* End Collection */344334};345335336336+/*337337+ * The default behavior of the Dualshock 4 is to send reports using report338338+ * type 1 when running over Bluetooth. However, as soon as it receives a339339+ * report of type 17 to set the LEDs or rumble it starts returning it's state340340+ * in report 17 instead of 1. Since report 17 is undefined in the default HID341341+ * descriptor the button and axis definitions must be moved to report 17 or342342+ * the HID layer won't process the received input once a report is sent.343343+ */344344+static u8 dualshock4_bt_rdesc[] = {345345+ 0x05, 0x01, /* Usage Page (Desktop), */346346+ 0x09, 0x05, /* Usage (Gamepad), */347347+ 0xA1, 0x01, /* Collection (Application), */348348+ 0x85, 0x01, /* Report ID (1), */349349+ 0x75, 0x08, /* Report Size (8), */350350+ 0x95, 0x0A, /* Report Count (9), */351351+ 0x81, 0x02, /* Input (Variable), */352352+ 0x06, 0x04, 0xFF, /* Usage Page (FF04h), */353353+ 0x85, 0x02, /* Report ID (2), */354354+ 0x09, 0x24, /* Usage (24h), */355355+ 0x95, 0x24, /* Report Count (36), */356356+ 0xB1, 0x02, /* Feature (Variable), */357357+ 0x85, 0xA3, /* Report ID (163), */358358+ 0x09, 0x25, /* Usage (25h), */359359+ 0x95, 0x30, /* Report Count (48), */360360+ 0xB1, 0x02, /* Feature (Variable), */361361+ 0x85, 0x05, /* Report ID (5), */362362+ 0x09, 0x26, /* Usage (26h), */363363+ 0x95, 0x28, /* Report Count (40), */364364+ 0xB1, 0x02, /* Feature (Variable), */365365+ 0x85, 0x06, /* Report ID (6), */366366+ 0x09, 0x27, /* Usage (27h), */367367+ 0x95, 0x34, /* Report Count (52), */368368+ 0xB1, 0x02, /* Feature (Variable), */369369+ 0x85, 0x07, /* Report ID (7), */370370+ 0x09, 0x28, /* Usage (28h), */371371+ 0x95, 0x30, /* Report Count (48), */372372+ 0xB1, 0x02, /* Feature (Variable), */373373+ 0x85, 0x08, /* Report ID (8), */374374+ 0x09, 0x29, /* Usage (29h), */375375+ 0x95, 0x2F, /* Report Count (47), */376376+ 0xB1, 0x02, /* Feature (Variable), */377377+ 0x06, 0x03, 0xFF, /* Usage Page (FF03h), */378378+ 0x85, 0x03, /* Report ID (3), */379379+ 0x09, 0x21, /* Usage (21h), */380380+ 0x95, 0x26, /* Report Count (38), */381381+ 0xB1, 0x02, /* Feature (Variable), */382382+ 0x85, 0x04, /* Report ID (4), */383383+ 0x09, 0x22, /* Usage (22h), */384384+ 0x95, 0x2E, /* Report Count (46), */385385+ 0xB1, 0x02, /* Feature (Variable), */386386+ 0x85, 0xF0, /* Report ID (240), */387387+ 0x09, 0x47, /* Usage (47h), */388388+ 0x95, 0x3F, /* Report Count (63), */389389+ 0xB1, 0x02, /* Feature (Variable), */390390+ 0x85, 0xF1, /* Report ID (241), */391391+ 0x09, 0x48, /* Usage (48h), */392392+ 0x95, 0x3F, /* Report Count (63), */393393+ 0xB1, 0x02, /* Feature (Variable), */394394+ 0x85, 0xF2, /* Report ID (242), */395395+ 0x09, 0x49, /* Usage (49h), */396396+ 0x95, 0x0F, /* Report Count (15), */397397+ 0xB1, 0x02, /* Feature (Variable), */398398+ 0x85, 0x11, /* Report ID (17), */399399+ 0x06, 0x00, 0xFF, /* Usage Page (FF00h), */400400+ 0x09, 0x20, /* Usage (20h), */401401+ 0x95, 0x02, /* Report Count (2), */402402+ 0x81, 0x02, /* Input (Variable), */403403+ 0x05, 0x01, /* Usage Page (Desktop), */404404+ 0x09, 0x30, /* Usage (X), */405405+ 0x09, 0x31, /* Usage (Y), */406406+ 0x09, 0x32, /* Usage (Z), */407407+ 0x09, 0x35, /* Usage (Rz), */408408+ 0x15, 0x00, /* Logical Minimum (0), */409409+ 0x26, 0xFF, 0x00, /* Logical Maximum (255), */410410+ 0x75, 0x08, /* Report Size (8), */411411+ 0x95, 0x04, /* Report Count (4), */412412+ 0x81, 0x02, /* Input (Variable), */413413+ 0x09, 0x39, /* Usage (Hat Switch), */414414+ 0x15, 0x00, /* Logical Minimum (0), */415415+ 0x25, 0x07, /* Logical Maximum (7), */416416+ 0x75, 0x04, /* Report Size (4), */417417+ 0x95, 0x01, /* Report Count (1), */418418+ 0x81, 0x42, /* Input (Variable, Null State), */419419+ 0x05, 0x09, /* Usage Page (Button), */420420+ 0x19, 0x01, /* Usage Minimum (01h), */421421+ 0x29, 0x0E, /* Usage Maximum (0Eh), */422422+ 0x15, 0x00, /* Logical Minimum (0), */423423+ 0x25, 0x01, /* Logical Maximum (1), */424424+ 0x75, 0x01, /* Report Size (1), */425425+ 0x95, 0x0E, /* Report Count (14), */426426+ 0x81, 0x02, /* Input (Variable), */427427+ 0x75, 0x06, /* Report Size (6), */428428+ 0x95, 0x01, /* Report Count (1), */429429+ 0x81, 0x01, /* Input (Constant), */430430+ 0x05, 0x01, /* Usage Page (Desktop), */431431+ 0x09, 0x33, /* Usage (Rx), */432432+ 0x09, 0x34, /* Usage (Ry), */433433+ 0x15, 0x00, /* Logical Minimum (0), */434434+ 0x26, 0xFF, 0x00, /* Logical Maximum (255), */435435+ 0x75, 0x08, /* Report Size (8), */436436+ 0x95, 0x02, /* Report Count (2), */437437+ 0x81, 0x02, /* Input (Variable), */438438+ 0x06, 0x00, 0xFF, /* Usage Page (FF00h), */439439+ 0x09, 0x20, /* Usage (20h), */440440+ 0x95, 0x03, /* Report Count (3), */441441+ 0x81, 0x02, /* Input (Variable), */442442+ 0x05, 0x01, /* Usage Page (Desktop), */443443+ 0x19, 0x40, /* Usage Minimum (40h), */444444+ 0x29, 0x42, /* Usage Maximum (42h), */445445+ 0x16, 0x00, 0x80, /* Logical Minimum (-32768), */446446+ 0x26, 0x00, 0x7F, /* Logical Maximum (32767), */447447+ 0x75, 0x10, /* Report Size (16), */448448+ 0x95, 0x03, /* Report Count (3), */449449+ 0x81, 0x02, /* Input (Variable), */450450+ 0x19, 0x43, /* Usage Minimum (43h), */451451+ 0x29, 0x45, /* Usage Maximum (45h), */452452+ 0x16, 0xFF, 0xBF, /* Logical Minimum (-16385), */453453+ 0x26, 0x00, 0x40, /* Logical Maximum (16384), */454454+ 0x95, 0x03, /* Report Count (3), */455455+ 0x81, 0x02, /* Input (Variable), */456456+ 0x06, 0x00, 0xFF, /* Usage Page (FF00h), */457457+ 0x09, 0x20, /* Usage (20h), */458458+ 0x15, 0x00, /* Logical Minimum (0), */459459+ 0x26, 0xFF, 0x00, /* Logical Maximum (255), */460460+ 0x75, 0x08, /* Report Size (8), */461461+ 0x95, 0x31, /* Report Count (51), */462462+ 0x81, 0x02, /* Input (Variable), */463463+ 0x09, 0x21, /* Usage (21h), */464464+ 0x75, 0x08, /* Report Size (8), */465465+ 0x95, 0x4D, /* Report Count (77), */466466+ 0x91, 0x02, /* Output (Variable), */467467+ 0x85, 0x12, /* Report ID (18), */468468+ 0x09, 0x22, /* Usage (22h), */469469+ 0x95, 0x8D, /* Report Count (141), */470470+ 0x81, 0x02, /* Input (Variable), */471471+ 0x09, 0x23, /* Usage (23h), */472472+ 0x91, 0x02, /* Output (Variable), */473473+ 0x85, 0x13, /* Report ID (19), */474474+ 0x09, 0x24, /* Usage (24h), */475475+ 0x95, 0xCD, /* Report Count (205), */476476+ 0x81, 0x02, /* Input (Variable), */477477+ 0x09, 0x25, /* Usage (25h), */478478+ 0x91, 0x02, /* Output (Variable), */479479+ 0x85, 0x14, /* Report ID (20), */480480+ 0x09, 0x26, /* Usage (26h), */481481+ 0x96, 0x0D, 0x01, /* Report Count (269), */482482+ 0x81, 0x02, /* Input (Variable), */483483+ 0x09, 0x27, /* Usage (27h), */484484+ 0x91, 0x02, /* Output (Variable), */485485+ 0x85, 0x15, /* Report ID (21), */486486+ 0x09, 0x28, /* Usage (28h), */487487+ 0x96, 0x4D, 0x01, /* Report Count (333), */488488+ 0x81, 0x02, /* Input (Variable), */489489+ 0x09, 0x29, /* Usage (29h), */490490+ 0x91, 0x02, /* Output (Variable), */491491+ 0x85, 0x16, /* Report ID (22), */492492+ 0x09, 0x2A, /* Usage (2Ah), */493493+ 0x96, 0x8D, 0x01, /* Report Count (397), */494494+ 0x81, 0x02, /* Input (Variable), */495495+ 0x09, 0x2B, /* Usage (2Bh), */496496+ 0x91, 0x02, /* Output (Variable), */497497+ 0x85, 0x17, /* Report ID (23), */498498+ 0x09, 0x2C, /* Usage (2Ch), */499499+ 0x96, 0xCD, 0x01, /* Report Count (461), */500500+ 0x81, 0x02, /* Input (Variable), */501501+ 0x09, 0x2D, /* Usage (2Dh), */502502+ 0x91, 0x02, /* Output (Variable), */503503+ 0x85, 0x18, /* Report ID (24), */504504+ 0x09, 0x2E, /* Usage (2Eh), */505505+ 0x96, 0x0D, 0x02, /* Report Count (525), */506506+ 0x81, 0x02, /* Input (Variable), */507507+ 0x09, 0x2F, /* Usage (2Fh), */508508+ 0x91, 0x02, /* Output (Variable), */509509+ 0x85, 0x19, /* Report ID (25), */510510+ 0x09, 0x30, /* Usage (30h), */511511+ 0x96, 0x22, 0x02, /* Report Count (546), */512512+ 0x81, 0x02, /* Input (Variable), */513513+ 0x09, 0x31, /* Usage (31h), */514514+ 0x91, 0x02, /* Output (Variable), */515515+ 0x06, 0x80, 0xFF, /* Usage Page (FF80h), */516516+ 0x85, 0x82, /* Report ID (130), */517517+ 0x09, 0x22, /* Usage (22h), */518518+ 0x95, 0x3F, /* Report Count (63), */519519+ 0xB1, 0x02, /* Feature (Variable), */520520+ 0x85, 0x83, /* Report ID (131), */521521+ 0x09, 0x23, /* Usage (23h), */522522+ 0xB1, 0x02, /* Feature (Variable), */523523+ 0x85, 0x84, /* Report ID (132), */524524+ 0x09, 0x24, /* Usage (24h), */525525+ 0xB1, 0x02, /* Feature (Variable), */526526+ 0x85, 0x90, /* Report ID (144), */527527+ 0x09, 0x30, /* Usage (30h), */528528+ 0xB1, 0x02, /* Feature (Variable), */529529+ 0x85, 0x91, /* Report ID (145), */530530+ 0x09, 0x31, /* Usage (31h), */531531+ 0xB1, 0x02, /* Feature (Variable), */532532+ 0x85, 0x92, /* Report ID (146), */533533+ 0x09, 0x32, /* Usage (32h), */534534+ 0xB1, 0x02, /* Feature (Variable), */535535+ 0x85, 0x93, /* Report ID (147), */536536+ 0x09, 0x33, /* Usage (33h), */537537+ 0xB1, 0x02, /* Feature (Variable), */538538+ 0x85, 0xA0, /* Report ID (160), */539539+ 0x09, 0x40, /* Usage (40h), */540540+ 0xB1, 0x02, /* Feature (Variable), */541541+ 0x85, 0xA4, /* Report ID (164), */542542+ 0x09, 0x44, /* Usage (44h), */543543+ 0xB1, 0x02, /* Feature (Variable), */544544+ 0xC0 /* End Collection */545545+};546546+346547static __u8 ps3remote_rdesc[] = {347548 0x05, 0x01, /* GUsagePage Generic Desktop */348549 0x09, 0x05, /* LUsage 0x05 [Game Pad] */···671450};672451673452static const unsigned int buzz_keymap[] = {674674- /* The controller has 4 remote buzzers, each with one LED and 5453453+ /*454454+ * The controller has 4 remote buzzers, each with one LED and 5675455 * buttons.676456 * 677457 * We use the mapping chosen by the controller, which is:···710488 [20] = BTN_TRIGGER_HAPPY20,711489};712490491491+static enum power_supply_property sony_battery_props[] = {492492+ POWER_SUPPLY_PROP_PRESENT,493493+ POWER_SUPPLY_PROP_CAPACITY,494494+ POWER_SUPPLY_PROP_SCOPE,495495+ POWER_SUPPLY_PROP_STATUS,496496+};497497+498498+static spinlock_t sony_dev_list_lock;499499+static LIST_HEAD(sony_device_list);500500+713501struct sony_sc {502502+ spinlock_t lock;503503+ struct list_head list_node;714504 struct hid_device *hdev;715505 struct led_classdev *leds[MAX_LEDS];716716- struct hid_report *output_report;717506 unsigned long quirks;718507 struct work_struct state_worker;508508+ struct power_supply battery;719509720510#ifdef CONFIG_SONY_FF721511 __u8 left;722512 __u8 right;723513#endif724514515515+ __u8 mac_address[6];725516 __u8 worker_initialized;517517+ __u8 cable_state;518518+ __u8 battery_charging;519519+ __u8 battery_capacity;726520 __u8 led_state[MAX_LEDS];727521 __u8 led_count;728522};···816578 hid_info(hdev, "Using modified Dualshock 4 report descriptor with gyroscope axes\n");817579 rdesc = dualshock4_usb_rdesc;818580 *rsize = sizeof(dualshock4_usb_rdesc);581581+ } else if ((sc->quirks & DUALSHOCK4_CONTROLLER_BT) && *rsize == 357) {582582+ hid_info(hdev, "Using modified Dualshock 4 Bluetooth report descriptor\n");583583+ rdesc = dualshock4_bt_rdesc;584584+ *rsize = sizeof(dualshock4_bt_rdesc);819585 }820586821587 /* The HID descriptor exposed over BT has a trailing zero byte */···843601 return rdesc;844602}845603604604+static void sixaxis_parse_report(struct sony_sc *sc, __u8 *rd, int size)605605+{606606+ static const __u8 sixaxis_battery_capacity[] = { 0, 1, 25, 50, 75, 100 };607607+ unsigned long flags;608608+ __u8 cable_state, battery_capacity, battery_charging;609609+610610+ /*611611+ * The sixaxis is charging if the battery value is 0xee612612+ * and it is fully charged if the value is 0xef.613613+ * It does not report the actual level while charging so it614614+ * is set to 100% while charging is in progress.615615+ */616616+ if (rd[30] >= 0xee) {617617+ battery_capacity = 100;618618+ battery_charging = !(rd[30] & 0x01);619619+ } else {620620+ __u8 index = rd[30] <= 5 ? rd[30] : 5;621621+ battery_capacity = sixaxis_battery_capacity[index];622622+ battery_charging = 0;623623+ }624624+ cable_state = !((rd[31] >> 4) & 0x01);625625+626626+ spin_lock_irqsave(&sc->lock, flags);627627+ sc->cable_state = cable_state;628628+ sc->battery_capacity = battery_capacity;629629+ sc->battery_charging = battery_charging;630630+ spin_unlock_irqrestore(&sc->lock, flags);631631+}632632+633633+static void dualshock4_parse_report(struct sony_sc *sc, __u8 *rd, int size)634634+{635635+ struct hid_input *hidinput = list_entry(sc->hdev->inputs.next,636636+ struct hid_input, list);637637+ struct input_dev *input_dev = hidinput->input;638638+ unsigned long flags;639639+ int n, offset;640640+ __u8 cable_state, battery_capacity, battery_charging;641641+642642+ /*643643+ * Battery and touchpad data starts at byte 30 in the USB report and644644+ * 32 in Bluetooth report.645645+ */646646+ offset = (sc->quirks & DUALSHOCK4_CONTROLLER_USB) ? 30 : 32;647647+648648+ /*649649+ * The lower 4 bits of byte 30 contain the battery level650650+ * and the 5th bit contains the USB cable state.651651+ */652652+ cable_state = (rd[offset] >> 4) & 0x01;653653+ battery_capacity = rd[offset] & 0x0F;654654+655655+ /*656656+ * When a USB power source is connected the battery level ranges from657657+ * 0 to 10, and when running on battery power it ranges from 0 to 9.658658+ * A battery level above 10 when plugged in means charge completed.659659+ */660660+ if (!cable_state || battery_capacity > 10)661661+ battery_charging = 0;662662+ else663663+ battery_charging = 1;664664+665665+ if (!cable_state)666666+ battery_capacity++;667667+ if (battery_capacity > 10)668668+ battery_capacity = 10;669669+670670+ battery_capacity *= 10;671671+672672+ spin_lock_irqsave(&sc->lock, flags);673673+ sc->cable_state = cable_state;674674+ sc->battery_capacity = battery_capacity;675675+ sc->battery_charging = battery_charging;676676+ spin_unlock_irqrestore(&sc->lock, flags);677677+678678+ offset += 5;679679+680680+ /*681681+ * The Dualshock 4 multi-touch trackpad data starts at offset 35 on USB682682+ * and 37 on Bluetooth.683683+ * The first 7 bits of the first byte is a counter and bit 8 is a touch684684+ * indicator that is 0 when pressed and 1 when not pressed.685685+ * The next 3 bytes are two 12 bit touch coordinates, X and Y.686686+ * The data for the second touch is in the same format and immediatly687687+ * follows the data for the first.688688+ */689689+ for (n = 0; n < 2; n++) {690690+ __u16 x, y;691691+692692+ x = rd[offset+1] | ((rd[offset+2] & 0xF) << 8);693693+ y = ((rd[offset+2] & 0xF0) >> 4) | (rd[offset+3] << 4);694694+695695+ input_mt_slot(input_dev, n);696696+ input_mt_report_slot_state(input_dev, MT_TOOL_FINGER,697697+ !(rd[offset] >> 7));698698+ input_report_abs(input_dev, ABS_MT_POSITION_X, x);699699+ input_report_abs(input_dev, ABS_MT_POSITION_Y, y);700700+701701+ offset += 4;702702+ }703703+}704704+846705static int sony_raw_event(struct hid_device *hdev, struct hid_report *report,847706 __u8 *rd, int size)848707{849708 struct sony_sc *sc = hid_get_drvdata(hdev);850709851851- /* Sixaxis HID report has acclerometers/gyro with MSByte first, this710710+ /*711711+ * Sixaxis HID report has acclerometers/gyro with MSByte first, this852712 * has to be BYTE_SWAPPED before passing up to joystick interface853713 */854854- if ((sc->quirks & (SIXAXIS_CONTROLLER_USB | SIXAXIS_CONTROLLER_BT)) &&855855- rd[0] == 0x01 && size == 49) {714714+ if ((sc->quirks & SIXAXIS_CONTROLLER) && rd[0] == 0x01 && size == 49) {856715 swap(rd[41], rd[42]);857716 swap(rd[43], rd[44]);858717 swap(rd[45], rd[46]);859718 swap(rd[47], rd[48]);719719+720720+ sixaxis_parse_report(sc, rd, size);721721+ } else if (((sc->quirks & DUALSHOCK4_CONTROLLER_USB) && rd[0] == 0x01 &&722722+ size == 64) || ((sc->quirks & DUALSHOCK4_CONTROLLER_BT)723723+ && rd[0] == 0x11 && size == 78)) {724724+ dualshock4_parse_report(sc, rd, size);860725 }861726862727 return 0;···1006657}10076581008659/*10091009- * The Sony Sixaxis does not handle HID Output Reports on the Interrupt EP10101010- * like it should according to usbhid/hid-core.c::usbhid_output_raw_report()10111011- * so we need to override that forcing HID Output Reports on the Control EP.10121012- *10131013- * There is also another issue about HID Output Reports via USB, the Sixaxis10141014- * does not want the report_id as part of the data packet, so we have to10151015- * discard buf[0] when sending the actual control message, even for numbered10161016- * reports, humpf!10171017- */10181018-static int sixaxis_usb_output_raw_report(struct hid_device *hid, __u8 *buf,10191019- size_t count, unsigned char report_type)10201020-{10211021- struct usb_interface *intf = to_usb_interface(hid->dev.parent);10221022- struct usb_device *dev = interface_to_usbdev(intf);10231023- struct usb_host_interface *interface = intf->cur_altsetting;10241024- int report_id = buf[0];10251025- int ret;10261026-10271027- if (report_type == HID_OUTPUT_REPORT) {10281028- /* Don't send the Report ID */10291029- buf++;10301030- count--;10311031- }10321032-10331033- ret = usb_control_msg(dev, usb_sndctrlpipe(dev, 0),10341034- HID_REQ_SET_REPORT,10351035- USB_DIR_OUT | USB_TYPE_CLASS | USB_RECIP_INTERFACE,10361036- ((report_type + 1) << 8) | report_id,10371037- interface->desc.bInterfaceNumber, buf, count,10381038- USB_CTRL_SET_TIMEOUT);10391039-10401040- /* Count also the Report ID, in case of an Output report. */10411041- if (ret > 0 && report_type == HID_OUTPUT_REPORT)10421042- ret++;10431043-10441044- return ret;10451045-}10461046-10471047-/*1048660 * Sending HID_REQ_GET_REPORT changes the operation mode of the ps3 controller1049661 * to "operational". Without this, the ps3 controller will not report any1050662 * events.···1018708 if (!buf)1019709 return -ENOMEM;102071010211021- ret = hdev->hid_get_raw_report(hdev, 0xf2, buf, 17, HID_FEATURE_REPORT);711711+ ret = hid_hw_raw_request(hdev, 0xf2, buf, 17, HID_FEATURE_REPORT,712712+ HID_REQ_GET_REPORT);10227131023714 if (ret < 0)1024715 hid_err(hdev, "can't set operational mode\n");···1032721static int sixaxis_set_operational_bt(struct hid_device *hdev)1033722{1034723 unsigned char buf[] = { 0xf4, 0x42, 0x03, 0x00, 0x00 };10351035- return hdev->hid_output_raw_report(hdev, buf, sizeof(buf), HID_FEATURE_REPORT);724724+ return hid_hw_raw_request(hdev, buf[0], buf, sizeof(buf),725725+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);726726+}727727+728728+/*729729+ * Requesting feature report 0x02 in Bluetooth mode changes the state of the730730+ * controller so that it sends full input reports of type 0x11.731731+ */732732+static int dualshock4_set_operational_bt(struct hid_device *hdev)733733+{734734+ __u8 buf[37] = { 0 };735735+736736+ return hid_hw_raw_request(hdev, 0x02, buf, sizeof(buf),737737+ HID_FEATURE_REPORT, HID_REQ_GET_REPORT);1036738}10377391038740static void buzz_set_leds(struct hid_device *hdev, const __u8 *leds)···10757511076752 if (drv_data->quirks & BUZZ_CONTROLLER && count == 4) {1077753 buzz_set_leds(hdev, leds);10781078- } else if ((drv_data->quirks & SIXAXIS_CONTROLLER_USB) ||10791079- (drv_data->quirks & DUALSHOCK4_CONTROLLER_USB)) {754754+ } else {1080755 for (n = 0; n < count; n++)1081756 drv_data->led_state[n] = leds[n];1082757 schedule_work(&drv_data->state_worker);···1115792 struct sony_sc *drv_data;11167931117794 int n;11181118- int on = 0;11197951120796 drv_data = hid_get_drvdata(hdev);1121797 if (!drv_data) {···1123801 }11248021125803 for (n = 0; n < drv_data->led_count; n++) {11261126- if (led == drv_data->leds[n]) {11271127- on = !!(drv_data->led_state[n]);11281128- break;11291129- }804804+ if (led == drv_data->leds[n])805805+ return drv_data->led_state[n];1130806 }113180711321132- return on ? LED_FULL : LED_OFF;808808+ return LED_OFF;1133809}11348101135811static void sony_leds_remove(struct hid_device *hdev)···1177857 /* Validate expected report characteristics. */1178858 if (!hid_validate_values(hdev, HID_OUTPUT_REPORT, 0, 0, 7))1179859 return -ENODEV;11801180- } else if (drv_data->quirks & DUALSHOCK4_CONTROLLER_USB) {860860+ } else if (drv_data->quirks & DUALSHOCK4_CONTROLLER) {1181861 drv_data->led_count = 3;1182862 max_brightness = 255;1183863 use_colors = 1;···1191871 name_fmt = "%s::sony%d";1192872 }119387311941194- /* Clear LEDs as we have no way of reading their initial state. This is874874+ /*875875+ * Clear LEDs as we have no way of reading their initial state. This is1195876 * only relevant if the driver is loaded after somebody actively set the11961196- * LEDs to on */877877+ * LEDs to on878878+ */1197879 sony_set_leds(hdev, initial_values, drv_data->led_count);11988801199881 name_sz = strlen(dev_name(&hdev->dev)) + name_len + 1;···1265943 buf[10] |= sc->led_state[2] << 3;1266944 buf[10] |= sc->led_state[3] << 4;126794512681268- sc->hdev->hid_output_raw_report(sc->hdev, buf, sizeof(buf),12691269- HID_OUTPUT_REPORT);946946+ hid_hw_raw_request(sc->hdev, 0x01, buf, sizeof(buf), HID_OUTPUT_REPORT,947947+ HID_REQ_SET_REPORT);1270948}12719491272950static void dualshock4_state_worker(struct work_struct *work)1273951{1274952 struct sony_sc *sc = container_of(work, struct sony_sc, state_worker);1275953 struct hid_device *hdev = sc->hdev;12761276- struct hid_report *report = sc->output_report;12771277- __s32 *value = report->field[0]->value;954954+ int offset;127895512791279- value[0] = 0x03;956956+ __u8 buf[78] = { 0 };957957+958958+ if (sc->quirks & DUALSHOCK4_CONTROLLER_USB) {959959+ buf[0] = 0x05;960960+ buf[1] = 0x03;961961+ offset = 4;962962+ } else {963963+ buf[0] = 0x11;964964+ buf[1] = 0xB0;965965+ buf[3] = 0x0F;966966+ offset = 6;967967+ }12809681281969#ifdef CONFIG_SONY_FF12821282- value[3] = sc->right;12831283- value[4] = sc->left;970970+ buf[offset++] = sc->right;971971+ buf[offset++] = sc->left;972972+#else973973+ offset += 2;1284974#endif128597512861286- value[5] = sc->led_state[0];12871287- value[6] = sc->led_state[1];12881288- value[7] = sc->led_state[2];976976+ buf[offset++] = sc->led_state[0];977977+ buf[offset++] = sc->led_state[1];978978+ buf[offset++] = sc->led_state[2];128997912901290- hid_hw_request(hdev, report, HID_REQ_SET_REPORT);980980+ if (sc->quirks & DUALSHOCK4_CONTROLLER_USB)981981+ hid_hw_output_report(hdev, buf, 32);982982+ else983983+ hid_hw_raw_request(hdev, 0x11, buf, 78,984984+ HID_OUTPUT_REPORT, HID_REQ_SET_REPORT);1291985}12929861293987#ifdef CONFIG_SONY_FF···13381000{13391001 return 0;13401002}10031003+13411004#endif1342100513431343-static int sony_set_output_report(struct sony_sc *sc, int req_id, int req_size)10061006+static int sony_battery_get_property(struct power_supply *psy,10071007+ enum power_supply_property psp,10081008+ union power_supply_propval *val)13441009{13451345- struct list_head *head, *list;13461346- struct hid_report *report;10101010+ struct sony_sc *sc = container_of(psy, struct sony_sc, battery);10111011+ unsigned long flags;10121012+ int ret = 0;10131013+ u8 battery_charging, battery_capacity, cable_state;10141014+10151015+ spin_lock_irqsave(&sc->lock, flags);10161016+ battery_charging = sc->battery_charging;10171017+ battery_capacity = sc->battery_capacity;10181018+ cable_state = sc->cable_state;10191019+ spin_unlock_irqrestore(&sc->lock, flags);10201020+10211021+ switch (psp) {10221022+ case POWER_SUPPLY_PROP_PRESENT:10231023+ val->intval = 1;10241024+ break;10251025+ case POWER_SUPPLY_PROP_SCOPE:10261026+ val->intval = POWER_SUPPLY_SCOPE_DEVICE;10271027+ break;10281028+ case POWER_SUPPLY_PROP_CAPACITY:10291029+ val->intval = battery_capacity;10301030+ break;10311031+ case POWER_SUPPLY_PROP_STATUS:10321032+ if (battery_charging)10331033+ val->intval = POWER_SUPPLY_STATUS_CHARGING;10341034+ else10351035+ if (battery_capacity == 100 && cable_state)10361036+ val->intval = POWER_SUPPLY_STATUS_FULL;10371037+ else10381038+ val->intval = POWER_SUPPLY_STATUS_DISCHARGING;10391039+ break;10401040+ default:10411041+ ret = -EINVAL;10421042+ break;10431043+ }10441044+ return ret;10451045+}10461046+10471047+static int sony_battery_probe(struct sony_sc *sc)10481048+{10491049+ static atomic_t power_id_seq = ATOMIC_INIT(0);10501050+ unsigned long power_id;13471051 struct hid_device *hdev = sc->hdev;10521052+ int ret;1348105313491349- list = &hdev->report_enum[HID_OUTPUT_REPORT].report_list;10541054+ /*10551055+ * Set the default battery level to 100% to avoid low battery warnings10561056+ * if the battery is polled before the first device report is received.10571057+ */10581058+ sc->battery_capacity = 100;1350105913511351- list_for_each(head, list) {13521352- report = list_entry(head, struct hid_report, list);10601060+ power_id = (unsigned long)atomic_inc_return(&power_id_seq);1353106113541354- if (report->id == req_id) {13551355- if (report->size < req_size) {13561356- hid_err(hdev, "Output report 0x%02x (%i bits) is smaller than requested size (%i bits)\n",13571357- req_id, report->size, req_size);13581358- return -EINVAL;13591359- }13601360- sc->output_report = report;13611361- return 0;10621062+ sc->battery.properties = sony_battery_props;10631063+ sc->battery.num_properties = ARRAY_SIZE(sony_battery_props);10641064+ sc->battery.get_property = sony_battery_get_property;10651065+ sc->battery.type = POWER_SUPPLY_TYPE_BATTERY;10661066+ sc->battery.use_for_apm = 0;10671067+ sc->battery.name = kasprintf(GFP_KERNEL, "sony_controller_battery_%lu",10681068+ power_id);10691069+ if (!sc->battery.name)10701070+ return -ENOMEM;10711071+10721072+ ret = power_supply_register(&hdev->dev, &sc->battery);10731073+ if (ret) {10741074+ hid_err(hdev, "Unable to register battery device\n");10751075+ goto err_free;10761076+ }10771077+10781078+ power_supply_powers(&sc->battery, &hdev->dev);10791079+ return 0;10801080+10811081+err_free:10821082+ kfree(sc->battery.name);10831083+ sc->battery.name = NULL;10841084+ return ret;10851085+}10861086+10871087+static void sony_battery_remove(struct sony_sc *sc)10881088+{10891089+ if (!sc->battery.name)10901090+ return;10911091+10921092+ power_supply_unregister(&sc->battery);10931093+ kfree(sc->battery.name);10941094+ sc->battery.name = NULL;10951095+}10961096+10971097+static int sony_register_touchpad(struct sony_sc *sc, int touch_count,10981098+ int w, int h)10991099+{11001100+ struct hid_input *hidinput = list_entry(sc->hdev->inputs.next,11011101+ struct hid_input, list);11021102+ struct input_dev *input_dev = hidinput->input;11031103+ int ret;11041104+11051105+ ret = input_mt_init_slots(input_dev, touch_count, 0);11061106+ if (ret < 0) {11071107+ hid_err(sc->hdev, "Unable to initialize multi-touch slots\n");11081108+ return ret;11091109+ }11101110+11111111+ input_set_abs_params(input_dev, ABS_MT_POSITION_X, 0, w, 0, 0);11121112+ input_set_abs_params(input_dev, ABS_MT_POSITION_Y, 0, h, 0, 0);11131113+11141114+ return 0;11151115+}11161116+11171117+/*11181118+ * If a controller is plugged in via USB while already connected via Bluetooth11191119+ * it will show up as two devices. A global list of connected controllers and11201120+ * their MAC addresses is maintained to ensure that a device is only connected11211121+ * once.11221122+ */11231123+static int sony_check_add_dev_list(struct sony_sc *sc)11241124+{11251125+ struct sony_sc *entry;11261126+ unsigned long flags;11271127+ int ret;11281128+11291129+ spin_lock_irqsave(&sony_dev_list_lock, flags);11301130+11311131+ list_for_each_entry(entry, &sony_device_list, list_node) {11321132+ ret = memcmp(sc->mac_address, entry->mac_address,11331133+ sizeof(sc->mac_address));11341134+ if (!ret) {11351135+ ret = -EEXIST;11361136+ hid_info(sc->hdev, "controller with MAC address %pMR already connected\n",11371137+ sc->mac_address);11381138+ goto unlock;13621139 }13631140 }1364114113651365- hid_err(hdev, "Unable to locate output report 0x%02x\n", req_id);11421142+ ret = 0;11431143+ list_add(&(sc->list_node), &sony_device_list);1366114413671367- return -EINVAL;11451145+unlock:11461146+ spin_unlock_irqrestore(&sony_dev_list_lock, flags);11471147+ return ret;13681148}11491149+11501150+static void sony_remove_dev_list(struct sony_sc *sc)11511151+{11521152+ unsigned long flags;11531153+11541154+ if (sc->list_node.next) {11551155+ spin_lock_irqsave(&sony_dev_list_lock, flags);11561156+ list_del(&(sc->list_node));11571157+ spin_unlock_irqrestore(&sony_dev_list_lock, flags);11581158+ }11591159+}11601160+11611161+static int sony_get_bt_devaddr(struct sony_sc *sc)11621162+{11631163+ int ret;11641164+11651165+ /* HIDP stores the device MAC address as a string in the uniq field. */11661166+ ret = strlen(sc->hdev->uniq);11671167+ if (ret != 17)11681168+ return -EINVAL;11691169+11701170+ ret = sscanf(sc->hdev->uniq,11711171+ "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",11721172+ &sc->mac_address[5], &sc->mac_address[4], &sc->mac_address[3],11731173+ &sc->mac_address[2], &sc->mac_address[1], &sc->mac_address[0]);11741174+11751175+ if (ret != 6)11761176+ return -EINVAL;11771177+11781178+ return 0;11791179+}11801180+11811181+static int sony_check_add(struct sony_sc *sc)11821182+{11831183+ int n, ret;11841184+11851185+ if ((sc->quirks & DUALSHOCK4_CONTROLLER_BT) ||11861186+ (sc->quirks & SIXAXIS_CONTROLLER_BT)) {11871187+ /*11881188+ * sony_get_bt_devaddr() attempts to parse the Bluetooth MAC11891189+ * address from the uniq string where HIDP stores it.11901190+ * As uniq cannot be guaranteed to be a MAC address in all cases11911191+ * a failure of this function should not prevent the connection.11921192+ */11931193+ if (sony_get_bt_devaddr(sc) < 0) {11941194+ hid_warn(sc->hdev, "UNIQ does not contain a MAC address; duplicate check skipped\n");11951195+ return 0;11961196+ }11971197+ } else if (sc->quirks & DUALSHOCK4_CONTROLLER_USB) {11981198+ __u8 buf[7];11991199+12001200+ /*12011201+ * The MAC address of a DS4 controller connected via USB can be12021202+ * retrieved with feature report 0x81. The address begins at12031203+ * offset 1.12041204+ */12051205+ ret = hid_hw_raw_request(sc->hdev, 0x81, buf, sizeof(buf),12061206+ HID_FEATURE_REPORT, HID_REQ_GET_REPORT);12071207+12081208+ if (ret != 7) {12091209+ hid_err(sc->hdev, "failed to retrieve feature report 0x81 with the DualShock 4 MAC address\n");12101210+ return ret < 0 ? ret : -EINVAL;12111211+ }12121212+12131213+ memcpy(sc->mac_address, &buf[1], sizeof(sc->mac_address));12141214+ } else if (sc->quirks & SIXAXIS_CONTROLLER_USB) {12151215+ __u8 buf[18];12161216+12171217+ /*12181218+ * The MAC address of a Sixaxis controller connected via USB can12191219+ * be retrieved with feature report 0xf2. The address begins at12201220+ * offset 4.12211221+ */12221222+ ret = hid_hw_raw_request(sc->hdev, 0xf2, buf, sizeof(buf),12231223+ HID_FEATURE_REPORT, HID_REQ_GET_REPORT);12241224+12251225+ if (ret != 18) {12261226+ hid_err(sc->hdev, "failed to retrieve feature report 0xf2 with the Sixaxis MAC address\n");12271227+ return ret < 0 ? ret : -EINVAL;12281228+ }12291229+12301230+ /*12311231+ * The Sixaxis device MAC in the report is big-endian and must12321232+ * be byte-swapped.12331233+ */12341234+ for (n = 0; n < 6; n++)12351235+ sc->mac_address[5-n] = buf[4+n];12361236+ } else {12371237+ return 0;12381238+ }12391239+12401240+ return sony_check_add_dev_list(sc);12411241+}12421242+1369124313701244static int sony_probe(struct hid_device *hdev, const struct hid_device_id *id)13711245{···16161066 }1617106716181068 if (sc->quirks & SIXAXIS_CONTROLLER_USB) {16191619- hdev->hid_output_raw_report = sixaxis_usb_output_raw_report;10691069+ /*10701070+ * The Sony Sixaxis does not handle HID Output Reports on the10711071+ * Interrupt EP like it could, so we need to force HID Output10721072+ * Reports to use HID_REQ_SET_REPORT on the Control EP.10731073+ *10741074+ * There is also another issue about HID Output Reports via USB,10751075+ * the Sixaxis does not want the report_id as part of the data10761076+ * packet, so we have to discard buf[0] when sending the actual10771077+ * control message, even for numbered reports, humpf!10781078+ */10791079+ hdev->quirks |= HID_QUIRK_NO_OUTPUT_REPORTS_ON_INTR_EP;10801080+ hdev->quirks |= HID_QUIRK_SKIP_OUTPUT_REPORT_ID;16201081 ret = sixaxis_set_operational_usb(hdev);16211621-16221082 sc->worker_initialized = 1;16231083 INIT_WORK(&sc->state_worker, sixaxis_state_worker);16241624- }16251625- else if (sc->quirks & SIXAXIS_CONTROLLER_BT)10841084+ } else if (sc->quirks & SIXAXIS_CONTROLLER_BT) {16261085 ret = sixaxis_set_operational_bt(hdev);16271627- else if (sc->quirks & DUALSHOCK4_CONTROLLER_USB) {16281628- /* Report 5 (31 bytes) is used to send data to the controller via USB */16291629- ret = sony_set_output_report(sc, 0x05, 248);10861086+ sc->worker_initialized = 1;10871087+ INIT_WORK(&sc->state_worker, sixaxis_state_worker);10881088+ } else if (sc->quirks & DUALSHOCK4_CONTROLLER) {10891089+ if (sc->quirks & DUALSHOCK4_CONTROLLER_BT) {10901090+ ret = dualshock4_set_operational_bt(hdev);10911091+ if (ret < 0) {10921092+ hid_err(hdev, "failed to set the Dualshock 4 operational mode\n");10931093+ goto err_stop;10941094+ }10951095+ }10961096+ /*10971097+ * The Dualshock 4 touchpad supports 2 touches and has a10981098+ * resolution of 1920x940.10991099+ */11001100+ ret = sony_register_touchpad(sc, 2, 1920, 940);16301101 if (ret < 0)16311102 goto err_stop;16321103···16571086 ret = 0;16581087 }1659108810891089+ if (ret < 0)10901090+ goto err_stop;10911091+10921092+ ret = sony_check_add(sc);16601093 if (ret < 0)16611094 goto err_stop;16621095···16741099 ret = sony_init_ff(hdev);16751100 if (ret < 0)16761101 goto err_stop;11021102+ if (sc->quirks & SONY_BATTERY_SUPPORT) {11031103+ ret = sony_battery_probe(sc);11041104+ if (ret < 0)11051105+ goto err_stop;11061106+11071107+ /* Open the device to receive reports with battery info */11081108+ ret = hid_hw_open(hdev);11091109+ if (ret < 0) {11101110+ hid_err(hdev, "hw open failed\n");11111111+ goto err_stop;11121112+ }11131113+ }11141114+11151115+ if (sc->quirks & SONY_FF_SUPPORT) {11161116+ ret = sony_init_ff(hdev);11171117+ if (ret < 0)11181118+ goto err_close;16771119 }1678112016791121 return 0;11221122+err_close:11231123+ hid_hw_close(hdev);16801124err_stop:16811125 if (sc->quirks & SONY_LED_SUPPORT)16821126 sony_leds_remove(hdev);11271127+ if (sc->quirks & SONY_BATTERY_SUPPORT)11281128+ sony_battery_remove(sc);11291129+ if (sc->worker_initialized)11301130+ cancel_work_sync(&sc->state_worker);11311131+ sony_remove_dev_list(sc);16831132 hid_hw_stop(hdev);16841133 return ret;16851134}···1717111817181119 if (sc->worker_initialized)17191120 cancel_work_sync(&sc->state_worker);11211121+ if (sc->quirks & SONY_BATTERY_SUPPORT) {11221122+ hid_hw_close(hdev);11231123+ sony_battery_remove(sc);11241124+ }11251125+11261126+ if (sc->worker_initialized)11271127+ cancel_work_sync(&sc->state_worker);11281128+11291129+ sony_remove_dev_list(sc);1720113017211131 hid_hw_stop(hdev);17221132}
+2-2
drivers/hid/hid-thingm.c
···4848 buf[0], buf[1], buf[2], buf[3], buf[4],4949 buf[5], buf[6], buf[7], buf[8]);50505151- ret = data->hdev->hid_output_raw_report(data->hdev, buf,5252- BLINK1_CMD_SIZE, HID_FEATURE_REPORT);5151+ ret = hid_hw_raw_request(data->hdev, buf[0], buf, BLINK1_CMD_SIZE,5252+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);53535454 return ret < 0 ? ret : 0;5555}
+15-13
drivers/hid/hid-wacom.c
···128128129129 rep_data[0] = WAC_CMD_ICON_START_STOP;130130 rep_data[1] = 0;131131- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,132132- HID_FEATURE_REPORT);131131+ ret = hid_hw_raw_request(hdev, rep_data[0], rep_data, 2,132132+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);133133 if (ret < 0)134134 goto err;135135···143143 rep_data[j + 3] = p[(i << 6) + j];144144145145 rep_data[2] = i;146146- ret = hdev->hid_output_raw_report(hdev, rep_data, 67,147147- HID_FEATURE_REPORT);146146+ ret = hid_hw_raw_request(hdev, rep_data[0], rep_data, 67,147147+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);148148 }149149150150 rep_data[0] = WAC_CMD_ICON_START_STOP;151151 rep_data[1] = 0;152152153153- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,154154- HID_FEATURE_REPORT);153153+ ret = hid_hw_raw_request(hdev, rep_data[0], rep_data, 2,154154+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);155155156156err:157157 return;···183183 buf[3] = value;184184 /* use fixed brightness for OLEDs */185185 buf[4] = 0x08;186186- hdev->hid_output_raw_report(hdev, buf, 9, HID_FEATURE_REPORT);186186+ hid_hw_raw_request(hdev, buf[0], buf, 9, HID_FEATURE_REPORT,187187+ HID_REQ_SET_REPORT);187188 kfree(buf);188189 }189190···340339 rep_data[0] = 0x03 ; rep_data[1] = 0x00;341340 limit = 3;342341 do {343343- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,344344- HID_FEATURE_REPORT);342342+ ret = hid_hw_raw_request(hdev, rep_data[0], rep_data, 2,343343+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);345344 } while (ret < 0 && limit-- > 0);346345347346 if (ret >= 0) {···353352 rep_data[1] = 0x00;354353 limit = 3;355354 do {356356- ret = hdev->hid_output_raw_report(hdev,357357- rep_data, 2, HID_FEATURE_REPORT);355355+ ret = hid_hw_raw_request(hdev, rep_data[0],356356+ rep_data, 2, HID_FEATURE_REPORT,357357+ HID_REQ_SET_REPORT);358358 } while (ret < 0 && limit-- > 0);359359360360 if (ret >= 0) {···380378 rep_data[0] = 0x03;381379 rep_data[1] = wdata->features;382380383383- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,384384- HID_FEATURE_REPORT);381381+ ret = hid_hw_raw_request(hdev, rep_data[0], rep_data, 2,382382+ HID_FEATURE_REPORT, HID_REQ_SET_REPORT);385383 if (ret >= 0)386384 wdata->high_speed = speed;387385 break;
+2-2
drivers/hid/hid-wiimote-core.c
···2828 __u8 *buf;2929 int ret;30303131- if (!hdev->hid_output_raw_report)3131+ if (!hdev->ll_driver->output_report)3232 return -ENODEV;33333434 buf = kmemdup(buffer, count, GFP_KERNEL);3535 if (!buf)3636 return -ENOMEM;37373838- ret = hdev->hid_output_raw_report(hdev, buf, count, HID_OUTPUT_REPORT);3838+ ret = hid_hw_output_report(hdev, buf, count);39394040 kfree(buf);4141 return ret;
+19-8
drivers/hid/hidraw.c
···123123124124 dev = hidraw_table[minor]->hid;125125126126- if (!dev->hid_output_raw_report) {127127- ret = -ENODEV;128128- goto out;129129- }130126131127 if (count > HID_MAX_BUFFER_SIZE) {132128 hid_warn(dev, "pid %d passed too large report\n",···149153 goto out_free;150154 }151155152152- ret = dev->hid_output_raw_report(dev, buf, count, report_type);156156+ if ((report_type == HID_OUTPUT_REPORT) &&157157+ !(dev->quirks & HID_QUIRK_NO_OUTPUT_REPORTS_ON_INTR_EP)) {158158+ ret = hid_hw_output_report(dev, buf, count);159159+ /*160160+ * compatibility with old implementation of USB-HID and I2C-HID:161161+ * if the device does not support receiving output reports,162162+ * on an interrupt endpoint, fallback to SET_REPORT HID command.163163+ */164164+ if (ret != -ENOSYS)165165+ goto out_free;166166+ }167167+168168+ ret = hid_hw_raw_request(dev, buf[0], buf, count, report_type,169169+ HID_REQ_SET_REPORT);170170+153171out_free:154172 kfree(buf);155173out:···199189200190 dev = hidraw_table[minor]->hid;201191202202- if (!dev->hid_get_raw_report) {192192+ if (!dev->ll_driver->raw_request) {203193 ret = -ENODEV;204194 goto out;205195 }···226216227217 /*228218 * Read the first byte from the user. This is the report number,229229- * which is passed to dev->hid_get_raw_report().219219+ * which is passed to hid_hw_raw_request().230220 */231221 if (copy_from_user(&report_number, buffer, 1)) {232222 ret = -EFAULT;233223 goto out_free;234224 }235225236236- ret = dev->hid_get_raw_report(dev, report_number, buf, count, report_type);226226+ ret = hid_hw_raw_request(dev, report_number, buf, count, report_type,227227+ HID_REQ_GET_REPORT);237228238229 if (ret < 0)239230 goto out_free;
+38-33
drivers/hid/i2c-hid/i2c-hid.c
···257257 return 0;258258}259259260260-static int i2c_hid_set_report(struct i2c_client *client, u8 reportType,261261- u8 reportID, unsigned char *buf, size_t data_len)260260+/**261261+ * i2c_hid_set_or_send_report: forward an incoming report to the device262262+ * @client: the i2c_client of the device263263+ * @reportType: 0x03 for HID_FEATURE_REPORT ; 0x02 for HID_OUTPUT_REPORT264264+ * @reportID: the report ID265265+ * @buf: the actual data to transfer, without the report ID266266+ * @len: size of buf267267+ * @use_data: true: use SET_REPORT HID command, false: send plain OUTPUT report268268+ */269269+static int i2c_hid_set_or_send_report(struct i2c_client *client, u8 reportType,270270+ u8 reportID, unsigned char *buf, size_t data_len, bool use_data)262271{263272 struct i2c_hid *ihid = i2c_get_clientdata(client);264273 u8 *args = ihid->argsbuf;265265- const struct i2c_hid_cmd * hidcmd = &hid_set_report_cmd;274274+ const struct i2c_hid_cmd *hidcmd;266275 int ret;267276 u16 dataRegister = le16_to_cpu(ihid->hdesc.wDataRegister);268277 u16 outputRegister = le16_to_cpu(ihid->hdesc.wOutputRegister);269278 u16 maxOutputLength = le16_to_cpu(ihid->hdesc.wMaxOutputLength);270279271271- /* hidraw already checked that data_len < HID_MAX_BUFFER_SIZE */280280+ /* hid_hw_* already checked that data_len < HID_MAX_BUFFER_SIZE */272281 u16 size = 2 /* size */ +273282 (reportID ? 1 : 0) /* reportID */ +274283 data_len /* buf */;···288279289280 i2c_hid_dbg(ihid, "%s\n", __func__);290281282282+ if (!use_data && maxOutputLength == 0)283283+ return -ENOSYS;284284+291285 if (reportID >= 0x0F) {292286 args[index++] = reportID;293287 reportID = 0x0F;···300288 * use the data register for feature reports or if the device does not301289 * support the output register302290 */303303- if (reportType == 0x03 || maxOutputLength == 0) {291291+ if (use_data) {304292 args[index++] = dataRegister & 0xFF;305293 args[index++] = dataRegister >> 8;294294+ hidcmd = &hid_set_report_cmd;306295 } else {307296 args[index++] = outputRegister & 0xFF;308297 args[index++] = outputRegister >> 8;···572559}573560574561static int i2c_hid_output_raw_report(struct hid_device *hid, __u8 *buf,575575- size_t count, unsigned char report_type)562562+ size_t count, unsigned char report_type, bool use_data)576563{577564 struct i2c_client *client = hid->driver_data;578565 int report_id = buf[0];···586573 count--;587574 }588575589589- ret = i2c_hid_set_report(client,576576+ ret = i2c_hid_set_or_send_report(client,590577 report_type == HID_FEATURE_REPORT ? 0x03 : 0x02,591591- report_id, buf, count);578578+ report_id, buf, count, use_data);592579593580 if (report_id && ret >= 0)594581 ret++; /* add report_id to the number of transfered bytes */···596583 return ret;597584}598585599599-static void i2c_hid_request(struct hid_device *hid, struct hid_report *rep,600600- int reqtype)586586+static int i2c_hid_output_report(struct hid_device *hid, __u8 *buf,587587+ size_t count)601588{602602- struct i2c_client *client = hid->driver_data;603603- char *buf;604604- int ret;605605- int len = i2c_hid_get_report_length(rep) - 2;589589+ return i2c_hid_output_raw_report(hid, buf, count, HID_OUTPUT_REPORT,590590+ false);591591+}606592607607- buf = hid_alloc_report_buf(rep, GFP_KERNEL);608608- if (!buf)609609- return;610610-593593+static int i2c_hid_raw_request(struct hid_device *hid, unsigned char reportnum,594594+ __u8 *buf, size_t len, unsigned char rtype,595595+ int reqtype)596596+{611597 switch (reqtype) {612598 case HID_REQ_GET_REPORT:613613- ret = i2c_hid_get_raw_report(hid, rep->id, buf, len, rep->type);614614- if (ret < 0)615615- dev_err(&client->dev, "%s: unable to get report: %d\n",616616- __func__, ret);617617- else618618- hid_input_report(hid, rep->type, buf, ret, 0);619619- break;599599+ return i2c_hid_get_raw_report(hid, reportnum, buf, len, rtype);620600 case HID_REQ_SET_REPORT:621621- hid_output_report(rep, buf);622622- i2c_hid_output_raw_report(hid, buf, len, rep->type);623623- break;601601+ if (buf[0] != reportnum)602602+ return -EINVAL;603603+ return i2c_hid_output_raw_report(hid, buf, len, rtype, true);604604+ default:605605+ return -EIO;624606 }625625-626626- kfree(buf);627607}628608629609static int i2c_hid_parse(struct hid_device *hid)···774768 .open = i2c_hid_open,775769 .close = i2c_hid_close,776770 .power = i2c_hid_power,777777- .request = i2c_hid_request,771771+ .output_report = i2c_hid_output_report,772772+ .raw_request = i2c_hid_raw_request,778773};779774780775static int i2c_hid_init_irq(struct i2c_client *client)···1024101710251018 hid->driver_data = client;10261019 hid->ll_driver = &i2c_hid_ll_driver;10271027- hid->hid_get_raw_report = i2c_hid_get_raw_report;10281028- hid->hid_output_raw_report = i2c_hid_output_raw_report;10291020 hid->dev.parent = &client->dev;10301021 ACPI_COMPANION_SET(&hid->dev, ACPI_COMPANION(&client->dev));10311022 hid->bus = BUS_I2C;