summaryrefslogtreecommitdiffstats
path: root/drivers/hid/hid-input.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/hid/hid-input.c')
-rw-r--r--drivers/hid/hid-input.c76
1 files changed, 54 insertions, 22 deletions
diff --git a/drivers/hid/hid-input.c b/drivers/hid/hid-input.c
index 052869d0ab78..008e89bf6f3c 100644
--- a/drivers/hid/hid-input.c
+++ b/drivers/hid/hid-input.c
@@ -339,7 +339,7 @@ static int hidinput_get_battery_property(struct power_supply *psy,
enum power_supply_property prop,
union power_supply_propval *val)
{
- struct hid_device *dev = container_of(psy, struct hid_device, battery);
+ struct hid_device *dev = power_supply_get_drvdata(psy);
int ret = 0;
__u8 *buf;
@@ -397,26 +397,32 @@ static int hidinput_get_battery_property(struct power_supply *psy,
static bool hidinput_setup_battery(struct hid_device *dev, unsigned report_type, struct hid_field *field)
{
- struct power_supply *battery = &dev->battery;
- int ret;
+ struct power_supply_desc *psy_desc = NULL;
+ struct power_supply_config psy_cfg = { .drv_data = dev, };
unsigned quirks;
s32 min, max;
if (field->usage->hid != HID_DC_BATTERYSTRENGTH)
return false; /* no match */
- if (battery->name != NULL)
+ if (dev->battery != NULL)
goto out; /* already initialized? */
- battery->name = kasprintf(GFP_KERNEL, "hid-%s-battery", dev->uniq);
- if (battery->name == NULL)
+ psy_desc = kzalloc(sizeof(*psy_desc), GFP_KERNEL);
+ if (psy_desc == NULL)
goto out;
- battery->type = POWER_SUPPLY_TYPE_BATTERY;
- battery->properties = hidinput_battery_props;
- battery->num_properties = ARRAY_SIZE(hidinput_battery_props);
- battery->use_for_apm = 0;
- battery->get_property = hidinput_get_battery_property;
+ psy_desc->name = kasprintf(GFP_KERNEL, "hid-%s-battery", dev->uniq);
+ if (psy_desc->name == NULL) {
+ kfree(psy_desc);
+ goto out;
+ }
+
+ psy_desc->type = POWER_SUPPLY_TYPE_BATTERY;
+ psy_desc->properties = hidinput_battery_props;
+ psy_desc->num_properties = ARRAY_SIZE(hidinput_battery_props);
+ psy_desc->use_for_apm = 0;
+ psy_desc->get_property = hidinput_get_battery_property;
quirks = find_battery_quirk(dev);
@@ -439,27 +445,30 @@ static bool hidinput_setup_battery(struct hid_device *dev, unsigned report_type,
dev->battery_report_type = report_type;
dev->battery_report_id = field->report->id;
- ret = power_supply_register(&dev->dev, battery);
- if (ret != 0) {
- hid_warn(dev, "can't register power supply: %d\n", ret);
- kfree(battery->name);
- battery->name = NULL;
+ dev->battery = power_supply_register(&dev->dev, psy_desc, &psy_cfg);
+ if (IS_ERR(dev->battery)) {
+ hid_warn(dev, "can't register power supply: %ld\n",
+ PTR_ERR(dev->battery));
+ kfree(psy_desc->name);
+ kfree(psy_desc);
+ dev->battery = NULL;
+ } else {
+ power_supply_powers(dev->battery, &dev->dev);
}
- power_supply_powers(battery, &dev->dev);
-
out:
return true;
}
static void hidinput_cleanup_battery(struct hid_device *dev)
{
- if (!dev->battery.name)
+ if (!dev->battery)
return;
- power_supply_unregister(&dev->battery);
- kfree(dev->battery.name);
- dev->battery.name = NULL;
+ power_supply_unregister(dev->battery);
+ kfree(dev->battery->desc->name);
+ kfree(dev->battery->desc);
+ dev->battery = NULL;
}
#else /* !CONFIG_HID_BATTERY_STRENGTH */
static bool hidinput_setup_battery(struct hid_device *dev, unsigned report_type,
@@ -711,6 +720,29 @@ static void hidinput_configure_usage(struct hid_input *hidinput, struct hid_fiel
}
break;
+ case HID_UP_TELEPHONY:
+ switch (usage->hid & HID_USAGE) {
+ case 0x2f: map_key_clear(KEY_MICMUTE); break;
+ case 0xb0: map_key_clear(KEY_NUMERIC_0); break;
+ case 0xb1: map_key_clear(KEY_NUMERIC_1); break;
+ case 0xb2: map_key_clear(KEY_NUMERIC_2); break;
+ case 0xb3: map_key_clear(KEY_NUMERIC_3); break;
+ case 0xb4: map_key_clear(KEY_NUMERIC_4); break;
+ case 0xb5: map_key_clear(KEY_NUMERIC_5); break;
+ case 0xb6: map_key_clear(KEY_NUMERIC_6); break;
+ case 0xb7: map_key_clear(KEY_NUMERIC_7); break;
+ case 0xb8: map_key_clear(KEY_NUMERIC_8); break;
+ case 0xb9: map_key_clear(KEY_NUMERIC_9); break;
+ case 0xba: map_key_clear(KEY_NUMERIC_STAR); break;
+ case 0xbb: map_key_clear(KEY_NUMERIC_POUND); break;
+ case 0xbc: map_key_clear(KEY_NUMERIC_A); break;
+ case 0xbd: map_key_clear(KEY_NUMERIC_B); break;
+ case 0xbe: map_key_clear(KEY_NUMERIC_C); break;
+ case 0xbf: map_key_clear(KEY_NUMERIC_D); break;
+ default: goto ignore;
+ }
+ break;
+
case HID_UP_CONSUMER: /* USB HUT v1.12, pages 75-84 */
switch (usage->hid & HID_USAGE) {
case 0x000: goto ignore;