diff options
-rw-r--r-- | drivers/staging/iio/adc/mxs-lradc.c | 91 |
1 files changed, 78 insertions, 13 deletions
diff --git a/drivers/staging/iio/adc/mxs-lradc.c b/drivers/staging/iio/adc/mxs-lradc.c index e2dd7830b320..5a4499c3d22a 100644 --- a/drivers/staging/iio/adc/mxs-lradc.c +++ b/drivers/staging/iio/adc/mxs-lradc.c | |||
@@ -759,20 +759,11 @@ static void mxs_lradc_handle_touch(struct mxs_lradc *lradc) | |||
759 | /* | 759 | /* |
760 | * Raw I/O operations | 760 | * Raw I/O operations |
761 | */ | 761 | */ |
762 | static int mxs_lradc_read_raw(struct iio_dev *iio_dev, | 762 | static int mxs_lradc_read_single(struct iio_dev *iio_dev, int chan, int *val) |
763 | const struct iio_chan_spec *chan, | ||
764 | int *val, int *val2, long m) | ||
765 | { | 763 | { |
766 | struct mxs_lradc *lradc = iio_priv(iio_dev); | 764 | struct mxs_lradc *lradc = iio_priv(iio_dev); |
767 | int ret; | 765 | int ret; |
768 | 766 | ||
769 | if (m != IIO_CHAN_INFO_RAW) | ||
770 | return -EINVAL; | ||
771 | |||
772 | /* Check for invalid channel */ | ||
773 | if (chan->channel > LRADC_MAX_TOTAL_CHANS) | ||
774 | return -EINVAL; | ||
775 | |||
776 | /* | 767 | /* |
777 | * See if there is no buffered operation in progess. If there is, simply | 768 | * See if there is no buffered operation in progess. If there is, simply |
778 | * bail out. This can be improved to support both buffered and raw IO at | 769 | * bail out. This can be improved to support both buffered and raw IO at |
@@ -797,7 +788,7 @@ static int mxs_lradc_read_raw(struct iio_dev *iio_dev, | |||
797 | 788 | ||
798 | /* Clean the slot's previous content, then set new one. */ | 789 | /* Clean the slot's previous content, then set new one. */ |
799 | mxs_lradc_reg_clear(lradc, LRADC_CTRL4_LRADCSELECT_MASK(0), LRADC_CTRL4); | 790 | mxs_lradc_reg_clear(lradc, LRADC_CTRL4_LRADCSELECT_MASK(0), LRADC_CTRL4); |
800 | mxs_lradc_reg_set(lradc, chan->channel, LRADC_CTRL4); | 791 | mxs_lradc_reg_set(lradc, chan, LRADC_CTRL4); |
801 | 792 | ||
802 | mxs_lradc_reg_wrt(lradc, 0, LRADC_CH(0)); | 793 | mxs_lradc_reg_wrt(lradc, 0, LRADC_CH(0)); |
803 | 794 | ||
@@ -824,6 +815,71 @@ err: | |||
824 | return ret; | 815 | return ret; |
825 | } | 816 | } |
826 | 817 | ||
818 | static int mxs_lradc_read_temp(struct iio_dev *iio_dev, int *val) | ||
819 | { | ||
820 | int ret, min, max; | ||
821 | |||
822 | ret = mxs_lradc_read_single(iio_dev, 8, &min); | ||
823 | if (ret != IIO_VAL_INT) | ||
824 | return ret; | ||
825 | |||
826 | ret = mxs_lradc_read_single(iio_dev, 9, &max); | ||
827 | if (ret != IIO_VAL_INT) | ||
828 | return ret; | ||
829 | |||
830 | *val = max - min; | ||
831 | |||
832 | return IIO_VAL_INT; | ||
833 | } | ||
834 | |||
835 | static int mxs_lradc_read_raw(struct iio_dev *iio_dev, | ||
836 | const struct iio_chan_spec *chan, | ||
837 | int *val, int *val2, long m) | ||
838 | { | ||
839 | /* Check for invalid channel */ | ||
840 | if (chan->channel > LRADC_MAX_TOTAL_CHANS) | ||
841 | return -EINVAL; | ||
842 | |||
843 | switch (m) { | ||
844 | case IIO_CHAN_INFO_RAW: | ||
845 | if (chan->type == IIO_TEMP) | ||
846 | return mxs_lradc_read_temp(iio_dev, val); | ||
847 | |||
848 | return mxs_lradc_read_single(iio_dev, chan->channel, val); | ||
849 | |||
850 | case IIO_CHAN_INFO_SCALE: | ||
851 | if (chan->type == IIO_TEMP) { | ||
852 | /* From the datasheet, we have to multiply by 1.012 and | ||
853 | * divide by 4 | ||
854 | */ | ||
855 | *val = 0; | ||
856 | *val2 = 253000; | ||
857 | return IIO_VAL_INT_PLUS_MICRO; | ||
858 | } | ||
859 | |||
860 | return -EINVAL; | ||
861 | |||
862 | case IIO_CHAN_INFO_OFFSET: | ||
863 | if (chan->type == IIO_TEMP) { | ||
864 | /* The calculated value from the ADC is in Kelvin, we | ||
865 | * want Celsius for hwmon so the offset is | ||
866 | * -272.15 * scale | ||
867 | */ | ||
868 | *val = -1075; | ||
869 | *val2 = 691699; | ||
870 | |||
871 | return IIO_VAL_INT_PLUS_MICRO; | ||
872 | } | ||
873 | |||
874 | return -EINVAL; | ||
875 | |||
876 | default: | ||
877 | break; | ||
878 | } | ||
879 | |||
880 | return -EINVAL; | ||
881 | } | ||
882 | |||
827 | static const struct iio_info mxs_lradc_iio_info = { | 883 | static const struct iio_info mxs_lradc_iio_info = { |
828 | .driver_module = THIS_MODULE, | 884 | .driver_module = THIS_MODULE, |
829 | .read_raw = mxs_lradc_read_raw, | 885 | .read_raw = mxs_lradc_read_raw, |
@@ -1151,8 +1207,17 @@ static const struct iio_chan_spec mxs_lradc_chan_spec[] = { | |||
1151 | MXS_ADC_CHAN(5, IIO_VOLTAGE), | 1207 | MXS_ADC_CHAN(5, IIO_VOLTAGE), |
1152 | MXS_ADC_CHAN(6, IIO_VOLTAGE), | 1208 | MXS_ADC_CHAN(6, IIO_VOLTAGE), |
1153 | MXS_ADC_CHAN(7, IIO_VOLTAGE), /* VBATT */ | 1209 | MXS_ADC_CHAN(7, IIO_VOLTAGE), /* VBATT */ |
1154 | MXS_ADC_CHAN(8, IIO_TEMP), /* Temp sense 0 */ | 1210 | /* Combined Temperature sensors */ |
1155 | MXS_ADC_CHAN(9, IIO_TEMP), /* Temp sense 1 */ | 1211 | { |
1212 | .type = IIO_TEMP, | ||
1213 | .indexed = 1, | ||
1214 | .scan_index = 8, | ||
1215 | .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | | ||
1216 | BIT(IIO_CHAN_INFO_OFFSET) | | ||
1217 | BIT(IIO_CHAN_INFO_SCALE), | ||
1218 | .channel = 8, | ||
1219 | .scan_type = {.sign = 'u', .realbits = 18, .storagebits = 32,}, | ||
1220 | }, | ||
1156 | MXS_ADC_CHAN(10, IIO_VOLTAGE), /* VDDIO */ | 1221 | MXS_ADC_CHAN(10, IIO_VOLTAGE), /* VDDIO */ |
1157 | MXS_ADC_CHAN(11, IIO_VOLTAGE), /* VTH */ | 1222 | MXS_ADC_CHAN(11, IIO_VOLTAGE), /* VTH */ |
1158 | MXS_ADC_CHAN(12, IIO_VOLTAGE), /* VDDA */ | 1223 | MXS_ADC_CHAN(12, IIO_VOLTAGE), /* VDDA */ |