Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'iio-for-3.15b' of git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio into staging-next

Jonathan writes:

Second round of IIO new driver, functionality and cleanups for the 3.15 series.

There are a few fixes in here that might, earlier in a cycle, have gone
to Greg as fixes. Given they are either minor or have never actually
been observed as causing trouble (the locking bug in the event code) and
are invasive, I have included them in this pull request, targeting the
3.15 merge window instead.

The rest are pretty uncontroversial new drivers, a handy little tool for
the example code in our documentation and little cleanups.

New drivers
* Freescale Vybrid and i.MX6SLX ADC driver.
* HID Sensor hub proximity sensors.
* HID Sensor hub pressure sensors.
* LPS25H Pressure sensors added to the ST micro pressure sensor driver.

New functionality
* lsiio tool. This is added to the staging tree as we haven't yet moved
the example code it sits with out. Moving this code out is now a reasonably
high priority but holding up this tool in the meantime did not seem
worthwhile.
* mag3110 - add missing scale factor for temperature output to userspace.

Cleanups
* Fix a bug in the event reporting in which a spin lock might be held over
when a sleep occured. A similar bug was found by Lars in the buffer code.
It has not to our knowledge been observed as actually occuring and is
a little too invasive to push out as a fix.
* Drop the IIO_ST macro after clearing out all users. This macro was a very
bad idea leading to a number of bugs after it stopped covering all elements
of the structure being assigned and people started making assumptions about
what it did cover. Glad to see it go!
* Avoid applying extended name to shared attributes as it makes no sense.
No in tree drivers were using the combination, hence not pushed out as
a fix.
* ad799x - move to devm_request_threaded_irq to reduce boilerplate clean up.
* bma180 - make the low_pass_filter_3db_frequency info element shared rather
than per attribute. The old approach was valid but not as clean as it might
be and was setting a bad example. Hence the cleanup.
* mxs-lradc - propogate the error code form a platform_get_irq call rather than
eating it up by returning -EINVAL on all errors.
* ad799x - typo fix in the copyright message. Either that or Michael was
asserting a copyright that moved backwards in time by about a thousand years.
* ad799x - use a regulator for vref rather than platform data. The driver
dates from just as the regulator framework was coming into common use so
provides an alternative way of specifying the reference voltage. We no
longer need that approach so drop it in favour of a regulator only approach.
* max1363 - some internal vref values were out by a small amount. The effect
would have been tiny and no one noticed hence not pushing this through as
a fix.
* core - replace some pointless goto error_ret (with no clean up) lines with
direct returns. This is my bad coding style so I'm glad to see it cleaned
up.
* core - avoid a kasprintf that just directly prints a string with no
formatting elements. This has always been there but Lars just noticed it.
Oops.

