Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/nab/target...
[firefly-linux-kernel-4.4.55.git] / drivers / staging / iio / iio_simple_dummy.c
index bf78e6f0311ff3699818bd42ef055e21e4b2710a..e4520213f627fe431597817ac8c4099bde40f1c4 100644 (file)
@@ -69,6 +69,34 @@ static const struct iio_event_spec iio_dummy_event = {
        .mask_separate = BIT(IIO_EV_INFO_VALUE) | BIT(IIO_EV_INFO_ENABLE),
 };
 
+/*
+ * simple step detect event - triggered when a step is detected
+ */
+static const struct iio_event_spec step_detect_event = {
+       .type = IIO_EV_TYPE_CHANGE,
+       .dir = IIO_EV_DIR_NONE,
+       .mask_separate = BIT(IIO_EV_INFO_ENABLE),
+};
+
+/*
+ * simple transition event - triggered when the reported running confidence
+ * value rises above a threshold value
+ */
+static const struct iio_event_spec iio_running_event = {
+       .type = IIO_EV_TYPE_THRESH,
+       .dir = IIO_EV_DIR_RISING,
+       .mask_separate = BIT(IIO_EV_INFO_VALUE) | BIT(IIO_EV_INFO_ENABLE),
+};
+
+/*
+ * simple transition event - triggered when the reported walking confidence
+ * value falls under a threshold value
+ */
+static const struct iio_event_spec iio_walking_event = {
+       .type = IIO_EV_TYPE_THRESH,
+       .dir = IIO_EV_DIR_FALLING,
+       .mask_separate = BIT(IIO_EV_INFO_VALUE) | BIT(IIO_EV_INFO_ENABLE),
+};
 #endif
 
 /*
@@ -211,10 +239,44 @@ static const struct iio_chan_spec iio_dummy_channels[] = {
        {
                .type = IIO_VOLTAGE,
                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
+               .scan_index = -1, /* No buffer support */
                .output = 1,
                .indexed = 1,
                .channel = 0,
        },
+       {
+               .type = IIO_STEPS,
+               .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_ENABLE) |
+                       BIT(IIO_CHAN_INFO_CALIBHEIGHT),
+               .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
+               .scan_index = -1, /* No buffer support */
+#ifdef CONFIG_IIO_SIMPLE_DUMMY_EVENTS
+               .event_spec = &step_detect_event,
+               .num_event_specs = 1,
+#endif /* CONFIG_IIO_SIMPLE_DUMMY_EVENTS */
+       },
+       {
+               .type = IIO_ACTIVITY,
+               .modified = 1,
+               .channel2 = IIO_MOD_RUNNING,
+               .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
+               .scan_index = -1, /* No buffer support */
+#ifdef CONFIG_IIO_SIMPLE_DUMMY_EVENTS
+               .event_spec = &iio_running_event,
+               .num_event_specs = 1,
+#endif /* CONFIG_IIO_SIMPLE_DUMMY_EVENTS */
+       },
+       {
+               .type = IIO_ACTIVITY,
+               .modified = 1,
+               .channel2 = IIO_MOD_WALKING,
+               .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
+               .scan_index = -1, /* No buffer support */
+#ifdef CONFIG_IIO_SIMPLE_DUMMY_EVENTS
+               .event_spec = &iio_walking_event,
+               .num_event_specs = 1,
+#endif /* CONFIG_IIO_SIMPLE_DUMMY_EVENTS */
+       },
 };
 
 /**
@@ -263,24 +325,55 @@ static int iio_dummy_read_raw(struct iio_dev *indio_dev,
                        break;
                }
                break;
+       case IIO_CHAN_INFO_PROCESSED:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       *val = st->steps;
+                       ret = IIO_VAL_INT;
+                       break;
+               case IIO_ACTIVITY:
+                       switch (chan->channel2) {
+                       case IIO_MOD_RUNNING:
+                               *val = st->activity_running;
+                               ret = IIO_VAL_INT;
+                               break;
+                       case IIO_MOD_WALKING:
+                               *val = st->activity_walking;
+                               ret = IIO_VAL_INT;
+                               break;
+                       default:
+                               break;
+                       }
+                       break;
+               default:
+                       break;
+               }
+               break;
        case IIO_CHAN_INFO_OFFSET:
                /* only single ended adc -> 7 */
                *val = 7;
                ret = IIO_VAL_INT;
                break;
        case IIO_CHAN_INFO_SCALE:
