Skip to content

Commit 1143823

Browse files
author
Benjamin Tissoires
committed
Merge branch 'for-6.6/cp2112' into for-linus
Cleanup of the hid-cp2112 driver by Andy Shevchenko
2 parents 0c4b941 + a6a5ecc commit 1143823

File tree

2 files changed

+58
-112
lines changed

2 files changed

+58
-112
lines changed

drivers/hid/hid-cp2112.c

Lines changed: 57 additions & 112 deletions
Original file line numberDiff line numberDiff line change
@@ -16,21 +16,23 @@
1616
* https://www.silabs.com/documents/public/application-notes/an495-cp2112-interface-specification.pdf
1717
*/
1818

19-
#include <linux/gpio/consumer.h>
20-
#include <linux/gpio/machine.h>
19+
#include <linux/bitops.h>
2120
#include <linux/gpio/driver.h>
2221
#include <linux/hid.h>
2322
#include <linux/hidraw.h>
2423
#include <linux/i2c.h>
2524
#include <linux/module.h>
2625
#include <linux/nls.h>
26+
#include <linux/string_choices.h>
2727
#include <linux/usb/ch9.h>
2828
#include "hid-ids.h"
2929

3030
#define CP2112_REPORT_MAX_LENGTH 64
3131
#define CP2112_GPIO_CONFIG_LENGTH 5
3232
#define CP2112_GPIO_GET_LENGTH 2
3333
#define CP2112_GPIO_SET_LENGTH 3
34+
#define CP2112_GPIO_MAX_GPIO 8
35+
#define CP2112_GPIO_ALL_GPIO_MASK GENMASK(7, 0)
3436

3537
enum {
3638
CP2112_GPIO_CONFIG = 0x02,
@@ -163,19 +165,17 @@ struct cp2112_device {
163165
atomic_t read_avail;
164166
atomic_t xfer_avail;
165167
struct gpio_chip gc;
166-
struct irq_chip irq;
167168
u8 *in_out_buffer;
168169
struct mutex lock;
169170

170-
struct gpio_desc *desc[8];
171171
bool gpio_poll;
172172
struct delayed_work gpio_poll_worker;
173173
unsigned long irq_mask;
174174
u8 gpio_prev_state;
175175
};
176176

177-
static int gpio_push_pull = 0xFF;
178-
module_param(gpio_push_pull, int, S_IRUGO | S_IWUSR);
177+
static int gpio_push_pull = CP2112_GPIO_ALL_GPIO_MASK;
178+
module_param(gpio_push_pull, int, 0644);
179179
MODULE_PARM_DESC(gpio_push_pull, "GPIO push-pull configuration bitmask");
180180

181181
static int cp2112_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
@@ -197,7 +197,7 @@ static int cp2112_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
197197
goto exit;
198198
}
199199

200-
buf[1] &= ~(1 << offset);
200+
buf[1] &= ~BIT(offset);
201201
buf[2] = gpio_push_pull;
202202

