diff options
Diffstat (limited to 'drivers/iio/light/hid-sensor-als.c')
| -rw-r--r-- | drivers/iio/light/hid-sensor-als.c | 74 |
1 files changed, 36 insertions, 38 deletions
diff --git a/drivers/iio/light/hid-sensor-als.c b/drivers/iio/light/hid-sensor-als.c index 6bf1bc9a38fe..929343e42d83 100644 --- a/drivers/iio/light/hid-sensor-als.c +++ b/drivers/iio/light/hid-sensor-als.c @@ -33,9 +33,9 @@ struct als_state { u32 illum[CHANNEL_SCAN_INDEX_MAX]; aligned_s64 timestamp; } scan; - int scale_pre_decml; - int scale_post_decml; - int scale_precision; + int scale_pre_decml[CHANNEL_SCAN_INDEX_MAX]; + int scale_post_decml[CHANNEL_SCAN_INDEX_MAX]; + int scale_precision[CHANNEL_SCAN_INDEX_MAX]; int value_offset; int num_channels; s64 timestamp; @@ -119,9 +119,8 @@ static const struct iio_chan_spec als_channels[] = { /* Channel read_raw handler */ static int als_read_raw(struct iio_dev *indio_dev, - struct iio_chan_spec const *chan, - int *val, int *val2, - long mask) + struct iio_chan_spec const *chan, + int *val, int *val2, long mask) { struct als_state *als_state = iio_priv(indio_dev); struct hid_sensor_hub_device *hsdev = als_state->common_attributes.hsdev; @@ -162,12 +161,12 @@ static int als_read_raw(struct iio_dev *indio_dev, } if (report_id >= 0) { hid_sensor_power_state(&als_state->common_attributes, - true); + true); *val = sensor_hub_input_attr_get_raw_value( hsdev, hsdev->usage, address, report_id, SENSOR_HUB_SYNC, min < 0); hid_sensor_power_state(&als_state->common_attributes, - false); + false); } else { *val = 0; return -EINVAL; @@ -175,9 +174,11 @@ static int als_read_raw(struct iio_dev *indio_dev, ret_type = IIO_VAL_INT; break; case IIO_CHAN_INFO_SCALE: - *val = als_state->scale_pre_decml; - *val2 = als_state->scale_post_decml; - ret_type = als_state->scale_precision; + if (chan->scan_index >= CHANNEL_SCAN_INDEX_MAX) + return -EINVAL; + *val = als_state->scale_pre_decml[chan->scan_index]; + *val2 = als_state->scale_post_decml[chan->scan_index]; + ret_type = als_state->scale_precision[chan->scan_index]; break; case IIO_CHAN_INFO_OFFSET: *val = als_state->value_offset; @@ -205,10 +206,8 @@ static int als_read_raw(struct iio_dev *indio_dev, /* Channel write_raw handler */ static int als_write_raw(struct iio_dev *indio_dev, - struct iio_chan_spec const *chan, - int val, - int val2, - long mask) + struct iio_chan_spec const *chan, + int val, int val2, long mask) { struct als_state *als_state = iio_priv(indio_dev); int ret = 0; @@ -240,8 +239,7 @@ static const struct iio_info als_info = { /* Callback handler to send event after all samples are received and captured */ static int als_proc_event(struct hid_sensor_hub_device *hsdev, - unsigned usage_id, - void *priv) + u32 usage_id, void *priv) { struct iio_dev *indio_dev = platform_get_drvdata(priv); struct als_state *als_state = iio_priv(indio_dev); @@ -262,9 +260,9 @@ static int als_proc_event(struct hid_sensor_hub_device *hsdev, /* Capture samples in local storage */ static int als_capture_sample(struct hid_sensor_hub_device *hsdev, - unsigned usage_id, - size_t raw_len, char *raw_data, - void *priv) + u32 usage_id, + size_t raw_len, char *raw_data, + void *priv) { struct iio_dev *indio_dev = platform_get_drvdata(priv); struct als_state *als_state = iio_priv(indio_dev); @@ -303,9 +301,9 @@ static int als_capture_sample(struct hid_sensor_hub_device *hsdev, /* Parse report which is specific to an usage id*/ static int als_parse_report(struct platform_device *pdev, - struct hid_sensor_hub_device *hsdev, - unsigned usage_id, - struct als_state *st) + struct hid_sensor_hub_device *hsdev, + u32 usage_id, + struct als_state *st) { struct iio_chan_spec *channels; int ret, index = 0; @@ -331,6 +329,10 @@ static int als_parse_report(struct platform_device *pdev, }; ++index; + st->scale_precision[i] = hid_sensor_format_scale(usage_id, + &st->als[i], &st->scale_pre_decml[i], + &st->scale_post_decml[i]); + dev_dbg(&pdev->dev, "als %x:%x\n", st->als[i].index, st->als[i].report_id); } @@ -340,10 +342,6 @@ static int als_parse_report(struct platform_device *pdev, if (index) ret = 0; - st->scale_precision = hid_sensor_format_scale(usage_id, - &st->als[CHANNEL_SCAN_INDEX_INTENSITY], - &st->scale_pre_decml, &st->scale_post_decml); - return ret; } @@ -399,31 +397,31 @@ static int hid_als_probe(struct platform_device *pdev) atomic_set(&als_state->common_attributes.data_ready, 0); ret = hid_sensor_setup_trigger(indio_dev, name, - &als_state->common_attributes); + &als_state->common_attributes); if (ret < 0) { dev_err(&pdev->dev, "trigger setup failed\n"); return ret; } - ret = iio_device_register(indio_dev); - if (ret) { - dev_err(&pdev->dev, "device register failed\n"); - goto error_remove_trigger; - } - als_state->callbacks.send_event = als_proc_event; als_state->callbacks.capture_sample = als_capture_sample; als_state->callbacks.pdev = pdev; ret = sensor_hub_register_callback(hsdev, hsdev->usage, &als_state->callbacks); if (ret < 0) { dev_err(&pdev->dev, "callback reg failed\n"); - goto error_iio_unreg; + goto error_remove_trigger; + } + + ret = iio_device_register(indio_dev); + if (ret) { + dev_err(&pdev->dev, "device register failed\n"); + goto error_remove_callback; } return ret; -error_iio_unreg: - iio_device_unregister(indio_dev); +error_remove_callback: + sensor_hub_remove_callback(hsdev, hsdev->usage); error_remove_trigger: hid_sensor_remove_trigger(indio_dev, &als_state->common_attributes); return ret; @@ -436,8 +434,8 @@ static void hid_als_remove(struct platform_device *pdev) struct iio_dev *indio_dev = platform_get_drvdata(pdev); struct als_state *als_state = iio_priv(indio_dev); - sensor_hub_remove_callback(hsdev, hsdev->usage); iio_device_unregister(indio_dev); + sensor_hub_remove_callback(hsdev, hsdev->usage); hid_sensor_remove_trigger(indio_dev, &als_state->common_attributes); } |