-               switch (chan->differential) {
-               case 0:
-                       /* only single ended adc -> 0.001333 */
-                       *val = 0;
-                       *val2 = 1333;
-                       ret = IIO_VAL_INT_PLUS_MICRO;
+               switch (chan->type) {
+               case IIO_VOLTAGE:
+                       switch (chan->differential) {
+                       case 0:
+                               /* only single ended adc -> 0.001333 */
+                               *val = 0;
+                               *val2 = 1333;
+                               ret = IIO_VAL_INT_PLUS_MICRO;
+                               break;
+                       case 1:
+                               /* all differential adc channels ->
+                                * 0.000001344 */
+                               *val = 0;
+                               *val2 = 1344;
+                               ret = IIO_VAL_INT_PLUS_NANO;
+                       }
+                       break;
+               default:
                        break;
-               case 1:
-                       /* all differential adc channels -> 0.000001344 */
-                       *val = 0;
-                       *val2 = 1344;
-                       ret = IIO_VAL_INT_PLUS_NANO;
                }
                break;
        case IIO_CHAN_INFO_CALIBBIAS:
@@ -298,6 +391,27 @@ static int iio_dummy_read_raw(struct iio_dev *indio_dev,
                *val2 = 33;
                ret = IIO_VAL_INT_PLUS_NANO;
                break;
+       case IIO_CHAN_INFO_ENABLE:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       *val = st->steps_enabled;
+                       ret = IIO_VAL_INT;
+                       break;
+               default:
+                       break;
+               }
+               break;
+       case IIO_CHAN_INFO_CALIBHEIGHT:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       *val = st->height;
+                       ret = IIO_VAL_INT;
+                       break;
+               default:
+                       break;
+               }
+               break;
+
        default:
                break;
        }
@@ -330,14 +444,45 @@ static int iio_dummy_write_raw(struct iio_dev *indio_dev,
 
        switch (mask) {
        case IIO_CHAN_INFO_RAW:
-               if (chan->output == 0)
+               switch (chan->type) {
+               case IIO_VOLTAGE:
+                       if (chan->output == 0)
+                               return -EINVAL;
+
+                       /* Locking not required as writing single value */
+                       mutex_lock(&st->lock);
+                       st->dac_val = val;
+                       mutex_unlock(&st->lock);
+                       return 0;
+               default:
                        return -EINVAL;
-
-               /* Locking not required as writing single value */
-               mutex_lock(&st->lock);
-               st->dac_val = val;
-               mutex_unlock(&st->lock);
-               return 0;
+               }
+       case IIO_CHAN_INFO_PROCESSED:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       mutex_lock(&st->lock);
+                       st->steps = val;
+                       mutex_unlock(&st->lock);
+                       return 0;
+               case IIO_ACTIVITY:
+                       if (val < 0)
+                               val = 0;
+                       if (val > 100)
+                               val = 100;
+                       switch (chan->channel2) {
+                       case IIO_MOD_RUNNING:
+                               st->activity_running = val;
+                               return 0;
+                       case IIO_MOD_WALKING:
+                               st->activity_walking = val;
+                               return 0;
+                       default:
+                               return -EINVAL;
+                       }
+                       break;
+               default:
+                       return -EINVAL;
+               }
        case IIO_CHAN_INFO_CALIBSCALE:
                mutex_lock(&st->lock);
                /* Compare against table - hard matching here */
@@ -356,6 +501,24 @@ static int iio_dummy_write_raw(struct iio_dev *indio_dev,
                st->accel_calibbias = val;
                mutex_unlock(&st->lock);
                return 0;
+       case IIO_CHAN_INFO_ENABLE:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       mutex_lock(&st->lock);
+                       st->steps_enabled = val;
+                       mutex_unlock(&st->lock);
+                       return 0;
+               default:
+                       return -EINVAL;
+               }
+       case IIO_CHAN_INFO_CALIBHEIGHT:
+               switch (chan->type) {
+               case IIO_STEPS:
+                       st->height = val;
+                       return 0;
+               default:
+                       return -EINVAL;
+               }
 
        default:
                return -EINVAL;
@@ -395,6 +558,9 @@ static int iio_dummy_init_device(struct iio_dev *indio_dev)
        st->accel_val = 34;
        st->accel_calibbias = -7;
        st->accel_calibscale = &dummy_scales[0];
+       st->steps = 47;
+       st->activity_running = 98;
+       st->activity_walking = 4;
 
        return 0;
 }
@@ -475,13 +641,7 @@ static int iio_dummy_probe(int index)
        if (ret < 0)
                goto error_free_device;
 
-       /*
-        * Configure buffered capture support and register the channels with the
-        * buffer, but avoid the output channel being registered by reducing the
-        * number of channels by 1.
-        */
-       ret = iio_simple_dummy_configure_buffer(indio_dev,
-                                               iio_dummy_channels, 5);
+       ret = iio_simple_dummy_configure_buffer(indio_dev);
        if (ret < 0)
                goto error_unregister_events;