203203
ret = hid_hw_raw_request(hdev, CP2112_GPIO_CONFIG, buf,
@@ -227,8 +227,8 @@ static void cp2112_gpio_set(struct gpio_chip *chip, unsigned offset, int value)
227227
mutex_lock(&dev->lock);
228228

229229
buf[0] = CP2112_GPIO_SET;
230-
buf[1] = value ? 0xff : 0;
231-
buf[2] = 1 << offset;
230+
buf[1] = value ? CP2112_GPIO_ALL_GPIO_MASK : 0;
231+
buf[2] = BIT(offset);
232232

233233
ret = hid_hw_raw_request(hdev, CP2112_GPIO_SET, buf,
234234
CP2112_GPIO_SET_LENGTH, HID_FEATURE_REPORT,
@@ -532,15 +532,13 @@ static int cp2112_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs,
532532
hid_dbg(hdev, "I2C %d messages\n", num);
533533

534534
if (num == 1) {
535+
hid_dbg(hdev, "I2C %s %#04x len %d\n",
536+
str_read_write(msgs->flags & I2C_M_RD), msgs->addr, msgs->len);
535537
if (msgs->flags & I2C_M_RD) {
536-
hid_dbg(hdev, "I2C read %#04x len %d\n",
537-
msgs->addr, msgs->len);
538538
read_length = msgs->len;
539539
read_buf = msgs->buf;
540540
count = cp2112_read_req(buf, msgs->addr, msgs->len);
541541
} else {
542-
hid_dbg(hdev, "I2C write %#04x len %d\n",
543-
msgs->addr, msgs->len);
544542
count = cp2112_i2c_write_req(buf, msgs->addr,
545543
msgs->buf, msgs->len);
546544
}
@@ -648,7 +646,7 @@ static int cp2112_xfer(struct i2c_adapter *adap, u16 addr,
648646
int ret;
649647

650648
hid_dbg(hdev, "%s addr 0x%x flags 0x%x cmd 0x%x size %d\n",
651-
read_write == I2C_SMBUS_WRITE ? "write" : "read",
649+
str_write_read(read_write == I2C_SMBUS_WRITE),
652650
addr, flags, command, size);
653651

654652
switch (size) {
@@ -895,7 +893,7 @@ static ssize_t name##_show(struct device *kdev, \
895893
int ret = cp2112_get_usb_config(hdev, &cfg); \
896894
if (ret) \
897895
return ret; \
898-
return scnprintf(buf, PAGE_SIZE, format, ##__VA_ARGS__); \
896+
return sysfs_emit(buf, format, ##__VA_ARGS__); \
899897
} \
900898
static DEVICE_ATTR_RW(name);
901899

@@ -946,26 +944,18 @@ CP2112_CONFIG_ATTR(release_version, ({
946944

947945
#undef CP2112_CONFIG_ATTR
948946

949-
struct cp2112_pstring_attribute {
950-
struct device_attribute attr;
951-
unsigned char report;
952-
};
953-
954-
static ssize_t pstr_store(struct device *kdev,
955-
struct device_attribute *kattr, const char *buf,
956-
size_t count)
947+
static ssize_t pstr_store(struct device *kdev, struct device_attribute *kattr,
948+
const char *buf, size_t count, int number)
957949
{
958950
struct hid_device *hdev = to_hid_device(kdev);
959-
struct cp2112_pstring_attribute *attr =
960-
container_of(kattr, struct cp2112_pstring_attribute, attr);
961951
struct cp2112_string_report report;
962952
int ret;
963953

964954
memset(&report, 0, sizeof(report));
965955

966956
ret = utf8s_to_utf16s(buf, count, UTF16_LITTLE_ENDIAN,
967957
report.string, ARRAY_SIZE(report.string));
968-
report.report = attr->report;
958+
report.report = number;
969959
report.length = ret * sizeof(report.string[0]) + 2;
970960
report.type = USB_DT_STRING;
971961

@@ -983,17 +973,15 @@ static ssize_t pstr_store(struct device *kdev,
983973
return count;
984974
}
985975

986-
static ssize_t pstr_show(struct device *kdev,
987-
struct device_attribute *kattr, char *buf)
976+
static ssize_t pstr_show(struct device *kdev, struct device_attribute *kattr,
977+
char *buf, int number)
988978
{
989979
struct hid_device *hdev = to_hid_device(kdev);
990-
struct cp2112_pstring_attribute *attr =
991-
container_of(kattr, struct cp2112_pstring_attribute, attr);
992980
struct cp2112_string_report report;
993981
u8 length;
994982
int ret;
995983

996-
ret = cp2112_hid_get(hdev, attr->report, (u8 *)&report.contents,
984+
ret = cp2112_hid_get(hdev, number, (u8 *)&report.contents,
997985
sizeof(report.contents), HID_FEATURE_REPORT);
998986
if (ret < 3) {
999987
hid_err(hdev, "error reading %s string: %d\n", kattr->attr.name,
@@ -1018,10 +1006,16 @@ static ssize_t pstr_show(struct device *kdev,
10181006
}
10191007

10201008
#define CP2112_PSTR_ATTR(name, _report) \
1021-
static struct cp2112_pstring_attribute dev_attr_##name = { \
1022-
.attr = __ATTR(name, (S_IWUSR | S_IRUGO), pstr_show, pstr_store), \
1023-
.report = _report, \
1024-
};
1009+
static ssize_t name##_store(struct device *kdev, struct device_attribute *kattr, \
1010+
const char *buf, size_t count) \
1011+
{ \
1012+
return pstr_store(kdev, kattr, buf, count, _report); \
1013+
} \
1014+
static ssize_t name##_show(struct device *kdev, struct device_attribute *kattr, char *buf) \
1015+
{ \
1016+
return pstr_show(kdev, kattr, buf, _report); \
1017+
} \
1018+
static DEVICE_ATTR_RW(name);
10251019

10261020
CP2112_PSTR_ATTR(manufacturer, CP2112_MANUFACTURER_STRING);
10271021
CP2112_PSTR_ATTR(product, CP2112_PRODUCT_STRING);
@@ -1036,9 +1030,9 @@ static const struct attribute_group cp2112_attr_group = {
10361030
&dev_attr_max_power.attr,
10371031
&dev_attr_power_mode.attr,
10381032
&dev_attr_release_version.attr,
1039-
&dev_attr_manufacturer.attr.attr,
1040-
&dev_attr_product.attr.attr,
1041-
&dev_attr_serial.attr.attr,
1033+
&dev_attr_manufacturer.attr,
1034+
&dev_attr_product.attr,
1035+
&dev_attr_serial.attr,
10421036
NULL
10431037
}
10441038
};
@@ -1063,7 +1057,7 @@ static void chmod_sysfs_attrs(struct hid_device *hdev)
10631057
}
10641058

10651059
for (attr = cp2112_attr_group.attrs; *attr; ++attr) {
1066-
umode_t mode = (buf[1] & 1) ? S_IWUSR | S_IRUGO : S_IRUGO;
1060+
umode_t mode = (buf[1] & 1) ? 0644 : 0444;
10671061
ret = sysfs_chmod_file(&hdev->dev.kobj, *attr, mode);
10681062
if (ret < 0)
10691063
hid_err(hdev, "error chmoding sysfs file %s\n",
@@ -1080,16 +1074,20 @@ static void cp2112_gpio_irq_mask(struct irq_data *d)
10801074
{
10811075
struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
10821076
struct cp2112_device *dev = gpiochip_get_data(gc);
1077+
irq_hw_number_t hwirq = irqd_to_hwirq(d);
10831078

1084-
__clear_bit(d->hwirq, &dev->irq_mask);
1079+
__clear_bit(hwirq, &dev->irq_mask);
1080+
gpiochip_disable_irq(gc, hwirq);
10851081
}
10861082

10871083
static void cp2112_gpio_irq_unmask(struct irq_data *d)
10881084
{
10891085
struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
10901086
struct cp2112_device *dev = gpiochip_get_data(gc);
1087+
irq_hw_number_t hwirq = irqd_to_hwirq(d);
10911088

1092-
__set_bit(d->hwirq, &dev->irq_mask);
1089+
gpiochip_enable_irq(gc, hwirq);
1090+
__set_bit(hwirq, &dev->irq_mask);
10931091
}
10941092

10951093
static void cp2112_gpio_poll_callback(struct work_struct *work)
@@ -1098,7 +1096,6 @@ static void cp2112_gpio_poll_callback(struct work_struct *work)
10981096
gpio_poll_worker.work);
10991097
struct irq_data *d;
11001098
u8 gpio_mask;
1101-
u8 virqs = (u8)dev->irq_mask;
11021099
u32 irq_type;
11031100
int irq, virq, ret;
11041101

@@ -1109,15 +1106,10 @@ static void cp2112_gpio_poll_callback(struct work_struct *work)
11091106
goto exit;
11101107

11111108
gpio_mask = ret;
1112-
1113-
while (virqs) {
1114-
virq = ffs(virqs) - 1;
1115-
virqs &= ~BIT(virq);
1116-
1117-
if (!dev->gc.to_irq)
1118-
break;
1119-
1120-
irq = dev->gc.to_irq(&dev->gc, virq);
1109+
for_each_set_bit(virq, &dev->irq_mask, CP2112_GPIO_MAX_GPIO) {
1110+
irq = irq_find_mapping(dev->gc.irq.domain, virq);
1111+
if (!irq)
1112+
continue;
11211113

11221114
d = irq_get_irq_data(irq);
11231115
if (!d)
@@ -1175,6 +1167,7 @@ static void cp2112_gpio_irq_shutdown(struct irq_data *d)
11751167
struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
11761168
struct cp2112_device *dev = gpiochip_get_data(gc);
11771169

1170+
cp2112_gpio_irq_mask(d);
11781171
cancel_delayed_work_sync(&dev->gpio_poll_worker);
11791172
}
11801173

@@ -1183,50 +1176,17 @@ static int cp2112_gpio_irq_type(struct irq_data *d, unsigned int type)
11831176
return 0;
11841177
}
11851178

1186-
static int __maybe_unused cp2112_allocate_irq(struct cp2112_device *dev,
1187-
int pin)
1188-
{
1189-
int ret;
1190-
1191-
if (dev->desc[pin])
1192-
return -EINVAL;
1193-
1194-
dev->desc[pin] = gpiochip_request_own_desc(&dev->gc, pin,
1195-
"HID/I2C:Event",
1196-
GPIO_ACTIVE_HIGH,
1197-
GPIOD_IN);
1198-
if (IS_ERR(dev->desc[pin])) {
1199-
dev_err(dev->gc.parent, "Failed to request GPIO\n");
1200-
return PTR_ERR(dev->desc[pin]);
1201-
}
1202-
1203-
ret = cp2112_gpio_direction_input(&dev->gc, pin);
1204-
if (ret < 0) {
1205-
dev_err(dev->gc.parent, "Failed to set GPIO to input dir\n");
1206-
goto err_desc;
1207-
}
1208-
1209-
ret = gpiochip_lock_as_irq(&dev->gc, pin);
1210-
if (ret) {
1211-
dev_err(dev->gc.parent, "Failed to lock GPIO as interrupt\n");
1212-
goto err_desc;
1213-
}
1214-
1215-
ret = gpiod_to_irq(dev->desc[pin]);
1216-
if (ret < 0) {
1217-
dev_err(dev->gc.parent, "Failed to translate GPIO to IRQ\n");
1218-
goto err_lock;
1219-
}
1220-
1221-
return ret;
1222-
1223-
err_lock:
1224-
gpiochip_unlock_as_irq(&dev->gc, pin);
1225-
err_desc:
1226-
gpiochip_free_own_desc(dev->desc[pin]);
1227-
dev->desc[pin] = NULL;
1228-
return ret;
1229-
}
1179+
static const struct irq_chip cp2112_gpio_irqchip = {
1180+
.name = "cp2112-gpio",
1181+
.irq_startup = cp2112_gpio_irq_startup,
1182+
.irq_shutdown = cp2112_gpio_irq_shutdown,
1183+
.irq_ack = cp2112_gpio_irq_ack,
1184+
.irq_mask = cp2112_gpio_irq_mask,
1185+
.irq_unmask = cp2112_gpio_irq_unmask,
1186+
.irq_set_type = cp2112_gpio_irq_type,
1187+
.flags = IRQCHIP_MASK_ON_SUSPEND | IRQCHIP_IMMUTABLE,
1188+
GPIOCHIP_IRQ_RESOURCE_HELPERS,
1189+
};
12301190

12311191
static int cp2112_probe(struct hid_device *hdev, const struct hid_device_id *id)
12321192
{
@@ -1333,21 +1293,12 @@ static int cp2112_probe(struct hid_device *hdev, const struct hid_device_id *id)
13331293
dev->gc.set = cp2112_gpio_set;
13341294
dev->gc.get = cp2112_gpio_get;
13351295
dev->gc.base = -1;
1336-
dev->gc.ngpio = 8;
1296+
dev->gc.ngpio = CP2112_GPIO_MAX_GPIO;
13371297
dev->gc.can_sleep = 1;
13381298
dev->gc.parent = &hdev->dev;
13391299

1340-
dev->irq.name = "cp2112-gpio";
1341-
dev->irq.irq_startup = cp2112_gpio_irq_startup;
1342-
dev->irq.irq_shutdown = cp2112_gpio_irq_shutdown;
1343-
dev->irq.irq_ack = cp2112_gpio_irq_ack;
1344-
dev->irq.irq_mask = cp2112_gpio_irq_mask;
1345-
dev->irq.irq_unmask = cp2112_gpio_irq_unmask;
1346-
dev->irq.irq_set_type = cp2112_gpio_irq_type;
1347-
dev->irq.flags = IRQCHIP_MASK_ON_SUSPEND;
1348-
13491300
girq = &dev->gc.irq;
1350-
girq->chip = &dev->irq;
1301+
gpio_irq_chip_set_chip(girq, &cp2112_gpio_irqchip);
13511302
/* The event comes from the outside so no parent handler */
13521303
girq->parent_handler = NULL;
13531304
girq->num_parents = 0;
@@ -1389,7 +1340,6 @@ static int cp2112_probe(struct hid_device *hdev, const struct hid_device_id *id)
13891340
static void cp2112_remove(struct hid_device *hdev)
13901341
{
13911342
struct cp2112_device *dev = hid_get_drvdata(hdev);
1392-
int i;
13931343

13941344
sysfs_remove_group(&hdev->dev.kobj, &cp2112_attr_group);
13951345
i2c_del_adapter(&dev->adap);
@@ -1399,11 +1349,6 @@ static void cp2112_remove(struct hid_device *hdev)
13991349
cancel_delayed_work_sync(&dev->gpio_poll_worker);
14001350
}
14011351

1402-
for (i = 0; i < ARRAY_SIZE(dev->desc); i++) {
1403-
gpiochip_unlock_as_irq(&dev->gc, i);
1404-
gpiochip_free_own_desc(dev->desc[i]);
1405-
}
1406-
14071352
gpiochip_remove(&dev->gc);
14081353
/* i2c_del_adapter has finished removing all i2c devices from our
14091354
* adapter. Well behaved devices should no longer call our cp2112_xfer

include/linux/string_choices.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ static inline const char *str_read_write(bool v)
3030
{
3131
return v ? "read" : "write";
3232
}
33+
#define str_write_read(v) str_read_write(!(v))
3334

3435
static inline const char *str_on_off(bool v)
3536
{

0 commit comments

Comments
 (0)