+1935 -166
+22
Documentation/devicetree/bindings/iio/adc/vf610-adc.txt
··· 1 + Freescale vf610 Analog to Digital Converter bindings 2 + 3 + The devicetree bindings are for the new ADC driver written for 4 + vf610/i.MX6slx and upward SoCs from Freescale. 5 + 6 + Required properties: 7 + - compatible: Should contain "fsl,vf610-adc" 8 + - reg: Offset and length of the register set for the device 9 + - interrupts: Should contain the interrupt for the device 10 + - clocks: The clock is needed by the ADC controller, ADC clock source is ipg clock. 11 + - clock-names: Must contain "adc", matching entry in the clocks property. 12 + - vref-supply: The regulator supply ADC refrence voltage. 13 + 14 + Example: 15 + adc0: adc@4003b000 { 16 + compatible = "fsl,vf610-adc"; 17 + reg = <0x4003b000 0x1000>; 18 + interrupts = <0 53 0x04>; 19 + clocks = <&clks VF610_CLK_ADC0>; 20 + clock-names = "adc"; 21 + vref-supply = <&reg_vcc_3v3_mcu>; 22 + };
+2 -2
drivers/iio/accel/bma180.c
··· 451 451 .type = IIO_ACCEL, \ 452 452 .modified = 1, \ 453 453 .channel2 = IIO_MOD_##_axis, \ 454 - .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \ 454 + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \ 455 + .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) | \ 455 456 BIT(IIO_CHAN_INFO_LOW_PASS_FILTER_3DB_FREQUENCY), \ 456 - .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \ 457 457 .scan_index = AXIS_##_axis, \ 458 458 .scan_type = { \ 459 459 .sign = 's', \
+10
drivers/iio/adc/Kconfig
··· 197 197 This driver can also be built as a module. If so, the module will be 198 198 called twl6030-gpadc. 199 199 200 + config VF610_ADC 201 + tristate "Freescale vf610 ADC driver" 202 + depends on OF 203 + help 204 + Say yes here to support for Vybrid board analog-to-digital converter. 205 + Since the IP is used for i.MX6SLX, the driver also support i.MX6SLX. 206 + 207 + This driver can also be built as a module. If so, the module will be 208 + called vf610_adc. 209 + 200 210 config VIPERBOARD_ADC 201 211 tristate "Viperboard ADC support" 202 212 depends on MFD_VIPERBOARD && USB
+1
drivers/iio/adc/Makefile
··· 21 21 obj-$(CONFIG_TI_ADC081C) += ti-adc081c.o 22 22 obj-$(CONFIG_TI_AM335X_ADC) += ti_am335x_adc.o 23 23 obj-$(CONFIG_TWL6030_GPADC) += twl6030-gpadc.o 24 + obj-$(CONFIG_VF610_ADC) += vf610_adc.o 24 25 obj-$(CONFIG_VIPERBOARD_ADC) += viperboard_adc.o
+3 -3
drivers/iio/adc/max1363.c
··· 1247 1247 }, 1248 1248 [max11604] = { 1249 1249 .bits = 8, 1250 - .int_vref_mv = 4098, 1250 + .int_vref_mv = 4096, 1251 1251 .mode_list = max1238_mode_list, 1252 1252 .num_modes = ARRAY_SIZE(max1238_mode_list), 1253 1253 .default_mode = s0to11, ··· 1307 1307 }, 1308 1308 [max11610] = { 1309 1309 .bits = 10, 1310 - .int_vref_mv = 4098, 1310 + .int_vref_mv = 4096, 1311 1311 .mode_list = max1238_mode_list, 1312 1312 .num_modes = ARRAY_SIZE(max1238_mode_list), 1313 1313 .default_mode = s0to11, ··· 1367 1367 }, 1368 1368 [max11616] = { 1369 1369 .bits = 12, 1370 - .int_vref_mv = 4098, 1370 + .int_vref_mv = 4096, 1371 1371 .mode_list = max1238_mode_list, 1372 1372 .num_modes = ARRAY_SIZE(max1238_mode_list), 1373 1373 .default_mode = s0to11,
+711
drivers/iio/adc/vf610_adc.c
··· 1 + /* 2 + * Freescale Vybrid vf610 ADC driver 3 + * 4 + * Copyright 2013 Freescale Semiconductor, Inc. 5 + * 6 + * This program is free software; you can redistribute it and/or modify 7 + * it under the terms of the GNU General Public License as published by 8 + * the Free Software Foundation; either version 2 of the License, or 9 + * (at your option) any later version. 10 + * 11 + * This program is distributed in the hope that it will be useful, 12 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 + * GNU General Public License for more details. 15 + * 16 + * You should have received a copy of the GNU General Public License 17 + * along with this program; if not, write to the Free Software 18 + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 19 + */ 20 + 21 + #include <linux/module.h> 22 + #include <linux/platform_device.h> 23 + #include <linux/interrupt.h> 24 + #include <linux/delay.h> 25 + #include <linux/kernel.h> 26 + #include <linux/slab.h> 27 + #include <linux/io.h> 28 + #include <linux/clk.h> 29 + #include <linux/completion.h> 30 + #include <linux/of.h> 31 + #include <linux/of_irq.h> 32 + #include <linux/regulator/consumer.h> 33 + #include <linux/of_platform.h> 34 + #include <linux/err.h> 35 + 36 + #include <linux/iio/iio.h> 37 + #include <linux/iio/sysfs.h> 38 + #include <linux/iio/driver.h> 39 + 40 + /* This will be the driver name the kernel reports */ 41 + #define DRIVER_NAME "vf610-adc" 42 + 43 + /* Vybrid/IMX ADC registers */ 44 + #define VF610_REG_ADC_HC0 0x00 45 + #define VF610_REG_ADC_HC1 0x04 46 + #define VF610_REG_ADC_HS 0x08 47 + #define VF610_REG_ADC_R0 0x0c 48 + #define VF610_REG_ADC_R1 0x10 49 + #define VF610_REG_ADC_CFG 0x14 50 + #define VF610_REG_ADC_GC 0x18 51 + #define VF610_REG_ADC_GS 0x1c 52 + #define VF610_REG_ADC_CV 0x20 53 + #define VF610_REG_ADC_OFS 0x24 54 + #define VF610_REG_ADC_CAL 0x28 55 + #define VF610_REG_ADC_PCTL 0x30 56 + 57 + /* Configuration register field define */ 58 + #define VF610_ADC_MODE_BIT8 0x00 59 + #define VF610_ADC_MODE_BIT10 0x04 60 + #define VF610_ADC_MODE_BIT12 0x08 61 + #define VF610_ADC_MODE_MASK 0x0c 62 + #define VF610_ADC_BUSCLK2_SEL 0x01 63 + #define VF610_ADC_ALTCLK_SEL 0x02 64 + #define VF610_ADC_ADACK_SEL 0x03 65 + #define VF610_ADC_ADCCLK_MASK 0x03 66 + #define VF610_ADC_CLK_DIV2 0x20 67 + #define VF610_ADC_CLK_DIV4 0x40 68 + #define VF610_ADC_CLK_DIV8 0x60 69 + #define VF610_ADC_CLK_MASK 0x60 70 + #define VF610_ADC_ADLSMP_LONG 0x10 71 + #define VF610_ADC_ADSTS_MASK 0x300 72 + #define VF610_ADC_ADLPC_EN 0x80 73 + #define VF610_ADC_ADHSC_EN 0x400 74 + #define VF610_ADC_REFSEL_VALT 0x100 75 + #define VF610_ADC_REFSEL_VBG 0x1000 76 + #define VF610_ADC_ADTRG_HARD 0x2000 77 + #define VF610_ADC_AVGS_8 0x4000 78 + #define VF610_ADC_AVGS_16 0x8000 79 + #define VF610_ADC_AVGS_32 0xC000 80 + #define VF610_ADC_AVGS_MASK 0xC000 81 + #define VF610_ADC_OVWREN 0x10000 82 + 83 + /* General control register field define */ 84 + #define VF610_ADC_ADACKEN 0x1 85 + #define VF610_ADC_DMAEN 0x2 86 + #define VF610_ADC_ACREN 0x4 87 + #define VF610_ADC_ACFGT 0x8 88 + #define VF610_ADC_ACFE 0x10 89 + #define VF610_ADC_AVGEN 0x20 90 + #define VF610_ADC_ADCON 0x40 91 + #define VF610_ADC_CAL 0x80 92 + 93 + /* Other field define */ 94 + #define VF610_ADC_ADCHC(x) ((x) & 0xF) 95 + #define VF610_ADC_AIEN (0x1 << 7) 96 + #define VF610_ADC_CONV_DISABLE 0x1F 97 + #define VF610_ADC_HS_COCO0 0x1 98 + #define VF610_ADC_CALF 0x2 99 + #define VF610_ADC_TIMEOUT msecs_to_jiffies(100) 100 + 101 + enum clk_sel { 102 + VF610_ADCIOC_BUSCLK_SET, 103 + VF610_ADCIOC_ALTCLK_SET, 104 + VF610_ADCIOC_ADACK_SET, 105 + }; 106 + 107 + enum vol_ref { 108 + VF610_ADCIOC_VR_VREF_SET, 109 + VF610_ADCIOC_VR_VALT_SET, 110 + VF610_ADCIOC_VR_VBG_SET, 111 + }; 112 + 113 + enum average_sel { 114 + VF610_ADC_SAMPLE_1, 115 + VF610_ADC_SAMPLE_4, 116 + VF610_ADC_SAMPLE_8, 117 + VF610_ADC_SAMPLE_16, 118 + VF610_ADC_SAMPLE_32, 119 + }; 120 + 121 + struct vf610_adc_feature { 122 + enum clk_sel clk_sel; 123 + enum vol_ref vol_ref; 124 + 125 + int clk_div; 126 + int sample_rate; 127 + int res_mode; 128 + 129 + bool lpm; 130 + bool calibration; 131 + bool ovwren; 132 + }; 133 + 134 + struct vf610_adc { 135 + struct device *dev; 136 + void __iomem *regs; 137 + struct clk *clk; 138 + 139 + u32 vref_uv; 140 + u32 value; 141 + struct regulator *vref; 142 + struct vf610_adc_feature adc_feature; 143 + 144 + struct completion completion; 145 + }; 146 + 147 + #define VF610_ADC_CHAN(_idx, _chan_type) { \ 148 + .type = (_chan_type), \ 149 + .indexed = 1, \ 150 + .channel = (_idx), \ 151 + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \ 152 + .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) | \ 153 + BIT(IIO_CHAN_INFO_SAMP_FREQ), \ 154 + } 155 + 156 + static const struct iio_chan_spec vf610_adc_iio_channels[] = { 157 + VF610_ADC_CHAN(0, IIO_VOLTAGE), 158 + VF610_ADC_CHAN(1, IIO_VOLTAGE), 159 + VF610_ADC_CHAN(2, IIO_VOLTAGE), 160 + VF610_ADC_CHAN(3, IIO_VOLTAGE), 161 + VF610_ADC_CHAN(4, IIO_VOLTAGE), 162 + VF610_ADC_CHAN(5, IIO_VOLTAGE), 163 + VF610_ADC_CHAN(6, IIO_VOLTAGE), 164 + VF610_ADC_CHAN(7, IIO_VOLTAGE), 165 + VF610_ADC_CHAN(8, IIO_VOLTAGE), 166 + VF610_ADC_CHAN(9, IIO_VOLTAGE), 167 + VF610_ADC_CHAN(10, IIO_VOLTAGE), 168 + VF610_ADC_CHAN(11, IIO_VOLTAGE), 169 + VF610_ADC_CHAN(12, IIO_VOLTAGE), 170 + VF610_ADC_CHAN(13, IIO_VOLTAGE), 171 + VF610_ADC_CHAN(14, IIO_VOLTAGE), 172 + VF610_ADC_CHAN(15, IIO_VOLTAGE), 173 + /* sentinel */ 174 + }; 175 + 176 + /* 177 + * ADC sample frequency, unit is ADCK cycles. 178 + * ADC clk source is ipg clock, which is the same as bus clock. 179 + * 180 + * ADC conversion time = SFCAdder + AverageNum x (BCT + LSTAdder) 181 + * SFCAdder: fixed to 6 ADCK cycles 182 + * AverageNum: 1, 4, 8, 16, 32 samples for hardware average. 183 + * BCT (Base Conversion Time): fixed to 25 ADCK cycles for 12 bit mode 184 + * LSTAdder(Long Sample Time): fixed to 3 ADCK cycles 185 + * 186 + * By default, enable 12 bit resolution mode, clock source 187 + * set to ipg clock, So get below frequency group: 188 + */ 189 + static const u32 vf610_sample_freq_avail[5] = 190 + {1941176, 559332, 286957, 145374, 73171}; 191 + 192 + static inline void vf610_adc_cfg_init(struct vf610_adc *info) 193 + { 194 + /* set default Configuration for ADC controller */ 195 + info->adc_feature.clk_sel = VF610_ADCIOC_BUSCLK_SET; 196 + info->adc_feature.vol_ref = VF610_ADCIOC_VR_VREF_SET; 197 + 198 + info->adc_feature.calibration = true; 199 + info->adc_feature.ovwren = true; 200 + 201 + info->adc_feature.clk_div = 1; 202 + info->adc_feature.res_mode = 12; 203 + info->adc_feature.sample_rate = 1; 204 + info->adc_feature.lpm = true; 205 + } 206 + 207 + static void vf610_adc_cfg_post_set(struct vf610_adc *info) 208 + { 209 + struct vf610_adc_feature *adc_feature = &info->adc_feature; 210 + int cfg_data = 0; 211 + int gc_data = 0; 212 + 213 + switch (adc_feature->clk_sel) { 214 + case VF610_ADCIOC_ALTCLK_SET: 215 + cfg_data |= VF610_ADC_ALTCLK_SEL; 216 + break; 217 + case VF610_ADCIOC_ADACK_SET: 218 + cfg_data |= VF610_ADC_ADACK_SEL; 219 + break; 220 + default: 221 + break; 222 + } 223 + 224 + /* low power set for calibration */ 225 + cfg_data |= VF610_ADC_ADLPC_EN; 226 + 227 + /* enable high speed for calibration */ 228 + cfg_data |= VF610_ADC_ADHSC_EN; 229 + 230 + /* voltage reference */ 231 + switch (adc_feature->vol_ref) { 232 + case VF610_ADCIOC_VR_VREF_SET: 233 + break; 234 + case VF610_ADCIOC_VR_VALT_SET: 235 + cfg_data |= VF610_ADC_REFSEL_VALT; 236 + break; 237 + case VF610_ADCIOC_VR_VBG_SET: 238 + cfg_data |= VF610_ADC_REFSEL_VBG; 239 + break; 240 + default: 241 + dev_err(info->dev, "error voltage reference\n"); 242 + } 243 + 244 + /* data overwrite enable */ 245 + if (adc_feature->ovwren) 246 + cfg_data |= VF610_ADC_OVWREN; 247 + 248 + writel(cfg_data, info->regs + VF610_REG_ADC_CFG); 249 + writel(gc_data, info->regs + VF610_REG_ADC_GC); 250 + } 251 + 252 + static void vf610_adc_calibration(struct vf610_adc *info) 253 + { 254 + int adc_gc, hc_cfg; 255 + int timeout; 256 + 257 + if (!info->adc_feature.calibration) 258 + return; 259 + 260 + /* enable calibration interrupt */ 261 + hc_cfg = VF610_ADC_AIEN | VF610_ADC_CONV_DISABLE; 262 + writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); 263 + 264 + adc_gc = readl(info->regs + VF610_REG_ADC_GC); 265 + writel(adc_gc | VF610_ADC_CAL, info->regs + VF610_REG_ADC_GC); 266 + 267 + timeout = wait_for_completion_timeout 268 + (&info->completion, VF610_ADC_TIMEOUT); 269 + if (timeout == 0) 270 + dev_err(info->dev, "Timeout for adc calibration\n"); 271 + 272 + adc_gc = readl(info->regs + VF610_REG_ADC_GS); 273 + if (adc_gc & VF610_ADC_CALF) 274 + dev_err(info->dev, "ADC calibration failed\n"); 275 + 276 + info->adc_feature.calibration = false; 277 + } 278 + 279 + static void vf610_adc_cfg_set(struct vf610_adc *info) 280 + { 281 + struct vf610_adc_feature *adc_feature = &(info->adc_feature); 282 + int cfg_data; 283 + 284 + cfg_data = readl(info->regs + VF610_REG_ADC_CFG); 285 + 286 + /* low power configuration */ 287 + cfg_data &= ~VF610_ADC_ADLPC_EN; 288 + if (adc_feature->lpm) 289 + cfg_data |= VF610_ADC_ADLPC_EN; 290 + 291 + /* disable high speed */ 292 + cfg_data &= ~VF610_ADC_ADHSC_EN; 293 + 294 + writel(cfg_data, info->regs + VF610_REG_ADC_CFG); 295 + } 296 + 297 + static void vf610_adc_sample_set(struct vf610_adc *info) 298 + { 299 + struct vf610_adc_feature *adc_feature = &(info->adc_feature); 300 + int cfg_data, gc_data; 301 + 302 + cfg_data = readl(info->regs + VF610_REG_ADC_CFG); 303 + gc_data = readl(info->regs + VF610_REG_ADC_GC); 304 + 305 + /* resolution mode */ 306 + cfg_data &= ~VF610_ADC_MODE_MASK; 307 + switch (adc_feature->res_mode) { 308 + case 8: 309 + cfg_data |= VF610_ADC_MODE_BIT8; 310 + break; 311 + case 10: 312 + cfg_data |= VF610_ADC_MODE_BIT10; 313 + break; 314 + case 12: 315 + cfg_data |= VF610_ADC_MODE_BIT12; 316 + break; 317 + default: 318 + dev_err(info->dev, "error resolution mode\n"); 319 + break; 320 + } 321 + 322 + /* clock select and clock divider */ 323 + cfg_data &= ~(VF610_ADC_CLK_MASK | VF610_ADC_ADCCLK_MASK); 324 + switch (adc_feature->clk_div) { 325 + case 1: 326 + break; 327 + case 2: 328 + cfg_data |= VF610_ADC_CLK_DIV2; 329 + break; 330 + case 4: 331 + cfg_data |= VF610_ADC_CLK_DIV4; 332 + break; 333 + case 8: 334 + cfg_data |= VF610_ADC_CLK_DIV8; 335 + break; 336 + case 16: 337 + switch (adc_feature->clk_sel) { 338 + case VF610_ADCIOC_BUSCLK_SET: 339 + cfg_data |= VF610_ADC_BUSCLK2_SEL | VF610_ADC_CLK_DIV8; 340 + break; 341 + default: 342 + dev_err(info->dev, "error clk divider\n"); 343 + break; 344 + } 345 + break; 346 + } 347 + 348 + /* Use the short sample mode */ 349 + cfg_data &= ~(VF610_ADC_ADLSMP_LONG | VF610_ADC_ADSTS_MASK); 350 + 351 + /* update hardware average selection */ 352 + cfg_data &= ~VF610_ADC_AVGS_MASK; 353 + gc_data &= ~VF610_ADC_AVGEN; 354 + switch (adc_feature->sample_rate) { 355 + case VF610_ADC_SAMPLE_1: 356 + break; 357 + case VF610_ADC_SAMPLE_4: 358 + gc_data |= VF610_ADC_AVGEN; 359 + break; 360 + case VF610_ADC_SAMPLE_8: 361 + gc_data |= VF610_ADC_AVGEN; 362 + cfg_data |= VF610_ADC_AVGS_8; 363 + break; 364 + case VF610_ADC_SAMPLE_16: 365 + gc_data |= VF610_ADC_AVGEN; 366 + cfg_data |= VF610_ADC_AVGS_16; 367 + break; 368 + case VF610_ADC_SAMPLE_32: 369 + gc_data |= VF610_ADC_AVGEN; 370 + cfg_data |= VF610_ADC_AVGS_32; 371 + break; 372 + default: 373 + dev_err(info->dev, 374 + "error hardware sample average select\n"); 375 + } 376 + 377 + writel(cfg_data, info->regs + VF610_REG_ADC_CFG); 378 + writel(gc_data, info->regs + VF610_REG_ADC_GC); 379 + } 380 + 381 + static void vf610_adc_hw_init(struct vf610_adc *info) 382 + { 383 + /* CFG: Feature set */ 384 + vf610_adc_cfg_post_set(info); 385 + vf610_adc_sample_set(info); 386 + 387 + /* adc calibration */ 388 + vf610_adc_calibration(info); 389 + 390 + /* CFG: power and speed set */ 391 + vf610_adc_cfg_set(info); 392 + } 393 + 394 + static int vf610_adc_read_data(struct vf610_adc *info) 395 + { 396 + int result; 397 + 398 + result = readl(info->regs + VF610_REG_ADC_R0); 399 + 400 + switch (info->adc_feature.res_mode) { 401 + case 8: 402 + result &= 0xFF; 403 + break; 404 + case 10: 405 + result &= 0x3FF; 406 + break; 407 + case 12: 408 + result &= 0xFFF; 409 + break; 410 + default: 411 + break; 412 + } 413 + 414 + return result; 415 + } 416 + 417 + static irqreturn_t vf610_adc_isr(int irq, void *dev_id) 418 + { 419 + struct vf610_adc *info = (struct vf610_adc *)dev_id; 420 + int coco; 421 + 422 + coco = readl(info->regs + VF610_REG_ADC_HS); 423 + if (coco & VF610_ADC_HS_COCO0) { 424 + info->value = vf610_adc_read_data(info); 425 + complete(&info->completion); 426 + } 427 + 428 + return IRQ_HANDLED; 429 + } 430 + 431 + static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("1941176, 559332, 286957, 145374, 73171"); 432 + 433 + static struct attribute *vf610_attributes[] = { 434 + &iio_const_attr_sampling_frequency_available.dev_attr.attr, 435 + NULL 436 + }; 437 + 438 + static const struct attribute_group vf610_attribute_group = { 439 + .attrs = vf610_attributes, 440 + }; 441 + 442 + static int vf610_read_raw(struct iio_dev *indio_dev, 443 + struct iio_chan_spec const *chan, 444 + int *val, 445 + int *val2, 446 + long mask) 447 + { 448 + struct vf610_adc *info = iio_priv(indio_dev); 449 + unsigned int hc_cfg; 450 + unsigned long ret; 451 + 452 + switch (mask) { 453 + case IIO_CHAN_INFO_RAW: 454 + mutex_lock(&indio_dev->mlock); 455 + reinit_completion(&info->completion); 456 + 457 + hc_cfg = VF610_ADC_ADCHC(chan->channel); 458 + hc_cfg |= VF610_ADC_AIEN; 459 + writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); 460 + ret = wait_for_completion_interruptible_timeout 461 + (&info->completion, VF610_ADC_TIMEOUT); 462 + if (ret == 0) { 463 + mutex_unlock(&indio_dev->mlock); 464 + return -ETIMEDOUT; 465 + } 466 + if (ret < 0) { 467 + mutex_unlock(&indio_dev->mlock); 468 + return ret; 469 + } 470 + 471 + *val = info->value; 472 + mutex_unlock(&indio_dev->mlock); 473 + return IIO_VAL_INT; 474 + 475 + case IIO_CHAN_INFO_SCALE: 476 + *val = info->vref_uv / 1000; 477 + *val2 = info->adc_feature.res_mode; 478 + return IIO_VAL_FRACTIONAL_LOG2; 479 + 480 + case IIO_CHAN_INFO_SAMP_FREQ: 481 + *val = vf610_sample_freq_avail[info->adc_feature.sample_rate]; 482 + *val2 = 0; 483 + return IIO_VAL_INT; 484 + 485 + default: 486 + break; 487 + } 488 + 489 + return -EINVAL; 490 + } 491 + 492 + static int vf610_write_raw(struct iio_dev *indio_dev, 493 + struct iio_chan_spec const *chan, 494 + int val, 495 + int val2, 496 + long mask) 497 + { 498 + struct vf610_adc *info = iio_priv(indio_dev); 499 + int i; 500 + 501 + switch (mask) { 502 + case IIO_CHAN_INFO_SAMP_FREQ: 503 + for (i = 0; 504 + i < ARRAY_SIZE(vf610_sample_freq_avail); 505 + i++) 506 + if (val == vf610_sample_freq_avail[i]) { 507 + info->adc_feature.sample_rate = i; 508 + vf610_adc_sample_set(info); 509 + return 0; 510 + } 511 + break; 512 + 513 + default: 514 + break; 515 + } 516 + 517 + return -EINVAL; 518 + } 519 + 520 + static int vf610_adc_reg_access(struct iio_dev *indio_dev, 521 + unsigned reg, unsigned writeval, 522 + unsigned *readval) 523 + { 524 + struct vf610_adc *info = iio_priv(indio_dev); 525 + 526 + if ((readval == NULL) || 527 + (!(reg % 4) || (reg > VF610_REG_ADC_PCTL))) 528 + return -EINVAL; 529 + 530 + *readval = readl(info->regs + reg); 531 + 532 + return 0; 533 + } 534 + 535 + static const struct iio_info vf610_adc_iio_info = { 536 + .driver_module = THIS_MODULE, 537 + .read_raw = &vf610_read_raw, 538 + .write_raw = &vf610_write_raw, 539 + .debugfs_reg_access = &vf610_adc_reg_access, 540 + .attrs = &vf610_attribute_group, 541 + }; 542 + 543 + static const struct of_device_id vf610_adc_match[] = { 544 + { .compatible = "fsl,vf610-adc", }, 545 + { /* sentinel */ } 546 + }; 547 + MODULE_DEVICE_TABLE(of, vf610_adc_match); 548 + 549 + static int vf610_adc_probe(struct platform_device *pdev) 550 + { 551 + struct vf610_adc *info; 552 + struct iio_dev *indio_dev; 553 + struct resource *mem; 554 + int irq; 555 + int ret; 556 + 557 + indio_dev = devm_iio_device_alloc(&pdev->dev, sizeof(struct vf610_adc)); 558 + if (!indio_dev) { 559 + dev_err(&pdev->dev, "Failed allocating iio device\n"); 560 + return -ENOMEM; 561 + } 562 + 563 + info = iio_priv(indio_dev); 564 + info->dev = &pdev->dev; 565 + 566 + mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); 567 + info->regs = devm_ioremap_resource(&pdev->dev, mem); 568 + if (IS_ERR(info->regs)) 569 + return PTR_ERR(info->regs); 570 + 571 + irq = platform_get_irq(pdev, 0); 572 + if (irq <= 0) { 573 + dev_err(&pdev->dev, "no irq resource?\n"); 574 + return -EINVAL; 575 + } 576 + 577 + ret = devm_request_irq(info->dev, irq, 578 + vf610_adc_isr, 0, 579 + dev_name(&pdev->dev), info); 580 + if (ret < 0) { 581 + dev_err(&pdev->dev, "failed requesting irq, irq = %d\n", irq); 582 + return ret; 583 + } 584 + 585 + info->clk = devm_clk_get(&pdev->dev, "adc"); 586 + if (IS_ERR(info->clk)) { 587 + dev_err(&pdev->dev, "failed getting clock, err = %ld\n", 588 + PTR_ERR(info->clk)); 589 + ret = PTR_ERR(info->clk); 590 + return ret; 591 + } 592 + 593 + info->vref = devm_regulator_get(&pdev->dev, "vref"); 594 + if (IS_ERR(info->vref)) 595 + return PTR_ERR(info->vref); 596 + 597 + ret = regulator_enable(info->vref); 598 + if (ret) 599 + return ret; 600 + 601 + info->vref_uv = regulator_get_voltage(info->vref); 602 + 603 + platform_set_drvdata(pdev, indio_dev); 604 + 605 + init_completion(&info->completion); 606 + 607 + indio_dev->name = dev_name(&pdev->dev); 608 + indio_dev->dev.parent = &pdev->dev; 609 + indio_dev->dev.of_node = pdev->dev.of_node; 610 + indio_dev->info = &vf610_adc_iio_info; 611 + indio_dev->modes = INDIO_DIRECT_MODE; 612 + indio_dev->channels = vf610_adc_iio_channels; 613 + indio_dev->num_channels = ARRAY_SIZE(vf610_adc_iio_channels); 614 + 615 + ret = clk_prepare_enable(info->clk); 616 + if (ret) { 617 + dev_err(&pdev->dev, 618 + "Could not prepare or enable the clock.\n"); 619 + goto error_adc_clk_enable; 620 + } 621 + 622 + vf610_adc_cfg_init(info); 623 + vf610_adc_hw_init(info); 624 + 625 + ret = iio_device_register(indio_dev); 626 + if (ret) { 627 + dev_err(&pdev->dev, "Couldn't register the device.\n"); 628 + goto error_iio_device_register; 629 + } 630 + 631 + return 0; 632 + 633 + 634 + error_iio_device_register: 635 + clk_disable_unprepare(info->clk); 636 + error_adc_clk_enable: 637 + regulator_disable(info->vref); 638 + 639 + return ret; 640 + } 641 + 642 + static int vf610_adc_remove(struct platform_device *pdev) 643 + { 644 + struct iio_dev *indio_dev = platform_get_drvdata(pdev); 645 + struct vf610_adc *info = iio_priv(indio_dev); 646 + 647 + iio_device_unregister(indio_dev); 648 + regulator_disable(info->vref); 649 + clk_disable_unprepare(info->clk); 650 + 651 + return 0; 652 + } 653 + 654 + #ifdef CONFIG_PM_SLEEP 655 + static int vf610_adc_suspend(struct device *dev) 656 + { 657 + struct iio_dev *indio_dev = dev_get_drvdata(dev); 658 + struct vf610_adc *info = iio_priv(indio_dev); 659 + int hc_cfg; 660 + 661 + /* ADC controller enters to stop mode */ 662 + hc_cfg = readl(info->regs + VF610_REG_ADC_HC0); 663 + hc_cfg |= VF610_ADC_CONV_DISABLE; 664 + writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); 665 + 666 + clk_disable_unprepare(info->clk); 667 + regulator_disable(info->vref); 668 + 669 + return 0; 670 + } 671 + 672 + static int vf610_adc_resume(struct device *dev) 673 + { 674 + struct iio_dev *indio_dev = dev_get_drvdata(dev); 675 + struct vf610_adc *info = iio_priv(indio_dev); 676 + int ret; 677 + 678 + ret = regulator_enable(info->vref); 679 + if (ret) 680 + return ret; 681 + 682 + ret = clk_prepare_enable(info->clk); 683 + if (ret) 684 + return ret; 685 + 686 + vf610_adc_hw_init(info); 687 + 688 + return 0; 689 + } 690 + #endif 691 + 692 + static SIMPLE_DEV_PM_OPS(vf610_adc_pm_ops, 693 + vf610_adc_suspend, 694 + vf610_adc_resume); 695 + 696 + static struct platform_driver vf610_adc_driver = { 697 + .probe = vf610_adc_probe, 698 + .remove = vf610_adc_remove, 699 + .driver = { 700 + .name = DRIVER_NAME, 701 + .owner = THIS_MODULE, 702 + .of_match_table = vf610_adc_match, 703 + .pm = &vf610_adc_pm_ops, 704 + }, 705 + }; 706 + 707 + module_platform_driver(vf610_adc_driver); 708 + 709 + MODULE_AUTHOR("Fugang Duan <B38611@freescale.com>"); 710 + MODULE_DESCRIPTION("Freescale VF610 ADC driver"); 711 + MODULE_LICENSE("GPL v2");
+2 -5
drivers/iio/buffer_cb.c
··· 46 46 struct iio_channel *chan; 47 47 48 48 cb_buff = kzalloc(sizeof(*cb_buff), GFP_KERNEL); 49 - if (cb_buff == NULL) { 50 - ret = -ENOMEM; 51 - goto error_ret; 52 - } 49 + if (cb_buff == NULL) 50 + return ERR_PTR(-ENOMEM); 53 51 54 52 iio_buffer_init(&cb_buff->buffer); 55 53 ··· 89 91 iio_channel_release_all(cb_buff->channels); 90 92 error_free_cb_buff: 91 93 kfree(cb_buff); 92 - error_ret: 93 94 return ERR_PTR(ret); 94 95 } 95 96 EXPORT_SYMBOL_GPL(iio_channel_get_all_cb);
+6 -10
drivers/iio/industrialio-buffer.c
··· 264 264 &indio_dev->dev, 265 265 &buffer->scan_el_dev_attr_list); 266 266 if (ret) 267 - goto error_ret; 267 + return ret; 268 268 attrcount++; 269 269 ret = __iio_add_chan_devattr("type", 270 270 chan, ··· 275 275 &indio_dev->dev, 276 276 &buffer->scan_el_dev_attr_list); 277 277 if (ret) 278 - goto error_ret; 278 + return ret; 279 279 attrcount++; 280 280 if (chan->type != IIO_TIMESTAMP) 281 281 ret = __iio_add_chan_devattr("en", ··· 296 296 &indio_dev->dev, 297 297 &buffer->scan_el_dev_attr_list); 298 298 if (ret) 299 - goto error_ret; 299 + return ret; 300 300 attrcount++; 301 301 ret = attrcount; 302 - error_ret: 303 302 return ret; 304 303 } 305 304 ··· 552 553 if (indio_dev->setup_ops->predisable) { 553 554 ret = indio_dev->setup_ops->predisable(indio_dev); 554 555 if (ret) 555 - goto error_ret; 556 + return ret; 556 557 } 557 558 indio_dev->currentmode = INDIO_DIRECT_MODE; 558 559 if (indio_dev->setup_ops->postdisable) { 559 560 ret = indio_dev->setup_ops->postdisable(indio_dev); 560 561 if (ret) 561 - goto error_ret; 562 + return ret; 562 563 } 563 564 } 564 565 /* Keep a copy of current setup to allow roll back */ ··· 612 613 else { 613 614 kfree(compound_mask); 614 615 ret = -EINVAL; 615 - goto error_ret; 616 + return ret; 616 617 } 617 618 } 618 619 } else { ··· 695 696 if (indio_dev->setup_ops->postdisable) 696 697 indio_dev->setup_ops->postdisable(indio_dev); 697 698 error_remove_inserted: 698 - 699 699 if (insert_buffer) 700 700 iio_buffer_deactivate(insert_buffer); 701 701 indio_dev->active_scan_mask = old_mask; 702 702 kfree(compound_mask); 703 - error_ret: 704 - 705 703 return ret; 706 704 } 707 705
+17 -34
drivers/iio/industrialio-core.c
··· 540 540 enum iio_shared_by shared_by) 541 541 { 542 542 int ret = 0; 543 - char *name_format = NULL; 543 + char *name = NULL; 544 544 char *full_postfix; 545 545 sysfs_attr_init(&dev_attr->attr); 546 546 ··· 558 558 ->channel2], 559 559 postfix); 560 560 } else { 561 - if (chan->extend_name == NULL) 561 + if (chan->extend_name == NULL || shared_by != IIO_SEPARATE) 562 562 full_postfix = kstrdup(postfix, GFP_KERNEL); 563 563 else 564 564 full_postfix = kasprintf(GFP_KERNEL, ··· 572 572 if (chan->differential) { /* Differential can not have modifier */ 573 573 switch (shared_by) { 574 574 case IIO_SHARED_BY_ALL: 575 - name_format = kasprintf(GFP_KERNEL, "%s", full_postfix); 575 + name = kasprintf(GFP_KERNEL, "%s", full_postfix); 576 576 break; 577 577 case IIO_SHARED_BY_DIR: 578 - name_format = kasprintf(GFP_KERNEL, "%s_%s", 578 + name = kasprintf(GFP_KERNEL, "%s_%s", 579 579 iio_direction[chan->output], 580 580 full_postfix); 581 581 break; 582 582 case IIO_SHARED_BY_TYPE: 583 - name_format 584 - = kasprintf(GFP_KERNEL, "%s_%s-%s_%s", 583 + name = kasprintf(GFP_KERNEL, "%s_%s-%s_%s", 585 584 iio_direction[chan->output], 586 585 iio_chan_type_name_spec[chan->type], 587 586 iio_chan_type_name_spec[chan->type], ··· 592 593 ret = -EINVAL; 593 594 goto error_free_full_postfix; 594 595 } 595 - name_format 596 - = kasprintf(GFP_KERNEL, 596 + name = kasprintf(GFP_KERNEL, 597 597 "%s_%s%d-%s%d_%s", 598 598 iio_direction[chan->output], 599 599 iio_chan_type_name_spec[chan->type], ··· 605 607 } else { /* Single ended */ 606 608 switch (shared_by) { 607 609 case IIO_SHARED_BY_ALL: 608 - name_format = kasprintf(GFP_KERNEL, "%s", full_postfix); 610 + name = kasprintf(GFP_KERNEL, "%s", full_postfix); 609 611 break; 610 612 case IIO_SHARED_BY_DIR: 611 - name_format = kasprintf(GFP_KERNEL, "%s_%s", 613 + name = kasprintf(GFP_KERNEL, "%s_%s", 612 614 iio_direction[chan->output], 613 615 full_postfix); 614 616 break; 615 617 case IIO_SHARED_BY_TYPE: 616 - name_format 617 - = kasprintf(GFP_KERNEL, "%s_%s_%s", 618 + name = kasprintf(GFP_KERNEL, "%s_%s_%s", 618 619 iio_direction[chan->output], 619 620 iio_chan_type_name_spec[chan->type], 620 621 full_postfix); ··· 621 624 622 625 case IIO_SEPARATE: 623 626 if (chan->indexed) 624 - name_format 625 - = kasprintf(GFP_KERNEL, "%s_%s%d_%s", 627 + name = kasprintf(GFP_KERNEL, "%s_%s%d_%s", 626 628 iio_direction[chan->output], 627 629 iio_chan_type_name_spec[chan->type], 628 630 chan->channel, 629 631 full_postfix); 630 632 else 631 - name_format 632 - = kasprintf(GFP_KERNEL, "%s_%s_%s", 633 + name = kasprintf(GFP_KERNEL, "%s_%s_%s", 633 634 iio_direction[chan->output], 634 635 iio_chan_type_name_spec[chan->type], 635 636 full_postfix); 636 637 break; 637 638 } 638 639 } 639 - if (name_format == NULL) { 640 + if (name == NULL) { 640 641 ret = -ENOMEM; 641 642 goto error_free_full_postfix; 642 643 } 643 - dev_attr->attr.name = kasprintf(GFP_KERNEL, 644 - name_format, 645 - chan->channel, 646 - chan->channel2); 647 - if (dev_attr->attr.name == NULL) { 648 - ret = -ENOMEM; 649 - goto error_free_name_format; 650 - } 644 + dev_attr->attr.name = name; 651 645 652 646 if (readfunc) { 653 647 dev_attr->attr.mode |= S_IRUGO; ··· 649 661 dev_attr->attr.mode |= S_IWUSR; 650 662 dev_attr->store = writefunc; 651 663 } 652 - error_free_name_format: 653 - kfree(name_format); 664 + 654 665 error_free_full_postfix: 655 666 kfree(full_postfix); 656 667 ··· 679 692 struct iio_dev_attr *iio_attr, *t; 680 693 681 694 iio_attr = kzalloc(sizeof(*iio_attr), GFP_KERNEL); 682 - if (iio_attr == NULL) { 683 - ret = -ENOMEM; 684 - goto error_ret; 685 - } 695 + if (iio_attr == NULL) 696 + return -ENOMEM; 686 697 ret = __iio_device_attr_init(&iio_attr->dev_attr, 687 698 postfix, chan, 688 699 readfunc, writefunc, shared_by); ··· 705 720 __iio_device_attr_deinit(&iio_attr->dev_attr); 706 721 error_iio_dev_attr_free: 707 722 kfree(iio_attr); 708 - error_ret: 709 723 return ret; 710 724 } 711 725 ··· 1118 1134 if (ret) { 1119 1135 dev_err(indio_dev->dev.parent, 1120 1136 "Failed to register debugfs interfaces\n"); 1121 - goto error_ret; 1137 + return ret; 1122 1138 } 1123 1139 ret = iio_device_register_sysfs(indio_dev); 1124 1140 if (ret) { ··· 1159 1175 iio_device_unregister_sysfs(indio_dev); 1160 1176 error_unreg_debugfs: 1161 1177 iio_device_unregister_debugfs(indio_dev); 1162 - error_ret: 1163 1178 return ret; 1164 1179 } 1165 1180 EXPORT_SYMBOL(iio_device_register);
+47 -53
drivers/iio/industrialio-event.c
··· 40 40 struct list_head dev_attr_list; 41 41 unsigned long flags; 42 42 struct attribute_group group; 43 + struct mutex read_lock; 43 44 }; 44 45 45 46 /** ··· 48 47 * @indio_dev: IIO device structure 49 48 * @ev_code: What event 50 49 * @timestamp: When the event occurred 50 + * 51 + * Note: The caller must make sure that this function is not running 52 + * concurrently for the same indio_dev more than once. 51 53 **/ 52 54 int iio_push_event(struct iio_dev *indio_dev, u64 ev_code, s64 timestamp) 53 55 { 54 56 struct iio_event_interface *ev_int = indio_dev->event_interface; 55 57 struct iio_event_data ev; 56 - unsigned long flags; 57 58 int copied; 58 59 59 60 /* Does anyone care? */ 60 - spin_lock_irqsave(&ev_int->wait.lock, flags); 61 61 if (test_bit(IIO_BUSY_BIT_POS, &ev_int->flags)) { 62 62 63 63 ev.id = ev_code; ··· 66 64 67 65 copied = kfifo_put(&ev_int->det_events, ev); 68 66 if (copied != 0) 69 - wake_up_locked_poll(&ev_int->wait, POLLIN); 67 + wake_up_poll(&ev_int->wait, POLLIN); 70 68 } 71 - spin_unlock_irqrestore(&ev_int->wait.lock, flags); 72 69 73 70 return 0; 74 71 } ··· 88 87 89 88 poll_wait(filep, &ev_int->wait, wait); 90 89 91 - spin_lock_irq(&ev_int->wait.lock); 92 90 if (!kfifo_is_empty(&ev_int->det_events)) 93 91 events = POLLIN | POLLRDNORM; 94 - spin_unlock_irq(&ev_int->wait.lock); 95 92 96 93 return events; 97 94 } ··· 110 111 if (count < sizeof(struct iio_event_data)) 111 112 return -EINVAL; 112 113 113 - spin_lock_irq(&ev_int->wait.lock); 114 - if (kfifo_is_empty(&ev_int->det_events)) { 115 - if (filep->f_flags & O_NONBLOCK) { 116 - ret = -EAGAIN; 117 - goto error_unlock; 118 - } 119 - /* Blocking on device; waiting for something to be there */ 120 - ret = wait_event_interruptible_locked_irq(ev_int->wait, 114 + do { 115 + if (kfifo_is_empty(&ev_int->det_events)) { 116 + if (filep->f_flags & O_NONBLOCK) 117 + return -EAGAIN; 118 + 119 + ret = wait_event_interruptible(ev_int->wait, 121 120 !kfifo_is_empty(&ev_int->det_events) || 122 121 indio_dev->info == NULL); 123 - if (ret) 124 - goto error_unlock; 125 - if (indio_dev->info == NULL) { 126 - ret = -ENODEV; 127 - goto error_unlock; 122 + if (ret) 123 + return ret; 124 + if (indio_dev->info == NULL) 125 + return -ENODEV; 128 126 } 129 - /* Single access device so no one else can get the data */ 130 - } 131 127 132 - ret = kfifo_to_user(&ev_int->det_events, buf, count, &copied); 128 + if (mutex_lock_interruptible(&ev_int->read_lock)) 129 + return -ERESTARTSYS; 130 + ret = kfifo_to_user(&ev_int->det_events, buf, count, &copied); 131 + mutex_unlock(&ev_int->read_lock); 133 132 134 - error_unlock: 135 - spin_unlock_irq(&ev_int->wait.lock); 133 + if (ret) 134 + return ret; 136 135 137 - return ret ? ret : copied; 136 + /* 137 + * If we couldn't read anything from the fifo (a different 138 + * thread might have been faster) we either return -EAGAIN if 139 + * the file descriptor is non-blocking, otherwise we go back to 140 + * sleep and wait for more data to arrive. 141 + */ 142 + if (copied == 0 && (filep->f_flags & O_NONBLOCK)) 143 + return -EAGAIN; 144 + 145 + } while (copied == 0); 146 + 147 + return copied; 138 148 } 139 149 140 150 static int iio_event_chrdev_release(struct inode *inode, struct file *filep) ··· 151 143 struct iio_dev *indio_dev = filep->private_data; 152 144 struct iio_event_interface *ev_int = indio_dev->event_interface; 153 145 154 - spin_lock_irq(&ev_int->wait.lock); 155 - __clear_bit(IIO_BUSY_BIT_POS, &ev_int->flags); 156 - /* 157 - * In order to maintain a clean state for reopening, 158 - * clear out any awaiting events. The mask will prevent 159 - * any new __iio_push_event calls running. 160 - */ 161 - kfifo_reset_out(&ev_int->det_events); 162 - spin_unlock_irq(&ev_int->wait.lock); 146 + clear_bit(IIO_BUSY_BIT_POS, &ev_int->flags); 163 147 164 148 iio_device_put(indio_dev); 165 149 ··· 174 174 if (ev_int == NULL) 175 175 return -ENODEV; 176 176 177 - spin_lock_irq(&ev_int->wait.lock); 178 - if (__test_and_set_bit(IIO_BUSY_BIT_POS, &ev_int->flags)) { 179 - spin_unlock_irq(&ev_int->wait.lock); 177 + if (test_and_set_bit(IIO_BUSY_BIT_POS, &ev_int->flags)) 180 178 return -EBUSY; 181 - } 182 - spin_unlock_irq(&ev_int->wait.lock); 179 + 183 180 iio_device_get(indio_dev); 184 181 185 182 fd = anon_inode_getfd("iio:event", &iio_event_chrdev_fileops, 186 183 indio_dev, O_RDONLY | O_CLOEXEC); 187 184 if (fd < 0) { 188 - spin_lock_irq(&ev_int->wait.lock); 189 - __clear_bit(IIO_BUSY_BIT_POS, &ev_int->flags); 190 - spin_unlock_irq(&ev_int->wait.lock); 185 + clear_bit(IIO_BUSY_BIT_POS, &ev_int->flags); 191 186 iio_device_put(indio_dev); 187 + } else { 188 + kfifo_reset_out(&ev_int->det_events); 192 189 } 190 + 193 191 return fd; 194 192 } 195 193 ··· 364 366 ret = iio_device_add_event(indio_dev, chan, i, type, dir, 365 367 IIO_SEPARATE, &chan->event_spec[i].mask_separate); 366 368 if (ret < 0) 367 - goto error_ret; 369 + return ret; 368 370 attrcount += ret; 369 371 370 372 ret = iio_device_add_event(indio_dev, chan, i, type, dir, 371 373 IIO_SHARED_BY_TYPE, 372 374 &chan->event_spec[i].mask_shared_by_type); 373 375 if (ret < 0) 374 - goto error_ret; 376 + return ret; 375 377 attrcount += ret; 376 378 377 379 ret = iio_device_add_event(indio_dev, chan, i, type, dir, 378 380 IIO_SHARED_BY_DIR, 379 381 &chan->event_spec[i].mask_shared_by_dir); 380 382 if (ret < 0) 381 - goto error_ret; 383 + return ret; 382 384 attrcount += ret; 383 385 384 386 ret = iio_device_add_event(indio_dev, chan, i, type, dir, 385 387 IIO_SHARED_BY_ALL, 386 388 &chan->event_spec[i].mask_shared_by_all); 387 389 if (ret < 0) 388 - goto error_ret; 390 + return ret; 389 391 attrcount += ret; 390 392 } 391 393 ret = attrcount; 392 - error_ret: 393 394 return ret; 394 395 } 395 396 ··· 422 425 { 423 426 INIT_KFIFO(ev_int->det_events); 424 427 init_waitqueue_head(&ev_int->wait); 428 + mutex_init(&ev_int->read_lock); 425 429 } 426 430 427 431 static const char *iio_event_group_name = "events"; ··· 438 440 439 441 indio_dev->event_interface = 440 442 kzalloc(sizeof(struct iio_event_interface), GFP_KERNEL); 441 - if (indio_dev->event_interface == NULL) { 442 - ret = -ENOMEM; 443 - goto error_ret; 444 - } 443 + if (indio_dev->event_interface == NULL) 444 + return -ENOMEM; 445 445 446 446 INIT_LIST_HEAD(&indio_dev->event_interface->dev_attr_list); 447 447 ··· 485 489 error_free_setup_event_lines: 486 490 iio_free_chan_devattr_list(&indio_dev->event_interface->dev_attr_list); 487 491 kfree(indio_dev->event_interface); 488 - error_ret: 489 - 490 492 return ret; 491 493 } 492 494
+4 -7
drivers/iio/industrialio-trigger.c
··· 62 62 int ret; 63 63 64 64 trig_info->id = ida_simple_get(&iio_trigger_ida, 0, 0, GFP_KERNEL); 65 - if (trig_info->id < 0) { 66 - ret = trig_info->id; 67 - goto error_ret; 68 - } 65 + if (trig_info->id < 0) 66 + return trig_info->id; 67 + 69 68 /* Set the name used for the sysfs directory etc */ 70 69 dev_set_name(&trig_info->dev, "trigger%ld", 71 70 (unsigned long) trig_info->id); ··· 82 83 83 84 error_unregister_id: 84 85 ida_simple_remove(&iio_trigger_ida, trig_info->id); 85 - error_ret: 86 86 return ret; 87 87 } 88 88 EXPORT_SYMBOL(iio_trigger_register); ··· 232 234 if (trig->ops && trig->ops->set_trigger_state && no_other_users) { 233 235 ret = trig->ops->set_trigger_state(trig, false); 234 236 if (ret) 235 - goto error_ret; 237 + return ret; 236 238 } 237 239 iio_trigger_put_irq(trig, pf->irq); 238 240 free_irq(pf->irq, pf); 239 241 module_put(pf->indio_dev->info->driver_module); 240 242 241 - error_ret: 242 243 return ret; 243 244 } 244 245
+14
drivers/iio/light/Kconfig
··· 73 73 Say yes here to build support for the HID SENSOR 74 74 Ambient light sensor. 75 75 76 + config HID_SENSOR_PROX 77 + depends on HID_SENSOR_HUB 78 + select IIO_BUFFER 79 + select IIO_TRIGGERED_BUFFER 80 + select HID_SENSOR_IIO_COMMON 81 + select HID_SENSOR_IIO_TRIGGER 82 + tristate "HID PROX" 83 + help 84 + Say yes here to build support for the HID SENSOR 85 + Proximity sensor. 86 + 87 + To compile this driver as a module, choose M here: the 88 + module will be called hid-sensor-prox. 89 + 76 90 config SENSORS_LM3533 77 91 tristate "LM3533 ambient light sensor" 78 92 depends on MFD_LM3533
+1
drivers/iio/light/Makefile
··· 9 9 obj-$(CONFIG_CM36651) += cm36651.o 10 10 obj-$(CONFIG_GP2AP020A00F) += gp2ap020a00f.o 11 11 obj-$(CONFIG_HID_SENSOR_ALS) += hid-sensor-als.o 12 + obj-$(CONFIG_HID_SENSOR_PROX) += hid-sensor-prox.o 12 13 obj-$(CONFIG_SENSORS_LM3533) += lm3533-als.o 13 14 obj-$(CONFIG_LTR501) += ltr501.o 14 15 obj-$(CONFIG_SENSORS_TSL2563) += tsl2563.o
+375
drivers/iio/light/hid-sensor-prox.c
··· 1 + /* 2 + * HID Sensors Driver 3 + * Copyright (c) 2014, Intel Corporation. 4 + * 5 + * This program is free software; you can redistribute it and/or modify it 6 + * under the terms and conditions of the GNU General Public License, 7 + * version 2, as published by the Free Software Foundation. 8 + * 9 + * This program is distributed in the hope it will be useful, but WITHOUT 10 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 12 + * more details. 13 + * 14 + * You should have received a copy of the GNU General Public License along with 15 + * this program. 16 + * 17 + */ 18 + #include <linux/device.h> 19 + #include <linux/platform_device.h> 20 + #include <linux/module.h> 21 + #include <linux/interrupt.h> 22 + #include <linux/irq.h> 23 + #include <linux/slab.h> 24 + #include <linux/hid-sensor-hub.h> 25 + #include <linux/iio/iio.h> 26 + #include <linux/iio/sysfs.h> 27 + #include <linux/iio/buffer.h> 28 + #include <linux/iio/trigger_consumer.h> 29 + #include <linux/iio/triggered_buffer.h> 30 + #include "../common/hid-sensors/hid-sensor-trigger.h" 31 + 32 + #define CHANNEL_SCAN_INDEX_PRESENCE 0 33 + 34 + struct prox_state { 35 + struct hid_sensor_hub_callbacks callbacks; 36 + struct hid_sensor_common common_attributes; 37 + struct hid_sensor_hub_attribute_info prox_attr; 38 + u32 human_presence; 39 + }; 40 + 41 + /* Channel definitions */ 42 + static const struct iio_chan_spec prox_channels[] = { 43 + { 44 + .type = IIO_PROXIMITY, 45 + .modified = 1, 46 + .channel2 = IIO_NO_MOD, 47 + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), 48 + .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) | 49 + BIT(IIO_CHAN_INFO_SCALE) | 50 + BIT(IIO_CHAN_INFO_SAMP_FREQ) | 51 + BIT(IIO_CHAN_INFO_HYSTERESIS), 52 + .scan_index = CHANNEL_SCAN_INDEX_PRESENCE, 53 + } 54 + }; 55 + 56 + /* Adjust channel real bits based on report descriptor */ 57 + static void prox_adjust_channel_bit_mask(struct iio_chan_spec *channels, 58 + int channel, int size) 59 + { 60 + channels[channel].scan_type.sign = 's'; 61 + /* Real storage bits will change based on the report desc. */ 62 + channels[channel].scan_type.realbits = size * 8; 63 + /* Maximum size of a sample to capture is u32 */ 64 + channels[channel].scan_type.storagebits = sizeof(u32) * 8; 65 + } 66 + 67 + /* Channel read_raw handler */ 68 + static int prox_read_raw(struct iio_dev *indio_dev, 69 + struct iio_chan_spec const *chan, 70 + int *val, int *val2, 71 + long mask) 72 + { 73 + struct prox_state *prox_state = iio_priv(indio_dev); 74 + int report_id = -1; 75 + u32 address; 76 + int ret; 77 + int ret_type; 78 + 79 + *val = 0; 80 + *val2 = 0; 81 + switch (mask) { 82 + case IIO_CHAN_INFO_RAW: 83 + switch (chan->scan_index) { 84 + case CHANNEL_SCAN_INDEX_PRESENCE: 85 + report_id = prox_state->prox_attr.report_id; 86 + address = 87 + HID_USAGE_SENSOR_HUMAN_PRESENCE; 88 + break; 89 + default: 90 + report_id = -1; 91 + break; 92 + } 93 + if (report_id >= 0) 94 + *val = sensor_hub_input_attr_get_raw_value( 95 + prox_state->common_attributes.hsdev, 96 + HID_USAGE_SENSOR_PROX, address, 97 + report_id); 98 + else { 99 + *val = 0; 100 + return -EINVAL; 101 + } 102 + ret_type = IIO_VAL_INT; 103 + break; 104 + case IIO_CHAN_INFO_SCALE: 105 + *val = prox_state->prox_attr.units; 106 + ret_type = IIO_VAL_INT; 107 + break; 108 + case IIO_CHAN_INFO_OFFSET: 109 + *val = hid_sensor_convert_exponent( 110 + prox_state->prox_attr.unit_expo); 111 + ret_type = IIO_VAL_INT; 112 + break; 113 + case IIO_CHAN_INFO_SAMP_FREQ: 114 + ret = hid_sensor_read_samp_freq_value( 115 + &prox_state->common_attributes, val, val2); 116 + ret_type = IIO_VAL_INT_PLUS_MICRO; 117 + break; 118 + case IIO_CHAN_INFO_HYSTERESIS: 119 + ret = hid_sensor_read_raw_hyst_value( 120 + &prox_state->common_attributes, val, val2); 121 + ret_type = IIO_VAL_INT_PLUS_MICRO; 122 + break; 123 + default: 124 + ret_type = -EINVAL; 125 + break; 126 + } 127 + 128 + return ret_type; 129 + } 130 + 131 + /* Channel write_raw handler */ 132 + static int prox_write_raw(struct iio_dev *indio_dev, 133 + struct iio_chan_spec const *chan, 134 + int val, 135 + int val2, 136 + long mask) 137 + { 138 + struct prox_state *prox_state = iio_priv(indio_dev); 139 + int ret = 0; 140 + 141 + switch (mask) { 142 + case IIO_CHAN_INFO_SAMP_FREQ: 143 + ret = hid_sensor_write_samp_freq_value( 144 + &prox_state->common_attributes, val, val2); 145 + break; 146 + case IIO_CHAN_INFO_HYSTERESIS: 147 + ret = hid_sensor_write_raw_hyst_value( 148 + &prox_state->common_attributes, val, val2); 149 + break; 150 + default: 151 + ret = -EINVAL; 152 + } 153 + 154 + return ret; 155 + } 156 + 157 + static const struct iio_info prox_info = { 158 + .driver_module = THIS_MODULE, 159 + .read_raw = &prox_read_raw, 160 + .write_raw = &prox_write_raw, 161 + }; 162 + 163 + /* Function to push data to buffer */ 164 + static void hid_sensor_push_data(struct iio_dev *indio_dev, const void *data, 165 + int len) 166 + { 167 + dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n"); 168 + iio_push_to_buffers(indio_dev, data); 169 + } 170 + 171 + /* Callback handler to send event after all samples are received and captured */ 172 + static int prox_proc_event(struct hid_sensor_hub_device *hsdev, 173 + unsigned usage_id, 174 + void *priv) 175 + { 176 + struct iio_dev *indio_dev = platform_get_drvdata(priv); 177 + struct prox_state *prox_state = iio_priv(indio_dev); 178 + 179 + dev_dbg(&indio_dev->dev, "prox_proc_event [%d]\n", 180 + prox_state->common_attributes.data_ready); 181 + if (prox_state->common_attributes.data_ready) 182 + hid_sensor_push_data(indio_dev, 183 + &prox_state->human_presence, 184 + sizeof(prox_state->human_presence)); 185 + 186 + return 0; 187 + } 188 + 189 + /* Capture samples in local storage */ 190 + static int prox_capture_sample(struct hid_sensor_hub_device *hsdev, 191 + unsigned usage_id, 192 + size_t raw_len, char *raw_data, 193 + void *priv) 194 + { 195 + struct iio_dev *indio_dev = platform_get_drvdata(priv); 196 + struct prox_state *prox_state = iio_priv(indio_dev); 197 + int ret = -EINVAL; 198 + 199 + switch (usage_id) { 200 + case HID_USAGE_SENSOR_HUMAN_PRESENCE: 201 + prox_state->human_presence = *(u32 *)raw_data; 202 + ret = 0; 203 + break; 204 + default: 205 + break; 206 + } 207 + 208 + return ret; 209 + } 210 + 211 + /* Parse report which is specific to an usage id*/ 212 + static int prox_parse_report(struct platform_device *pdev, 213 + struct hid_sensor_hub_device *hsdev, 214 + struct iio_chan_spec *channels, 215 + unsigned usage_id, 216 + struct prox_state *st) 217 + { 218 + int ret; 219 + 220 + ret = sensor_hub_input_get_attribute_info(hsdev, HID_INPUT_REPORT, 221 + usage_id, 222 + HID_USAGE_SENSOR_HUMAN_PRESENCE, 223 + &st->prox_attr); 224 + if (ret < 0) 225 + return ret; 226 + prox_adjust_channel_bit_mask(channels, CHANNEL_SCAN_INDEX_PRESENCE, 227 + st->prox_attr.size); 228 + 229 + dev_dbg(&pdev->dev, "prox %x:%x\n", st->prox_attr.index, 230 + st->prox_attr.report_id); 231 + 232 + /* Set Sensitivity field ids, when there is no individual modifier */ 233 + if (st->common_attributes.sensitivity.index < 0) { 234 + sensor_hub_input_get_attribute_info(hsdev, 235 + HID_FEATURE_REPORT, usage_id, 236 + HID_USAGE_SENSOR_DATA_MOD_CHANGE_SENSITIVITY_ABS | 237 + HID_USAGE_SENSOR_DATA_PRESENCE, 238 + &st->common_attributes.sensitivity); 239 + dev_dbg(&pdev->dev, "Sensitivity index:report %d:%d\n", 240 + st->common_attributes.sensitivity.index, 241 + st->common_attributes.sensitivity.report_id); 242 + } 243 + return ret; 244 + } 245 + 246 + /* Function to initialize the processing for usage id */ 247 + static int hid_prox_probe(struct platform_device *pdev) 248 + { 249 + int ret = 0; 250 + static const char *name = "prox"; 251 + struct iio_dev *indio_dev; 252 + struct prox_state *prox_state; 253 + struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 254 + struct iio_chan_spec *channels; 255 + 256 + indio_dev = devm_iio_device_alloc(&pdev->dev, 257 + sizeof(struct prox_state)); 258 + if (!indio_dev) 259 + return -ENOMEM; 260 + platform_set_drvdata(pdev, indio_dev); 261 + 262 + prox_state = iio_priv(indio_dev); 263 + prox_state->common_attributes.hsdev = hsdev; 264 + prox_state->common_attributes.pdev = pdev; 265 + 266 + ret = hid_sensor_parse_common_attributes(hsdev, HID_USAGE_SENSOR_PROX, 267 + &prox_state->common_attributes); 268 + if (ret) { 269 + dev_err(&pdev->dev, "failed to setup common attributes\n"); 270 + return ret; 271 + } 272 + 273 + channels = kmemdup(prox_channels, sizeof(prox_channels), GFP_KERNEL); 274 + if (!channels) { 275 + dev_err(&pdev->dev, "failed to duplicate channels\n"); 276 + return -ENOMEM; 277 + } 278 + 279 + ret = prox_parse_report(pdev, hsdev, channels, 280 + HID_USAGE_SENSOR_PROX, prox_state); 281 + if (ret) { 282 + dev_err(&pdev->dev, "failed to setup attributes\n"); 283 + goto error_free_dev_mem; 284 + } 285 + 286 + indio_dev->channels = channels; 287 + indio_dev->num_channels = 288 + ARRAY_SIZE(prox_channels); 289 + indio_dev->dev.parent = &pdev->dev; 290 + indio_dev->info = &prox_info; 291 + indio_dev->name = name; 292 + indio_dev->modes = INDIO_DIRECT_MODE; 293 + 294 + ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time, 295 + NULL, NULL); 296 + if (ret) { 297 + dev_err(&pdev->dev, "failed to initialize trigger buffer\n"); 298 + goto error_free_dev_mem; 299 + } 300 + prox_state->common_attributes.data_ready = false; 301 + ret = hid_sensor_setup_trigger(indio_dev, name, 302 + &prox_state->common_attributes); 303 + if (ret) { 304 + dev_err(&pdev->dev, "trigger setup failed\n"); 305 + goto error_unreg_buffer_funcs; 306 + } 307 + 308 + ret = iio_device_register(indio_dev); 309 + if (ret) { 310 + dev_err(&pdev->dev, "device register failed\n"); 311 + goto error_remove_trigger; 312 + } 313 + 314 + prox_state->callbacks.send_event = prox_proc_event; 315 + prox_state->callbacks.capture_sample = prox_capture_sample; 316 + prox_state->callbacks.pdev = pdev; 317 + ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_PROX, 318 + &prox_state->callbacks); 319 + if (ret < 0) { 320 + dev_err(&pdev->dev, "callback reg failed\n"); 321 + goto error_iio_unreg; 322 + } 323 + 324 + return ret; 325 + 326 + error_iio_unreg: 327 + iio_device_unregister(indio_dev); 328 + error_remove_trigger: 329 + hid_sensor_remove_trigger(&prox_state->common_attributes); 330 + error_unreg_buffer_funcs: 331 + iio_triggered_buffer_cleanup(indio_dev); 332 + error_free_dev_mem: 333 + kfree(indio_dev->channels); 334 + return ret; 335 + } 336 + 337 + /* Function to deinitialize the processing for usage id */ 338 + static int hid_prox_remove(struct platform_device *pdev) 339 + { 340 + struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 341 + struct iio_dev *indio_dev = platform_get_drvdata(pdev); 342 + struct prox_state *prox_state = iio_priv(indio_dev); 343 + 344 + sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_PROX); 345 + iio_device_unregister(indio_dev); 346 + hid_sensor_remove_trigger(&prox_state->common_attributes); 347 + iio_triggered_buffer_cleanup(indio_dev); 348 + kfree(indio_dev->channels); 349 + 350 + return 0; 351 + } 352 + 353 + static struct platform_device_id hid_prox_ids[] = { 354 + { 355 + /* Format: HID-SENSOR-usage_id_in_hex_lowercase */ 356 + .name = "HID-SENSOR-200011", 357 + }, 358 + { /* sentinel */ } 359 + }; 360 + MODULE_DEVICE_TABLE(platform, hid_prox_ids); 361 + 362 + static struct platform_driver hid_prox_platform_driver = { 363 + .id_table = hid_prox_ids, 364 + .driver = { 365 + .name = KBUILD_MODNAME, 366 + .owner = THIS_MODULE, 367 + }, 368 + .probe = hid_prox_probe, 369 + .remove = hid_prox_remove, 370 + }; 371 + module_platform_driver(hid_prox_platform_driver); 372 + 373 + MODULE_DESCRIPTION("HID Sensor Proximity"); 374 + MODULE_AUTHOR("Archana Patni <archana.patni@intel.com>"); 375 + MODULE_LICENSE("GPL");
+13 -3
drivers/iio/magnetometer/mag3110.c
··· 183 183 return -EINVAL; 184 184 } 185 185 case IIO_CHAN_INFO_SCALE: 186 - *val = 0; 187 - *val2 = 1000; 186 + switch (chan->type) { 187 + case IIO_MAGN: 188 + *val = 0; 189 + *val2 = 1000; 190 + return IIO_VAL_INT_PLUS_MICRO; 191 + case IIO_TEMP: 192 + *val = 1000; 193 + return IIO_VAL_INT; 194 + default: 195 + return -EINVAL; 196 + } 188 197 return IIO_VAL_INT_PLUS_MICRO; 189 198 case IIO_CHAN_INFO_SAMP_FREQ: 190 199 i = data->ctrl_reg1 >> MAG3110_CTRL_DR_SHIFT; ··· 279 270 MAG3110_CHANNEL(Z, 2), 280 271 { 281 272 .type = IIO_TEMP, 282 - .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), 273 + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | 274 + BIT(IIO_CHAN_INFO_SCALE), 283 275 .scan_index = 3, 284 276 .scan_type = { 285 277 .sign = 's',
+15 -1
drivers/iio/pressure/Kconfig
··· 5 5 6 6 menu "Pressure sensors" 7 7 8 + config HID_SENSOR_PRESS 9 + depends on HID_SENSOR_HUB 10 + select IIO_BUFFER 11 + select IIO_TRIGGERED_BUFFER 12 + select HID_SENSOR_IIO_COMMON 13 + select HID_SENSOR_IIO_TRIGGER 14 + tristate "HID PRESS" 15 + help 16 + Say yes here to build support for the HID SENSOR 17 + Pressure driver 18 + 19 + To compile this driver as a module, choose M here: the module 20 + will be called hid-sensor-press. 21 + 8 22 config MPL3115 9 23 tristate "Freescale MPL3115A2 pressure sensor driver" 10 24 depends on I2C ··· 40 26 select IIO_TRIGGERED_BUFFER if (IIO_BUFFER) 41 27 help 42 28 Say yes here to build support for STMicroelectronics pressure 43 - sensors: LPS001WP, LPS331AP. 29 + sensors: LPS001WP, LPS25H, LPS331AP. 44 30 45 31 This driver can also be built as a module. If so, these modules 46 32 will be created:
+1
drivers/iio/pressure/Makefile
··· 3 3 # 4 4 5 5 # When adding new entries keep the list in alphabetical order 6 + obj-$(CONFIG_HID_SENSOR_PRESS) += hid-sensor-press.o 6 7 obj-$(CONFIG_MPL3115) += mpl3115.o 7 8 obj-$(CONFIG_IIO_ST_PRESS) += st_pressure.o 8 9 st_pressure-y := st_pressure_core.o
+376
drivers/iio/pressure/hid-sensor-press.c
··· 1 + /* 2 + * HID Sensors Driver 3 + * Copyright (c) 2014, Intel Corporation. 4 + * 5 + * This program is free software; you can redistribute it and/or modify it 6 + * under the terms and conditions of the GNU General Public License, 7 + * version 2, as published by the Free Software Foundation. 8 + * 9 + * This program is distributed in the hope it will be useful, but WITHOUT 10 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 12 + * more details. 13 + * 14 + * You should have received a copy of the GNU General Public License along with 15 + * this program. 16 + * 17 + */ 18 + #include <linux/device.h> 19 + #include <linux/platform_device.h> 20 + #include <linux/module.h> 21 + #include <linux/interrupt.h> 22 + #include <linux/irq.h> 23 + #include <linux/slab.h> 24 + #include <linux/hid-sensor-hub.h> 25 + #include <linux/iio/iio.h> 26 + #include <linux/iio/sysfs.h> 27 + #include <linux/iio/buffer.h> 28 + #include <linux/iio/trigger_consumer.h> 29 + #include <linux/iio/triggered_buffer.h> 30 + #include "../common/hid-sensors/hid-sensor-trigger.h" 31 + 32 + #define CHANNEL_SCAN_INDEX_PRESSURE 0 33 + 34 + struct press_state { 35 + struct hid_sensor_hub_callbacks callbacks; 36 + struct hid_sensor_common common_attributes; 37 + struct hid_sensor_hub_attribute_info press_attr; 38 + u32 press_data; 39 + }; 40 + 41 + /* Channel definitions */ 42 + static const struct iio_chan_spec press_channels[] = { 43 + { 44 + .type = IIO_PRESSURE, 45 + .modified = 1, 46 + .channel2 = IIO_NO_MOD, 47 + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), 48 + .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) | 49 + BIT(IIO_CHAN_INFO_SCALE) | 50 + BIT(IIO_CHAN_INFO_SAMP_FREQ) | 51 + BIT(IIO_CHAN_INFO_HYSTERESIS), 52 + .scan_index = CHANNEL_SCAN_INDEX_PRESSURE, 53 + } 54 + }; 55 + 56 + /* Adjust channel real bits based on report descriptor */ 57 + static void press_adjust_channel_bit_mask(struct iio_chan_spec *channels, 58 + int channel, int size) 59 + { 60 + channels[channel].scan_type.sign = 's'; 61 + /* Real storage bits will change based on the report desc. */ 62 + channels[channel].scan_type.realbits = size * 8; 63 + /* Maximum size of a sample to capture is u32 */ 64 + channels[channel].scan_type.storagebits = sizeof(u32) * 8; 65 + } 66 + 67 + /* Channel read_raw handler */ 68 + static int press_read_raw(struct iio_dev *indio_dev, 69 + struct iio_chan_spec const *chan, 70 + int *val, int *val2, 71 + long mask) 72 + { 73 + struct press_state *press_state = iio_priv(indio_dev); 74 + int report_id = -1; 75 + u32 address; 76 + int ret; 77 + int ret_type; 78 + 79 + *val = 0; 80 + *val2 = 0; 81 + switch (mask) { 82 + case IIO_CHAN_INFO_RAW: 83 + switch (chan->scan_index) { 84 + case CHANNEL_SCAN_INDEX_PRESSURE: 85 + report_id = press_state->press_attr.report_id; 86 + address = 87 + HID_USAGE_SENSOR_ATMOSPHERIC_PRESSURE; 88 + break; 89 + default: 90 + report_id = -1; 91 + break; 92 + } 93 + if (report_id >= 0) 94 + *val = sensor_hub_input_attr_get_raw_value( 95 + press_state->common_attributes.hsdev, 96 + HID_USAGE_SENSOR_PRESSURE, address, 97 + report_id); 98 + else { 99 + *val = 0; 100 + return -EINVAL; 101 + } 102 + ret_type = IIO_VAL_INT; 103 + break; 104 + case IIO_CHAN_INFO_SCALE: 105 + *val = press_state->press_attr.units; 106 + ret_type = IIO_VAL_INT; 107 + break; 108 + case IIO_CHAN_INFO_OFFSET: 109 + *val = hid_sensor_convert_exponent( 110 + press_state->press_attr.unit_expo); 111 + ret_type = IIO_VAL_INT; 112 + break; 113 + case IIO_CHAN_INFO_SAMP_FREQ: 114 + ret = hid_sensor_read_samp_freq_value( 115 + &press_state->common_attributes, val, val2); 116 + ret_type = IIO_VAL_INT_PLUS_MICRO; 117 + break; 118 + case IIO_CHAN_INFO_HYSTERESIS: 119 + ret = hid_sensor_read_raw_hyst_value( 120 + &press_state->common_attributes, val, val2); 121 + ret_type = IIO_VAL_INT_PLUS_MICRO; 122 + break; 123 + default: 124 + ret_type = -EINVAL; 125 + break; 126 + } 127 + 128 + return ret_type; 129 + } 130 + 131 + /* Channel write_raw handler */ 132 + static int press_write_raw(struct iio_dev *indio_dev, 133 + struct iio_chan_spec const *chan, 134 + int val, 135 + int val2, 136 + long mask) 137 + { 138 + struct press_state *press_state = iio_priv(indio_dev); 139 + int ret = 0; 140 + 141 + switch (mask) { 142 + case IIO_CHAN_INFO_SAMP_FREQ: 143 + ret = hid_sensor_write_samp_freq_value( 144 + &press_state->common_attributes, val, val2); 145 + break; 146 + case IIO_CHAN_INFO_HYSTERESIS: 147 + ret = hid_sensor_write_raw_hyst_value( 148 + &press_state->common_attributes, val, val2); 149 + break; 150 + default: 151 + ret = -EINVAL; 152 + } 153 + 154 + return ret; 155 + } 156 + 157 + static const struct iio_info press_info = { 158 + .driver_module = THIS_MODULE, 159 + .read_raw = &press_read_raw, 160 + .write_raw = &press_write_raw, 161 + }; 162 + 163 + /* Function to push data to buffer */ 164 + static void hid_sensor_push_data(struct iio_dev *indio_dev, const void *data, 165 + int len) 166 + { 167 + dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n"); 168 + iio_push_to_buffers(indio_dev, data); 169 + } 170 + 171 + /* Callback handler to send event after all samples are received and captured */ 172 + static int press_proc_event(struct hid_sensor_hub_device *hsdev, 173 + unsigned usage_id, 174 + void *priv) 175 + { 176 + struct iio_dev *indio_dev = platform_get_drvdata(priv); 177 + struct press_state *press_state = iio_priv(indio_dev); 178 + 179 + dev_dbg(&indio_dev->dev, "press_proc_event [%d]\n", 180 + press_state->common_attributes.data_ready); 181 + if (press_state->common_attributes.data_ready) 182 + hid_sensor_push_data(indio_dev, 183 + &press_state->press_data, 184 + sizeof(press_state->press_data)); 185 + 186 + return 0; 187 + } 188 + 189 + /* Capture samples in local storage */ 190 + static int press_capture_sample(struct hid_sensor_hub_device *hsdev, 191 + unsigned usage_id, 192 + size_t raw_len, char *raw_data, 193 + void *priv) 194 + { 195 + struct iio_dev *indio_dev = platform_get_drvdata(priv); 196 + struct press_state *press_state = iio_priv(indio_dev); 197 + int ret = -EINVAL; 198 + 199 + switch (usage_id) { 200 + case HID_USAGE_SENSOR_ATMOSPHERIC_PRESSURE: 201 + press_state->press_data = *(u32 *)raw_data; 202 + ret = 0; 203 + break; 204 + default: 205 + break; 206 + } 207 + 208 + return ret; 209 + } 210 + 211 + /* Parse report which is specific to an usage id*/ 212 + static int press_parse_report(struct platform_device *pdev, 213 + struct hid_sensor_hub_device *hsdev, 214 + struct iio_chan_spec *channels, 215 + unsigned usage_id, 216 + struct press_state *st) 217 + { 218 + int ret; 219 + 220 + ret = sensor_hub_input_get_attribute_info(hsdev, HID_INPUT_REPORT, 221 + usage_id, 222 + HID_USAGE_SENSOR_ATMOSPHERIC_PRESSURE, 223 + &st->press_attr); 224 + if (ret < 0) 225 + return ret; 226 + press_adjust_channel_bit_mask(channels, CHANNEL_SCAN_INDEX_PRESSURE, 227 + st->press_attr.size); 228 + 229 + dev_dbg(&pdev->dev, "press %x:%x\n", st->press_attr.index, 230 + st->press_attr.report_id); 231 + 232 + /* Set Sensitivity field ids, when there is no individual modifier */ 233 + if (st->common_attributes.sensitivity.index < 0) { 234 + sensor_hub_input_get_attribute_info(hsdev, 235 + HID_FEATURE_REPORT, usage_id, 236 + HID_USAGE_SENSOR_DATA_MOD_CHANGE_SENSITIVITY_ABS | 237 + HID_USAGE_SENSOR_DATA_ATMOSPHERIC_PRESSURE, 238 + &st->common_attributes.sensitivity); 239 + dev_dbg(&pdev->dev, "Sensitivity index:report %d:%d\n", 240 + st->common_attributes.sensitivity.index, 241 + st->common_attributes.sensitivity.report_id); 242 + } 243 + return ret; 244 + } 245 + 246 + /* Function to initialize the processing for usage id */ 247 + static int hid_press_probe(struct platform_device *pdev) 248 + { 249 + int ret = 0; 250 + static const char *name = "press"; 251 + struct iio_dev *indio_dev; 252 + struct press_state *press_state; 253 + struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 254 + struct iio_chan_spec *channels; 255 + 256 + indio_dev = devm_iio_device_alloc(&pdev->dev, 257 + sizeof(struct press_state)); 258 + if (!indio_dev) 259 + return -ENOMEM; 260 + platform_set_drvdata(pdev, indio_dev); 261 + 262 + press_state = iio_priv(indio_dev); 263 + press_state->common_attributes.hsdev = hsdev; 264 + press_state->common_attributes.pdev = pdev; 265 + 266 + ret = hid_sensor_parse_common_attributes(hsdev, 267 + HID_USAGE_SENSOR_PRESSURE, 268 + &press_state->common_attributes); 269 + if (ret) { 270 + dev_err(&pdev->dev, "failed to setup common attributes\n"); 271 + return ret; 272 + } 273 + 274 + channels = kmemdup(press_channels, sizeof(press_channels), GFP_KERNEL); 275 + if (!channels) { 276 + dev_err(&pdev->dev, "failed to duplicate channels\n"); 277 + return -ENOMEM; 278 + } 279 + 280 + ret = press_parse_report(pdev, hsdev, channels, 281 + HID_USAGE_SENSOR_PRESSURE, press_state); 282 + if (ret) { 283 + dev_err(&pdev->dev, "failed to setup attributes\n"); 284 + goto error_free_dev_mem; 285 + } 286 + 287 + indio_dev->channels = channels; 288 + indio_dev->num_channels = 289 + ARRAY_SIZE(press_channels); 290 + indio_dev->dev.parent = &pdev->dev; 291 + indio_dev->info = &press_info; 292 + indio_dev->name = name; 293 + indio_dev->modes = INDIO_DIRECT_MODE; 294 + 295 + ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time, 296 + NULL, NULL); 297 + if (ret) { 298 + dev_err(&pdev->dev, "failed to initialize trigger buffer\n"); 299 + goto error_free_dev_mem; 300 + } 301 + press_state->common_attributes.data_ready = false; 302 + ret = hid_sensor_setup_trigger(indio_dev, name, 303 + &press_state->common_attributes); 304 + if (ret) { 305 + dev_err(&pdev->dev, "trigger setup failed\n"); 306 + goto error_unreg_buffer_funcs; 307 + } 308 + 309 + ret = iio_device_register(indio_dev); 310 + if (ret) { 311 + dev_err(&pdev->dev, "device register failed\n"); 312 + goto error_remove_trigger; 313 + } 314 + 315 + press_state->callbacks.send_event = press_proc_event; 316 + press_state->callbacks.capture_sample = press_capture_sample; 317 + press_state->callbacks.pdev = pdev; 318 + ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_PRESSURE, 319 + &press_state->callbacks); 320 + if (ret < 0) { 321 + dev_err(&pdev->dev, "callback reg failed\n"); 322 + goto error_iio_unreg; 323 + } 324 + 325 + return ret; 326 + 327 + error_iio_unreg: 328 + iio_device_unregister(indio_dev); 329 + error_remove_trigger: 330 + hid_sensor_remove_trigger(&press_state->common_attributes); 331 + error_unreg_buffer_funcs: 332 + iio_triggered_buffer_cleanup(indio_dev); 333 + error_free_dev_mem: 334 + kfree(indio_dev->channels); 335 + return ret; 336 + } 337 + 338 + /* Function to deinitialize the processing for usage id */ 339 + static int hid_press_remove(struct platform_device *pdev) 340 + { 341 + struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data; 342 + struct iio_dev *indio_dev = platform_get_drvdata(pdev); 343 + struct press_state *press_state = iio_priv(indio_dev); 344 + 345 + sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_PRESSURE); 346 + iio_device_unregister(indio_dev); 347 + hid_sensor_remove_trigger(&press_state->common_attributes); 348 + iio_triggered_buffer_cleanup(indio_dev); 349 + kfree(indio_dev->channels); 350 + 351 + return 0; 352 + } 353 + 354 + static struct platform_device_id hid_press_ids[] = { 355 + { 356 + /* Format: HID-SENSOR-usage_id_in_hex_lowercase */ 357 + .name = "HID-SENSOR-200031", 358 + }, 359 + { /* sentinel */ } 360 + }; 361 + MODULE_DEVICE_TABLE(platform, hid_press_ids); 362 + 363 + static struct platform_driver hid_press_platform_driver = { 364 + .id_table = hid_press_ids, 365 + .driver = { 366 + .name = KBUILD_MODNAME, 367 + .owner = THIS_MODULE, 368 + }, 369 + .probe = hid_press_probe, 370 + .remove = hid_press_remove, 371 + }; 372 + module_platform_driver(hid_press_platform_driver); 373 + 374 + MODULE_DESCRIPTION("HID Sensor Pressure"); 375 + MODULE_AUTHOR("Archana Patni <archana.patni@intel.com>"); 376 + MODULE_LICENSE("GPL");
+1
drivers/iio/pressure/st_pressure.h
··· 15 15 #include <linux/iio/common/st_sensors.h> 16 16 17 17 #define LPS001WP_PRESS_DEV_NAME "lps001wp" 18 + #define LPS25H_PRESS_DEV_NAME "lps25h" 18 19 #define LPS331AP_PRESS_DEV_NAME "lps331ap" 19 20 20 21 /**
+80 -7
drivers/iio/pressure/st_pressure_core.c
··· 40 40 /* FULLSCALE */ 41 41 #define ST_PRESS_FS_AVL_1260MB 1260 42 42 43 + #define ST_PRESS_1_OUT_XL_ADDR 0x28 44 + #define ST_TEMP_1_OUT_L_ADDR 0x2b 45 + 43 46 /* CUSTOM VALUES FOR LPS331AP SENSOR */ 44 47 #define ST_PRESS_LPS331AP_WAI_EXP 0xbb 45 48 #define ST_PRESS_LPS331AP_ODR_ADDR 0x20 ··· 65 62 #define ST_PRESS_LPS331AP_DRDY_IRQ_INT2_MASK 0x20 66 63 #define ST_PRESS_LPS331AP_MULTIREAD_BIT true 67 64 #define ST_PRESS_LPS331AP_TEMP_OFFSET 42500 68 - #define ST_PRESS_LPS331AP_OUT_XL_ADDR 0x28 69 - #define ST_TEMP_LPS331AP_OUT_L_ADDR 0x2b 70 65 71 66 /* CUSTOM VALUES FOR LPS001WP SENSOR */ 72 67 #define ST_PRESS_LPS001WP_WAI_EXP 0xba ··· 81 80 #define ST_PRESS_LPS001WP_OUT_L_ADDR 0x28 82 81 #define ST_TEMP_LPS001WP_OUT_L_ADDR 0x2a 83 82 84 - static const struct iio_chan_spec st_press_lps331ap_channels[] = { 83 + /* CUSTOM VALUES FOR LPS25H SENSOR */ 84 + #define ST_PRESS_LPS25H_WAI_EXP 0xbd 85 + #define ST_PRESS_LPS25H_ODR_ADDR 0x20 86 + #define ST_PRESS_LPS25H_ODR_MASK 0x70 87 + #define ST_PRESS_LPS25H_ODR_AVL_1HZ_VAL 0x01 88 + #define ST_PRESS_LPS25H_ODR_AVL_7HZ_VAL 0x02 89 + #define ST_PRESS_LPS25H_ODR_AVL_13HZ_VAL 0x03 90 + #define ST_PRESS_LPS25H_ODR_AVL_25HZ_VAL 0x04 91 + #define ST_PRESS_LPS25H_PW_ADDR 0x20 92 + #define ST_PRESS_LPS25H_PW_MASK 0x80 93 + #define ST_PRESS_LPS25H_FS_ADDR 0x00 94 + #define ST_PRESS_LPS25H_FS_MASK 0x00 95 + #define ST_PRESS_LPS25H_FS_AVL_1260_VAL 0x00 96 + #define ST_PRESS_LPS25H_FS_AVL_1260_GAIN ST_PRESS_KPASCAL_NANO_SCALE 97 + #define ST_PRESS_LPS25H_FS_AVL_TEMP_GAIN ST_PRESS_CELSIUS_NANO_SCALE 98 + #define ST_PRESS_LPS25H_BDU_ADDR 0x20 99 + #define ST_PRESS_LPS25H_BDU_MASK 0x04 100 + #define ST_PRESS_LPS25H_DRDY_IRQ_ADDR 0x23 101 + #define ST_PRESS_LPS25H_DRDY_IRQ_INT1_MASK 0x01 102 + #define ST_PRESS_LPS25H_DRDY_IRQ_INT2_MASK 0x10 103 + #define ST_PRESS_LPS25H_MULTIREAD_BIT true 104 + #define ST_PRESS_LPS25H_TEMP_OFFSET 42500 105 + #define ST_PRESS_LPS25H_OUT_XL_ADDR 0x28 106 + #define ST_TEMP_LPS25H_OUT_L_ADDR 0x2b 107 + 108 + static const struct iio_chan_spec st_press_1_channels[] = { 85 109 { 86 110 .type = IIO_PRESSURE, 87 111 .channel2 = IIO_NO_MOD, 88 - .address = ST_PRESS_LPS331AP_OUT_XL_ADDR, 112 + .address = ST_PRESS_1_OUT_XL_ADDR, 89 113 .scan_index = ST_SENSORS_SCAN_X, 90 114 .scan_type = { 91 115 .sign = 'u', ··· 125 99 { 126 100 .type = IIO_TEMP, 127 101 .channel2 = IIO_NO_MOD, 128 - .address = ST_TEMP_LPS331AP_OUT_L_ADDR, 102 + .address = ST_TEMP_1_OUT_L_ADDR, 129 103 .scan_index = -1, 130 104 .scan_type = { 131 105 .sign = 'u', ··· 182 156 .sensors_supported = { 183 157 [0] = LPS331AP_PRESS_DEV_NAME, 184 158 }, 185 - .ch = (struct iio_chan_spec *)st_press_lps331ap_channels, 186 - .num_ch = ARRAY_SIZE(st_press_lps331ap_channels), 159 + .ch = (struct iio_chan_spec *)st_press_1_channels, 160 + .num_ch = ARRAY_SIZE(st_press_1_channels), 187 161 .odr = { 188 162 .addr = ST_PRESS_LPS331AP_ODR_ADDR, 189 163 .mask = ST_PRESS_LPS331AP_ODR_MASK, ··· 257 231 .addr = 0, 258 232 }, 259 233 .multi_read_bit = ST_PRESS_LPS001WP_MULTIREAD_BIT, 234 + .bootime = 2, 235 + }, 236 + { 237 + .wai = ST_PRESS_LPS25H_WAI_EXP, 238 + .sensors_supported = { 239 + [0] = LPS25H_PRESS_DEV_NAME, 240 + }, 241 + .ch = (struct iio_chan_spec *)st_press_1_channels, 242 + .num_ch = ARRAY_SIZE(st_press_1_channels), 243 + .odr = { 244 + .addr = ST_PRESS_LPS25H_ODR_ADDR, 245 + .mask = ST_PRESS_LPS25H_ODR_MASK, 246 + .odr_avl = { 247 + { 1, ST_PRESS_LPS25H_ODR_AVL_1HZ_VAL, }, 248 + { 7, ST_PRESS_LPS25H_ODR_AVL_7HZ_VAL, }, 249 + { 13, ST_PRESS_LPS25H_ODR_AVL_13HZ_VAL, }, 250 + { 25, ST_PRESS_LPS25H_ODR_AVL_25HZ_VAL, }, 251 + }, 252 + }, 253 + .pw = { 254 + .addr = ST_PRESS_LPS25H_PW_ADDR, 255 + .mask = ST_PRESS_LPS25H_PW_MASK, 256 + .value_on = ST_SENSORS_DEFAULT_POWER_ON_VALUE, 257 + .value_off = ST_SENSORS_DEFAULT_POWER_OFF_VALUE, 258 + }, 259 + .fs = { 260 + .addr = ST_PRESS_LPS25H_FS_ADDR, 261 + .mask = ST_PRESS_LPS25H_FS_MASK, 262 + .fs_avl = { 263 + [0] = { 264 + .num = ST_PRESS_FS_AVL_1260MB, 265 + .value = ST_PRESS_LPS25H_FS_AVL_1260_VAL, 266 + .gain = ST_PRESS_LPS25H_FS_AVL_1260_GAIN, 267 + .gain2 = ST_PRESS_LPS25H_FS_AVL_TEMP_GAIN, 268 + }, 269 + }, 270 + }, 271 + .bdu = { 272 + .addr = ST_PRESS_LPS25H_BDU_ADDR, 273 + .mask = ST_PRESS_LPS25H_BDU_MASK, 274 + }, 275 + .drdy_irq = { 276 + .addr = ST_PRESS_LPS25H_DRDY_IRQ_ADDR, 277 + .mask_int1 = ST_PRESS_LPS25H_DRDY_IRQ_INT1_MASK, 278 + .mask_int2 = ST_PRESS_LPS25H_DRDY_IRQ_INT2_MASK, 279 + }, 280 + .multi_read_bit = ST_PRESS_LPS25H_MULTIREAD_BIT, 260 281 .bootime = 2, 261 282 }, 262 283 };
+1
drivers/iio/pressure/st_pressure_i2c.c
··· 50 50 51 51 static const struct i2c_device_id st_press_id_table[] = { 52 52 { LPS001WP_PRESS_DEV_NAME }, 53 + { LPS25H_PRESS_DEV_NAME }, 53 54 { LPS331AP_PRESS_DEV_NAME }, 54 55 {}, 55 56 };
+1
drivers/iio/pressure/st_pressure_spi.c
··· 49 49 50 50 static const struct spi_device_id st_press_id_table[] = { 51 51 { LPS001WP_PRESS_DEV_NAME }, 52 + { LPS25H_PRESS_DEV_NAME }, 52 53 { LPS331AP_PRESS_DEV_NAME }, 53 54 {}, 54 55 };
+22
drivers/staging/iio/Documentation/iio_utils.h
··· 652 652 free(temp); 653 653 return ret; 654 654 } 655 + 656 + read_sysfs_string(const char *filename, const char *basedir, char *str) 657 + { 658 + float ret = 0; 659 + FILE *sysfsfp; 660 + char *temp = malloc(strlen(basedir) + strlen(filename) + 2); 661 + if (temp == NULL) { 662 + printf("Memory allocation failed"); 663 + return -ENOMEM; 664 + } 665 + sprintf(temp, "%s/%s", basedir, filename); 666 + sysfsfp = fopen(temp, "r"); 667 + if (sysfsfp == NULL) { 668 + ret = -errno; 669 + goto error_free; 670 + } 671 + fscanf(sysfsfp, "%s\n", str); 672 + fclose(sysfsfp); 673 + error_free: 674 + free(temp); 675 + return ret; 676 + }
+157
drivers/staging/iio/Documentation/lsiio.c
··· 1 + /* 2 + * Industrial I/O utilities - lsiio.c 3 + * 4 + * Copyright (c) 2010 Manuel Stahl <manuel.stahl@iis.fraunhofer.de> 5 + * 6 + * This program is free software; you can redistribute it and/or modify it 7 + * under the terms of the GNU General Public License version 2 as published by 8 + * the Free Software Foundation. 9 + */ 10 + 11 + #include <string.h> 12 + #include <dirent.h> 13 + #include <stdio.h> 14 + #include <errno.h> 15 + #include <stdint.h> 16 + #include <stdlib.h> 17 + #include <unistd.h> 18 + #include <sys/types.h> 19 + #include <sys/stat.h> 20 + #include <sys/dir.h> 21 + #include "iio_utils.h" 22 + 23 + 24 + static enum verbosity { 25 + VERBLEVEL_DEFAULT, /* 0 gives lspci behaviour */ 26 + VERBLEVEL_SENSORS, /* 1 lists sensors */ 27 + } verblevel = VERBLEVEL_DEFAULT; 28 + 29 + const char *type_device = "iio:device"; 30 + const char *type_trigger = "trigger"; 31 + 32 + 33 + static inline int check_prefix(const char *str, const char *prefix) 34 + { 35 + return strlen(str) > strlen(prefix) && 36 + strncmp(str, prefix, strlen(prefix)) == 0; 37 + } 38 + 39 + static inline int check_postfix(const char *str, const char *postfix) 40 + { 41 + return strlen(str) > strlen(postfix) && 42 + strcmp(str + strlen(str) - strlen(postfix), postfix) == 0; 43 + } 44 + 45 + static int dump_channels(const char *dev_dir_name) 46 + { 47 + DIR *dp; 48 + const struct dirent *ent; 49 + dp = opendir(dev_dir_name); 50 + if (dp == NULL) 51 + return -errno; 52 + while (ent = readdir(dp), ent != NULL) 53 + if (check_prefix(ent->d_name, "in_") && 54 + check_postfix(ent->d_name, "_raw")) { 55 + printf(" %-10s\n", ent->d_name); 56 + } 57 + 58 + return 0; 59 + } 60 + 61 + static int dump_one_device(const char *dev_dir_name) 62 + { 63 + char name[IIO_MAX_NAME_LENGTH]; 64 + int dev_idx; 65 + 66 + sscanf(dev_dir_name + strlen(iio_dir) + strlen(type_device), 67 + "%i", &dev_idx); 68 + read_sysfs_string("name", dev_dir_name, name); 69 + printf("Device %03d: %s\n", dev_idx, name); 70 + 71 + if (verblevel >= VERBLEVEL_SENSORS) { 72 + int ret = dump_channels(dev_dir_name); 73 + if (ret) 74 + return ret; 75 + } 76 + return 0; 77 + } 78 + 79 + static int dump_one_trigger(const char *dev_dir_name) 80 + { 81 + char name[IIO_MAX_NAME_LENGTH]; 82 + int dev_idx; 83 + 84 + sscanf(dev_dir_name + strlen(iio_dir) + strlen(type_trigger), 85 + "%i", &dev_idx); 86 + read_sysfs_string("name", dev_dir_name, name); 87 + printf("Trigger %03d: %s\n", dev_idx, name); 88 + return 0; 89 + } 90 + 91 + static void dump_devices(void) 92 + { 93 + const struct dirent *ent; 94 + int number, numstrlen; 95 + 96 + FILE *nameFile; 97 + DIR *dp; 98 + char thisname[IIO_MAX_NAME_LENGTH]; 99 + char *filename; 100 + 101 + dp = opendir(iio_dir); 102 + if (dp == NULL) { 103 + printf("No industrial I/O devices available\n"); 104 + return; 105 + } 106 + 107 + while (ent = readdir(dp), ent != NULL) { 108 + if (check_prefix(ent->d_name, type_device)) { 109 + char *dev_dir_name; 110 + asprintf(&dev_dir_name, "%s%s", iio_dir, ent->d_name); 111 + dump_one_device(dev_dir_name); 112 + free(dev_dir_name); 113 + if (verblevel >= VERBLEVEL_SENSORS) 114 + printf("\n"); 115 + } 116 + } 117 + rewinddir(dp); 118 + while (ent = readdir(dp), ent != NULL) { 119 + if (check_prefix(ent->d_name, type_trigger)) { 120 + char *dev_dir_name; 121 + asprintf(&dev_dir_name, "%s%s", iio_dir, ent->d_name); 122 + dump_one_trigger(dev_dir_name); 123 + free(dev_dir_name); 124 + } 125 + } 126 + closedir(dp); 127 + } 128 + 129 + int main(int argc, char **argv) 130 + { 131 + int c, err = 0; 132 + 133 + while ((c = getopt(argc, argv, "d:D:v")) != EOF) { 134 + switch (c) { 135 + case 'v': 136 + verblevel++; 137 + break; 138 + 139 + case '?': 140 + default: 141 + err++; 142 + break; 143 + } 144 + } 145 + if (err || argc > optind) { 146 + fprintf(stderr, "Usage: lsiio [options]...\n" 147 + "List industrial I/O devices\n" 148 + " -v, --verbose\n" 149 + " Increase verbosity (may be given multiple times)\n" 150 + ); 151 + exit(1); 152 + } 153 + 154 + dump_devices(); 155 + 156 + return 0; 157 + }
+1 -9
drivers/staging/iio/adc/ad799x.h
··· 95 95 struct i2c_client *client; 96 96 const struct ad799x_chip_info *chip_info; 97 97 struct regulator *reg; 98 - u16 int_vref_mv; 98 + struct regulator *vref; 99 99 unsigned id; 100 100 u16 config; 101 101 102 102 u8 *rx_buf; 103 103 unsigned int transfer_size; 104 - }; 105 - 106 - /* 107 - * TODO: struct ad799x_platform_data needs to go into include/linux/iio 108 - */ 109 - 110 - struct ad799x_platform_data { 111 - u16 vref_mv; 112 104 }; 113 105 114 106 #ifdef CONFIG_AD799X_RING_BUFFER
+31 -25
drivers/staging/iio/adc/ad799x_core.c
··· 1 1 /* 2 2 * iio/adc/ad799x.c 3 - * Copyright (C) 2010-1011 Michael Hennerich, Analog Devices Inc. 3 + * Copyright (C) 2010-2011 Michael Hennerich, Analog Devices Inc. 4 4 * 5 5 * based on iio/adc/max1363 6 6 * Copyright (C) 2008-2010 Jonathan Cameron ··· 179 179 RES_MASK(chan->scan_type.realbits); 180 180 return IIO_VAL_INT; 181 181 case IIO_CHAN_INFO_SCALE: 182 - *val = st->int_vref_mv; 182 + ret = regulator_get_voltage(st->vref); 183 + if (ret < 0) 184 + return ret; 185 + *val = ret / 1000; 183 186 *val2 = chan->scan_type.realbits; 184 187 return IIO_VAL_FRACTIONAL_LOG2; 185 188 } ··· 536 533 const struct i2c_device_id *id) 537 534 { 538 535 int ret; 539 - struct ad799x_platform_data *pdata = client->dev.platform_data; 540 536 struct ad799x_state *st; 541 537 struct iio_dev *indio_dev; 542 538 ··· 553 551 554 552 /* TODO: Add pdata options for filtering and bit delay */ 555 553 556 - if (!pdata) 557 - return -EINVAL; 558 - 559 - st->int_vref_mv = pdata->vref_mv; 560 - 561 554 st->reg = devm_regulator_get(&client->dev, "vcc"); 562 - if (!IS_ERR(st->reg)) { 563 - ret = regulator_enable(st->reg); 564 - if (ret) 565 - return ret; 555 + if (IS_ERR(st->reg)) 556 + return PTR_ERR(st->reg); 557 + ret = regulator_enable(st->reg); 558 + if (ret) 559 + return ret; 560 + st->vref = devm_regulator_get(&client->dev, "vref"); 561 + if (IS_ERR(st->vref)) { 562 + ret = PTR_ERR(st->vref); 563 + goto error_disable_reg; 566 564 } 565 + ret = regulator_enable(st->vref); 566 + if (ret) 567 + goto error_disable_reg; 568 + 567 569 st->client = client; 568 570 569 571 indio_dev->dev.parent = &client->dev; ··· 583 577 goto error_disable_reg; 584 578 585 579 if (client->irq > 0) { 586 - ret = request_threaded_irq(client->irq, 587 - NULL, 588 - ad799x_event_handler, 589 - IRQF_TRIGGER_FALLING | 590 - IRQF_ONESHOT, 591 - client->name, 592 - indio_dev); 580 + ret = devm_request_threaded_irq(&client->dev, 581 + client->irq, 582 + NULL, 583 + ad799x_event_handler, 584 + IRQF_TRIGGER_FALLING | 585 + IRQF_ONESHOT, 586 + client->name, 587 + indio_dev); 593 588 if (ret) 594 589 goto error_cleanup_ring; 595 590 } 596 591 ret = iio_device_register(indio_dev); 597 592 if (ret) 598 - goto error_free_irq; 593 + goto error_cleanup_ring; 599 594 600 595 return 0; 601 596 602 - error_free_irq: 603 - if (client->irq > 0) 604 - free_irq(client->irq, indio_dev); 605 597 error_cleanup_ring: 606 598 ad799x_ring_cleanup(indio_dev); 607 599 error_disable_reg: 600 + if (!IS_ERR(st->vref)) 601 + regulator_disable(st->vref); 608 602 if (!IS_ERR(st->reg)) 609 603 regulator_disable(st->reg); 610 604 ··· 617 611 struct ad799x_state *st = iio_priv(indio_dev); 618 612 619 613 iio_device_unregister(indio_dev); 620 - if (client->irq > 0) 621 - free_irq(client->irq, indio_dev); 622 614 623 615 ad799x_ring_cleanup(indio_dev); 616 + if (!IS_ERR(st->vref)) 617 + regulator_disable(st->vref); 624 618 if (!IS_ERR(st->reg)) 625 619 regulator_disable(st->reg); 626 620 kfree(st->rx_buf);
+1 -1
drivers/staging/iio/adc/mxs-lradc.c
··· 1558 1558 for (i = 0; i < of_cfg->irq_count; i++) { 1559 1559 lradc->irq[i] = platform_get_irq(pdev, i); 1560 1560 if (lradc->irq[i] < 0) 1561 - return -EINVAL; 1561 + return lradc->irq[i]; 1562 1562 1563 1563 ret = devm_request_irq(dev, lradc->irq[i], 1564 1564 mxs_lradc_handle_irq, 0,
+10
include/linux/hid-sensor-ids.h
··· 33 33 #define HID_USAGE_SENSOR_DATA_LIGHT 0x2004d0 34 34 #define HID_USAGE_SENSOR_LIGHT_ILLUM 0x2004d1 35 35 36 + /* PROX (200011) */ 37 + #define HID_USAGE_SENSOR_PROX 0x200011 38 + #define HID_USAGE_SENSOR_DATA_PRESENCE 0x2004b0 39 + #define HID_USAGE_SENSOR_HUMAN_PRESENCE 0x2004b1 40 + 41 + /* Pressure (200031) */ 42 + #define HID_USAGE_SENSOR_PRESSURE 0x200031 43 + #define HID_USAGE_SENSOR_DATA_ATMOSPHERIC_PRESSURE 0x200430 44 + #define HID_USAGE_SENSOR_ATMOSPHERIC_PRESSURE 0x200431 45 + 36 46 /* Gyro 3D: (200076) */ 37 47 #define HID_USAGE_SENSOR_GYRO_3D 0x200076 38 48 #define HID_USAGE_SENSOR_DATA_ANGL_VELOCITY 0x200456
+10 -6
include/linux/iio/iio.h
··· 254 254 (chan->info_mask_shared_by_all & BIT(type)); 255 255 } 256 256 257 - #define IIO_ST(si, rb, sb, sh) \ 258 - { .sign = si, .realbits = rb, .storagebits = sb, .shift = sh } 259 - 260 - #define IIO_CHAN_SOFT_TIMESTAMP(_si) \ 261 - { .type = IIO_TIMESTAMP, .channel = -1, \ 262 - .scan_index = _si, .scan_type = IIO_ST('s', 64, 64, 0) } 257 + #define IIO_CHAN_SOFT_TIMESTAMP(_si) { \ 258 + .type = IIO_TIMESTAMP, \ 259 + .channel = -1, \ 260 + .scan_index = _si, \ 261 + .scan_type = { \ 262 + .sign = 's', \ 263 + .realbits = 64, \ 264 + .storagebits = 64, \ 265 + }, \ 266 + } 263 267 264 268 /** 265 269 * iio_get_time_ns() - utility function to get a time stamp for events etc