1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * HID Sensors Driver 4 * Copyright (c) 2014, Intel Corporation. 5 */ 6 #include <linux/device.h> 7 #include <linux/platform_device.h> 8 #include <linux/module.h> 9 #include <linux/interrupt.h> 10 #include <linux/irq.h> 11 #include <linux/slab.h> 12 #include <linux/delay.h> 13 #include <linux/hid-sensor-hub.h> 14 #include <linux/iio/iio.h> 15 #include <linux/iio/sysfs.h> 16 #include <linux/iio/buffer.h> 17 #include <linux/iio/trigger_consumer.h> 18 #include <linux/iio/triggered_buffer.h> 19 #include "../common/hid-sensors/hid-sensor-trigger.h" 20 21 #define CHANNEL_SCAN_INDEX_PRESENCE 0 22 23 struct prox_state { 24 struct hid_sensor_hub_callbacks callbacks; 25 struct hid_sensor_common common_attributes; 26 struct hid_sensor_hub_attribute_info prox_attr; 27 u32 human_presence; 28 }; 29 30 /* Channel definitions */ 31 static const struct iio_chan_spec prox_channels[] = { 32 { 33 .type = IIO_PROXIMITY, 34 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), 35 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) | 36 BIT(IIO_CHAN_INFO_SCALE) | 37 BIT(IIO_CHAN_INFO_SAMP_FREQ) | 38 BIT(IIO_CHAN_INFO_HYSTERESIS), 39 .scan_index = CHANNEL_SCAN_INDEX_PRESENCE, 40 } 41 }; 42 43 /* Adjust channel real bits based on report descriptor */ 44 static void prox_adjust_channel_bit_mask(struct iio_chan_spec *channels, 45 int channel, int size) 46 { 47 channels[channel].scan_type.sign = 's'; 48 /* Real storage bits will change based on the report desc. */ 49 channels[channel].scan_type.realbits = size * 8; 50 /* Maximum size of a sample to capture is u32 */ 51 channels[channel].scan_type.storagebits = sizeof(u32) * 8; 52 } 53 54 /* Channel read_raw handler */ 55 static int prox_read_raw(struct iio_dev *indio_dev, 56 struct iio_chan_spec const *chan, 57 int *val, int *val2, 58 long mask) 59 { 60 struct prox_state *prox_state = iio_priv(indio_dev); 61 int report_id = -1; 62 u32 address; 63 int ret_type; 64 s32 min; 65 66 *val = 0; 67 *val2 = 0; 68 switch (mask) { 69 case IIO_CHAN_INFO_RAW: 70 switch (chan->scan_index) { 71 case CHANNEL_SCAN_INDEX_PRESENCE: 72 report_id = prox_state->prox_attr.report_id; 73 min = prox_state->prox_attr.logical_minimum; 74 address = HID_USAGE_SENSOR_HUMAN_PRESENCE; 75 break; 76 default: 77 report_id = -1; 78 break; 79 } 80 if (report_id >= 0) { 81 hid_sensor_power_state(&prox_state->common_attributes, 82 true); 83 *val = sensor_hub_input_attr_get_raw_value( 84 prox_state->common_attributes.hsdev, 85 HID_USAGE_SENSOR_PROX, address, 86 report_id, 87 SENSOR_HUB_SYNC, 88 min < 0); 89 hid_sensor_power_state(&prox_state->common_attributes, 90 false); 91 } else { 92 *val = 0; 93 return -EINVAL; 94 } 95 ret_type = IIO_VAL_INT; 96 break; 97 case IIO_CHAN_INFO_SCALE: 98 *val = prox_state->prox_attr.units; 99 ret_type = IIO_VAL_INT; 100 break; 101 case IIO_CHAN_INFO_OFFSET: 102 *val = hid_sensor_convert_exponent( 103 prox_state->prox_attr.unit_expo); 104 ret_type = IIO_VAL_INT; 105 break; 106 case IIO_CHAN_INFO_SAMP_FREQ: 107 ret_type = hid_sensor_read_samp_freq_value( 108 &prox_state->common_attributes, val, val2); 109 break; 110 case IIO_CHAN_INFO_HYSTERESIS: 111 ret_type = hid_sensor_read_raw_hyst_value( 112 &prox_state->common_attributes, val, val2); 113 break; 114 default: 115 ret_type = -EINVAL; 116 break; 117 } 118 119 return ret_type; 120 } 121 122 /* Channel write_raw handler */ 123 static int prox_write_raw(struct iio_dev *indio_dev, 124 struct iio_chan_spec const *chan, 125 int val, 126 int val2, 127 long mask) 128 { 129 struct prox_state *prox_state = iio_priv(indio_dev); 130 int ret = 0; 131 132 switch (mask) { 133 case IIO_CHAN_INFO_SAMP_FREQ: 134 ret = hid_sensor_write_samp_freq_value( 135 &prox_state->common_attributes, val, val2); 136 break; 137 case IIO_CHAN_INFO_HYSTERESIS: 138 ret = hid_sensor_write_raw_hyst_value( 139 &prox_state->common_attributes, val, val2); 140 break; 141 default: 142 ret = -EINVAL; 143 } 144 145 return ret; 146 } 147 148 static const struct iio_info prox_info = { 149 .read_raw = &prox_read_raw, 150 .write_raw = &prox_write_raw, 151 }; 152 153 /* Function to push data to buffer */ 154 static void hid_sensor_push_data(struct iio_dev *indio_dev, const void *data, 155 int len) 156 { 157 dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n"); 158 iio_push_to_buffers(indio_dev, data); 159 } 160 161 /* Callback handler to send event after all samples are received and captured */ 162 static int prox_proc_event(struct hid_sensor_hub_device *hsdev, 163 unsigned usage_id, 164 void *priv) 165 { 166 struct iio_dev *indio_dev = platform_get_drvdata(priv); 167 struct prox_state *prox_state = iio_priv(indio_dev); 168 169 dev_dbg(&indio_dev->dev, "prox_proc_event\n"); 170 if (atomic_read(&prox_state->common_attributes.data_ready)) 171 hid_sensor_push_data(indio_dev, 172 &prox_state->human_presence, 173 sizeof(prox_state->human_presence)); 174 175 return 0; 176 } 177 178 /* Capture samples in local storage */ 179 static int prox_capture_sample(struct hid_sensor_hub_device *hsdev, 180 unsigned usage_id, 181 size_t raw_len, char *raw_data, 182 void *priv) 183 { 184 struct iio_dev *indio_dev = platform_get_drvdata(priv); 185 struct prox_state *prox_state = iio_priv(indio_dev); 186 int ret = -EINVAL; 187 188 switch (usage_id) { 189 case HID_USAGE_SENSOR_HUMAN_PRESENCE: 190 prox_state->human_presence = *(u32 *)raw_data; 191 ret = 0; 192 break; 193 default: 194 break; 195 } 196 197 return ret; 198 } 199 200 /* Parse report which is specific to an usage id*/ 201 static int prox_parse_report(struct platform_device *pdev, 202 struct hid_sensor_hub_device *hsdev, 203 struct iio_chan_spec *channels, 204 unsigned usage_id, 205 struct prox_state *st) 206 { 207 int ret; 208 209 ret = sensor_hub_input_get_attribute_info(hsdev, HID_INPUT_REPORT, 210 usage_id, 211 HID_USAGE_SENSOR_HUMAN_PRESENCE, 212 &st->prox_attr); 213 if (ret < 0) 214 return ret; 215 prox_adjust_channel_bit_mask(channels, CHANNEL_SCAN_INDEX_PRESENCE, 216 st->prox_attr.size); 217 218 dev_dbg(&pdev->dev, "prox %x:%x\n", st->prox_attr.index, 219 st->prox_attr.report_id); 220 221 /* Set Sensitivity field ids, when there is no individual modifier */ 222 if (st->common_attributes.sensitivity.index < 0) { 223 sensor_hub_input_get_attribute_info(hsdev, 224 HID_FEATURE_REPORT, usage_id, 225 HID_USAGE_SENSOR_DATA_MOD_CHANGE_SENSITIVITY_ABS | 226 HID_USAGE_SENSOR_DATA_PRESENCE, 227 &st->common_attributes.sensitivity); 228 dev_dbg(&pdev->dev, "Sensitivity index:report %d:%d\n", 229 st->common_attributes.sensitivity.index, 230 st->common_attributes.sensitivity.report_id); 231 } 232 if (st->common_attributes.sensitivity.index < 0) 233 sensor_hub_input_get_attribute_info(hsdev, 234 HID_FEATURE_REPORT, usage_id, 235 HID_USAGE_SENSOR_DATA_MOD_CHANGE_SENSITIVITY_ABS | 236 HID_USAGE_SENSOR_HUMAN_PRESENCE, 237 &st->common_attributes.sensitivity); 238 239 return ret; 240 } 241 242 /* Function to initialize the processing for usage id */ 243 static int hid_prox_probe(struct platform_device *pdev) 244 { 245 int ret = 0; 246 static const char *name = "prox"; 247 struct iio_dev *indio_dev; 248 struct prox_state *prox_state; 249 struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 250 251 indio_dev = devm_iio_device_alloc(&pdev->dev, 252 sizeof(struct prox_state)); 253 if (!indio_dev) 254 return -ENOMEM; 255 platform_set_drvdata(pdev, indio_dev); 256 257 prox_state = iio_priv(indio_dev); 258 prox_state->common_attributes.hsdev = hsdev; 259 prox_state->common_attributes.pdev = pdev; 260 261 ret = hid_sensor_parse_common_attributes(hsdev, HID_USAGE_SENSOR_PROX, 262 &prox_state->common_attributes); 263 if (ret) { 264 dev_err(&pdev->dev, "failed to setup common attributes\n"); 265 return ret; 266 } 267 268 indio_dev->channels = kmemdup(prox_channels, sizeof(prox_channels), 269 GFP_KERNEL); 270 if (!indio_dev->channels) { 271 dev_err(&pdev->dev, "failed to duplicate channels\n"); 272 return -ENOMEM; 273 } 274 275 ret = prox_parse_report(pdev, hsdev, 276 (struct iio_chan_spec *)indio_dev->channels, 277 HID_USAGE_SENSOR_PROX, prox_state); 278 if (ret) { 279 dev_err(&pdev->dev, "failed to setup attributes\n"); 280 goto error_free_dev_mem; 281 } 282 283 indio_dev->num_channels = ARRAY_SIZE(prox_channels); 284 indio_dev->dev.parent = &pdev->dev; 285 indio_dev->info = &prox_info; 286 indio_dev->name = name; 287 indio_dev->modes = INDIO_DIRECT_MODE; 288 289 ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time, 290 NULL, NULL); 291 if (ret) { 292 dev_err(&pdev->dev, "failed to initialize trigger buffer\n"); 293 goto error_free_dev_mem; 294 } 295 atomic_set(&prox_state->common_attributes.data_ready, 0); 296 ret = hid_sensor_setup_trigger(indio_dev, name, 297 &prox_state->common_attributes); 298 if (ret) { 299 dev_err(&pdev->dev, "trigger setup failed\n"); 300 goto error_unreg_buffer_funcs; 301 } 302 303 ret = iio_device_register(indio_dev); 304 if (ret) { 305 dev_err(&pdev->dev, "device register failed\n"); 306 goto error_remove_trigger; 307 } 308 309 prox_state->callbacks.send_event = prox_proc_event; 310 prox_state->callbacks.capture_sample = prox_capture_sample; 311 prox_state->callbacks.pdev = pdev; 312 ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_PROX, 313 &prox_state->callbacks); 314 if (ret < 0) { 315 dev_err(&pdev->dev, "callback reg failed\n"); 316 goto error_iio_unreg; 317 } 318 319 return ret; 320 321 error_iio_unreg: 322 iio_device_unregister(indio_dev); 323 error_remove_trigger: 324 hid_sensor_remove_trigger(&prox_state->common_attributes); 325 error_unreg_buffer_funcs: 326 iio_triggered_buffer_cleanup(indio_dev); 327 error_free_dev_mem: 328 kfree(indio_dev->channels); 329 return ret; 330 } 331 332 /* Function to deinitialize the processing for usage id */ 333 static int hid_prox_remove(struct platform_device *pdev) 334 { 335 struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 336 struct iio_dev *indio_dev = platform_get_drvdata(pdev); 337 struct prox_state *prox_state = iio_priv(indio_dev); 338 339 sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_PROX); 340 iio_device_unregister(indio_dev); 341 hid_sensor_remove_trigger(&prox_state->common_attributes); 342 iio_triggered_buffer_cleanup(indio_dev); 343 kfree(indio_dev->channels); 344 345 return 0; 346 } 347 348 static const struct platform_device_id hid_prox_ids[] = { 349 { 350 /* Format: HID-SENSOR-usage_id_in_hex_lowercase */ 351 .name = "HID-SENSOR-200011", 352 }, 353 { /* sentinel */ } 354 }; 355 MODULE_DEVICE_TABLE(platform, hid_prox_ids); 356 357 static struct platform_driver hid_prox_platform_driver = { 358 .id_table = hid_prox_ids, 359 .driver = { 360 .name = KBUILD_MODNAME, 361 .pm = &hid_sensor_pm_ops, 362 }, 363 .probe = hid_prox_probe, 364 .remove = hid_prox_remove, 365 }; 366 module_platform_driver(hid_prox_platform_driver); 367 368 MODULE_DESCRIPTION("HID Sensor Proximity"); 369 MODULE_AUTHOR("Archana Patni <archana.patni@intel.com>"); 370 MODULE_LICENSE("GPL"); 371