History

Merge tag 'staging-4.18-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging

Pull staging/IIO updates from Greg KH: "Here is the big staging and IIO driver update for 4.18-rc1. It was delayed as I wanted to make sure the final driver deletions did not cause any major merge issues, and all now looks good. There are a lot of patches here, just over 1000. The diffstat summary shows the major changes here: 1007 files changed, 16828 insertions(+), 227770 deletions(-) Because of this, we might be close to shrinking the overall kernel source code size for two releases in a row. There was loads of work in this release cycle, primarily: - tons of ks7010 driver cleanups - lots of mt7621 driver fixes and cleanups - most driver cleanups - wilc1000 fixes and cleanups - lots and lots of IIO driver cleanups and new additions - debugfs cleanups for all staging drivers - lots of other staging driver cleanups and fixes, the shortlog has the full details. but the big user-visable things here are the removal of 3 chunks of code: - ncpfs and ipx were removed on schedule, no one has cared about this code since it moved to staging last year, and if it needs to come back, it can be reverted. - lustre file system is removed. I've ranted at the lustre developers about once a year for the past 5 years, with no real forward progress at all to clean things up and get the code into the "real" part of the kernel. Given that the lustre developers continue to work on an external tree and try to port those changes to the in-kernel tree every once in a while, this whole thing really really is not working out at all. So I'm deleting it so that the developers can spend the time working in their out-of-tree location and get things cleaned up properly to get merged into the tree correctly at a later date. Because of these file removals, you will have merge issues on some of these files (2 in the ipx code, 1 in the ncpfs code, and 1 in the atomisp driver). Just delete those files, it's a simple merge :) All of this has been in linux-next for a while with no reported problems" * tag 'staging-4.18-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging: (1011 commits) staging: ipx: delete it from the tree ncpfs: remove uapi .h files ncpfs: remove Documentation ncpfs: remove compat functionality staging: ncpfs: delete it staging: lustre: delete the filesystem from the tree. staging: vc04_services: no need to save the log debufs dentries staging: vc04_services: vchiq_debugfs_log_entry can be a void * staging: vc04_services: remove struct vchiq_debugfs_info staging: vc04_services: move client dbg directory into static variable staging: vc04_services: remove odd vchiq_debugfs_top() wrapper staging: vc04_services: no need to check debugfs return values staging: mt7621-gpio: reorder includes alphabetically staging: mt7621-gpio: change gc_map to don't use pointers staging: mt7621-gpio: use GPIOF_DIR_OUT and GPIOF_DIR_IN macros instead of custom values staging: mt7621-gpio: change 'to_mediatek_gpio' to make just a one line return staging: mt7621-gpio: dt-bindings: update documentation for #interrupt-cells property staging: mt7621-gpio: update #interrupt-cells for the gpio node staging: mt7621-gpio: dt-bindings: complete documentation for the gpio staging: mt7621-dts: add missing properties to gpio node ...

Linus Torvalds committed 8 years ago

Commit eafdca42 parents 7d3bf61 7a2e8381006 files · +16823 −227723Browse files

Unified · Split

1006 files
  1. Documentation/ABI/testing/sysfs-bus-iio +9 −0
  2. Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt +1 −0
  3. Documentation/devicetree/bindings/iio/adc/mcp320x.txt +1 −1
  4. Documentation/devicetree/bindings/iio/adc/st,stm32-adc.txt +5 −1
  5. Documentation/devicetree/bindings/iio/adc/st,stm32-dfsdm-adc.txt +5 −2
  6. Documentation/devicetree/bindings/iio/afe/current-sense-amplifier.txt +26 −0
  7. Documentation/devicetree/bindings/iio/afe/current-sense-shunt.txt +41 −0
  8. Documentation/devicetree/bindings/iio/afe/voltage-divider.txt +53 −0
  9. Documentation/devicetree/bindings/iio/dac/ltc2632.txt +14 −0
  10. Documentation/devicetree/bindings/iio/dac/ti,dac5571.txt +24 −0
  11. Documentation/devicetree/bindings/iio/imu/inv_mpu6050.txt +9 −3
  12. Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt +1 −0
  13. Documentation/devicetree/bindings/iio/potentiostat/lmp91000.txt +6 −3
  14. Documentation/filesystems/00-INDEX +0 −2
  15. Documentation/filesystems/ncpfs.txt +0 −12
  16. MAINTAINERS +23 −9
  17. drivers/iio/Kconfig +2 −0
  18. drivers/iio/Makefile +2 −0
  19. drivers/iio/accel/Kconfig +24 −0
  20. drivers/iio/accel/Makefile +2 −0
  21. drivers/iio/accel/adis16201.c +321 −0
  22. drivers/iio/accel/adis16209.c +24 −28
  23. drivers/iio/accel/bmc150-accel-core.c +3 −20
  24. drivers/iio/accel/mma8452.c +23 −1
  25. drivers/iio/accel/sca3000.c +4 −9
  26. drivers/iio/accel/st_accel_i2c.c +1 −0
  27. drivers/iio/adc/ad7791.c +47 −40
  28. drivers/iio/adc/imx7d_adc.c +1 −1
  29. drivers/iio/adc/meson_saradc.c +50 −33
  30. drivers/iio/adc/stm32-adc-core.c +48 −18
  31. drivers/iio/adc/stm32-adc.c +43 −4
  32. drivers/iio/adc/stm32-dfsdm-adc.c +8 −9
  33. drivers/iio/adc/stm32-dfsdm-core.c +26 −0
  34. drivers/iio/adc/stx104.c +11 −0
  35. drivers/iio/adc/ti-ads8688.c +45 −3
  36. drivers/iio/afe/Kconfig +19 −0
  37. drivers/iio/afe/Makefile +6 −0
  38. drivers/iio/afe/iio-rescale.c +359 −0
  39. drivers/iio/amplifiers/ad8366.c +4 −2
  40. drivers/iio/chemical/atlas-ph-sensor.c +7 −7
  41. drivers/iio/common/cros_ec_sensors/cros_ec_sensors.c +1 −2
  42. drivers/iio/common/cros_ec_sensors/cros_ec_sensors_core.c +3 −6
  43. drivers/iio/common/hid-sensors/hid-sensor-trigger.c +3 −6
  44. drivers/iio/dac/Kconfig +29 −4
  45. drivers/iio/dac/Makefile +3 −0
  46. drivers/iio/dac/ad5686-spi.c +119 −0
  47. drivers/iio/dac/ad5686.c +245 −183
  48. drivers/iio/dac/ad5686.h +145 −0
  49. drivers/iio/dac/ad5696-i2c.c +102 −0
  50. drivers/iio/dac/ltc2632.c +71 −18
  51. drivers/iio/dac/ti-dac5571.c +439 −0
  52. drivers/iio/imu/inv_mpu6050/inv_mpu_core.c +164 −120
  53. drivers/iio/imu/inv_mpu6050/inv_mpu_i2c.c +44 −42
  54. drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h +17 −5
  55. drivers/iio/imu/inv_mpu6050/inv_mpu_ring.c +33 −14
  56. drivers/iio/imu/inv_mpu6050/inv_mpu_spi.c +4 −8
  57. drivers/iio/imu/inv_mpu6050/inv_mpu_trigger.c +32 −20
  58. drivers/iio/imu/st_lsm6dsx/Kconfig +2 −1
  59. drivers/iio/imu/st_lsm6dsx/st_lsm6dsx.h +2 −0
  60. drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_buffer.c +5 −5
  61. drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_core.c +4 −3
  62. drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_i2c.c +5 −0
  63. drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_spi.c +5 −0
  64. drivers/iio/light/Kconfig +8 −0
  65. drivers/iio/light/Makefile +1 −0
  66. drivers/iio/light/cros_ec_light_prox.c +1 −2
  67. drivers/iio/light/tsl2583.c +1 −1
  68. drivers/iio/light/tsl2772.c +1800 −0
  69. drivers/iio/magnetometer/mag3110.c +140 −18
  70. drivers/iio/potentiometer/mcp4018.c +20 −21
  71. drivers/iio/potentiometer/mcp4531.c +72 −73
  72. drivers/iio/potentiostat/lmp91000.c +2 −0
  73. drivers/iio/pressure/cros_ec_baro.c +1 −2
  74. drivers/iio/resolver/Kconfig +17 −0
  75. drivers/iio/resolver/Makefile +5 −0
  76. drivers/iio/resolver/ad2s1200.c +106 −61
  77. drivers/staging/Kconfig +0 −6
  78. drivers/staging/Makefile +0 −3
  79. drivers/staging/android/Kconfig +10 −1
  80. drivers/staging/android/Makefile +1 −0
  81. drivers/staging/android/TODO +9 −0
  82. drivers/staging/android/ashmem.h +1 −5
  83. drivers/staging/android/ion/Kconfig +1 −1
  84. drivers/staging/android/ion/ion.c +14 −8
  85. drivers/staging/android/ion/ion.h +1 −1
  86. drivers/staging/android/ion/ion_page_pool.c +5 −0
  87. drivers/staging/android/uapi/ashmem.h +1 −5
  88. drivers/staging/android/uapi/ion.h +1 −1
  89. drivers/staging/android/uapi/vsoc_shm.h +295 −0
  90. drivers/staging/android/vsoc.c +1152 −0
  91. drivers/staging/board/armadillo800eva.c +1 −9
  92. drivers/staging/board/board.c +1 −4
  93. drivers/staging/comedi/comedi_compat32.c +6 −6
  94. drivers/staging/comedi/comedi_usb.h +2 −3
  95. drivers/staging/comedi/comedidev.h +1 −1
  96. drivers/staging/comedi/drivers/cb_pcidas64.c +3 −3
  97. drivers/staging/emxx_udc/Kconfig +1 −1
  98. drivers/staging/emxx_udc/TODO +2 −0
  99. drivers/staging/fbtft/TODO +4 −0
  100. drivers/staging/fbtft/fbtft-bus.c +9 −4
  101. drivers/staging/fsl-dpaa2/Kconfig +8 −0
  102. drivers/staging/fsl-dpaa2/Makefile +3 −2
  103. drivers/staging/fsl-dpaa2/ethernet/dpaa2-eth.c +107 −4
  104. drivers/staging/fsl-dpaa2/ethernet/dpaa2-eth.h +47 −2
  105. drivers/staging/fsl-dpaa2/ethernet/dpaa2-ethtool.c +23 −0
  106. drivers/staging/fsl-dpaa2/ethsw/dpsw-cmd.h +13 −0
  107. drivers/staging/fsl-dpaa2/ethsw/dpsw.c +42 −0
  108. drivers/staging/fsl-dpaa2/ethsw/dpsw.h +6 −0
  109. drivers/staging/fsl-dpaa2/ethsw/ethsw.c +18 −21
  110. drivers/staging/fsl-dpaa2/rtc/Makefile +7 −0
  111. drivers/staging/fsl-dpaa2/rtc/dprtc-cmd.h +137 −0
  112. drivers/staging/fsl-dpaa2/rtc/dprtc.c +701 −0
  113. drivers/staging/fsl-dpaa2/rtc/dprtc.h +164 −0
  114. drivers/staging/fsl-dpaa2/rtc/rtc.c +229 −0
  115. drivers/staging/fsl-dpaa2/rtc/rtc.h +14 −0
  116. drivers/staging/fsl-mc/bus/dpio/dpio-driver.c +19 −9
  117. drivers/staging/fsl-mc/bus/dpio/qbman-portal.h +2 −2
  118. drivers/staging/fsl-mc/include/dpaa2-io.h +1 −1
  119. drivers/staging/gdm724x/gdm_endian.c +2 −12
  120. drivers/staging/gdm724x/gdm_endian.h +2 −12
  121. drivers/staging/gdm724x/gdm_lte.c +3 −13
  122. drivers/staging/gdm724x/gdm_lte.h +2 −12
  123. drivers/staging/gdm724x/gdm_mux.c +2 −12
  124. drivers/staging/gdm724x/gdm_mux.h +2 −12
  125. drivers/staging/gdm724x/gdm_tty.c +2 −12
  126. drivers/staging/gdm724x/gdm_tty.h +2 −12
  127. drivers/staging/gdm724x/gdm_usb.c +2 −12
  128. drivers/staging/gdm724x/gdm_usb.h +2 −12
  129. drivers/staging/gdm724x/hci.h +2 −12
  130. drivers/staging/gdm724x/hci_packet.h +2 −12
  131. drivers/staging/gdm724x/netlink_k.c +2 −12
  132. drivers/staging/gdm724x/netlink_k.h +2 −12
  133. drivers/staging/goldfish/Kconfig +1 −8
  134. drivers/staging/goldfish/Makefile +0 −1
  135. drivers/staging/goldfish/goldfish_nand.c +0 −441
  136. drivers/staging/goldfish/goldfish_nand_reg.h +0 −76
  137. drivers/staging/greybus/TODO +5 −0
  138. drivers/staging/greybus/arche-platform.c +4 −5
  139. drivers/staging/greybus/audio_codec.h +4 −1
  140. drivers/staging/greybus/audio_topology.c +1 −1
  141. drivers/staging/greybus/camera.c +3 −14
  142. drivers/staging/greybus/svc.c +0 −3
  143. drivers/staging/iio/Kconfig +0 −1
  144. drivers/staging/iio/Makefile +0 −1
  145. drivers/staging/iio/TODO +8 −1
  146. drivers/staging/iio/accel/Kconfig +0 −24
  147. drivers/staging/iio/accel/Makefile +0 −2
  148. drivers/staging/iio/accel/adis16201.c +0 −385
  149. drivers/staging/iio/adc/ad7606_par.c +2 −4
  150. drivers/staging/iio/adc/ad7780.c +1 −1
  151. drivers/staging/iio/cdc/ad7746.c +22 −22
  152. drivers/staging/iio/light/Kconfig +0 −14
  153. drivers/staging/iio/light/Makefile +0 −5
  154. drivers/staging/iio/light/tsl2x7x.c +0 −1889
  155. drivers/staging/iio/light/tsl2x7x.h +0 −99
  156. drivers/staging/iio/meter/Kconfig +0 −42
  157. drivers/staging/iio/meter/Makefile +0 −8
  158. drivers/staging/iio/meter/ade7753.c +0 −630
  159. drivers/staging/iio/meter/ade7754.c +0 −664
  160. drivers/staging/iio/meter/ade7758.h +0 −183
  161. drivers/staging/iio/meter/ade7758_core.c +0 −955
  162. drivers/staging/iio/meter/ade7758_ring.c +0 −177
  163. drivers/staging/iio/meter/ade7758_trigger.c +0 −108
  164. drivers/staging/iio/meter/ade7759.c +0 −558
  165. drivers/staging/iio/meter/ade7854-i2c.c +70 −168
  166. drivers/staging/iio/meter/ade7854-spi.c +55 −213
  167. drivers/staging/iio/meter/ade7854.c +20 −20
  168. drivers/staging/iio/meter/ade7854.h +7 −9
  169. drivers/staging/iio/resolver/Kconfig +0 −12
  170. drivers/staging/iio/resolver/Makefile +0 −1
  171. drivers/staging/ipx/Kconfig +0 −61
  172. drivers/staging/ipx/Makefile +0 −8
  173. drivers/staging/ipx/TODO +0 −4
  174. drivers/staging/ipx/af_ipx.c +0 −2082
  175. drivers/staging/ipx/ipx_proc.c +0 −303
  176. drivers/staging/ipx/ipx_route.c +0 −293
  177. drivers/staging/ipx/pe2.c +0 −36
  178. drivers/staging/ipx/sysctl_net_ipx.c +0 −40
  179. drivers/staging/ks7010/eap_packet.h +4 −72
  180. drivers/staging/ks7010/ks7010_sdio.c +368 −264
  181. drivers/staging/ks7010/ks7010_sdio.h +0 −164
  182. drivers/staging/ks7010/ks_hostif.c +431 −612
  183. drivers/staging/ks7010/ks_hostif.h +220 −245
  184. drivers/staging/ks7010/ks_wlan.h +173 −105
  185. drivers/staging/ks7010/ks_wlan_ioctl.h +1 −6
  186. drivers/staging/ks7010/ks_wlan_net.c +424 −694
  187. drivers/staging/ks7010/michael_mic.c +12 −16
  188. drivers/staging/ks7010/michael_mic.h +4 −7
  189. drivers/staging/lustre/Kconfig +0 −3
  190. drivers/staging/lustre/Makefile +0 −2
  191. drivers/staging/lustre/README.txt +0 −83
  192. drivers/staging/lustre/TODO +0 −302
  193. drivers/staging/lustre/include/linux/libcfs/curproc.h +0 −85
  194. drivers/staging/lustre/include/linux/libcfs/libcfs.h +0 −135
  195. drivers/staging/lustre/include/linux/libcfs/libcfs_cpu.h +0 −295
  196. drivers/staging/lustre/include/linux/libcfs/libcfs_crypto.h +0 −205
  197. drivers/staging/lustre/include/linux/libcfs/libcfs_debug.h +0 −167
  198. drivers/staging/lustre/include/linux/libcfs/libcfs_fail.h +0 −191
  199. drivers/staging/lustre/include/linux/libcfs/libcfs_hash.h +0 −866
  200. drivers/staging/lustre/include/linux/libcfs/libcfs_prim.h +0 −82
  201. drivers/staging/lustre/include/linux/libcfs/libcfs_private.h +0 −200
  202. drivers/staging/lustre/include/linux/libcfs/libcfs_string.h +0 −100
  203. drivers/staging/lustre/include/linux/libcfs/libcfs_time.h +0 −79
  204. drivers/staging/lustre/include/linux/libcfs/linux/libcfs.h +0 −133
  205. drivers/staging/lustre/include/linux/libcfs/linux/linux-cpu.h +0 −78
  206. drivers/staging/lustre/include/linux/libcfs/linux/linux-time.h +0 −103
  207. drivers/staging/lustre/include/linux/lnet/api.h +0 −212
  208. drivers/staging/lustre/include/linux/lnet/lib-lnet.h +0 −644
  209. drivers/staging/lustre/include/linux/lnet/lib-types.h +0 −666
  210. drivers/staging/lustre/include/linux/lnet/socklnd.h +0 −87
  211. drivers/staging/lustre/include/uapi/linux/lnet/libcfs_debug.h +0 −149
  212. drivers/staging/lustre/include/uapi/linux/lnet/libcfs_ioctl.h +0 −141
  213. drivers/staging/lustre/include/uapi/linux/lnet/lnet-dlc.h +0 −149
  214. drivers/staging/lustre/include/uapi/linux/lnet/lnet-types.h +0 −669
  215. drivers/staging/lustre/include/uapi/linux/lnet/lnetctl.h +0 −134
  216. drivers/staging/lustre/include/uapi/linux/lnet/lnetst.h +0 −556
  217. drivers/staging/lustre/include/uapi/linux/lnet/nidstr.h +0 −119
  218. drivers/staging/lustre/include/uapi/linux/lnet/socklnd.h +0 −44
  219. drivers/staging/lustre/include/uapi/linux/lustre/lustre_cfg.h +0 −261
  220. drivers/staging/lustre/include/uapi/linux/lustre/lustre_fid.h +0 −293
  221. drivers/staging/lustre/include/uapi/linux/lustre/lustre_fiemap.h +0 −72
  222. drivers/staging/lustre/include/uapi/linux/lustre/lustre_idl.h +0 −2688
  223. drivers/staging/lustre/include/uapi/linux/lustre/lustre_ioctl.h +0 −231
  224. drivers/staging/lustre/include/uapi/linux/lustre/lustre_kernelcomm.h +0 −94
  225. drivers/staging/lustre/include/uapi/linux/lustre/lustre_ostid.h +0 −236
  226. drivers/staging/lustre/include/uapi/linux/lustre/lustre_param.h +0 −94
  227. drivers/staging/lustre/include/uapi/linux/lustre/lustre_user.h +0 −1325
  228. drivers/staging/lustre/include/uapi/linux/lustre/lustre_ver.h +0 −27
  229. drivers/staging/lustre/lnet/Kconfig +0 −46
  230. drivers/staging/lustre/lnet/Makefile +0 −1
  231. drivers/staging/lustre/lnet/klnds/Makefile +0 −1
  232. drivers/staging/lustre/lnet/klnds/o2iblnd/Makefile +0 −5
  233. drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd.c +0 −2952
  234. drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd.h +0 −1038
  235. drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd_cb.c +0 −3751
  236. drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd_modparams.c +0 −287
  237. drivers/staging/lustre/lnet/klnds/socklnd/Makefile +0 −6
  238. drivers/staging/lustre/lnet/klnds/socklnd/socklnd.c +0 −2918
  239. drivers/staging/lustre/lnet/klnds/socklnd/socklnd.h +0 −705
  240. drivers/staging/lustre/lnet/klnds/socklnd/socklnd_cb.c +0 −2592
  241. drivers/staging/lustre/lnet/klnds/socklnd/socklnd_lib.c +0 −533
  242. drivers/staging/lustre/lnet/klnds/socklnd/socklnd_modparams.c +0 −184
  243. drivers/staging/lustre/lnet/klnds/socklnd/socklnd_proto.c +0 −810
  244. drivers/staging/lustre/lnet/libcfs/Makefile +0 −19
  245. drivers/staging/lustre/lnet/libcfs/debug.c +0 −458
  246. drivers/staging/lustre/lnet/libcfs/fail.c +0 −142
  247. drivers/staging/lustre/lnet/libcfs/hash.c +0 −2064
  248. drivers/staging/lustre/lnet/libcfs/libcfs_cpu.c +0 −228
  249. drivers/staging/lustre/lnet/libcfs/libcfs_lock.c +0 −152
  250. drivers/staging/lustre/lnet/libcfs/libcfs_mem.c +0 −167
  251. drivers/staging/lustre/lnet/libcfs/libcfs_string.c +0 −556
  252. drivers/staging/lustre/lnet/libcfs/linux/linux-cpu.c +0 −1079
  253. drivers/staging/lustre/lnet/libcfs/linux/linux-crypto-adler.c +0 −139
  254. drivers/staging/lustre/lnet/libcfs/linux/linux-crypto.c +0 −443
  255. drivers/staging/lustre/lnet/libcfs/linux/linux-crypto.h +0 −30
  256. drivers/staging/lustre/lnet/libcfs/linux/linux-debug.c +0 −145
  257. drivers/staging/lustre/lnet/libcfs/linux/linux-module.c +0 −197
  258. drivers/staging/lustre/lnet/libcfs/linux/linux-tracefile.c +0 −257
  259. drivers/staging/lustre/lnet/libcfs/module.c +0 −604
  260. drivers/staging/lustre/lnet/libcfs/tracefile.c +0 −1191
  261. drivers/staging/lustre/lnet/libcfs/tracefile.h +0 −263
  262. drivers/staging/lustre/lnet/lnet/Makefile +0 −10
  263. drivers/staging/lustre/lnet/lnet/acceptor.c +0 −501
  264. drivers/staging/lustre/lnet/lnet/api-ni.c +0 −2307
  265. drivers/staging/lustre/lnet/lnet/config.c +0 −1234
  266. drivers/staging/lustre/lnet/lnet/lib-eq.c +0 −426
  267. drivers/staging/lustre/lnet/lnet/lib-md.c +0 −463
  268. drivers/staging/lustre/lnet/lnet/lib-me.c +0 −274
  269. drivers/staging/lustre/lnet/lnet/lib-move.c +0 −2388
  270. drivers/staging/lustre/lnet/lnet/lib-msg.c +0 −625
  271. drivers/staging/lustre/lnet/lnet/lib-ptl.c +0 −987
  272. drivers/staging/lustre/lnet/lnet/lib-socket.c +0 −586
  273. drivers/staging/lustre/lnet/lnet/lo.c +0 −105
  274. drivers/staging/lustre/lnet/lnet/module.c +0 −223
  275. drivers/staging/lustre/lnet/lnet/net_fault.c +0 −1023
  276. drivers/staging/lustre/lnet/lnet/nidstrings.c +0 −1258
  277. drivers/staging/lustre/lnet/lnet/peer.c +0 −456
  278. drivers/staging/lustre/lnet/lnet/router.c +0 −1800
  279. drivers/staging/lustre/lnet/lnet/router_proc.c +0 −909
  280. drivers/staging/lustre/lnet/selftest/Makefile +0 −7
  281. drivers/staging/lustre/lnet/selftest/brw_test.c +0 −526
  282. drivers/staging/lustre/lnet/selftest/conctl.c +0 −799
  283. drivers/staging/lustre/lnet/selftest/conrpc.c +0 −1397
  284. drivers/staging/lustre/lnet/selftest/conrpc.h +0 −143
  285. drivers/staging/lustre/lnet/selftest/console.c +0 −2101
  286. drivers/staging/lustre/lnet/selftest/console.h +0 −244
  287. drivers/staging/lustre/lnet/selftest/framework.c +0 −1786
  288. drivers/staging/lustre/lnet/selftest/module.c +0 −165
  289. drivers/staging/lustre/lnet/selftest/ping_test.c +0 −228
  290. drivers/staging/lustre/lnet/selftest/rpc.c +0 −1682
  291. drivers/staging/lustre/lnet/selftest/rpc.h +0 −295
  292. drivers/staging/lustre/lnet/selftest/selftest.h +0 −623
  293. drivers/staging/lustre/lnet/selftest/timer.c +0 −244
  294. drivers/staging/lustre/lnet/selftest/timer.h +0 −50
  295. drivers/staging/lustre/lustre/Kconfig +0 −45
  296. drivers/staging/lustre/lustre/Makefile +0 −2
  297. drivers/staging/lustre/lustre/fid/Makefile +0 −5
  298. drivers/staging/lustre/lustre/fid/fid_internal.h +0 −47
  299. drivers/staging/lustre/lustre/fid/fid_lib.c +0 −88
  300. drivers/staging/lustre/lustre/fid/fid_request.c +0 −440
  301. drivers/staging/lustre/lustre/fid/lproc_fid.c +0 −226
  302. drivers/staging/lustre/lustre/fld/Makefile +0 −5
  303. drivers/staging/lustre/lustre/fld/fld_cache.c +0 −517
  304. drivers/staging/lustre/lustre/fld/fld_internal.h +0 −171
  305. drivers/staging/lustre/lustre/fld/fld_request.c +0 −471
  306. drivers/staging/lustre/lustre/fld/lproc_fld.c +0 −155
  307. drivers/staging/lustre/lustre/include/cl_object.h +0 −2463
  308. drivers/staging/lustre/lustre/include/interval_tree.h +0 −119
  309. drivers/staging/lustre/lustre/include/llog_swab.h +0 −67
  310. drivers/staging/lustre/lustre/include/lprocfs_status.h +0 −672
  311. drivers/staging/lustre/lustre/include/lu_object.h +0 −1335
  312. drivers/staging/lustre/lustre/include/lu_ref.h +0 −178
  313. drivers/staging/lustre/lustre/include/lustre_acl.h +0 −46
  314. drivers/staging/lustre/lustre/include/lustre_compat.h +0 −81
  315. drivers/staging/lustre/lustre/include/lustre_debug.h +0 −52
  316. drivers/staging/lustre/lustre/include/lustre_disk.h +0 −153
  317. drivers/staging/lustre/lustre/include/lustre_dlm.h +0 −1354
  318. drivers/staging/lustre/lustre/include/lustre_dlm_flags.h +0 −402
  319. drivers/staging/lustre/lustre/include/lustre_errno.h +0 −198
  320. drivers/staging/lustre/lustre/include/lustre_export.h +0 −257
  321. drivers/staging/lustre/lustre/include/lustre_fid.h +0 −676
  322. drivers/staging/lustre/lustre/include/lustre_fld.h +0 −138
  323. drivers/staging/lustre/lustre/include/lustre_ha.h +0 −61
  324. drivers/staging/lustre/lustre/include/lustre_handles.h +0 −93
  325. drivers/staging/lustre/lustre/include/lustre_import.h +0 −368
  326. drivers/staging/lustre/lustre/include/lustre_intent.h +0 −69
  327. drivers/staging/lustre/lustre/include/lustre_kernelcomm.h +0 −56
  328. drivers/staging/lustre/lustre/include/lustre_lib.h +0 −124
  329. drivers/staging/lustre/lustre/include/lustre_linkea.h +0 −93
  330. drivers/staging/lustre/lustre/include/lustre_lmv.h +0 −174
  331. drivers/staging/lustre/lustre/include/lustre_log.h +0 −382
  332. drivers/staging/lustre/lustre/include/lustre_mdc.h +0 −229
  333. drivers/staging/lustre/lustre/include/lustre_mds.h +0 −63
  334. drivers/staging/lustre/lustre/include/lustre_net.h +0 −2359
  335. drivers/staging/lustre/lustre/include/lustre_nrs.h +0 −718
  336. drivers/staging/lustre/lustre/include/lustre_nrs_fifo.h +0 −71
  337. drivers/staging/lustre/lustre/include/lustre_obdo.h +0 −55
  338. drivers/staging/lustre/lustre/include/lustre_patchless_compat.h +0 −67
  339. drivers/staging/lustre/lustre/include/lustre_req_layout.h +0 −307
  340. drivers/staging/lustre/lustre/include/lustre_sec.h +0 −1070
  341. drivers/staging/lustre/lustre/include/lustre_swab.h +0 −109
  342. drivers/staging/lustre/lustre/include/obd.h +0 −1101
  343. drivers/staging/lustre/lustre/include/obd_cksum.h +0 −153
  344. drivers/staging/lustre/lustre/include/obd_class.h +0 −1607
  345. drivers/staging/lustre/lustre/include/obd_support.h +0 −545
  346. drivers/staging/lustre/lustre/include/seq_range.h +0 −200
  347. drivers/staging/lustre/lustre/ldlm/interval_tree.c +0 −599
  348. drivers/staging/lustre/lustre/ldlm/l_lock.c +0 −74
  349. drivers/staging/lustre/lustre/ldlm/ldlm_extent.c +0 −259
  350. drivers/staging/lustre/lustre/ldlm/ldlm_flock.c +0 −495
  351. drivers/staging/lustre/lustre/ldlm/ldlm_inodebits.c +0 −69
  352. drivers/staging/lustre/lustre/ldlm/ldlm_internal.h +0 −342
  353. drivers/staging/lustre/lustre/ldlm/ldlm_lib.c +0 −843
  354. drivers/staging/lustre/lustre/ldlm/ldlm_lock.c +0 −2146
  355. drivers/staging/lustre/lustre/ldlm/ldlm_lockd.c +0 −1163
  356. drivers/staging/lustre/lustre/ldlm/ldlm_plain.c +0 −68
  357. drivers/staging/lustre/lustre/ldlm/ldlm_pool.c +0 −1023
  358. drivers/staging/lustre/lustre/ldlm/ldlm_request.c +0 −2080
  359. drivers/staging/lustre/lustre/ldlm/ldlm_resource.c +0 −1369
  360. drivers/staging/lustre/lustre/llite/Makefile +0 −11
  361. drivers/staging/lustre/lustre/llite/dcache.c +0 −300
  362. drivers/staging/lustre/lustre/llite/dir.c +0 −1706
  363. drivers/staging/lustre/lustre/llite/file.c +0 −3600
  364. drivers/staging/lustre/lustre/llite/glimpse.c +0 −206
  365. drivers/staging/lustre/lustre/llite/lcommon_cl.c +0 −293
  366. drivers/staging/lustre/lustre/llite/lcommon_misc.c +0 −186
  367. drivers/staging/lustre/lustre/llite/llite_internal.h +0 −1337
  368. drivers/staging/lustre/lustre/llite/llite_lib.c +0 −2666
  369. drivers/staging/lustre/lustre/llite/llite_mmap.c +0 −478
  370. drivers/staging/lustre/lustre/llite/llite_nfs.c +0 −375
  371. drivers/staging/lustre/lustre/llite/lproc_llite.c +0 −1684
  372. drivers/staging/lustre/lustre/llite/namei.c +0 −1202
  373. drivers/staging/lustre/lustre/llite/range_lock.c +0 −240
  374. drivers/staging/lustre/lustre/llite/range_lock.h +0 −83
  375. drivers/staging/lustre/lustre/llite/rw.c +0 −1214
  376. drivers/staging/lustre/lustre/llite/rw26.c +0 −641
  377. drivers/staging/lustre/lustre/llite/statahead.c +0 −1577
  378. drivers/staging/lustre/lustre/llite/super25.c +0 −185
  379. drivers/staging/lustre/lustre/llite/symlink.c +0 −159
  380. drivers/staging/lustre/lustre/llite/vvp_dev.c +0 −659
  381. drivers/staging/lustre/lustre/llite/vvp_internal.h +0 −321
  382. drivers/staging/lustre/lustre/llite/vvp_io.c +0 −1374
  383. drivers/staging/lustre/lustre/llite/vvp_lock.c +0 −87
  384. drivers/staging/lustre/lustre/llite/vvp_object.c +0 −305
  385. drivers/staging/lustre/lustre/llite/vvp_page.c +0 −523
  386. drivers/staging/lustre/lustre/llite/xattr.c +0 −638
  387. drivers/staging/lustre/lustre/llite/xattr_cache.c +0 −523
  388. drivers/staging/lustre/lustre/llite/xattr_security.c +0 −96
  389. drivers/staging/lustre/lustre/lmv/Makefile +0 −5
  390. drivers/staging/lustre/lustre/lmv/lmv_fld.c +0 −82
  391. drivers/staging/lustre/lustre/lmv/lmv_intent.c +0 −517
  392. drivers/staging/lustre/lustre/lmv/lmv_internal.h +0 −164
  393. drivers/staging/lustre/lustre/lmv/lmv_obd.c +0 −3131
  394. drivers/staging/lustre/lustre/lmv/lproc_lmv.c +0 −173
  395. drivers/staging/lustre/lustre/lov/Makefile +0 −9
  396. drivers/staging/lustre/lustre/lov/lov_cl_internal.h +0 −641
  397. drivers/staging/lustre/lustre/lov/lov_dev.c +0 −384
  398. drivers/staging/lustre/lustre/lov/lov_ea.c +0 −332
  399. drivers/staging/lustre/lustre/lov/lov_internal.h +0 −283
  400. drivers/staging/lustre/lustre/lov/lov_io.c +0 −1023
  401. drivers/staging/lustre/lustre/lov/lov_lock.c +0 −348
  402. drivers/staging/lustre/lustre/lov/lov_merge.c +0 −107
  403. drivers/staging/lustre/lustre/lov/lov_obd.c +0 −1448
  404. drivers/staging/lustre/lustre/lov/lov_object.c +0 −1625
  405. drivers/staging/lustre/lustre/lov/lov_offset.c +0 −271
  406. drivers/staging/lustre/lustre/lov/lov_pack.c +0 −400
  407. drivers/staging/lustre/lustre/lov/lov_page.c +0 −136
  408. drivers/staging/lustre/lustre/lov/lov_pool.c +0 −586
  409. drivers/staging/lustre/lustre/lov/lov_request.c +0 −356
  410. drivers/staging/lustre/lustre/lov/lovsub_dev.c +0 −147
  411. drivers/staging/lustre/lustre/lov/lovsub_lock.c +0 −81
  412. drivers/staging/lustre/lustre/lov/lovsub_object.c +0 −180
  413. drivers/staging/lustre/lustre/lov/lovsub_page.c +0 −68
  414. drivers/staging/lustre/lustre/lov/lproc_lov.c +0 −299
  415. drivers/staging/lustre/lustre/mdc/Makefile +0 −5
  416. drivers/staging/lustre/lustre/mdc/lproc_mdc.c +0 −231
  417. drivers/staging/lustre/lustre/mdc/mdc_internal.h +0 −144
  418. drivers/staging/lustre/lustre/mdc/mdc_lib.c +0 −497
  419. drivers/staging/lustre/lustre/mdc/mdc_locks.c +0 −1202
  420. drivers/staging/lustre/lustre/mdc/mdc_reint.c +0 −419
  421. drivers/staging/lustre/lustre/mdc/mdc_request.c +0 −2754
  422. drivers/staging/lustre/lustre/mgc/Makefile +0 −5
  423. drivers/staging/lustre/lustre/mgc/lproc_mgc.c +0 −69
  424. drivers/staging/lustre/lustre/mgc/mgc_internal.h +0 −58
  425. drivers/staging/lustre/lustre/mgc/mgc_request.c +0 −1844
  426. drivers/staging/lustre/lustre/obdclass/Makefile +0 −12
  427. drivers/staging/lustre/lustre/obdclass/cl_internal.h +0 −95
  428. drivers/staging/lustre/lustre/obdclass/cl_io.c +0 −1152
  429. drivers/staging/lustre/lustre/obdclass/cl_lock.c +0 −275
  430. drivers/staging/lustre/lustre/obdclass/cl_object.c +0 −1061
  431. drivers/staging/lustre/lustre/obdclass/cl_page.c +0 −1046
  432. drivers/staging/lustre/lustre/obdclass/class_obd.c +0 −535
  433. drivers/staging/lustre/lustre/obdclass/debug.c +0 −96
  434. drivers/staging/lustre/lustre/obdclass/genops.c +0 −1514
  435. drivers/staging/lustre/lustre/obdclass/kernelcomm.c +0 −238
  436. drivers/staging/lustre/lustre/obdclass/linkea.c +0 −249
  437. drivers/staging/lustre/lustre/obdclass/linux/linux-module.c +0 −531
  438. drivers/staging/lustre/lustre/obdclass/linux/linux-sysctl.c +0 −162
  439. drivers/staging/lustre/lustre/obdclass/llog.c +0 −523
  440. drivers/staging/lustre/lustre/obdclass/llog_cat.c +0 −236
  441. drivers/staging/lustre/lustre/obdclass/llog_internal.h +0 −79
  442. drivers/staging/lustre/lustre/obdclass/llog_obd.c +0 −225
  443. drivers/staging/lustre/lustre/obdclass/llog_swab.c +0 −412
  444. drivers/staging/lustre/lustre/obdclass/lprocfs_counters.c +0 −133
  445. drivers/staging/lustre/lustre/obdclass/lprocfs_status.c +0 −1810
  446. drivers/staging/lustre/lustre/obdclass/lu_object.c +0 −2058
  447. drivers/staging/lustre/lustre/obdclass/lu_ref.c +0 −47
  448. drivers/staging/lustre/lustre/obdclass/lustre_handles.c +0 −240
  449. drivers/staging/lustre/lustre/obdclass/lustre_peer.c +0 −214
  450. drivers/staging/lustre/lustre/obdclass/obd_config.c +0 −1559
  451. drivers/staging/lustre/lustre/obdclass/obd_mount.c +0 −1244
  452. drivers/staging/lustre/lustre/obdclass/obdo.c +0 −181
  453. drivers/staging/lustre/lustre/obdclass/statfs_pack.c +0 −58
  454. drivers/staging/lustre/lustre/obdclass/uuid.c +0 −47
  455. drivers/staging/lustre/lustre/obdecho/Makefile +0 −5
  456. drivers/staging/lustre/lustre/obdecho/echo_client.c +0 −1724
  457. drivers/staging/lustre/lustre/obdecho/echo_internal.h +0 −42
  458. drivers/staging/lustre/lustre/osc/Makefile +0 −6
  459. drivers/staging/lustre/lustre/osc/lproc_osc.c +0 −843
  460. drivers/staging/lustre/lustre/osc/osc_cache.c +0 −3306
  461. drivers/staging/lustre/lustre/osc/osc_cl_internal.h +0 −683
  462. drivers/staging/lustre/lustre/osc/osc_dev.c +0 −246
  463. drivers/staging/lustre/lustre/osc/osc_internal.h +0 −236
  464. drivers/staging/lustre/lustre/osc/osc_io.c +0 −918
  465. drivers/staging/lustre/lustre/osc/osc_lock.c +0 −1231
  466. drivers/staging/lustre/lustre/osc/osc_object.c +0 −474
  467. drivers/staging/lustre/lustre/osc/osc_page.c +0 −1094
  468. drivers/staging/lustre/lustre/osc/osc_quota.c +0 −284
  469. drivers/staging/lustre/lustre/osc/osc_request.c +0 −2899
  470. drivers/staging/lustre/lustre/ptlrpc/Makefile +0 −23
  471. drivers/staging/lustre/lustre/ptlrpc/client.c +0 −3269
  472. drivers/staging/lustre/lustre/ptlrpc/connection.c +0 −234
  473. drivers/staging/lustre/lustre/ptlrpc/errno.c +0 −381
  474. drivers/staging/lustre/lustre/ptlrpc/events.c +0 −585
  475. drivers/staging/lustre/lustre/ptlrpc/import.c +0 −1676
  476. drivers/staging/lustre/lustre/ptlrpc/layout.c +0 −2234
  477. drivers/staging/lustre/lustre/ptlrpc/llog_client.c +0 −340
  478. drivers/staging/lustre/lustre/ptlrpc/llog_net.c +0 −69
  479. drivers/staging/lustre/lustre/ptlrpc/lproc_ptlrpc.c +0 −1332
  480. drivers/staging/lustre/lustre/ptlrpc/niobuf.c +0 −770
  481. drivers/staging/lustre/lustre/ptlrpc/nrs.c +0 −1612
  482. drivers/staging/lustre/lustre/ptlrpc/nrs_fifo.c +0 −269
  483. drivers/staging/lustre/lustre/ptlrpc/pack_generic.c +0 −2313
  484. drivers/staging/lustre/lustre/ptlrpc/pers.c +0 −72
  485. drivers/staging/lustre/lustre/ptlrpc/pinger.c +0 −477
  486. drivers/staging/lustre/lustre/ptlrpc/ptlrpc_internal.h +0 −371
  487. drivers/staging/lustre/lustre/ptlrpc/ptlrpc_module.c +0 −182
  488. drivers/staging/lustre/lustre/ptlrpc/ptlrpcd.c +0 −912
  489. drivers/staging/lustre/lustre/ptlrpc/recover.c +0 −374
  490. drivers/staging/lustre/lustre/ptlrpc/sec.c +0 −2383
  491. drivers/staging/lustre/lustre/ptlrpc/sec_bulk.c +0 −572
  492. drivers/staging/lustre/lustre/ptlrpc/sec_config.c +0 −850
  493. drivers/staging/lustre/lustre/ptlrpc/sec_gc.c +0 −190
  494. drivers/staging/lustre/lustre/ptlrpc/sec_lproc.c +0 −195
  495. drivers/staging/lustre/lustre/ptlrpc/sec_null.c +0 −459
  496. drivers/staging/lustre/lustre/ptlrpc/sec_plain.c +0 −1023
  497. drivers/staging/lustre/lustre/ptlrpc/service.c +0 −2804
  498. drivers/staging/lustre/lustre/ptlrpc/wiretest.c +0 −4210
  499. drivers/staging/lustre/sysfs-fs-lustre +0 −654
  500. drivers/staging/most/cdev/cdev.c +10 −6
  501. drivers/staging/most/core.c +48 −20
  502. drivers/staging/most/core.h +4 −0
  503. drivers/staging/most/dim2/Kconfig +1 −1
  504. drivers/staging/most/dim2/dim2.c +296 −101
  505. drivers/staging/most/dim2/dim2.h +0 −21
  506. drivers/staging/most/dim2/hal.c +6 −3
  507. drivers/staging/most/dim2/reg.h +42 −42
  508. drivers/staging/most/i2c/i2c.c +49 −91
  509. drivers/staging/most/sound/sound.c +63 −60
  510. drivers/staging/most/usb/usb.c +42 −13
  511. drivers/staging/most/video/video.c +0 −32
  512. drivers/staging/mt7621-dts/gbpc1.dts +1 −2
  513. drivers/staging/mt7621-dts/mt7621.dtsi +15 −9
  514. drivers/staging/mt7621-eth/ethtool.c +39 −15
  515. drivers/staging/mt7621-eth/gsw_mt7620.h +2 −2
  516. drivers/staging/mt7621-eth/gsw_mt7621.c +5 −5
  517. drivers/staging/mt7621-eth/mdio.c +5 −1
  518. drivers/staging/mt7621-eth/mtk_eth_soc.c +20 −24
  519. drivers/staging/mt7621-eth/mtk_eth_soc.h +14 −19
  520. drivers/staging/mt7621-eth/soc_mt7621.c +4 −3
  521. drivers/staging/mt7621-gpio/TODO +0 −2
  522. drivers/staging/mt7621-gpio/gpio-mt7621.c +109 −91
  523. drivers/staging/mt7621-gpio/mediatek,mt7621-gpio.txt +68 −0
  524. drivers/staging/mt7621-mmc/board.h +4 −78
  525. drivers/staging/mt7621-mmc/dbg.c +179 −219
  526. drivers/staging/mt7621-mmc/dbg.h +48 −49
  527. drivers/staging/mt7621-mmc/mt6575_sd.h +536 −551
  528. drivers/staging/mt7621-mmc/sd.c +1920 −2538
  529. drivers/staging/mt7621-pci/pci-mt7621.c +170 −311
  530. drivers/staging/mt7621-pinctrl/pinctrl-rt2880.c +0 −1
  531. drivers/staging/mt7621-spi/spi-mt7621.c +0 −4
  532. drivers/staging/ncpfs/Kconfig +0 −108
  533. drivers/staging/ncpfs/Makefile +0 −17
  534. drivers/staging/ncpfs/TODO +0 −4
  535. drivers/staging/ncpfs/dir.c +0 −1220
  536. drivers/staging/ncpfs/file.c +0 −263
  537. drivers/staging/ncpfs/getopt.c +0 −76
  538. drivers/staging/ncpfs/getopt.h +0 −17
  539. drivers/staging/ncpfs/inode.c +0 −1067
  540. drivers/staging/ncpfs/ioctl.c +0 −923
  541. drivers/staging/ncpfs/mmap.c +0 −125
  542. drivers/staging/ncpfs/ncp_fs.h +0 −101
  543. drivers/staging/ncpfs/ncp_fs_i.h +0 −31
  544. drivers/staging/ncpfs/ncp_fs_sb.h +0 −174
  545. drivers/staging/ncpfs/ncplib_kernel.c +0 −1326
  546. drivers/staging/ncpfs/ncplib_kernel.h +0 −215
  547. drivers/staging/ncpfs/ncpsign_kernel.c +0 −128
  548. drivers/staging/ncpfs/ncpsign_kernel.h +0 −27
  549. drivers/staging/ncpfs/sock.c +0 −855
  550. drivers/staging/ncpfs/symlink.c +0 −182
  551. drivers/staging/nvec/nvec.c +29 −52
  552. drivers/staging/nvec/nvec.h +1 −1
  553. drivers/staging/olpc_dcon/TODO +4 −0
  554. drivers/staging/pi433/Documentation/devicetree/pi433.txt +3 −3
  555. drivers/staging/pi433/Documentation/pi433.txt +5 −5
  556. drivers/staging/pi433/Kconfig +1 −1
  557. drivers/staging/pi433/pi433_if.c +26 −13
  558. drivers/staging/pi433/rf69.c +129 −53
  559. drivers/staging/pi433/rf69.h +19 −9
  560. drivers/staging/rtl8188eu/TODO +0 −5
  561. drivers/staging/rtl8188eu/core/rtw_ap.c +36 −36
  562. drivers/staging/rtl8188eu/core/rtw_cmd.c +13 −13
  563. drivers/staging/rtl8188eu/core/rtw_ieee80211.c +10 −10
  564. drivers/staging/rtl8188eu/core/rtw_ioctl_set.c +1 −1
  565. drivers/staging/rtl8188eu/core/rtw_mlme.c +19 −19
  566. drivers/staging/rtl8188eu/core/rtw_mlme_ext.c +50 −50
  567. drivers/staging/rtl8188eu/core/rtw_wlan_util.c +17 −17
  568. drivers/staging/rtl8188eu/hal/rtl8188e_cmd.c +8 −8
  569. drivers/staging/rtl8188eu/include/wlan_bssdef.h +5 −5
  570. drivers/staging/rtl8188eu/os_dep/ioctl_linux.c +6 −6
  571. drivers/staging/rtl8188eu/os_dep/recv_linux.c +0 −4
  572. drivers/staging/rtl8192e/dot11d.c +1 −1
  573. drivers/staging/rtl8192e/rtllib_tx.c +7 −7
  574. drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_ccmp.c +1 −1
  575. drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c +1 −1
  576. drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_wep.c +1 −1
  577. drivers/staging/rtl8192u/ieee80211/ieee80211_softmac.c +1 −1
  578. drivers/staging/rtl8192u/ieee80211/rtl819x_HTProc.c +204 −263
  579. drivers/staging/rtl8192u/r8192U_core.c +1 −1
  580. drivers/staging/rtl8192u/r8192U_dm.c +2 −2
  581. drivers/staging/rtl8723bs/Makefile +1 −1
  582. drivers/staging/rtl8723bs/core/rtw_ap.c +1 −9
  583. drivers/staging/rtl8723bs/core/rtw_btcoex.c +1 −9
  584. drivers/staging/rtl8723bs/core/rtw_cmd.c +1 −9
  585. drivers/staging/rtl8723bs/core/rtw_debug.c +1 −9
  586. drivers/staging/rtl8723bs/core/rtw_eeprom.c +1 −9
  587. drivers/staging/rtl8723bs/core/rtw_efuse.c +1 −9
  588. drivers/staging/rtl8723bs/core/rtw_ieee80211.c +1 −9
  589. drivers/staging/rtl8723bs/core/rtw_io.c +1 −9
  590. drivers/staging/rtl8723bs/core/rtw_ioctl_set.c +1 −9
  591. drivers/staging/rtl8723bs/core/rtw_mlme.c +1 −9
  592. drivers/staging/rtl8723bs/core/rtw_mlme_ext.c +1 −9
  593. drivers/staging/rtl8723bs/core/rtw_odm.c +1 −9
  594. drivers/staging/rtl8723bs/core/rtw_pwrctrl.c +1 −9
  595. drivers/staging/rtl8723bs/core/rtw_recv.c +1 −9
  596. drivers/staging/rtl8723bs/core/rtw_rf.c +1 −9
  597. drivers/staging/rtl8723bs/core/rtw_security.c +1 −9
  598. drivers/staging/rtl8723bs/core/rtw_sta_mgt.c +1 −9
  599. drivers/staging/rtl8723bs/core/rtw_wlan_util.c +1 −9
  600. drivers/staging/rtl8723bs/core/rtw_xmit.c +1 −9
  601. drivers/staging/rtl8723bs/hal/HalBtc8723b1Ant.c +1 −9
  602. drivers/staging/rtl8723bs/hal/HalBtc8723b1Ant.h +1 −9
  603. drivers/staging/rtl8723bs/hal/HalBtc8723b2Ant.c +2 −10
  604. drivers/staging/rtl8723bs/hal/HalBtc8723b2Ant.h +1 −9
  605. drivers/staging/rtl8723bs/hal/HalBtcOutSrc.h +1 −9
  606. drivers/staging/rtl8723bs/hal/HalHWImg8723B_BB.c +1 −9
  607. drivers/staging/rtl8723bs/hal/HalHWImg8723B_BB.h +1 −9
  608. drivers/staging/rtl8723bs/hal/HalHWImg8723B_MAC.c +1 −9
  609. drivers/staging/rtl8723bs/hal/HalHWImg8723B_MAC.h +1 −9
  610. drivers/staging/rtl8723bs/hal/HalHWImg8723B_RF.c +1 −9
  611. drivers/staging/rtl8723bs/hal/HalHWImg8723B_RF.h +1 −9
  612. drivers/staging/rtl8723bs/hal/HalPhyRf.c +1 −9
  613. drivers/staging/rtl8723bs/hal/HalPhyRf.h +1 −9
  614. drivers/staging/rtl8723bs/hal/HalPhyRf_8723B.c +1 −9
  615. drivers/staging/rtl8723bs/hal/HalPhyRf_8723B.h +1 −9
  616. drivers/staging/rtl8723bs/hal/HalPwrSeqCmd.c +1 −9
  617. drivers/staging/rtl8723bs/hal/Mp_Precomp.h +1 −9
  618. drivers/staging/rtl8723bs/hal/hal_btcoex.c +1 −9
  619. drivers/staging/rtl8723bs/hal/hal_com.c +1 −9
  620. drivers/staging/rtl8723bs/hal/hal_com_phycfg.c +1 −9
  621. drivers/staging/rtl8723bs/hal/hal_intf.c +1 −9
  622. drivers/staging/rtl8723bs/hal/hal_phy.c +1 −9
  623. drivers/staging/rtl8723bs/hal/hal_pwr_seq.c +2 −10
  624. drivers/staging/rtl8723bs/hal/hal_sdio.c +1 −9
  625. drivers/staging/rtl8723bs/hal/odm.c +1 −9
  626. drivers/staging/rtl8723bs/hal/odm.h +1 −9
  627. drivers/staging/rtl8723bs/hal/odm_AntDiv.c +1 −9
  628. drivers/staging/rtl8723bs/hal/odm_AntDiv.h +1 −9
  629. drivers/staging/rtl8723bs/hal/odm_CfoTracking.c +1 −9
  630. drivers/staging/rtl8723bs/hal/odm_CfoTracking.h +1 −9
  631. drivers/staging/rtl8723bs/hal/odm_DIG.c +1 −9
  632. drivers/staging/rtl8723bs/hal/odm_DIG.h +1 −9
  633. drivers/staging/rtl8723bs/hal/odm_DynamicBBPowerSaving.c +1 −9
  634. drivers/staging/rtl8723bs/hal/odm_DynamicBBPowerSaving.h +1 −9
  635. drivers/staging/rtl8723bs/hal/odm_DynamicTxPower.c +1 −9
  636. drivers/staging/rtl8723bs/hal/odm_DynamicTxPower.h +1 −9
  637. drivers/staging/rtl8723bs/hal/odm_EdcaTurboCheck.c +1 −9
  638. drivers/staging/rtl8723bs/hal/odm_EdcaTurboCheck.h +1 −9
  639. drivers/staging/rtl8723bs/hal/odm_HWConfig.c +1 −9
  640. drivers/staging/rtl8723bs/hal/odm_HWConfig.h +1 −9
  641. drivers/staging/rtl8723bs/hal/odm_NoiseMonitor.c +1 −9
  642. drivers/staging/rtl8723bs/hal/odm_NoiseMonitor.h +1 −9
  643. drivers/staging/rtl8723bs/hal/odm_PathDiv.c +1 −9
  644. drivers/staging/rtl8723bs/hal/odm_PathDiv.h +1 −9
  645. drivers/staging/rtl8723bs/hal/odm_RTL8723B.c +1 −9
  646. drivers/staging/rtl8723bs/hal/odm_RTL8723B.h +1 −9
  647. drivers/staging/rtl8723bs/hal/odm_RegConfig8723B.c +1 −9
  648. drivers/staging/rtl8723bs/hal/odm_RegConfig8723B.h +1 −9
  649. drivers/staging/rtl8723bs/hal/odm_RegDefine11N.h +1 −9
  650. drivers/staging/rtl8723bs/hal/odm_debug.c +1 −9
  651. drivers/staging/rtl8723bs/hal/odm_debug.h +1 −9
  652. drivers/staging/rtl8723bs/hal/odm_interface.h +1 −9
  653. drivers/staging/rtl8723bs/hal/odm_precomp.h +1 −9
  654. drivers/staging/rtl8723bs/hal/odm_reg.h +1 −9
  655. drivers/staging/rtl8723bs/hal/odm_types.h +1 −9
  656. drivers/staging/rtl8723bs/hal/rtl8723b_cmd.c +1 −9
  657. drivers/staging/rtl8723bs/hal/rtl8723b_dm.c +1 −9
  658. drivers/staging/rtl8723bs/hal/rtl8723b_hal_init.c +16 −24
  659. drivers/staging/rtl8723bs/hal/rtl8723b_phycfg.c +1 −9
  660. drivers/staging/rtl8723bs/hal/rtl8723b_rf6052.c +1 −9
  661. drivers/staging/rtl8723bs/hal/rtl8723b_rxdesc.c +1 −9
  662. drivers/staging/rtl8723bs/hal/rtl8723bs_recv.c +1 −9
  663. drivers/staging/rtl8723bs/hal/rtl8723bs_xmit.c +1 −9
  664. drivers/staging/rtl8723bs/hal/sdio_halinit.c +1 −9
  665. drivers/staging/rtl8723bs/hal/sdio_ops.c +1 −9
  666. drivers/staging/rtl8723bs/include/Hal8192CPhyReg.h +1 −9
  667. drivers/staging/rtl8723bs/include/HalPwrSeqCmd.h +1 −9
  668. drivers/staging/rtl8723bs/include/HalVerDef.h +1 −9
  669. drivers/staging/rtl8723bs/include/autoconf.h +1 −9
  670. drivers/staging/rtl8723bs/include/basic_types.h +1 −9
  671. drivers/staging/rtl8723bs/include/cmd_osdep.h +1 −9
  672. drivers/staging/rtl8723bs/include/drv_conf.h +1 −9
  673. drivers/staging/rtl8723bs/include/drv_types.h +1 −9
  674. drivers/staging/rtl8723bs/include/drv_types_sdio.h +1 −9
  675. drivers/staging/rtl8723bs/include/ethernet.h +1 −9
  676. drivers/staging/rtl8723bs/include/hal_btcoex.h +1 −9
  677. drivers/staging/rtl8723bs/include/hal_com.h +1 −9
  678. drivers/staging/rtl8723bs/include/hal_com_h2c.h +1 −9
  679. drivers/staging/rtl8723bs/include/hal_com_phycfg.h +1 −9
  680. drivers/staging/rtl8723bs/include/hal_com_reg.h +1 −9
  681. drivers/staging/rtl8723bs/include/hal_data.h +1 −9
  682. drivers/staging/rtl8723bs/include/hal_intf.h +1 −9
  683. drivers/staging/rtl8723bs/include/hal_pg.h +1 −9
  684. drivers/staging/rtl8723bs/include/hal_phy.h +1 −9
  685. drivers/staging/rtl8723bs/include/hal_phy_cfg.h +1 −9
  686. drivers/staging/rtl8723bs/include/hal_phy_reg.h +1 −9
  687. drivers/staging/rtl8723bs/include/hal_phy_reg_8723b.h +1 −9
  688. drivers/staging/rtl8723bs/include/hal_pwr_seq.h +0 −0
  689. drivers/staging/rtl8723bs/include/hal_sdio.h +1 −9
  690. drivers/staging/rtl8723bs/include/ieee80211.h +1 −9
  691. drivers/staging/rtl8723bs/include/ioctl_cfg80211.h +1 −9
  692. drivers/staging/rtl8723bs/include/mlme_osdep.h +1 −9
  693. drivers/staging/rtl8723bs/include/osdep_intf.h +1 −9
  694. drivers/staging/rtl8723bs/include/osdep_service.h +1 −9
  695. drivers/staging/rtl8723bs/include/osdep_service_linux.h +1 −9
  696. drivers/staging/rtl8723bs/include/recv_osdep.h +1 −9
  697. drivers/staging/rtl8723bs/include/rtl8192c_recv.h +1 −9
  698. drivers/staging/rtl8723bs/include/rtl8192c_rf.h +1 −9
  699. drivers/staging/rtl8723bs/include/rtl8723b_cmd.h +1 −9
  700. drivers/staging/rtl8723bs/include/rtl8723b_dm.h +1 −9
  701. drivers/staging/rtl8723bs/include/rtl8723b_hal.h +151 −132
  702. drivers/staging/rtl8723bs/include/rtl8723b_recv.h +1 −9
  703. drivers/staging/rtl8723bs/include/rtl8723b_rf.h +1 −9
  704. drivers/staging/rtl8723bs/include/rtl8723b_spec.h +1 −9
  705. drivers/staging/rtl8723bs/include/rtl8723b_xmit.h +1 −9
  706. drivers/staging/rtl8723bs/include/rtw_ap.h +1 −9
  707. drivers/staging/rtl8723bs/include/rtw_beamforming.h +1 −9
  708. drivers/staging/rtl8723bs/include/rtw_br_ext.h +1 −9
  709. drivers/staging/rtl8723bs/include/rtw_btcoex.h +1 −9
  710. drivers/staging/rtl8723bs/include/rtw_byteorder.h +1 −9
  711. drivers/staging/rtl8723bs/include/rtw_cmd.h +1 −9
  712. drivers/staging/rtl8723bs/include/rtw_debug.h +1 −9
  713. drivers/staging/rtl8723bs/include/rtw_eeprom.h +1 −9
  714. drivers/staging/rtl8723bs/include/rtw_efuse.h +1 −9
  715. drivers/staging/rtl8723bs/include/rtw_event.h +1 −9
  716. drivers/staging/rtl8723bs/include/rtw_ht.h +1 −9
  717. drivers/staging/rtl8723bs/include/rtw_io.h +1 −9
  718. drivers/staging/rtl8723bs/include/rtw_ioctl.h +1 −9
  719. drivers/staging/rtl8723bs/include/rtw_ioctl_set.h +1 −9
  720. drivers/staging/rtl8723bs/include/rtw_mlme.h +1 −9
  721. drivers/staging/rtl8723bs/include/rtw_mlme_ext.h +1 −9
  722. drivers/staging/rtl8723bs/include/rtw_mp.h +1 −9
  723. drivers/staging/rtl8723bs/include/rtw_odm.h +1 −9
  724. drivers/staging/rtl8723bs/include/rtw_pwrctrl.h +13 −22
  725. drivers/staging/rtl8723bs/include/rtw_qos.h +1 −9
  726. drivers/staging/rtl8723bs/include/rtw_recv.h +1 −9
  727. drivers/staging/rtl8723bs/include/rtw_rf.h +1 −9
  728. drivers/staging/rtl8723bs/include/rtw_security.h +1 −9
  729. drivers/staging/rtl8723bs/include/rtw_version.h +1 −0
  730. drivers/staging/rtl8723bs/include/rtw_xmit.h +1 −9
  731. drivers/staging/rtl8723bs/include/sdio_hal.h +1 −9
  732. drivers/staging/rtl8723bs/include/sdio_ops.h +1 −9
  733. drivers/staging/rtl8723bs/include/sdio_ops_linux.h +1 −9
  734. drivers/staging/rtl8723bs/include/sdio_osintf.h +1 −9
  735. drivers/staging/rtl8723bs/include/sta_info.h +1 −9
  736. drivers/staging/rtl8723bs/include/wifi.h +7 −15
  737. drivers/staging/rtl8723bs/include/wlan_bssdef.h +1 −9
  738. drivers/staging/rtl8723bs/include/xmit_osdep.h +1 −9
  739. drivers/staging/rtl8723bs/os_dep/ioctl_cfg80211.c +2 −10
  740. drivers/staging/rtl8723bs/os_dep/ioctl_linux.c +1 −9
  741. drivers/staging/rtl8723bs/os_dep/mlme_linux.c +1 −9
  742. drivers/staging/rtl8723bs/os_dep/os_intfs.c +1 −9
  743. drivers/staging/rtl8723bs/os_dep/osdep_service.c +1 −9
  744. drivers/staging/rtl8723bs/os_dep/recv_linux.c +1 −9
  745. drivers/staging/rtl8723bs/os_dep/rtw_proc.c +1 −9
  746. drivers/staging/rtl8723bs/os_dep/rtw_proc.h +1 −9
  747. drivers/staging/rtl8723bs/os_dep/sdio_intf.c +1 −9
  748. drivers/staging/rtl8723bs/os_dep/sdio_ops_linux.c +1 −9
  749. drivers/staging/rtl8723bs/os_dep/xmit_linux.c +1 −9
  750. drivers/staging/rtlwifi/base.c +1 −12
  751. drivers/staging/rtlwifi/base.h +1 −12
  752. drivers/staging/rtlwifi/btcoexist/halbt_precomp.h +1 −12
  753. drivers/staging/rtlwifi/btcoexist/halbtc8822b1ant.c +1 −12
  754. drivers/staging/rtlwifi/btcoexist/halbtc8822b1ant.h +1 −12
  755. drivers/staging/rtlwifi/btcoexist/halbtc8822b2ant.c +1 −12
  756. drivers/staging/rtlwifi/btcoexist/halbtc8822b2ant.h +1 −12
  757. drivers/staging/rtlwifi/btcoexist/halbtc8822bwifionly.c +1 −12
  758. drivers/staging/rtlwifi/btcoexist/halbtc8822bwifionly.h +1 −12
  759. drivers/staging/rtlwifi/btcoexist/halbtcoutsrc.c +1 −12
  760. drivers/staging/rtlwifi/btcoexist/halbtcoutsrc.h +1 −12
  761. drivers/staging/rtlwifi/btcoexist/rtl_btc.c +1 −12
  762. drivers/staging/rtlwifi/btcoexist/rtl_btc.h +1 −12
  763. drivers/staging/rtlwifi/cam.c +1 −12
  764. drivers/staging/rtlwifi/cam.h +1 −12
  765. drivers/staging/rtlwifi/core.c +1 −12
  766. drivers/staging/rtlwifi/core.h +1 −12
  767. drivers/staging/rtlwifi/debug.c +10 −22
  768. drivers/staging/rtlwifi/debug.h +1 −12
  769. drivers/staging/rtlwifi/efuse.c +1 −12
  770. drivers/staging/rtlwifi/efuse.h +1 −12
  771. drivers/staging/rtlwifi/halmac/halmac_2_platform.h +1 −12
  772. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_cfg.h +1 −12
  773. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_phy.c +1 −12
  774. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_pwr_seq.c +1 −12
  775. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_pwr_seq.h +1 −12
  776. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b.c +1 −12
  777. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b.h +1 −12
  778. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_pcie.c +1 −12
  779. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_pcie.h +1 −12
  780. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_sdio.c +1 −12
  781. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_sdio.h +1 −12
  782. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_usb.c +1 −12
  783. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_usb.h +1 −12
  784. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_func_8822b.c +1 −12
  785. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_func_8822b.h +1 −12
  786. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_88xx_cfg.h +1 −12
  787. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx.c +1 −12
  788. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx.h +1 −12
  789. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_pcie.c +1 −12
  790. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_pcie.h +1 −12
  791. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_sdio.c +1 −12
  792. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_sdio.h +1 −12
  793. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_usb.c +1 −12
  794. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_usb.h +1 −12
  795. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_func_88xx.c +1 −12
  796. drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_func_88xx.h +1 −12
  797. drivers/staging/rtlwifi/halmac/halmac_api.c +1 −12
  798. drivers/staging/rtlwifi/halmac/halmac_api.h +1 −12
  799. drivers/staging/rtlwifi/halmac/halmac_bit2.h +1 −12
  800. drivers/staging/rtlwifi/halmac/halmac_bit_8822b.h +1 −12
  801. drivers/staging/rtlwifi/halmac/halmac_fw_info.h +1 −12
  802. drivers/staging/rtlwifi/halmac/halmac_fw_offload_c2h_nic.h +1 −12
  803. drivers/staging/rtlwifi/halmac/halmac_fw_offload_h2c_nic.h +1 −12
  804. drivers/staging/rtlwifi/halmac/halmac_h2c_extra_info_nic.h +1 −12
  805. drivers/staging/rtlwifi/halmac/halmac_intf_phy_cmd.h +1 −12
  806. drivers/staging/rtlwifi/halmac/halmac_original_c2h_nic.h +1 −12
  807. drivers/staging/rtlwifi/halmac/halmac_original_h2c_nic.h +1 −12
  808. drivers/staging/rtlwifi/halmac/halmac_pcie_reg.h +1 −12
  809. drivers/staging/rtlwifi/halmac/halmac_pwr_seq_cmd.h +1 −12
  810. drivers/staging/rtlwifi/halmac/halmac_reg2.h +1 −12
  811. drivers/staging/rtlwifi/halmac/halmac_reg_8822b.h +1 −12
  812. drivers/staging/rtlwifi/halmac/halmac_rx_bd_chip.h +1 −12
  813. drivers/staging/rtlwifi/halmac/halmac_rx_bd_nic.h +1 −12
  814. drivers/staging/rtlwifi/halmac/halmac_rx_desc_chip.h +1 −12
  815. drivers/staging/rtlwifi/halmac/halmac_rx_desc_nic.h +1 −12
  816. drivers/staging/rtlwifi/halmac/halmac_sdio_reg.h +1 −12
  817. drivers/staging/rtlwifi/halmac/halmac_tx_bd_chip.h +1 −12
  818. drivers/staging/rtlwifi/halmac/halmac_tx_bd_nic.h +1 −12
  819. drivers/staging/rtlwifi/halmac/halmac_tx_desc_chip.h +1 −12
  820. drivers/staging/rtlwifi/halmac/halmac_tx_desc_nic.h +1 −12
  821. drivers/staging/rtlwifi/halmac/halmac_type.h +1 −12
  822. drivers/staging/rtlwifi/halmac/halmac_usb_reg.h +1 −12
  823. drivers/staging/rtlwifi/halmac/rtl_halmac.c +1 −12
  824. drivers/staging/rtlwifi/halmac/rtl_halmac.h +1 −12
  825. drivers/staging/rtlwifi/pci.c +1 −12
  826. drivers/staging/rtlwifi/pci.h +1 −12
  827. drivers/staging/rtlwifi/phydm/halphyrf_ce.c +1 −12
  828. drivers/staging/rtlwifi/phydm/halphyrf_ce.h +1 −12
  829. drivers/staging/rtlwifi/phydm/mp_precomp.h +1 −12
  830. drivers/staging/rtlwifi/phydm/phydm.c +1 −12
  831. drivers/staging/rtlwifi/phydm/phydm.h +1 −12
  832. drivers/staging/rtlwifi/phydm/phydm_acs.c +1 −12
  833. drivers/staging/rtlwifi/phydm/phydm_acs.h +1 −12
  834. drivers/staging/rtlwifi/phydm/phydm_adaptivity.c +1 −12
  835. drivers/staging/rtlwifi/phydm/phydm_adaptivity.h +1 −12
  836. drivers/staging/rtlwifi/phydm/phydm_adc_sampling.c +1 −12
  837. drivers/staging/rtlwifi/phydm/phydm_adc_sampling.h +1 −12
  838. drivers/staging/rtlwifi/phydm/phydm_antdiv.c +1 −12
  839. drivers/staging/rtlwifi/phydm/phydm_antdiv.h +1 −12
  840. drivers/staging/rtlwifi/phydm/phydm_beamforming.h +1 −12
  841. drivers/staging/rtlwifi/phydm/phydm_ccx.c +1 −12
  842. drivers/staging/rtlwifi/phydm/phydm_ccx.h +1 −12
  843. drivers/staging/rtlwifi/phydm/phydm_cfotracking.c +1 −12
  844. drivers/staging/rtlwifi/phydm/phydm_cfotracking.h +1 −12
  845. drivers/staging/rtlwifi/phydm/phydm_debug.c +1 −12
  846. drivers/staging/rtlwifi/phydm/phydm_debug.h +1 −12
  847. drivers/staging/rtlwifi/phydm/phydm_dfs.h +1 −12
  848. drivers/staging/rtlwifi/phydm/phydm_dig.c +1 −12
  849. drivers/staging/rtlwifi/phydm/phydm_dig.h +1 −12
  850. drivers/staging/rtlwifi/phydm/phydm_dynamic_rx_path.h +1 −12
  851. drivers/staging/rtlwifi/phydm/phydm_dynamicbbpowersaving.c +1 −12
  852. drivers/staging/rtlwifi/phydm/phydm_dynamicbbpowersaving.h +1 −12
  853. drivers/staging/rtlwifi/phydm/phydm_dynamictxpower.c +1 −12
  854. drivers/staging/rtlwifi/phydm/phydm_dynamictxpower.h +1 −12
  855. drivers/staging/rtlwifi/phydm/phydm_edcaturbocheck.c +1 −12
  856. drivers/staging/rtlwifi/phydm/phydm_edcaturbocheck.h +1 −12
  857. drivers/staging/rtlwifi/phydm/phydm_features.h +1 −12
  858. drivers/staging/rtlwifi/phydm/phydm_hwconfig.c +1 −12
  859. drivers/staging/rtlwifi/phydm/phydm_hwconfig.h +1 −12
  860. drivers/staging/rtlwifi/phydm/phydm_interface.c +1 −12
  861. drivers/staging/rtlwifi/phydm/phydm_interface.h +1 −12
  862. drivers/staging/rtlwifi/phydm/phydm_iqk.h +1 −12
  863. drivers/staging/rtlwifi/phydm/phydm_kfree.c +1 −12
  864. drivers/staging/rtlwifi/phydm/phydm_kfree.h +1 −12
  865. drivers/staging/rtlwifi/phydm/phydm_noisemonitor.c +1 −12
  866. drivers/staging/rtlwifi/phydm/phydm_noisemonitor.h +1 −12
  867. drivers/staging/rtlwifi/phydm/phydm_powertracking_ce.c +1 −12
  868. drivers/staging/rtlwifi/phydm/phydm_powertracking_ce.h +1 −12
  869. drivers/staging/rtlwifi/phydm/phydm_pre_define.h +1 −12
  870. drivers/staging/rtlwifi/phydm/phydm_precomp.h +1 −12
  871. drivers/staging/rtlwifi/phydm/phydm_psd.c +1 −12
  872. drivers/staging/rtlwifi/phydm/phydm_psd.h +1 −12
  873. drivers/staging/rtlwifi/phydm/phydm_rainfo.c +3 −14
  874. drivers/staging/rtlwifi/phydm/phydm_rainfo.h +1 −12
  875. drivers/staging/rtlwifi/phydm/phydm_reg.h +1 −12
  876. drivers/staging/rtlwifi/phydm/phydm_regdefine11ac.h +1 −12
  877. drivers/staging/rtlwifi/phydm/phydm_regdefine11n.h +1 −12
  878. drivers/staging/rtlwifi/phydm/phydm_types.h +1 −12
  879. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_bb.c +1 −12
  880. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_bb.h +1 −12
  881. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_mac.c +1 −12
  882. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_mac.h +1 −12
  883. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_rf.c +1 −12
  884. drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_rf.h +1 −12
  885. drivers/staging/rtlwifi/phydm/rtl8822b/halphyrf_8822b.c +18 −29
  886. drivers/staging/rtlwifi/phydm/rtl8822b/halphyrf_8822b.h +1 −12
  887. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_hal_api8822b.c +1 −12
  888. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_hal_api8822b.h +1 −12
  889. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_iqk_8822b.c +1 −12
  890. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_iqk_8822b.h +1 −12
  891. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_regconfig8822b.c +1 −12
  892. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_regconfig8822b.h +1 −12
  893. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_rtl8822b.c +1 −12
  894. drivers/staging/rtlwifi/phydm/rtl8822b/phydm_rtl8822b.h +1 −12
  895. drivers/staging/rtlwifi/phydm/rtl8822b/version_rtl8822b.h +1 −12
  896. drivers/staging/rtlwifi/phydm/rtl_phydm.c +1 −12
  897. drivers/staging/rtlwifi/phydm/rtl_phydm.h +1 −12
  898. drivers/staging/rtlwifi/phydm/txbf/halcomtxbf.h +1 −12
  899. drivers/staging/rtlwifi/phydm/txbf/haltxbf8822b.h +1 −12
  900. drivers/staging/rtlwifi/phydm/txbf/haltxbfinterface.h +1 −12
  901. drivers/staging/rtlwifi/phydm/txbf/haltxbfjaguar.h +1 −12
  902. drivers/staging/rtlwifi/phydm/txbf/phydm_hal_txbf_api.h +1 −12
  903. drivers/staging/rtlwifi/ps.c +1 −12
  904. drivers/staging/rtlwifi/ps.h +1 −12
  905. drivers/staging/rtlwifi/pwrseqcmd.h +1 −12
  906. drivers/staging/rtlwifi/rc.c +1 −12
  907. drivers/staging/rtlwifi/rc.h +1 −12
  908. drivers/staging/rtlwifi/regd.c +1 −12
  909. drivers/staging/rtlwifi/regd.h +1 −12
  910. drivers/staging/rtlwifi/rtl8822be/def.h +1 −12
  911. drivers/staging/rtlwifi/rtl8822be/fw.c +1 −12
  912. drivers/staging/rtlwifi/rtl8822be/fw.h +1 −12
  913. drivers/staging/rtlwifi/rtl8822be/hw.c +1 −12
  914. drivers/staging/rtlwifi/rtl8822be/hw.h +1 −12
  915. drivers/staging/rtlwifi/rtl8822be/led.c +1 −12
  916. drivers/staging/rtlwifi/rtl8822be/led.h +1 −12
  917. drivers/staging/rtlwifi/rtl8822be/phy.c +1 −12
  918. drivers/staging/rtlwifi/rtl8822be/phy.h +1 −12
  919. drivers/staging/rtlwifi/rtl8822be/reg.h +1 −12
  920. drivers/staging/rtlwifi/rtl8822be/sw.c +1 −12
  921. drivers/staging/rtlwifi/rtl8822be/sw.h +1 −12
  922. drivers/staging/rtlwifi/rtl8822be/trx.c +1 −12
  923. drivers/staging/rtlwifi/rtl8822be/trx.h +1 −12
  924. drivers/staging/rtlwifi/stats.c +1 −12
  925. drivers/staging/rtlwifi/stats.h +1 −12
  926. drivers/staging/rtlwifi/wifi.h +1 −12
  927. drivers/staging/sm750fb/TODO +4 −1
  928. drivers/staging/speakup/buffers.c +4 −0
  929. drivers/staging/speakup/main.c +6 −0
  930. drivers/staging/speakup/speakup.h +2 −1
  931. drivers/staging/speakup/speakup_dummy.c +1 −0
  932. drivers/staging/speakup/speakup_soft.c +2 −1
  933. drivers/staging/speakup/spk_types.h +1 −1
  934. drivers/staging/speakup/varhandlers.c +1 −0
  935. drivers/staging/unisys/visornic/visornic_main.c +7 −18
  936. drivers/staging/vboxvideo/vbox_main.c +2 −1
  937. drivers/staging/vboxvideo/vbox_mode.c +1 −1
  938. drivers/staging/vc04_services/Kconfig +0 −1
  939. drivers/staging/vc04_services/Makefile +1 −1
  940. drivers/staging/vc04_services/bcm2835-audio/bcm2835-vchiq.c +38 −26
  941. drivers/staging/vc04_services/bcm2835-audio/bcm2835.c +41 −2
  942. drivers/staging/vc04_services/bcm2835-audio/bcm2835.h +12 −0
  943. drivers/staging/vc04_services/bcm2835-camera/TODO +0 −11
  944. drivers/staging/vc04_services/bcm2835-camera/bcm2835-camera.c +222 −180
  945. drivers/staging/vc04_services/bcm2835-camera/mmal-common.h +8 −1
  946. drivers/staging/vc04_services/bcm2835-camera/mmal-msg-port.h +1 −1
  947. drivers/staging/vc04_services/bcm2835-camera/mmal-parameters.h +13 −0
  948. drivers/staging/vc04_services/bcm2835-camera/mmal-vchiq.c +83 −262
  949. drivers/staging/vc04_services/bcm2835-camera/mmal-vchiq.h +3 −12
  950. drivers/staging/vc04_services/interface/vchi/TODO +2 −7
  951. drivers/staging/vc04_services/interface/vchi/vchi_common.h +0 −2
  952. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_2835_arm.c +3 −3
  953. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_arm.c +51 −45
  954. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_core.c +36 −19
  955. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_core.h +0 −1
  956. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_debugfs.c +24 −113
  957. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_debugfs.h +2 −2
  958. drivers/staging/vc04_services/interface/vchiq_arm/vchiq_shim.c +0 −1
  959. drivers/staging/vt6655/card.c +1 −4
  960. drivers/staging/vt6655/device_main.c +123 −27
  961. drivers/staging/wilc1000/TODO +4 −8
  962. drivers/staging/wilc1000/coreconfigurator.c +46 −94
  963. drivers/staging/wilc1000/coreconfigurator.h +1 −36
  964. drivers/staging/wilc1000/host_interface.c +241 −308
  965. drivers/staging/wilc1000/host_interface.h +2 −4
  966. drivers/staging/wilc1000/linux_mon.c +21 −69
  967. drivers/staging/wilc1000/linux_wlan.c +140 −238
  968. drivers/staging/wilc1000/wilc_debugfs.c +0 −2
  969. drivers/staging/wilc1000/wilc_sdio.c +52 −57
  970. drivers/staging/wilc1000/wilc_spi.c +36 −63
  971. drivers/staging/wilc1000/wilc_wfi_cfgoperations.c +524 −525
  972. drivers/staging/wilc1000/wilc_wfi_cfgoperations.h +6 −12
  973. drivers/staging/wilc1000/wilc_wfi_netdevice.h +19 −64
  974. drivers/staging/wilc1000/wilc_wlan.c +9 −17
  975. drivers/staging/wilc1000/wilc_wlan.h +15 −22
  976. drivers/staging/wilc1000/wilc_wlan_cfg.c +0 −1
  977. drivers/staging/wilc1000/wilc_wlan_if.h +4 −12
  978. drivers/staging/wlan-ng/hfa384x.h +1 −1
  979. drivers/staging/wlan-ng/hfa384x_usb.c +3 −4
  980. drivers/staging/wlan-ng/p80211conv.c +4 −4
  981. drivers/staging/wlan-ng/p80211conv.h +15 −11
  982. drivers/staging/wlan-ng/p80211hdr.h +1 −1
  983. drivers/staging/wlan-ng/p80211ioctl.h +1 −1
  984. drivers/staging/wlan-ng/p80211metadef.h +1 −1
  985. drivers/staging/wlan-ng/p80211metastruct.h +45 −45
  986. drivers/staging/wlan-ng/p80211mgmt.h +1 −1
  987. drivers/staging/wlan-ng/p80211msg.h +1 −1
  988. drivers/staging/wlan-ng/p80211netdev.c +4 −4
  989. drivers/staging/wlan-ng/p80211netdev.h +4 −4
  990. drivers/staging/wlan-ng/p80211req.h +1 −1
  991. drivers/staging/wlan-ng/p80211types.h +1 −32
  992. drivers/staging/wlan-ng/prism2mgmt.h +1 −1
  993. drivers/staging/wlan-ng/prism2sta.c +24 −28
  994. fs/compat.c +1 −71
  995. include/linux/iio/adc/ad_sigma_delta.h +17 −7
  996. include/linux/iio/adc/stm32-dfsdm-adc.h +2 −0
  997. include/linux/iio/common/cros_ec_sensors_core.h +3 −0
  998. include/linux/iio/iio.h +12 −12
  999. include/linux/kernel.h +16 −0
  1000. include/linux/platform_data/tsl2772.h +101 −0
  1001. include/uapi/linux/ncp.h +0 −202
  1002. include/uapi/linux/ncp_fs.h +0 −147
  1003. include/uapi/linux/ncp_mount.h +0 −72
  1004. include/uapi/linux/ncp_no.h +0 −20
  1005. scripts/selinux/mdp/mdp.c +0 −1
  1006. tools/iio/iio_generic_buffer.c +8 −5
Documentation/ABI/testing/sysfs-bus-iio+9−0
@@ -190,6 +190,13 @@ Description: · 189 unmodified lines
190 but should match other such assignments on device).190 but should match other such assignments on device).
191 Units after application of scale and offset are m/s^2.191 Units after application of scale and offset are m/s^2.
192 192
193What: /sys/bus/iio/devices/iio:deviceX/in_angl_raw
194KernelVersion: 4.17
195Contact: linux-iio@vger.kernel.org
196Description:
197 Angle of rotation. Units after application of scale and offset
198 are radians.
199
193What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_x_raw200What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_x_raw
194What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_y_raw201What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_y_raw
195What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_z_raw202What: /sys/bus/iio/devices/iio:deviceX/in_anglvel_z_raw
@@ -297,6 +304,7 @@ What: /sys/bus/iio/devices/iio:deviceX/in_pressure_offset · 101 unmodified lines
297What: /sys/bus/iio/devices/iio:deviceX/in_humidityrelative_offset304What: /sys/bus/iio/devices/iio:deviceX/in_humidityrelative_offset
298What: /sys/bus/iio/devices/iio:deviceX/in_magn_offset305What: /sys/bus/iio/devices/iio:deviceX/in_magn_offset
299What: /sys/bus/iio/devices/iio:deviceX/in_rot_offset306What: /sys/bus/iio/devices/iio:deviceX/in_rot_offset
307What: /sys/bus/iio/devices/iio:deviceX/in_angl_offset
300KernelVersion: 2.6.35308KernelVersion: 2.6.35
301Contact: linux-iio@vger.kernel.org309Contact: linux-iio@vger.kernel.org
302Description:310Description:
@@ -350,6 +358,7 @@ What: /sys/bus/iio/devices/iio:deviceX/in_humidityrelative_scale · 47 unmodified lines
350What: /sys/bus/iio/devices/iio:deviceX/in_velocity_sqrt(x^2+y^2+z^2)_scale358What: /sys/bus/iio/devices/iio:deviceX/in_velocity_sqrt(x^2+y^2+z^2)_scale
351What: /sys/bus/iio/devices/iio:deviceX/in_illuminance_scale359What: /sys/bus/iio/devices/iio:deviceX/in_illuminance_scale
352What: /sys/bus/iio/devices/iio:deviceX/in_countY_scale360What: /sys/bus/iio/devices/iio:deviceX/in_countY_scale
361What: /sys/bus/iio/devices/iio:deviceX/in_angl_scale
353KernelVersion: 2.6.35362KernelVersion: 2.6.35
354Contact: linux-iio@vger.kernel.org363Contact: linux-iio@vger.kernel.org
355Description:364Description:
Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt+1−0
@@ -7,6 +7,7 @@ Required properties: · 6 unmodified lines
7 - "amlogic,meson-gxbb-saradc" for GXBB7 - "amlogic,meson-gxbb-saradc" for GXBB
8 - "amlogic,meson-gxl-saradc" for GXL8 - "amlogic,meson-gxl-saradc" for GXL
9 - "amlogic,meson-gxm-saradc" for GXM9 - "amlogic,meson-gxm-saradc" for GXM
10 - "amlogic,meson-axg-saradc" for AXG
10 along with the generic "amlogic,meson-saradc"11 along with the generic "amlogic,meson-saradc"
11- reg: the physical base address and length of the registers12- reg: the physical base address and length of the registers
12- interrupts: the interrupt indicating end of sampling13- interrupts: the interrupt indicating end of sampling
Documentation/devicetree/bindings/iio/adc/mcp320x.txt+1−1
@@ -49,7 +49,7 @@ Required properties: · 48 unmodified lines
49Examples:49Examples:
50spi_controller {50spi_controller {
51 mcp3x0x@0 {51 mcp3x0x@0 {
52 compatible = "mcp3002";52 compatible = "microchip,mcp3002";
53 reg = <0>;53 reg = <0>;
54 spi-max-frequency = <1000000>;54 spi-max-frequency = <1000000>;
55 vref-supply = <&vref_reg>;55 vref-supply = <&vref_reg>;
Documentation/devicetree/bindings/iio/adc/st,stm32-adc.txt+5−1
@@ -24,8 +24,11 @@ Required properties: · 23 unmodified lines
24- compatible: Should be one of:24- compatible: Should be one of:
25 "st,stm32f4-adc-core"25 "st,stm32f4-adc-core"
26 "st,stm32h7-adc-core"26 "st,stm32h7-adc-core"
27 "st,stm32mp1-adc-core"
27- reg: Offset and length of the ADC block register set.28- reg: Offset and length of the ADC block register set.
28- interrupts: Must contain the interrupt for ADC block.29- interrupts: One or more interrupts for ADC block. Some parts like stm32f4
30 and stm32h7 share a common ADC interrupt line. stm32mp1 has two separate
31 interrupt lines, one for each ADC within ADC block.
29- clocks: Core can use up to two clocks, depending on part used:32- clocks: Core can use up to two clocks, depending on part used:
30 - "adc" clock: for the analog circuitry, common to all ADCs.33 - "adc" clock: for the analog circuitry, common to all ADCs.
31 It's required on stm32f4.34 It's required on stm32f4.
@@ -53,6 +56,7 @@ Required properties: · 21 unmodified lines
53- compatible: Should be one of:56- compatible: Should be one of:
54 "st,stm32f4-adc"57 "st,stm32f4-adc"
55 "st,stm32h7-adc"58 "st,stm32h7-adc"
59 "st,stm32mp1-adc"
56- reg: Offset of ADC instance in ADC block (e.g. may be 0x0, 0x100, 0x200).60- reg: Offset of ADC instance in ADC block (e.g. may be 0x0, 0x100, 0x200).
57- clocks: Input clock private to this ADC instance. It's required only on61- clocks: Input clock private to this ADC instance. It's required only on
58 stm32f4, that has per instance clock input for registers access.62 stm32f4, that has per instance clock input for registers access.
Documentation/devicetree/bindings/iio/adc/st,stm32-dfsdm-adc.txt+5−2
@@ -8,14 +8,16 @@ It is mainly targeted for: · 7 unmodified lines
8- PDM microphones (audio digital microphone)8- PDM microphones (audio digital microphone)
9 9
10It features up to 8 serial digital interfaces (SPI or Manchester) and10It features up to 8 serial digital interfaces (SPI or Manchester) and
11up to 4 filters on stm32h7.11up to 4 filters on stm32h7 or 6 filters on stm32mp1.
12 12
13Each child node match with a filter instance.13Each child node match with a filter instance.
14 14
15Contents of a STM32 DFSDM root node:15Contents of a STM32 DFSDM root node:
16------------------------------------16------------------------------------
17Required properties:17Required properties:
18- compatible: Should be "st,stm32h7-dfsdm".18- compatible: Should be one of:
19 "st,stm32h7-dfsdm"
20 "st,stm32mp1-dfsdm"
19- reg: Offset and length of the DFSDM block register set.21- reg: Offset and length of the DFSDM block register set.
20- clocks: IP and serial interfaces clocking. Should be set according22- clocks: IP and serial interfaces clocking. Should be set according
21 to rcc clock ID and "clock-names".23 to rcc clock ID and "clock-names".
@@ -45,6 +47,7 @@ Required properties: · 23 unmodified lines
45 "st,stm32-dfsdm-adc" for sigma delta ADCs47 "st,stm32-dfsdm-adc" for sigma delta ADCs
46 "st,stm32-dfsdm-dmic" for audio digital microphone.48 "st,stm32-dfsdm-dmic" for audio digital microphone.
47- reg: Specifies the DFSDM filter instance used.49- reg: Specifies the DFSDM filter instance used.
50 Valid values are from 0 to 3 on stm32h7, 0 to 5 on stm32mp1.
48- interrupts: IRQ lines connected to each DFSDM filter instance.51- interrupts: IRQ lines connected to each DFSDM filter instance.
49- st,adc-channels: List of single-ended channels muxed for this ADC.52- st,adc-channels: List of single-ended channels muxed for this ADC.
50 valid values:53 valid values:
Documentation/devicetree/bindings/iio/afe/current-sense-amplifier.txt+26−0
@@ -0,0 +1,26 @@
1Current Sense Amplifier
2=======================
3
4When an io-channel measures the output voltage from a current sense
5amplifier, the interesting measurement is almost always the current
6through the sense resistor, not the voltage output. This binding
7describes such a current sense circuit.
8
9Required properties:
10- compatible : "current-sense-amplifier"
11- io-channels : Channel node of a voltage io-channel.
12- sense-resistor-micro-ohms : The sense resistance in microohms.
13
14Optional properties:
15- sense-gain-mult: Amplifier gain multiplier. The default is <1>.
16- sense-gain-div: Amplifier gain divider. The default is <1>.
17
18Example:
19
20sysi {
21 compatible = "current-sense-amplifier";
22 io-channels = <&tiadc 0>;
23
24 sense-resistor-micro-ohms = <20000>;
25 sense-gain-mul = <50>;
26};
Documentation/devicetree/bindings/iio/afe/current-sense-shunt.txt+41−0
@@ -0,0 +1,41 @@
1Current Sense Shunt
2===================
3
4When an io-channel measures the voltage over a current sense shunt,
5the interesting measurement is almost always the current through the
6shunt, not the voltage over it. This binding describes such a current
7sense circuit.
8
9Required properties:
10- compatible : "current-sense-shunt"
11- io-channels : Channel node of a voltage io-channel.
12- shunt-resistor-micro-ohms : The shunt resistance in microohms.
13
14Example:
15The system current is measured by measuring the voltage over a
163.3 ohms shunt resistor.
17
18sysi {
19 compatible = "current-sense-shunt";
20 io-channels = <&tiadc 0>;
21
22 /* Divide the voltage by 3300000/1000000 (or 3.3) for the current. */
23 shunt-resistor-micro-ohms = <3300000>;
24};
25
26&i2c {
27 tiadc: adc@48 {
28 compatible = "ti,ads1015";
29 reg = <0x48>;
30 #io-channel-cells = <1>;
31
32 #address-cells = <1>;
33 #size-cells = <0>;
34
35 channel@0 { /* IN0,IN1 differential */
36 reg = <0>;
37 ti,gain = <1>;
38 ti,datarate = <4>;
39 };
40 };
41};
Documentation/devicetree/bindings/iio/afe/voltage-divider.txt+53−0
@@ -0,0 +1,53 @@
1Voltage divider
2===============
3
4When an io-channel measures the midpoint of a voltage divider, the
5interesting voltage is often the voltage over the full resistance
6of the divider. This binding describes the voltage divider in such
7a curcuit.
8
9 Vin ----.
10 |
11 .-----.
12 | R |
13 '-----'
14 |
15 +---- Vout
16 |
17 .-----.
18 | Rout|
19 '-----'
20 |
21 GND
22
23Required properties:
24- compatible : "voltage-divider"
25- io-channels : Channel node of a voltage io-channel measuring Vout.
26- output-ohms : Resistance Rout over which the output voltage is measured.
27 See full-ohms.
28- full-ohms : Resistance R + Rout for the full divider. The io-channel
29 is scaled by the Rout / (R + Rout) quotient.
30
31Example:
32The system voltage is circa 12V, but divided down with a 22/222
33voltage divider (R = 200 Ohms, Rout = 22 Ohms) and fed to an ADC.
34
35sysv {
36 compatible = "voltage-divider";
37 io-channels = <&maxadc 1>;
38
39 /* Scale the system voltage by 22/222 to fit the ADC range. */
40 output-ohms = <22>;
41 full-ohms = <222>; /* 200 + 22 */
42};
43
44&spi {
45 maxadc: adc@0 {
46 compatible = "maxim,max1027";
47 reg = <0>;
48 #io-channel-cells = <1>;
49 interrupt-parent = <&gpio5>;
50 interrupts = <15 IRQ_TYPE_EDGE_RISING>;
51 spi-max-frequency = <1000000>;
52 };
53};
Documentation/devicetree/bindings/iio/dac/ltc2632.txt+14−0
@@ -12,12 +12,26 @@ Required properties: · 11 unmodified lines
12Property rules described in Documentation/devicetree/bindings/spi/spi-bus.txt12Property rules described in Documentation/devicetree/bindings/spi/spi-bus.txt
13apply. In particular, "reg" and "spi-max-frequency" properties must be given.13apply. In particular, "reg" and "spi-max-frequency" properties must be given.
14 14
15Optional properties:
16 - vref-supply: Phandle to the external reference voltage supply. This should
17 only be set if there is an external reference voltage connected to the VREF
18 pin. If the property is not set the internal reference is used.
19
15Example:20Example:
16 21
22 vref: regulator-vref {
23 compatible = "regulator-fixed";
24 regulator-name = "vref-ltc2632";
25 regulator-min-microvolt = <1250000>;
26 regulator-max-microvolt = <1250000>;
27 regulator-always-on;
28 };
29
17 spi_master {30 spi_master {
18 dac: ltc2632@0 {31 dac: ltc2632@0 {
19 compatible = "lltc,ltc2632-l12";32 compatible = "lltc,ltc2632-l12";
20 reg = <0>; /* CS0 */33 reg = <0>; /* CS0 */
21 spi-max-frequency = <1000000>;34 spi-max-frequency = <1000000>;
35 vref-supply = <&vref>; /* optional */
22 };36 };
23 };37 };
Documentation/devicetree/bindings/iio/dac/ti,dac5571.txt+24−0
@@ -0,0 +1,24 @@
1* Texas Instruments DAC5571 Family
2
3Required properties:
4 - compatible: Should contain
5 "ti,dac5571"
6 "ti,dac6571"
7 "ti,dac7571"
8 "ti,dac5574"
9 "ti,dac6574"
10 "ti,dac7574"
11 "ti,dac5573"
12 "ti,dac6573"
13 "ti,dac7573"
14 - reg: Should contain the DAC I2C address
15
16Optional properties:
17 - vref-supply: The regulator supply for DAC reference voltage
18
19Example:
20dac@0 {
21 compatible = "ti,dac5571";
22 reg = <0x4C>;
23 vref-supply = <&vdd_supply>;
24};
Documentation/devicetree/bindings/iio/imu/inv_mpu6050.txt+9−3
@@ -8,10 +8,16 @@ Required properties: · 7 unmodified lines
8 "invensense,mpu6500"8 "invensense,mpu6500"
9 "invensense,mpu9150"9 "invensense,mpu9150"
10 "invensense,mpu9250"10 "invensense,mpu9250"
11 "invensense,mpu9255"
11 "invensense,icm20608"12 "invensense,icm20608"
12 - reg : the I2C address of the sensor13 - reg : the I2C address of the sensor
13 - interrupt-parent : should be the phandle for the interrupt controller14 - interrupt-parent : should be the phandle for the interrupt controller
14 - interrupts : interrupt mapping for GPIO IRQ15 - interrupts: interrupt mapping for IRQ. It should be configured with flags
16 IRQ_TYPE_LEVEL_HIGH, IRQ_TYPE_EDGE_RISING, IRQ_TYPE_LEVEL_LOW or
17 IRQ_TYPE_EDGE_FALLING.
18
19 Refer to interrupt-controller/interrupts.txt for generic interrupt client node
20 bindings.
15 21
16Optional properties:22Optional properties:
17 - mount-matrix: an optional 3x3 mounting rotation matrix23 - mount-matrix: an optional 3x3 mounting rotation matrix
@@ -24,7 +30,7 @@ Example: · 6 unmodified lines
24 compatible = "invensense,mpu6050";30 compatible = "invensense,mpu6050";
25 reg = <0x68>;31 reg = <0x68>;
26 interrupt-parent = <&gpio1>;32 interrupt-parent = <&gpio1>;
27 interrupts = <18 1>;33 interrupts = <18 IRQ_TYPE_EDGE_RISING>;
28 mount-matrix = "-0.984807753012208", /* x0 */34 mount-matrix = "-0.984807753012208", /* x0 */
29 "0", /* y0 */35 "0", /* y0 */
30 "-0.173648177666930", /* z0 */36 "-0.173648177666930", /* z0 */
@@ -41,7 +47,7 @@ Example: · 10 unmodified lines
41 compatible = "invensense,mpu9250";47 compatible = "invensense,mpu9250";
42 reg = <0x68>;48 reg = <0x68>;
43 interrupt-parent = <&gpio3>;49 interrupt-parent = <&gpio3>;
44 interrupts = <21 1>;50 interrupts = <21 IRQ_TYPE_LEVEL_HIGH>;
45 i2c-gate {51 i2c-gate {
46 #address-cells = <1>;52 #address-cells = <1>;
47 #size-cells = <0>;53 #size-cells = <0>;
Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt+1−0
@@ -6,6 +6,7 @@ Required properties: · 5 unmodified lines
6 "st,lsm6ds3h"6 "st,lsm6ds3h"
7 "st,lsm6dsl"7 "st,lsm6dsl"
8 "st,lsm6dsm"8 "st,lsm6dsm"
9 "st,ism330dlc"
9- reg: i2c address of the sensor / spi cs line10- reg: i2c address of the sensor / spi cs line
10 11
11Optional properties:12Optional properties:
Documentation/devicetree/bindings/iio/potentiostat/lmp91000.txt+6−3
@@ -1,10 +1,13 @@
1* Texas Instruments LMP91000 potentiostat1* Texas Instruments LMP91000 series of potentiostats
2 2
3http://www.ti.com/lit/ds/symlink/lmp91000.pdf3LMP91000: http://www.ti.com/lit/ds/symlink/lmp91000.pdf
4LMP91002: http://www.ti.com/lit/ds/symlink/lmp91002.pdf
4 5
5Required properties:6Required properties:
6 7
7 - compatible: should be "ti,lmp91000"8 - compatible: should be one of the following:
9 "ti,lmp91000"
10 "ti,lmp91002"
8 - reg: the I2C address of the device11 - reg: the I2C address of the device
9 - io-channels: the phandle of the iio provider12 - io-channels: the phandle of the iio provider
10 13
Documentation/filesystems/00-INDEX+0−2
@@ -89,8 +89,6 @@ locks.txt · 88 unmodified lines
89 - info on file locking implementations, flock() vs. fcntl(), etc.89 - info on file locking implementations, flock() vs. fcntl(), etc.
90mandatory-locking.txt90mandatory-locking.txt
91 - info on the Linux implementation of Sys V mandatory file locking.91 - info on the Linux implementation of Sys V mandatory file locking.
92ncpfs.txt
93 - info on Novell Netware(tm) filesystem using NCP protocol.
94nfs/92nfs/
95 - nfs-related documentation.93 - nfs-related documentation.
96nilfs2.txt94nilfs2.txt
Documentation/filesystems/ncpfs.txt+0−12
@@ -1,12 +0,0 @@
1The ncpfs filesystem understands the NCP protocol, designed by the
2Novell Corporation for their NetWare(tm) product. NCP is functionally
3similar to the NFS used in the TCP/IP community.
4To mount a NetWare filesystem, you need a special mount program, which
5can be found in the ncpfs package. The home site for ncpfs is
6ftp.gwdg.de/pub/linux/misc/ncpfs, but sunsite and its many mirrors
7will have it as well.
8
9Related products are linware and mars_nwe, which will give Linux partial
10NetWare server functionality.
11
12mars_nwe can be found on ftp.gwdg.de/pub/linux/misc/ncpfs.
MAINTAINERS+23−9
@@ -796,6 +796,14 @@ M: Michael Hanselmann <linux-kernel@hansmi.ch> · 795 unmodified lines
796S: Supported796S: Supported
797F: drivers/macintosh/ams/797F: drivers/macintosh/ams/
798 798
799ANALOG DEVICES INC AD5686 DRIVER
800M: Stefan Popa <stefan.popa@analog.com>
801L: linux-pm@vger.kernel.org
802W: http://ez.analog.com/community/linux-device-drivers
803S: Supported
804F: drivers/iio/dac/ad5686*
805F: drivers/iio/dac/ad5696*
806
799ANALOG DEVICES INC AD9389B DRIVER807ANALOG DEVICES INC AD9389B DRIVER
800M: Hans Verkuil <hans.verkuil@cisco.com>808M: Hans Verkuil <hans.verkuil@cisco.com>
801L: linux-media@vger.kernel.org809L: linux-media@vger.kernel.org
@@ -4421,6 +4429,12 @@ L: linux-kernel@vger.kernel.org · 3619 unmodified lines
4421S: Maintained4429S: Maintained
4422F: drivers/staging/fsl-dpaa2/ethsw4430F: drivers/staging/fsl-dpaa2/ethsw
4423 4431
4432DPAA2 PTP CLOCK DRIVER
4433M: Yangbo Lu <yangbo.lu@nxp.com>
4434L: linux-kernel@vger.kernel.org
4435S: Maintained
4436F: drivers/staging/fsl-dpaa2/rtc
4437
4424DPT_I2O SCSI RAID DRIVER4438DPT_I2O SCSI RAID DRIVER
4425M: Adaptec OEM Raid Solutions <aacraid@microsemi.com>4439M: Adaptec OEM Raid Solutions <aacraid@microsemi.com>
4426L: linux-scsi@vger.kernel.org4440L: linux-scsi@vger.kernel.org
@@ -6968,6 +6982,15 @@ F: drivers/staging/iio/ · 2541 unmodified lines
6968F: include/linux/iio/6982F: include/linux/iio/
6969F: tools/iio/6983F: tools/iio/
6970 6984
6985IIO UNIT CONVERTER
6986M: Peter Rosin <peda@axentia.se>
6987L: linux-iio@vger.kernel.org
6988S: Maintained
6989F: Documentation/devicetree/bindings/iio/afe/current-sense-amplifier.txt
6990F: Documentation/devicetree/bindings/iio/afe/current-sense-shunt.txt
6991F: Documentation/devicetree/bindings/iio/afe/voltage-divider.txt
6992F: drivers/iio/afe/iio-rescale.c
6993
6971IKANOS/ADI EAGLE ADSL USB DRIVER6994IKANOS/ADI EAGLE ADSL USB DRIVER
6972M: Matthieu Castet <castet.matthieu@free.fr>6995M: Matthieu Castet <castet.matthieu@free.fr>
6973M: Stanislaw Gruszka <stf_xl@wp.pl>6996M: Stanislaw Gruszka <stf_xl@wp.pl>
@@ -13433,15 +13456,6 @@ S: Odd Fixes · 6459 unmodified lines
13433F: Documentation/devicetree/bindings/staging/iio/13456F: Documentation/devicetree/bindings/staging/iio/
13434F: drivers/staging/iio/13457F: drivers/staging/iio/
13435 13458
13436STAGING - LUSTRE PARALLEL FILESYSTEM
13437M: Oleg Drokin <oleg.drokin@intel.com>
13438M: Andreas Dilger <andreas.dilger@intel.com>
13439M: James Simmons <jsimmons@infradead.org>
13440L: lustre-devel@lists.lustre.org (moderated for non-subscribers)
13441W: http://wiki.lustre.org/
13442S: Maintained
13443F: drivers/staging/lustre
13444
13445STAGING - NVIDIA COMPLIANT EMBEDDED CONTROLLER INTERFACE (nvec)13459STAGING - NVIDIA COMPLIANT EMBEDDED CONTROLLER INTERFACE (nvec)
13446M: Marc Dietrich <marvin24@gmx.de>13460M: Marc Dietrich <marvin24@gmx.de>
13447L: ac100@lists.launchpad.net (moderated for non-subscribers)13461L: ac100@lists.launchpad.net (moderated for non-subscribers)
drivers/iio/Kconfig+2−0
@@ -70,6 +70,7 @@ config IIO_TRIGGERED_EVENT · 69 unmodified lines
70 70
71source "drivers/iio/accel/Kconfig"71source "drivers/iio/accel/Kconfig"
72source "drivers/iio/adc/Kconfig"72source "drivers/iio/adc/Kconfig"
73source "drivers/iio/afe/Kconfig"
73source "drivers/iio/amplifiers/Kconfig"74source "drivers/iio/amplifiers/Kconfig"
74source "drivers/iio/chemical/Kconfig"75source "drivers/iio/chemical/Kconfig"
75source "drivers/iio/common/Kconfig"76source "drivers/iio/common/Kconfig"
@@ -92,6 +93,7 @@ source "drivers/iio/potentiometer/Kconfig" · 16 unmodified lines
92source "drivers/iio/potentiostat/Kconfig"93source "drivers/iio/potentiostat/Kconfig"
93source "drivers/iio/pressure/Kconfig"94source "drivers/iio/pressure/Kconfig"
94source "drivers/iio/proximity/Kconfig"95source "drivers/iio/proximity/Kconfig"
96source "drivers/iio/resolver/Kconfig"
95source "drivers/iio/temperature/Kconfig"97source "drivers/iio/temperature/Kconfig"
96 98
97endif # IIO99endif # IIO
drivers/iio/Makefile+2−0
@@ -15,6 +15,7 @@ obj-$(CONFIG_IIO_TRIGGERED_EVENT) += industrialio-triggered-event.o · 14 unmodified lines
15 15
16obj-y += accel/16obj-y += accel/
17obj-y += adc/17obj-y += adc/
18obj-y += afe/
18obj-y += amplifiers/19obj-y += amplifiers/
19obj-y += buffer/20obj-y += buffer/
20obj-y += chemical/21obj-y += chemical/
@@ -35,5 +36,6 @@ obj-y += potentiometer/ · 14 unmodified lines
35obj-y += potentiostat/36obj-y += potentiostat/
36obj-y += pressure/37obj-y += pressure/
37obj-y += proximity/38obj-y += proximity/
39obj-y += resolver/
38obj-y += temperature/40obj-y += temperature/
39obj-y += trigger/41obj-y += trigger/
drivers/iio/accel/Kconfig+24−0
@@ -5,6 +5,30 @@ · 4 unmodified lines
5 5
6menu "Accelerometers"6menu "Accelerometers"
7 7
8config ADIS16201
9 tristate "Analog Devices ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer"
10 depends on SPI
11 select IIO_ADIS_LIB
12 select IIO_ADIS_LIB_BUFFER if IIO_BUFFER
13 help
14 Say Y here to build support for Analog Devices adis16201 dual-axis
15 digital inclinometer and accelerometer.
16
17 To compile this driver as a module, say M here: the module will
18 be called adis16201.
19
20config ADIS16209
21 tristate "Analog Devices ADIS16209 Dual-Axis Digital Inclinometer and Accelerometer"
22 depends on SPI
23 select IIO_ADIS_LIB
24 select IIO_ADIS_LIB_BUFFER if IIO_BUFFER
25 help
26 Say Y here to build support for Analog Devices adis16209 dual-axis digital inclinometer
27 and accelerometer.
28
29 To compile this driver as a module, say M here: the module will be
30 called adis16209.
31
8config ADXL34532config ADXL345
9 tristate33 tristate
10 34
drivers/iio/accel/Makefile+2−0
@@ -4,6 +4,8 @@ · 3 unmodified lines
4#4#
5 5
6# When adding new entries keep the list in alphabetical order6# When adding new entries keep the list in alphabetical order
7obj-$(CONFIG_ADIS16201) += adis16201.o
8obj-$(CONFIG_ADIS16209) += adis16209.o
7obj-$(CONFIG_ADXL345) += adxl345_core.o9obj-$(CONFIG_ADXL345) += adxl345_core.o
8obj-$(CONFIG_ADXL345_I2C) += adxl345_i2c.o10obj-$(CONFIG_ADXL345_I2C) += adxl345_i2c.o
9obj-$(CONFIG_ADXL345_SPI) += adxl345_spi.o11obj-$(CONFIG_ADXL345_SPI) += adxl345_spi.o
drivers/iio/accel/adis16201.c+321−0
@@ -0,0 +1,321 @@
1/*
2 * ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer
3 *
4 * Copyright 2010 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2 or later.
7 */
8
9#include <linux/device.h>
10#include <linux/kernel.h>
11#include <linux/module.h>
12#include <linux/mutex.h>
13#include <linux/slab.h>
14#include <linux/spi/spi.h>
15#include <linux/sysfs.h>
16
17#include <linux/iio/iio.h>
18#include <linux/iio/imu/adis.h>
19
20#define ADIS16201_STARTUP_DELAY_MS 220
21#define ADIS16201_FLASH_CNT 0x00
22
23/* Data Output Register Information */
24#define ADIS16201_SUPPLY_OUT_REG 0x02
25#define ADIS16201_XACCL_OUT_REG 0x04
26#define ADIS16201_YACCL_OUT_REG 0x06
27#define ADIS16201_AUX_ADC_REG 0x08
28#define ADIS16201_TEMP_OUT_REG 0x0A
29#define ADIS16201_XINCL_OUT_REG 0x0C
30#define ADIS16201_YINCL_OUT_REG 0x0E
31
32/* Calibration Register Definition */
33#define ADIS16201_XACCL_OFFS_REG 0x10
34#define ADIS16201_YACCL_OFFS_REG 0x12
35#define ADIS16201_XACCL_SCALE_REG 0x14
36#define ADIS16201_YACCL_SCALE_REG 0x16
37#define ADIS16201_XINCL_OFFS_REG 0x18
38#define ADIS16201_YINCL_OFFS_REG 0x1A
39#define ADIS16201_XINCL_SCALE_REG 0x1C
40#define ADIS16201_YINCL_SCALE_REG 0x1E
41
42/* Alarm Register Definition */
43#define ADIS16201_ALM_MAG1_REG 0x20
44#define ADIS16201_ALM_MAG2_REG 0x22
45#define ADIS16201_ALM_SMPL1_REG 0x24
46#define ADIS16201_ALM_SMPL2_REG 0x26
47#define ADIS16201_ALM_CTRL_REG 0x28
48
49#define ADIS16201_AUX_DAC_REG 0x30
50#define ADIS16201_GPIO_CTRL_REG 0x32
51#define ADIS16201_SMPL_PRD_REG 0x36
52/* Operation, filter configuration */
53#define ADIS16201_AVG_CNT_REG 0x38
54#define ADIS16201_SLP_CNT_REG 0x3A
55
56/* Miscellaneous Control Register Definition */
57#define ADIS16201_MSC_CTRL_REG 0x34
58#define ADIS16201_MSC_CTRL_SELF_TEST_EN BIT(8)
59/* Data-ready enable: 1 = enabled, 0 = disabled */
60#define ADIS16201_MSC_CTRL_DATA_RDY_EN BIT(2)
61/* Data-ready polarity: 1 = active high, 0 = active low */
62#define ADIS16201_MSC_CTRL_ACTIVE_DATA_RDY_HIGH BIT(1)
63/* Data-ready line selection: 1 = DIO1, 0 = DIO0 */
64#define ADIS16201_MSC_CTRL_DATA_RDY_DIO1 BIT(0)
65
66/* Diagnostics System Status Register Definition */
67#define ADIS16201_DIAG_STAT_REG 0x3C
68#define ADIS16201_DIAG_STAT_ALARM2 BIT(9)
69#define ADIS16201_DIAG_STAT_ALARM1 BIT(8)
70#define ADIS16201_DIAG_STAT_SPI_FAIL_BIT 3
71#define ADIS16201_DIAG_STAT_FLASH_UPT_FAIL_BIT 2
72/* Power supply above 3.625 V */
73#define ADIS16201_DIAG_STAT_POWER_HIGH_BIT 1
74/* Power supply below 3.15 V */
75#define ADIS16201_DIAG_STAT_POWER_LOW_BIT 0
76
77/* System Command Register Definition */
78#define ADIS16201_GLOB_CMD_REG 0x3E
79#define ADIS16201_GLOB_CMD_SW_RESET BIT(7)
80#define ADIS16201_GLOB_CMD_FACTORY_RESET BIT(1)
81
82#define ADIS16201_ERROR_ACTIVE BIT(14)
83
84enum adis16201_scan {
85 ADIS16201_SCAN_ACC_X,
86 ADIS16201_SCAN_ACC_Y,
87 ADIS16201_SCAN_INCLI_X,
88 ADIS16201_SCAN_INCLI_Y,
89 ADIS16201_SCAN_SUPPLY,
90 ADIS16201_SCAN_AUX_ADC,
91 ADIS16201_SCAN_TEMP,
92};
93
94static const u8 adis16201_addresses[] = {
95 [ADIS16201_SCAN_ACC_X] = ADIS16201_XACCL_OFFS_REG,
96 [ADIS16201_SCAN_ACC_Y] = ADIS16201_YACCL_OFFS_REG,
97 [ADIS16201_SCAN_INCLI_X] = ADIS16201_XINCL_OFFS_REG,
98 [ADIS16201_SCAN_INCLI_Y] = ADIS16201_YINCL_OFFS_REG,
99};
100
101static int adis16201_read_raw(struct iio_dev *indio_dev,
102 struct iio_chan_spec const *chan,
103 int *val, int *val2,
104 long mask)
105{
106 struct adis *st = iio_priv(indio_dev);
107 int ret;
108 int bits;
109 u8 addr;
110 s16 val16;
111
112 switch (mask) {
113 case IIO_CHAN_INFO_RAW:
114 return adis_single_conversion(indio_dev, chan,
115 ADIS16201_ERROR_ACTIVE, val);
116 case IIO_CHAN_INFO_SCALE:
117 switch (chan->type) {
118 case IIO_VOLTAGE:
119 if (chan->channel == 0) {
120 /* Voltage base units are mV hence 1.22 mV */
121 *val = 1;
122 *val2 = 220000;
123 } else {
124 /* Voltage base units are mV hence 0.61 mV */
125 *val = 0;
126 *val2 = 610000;
127 }
128 return IIO_VAL_INT_PLUS_MICRO;
129 case IIO_TEMP:
130 *val = -470;
131 *val2 = 0;
132 return IIO_VAL_INT_PLUS_MICRO;
133 case IIO_ACCEL:
134 /*
135 * IIO base unit for sensitivity of accelerometer
136 * is milli g.
137 * 1 LSB represents 0.244 mg.
138 */
139 *val = 0;
140 *val2 = IIO_G_TO_M_S_2(462400);
141 return IIO_VAL_INT_PLUS_NANO;
142 case IIO_INCLI:
143 *val = 0;
144 *val2 = 100000;
145 return IIO_VAL_INT_PLUS_MICRO;
146 default:
147 return -EINVAL;
148 }
149 break;
150 case IIO_CHAN_INFO_OFFSET:
151 /*
152 * The raw ADC value is 1278 when the temperature
153 * is 25 degrees and the scale factor per milli
154 * degree celcius is -470.
155 */
156 *val = 25000 / -470 - 1278;
157 return IIO_VAL_INT;
158 case IIO_CHAN_INFO_CALIBBIAS:
159 switch (chan->type) {
160 case IIO_ACCEL:
161 bits = 12;
162 break;
163 case IIO_INCLI:
164 bits = 9;
165 break;
166 default:
167 return -EINVAL;
168 }
169 addr = adis16201_addresses[chan->scan_index];
170 ret = adis_read_reg_16(st, addr, &val16);
171 if (ret)
172 return ret;
173
174 *val = sign_extend32(val16, bits - 1);
175 return IIO_VAL_INT;
176 }
177
178 return -EINVAL;
179}
180
181static int adis16201_write_raw(struct iio_dev *indio_dev,
182 struct iio_chan_spec const *chan,
183 int val,
184 int val2,
185 long mask)
186{
187 struct adis *st = iio_priv(indio_dev);
188 int m;
189
190 if (mask != IIO_CHAN_INFO_CALIBBIAS)
191 return -EINVAL;
192
193 switch (chan->type) {
194 case IIO_ACCEL:
195 m = GENMASK(11, 0);
196 break;
197 case IIO_INCLI:
198 m = GENMASK(8, 0);
199 break;
200 default:
201 return -EINVAL;
202 }
203
204 return adis_write_reg_16(st, adis16201_addresses[chan->scan_index],
205 val & m);
206}
207
208static const struct iio_chan_spec adis16201_channels[] = {
209 ADIS_SUPPLY_CHAN(ADIS16201_SUPPLY_OUT_REG, ADIS16201_SCAN_SUPPLY, 0,
210 12),
211 ADIS_TEMP_CHAN(ADIS16201_TEMP_OUT_REG, ADIS16201_SCAN_TEMP, 0, 12),
212 ADIS_ACCEL_CHAN(X, ADIS16201_XACCL_OUT_REG, ADIS16201_SCAN_ACC_X,
213 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
214 ADIS_ACCEL_CHAN(Y, ADIS16201_YACCL_OUT_REG, ADIS16201_SCAN_ACC_Y,
215 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
216 ADIS_AUX_ADC_CHAN(ADIS16201_AUX_ADC_REG, ADIS16201_SCAN_AUX_ADC, 0, 12),
217 ADIS_INCLI_CHAN(X, ADIS16201_XINCL_OUT_REG, ADIS16201_SCAN_INCLI_X,
218 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
219 ADIS_INCLI_CHAN(X, ADIS16201_YINCL_OUT_REG, ADIS16201_SCAN_INCLI_Y,
220 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
221 IIO_CHAN_SOFT_TIMESTAMP(7)
222};
223
224static const struct iio_info adis16201_info = {
225 .read_raw = adis16201_read_raw,
226 .write_raw = adis16201_write_raw,
227 .update_scan_mode = adis_update_scan_mode,
228};
229
230static const char * const adis16201_status_error_msgs[] = {
231 [ADIS16201_DIAG_STAT_SPI_FAIL_BIT] = "SPI failure",
232 [ADIS16201_DIAG_STAT_FLASH_UPT_FAIL_BIT] = "Flash update failed",
233 [ADIS16201_DIAG_STAT_POWER_HIGH_BIT] = "Power supply above 3.625V",
234 [ADIS16201_DIAG_STAT_POWER_LOW_BIT] = "Power supply below 3.15V",
235};
236
237static const struct adis_data adis16201_data = {
238 .read_delay = 20,
239 .msc_ctrl_reg = ADIS16201_MSC_CTRL_REG,
240 .glob_cmd_reg = ADIS16201_GLOB_CMD_REG,
241 .diag_stat_reg = ADIS16201_DIAG_STAT_REG,
242
243 .self_test_mask = ADIS16201_MSC_CTRL_SELF_TEST_EN,
244 .self_test_no_autoclear = true,
245 .startup_delay = ADIS16201_STARTUP_DELAY_MS,
246
247 .status_error_msgs = adis16201_status_error_msgs,
248 .status_error_mask = BIT(ADIS16201_DIAG_STAT_SPI_FAIL_BIT) |
249 BIT(ADIS16201_DIAG_STAT_FLASH_UPT_FAIL_BIT) |
250 BIT(ADIS16201_DIAG_STAT_POWER_HIGH_BIT) |
251 BIT(ADIS16201_DIAG_STAT_POWER_LOW_BIT),
252};
253
254static int adis16201_probe(struct spi_device *spi)
255{
256 struct iio_dev *indio_dev;
257 struct adis *st;
258 int ret;
259
260 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
261 if (!indio_dev)
262 return -ENOMEM;
263
264 st = iio_priv(indio_dev);
265 spi_set_drvdata(spi, indio_dev);
266
267 indio_dev->name = spi->dev.driver->name;
268 indio_dev->dev.parent = &spi->dev;
269 indio_dev->info = &adis16201_info;
270
271 indio_dev->channels = adis16201_channels;
272 indio_dev->num_channels = ARRAY_SIZE(adis16201_channels);
273 indio_dev->modes = INDIO_DIRECT_MODE;
274
275 ret = adis_init(st, indio_dev, spi, &adis16201_data);
276 if (ret)
277 return ret;
278
279 ret = adis_setup_buffer_and_trigger(st, indio_dev, NULL);
280 if (ret)
281 return ret;
282
283 ret = adis_initial_startup(st);
284 if (ret)
285 goto error_cleanup_buffer_trigger;
286
287 ret = iio_device_register(indio_dev);
288 if (ret < 0)
289 goto error_cleanup_buffer_trigger;
290
291 return 0;
292
293error_cleanup_buffer_trigger:
294 adis_cleanup_buffer_and_trigger(st, indio_dev);
295 return ret;
296}
297
298static int adis16201_remove(struct spi_device *spi)
299{
300 struct iio_dev *indio_dev = spi_get_drvdata(spi);
301 struct adis *st = iio_priv(indio_dev);
302
303 iio_device_unregister(indio_dev);
304 adis_cleanup_buffer_and_trigger(st, indio_dev);
305
306 return 0;
307}
308
309static struct spi_driver adis16201_driver = {
310 .driver = {
311 .name = "adis16201",
312 },
313 .probe = adis16201_probe,
314 .remove = adis16201_remove,
315};
316module_spi_driver(adis16201_driver);
317
318MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
319MODULE_DESCRIPTION("Analog Devices ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer");
320MODULE_LICENSE("GPL v2");
321MODULE_ALIAS("spi:adis16201");
drivers/iio/accel/adis16209.crenamed from drivers/staging/iio/accel/adis16209.c+24−28
@@ -6,7 +6,6 @@ · 5 unmodified lines
6 * Licensed under the GPL-2 or later.6 * Licensed under the GPL-2 or later.
7 */7 */
8 8
9#include <linux/delay.h>
10#include <linux/device.h>9#include <linux/device.h>
11#include <linux/kernel.h>10#include <linux/kernel.h>
12#include <linux/list.h>11#include <linux/list.h>
@@ -16,8 +15,6 @@ · 3 unmodified lines
16#include <linux/sysfs.h>15#include <linux/sysfs.h>
17 16
18#include <linux/iio/iio.h>17#include <linux/iio/iio.h>
19#include <linux/iio/sysfs.h>
20#include <linux/iio/buffer.h>
21#include <linux/iio/imu/adis.h>18#include <linux/iio/imu/adis.h>
22 19
23#define ADIS16209_STARTUP_DELAY_MS 22020#define ADIS16209_STARTUP_DELAY_MS 220
@@ -71,13 +68,13 @@ · 47 unmodified lines
71#define ADIS16209_STAT_REG 0x3C68#define ADIS16209_STAT_REG 0x3C
72#define ADIS16209_STAT_ALARM2 BIT(9)69#define ADIS16209_STAT_ALARM2 BIT(9)
73#define ADIS16209_STAT_ALARM1 BIT(8)70#define ADIS16209_STAT_ALARM1 BIT(8)
74#define ADIS16209_STAT_SELFTEST_FAIL_BIT 571#define ADIS16209_STAT_SELFTEST_FAIL_BIT 5
75#define ADIS16209_STAT_SPI_FAIL_BIT 372#define ADIS16209_STAT_SPI_FAIL_BIT 3
76#define ADIS16209_STAT_FLASH_UPT_FAIL_BIT 273#define ADIS16209_STAT_FLASH_UPT_FAIL_BIT 2
77/* Power supply above 3.625 V */74/* Power supply above 3.625 V */
78#define ADIS16209_STAT_POWER_HIGH_BIT 175#define ADIS16209_STAT_POWER_HIGH_BIT 1
79/* Power supply below 3.15 V */76/* Power supply below 3.15 V */
80#define ADIS16209_STAT_POWER_LOW_BIT 077#define ADIS16209_STAT_POWER_LOW_BIT 0
81 78
82#define ADIS16209_CMD_REG 0x3E79#define ADIS16209_CMD_REG 0x3E
83#define ADIS16209_CMD_SW_RESET BIT(7)80#define ADIS16209_CMD_SW_RESET BIT(7)
@@ -115,25 +112,22 @@ static int adis16209_write_raw(struct iio_dev *indio_dev, · 31 unmodified lines
115 long mask)112 long mask)
116{113{
117 struct adis *st = iio_priv(indio_dev);114 struct adis *st = iio_priv(indio_dev);
118 int bits;115 int m;
119 s16 val16;
120 u8 addr;
121 116
122 switch (mask) {117 if (mask != IIO_CHAN_INFO_CALIBBIAS)
123 case IIO_CHAN_INFO_CALIBBIAS:118 return -EINVAL;
124 switch (chan->type) {119
125 case IIO_ACCEL:120 switch (chan->type) {
126 case IIO_INCLI:121 case IIO_ACCEL:
127 bits = 14;122 case IIO_INCLI:
128 break;123 m = GENMASK(13, 0);
129 default:124 break;
130 return -EINVAL;125 default:
131 }126 return -EINVAL;
132 val16 = val & ((1 << bits) - 1);
133 addr = adis16209_addresses[chan->scan_index][0];
134 return adis_write_reg_16(st, addr, val16);
135 }127 }
136 return -EINVAL;128
129 return adis_write_reg_16(st, adis16209_addresses[chan->scan_index][0],
130 val & m);
137}131}
138 132
139static int adis16209_read_raw(struct iio_dev *indio_dev,133static int adis16209_read_raw(struct iio_dev *indio_dev,
@@ -195,7 +189,7 @@ static int adis16209_read_raw(struct iio_dev *indio_dev, · 55 unmodified lines
195 case IIO_CHAN_INFO_OFFSET:189 case IIO_CHAN_INFO_OFFSET:
196 /*190 /*
197 * The raw ADC value is 0x4FE when the temperature191 * The raw ADC value is 0x4FE when the temperature
198 * is 25 degrees and the scale factor per milli192 * is 45 degrees and the scale factor per milli
199 * degree celcius is -470.193 * degree celcius is -470.
200 */194 */
201 *val = 25000 / -470 - 0x4FE;195 *val = 25000 / -470 - 0x4FE;
@@ -270,13 +264,14 @@ static const struct adis_data adis16209_data = { · 68 unmodified lines
270 264
271static int adis16209_probe(struct spi_device *spi)265static int adis16209_probe(struct spi_device *spi)
272{266{
273 int ret;
274 struct adis *st;
275 struct iio_dev *indio_dev;267 struct iio_dev *indio_dev;
268 struct adis *st;
269 int ret;
276 270
277 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));271 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
278 if (!indio_dev)272 if (!indio_dev)
279 return -ENOMEM;273 return -ENOMEM;
274
280 st = iio_priv(indio_dev);275 st = iio_priv(indio_dev);
281 spi_set_drvdata(spi, indio_dev);276 spi_set_drvdata(spi, indio_dev);
282 277
@@ -290,6 +285,7 @@ static int adis16209_probe(struct spi_device *spi) · 7 unmodified lines
290 ret = adis_init(st, indio_dev, spi, &adis16209_data);285 ret = adis_init(st, indio_dev, spi, &adis16209_data);
291 if (ret)286 if (ret)
292 return ret;287 return ret;
288
293 ret = adis_setup_buffer_and_trigger(st, indio_dev, NULL);289 ret = adis_setup_buffer_and_trigger(st, indio_dev, NULL);
294 if (ret)290 if (ret)
295 return ret;291 return ret;
drivers/iio/accel/bmc150-accel-core.c+3−20
@@ -837,29 +837,12 @@ static int bmc150_accel_fifo_transfer(struct bmc150_accel_data *data, · 836 unmodified lines
837 int sample_length = 3 * 2;837 int sample_length = 3 * 2;
838 int ret;838 int ret;
839 int total_length = samples * sample_length;839 int total_length = samples * sample_length;
840 int i;
841 size_t step = regmap_get_raw_read_max(data->regmap);
842
843 if (!step || step > total_length)
844 step = total_length;
845 else if (step < total_length)
846 step = sample_length;
847
848 /*
849 * Seems we have a bus with size limitation so we have to execute
850 * multiple reads
851 */
852 for (i = 0; i < total_length; i += step) {
853 ret = regmap_raw_read(data->regmap, BMC150_ACCEL_REG_FIFO_DATA,
854 &buffer[i], step);
855 if (ret)
856 break;
857 }
858 840
841 ret = regmap_raw_read(data->regmap, BMC150_ACCEL_REG_FIFO_DATA,
842 buffer, total_length);
859 if (ret)843 if (ret)
860 dev_err(dev,844 dev_err(dev,
861 "Error transferring data from fifo in single steps of %zu\n",845 "Error transferring data from fifo: %d\n", ret);
862 step);
863 846
864 return ret;847 return ret;
865}848}
drivers/iio/accel/mma8452.c+23−1
@@ -106,6 +106,7 @@ struct mma8452_data { · 105 unmodified lines
106 u8 ctrl_reg1;106 u8 ctrl_reg1;
107 u8 data_cfg;107 u8 data_cfg;
108 const struct mma_chip_info *chip_info;108 const struct mma_chip_info *chip_info;
109 int sleep_val;
109};110};
110 111
111 /**112 /**
@@ -193,7 +194,11 @@ static int mma8452_drdy(struct mma8452_data *data) · 81 unmodified lines
193 if ((ret & MMA8452_STATUS_DRDY) == MMA8452_STATUS_DRDY)194 if ((ret & MMA8452_STATUS_DRDY) == MMA8452_STATUS_DRDY)
194 return 0;195 return 0;
195 196
196 msleep(20);197 if (data->sleep_val <= 20)
198 usleep_range(data->sleep_val * 250,
199 data->sleep_val * 500);
200 else
201 msleep(20);
197 }202 }
198 203
199 dev_err(&data->client->dev, "data not ready\n");204 dev_err(&data->client->dev, "data not ready\n");
@@ -544,6 +549,18 @@ static int mma8452_read_raw(struct iio_dev *indio_dev, · 344 unmodified lines
544 return -EINVAL;549 return -EINVAL;
545}550}
546 551
552static int mma8452_calculate_sleep(struct mma8452_data *data)
553{
554 int ret, i = mma8452_get_odr_index(data);
555
556 if (mma8452_samp_freq[i][0] > 0)
557 ret = 1000 / mma8452_samp_freq[i][0];
558 else
559 ret = 1000;
560
561 return ret == 0 ? 1 : ret;
562}
563
547static int mma8452_standby(struct mma8452_data *data)564static int mma8452_standby(struct mma8452_data *data)
548{565{
549 return i2c_smbus_write_byte_data(data->client, MMA8452_CTRL_REG1,566 return i2c_smbus_write_byte_data(data->client, MMA8452_CTRL_REG1,
@@ -700,6 +717,8 @@ static int mma8452_write_raw(struct iio_dev *indio_dev, · 150 unmodified lines
700 data->ctrl_reg1 &= ~MMA8452_CTRL_DR_MASK;717 data->ctrl_reg1 &= ~MMA8452_CTRL_DR_MASK;
701 data->ctrl_reg1 |= i << MMA8452_CTRL_DR_SHIFT;718 data->ctrl_reg1 |= i << MMA8452_CTRL_DR_SHIFT;
702 719
720 data->sleep_val = mma8452_calculate_sleep(data);
721
703 ret = mma8452_change_config(data, MMA8452_CTRL_REG1,722 ret = mma8452_change_config(data, MMA8452_CTRL_REG1,
704 data->ctrl_reg1);723 data->ctrl_reg1);
705 break;724 break;
@@ -1593,6 +1612,9 @@ static int mma8452_probe(struct i2c_client *client, · 887 unmodified lines
1593 1612
1594 data->ctrl_reg1 = MMA8452_CTRL_ACTIVE |1613 data->ctrl_reg1 = MMA8452_CTRL_ACTIVE |
1595 (MMA8452_CTRL_DR_DEFAULT << MMA8452_CTRL_DR_SHIFT);1614 (MMA8452_CTRL_DR_DEFAULT << MMA8452_CTRL_DR_SHIFT);
1615
1616 data->sleep_val = mma8452_calculate_sleep(data);
1617
1596 ret = i2c_smbus_write_byte_data(client, MMA8452_CTRL_REG1,1618 ret = i2c_smbus_write_byte_data(client, MMA8452_CTRL_REG1,
1597 data->ctrl_reg1);1619 data->ctrl_reg1);
1598 if (ret < 0)1620 if (ret < 0)
drivers/iio/accel/sca3000.c+4−9
@@ -1277,7 +1277,7 @@ static int sca3000_configure_ring(struct iio_dev *indio_dev) · 1276 unmodified lines
1277{1277{
1278 struct iio_buffer *buffer;1278 struct iio_buffer *buffer;
1279 1279
1280 buffer = iio_kfifo_allocate();1280 buffer = devm_iio_kfifo_allocate(&indio_dev->dev);
1281 if (!buffer)1281 if (!buffer)
1282 return -ENOMEM;1282 return -ENOMEM;
1283 1283
@@ -1287,11 +1287,6 @@ static int sca3000_configure_ring(struct iio_dev *indio_dev) · 3 unmodified lines
1287 return 0;1287 return 0;
1288}1288}
1289 1289
1290static void sca3000_unconfigure_ring(struct iio_dev *indio_dev)
1291{
1292 iio_kfifo_free(indio_dev->buffer);
1293}
1294
1295static inline1290static inline
1296int __sca3000_hw_ring_state_set(struct iio_dev *indio_dev, bool state)1291int __sca3000_hw_ring_state_set(struct iio_dev *indio_dev, bool state)
1297{1292{
@@ -1486,7 +1481,9 @@ static int sca3000_probe(struct spi_device *spi) · 188 unmodified lines
1486 }1481 }
1487 indio_dev->modes = INDIO_DIRECT_MODE;1482 indio_dev->modes = INDIO_DIRECT_MODE;
1488 1483
1489 sca3000_configure_ring(indio_dev);1484 ret = sca3000_configure_ring(indio_dev);
1485 if (ret)
1486 return ret;
1490 1487
1491 if (spi->irq) {1488 if (spi->irq) {
1492 ret = request_threaded_irq(spi->irq,1489 ret = request_threaded_irq(spi->irq,
@@ -1546,8 +1543,6 @@ static int sca3000_remove(struct spi_device *spi) · 53 unmodified lines
1546 if (spi->irq)1543 if (spi->irq)
1547 free_irq(spi->irq, indio_dev);1544 free_irq(spi->irq, indio_dev);
1548 1545
1549 sca3000_unconfigure_ring(indio_dev);
1550
1551 return 0;1546 return 0;
1552}1547}
1553 1548
drivers/iio/accel/st_accel_i2c.c+1−0
@@ -107,6 +107,7 @@ MODULE_DEVICE_TABLE(of, st_accel_of_match); · 106 unmodified lines
107 107
108#ifdef CONFIG_ACPI108#ifdef CONFIG_ACPI
109static const struct acpi_device_id st_accel_acpi_match[] = {109static const struct acpi_device_id st_accel_acpi_match[] = {
110 {"SMO8840", LNG2DM},
110 {"SMO8A90", LNG2DM},111 {"SMO8A90", LNG2DM},
111 { },112 { },
112};113};
drivers/iio/adc/ad7791.c+47−40
@@ -153,6 +153,17 @@ struct ad7791_state { · 152 unmodified lines
153 const struct ad7791_chip_info *info;153 const struct ad7791_chip_info *info;
154};154};
155 155
156static const int ad7791_sample_freq_avail[8][2] = {
157 [AD7791_FILTER_RATE_120] = { 120, 0 },
158 [AD7791_FILTER_RATE_100] = { 100, 0 },
159 [AD7791_FILTER_RATE_33_3] = { 33, 300000 },
160 [AD7791_FILTER_RATE_20] = { 20, 0 },
161 [AD7791_FILTER_RATE_16_6] = { 16, 600000 },
162 [AD7791_FILTER_RATE_16_7] = { 16, 700000 },
163 [AD7791_FILTER_RATE_13_3] = { 13, 300000 },
164 [AD7791_FILTER_RATE_9_5] = { 9, 500000 },
165};
166
156static struct ad7791_state *ad_sigma_delta_to_ad7791(struct ad_sigma_delta *sd)167static struct ad7791_state *ad_sigma_delta_to_ad7791(struct ad_sigma_delta *sd)
157{168{
158 return container_of(sd, struct ad7791_state, sd);169 return container_of(sd, struct ad7791_state, sd);
@@ -202,6 +213,7 @@ static int ad7791_read_raw(struct iio_dev *indio_dev, · 43 unmodified lines
202{213{
203 struct ad7791_state *st = iio_priv(indio_dev);214 struct ad7791_state *st = iio_priv(indio_dev);
204 bool unipolar = !!(st->mode & AD7791_MODE_UNIPOLAR);215 bool unipolar = !!(st->mode & AD7791_MODE_UNIPOLAR);
216 unsigned int rate;
205 217
206 switch (info) {218 switch (info) {
207 case IIO_CHAN_INFO_RAW:219 case IIO_CHAN_INFO_RAW:
@@ -239,63 +251,56 @@ static int ad7791_read_raw(struct iio_dev *indio_dev, · 31 unmodified lines
239 *val2 = chan->scan_type.realbits - 1;251 *val2 = chan->scan_type.realbits - 1;
240 252
241 return IIO_VAL_FRACTIONAL_LOG2;253 return IIO_VAL_FRACTIONAL_LOG2;
254 case IIO_CHAN_INFO_SAMP_FREQ:
255 rate = st->filter & AD7791_FILTER_RATE_MASK;
256 *val = ad7791_sample_freq_avail[rate][0];
257 *val2 = ad7791_sample_freq_avail[rate][1];
258 return IIO_VAL_INT_PLUS_MICRO;
242 }259 }
243 260
244 return -EINVAL;261 return -EINVAL;
245}262}
246 263
247static const char * const ad7791_sample_freq_avail[] = {264static int ad7791_write_raw(struct iio_dev *indio_dev,
248 [AD7791_FILTER_RATE_120] = "120",265 struct iio_chan_spec const *chan, int val, int val2, long mask)
249 [AD7791_FILTER_RATE_100] = "100",
250 [AD7791_FILTER_RATE_33_3] = "33.3",
251 [AD7791_FILTER_RATE_20] = "20",
252 [AD7791_FILTER_RATE_16_6] = "16.6",
253 [AD7791_FILTER_RATE_16_7] = "16.7",
254 [AD7791_FILTER_RATE_13_3] = "13.3",
255 [AD7791_FILTER_RATE_9_5] = "9.5",
256};
257
258static ssize_t ad7791_read_frequency(struct device *dev,
259 struct device_attribute *attr, char *buf)
260{266{
261 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
262 struct ad7791_state *st = iio_priv(indio_dev);267 struct ad7791_state *st = iio_priv(indio_dev);
263 unsigned int rate = st->filter & AD7791_FILTER_RATE_MASK;268 int ret, i;
264
265 return sprintf(buf, "%s\n", ad7791_sample_freq_avail[rate]);
266}
267
268static ssize_t ad7791_write_frequency(struct device *dev,
269 struct device_attribute *attr, const char *buf, size_t len)
270{
271 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
272 struct ad7791_state *st = iio_priv(indio_dev);
273 int i, ret;
274
275 i = sysfs_match_string(ad7791_sample_freq_avail, buf);
276 if (i < 0)
277 return i;
278 269
279 ret = iio_device_claim_direct_mode(indio_dev);270 ret = iio_device_claim_direct_mode(indio_dev);
280 if (ret)271 if (ret)
281 return ret;272 return ret;
282 st->filter &= ~AD7791_FILTER_RATE_MASK;
283 st->filter |= i;
284 ad_sd_write_reg(&st->sd, AD7791_REG_FILTER, sizeof(st->filter),
285 st->filter);
286 iio_device_release_direct_mode(indio_dev);
287 273
288 return len;274 switch (mask) {
289}275 case IIO_CHAN_INFO_SAMP_FREQ:
276 for (i = 0; i < ARRAY_SIZE(ad7791_sample_freq_avail); i++) {
277 if (ad7791_sample_freq_avail[i][0] == val &&
278 ad7791_sample_freq_avail[i][1] == val2)
279 break;
280 }
281
282 if (i == ARRAY_SIZE(ad7791_sample_freq_avail)) {
283 ret = -EINVAL;
284 break;
285 }
286
287 st->filter &= ~AD7791_FILTER_RATE_MASK;
288 st->filter |= i;
289 ad_sd_write_reg(&st->sd, AD7791_REG_FILTER,
290 sizeof(st->filter),
291 st->filter);
292 break;
293 default:
294 ret = -EINVAL;
295 }
290 296
291static IIO_DEV_ATTR_SAMP_FREQ(S_IWUSR | S_IRUGO,297 iio_device_release_direct_mode(indio_dev);
292 ad7791_read_frequency,298 return ret;
293 ad7791_write_frequency);299}
294 300
295static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("120 100 33.3 20 16.7 16.6 13.3 9.5");301static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("120 100 33.3 20 16.7 16.6 13.3 9.5");
296 302
297static struct attribute *ad7791_attributes[] = {303static struct attribute *ad7791_attributes[] = {
298 &iio_dev_attr_sampling_frequency.dev_attr.attr,
299 &iio_const_attr_sampling_frequency_available.dev_attr.attr,304 &iio_const_attr_sampling_frequency_available.dev_attr.attr,
300 NULL305 NULL
301};306};
@@ -306,12 +311,14 @@ static const struct attribute_group ad7791_attribute_group = { · 4 unmodified lines
306 311
307static const struct iio_info ad7791_info = {312static const struct iio_info ad7791_info = {
308 .read_raw = &ad7791_read_raw,313 .read_raw = &ad7791_read_raw,
314 .write_raw = &ad7791_write_raw,
309 .attrs = &ad7791_attribute_group,315 .attrs = &ad7791_attribute_group,
310 .validate_trigger = ad_sd_validate_trigger,316 .validate_trigger = ad_sd_validate_trigger,
311};317};
312 318
313static const struct iio_info ad7791_no_filter_info = {319static const struct iio_info ad7791_no_filter_info = {
314 .read_raw = &ad7791_read_raw,320 .read_raw = &ad7791_read_raw,
321 .write_raw = &ad7791_write_raw,
315 .validate_trigger = ad_sd_validate_trigger,322 .validate_trigger = ad_sd_validate_trigger,
316};323};
317 324
drivers/iio/adc/imx7d_adc.c+1−1
@@ -604,5 +604,5 @@ static struct platform_driver imx7d_adc_driver = { · 603 unmodified lines
604module_platform_driver(imx7d_adc_driver);604module_platform_driver(imx7d_adc_driver);
605 605
606MODULE_AUTHOR("Haibo Chen <haibo.chen@freescale.com>");606MODULE_AUTHOR("Haibo Chen <haibo.chen@freescale.com>");
607MODULE_DESCRIPTION("Freeacale IMX7D ADC driver");607MODULE_DESCRIPTION("Freescale IMX7D ADC driver");
608MODULE_LICENSE("GPL v2");608MODULE_LICENSE("GPL v2");
drivers/iio/adc/meson_saradc.c+50−33
@@ -219,15 +219,19 @@ enum meson_sar_adc_chan7_mux_sel { · 218 unmodified lines
219 CHAN7_MUX_CH7_INPUT = 0x7,219 CHAN7_MUX_CH7_INPUT = 0x7,
220};220};
221 221
222struct meson_sar_adc_data {222struct meson_sar_adc_param {
223 bool has_bl30_integration;223 bool has_bl30_integration;
224 unsigned long clock_rate;224 unsigned long clock_rate;
225 u32 bandgap_reg;225 u32 bandgap_reg;
226 unsigned int resolution;226 unsigned int resolution;
227 const char *name;
228 const struct regmap_config *regmap_config;227 const struct regmap_config *regmap_config;
229};228};
230 229
230struct meson_sar_adc_data {
231 const struct meson_sar_adc_param *param;
232 const char *name;
233};
234
231struct meson_sar_adc_priv {235struct meson_sar_adc_priv {
232 struct regmap *regmap;236 struct regmap *regmap;
233 struct regulator *vref;237 struct regulator *vref;
@@ -276,7 +280,7 @@ static int meson_sar_adc_calib_val(struct iio_dev *indio_dev, int val) · 42 unmodified lines
276 /* use val_calib = scale * val_raw + offset calibration function */280 /* use val_calib = scale * val_raw + offset calibration function */
277 tmp = div_s64((s64)val * priv->calibscale, MILLION) + priv->calibbias;281 tmp = div_s64((s64)val * priv->calibscale, MILLION) + priv->calibbias;
278 282
279 return clamp(tmp, 0, (1 << priv->data->resolution) - 1);283 return clamp(tmp, 0, (1 << priv->data->param->resolution) - 1);
280}284}
281 285
282static int meson_sar_adc_wait_busy_clear(struct iio_dev *indio_dev)286static int meson_sar_adc_wait_busy_clear(struct iio_dev *indio_dev)
@@ -328,7 +332,7 @@ static int meson_sar_adc_read_raw_sample(struct iio_dev *indio_dev, · 45 unmodified lines
328 }332 }
329 333
330 fifo_val = FIELD_GET(MESON_SAR_ADC_FIFO_RD_SAMPLE_VALUE_MASK, regval);334 fifo_val = FIELD_GET(MESON_SAR_ADC_FIFO_RD_SAMPLE_VALUE_MASK, regval);
331 fifo_val &= GENMASK(priv->data->resolution - 1, 0);335 fifo_val &= GENMASK(priv->data->param->resolution - 1, 0);
332 *val = meson_sar_adc_calib_val(indio_dev, fifo_val);336 *val = meson_sar_adc_calib_val(indio_dev, fifo_val);
333 337
334 return 0;338 return 0;
@@ -447,7 +451,7 @@ static int meson_sar_adc_lock(struct iio_dev *indio_dev) · 112 unmodified lines
447 451
448 mutex_lock(&indio_dev->mlock);452 mutex_lock(&indio_dev->mlock);
449 453
450 if (priv->data->has_bl30_integration) {454 if (priv->data->param->has_bl30_integration) {
451 /* prevent BL30 from using the SAR ADC while we are using it */455 /* prevent BL30 from using the SAR ADC while we are using it */
452 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,456 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
453 MESON_SAR_ADC_DELAY_KERNEL_BUSY,457 MESON_SAR_ADC_DELAY_KERNEL_BUSY,
@@ -475,7 +479,7 @@ static void meson_sar_adc_unlock(struct iio_dev *indio_dev) · 21 unmodified lines
475{479{
476 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);480 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
477 481
478 if (priv->data->has_bl30_integration)482 if (priv->data->param->has_bl30_integration)
479 /* allow BL30 to use the SAR ADC again */483 /* allow BL30 to use the SAR ADC again */
480 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,484 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
481 MESON_SAR_ADC_DELAY_KERNEL_BUSY, 0);485 MESON_SAR_ADC_DELAY_KERNEL_BUSY, 0);
@@ -559,7 +563,7 @@ static int meson_sar_adc_iio_info_read_raw(struct iio_dev *indio_dev, · 77 unmodified lines
559 }563 }
560 564
561 *val = ret / 1000;565 *val = ret / 1000;
562 *val2 = priv->data->resolution;566 *val2 = priv->data->param->resolution;
563 return IIO_VAL_FRACTIONAL_LOG2;567 return IIO_VAL_FRACTIONAL_LOG2;
564 568
565 case IIO_CHAN_INFO_CALIBBIAS:569 case IIO_CHAN_INFO_CALIBBIAS:
@@ -632,7 +636,7 @@ static int meson_sar_adc_init(struct iio_dev *indio_dev) · 66 unmodified lines
632 */636 */
633 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_CH7_INPUT);637 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_CH7_INPUT);
634 638
635 if (priv->data->has_bl30_integration) {639 if (priv->data->param->has_bl30_integration) {
636 /*640 /*
637 * leave sampling delay and the input clocks as configured by641 * leave sampling delay and the input clocks as configured by
638 * BL30 to make sure BL30 gets the values it expects when642 * BL30 to make sure BL30 gets the values it expects when
@@ -712,7 +716,7 @@ static int meson_sar_adc_init(struct iio_dev *indio_dev) · 73 unmodified lines
712 return ret;716 return ret;
713 }717 }
714 718
715 ret = clk_set_rate(priv->adc_clk, priv->data->clock_rate);719 ret = clk_set_rate(priv->adc_clk, priv->data->param->clock_rate);
716 if (ret) {720 if (ret) {
717 dev_err(indio_dev->dev.parent,721 dev_err(indio_dev->dev.parent,
718 "failed to set adc clock rate\n");722 "failed to set adc clock rate\n");
@@ -725,14 +729,15 @@ static int meson_sar_adc_init(struct iio_dev *indio_dev) · 6 unmodified lines
725static void meson_sar_adc_set_bandgap(struct iio_dev *indio_dev, bool on_off)729static void meson_sar_adc_set_bandgap(struct iio_dev *indio_dev, bool on_off)
726{730{
727 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);731 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
732 const struct meson_sar_adc_param *param = priv->data->param;
728 u32 enable_mask;733 u32 enable_mask;
729 734
730 if (priv->data->bandgap_reg == MESON_SAR_ADC_REG11)735 if (param->bandgap_reg == MESON_SAR_ADC_REG11)
731 enable_mask = MESON_SAR_ADC_REG11_BANDGAP_EN;736 enable_mask = MESON_SAR_ADC_REG11_BANDGAP_EN;
732 else737 else
733 enable_mask = MESON_SAR_ADC_DELTA_10_TS_VBG_EN;738 enable_mask = MESON_SAR_ADC_DELTA_10_TS_VBG_EN;
734 739
735 regmap_update_bits(priv->regmap, priv->data->bandgap_reg, enable_mask,740 regmap_update_bits(priv->regmap, param->bandgap_reg, enable_mask,
736 on_off ? enable_mask : 0);741 on_off ? enable_mask : 0);
737}742}
738 743
@@ -844,8 +849,8 @@ static int meson_sar_adc_calib(struct iio_dev *indio_dev) · 105 unmodified lines
844 int ret, nominal0, nominal1, value0, value1;849 int ret, nominal0, nominal1, value0, value1;
845 850
846 /* use points 25% and 75% for calibration */851 /* use points 25% and 75% for calibration */
847 nominal0 = (1 << priv->data->resolution) / 4;852 nominal0 = (1 << priv->data->param->resolution) / 4;
848 nominal1 = (1 << priv->data->resolution) * 3 / 4;853 nominal1 = (1 << priv->data->param->resolution) * 3 / 4;
849 854
850 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_VDD_DIV4);855 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_VDD_DIV4);
851 usleep_range(10, 20);856 usleep_range(10, 20);
@@ -883,51 +888,60 @@ static const struct iio_info meson_sar_adc_iio_info = { · 31 unmodified lines
883 .read_raw = meson_sar_adc_iio_info_read_raw,888 .read_raw = meson_sar_adc_iio_info_read_raw,
884};889};
885 890
886static const struct meson_sar_adc_data meson_sar_adc_meson8_data = {891static const struct meson_sar_adc_param meson_sar_adc_meson8_param = {
887 .has_bl30_integration = false,
888 .clock_rate = 1150000,
889 .bandgap_reg = MESON_SAR_ADC_DELTA_10,
890 .regmap_config = &meson_sar_adc_regmap_config_meson8,
891 .resolution = 10,
892 .name = "meson-meson8-saradc",
893};
894
895static const struct meson_sar_adc_data meson_sar_adc_meson8b_data = {
896 .has_bl30_integration = false,892 .has_bl30_integration = false,
897 .clock_rate = 1150000,893 .clock_rate = 1150000,
898 .bandgap_reg = MESON_SAR_ADC_DELTA_10,894 .bandgap_reg = MESON_SAR_ADC_DELTA_10,
899 .regmap_config = &meson_sar_adc_regmap_config_meson8,895 .regmap_config = &meson_sar_adc_regmap_config_meson8,
900 .resolution = 10,896 .resolution = 10,
901 .name = "meson-meson8b-saradc",
902};897};
903 898
904static const struct meson_sar_adc_data meson_sar_adc_gxbb_data = {899static const struct meson_sar_adc_param meson_sar_adc_gxbb_param = {
905 .has_bl30_integration = true,900 .has_bl30_integration = true,
906 .clock_rate = 1200000,901 .clock_rate = 1200000,
907 .bandgap_reg = MESON_SAR_ADC_REG11,902 .bandgap_reg = MESON_SAR_ADC_REG11,
908 .regmap_config = &meson_sar_adc_regmap_config_gxbb,903 .regmap_config = &meson_sar_adc_regmap_config_gxbb,
909 .resolution = 10,904 .resolution = 10,
910 .name = "meson-gxbb-saradc",
911};905};
912 906
913static const struct meson_sar_adc_data meson_sar_adc_gxl_data = {907static const struct meson_sar_adc_param meson_sar_adc_gxl_param = {
914 .has_bl30_integration = true,908 .has_bl30_integration = true,
915 .clock_rate = 1200000,909 .clock_rate = 1200000,
916 .bandgap_reg = MESON_SAR_ADC_REG11,910 .bandgap_reg = MESON_SAR_ADC_REG11,
917 .regmap_config = &meson_sar_adc_regmap_config_gxbb,911 .regmap_config = &meson_sar_adc_regmap_config_gxbb,
918 .resolution = 12,912 .resolution = 12,
913};
914
915static const struct meson_sar_adc_data meson_sar_adc_meson8_data = {
916 .param = &meson_sar_adc_meson8_param,
917 .name = "meson-meson8-saradc",
918};
919
920static const struct meson_sar_adc_data meson_sar_adc_meson8b_data = {
921 .param = &meson_sar_adc_meson8_param,
922 .name = "meson-meson8b-saradc",
923};
924
925static const struct meson_sar_adc_data meson_sar_adc_gxbb_data = {
926 .param = &meson_sar_adc_gxbb_param,
927 .name = "meson-gxbb-saradc",
928};
929
930static const struct meson_sar_adc_data meson_sar_adc_gxl_data = {
931 .param = &meson_sar_adc_gxl_param,
919 .name = "meson-gxl-saradc",932 .name = "meson-gxl-saradc",
920};933};
921 934
922static const struct meson_sar_adc_data meson_sar_adc_gxm_data = {935static const struct meson_sar_adc_data meson_sar_adc_gxm_data = {
923 .has_bl30_integration = true,936 .param = &meson_sar_adc_gxl_param,
924 .clock_rate = 1200000,
925 .bandgap_reg = MESON_SAR_ADC_REG11,
926 .regmap_config = &meson_sar_adc_regmap_config_gxbb,
927 .resolution = 12,
928 .name = "meson-gxm-saradc",937 .name = "meson-gxm-saradc",
929};938};
930 939
940static const struct meson_sar_adc_data meson_sar_adc_axg_data = {
941 .param = &meson_sar_adc_gxl_param,
942 .name = "meson-axg-saradc",
943};
944
931static const struct of_device_id meson_sar_adc_of_match[] = {945static const struct of_device_id meson_sar_adc_of_match[] = {
932 {946 {
933 .compatible = "amlogic,meson8-saradc",947 .compatible = "amlogic,meson8-saradc",
@@ -946,6 +960,9 @@ static const struct of_device_id meson_sar_adc_of_match[] = { · 12 unmodified lines
946 }, {960 }, {
947 .compatible = "amlogic,meson-gxm-saradc",961 .compatible = "amlogic,meson-gxm-saradc",
948 .data = &meson_sar_adc_gxm_data,962 .data = &meson_sar_adc_gxm_data,
963 }, {
964 .compatible = "amlogic,meson-axg-saradc",
965 .data = &meson_sar_adc_axg_data,
949 },966 },
950 {},967 {},
951};968};
@@ -1001,7 +1018,7 @@ static int meson_sar_adc_probe(struct platform_device *pdev) · 49 unmodified lines
1001 return ret;1018 return ret;
1002 1019
1003 priv->regmap = devm_regmap_init_mmio(&pdev->dev, base,1020 priv->regmap = devm_regmap_init_mmio(&pdev->dev, base,
1004 priv->data->regmap_config);1021 priv->data->param->regmap_config);
1005 if (IS_ERR(priv->regmap))1022 if (IS_ERR(priv->regmap))
1006 return PTR_ERR(priv->regmap);1023 return PTR_ERR(priv->regmap);
1007 1024
drivers/iio/adc/stm32-adc-core.c+48−18
@@ -34,9 +34,6 @@ · 33 unmodified lines
34#define STM32F4_ADC_ADCPRE_SHIFT 1634#define STM32F4_ADC_ADCPRE_SHIFT 16
35#define STM32F4_ADC_ADCPRE_MASK GENMASK(17, 16)35#define STM32F4_ADC_ADCPRE_MASK GENMASK(17, 16)
36 36
37/* STM32 F4 maximum analog clock rate (from datasheet) */
38#define STM32F4_ADC_MAX_CLK_RATE 36000000
39
40/* STM32H7 - common registers for all ADC instances */37/* STM32H7 - common registers for all ADC instances */
41#define STM32H7_ADC_CSR (STM32_ADCX_COMN_OFFSET + 0x00)38#define STM32H7_ADC_CSR (STM32_ADCX_COMN_OFFSET + 0x00)
42#define STM32H7_ADC_CCR (STM32_ADCX_COMN_OFFSET + 0x08)39#define STM32H7_ADC_CCR (STM32_ADCX_COMN_OFFSET + 0x08)
@@ -51,9 +48,6 @@ · 8 unmodified lines
51#define STM32H7_CKMODE_SHIFT 1648#define STM32H7_CKMODE_SHIFT 16
52#define STM32H7_CKMODE_MASK GENMASK(17, 16)49#define STM32H7_CKMODE_MASK GENMASK(17, 16)
53 50
54/* STM32 H7 maximum analog clock rate (from datasheet) */
55#define STM32H7_ADC_MAX_CLK_RATE 36000000
56
57/**51/**
58 * stm32_adc_common_regs - stm32 common registers, compatible dependent data52 * stm32_adc_common_regs - stm32 common registers, compatible dependent data
59 * @csr: common status register offset53 * @csr: common status register offset
@@ -74,15 +68,17 @@ struct stm32_adc_priv; · 14 unmodified lines
74 * stm32_adc_priv_cfg - stm32 core compatible configuration data68 * stm32_adc_priv_cfg - stm32 core compatible configuration data
75 * @regs: common registers for all instances69 * @regs: common registers for all instances
76 * @clk_sel: clock selection routine70 * @clk_sel: clock selection routine
71 * @max_clk_rate_hz: maximum analog clock rate (Hz, from datasheet)
77 */72 */
78struct stm32_adc_priv_cfg {73struct stm32_adc_priv_cfg {
79 const struct stm32_adc_common_regs *regs;74 const struct stm32_adc_common_regs *regs;
80 int (*clk_sel)(struct platform_device *, struct stm32_adc_priv *);75 int (*clk_sel)(struct platform_device *, struct stm32_adc_priv *);
76 u32 max_clk_rate_hz;
81};77};
82 78
83/**79/**
84 * struct stm32_adc_priv - stm32 ADC core private data80 * struct stm32_adc_priv - stm32 ADC core private data
85 * @irq: irq for ADC block81 * @irq: irq(s) for ADC block
86 * @domain: irq domain reference82 * @domain: irq domain reference
87 * @aclk: clock reference for the analog circuitry83 * @aclk: clock reference for the analog circuitry
88 * @bclk: bus clock common for all ADCs, depends on part used84 * @bclk: bus clock common for all ADCs, depends on part used
@@ -91,7 +87,7 @@ struct stm32_adc_priv_cfg { · 2 unmodified lines
91 * @common: common data for all ADC instances87 * @common: common data for all ADC instances
92 */88 */
93struct stm32_adc_priv {89struct stm32_adc_priv {
94 int irq;90 int irq[STM32_ADC_MAX_ADCS];
95 struct irq_domain *domain;91 struct irq_domain *domain;
96 struct clk *aclk;92 struct clk *aclk;
97 struct clk *bclk;93 struct clk *bclk;
@@ -133,7 +129,7 @@ static int stm32f4_adc_clk_sel(struct platform_device *pdev, · 35 unmodified lines
133 }129 }
134 130
135 for (i = 0; i < ARRAY_SIZE(stm32f4_pclk_div); i++) {131 for (i = 0; i < ARRAY_SIZE(stm32f4_pclk_div); i++) {
136 if ((rate / stm32f4_pclk_div[i]) <= STM32F4_ADC_MAX_CLK_RATE)132 if ((rate / stm32f4_pclk_div[i]) <= priv->cfg->max_clk_rate_hz)
137 break;133 break;
138 }134 }
139 if (i >= ARRAY_SIZE(stm32f4_pclk_div)) {135 if (i >= ARRAY_SIZE(stm32f4_pclk_div)) {
@@ -222,7 +218,7 @@ static int stm32h7_adc_clk_sel(struct platform_device *pdev, · 82 unmodified lines
222 if (ckmode)218 if (ckmode)
223 continue;219 continue;
224 220
225 if ((rate / div) <= STM32H7_ADC_MAX_CLK_RATE)221 if ((rate / div) <= priv->cfg->max_clk_rate_hz)
226 goto out;222 goto out;
227 }223 }
228 }224 }
@@ -242,7 +238,7 @@ static int stm32h7_adc_clk_sel(struct platform_device *pdev, · 13 unmodified lines
242 if (!ckmode)238 if (!ckmode)
243 continue;239 continue;
244 240
245 if ((rate / div) <= STM32H7_ADC_MAX_CLK_RATE)241 if ((rate / div) <= priv->cfg->max_clk_rate_hz)
246 goto out;242 goto out;
247 }243 }
248 244
@@ -328,11 +324,24 @@ static int stm32_adc_irq_probe(struct platform_device *pdev, · 79 unmodified lines
328 struct stm32_adc_priv *priv)324 struct stm32_adc_priv *priv)
329{325{
330 struct device_node *np = pdev->dev.of_node;326 struct device_node *np = pdev->dev.of_node;
327 unsigned int i;
328
329 for (i = 0; i < STM32_ADC_MAX_ADCS; i++) {
330 priv->irq[i] = platform_get_irq(pdev, i);
331 if (priv->irq[i] < 0) {
332 /*
333 * At least one interrupt must be provided, make others
334 * optional:
335 * - stm32f4/h7 shares a common interrupt.
336 * - stm32mp1, has one line per ADC (either for ADC1,
337 * ADC2 or both).
338 */
339 if (i && priv->irq[i] == -ENXIO)
340 continue;
341 dev_err(&pdev->dev, "failed to get irq\n");
331 342
332 priv->irq = platform_get_irq(pdev, 0);343 return priv->irq[i];
333 if (priv->irq < 0) {344 }
334 dev_err(&pdev->dev, "failed to get irq\n");
335 return priv->irq;
336 }345 }
337 346
338 priv->domain = irq_domain_add_simple(np, STM32_ADC_MAX_ADCS, 0,347 priv->domain = irq_domain_add_simple(np, STM32_ADC_MAX_ADCS, 0,
@@ -343,8 +352,12 @@ static int stm32_adc_irq_probe(struct platform_device *pdev, · 4 unmodified lines
343 return -ENOMEM;352 return -ENOMEM;
344 }353 }
345 354
346 irq_set_chained_handler(priv->irq, stm32_adc_irq_handler);355 for (i = 0; i < STM32_ADC_MAX_ADCS; i++) {
347 irq_set_handler_data(priv->irq, priv);356 if (priv->irq[i] < 0)
357 continue;
358 irq_set_chained_handler(priv->irq[i], stm32_adc_irq_handler);
359 irq_set_handler_data(priv->irq[i], priv);
360 }
348 361
349 return 0;362 return 0;
350}363}
@@ -353,11 +366,17 @@ static void stm32_adc_irq_remove(struct platform_device *pdev, · 2 unmodified lines
353 struct stm32_adc_priv *priv)366 struct stm32_adc_priv *priv)
354{367{
355 int hwirq;368 int hwirq;
369 unsigned int i;
356 370
357 for (hwirq = 0; hwirq < STM32_ADC_MAX_ADCS; hwirq++)371 for (hwirq = 0; hwirq < STM32_ADC_MAX_ADCS; hwirq++)
358 irq_dispose_mapping(irq_find_mapping(priv->domain, hwirq));372 irq_dispose_mapping(irq_find_mapping(priv->domain, hwirq));
359 irq_domain_remove(priv->domain);373 irq_domain_remove(priv->domain);
360 irq_set_chained_handler(priv->irq, NULL);374
375 for (i = 0; i < STM32_ADC_MAX_ADCS; i++) {
376 if (priv->irq[i] < 0)
377 continue;
378 irq_set_chained_handler(priv->irq[i], NULL);
379 }
361}380}
362 381
363static int stm32_adc_probe(struct platform_device *pdev)382static int stm32_adc_probe(struct platform_device *pdev)
@@ -497,11 +516,19 @@ static int stm32_adc_remove(struct platform_device *pdev) · 133 unmodified lines
497static const struct stm32_adc_priv_cfg stm32f4_adc_priv_cfg = {516static const struct stm32_adc_priv_cfg stm32f4_adc_priv_cfg = {
498 .regs = &stm32f4_adc_common_regs,517 .regs = &stm32f4_adc_common_regs,
499 .clk_sel = stm32f4_adc_clk_sel,518 .clk_sel = stm32f4_adc_clk_sel,
519 .max_clk_rate_hz = 36000000,
500};520};
501 521
502static const struct stm32_adc_priv_cfg stm32h7_adc_priv_cfg = {522static const struct stm32_adc_priv_cfg stm32h7_adc_priv_cfg = {
503 .regs = &stm32h7_adc_common_regs,523 .regs = &stm32h7_adc_common_regs,
504 .clk_sel = stm32h7_adc_clk_sel,524 .clk_sel = stm32h7_adc_clk_sel,
525 .max_clk_rate_hz = 36000000,
526};
527
528static const struct stm32_adc_priv_cfg stm32mp1_adc_priv_cfg = {
529 .regs = &stm32h7_adc_common_regs,
530 .clk_sel = stm32h7_adc_clk_sel,
531 .max_clk_rate_hz = 40000000,
505};532};
506 533
507static const struct of_device_id stm32_adc_of_match[] = {534static const struct of_device_id stm32_adc_of_match[] = {
@@ -511,6 +538,9 @@ static const struct of_device_id stm32_adc_of_match[] = { · 3 unmodified lines
511 }, {538 }, {
512 .compatible = "st,stm32h7-adc-core",539 .compatible = "st,stm32h7-adc-core",
513 .data = (void *)&stm32h7_adc_priv_cfg540 .data = (void *)&stm32h7_adc_priv_cfg
541 }, {
542 .compatible = "st,stm32mp1-adc-core",
543 .data = (void *)&stm32mp1_adc_priv_cfg
514 }, {544 }, {
515 },545 },
516};546};
drivers/iio/adc/stm32-adc.c+43−4
@@ -84,6 +84,7 @@ · 83 unmodified lines
84#define STM32H7_ADC_CALFACT2 0xC884#define STM32H7_ADC_CALFACT2 0xC8
85 85
86/* STM32H7_ADC_ISR - bit fields */86/* STM32H7_ADC_ISR - bit fields */
87#define STM32MP1_VREGREADY BIT(12)
87#define STM32H7_EOC BIT(2)88#define STM32H7_EOC BIT(2)
88#define STM32H7_ADRDY BIT(0)89#define STM32H7_ADRDY BIT(0)
89 90
@@ -249,6 +250,7 @@ struct stm32_adc; · 159 unmodified lines
249 * @adc_info: per instance input channels definitions250 * @adc_info: per instance input channels definitions
250 * @trigs: external trigger sources251 * @trigs: external trigger sources
251 * @clk_required: clock is required252 * @clk_required: clock is required
253 * @has_vregready: vregready status flag presence
252 * @selfcalib: optional routine for self-calibration254 * @selfcalib: optional routine for self-calibration
253 * @prepare: optional prepare routine (power-up, enable)255 * @prepare: optional prepare routine (power-up, enable)
254 * @start_conv: routine to start conversions256 * @start_conv: routine to start conversions
@@ -261,6 +263,7 @@ struct stm32_adc_cfg { · 6 unmodified lines
261 const struct stm32_adc_info *adc_info;263 const struct stm32_adc_info *adc_info;
262 struct stm32_adc_trig_info *trigs;264 struct stm32_adc_trig_info *trigs;
263 bool clk_required;265 bool clk_required;
266 bool has_vregready;
264 int (*selfcalib)(struct stm32_adc *);267 int (*selfcalib)(struct stm32_adc *);
265 int (*prepare)(struct stm32_adc *);268 int (*prepare)(struct stm32_adc *);
266 void (*start_conv)(struct stm32_adc *, bool dma);269 void (*start_conv)(struct stm32_adc *, bool dma);
@@ -695,8 +698,12 @@ static void stm32h7_adc_stop_conv(struct stm32_adc *adc) · 428 unmodified lines
695 stm32_adc_clr_bits(adc, STM32H7_ADC_CFGR, STM32H7_DMNGT_MASK);698 stm32_adc_clr_bits(adc, STM32H7_ADC_CFGR, STM32H7_DMNGT_MASK);
696}699}
697 700
698static void stm32h7_adc_exit_pwr_down(struct stm32_adc *adc)701static int stm32h7_adc_exit_pwr_down(struct stm32_adc *adc)
699{702{
703 struct iio_dev *indio_dev = iio_priv_to_dev(adc);
704 int ret;
705 u32 val;
706
700 /* Exit deep power down, then enable ADC voltage regulator */707 /* Exit deep power down, then enable ADC voltage regulator */
701 stm32_adc_clr_bits(adc, STM32H7_ADC_CR, STM32H7_DEEPPWD);708 stm32_adc_clr_bits(adc, STM32H7_ADC_CR, STM32H7_DEEPPWD);
702 stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_ADVREGEN);709 stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_ADVREGEN);
@@ -705,7 +712,20 @@ static void stm32h7_adc_exit_pwr_down(struct stm32_adc *adc) · 2 unmodified lines
705 stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_BOOST);712 stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_BOOST);
706 713
707 /* Wait for startup time */714 /* Wait for startup time */
708 usleep_range(10, 20);715 if (!adc->cfg->has_vregready) {
716 usleep_range(10, 20);
717 return 0;
718 }
719
720 ret = stm32_adc_readl_poll_timeout(STM32H7_ADC_ISR, val,
721 val & STM32MP1_VREGREADY, 100,
722 STM32_ADC_TIMEOUT_US);
723 if (ret) {
724 stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_DEEPPWD);
725 dev_err(&indio_dev->dev, "Failed to exit power down\n");
726 }
727
728 return ret;
709}729}
710 730
711static void stm32h7_adc_enter_pwr_down(struct stm32_adc *adc)731static void stm32h7_adc_enter_pwr_down(struct stm32_adc *adc)
@@ -888,7 +908,9 @@ static int stm32h7_adc_selfcalib(struct stm32_adc *adc) · 176 unmodified lines
888 int ret;908 int ret;
889 u32 val;909 u32 val;
890 910
891 stm32h7_adc_exit_pwr_down(adc);911 ret = stm32h7_adc_exit_pwr_down(adc);
912 if (ret)
913 return ret;
892 914
893 /*915 /*
894 * Select calibration mode:916 * Select calibration mode:
@@ -952,7 +974,10 @@ static int stm32h7_adc_prepare(struct stm32_adc *adc) · 57 unmodified lines
952{974{
953 int ret;975 int ret;
954 976
955 stm32h7_adc_exit_pwr_down(adc);977 ret = stm32h7_adc_exit_pwr_down(adc);
978 if (ret)
979 return ret;
980
956 stm32_adc_writel(adc, STM32H7_ADC_DIFSEL, adc->difsel);981 stm32_adc_writel(adc, STM32H7_ADC_DIFSEL, adc->difsel);
957 982
958 ret = stm32h7_adc_enable(adc);983 ret = stm32h7_adc_enable(adc);
@@ -1944,9 +1969,23 @@ static const struct stm32_adc_cfg stm32h7_adc_cfg = { · 985 unmodified lines
1944 .smp_cycles = stm32h7_adc_smp_cycles,1969 .smp_cycles = stm32h7_adc_smp_cycles,
1945};1970};
1946 1971
1972static const struct stm32_adc_cfg stm32mp1_adc_cfg = {
1973 .regs = &stm32h7_adc_regspec,
1974 .adc_info = &stm32h7_adc_info,
1975 .trigs = stm32h7_adc_trigs,
1976 .has_vregready = true,
1977 .selfcalib = stm32h7_adc_selfcalib,
1978 .start_conv = stm32h7_adc_start_conv,
1979 .stop_conv = stm32h7_adc_stop_conv,
1980 .prepare = stm32h7_adc_prepare,
1981 .unprepare = stm32h7_adc_unprepare,
1982 .smp_cycles = stm32h7_adc_smp_cycles,
1983};
1984
1947static const struct of_device_id stm32_adc_of_match[] = {1985static const struct of_device_id stm32_adc_of_match[] = {
1948 { .compatible = "st,stm32f4-adc", .data = (void *)&stm32f4_adc_cfg },1986 { .compatible = "st,stm32f4-adc", .data = (void *)&stm32f4_adc_cfg },
1949 { .compatible = "st,stm32h7-adc", .data = (void *)&stm32h7_adc_cfg },1987 { .compatible = "st,stm32h7-adc", .data = (void *)&stm32h7_adc_cfg },
1988 { .compatible = "st,stm32mp1-adc", .data = (void *)&stm32mp1_adc_cfg },
1950 {},1989 {},
1951};1990};
1952MODULE_DEVICE_TABLE(of, stm32_adc_of_match);1991MODULE_DEVICE_TABLE(of, stm32_adc_of_match);
drivers/iio/adc/stm32-dfsdm-adc.c+8−9
@@ -8,11 +8,11 @@ · 7 unmodified lines
8 8
9#include <linux/dmaengine.h>9#include <linux/dmaengine.h>
10#include <linux/dma-mapping.h>10#include <linux/dma-mapping.h>
11#include <linux/interrupt.h>11#include <linux/iio/adc/stm32-dfsdm-adc.h>
12#include <linux/iio/buffer.h>12#include <linux/iio/buffer.h>
13#include <linux/iio/hw-consumer.h>13#include <linux/iio/hw-consumer.h>
14#include <linux/iio/iio.h>
15#include <linux/iio/sysfs.h>14#include <linux/iio/sysfs.h>
15#include <linux/interrupt.h>
16#include <linux/module.h>16#include <linux/module.h>
17#include <linux/of_device.h>17#include <linux/of_device.h>
18#include <linux/platform_device.h>18#include <linux/platform_device.h>
@@ -254,7 +254,8 @@ static int stm32_dfsdm_start_filter(struct stm32_dfsdm *dfsdm, · 235 unmodified lines
254 DFSDM_CR1_RSWSTART(1));254 DFSDM_CR1_RSWSTART(1));
255}255}
256 256
257static void stm32_dfsdm_stop_filter(struct stm32_dfsdm *dfsdm, unsigned int fl_id)257static void stm32_dfsdm_stop_filter(struct stm32_dfsdm *dfsdm,
258 unsigned int fl_id)
258{259{
259 /* Disable conversion */260 /* Disable conversion */
260 regmap_update_bits(dfsdm->regmap, DFSDM_CR1(fl_id),261 regmap_update_bits(dfsdm->regmap, DFSDM_CR1(fl_id),
@@ -338,7 +339,7 @@ static int stm32_dfsdm_channel_parse_of(struct stm32_dfsdm *dfsdm, · 77 unmodified lines
338 "st,adc-channel-types", chan_idx,339 "st,adc-channel-types", chan_idx,
339 &of_str);340 &of_str);
340 if (!ret) {341 if (!ret) {
341 val = stm32_dfsdm_str2val(of_str, stm32_dfsdm_chan_type);342 val = stm32_dfsdm_str2val(of_str, stm32_dfsdm_chan_type);
342 if (val < 0)343 if (val < 0)
343 return val;344 return val;
344 } else {345 } else {
@@ -350,7 +351,7 @@ static int stm32_dfsdm_channel_parse_of(struct stm32_dfsdm *dfsdm, · 5 unmodified lines
350 "st,adc-channel-clk-src", chan_idx,351 "st,adc-channel-clk-src", chan_idx,
351 &of_str);352 &of_str);
352 if (!ret) {353 if (!ret) {
353 val = stm32_dfsdm_str2val(of_str, stm32_dfsdm_chan_src);354 val = stm32_dfsdm_str2val(of_str, stm32_dfsdm_chan_src);
354 if (val < 0)355 if (val < 0)
355 return val;356 return val;
356 } else {357 } else {
@@ -1104,7 +1105,6 @@ static int stm32_dfsdm_adc_probe(struct platform_device *pdev) · 747 unmodified lines
1104 char *name;1105 char *name;
1105 int ret, irq, val;1106 int ret, irq, val;
1106 1107
1107
1108 dev_data = of_device_get_match_data(dev);1108 dev_data = of_device_get_match_data(dev);
1109 iio = devm_iio_device_alloc(dev, sizeof(*adc));1109 iio = devm_iio_device_alloc(dev, sizeof(*adc));
1110 if (!iio) {1110 if (!iio) {
@@ -1122,8 +1122,8 @@ static int stm32_dfsdm_adc_probe(struct platform_device *pdev) · 11 unmodified lines
1122 platform_set_drvdata(pdev, adc);1122 platform_set_drvdata(pdev, adc);
1123 1123
1124 ret = of_property_read_u32(dev->of_node, "reg", &adc->fl_id);1124 ret = of_property_read_u32(dev->of_node, "reg", &adc->fl_id);
1125 if (ret != 0) {1125 if (ret != 0 || adc->fl_id >= adc->dfsdm->num_fls) {
1126 dev_err(dev, "Missing reg property\n");1126 dev_err(dev, "Missing or bad reg property\n");
1127 return -EINVAL;1127 return -EINVAL;
1128 }1128 }
1129 1129
@@ -1172,7 +1172,6 @@ static int stm32_dfsdm_adc_probe(struct platform_device *pdev) · 42 unmodified lines
1172 if (ret < 0)1172 if (ret < 0)
1173 goto err_cleanup;1173 goto err_cleanup;
1174 1174
1175 dev_err(dev, "of_platform_populate\n");
1176 if (dev_data->type == DFSDM_AUDIO) {1175 if (dev_data->type == DFSDM_AUDIO) {
1177 ret = of_platform_populate(np, NULL, NULL, dev);1176 ret = of_platform_populate(np, NULL, NULL, dev);
1178 if (ret < 0) {1177 if (ret < 0) {
drivers/iio/adc/stm32-dfsdm-core.c+26−0
@@ -25,6 +25,8 @@ struct stm32_dfsdm_dev_data { · 24 unmodified lines
25 25
26#define STM32H7_DFSDM_NUM_FILTERS 426#define STM32H7_DFSDM_NUM_FILTERS 4
27#define STM32H7_DFSDM_NUM_CHANNELS 827#define STM32H7_DFSDM_NUM_CHANNELS 8
28#define STM32MP1_DFSDM_NUM_FILTERS 6
29#define STM32MP1_DFSDM_NUM_CHANNELS 8
28 30
29static bool stm32_dfsdm_volatile_reg(struct device *dev, unsigned int reg)31static bool stm32_dfsdm_volatile_reg(struct device *dev, unsigned int reg)
30{32{
@@ -61,6 +63,21 @@ static const struct stm32_dfsdm_dev_data stm32h7_dfsdm_data = { · 30 unmodified lines
61 .regmap_cfg = &stm32h7_dfsdm_regmap_cfg,63 .regmap_cfg = &stm32h7_dfsdm_regmap_cfg,
62};64};
63 65
66static const struct regmap_config stm32mp1_dfsdm_regmap_cfg = {
67 .reg_bits = 32,
68 .val_bits = 32,
69 .reg_stride = sizeof(u32),
70 .max_register = 0x7fc,
71 .volatile_reg = stm32_dfsdm_volatile_reg,
72 .fast_io = true,
73};
74
75static const struct stm32_dfsdm_dev_data stm32mp1_dfsdm_data = {
76 .num_filters = STM32MP1_DFSDM_NUM_FILTERS,
77 .num_channels = STM32MP1_DFSDM_NUM_CHANNELS,
78 .regmap_cfg = &stm32mp1_dfsdm_regmap_cfg,
79};
80
64struct dfsdm_priv {81struct dfsdm_priv {
65 struct platform_device *pdev; /* platform device */82 struct platform_device *pdev; /* platform device */
66 83
@@ -227,6 +244,11 @@ static int stm32_dfsdm_parse_of(struct platform_device *pdev, · 160 unmodified lines
227 }244 }
228 245
229 priv->spi_clk_out_div = div_u64_rem(clk_freq, spi_freq, &rem) - 1;246 priv->spi_clk_out_div = div_u64_rem(clk_freq, spi_freq, &rem) - 1;
247 if (!priv->spi_clk_out_div) {
248 /* spi_clk_out_div == 0 means ckout is OFF */
249 dev_err(&pdev->dev, "spi-max-frequency not achievable\n");
250 return -EINVAL;
251 }
230 priv->dfsdm.spi_master_freq = spi_freq;252 priv->dfsdm.spi_master_freq = spi_freq;
231 253
232 if (rem) {254 if (rem) {
@@ -243,6 +265,10 @@ static const struct of_device_id stm32_dfsdm_of_match[] = { · 10 unmodified lines
243 .compatible = "st,stm32h7-dfsdm",265 .compatible = "st,stm32h7-dfsdm",
244 .data = &stm32h7_dfsdm_data,266 .data = &stm32h7_dfsdm_data,
245 },267 },
268 {
269 .compatible = "st,stm32mp1-dfsdm",
270 .data = &stm32mp1_dfsdm_data,
271 },
246 {}272 {}
247};273};
248MODULE_DEVICE_TABLE(of, stm32_dfsdm_of_match);274MODULE_DEVICE_TABLE(of, stm32_dfsdm_of_match);
drivers/iio/adc/stx104.c+11−0
@@ -233,6 +233,16 @@ static int stx104_gpio_get(struct gpio_chip *chip, unsigned int offset) · 232 unmodified lines
233 return !!(inb(stx104gpio->base) & BIT(offset));233 return !!(inb(stx104gpio->base) & BIT(offset));
234}234}
235 235
236static int stx104_gpio_get_multiple(struct gpio_chip *chip, unsigned long *mask,
237 unsigned long *bits)
238{
239 struct stx104_gpio *const stx104gpio = gpiochip_get_data(chip);
240
241 *bits = inb(stx104gpio->base);
242
243 return 0;
244}
245
236static void stx104_gpio_set(struct gpio_chip *chip, unsigned int offset,246static void stx104_gpio_set(struct gpio_chip *chip, unsigned int offset,
237 int value)247 int value)
238{248{
@@ -342,6 +352,7 @@ static int stx104_probe(struct device *dev, unsigned int id) · 103 unmodified lines
342 stx104gpio->chip.direction_input = stx104_gpio_direction_input;352 stx104gpio->chip.direction_input = stx104_gpio_direction_input;
343 stx104gpio->chip.direction_output = stx104_gpio_direction_output;353 stx104gpio->chip.direction_output = stx104_gpio_direction_output;
344 stx104gpio->chip.get = stx104_gpio_get;354 stx104gpio->chip.get = stx104_gpio_get;
355 stx104gpio->chip.get_multiple = stx104_gpio_get_multiple;
345 stx104gpio->chip.set = stx104_gpio_set;356 stx104gpio->chip.set = stx104_gpio_set;
346 stx104gpio->chip.set_multiple = stx104_gpio_set_multiple;357 stx104gpio->chip.set_multiple = stx104_gpio_set_multiple;
347 stx104gpio->base = base[id] + 3;358 stx104gpio->base = base[id] + 3;
drivers/iio/adc/ti-ads8688.c+45−3
@@ -17,6 +17,9 @@ · 16 unmodified lines
17#include <linux/of.h>17#include <linux/of.h>
18 18
19#include <linux/iio/iio.h>19#include <linux/iio/iio.h>
20#include <linux/iio/buffer.h>
21#include <linux/iio/trigger_consumer.h>
22#include <linux/iio/triggered_buffer.h>
20#include <linux/iio/sysfs.h>23#include <linux/iio/sysfs.h>
21 24
22#define ADS8688_CMD_REG(x) (x << 8)25#define ADS8688_CMD_REG(x) (x << 8)
@@ -155,6 +158,13 @@ static const struct attribute_group ads8688_attribute_group = { · 132 unmodified lines
155 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) \158 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) \
156 | BIT(IIO_CHAN_INFO_SCALE) \159 | BIT(IIO_CHAN_INFO_SCALE) \
157 | BIT(IIO_CHAN_INFO_OFFSET), \160 | BIT(IIO_CHAN_INFO_OFFSET), \
161 .scan_index = index, \
162 .scan_type = { \
163 .sign = 'u', \
164 .realbits = 16, \
165 .storagebits = 16, \
166 .endianness = IIO_BE, \
167 }, \
158}168}
159 169
160static const struct iio_chan_spec ads8684_channels[] = {170static const struct iio_chan_spec ads8684_channels[] = {
@@ -371,6 +381,28 @@ static const struct iio_info ads8688_info = { · 210 unmodified lines
371 .attrs = &ads8688_attribute_group,381 .attrs = &ads8688_attribute_group,
372};382};
373 383
384static irqreturn_t ads8688_trigger_handler(int irq, void *p)
385{
386 struct iio_poll_func *pf = p;
387 struct iio_dev *indio_dev = pf->indio_dev;
388 u16 buffer[8];
389 int i, j = 0;
390
391 for (i = 0; i < indio_dev->masklength; i++) {
392 if (!test_bit(i, indio_dev->active_scan_mask))
393 continue;
394 buffer[j] = ads8688_read(indio_dev, i);
395 j++;
396 }
397
398 iio_push_to_buffers_with_timestamp(indio_dev, buffer,
399 pf->timestamp);
400
401 iio_trigger_notify_done(indio_dev->trig);
402
403 return IRQ_HANDLED;
404}
405
374static const struct ads8688_chip_info ads8688_chip_info_tbl[] = {406static const struct ads8688_chip_info ads8688_chip_info_tbl[] = {
375 [ID_ADS8684] = {407 [ID_ADS8684] = {
376 .channels = ads8684_channels,408 .channels = ads8684_channels,
@@ -402,7 +434,7 @@ static int ads8688_probe(struct spi_device *spi) · 25 unmodified lines
402 434
403 ret = regulator_get_voltage(st->reg);435 ret = regulator_get_voltage(st->reg);
404 if (ret < 0)436 if (ret < 0)
405 goto error_out;437 goto err_regulator_disable;
406 438
407 st->vref_mv = ret / 1000;439 st->vref_mv = ret / 1000;
408 } else {440 } else {
@@ -430,13 +462,22 @@ static int ads8688_probe(struct spi_device *spi) · 21 unmodified lines
430 462
431 mutex_init(&st->lock);463 mutex_init(&st->lock);
432 464
465 ret = iio_triggered_buffer_setup(indio_dev, NULL, ads8688_trigger_handler, NULL);
466 if (ret < 0) {
467 dev_err(&spi->dev, "iio triggered buffer setup failed\n");
468 goto err_regulator_disable;
469 }
470
433 ret = iio_device_register(indio_dev);471 ret = iio_device_register(indio_dev);
434 if (ret)472 if (ret)
435 goto error_out;473 goto err_buffer_cleanup;
436 474
437 return 0;475 return 0;
438 476
439error_out:477err_buffer_cleanup:
478 iio_triggered_buffer_cleanup(indio_dev);
479
480err_regulator_disable:
440 if (!IS_ERR(st->reg))481 if (!IS_ERR(st->reg))
441 regulator_disable(st->reg);482 regulator_disable(st->reg);
442 483
@@ -449,6 +490,7 @@ static int ads8688_remove(struct spi_device *spi) · 6 unmodified lines
449 struct ads8688_state *st = iio_priv(indio_dev);490 struct ads8688_state *st = iio_priv(indio_dev);
450 491
451 iio_device_unregister(indio_dev);492 iio_device_unregister(indio_dev);
493 iio_triggered_buffer_cleanup(indio_dev);
452 494
453 if (!IS_ERR(st->reg))495 if (!IS_ERR(st->reg))
454 regulator_disable(st->reg);496 regulator_disable(st->reg);
drivers/iio/afe/Kconfig+19−0
@@ -0,0 +1,19 @@
1#
2# Analog Front End drivers
3#
4# When adding new entries keep the list in alphabetical order
5
6menu "Analog Front Ends"
7
8config IIO_RESCALE
9 tristate "IIO rescale"
10 depends on OF || COMPILE_TEST
11 help
12 Say yes here to build support for the IIO rescaling
13 that handles voltage dividers, current sense shunts and
14 current sense amplifiers.
15
16 To compile this driver as a module, choose M here: the
17 module will be called iio-rescale.
18
19endmenu
drivers/iio/afe/Makefile+6−0
@@ -0,0 +1,6 @@
1#
2# Makefile for industrial I/O Analog Front Ends (AFE)
3#
4
5# When adding new entries keep the list in alphabetical order
6obj-$(CONFIG_IIO_RESCALE) += iio-rescale.o
drivers/iio/afe/iio-rescale.c+359−0
@@ -0,0 +1,359 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * IIO rescale driver
4 *
5 * Copyright (C) 2018 Axentia Technologies AB
6 *
7 * Author: Peter Rosin <peda@axentia.se>
8 */
9
10#include <linux/err.h>
11#include <linux/gcd.h>
12#include <linux/iio/consumer.h>
13#include <linux/iio/iio.h>
14#include <linux/module.h>
15#include <linux/of.h>
16#include <linux/of_device.h>
17#include <linux/platform_device.h>
18#include <linux/property.h>
19
20struct rescale;
21
22struct rescale_cfg {
23 enum iio_chan_type type;
24 int (*props)(struct device *dev, struct rescale *rescale);
25};
26
27struct rescale {
28 const struct rescale_cfg *cfg;
29 struct iio_channel *source;
30 struct iio_chan_spec chan;
31 struct iio_chan_spec_ext_info *ext_info;
32 s32 numerator;
33 s32 denominator;
34};
35
36static int rescale_read_raw(struct iio_dev *indio_dev,
37 struct iio_chan_spec const *chan,
38 int *val, int *val2, long mask)
39{
40 struct rescale *rescale = iio_priv(indio_dev);
41 unsigned long long tmp;
42 int ret;
43
44 switch (mask) {
45 case IIO_CHAN_INFO_RAW:
46 return iio_read_channel_raw(rescale->source, val);
47
48 case IIO_CHAN_INFO_SCALE:
49 ret = iio_read_channel_scale(rescale->source, val, val2);
50 switch (ret) {
51 case IIO_VAL_FRACTIONAL:
52 *val *= rescale->numerator;
53 *val2 *= rescale->denominator;
54 return ret;
55 case IIO_VAL_INT:
56 *val *= rescale->numerator;
57 if (rescale->denominator == 1)
58 return ret;
59 *val2 = rescale->denominator;
60 return IIO_VAL_FRACTIONAL;
61 case IIO_VAL_FRACTIONAL_LOG2:
62 tmp = *val * 1000000000LL;
63 do_div(tmp, rescale->denominator);
64 tmp *= rescale->numerator;
65 do_div(tmp, 1000000000LL);
66 *val = tmp;
67 return ret;
68 default:
69 return -EOPNOTSUPP;
70 }
71 default:
72 return -EINVAL;
73 }
74}
75
76static int rescale_read_avail(struct iio_dev *indio_dev,
77 struct iio_chan_spec const *chan,
78 const int **vals, int *type, int *length,
79 long mask)
80{
81 struct rescale *rescale = iio_priv(indio_dev);
82
83 switch (mask) {
84 case IIO_CHAN_INFO_RAW:
85 *type = IIO_VAL_INT;
86 return iio_read_avail_channel_raw(rescale->source,
87 vals, length);
88 default:
89 return -EINVAL;
90 }
91}
92
93static const struct iio_info rescale_info = {
94 .read_raw = rescale_read_raw,
95 .read_avail = rescale_read_avail,
96};
97
98static ssize_t rescale_read_ext_info(struct iio_dev *indio_dev,
99 uintptr_t private,
100 struct iio_chan_spec const *chan,
101 char *buf)
102{
103 struct rescale *rescale = iio_priv(indio_dev);
104
105 return iio_read_channel_ext_info(rescale->source,
106 rescale->ext_info[private].name,
107 buf);
108}
109
110static ssize_t rescale_write_ext_info(struct iio_dev *indio_dev,
111 uintptr_t private,
112 struct iio_chan_spec const *chan,
113 const char *buf, size_t len)
114{
115 struct rescale *rescale = iio_priv(indio_dev);
116
117 return iio_write_channel_ext_info(rescale->source,
118 rescale->ext_info[private].name,
119 buf, len);
120}
121
122static int rescale_configure_channel(struct device *dev,
123 struct rescale *rescale)
124{
125 struct iio_chan_spec *chan = &rescale->chan;
126 struct iio_chan_spec const *schan = rescale->source->channel;
127
128 chan->indexed = 1;
129 chan->output = schan->output;
130 chan->ext_info = rescale->ext_info;
131 chan->type = rescale->cfg->type;
132
133 if (!iio_channel_has_info(schan, IIO_CHAN_INFO_RAW) ||
134 !iio_channel_has_info(schan, IIO_CHAN_INFO_SCALE)) {
135 dev_err(dev, "source channel does not support raw/scale\n");
136 return -EINVAL;
137 }
138
139 chan->info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
140 BIT(IIO_CHAN_INFO_SCALE);
141
142 if (iio_channel_has_available(schan, IIO_CHAN_INFO_RAW))
143 chan->info_mask_separate_available |= BIT(IIO_CHAN_INFO_RAW);
144
145 return 0;
146}
147
148static int rescale_current_sense_amplifier_props(struct device *dev,
149 struct rescale *rescale)
150{
151 u32 sense;
152 u32 gain_mult = 1;
153 u32 gain_div = 1;
154 u32 factor;
155 int ret;
156
157 ret = device_property_read_u32(dev, "sense-resistor-micro-ohms",
158 &sense);
159 if (ret) {
160 dev_err(dev, "failed to read the sense resistance: %d\n", ret);
161 return ret;
162 }
163
164 device_property_read_u32(dev, "sense-gain-mult", &gain_mult);
165 device_property_read_u32(dev, "sense-gain-div", &gain_div);
166
167 /*
168 * Calculate the scaling factor, 1 / (gain * sense), or
169 * gain_div / (gain_mult * sense), while trying to keep the
170 * numerator/denominator from overflowing.
171 */
172 factor = gcd(sense, 1000000);
173 rescale->numerator = 1000000 / factor;
174 rescale->denominator = sense / factor;
175
176 factor = gcd(rescale->numerator, gain_mult);
177 rescale->numerator /= factor;
178 rescale->denominator *= gain_mult / factor;
179
180 factor = gcd(rescale->denominator, gain_div);
181 rescale->numerator *= gain_div / factor;
182 rescale->denominator /= factor;
183
184 return 0;
185}
186
187static int rescale_current_sense_shunt_props(struct device *dev,
188 struct rescale *rescale)
189{
190 u32 shunt;
191 u32 factor;
192 int ret;
193
194 ret = device_property_read_u32(dev, "shunt-resistor-micro-ohms",
195 &shunt);
196 if (ret) {
197 dev_err(dev, "failed to read the shunt resistance: %d\n", ret);
198 return ret;
199 }
200
201 factor = gcd(shunt, 1000000);
202 rescale->numerator = 1000000 / factor;
203 rescale->denominator = shunt / factor;
204
205 return 0;
206}
207
208static int rescale_voltage_divider_props(struct device *dev,
209 struct rescale *rescale)
210{
211 int ret;
212 u32 factor;
213
214 ret = device_property_read_u32(dev, "output-ohms",
215 &rescale->denominator);
216 if (ret) {
217 dev_err(dev, "failed to read output-ohms: %d\n", ret);
218 return ret;
219 }
220
221 ret = device_property_read_u32(dev, "full-ohms",
222 &rescale->numerator);
223 if (ret) {
224 dev_err(dev, "failed to read full-ohms: %d\n", ret);
225 return ret;
226 }
227
228 factor = gcd(rescale->numerator, rescale->denominator);
229 rescale->numerator /= factor;
230 rescale->denominator /= factor;
231
232 return 0;
233}
234
235enum rescale_variant {
236 CURRENT_SENSE_AMPLIFIER,
237 CURRENT_SENSE_SHUNT,
238 VOLTAGE_DIVIDER,
239};
240
241static const struct rescale_cfg rescale_cfg[] = {
242 [CURRENT_SENSE_AMPLIFIER] = {
243 .type = IIO_CURRENT,
244 .props = rescale_current_sense_amplifier_props,
245 },
246 [CURRENT_SENSE_SHUNT] = {
247 .type = IIO_CURRENT,
248 .props = rescale_current_sense_shunt_props,
249 },
250 [VOLTAGE_DIVIDER] = {
251 .type = IIO_VOLTAGE,
252 .props = rescale_voltage_divider_props,
253 },
254};
255
256static const struct of_device_id rescale_match[] = {
257 { .compatible = "current-sense-amplifier",
258 .data = &rescale_cfg[CURRENT_SENSE_AMPLIFIER], },
259 { .compatible = "current-sense-shunt",
260 .data = &rescale_cfg[CURRENT_SENSE_SHUNT], },
261 { .compatible = "voltage-divider",
262 .data = &rescale_cfg[VOLTAGE_DIVIDER], },
263 { /* sentinel */ }
264};
265MODULE_DEVICE_TABLE(of, rescale_match);
266
267static int rescale_probe(struct platform_device *pdev)
268{
269 struct device *dev = &pdev->dev;
270 struct iio_dev *indio_dev;
271 struct iio_channel *source;
272 struct rescale *rescale;
273 int sizeof_ext_info;
274 int sizeof_priv;
275 int i;
276 int ret;
277
278 source = devm_iio_channel_get(dev, NULL);
279 if (IS_ERR(source)) {
280 if (PTR_ERR(source) != -EPROBE_DEFER)
281 dev_err(dev, "failed to get source channel\n");
282 return PTR_ERR(source);
283 }
284
285 sizeof_ext_info = iio_get_channel_ext_info_count(source);
286 if (sizeof_ext_info) {
287 sizeof_ext_info += 1; /* one extra entry for the sentinel */
288 sizeof_ext_info *= sizeof(*rescale->ext_info);
289 }
290
291 sizeof_priv = sizeof(*rescale) + sizeof_ext_info;
292
293 indio_dev = devm_iio_device_alloc(dev, sizeof_priv);
294 if (!indio_dev)
295 return -ENOMEM;
296
297 rescale = iio_priv(indio_dev);
298
299 rescale->cfg = of_device_get_match_data(dev);
300 rescale->numerator = 1;
301 rescale->denominator = 1;
302
303 ret = rescale->cfg->props(dev, rescale);
304 if (ret)
305 return ret;
306
307 if (!rescale->numerator || !rescale->denominator) {
308 dev_err(dev, "invalid scaling factor.\n");
309 return -EINVAL;
310 }
311
312 platform_set_drvdata(pdev, indio_dev);
313
314 rescale->source = source;
315
316 indio_dev->name = dev_name(dev);
317 indio_dev->dev.parent = dev;
318 indio_dev->info = &rescale_info;
319 indio_dev->modes = INDIO_DIRECT_MODE;
320 indio_dev->channels = &rescale->chan;
321 indio_dev->num_channels = 1;
322 if (sizeof_ext_info) {
323 rescale->ext_info = devm_kmemdup(dev,
324 source->channel->ext_info,
325 sizeof_ext_info, GFP_KERNEL);
326 if (!rescale->ext_info)
327 return -ENOMEM;
328
329 for (i = 0; rescale->ext_info[i].name; ++i) {
330 struct iio_chan_spec_ext_info *ext_info =
331 &rescale->ext_info[i];
332
333 if (source->channel->ext_info[i].read)
334 ext_info->read = rescale_read_ext_info;
335 if (source->channel->ext_info[i].write)
336 ext_info->write = rescale_write_ext_info;
337 ext_info->private = i;
338 }
339 }
340
341 ret = rescale_configure_channel(dev, rescale);
342 if (ret)
343 return ret;
344
345 return devm_iio_device_register(dev, indio_dev);
346}
347
348static struct platform_driver rescale_driver = {
349 .probe = rescale_probe,
350 .driver = {
351 .name = "iio-rescale",
352 .of_match_table = rescale_match,
353 },
354};
355module_platform_driver(rescale_driver);
356
357MODULE_DESCRIPTION("IIO rescale driver");
358MODULE_AUTHOR("Peter Rosin <peda@axentia.se>");
359MODULE_LICENSE("GPL v2");
drivers/iio/amplifiers/ad8366.c+4−2
@@ -161,12 +161,14 @@ static int ad8366_probe(struct spi_device *spi) · 160 unmodified lines
161 indio_dev->channels = ad8366_channels;161 indio_dev->channels = ad8366_channels;
162 indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);162 indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
163 163
164 ret = ad8366_write(indio_dev, 0 , 0);
165 if (ret < 0)
166 goto error_disable_reg;
167
164 ret = iio_device_register(indio_dev);168 ret = iio_device_register(indio_dev);
165 if (ret)169 if (ret)
166 goto error_disable_reg;170 goto error_disable_reg;
167 171
168 ad8366_write(indio_dev, 0, 0);
169
170 return 0;172 return 0;
171 173
172error_disable_reg:174error_disable_reg:
drivers/iio/chemical/atlas-ph-sensor.c+7−7
@@ -61,9 +61,9 @@ · 60 unmodified lines
61#define ATLAS_REG_ORP_CALIB_STATUS 0x0d61#define ATLAS_REG_ORP_CALIB_STATUS 0x0d
62#define ATLAS_REG_ORP_DATA 0x0e62#define ATLAS_REG_ORP_DATA 0x0e
63 63
64#define ATLAS_PH_INT_TIME_IN_US 45000064#define ATLAS_PH_INT_TIME_IN_MS 450
65#define ATLAS_EC_INT_TIME_IN_US 65000065#define ATLAS_EC_INT_TIME_IN_MS 650
66#define ATLAS_ORP_INT_TIME_IN_US 45000066#define ATLAS_ORP_INT_TIME_IN_MS 450
67 67
68enum {68enum {
69 ATLAS_PH_SM,69 ATLAS_PH_SM,
@@ -270,21 +270,21 @@ static struct atlas_device atlas_devices[] = { · 200 unmodified lines
270 .num_channels = 3,270 .num_channels = 3,
271 .data_reg = ATLAS_REG_PH_DATA,271 .data_reg = ATLAS_REG_PH_DATA,
272 .calibration = &atlas_check_ph_calibration,272 .calibration = &atlas_check_ph_calibration,
273 .delay = ATLAS_PH_INT_TIME_IN_US,273 .delay = ATLAS_PH_INT_TIME_IN_MS,
274 },274 },
275 [ATLAS_EC_SM] = {275 [ATLAS_EC_SM] = {
276 .channels = atlas_ec_channels,276 .channels = atlas_ec_channels,
277 .num_channels = 5,277 .num_channels = 5,
278 .data_reg = ATLAS_REG_EC_DATA,278 .data_reg = ATLAS_REG_EC_DATA,
279 .calibration = &atlas_check_ec_calibration,279 .calibration = &atlas_check_ec_calibration,
280 .delay = ATLAS_EC_INT_TIME_IN_US,280 .delay = ATLAS_EC_INT_TIME_IN_MS,
281 },281 },
282 [ATLAS_ORP_SM] = {282 [ATLAS_ORP_SM] = {
283 .channels = atlas_orp_channels,283 .channels = atlas_orp_channels,
284 .num_channels = 2,284 .num_channels = 2,
285 .data_reg = ATLAS_REG_ORP_DATA,285 .data_reg = ATLAS_REG_ORP_DATA,
286 .calibration = &atlas_check_orp_calibration,286 .calibration = &atlas_check_orp_calibration,
287 .delay = ATLAS_ORP_INT_TIME_IN_US,287 .delay = ATLAS_ORP_INT_TIME_IN_MS,
288 },288 },
289};289};
290 290
@@ -393,7 +393,7 @@ static int atlas_read_measurement(struct atlas_data *data, int reg, __be32 *val) · 102 unmodified lines
393 }393 }
394 394
395 if (suspended)395 if (suspended)
396 usleep_range(data->chip->delay, data->chip->delay + 100000);396 msleep(data->chip->delay);
397 397
398 ret = regmap_bulk_read(data->regmap, reg, (u8 *) val, sizeof(*val));398 ret = regmap_bulk_read(data->regmap, reg, (u8 *) val, sizeof(*val));
399 399
drivers/iio/common/cros_ec_sensors/cros_ec_sensors.c+1−2
@@ -19,6 +19,7 @@ · 18 unmodified lines
19#include <linux/delay.h>19#include <linux/delay.h>
20#include <linux/device.h>20#include <linux/device.h>
21#include <linux/iio/buffer.h>21#include <linux/iio/buffer.h>
22#include <linux/iio/common/cros_ec_sensors_core.h>
22#include <linux/iio/iio.h>23#include <linux/iio/iio.h>
23#include <linux/iio/kfifo_buf.h>24#include <linux/iio/kfifo_buf.h>
24#include <linux/iio/trigger_consumer.h>25#include <linux/iio/trigger_consumer.h>
@@ -31,8 +32,6 @@ · 6 unmodified lines
31#include <linux/slab.h>32#include <linux/slab.h>
32#include <linux/sysfs.h>33#include <linux/sysfs.h>
33 34
34#include "cros_ec_sensors_core.h"
35
36#define CROS_EC_SENSORS_MAX_CHANNELS 435#define CROS_EC_SENSORS_MAX_CHANNELS 4
37 36
38/* State data for ec_sensors iio driver. */37/* State data for ec_sensors iio driver. */
drivers/iio/common/cros_ec_sensors/cros_ec_sensors_core.c+3−6
@@ -16,6 +16,7 @@ · 15 unmodified lines
16#include <linux/delay.h>16#include <linux/delay.h>
17#include <linux/device.h>17#include <linux/device.h>
18#include <linux/iio/buffer.h>18#include <linux/iio/buffer.h>
19#include <linux/iio/common/cros_ec_sensors_core.h>
19#include <linux/iio/iio.h>20#include <linux/iio/iio.h>
20#include <linux/iio/kfifo_buf.h>21#include <linux/iio/kfifo_buf.h>
21#include <linux/iio/trigger_consumer.h>22#include <linux/iio/trigger_consumer.h>
@@ -27,8 +28,6 @@ · 5 unmodified lines
27#include <linux/sysfs.h>28#include <linux/sysfs.h>
28#include <linux/platform_device.h>29#include <linux/platform_device.h>
29 30
30#include "cros_ec_sensors_core.h"
31
32static char *cros_ec_loc[] = {31static char *cros_ec_loc[] = {
33 [MOTIONSENSE_LOC_BASE] = "base",32 [MOTIONSENSE_LOC_BASE] = "base",
34 [MOTIONSENSE_LOC_LID] = "lid",33 [MOTIONSENSE_LOC_LID] = "lid",
@@ -448,8 +447,7 @@ EXPORT_SYMBOL_GPL(cros_ec_sensors_core_write); · 413 unmodified lines
448 447
449static int __maybe_unused cros_ec_sensors_prepare(struct device *dev)448static int __maybe_unused cros_ec_sensors_prepare(struct device *dev)
450{449{
451 struct platform_device *pdev = to_platform_device(dev);450 struct iio_dev *indio_dev = dev_get_drvdata(dev);
452 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
453 struct cros_ec_sensors_core_state *st = iio_priv(indio_dev);451 struct cros_ec_sensors_core_state *st = iio_priv(indio_dev);
454 452
455 if (st->curr_sampl_freq == 0)453 if (st->curr_sampl_freq == 0)
@@ -471,8 +469,7 @@ static int __maybe_unused cros_ec_sensors_prepare(struct device *dev) · 15 unmodified lines
471 469
472static void __maybe_unused cros_ec_sensors_complete(struct device *dev)470static void __maybe_unused cros_ec_sensors_complete(struct device *dev)
473{471{
474 struct platform_device *pdev = to_platform_device(dev);472 struct iio_dev *indio_dev = dev_get_drvdata(dev);
475 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
476 struct cros_ec_sensors_core_state *st = iio_priv(indio_dev);473 struct cros_ec_sensors_core_state *st = iio_priv(indio_dev);
477 474
478 if (st->curr_sampl_freq == 0)475 if (st->curr_sampl_freq == 0)
drivers/iio/common/hid-sensors/hid-sensor-trigger.c+3−6
@@ -304,8 +304,7 @@ EXPORT_SYMBOL(hid_sensor_setup_trigger); · 303 unmodified lines
304 304
305static int __maybe_unused hid_sensor_suspend(struct device *dev)305static int __maybe_unused hid_sensor_suspend(struct device *dev)
306{306{
307 struct platform_device *pdev = to_platform_device(dev);307 struct iio_dev *indio_dev = dev_get_drvdata(dev);
308 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
309 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);308 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);
310 309
311 return _hid_sensor_power_state(attrb, false);310 return _hid_sensor_power_state(attrb, false);
@@ -313,8 +312,7 @@ static int __maybe_unused hid_sensor_suspend(struct device *dev) · 1 unmodified line
313 312
314static int __maybe_unused hid_sensor_resume(struct device *dev)313static int __maybe_unused hid_sensor_resume(struct device *dev)
315{314{
316 struct platform_device *pdev = to_platform_device(dev);315 struct iio_dev *indio_dev = dev_get_drvdata(dev);
317 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
318 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);316 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);
319 schedule_work(&attrb->work);317 schedule_work(&attrb->work);
320 return 0;318 return 0;
@@ -322,8 +320,7 @@ static int __maybe_unused hid_sensor_resume(struct device *dev) · 1 unmodified line
322 320
323static int __maybe_unused hid_sensor_runtime_resume(struct device *dev)321static int __maybe_unused hid_sensor_runtime_resume(struct device *dev)
324{322{
325 struct platform_device *pdev = to_platform_device(dev);323 struct iio_dev *indio_dev = dev_get_drvdata(dev);
326 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
327 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);324 struct hid_sensor_common *attrb = iio_device_get_drvdata(indio_dev);
328 return _hid_sensor_power_state(attrb, true);325 return _hid_sensor_power_state(attrb, true);
329}326}
drivers/iio/dac/Kconfig+29−4
@@ -131,16 +131,31 @@ config LTC2632 · 130 unmodified lines
131 module will be called ltc2632.131 module will be called ltc2632.
132 132
133config AD5686133config AD5686
134 tristate "Analog Devices AD5686R/AD5685R/AD5684R DAC SPI driver"134 tristate
135
136config AD5686_SPI
137 tristate "Analog Devices AD5686 and similar multi-channel DACs (SPI)"
135 depends on SPI138 depends on SPI
139 select AD5686
136 help140 help
137 Say yes here to build support for Analog Devices AD5686R, AD5685R,141 Say yes here to build support for Analog Devices AD5672R, AD5676,
138 AD5684R, AD5791 Voltage Output Digital to142 AD5676R, AD5684, AD5684R, AD5684R, AD5685R, AD5686, AD5686R.
139 Analog Converter.143 Voltage Output Digital to Analog Converter.
140 144
141 To compile this driver as a module, choose M here: the145 To compile this driver as a module, choose M here: the
142 module will be called ad5686.146 module will be called ad5686.
143 147
148config AD5696_I2C
149 tristate "Analog Devices AD5696 and similar multi-channel DACs (I2C)"
150 depends on I2C
151 select AD5686
152 help
153 Say yes here to build support for Analog Devices AD5671R, AD5675R,
154 AD5694, AD5694R, AD5695R, AD5696, AD5696R Voltage Output Digital to
155 Analog Converter.
156 To compile this driver as a module, choose M here: the module will be
157 called ad5696.
158
144config AD5755159config AD5755
145 tristate "Analog Devices AD5755/AD5755-1/AD5757/AD5735/AD5737 DAC driver"160 tristate "Analog Devices AD5755/AD5755-1/AD5757/AD5735/AD5737 DAC driver"
146 depends on SPI_MASTER161 depends on SPI_MASTER
@@ -321,6 +336,16 @@ config TI_DAC082S085 · 174 unmodified lines
321 336
322 If compiled as a module, it will be called ti-dac082s085.337 If compiled as a module, it will be called ti-dac082s085.
323 338
339config TI_DAC5571
340 tristate "Texas Instruments 8/10/12/16-bit 1/2/4-channel DAC driver"
341 depends on I2C
342 help
343 Driver for the Texas Instruments
344 DAC5571, DAC6571, DAC7571, DAC5574, DAC6574, DAC7574, DAC5573,
345 DAC6573, DAC7573, DAC8571, DAC8574.
346
347 If compiled as a module, it will be called ti-dac5571.
348
324config VF610_DAC349config VF610_DAC
325 tristate "Vybrid vf610 DAC driver"350 tristate "Vybrid vf610 DAC driver"
326 depends on OF351 depends on OF
drivers/iio/dac/Makefile+3−0
@@ -20,6 +20,8 @@ obj-$(CONFIG_AD5761) += ad5761.o · 19 unmodified lines
20obj-$(CONFIG_AD5764) += ad5764.o20obj-$(CONFIG_AD5764) += ad5764.o
21obj-$(CONFIG_AD5791) += ad5791.o21obj-$(CONFIG_AD5791) += ad5791.o
22obj-$(CONFIG_AD5686) += ad5686.o22obj-$(CONFIG_AD5686) += ad5686.o
23obj-$(CONFIG_AD5686_SPI) += ad5686-spi.o
24obj-$(CONFIG_AD5696_I2C) += ad5696-i2c.o
23obj-$(CONFIG_AD7303) += ad7303.o25obj-$(CONFIG_AD7303) += ad7303.o
24obj-$(CONFIG_AD8801) += ad8801.o26obj-$(CONFIG_AD8801) += ad8801.o
25obj-$(CONFIG_CIO_DAC) += cio-dac.o27obj-$(CONFIG_CIO_DAC) += cio-dac.o
@@ -35,4 +37,5 @@ obj-$(CONFIG_MCP4922) += mcp4922.o · 9 unmodified lines
35obj-$(CONFIG_STM32_DAC_CORE) += stm32-dac-core.o37obj-$(CONFIG_STM32_DAC_CORE) += stm32-dac-core.o
36obj-$(CONFIG_STM32_DAC) += stm32-dac.o38obj-$(CONFIG_STM32_DAC) += stm32-dac.o
37obj-$(CONFIG_TI_DAC082S085) += ti-dac082s085.o39obj-$(CONFIG_TI_DAC082S085) += ti-dac082s085.o
40obj-$(CONFIG_TI_DAC5571) += ti-dac5571.o
38obj-$(CONFIG_VF610_DAC) += vf610_dac.o41obj-$(CONFIG_VF610_DAC) += vf610_dac.o
drivers/iio/dac/ad5686-spi.c+119−0
@@ -0,0 +1,119 @@
1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * AD5672R, AD5676, AD5676R, AD5681R, AD5682R, AD5683, AD5683R,
4 * AD5684, AD5684R, AD5685R, AD5686, AD5686R
5 * Digital to analog converters driver
6 *
7 * Copyright 2018 Analog Devices Inc.
8 */
9
10#include "ad5686.h"
11
12#include <linux/module.h>
13#include <linux/spi/spi.h>
14
15static int ad5686_spi_write(struct ad5686_state *st,
16 u8 cmd, u8 addr, u16 val)
17{
18 struct spi_device *spi = to_spi_device(st->dev);
19 u8 tx_len, *buf;
20
21 switch (st->chip_info->regmap_type) {
22 case AD5683_REGMAP:
23 st->data[0].d32 = cpu_to_be32(AD5686_CMD(cmd) |
24 AD5683_DATA(val));
25 buf = &st->data[0].d8[1];
26 tx_len = 3;
27 break;
28 case AD5686_REGMAP:
29 st->data[0].d32 = cpu_to_be32(AD5686_CMD(cmd) |
30 AD5686_ADDR(addr) |
31 val);
32 buf = &st->data[0].d8[1];
33 tx_len = 3;
34 break;
35 default:
36 return -EINVAL;
37 }
38
39 return spi_write(spi, buf, tx_len);
40}
41
42static int ad5686_spi_read(struct ad5686_state *st, u8 addr)
43{
44 struct spi_transfer t[] = {
45 {
46 .tx_buf = &st->data[0].d8[1],
47 .len = 3,
48 .cs_change = 1,
49 }, {
50 .tx_buf = &st->data[1].d8[1],
51 .rx_buf = &st->data[2].d8[1],
52 .len = 3,
53 },
54 };
55 struct spi_device *spi = to_spi_device(st->dev);
56 u8 cmd = 0;
57 int ret;
58
59 if (st->chip_info->regmap_type == AD5686_REGMAP)
60 cmd = AD5686_CMD_READBACK_ENABLE;
61 else if (st->chip_info->regmap_type == AD5683_REGMAP)
62 cmd = AD5686_CMD_READBACK_ENABLE_V2;
63
64 st->data[0].d32 = cpu_to_be32(AD5686_CMD(cmd) |
65 AD5686_ADDR(addr));
66 st->data[1].d32 = cpu_to_be32(AD5686_CMD(AD5686_CMD_NOOP));
67
68 ret = spi_sync_transfer(spi, t, ARRAY_SIZE(t));
69 if (ret < 0)
70 return ret;
71
72 return be32_to_cpu(st->data[2].d32);
73}
74
75static int ad5686_spi_probe(struct spi_device *spi)
76{
77 const struct spi_device_id *id = spi_get_device_id(spi);
78
79 return ad5686_probe(&spi->dev, id->driver_data, id->name,
80 ad5686_spi_write, ad5686_spi_read);
81}
82
83static int ad5686_spi_remove(struct spi_device *spi)
84{
85 return ad5686_remove(&spi->dev);
86}
87
88static const struct spi_device_id ad5686_spi_id[] = {
89 {"ad5672r", ID_AD5672R},
90 {"ad5676", ID_AD5676},
91 {"ad5676r", ID_AD5676R},
92 {"ad5681r", ID_AD5681R},
93 {"ad5682r", ID_AD5682R},
94 {"ad5683", ID_AD5683},
95 {"ad5683r", ID_AD5683R},
96 {"ad5684", ID_AD5684},
97 {"ad5684r", ID_AD5684R},
98 {"ad5685", ID_AD5685R}, /* Does not exist */
99 {"ad5685r", ID_AD5685R},
100 {"ad5686", ID_AD5686},
101 {"ad5686r", ID_AD5686R},
102 {}
103};
104MODULE_DEVICE_TABLE(spi, ad5686_spi_id);
105
106static struct spi_driver ad5686_spi_driver = {
107 .driver = {
108 .name = "ad5686",
109 },
110 .probe = ad5686_spi_probe,
111 .remove = ad5686_spi_remove,
112 .id_table = ad5686_spi_id,
113};
114
115module_spi_driver(ad5686_spi_driver);
116
117MODULE_AUTHOR("Stefan Popa <stefan.popa@analog.com>");
118MODULE_DESCRIPTION("Analog Devices AD5686 and similar multi-channel DACs");
119MODULE_LICENSE("GPL v2");
drivers/iio/dac/ad5686.c+245−183
@@ -1,9 +1,8 @@
1// SPDX-License-Identifier: GPL-2.0+
1/*2/*
2 * AD5686R, AD5685R, AD5684R Digital to analog converters driver3 * AD5686R, AD5685R, AD5684R Digital to analog converters driver
3 *4 *
4 * Copyright 2011 Analog Devices Inc.5 * Copyright 2011 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2.
7 */6 */
8 7
9#include <linux/interrupt.h>8#include <linux/interrupt.h>
@@ -11,7 +10,6 @@ · 1 unmodified line
11#include <linux/device.h>10#include <linux/device.h>
12#include <linux/module.h>11#include <linux/module.h>
13#include <linux/kernel.h>12#include <linux/kernel.h>
14#include <linux/spi/spi.h>
15#include <linux/slab.h>13#include <linux/slab.h>
16#include <linux/sysfs.h>14#include <linux/sysfs.h>
17#include <linux/regulator/consumer.h>15#include <linux/regulator/consumer.h>
@@ -19,116 +17,7 @@ · 1 unmodified line
19#include <linux/iio/iio.h>17#include <linux/iio/iio.h>
20#include <linux/iio/sysfs.h>18#include <linux/iio/sysfs.h>
21 19
22#define AD5686_DAC_CHANNELS 420#include "ad5686.h"
23
24#define AD5686_ADDR(x) ((x) << 16)
25#define AD5686_CMD(x) ((x) << 20)
26
27#define AD5686_ADDR_DAC(chan) (0x1 << (chan))
28#define AD5686_ADDR_ALL_DAC 0xF
29
30#define AD5686_CMD_NOOP 0x0
31#define AD5686_CMD_WRITE_INPUT_N 0x1
32#define AD5686_CMD_UPDATE_DAC_N 0x2
33#define AD5686_CMD_WRITE_INPUT_N_UPDATE_N 0x3
34#define AD5686_CMD_POWERDOWN_DAC 0x4
35#define AD5686_CMD_LDAC_MASK 0x5
36#define AD5686_CMD_RESET 0x6
37#define AD5686_CMD_INTERNAL_REFER_SETUP 0x7
38#define AD5686_CMD_DAISY_CHAIN_ENABLE 0x8
39#define AD5686_CMD_READBACK_ENABLE 0x9
40
41#define AD5686_LDAC_PWRDN_NONE 0x0
42#define AD5686_LDAC_PWRDN_1K 0x1
43#define AD5686_LDAC_PWRDN_100K 0x2
44#define AD5686_LDAC_PWRDN_3STATE 0x3
45
46/**
47 * struct ad5686_chip_info - chip specific information
48 * @int_vref_mv: AD5620/40/60: the internal reference voltage
49 * @channel: channel specification
50*/
51
52struct ad5686_chip_info {
53 u16 int_vref_mv;
54 struct iio_chan_spec channel[AD5686_DAC_CHANNELS];
55};
56
57/**
58 * struct ad5446_state - driver instance specific data
59 * @spi: spi_device
60 * @chip_info: chip model specific constants, available modes etc
61 * @reg: supply regulator
62 * @vref_mv: actual reference voltage used
63 * @pwr_down_mask: power down mask
64 * @pwr_down_mode: current power down mode
65 * @data: spi transfer buffers
66 */
67
68struct ad5686_state {
69 struct spi_device *spi;
70 const struct ad5686_chip_info *chip_info;
71 struct regulator *reg;
72 unsigned short vref_mv;
73 unsigned pwr_down_mask;
74 unsigned pwr_down_mode;
75 /*
76 * DMA (thus cache coherency maintenance) requires the
77 * transfer buffers to live in their own cache lines.
78 */
79
80 union {
81 __be32 d32;
82 u8 d8[4];
83 } data[3] ____cacheline_aligned;
84};
85
86/**
87 * ad5686_supported_device_ids:
88 */
89
90enum ad5686_supported_device_ids {
91 ID_AD5684,
92 ID_AD5685,
93 ID_AD5686,
94};
95static int ad5686_spi_write(struct ad5686_state *st,
96 u8 cmd, u8 addr, u16 val, u8 shift)
97{
98 val <<= shift;
99
100 st->data[0].d32 = cpu_to_be32(AD5686_CMD(cmd) |
101 AD5686_ADDR(addr) |
102 val);
103
104 return spi_write(st->spi, &st->data[0].d8[1], 3);
105}
106
107static int ad5686_spi_read(struct ad5686_state *st, u8 addr)
108{
109 struct spi_transfer t[] = {
110 {
111 .tx_buf = &st->data[0].d8[1],
112 .len = 3,
113 .cs_change = 1,
114 }, {
115 .tx_buf = &st->data[1].d8[1],
116 .rx_buf = &st->data[2].d8[1],
117 .len = 3,
118 },
119 };
120 int ret;
121
122 st->data[0].d32 = cpu_to_be32(AD5686_CMD(AD5686_CMD_READBACK_ENABLE) |
123 AD5686_ADDR(addr));
124 st->data[1].d32 = cpu_to_be32(AD5686_CMD(AD5686_CMD_NOOP));
125
126 ret = spi_sync_transfer(st->spi, t, ARRAY_SIZE(t));
127 if (ret < 0)
128 return ret;
129
130 return be32_to_cpu(st->data[2].d32);
131}
132 21
133static const char * const ad5686_powerdown_modes[] = {22static const char * const ad5686_powerdown_modes[] = {
134 "1kohm_to_gnd",23 "1kohm_to_gnd",
@@ -137,7 +26,7 @@ static const char * const ad5686_powerdown_modes[] = { · 2 unmodified lines
137};26};
138 27
139static int ad5686_get_powerdown_mode(struct iio_dev *indio_dev,28static int ad5686_get_powerdown_mode(struct iio_dev *indio_dev,
140 const struct iio_chan_spec *chan)29 const struct iio_chan_spec *chan)
141{30{
142 struct ad5686_state *st = iio_priv(indio_dev);31 struct ad5686_state *st = iio_priv(indio_dev);
143 32
@@ -145,7 +34,8 @@ static int ad5686_get_powerdown_mode(struct iio_dev *indio_dev, · 1 unmodified line
145}34}
146 35
147static int ad5686_set_powerdown_mode(struct iio_dev *indio_dev,36static int ad5686_set_powerdown_mode(struct iio_dev *indio_dev,
148 const struct iio_chan_spec *chan, unsigned int mode)37 const struct iio_chan_spec *chan,
38 unsigned int mode)
149{39{
150 struct ad5686_state *st = iio_priv(indio_dev);40 struct ad5686_state *st = iio_priv(indio_dev);
151 41
@@ -163,21 +53,25 @@ static const struct iio_enum ad5686_powerdown_mode_enum = { · 11 unmodified lines
163};53};
164 54
165static ssize_t ad5686_read_dac_powerdown(struct iio_dev *indio_dev,55static ssize_t ad5686_read_dac_powerdown(struct iio_dev *indio_dev,
166 uintptr_t private, const struct iio_chan_spec *chan, char *buf)56 uintptr_t private, const struct iio_chan_spec *chan, char *buf)
167{57{
168 struct ad5686_state *st = iio_priv(indio_dev);58 struct ad5686_state *st = iio_priv(indio_dev);
169 59
170 return sprintf(buf, "%d\n", !!(st->pwr_down_mask &60 return sprintf(buf, "%d\n", !!(st->pwr_down_mask &
171 (0x3 << (chan->channel * 2))));61 (0x3 << (chan->channel * 2))));
172}62}
173 63
174static ssize_t ad5686_write_dac_powerdown(struct iio_dev *indio_dev,64static ssize_t ad5686_write_dac_powerdown(struct iio_dev *indio_dev,
175 uintptr_t private, const struct iio_chan_spec *chan, const char *buf,65 uintptr_t private,
176 size_t len)66 const struct iio_chan_spec *chan,
67 const char *buf,
68 size_t len)
177{69{
178 bool readin;70 bool readin;
179 int ret;71 int ret;
180 struct ad5686_state *st = iio_priv(indio_dev);72 struct ad5686_state *st = iio_priv(indio_dev);
73 unsigned int val, ref_bit_msk;
74 u8 shift;
181 75
182 ret = strtobool(buf, &readin);76 ret = strtobool(buf, &readin);
183 if (ret)77 if (ret)
@@ -188,8 +82,28 @@ static ssize_t ad5686_write_dac_powerdown(struct iio_dev *indio_dev, · 4 unmodified lines
188 else82 else
189 st->pwr_down_mask &= ~(0x3 << (chan->channel * 2));83 st->pwr_down_mask &= ~(0x3 << (chan->channel * 2));
190 84
191 ret = ad5686_spi_write(st, AD5686_CMD_POWERDOWN_DAC, 0,85 switch (st->chip_info->regmap_type) {
192 st->pwr_down_mask & st->pwr_down_mode, 0);86 case AD5683_REGMAP:
87 shift = 13;
88 ref_bit_msk = AD5683_REF_BIT_MSK;
89 break;
90 case AD5686_REGMAP:
91 shift = 0;
92 ref_bit_msk = 0;
93 break;
94 case AD5693_REGMAP:
95 shift = 13;
96 ref_bit_msk = AD5693_REF_BIT_MSK;
97 break;
98 default:
99 return -EINVAL;
100 }
101
102 val = ((st->pwr_down_mask & st->pwr_down_mode) << shift);
103 if (!st->use_internal_vref)
104 val |= ref_bit_msk;
105
106 ret = st->write(st, AD5686_CMD_POWERDOWN_DAC, 0, val);
193 107
194 return ret ? ret : len;108 return ret ? ret : len;
195}109}
@@ -206,7 +120,7 @@ static int ad5686_read_raw(struct iio_dev *indio_dev, · 10 unmodified lines
206 switch (m) {120 switch (m) {
207 case IIO_CHAN_INFO_RAW:121 case IIO_CHAN_INFO_RAW:
208 mutex_lock(&indio_dev->mlock);122 mutex_lock(&indio_dev->mlock);
209 ret = ad5686_spi_read(st, chan->address);123 ret = st->read(st, chan->address);
210 mutex_unlock(&indio_dev->mlock);124 mutex_unlock(&indio_dev->mlock);
211 if (ret < 0)125 if (ret < 0)
212 return ret;126 return ret;
@@ -221,10 +135,10 @@ static int ad5686_read_raw(struct iio_dev *indio_dev, · 8 unmodified lines
221}135}
222 136
223static int ad5686_write_raw(struct iio_dev *indio_dev,137static int ad5686_write_raw(struct iio_dev *indio_dev,
224 struct iio_chan_spec const *chan,138 struct iio_chan_spec const *chan,
225 int val,139 int val,
226 int val2,140 int val2,
227 long mask)141 long mask)
228{142{
229 struct ad5686_state *st = iio_priv(indio_dev);143 struct ad5686_state *st = iio_priv(indio_dev);
230 int ret;144 int ret;
@@ -235,11 +149,10 @@ static int ad5686_write_raw(struct iio_dev *indio_dev, · 4 unmodified lines
235 return -EINVAL;149 return -EINVAL;
236 150
237 mutex_lock(&indio_dev->mlock);151 mutex_lock(&indio_dev->mlock);
238 ret = ad5686_spi_write(st,152 ret = st->write(st,
239 AD5686_CMD_WRITE_INPUT_N_UPDATE_N,153 AD5686_CMD_WRITE_INPUT_N_UPDATE_N,
240 chan->address,154 chan->address,
241 val,155 val << chan->scan_type.shift);
242 chan->scan_type.shift);
243 mutex_unlock(&indio_dev->mlock);156 mutex_unlock(&indio_dev->mlock);
244 break;157 break;
245 default:158 default:
@@ -266,14 +179,14 @@ static const struct iio_chan_spec_ext_info ad5686_ext_info[] = { · 20 unmodified lines
266 { },179 { },
267};180};
268 181
269#define AD5868_CHANNEL(chan, bits, _shift) { \182#define AD5868_CHANNEL(chan, addr, bits, _shift) { \
270 .type = IIO_VOLTAGE, \183 .type = IIO_VOLTAGE, \
271 .indexed = 1, \184 .indexed = 1, \
272 .output = 1, \185 .output = 1, \
273 .channel = chan, \186 .channel = chan, \
274 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \187 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
275 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE),\188 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE),\
276 .address = AD5686_ADDR_DAC(chan), \189 .address = addr, \
277 .scan_type = { \190 .scan_type = { \
278 .sign = 'u', \191 .sign = 'u', \
279 .realbits = (bits), \192 .realbits = (bits), \
@@ -283,45 +196,191 @@ static const struct iio_chan_spec_ext_info ad5686_ext_info[] = { · 3 unmodified lines
283 .ext_info = ad5686_ext_info, \196 .ext_info = ad5686_ext_info, \
284}197}
285 198
199#define DECLARE_AD5693_CHANNELS(name, bits, _shift) \
200static struct iio_chan_spec name[] = { \
201 AD5868_CHANNEL(0, 0, bits, _shift), \
202}
203
204#define DECLARE_AD5686_CHANNELS(name, bits, _shift) \
205static struct iio_chan_spec name[] = { \
206 AD5868_CHANNEL(0, 1, bits, _shift), \
207 AD5868_CHANNEL(1, 2, bits, _shift), \
208 AD5868_CHANNEL(2, 4, bits, _shift), \
209 AD5868_CHANNEL(3, 8, bits, _shift), \
210}
211
212#define DECLARE_AD5676_CHANNELS(name, bits, _shift) \
213static struct iio_chan_spec name[] = { \
214 AD5868_CHANNEL(0, 0, bits, _shift), \
215 AD5868_CHANNEL(1, 1, bits, _shift), \
216 AD5868_CHANNEL(2, 2, bits, _shift), \
217 AD5868_CHANNEL(3, 3, bits, _shift), \
218 AD5868_CHANNEL(4, 4, bits, _shift), \
219 AD5868_CHANNEL(5, 5, bits, _shift), \
220 AD5868_CHANNEL(6, 6, bits, _shift), \
221 AD5868_CHANNEL(7, 7, bits, _shift), \
222}
223
224DECLARE_AD5676_CHANNELS(ad5672_channels, 12, 4);
225DECLARE_AD5676_CHANNELS(ad5676_channels, 16, 0);
226DECLARE_AD5686_CHANNELS(ad5684_channels, 12, 4);
227DECLARE_AD5686_CHANNELS(ad5685r_channels, 14, 2);
228DECLARE_AD5686_CHANNELS(ad5686_channels, 16, 0);
229DECLARE_AD5693_CHANNELS(ad5693_channels, 16, 0);
230DECLARE_AD5693_CHANNELS(ad5692r_channels, 14, 2);
231DECLARE_AD5693_CHANNELS(ad5691r_channels, 12, 4);
232
286static const struct ad5686_chip_info ad5686_chip_info_tbl[] = {233static const struct ad5686_chip_info ad5686_chip_info_tbl[] = {
234 [ID_AD5671R] = {
235 .channels = ad5672_channels,
236 .int_vref_mv = 2500,
237 .num_channels = 8,
238 .regmap_type = AD5686_REGMAP,
239 },
240 [ID_AD5672R] = {
241 .channels = ad5672_channels,
242 .int_vref_mv = 2500,
243 .num_channels = 8,
244 .regmap_type = AD5686_REGMAP,
245 },
246 [ID_AD5675R] = {
247 .channels = ad5676_channels,
248 .int_vref_mv = 2500,
249 .num_channels = 8,
250 .regmap_type = AD5686_REGMAP,
251 },
252 [ID_AD5676] = {
253 .channels = ad5676_channels,
254 .num_channels = 8,
255 .regmap_type = AD5686_REGMAP,
256 },
257 [ID_AD5676R] = {
258 .channels = ad5676_channels,
259 .int_vref_mv = 2500,
260 .num_channels = 8,
261 .regmap_type = AD5686_REGMAP,
262 },
263 [ID_AD5681R] = {
264 .channels = ad5691r_channels,
265 .int_vref_mv = 2500,
266 .num_channels = 1,
267 .regmap_type = AD5683_REGMAP,
268 },
269 [ID_AD5682R] = {
270 .channels = ad5692r_channels,
271 .int_vref_mv = 2500,
272 .num_channels = 1,
273 .regmap_type = AD5683_REGMAP,
274 },
275 [ID_AD5683] = {
276 .channels = ad5693_channels,
277 .num_channels = 1,
278 .regmap_type = AD5683_REGMAP,
279 },
280 [ID_AD5683R] = {
281 .channels = ad5693_channels,
282 .int_vref_mv = 2500,
283 .num_channels = 1,
284 .regmap_type = AD5683_REGMAP,
285 },
287 [ID_AD5684] = {286 [ID_AD5684] = {
288 .channel[0] = AD5868_CHANNEL(0, 12, 4),287 .channels = ad5684_channels,
289 .channel[1] = AD5868_CHANNEL(1, 12, 4),288 .num_channels = 4,
290 .channel[2] = AD5868_CHANNEL(2, 12, 4),289 .regmap_type = AD5686_REGMAP,
291 .channel[3] = AD5868_CHANNEL(3, 12, 4),290 },
291 [ID_AD5684R] = {
292 .channels = ad5684_channels,
292 .int_vref_mv = 2500,293 .int_vref_mv = 2500,
294 .num_channels = 4,
295 .regmap_type = AD5686_REGMAP,
293 },296 },
294 [ID_AD5685] = {297 [ID_AD5685R] = {
295 .channel[0] = AD5868_CHANNEL(0, 14, 2),298 .channels = ad5685r_channels,
296 .channel[1] = AD5868_CHANNEL(1, 14, 2),
297 .channel[2] = AD5868_CHANNEL(2, 14, 2),
298 .channel[3] = AD5868_CHANNEL(3, 14, 2),
299 .int_vref_mv = 2500,299 .int_vref_mv = 2500,
300 .num_channels = 4,
301 .regmap_type = AD5686_REGMAP,
300 },302 },
301 [ID_AD5686] = {303 [ID_AD5686] = {
302 .channel[0] = AD5868_CHANNEL(0, 16, 0),304 .channels = ad5686_channels,
303 .channel[1] = AD5868_CHANNEL(1, 16, 0),305 .num_channels = 4,
304 .channel[2] = AD5868_CHANNEL(2, 16, 0),306 .regmap_type = AD5686_REGMAP,
305 .channel[3] = AD5868_CHANNEL(3, 16, 0),307 },
308 [ID_AD5686R] = {
309 .channels = ad5686_channels,
310 .int_vref_mv = 2500,
311 .num_channels = 4,
312 .regmap_type = AD5686_REGMAP,
313 },
314 [ID_AD5691R] = {
315 .channels = ad5691r_channels,
316 .int_vref_mv = 2500,
317 .num_channels = 1,
318 .regmap_type = AD5693_REGMAP,
319 },
320 [ID_AD5692R] = {
321 .channels = ad5692r_channels,
322 .int_vref_mv = 2500,
323 .num_channels = 1,
324 .regmap_type = AD5693_REGMAP,
325 },
326 [ID_AD5693] = {
327 .channels = ad5693_channels,
328 .num_channels = 1,
329 .regmap_type = AD5693_REGMAP,
330 },
331 [ID_AD5693R] = {
332 .channels = ad5693_channels,
306 .int_vref_mv = 2500,333 .int_vref_mv = 2500,
334 .num_channels = 1,
335 .regmap_type = AD5693_REGMAP,
336 },
337 [ID_AD5694] = {
338 .channels = ad5684_channels,
339 .num_channels = 4,
340 .regmap_type = AD5686_REGMAP,
341 },
342 [ID_AD5694R] = {
343 .channels = ad5684_channels,
344 .int_vref_mv = 2500,
345 .num_channels = 4,
346 .regmap_type = AD5686_REGMAP,
347 },
348 [ID_AD5696] = {
349 .channels = ad5686_channels,
350 .num_channels = 4,
351 .regmap_type = AD5686_REGMAP,
352 },
353 [ID_AD5696R] = {
354 .channels = ad5686_channels,
355 .int_vref_mv = 2500,
356 .num_channels = 4,
357 .regmap_type = AD5686_REGMAP,
307 },358 },
308};359};
309 360
310 361int ad5686_probe(struct device *dev,
311static int ad5686_probe(struct spi_device *spi)362 enum ad5686_supported_device_ids chip_type,
363 const char *name, ad5686_write_func write,
364 ad5686_read_func read)
312{365{
313 struct ad5686_state *st;366 struct ad5686_state *st;
314 struct iio_dev *indio_dev;367 struct iio_dev *indio_dev;
315 int ret, voltage_uv = 0;368 unsigned int val, ref_bit_msk;
369 u8 cmd;
370 int ret, i, voltage_uv = 0;
316 371
317 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));372 indio_dev = devm_iio_device_alloc(dev, sizeof(*st));
318 if (indio_dev == NULL)373 if (indio_dev == NULL)
319 return -ENOMEM;374 return -ENOMEM;
320 375
321 st = iio_priv(indio_dev);376 st = iio_priv(indio_dev);
322 spi_set_drvdata(spi, indio_dev);377 dev_set_drvdata(dev, indio_dev);
378
379 st->dev = dev;
380 st->write = write;
381 st->read = read;
323 382
324 st->reg = devm_regulator_get_optional(&spi->dev, "vcc");383 st->reg = devm_regulator_get_optional(dev, "vcc");
325 if (!IS_ERR(st->reg)) {384 if (!IS_ERR(st->reg)) {
326 ret = regulator_enable(st->reg);385 ret = regulator_enable(st->reg);
327 if (ret)386 if (ret)
@@ -334,28 +393,47 @@ static int ad5686_probe(struct spi_device *spi) · 6 unmodified lines
334 voltage_uv = ret;393 voltage_uv = ret;
335 }394 }
336 395
337 st->chip_info =396 st->chip_info = &ad5686_chip_info_tbl[chip_type];
338 &ad5686_chip_info_tbl[spi_get_device_id(spi)->driver_data];
339 397
340 if (voltage_uv)398 if (voltage_uv)
341 st->vref_mv = voltage_uv / 1000;399 st->vref_mv = voltage_uv / 1000;
342 else400 else
343 st->vref_mv = st->chip_info->int_vref_mv;401 st->vref_mv = st->chip_info->int_vref_mv;
344 402
345 st->spi = spi;
346
347 /* Set all the power down mode for all channels to 1K pulldown */403 /* Set all the power down mode for all channels to 1K pulldown */
348 st->pwr_down_mode = 0x55;404 for (i = 0; i < st->chip_info->num_channels; i++)
405 st->pwr_down_mode |= (0x01 << (i * 2));
349 406
350 indio_dev->dev.parent = &spi->dev;407 indio_dev->dev.parent = dev;
351 indio_dev->name = spi_get_device_id(spi)->name;408 indio_dev->name = name;
352 indio_dev->info = &ad5686_info;409 indio_dev->info = &ad5686_info;
353 indio_dev->modes = INDIO_DIRECT_MODE;410 indio_dev->modes = INDIO_DIRECT_MODE;
354 indio_dev->channels = st->chip_info->channel;411 indio_dev->channels = st->chip_info->channels;
355 indio_dev->num_channels = AD5686_DAC_CHANNELS;412 indio_dev->num_channels = st->chip_info->num_channels;
413
414 switch (st->chip_info->regmap_type) {
415 case AD5683_REGMAP:
416 cmd = AD5686_CMD_CONTROL_REG;
417 ref_bit_msk = AD5683_REF_BIT_MSK;
418 st->use_internal_vref = !voltage_uv;
419 break;
420 case AD5686_REGMAP:
421 cmd = AD5686_CMD_INTERNAL_REFER_SETUP;
422 ref_bit_msk = 0;
423 break;
424 case AD5693_REGMAP:
425 cmd = AD5686_CMD_CONTROL_REG;
426 ref_bit_msk = AD5693_REF_BIT_MSK;
427 st->use_internal_vref = !voltage_uv;
428 break;
429 default:
430 ret = -EINVAL;
431 goto error_disable_reg;
432 }
433
434 val = (voltage_uv | ref_bit_msk);
356 435
357 ret = ad5686_spi_write(st, AD5686_CMD_INTERNAL_REFER_SETUP, 0,436 ret = st->write(st, cmd, 0, !!val);
358 !!voltage_uv, 0);
359 if (ret)437 if (ret)
360 goto error_disable_reg;438 goto error_disable_reg;
361 439
@@ -370,10 +448,11 @@ error_disable_reg: · 8 unmodified lines
370 regulator_disable(st->reg);448 regulator_disable(st->reg);
371 return ret;449 return ret;
372}450}
451EXPORT_SYMBOL_GPL(ad5686_probe);
373 452
374static int ad5686_remove(struct spi_device *spi)453int ad5686_remove(struct device *dev)
375{454{
376 struct iio_dev *indio_dev = spi_get_drvdata(spi);455 struct iio_dev *indio_dev = dev_get_drvdata(dev);
377 struct ad5686_state *st = iio_priv(indio_dev);456 struct ad5686_state *st = iio_priv(indio_dev);
378 457
379 iio_device_unregister(indio_dev);458 iio_device_unregister(indio_dev);
@@ -382,24 +461,7 @@ static int ad5686_remove(struct spi_device *spi) · 2 unmodified lines
382 461
383 return 0;462 return 0;
384}463}
385 464EXPORT_SYMBOL_GPL(ad5686_remove);
386static const struct spi_device_id ad5686_id[] = {
387 {"ad5684", ID_AD5684},
388 {"ad5685", ID_AD5685},
389 {"ad5686", ID_AD5686},
390 {}
391};
392MODULE_DEVICE_TABLE(spi, ad5686_id);
393
394static struct spi_driver ad5686_driver = {
395 .driver = {
396 .name = "ad5686",
397 },
398 .probe = ad5686_probe,
399 .remove = ad5686_remove,
400 .id_table = ad5686_id,
401};
402module_spi_driver(ad5686_driver);
403 465
404MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");466MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
405MODULE_DESCRIPTION("Analog Devices AD5686/85/84 DAC");467MODULE_DESCRIPTION("Analog Devices AD5686/85/84 DAC");
drivers/iio/dac/ad5686.h+145−0
@@ -0,0 +1,145 @@
1/* SPDX-License-Identifier: GPL-2.0+ */
2/*
3 * This file is part of AD5686 DAC driver
4 *
5 * Copyright 2018 Analog Devices Inc.
6 */
7
8#ifndef __DRIVERS_IIO_DAC_AD5686_H__
9#define __DRIVERS_IIO_DAC_AD5686_H__
10
11#include <linux/types.h>
12#include <linux/cache.h>
13#include <linux/mutex.h>
14#include <linux/kernel.h>
15
16#define AD5683_DATA(x) ((x) << 4)
17#define AD5686_ADDR(x) ((x) << 16)
18#define AD5686_CMD(x) ((x) << 20)
19
20#define AD5686_ADDR_DAC(chan) (0x1 << (chan))
21#define AD5686_ADDR_ALL_DAC 0xF
22
23#define AD5686_CMD_NOOP 0x0
24#define AD5686_CMD_WRITE_INPUT_N 0x1
25#define AD5686_CMD_UPDATE_DAC_N 0x2
26#define AD5686_CMD_WRITE_INPUT_N_UPDATE_N 0x3
27#define AD5686_CMD_POWERDOWN_DAC 0x4
28#define AD5686_CMD_LDAC_MASK 0x5
29#define AD5686_CMD_RESET 0x6
30#define AD5686_CMD_INTERNAL_REFER_SETUP 0x7
31#define AD5686_CMD_DAISY_CHAIN_ENABLE 0x8
32#define AD5686_CMD_READBACK_ENABLE 0x9
33
34#define AD5686_LDAC_PWRDN_NONE 0x0
35#define AD5686_LDAC_PWRDN_1K 0x1
36#define AD5686_LDAC_PWRDN_100K 0x2
37#define AD5686_LDAC_PWRDN_3STATE 0x3
38
39#define AD5686_CMD_CONTROL_REG 0x4
40#define AD5686_CMD_READBACK_ENABLE_V2 0x5
41#define AD5683_REF_BIT_MSK BIT(12)
42#define AD5693_REF_BIT_MSK BIT(12)
43
44/**
45 * ad5686_supported_device_ids:
46 */
47enum ad5686_supported_device_ids {
48 ID_AD5671R,
49 ID_AD5672R,
50 ID_AD5675R,
51 ID_AD5676,
52 ID_AD5676R,
53 ID_AD5681R,
54 ID_AD5682R,
55 ID_AD5683,
56 ID_AD5683R,
57 ID_AD5684,
58 ID_AD5684R,
59 ID_AD5685R,
60 ID_AD5686,
61 ID_AD5686R,
62 ID_AD5691R,
63 ID_AD5692R,
64 ID_AD5693,
65 ID_AD5693R,
66 ID_AD5694,
67 ID_AD5694R,
68 ID_AD5695R,
69 ID_AD5696,
70 ID_AD5696R,
71};
72
73enum ad5686_regmap_type {
74 AD5683_REGMAP,
75 AD5686_REGMAP,
76 AD5693_REGMAP
77};
78
79struct ad5686_state;
80
81typedef int (*ad5686_write_func)(struct ad5686_state *st,
82 u8 cmd, u8 addr, u16 val);
83
84typedef int (*ad5686_read_func)(struct ad5686_state *st, u8 addr);
85
86/**
87 * struct ad5686_chip_info - chip specific information
88 * @int_vref_mv: AD5620/40/60: the internal reference voltage
89 * @num_channels: number of channels
90 * @channel: channel specification
91 * @regmap_type: register map layout variant
92 */
93
94struct ad5686_chip_info {
95 u16 int_vref_mv;
96 unsigned int num_channels;
97 struct iio_chan_spec *channels;
98 enum ad5686_regmap_type regmap_type;
99};
100
101/**
102 * struct ad5446_state - driver instance specific data
103 * @spi: spi_device
104 * @chip_info: chip model specific constants, available modes etc
105 * @reg: supply regulator
106 * @vref_mv: actual reference voltage used
107 * @pwr_down_mask: power down mask
108 * @pwr_down_mode: current power down mode
109 * @use_internal_vref: set to true if the internal reference voltage is used
110 * @data: spi transfer buffers
111 */
112
113struct ad5686_state {
114 struct device *dev;
115 const struct ad5686_chip_info *chip_info;
116 struct regulator *reg;
117 unsigned short vref_mv;
118 unsigned int pwr_down_mask;
119 unsigned int pwr_down_mode;
120 ad5686_write_func write;
121 ad5686_read_func read;
122 bool use_internal_vref;
123
124 /*
125 * DMA (thus cache coherency maintenance) requires the
126 * transfer buffers to live in their own cache lines.
127 */
128
129 union {
130 __be32 d32;
131 __be16 d16;
132 u8 d8[4];
133 } data[3] ____cacheline_aligned;
134};
135
136
137int ad5686_probe(struct device *dev,
138 enum ad5686_supported_device_ids chip_type,
139 const char *name, ad5686_write_func write,
140 ad5686_read_func read);
141
142int ad5686_remove(struct device *dev);
143
144
145#endif /* __DRIVERS_IIO_DAC_AD5686_H__ */
drivers/iio/dac/ad5696-i2c.c+102−0
@@ -0,0 +1,102 @@
1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * AD5671R, AD5675R, AD5691R, AD5692R, AD5693, AD5693R,
4 * AD5694, AD5694R, AD5695R, AD5696, AD5696R
5 * Digital to analog converters driver
6 *
7 * Copyright 2018 Analog Devices Inc.
8 */
9
10#include "ad5686.h"
11
12#include <linux/module.h>
13#include <linux/i2c.h>
14
15static int ad5686_i2c_read(struct ad5686_state *st, u8 addr)
16{
17 struct i2c_client *i2c = to_i2c_client(st->dev);
18 struct i2c_msg msg[2] = {
19 {
20 .addr = i2c->addr,
21 .flags = i2c->flags,
22 .len = 3,
23 .buf = &st->data[0].d8[1],
24 },
25 {
26 .addr = i2c->addr,
27 .flags = i2c->flags | I2C_M_RD,
28 .len = 2,
29 .buf = (char *)&st->data[0].d16,
30 },
31 };
32 int ret;
33
34 st->data[0].d32 = cpu_to_be32(AD5686_CMD(AD5686_CMD_NOOP) |
35 AD5686_ADDR(addr) |
36 0x00);
37
38 ret = i2c_transfer(i2c->adapter, msg, 2);
39 if (ret < 0)
40 return ret;
41
42 return be16_to_cpu(st->data[0].d16);
43}
44
45static int ad5686_i2c_write(struct ad5686_state *st,
46 u8 cmd, u8 addr, u16 val)
47{
48 struct i2c_client *i2c = to_i2c_client(st->dev);
49 int ret;
50
51 st->data[0].d32 = cpu_to_be32(AD5686_CMD(cmd) | AD5686_ADDR(addr)
52 | val);
53
54 ret = i2c_master_send(i2c, &st->data[0].d8[1], 3);
55 if (ret < 0)
56 return ret;
57
58 return (ret != 3) ? -EIO : 0;
59}
60
61static int ad5686_i2c_probe(struct i2c_client *i2c,
62 const struct i2c_device_id *id)
63{
64 return ad5686_probe(&i2c->dev, id->driver_data, id->name,
65 ad5686_i2c_write, ad5686_i2c_read);
66}
67
68static int ad5686_i2c_remove(struct i2c_client *i2c)
69{
70 return ad5686_remove(&i2c->dev);
71}
72
73static const struct i2c_device_id ad5686_i2c_id[] = {
74 {"ad5671r", ID_AD5671R},
75 {"ad5675r", ID_AD5675R},
76 {"ad5691r", ID_AD5691R},
77 {"ad5692r", ID_AD5692R},
78 {"ad5693", ID_AD5693},
79 {"ad5693r", ID_AD5693R},
80 {"ad5694", ID_AD5694},
81 {"ad5694r", ID_AD5694R},
82 {"ad5695r", ID_AD5695R},
83 {"ad5696", ID_AD5696},
84 {"ad5696r", ID_AD5696R},
85 {}
86};
87MODULE_DEVICE_TABLE(i2c, ad5686_i2c_id);
88
89static struct i2c_driver ad5686_i2c_driver = {
90 .driver = {
91 .name = "ad5696",
92 },
93 .probe = ad5686_i2c_probe,
94 .remove = ad5686_i2c_remove,
95 .id_table = ad5686_i2c_id,
96};
97
98module_i2c_driver(ad5686_i2c_driver);
99
100MODULE_AUTHOR("Stefan Popa <stefan.popa@analog.com>");
101MODULE_DESCRIPTION("Analog Devices AD5686 and similar multi-channel DACs");
102MODULE_LICENSE("GPL v2");
drivers/iio/dac/ltc2632.c+71−18
@@ -2,6 +2,7 @@ · 1 unmodified line
2 * LTC2632 Digital to analog convertors spi driver2 * LTC2632 Digital to analog convertors spi driver
3 *3 *
4 * Copyright 2017 Maxime Roussin-B�langer4 * Copyright 2017 Maxime Roussin-B�langer
5 * expanded by Silvan Murer <silvan.murer@gmail.com>
5 *6 *
6 * Licensed under the GPL-2.7 * Licensed under the GPL-2.
7 */8 */
@@ -10,6 +11,7 @@ · 2 unmodified lines
10#include <linux/spi/spi.h>11#include <linux/spi/spi.h>
11#include <linux/module.h>12#include <linux/module.h>
12#include <linux/iio/iio.h>13#include <linux/iio/iio.h>
14#include <linux/regulator/consumer.h>
13 15
14#define LTC2632_DAC_CHANNELS 216#define LTC2632_DAC_CHANNELS 2
15 17
@@ -28,7 +30,7 @@ · 12 unmodified lines
28/**30/**
29 * struct ltc2632_chip_info - chip specific information31 * struct ltc2632_chip_info - chip specific information
30 * @channels: channel spec for the DAC32 * @channels: channel spec for the DAC
31 * @vref_mv: reference voltage33 * @vref_mv: internal reference voltage
32 */34 */
33struct ltc2632_chip_info {35struct ltc2632_chip_info {
34 const struct iio_chan_spec *channels;36 const struct iio_chan_spec *channels;
@@ -39,10 +41,14 @@ struct ltc2632_chip_info { · 4 unmodified lines
39 * struct ltc2632_state - driver instance specific data41 * struct ltc2632_state - driver instance specific data
40 * @spi_dev: pointer to the spi_device struct42 * @spi_dev: pointer to the spi_device struct
41 * @powerdown_cache_mask used to show current channel powerdown state43 * @powerdown_cache_mask used to show current channel powerdown state
44 * @vref_mv used reference voltage (internal or external)
45 * @vref_reg regulator for the reference voltage
42 */46 */
43struct ltc2632_state {47struct ltc2632_state {
44 struct spi_device *spi_dev;48 struct spi_device *spi_dev;
45 unsigned int powerdown_cache_mask;49 unsigned int powerdown_cache_mask;
50 int vref_mv;
51 struct regulator *vref_reg;
46};52};
47 53
48enum ltc2632_supported_device_ids {54enum ltc2632_supported_device_ids {
@@ -90,7 +96,7 @@ static int ltc2632_read_raw(struct iio_dev *indio_dev, · 41 unmodified lines
90 96
91 switch (m) {97 switch (m) {
92 case IIO_CHAN_INFO_SCALE:98 case IIO_CHAN_INFO_SCALE:
93 *val = chip_info->vref_mv;99 *val = st->vref_mv;
94 *val2 = chan->scan_type.realbits;100 *val2 = chan->scan_type.realbits;
95 return IIO_VAL_FRACTIONAL_LOG2;101 return IIO_VAL_FRACTIONAL_LOG2;
96 }102 }
@@ -246,6 +252,45 @@ static int ltc2632_probe(struct spi_device *spi) · 149 unmodified lines
246 chip_info = (struct ltc2632_chip_info *)252 chip_info = (struct ltc2632_chip_info *)
247 spi_get_device_id(spi)->driver_data;253 spi_get_device_id(spi)->driver_data;
248 254
255 st->vref_reg = devm_regulator_get_optional(&spi->dev, "vref");
256 if (PTR_ERR(st->vref_reg) == -ENODEV) {
257 /* use internal reference voltage */
258 st->vref_reg = NULL;
259 st->vref_mv = chip_info->vref_mv;
260
261 ret = ltc2632_spi_write(spi, LTC2632_CMD_INTERNAL_REFER,
262 0, 0, 0);
263 if (ret) {
264 dev_err(&spi->dev,
265 "Set internal reference command failed, %d\n",
266 ret);
267 return ret;
268 }
269 } else if (IS_ERR(st->vref_reg)) {
270 dev_err(&spi->dev,
271 "Error getting voltage reference regulator\n");
272 return PTR_ERR(st->vref_reg);
273 } else {
274 /* use external reference voltage */
275 ret = regulator_enable(st->vref_reg);
276 if (ret) {
277 dev_err(&spi->dev,
278 "enable reference regulator failed, %d\n",
279 ret);
280 return ret;
281 }
282 st->vref_mv = regulator_get_voltage(st->vref_reg) / 1000;
283
284 ret = ltc2632_spi_write(spi, LTC2632_CMD_EXTERNAL_REFER,
285 0, 0, 0);
286 if (ret) {
287 dev_err(&spi->dev,
288 "Set external reference command failed, %d\n",
289 ret);
290 return ret;
291 }
292 }
293
249 indio_dev->dev.parent = &spi->dev;294 indio_dev->dev.parent = &spi->dev;
250 indio_dev->name = dev_of_node(&spi->dev) ? dev_of_node(&spi->dev)->name295 indio_dev->name = dev_of_node(&spi->dev) ? dev_of_node(&spi->dev)->name
251 : spi_get_device_id(spi)->name;296 : spi_get_device_id(spi)->name;
@@ -254,14 +299,20 @@ static int ltc2632_probe(struct spi_device *spi) · 2 unmodified lines
254 indio_dev->channels = chip_info->channels;299 indio_dev->channels = chip_info->channels;
255 indio_dev->num_channels = LTC2632_DAC_CHANNELS;300 indio_dev->num_channels = LTC2632_DAC_CHANNELS;
256 301
257 ret = ltc2632_spi_write(spi, LTC2632_CMD_INTERNAL_REFER, 0, 0, 0);302 return iio_device_register(indio_dev);
258 if (ret) {303}
259 dev_err(&spi->dev,
260 "Set internal reference command failed, %d\n", ret);
261 return ret;
262 }
263 304
264 return devm_iio_device_register(&spi->dev, indio_dev);305static int ltc2632_remove(struct spi_device *spi)
306{
307 struct iio_dev *indio_dev = spi_get_drvdata(spi);
308 struct ltc2632_state *st = iio_priv(indio_dev);
309
310 iio_device_unregister(indio_dev);
311
312 if (st->vref_reg)
313 regulator_disable(st->vref_reg);
314
315 return 0;
265}316}
266 317
267static const struct spi_device_id ltc2632_id[] = {318static const struct spi_device_id ltc2632_id[] = {
@@ -275,15 +326,6 @@ static const struct spi_device_id ltc2632_id[] = { · 7 unmodified lines
275};326};
276MODULE_DEVICE_TABLE(spi, ltc2632_id);327MODULE_DEVICE_TABLE(spi, ltc2632_id);
277 328
278static struct spi_driver ltc2632_driver = {
279 .driver = {
280 .name = "ltc2632",
281 },
282 .probe = ltc2632_probe,
283 .id_table = ltc2632_id,
284};
285module_spi_driver(ltc2632_driver);
286
287static const struct of_device_id ltc2632_of_match[] = {329static const struct of_device_id ltc2632_of_match[] = {
288 {330 {
289 .compatible = "lltc,ltc2632-l12",331 .compatible = "lltc,ltc2632-l12",
@@ -308,6 +350,17 @@ static const struct of_device_id ltc2632_of_match[] = { · 18 unmodified lines
308};350};
309MODULE_DEVICE_TABLE(of, ltc2632_of_match);351MODULE_DEVICE_TABLE(of, ltc2632_of_match);
310 352
353static struct spi_driver ltc2632_driver = {
354 .driver = {
355 .name = "ltc2632",
356 .of_match_table = of_match_ptr(ltc2632_of_match),
357 },
358 .probe = ltc2632_probe,
359 .remove = ltc2632_remove,
360 .id_table = ltc2632_id,
361};
362module_spi_driver(ltc2632_driver);
363
311MODULE_AUTHOR("Maxime Roussin-Belanger <maxime.roussinbelanger@gmail.com>");364MODULE_AUTHOR("Maxime Roussin-Belanger <maxime.roussinbelanger@gmail.com>");
312MODULE_DESCRIPTION("LTC2632 DAC SPI driver");365MODULE_DESCRIPTION("LTC2632 DAC SPI driver");
313MODULE_LICENSE("GPL v2");366MODULE_LICENSE("GPL v2");
drivers/iio/dac/ti-dac5571.c+439−0
@@ -0,0 +1,439 @@
1/*
2 * ti-dac5571.c - Texas Instruments 8/10/12-bit 1/4-channel DAC driver
3 *
4 * Copyright (C) 2018 Prevas A/S
5 *
6 * http://www.ti.com/lit/ds/symlink/dac5571.pdf
7 * http://www.ti.com/lit/ds/symlink/dac6571.pdf
8 * http://www.ti.com/lit/ds/symlink/dac7571.pdf
9 * http://www.ti.com/lit/ds/symlink/dac5574.pdf
10 * http://www.ti.com/lit/ds/symlink/dac6574.pdf
11 * http://www.ti.com/lit/ds/symlink/dac7574.pdf
12 * http://www.ti.com/lit/ds/symlink/dac5573.pdf
13 * http://www.ti.com/lit/ds/symlink/dac6573.pdf
14 * http://www.ti.com/lit/ds/symlink/dac7573.pdf
15 *
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License (version 2) as
18 * published by the Free Software Foundation.
19 */
20
21#include <linux/iio/iio.h>
22#include <linux/i2c.h>
23#include <linux/module.h>
24#include <linux/of_device.h>
25#include <linux/of.h>
26#include <linux/regulator/consumer.h>
27
28enum chip_id {
29 single_8bit, single_10bit, single_12bit,
30 quad_8bit, quad_10bit, quad_12bit
31};
32
33struct dac5571_spec {
34 u8 num_channels;
35 u8 resolution;
36};
37
38static const struct dac5571_spec dac5571_spec[] = {
39 [single_8bit] = {.num_channels = 1, .resolution = 8},
40 [single_10bit] = {.num_channels = 1, .resolution = 10},
41 [single_12bit] = {.num_channels = 1, .resolution = 12},
42 [quad_8bit] = {.num_channels = 4, .resolution = 8},
43 [quad_10bit] = {.num_channels = 4, .resolution = 10},
44 [quad_12bit] = {.num_channels = 4, .resolution = 12},
45};
46
47struct dac5571_data {
48 struct i2c_client *client;
49 int id;
50 struct mutex lock;
51 struct regulator *vref;
52 u16 val[4];
53 bool powerdown;
54 u8 powerdown_mode;
55 struct dac5571_spec const *spec;
56 int (*dac5571_cmd)(struct dac5571_data *data, int channel, u16 val);
57 int (*dac5571_pwrdwn)(struct dac5571_data *data, int channel, u8 pwrdwn);
58 u8 buf[3] ____cacheline_aligned;
59};
60
61#define DAC5571_POWERDOWN(mode) ((mode) + 1)
62#define DAC5571_POWERDOWN_FLAG BIT(0)
63#define DAC5571_CHANNEL_SELECT 1
64#define DAC5571_LOADMODE_DIRECT BIT(4)
65#define DAC5571_SINGLE_PWRDWN_BITS 4
66#define DAC5571_QUAD_PWRDWN_BITS 6
67
68static int dac5571_cmd_single(struct dac5571_data *data, int channel, u16 val)
69{
70 unsigned int shift;
71
72 shift = 12 - data->spec->resolution;
73 data->buf[1] = val << shift;
74 data->buf[0] = val >> (8 - shift);
75
76 if (i2c_master_send(data->client, data->buf, 2) != 2)
77 return -EIO;
78
79 return 0;
80}
81
82static int dac5571_cmd_quad(struct dac5571_data *data, int channel, u16 val)
83{
84 unsigned int shift;
85
86 shift = 16 - data->spec->resolution;
87 data->buf[2] = val << shift;
88 data->buf[1] = (val >> (8 - shift));
89 data->buf[0] = (channel << DAC5571_CHANNEL_SELECT) |
90 DAC5571_LOADMODE_DIRECT;
91
92 if (i2c_master_send(data->client, data->buf, 3) != 3)
93 return -EIO;
94
95 return 0;
96}
97
98static int dac5571_pwrdwn_single(struct dac5571_data *data, int channel, u8 pwrdwn)
99{
100 unsigned int shift;
101
102 shift = 12 - data->spec->resolution;
103 data->buf[1] = 0;
104 data->buf[0] = pwrdwn << DAC5571_SINGLE_PWRDWN_BITS;
105
106 if (i2c_master_send(data->client, data->buf, 2) != 2)
107 return -EIO;
108
109 return 0;
110}
111
112static int dac5571_pwrdwn_quad(struct dac5571_data *data, int channel, u8 pwrdwn)
113{
114 unsigned int shift;
115
116 shift = 16 - data->spec->resolution;
117 data->buf[2] = 0;
118 data->buf[1] = pwrdwn << DAC5571_QUAD_PWRDWN_BITS;
119 data->buf[0] = (channel << DAC5571_CHANNEL_SELECT) |
120 DAC5571_LOADMODE_DIRECT | DAC5571_POWERDOWN_FLAG;
121
122 if (i2c_master_send(data->client, data->buf, 3) != 3)
123 return -EIO;
124
125 return 0;
126}
127
128static const char *const dac5571_powerdown_modes[] = {
129 "1kohm_to_gnd", "100kohm_to_gnd", "three_state",
130};
131
132static int dac5571_get_powerdown_mode(struct iio_dev *indio_dev,
133 const struct iio_chan_spec *chan)
134{
135 struct dac5571_data *data = iio_priv(indio_dev);
136
137 return data->powerdown_mode;
138}
139
140static int dac5571_set_powerdown_mode(struct iio_dev *indio_dev,
141 const struct iio_chan_spec *chan,
142 unsigned int mode)
143{
144 struct dac5571_data *data = iio_priv(indio_dev);
145 int ret = 0;
146
147 if (data->powerdown_mode == mode)
148 return 0;
149
150 mutex_lock(&data->lock);
151 if (data->powerdown) {
152 ret = data->dac5571_pwrdwn(data, chan->channel,
153 DAC5571_POWERDOWN(mode));
154 if (ret)
155 goto out;
156 }
157 data->powerdown_mode = mode;
158
159 out:
160 mutex_unlock(&data->lock);
161
162 return ret;
163}
164
165static const struct iio_enum dac5571_powerdown_mode = {
166 .items = dac5571_powerdown_modes,
167 .num_items = ARRAY_SIZE(dac5571_powerdown_modes),
168 .get = dac5571_get_powerdown_mode,
169 .set = dac5571_set_powerdown_mode,
170};
171
172static ssize_t dac5571_read_powerdown(struct iio_dev *indio_dev,
173 uintptr_t private,
174 const struct iio_chan_spec *chan,
175 char *buf)
176{
177 struct dac5571_data *data = iio_priv(indio_dev);
178
179 return sprintf(buf, "%d\n", data->powerdown);
180}
181
182static ssize_t dac5571_write_powerdown(struct iio_dev *indio_dev,
183 uintptr_t private,
184 const struct iio_chan_spec *chan,
185 const char *buf, size_t len)
186{
187 struct dac5571_data *data = iio_priv(indio_dev);
188 bool powerdown;
189 int ret;
190
191 ret = strtobool(buf, &powerdown);
192 if (ret)
193 return ret;
194
195 if (data->powerdown == powerdown)
196 return len;
197
198 mutex_lock(&data->lock);
199 if (powerdown)
200 ret = data->dac5571_pwrdwn(data, chan->channel,
201 DAC5571_POWERDOWN(data->powerdown_mode));
202 else
203 ret = data->dac5571_cmd(data, chan->channel, data->val[0]);
204 if (ret)
205 goto out;
206
207 data->powerdown = powerdown;
208
209 out:
210 mutex_unlock(&data->lock);
211
212 return ret ? ret : len;
213}
214
215
216static const struct iio_chan_spec_ext_info dac5571_ext_info[] = {
217 {
218 .name = "powerdown",
219 .read = dac5571_read_powerdown,
220 .write = dac5571_write_powerdown,
221 .shared = IIO_SHARED_BY_TYPE,
222 },
223 IIO_ENUM("powerdown_mode", IIO_SHARED_BY_TYPE, &dac5571_powerdown_mode),
224 IIO_ENUM_AVAILABLE("powerdown_mode", &dac5571_powerdown_mode),
225 {},
226};
227
228#define dac5571_CHANNEL(chan, name) { \
229 .type = IIO_VOLTAGE, \
230 .channel = (chan), \
231 .address = (chan), \
232 .indexed = true, \
233 .output = true, \
234 .datasheet_name = name, \
235 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
236 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \
237 .ext_info = dac5571_ext_info, \
238}
239
240static const struct iio_chan_spec dac5571_channels[] = {
241 dac5571_CHANNEL(0, "A"),
242 dac5571_CHANNEL(1, "B"),
243 dac5571_CHANNEL(2, "C"),
244 dac5571_CHANNEL(3, "D"),
245};
246
247static int dac5571_read_raw(struct iio_dev *indio_dev,
248 struct iio_chan_spec const *chan,
249 int *val, int *val2, long mask)
250{
251 struct dac5571_data *data = iio_priv(indio_dev);
252 int ret;
253
254 switch (mask) {
255 case IIO_CHAN_INFO_RAW:
256 *val = data->val[chan->channel];
257 return IIO_VAL_INT;
258
259 case IIO_CHAN_INFO_SCALE:
260 ret = regulator_get_voltage(data->vref);
261 if (ret < 0)
262 return ret;
263
264 *val = ret / 1000;
265 *val2 = data->spec->resolution;
266 return IIO_VAL_FRACTIONAL_LOG2;
267
268 default:
269 return -EINVAL;
270 }
271}
272
273static int dac5571_write_raw(struct iio_dev *indio_dev,
274 struct iio_chan_spec const *chan,
275 int val, int val2, long mask)
276{
277 struct dac5571_data *data = iio_priv(indio_dev);
278 int ret;
279
280 switch (mask) {
281 case IIO_CHAN_INFO_RAW:
282 if (data->val[chan->channel] == val)
283 return 0;
284
285 if (val >= (1 << data->spec->resolution) || val < 0)
286 return -EINVAL;
287
288 if (data->powerdown)
289 return -EBUSY;
290
291 mutex_lock(&data->lock);
292 ret = data->dac5571_cmd(data, chan->channel, val);
293 if (ret == 0)
294 data->val[chan->channel] = val;
295 mutex_unlock(&data->lock);
296 return ret;
297
298 default:
299 return -EINVAL;
300 }
301}
302
303static int dac5571_write_raw_get_fmt(struct iio_dev *indio_dev,
304 struct iio_chan_spec const *chan,
305 long mask)
306{
307 return IIO_VAL_INT;
308}
309
310static const struct iio_info dac5571_info = {
311 .read_raw = dac5571_read_raw,
312 .write_raw = dac5571_write_raw,
313 .write_raw_get_fmt = dac5571_write_raw_get_fmt,
314};
315
316static int dac5571_probe(struct i2c_client *client,
317 const struct i2c_device_id *id)
318{
319 struct device *dev = &client->dev;
320 const struct dac5571_spec *spec;
321 struct dac5571_data *data;
322 struct iio_dev *indio_dev;
323 int ret, i;
324
325 indio_dev = devm_iio_device_alloc(dev, sizeof(*data));
326 if (!indio_dev)
327 return -ENOMEM;
328
329 data = iio_priv(indio_dev);
330 i2c_set_clientdata(client, indio_dev);
331 data->client = client;
332
333 indio_dev->dev.parent = dev;
334 indio_dev->dev.of_node = client->dev.of_node;
335 indio_dev->info = &dac5571_info;
336 indio_dev->name = id->name;
337 indio_dev->modes = INDIO_DIRECT_MODE;
338 indio_dev->channels = dac5571_channels;
339
340 spec = &dac5571_spec[id->driver_data];
341 indio_dev->num_channels = spec->num_channels;
342 data->spec = spec;
343
344 data->vref = devm_regulator_get(dev, "vref");
345 if (IS_ERR(data->vref))
346 return PTR_ERR(data->vref);
347
348 ret = regulator_enable(data->vref);
349 if (ret < 0)
350 return ret;
351
352 mutex_init(&data->lock);
353
354 switch (spec->num_channels) {
355 case 1:
356 data->dac5571_cmd = dac5571_cmd_single;
357 data->dac5571_pwrdwn = dac5571_pwrdwn_single;
358 break;
359 case 4:
360 data->dac5571_cmd = dac5571_cmd_quad;
361 data->dac5571_pwrdwn = dac5571_pwrdwn_quad;
362 break;
363 default:
364 goto err;
365 }
366
367 for (i = 0; i < spec->num_channels; i++) {
368 ret = data->dac5571_cmd(data, i, 0);
369 if (ret) {
370 dev_err(dev, "failed to initialize channel %d to 0\n", i);
371 goto err;
372 }
373 }
374
375 ret = iio_device_register(indio_dev);
376 if (ret)
377 goto err;
378
379 return 0;
380
381 err:
382 regulator_disable(data->vref);
383 return ret;
384}
385
386static int dac5571_remove(struct i2c_client *i2c)
387{
388 struct iio_dev *indio_dev = i2c_get_clientdata(i2c);
389 struct dac5571_data *data = iio_priv(indio_dev);
390
391 iio_device_unregister(indio_dev);
392 regulator_disable(data->vref);
393
394 return 0;
395}
396
397#ifdef CONFIG_OF
398static const struct of_device_id dac5571_of_id[] = {
399 {.compatible = "ti,dac5571"},
400 {.compatible = "ti,dac6571"},
401 {.compatible = "ti,dac7571"},
402 {.compatible = "ti,dac5574"},
403 {.compatible = "ti,dac6574"},
404 {.compatible = "ti,dac7574"},
405 {.compatible = "ti,dac5573"},
406 {.compatible = "ti,dac6573"},
407 {.compatible = "ti,dac7573"},
408 {}
409};
410MODULE_DEVICE_TABLE(of, dac5571_of_id);
411#endif
412
413static const struct i2c_device_id dac5571_id[] = {
414 {"dac5571", single_8bit},
415 {"dac6571", single_10bit},
416 {"dac7571", single_12bit},
417 {"dac5574", quad_8bit},
418 {"dac6574", quad_10bit},
419 {"dac7574", quad_12bit},
420 {"dac5573", quad_8bit},
421 {"dac6573", quad_10bit},
422 {"dac7573", quad_12bit},
423 {}
424};
425MODULE_DEVICE_TABLE(i2c, dac5571_id);
426
427static struct i2c_driver dac5571_driver = {
428 .driver = {
429 .name = "ti-dac5571",
430 },
431 .probe = dac5571_probe,
432 .remove = dac5571_remove,
433 .id_table = dac5571_id,
434};
435module_i2c_driver(dac5571_driver);
436
437MODULE_AUTHOR("Sean Nyekjaer <sean.nyekjaer@prevas.dk>");
438MODULE_DESCRIPTION("Texas Instruments 8/10/12-bit 1/4-channel DAC driver");
439MODULE_LICENSE("GPL v2");
drivers/iio/imu/inv_mpu6050/inv_mpu_core.c+164−120
@@ -24,6 +24,7 @@ · 23 unmodified lines
24#include <linux/spinlock.h>24#include <linux/spinlock.h>
25#include <linux/iio/iio.h>25#include <linux/iio/iio.h>
26#include <linux/acpi.h>26#include <linux/acpi.h>
27#include <linux/platform_device.h>
27#include "inv_mpu_iio.h"28#include "inv_mpu_iio.h"
28 29
29/*30/*
@@ -52,6 +53,7 @@ static const struct inv_mpu6050_reg_map reg_set_6500 = { · 22 unmodified lines
52 .raw_accl = INV_MPU6050_REG_RAW_ACCEL,53 .raw_accl = INV_MPU6050_REG_RAW_ACCEL,
53 .temperature = INV_MPU6050_REG_TEMPERATURE,54 .temperature = INV_MPU6050_REG_TEMPERATURE,
54 .int_enable = INV_MPU6050_REG_INT_ENABLE,55 .int_enable = INV_MPU6050_REG_INT_ENABLE,
56 .int_status = INV_MPU6050_REG_INT_STATUS,
55 .pwr_mgmt_1 = INV_MPU6050_REG_PWR_MGMT_1,57 .pwr_mgmt_1 = INV_MPU6050_REG_PWR_MGMT_1,
56 .pwr_mgmt_2 = INV_MPU6050_REG_PWR_MGMT_2,58 .pwr_mgmt_2 = INV_MPU6050_REG_PWR_MGMT_2,
57 .int_pin_cfg = INV_MPU6050_REG_INT_PIN_CFG,59 .int_pin_cfg = INV_MPU6050_REG_INT_PIN_CFG,
@@ -86,6 +88,7 @@ static const struct inv_mpu6050_chip_config chip_config_6050 = { · 28 unmodified lines
86 .gyro_fifo_enable = false,88 .gyro_fifo_enable = false,
87 .accl_fifo_enable = false,89 .accl_fifo_enable = false,
88 .accl_fs = INV_MPU6050_FS_02G,90 .accl_fs = INV_MPU6050_FS_02G,
91 .user_ctrl = 0,
89};92};
90 93
91/* Indexed by enum inv_devices */94/* Indexed by enum inv_devices */
@@ -120,6 +123,12 @@ static const struct inv_mpu6050_hw hw_info[] = { · 28 unmodified lines
120 .reg = &reg_set_6500,123 .reg = &reg_set_6500,
121 .config = &chip_config_6050,124 .config = &chip_config_6050,
122 },125 },
126 {
127 .whoami = INV_MPU9255_WHOAMI_VALUE,
128 .name = "MPU9255",
129 .reg = &reg_set_6500,
130 .config = &chip_config_6050,
131 },
123 {132 {
124 .whoami = INV_ICM20608_WHOAMI_VALUE,133 .whoami = INV_ICM20608_WHOAMI_VALUE,
125 .name = "ICM20608",134 .name = "ICM20608",
@@ -168,7 +177,7 @@ int inv_mpu6050_switch_engine(struct inv_mpu6050_state *st, bool en, u32 mask) · 42 unmodified lines
168 return result;177 return result;
169 178
170 if (en) {179 if (en) {
171 /* Wait for output stabilize */180 /* Wait for output to stabilize */
172 msleep(INV_MPU6050_TEMP_UP_TIME);181 msleep(INV_MPU6050_TEMP_UP_TIME);
173 if (mask == INV_MPU6050_BIT_PWR_GYRO_STBY) {182 if (mask == INV_MPU6050_BIT_PWR_GYRO_STBY) {
174 /* switch internal clock to PLL */183 /* switch internal clock to PLL */
@@ -185,26 +194,29 @@ int inv_mpu6050_switch_engine(struct inv_mpu6050_state *st, bool en, u32 mask) · 10 unmodified lines
185 194
186int inv_mpu6050_set_power_itg(struct inv_mpu6050_state *st, bool power_on)195int inv_mpu6050_set_power_itg(struct inv_mpu6050_state *st, bool power_on)
187{196{
188 int result = 0;197 int result;
189 198
190 if (power_on) {199 if (power_on) {
191 if (!st->powerup_count)200 if (!st->powerup_count) {
192 result = regmap_write(st->map, st->reg->pwr_mgmt_1, 0);201 result = regmap_write(st->map, st->reg->pwr_mgmt_1, 0);
193 if (!result)202 if (result)
194 st->powerup_count++;203 return result;
204 usleep_range(INV_MPU6050_REG_UP_TIME_MIN,
205 INV_MPU6050_REG_UP_TIME_MAX);
206 }
207 st->powerup_count++;
195 } else {208 } else {
196 st->powerup_count--;209 if (st->powerup_count == 1) {
197 if (!st->powerup_count)
198 result = regmap_write(st->map, st->reg->pwr_mgmt_1,210 result = regmap_write(st->map, st->reg->pwr_mgmt_1,
199 INV_MPU6050_BIT_SLEEP);211 INV_MPU6050_BIT_SLEEP);
212 if (result)
213 return result;
214 }
215 st->powerup_count--;
200 }216 }
201 217
202 if (result)218 dev_dbg(regmap_get_device(st->map), "set power %d, count=%u\n",
203 return result;219 power_on, st->powerup_count);
204
205 if (power_on)
206 usleep_range(INV_MPU6050_REG_UP_TIME_MIN,
207 INV_MPU6050_REG_UP_TIME_MAX);
208 220
209 return 0;221 return 0;
210}222}
@@ -262,26 +274,33 @@ static int inv_mpu6050_init_config(struct iio_dev *indio_dev) · 51 unmodified lines
262 d = (INV_MPU6050_FSR_2000DPS << INV_MPU6050_GYRO_CONFIG_FSR_SHIFT);274 d = (INV_MPU6050_FSR_2000DPS << INV_MPU6050_GYRO_CONFIG_FSR_SHIFT);
263 result = regmap_write(st->map, st->reg->gyro_config, d);275 result = regmap_write(st->map, st->reg->gyro_config, d);
264 if (result)276 if (result)
265 return result;277 goto error_power_off;
266 278
267 result = inv_mpu6050_set_lpf_regs(st, INV_MPU6050_FILTER_20HZ);279 result = inv_mpu6050_set_lpf_regs(st, INV_MPU6050_FILTER_20HZ);
268 if (result)280 if (result)
269 return result;281 goto error_power_off;
270 282
271 d = INV_MPU6050_ONE_K_HZ / INV_MPU6050_INIT_FIFO_RATE - 1;283 d = INV_MPU6050_ONE_K_HZ / INV_MPU6050_INIT_FIFO_RATE - 1;
272 result = regmap_write(st->map, st->reg->sample_rate_div, d);284 result = regmap_write(st->map, st->reg->sample_rate_div, d);
273 if (result)285 if (result)
274 return result;286 goto error_power_off;
275 287
276 d = (INV_MPU6050_FS_02G << INV_MPU6050_ACCL_CONFIG_FSR_SHIFT);288 d = (INV_MPU6050_FS_02G << INV_MPU6050_ACCL_CONFIG_FSR_SHIFT);
277 result = regmap_write(st->map, st->reg->accl_config, d);289 result = regmap_write(st->map, st->reg->accl_config, d);
290 if (result)
291 goto error_power_off;
292
293 result = regmap_write(st->map, st->reg->int_pin_cfg, st->irq_mask);
278 if (result)294 if (result)
279 return result;295 return result;
280 296
281 memcpy(&st->chip_config, hw_info[st->chip_type].config,297 memcpy(&st->chip_config, hw_info[st->chip_type].config,
282 sizeof(struct inv_mpu6050_chip_config));298 sizeof(struct inv_mpu6050_chip_config));
283 result = inv_mpu6050_set_power_itg(st, false);
284 299
300 return inv_mpu6050_set_power_itg(st, false);
301
302error_power_off:
303 inv_mpu6050_set_power_itg(st, false);
285 return result;304 return result;
286}305}
287 306
@@ -314,6 +333,65 @@ static int inv_mpu6050_sensor_show(struct inv_mpu6050_state *st, int reg, · 26 unmodified lines
314 return IIO_VAL_INT;333 return IIO_VAL_INT;
315}334}
316 335
336static int inv_mpu6050_read_channel_data(struct iio_dev *indio_dev,
337 struct iio_chan_spec const *chan,
338 int *val)
339{
340 struct inv_mpu6050_state *st = iio_priv(indio_dev);
341 int result;
342 int ret;
343
344 result = inv_mpu6050_set_power_itg(st, true);
345 if (result)
346 return result;
347
348 switch (chan->type) {
349 case IIO_ANGL_VEL:
350 result = inv_mpu6050_switch_engine(st, true,
351 INV_MPU6050_BIT_PWR_GYRO_STBY);
352 if (result)
353 goto error_power_off;
354 ret = inv_mpu6050_sensor_show(st, st->reg->raw_gyro,
355 chan->channel2, val);
356 result = inv_mpu6050_switch_engine(st, false,
357 INV_MPU6050_BIT_PWR_GYRO_STBY);
358 if (result)
359 goto error_power_off;
360 break;
361 case IIO_ACCEL:
362 result = inv_mpu6050_switch_engine(st, true,
363 INV_MPU6050_BIT_PWR_ACCL_STBY);
364 if (result)
365 goto error_power_off;
366 ret = inv_mpu6050_sensor_show(st, st->reg->raw_accl,
367 chan->channel2, val);
368 result = inv_mpu6050_switch_engine(st, false,
369 INV_MPU6050_BIT_PWR_ACCL_STBY);
370 if (result)
371 goto error_power_off;
372 break;
373 case IIO_TEMP:
374 /* wait for stablization */
375 msleep(INV_MPU6050_SENSOR_UP_TIME);
376 ret = inv_mpu6050_sensor_show(st, st->reg->temperature,
377 IIO_MOD_X, val);
378 break;
379 default:
380 ret = -EINVAL;
381 break;
382 }
383
384 result = inv_mpu6050_set_power_itg(st, false);
385 if (result)
386 goto error_power_off;
387
388 return ret;
389
390error_power_off:
391 inv_mpu6050_set_power_itg(st, false);
392 return result;
393}
394
317static int395static int
318inv_mpu6050_read_raw(struct iio_dev *indio_dev,396inv_mpu6050_read_raw(struct iio_dev *indio_dev,
319 struct iio_chan_spec const *chan,397 struct iio_chan_spec const *chan,
@@ -324,63 +402,14 @@ inv_mpu6050_read_raw(struct iio_dev *indio_dev, · 4 unmodified lines
324 402
325 switch (mask) {403 switch (mask) {
326 case IIO_CHAN_INFO_RAW:404 case IIO_CHAN_INFO_RAW:
327 {405 ret = iio_device_claim_direct_mode(indio_dev);
328 int result;406 if (ret)
329 407 return ret;
330 ret = IIO_VAL_INT;
331 mutex_lock(&st->lock);408 mutex_lock(&st->lock);
332 result = iio_device_claim_direct_mode(indio_dev);409 ret = inv_mpu6050_read_channel_data(indio_dev, chan, val);
333 if (result)
334 goto error_read_raw_unlock;
335 result = inv_mpu6050_set_power_itg(st, true);
336 if (result)
337 goto error_read_raw_release;
338 switch (chan->type) {
339 case IIO_ANGL_VEL:
340 result = inv_mpu6050_switch_engine(st, true,
341 INV_MPU6050_BIT_PWR_GYRO_STBY);
342 if (result)
343 goto error_read_raw_power_off;
344 ret = inv_mpu6050_sensor_show(st, st->reg->raw_gyro,
345 chan->channel2, val);
346 result = inv_mpu6050_switch_engine(st, false,
347 INV_MPU6050_BIT_PWR_GYRO_STBY);
348 if (result)
349 goto error_read_raw_power_off;
350 break;
351 case IIO_ACCEL:
352 result = inv_mpu6050_switch_engine(st, true,
353 INV_MPU6050_BIT_PWR_ACCL_STBY);
354 if (result)
355 goto error_read_raw_power_off;
356 ret = inv_mpu6050_sensor_show(st, st->reg->raw_accl,
357 chan->channel2, val);
358 result = inv_mpu6050_switch_engine(st, false,
359 INV_MPU6050_BIT_PWR_ACCL_STBY);
360 if (result)
361 goto error_read_raw_power_off;
362 break;
363 case IIO_TEMP:
364 /* wait for stablization */
365 msleep(INV_MPU6050_SENSOR_UP_TIME);
366 ret = inv_mpu6050_sensor_show(st, st->reg->temperature,
367 IIO_MOD_X, val);
368 break;
369 default:
370 ret = -EINVAL;
371 break;
372 }
373error_read_raw_power_off:
374 result |= inv_mpu6050_set_power_itg(st, false);
375error_read_raw_release:
376 iio_device_release_direct_mode(indio_dev);
377error_read_raw_unlock:
378 mutex_unlock(&st->lock);410 mutex_unlock(&st->lock);
379 if (result)411 iio_device_release_direct_mode(indio_dev);
380 return result;
381
382 return ret;412 return ret;
383 }
384 case IIO_CHAN_INFO_SCALE:413 case IIO_CHAN_INFO_SCALE:
385 switch (chan->type) {414 switch (chan->type) {
386 case IIO_ANGL_VEL:415 case IIO_ANGL_VEL:
@@ -502,17 +531,18 @@ static int inv_mpu6050_write_raw(struct iio_dev *indio_dev, · 115 unmodified lines
502 struct inv_mpu6050_state *st = iio_priv(indio_dev);531 struct inv_mpu6050_state *st = iio_priv(indio_dev);
503 int result;532 int result;
504 533
505 mutex_lock(&st->lock);
506 /*534 /*
507 * we should only update scale when the chip is disabled, i.e.535 * we should only update scale when the chip is disabled, i.e.
508 * not running536 * not running
509 */537 */
510 result = iio_device_claim_direct_mode(indio_dev);538 result = iio_device_claim_direct_mode(indio_dev);
511 if (result)539 if (result)
512 goto error_write_raw_unlock;540 return result;
541
542 mutex_lock(&st->lock);
513 result = inv_mpu6050_set_power_itg(st, true);543 result = inv_mpu6050_set_power_itg(st, true);
514 if (result)544 if (result)
515 goto error_write_raw_release;545 goto error_write_raw_unlock;
516 546
517 switch (mask) {547 switch (mask) {
518 case IIO_CHAN_INFO_SCALE:548 case IIO_CHAN_INFO_SCALE:
@@ -551,10 +581,9 @@ static int inv_mpu6050_write_raw(struct iio_dev *indio_dev, · 32 unmodified lines
551 }581 }
552 582
553 result |= inv_mpu6050_set_power_itg(st, false);583 result |= inv_mpu6050_set_power_itg(st, false);
554error_write_raw_release:
555 iio_device_release_direct_mode(indio_dev);
556error_write_raw_unlock:584error_write_raw_unlock:
557 mutex_unlock(&st->lock);585 mutex_unlock(&st->lock);
586 iio_device_release_direct_mode(indio_dev);
558 587
559 return result;588 return result;
560}589}
@@ -613,17 +642,18 @@ inv_mpu6050_fifo_rate_store(struct device *dev, struct device_attribute *attr, · 52 unmodified lines
613 fifo_rate > INV_MPU6050_MAX_FIFO_RATE)642 fifo_rate > INV_MPU6050_MAX_FIFO_RATE)
614 return -EINVAL;643 return -EINVAL;
615 644
645 result = iio_device_claim_direct_mode(indio_dev);
646 if (result)
647 return result;
648
616 mutex_lock(&st->lock);649 mutex_lock(&st->lock);
617 if (fifo_rate == st->chip_config.fifo_rate) {650 if (fifo_rate == st->chip_config.fifo_rate) {
618 result = 0;651 result = 0;
619 goto fifo_rate_fail_unlock;652 goto fifo_rate_fail_unlock;
620 }653 }
621 result = iio_device_claim_direct_mode(indio_dev);
622 if (result)
623 goto fifo_rate_fail_unlock;
624 result = inv_mpu6050_set_power_itg(st, true);654 result = inv_mpu6050_set_power_itg(st, true);
625 if (result)655 if (result)
626 goto fifo_rate_fail_release;656 goto fifo_rate_fail_unlock;
627 657
628 d = INV_MPU6050_ONE_K_HZ / fifo_rate - 1;658 d = INV_MPU6050_ONE_K_HZ / fifo_rate - 1;
629 result = regmap_write(st->map, st->reg->sample_rate_div, d);659 result = regmap_write(st->map, st->reg->sample_rate_div, d);
@@ -637,10 +667,9 @@ inv_mpu6050_fifo_rate_store(struct device *dev, struct device_attribute *attr, · 7 unmodified lines
637 667
638fifo_rate_fail_power_off:668fifo_rate_fail_power_off:
639 result |= inv_mpu6050_set_power_itg(st, false);669 result |= inv_mpu6050_set_power_itg(st, false);
640fifo_rate_fail_release:
641 iio_device_release_direct_mode(indio_dev);
642fifo_rate_fail_unlock:670fifo_rate_fail_unlock:
643 mutex_unlock(&st->lock);671 mutex_unlock(&st->lock);
672 iio_device_release_direct_mode(indio_dev);
644 if (result)673 if (result)
645 return result;674 return result;
646 675
@@ -769,7 +798,14 @@ static const struct iio_chan_spec inv_mpu_channels[] = { · 122 unmodified lines
769 INV_MPU6050_CHAN(IIO_ACCEL, IIO_MOD_Z, INV_MPU6050_SCAN_ACCL_Z),798 INV_MPU6050_CHAN(IIO_ACCEL, IIO_MOD_Z, INV_MPU6050_SCAN_ACCL_Z),
770};799};
771 800
772/* constant IIO attribute */801/*
802 * The user can choose any frequency between INV_MPU6050_MIN_FIFO_RATE and
803 * INV_MPU6050_MAX_FIFO_RATE, but only these frequencies are matched by the
804 * low-pass filter. Specifically, each of these sampling rates are about twice
805 * the bandwidth of a corresponding low-pass filter, which should eliminate
806 * aliasing following the Nyquist principle. By picking a frequency different
807 * from these, the user risks aliasing effects.
808 */
773static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("10 20 50 100 200 500");809static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("10 20 50 100 200 500");
774static IIO_CONST_ATTR(in_anglvel_scale_available,810static IIO_CONST_ATTR(in_anglvel_scale_available,
775 "0.000133090 0.000266181 0.000532362 0.001064724");811 "0.000133090 0.000266181 0.000532362 0.001064724");
@@ -850,14 +886,11 @@ static int inv_check_and_setup_chip(struct inv_mpu6050_state *st) · 74 unmodified lines
850 msleep(INV_MPU6050_POWER_UP_TIME);886 msleep(INV_MPU6050_POWER_UP_TIME);
851 887
852 /*888 /*
853 * toggle power state. After reset, the sleep bit could be on889 * Turn power on. After reset, the sleep bit could be on
854 * or off depending on the OTP settings. Toggling power would890 * or off depending on the OTP settings. Turning power on
855 * make it in a definite state as well as making the hardware891 * make it in a definite state as well as making the hardware
856 * state align with the software state892 * state align with the software state
857 */893 */
858 result = inv_mpu6050_set_power_itg(st, false);
859 if (result)
860 return result;
861 result = inv_mpu6050_set_power_itg(st, true);894 result = inv_mpu6050_set_power_itg(st, true);
862 if (result)895 if (result)
863 return result;896 return result;
@@ -865,13 +898,17 @@ static int inv_check_and_setup_chip(struct inv_mpu6050_state *st) · 1 unmodified line
865 result = inv_mpu6050_switch_engine(st, false,898 result = inv_mpu6050_switch_engine(st, false,
866 INV_MPU6050_BIT_PWR_ACCL_STBY);899 INV_MPU6050_BIT_PWR_ACCL_STBY);
867 if (result)900 if (result)
868 return result;901 goto error_power_off;
869 result = inv_mpu6050_switch_engine(st, false,902 result = inv_mpu6050_switch_engine(st, false,
870 INV_MPU6050_BIT_PWR_GYRO_STBY);903 INV_MPU6050_BIT_PWR_GYRO_STBY);
871 if (result)904 if (result)
872 return result;905 goto error_power_off;
873 906
874 return 0;907 return inv_mpu6050_set_power_itg(st, false);
908
909error_power_off:
910 inv_mpu6050_set_power_itg(st, false);
911 return result;
875}912}
876 913
877int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name,914int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name,
@@ -882,6 +919,8 @@ int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name, · 4 unmodified lines
882 struct inv_mpu6050_platform_data *pdata;919 struct inv_mpu6050_platform_data *pdata;
883 struct device *dev = regmap_get_device(regmap);920 struct device *dev = regmap_get_device(regmap);
884 int result;921 int result;
922 struct irq_data *desc;
923 int irq_type;
885 924
886 indio_dev = devm_iio_device_alloc(dev, sizeof(*st));925 indio_dev = devm_iio_device_alloc(dev, sizeof(*st));
887 if (!indio_dev)926 if (!indio_dev)
@@ -913,20 +952,43 @@ int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name, · 25 unmodified lines
913 st->plat_data = *pdata;952 st->plat_data = *pdata;
914 }953 }
915 954
955 desc = irq_get_irq_data(irq);
956 if (!desc) {
957 dev_err(dev, "Could not find IRQ %d\n", irq);
958 return -EINVAL;
959 }
960
961 irq_type = irqd_get_trigger_type(desc);
962 if (irq_type == IRQF_TRIGGER_RISING)
963 st->irq_mask = INV_MPU6050_ACTIVE_HIGH;
964 else if (irq_type == IRQF_TRIGGER_FALLING)
965 st->irq_mask = INV_MPU6050_ACTIVE_LOW;
966 else if (irq_type == IRQF_TRIGGER_HIGH)
967 st->irq_mask = INV_MPU6050_ACTIVE_HIGH |
968 INV_MPU6050_LATCH_INT_EN;
969 else if (irq_type == IRQF_TRIGGER_LOW)
970 st->irq_mask = INV_MPU6050_ACTIVE_LOW |
971 INV_MPU6050_LATCH_INT_EN;
972 else {
973 dev_err(dev, "Invalid interrupt type 0x%x specified\n",
974 irq_type);
975 return -EINVAL;
976 }
977
916 /* power is turned on inside check chip type*/978 /* power is turned on inside check chip type*/
917 result = inv_check_and_setup_chip(st);979 result = inv_check_and_setup_chip(st);
918 if (result)980 if (result)
919 return result;981 return result;
920 982
921 if (inv_mpu_bus_setup)
922 inv_mpu_bus_setup(indio_dev);
923
924 result = inv_mpu6050_init_config(indio_dev);983 result = inv_mpu6050_init_config(indio_dev);
925 if (result) {984 if (result) {
926 dev_err(dev, "Could not initialize device.\n");985 dev_err(dev, "Could not initialize device.\n");
927 return result;986 return result;
928 }987 }
929 988
989 if (inv_mpu_bus_setup)
990 inv_mpu_bus_setup(indio_dev);
991
930 dev_set_drvdata(dev, indio_dev);992 dev_set_drvdata(dev, indio_dev);
931 indio_dev->dev.parent = dev;993 indio_dev->dev.parent = dev;
932 /* name will be NULL when enumerated via ACPI */994 /* name will be NULL when enumerated via ACPI */
@@ -940,50 +1002,32 @@ int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name, · 7 unmodified lines
940 indio_dev->info = &mpu_info;1002 indio_dev->info = &mpu_info;
941 indio_dev->modes = INDIO_BUFFER_TRIGGERED;1003 indio_dev->modes = INDIO_BUFFER_TRIGGERED;
942 1004
943 result = iio_triggered_buffer_setup(indio_dev,1005 result = devm_iio_triggered_buffer_setup(dev, indio_dev,
944 inv_mpu6050_irq_handler,1006 inv_mpu6050_irq_handler,
945 inv_mpu6050_read_fifo,1007 inv_mpu6050_read_fifo,
946 NULL);1008 NULL);
947 if (result) {1009 if (result) {
948 dev_err(dev, "configure buffer fail %d\n", result);1010 dev_err(dev, "configure buffer fail %d\n", result);
949 return result;1011 return result;
950 }1012 }
951 result = inv_mpu6050_probe_trigger(indio_dev);1013 result = inv_mpu6050_probe_trigger(indio_dev, irq_type);
952 if (result) {1014 if (result) {
953 dev_err(dev, "trigger probe fail %d\n", result);1015 dev_err(dev, "trigger probe fail %d\n", result);
954 goto out_unreg_ring;1016 return result;
955 }1017 }
956 1018
957 INIT_KFIFO(st->timestamps);1019 INIT_KFIFO(st->timestamps);
958 spin_lock_init(&st->time_stamp_lock);1020 spin_lock_init(&st->time_stamp_lock);
959 result = iio_device_register(indio_dev);1021 result = devm_iio_device_register(dev, indio_dev);
960 if (result) {1022 if (result) {
961 dev_err(dev, "IIO register fail %d\n", result);1023 dev_err(dev, "IIO register fail %d\n", result);
962 goto out_remove_trigger;1024 return result;
963 }1025 }
964 1026
965 return 0;1027 return 0;
966
967out_remove_trigger:
968 inv_mpu6050_remove_trigger(st);
969out_unreg_ring:
970 iio_triggered_buffer_cleanup(indio_dev);
971 return result;
972}1028}
973EXPORT_SYMBOL_GPL(inv_mpu_core_probe);1029EXPORT_SYMBOL_GPL(inv_mpu_core_probe);
974 1030
975int inv_mpu_core_remove(struct device *dev)
976{
977 struct iio_dev *indio_dev = dev_get_drvdata(dev);
978
979 iio_device_unregister(indio_dev);
980 inv_mpu6050_remove_trigger(iio_priv(indio_dev));
981 iio_triggered_buffer_cleanup(indio_dev);
982
983 return 0;
984}
985EXPORT_SYMBOL_GPL(inv_mpu_core_remove);
986
987#ifdef CONFIG_PM_SLEEP1031#ifdef CONFIG_PM_SLEEP
988 1032
989static int inv_mpu_resume(struct device *dev)1033static int inv_mpu_resume(struct device *dev)
drivers/iio/imu/inv_mpu6050/inv_mpu_i2c.c+44−42
@@ -29,25 +29,18 @@ static int inv_mpu6050_select_bypass(struct i2c_mux_core *muxc, u32 chan_id) · 28 unmodified lines
29{29{
30 struct iio_dev *indio_dev = i2c_mux_priv(muxc);30 struct iio_dev *indio_dev = i2c_mux_priv(muxc);
31 struct inv_mpu6050_state *st = iio_priv(indio_dev);31 struct inv_mpu6050_state *st = iio_priv(indio_dev);
32 int ret = 0;32 int ret;
33 33
34 /* Use the same mutex which was used everywhere to protect power-op */
35 mutex_lock(&st->lock);34 mutex_lock(&st->lock);
36 if (!st->powerup_count) {
37 ret = regmap_write(st->map, st->reg->pwr_mgmt_1, 0);
38 if (ret)
39 goto write_error;
40 35
41 usleep_range(INV_MPU6050_REG_UP_TIME_MIN,36 ret = inv_mpu6050_set_power_itg(st, true);
42 INV_MPU6050_REG_UP_TIME_MAX);37 if (ret)
43 }38 goto error_unlock;
44 if (!ret) {39
45 st->powerup_count++;40 ret = regmap_write(st->map, st->reg->int_pin_cfg,
46 ret = regmap_write(st->map, st->reg->int_pin_cfg,41 st->irq_mask | INV_MPU6050_BIT_BYPASS_EN);
47 INV_MPU6050_INT_PIN_CFG |42
48 INV_MPU6050_BIT_BYPASS_EN);43error_unlock:
49 }
50write_error:
51 mutex_unlock(&st->lock);44 mutex_unlock(&st->lock);
52 45
53 return ret;46 return ret;
@@ -59,12 +52,11 @@ static int inv_mpu6050_deselect_bypass(struct i2c_mux_core *muxc, u32 chan_id) · 5 unmodified lines
59 struct inv_mpu6050_state *st = iio_priv(indio_dev);52 struct inv_mpu6050_state *st = iio_priv(indio_dev);
60 53
61 mutex_lock(&st->lock);54 mutex_lock(&st->lock);
62 /* It doesn't really mattter, if any of the calls fails */55
63 regmap_write(st->map, st->reg->int_pin_cfg, INV_MPU6050_INT_PIN_CFG);56 /* It doesn't really matter if any of the calls fail */
64 st->powerup_count--;57 regmap_write(st->map, st->reg->int_pin_cfg, st->irq_mask);
65 if (!st->powerup_count)58 inv_mpu6050_set_power_itg(st, false);
66 regmap_write(st->map, st->reg->pwr_mgmt_1,59
67 INV_MPU6050_BIT_SLEEP);
68 mutex_unlock(&st->lock);60 mutex_unlock(&st->lock);
69 61
70 return 0;62 return 0;
@@ -133,29 +125,32 @@ static int inv_mpu_probe(struct i2c_client *client, · 62 unmodified lines
133 return result;125 return result;
134 126
135 st = iio_priv(dev_get_drvdata(&client->dev));127 st = iio_priv(dev_get_drvdata(&client->dev));
136 st->muxc = i2c_mux_alloc(client->adapter, &client->dev,128 switch (st->chip_type) {
137 1, 0, I2C_MUX_LOCKED | I2C_MUX_GATE,129 case INV_ICM20608:
138 inv_mpu6050_select_bypass,130 /* no i2c auxiliary bus on the chip */
139 inv_mpu6050_deselect_bypass);131 break;
140 if (!st->muxc) {132 default:
141 result = -ENOMEM;133 /* declare i2c auxiliary bus */
142 goto out_unreg_device;134 st->muxc = i2c_mux_alloc(client->adapter, &client->dev,
135 1, 0, I2C_MUX_LOCKED | I2C_MUX_GATE,
136 inv_mpu6050_select_bypass,
137 inv_mpu6050_deselect_bypass);
138 if (!st->muxc)
139 return -ENOMEM;
140 st->muxc->priv = dev_get_drvdata(&client->dev);
141 result = i2c_mux_add_adapter(st->muxc, 0, 0, 0);
142 if (result)
143 return result;
144 result = inv_mpu_acpi_create_mux_client(client);
145 if (result)
146 goto out_del_mux;
147 break;
143 }148 }
144 st->muxc->priv = dev_get_drvdata(&client->dev);
145 result = i2c_mux_add_adapter(st->muxc, 0, 0, 0);
146 if (result)
147 goto out_unreg_device;
148
149 result = inv_mpu_acpi_create_mux_client(client);
150 if (result)
151 goto out_del_mux;
152 149
153 return 0;150 return 0;
154 151
155out_del_mux:152out_del_mux:
156 i2c_mux_del_adapters(st->muxc);153 i2c_mux_del_adapters(st->muxc);
157out_unreg_device:
158 inv_mpu_core_remove(&client->dev);
159 return result;154 return result;
160}155}
161 156
@@ -164,10 +159,12 @@ static int inv_mpu_remove(struct i2c_client *client) · 2 unmodified lines
164 struct iio_dev *indio_dev = i2c_get_clientdata(client);159 struct iio_dev *indio_dev = i2c_get_clientdata(client);
165 struct inv_mpu6050_state *st = iio_priv(indio_dev);160 struct inv_mpu6050_state *st = iio_priv(indio_dev);
166 161
167 inv_mpu_acpi_delete_mux_client(client);162 if (st->muxc) {
168 i2c_mux_del_adapters(st->muxc);163 inv_mpu_acpi_delete_mux_client(client);
164 i2c_mux_del_adapters(st->muxc);
165 }
169 166
170 return inv_mpu_core_remove(&client->dev);167 return 0;
171}168}
172 169
173/*170/*
@@ -179,6 +176,7 @@ static const struct i2c_device_id inv_mpu_id[] = { · 5 unmodified lines
179 {"mpu6500", INV_MPU6500},176 {"mpu6500", INV_MPU6500},
180 {"mpu9150", INV_MPU9150},177 {"mpu9150", INV_MPU9150},
181 {"mpu9250", INV_MPU9250},178 {"mpu9250", INV_MPU9250},
179 {"mpu9255", INV_MPU9255},
182 {"icm20608", INV_ICM20608},180 {"icm20608", INV_ICM20608},
183 {}181 {}
184};182};
@@ -202,6 +200,10 @@ static const struct of_device_id inv_of_match[] = { · 17 unmodified lines
202 .compatible = "invensense,mpu9250",200 .compatible = "invensense,mpu9250",
203 .data = (void *)INV_MPU9250201 .data = (void *)INV_MPU9250
204 },202 },
203 {
204 .compatible = "invensense,mpu9255",
205 .data = (void *)INV_MPU9255
206 },
205 {207 {
206 .compatible = "invensense,icm20608",208 .compatible = "invensense,icm20608",
207 .data = (void *)INV_ICM20608209 .data = (void *)INV_ICM20608
drivers/iio/imu/inv_mpu6050/inv_mpu_iio.h+17−5
@@ -40,6 +40,7 @@ · 39 unmodified lines
40 * @raw_accl: Address of first accel register.40 * @raw_accl: Address of first accel register.
41 * @temperature: temperature register41 * @temperature: temperature register
42 * @int_enable: Interrupt enable register.42 * @int_enable: Interrupt enable register.
43 * @int_status: Interrupt status register.
43 * @pwr_mgmt_1: Controls chip's power state and clock source.44 * @pwr_mgmt_1: Controls chip's power state and clock source.
44 * @pwr_mgmt_2: Controls power state of individual sensors.45 * @pwr_mgmt_2: Controls power state of individual sensors.
45 * @int_pin_cfg; Controls interrupt pin configuration.46 * @int_pin_cfg; Controls interrupt pin configuration.
@@ -60,6 +61,7 @@ struct inv_mpu6050_reg_map { · 14 unmodified lines
60 u8 raw_accl;61 u8 raw_accl;
61 u8 temperature;62 u8 temperature;
62 u8 int_enable;63 u8 int_enable;
64 u8 int_status;
63 u8 pwr_mgmt_1;65 u8 pwr_mgmt_1;
64 u8 pwr_mgmt_2;66 u8 pwr_mgmt_2;
65 u8 int_pin_cfg;67 u8 int_pin_cfg;
@@ -74,6 +76,7 @@ enum inv_devices { · 8 unmodified lines
74 INV_MPU6000,76 INV_MPU6000,
75 INV_MPU9150,77 INV_MPU9150,
76 INV_MPU9250,78 INV_MPU9250,
79 INV_MPU9255,
77 INV_ICM20608,80 INV_ICM20608,
78 INV_NUM_PARTS81 INV_NUM_PARTS
79};82};
@@ -94,6 +97,7 @@ struct inv_mpu6050_chip_config { · 14 unmodified lines
94 unsigned int accl_fifo_enable:1;97 unsigned int accl_fifo_enable:1;
95 unsigned int gyro_fifo_enable:1;98 unsigned int gyro_fifo_enable:1;
96 u16 fifo_rate;99 u16 fifo_rate;
100 u8 user_ctrl;
97};101};
98 102
99/**103/**
@@ -125,6 +129,7 @@ struct inv_mpu6050_hw { · 25 unmodified lines
125 * @timestamps: kfifo queue to store time stamp.129 * @timestamps: kfifo queue to store time stamp.
126 * @map regmap pointer.130 * @map regmap pointer.
127 * @irq interrupt number.131 * @irq interrupt number.
132 * @irq_mask the int_pin_cfg mask to configure interrupt type.
128 */133 */
129struct inv_mpu6050_state {134struct inv_mpu6050_state {
130#define TIMESTAMP_FIFO_SIZE 16135#define TIMESTAMP_FIFO_SIZE 16
@@ -143,6 +148,8 @@ struct inv_mpu6050_state { · 12 unmodified lines
143 DECLARE_KFIFO(timestamps, long long, TIMESTAMP_FIFO_SIZE);148 DECLARE_KFIFO(timestamps, long long, TIMESTAMP_FIFO_SIZE);
144 struct regmap *map;149 struct regmap *map;
145 int irq;150 int irq;
151 u8 irq_mask;
152 unsigned skip_samples;
146};153};
147 154
148/*register and associated bit definition*/155/*register and associated bit definition*/
@@ -166,6 +173,9 @@ struct inv_mpu6050_state { · 17 unmodified lines
166#define INV_MPU6050_REG_TEMPERATURE 0x41173#define INV_MPU6050_REG_TEMPERATURE 0x41
167#define INV_MPU6050_REG_RAW_GYRO 0x43174#define INV_MPU6050_REG_RAW_GYRO 0x43
168 175
176#define INV_MPU6050_REG_INT_STATUS 0x3A
177#define INV_MPU6050_BIT_RAW_DATA_RDY_INT 0x01
178
169#define INV_MPU6050_REG_USER_CTRL 0x6A179#define INV_MPU6050_REG_USER_CTRL 0x6A
170#define INV_MPU6050_BIT_FIFO_RST 0x04180#define INV_MPU6050_BIT_FIFO_RST 0x04
171#define INV_MPU6050_BIT_DMP_RST 0x08181#define INV_MPU6050_BIT_DMP_RST 0x08
@@ -215,8 +225,12 @@ struct inv_mpu6050_state { · 43 unmodified lines
215#define INV_MPU6050_OUTPUT_DATA_SIZE 24225#define INV_MPU6050_OUTPUT_DATA_SIZE 24
216 226
217#define INV_MPU6050_REG_INT_PIN_CFG 0x37227#define INV_MPU6050_REG_INT_PIN_CFG 0x37
228#define INV_MPU6050_ACTIVE_HIGH 0x00
229#define INV_MPU6050_ACTIVE_LOW 0x80
230/* enable level triggering */
231#define INV_MPU6050_LATCH_INT_EN 0x20
218#define INV_MPU6050_BIT_BYPASS_EN 0x2232#define INV_MPU6050_BIT_BYPASS_EN 0x2
219#define INV_MPU6050_INT_PIN_CFG 0233
220 234
221/* init parameters */235/* init parameters */
222#define INV_MPU6050_INIT_FIFO_RATE 50236#define INV_MPU6050_INIT_FIFO_RATE 50
@@ -232,6 +246,7 @@ struct inv_mpu6050_state { · 9 unmodified lines
232#define INV_MPU6500_WHOAMI_VALUE 0x70246#define INV_MPU6500_WHOAMI_VALUE 0x70
233#define INV_MPU9150_WHOAMI_VALUE 0x68247#define INV_MPU9150_WHOAMI_VALUE 0x68
234#define INV_MPU9250_WHOAMI_VALUE 0x71248#define INV_MPU9250_WHOAMI_VALUE 0x71
249#define INV_MPU9255_WHOAMI_VALUE 0x73
235#define INV_ICM20608_WHOAMI_VALUE 0xAF250#define INV_ICM20608_WHOAMI_VALUE 0xAF
236 251
237/* scan element definition */252/* scan element definition */
@@ -287,8 +302,7 @@ enum inv_mpu6050_clock_sel_e { · 49 unmodified lines
287 302
288irqreturn_t inv_mpu6050_irq_handler(int irq, void *p);303irqreturn_t inv_mpu6050_irq_handler(int irq, void *p);
289irqreturn_t inv_mpu6050_read_fifo(int irq, void *p);304irqreturn_t inv_mpu6050_read_fifo(int irq, void *p);
290int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev);305int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev, int irq_type);
291void inv_mpu6050_remove_trigger(struct inv_mpu6050_state *st);
292int inv_reset_fifo(struct iio_dev *indio_dev);306int inv_reset_fifo(struct iio_dev *indio_dev);
293int inv_mpu6050_switch_engine(struct inv_mpu6050_state *st, bool en, u32 mask);307int inv_mpu6050_switch_engine(struct inv_mpu6050_state *st, bool en, u32 mask);
294int inv_mpu6050_write_reg(struct inv_mpu6050_state *st, int reg, u8 val);308int inv_mpu6050_write_reg(struct inv_mpu6050_state *st, int reg, u8 val);
@@ -297,6 +311,4 @@ int inv_mpu_acpi_create_mux_client(struct i2c_client *client); · 2 unmodified lines
297void inv_mpu_acpi_delete_mux_client(struct i2c_client *client);311void inv_mpu_acpi_delete_mux_client(struct i2c_client *client);
298int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name,312int inv_mpu_core_probe(struct regmap *regmap, int irq, const char *name,
299 int (*inv_mpu_bus_setup)(struct iio_dev *), int chip_type);313 int (*inv_mpu_bus_setup)(struct iio_dev *), int chip_type);
300int inv_mpu_core_remove(struct device *dev);
301int inv_mpu6050_set_power_itg(struct inv_mpu6050_state *st, bool power_on);
302extern const struct dev_pm_ops inv_mpu_pmops;314extern const struct dev_pm_ops inv_mpu_pmops;
drivers/iio/imu/inv_mpu6050/inv_mpu_ring.c+33−14
@@ -51,13 +51,14 @@ int inv_reset_fifo(struct iio_dev *indio_dev) · 50 unmodified lines
51 if (result)51 if (result)
52 goto reset_fifo_fail;52 goto reset_fifo_fail;
53 /* disable fifo reading */53 /* disable fifo reading */
54 result = regmap_write(st->map, st->reg->user_ctrl, 0);54 result = regmap_write(st->map, st->reg->user_ctrl,
55 st->chip_config.user_ctrl);
55 if (result)56 if (result)
56 goto reset_fifo_fail;57 goto reset_fifo_fail;
57 58
58 /* reset FIFO*/59 /* reset FIFO*/
59 result = regmap_write(st->map, st->reg->user_ctrl,60 d = st->chip_config.user_ctrl | INV_MPU6050_BIT_FIFO_RST;
60 INV_MPU6050_BIT_FIFO_RST);61 result = regmap_write(st->map, st->reg->user_ctrl, d);
61 if (result)62 if (result)
62 goto reset_fifo_fail;63 goto reset_fifo_fail;
63 64
@@ -72,9 +73,9 @@ int inv_reset_fifo(struct iio_dev *indio_dev) · 8 unmodified lines
72 if (result)73 if (result)
73 return result;74 return result;
74 }75 }
75 /* enable FIFO reading and I2C master interface*/76 /* enable FIFO reading */
76 result = regmap_write(st->map, st->reg->user_ctrl,77 d = st->chip_config.user_ctrl | INV_MPU6050_BIT_FIFO_EN;
77 INV_MPU6050_BIT_FIFO_EN);78 result = regmap_write(st->map, st->reg->user_ctrl, d);
78 if (result)79 if (result)
79 goto reset_fifo_fail;80 goto reset_fifo_fail;
80 /* enable sensor output to FIFO */81 /* enable sensor output to FIFO */
@@ -127,8 +128,23 @@ irqreturn_t inv_mpu6050_read_fifo(int irq, void *p) · 46 unmodified lines
127 u8 data[INV_MPU6050_OUTPUT_DATA_SIZE];128 u8 data[INV_MPU6050_OUTPUT_DATA_SIZE];
128 u16 fifo_count;129 u16 fifo_count;
129 s64 timestamp;130 s64 timestamp;
131 int int_status;
130 132
131 mutex_lock(&st->lock);133 mutex_lock(&st->lock);
134
135 /* ack interrupt and check status */
136 result = regmap_read(st->map, st->reg->int_status, &int_status);
137 if (result) {
138 dev_err(regmap_get_device(st->map),
139 "failed to ack interrupt\n");
140 goto flush_fifo;
141 }
142 if (!(int_status & INV_MPU6050_BIT_RAW_DATA_RDY_INT)) {
143 dev_warn(regmap_get_device(st->map),
144 "spurious interrupt with status 0x%x\n", int_status);
145 goto end_session;
146 }
147
132 if (!(st->chip_config.accl_fifo_enable |148 if (!(st->chip_config.accl_fifo_enable |
133 st->chip_config.gyro_fifo_enable))149 st->chip_config.gyro_fifo_enable))
134 goto end_session;150 goto end_session;
@@ -140,7 +156,7 @@ irqreturn_t inv_mpu6050_read_fifo(int irq, void *p) · 5 unmodified lines
140 bytes_per_datum += INV_MPU6050_BYTES_PER_3AXIS_SENSOR;156 bytes_per_datum += INV_MPU6050_BYTES_PER_3AXIS_SENSOR;
141 157
142 /*158 /*
143 * read fifo_count register to know how many bytes inside FIFO159 * read fifo_count register to know how many bytes are inside the FIFO
144 * right now160 * right now
145 */161 */
146 result = regmap_bulk_read(st->map, st->reg->fifo_count_h, data,162 result = regmap_bulk_read(st->map, st->reg->fifo_count_h, data,
@@ -150,7 +166,7 @@ irqreturn_t inv_mpu6050_read_fifo(int irq, void *p) · 3 unmodified lines
150 fifo_count = be16_to_cpup((__be16 *)(&data[0]));166 fifo_count = be16_to_cpup((__be16 *)(&data[0]));
151 if (fifo_count < bytes_per_datum)167 if (fifo_count < bytes_per_datum)
152 goto end_session;168 goto end_session;
153 /* fifo count can't be odd number, if it is odd, reset fifo*/169 /* fifo count can't be an odd number. If it is odd, reset the FIFO. */
154 if (fifo_count & 1)170 if (fifo_count & 1)
155 goto flush_fifo;171 goto flush_fifo;
156 if (fifo_count > INV_MPU6050_FIFO_THRESHOLD)172 if (fifo_count > INV_MPU6050_FIFO_THRESHOLD)
@@ -159,7 +175,7 @@ irqreturn_t inv_mpu6050_read_fifo(int irq, void *p) · 2 unmodified lines
159 if (kfifo_len(&st->timestamps) >175 if (kfifo_len(&st->timestamps) >
160 fifo_count / bytes_per_datum + INV_MPU6050_TIME_STAMP_TOR)176 fifo_count / bytes_per_datum + INV_MPU6050_TIME_STAMP_TOR)
161 goto flush_fifo;177 goto flush_fifo;
162 while (fifo_count >= bytes_per_datum) {178 do {
163 result = regmap_bulk_read(st->map, st->reg->fifo_r_w,179 result = regmap_bulk_read(st->map, st->reg->fifo_r_w,
164 data, bytes_per_datum);180 data, bytes_per_datum);
165 if (result)181 if (result)
@@ -170,12 +186,15 @@ irqreturn_t inv_mpu6050_read_fifo(int irq, void *p) · 4 unmodified lines
170 if (result == 0)186 if (result == 0)
171 timestamp = 0;187 timestamp = 0;
172 188
173 result = iio_push_to_buffers_with_timestamp(indio_dev, data,189 /* skip first samples if needed */
174 timestamp);190 if (st->skip_samples)
175 if (result)191 st->skip_samples--;
176 goto flush_fifo;192 else
193 iio_push_to_buffers_with_timestamp(indio_dev, data,
194 timestamp);
195
177 fifo_count -= bytes_per_datum;196 fifo_count -= bytes_per_datum;
178 }197 } while (fifo_count >= bytes_per_datum);
179 198
180end_session:199end_session:
181 mutex_unlock(&st->lock);200 mutex_unlock(&st->lock);
drivers/iio/imu/inv_mpu6050/inv_mpu_spi.c+4−8
@@ -31,8 +31,9 @@ static int inv_mpu_i2c_disable(struct iio_dev *indio_dev) · 30 unmodified lines
31 if (ret)31 if (ret)
32 return ret;32 return ret;
33 33
34 ret = regmap_write(st->map, INV_MPU6050_REG_USER_CTRL,34 st->chip_config.user_ctrl |= INV_MPU6050_BIT_I2C_IF_DIS;
35 INV_MPU6050_BIT_I2C_IF_DIS);35 ret = regmap_write(st->map, st->reg->user_ctrl,
36 st->chip_config.user_ctrl);
36 if (ret) {37 if (ret) {
37 inv_mpu6050_set_power_itg(st, false);38 inv_mpu6050_set_power_itg(st, false);
38 return ret;39 return ret;
@@ -69,11 +70,6 @@ static int inv_mpu_probe(struct spi_device *spi) · 30 unmodified lines
69 inv_mpu_i2c_disable, chip_type);70 inv_mpu_i2c_disable, chip_type);
70}71}
71 72
72static int inv_mpu_remove(struct spi_device *spi)
73{
74 return inv_mpu_core_remove(&spi->dev);
75}
76
77/*73/*
78 * device id table is used to identify what device can be74 * device id table is used to identify what device can be
79 * supported by this driver75 * supported by this driver
@@ -83,6 +79,7 @@ static const struct spi_device_id inv_mpu_id[] = { · 3 unmodified lines
83 {"mpu6500", INV_MPU6500},79 {"mpu6500", INV_MPU6500},
84 {"mpu9150", INV_MPU9150},80 {"mpu9150", INV_MPU9150},
85 {"mpu9250", INV_MPU9250},81 {"mpu9250", INV_MPU9250},
82 {"mpu9255", INV_MPU9255},
86 {"icm20608", INV_ICM20608},83 {"icm20608", INV_ICM20608},
87 {}84 {}
88};85};
@@ -97,7 +94,6 @@ MODULE_DEVICE_TABLE(acpi, inv_acpi_match); · 8 unmodified lines
97 94
98static struct spi_driver inv_mpu_driver = {95static struct spi_driver inv_mpu_driver = {
99 .probe = inv_mpu_probe,96 .probe = inv_mpu_probe,
100 .remove = inv_mpu_remove,
101 .id_table = inv_mpu_id,97 .id_table = inv_mpu_id,
102 .driver = {98 .driver = {
103 .acpi_match_table = ACPI_PTR(inv_acpi_match),99 .acpi_match_table = ACPI_PTR(inv_acpi_match),
drivers/iio/imu/inv_mpu6050/inv_mpu_trigger.c+32−20
@@ -49,49 +49,66 @@ static int inv_mpu6050_set_enable(struct iio_dev *indio_dev, bool enable) · 48 unmodified lines
49 if (result)49 if (result)
50 return result;50 return result;
51 inv_scan_query(indio_dev);51 inv_scan_query(indio_dev);
52 st->skip_samples = 0;
52 if (st->chip_config.gyro_fifo_enable) {53 if (st->chip_config.gyro_fifo_enable) {
53 result = inv_mpu6050_switch_engine(st, true,54 result = inv_mpu6050_switch_engine(st, true,
54 INV_MPU6050_BIT_PWR_GYRO_STBY);55 INV_MPU6050_BIT_PWR_GYRO_STBY);
55 if (result)56 if (result)
56 return result;57 goto error_power_off;
58 /* gyro first sample is out of specs, skip it */
59 st->skip_samples = 1;
57 }60 }
58 if (st->chip_config.accl_fifo_enable) {61 if (st->chip_config.accl_fifo_enable) {
59 result = inv_mpu6050_switch_engine(st, true,62 result = inv_mpu6050_switch_engine(st, true,
60 INV_MPU6050_BIT_PWR_ACCL_STBY);63 INV_MPU6050_BIT_PWR_ACCL_STBY);
61 if (result)64 if (result)
62 return result;65 goto error_gyro_off;
63 }66 }
64 result = inv_reset_fifo(indio_dev);67 result = inv_reset_fifo(indio_dev);
65 if (result)68 if (result)
66 return result;69 goto error_accl_off;
67 } else {70 } else {
68 result = regmap_write(st->map, st->reg->fifo_en, 0);71 result = regmap_write(st->map, st->reg->fifo_en, 0);
69 if (result)72 if (result)
70 return result;73 goto error_accl_off;
71 74
72 result = regmap_write(st->map, st->reg->int_enable, 0);75 result = regmap_write(st->map, st->reg->int_enable, 0);
73 if (result)76 if (result)
74 return result;77 goto error_accl_off;
75 78
76 result = regmap_write(st->map, st->reg->user_ctrl, 0);79 result = regmap_write(st->map, st->reg->user_ctrl,
80 st->chip_config.user_ctrl);
77 if (result)81 if (result)
78 return result;82 goto error_accl_off;
79 83
80 result = inv_mpu6050_switch_engine(st, false,84 result = inv_mpu6050_switch_engine(st, false,
81 INV_MPU6050_BIT_PWR_GYRO_STBY);85 INV_MPU6050_BIT_PWR_ACCL_STBY);
82 if (result)86 if (result)
83 return result;87 goto error_accl_off;
84 88
85 result = inv_mpu6050_switch_engine(st, false,89 result = inv_mpu6050_switch_engine(st, false,
86 INV_MPU6050_BIT_PWR_ACCL_STBY);90 INV_MPU6050_BIT_PWR_GYRO_STBY);
87 if (result)91 if (result)
88 return result;92 goto error_gyro_off;
93
89 result = inv_mpu6050_set_power_itg(st, false);94 result = inv_mpu6050_set_power_itg(st, false);
90 if (result)95 if (result)
91 return result;96 goto error_power_off;
92 }97 }
93 98
94 return 0;99 return 0;
100
101error_accl_off:
102 if (st->chip_config.accl_fifo_enable)
103 inv_mpu6050_switch_engine(st, false,
104 INV_MPU6050_BIT_PWR_ACCL_STBY);
105error_gyro_off:
106 if (st->chip_config.gyro_fifo_enable)
107 inv_mpu6050_switch_engine(st, false,
108 INV_MPU6050_BIT_PWR_GYRO_STBY);
109error_power_off:
110 inv_mpu6050_set_power_itg(st, false);
111 return result;
95}112}
96 113
97/**114/**
@@ -117,7 +134,7 @@ static const struct iio_trigger_ops inv_mpu_trigger_ops = { · 19 unmodified lines
117 .set_trigger_state = &inv_mpu_data_rdy_trigger_set_state,134 .set_trigger_state = &inv_mpu_data_rdy_trigger_set_state,
118};135};
119 136
120int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev)137int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev, int irq_type)
121{138{
122 int ret;139 int ret;
123 struct inv_mpu6050_state *st = iio_priv(indio_dev);140 struct inv_mpu6050_state *st = iio_priv(indio_dev);
@@ -131,7 +148,7 @@ int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev) · 7 unmodified lines
131 148
132 ret = devm_request_irq(&indio_dev->dev, st->irq,149 ret = devm_request_irq(&indio_dev->dev, st->irq,
133 &iio_trigger_generic_data_rdy_poll,150 &iio_trigger_generic_data_rdy_poll,
134 IRQF_TRIGGER_RISING,151 irq_type,
135 "inv_mpu",152 "inv_mpu",
136 st->trig);153 st->trig);
137 if (ret)154 if (ret)
@@ -141,7 +158,7 @@ int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev) · 3 unmodified lines
141 st->trig->ops = &inv_mpu_trigger_ops;158 st->trig->ops = &inv_mpu_trigger_ops;
142 iio_trigger_set_drvdata(st->trig, indio_dev);159 iio_trigger_set_drvdata(st->trig, indio_dev);
143 160
144 ret = iio_trigger_register(st->trig);161 ret = devm_iio_trigger_register(&indio_dev->dev, st->trig);
145 if (ret)162 if (ret)
146 return ret;163 return ret;
147 164
@@ -149,8 +166,3 @@ int inv_mpu6050_probe_trigger(struct iio_dev *indio_dev) · 1 unmodified line
149 166
150 return 0;167 return 0;
151}168}
152
153void inv_mpu6050_remove_trigger(struct inv_mpu6050_state *st)
154{
155 iio_trigger_unregister(st->trig);
156}
drivers/iio/imu/st_lsm6dsx/Kconfig+2−1
@@ -8,7 +8,8 @@ config IIO_ST_LSM6DSX · 7 unmodified lines
8 select IIO_ST_LSM6DSX_SPI if (SPI_MASTER)8 select IIO_ST_LSM6DSX_SPI if (SPI_MASTER)
9 help9 help
10 Say yes here to build support for STMicroelectronics LSM6DSx imu10 Say yes here to build support for STMicroelectronics LSM6DSx imu
11 sensor. Supported devices: lsm6ds3, lsm6ds3h, lsm6dsl, lsm6dsm11 sensor. Supported devices: lsm6ds3, lsm6ds3h, lsm6dsl, lsm6dsm,
12 ism330dlc
12 13
13 To compile this driver as a module, choose M here: the module14 To compile this driver as a module, choose M here: the module
14 will be called st_lsm6dsx.15 will be called st_lsm6dsx.
drivers/iio/imu/st_lsm6dsx/st_lsm6dsx.h+2−0
@@ -18,12 +18,14 @@ · 17 unmodified lines
18#define ST_LSM6DS3H_DEV_NAME "lsm6ds3h"18#define ST_LSM6DS3H_DEV_NAME "lsm6ds3h"
19#define ST_LSM6DSL_DEV_NAME "lsm6dsl"19#define ST_LSM6DSL_DEV_NAME "lsm6dsl"
20#define ST_LSM6DSM_DEV_NAME "lsm6dsm"20#define ST_LSM6DSM_DEV_NAME "lsm6dsm"
21#define ST_ISM330DLC_DEV_NAME "ism330dlc"
21 22
22enum st_lsm6dsx_hw_id {23enum st_lsm6dsx_hw_id {
23 ST_LSM6DS3_ID,24 ST_LSM6DS3_ID,
24 ST_LSM6DS3H_ID,25 ST_LSM6DS3H_ID,
25 ST_LSM6DSL_ID,26 ST_LSM6DSL_ID,
26 ST_LSM6DSM_ID,27 ST_LSM6DSM_ID,
28 ST_ISM330DLC_ID,
27 ST_LSM6DSX_MAX_ID,29 ST_LSM6DSX_MAX_ID,
28};30};
29 31
drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_buffer.c+5−5
@@ -1,10 +1,10 @@
1/*1/*
2 * STMicroelectronics st_lsm6dsx FIFO buffer library driver2 * STMicroelectronics st_lsm6dsx FIFO buffer library driver
3 *3 *
4 * LSM6DS3/LSM6DS3H/LSM6DSL/LSM6DSM: The FIFO buffer can be configured4 * LSM6DS3/LSM6DS3H/LSM6DSL/LSM6DSM/ISM330DLC: The FIFO buffer can be
5 * to store data from gyroscope and accelerometer. Samples are queued5 * configured to store data from gyroscope and accelerometer. Samples are
6 * without any tag according to a specific pattern based on 'FIFO data sets'6 * queued without any tag according to a specific pattern based on
7 * (6 bytes each):7 * 'FIFO data sets' (6 bytes each):
8 * - 1st data set is reserved for gyroscope data8 * - 1st data set is reserved for gyroscope data
9 * - 2nd data set is reserved for accelerometer data9 * - 2nd data set is reserved for accelerometer data
10 * The FIFO pattern changes depending on the ODRs and decimation factors10 * The FIFO pattern changes depending on the ODRs and decimation factors
@@ -276,7 +276,7 @@ static inline int st_lsm6dsx_read_block(struct st_lsm6dsx_hw *hw, u8 *data, · 265 unmodified lines
276#define ST_LSM6DSX_IIO_BUFF_SIZE (ALIGN(ST_LSM6DSX_SAMPLE_SIZE, \276#define ST_LSM6DSX_IIO_BUFF_SIZE (ALIGN(ST_LSM6DSX_SAMPLE_SIZE, \
277 sizeof(s64)) + sizeof(s64))277 sizeof(s64)) + sizeof(s64))
278/**278/**
279 * st_lsm6dsx_read_fifo() - LSM6DS3-LSM6DS3H-LSM6DSL-LSM6DSM read FIFO routine279 * st_lsm6dsx_read_fifo() - hw FIFO read routine
280 * @hw: Pointer to instance of struct st_lsm6dsx_hw.280 * @hw: Pointer to instance of struct st_lsm6dsx_hw.
281 *281 *
282 * Read samples from the hw FIFO and push them to IIO buffers.282 * Read samples from the hw FIFO and push them to IIO buffers.
drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_core.c+4−3
@@ -17,7 +17,7 @@ · 16 unmodified lines
17 * - Gyroscope supported full-scale [dps]: +-125/+-245/+-500/+-1000/+-200017 * - Gyroscope supported full-scale [dps]: +-125/+-245/+-500/+-1000/+-2000
18 * - FIFO size: 8KB18 * - FIFO size: 8KB
19 *19 *
20 * - LSM6DS3H/LSM6DSL/LSM6DSM:20 * - LSM6DS3H/LSM6DSL/LSM6DSM/ISM330DLC:
21 * - Accelerometer/Gyroscope supported ODR [Hz]: 13, 26, 52, 104, 208, 41621 * - Accelerometer/Gyroscope supported ODR [Hz]: 13, 26, 52, 104, 208, 416
22 * - Accelerometer supported full-scale [g]: +-2/+-4/+-8/+-1622 * - Accelerometer supported full-scale [g]: +-2/+-4/+-8/+-16
23 * - Gyroscope supported full-scale [dps]: +-125/+-245/+-500/+-1000/+-200023 * - Gyroscope supported full-scale [dps]: +-125/+-245/+-500/+-1000/+-2000
@@ -252,6 +252,7 @@ static const struct st_lsm6dsx_settings st_lsm6dsx_sensor_settings[] = { · 228 unmodified lines
252 .id = {252 .id = {
253 [0] = ST_LSM6DSL_ID,253 [0] = ST_LSM6DSL_ID,
254 [1] = ST_LSM6DSM_ID,254 [1] = ST_LSM6DSM_ID,
255 [2] = ST_ISM330DLC_ID,
255 },256 },
256 .decimator = {257 .decimator = {
257 [ST_LSM6DSX_ID_ACC] = {258 [ST_LSM6DSX_ID_ACC] = {
@@ -266,11 +267,11 @@ static const struct st_lsm6dsx_settings st_lsm6dsx_sensor_settings[] = { · 8 unmodified lines
266 .fifo_ops = {267 .fifo_ops = {
267 .fifo_th = {268 .fifo_th = {
268 .addr = 0x06,269 .addr = 0x06,
269 .mask = GENMASK(11, 0),270 .mask = GENMASK(10, 0),
270 },271 },
271 .fifo_diff = {272 .fifo_diff = {
272 .addr = 0x3a,273 .addr = 0x3a,
273 .mask = GENMASK(11, 0),274 .mask = GENMASK(10, 0),
274 },275 },
275 .th_wl = 3, /* 1LSB = 2B */276 .th_wl = 3, /* 1LSB = 2B */
276 },277 },
drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_i2c.c+5−0
@@ -57,6 +57,10 @@ static const struct of_device_id st_lsm6dsx_i2c_of_match[] = { · 56 unmodified lines
57 .compatible = "st,lsm6dsm",57 .compatible = "st,lsm6dsm",
58 .data = (void *)ST_LSM6DSM_ID,58 .data = (void *)ST_LSM6DSM_ID,
59 },59 },
60 {
61 .compatible = "st,ism330dlc",
62 .data = (void *)ST_ISM330DLC_ID,
63 },
60 {},64 {},
61};65};
62MODULE_DEVICE_TABLE(of, st_lsm6dsx_i2c_of_match);66MODULE_DEVICE_TABLE(of, st_lsm6dsx_i2c_of_match);
@@ -66,6 +70,7 @@ static const struct i2c_device_id st_lsm6dsx_i2c_id_table[] = { · 3 unmodified lines
66 { ST_LSM6DS3H_DEV_NAME, ST_LSM6DS3H_ID },70 { ST_LSM6DS3H_DEV_NAME, ST_LSM6DS3H_ID },
67 { ST_LSM6DSL_DEV_NAME, ST_LSM6DSL_ID },71 { ST_LSM6DSL_DEV_NAME, ST_LSM6DSL_ID },
68 { ST_LSM6DSM_DEV_NAME, ST_LSM6DSM_ID },72 { ST_LSM6DSM_DEV_NAME, ST_LSM6DSM_ID },
73 { ST_ISM330DLC_DEV_NAME, ST_ISM330DLC_ID },
69 {},74 {},
70};75};
71MODULE_DEVICE_TABLE(i2c, st_lsm6dsx_i2c_id_table);76MODULE_DEVICE_TABLE(i2c, st_lsm6dsx_i2c_id_table);
drivers/iio/imu/st_lsm6dsx/st_lsm6dsx_spi.c+5−0
@@ -57,6 +57,10 @@ static const struct of_device_id st_lsm6dsx_spi_of_match[] = { · 56 unmodified lines
57 .compatible = "st,lsm6dsm",57 .compatible = "st,lsm6dsm",
58 .data = (void *)ST_LSM6DSM_ID,58 .data = (void *)ST_LSM6DSM_ID,
59 },59 },
60 {
61 .compatible = "st,ism330dlc",
62 .data = (void *)ST_ISM330DLC_ID,
63 },
60 {},64 {},
61};65};
62MODULE_DEVICE_TABLE(of, st_lsm6dsx_spi_of_match);66MODULE_DEVICE_TABLE(of, st_lsm6dsx_spi_of_match);
@@ -66,6 +70,7 @@ static const struct spi_device_id st_lsm6dsx_spi_id_table[] = { · 3 unmodified lines
66 { ST_LSM6DS3H_DEV_NAME, ST_LSM6DS3H_ID },70 { ST_LSM6DS3H_DEV_NAME, ST_LSM6DS3H_ID },
67 { ST_LSM6DSL_DEV_NAME, ST_LSM6DSL_ID },71 { ST_LSM6DSL_DEV_NAME, ST_LSM6DSL_ID },
68 { ST_LSM6DSM_DEV_NAME, ST_LSM6DSM_ID },72 { ST_LSM6DSM_DEV_NAME, ST_LSM6DSM_ID },
73 { ST_ISM330DLC_DEV_NAME, ST_ISM330DLC_ID },
69 {},74 {},
70};75};
71MODULE_DEVICE_TABLE(spi, st_lsm6dsx_spi_id_table);76MODULE_DEVICE_TABLE(spi, st_lsm6dsx_spi_id_table);
drivers/iio/light/Kconfig+8−0
@@ -409,6 +409,14 @@ config TSL2583 · 408 unmodified lines
409 Provides support for the TAOS tsl2580, tsl2581 and tsl2583 devices.409 Provides support for the TAOS tsl2580, tsl2581 and tsl2583 devices.
410 Access ALS data via iio, sysfs.410 Access ALS data via iio, sysfs.
411 411
412config TSL2772
413 tristate "TAOS TSL/TMD2x71 and TSL/TMD2x72 Family of light and proximity sensors"
414 depends on I2C
415 help
416 Support for: tsl2571, tsl2671, tmd2671, tsl2771, tmd2771, tsl2572, tsl2672,
417 tmd2672, tsl2772, tmd2772 devices.
418 Provides iio_events and direct access via sysfs.
419
412config TSL4531420config TSL4531
413 tristate "TAOS TSL4531 ambient light sensors"421 tristate "TAOS TSL4531 ambient light sensors"
414 depends on I2C422 depends on I2C
drivers/iio/light/Makefile+1−0
@@ -40,6 +40,7 @@ obj-$(CONFIG_ST_UVIS25_SPI) += st_uvis25_spi.o · 39 unmodified lines
40obj-$(CONFIG_TCS3414) += tcs3414.o40obj-$(CONFIG_TCS3414) += tcs3414.o
41obj-$(CONFIG_TCS3472) += tcs3472.o41obj-$(CONFIG_TCS3472) += tcs3472.o
42obj-$(CONFIG_TSL2583) += tsl2583.o42obj-$(CONFIG_TSL2583) += tsl2583.o
43obj-$(CONFIG_TSL2772) += tsl2772.o
43obj-$(CONFIG_TSL4531) += tsl4531.o44obj-$(CONFIG_TSL4531) += tsl4531.o
44obj-$(CONFIG_US5182D) += us5182d.o45obj-$(CONFIG_US5182D) += us5182d.o
45obj-$(CONFIG_VCNL4000) += vcnl4000.o46obj-$(CONFIG_VCNL4000) += vcnl4000.o
drivers/iio/light/cros_ec_light_prox.c+1−2
@@ -16,6 +16,7 @@ · 15 unmodified lines
16#include <linux/delay.h>16#include <linux/delay.h>
17#include <linux/device.h>17#include <linux/device.h>
18#include <linux/iio/buffer.h>18#include <linux/iio/buffer.h>
19#include <linux/iio/common/cros_ec_sensors_core.h>
19#include <linux/iio/iio.h>20#include <linux/iio/iio.h>
20#include <linux/iio/kfifo_buf.h>21#include <linux/iio/kfifo_buf.h>
21#include <linux/iio/trigger.h>22#include <linux/iio/trigger.h>
@@ -29,8 +30,6 @@ · 7 unmodified lines
29#include <linux/slab.h>30#include <linux/slab.h>
30#include <linux/sysfs.h>31#include <linux/sysfs.h>
31 32
32#include "../common/cros_ec_sensors/cros_ec_sensors_core.h"
33
34/*33/*
35 * We only represent one entry for light or proximity. EC is merging different34 * We only represent one entry for light or proximity. EC is merging different
36 * light sensors to return the what the eye would see. For proximity, we35 * light sensors to return the what the eye would see. For proximity, we
drivers/iio/light/tsl2583.c+1−1
@@ -600,7 +600,7 @@ done: · 599 unmodified lines
600 600
601static IIO_CONST_ATTR(in_illuminance_calibscale_available, "1 8 16 111");601static IIO_CONST_ATTR(in_illuminance_calibscale_available, "1 8 16 111");
602static IIO_CONST_ATTR(in_illuminance_integration_time_available,602static IIO_CONST_ATTR(in_illuminance_integration_time_available,
603 "0.000050 0.000100 0.000150 0.000200 0.000250 0.000300 0.000350 0.000400 0.000450 0.000500 0.000550 0.000600 0.000650");603 "0.050 0.100 0.150 0.200 0.250 0.300 0.350 0.400 0.450 0.500 0.550 0.600 0.650");
604static IIO_DEVICE_ATTR_RW(in_illuminance_input_target, 0);604static IIO_DEVICE_ATTR_RW(in_illuminance_input_target, 0);
605static IIO_DEVICE_ATTR_WO(in_illuminance_calibrate, 0);605static IIO_DEVICE_ATTR_WO(in_illuminance_calibrate, 0);
606static IIO_DEVICE_ATTR_RW(in_illuminance_lux_table, 0);606static IIO_DEVICE_ATTR_RW(in_illuminance_lux_table, 0);
drivers/iio/light/tsl2772.c+1800−0
@@ -0,0 +1,1800 @@
1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * Device driver for monitoring ambient light intensity in (lux) and proximity
4 * detection (prox) within the TAOS TSL2571, TSL2671, TMD2671, TSL2771, TMD2771,
5 * TSL2572, TSL2672, TMD2672, TSL2772, and TMD2772 devices.
6 *
7 * Copyright (c) 2012, TAOS Corporation.
8 * Copyright (c) 2017-2018 Brian Masney <masneyb@onstation.org>
9 */
10
11#include <linux/delay.h>
12#include <linux/errno.h>
13#include <linux/i2c.h>
14#include <linux/interrupt.h>
15#include <linux/kernel.h>
16#include <linux/module.h>
17#include <linux/mutex.h>
18#include <linux/slab.h>
19#include <linux/iio/events.h>
20#include <linux/iio/iio.h>
21#include <linux/iio/sysfs.h>
22#include <linux/platform_data/tsl2772.h>
23
24/* Cal defs */
25#define PROX_STAT_CAL 0
26#define PROX_STAT_SAMP 1
27#define MAX_SAMPLES_CAL 200
28
29/* TSL2772 Device ID */
30#define TRITON_ID 0x00
31#define SWORDFISH_ID 0x30
32#define HALIBUT_ID 0x20
33
34/* Lux calculation constants */
35#define TSL2772_LUX_CALC_OVER_FLOW 65535
36
37/*
38 * TAOS Register definitions - Note: depending on device, some of these register
39 * are not used and the register address is benign.
40 */
41
42/* Register offsets */
43#define TSL2772_MAX_CONFIG_REG 16
44
45/* Device Registers and Masks */
46#define TSL2772_CNTRL 0x00
47#define TSL2772_ALS_TIME 0X01
48#define TSL2772_PRX_TIME 0x02
49#define TSL2772_WAIT_TIME 0x03
50#define TSL2772_ALS_MINTHRESHLO 0X04
51#define TSL2772_ALS_MINTHRESHHI 0X05
52#define TSL2772_ALS_MAXTHRESHLO 0X06
53#define TSL2772_ALS_MAXTHRESHHI 0X07
54#define TSL2772_PRX_MINTHRESHLO 0X08
55#define TSL2772_PRX_MINTHRESHHI 0X09
56#define TSL2772_PRX_MAXTHRESHLO 0X0A
57#define TSL2772_PRX_MAXTHRESHHI 0X0B
58#define TSL2772_PERSISTENCE 0x0C
59#define TSL2772_ALS_PRX_CONFIG 0x0D
60#define TSL2772_PRX_COUNT 0x0E
61#define TSL2772_GAIN 0x0F
62#define TSL2772_NOTUSED 0x10
63#define TSL2772_REVID 0x11
64#define TSL2772_CHIPID 0x12
65#define TSL2772_STATUS 0x13
66#define TSL2772_ALS_CHAN0LO 0x14
67#define TSL2772_ALS_CHAN0HI 0x15
68#define TSL2772_ALS_CHAN1LO 0x16
69#define TSL2772_ALS_CHAN1HI 0x17
70#define TSL2772_PRX_LO 0x18
71#define TSL2772_PRX_HI 0x19
72
73/* tsl2772 cmd reg masks */
74#define TSL2772_CMD_REG 0x80
75#define TSL2772_CMD_SPL_FN 0x60
76#define TSL2772_CMD_REPEAT_PROTO 0x00
77#define TSL2772_CMD_AUTOINC_PROTO 0x20
78
79#define TSL2772_CMD_PROX_INT_CLR 0X05
80#define TSL2772_CMD_ALS_INT_CLR 0x06
81#define TSL2772_CMD_PROXALS_INT_CLR 0X07
82
83/* tsl2772 cntrl reg masks */
84#define TSL2772_CNTL_ADC_ENBL 0x02
85#define TSL2772_CNTL_PWR_ON 0x01
86
87/* tsl2772 status reg masks */
88#define TSL2772_STA_ADC_VALID 0x01
89#define TSL2772_STA_PRX_VALID 0x02
90#define TSL2772_STA_ADC_PRX_VALID (TSL2772_STA_ADC_VALID | \
91 TSL2772_STA_PRX_VALID)
92#define TSL2772_STA_ALS_INTR 0x10
93#define TSL2772_STA_PRX_INTR 0x20
94
95/* tsl2772 cntrl reg masks */
96#define TSL2772_CNTL_REG_CLEAR 0x00
97#define TSL2772_CNTL_PROX_INT_ENBL 0X20
98#define TSL2772_CNTL_ALS_INT_ENBL 0X10
99#define TSL2772_CNTL_WAIT_TMR_ENBL 0X08
100#define TSL2772_CNTL_PROX_DET_ENBL 0X04
101#define TSL2772_CNTL_PWRON 0x01
102#define TSL2772_CNTL_ALSPON_ENBL 0x03
103#define TSL2772_CNTL_INTALSPON_ENBL 0x13
104#define TSL2772_CNTL_PROXPON_ENBL 0x0F
105#define TSL2772_CNTL_INTPROXPON_ENBL 0x2F
106
107#define TSL2772_ALS_GAIN_TRIM_MIN 250
108#define TSL2772_ALS_GAIN_TRIM_MAX 4000
109
110/* Device family members */
111enum {
112 tsl2571,
113 tsl2671,
114 tmd2671,
115 tsl2771,
116 tmd2771,
117 tsl2572,
118 tsl2672,
119 tmd2672,
120 tsl2772,
121 tmd2772
122};
123
124enum {
125 TSL2772_CHIP_UNKNOWN = 0,
126 TSL2772_CHIP_WORKING = 1,
127 TSL2772_CHIP_SUSPENDED = 2
128};
129
130/* Per-device data */
131struct tsl2772_als_info {
132 u16 als_ch0;
133 u16 als_ch1;
134 u16 lux;
135};
136
137struct tsl2772_chip_info {
138 int chan_table_elements;
139 struct iio_chan_spec channel_with_events[4];
140 struct iio_chan_spec channel_without_events[4];
141 const struct iio_info *info;
142};
143
144struct tsl2772_chip {
145 kernel_ulong_t id;
146 struct mutex prox_mutex;
147 struct mutex als_mutex;
148 struct i2c_client *client;
149 u16 prox_data;
150 struct tsl2772_als_info als_cur_info;
151 struct tsl2772_settings settings;
152 struct tsl2772_platform_data *pdata;
153 int als_gain_time_scale;
154 int als_saturation;
155 int tsl2772_chip_status;
156 u8 tsl2772_config[TSL2772_MAX_CONFIG_REG];
157 const struct tsl2772_chip_info *chip_info;
158 const struct iio_info *info;
159 s64 event_timestamp;
160 /*
161 * This structure is intentionally large to accommodate
162 * updates via sysfs.
163 * Sized to 9 = max 8 segments + 1 termination segment
164 */
165 struct tsl2772_lux tsl2772_device_lux[TSL2772_MAX_LUX_TABLE_SIZE];
166};
167
168/*
169 * Different devices require different coefficents, and these numbers were
170 * derived from the 'Lux Equation' section of the various device datasheets.
171 * All of these coefficients assume a Glass Attenuation (GA) factor of 1.
172 * The coefficients are multiplied by 1000 to avoid floating point operations.
173 * The two rows in each table correspond to the Lux1 and Lux2 equations from
174 * the datasheets.
175 */
176static const struct tsl2772_lux tsl2x71_lux_table[TSL2772_DEF_LUX_TABLE_SZ] = {
177 { 53000, 106000 },
178 { 31800, 53000 },
179 { 0, 0 },
180};
181
182static const struct tsl2772_lux tmd2x71_lux_table[TSL2772_DEF_LUX_TABLE_SZ] = {
183 { 24000, 48000 },
184 { 14400, 24000 },
185 { 0, 0 },
186};
187
188static const struct tsl2772_lux tsl2x72_lux_table[TSL2772_DEF_LUX_TABLE_SZ] = {
189 { 60000, 112200 },
190 { 37800, 60000 },
191 { 0, 0 },
192};
193
194static const struct tsl2772_lux tmd2x72_lux_table[TSL2772_DEF_LUX_TABLE_SZ] = {
195 { 20000, 35000 },
196 { 12600, 20000 },
197 { 0, 0 },
198};
199
200static const struct tsl2772_lux *tsl2772_default_lux_table_group[] = {
201 [tsl2571] = tsl2x71_lux_table,
202 [tsl2671] = tsl2x71_lux_table,
203 [tmd2671] = tmd2x71_lux_table,
204 [tsl2771] = tsl2x71_lux_table,
205 [tmd2771] = tmd2x71_lux_table,
206 [tsl2572] = tsl2x72_lux_table,
207 [tsl2672] = tsl2x72_lux_table,
208 [tmd2672] = tmd2x72_lux_table,
209 [tsl2772] = tsl2x72_lux_table,
210 [tmd2772] = tmd2x72_lux_table,
211};
212
213static const struct tsl2772_settings tsl2772_default_settings = {
214 .als_time = 255, /* 2.72 / 2.73 ms */
215 .als_gain = 0,
216 .prox_time = 255, /* 2.72 / 2.73 ms */
217 .prox_gain = 0,
218 .wait_time = 255,
219 .als_prox_config = 0,
220 .als_gain_trim = 1000,
221 .als_cal_target = 150,
222 .als_persistence = 1,
223 .als_interrupt_en = false,
224 .als_thresh_low = 200,
225 .als_thresh_high = 256,
226 .prox_persistence = 1,
227 .prox_interrupt_en = false,
228 .prox_thres_low = 0,
229 .prox_thres_high = 512,
230 .prox_max_samples_cal = 30,
231 .prox_pulse_count = 8,
232 .prox_diode = TSL2772_DIODE1,
233 .prox_power = TSL2772_100_mA
234};
235
236static const s16 tsl2772_als_gain[] = {
237 1,
238 8,
239 16,
240 120
241};
242
243static const s16 tsl2772_prox_gain[] = {
244 1,
245 2,
246 4,
247 8
248};
249
250static const int tsl2772_int_time_avail[][6] = {
251 [tsl2571] = { 0, 2720, 0, 2720, 0, 696000 },
252 [tsl2671] = { 0, 2720, 0, 2720, 0, 696000 },
253 [tmd2671] = { 0, 2720, 0, 2720, 0, 696000 },
254 [tsl2771] = { 0, 2720, 0, 2720, 0, 696000 },
255 [tmd2771] = { 0, 2720, 0, 2720, 0, 696000 },
256 [tsl2572] = { 0, 2730, 0, 2730, 0, 699000 },
257 [tsl2672] = { 0, 2730, 0, 2730, 0, 699000 },
258 [tmd2672] = { 0, 2730, 0, 2730, 0, 699000 },
259 [tsl2772] = { 0, 2730, 0, 2730, 0, 699000 },
260 [tmd2772] = { 0, 2730, 0, 2730, 0, 699000 },
261};
262
263static int tsl2772_int_calibscale_avail[] = { 1, 8, 16, 120 };
264
265static int tsl2772_prox_calibscale_avail[] = { 1, 2, 4, 8 };
266
267/* Channel variations */
268enum {
269 ALS,
270 PRX,
271 ALSPRX,
272 PRX2,
273 ALSPRX2,
274};
275
276static const u8 device_channel_config[] = {
277 [tsl2571] = ALS,
278 [tsl2671] = PRX,
279 [tmd2671] = PRX,
280 [tsl2771] = ALSPRX,
281 [tmd2771] = ALSPRX,
282 [tsl2572] = ALS,
283 [tsl2672] = PRX2,
284 [tmd2672] = PRX2,
285 [tsl2772] = ALSPRX2,
286 [tmd2772] = ALSPRX2
287};
288
289static int tsl2772_read_status(struct tsl2772_chip *chip)
290{
291 int ret;
292
293 ret = i2c_smbus_read_byte_data(chip->client,
294 TSL2772_CMD_REG | TSL2772_STATUS);
295 if (ret < 0)
296 dev_err(&chip->client->dev,
297 "%s: failed to read STATUS register: %d\n", __func__,
298 ret);
299
300 return ret;
301}
302
303static int tsl2772_write_control_reg(struct tsl2772_chip *chip, u8 data)
304{
305 int ret;
306
307 ret = i2c_smbus_write_byte_data(chip->client,
308 TSL2772_CMD_REG | TSL2772_CNTRL, data);
309 if (ret < 0) {
310 dev_err(&chip->client->dev,
311 "%s: failed to write to control register %x: %d\n",
312 __func__, data, ret);
313 }
314
315 return ret;
316}
317
318static int tsl2772_read_autoinc_regs(struct tsl2772_chip *chip, int lower_reg,
319 int upper_reg)
320{
321 u8 buf[2];
322 int ret;
323
324 ret = i2c_smbus_write_byte(chip->client,
325 TSL2772_CMD_REG | TSL2772_CMD_AUTOINC_PROTO |
326 lower_reg);
327 if (ret < 0) {
328 dev_err(&chip->client->dev,
329 "%s: failed to enable auto increment protocol: %d\n",
330 __func__, ret);
331 return ret;
332 }
333
334 ret = i2c_smbus_read_byte_data(chip->client,
335 TSL2772_CMD_REG | lower_reg);
336 if (ret < 0) {
337 dev_err(&chip->client->dev,
338 "%s: failed to read from register %x: %d\n", __func__,
339 lower_reg, ret);
340 return ret;
341 }
342 buf[0] = ret;
343
344 ret = i2c_smbus_read_byte_data(chip->client,
345 TSL2772_CMD_REG | upper_reg);
346 if (ret < 0) {
347 dev_err(&chip->client->dev,
348 "%s: failed to read from register %x: %d\n", __func__,
349 upper_reg, ret);
350 return ret;
351 }
352 buf[1] = ret;
353
354 ret = i2c_smbus_write_byte(chip->client,
355 TSL2772_CMD_REG | TSL2772_CMD_REPEAT_PROTO |
356 lower_reg);
357 if (ret < 0) {
358 dev_err(&chip->client->dev,
359 "%s: failed to enable repeated byte protocol: %d\n",
360 __func__, ret);
361 return ret;
362 }
363
364 return le16_to_cpup((const __le16 *)&buf[0]);
365}
366
367/**
368 * tsl2772_get_lux() - Reads and calculates current lux value.
369 * @indio_dev: pointer to IIO device
370 *
371 * The raw ch0 and ch1 values of the ambient light sensed in the last
372 * integration cycle are read from the device. The raw values are multiplied
373 * by a device-specific scale factor, and divided by the integration time and
374 * device gain. The code supports multiple lux equations through the lux table
375 * coefficients. A lux gain trim is applied to each lux equation, and then the
376 * maximum lux within the interval 0..65535 is selected.
377 */
378static int tsl2772_get_lux(struct iio_dev *indio_dev)
379{
380 struct tsl2772_chip *chip = iio_priv(indio_dev);
381 struct tsl2772_lux *p;
382 int max_lux, ret;
383 bool overflow;
384
385 mutex_lock(&chip->als_mutex);
386
387 if (chip->tsl2772_chip_status != TSL2772_CHIP_WORKING) {
388 dev_err(&chip->client->dev, "%s: device is not enabled\n",
389 __func__);
390 ret = -EBUSY;
391 goto out_unlock;
392 }
393
394 ret = tsl2772_read_status(chip);
395 if (ret < 0)
396 goto out_unlock;
397
398 if (!(ret & TSL2772_STA_ADC_VALID)) {
399 dev_err(&chip->client->dev,
400 "%s: data not valid yet\n", __func__);
401 ret = chip->als_cur_info.lux; /* return LAST VALUE */
402 goto out_unlock;
403 }
404
405 ret = tsl2772_read_autoinc_regs(chip, TSL2772_ALS_CHAN0LO,
406 TSL2772_ALS_CHAN0HI);
407 if (ret < 0)
408 goto out_unlock;
409 chip->als_cur_info.als_ch0 = ret;
410
411 ret = tsl2772_read_autoinc_regs(chip, TSL2772_ALS_CHAN1LO,
412 TSL2772_ALS_CHAN1HI);
413 if (ret < 0)
414 goto out_unlock;
415 chip->als_cur_info.als_ch1 = ret;
416
417 if (chip->als_cur_info.als_ch0 >= chip->als_saturation) {
418 max_lux = TSL2772_LUX_CALC_OVER_FLOW;
419 goto update_struct_with_max_lux;
420 }
421
422 if (!chip->als_cur_info.als_ch0) {
423 /* have no data, so return LAST VALUE */
424 ret = chip->als_cur_info.lux;
425 goto out_unlock;
426 }
427
428 max_lux = 0;
429 overflow = false;
430 for (p = (struct tsl2772_lux *)chip->tsl2772_device_lux; p->ch0 != 0;
431 p++) {
432 int lux;
433
434 lux = ((chip->als_cur_info.als_ch0 * p->ch0) -
435 (chip->als_cur_info.als_ch1 * p->ch1)) /
436 chip->als_gain_time_scale;
437
438 /*
439 * The als_gain_trim can have a value within the range 250..4000
440 * and is a multiplier for the lux. A trim of 1000 makes no
441 * changes to the lux, less than 1000 scales it down, and
442 * greater than 1000 scales it up.
443 */
444 lux = (lux * chip->settings.als_gain_trim) / 1000;
445
446 if (lux > TSL2772_LUX_CALC_OVER_FLOW) {
447 overflow = true;
448 continue;
449 }
450
451 max_lux = max(max_lux, lux);
452 }
453
454 if (overflow && max_lux == 0)
455 max_lux = TSL2772_LUX_CALC_OVER_FLOW;
456
457update_struct_with_max_lux:
458 chip->als_cur_info.lux = max_lux;
459 ret = max_lux;
460
461out_unlock:
462 mutex_unlock(&chip->als_mutex);
463
464 return ret;
465}
466
467/**
468 * tsl2772_get_prox() - Reads proximity data registers and updates
469 * chip->prox_data.
470 *
471 * @indio_dev: pointer to IIO device
472 */
473static int tsl2772_get_prox(struct iio_dev *indio_dev)
474{
475 struct tsl2772_chip *chip = iio_priv(indio_dev);
476 int ret;
477
478 mutex_lock(&chip->prox_mutex);
479
480 ret = tsl2772_read_status(chip);
481 if (ret < 0)
482 goto prox_poll_err;
483
484 switch (chip->id) {
485 case tsl2571:
486 case tsl2671:
487 case tmd2671:
488 case tsl2771:
489 case tmd2771:
490 if (!(ret & TSL2772_STA_ADC_VALID)) {
491 ret = -EINVAL;
492 goto prox_poll_err;
493 }
494 break;
495 case tsl2572:
496 case tsl2672:
497 case tmd2672:
498 case tsl2772:
499 case tmd2772:
500 if (!(ret & TSL2772_STA_PRX_VALID)) {
501 ret = -EINVAL;
502 goto prox_poll_err;
503 }
504 break;
505 }
506
507 ret = tsl2772_read_autoinc_regs(chip, TSL2772_PRX_LO, TSL2772_PRX_HI);
508 if (ret < 0)
509 goto prox_poll_err;
510 chip->prox_data = ret;
511
512prox_poll_err:
513 mutex_unlock(&chip->prox_mutex);
514
515 return ret;
516}
517
518/**
519 * tsl2772_defaults() - Populates the device nominal operating parameters
520 * with those provided by a 'platform' data struct or
521 * with prefined defaults.
522 *
523 * @chip: pointer to device structure.
524 */
525static void tsl2772_defaults(struct tsl2772_chip *chip)
526{
527 /* If Operational settings defined elsewhere.. */
528 if (chip->pdata && chip->pdata->platform_default_settings)
529 memcpy(&chip->settings, chip->pdata->platform_default_settings,
530 sizeof(tsl2772_default_settings));
531 else
532 memcpy(&chip->settings, &tsl2772_default_settings,
533 sizeof(tsl2772_default_settings));
534
535 /* Load up the proper lux table. */
536 if (chip->pdata && chip->pdata->platform_lux_table[0].ch0 != 0)
537 memcpy(chip->tsl2772_device_lux,
538 chip->pdata->platform_lux_table,
539 sizeof(chip->pdata->platform_lux_table));
540 else
541 memcpy(chip->tsl2772_device_lux,
542 tsl2772_default_lux_table_group[chip->id],
543 TSL2772_DEFAULT_TABLE_BYTES);
544}
545
546/**
547 * tsl2772_als_calibrate() - Obtain single reading and calculate
548 * the als_gain_trim.
549 *
550 * @indio_dev: pointer to IIO device
551 */
552static int tsl2772_als_calibrate(struct iio_dev *indio_dev)
553{
554 struct tsl2772_chip *chip = iio_priv(indio_dev);
555 int ret, lux_val;
556
557 ret = i2c_smbus_read_byte_data(chip->client,
558 TSL2772_CMD_REG | TSL2772_CNTRL);
559 if (ret < 0) {
560 dev_err(&chip->client->dev,
561 "%s: failed to read from the CNTRL register\n",
562 __func__);
563 return ret;
564 }
565
566 if ((ret & (TSL2772_CNTL_ADC_ENBL | TSL2772_CNTL_PWR_ON))
567 != (TSL2772_CNTL_ADC_ENBL | TSL2772_CNTL_PWR_ON)) {
568 dev_err(&chip->client->dev,
569 "%s: Device is not powered on and/or ADC is not enabled\n",
570 __func__);
571 return -EINVAL;
572 } else if ((ret & TSL2772_STA_ADC_VALID) != TSL2772_STA_ADC_VALID) {
573 dev_err(&chip->client->dev,
574 "%s: The two ADC channels have not completed an integration cycle\n",
575 __func__);
576 return -ENODATA;
577 }
578
579 lux_val = tsl2772_get_lux(indio_dev);
580 if (lux_val < 0) {
581 dev_err(&chip->client->dev,
582 "%s: failed to get lux\n", __func__);
583 return lux_val;
584 }
585
586 ret = (chip->settings.als_cal_target * chip->settings.als_gain_trim) /
587 lux_val;
588 if (ret < TSL2772_ALS_GAIN_TRIM_MIN || ret > TSL2772_ALS_GAIN_TRIM_MAX)
589 return -ERANGE;
590
591 chip->settings.als_gain_trim = ret;
592
593 return ret;
594}
595
596static int tsl2772_chip_on(struct iio_dev *indio_dev)
597{
598 struct tsl2772_chip *chip = iio_priv(indio_dev);
599 int ret, i, als_count, als_time_us;
600 u8 *dev_reg, reg_val;
601
602 /* Non calculated parameters */
603 chip->tsl2772_config[TSL2772_ALS_TIME] = chip->settings.als_time;
604 chip->tsl2772_config[TSL2772_PRX_TIME] = chip->settings.prox_time;
605 chip->tsl2772_config[TSL2772_WAIT_TIME] = chip->settings.wait_time;
606 chip->tsl2772_config[TSL2772_ALS_PRX_CONFIG] =
607 chip->settings.als_prox_config;
608
609 chip->tsl2772_config[TSL2772_ALS_MINTHRESHLO] =
610 (chip->settings.als_thresh_low) & 0xFF;
611 chip->tsl2772_config[TSL2772_ALS_MINTHRESHHI] =
612 (chip->settings.als_thresh_low >> 8) & 0xFF;
613 chip->tsl2772_config[TSL2772_ALS_MAXTHRESHLO] =
614 (chip->settings.als_thresh_high) & 0xFF;
615 chip->tsl2772_config[TSL2772_ALS_MAXTHRESHHI] =
616 (chip->settings.als_thresh_high >> 8) & 0xFF;
617 chip->tsl2772_config[TSL2772_PERSISTENCE] =
618 (chip->settings.prox_persistence & 0xFF) << 4 |
619 (chip->settings.als_persistence & 0xFF);
620
621 chip->tsl2772_config[TSL2772_PRX_COUNT] =
622 chip->settings.prox_pulse_count;
623 chip->tsl2772_config[TSL2772_PRX_MINTHRESHLO] =
624 (chip->settings.prox_thres_low) & 0xFF;
625 chip->tsl2772_config[TSL2772_PRX_MINTHRESHHI] =
626 (chip->settings.prox_thres_low >> 8) & 0xFF;
627 chip->tsl2772_config[TSL2772_PRX_MAXTHRESHLO] =
628 (chip->settings.prox_thres_high) & 0xFF;
629 chip->tsl2772_config[TSL2772_PRX_MAXTHRESHHI] =
630 (chip->settings.prox_thres_high >> 8) & 0xFF;
631
632 /* and make sure we're not already on */
633 if (chip->tsl2772_chip_status == TSL2772_CHIP_WORKING) {
634 /* if forcing a register update - turn off, then on */
635 dev_info(&chip->client->dev, "device is already enabled\n");
636 return -EINVAL;
637 }
638
639 /* Set the gain based on tsl2772_settings struct */
640 chip->tsl2772_config[TSL2772_GAIN] =
641 (chip->settings.als_gain & 0xFF) |
642 ((chip->settings.prox_gain & 0xFF) << 2) |
643 (chip->settings.prox_diode << 4) |
644 (chip->settings.prox_power << 6);
645
646 /* set chip time scaling and saturation */
647 als_count = 256 - chip->settings.als_time;
648 als_time_us = als_count * tsl2772_int_time_avail[chip->id][3];
649 chip->als_saturation = als_count * 768; /* 75% of full scale */
650 chip->als_gain_time_scale = als_time_us *
651 tsl2772_als_gain[chip->settings.als_gain];
652
653 /*
654 * TSL2772 Specific power-on / adc enable sequence
655 * Power on the device 1st.
656 */
657 ret = tsl2772_write_control_reg(chip, TSL2772_CNTL_PWR_ON);
658 if (ret < 0)
659 return ret;
660
661 /*
662 * Use the following shadow copy for our delay before enabling ADC.
663 * Write all the registers.
664 */
665 for (i = 0, dev_reg = chip->tsl2772_config;
666 i < TSL2772_MAX_CONFIG_REG; i++) {
667 int reg = TSL2772_CMD_REG + i;
668
669 ret = i2c_smbus_write_byte_data(chip->client, reg,
670 *dev_reg++);
671 if (ret < 0) {
672 dev_err(&chip->client->dev,
673 "%s: failed to write to register %x: %d\n",
674 __func__, reg, ret);
675 return ret;
676 }
677 }
678
679 /* Power-on settling time */
680 usleep_range(3000, 3500);
681
682 reg_val = TSL2772_CNTL_PWR_ON | TSL2772_CNTL_ADC_ENBL |
683 TSL2772_CNTL_PROX_DET_ENBL;
684 if (chip->settings.als_interrupt_en)
685 reg_val |= TSL2772_CNTL_ALS_INT_ENBL;
686 if (chip->settings.prox_interrupt_en)
687 reg_val |= TSL2772_CNTL_PROX_INT_ENBL;
688
689 ret = tsl2772_write_control_reg(chip, reg_val);
690 if (ret < 0)
691 return ret;
692
693 ret = i2c_smbus_write_byte(chip->client,
694 TSL2772_CMD_REG | TSL2772_CMD_SPL_FN |
695 TSL2772_CMD_PROXALS_INT_CLR);
696 if (ret < 0) {
697 dev_err(&chip->client->dev,
698 "%s: failed to clear interrupt status: %d\n",
699 __func__, ret);
700 return ret;
701 }
702
703 chip->tsl2772_chip_status = TSL2772_CHIP_WORKING;
704
705 return ret;
706}
707
708static int tsl2772_chip_off(struct iio_dev *indio_dev)
709{
710 struct tsl2772_chip *chip = iio_priv(indio_dev);
711
712 /* turn device off */
713 chip->tsl2772_chip_status = TSL2772_CHIP_SUSPENDED;
714 return tsl2772_write_control_reg(chip, 0x00);
715}
716
717/**
718 * tsl2772_invoke_change - power cycle the device to implement the user
719 * parameters
720 * @indio_dev: pointer to IIO device
721 *
722 * Obtain and lock both ALS and PROX resources, determine and save device state
723 * (On/Off), cycle device to implement updated parameter, put device back into
724 * proper state, and unlock resource.
725 */
726static int tsl2772_invoke_change(struct iio_dev *indio_dev)
727{
728 struct tsl2772_chip *chip = iio_priv(indio_dev);
729 int device_status = chip->tsl2772_chip_status;
730 int ret;
731
732 mutex_lock(&chip->als_mutex);
733 mutex_lock(&chip->prox_mutex);
734
735 if (device_status == TSL2772_CHIP_WORKING) {
736 ret = tsl2772_chip_off(indio_dev);
737 if (ret < 0)
738 goto unlock;
739 }
740
741 ret = tsl2772_chip_on(indio_dev);
742
743unlock:
744 mutex_unlock(&chip->prox_mutex);
745 mutex_unlock(&chip->als_mutex);
746
747 return ret;
748}
749
750static int tsl2772_prox_cal(struct iio_dev *indio_dev)
751{
752 struct tsl2772_chip *chip = iio_priv(indio_dev);
753 int prox_history[MAX_SAMPLES_CAL + 1];
754 int i, ret, mean, max, sample_sum;
755
756 if (chip->settings.prox_max_samples_cal < 1 ||
757 chip->settings.prox_max_samples_cal > MAX_SAMPLES_CAL)
758 return -EINVAL;
759
760 for (i = 0; i < chip->settings.prox_max_samples_cal; i++) {
761 usleep_range(15000, 17500);
762 ret = tsl2772_get_prox(indio_dev);
763 if (ret < 0)
764 return ret;
765
766 prox_history[i] = chip->prox_data;
767 }
768
769 sample_sum = 0;
770 max = INT_MIN;
771 for (i = 0; i < chip->settings.prox_max_samples_cal; i++) {
772 sample_sum += prox_history[i];
773 max = max(max, prox_history[i]);
774 }
775 mean = sample_sum / chip->settings.prox_max_samples_cal;
776
777 chip->settings.prox_thres_high = (max << 1) - mean;
778
779 return tsl2772_invoke_change(indio_dev);
780}
781
782static int tsl2772_read_avail(struct iio_dev *indio_dev,
783 struct iio_chan_spec const *chan,
784 const int **vals, int *type, int *length,
785 long mask)
786{
787 struct tsl2772_chip *chip = iio_priv(indio_dev);
788
789 switch (mask) {
790 case IIO_CHAN_INFO_CALIBSCALE:
791 if (chan->type == IIO_INTENSITY) {
792 *length = ARRAY_SIZE(tsl2772_int_calibscale_avail);
793 *vals = tsl2772_int_calibscale_avail;
794 } else {
795 *length = ARRAY_SIZE(tsl2772_prox_calibscale_avail);
796 *vals = tsl2772_prox_calibscale_avail;
797 }
798 *type = IIO_VAL_INT;
799 return IIO_AVAIL_LIST;
800 case IIO_CHAN_INFO_INT_TIME:
801 *length = ARRAY_SIZE(tsl2772_int_time_avail[chip->id]);
802 *vals = tsl2772_int_time_avail[chip->id];
803 *type = IIO_VAL_INT_PLUS_MICRO;
804 return IIO_AVAIL_RANGE;
805 }
806
807 return -EINVAL;
808}
809
810static ssize_t in_illuminance0_target_input_show(struct device *dev,
811 struct device_attribute *attr,
812 char *buf)
813{
814 struct tsl2772_chip *chip = iio_priv(dev_to_iio_dev(dev));
815
816 return snprintf(buf, PAGE_SIZE, "%d\n", chip->settings.als_cal_target);
817}
818
819static ssize_t in_illuminance0_target_input_store(struct device *dev,
820 struct device_attribute *attr,
821 const char *buf, size_t len)
822{
823 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
824 struct tsl2772_chip *chip = iio_priv(indio_dev);
825 u16 value;
826 int ret;
827
828 if (kstrtou16(buf, 0, &value))
829 return -EINVAL;
830
831 chip->settings.als_cal_target = value;
832 ret = tsl2772_invoke_change(indio_dev);
833 if (ret < 0)
834 return ret;
835
836 return len;
837}
838
839static ssize_t in_illuminance0_calibrate_store(struct device *dev,
840 struct device_attribute *attr,
841 const char *buf, size_t len)
842{
843 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
844 bool value;
845 int ret;
846
847 if (kstrtobool(buf, &value) || !value)
848 return -EINVAL;
849
850 ret = tsl2772_als_calibrate(indio_dev);
851 if (ret < 0)
852 return ret;
853
854 ret = tsl2772_invoke_change(indio_dev);
855 if (ret < 0)
856 return ret;
857
858 return len;
859}
860
861static ssize_t in_illuminance0_lux_table_show(struct device *dev,
862 struct device_attribute *attr,
863 char *buf)
864{
865 struct tsl2772_chip *chip = iio_priv(dev_to_iio_dev(dev));
866 int i = 0;
867 int offset = 0;
868
869 while (i < TSL2772_MAX_LUX_TABLE_SIZE) {
870 offset += snprintf(buf + offset, PAGE_SIZE, "%u,%u,",
871 chip->tsl2772_device_lux[i].ch0,
872 chip->tsl2772_device_lux[i].ch1);
873 if (chip->tsl2772_device_lux[i].ch0 == 0) {
874 /*
875 * We just printed the first "0" entry.
876 * Now get rid of the extra "," and break.
877 */
878 offset--;
879 break;
880 }
881 i++;
882 }
883
884 offset += snprintf(buf + offset, PAGE_SIZE, "\n");
885 return offset;
886}
887
888static ssize_t in_illuminance0_lux_table_store(struct device *dev,
889 struct device_attribute *attr,
890 const char *buf, size_t len)
891{
892 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
893 struct tsl2772_chip *chip = iio_priv(indio_dev);
894 int value[ARRAY_SIZE(chip->tsl2772_device_lux) * 2 + 1];
895 int n, ret;
896
897 get_options(buf, ARRAY_SIZE(value), value);
898
899 /*
900 * We now have an array of ints starting at value[1], and
901 * enumerated by value[0].
902 * We expect each group of two ints to be one table entry,
903 * and the last table entry is all 0.
904 */
905 n = value[0];
906 if ((n % 2) || n < 4 ||
907 n > ((ARRAY_SIZE(chip->tsl2772_device_lux) - 1) * 2))
908 return -EINVAL;
909
910 if ((value[(n - 1)] | value[n]) != 0)
911 return -EINVAL;
912
913 if (chip->tsl2772_chip_status == TSL2772_CHIP_WORKING) {
914 ret = tsl2772_chip_off(indio_dev);
915 if (ret < 0)
916 return ret;
917 }
918
919 /* Zero out the table */
920 memset(chip->tsl2772_device_lux, 0, sizeof(chip->tsl2772_device_lux));
921 memcpy(chip->tsl2772_device_lux, &value[1], (value[0] * 4));
922
923 ret = tsl2772_invoke_change(indio_dev);
924 if (ret < 0)
925 return ret;
926
927 return len;
928}
929
930static ssize_t in_proximity0_calibrate_store(struct device *dev,
931 struct device_attribute *attr,
932 const char *buf, size_t len)
933{
934 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
935 bool value;
936 int ret;
937
938 if (kstrtobool(buf, &value) || !value)
939 return -EINVAL;
940
941 ret = tsl2772_prox_cal(indio_dev);
942 if (ret < 0)
943 return ret;
944
945 ret = tsl2772_invoke_change(indio_dev);
946 if (ret < 0)
947 return ret;
948
949 return len;
950}
951
952static int tsl2772_read_interrupt_config(struct iio_dev *indio_dev,
953 const struct iio_chan_spec *chan,
954 enum iio_event_type type,
955 enum iio_event_direction dir)
956{
957 struct tsl2772_chip *chip = iio_priv(indio_dev);
958
959 if (chan->type == IIO_INTENSITY)
960 return chip->settings.als_interrupt_en;
961 else
962 return chip->settings.prox_interrupt_en;
963}
964
965static int tsl2772_write_interrupt_config(struct iio_dev *indio_dev,
966 const struct iio_chan_spec *chan,
967 enum iio_event_type type,
968 enum iio_event_direction dir,
969 int val)
970{
971 struct tsl2772_chip *chip = iio_priv(indio_dev);
972
973 if (chan->type == IIO_INTENSITY)
974 chip->settings.als_interrupt_en = val ? true : false;
975 else
976 chip->settings.prox_interrupt_en = val ? true : false;
977
978 return tsl2772_invoke_change(indio_dev);
979}
980
981static int tsl2772_write_event_value(struct iio_dev *indio_dev,
982 const struct iio_chan_spec *chan,
983 enum iio_event_type type,
984 enum iio_event_direction dir,
985 enum iio_event_info info,
986 int val, int val2)
987{
988 struct tsl2772_chip *chip = iio_priv(indio_dev);
989 int ret = -EINVAL, count, persistence;
990 u8 time;
991
992 switch (info) {
993 case IIO_EV_INFO_VALUE:
994 if (chan->type == IIO_INTENSITY) {
995 switch (dir) {
996 case IIO_EV_DIR_RISING:
997 chip->settings.als_thresh_high = val;
998 ret = 0;
999 break;
1000 case IIO_EV_DIR_FALLING:
1001 chip->settings.als_thresh_low = val;
1002 ret = 0;
1003 break;
1004 default:
1005 break;
1006 }
1007 } else {
1008 switch (dir) {
1009 case IIO_EV_DIR_RISING:
1010 chip->settings.prox_thres_high = val;
1011 ret = 0;
1012 break;
1013 case IIO_EV_DIR_FALLING:
1014 chip->settings.prox_thres_low = val;
1015 ret = 0;
1016 break;
1017 default:
1018 break;
1019 }
1020 }
1021 break;
1022 case IIO_EV_INFO_PERIOD:
1023 if (chan->type == IIO_INTENSITY)
1024 time = chip->settings.als_time;
1025 else
1026 time = chip->settings.prox_time;
1027
1028 count = 256 - time;
1029 persistence = ((val * 1000000) + val2) /
1030 (count * tsl2772_int_time_avail[chip->id][3]);
1031
1032 if (chan->type == IIO_INTENSITY) {
1033 /* ALS filter values are 1, 2, 3, 5, 10, 15, ..., 60 */
1034 if (persistence > 3)
1035 persistence = (persistence / 5) + 3;
1036
1037 chip->settings.als_persistence = persistence;
1038 } else {
1039 chip->settings.prox_persistence = persistence;
1040 }
1041
1042 ret = 0;
1043 break;
1044 default:
1045 break;
1046 }
1047
1048 if (ret < 0)
1049 return ret;
1050
1051 return tsl2772_invoke_change(indio_dev);
1052}
1053
1054static int tsl2772_read_event_value(struct iio_dev *indio_dev,
1055 const struct iio_chan_spec *chan,
1056 enum iio_event_type type,
1057 enum iio_event_direction dir,
1058 enum iio_event_info info,
1059 int *val, int *val2)
1060{
1061 struct tsl2772_chip *chip = iio_priv(indio_dev);
1062 int filter_delay, persistence;
1063 u8 time;
1064
1065 switch (info) {
1066 case IIO_EV_INFO_VALUE:
1067 if (chan->type == IIO_INTENSITY) {
1068 switch (dir) {
1069 case IIO_EV_DIR_RISING:
1070 *val = chip->settings.als_thresh_high;
1071 return IIO_VAL_INT;
1072 case IIO_EV_DIR_FALLING:
1073 *val = chip->settings.als_thresh_low;
1074 return IIO_VAL_INT;
1075 default:
1076 return -EINVAL;
1077 }
1078 } else {
1079 switch (dir) {
1080 case IIO_EV_DIR_RISING:
1081 *val = chip->settings.prox_thres_high;
1082 return IIO_VAL_INT;
1083 case IIO_EV_DIR_FALLING:
1084 *val = chip->settings.prox_thres_low;
1085 return IIO_VAL_INT;
1086 default:
1087 return -EINVAL;
1088 }
1089 }
1090 break;
1091 case IIO_EV_INFO_PERIOD:
1092 if (chan->type == IIO_INTENSITY) {
1093 time = chip->settings.als_time;
1094 persistence = chip->settings.als_persistence;
1095
1096 /* ALS filter values are 1, 2, 3, 5, 10, 15, ..., 60 */
1097 if (persistence > 3)
1098 persistence = (persistence - 3) * 5;
1099 } else {
1100 time = chip->settings.prox_time;
1101 persistence = chip->settings.prox_persistence;
1102 }
1103
1104 filter_delay = persistence * (256 - time) *
1105 tsl2772_int_time_avail[chip->id][3];
1106
1107 *val = filter_delay / 1000000;
1108 *val2 = filter_delay % 1000000;
1109 return IIO_VAL_INT_PLUS_MICRO;
1110 default:
1111 return -EINVAL;
1112 }
1113}
1114
1115static int tsl2772_read_raw(struct iio_dev *indio_dev,
1116 struct iio_chan_spec const *chan,
1117 int *val,
1118 int *val2,
1119 long mask)
1120{
1121 struct tsl2772_chip *chip = iio_priv(indio_dev);
1122
1123 switch (mask) {
1124 case IIO_CHAN_INFO_PROCESSED:
1125 switch (chan->type) {
1126 case IIO_LIGHT:
1127 tsl2772_get_lux(indio_dev);
1128 *val = chip->als_cur_info.lux;
1129 return IIO_VAL_INT;
1130 default:
1131 return -EINVAL;
1132 }
1133 case IIO_CHAN_INFO_RAW:
1134 switch (chan->type) {
1135 case IIO_INTENSITY:
1136 tsl2772_get_lux(indio_dev);
1137 if (chan->channel == 0)
1138 *val = chip->als_cur_info.als_ch0;
1139 else
1140 *val = chip->als_cur_info.als_ch1;
1141 return IIO_VAL_INT;
1142 case IIO_PROXIMITY:
1143 tsl2772_get_prox(indio_dev);
1144 *val = chip->prox_data;
1145 return IIO_VAL_INT;
1146 default:
1147 return -EINVAL;
1148 }
1149 break;
1150 case IIO_CHAN_INFO_CALIBSCALE:
1151 if (chan->type == IIO_LIGHT)
1152 *val = tsl2772_als_gain[chip->settings.als_gain];
1153 else
1154 *val = tsl2772_prox_gain[chip->settings.prox_gain];
1155 return IIO_VAL_INT;
1156 case IIO_CHAN_INFO_CALIBBIAS:
1157 *val = chip->settings.als_gain_trim;
1158 return IIO_VAL_INT;
1159 case IIO_CHAN_INFO_INT_TIME:
1160 *val = 0;
1161 *val2 = (256 - chip->settings.als_time) *
1162 tsl2772_int_time_avail[chip->id][3];
1163 return IIO_VAL_INT_PLUS_MICRO;
1164 default:
1165 return -EINVAL;
1166 }
1167}
1168
1169static int tsl2772_write_raw(struct iio_dev *indio_dev,
1170 struct iio_chan_spec const *chan,
1171 int val,
1172 int val2,
1173 long mask)
1174{
1175 struct tsl2772_chip *chip = iio_priv(indio_dev);
1176
1177 switch (mask) {
1178 case IIO_CHAN_INFO_CALIBSCALE:
1179 if (chan->type == IIO_INTENSITY) {
1180 switch (val) {
1181 case 1:
1182 chip->settings.als_gain = 0;
1183 break;
1184 case 8:
1185 chip->settings.als_gain = 1;
1186 break;
1187 case 16:
1188 chip->settings.als_gain = 2;
1189 break;
1190 case 120:
1191 chip->settings.als_gain = 3;
1192 break;
1193 default:
1194 return -EINVAL;
1195 }
1196 } else {
1197 switch (val) {
1198 case 1:
1199 chip->settings.prox_gain = 0;
1200 break;
1201 case 2:
1202 chip->settings.prox_gain = 1;
1203 break;
1204 case 4:
1205 chip->settings.prox_gain = 2;
1206 break;
1207 case 8:
1208 chip->settings.prox_gain = 3;
1209 break;
1210 default:
1211 return -EINVAL;
1212 }
1213 }
1214 break;
1215 case IIO_CHAN_INFO_CALIBBIAS:
1216 if (val < TSL2772_ALS_GAIN_TRIM_MIN ||
1217 val > TSL2772_ALS_GAIN_TRIM_MAX)
1218 return -EINVAL;
1219
1220 chip->settings.als_gain_trim = val;
1221 break;
1222 case IIO_CHAN_INFO_INT_TIME:
1223 if (val != 0 || val2 < tsl2772_int_time_avail[chip->id][1] ||
1224 val2 > tsl2772_int_time_avail[chip->id][5])
1225 return -EINVAL;
1226
1227 chip->settings.als_time = 256 -
1228 (val2 / tsl2772_int_time_avail[chip->id][3]);
1229 break;
1230 default:
1231 return -EINVAL;
1232 }
1233
1234 return tsl2772_invoke_change(indio_dev);
1235}
1236
1237static DEVICE_ATTR_RW(in_illuminance0_target_input);
1238
1239static DEVICE_ATTR_WO(in_illuminance0_calibrate);
1240
1241static DEVICE_ATTR_WO(in_proximity0_calibrate);
1242
1243static DEVICE_ATTR_RW(in_illuminance0_lux_table);
1244
1245/* Use the default register values to identify the Taos device */
1246static int tsl2772_device_id_verif(int id, int target)
1247{
1248 switch (target) {
1249 case tsl2571:
1250 case tsl2671:
1251 case tsl2771:
1252 return (id & 0xf0) == TRITON_ID;
1253 case tmd2671:
1254 case tmd2771:
1255 return (id & 0xf0) == HALIBUT_ID;
1256 case tsl2572:
1257 case tsl2672:
1258 case tmd2672:
1259 case tsl2772:
1260 case tmd2772:
1261 return (id & 0xf0) == SWORDFISH_ID;
1262 }
1263
1264 return -EINVAL;
1265}
1266
1267static irqreturn_t tsl2772_event_handler(int irq, void *private)
1268{
1269 struct iio_dev *indio_dev = private;
1270 struct tsl2772_chip *chip = iio_priv(indio_dev);
1271 s64 timestamp = iio_get_time_ns(indio_dev);
1272 int ret;
1273
1274 ret = tsl2772_read_status(chip);
1275 if (ret < 0)
1276 return IRQ_HANDLED;
1277
1278 /* What type of interrupt do we need to process */
1279 if (ret & TSL2772_STA_PRX_INTR) {
1280 iio_push_event(indio_dev,
1281 IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY,
1282 0,
1283 IIO_EV_TYPE_THRESH,
1284 IIO_EV_DIR_EITHER),
1285 timestamp);
1286 }
1287
1288 if (ret & TSL2772_STA_ALS_INTR) {
1289 iio_push_event(indio_dev,
1290 IIO_UNMOD_EVENT_CODE(IIO_LIGHT,
1291 0,
1292 IIO_EV_TYPE_THRESH,
1293 IIO_EV_DIR_EITHER),
1294 timestamp);
1295 }
1296
1297 ret = i2c_smbus_write_byte(chip->client,
1298 TSL2772_CMD_REG | TSL2772_CMD_SPL_FN |
1299 TSL2772_CMD_PROXALS_INT_CLR);
1300 if (ret < 0)
1301 dev_err(&chip->client->dev,
1302 "%s: failed to clear interrupt status: %d\n",
1303 __func__, ret);
1304
1305 return IRQ_HANDLED;
1306}
1307
1308static struct attribute *tsl2772_ALS_device_attrs[] = {
1309 &dev_attr_in_illuminance0_target_input.attr,
1310 &dev_attr_in_illuminance0_calibrate.attr,
1311 &dev_attr_in_illuminance0_lux_table.attr,
1312 NULL
1313};
1314
1315static struct attribute *tsl2772_PRX_device_attrs[] = {
1316 &dev_attr_in_proximity0_calibrate.attr,
1317 NULL
1318};
1319
1320static struct attribute *tsl2772_ALSPRX_device_attrs[] = {
1321 &dev_attr_in_illuminance0_target_input.attr,
1322 &dev_attr_in_illuminance0_calibrate.attr,
1323 &dev_attr_in_illuminance0_lux_table.attr,
1324 NULL
1325};
1326
1327static struct attribute *tsl2772_PRX2_device_attrs[] = {
1328 &dev_attr_in_proximity0_calibrate.attr,
1329 NULL
1330};
1331
1332static struct attribute *tsl2772_ALSPRX2_device_attrs[] = {
1333 &dev_attr_in_illuminance0_target_input.attr,
1334 &dev_attr_in_illuminance0_calibrate.attr,
1335 &dev_attr_in_illuminance0_lux_table.attr,
1336 &dev_attr_in_proximity0_calibrate.attr,
1337 NULL
1338};
1339
1340static const struct attribute_group tsl2772_device_attr_group_tbl[] = {
1341 [ALS] = {
1342 .attrs = tsl2772_ALS_device_attrs,
1343 },
1344 [PRX] = {
1345 .attrs = tsl2772_PRX_device_attrs,
1346 },
1347 [ALSPRX] = {
1348 .attrs = tsl2772_ALSPRX_device_attrs,
1349 },
1350 [PRX2] = {
1351 .attrs = tsl2772_PRX2_device_attrs,
1352 },
1353 [ALSPRX2] = {
1354 .attrs = tsl2772_ALSPRX2_device_attrs,
1355 },
1356};
1357
1358#define TSL2772_DEVICE_INFO(type)[type] = \
1359 { \
1360 .attrs = &tsl2772_device_attr_group_tbl[type], \
1361 .read_raw = &tsl2772_read_raw, \
1362 .read_avail = &tsl2772_read_avail, \
1363 .write_raw = &tsl2772_write_raw, \
1364 .read_event_value = &tsl2772_read_event_value, \
1365 .write_event_value = &tsl2772_write_event_value, \
1366 .read_event_config = &tsl2772_read_interrupt_config, \
1367 .write_event_config = &tsl2772_write_interrupt_config, \
1368 }
1369
1370static const struct iio_info tsl2772_device_info[] = {
1371 TSL2772_DEVICE_INFO(ALS),
1372 TSL2772_DEVICE_INFO(PRX),
1373 TSL2772_DEVICE_INFO(ALSPRX),
1374 TSL2772_DEVICE_INFO(PRX2),
1375 TSL2772_DEVICE_INFO(ALSPRX2),
1376};
1377
1378static const struct iio_event_spec tsl2772_events[] = {
1379 {
1380 .type = IIO_EV_TYPE_THRESH,
1381 .dir = IIO_EV_DIR_RISING,
1382 .mask_separate = BIT(IIO_EV_INFO_VALUE),
1383 }, {
1384 .type = IIO_EV_TYPE_THRESH,
1385 .dir = IIO_EV_DIR_FALLING,
1386 .mask_separate = BIT(IIO_EV_INFO_VALUE),
1387 }, {
1388 .type = IIO_EV_TYPE_THRESH,
1389 .dir = IIO_EV_DIR_EITHER,
1390 .mask_separate = BIT(IIO_EV_INFO_PERIOD) |
1391 BIT(IIO_EV_INFO_ENABLE),
1392 },
1393};
1394
1395static const struct tsl2772_chip_info tsl2772_chip_info_tbl[] = {
1396 [ALS] = {
1397 .channel_with_events = {
1398 {
1399 .type = IIO_LIGHT,
1400 .indexed = 1,
1401 .channel = 0,
1402 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1403 }, {
1404 .type = IIO_INTENSITY,
1405 .indexed = 1,
1406 .channel = 0,
1407 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1408 BIT(IIO_CHAN_INFO_INT_TIME) |
1409 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1410 BIT(IIO_CHAN_INFO_CALIBBIAS),
1411 .info_mask_separate_available =
1412 BIT(IIO_CHAN_INFO_INT_TIME) |
1413 BIT(IIO_CHAN_INFO_CALIBSCALE),
1414 .event_spec = tsl2772_events,
1415 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1416 }, {
1417 .type = IIO_INTENSITY,
1418 .indexed = 1,
1419 .channel = 1,
1420 },
1421 },
1422 .channel_without_events = {
1423 {
1424 .type = IIO_LIGHT,
1425 .indexed = 1,
1426 .channel = 0,
1427 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1428 }, {
1429 .type = IIO_INTENSITY,
1430 .indexed = 1,
1431 .channel = 0,
1432 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1433 BIT(IIO_CHAN_INFO_INT_TIME) |
1434 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1435 BIT(IIO_CHAN_INFO_CALIBBIAS),
1436 .info_mask_separate_available =
1437 BIT(IIO_CHAN_INFO_INT_TIME) |
1438 BIT(IIO_CHAN_INFO_CALIBSCALE),
1439 }, {
1440 .type = IIO_INTENSITY,
1441 .indexed = 1,
1442 .channel = 1,
1443 },
1444 },
1445 .chan_table_elements = 3,
1446 .info = &tsl2772_device_info[ALS],
1447 },
1448 [PRX] = {
1449 .channel_with_events = {
1450 {
1451 .type = IIO_PROXIMITY,
1452 .indexed = 1,
1453 .channel = 0,
1454 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1455 .event_spec = tsl2772_events,
1456 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1457 },
1458 },
1459 .channel_without_events = {
1460 {
1461 .type = IIO_PROXIMITY,
1462 .indexed = 1,
1463 .channel = 0,
1464 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1465 },
1466 },
1467 .chan_table_elements = 1,
1468 .info = &tsl2772_device_info[PRX],
1469 },
1470 [ALSPRX] = {
1471 .channel_with_events = {
1472 {
1473 .type = IIO_LIGHT,
1474 .indexed = 1,
1475 .channel = 0,
1476 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1477 }, {
1478 .type = IIO_INTENSITY,
1479 .indexed = 1,
1480 .channel = 0,
1481 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1482 BIT(IIO_CHAN_INFO_INT_TIME) |
1483 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1484 BIT(IIO_CHAN_INFO_CALIBBIAS),
1485 .info_mask_separate_available =
1486 BIT(IIO_CHAN_INFO_INT_TIME) |
1487 BIT(IIO_CHAN_INFO_CALIBSCALE),
1488 .event_spec = tsl2772_events,
1489 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1490 }, {
1491 .type = IIO_INTENSITY,
1492 .indexed = 1,
1493 .channel = 1,
1494 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1495 }, {
1496 .type = IIO_PROXIMITY,
1497 .indexed = 1,
1498 .channel = 0,
1499 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1500 .event_spec = tsl2772_events,
1501 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1502 },
1503 },
1504 .channel_without_events = {
1505 {
1506 .type = IIO_LIGHT,
1507 .indexed = 1,
1508 .channel = 0,
1509 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1510 }, {
1511 .type = IIO_INTENSITY,
1512 .indexed = 1,
1513 .channel = 0,
1514 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1515 BIT(IIO_CHAN_INFO_INT_TIME) |
1516 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1517 BIT(IIO_CHAN_INFO_CALIBBIAS),
1518 .info_mask_separate_available =
1519 BIT(IIO_CHAN_INFO_INT_TIME) |
1520 BIT(IIO_CHAN_INFO_CALIBSCALE),
1521 }, {
1522 .type = IIO_INTENSITY,
1523 .indexed = 1,
1524 .channel = 1,
1525 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1526 }, {
1527 .type = IIO_PROXIMITY,
1528 .indexed = 1,
1529 .channel = 0,
1530 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1531 },
1532 },
1533 .chan_table_elements = 4,
1534 .info = &tsl2772_device_info[ALSPRX],
1535 },
1536 [PRX2] = {
1537 .channel_with_events = {
1538 {
1539 .type = IIO_PROXIMITY,
1540 .indexed = 1,
1541 .channel = 0,
1542 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1543 BIT(IIO_CHAN_INFO_CALIBSCALE),
1544 .info_mask_separate_available =
1545 BIT(IIO_CHAN_INFO_CALIBSCALE),
1546 .event_spec = tsl2772_events,
1547 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1548 },
1549 },
1550 .channel_without_events = {
1551 {
1552 .type = IIO_PROXIMITY,
1553 .indexed = 1,
1554 .channel = 0,
1555 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1556 BIT(IIO_CHAN_INFO_CALIBSCALE),
1557 .info_mask_separate_available =
1558 BIT(IIO_CHAN_INFO_CALIBSCALE),
1559 },
1560 },
1561 .chan_table_elements = 1,
1562 .info = &tsl2772_device_info[PRX2],
1563 },
1564 [ALSPRX2] = {
1565 .channel_with_events = {
1566 {
1567 .type = IIO_LIGHT,
1568 .indexed = 1,
1569 .channel = 0,
1570 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1571 }, {
1572 .type = IIO_INTENSITY,
1573 .indexed = 1,
1574 .channel = 0,
1575 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1576 BIT(IIO_CHAN_INFO_INT_TIME) |
1577 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1578 BIT(IIO_CHAN_INFO_CALIBBIAS),
1579 .info_mask_separate_available =
1580 BIT(IIO_CHAN_INFO_INT_TIME) |
1581 BIT(IIO_CHAN_INFO_CALIBSCALE),
1582 .event_spec = tsl2772_events,
1583 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1584 }, {
1585 .type = IIO_INTENSITY,
1586 .indexed = 1,
1587 .channel = 1,
1588 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1589 }, {
1590 .type = IIO_PROXIMITY,
1591 .indexed = 1,
1592 .channel = 0,
1593 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1594 BIT(IIO_CHAN_INFO_CALIBSCALE),
1595 .info_mask_separate_available =
1596 BIT(IIO_CHAN_INFO_CALIBSCALE),
1597 .event_spec = tsl2772_events,
1598 .num_event_specs = ARRAY_SIZE(tsl2772_events),
1599 },
1600 },
1601 .channel_without_events = {
1602 {
1603 .type = IIO_LIGHT,
1604 .indexed = 1,
1605 .channel = 0,
1606 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED),
1607 }, {
1608 .type = IIO_INTENSITY,
1609 .indexed = 1,
1610 .channel = 0,
1611 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1612 BIT(IIO_CHAN_INFO_INT_TIME) |
1613 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1614 BIT(IIO_CHAN_INFO_CALIBBIAS),
1615 .info_mask_separate_available =
1616 BIT(IIO_CHAN_INFO_INT_TIME) |
1617 BIT(IIO_CHAN_INFO_CALIBSCALE),
1618 }, {
1619 .type = IIO_INTENSITY,
1620 .indexed = 1,
1621 .channel = 1,
1622 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1623 }, {
1624 .type = IIO_PROXIMITY,
1625 .indexed = 1,
1626 .channel = 0,
1627 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1628 BIT(IIO_CHAN_INFO_CALIBSCALE),
1629 .info_mask_separate_available =
1630 BIT(IIO_CHAN_INFO_CALIBSCALE),
1631 },
1632 },
1633 .chan_table_elements = 4,
1634 .info = &tsl2772_device_info[ALSPRX2],
1635 },
1636};
1637
1638static int tsl2772_probe(struct i2c_client *clientp,
1639 const struct i2c_device_id *id)
1640{
1641 struct iio_dev *indio_dev;
1642 struct tsl2772_chip *chip;
1643 int ret;
1644
1645 indio_dev = devm_iio_device_alloc(&clientp->dev, sizeof(*chip));
1646 if (!indio_dev)
1647 return -ENOMEM;
1648
1649 chip = iio_priv(indio_dev);
1650 chip->client = clientp;
1651 i2c_set_clientdata(clientp, indio_dev);
1652
1653 ret = i2c_smbus_read_byte_data(chip->client,
1654 TSL2772_CMD_REG | TSL2772_CHIPID);
1655 if (ret < 0)
1656 return ret;
1657
1658 if (tsl2772_device_id_verif(ret, id->driver_data) <= 0) {
1659 dev_info(&chip->client->dev,
1660 "%s: i2c device found does not match expected id\n",
1661 __func__);
1662 return -EINVAL;
1663 }
1664
1665 ret = i2c_smbus_write_byte(clientp, TSL2772_CMD_REG | TSL2772_CNTRL);
1666 if (ret < 0) {
1667 dev_err(&clientp->dev,
1668 "%s: Failed to write to CMD register: %d\n",
1669 __func__, ret);
1670 return ret;
1671 }
1672
1673 mutex_init(&chip->als_mutex);
1674 mutex_init(&chip->prox_mutex);
1675
1676 chip->tsl2772_chip_status = TSL2772_CHIP_UNKNOWN;
1677 chip->pdata = dev_get_platdata(&clientp->dev);
1678 chip->id = id->driver_data;
1679 chip->chip_info =
1680 &tsl2772_chip_info_tbl[device_channel_config[id->driver_data]];
1681
1682 indio_dev->info = chip->chip_info->info;
1683 indio_dev->dev.parent = &clientp->dev;
1684 indio_dev->modes = INDIO_DIRECT_MODE;
1685 indio_dev->name = chip->client->name;
1686 indio_dev->num_channels = chip->chip_info->chan_table_elements;
1687
1688 if (clientp->irq) {
1689 indio_dev->channels = chip->chip_info->channel_with_events;
1690
1691 ret = devm_request_threaded_irq(&clientp->dev, clientp->irq,
1692 NULL,
1693 &tsl2772_event_handler,
1694 IRQF_TRIGGER_FALLING |
1695 IRQF_ONESHOT,
1696 "TSL2772_event",
1697 indio_dev);
1698 if (ret) {
1699 dev_err(&clientp->dev,
1700 "%s: irq request failed\n", __func__);
1701 return ret;
1702 }
1703 } else {
1704 indio_dev->channels = chip->chip_info->channel_without_events;
1705 }
1706
1707 tsl2772_defaults(chip);
1708 ret = tsl2772_chip_on(indio_dev);
1709 if (ret < 0)
1710 return ret;
1711
1712 ret = iio_device_register(indio_dev);
1713 if (ret) {
1714 tsl2772_chip_off(indio_dev);
1715 dev_err(&clientp->dev,
1716 "%s: iio registration failed\n", __func__);
1717 return ret;
1718 }
1719
1720 return 0;
1721}
1722
1723static int tsl2772_suspend(struct device *dev)
1724{
1725 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1726
1727 return tsl2772_chip_off(indio_dev);
1728}
1729
1730static int tsl2772_resume(struct device *dev)
1731{
1732 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1733
1734 return tsl2772_chip_on(indio_dev);
1735}
1736
1737static int tsl2772_remove(struct i2c_client *client)
1738{
1739 struct iio_dev *indio_dev = i2c_get_clientdata(client);
1740
1741 tsl2772_chip_off(indio_dev);
1742
1743 iio_device_unregister(indio_dev);
1744
1745 return 0;
1746}
1747
1748static const struct i2c_device_id tsl2772_idtable[] = {
1749 { "tsl2571", tsl2571 },
1750 { "tsl2671", tsl2671 },
1751 { "tmd2671", tmd2671 },
1752 { "tsl2771", tsl2771 },
1753 { "tmd2771", tmd2771 },
1754 { "tsl2572", tsl2572 },
1755 { "tsl2672", tsl2672 },
1756 { "tmd2672", tmd2672 },
1757 { "tsl2772", tsl2772 },
1758 { "tmd2772", tmd2772 },
1759 {}
1760};
1761
1762MODULE_DEVICE_TABLE(i2c, tsl2772_idtable);
1763
1764static const struct of_device_id tsl2772_of_match[] = {
1765 { .compatible = "amstaos,tsl2571" },
1766 { .compatible = "amstaos,tsl2671" },
1767 { .compatible = "amstaos,tmd2671" },
1768 { .compatible = "amstaos,tsl2771" },
1769 { .compatible = "amstaos,tmd2771" },
1770 { .compatible = "amstaos,tsl2572" },
1771 { .compatible = "amstaos,tsl2672" },
1772 { .compatible = "amstaos,tmd2672" },
1773 { .compatible = "amstaos,tsl2772" },
1774 { .compatible = "amstaos,tmd2772" },
1775 {}
1776};
1777MODULE_DEVICE_TABLE(of, tsl2772_of_match);
1778
1779static const struct dev_pm_ops tsl2772_pm_ops = {
1780 .suspend = tsl2772_suspend,
1781 .resume = tsl2772_resume,
1782};
1783
1784static struct i2c_driver tsl2772_driver = {
1785 .driver = {
1786 .name = "tsl2772",
1787 .of_match_table = tsl2772_of_match,
1788 .pm = &tsl2772_pm_ops,
1789 },
1790 .id_table = tsl2772_idtable,
1791 .probe = tsl2772_probe,
1792 .remove = tsl2772_remove,
1793};
1794
1795module_i2c_driver(tsl2772_driver);
1796
1797MODULE_AUTHOR("J. August Brenner <Jon.Brenner@ams.com>");
1798MODULE_AUTHOR("Brian Masney <masneyb@onstation.org>");
1799MODULE_DESCRIPTION("TAOS tsl2772 ambient and proximity light sensor driver");
1800MODULE_LICENSE("GPL");
drivers/iio/magnetometer/mag3110.c+140−18
@@ -26,6 +26,7 @@ · 25 unmodified lines
26#define MAG3110_OUT_Y 0x0326#define MAG3110_OUT_Y 0x03
27#define MAG3110_OUT_Z 0x0527#define MAG3110_OUT_Z 0x05
28#define MAG3110_WHO_AM_I 0x0728#define MAG3110_WHO_AM_I 0x07
29#define MAG3110_SYSMOD 0x08
29#define MAG3110_OFF_X 0x09 /* MSB first */30#define MAG3110_OFF_X 0x09 /* MSB first */
30#define MAG3110_OFF_Y 0x0b31#define MAG3110_OFF_Y 0x0b
31#define MAG3110_OFF_Z 0x0d32#define MAG3110_OFF_Z 0x0d
@@ -39,6 +40,8 @@ · 7 unmodified lines
39#define MAG3110_CTRL_DR_SHIFT 540#define MAG3110_CTRL_DR_SHIFT 5
40#define MAG3110_CTRL_DR_DEFAULT 041#define MAG3110_CTRL_DR_DEFAULT 0
41 42
43#define MAG3110_SYSMOD_MODE_MASK GENMASK(1, 0)
44
42#define MAG3110_CTRL_TM BIT(1) /* trigger single measurement */45#define MAG3110_CTRL_TM BIT(1) /* trigger single measurement */
43#define MAG3110_CTRL_AC BIT(0) /* continuous measurements */46#define MAG3110_CTRL_AC BIT(0) /* continuous measurements */
44 47
@@ -52,17 +55,20 @@ struct mag3110_data { · 7 unmodified lines
52 struct i2c_client *client;55 struct i2c_client *client;
53 struct mutex lock;56 struct mutex lock;
54 u8 ctrl_reg1;57 u8 ctrl_reg1;
58 int sleep_val;
55};59};
56 60
57static int mag3110_request(struct mag3110_data *data)61static int mag3110_request(struct mag3110_data *data)
58{62{
59 int ret, tries = 150;63 int ret, tries = 150;
60 64
61 /* trigger measurement */65 if ((data->ctrl_reg1 & MAG3110_CTRL_AC) == 0) {
62 ret = i2c_smbus_write_byte_data(data->client, MAG3110_CTRL_REG1,66 /* trigger measurement */
63 data->ctrl_reg1 | MAG3110_CTRL_TM);67 ret = i2c_smbus_write_byte_data(data->client, MAG3110_CTRL_REG1,
64 if (ret < 0)68 data->ctrl_reg1 | MAG3110_CTRL_TM);
65 return ret;69 if (ret < 0)
70 return ret;
71 }
66 72
67 while (tries-- > 0) {73 while (tries-- > 0) {
68 ret = i2c_smbus_read_byte_data(data->client, MAG3110_STATUS);74 ret = i2c_smbus_read_byte_data(data->client, MAG3110_STATUS);
@@ -71,7 +77,11 @@ static int mag3110_request(struct mag3110_data *data) · 2 unmodified lines
71 /* wait for data ready */77 /* wait for data ready */
72 if ((ret & MAG3110_STATUS_DRDY) == MAG3110_STATUS_DRDY)78 if ((ret & MAG3110_STATUS_DRDY) == MAG3110_STATUS_DRDY)
73 break;79 break;
74 msleep(20);80
81 if (data->sleep_val <= 20)
82 usleep_range(data->sleep_val * 250, data->sleep_val * 500);
83 else
84 msleep(20);
75 }85 }
76 86
77 if (tries < 0) {87 if (tries < 0) {
@@ -144,6 +154,117 @@ static int mag3110_get_samp_freq_index(struct mag3110_data *data, · 66 unmodified lines
144 val2);154 val2);
145}155}
146 156
157static int mag3110_calculate_sleep(struct mag3110_data *data)
158{
159 int ret, i = data->ctrl_reg1 >> MAG3110_CTRL_DR_SHIFT;
160
161 if (mag3110_samp_freq[i][0] > 0)
162 ret = 1000 / mag3110_samp_freq[i][0];
163 else
164 ret = 1000;
165
166 return ret == 0 ? 1 : ret;
167}
168
169static int mag3110_standby(struct mag3110_data *data)
170{
171 return i2c_smbus_write_byte_data(data->client, MAG3110_CTRL_REG1,
172 data->ctrl_reg1 & ~MAG3110_CTRL_AC);
173}
174
175static int mag3110_wait_standby(struct mag3110_data *data)
176{
177 int ret, tries = 30;
178
179 /*
180 * Takes up to 1/ODR to come out of active mode into stby
181 * Longest expected period is 12.5seconds.
182 * We'll sleep for 500ms between checks
183 */
184 while (tries-- > 0) {
185 ret = i2c_smbus_read_byte_data(data->client, MAG3110_SYSMOD);
186 if (ret < 0) {
187 dev_err(&data->client->dev, "i2c error\n");
188 return ret;
189 }
190 /* wait for standby */
191 if ((ret & MAG3110_SYSMOD_MODE_MASK) == 0)
192 break;
193
194 msleep_interruptible(500);
195 }
196
197 if (tries < 0) {
198 dev_err(&data->client->dev, "device not entering standby mode\n");
199 return -EIO;
200 }
201
202 return 0;
203}
204
205static int mag3110_active(struct mag3110_data *data)
206{
207 return i2c_smbus_write_byte_data(data->client, MAG3110_CTRL_REG1,
208 data->ctrl_reg1);
209}
210
211/* returns >0 if active, 0 if in standby and <0 on error */
212static int mag3110_is_active(struct mag3110_data *data)
213{
214 int reg;
215
216 reg = i2c_smbus_read_byte_data(data->client, MAG3110_CTRL_REG1);
217 if (reg < 0)
218 return reg;
219
220 return reg & MAG3110_CTRL_AC;
221}
222
223static int mag3110_change_config(struct mag3110_data *data, u8 reg, u8 val)
224{
225 int ret;
226 int is_active;
227
228 mutex_lock(&data->lock);
229
230 is_active = mag3110_is_active(data);
231 if (is_active < 0) {
232 ret = is_active;
233 goto fail;
234 }
235
236 /* config can only be changed when in standby */
237 if (is_active > 0) {
238 ret = mag3110_standby(data);
239 if (ret < 0)
240 goto fail;
241 }
242
243 /*
244 * After coming out of active we must wait for the part
245 * to transition to STBY. This can take up to 1 /ODR to occur
246 */
247 ret = mag3110_wait_standby(data);
248 if (ret < 0)
249 goto fail;
250
251 ret = i2c_smbus_write_byte_data(data->client, reg, val);
252 if (ret < 0)
253 goto fail;
254
255 if (is_active > 0) {
256 ret = mag3110_active(data);
257 if (ret < 0)
258 goto fail;
259 }
260
261 ret = 0;
262fail:
263 mutex_unlock(&data->lock);
264
265 return ret;
266}
267
147static int mag3110_read_raw(struct iio_dev *indio_dev,268static int mag3110_read_raw(struct iio_dev *indio_dev,
148 struct iio_chan_spec const *chan,269 struct iio_chan_spec const *chan,
149 int *val, int *val2, long mask)270 int *val, int *val2, long mask)
@@ -235,11 +356,15 @@ static int mag3110_write_raw(struct iio_dev *indio_dev, · 85 unmodified lines
235 ret = -EINVAL;356 ret = -EINVAL;
236 break;357 break;
237 }358 }
238 359 data->ctrl_reg1 &= 0xff & ~MAG3110_CTRL_DR_MASK
239 data->ctrl_reg1 &= ~MAG3110_CTRL_DR_MASK;360 & ~MAG3110_CTRL_AC;
240 data->ctrl_reg1 |= rate << MAG3110_CTRL_DR_SHIFT;361 data->ctrl_reg1 |= rate << MAG3110_CTRL_DR_SHIFT;
241 ret = i2c_smbus_write_byte_data(data->client,362 data->sleep_val = mag3110_calculate_sleep(data);
242 MAG3110_CTRL_REG1, data->ctrl_reg1);363 if (data->sleep_val < 40)
364 data->ctrl_reg1 |= MAG3110_CTRL_AC;
365
366 ret = mag3110_change_config(data, MAG3110_CTRL_REG1,
367 data->ctrl_reg1);
243 break;368 break;
244 case IIO_CHAN_INFO_CALIBBIAS:369 case IIO_CHAN_INFO_CALIBBIAS:
245 if (val < -10000 || val > 10000) {370 if (val < -10000 || val > 10000) {
@@ -337,12 +462,6 @@ static const struct iio_info mag3110_info = { · 91 unmodified lines
337 462
338static const unsigned long mag3110_scan_masks[] = {0x7, 0xf, 0};463static const unsigned long mag3110_scan_masks[] = {0x7, 0xf, 0};
339 464
340static int mag3110_standby(struct mag3110_data *data)
341{
342 return i2c_smbus_write_byte_data(data->client, MAG3110_CTRL_REG1,
343 data->ctrl_reg1 & ~MAG3110_CTRL_AC);
344}
345
346static int mag3110_probe(struct i2c_client *client,465static int mag3110_probe(struct i2c_client *client,
347 const struct i2c_device_id *id)466 const struct i2c_device_id *id)
348{467{
@@ -374,8 +493,11 @@ static int mag3110_probe(struct i2c_client *client, · 25 unmodified lines
374 indio_dev->available_scan_masks = mag3110_scan_masks;493 indio_dev->available_scan_masks = mag3110_scan_masks;
375 494
376 data->ctrl_reg1 = MAG3110_CTRL_DR_DEFAULT << MAG3110_CTRL_DR_SHIFT;495 data->ctrl_reg1 = MAG3110_CTRL_DR_DEFAULT << MAG3110_CTRL_DR_SHIFT;
377 ret = i2c_smbus_write_byte_data(client, MAG3110_CTRL_REG1,496 data->sleep_val = mag3110_calculate_sleep(data);
378 data->ctrl_reg1);497 if (data->sleep_val < 40)
498 data->ctrl_reg1 |= MAG3110_CTRL_AC;
499
500 ret = mag3110_change_config(data, MAG3110_CTRL_REG1, data->ctrl_reg1);
379 if (ret < 0)501 if (ret < 0)
380 return ret;502 return ret;
381 503
drivers/iio/potentiometer/mcp4018.c+20−21
@@ -99,6 +99,23 @@ static const struct iio_info mcp4018_info = { · 98 unmodified lines
99 .write_raw = mcp4018_write_raw,99 .write_raw = mcp4018_write_raw,
100};100};
101 101
102static const struct i2c_device_id mcp4018_id[] = {
103 { "mcp4017-502", MCP4018_502 },
104 { "mcp4017-103", MCP4018_103 },
105 { "mcp4017-503", MCP4018_503 },
106 { "mcp4017-104", MCP4018_104 },
107 { "mcp4018-502", MCP4018_502 },
108 { "mcp4018-103", MCP4018_103 },
109 { "mcp4018-503", MCP4018_503 },
110 { "mcp4018-104", MCP4018_104 },
111 { "mcp4019-502", MCP4018_502 },
112 { "mcp4019-103", MCP4018_103 },
113 { "mcp4019-503", MCP4018_503 },
114 { "mcp4019-104", MCP4018_104 },
115 {}
116};
117MODULE_DEVICE_TABLE(i2c, mcp4018_id);
118
102#ifdef CONFIG_OF119#ifdef CONFIG_OF
103 120
104#define MCP4018_COMPATIBLE(of_compatible, cfg) { \121#define MCP4018_COMPATIBLE(of_compatible, cfg) { \
@@ -125,8 +142,7 @@ MODULE_DEVICE_TABLE(of, mcp4018_of_match); · 20 unmodified lines
125 142
126#endif143#endif
127 144
128static int mcp4018_probe(struct i2c_client *client,145static int mcp4018_probe(struct i2c_client *client)
129 const struct i2c_device_id *id)
130{146{
131 struct device *dev = &client->dev;147 struct device *dev = &client->dev;
132 struct mcp4018_data *data;148 struct mcp4018_data *data;
@@ -150,7 +166,7 @@ static int mcp4018_probe(struct i2c_client *client, · 17 unmodified lines
150 if (match)166 if (match)
151 data->cfg = of_device_get_match_data(dev);167 data->cfg = of_device_get_match_data(dev);
152 else168 else
153 data->cfg = &mcp4018_cfg[id->driver_data];169 data->cfg = &mcp4018_cfg[i2c_match_id(mcp4018_id, client)->driver_data];
154 170
155 indio_dev->dev.parent = dev;171 indio_dev->dev.parent = dev;
156 indio_dev->info = &mcp4018_info;172 indio_dev->info = &mcp4018_info;
@@ -161,29 +177,12 @@ static int mcp4018_probe(struct i2c_client *client, · 4 unmodified lines
161 return devm_iio_device_register(dev, indio_dev);177 return devm_iio_device_register(dev, indio_dev);
162}178}
163 179
164static const struct i2c_device_id mcp4018_id[] = {
165 { "mcp4017-502", MCP4018_502 },
166 { "mcp4017-103", MCP4018_103 },
167 { "mcp4017-503", MCP4018_503 },
168 { "mcp4017-104", MCP4018_104 },
169 { "mcp4018-502", MCP4018_502 },
170 { "mcp4018-103", MCP4018_103 },
171 { "mcp4018-503", MCP4018_503 },
172 { "mcp4018-104", MCP4018_104 },
173 { "mcp4019-502", MCP4018_502 },
174 { "mcp4019-103", MCP4018_103 },
175 { "mcp4019-503", MCP4018_503 },
176 { "mcp4019-104", MCP4018_104 },
177 {}
178};
179MODULE_DEVICE_TABLE(i2c, mcp4018_id);
180
181static struct i2c_driver mcp4018_driver = {180static struct i2c_driver mcp4018_driver = {
182 .driver = {181 .driver = {
183 .name = "mcp4018",182 .name = "mcp4018",
184 .of_match_table = of_match_ptr(mcp4018_of_match),183 .of_match_table = of_match_ptr(mcp4018_of_match),
185 },184 },
186 .probe = mcp4018_probe,185 .probe_new = mcp4018_probe,
187 .id_table = mcp4018_id,186 .id_table = mcp4018_id,
188};187};
189 188
drivers/iio/potentiometer/mcp4531.c+72−73
@@ -209,6 +209,75 @@ static const struct iio_info mcp4531_info = { · 208 unmodified lines
209 .write_raw = mcp4531_write_raw,209 .write_raw = mcp4531_write_raw,
210};210};
211 211
212static const struct i2c_device_id mcp4531_id[] = {
213 { "mcp4531-502", MCP453x_502 },
214 { "mcp4531-103", MCP453x_103 },
215 { "mcp4531-503", MCP453x_503 },
216 { "mcp4531-104", MCP453x_104 },
217 { "mcp4532-502", MCP453x_502 },
218 { "mcp4532-103", MCP453x_103 },
219 { "mcp4532-503", MCP453x_503 },
220 { "mcp4532-104", MCP453x_104 },
221 { "mcp4541-502", MCP454x_502 },
222 { "mcp4541-103", MCP454x_103 },
223 { "mcp4541-503", MCP454x_503 },
224 { "mcp4541-104", MCP454x_104 },
225 { "mcp4542-502", MCP454x_502 },
226 { "mcp4542-103", MCP454x_103 },
227 { "mcp4542-503", MCP454x_503 },
228 { "mcp4542-104", MCP454x_104 },
229 { "mcp4551-502", MCP455x_502 },
230 { "mcp4551-103", MCP455x_103 },
231 { "mcp4551-503", MCP455x_503 },
232 { "mcp4551-104", MCP455x_104 },
233 { "mcp4552-502", MCP455x_502 },
234 { "mcp4552-103", MCP455x_103 },
235 { "mcp4552-503", MCP455x_503 },
236 { "mcp4552-104", MCP455x_104 },
237 { "mcp4561-502", MCP456x_502 },
238 { "mcp4561-103", MCP456x_103 },
239 { "mcp4561-503", MCP456x_503 },
240 { "mcp4561-104", MCP456x_104 },
241 { "mcp4562-502", MCP456x_502 },
242 { "mcp4562-103", MCP456x_103 },
243 { "mcp4562-503", MCP456x_503 },
244 { "mcp4562-104", MCP456x_104 },
245 { "mcp4631-502", MCP463x_502 },
246 { "mcp4631-103", MCP463x_103 },
247 { "mcp4631-503", MCP463x_503 },
248 { "mcp4631-104", MCP463x_104 },
249 { "mcp4632-502", MCP463x_502 },
250 { "mcp4632-103", MCP463x_103 },
251 { "mcp4632-503", MCP463x_503 },
252 { "mcp4632-104", MCP463x_104 },
253 { "mcp4641-502", MCP464x_502 },
254 { "mcp4641-103", MCP464x_103 },
255 { "mcp4641-503", MCP464x_503 },
256 { "mcp4641-104", MCP464x_104 },
257 { "mcp4642-502", MCP464x_502 },
258 { "mcp4642-103", MCP464x_103 },
259 { "mcp4642-503", MCP464x_503 },
260 { "mcp4642-104", MCP464x_104 },
261 { "mcp4651-502", MCP465x_502 },
262 { "mcp4651-103", MCP465x_103 },
263 { "mcp4651-503", MCP465x_503 },
264 { "mcp4651-104", MCP465x_104 },
265 { "mcp4652-502", MCP465x_502 },
266 { "mcp4652-103", MCP465x_103 },
267 { "mcp4652-503", MCP465x_503 },
268 { "mcp4652-104", MCP465x_104 },
269 { "mcp4661-502", MCP466x_502 },
270 { "mcp4661-103", MCP466x_103 },
271 { "mcp4661-503", MCP466x_503 },
272 { "mcp4661-104", MCP466x_104 },
273 { "mcp4662-502", MCP466x_502 },
274 { "mcp4662-103", MCP466x_103 },
275 { "mcp4662-503", MCP466x_503 },
276 { "mcp4662-104", MCP466x_104 },
277 {}
278};
279MODULE_DEVICE_TABLE(i2c, mcp4531_id);
280
212#ifdef CONFIG_OF281#ifdef CONFIG_OF
213 282
214#define MCP4531_COMPATIBLE(of_compatible, cfg) { \283#define MCP4531_COMPATIBLE(of_compatible, cfg) { \
@@ -286,8 +355,7 @@ static const struct of_device_id mcp4531_of_match[] = { · 71 unmodified lines
286MODULE_DEVICE_TABLE(of, mcp4531_of_match);355MODULE_DEVICE_TABLE(of, mcp4531_of_match);
287#endif356#endif
288 357
289static int mcp4531_probe(struct i2c_client *client,358static int mcp4531_probe(struct i2c_client *client)
290 const struct i2c_device_id *id)
291{359{
292 struct device *dev = &client->dev;360 struct device *dev = &client->dev;
293 struct mcp4531_data *data;361 struct mcp4531_data *data;
@@ -311,7 +379,7 @@ static int mcp4531_probe(struct i2c_client *client, · 17 unmodified lines
311 if (match)379 if (match)
312 data->cfg = of_device_get_match_data(dev);380 data->cfg = of_device_get_match_data(dev);
313 else381 else
314 data->cfg = &mcp4531_cfg[id->driver_data];382 data->cfg = &mcp4531_cfg[i2c_match_id(mcp4531_id, client)->driver_data];
315 383
316 indio_dev->dev.parent = dev;384 indio_dev->dev.parent = dev;
317 indio_dev->info = &mcp4531_info;385 indio_dev->info = &mcp4531_info;
@@ -322,81 +390,12 @@ static int mcp4531_probe(struct i2c_client *client, · 4 unmodified lines
322 return devm_iio_device_register(dev, indio_dev);390 return devm_iio_device_register(dev, indio_dev);
323}391}
324 392
325static const struct i2c_device_id mcp4531_id[] = {
326 { "mcp4531-502", MCP453x_502 },
327 { "mcp4531-103", MCP453x_103 },
328 { "mcp4531-503", MCP453x_503 },
329 { "mcp4531-104", MCP453x_104 },
330 { "mcp4532-502", MCP453x_502 },
331 { "mcp4532-103", MCP453x_103 },
332 { "mcp4532-503", MCP453x_503 },
333 { "mcp4532-104", MCP453x_104 },
334 { "mcp4541-502", MCP454x_502 },
335 { "mcp4541-103", MCP454x_103 },
336 { "mcp4541-503", MCP454x_503 },
337 { "mcp4541-104", MCP454x_104 },
338 { "mcp4542-502", MCP454x_502 },
339 { "mcp4542-103", MCP454x_103 },
340 { "mcp4542-503", MCP454x_503 },
341 { "mcp4542-104", MCP454x_104 },
342 { "mcp4551-502", MCP455x_502 },
343 { "mcp4551-103", MCP455x_103 },
344 { "mcp4551-503", MCP455x_503 },
345 { "mcp4551-104", MCP455x_104 },
346 { "mcp4552-502", MCP455x_502 },
347 { "mcp4552-103", MCP455x_103 },
348 { "mcp4552-503", MCP455x_503 },
349 { "mcp4552-104", MCP455x_104 },
350 { "mcp4561-502", MCP456x_502 },
351 { "mcp4561-103", MCP456x_103 },
352 { "mcp4561-503", MCP456x_503 },
353 { "mcp4561-104", MCP456x_104 },
354 { "mcp4562-502", MCP456x_502 },
355 { "mcp4562-103", MCP456x_103 },
356 { "mcp4562-503", MCP456x_503 },
357 { "mcp4562-104", MCP456x_104 },
358 { "mcp4631-502", MCP463x_502 },
359 { "mcp4631-103", MCP463x_103 },
360 { "mcp4631-503", MCP463x_503 },
361 { "mcp4631-104", MCP463x_104 },
362 { "mcp4632-502", MCP463x_502 },
363 { "mcp4632-103", MCP463x_103 },
364 { "mcp4632-503", MCP463x_503 },
365 { "mcp4632-104", MCP463x_104 },
366 { "mcp4641-502", MCP464x_502 },
367 { "mcp4641-103", MCP464x_103 },
368 { "mcp4641-503", MCP464x_503 },
369 { "mcp4641-104", MCP464x_104 },
370 { "mcp4642-502", MCP464x_502 },
371 { "mcp4642-103", MCP464x_103 },
372 { "mcp4642-503", MCP464x_503 },
373 { "mcp4642-104", MCP464x_104 },
374 { "mcp4651-502", MCP465x_502 },
375 { "mcp4651-103", MCP465x_103 },
376 { "mcp4651-503", MCP465x_503 },
377 { "mcp4651-104", MCP465x_104 },
378 { "mcp4652-502", MCP465x_502 },
379 { "mcp4652-103", MCP465x_103 },
380 { "mcp4652-503", MCP465x_503 },
381 { "mcp4652-104", MCP465x_104 },
382 { "mcp4661-502", MCP466x_502 },
383 { "mcp4661-103", MCP466x_103 },
384 { "mcp4661-503", MCP466x_503 },
385 { "mcp4661-104", MCP466x_104 },
386 { "mcp4662-502", MCP466x_502 },
387 { "mcp4662-103", MCP466x_103 },
388 { "mcp4662-503", MCP466x_503 },
389 { "mcp4662-104", MCP466x_104 },
390 {}
391};
392MODULE_DEVICE_TABLE(i2c, mcp4531_id);
393
394static struct i2c_driver mcp4531_driver = {393static struct i2c_driver mcp4531_driver = {
395 .driver = {394 .driver = {
396 .name = "mcp4531",395 .name = "mcp4531",
397 .of_match_table = of_match_ptr(mcp4531_of_match),396 .of_match_table = of_match_ptr(mcp4531_of_match),
398 },397 },
399 .probe = mcp4531_probe,398 .probe_new = mcp4531_probe,
400 .id_table = mcp4531_id,399 .id_table = mcp4531_id,
401};400};
402 401
drivers/iio/potentiostat/lmp91000.c+2−0
@@ -411,12 +411,14 @@ static int lmp91000_remove(struct i2c_client *client) · 410 unmodified lines
411 411
412static const struct of_device_id lmp91000_of_match[] = {412static const struct of_device_id lmp91000_of_match[] = {
413 { .compatible = "ti,lmp91000", },413 { .compatible = "ti,lmp91000", },
414 { .compatible = "ti,lmp91002", },
414 { },415 { },
415};416};
416MODULE_DEVICE_TABLE(of, lmp91000_of_match);417MODULE_DEVICE_TABLE(of, lmp91000_of_match);
417 418
418static const struct i2c_device_id lmp91000_id[] = {419static const struct i2c_device_id lmp91000_id[] = {
419 { "lmp91000", 0 },420 { "lmp91000", 0 },
421 { "lmp91002", 0 },
420 {}422 {}
421};423};
422MODULE_DEVICE_TABLE(i2c, lmp91000_id);424MODULE_DEVICE_TABLE(i2c, lmp91000_id);
drivers/iio/pressure/cros_ec_baro.c+1−2
@@ -16,6 +16,7 @@ · 15 unmodified lines
16#include <linux/delay.h>16#include <linux/delay.h>
17#include <linux/device.h>17#include <linux/device.h>
18#include <linux/iio/buffer.h>18#include <linux/iio/buffer.h>
19#include <linux/iio/common/cros_ec_sensors_core.h>
19#include <linux/iio/iio.h>20#include <linux/iio/iio.h>
20#include <linux/iio/kfifo_buf.h>21#include <linux/iio/kfifo_buf.h>
21#include <linux/iio/trigger.h>22#include <linux/iio/trigger.h>
@@ -28,8 +29,6 @@ · 6 unmodified lines
28#include <linux/slab.h>29#include <linux/slab.h>
29#include <linux/platform_device.h>30#include <linux/platform_device.h>
30 31
31#include "../common/cros_ec_sensors/cros_ec_sensors_core.h"
32
33/*32/*
34 * One channel for pressure, the other for timestamp.33 * One channel for pressure, the other for timestamp.
35 */34 */
drivers/iio/resolver/Kconfig+17−0
@@ -0,0 +1,17 @@
1#
2# Resolver/Synchro drivers
3#
4menu "Resolver to digital converters"
5
6config AD2S1200
7 tristate "Analog Devices ad2s1200/ad2s1205 driver"
8 depends on SPI
9 depends on GPIOLIB || COMPILE_TEST
10 help
11 Say yes here to build support for Analog Devices spi resolver
12 to digital converters, ad2s1200 and ad2s1205, provides direct access
13 via sysfs.
14
15 To compile this driver as a module, choose M here: the
16 module will be called ad2s1200.
17endmenu
drivers/iio/resolver/Makefile+5−0
@@ -0,0 +1,5 @@
1#
2# Makefile for Resolver/Synchro drivers
3#
4
5obj-$(CONFIG_AD2S1200) += ad2s1200.o
drivers/iio/resolver/ad2s1200.crenamed from drivers/staging/iio/resolver/ad2s1200.c+106−61
@@ -2,43 +2,49 @@ · 1 unmodified line
2 * ad2s1200.c simple support for the ADI Resolver to Digital Converters:2 * ad2s1200.c simple support for the ADI Resolver to Digital Converters:
3 * AD2S1200/12053 * AD2S1200/1205
4 *4 *
5 * Copyright (c) 2018-2018 David Veenstra <davidjulianveenstra@gmail.com>
5 * Copyright (c) 2010-2010 Analog Devices Inc.6 * Copyright (c) 2010-2010 Analog Devices Inc.
6 *7 *
7 * This program is free software; you can redistribute it and/or modify8 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as9 * it under the terms of the GNU General Public License version 2 as
9 * published by the Free Software Foundation.10 * published by the Free Software Foundation.
10 *
11 */11 */
12#include <linux/types.h>12
13#include <linux/mutex.h>13#include <linux/bitops.h>
14#include <linux/device.h>
15#include <linux/spi/spi.h>
16#include <linux/slab.h>
17#include <linux/sysfs.h>
18#include <linux/delay.h>14#include <linux/delay.h>
15#include <linux/device.h>
19#include <linux/gpio.h>16#include <linux/gpio.h>
17#include <linux/gpio/consumer.h>
20#include <linux/module.h>18#include <linux/module.h>
21#include <linux/bitops.h>19#include <linux/mutex.h>
20#include <linux/spi/spi.h>
21#include <linux/sysfs.h>
22#include <linux/types.h>
22 23
23#include <linux/iio/iio.h>24#include <linux/iio/iio.h>
24#include <linux/iio/sysfs.h>25#include <linux/iio/sysfs.h>
25 26
26#define DRV_NAME "ad2s1200"27#define DRV_NAME "ad2s1200"
27 28
28/* input pin sample and rdvel is controlled by driver */
29#define AD2S1200_PN 2
30
31/* input clock on serial interface */29/* input clock on serial interface */
32#define AD2S1200_HZ 819200030#define AD2S1200_HZ 8192000
33/* clock period in nano second */31/* clock period in nano second */
34#define AD2S1200_TSCLK (1000000000 / AD2S1200_HZ)32#define AD2S1200_TSCLK (1000000000 / AD2S1200_HZ)
35 33
34/**
35 * struct ad2s1200_state - driver instance specific data.
36 * @lock: protects both the GPIO pins and the rx buffer.
37 * @sdev: spi device.
38 * @sample: GPIO pin SAMPLE.
39 * @rdvel: GPIO pin RDVEL.
40 * @rx: buffer for spi transfers.
41 */
36struct ad2s1200_state {42struct ad2s1200_state {
37 struct mutex lock;43 struct mutex lock;
38 struct spi_device *sdev;44 struct spi_device *sdev;
39 int sample;45 struct gpio_desc *sample;
40 int rdvel;46 struct gpio_desc *rdvel;
41 u8 rx[2] ____cacheline_aligned;47 __be16 rx ____cacheline_aligned;
42};48};
43 49
44static int ad2s1200_read_raw(struct iio_dev *indio_dev,50static int ad2s1200_read_raw(struct iio_dev *indio_dev,
@@ -47,39 +53,63 @@ static int ad2s1200_read_raw(struct iio_dev *indio_dev, · 2 unmodified lines
47 int *val2,53 int *val2,
48 long m)54 long m)
49{55{
50 int ret = 0;
51 s16 vel;
52 struct ad2s1200_state *st = iio_priv(indio_dev);56 struct ad2s1200_state *st = iio_priv(indio_dev);
57 int ret;
58
59 switch (m) {
60 case IIO_CHAN_INFO_SCALE:
61 switch (chan->type) {
62 case IIO_ANGL:
63 /* 2 * Pi / (2^12 - 1) ~= 0.001534355 */
64 *val = 0;
65 *val2 = 1534355;
66 return IIO_VAL_INT_PLUS_NANO;
67 case IIO_ANGL_VEL:
68 /* 2 * Pi ~= 6.283185 */
69 *val = 6;
70 *val2 = 283185;
71 return IIO_VAL_INT_PLUS_MICRO;
72 default:
73 return -EINVAL;
74 }
75 break;
76 case IIO_CHAN_INFO_RAW:
77 mutex_lock(&st->lock);
78 gpiod_set_value(st->sample, 0);
79
80 /* delay (6 * AD2S1200_TSCLK + 20) nano seconds */
81 udelay(1);
82 gpiod_set_value(st->sample, 1);
83 gpiod_set_value(st->rdvel, !!(chan->type == IIO_ANGL));
84
85 ret = spi_read(st->sdev, &st->rx, 2);
86 if (ret < 0) {
87 mutex_unlock(&st->lock);
88 return ret;
89 }
53 90
54 mutex_lock(&st->lock);91 switch (chan->type) {
55 gpio_set_value(st->sample, 0);92 case IIO_ANGL:
56 /* delay (6 * AD2S1200_TSCLK + 20) nano seconds */93 *val = be16_to_cpup(&st->rx) >> 4;
57 udelay(1);94 break;
58 gpio_set_value(st->sample, 1);95 case IIO_ANGL_VEL:
59 gpio_set_value(st->rdvel, !!(chan->type == IIO_ANGL));96 *val = sign_extend32(be16_to_cpup(&st->rx) >> 4, 11);
60 ret = spi_read(st->sdev, st->rx, 2);97 break;
61 if (ret < 0) {98 default:
99 mutex_unlock(&st->lock);
100 return -EINVAL;
101 }
102
103 /* delay (2 * AD2S1200_TSCLK + 20) ns for sample pulse */
104 udelay(1);
62 mutex_unlock(&st->lock);105 mutex_unlock(&st->lock);
63 return ret;
64 }
65 106
66 switch (chan->type) {107 return IIO_VAL_INT;
67 case IIO_ANGL:
68 *val = (((u16)(st->rx[0])) << 4) | ((st->rx[1] & 0xF0) >> 4);
69 break;
70 case IIO_ANGL_VEL:
71 vel = (((s16)(st->rx[0])) << 4) | ((st->rx[1] & 0xF0) >> 4);
72 vel = sign_extend32(vel, 11);
73 *val = vel;
74 break;
75 default:108 default:
76 mutex_unlock(&st->lock);109 break;
77 return -EINVAL;
78 }110 }
79 /* delay (2 * AD2S1200_TSCLK + 20) ns for sample pulse */111
80 udelay(1);112 return -EINVAL;
81 mutex_unlock(&st->lock);
82 return IIO_VAL_INT;
83}113}
84 114
85static const struct iio_chan_spec ad2s1200_channels[] = {115static const struct iio_chan_spec ad2s1200_channels[] = {
@@ -88,11 +118,13 @@ static const struct iio_chan_spec ad2s1200_channels[] = { · 2 unmodified lines
88 .indexed = 1,118 .indexed = 1,
89 .channel = 0,119 .channel = 0,
90 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),120 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
121 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE),
91 }, {122 }, {
92 .type = IIO_ANGL_VEL,123 .type = IIO_ANGL_VEL,
93 .indexed = 1,124 .indexed = 1,
94 .channel = 0,125 .channel = 0,
95 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),126 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
127 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE),
96 }128 }
97};129};
98 130
@@ -104,27 +136,30 @@ static int ad2s1200_probe(struct spi_device *spi) · 5 unmodified lines
104{136{
105 struct ad2s1200_state *st;137 struct ad2s1200_state *st;
106 struct iio_dev *indio_dev;138 struct iio_dev *indio_dev;
107 int pn, ret = 0;139 int ret;
108 unsigned short *pins = spi->dev.platform_data;140
109
110 for (pn = 0; pn < AD2S1200_PN; pn++) {
111 ret = devm_gpio_request_one(&spi->dev, pins[pn], GPIOF_DIR_OUT,
112 DRV_NAME);
113 if (ret) {
114 dev_err(&spi->dev, "request gpio pin %d failed\n",
115 pins[pn]);
116 return ret;
117 }
118 }
119 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));141 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
120 if (!indio_dev)142 if (!indio_dev)
121 return -ENOMEM;143 return -ENOMEM;
144
122 spi_set_drvdata(spi, indio_dev);145 spi_set_drvdata(spi, indio_dev);
123 st = iio_priv(indio_dev);146 st = iio_priv(indio_dev);
124 mutex_init(&st->lock);147 mutex_init(&st->lock);
125 st->sdev = spi;148 st->sdev = spi;
126 st->sample = pins[0];149
127 st->rdvel = pins[1];150 st->sample = devm_gpiod_get(&spi->dev, "adi,sample", GPIOD_OUT_LOW);
151 if (IS_ERR(st->sample)) {
152 dev_err(&spi->dev, "Failed to claim SAMPLE gpio: err=%ld\n",
153 PTR_ERR(st->sample));
154 return PTR_ERR(st->sample);
155 }
156
157 st->rdvel = devm_gpiod_get(&spi->dev, "adi,rdvel", GPIOD_OUT_LOW);
158 if (IS_ERR(st->rdvel)) {
159 dev_err(&spi->dev, "Failed to claim RDVEL gpio: err=%ld\n",
160 PTR_ERR(st->rdvel));
161 return PTR_ERR(st->rdvel);
162 }
128 163
129 indio_dev->dev.parent = &spi->dev;164 indio_dev->dev.parent = &spi->dev;
130 indio_dev->info = &ad2s1200_info;165 indio_dev->info = &ad2s1200_info;
@@ -133,17 +168,25 @@ static int ad2s1200_probe(struct spi_device *spi) · 2 unmodified lines
133 indio_dev->num_channels = ARRAY_SIZE(ad2s1200_channels);168 indio_dev->num_channels = ARRAY_SIZE(ad2s1200_channels);
134 indio_dev->name = spi_get_device_id(spi)->name;169 indio_dev->name = spi_get_device_id(spi)->name;
135 170
136 ret = devm_iio_device_register(&spi->dev, indio_dev);
137 if (ret)
138 return ret;
139
140 spi->max_speed_hz = AD2S1200_HZ;171 spi->max_speed_hz = AD2S1200_HZ;
141 spi->mode = SPI_MODE_3;172 spi->mode = SPI_MODE_3;
142 spi_setup(spi);173 ret = spi_setup(spi);
143 174
144 return 0;175 if (ret < 0) {
176 dev_err(&spi->dev, "spi_setup failed!\n");
177 return ret;
178 }
179
180 return devm_iio_device_register(&spi->dev, indio_dev);
145}181}
146 182
183static const struct of_device_id ad2s1200_of_match[] = {
184 { .compatible = "adi,ad2s1200", },
185 { .compatible = "adi,ad2s1205", },
186 { }
187};
188MODULE_DEVICE_TABLE(of, ad2s1200_of_match);
189
147static const struct spi_device_id ad2s1200_id[] = {190static const struct spi_device_id ad2s1200_id[] = {
148 { "ad2s1200" },191 { "ad2s1200" },
149 { "ad2s1205" },192 { "ad2s1205" },
@@ -154,12 +197,14 @@ MODULE_DEVICE_TABLE(spi, ad2s1200_id); · 4 unmodified lines
154static struct spi_driver ad2s1200_driver = {197static struct spi_driver ad2s1200_driver = {
155 .driver = {198 .driver = {
156 .name = DRV_NAME,199 .name = DRV_NAME,
200 .of_match_table = of_match_ptr(ad2s1200_of_match),
157 },201 },
158 .probe = ad2s1200_probe,202 .probe = ad2s1200_probe,
159 .id_table = ad2s1200_id,203 .id_table = ad2s1200_id,
160};204};
161module_spi_driver(ad2s1200_driver);205module_spi_driver(ad2s1200_driver);
162 206
207MODULE_AUTHOR("David Veenstra <davidjulianveenstra@gmail.com>");
163MODULE_AUTHOR("Graff Yang <graff.yang@gmail.com>");208MODULE_AUTHOR("Graff Yang <graff.yang@gmail.com>");
164MODULE_DESCRIPTION("Analog Devices AD2S1200/1205 Resolver to Digital SPI driver");209MODULE_DESCRIPTION("Analog Devices AD2S1200/1205 Resolver to Digital SPI driver");
165MODULE_LICENSE("GPL v2");210MODULE_LICENSE("GPL v2");
drivers/staging/Kconfig+0−6
@@ -24,10 +24,6 @@ menuconfig STAGING · 23 unmodified lines
24 24
25if STAGING25if STAGING
26 26
27source "drivers/staging/ipx/Kconfig"
28
29source "drivers/staging/ncpfs/Kconfig"
30
31source "drivers/staging/wlan-ng/Kconfig"27source "drivers/staging/wlan-ng/Kconfig"
32 28
33source "drivers/staging/comedi/Kconfig"29source "drivers/staging/comedi/Kconfig"
@@ -84,8 +80,6 @@ source "drivers/staging/netlogic/Kconfig" · 50 unmodified lines
84 80
85source "drivers/staging/mt29f_spinand/Kconfig"81source "drivers/staging/mt29f_spinand/Kconfig"
86 82
87source "drivers/staging/lustre/Kconfig"
88
89source "drivers/staging/dgnc/Kconfig"83source "drivers/staging/dgnc/Kconfig"
90 84
91source "drivers/staging/gs_fpgaboot/Kconfig"85source "drivers/staging/gs_fpgaboot/Kconfig"
drivers/staging/Makefile+0−3
@@ -3,8 +3,6 @@ · 2 unmodified lines
3 3
4obj-y += media/4obj-y += media/
5obj-y += typec/5obj-y += typec/
6obj-$(CONFIG_IPX) += ipx/
7obj-$(CONFIG_NCP_FS) += ncpfs/
8obj-$(CONFIG_PRISM2_USB) += wlan-ng/6obj-$(CONFIG_PRISM2_USB) += wlan-ng/
9obj-$(CONFIG_COMEDI) += comedi/7obj-$(CONFIG_COMEDI) += comedi/
10obj-$(CONFIG_FB_OLPC_DCON) += olpc_dcon/8obj-$(CONFIG_FB_OLPC_DCON) += olpc_dcon/
@@ -32,7 +30,6 @@ obj-$(CONFIG_STAGING_BOARD) += board/ · 21 unmodified lines
32obj-$(CONFIG_LTE_GDM724X) += gdm724x/30obj-$(CONFIG_LTE_GDM724X) += gdm724x/
33obj-$(CONFIG_FIREWIRE_SERIAL) += fwserial/31obj-$(CONFIG_FIREWIRE_SERIAL) += fwserial/
34obj-$(CONFIG_GOLDFISH) += goldfish/32obj-$(CONFIG_GOLDFISH) += goldfish/
35obj-$(CONFIG_LNET) += lustre/
36obj-$(CONFIG_DGNC) += dgnc/33obj-$(CONFIG_DGNC) += dgnc/
37obj-$(CONFIG_MTD_SPINAND_MT29F) += mt29f_spinand/34obj-$(CONFIG_MTD_SPINAND_MT29F) += mt29f_spinand/
38obj-$(CONFIG_GS_FPGABOOT) += gs_fpgaboot/35obj-$(CONFIG_GS_FPGABOOT) += gs_fpgaboot/
drivers/staging/android/Kconfig+10−1
@@ -6,7 +6,7 @@ config ASHMEM · 5 unmodified lines
6 bool "Enable the Anonymous Shared Memory Subsystem"6 bool "Enable the Anonymous Shared Memory Subsystem"
7 default n7 default n
8 depends on SHMEM8 depends on SHMEM
9 ---help---9 help
10 The ashmem subsystem is a new shared memory allocator, similar to10 The ashmem subsystem is a new shared memory allocator, similar to
11 POSIX SHM but with different behavior and sporting a simpler11 POSIX SHM but with different behavior and sporting a simpler
12 file-based API.12 file-based API.
@@ -14,6 +14,15 @@ config ASHMEM · 1 unmodified line
14 It is, in theory, a good memory allocator for low-memory devices,14 It is, in theory, a good memory allocator for low-memory devices,
15 because it can discard shared memory units when under memory pressure.15 because it can discard shared memory units when under memory pressure.
16 16
17config ANDROID_VSOC
18 tristate "Android Virtual SoC support"
19 default n
20 depends on PCI_MSI
21 help
22 This option adds support for the Virtual SoC driver needed to boot
23 a 'cuttlefish' Android image inside QEmu. The driver interacts with
24 a QEmu ivshmem device. If built as a module, it will be called vsoc.
25
17source "drivers/staging/android/ion/Kconfig"26source "drivers/staging/android/ion/Kconfig"
18 27
19endif # if ANDROID28endif # if ANDROID
drivers/staging/android/Makefile+1−0
@@ -3,3 +3,4 @@ ccflags-y += -I$(src) # needed for trace events · 2 unmodified lines
3obj-y += ion/3obj-y += ion/
4 4
5obj-$(CONFIG_ASHMEM) += ashmem.o5obj-$(CONFIG_ASHMEM) += ashmem.o
6obj-$(CONFIG_ANDROID_VSOC) += vsoc.o
drivers/staging/android/TODO+9−0
@@ -11,5 +11,14 @@ ion/ · 10 unmodified lines
11 - Split /dev/ion up into multiple nodes (e.g. /dev/ion/heap0)11 - Split /dev/ion up into multiple nodes (e.g. /dev/ion/heap0)
12 - Better test framework (integration with VGEM was suggested)12 - Better test framework (integration with VGEM was suggested)
13 13
14vsoc.c, uapi/vsoc_shm.h
15 - The current driver uses the same wait queue for all of the futexes in a
16 region. This will cause false wakeups in regions with a large number of
17 waiting threads. We should eventually use multiple queues and select the
18 queue based on the region.
19 - Add debugfs support for examining the permissions of regions.
20 - Remove VSOC_WAIT_FOR_INCOMING_INTERRUPT ioctl. This functionality has been
21 superseded by the futex and is there for legacy reasons.
22
14Please send patches to Greg Kroah-Hartman <greg@kroah.com> and Cc:23Please send patches to Greg Kroah-Hartman <greg@kroah.com> and Cc:
15Arve Hjønnevåg <arve@android.com> and Riley Andrews <riandrews@android.com>24Arve Hjønnevåg <arve@android.com> and Riley Andrews <riandrews@android.com>
drivers/staging/android/ashmem.h+1−5
@@ -1,13 +1,9 @@
1// SPDX-License-Identifier: (GPL-2.0 OR Apache-2.0)1/* SPDX-License-Identifier: GPL-2.0 OR Apache-2.0 */
2/*2/*
3 * include/linux/ashmem.h3 * include/linux/ashmem.h
4 *4 *
5 * Copyright 2008 Google Inc.5 * Copyright 2008 Google Inc.
6 * Author: Robert Love6 * Author: Robert Love
7 *
8 * This file is dual licensed. It may be redistributed and/or modified
9 * under the terms of the Apache 2.0 License OR version 2 of the GNU
10 * General Public License.
11 */7 */
12 8
13#ifndef _LINUX_ASHMEM_H9#ifndef _LINUX_ASHMEM_H
drivers/staging/android/ion/Kconfig+1−1
@@ -3,7 +3,7 @@ menuconfig ION · 2 unmodified lines
3 depends on HAVE_MEMBLOCK && HAS_DMA && MMU3 depends on HAVE_MEMBLOCK && HAS_DMA && MMU
4 select GENERIC_ALLOCATOR4 select GENERIC_ALLOCATOR
5 select DMA_SHARED_BUFFER5 select DMA_SHARED_BUFFER
6 ---help---6 help
7 Choose this option to enable the ION Memory Manager,7 Choose this option to enable the ION Memory Manager,
8 used by Android to efficiently allocate buffers8 used by Android to efficiently allocate buffers
9 from userspace that can be shared between drivers.9 from userspace that can be shared between drivers.
drivers/staging/android/ion/ion.c+14−8
@@ -74,6 +74,8 @@ static struct ion_buffer *ion_buffer_create(struct ion_heap *heap, · 73 unmodified lines
74 74
75 buffer->heap = heap;75 buffer->heap = heap;
76 buffer->flags = flags;76 buffer->flags = flags;
77 buffer->dev = dev;
78 buffer->size = len;
77 79
78 ret = heap->ops->allocate(heap, buffer, len, flags);80 ret = heap->ops->allocate(heap, buffer, len, flags);
79 81
@@ -93,11 +95,6 @@ static struct ion_buffer *ion_buffer_create(struct ion_heap *heap, · 13 unmodified lines
93 goto err1;95 goto err1;
94 }96 }
95 97
96 buffer->dev = dev;
97 buffer->size = len;
98
99 buffer->dev = dev;
100 buffer->size = len;
101 INIT_LIST_HEAD(&buffer->attachments);98 INIT_LIST_HEAD(&buffer->attachments);
102 mutex_init(&buffer->lock);99 mutex_init(&buffer->lock);
103 mutex_lock(&dev->buffer_lock);100 mutex_lock(&dev->buffer_lock);
@@ -114,8 +111,11 @@ err2: · 10 unmodified lines
114 111
115void ion_buffer_destroy(struct ion_buffer *buffer)112void ion_buffer_destroy(struct ion_buffer *buffer)
116{113{
117 if (WARN_ON(buffer->kmap_cnt > 0))114 if (buffer->kmap_cnt > 0) {
115 pr_warn_once("%s: buffer still mapped in the kernel\n",
116 __func__);
118 buffer->heap->ops->unmap_kernel(buffer->heap, buffer);117 buffer->heap->ops->unmap_kernel(buffer->heap, buffer);
118 }
119 buffer->heap->ops->free(buffer);119 buffer->heap->ops->free(buffer);
120 kfree(buffer);120 kfree(buffer);
121}121}
@@ -318,6 +318,7 @@ static int ion_dma_buf_begin_cpu_access(struct dma_buf *dmabuf, · 196 unmodified lines
318 struct ion_buffer *buffer = dmabuf->priv;318 struct ion_buffer *buffer = dmabuf->priv;
319 void *vaddr;319 void *vaddr;
320 struct ion_dma_buf_attachment *a;320 struct ion_dma_buf_attachment *a;
321 int ret = 0;
321 322
322 /*323 /*
323 * TODO: Move this elsewhere because we don't always need a vaddr324 * TODO: Move this elsewhere because we don't always need a vaddr
@@ -325,6 +326,10 @@ static int ion_dma_buf_begin_cpu_access(struct dma_buf *dmabuf, · 1 unmodified line
325 if (buffer->heap->ops->map_kernel) {326 if (buffer->heap->ops->map_kernel) {
326 mutex_lock(&buffer->lock);327 mutex_lock(&buffer->lock);
327 vaddr = ion_buffer_kmap_get(buffer);328 vaddr = ion_buffer_kmap_get(buffer);
329 if (IS_ERR(vaddr)) {
330 ret = PTR_ERR(vaddr);
331 goto unlock;
332 }
328 mutex_unlock(&buffer->lock);333 mutex_unlock(&buffer->lock);
329 }334 }
330 335
@@ -333,9 +338,10 @@ static int ion_dma_buf_begin_cpu_access(struct dma_buf *dmabuf, · 2 unmodified lines
333 dma_sync_sg_for_cpu(a->dev, a->table->sgl, a->table->nents,338 dma_sync_sg_for_cpu(a->dev, a->table->sgl, a->table->nents,
334 direction);339 direction);
335 }340 }
336 mutex_unlock(&buffer->lock);
337 341
338 return 0;342unlock:
343 mutex_unlock(&buffer->lock);
344 return ret;
339}345}
340 346
341static int ion_dma_buf_end_cpu_access(struct dma_buf *dmabuf,347static int ion_dma_buf_end_cpu_access(struct dma_buf *dmabuf,
drivers/staging/android/ion/ion.h+1−1
@@ -1,4 +1,4 @@
1// SPDX-License-Identifier: GPL-2.01/* SPDX-License-Identifier: GPL-2.0 */
2/*2/*
3 * drivers/staging/android/ion/ion.h3 * drivers/staging/android/ion/ion.h
4 *4 *
drivers/staging/android/ion/ion_page_pool.c+5−0
@@ -32,6 +32,9 @@ static void ion_page_pool_add(struct ion_page_pool *pool, struct page *page) · 31 unmodified lines
32 list_add_tail(&page->lru, &pool->low_items);32 list_add_tail(&page->lru, &pool->low_items);
33 pool->low_count++;33 pool->low_count++;
34 }34 }
35
36 mod_node_page_state(page_pgdat(page), NR_INDIRECTLY_RECLAIMABLE_BYTES,
37 (1 << (PAGE_SHIFT + pool->order)));
35 mutex_unlock(&pool->mutex);38 mutex_unlock(&pool->mutex);
36}39}
37 40
@@ -50,6 +53,8 @@ static struct page *ion_page_pool_remove(struct ion_page_pool *pool, bool high) · 12 unmodified lines
50 }53 }
51 54
52 list_del(&page->lru);55 list_del(&page->lru);
56 mod_node_page_state(page_pgdat(page), NR_INDIRECTLY_RECLAIMABLE_BYTES,
57 -(1 << (PAGE_SHIFT + pool->order)));
53 return page;58 return page;
54}59}
55 60
drivers/staging/android/uapi/ashmem.h+1−5
@@ -1,13 +1,9 @@
1// SPDX-License-Identifier: (GPL-2.0 OR Apache-2.0)1/* SPDX-License-Identifier: GPL-2.0 OR Apache-2.0 */
2/*2/*
3 * drivers/staging/android/uapi/ashmem.h3 * drivers/staging/android/uapi/ashmem.h
4 *4 *
5 * Copyright 2008 Google Inc.5 * Copyright 2008 Google Inc.
6 * Author: Robert Love6 * Author: Robert Love
7 *
8 * This file is dual licensed. It may be redistributed and/or modified
9 * under the terms of the Apache 2.0 License OR version 2 of the GNU
10 * General Public License.
11 */7 */
12 8
13#ifndef _UAPI_LINUX_ASHMEM_H9#ifndef _UAPI_LINUX_ASHMEM_H
drivers/staging/android/uapi/ion.h+1−1
@@ -1,4 +1,4 @@
1// SPDX-License-Identifier: GPL-2.01/* SPDX-License-Identifier: GPL-2.0 */
2/*2/*
3 * drivers/staging/android/uapi/ion.h3 * drivers/staging/android/uapi/ion.h
4 *4 *
drivers/staging/android/uapi/vsoc_shm.h+295−0
@@ -0,0 +1,295 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2/*
3 * Copyright (C) 2017 Google, Inc.
4 *
5 */
6
7#ifndef _UAPI_LINUX_VSOC_SHM_H
8#define _UAPI_LINUX_VSOC_SHM_H
9
10#include <linux/types.h>
11
12/**
13 * A permission is a token that permits a receiver to read and/or write an area
14 * of memory within a Vsoc region.
15 *
16 * An fd_scoped permission grants both read and write access, and can be
17 * attached to a file description (see open(2)).
18 * Ownership of the area can then be shared by passing a file descriptor
19 * among processes.
20 *
21 * begin_offset and end_offset define the area of memory that is controlled by
22 * the permission. owner_offset points to a word, also in shared memory, that
23 * controls ownership of the area.
24 *
25 * ownership of the region expires when the associated file description is
26 * released.
27 *
28 * At most one permission can be attached to each file description.
29 *
30 * This is useful when implementing HALs like gralloc that scope and pass
31 * ownership of shared resources via file descriptors.
32 *
33 * The caller is responsibe for doing any fencing.
34 *
35 * The calling process will normally identify a currently free area of
36 * memory. It will construct a proposed fd_scoped_permission_arg structure:
37 *
38 * begin_offset and end_offset describe the area being claimed
39 *
40 * owner_offset points to the location in shared memory that indicates the
41 * owner of the area.
42 *
43 * owned_value is the value that will be stored in owner_offset iff the
44 * permission can be granted. It must be different than VSOC_REGION_FREE.
45 *
46 * Two fd_scoped_permission structures are compatible if they vary only by
47 * their owned_value fields.
48 *
49 * The driver ensures that, for any group of simultaneous callers proposing
50 * compatible fd_scoped_permissions, it will accept exactly one of the
51 * propopsals. The other callers will get a failure with errno of EAGAIN.
52 *
53 * A process receiving a file descriptor can identify the region being
54 * granted using the VSOC_GET_FD_SCOPED_PERMISSION ioctl.
55 */
56struct fd_scoped_permission {
57 __u32 begin_offset;
58 __u32 end_offset;
59 __u32 owner_offset;
60 __u32 owned_value;
61};
62
63/*
64 * This value represents a free area of memory. The driver expects to see this
65 * value at owner_offset when creating a permission otherwise it will not do it,
66 * and will write this value back once the permission is no longer needed.
67 */
68#define VSOC_REGION_FREE ((__u32)0)
69
70/**
71 * ioctl argument for VSOC_CREATE_FD_SCOPE_PERMISSION
72 */
73struct fd_scoped_permission_arg {
74 struct fd_scoped_permission perm;
75 __s32 managed_region_fd;
76};
77
78#define VSOC_NODE_FREE ((__u32)0)
79
80/*
81 * Describes a signal table in shared memory. Each non-zero entry in the
82 * table indicates that the receiver should signal the futex at the given
83 * offset. Offsets are relative to the region, not the shared memory window.
84 *
85 * interrupt_signalled_offset is used to reliably signal interrupts across the
86 * vmm boundary. There are two roles: transmitter and receiver. For example,
87 * in the host_to_guest_signal_table the host is the transmitter and the
88 * guest is the receiver. The protocol is as follows:
89 *
90 * 1. The transmitter should convert the offset of the futex to an offset
91 * in the signal table [0, (1 << num_nodes_lg2))
92 * The transmitter can choose any appropriate hashing algorithm, including
93 * hash = futex_offset & ((1 << num_nodes_lg2) - 1)
94 *
95 * 3. The transmitter should atomically compare and swap futex_offset with 0
96 * at hash. There are 3 possible outcomes
97 * a. The swap fails because the futex_offset is already in the table.
98 * The transmitter should stop.
99 * b. Some other offset is in the table. This is a hash collision. The
100 * transmitter should move to another table slot and try again. One
101 * possible algorithm:
102 * hash = (hash + 1) & ((1 << num_nodes_lg2) - 1)
103 * c. The swap worked. Continue below.
104 *
105 * 3. The transmitter atomically swaps 1 with the value at the
106 * interrupt_signalled_offset. There are two outcomes:
107 * a. The prior value was 1. In this case an interrupt has already been
108 * posted. The transmitter is done.
109 * b. The prior value was 0, indicating that the receiver may be sleeping.
110 * The transmitter will issue an interrupt.
111 *
112 * 4. On waking the receiver immediately exchanges a 0 with the
113 * interrupt_signalled_offset. If it receives a 0 then this a spurious
114 * interrupt. That may occasionally happen in the current protocol, but
115 * should be rare.
116 *
117 * 5. The receiver scans the signal table by atomicaly exchanging 0 at each
118 * location. If a non-zero offset is returned from the exchange the
119 * receiver wakes all sleepers at the given offset:
120 * futex((int*)(region_base + old_value), FUTEX_WAKE, MAX_INT);
121 *
122 * 6. The receiver thread then does a conditional wait, waking immediately
123 * if the value at interrupt_signalled_offset is non-zero. This catches cases
124 * here additional signals were posted while the table was being scanned.
125 * On the guest the wait is handled via the VSOC_WAIT_FOR_INCOMING_INTERRUPT
126 * ioctl.
127 */
128struct vsoc_signal_table_layout {
129 /* log_2(Number of signal table entries) */
130 __u32 num_nodes_lg2;
131 /*
132 * Offset to the first signal table entry relative to the start of the
133 * region
134 */
135 __u32 futex_uaddr_table_offset;
136 /*
137 * Offset to an atomic_t / atomic uint32_t. A non-zero value indicates
138 * that one or more offsets are currently posted in the table.
139 * semi-unique access to an entry in the table
140 */
141 __u32 interrupt_signalled_offset;
142};
143
144#define VSOC_REGION_WHOLE ((__s32)0)
145#define VSOC_DEVICE_NAME_SZ 16
146
147/**
148 * Each HAL would (usually) talk to a single device region
149 * Mulitple entities care about these regions:
150 * - The ivshmem_server will populate the regions in shared memory
151 * - The guest kernel will read the region, create minor device nodes, and
152 * allow interested parties to register for FUTEX_WAKE events in the region
153 * - HALs will access via the minor device nodes published by the guest kernel
154 * - Host side processes will access the region via the ivshmem_server:
155 * 1. Pass name to ivshmem_server at a UNIX socket
156 * 2. ivshmemserver will reply with 2 fds:
157 * - host->guest doorbell fd
158 * - guest->host doorbell fd
159 * - fd for the shared memory region
160 * - region offset
161 * 3. Start a futex receiver thread on the doorbell fd pointed at the
162 * signal_nodes
163 */
164struct vsoc_device_region {
165 __u16 current_version;
166 __u16 min_compatible_version;
167 __u32 region_begin_offset;
168 __u32 region_end_offset;
169 __u32 offset_of_region_data;
170 struct vsoc_signal_table_layout guest_to_host_signal_table;
171 struct vsoc_signal_table_layout host_to_guest_signal_table;
172 /* Name of the device. Must always be terminated with a '\0', so
173 * the longest supported device name is 15 characters.
174 */
175 char device_name[VSOC_DEVICE_NAME_SZ];
176 /* There are two ways that permissions to access regions are handled:
177 * - When subdivided_by is VSOC_REGION_WHOLE, any process that can
178 * open the device node for the region gains complete access to it.
179 * - When subdivided is set processes that open the region cannot
180 * access it. Access to a sub-region must be established by invoking
181 * the VSOC_CREATE_FD_SCOPE_PERMISSION ioctl on the region
182 * referenced in subdivided_by, providing a fileinstance
183 * (represented by a fd) opened on this region.
184 */
185 __u32 managed_by;
186};
187
188/*
189 * The vsoc layout descriptor.
190 * The first 4K should be reserved for the shm header and region descriptors.
191 * The regions should be page aligned.
192 */
193
194struct vsoc_shm_layout_descriptor {
195 __u16 major_version;
196 __u16 minor_version;
197
198 /* size of the shm. This may be redundant but nice to have */
199 __u32 size;
200
201 /* number of shared memory regions */
202 __u32 region_count;
203
204 /* The offset to the start of region descriptors */
205 __u32 vsoc_region_desc_offset;
206};
207
208/*
209 * This specifies the current version that should be stored in
210 * vsoc_shm_layout_descriptor.major_version and
211 * vsoc_shm_layout_descriptor.minor_version.
212 * It should be updated only if the vsoc_device_region and
213 * vsoc_shm_layout_descriptor structures have changed.
214 * Versioning within each region is transferred
215 * via the min_compatible_version and current_version fields in
216 * vsoc_device_region. The driver does not consult these fields: they are left
217 * for the HALs and host processes and will change independently of the layout
218 * version.
219 */
220#define CURRENT_VSOC_LAYOUT_MAJOR_VERSION 2
221#define CURRENT_VSOC_LAYOUT_MINOR_VERSION 0
222
223#define VSOC_CREATE_FD_SCOPED_PERMISSION \
224 _IOW(0xF5, 0, struct fd_scoped_permission)
225#define VSOC_GET_FD_SCOPED_PERMISSION _IOR(0xF5, 1, struct fd_scoped_permission)
226
227/*
228 * This is used to signal the host to scan the guest_to_host_signal_table
229 * for new futexes to wake. This sends an interrupt if one is not already
230 * in flight.
231 */
232#define VSOC_MAYBE_SEND_INTERRUPT_TO_HOST _IO(0xF5, 2)
233
234/*
235 * When this returns the guest will scan host_to_guest_signal_table to
236 * check for new futexes to wake.
237 */
238/* TODO(ghartman): Consider moving this to the bottom half */
239#define VSOC_WAIT_FOR_INCOMING_INTERRUPT _IO(0xF5, 3)
240
241/*
242 * Guest HALs will use this to retrieve the region description after
243 * opening their device node.
244 */
245#define VSOC_DESCRIBE_REGION _IOR(0xF5, 4, struct vsoc_device_region)
246
247/*
248 * Wake any threads that may be waiting for a host interrupt on this region.
249 * This is mostly used during shutdown.
250 */
251#define VSOC_SELF_INTERRUPT _IO(0xF5, 5)
252
253/*
254 * This is used to signal the host to scan the guest_to_host_signal_table
255 * for new futexes to wake. This sends an interrupt unconditionally.
256 */
257#define VSOC_SEND_INTERRUPT_TO_HOST _IO(0xF5, 6)
258
259enum wait_types {
260 VSOC_WAIT_UNDEFINED = 0,
261 VSOC_WAIT_IF_EQUAL = 1,
262 VSOC_WAIT_IF_EQUAL_TIMEOUT = 2
263};
264
265/*
266 * Wait for a condition to be true
267 *
268 * Note, this is sized and aligned so the 32 bit and 64 bit layouts are
269 * identical.
270 */
271struct vsoc_cond_wait {
272 /* Input: Offset of the 32 bit word to check */
273 __u32 offset;
274 /* Input: Value that will be compared with the offset */
275 __u32 value;
276 /* Monotonic time to wake at in seconds */
277 __u64 wake_time_sec;
278 /* Input: Monotonic time to wait in nanoseconds */
279 __u32 wake_time_nsec;
280 /* Input: Type of wait */
281 __u32 wait_type;
282 /* Output: Number of times the thread woke before returning. */
283 __u32 wakes;
284 /* Ensure that we're 8-byte aligned and 8 byte length for 32/64 bit
285 * compatibility.
286 */
287 __u32 reserved_1;
288};
289
290#define VSOC_COND_WAIT _IOWR(0xF5, 7, struct vsoc_cond_wait)
291
292/* Wake any local threads waiting at the offset given in arg */
293#define VSOC_COND_WAKE _IO(0xF5, 8)
294
295#endif /* _UAPI_LINUX_VSOC_SHM_H */
drivers/staging/android/vsoc.c+1152−0
@@ -0,0 +1,1152 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * drivers/android/staging/vsoc.c
4 *
5 * Android Virtual System on a Chip (VSoC) driver
6 *
7 * Copyright (C) 2017 Google, Inc.
8 *
9 * Author: ghartman@google.com
10 *
11 * Based on drivers/char/kvm_ivshmem.c - driver for KVM Inter-VM shared memory
12 * Copyright 2009 Cam Macdonell <cam@cs.ualberta.ca>
13 *
14 * Based on cirrusfb.c and 8139cp.c:
15 * Copyright 1999-2001 Jeff Garzik
16 * Copyright 2001-2004 Jeff Garzik
17 */
18
19#include <linux/dma-mapping.h>
20#include <linux/freezer.h>
21#include <linux/futex.h>
22#include <linux/init.h>
23#include <linux/kernel.h>
24#include <linux/module.h>
25#include <linux/mutex.h>
26#include <linux/pci.h>
27#include <linux/proc_fs.h>
28#include <linux/sched.h>
29#include <linux/syscalls.h>
30#include <linux/uaccess.h>
31#include <linux/interrupt.h>
32#include <linux/mutex.h>
33#include <linux/cdev.h>
34#include <linux/file.h>
35#include "uapi/vsoc_shm.h"
36
37#define VSOC_DEV_NAME "vsoc"
38
39/*
40 * Description of the ivshmem-doorbell PCI device used by QEmu. These
41 * constants follow docs/specs/ivshmem-spec.txt, which can be found in
42 * the QEmu repository. This was last reconciled with the version that
43 * came out with 2.8
44 */
45
46/*
47 * These constants are determined KVM Inter-VM shared memory device
48 * register offsets
49 */
50enum {
51 INTR_MASK = 0x00, /* Interrupt Mask */
52 INTR_STATUS = 0x04, /* Interrupt Status */
53 IV_POSITION = 0x08, /* VM ID */
54 DOORBELL = 0x0c, /* Doorbell */
55};
56
57static const int REGISTER_BAR; /* Equal to 0 */
58static const int MAX_REGISTER_BAR_LEN = 0x100;
59/*
60 * The MSI-x BAR is not used directly.
61 *
62 * static const int MSI_X_BAR = 1;
63 */
64static const int SHARED_MEMORY_BAR = 2;
65
66struct vsoc_region_data {
67 char name[VSOC_DEVICE_NAME_SZ + 1];
68 wait_queue_head_t interrupt_wait_queue;
69 /* TODO(b/73664181): Use multiple futex wait queues */
70 wait_queue_head_t futex_wait_queue;
71 /* Flag indicating that an interrupt has been signalled by the host. */
72 atomic_t *incoming_signalled;
73 /* Flag indicating the guest has signalled the host. */
74 atomic_t *outgoing_signalled;
75 bool irq_requested;
76 bool device_created;
77};
78
79struct vsoc_device {
80 /* Kernel virtual address of REGISTER_BAR. */
81 void __iomem *regs;
82 /* Physical address of SHARED_MEMORY_BAR. */
83 phys_addr_t shm_phys_start;
84 /* Kernel virtual address of SHARED_MEMORY_BAR. */
85 void __iomem *kernel_mapped_shm;
86 /* Size of the entire shared memory window in bytes. */
87 size_t shm_size;
88 /*
89 * Pointer to the virtual address of the shared memory layout structure.
90 * This is probably identical to kernel_mapped_shm, but saving this
91 * here saves a lot of annoying casts.
92 */
93 struct vsoc_shm_layout_descriptor *layout;
94 /*
95 * Points to a table of region descriptors in the kernel's virtual
96 * address space. Calculated from
97 * vsoc_shm_layout_descriptor.vsoc_region_desc_offset
98 */
99 struct vsoc_device_region *regions;
100 /* Head of a list of permissions that have been granted. */
101 struct list_head permissions;
102 struct pci_dev *dev;
103 /* Per-region (and therefore per-interrupt) information. */
104 struct vsoc_region_data *regions_data;
105 /*
106 * Table of msi-x entries. This has to be separated from struct
107 * vsoc_region_data because the kernel deals with them as an array.
108 */
109 struct msix_entry *msix_entries;
110 /* Mutex that protectes the permission list */
111 struct mutex mtx;
112 /* Major number assigned by the kernel */
113 int major;
114 /* Character device assigned by the kernel */
115 struct cdev cdev;
116 /* Device class assigned by the kernel */
117 struct class *class;
118 /*
119 * Flags that indicate what we've initialized. These are used to do an
120 * orderly cleanup of the device.
121 */
122 bool enabled_device;
123 bool requested_regions;
124 bool cdev_added;
125 bool class_added;
126 bool msix_enabled;
127};
128
129static struct vsoc_device vsoc_dev;
130
131/*
132 * TODO(ghartman): Add a /sys filesystem entry that summarizes the permissions.
133 */
134
135struct fd_scoped_permission_node {
136 struct fd_scoped_permission permission;
137 struct list_head list;
138};
139
140struct vsoc_private_data {
141 struct fd_scoped_permission_node *fd_scoped_permission_node;
142};
143
144static long vsoc_ioctl(struct file *, unsigned int, unsigned long);
145static int vsoc_mmap(struct file *, struct vm_area_struct *);
146static int vsoc_open(struct inode *, struct file *);
147static int vsoc_release(struct inode *, struct file *);
148static ssize_t vsoc_read(struct file *, char __user *, size_t, loff_t *);
149static ssize_t vsoc_write(struct file *, const char __user *, size_t, loff_t *);
150static loff_t vsoc_lseek(struct file *filp, loff_t offset, int origin);
151static int
152do_create_fd_scoped_permission(struct vsoc_device_region *region_p,
153 struct fd_scoped_permission_node *np,
154 struct fd_scoped_permission_arg __user *arg);
155static void
156do_destroy_fd_scoped_permission(struct vsoc_device_region *owner_region_p,
157 struct fd_scoped_permission *perm);
158static long do_vsoc_describe_region(struct file *,
159 struct vsoc_device_region __user *);
160static ssize_t vsoc_get_area(struct file *filp, __u32 *perm_off);
161
162/**
163 * Validate arguments on entry points to the driver.
164 */
165inline int vsoc_validate_inode(struct inode *inode)
166{
167 if (iminor(inode) >= vsoc_dev.layout->region_count) {
168 dev_err(&vsoc_dev.dev->dev,
169 "describe_region: invalid region %d\n", iminor(inode));
170 return -ENODEV;
171 }
172 return 0;
173}
174
175inline int vsoc_validate_filep(struct file *filp)
176{
177 int ret = vsoc_validate_inode(file_inode(filp));
178
179 if (ret)
180 return ret;
181 if (!filp->private_data) {
182 dev_err(&vsoc_dev.dev->dev,
183 "No private data on fd, region %d\n",
184 iminor(file_inode(filp)));
185 return -EBADFD;
186 }
187 return 0;
188}
189
190/* Converts from shared memory offset to virtual address */
191static inline void *shm_off_to_virtual_addr(__u32 offset)
192{
193 return (void __force *)vsoc_dev.kernel_mapped_shm + offset;
194}
195
196/* Converts from shared memory offset to physical address */
197static inline phys_addr_t shm_off_to_phys_addr(__u32 offset)
198{
199 return vsoc_dev.shm_phys_start + offset;
200}
201
202/**
203 * Convenience functions to obtain the region from the inode or file.
204 * Dangerous to call before validating the inode/file.
205 */
206static
207inline struct vsoc_device_region *vsoc_region_from_inode(struct inode *inode)
208{
209 return &vsoc_dev.regions[iminor(inode)];
210}
211
212static
213inline struct vsoc_device_region *vsoc_region_from_filep(struct file *inode)
214{
215 return vsoc_region_from_inode(file_inode(inode));
216}
217
218static inline uint32_t vsoc_device_region_size(struct vsoc_device_region *r)
219{
220 return r->region_end_offset - r->region_begin_offset;
221}
222
223static const struct file_operations vsoc_ops = {
224 .owner = THIS_MODULE,
225 .open = vsoc_open,
226 .mmap = vsoc_mmap,
227 .read = vsoc_read,
228 .unlocked_ioctl = vsoc_ioctl,
229 .compat_ioctl = vsoc_ioctl,
230 .write = vsoc_write,
231 .llseek = vsoc_lseek,
232 .release = vsoc_release,
233};
234
235static struct pci_device_id vsoc_id_table[] = {
236 {0x1af4, 0x1110, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
237 {0},
238};
239
240MODULE_DEVICE_TABLE(pci, vsoc_id_table);
241
242static void vsoc_remove_device(struct pci_dev *pdev);
243static int vsoc_probe_device(struct pci_dev *pdev,
244 const struct pci_device_id *ent);
245
246static struct pci_driver vsoc_pci_driver = {
247 .name = "vsoc",
248 .id_table = vsoc_id_table,
249 .probe = vsoc_probe_device,
250 .remove = vsoc_remove_device,
251};
252
253static int
254do_create_fd_scoped_permission(struct vsoc_device_region *region_p,
255 struct fd_scoped_permission_node *np,
256 struct fd_scoped_permission_arg __user *arg)
257{
258 struct file *managed_filp;
259 s32 managed_fd;
260 atomic_t *owner_ptr = NULL;
261 struct vsoc_device_region *managed_region_p;
262
263 if (copy_from_user(&np->permission, &arg->perm, sizeof(*np)) ||
264 copy_from_user(&managed_fd,
265 &arg->managed_region_fd, sizeof(managed_fd))) {
266 return -EFAULT;
267 }
268 managed_filp = fdget(managed_fd).file;
269 /* Check that it's a valid fd, */
270 if (!managed_filp || vsoc_validate_filep(managed_filp))
271 return -EPERM;
272 /* EEXIST if the given fd already has a permission. */
273 if (((struct vsoc_private_data *)managed_filp->private_data)->
274 fd_scoped_permission_node)
275 return -EEXIST;
276 managed_region_p = vsoc_region_from_filep(managed_filp);
277 /* Check that the provided region is managed by this one */
278 if (&vsoc_dev.regions[managed_region_p->managed_by] != region_p)
279 return -EPERM;
280 /* The area must be well formed and have non-zero size */
281 if (np->permission.begin_offset >= np->permission.end_offset)
282 return -EINVAL;
283 /* The area must fit in the memory window */
284 if (np->permission.end_offset >
285 vsoc_device_region_size(managed_region_p))
286 return -ERANGE;
287 /* The area must be in the region data section */
288 if (np->permission.begin_offset <
289 managed_region_p->offset_of_region_data)
290 return -ERANGE;
291 /* The area must be page aligned */
292 if (!PAGE_ALIGNED(np->permission.begin_offset) ||
293 !PAGE_ALIGNED(np->permission.end_offset))
294 return -EINVAL;
295 /* Owner offset must be naturally aligned in the window */
296 if (np->permission.owner_offset &
297 (sizeof(np->permission.owner_offset) - 1))
298 return -EINVAL;
299 /* The owner flag must reside in the owner memory */
300 if (np->permission.owner_offset + sizeof(np->permission.owner_offset) >
301 vsoc_device_region_size(region_p))
302 return -ERANGE;
303 /* The owner flag must reside in the data section */
304 if (np->permission.owner_offset < region_p->offset_of_region_data)
305 return -EINVAL;
306 /* The owner value must change to claim the memory */
307 if (np->permission.owned_value == VSOC_REGION_FREE)
308 return -EINVAL;
309 owner_ptr =
310 (atomic_t *)shm_off_to_virtual_addr(region_p->region_begin_offset +
311 np->permission.owner_offset);
312 /* We've already verified that this is in the shared memory window, so
313 * it should be safe to write to this address.
314 */
315 if (atomic_cmpxchg(owner_ptr,
316 VSOC_REGION_FREE,
317 np->permission.owned_value) != VSOC_REGION_FREE) {
318 return -EBUSY;
319 }
320 ((struct vsoc_private_data *)managed_filp->private_data)->
321 fd_scoped_permission_node = np;
322 /* The file offset needs to be adjusted if the calling
323 * process did any read/write operations on the fd
324 * before creating the permission.
325 */
326 if (managed_filp->f_pos) {
327 if (managed_filp->f_pos > np->permission.end_offset) {
328 /* If the offset is beyond the permission end, set it
329 * to the end.
330 */
331 managed_filp->f_pos = np->permission.end_offset;
332 } else {
333 /* If the offset is within the permission interval
334 * keep it there otherwise reset it to zero.
335 */
336 if (managed_filp->f_pos < np->permission.begin_offset) {
337 managed_filp->f_pos = 0;
338 } else {
339 managed_filp->f_pos -=
340 np->permission.begin_offset;
341 }
342 }
343 }
344 return 0;
345}
346
347static void
348do_destroy_fd_scoped_permission_node(struct vsoc_device_region *owner_region_p,
349 struct fd_scoped_permission_node *node)
350{
351 if (node) {
352 do_destroy_fd_scoped_permission(owner_region_p,
353 &node->permission);
354 mutex_lock(&vsoc_dev.mtx);
355 list_del(&node->list);
356 mutex_unlock(&vsoc_dev.mtx);
357 kfree(node);
358 }
359}
360
361static void
362do_destroy_fd_scoped_permission(struct vsoc_device_region *owner_region_p,
363 struct fd_scoped_permission *perm)
364{
365 atomic_t *owner_ptr = NULL;
366 int prev = 0;
367
368 if (!perm)
369 return;
370 owner_ptr = (atomic_t *)shm_off_to_virtual_addr
371 (owner_region_p->region_begin_offset + perm->owner_offset);
372 prev = atomic_xchg(owner_ptr, VSOC_REGION_FREE);
373 if (prev != perm->owned_value)
374 dev_err(&vsoc_dev.dev->dev,
375 "%x-%x: owner (%s) %x: expected to be %x was %x",
376 perm->begin_offset, perm->end_offset,
377 owner_region_p->device_name, perm->owner_offset,
378 perm->owned_value, prev);
379}
380
381static long do_vsoc_describe_region(struct file *filp,
382 struct vsoc_device_region __user *dest)
383{
384 struct vsoc_device_region *region_p;
385 int retval = vsoc_validate_filep(filp);
386
387 if (retval)
388 return retval;
389 region_p = vsoc_region_from_filep(filp);
390 if (copy_to_user(dest, region_p, sizeof(*region_p)))
391 return -EFAULT;
392 return 0;
393}
394
395/**
396 * Implements the inner logic of cond_wait. Copies to and from userspace are
397 * done in the helper function below.
398 */
399static int handle_vsoc_cond_wait(struct file *filp, struct vsoc_cond_wait *arg)
400{
401 DEFINE_WAIT(wait);
402 u32 region_number = iminor(file_inode(filp));
403 struct vsoc_region_data *data = vsoc_dev.regions_data + region_number;
404 struct hrtimer_sleeper timeout, *to = NULL;
405 int ret = 0;
406 struct vsoc_device_region *region_p = vsoc_region_from_filep(filp);
407 atomic_t *address = NULL;
408 struct timespec ts;
409
410 /* Ensure that the offset is aligned */
411 if (arg->offset & (sizeof(uint32_t) - 1))
412 return -EADDRNOTAVAIL;
413 /* Ensure that the offset is within shared memory */
414 if (((uint64_t)arg->offset) + region_p->region_begin_offset +
415 sizeof(uint32_t) > region_p->region_end_offset)
416 return -E2BIG;
417 address = shm_off_to_virtual_addr(region_p->region_begin_offset +
418 arg->offset);
419
420 /* Ensure that the type of wait is valid */
421 switch (arg->wait_type) {
422 case VSOC_WAIT_IF_EQUAL:
423 break;
424 case VSOC_WAIT_IF_EQUAL_TIMEOUT:
425 to = &timeout;
426 break;
427 default:
428 return -EINVAL;
429 }
430
431 if (to) {
432 /* Copy the user-supplied timesec into the kernel structure.
433 * We do things this way to flatten differences between 32 bit
434 * and 64 bit timespecs.
435 */
436 ts.tv_sec = arg->wake_time_sec;
437 ts.tv_nsec = arg->wake_time_nsec;
438
439 if (!timespec_valid(&ts))
440 return -EINVAL;
441 hrtimer_init_on_stack(&to->timer, CLOCK_MONOTONIC,
442 HRTIMER_MODE_ABS);
443 hrtimer_set_expires_range_ns(&to->timer, timespec_to_ktime(ts),
444 current->timer_slack_ns);
445
446 hrtimer_init_sleeper(to, current);
447 }
448
449 while (1) {
450 prepare_to_wait(&data->futex_wait_queue, &wait,
451 TASK_INTERRUPTIBLE);
452 /*
453 * Check the sentinel value after prepare_to_wait. If the value
454 * changes after this check the writer will call signal,
455 * changing the task state from INTERRUPTIBLE to RUNNING. That
456 * will ensure that schedule() will eventually schedule this
457 * task.
458 */
459 if (atomic_read(address) != arg->value) {
460 ret = 0;
461 break;
462 }
463 if (to) {
464 hrtimer_start_expires(&to->timer, HRTIMER_MODE_ABS);
465 if (likely(to->task))
466 freezable_schedule();
467 hrtimer_cancel(&to->timer);
468 if (!to->task) {
469 ret = -ETIMEDOUT;
470 break;
471 }
472 } else {
473 freezable_schedule();
474 }
475 /* Count the number of times that we woke up. This is useful
476 * for unit testing.
477 */
478 ++arg->wakes;
479 if (signal_pending(current)) {
480 ret = -EINTR;
481 break;
482 }
483 }
484 finish_wait(&data->futex_wait_queue, &wait);
485 if (to)
486 destroy_hrtimer_on_stack(&to->timer);
487 return ret;
488}
489
490/**
491 * Handles the details of copying from/to userspace to ensure that the copies
492 * happen on all of the return paths of cond_wait.
493 */
494static int do_vsoc_cond_wait(struct file *filp,
495 struct vsoc_cond_wait __user *untrusted_in)
496{
497 struct vsoc_cond_wait arg;
498 int rval = 0;
499
500 if (copy_from_user(&arg, untrusted_in, sizeof(arg)))
501 return -EFAULT;
502 /* wakes is an out parameter. Initialize it to something sensible. */
503 arg.wakes = 0;
504 rval = handle_vsoc_cond_wait(filp, &arg);
505 if (copy_to_user(untrusted_in, &arg, sizeof(arg)))
506 return -EFAULT;
507 return rval;
508}
509
510static int do_vsoc_cond_wake(struct file *filp, uint32_t offset)
511{
512 struct vsoc_device_region *region_p = vsoc_region_from_filep(filp);
513 u32 region_number = iminor(file_inode(filp));
514 struct vsoc_region_data *data = vsoc_dev.regions_data + region_number;
515 /* Ensure that the offset is aligned */
516 if (offset & (sizeof(uint32_t) - 1))
517 return -EADDRNOTAVAIL;
518 /* Ensure that the offset is within shared memory */
519 if (((uint64_t)offset) + region_p->region_begin_offset +
520 sizeof(uint32_t) > region_p->region_end_offset)
521 return -E2BIG;
522 /*
523 * TODO(b/73664181): Use multiple futex wait queues.
524 * We need to wake every sleeper when the condition changes. Typically
525 * only a single thread will be waiting on the condition, but there
526 * are exceptions. The worst case is about 10 threads.
527 */
528 wake_up_interruptible_all(&data->futex_wait_queue);
529 return 0;
530}
531
532static long vsoc_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
533{
534 int rv = 0;
535 struct vsoc_device_region *region_p;
536 u32 reg_num;
537 struct vsoc_region_data *reg_data;
538 int retval = vsoc_validate_filep(filp);
539
540 if (retval)
541 return retval;
542 region_p = vsoc_region_from_filep(filp);
543 reg_num = iminor(file_inode(filp));
544 reg_data = vsoc_dev.regions_data + reg_num;
545 switch (cmd) {
546 case VSOC_CREATE_FD_SCOPED_PERMISSION:
547 {
548 struct fd_scoped_permission_node *node = NULL;
549
550 node = kzalloc(sizeof(*node), GFP_KERNEL);
551 /* We can't allocate memory for the permission */
552 if (!node)
553 return -ENOMEM;
554 INIT_LIST_HEAD(&node->list);
555 rv = do_create_fd_scoped_permission
556 (region_p,
557 node,
558 (struct fd_scoped_permission_arg __user *)arg);
559 if (!rv) {
560 mutex_lock(&vsoc_dev.mtx);
561 list_add(&node->list, &vsoc_dev.permissions);
562 mutex_unlock(&vsoc_dev.mtx);
563 } else {
564 kfree(node);
565 return rv;
566 }
567 }
568 break;
569
570 case VSOC_GET_FD_SCOPED_PERMISSION:
571 {
572 struct fd_scoped_permission_node *node =
573 ((struct vsoc_private_data *)filp->private_data)->
574 fd_scoped_permission_node;
575 if (!node)
576 return -ENOENT;
577 if (copy_to_user
578 ((struct fd_scoped_permission __user *)arg,
579 &node->permission, sizeof(node->permission)))
580 return -EFAULT;
581 }
582 break;
583
584 case VSOC_MAYBE_SEND_INTERRUPT_TO_HOST:
585 if (!atomic_xchg(reg_data->outgoing_signalled, 1)) {
586 writel(reg_num, vsoc_dev.regs + DOORBELL);
587 return 0;
588 } else {
589 return -EBUSY;
590 }
591 break;
592
593 case VSOC_SEND_INTERRUPT_TO_HOST:
594 writel(reg_num, vsoc_dev.regs + DOORBELL);
595 return 0;
596 case VSOC_WAIT_FOR_INCOMING_INTERRUPT:
597 wait_event_interruptible
598 (reg_data->interrupt_wait_queue,
599 (atomic_read(reg_data->incoming_signalled) != 0));
600 break;
601
602 case VSOC_DESCRIBE_REGION:
603 return do_vsoc_describe_region
604 (filp,
605 (struct vsoc_device_region __user *)arg);
606
607 case VSOC_SELF_INTERRUPT:
608 atomic_set(reg_data->incoming_signalled, 1);
609 wake_up_interruptible(&reg_data->interrupt_wait_queue);
610 break;
611
612 case VSOC_COND_WAIT:
613 return do_vsoc_cond_wait(filp,
614 (struct vsoc_cond_wait __user *)arg);
615 case VSOC_COND_WAKE:
616 return do_vsoc_cond_wake(filp, arg);
617
618 default:
619 return -EINVAL;
620 }
621 return 0;
622}
623
624static ssize_t vsoc_read(struct file *filp, char __user *buffer, size_t len,
625 loff_t *poffset)
626{
627 __u32 area_off;
628 const void *area_p;
629 ssize_t area_len;
630 int retval = vsoc_validate_filep(filp);
631
632 if (retval)
633 return retval;
634 area_len = vsoc_get_area(filp, &area_off);
635 area_p = shm_off_to_virtual_addr(area_off);
636 area_p += *poffset;
637 area_len -= *poffset;
638 if (area_len <= 0)
639 return 0;
640 if (area_len < len)
641 len = area_len;
642 if (copy_to_user(buffer, area_p, len))
643 return -EFAULT;
644 *poffset += len;
645 return len;
646}
647
648static loff_t vsoc_lseek(struct file *filp, loff_t offset, int origin)
649{
650 ssize_t area_len = 0;
651 int retval = vsoc_validate_filep(filp);
652
653 if (retval)
654 return retval;
655 area_len = vsoc_get_area(filp, NULL);
656 switch (origin) {
657 case SEEK_SET:
658 break;
659
660 case SEEK_CUR:
661 if (offset > 0 && offset + filp->f_pos < 0)
662 return -EOVERFLOW;
663 offset += filp->f_pos;
664 break;
665
666 case SEEK_END:
667 if (offset > 0 && offset + area_len < 0)
668 return -EOVERFLOW;
669 offset += area_len;
670 break;
671
672 case SEEK_DATA:
673 if (offset >= area_len)
674 return -EINVAL;
675 if (offset < 0)
676 offset = 0;
677 break;
678
679 case SEEK_HOLE:
680 /* Next hole is always the end of the region, unless offset is
681 * beyond that
682 */
683 if (offset < area_len)
684 offset = area_len;
685 break;
686
687 default:
688 return -EINVAL;
689 }
690
691 if (offset < 0 || offset > area_len)
692 return -EINVAL;
693 filp->f_pos = offset;
694
695 return offset;
696}
697
698static ssize_t vsoc_write(struct file *filp, const char __user *buffer,
699 size_t len, loff_t *poffset)
700{
701 __u32 area_off;
702 void *area_p;
703 ssize_t area_len;
704 int retval = vsoc_validate_filep(filp);
705
706 if (retval)
707 return retval;
708 area_len = vsoc_get_area(filp, &area_off);
709 area_p = shm_off_to_virtual_addr(area_off);
710 area_p += *poffset;
711 area_len -= *poffset;
712 if (area_len <= 0)
713 return 0;
714 if (area_len < len)
715 len = area_len;
716 if (copy_from_user(area_p, buffer, len))
717 return -EFAULT;
718 *poffset += len;
719 return len;
720}
721
722static irqreturn_t vsoc_interrupt(int irq, void *region_data_v)
723{
724 struct vsoc_region_data *region_data =
725 (struct vsoc_region_data *)region_data_v;
726 int reg_num = region_data - vsoc_dev.regions_data;
727
728 if (unlikely(!region_data))
729 return IRQ_NONE;
730
731 if (unlikely(reg_num < 0 ||
732 reg_num >= vsoc_dev.layout->region_count)) {
733 dev_err(&vsoc_dev.dev->dev,
734 "invalid irq @%p reg_num=0x%04x\n",
735 region_data, reg_num);
736 return IRQ_NONE;
737 }
738 if (unlikely(vsoc_dev.regions_data + reg_num != region_data)) {
739 dev_err(&vsoc_dev.dev->dev,
740 "irq not aligned @%p reg_num=0x%04x\n",
741 region_data, reg_num);
742 return IRQ_NONE;
743 }
744 wake_up_interruptible(&region_data->interrupt_wait_queue);
745 return IRQ_HANDLED;
746}
747
748static int vsoc_probe_device(struct pci_dev *pdev,
749 const struct pci_device_id *ent)
750{
751 int result;
752 int i;
753 resource_size_t reg_size;
754 dev_t devt;
755
756 vsoc_dev.dev = pdev;
757 result = pci_enable_device(pdev);
758 if (result) {
759 dev_err(&pdev->dev,
760 "pci_enable_device failed %s: error %d\n",
761 pci_name(pdev), result);
762 return result;
763 }
764 vsoc_dev.enabled_device = true;
765 result = pci_request_regions(pdev, "vsoc");
766 if (result < 0) {
767 dev_err(&pdev->dev, "pci_request_regions failed\n");
768 vsoc_remove_device(pdev);
769 return -EBUSY;
770 }
771 vsoc_dev.requested_regions = true;
772 /* Set up the control registers in BAR 0 */
773 reg_size = pci_resource_len(pdev, REGISTER_BAR);
774 if (reg_size > MAX_REGISTER_BAR_LEN)
775 vsoc_dev.regs =
776 pci_iomap(pdev, REGISTER_BAR, MAX_REGISTER_BAR_LEN);
777 else
778 vsoc_dev.regs = pci_iomap(pdev, REGISTER_BAR, reg_size);
779
780 if (!vsoc_dev.regs) {
781 dev_err(&pdev->dev,
782 "cannot map registers of size %zu\n",
783 (size_t)reg_size);
784 vsoc_remove_device(pdev);
785 return -EBUSY;
786 }
787
788 /* Map the shared memory in BAR 2 */
789 vsoc_dev.shm_phys_start = pci_resource_start(pdev, SHARED_MEMORY_BAR);
790 vsoc_dev.shm_size = pci_resource_len(pdev, SHARED_MEMORY_BAR);
791
792 dev_info(&pdev->dev, "shared memory @ DMA %pa size=0x%zx\n",
793 &vsoc_dev.shm_phys_start, vsoc_dev.shm_size);
794 vsoc_dev.kernel_mapped_shm = pci_iomap_wc(pdev, SHARED_MEMORY_BAR, 0);
795 if (!vsoc_dev.kernel_mapped_shm) {
796 dev_err(&vsoc_dev.dev->dev, "cannot iomap region\n");
797 vsoc_remove_device(pdev);
798 return -EBUSY;
799 }
800
801 vsoc_dev.layout = (struct vsoc_shm_layout_descriptor __force *)
802 vsoc_dev.kernel_mapped_shm;
803 dev_info(&pdev->dev, "major_version: %d\n",
804 vsoc_dev.layout->major_version);
805 dev_info(&pdev->dev, "minor_version: %d\n",
806 vsoc_dev.layout->minor_version);
807 dev_info(&pdev->dev, "size: 0x%x\n", vsoc_dev.layout->size);
808 dev_info(&pdev->dev, "regions: %d\n", vsoc_dev.layout->region_count);
809 if (vsoc_dev.layout->major_version !=
810 CURRENT_VSOC_LAYOUT_MAJOR_VERSION) {
811 dev_err(&vsoc_dev.dev->dev,
812 "driver supports only major_version %d\n",
813 CURRENT_VSOC_LAYOUT_MAJOR_VERSION);
814 vsoc_remove_device(pdev);
815 return -EBUSY;
816 }
817 result = alloc_chrdev_region(&devt, 0, vsoc_dev.layout->region_count,
818 VSOC_DEV_NAME);
819 if (result) {
820 dev_err(&vsoc_dev.dev->dev, "alloc_chrdev_region failed\n");
821 vsoc_remove_device(pdev);
822 return -EBUSY;
823 }
824 vsoc_dev.major = MAJOR(devt);
825 cdev_init(&vsoc_dev.cdev, &vsoc_ops);
826 vsoc_dev.cdev.owner = THIS_MODULE;
827 result = cdev_add(&vsoc_dev.cdev, devt, vsoc_dev.layout->region_count);
828 if (result) {
829 dev_err(&vsoc_dev.dev->dev, "cdev_add error\n");
830 vsoc_remove_device(pdev);
831 return -EBUSY;
832 }
833 vsoc_dev.cdev_added = true;
834 vsoc_dev.class = class_create(THIS_MODULE, VSOC_DEV_NAME);
835 if (IS_ERR(vsoc_dev.class)) {
836 dev_err(&vsoc_dev.dev->dev, "class_create failed\n");
837 vsoc_remove_device(pdev);
838 return PTR_ERR(vsoc_dev.class);
839 }
840 vsoc_dev.class_added = true;
841 vsoc_dev.regions = (struct vsoc_device_region __force *)
842 ((void *)vsoc_dev.layout +
843 vsoc_dev.layout->vsoc_region_desc_offset);
844 vsoc_dev.msix_entries =
845 kcalloc(vsoc_dev.layout->region_count,
846 sizeof(vsoc_dev.msix_entries[0]), GFP_KERNEL);
847 if (!vsoc_dev.msix_entries) {
848 dev_err(&vsoc_dev.dev->dev,
849 "unable to allocate msix_entries\n");
850 vsoc_remove_device(pdev);
851 return -ENOSPC;
852 }
853 vsoc_dev.regions_data =
854 kcalloc(vsoc_dev.layout->region_count,
855 sizeof(vsoc_dev.regions_data[0]), GFP_KERNEL);
856 if (!vsoc_dev.regions_data) {
857 dev_err(&vsoc_dev.dev->dev,
858 "unable to allocate regions' data\n");
859 vsoc_remove_device(pdev);
860 return -ENOSPC;
861 }
862 for (i = 0; i < vsoc_dev.layout->region_count; ++i)
863 vsoc_dev.msix_entries[i].entry = i;
864
865 result = pci_enable_msix_exact(vsoc_dev.dev, vsoc_dev.msix_entries,
866 vsoc_dev.layout->region_count);
867 if (result) {
868 dev_info(&pdev->dev, "pci_enable_msix failed: %d\n", result);
869 vsoc_remove_device(pdev);
870 return -ENOSPC;
871 }
872 /* Check that all regions are well formed */
873 for (i = 0; i < vsoc_dev.layout->region_count; ++i) {
874 const struct vsoc_device_region *region = vsoc_dev.regions + i;
875
876 if (!PAGE_ALIGNED(region->region_begin_offset) ||
877 !PAGE_ALIGNED(region->region_end_offset)) {
878 dev_err(&vsoc_dev.dev->dev,
879 "region %d not aligned (%x:%x)", i,
880 region->region_begin_offset,
881 region->region_end_offset);
882 vsoc_remove_device(pdev);
883 return -EFAULT;
884 }
885 if (region->region_begin_offset >= region->region_end_offset ||
886 region->region_end_offset > vsoc_dev.shm_size) {
887 dev_err(&vsoc_dev.dev->dev,
888 "region %d offsets are wrong: %x %x %zx",
889 i, region->region_begin_offset,
890 region->region_end_offset, vsoc_dev.shm_size);
891 vsoc_remove_device(pdev);
892 return -EFAULT;
893 }
894 if (region->managed_by >= vsoc_dev.layout->region_count) {
895 dev_err(&vsoc_dev.dev->dev,
896 "region %d has invalid owner: %u",
897 i, region->managed_by);
898 vsoc_remove_device(pdev);
899 return -EFAULT;
900 }
901 }
902 vsoc_dev.msix_enabled = true;
903 for (i = 0; i < vsoc_dev.layout->region_count; ++i) {
904 const struct vsoc_device_region *region = vsoc_dev.regions + i;
905 size_t name_sz = sizeof(vsoc_dev.regions_data[i].name) - 1;
906 const struct vsoc_signal_table_layout *h_to_g_signal_table =
907 &region->host_to_guest_signal_table;
908 const struct vsoc_signal_table_layout *g_to_h_signal_table =
909 &region->guest_to_host_signal_table;
910
911 vsoc_dev.regions_data[i].name[name_sz] = '\0';
912 memcpy(vsoc_dev.regions_data[i].name, region->device_name,
913 name_sz);
914 dev_info(&pdev->dev, "region %d name=%s\n",
915 i, vsoc_dev.regions_data[i].name);
916 init_waitqueue_head
917 (&vsoc_dev.regions_data[i].interrupt_wait_queue);
918 init_waitqueue_head(&vsoc_dev.regions_data[i].futex_wait_queue);
919 vsoc_dev.regions_data[i].incoming_signalled =
920 shm_off_to_virtual_addr(region->region_begin_offset) +
921 h_to_g_signal_table->interrupt_signalled_offset;
922 vsoc_dev.regions_data[i].outgoing_signalled =
923 shm_off_to_virtual_addr(region->region_begin_offset) +
924 g_to_h_signal_table->interrupt_signalled_offset;
925 result = request_irq(vsoc_dev.msix_entries[i].vector,
926 vsoc_interrupt, 0,
927 vsoc_dev.regions_data[i].name,
928 vsoc_dev.regions_data + i);
929 if (result) {
930 dev_info(&pdev->dev,
931 "request_irq failed irq=%d vector=%d\n",
932 i, vsoc_dev.msix_entries[i].vector);
933 vsoc_remove_device(pdev);
934 return -ENOSPC;
935 }
936 vsoc_dev.regions_data[i].irq_requested = true;
937 if (!device_create(vsoc_dev.class, NULL,
938 MKDEV(vsoc_dev.major, i),
939 NULL, vsoc_dev.regions_data[i].name)) {
940 dev_err(&vsoc_dev.dev->dev, "device_create failed\n");
941 vsoc_remove_device(pdev);
942 return -EBUSY;
943 }
944 vsoc_dev.regions_data[i].device_created = true;
945 }
946 return 0;
947}
948
949/*
950 * This should undo all of the allocations in the probe function in reverse
951 * order.
952 *
953 * Notes:
954 *
955 * The device may have been partially initialized, so double check
956 * that the allocations happened.
957 *
958 * This function may be called multiple times, so mark resources as freed
959 * as they are deallocated.
960 */
961static void vsoc_remove_device(struct pci_dev *pdev)
962{
963 int i;
964 /*
965 * pdev is the first thing to be set on probe and the last thing
966 * to be cleared here. If it's NULL then there is no cleanup.
967 */
968 if (!pdev || !vsoc_dev.dev)
969 return;
970 dev_info(&pdev->dev, "remove_device\n");
971 if (vsoc_dev.regions_data) {
972 for (i = 0; i < vsoc_dev.layout->region_count; ++i) {
973 if (vsoc_dev.regions_data[i].device_created) {
974 device_destroy(vsoc_dev.class,
975 MKDEV(vsoc_dev.major, i));
976 vsoc_dev.regions_data[i].device_created = false;
977 }
978 if (vsoc_dev.regions_data[i].irq_requested)
979 free_irq(vsoc_dev.msix_entries[i].vector, NULL);
980 vsoc_dev.regions_data[i].irq_requested = false;
981 }
982 kfree(vsoc_dev.regions_data);
983 vsoc_dev.regions_data = NULL;
984 }
985 if (vsoc_dev.msix_enabled) {
986 pci_disable_msix(pdev);
987 vsoc_dev.msix_enabled = false;
988 }
989 kfree(vsoc_dev.msix_entries);
990 vsoc_dev.msix_entries = NULL;
991 vsoc_dev.regions = NULL;
992 if (vsoc_dev.class_added) {
993 class_destroy(vsoc_dev.class);
994 vsoc_dev.class_added = false;
995 }
996 if (vsoc_dev.cdev_added) {
997 cdev_del(&vsoc_dev.cdev);
998 vsoc_dev.cdev_added = false;
999 }
1000 if (vsoc_dev.major && vsoc_dev.layout) {
1001 unregister_chrdev_region(MKDEV(vsoc_dev.major, 0),
1002 vsoc_dev.layout->region_count);
1003 vsoc_dev.major = 0;
1004 }
1005 vsoc_dev.layout = NULL;
1006 if (vsoc_dev.kernel_mapped_shm) {
1007 pci_iounmap(pdev, vsoc_dev.kernel_mapped_shm);
1008 vsoc_dev.kernel_mapped_shm = NULL;
1009 }
1010 if (vsoc_dev.regs) {
1011 pci_iounmap(pdev, vsoc_dev.regs);
1012 vsoc_dev.regs = NULL;
1013 }
1014 if (vsoc_dev.requested_regions) {
1015 pci_release_regions(pdev);
1016 vsoc_dev.requested_regions = false;
1017 }
1018 if (vsoc_dev.enabled_device) {
1019 pci_disable_device(pdev);
1020 vsoc_dev.enabled_device = false;
1021 }
1022 /* Do this last: it indicates that the device is not initialized. */
1023 vsoc_dev.dev = NULL;
1024}
1025
1026static void __exit vsoc_cleanup_module(void)
1027{
1028 vsoc_remove_device(vsoc_dev.dev);
1029 pci_unregister_driver(&vsoc_pci_driver);
1030}
1031
1032static int __init vsoc_init_module(void)
1033{
1034 int err = -ENOMEM;
1035
1036 INIT_LIST_HEAD(&vsoc_dev.permissions);
1037 mutex_init(&vsoc_dev.mtx);
1038
1039 err = pci_register_driver(&vsoc_pci_driver);
1040 if (err < 0)
1041 return err;
1042 return 0;
1043}
1044
1045static int vsoc_open(struct inode *inode, struct file *filp)
1046{
1047 /* Can't use vsoc_validate_filep because filp is still incomplete */
1048 int ret = vsoc_validate_inode(inode);
1049
1050 if (ret)
1051 return ret;
1052 filp->private_data =
1053 kzalloc(sizeof(struct vsoc_private_data), GFP_KERNEL);
1054 if (!filp->private_data)
1055 return -ENOMEM;
1056 return 0;
1057}
1058
1059static int vsoc_release(struct inode *inode, struct file *filp)
1060{
1061 struct vsoc_private_data *private_data = NULL;
1062 struct fd_scoped_permission_node *node = NULL;
1063 struct vsoc_device_region *owner_region_p = NULL;
1064 int retval = vsoc_validate_filep(filp);
1065
1066 if (retval)
1067 return retval;
1068 private_data = (struct vsoc_private_data *)filp->private_data;
1069 if (!private_data)
1070 return 0;
1071
1072 node = private_data->fd_scoped_permission_node;
1073 if (node) {
1074 owner_region_p = vsoc_region_from_inode(inode);
1075 if (owner_region_p->managed_by != VSOC_REGION_WHOLE) {
1076 owner_region_p =
1077 &vsoc_dev.regions[owner_region_p->managed_by];
1078 }
1079 do_destroy_fd_scoped_permission_node(owner_region_p, node);
1080 private_data->fd_scoped_permission_node = NULL;
1081 }
1082 kfree(private_data);
1083 filp->private_data = NULL;
1084
1085 return 0;
1086}
1087
1088/*
1089 * Returns the device relative offset and length of the area specified by the
1090 * fd scoped permission. If there is no fd scoped permission set, a default
1091 * permission covering the entire region is assumed, unless the region is owned
1092 * by another one, in which case the default is a permission with zero size.
1093 */
1094static ssize_t vsoc_get_area(struct file *filp, __u32 *area_offset)
1095{
1096 __u32 off = 0;
1097 ssize_t length = 0;
1098 struct vsoc_device_region *region_p;
1099 struct fd_scoped_permission *perm;
1100
1101 region_p = vsoc_region_from_filep(filp);
1102 off = region_p->region_begin_offset;
1103 perm = &((struct vsoc_private_data *)filp->private_data)->
1104 fd_scoped_permission_node->permission;
1105 if (perm) {
1106 off += perm->begin_offset;
1107 length = perm->end_offset - perm->begin_offset;
1108 } else if (region_p->managed_by == VSOC_REGION_WHOLE) {
1109 /* No permission set and the regions is not owned by another,
1110 * default to full region access.
1111 */
1112 length = vsoc_device_region_size(region_p);
1113 } else {
1114 /* return zero length, access is denied. */
1115 length = 0;
1116 }
1117 if (area_offset)
1118 *area_offset = off;
1119 return length;
1120}
1121
1122static int vsoc_mmap(struct file *filp, struct vm_area_struct *vma)
1123{
1124 unsigned long len = vma->vm_end - vma->vm_start;
1125 __u32 area_off;
1126 phys_addr_t mem_off;
1127 ssize_t area_len;
1128 int retval = vsoc_validate_filep(filp);
1129
1130 if (retval)
1131 return retval;
1132 area_len = vsoc_get_area(filp, &area_off);
1133 /* Add the requested offset */
1134 area_off += (vma->vm_pgoff << PAGE_SHIFT);
1135 area_len -= (vma->vm_pgoff << PAGE_SHIFT);
1136 if (area_len < len)
1137 return -EINVAL;
1138 vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
1139 mem_off = shm_off_to_phys_addr(area_off);
1140 if (io_remap_pfn_range(vma, vma->vm_start, mem_off >> PAGE_SHIFT,
1141 len, vma->vm_page_prot))
1142 return -EAGAIN;
1143 return 0;
1144}
1145
1146module_init(vsoc_init_module);
1147module_exit(vsoc_cleanup_module);
1148
1149MODULE_LICENSE("GPL");
1150MODULE_AUTHOR("Greg Hartman <ghartman@google.com>");
1151MODULE_DESCRIPTION("VSoC interpretation of QEmu's ivshmem device");
1152MODULE_VERSION("1.0");
drivers/staging/board/armadillo800eva.c+1−9
@@ -1,3 +1,4 @@
1// SPDX-License-Identifier: GPL-2.0
1/*2/*
2 * Staging board support for Armadillo 800 eva.3 * Staging board support for Armadillo 800 eva.
3 * Enable not-yet-DT-capable devices here.4 * Enable not-yet-DT-capable devices here.
@@ -6,15 +7,6 @@ · 2 unmodified lines
6 *7 *
7 * Copyright (C) 2012 Renesas Solutions Corp.8 * Copyright (C) 2012 Renesas Solutions Corp.
8 * Copyright (C) 2012 Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>9 * Copyright (C) 2012 Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; version 2 of the License.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 */10 */
19 11
20#include <linux/dma-mapping.h>12#include <linux/dma-mapping.h>
drivers/staging/board/board.c+1−4
@@ -1,10 +1,7 @@
1// SPDX-License-Identifier: GPL-2.0
1/*2/*
2 * Copyright (C) 2014 Magnus Damm3 * Copyright (C) 2014 Magnus Damm
3 * Copyright (C) 2015 Glider bvba4 * Copyright (C) 2015 Glider bvba
4 *
5 * This file is subject to the terms and conditions of the GNU General Public
6 * License. See the file "COPYING" in the main directory of this archive
7 * for more details.
8 */5 */
9 6
10#define pr_fmt(fmt) "board_staging: " fmt7#define pr_fmt(fmt) "board_staging: " fmt
drivers/staging/comedi/comedi_compat32.c+6−6
@@ -34,7 +34,7 @@ · 33 unmodified lines
34struct comedi32_chaninfo_struct {34struct comedi32_chaninfo_struct {
35 unsigned int subdev;35 unsigned int subdev;
36 compat_uptr_t maxdata_list; /* 32-bit 'unsigned int *' */36 compat_uptr_t maxdata_list; /* 32-bit 'unsigned int *' */
37 compat_uptr_t flaglist; /* 32-bit 'unsigned int *' */37 compat_uptr_t flaglist; /* 32-bit 'unsigned int *' */
38 compat_uptr_t rangelist; /* 32-bit 'unsigned int *' */38 compat_uptr_t rangelist; /* 32-bit 'unsigned int *' */
39 unsigned int unused[4];39 unsigned int unused[4];
40};40};
@@ -57,16 +57,16 @@ struct comedi32_cmd_struct { · 16 unmodified lines
57 unsigned int scan_end_arg;57 unsigned int scan_end_arg;
58 unsigned int stop_src;58 unsigned int stop_src;
59 unsigned int stop_arg;59 unsigned int stop_arg;
60 compat_uptr_t chanlist; /* 32-bit 'unsigned int *' */60 compat_uptr_t chanlist; /* 32-bit 'unsigned int *' */
61 unsigned int chanlist_len;61 unsigned int chanlist_len;
62 compat_uptr_t data; /* 32-bit 'short *' */62 compat_uptr_t data; /* 32-bit 'short *' */
63 unsigned int data_len;63 unsigned int data_len;
64};64};
65 65
66struct comedi32_insn_struct {66struct comedi32_insn_struct {
67 unsigned int insn;67 unsigned int insn;
68 unsigned int n;68 unsigned int n;
69 compat_uptr_t data; /* 32-bit 'unsigned int *' */69 compat_uptr_t data; /* 32-bit 'unsigned int *' */
70 unsigned int subdev;70 unsigned int subdev;
71 unsigned int chanspec;71 unsigned int chanspec;
72 unsigned int unused[3];72 unsigned int unused[3];
@@ -74,7 +74,7 @@ struct comedi32_insn_struct { · 1 unmodified line
74 74
75struct comedi32_insnlist_struct {75struct comedi32_insnlist_struct {
76 unsigned int n_insns;76 unsigned int n_insns;
77 compat_uptr_t insns; /* 32-bit 'struct comedi_insn *' */77 compat_uptr_t insns; /* 32-bit 'struct comedi_insn *' */
78};78};
79 79
80/* Handle translated ioctl. */80/* Handle translated ioctl. */
@@ -194,7 +194,7 @@ static int get_compat_cmd(struct comedi_cmd __user *cmd, · 113 unmodified lines
194 err |= __put_user(temp.uint, &cmd->stop_arg);194 err |= __put_user(temp.uint, &cmd->stop_arg);
195 err |= __get_user(temp.uptr, &cmd32->chanlist);195 err |= __get_user(temp.uptr, &cmd32->chanlist);
196 err |= __put_user((unsigned int __force *)compat_ptr(temp.uptr),196 err |= __put_user((unsigned int __force *)compat_ptr(temp.uptr),
197 &cmd->chanlist);197 &cmd->chanlist);
198 err |= __get_user(temp.uint, &cmd32->chanlist_len);198 err |= __get_user(temp.uint, &cmd32->chanlist_len);
199 err |= __put_user(temp.uint, &cmd->chanlist_len);199 err |= __put_user(temp.uint, &cmd->chanlist_len);
200 err |= __get_user(temp.uptr, &cmd32->data);200 err |= __get_user(temp.uptr, &cmd32->data);
drivers/staging/comedi/comedi_usb.h+2−3
@@ -1,6 +1,5 @@
1// SPDX-License-Identifier: GPL-2.0+1/* SPDX-License-Identifier: GPL-2.0+ */
2/*2/* comedi_usb.h
3 * comedi_usb.h
4 * header file for USB Comedi drivers3 * header file for USB Comedi drivers
5 *4 *
6 * COMEDI - Linux Control and Measurement Device Interface5 * COMEDI - Linux Control and Measurement Device Interface
drivers/staging/comedi/comedidev.h+1−1
@@ -1,4 +1,4 @@
1// SPDX-License-Identifier: GPL-2.0+1/* SPDX-License-Identifier: GPL-2.0+ */
2/*2/*
3 * comedidev.h3 * comedidev.h
4 * header file for kernel-only structures, variables, and constants4 * header file for kernel-only structures, variables, and constants
drivers/staging/comedi/drivers/cb_pcidas64.c+3−3
@@ -2268,14 +2268,14 @@ static inline unsigned int dma_transfer_size(struct comedi_device *dev) · 2267 unmodified lines
2268}2268}
2269 2269
2270static u32 ai_convert_counter_6xxx(const struct comedi_device *dev,2270static u32 ai_convert_counter_6xxx(const struct comedi_device *dev,
2271 const struct comedi_cmd *cmd)2271 const struct comedi_cmd *cmd)
2272{2272{
2273 /* supposed to load counter with desired divisor minus 3 */2273 /* supposed to load counter with desired divisor minus 3 */
2274 return cmd->convert_arg / TIMER_BASE - 3;2274 return cmd->convert_arg / TIMER_BASE - 3;
2275}2275}
2276 2276
2277static u32 ai_scan_counter_6xxx(struct comedi_device *dev,2277static u32 ai_scan_counter_6xxx(struct comedi_device *dev,
2278 struct comedi_cmd *cmd)2278 struct comedi_cmd *cmd)
2279{2279{
2280 u32 count;2280 u32 count;
2281 2281
@@ -2296,7 +2296,7 @@ static u32 ai_scan_counter_6xxx(struct comedi_device *dev, · 14 unmodified lines
2296}2296}
2297 2297
2298static u32 ai_convert_counter_4020(struct comedi_device *dev,2298static u32 ai_convert_counter_4020(struct comedi_device *dev,
2299 struct comedi_cmd *cmd)2299 struct comedi_cmd *cmd)
2300{2300{
2301 struct pcidas64_private *devpriv = dev->private;2301 struct pcidas64_private *devpriv = dev->private;
2302 unsigned int divisor;2302 unsigned int divisor;
drivers/staging/emxx_udc/Kconfig+1−1
@@ -1,6 +1,6 @@
1config USB_EMXX1config USB_EMXX
2 tristate "EMXX USB Function Device Controller"2 tristate "EMXX USB Function Device Controller"
3 depends on USB_GADGET && (ARCH_SHMOBILE || (ARM && COMPILE_TEST))3 depends on USB_GADGET && (ARCH_RENESAS || (ARM && COMPILE_TEST))
4 help4 help
5 The Emma Mobile series of SoCs from Renesas Electronics and5 The Emma Mobile series of SoCs from Renesas Electronics and
6 former NEC Electronics include USB Function hardware.6 former NEC Electronics include USB Function hardware.
drivers/staging/emxx_udc/TODO+2−0
@@ -1,4 +1,6 @@
1* add clock framework support (platform device with CCF needs special care)1* add clock framework support (platform device with CCF needs special care)
2* break out board-specific VBUS GPIO to work with multiplatform2* break out board-specific VBUS GPIO to work with multiplatform
3* convert VBUS GPIO to use GPIO descriptors from <linux/gpio/consumer.h>
4 and stop using the old GPIO API
3* DT bindings5* DT bindings
4* move driver into drivers/usb/gadget/6* move driver into drivers/usb/gadget/
drivers/staging/fbtft/TODO+4−0
@@ -0,0 +1,4 @@
1* convert all uses of the old GPIO API from <linux/gpio.h> to the
2 GPIO descriptor API in <linux/gpio/consumer.h> and look up GPIO
3 lines from device tree, ACPI or board files, board files should
4 use <linux/gpio/machine.h>
drivers/staging/fbtft/fbtft-bus.c+9−4
@@ -22,10 +22,13 @@ void func(struct fbtft_par *par, int len, ...) \ · 21 unmodified lines
22 if (unlikely(par->debug & DEBUG_WRITE_REGISTER)) { \22 if (unlikely(par->debug & DEBUG_WRITE_REGISTER)) { \
23 va_start(args, len); \23 va_start(args, len); \
24 for (i = 0; i < len; i++) { \24 for (i = 0; i < len; i++) { \
25 buf[i] = modifier((data_type)va_arg(args, unsigned int)); \25 buf[i] = modifier((data_type)va_arg(args, \
26 unsigned int)); \
26 } \27 } \
27 va_end(args); \28 va_end(args); \
28 fbtft_par_dbg_hex(DEBUG_WRITE_REGISTER, par, par->info->device, buffer_type, buf, len, "%s: ", __func__); \29 fbtft_par_dbg_hex(DEBUG_WRITE_REGISTER, par, \
30 par->info->device, buffer_type, buf, len, \
31 "%s: ", __func__); \
29 } \32 } \
30 \33 \
31 va_start(args, len); \34 va_start(args, len); \
@@ -37,7 +40,8 @@ void func(struct fbtft_par *par, int len, ...) \ · 5 unmodified lines
37 } \40 } \
38 \41 \
39 *buf = modifier((data_type)va_arg(args, unsigned int)); \42 *buf = modifier((data_type)va_arg(args, unsigned int)); \
40 ret = fbtft_write_buf_dc(par, par->buf, sizeof(data_type) + offset, 0); \43 ret = fbtft_write_buf_dc(par, par->buf, sizeof(data_type) + offset, \
44 0); \
41 if (ret < 0) \45 if (ret < 0) \
42 goto out; \46 goto out; \
43 len--; \47 len--; \
@@ -48,7 +52,8 @@ void func(struct fbtft_par *par, int len, ...) \ · 4 unmodified lines
48 if (len) { \52 if (len) { \
49 i = len; \53 i = len; \
50 while (i--) \54 while (i--) \
51 *buf++ = modifier((data_type)va_arg(args, unsigned int)); \55 *buf++ = modifier((data_type)va_arg(args, \
56 unsigned int)); \
52 fbtft_write_buf_dc(par, par->buf, \57 fbtft_write_buf_dc(par, par->buf, \
53 len * (sizeof(data_type) + offset), 1); \58 len * (sizeof(data_type) + offset), 1); \
54 } \59 } \
drivers/staging/fsl-dpaa2/Kconfig+8−0
@@ -24,3 +24,11 @@ config FSL_DPAA2_ETHSW · 23 unmodified lines
24 ---help---24 ---help---
25 Driver for Freescale DPAA2 Ethernet Switch. Select25 Driver for Freescale DPAA2 Ethernet Switch. Select
26 BRIDGE to have support for bridge tools.26 BRIDGE to have support for bridge tools.
27
28config FSL_DPAA2_PTP_CLOCK
29 tristate "Freescale DPAA2 PTP Clock"
30 depends on FSL_DPAA2_ETH && POSIX_TIMERS
31 select PTP_1588_CLOCK
32 help
33 This driver adds support for using the DPAA2 1588 timer module
34 as a PTP clock.
drivers/staging/fsl-dpaa2/Makefile+3−2
@@ -2,5 +2,6 @@ · 1 unmodified line
2# Freescale DataPath Acceleration Architecture Gen2 (DPAA2) drivers2# Freescale DataPath Acceleration Architecture Gen2 (DPAA2) drivers
3#3#
4 4
5obj-$(CONFIG_FSL_DPAA2_ETH) += ethernet/5obj-$(CONFIG_FSL_DPAA2_ETH) += ethernet/
6obj-$(CONFIG_FSL_DPAA2_ETHSW) += ethsw/6obj-$(CONFIG_FSL_DPAA2_ETHSW) += ethsw/
7obj-$(CONFIG_FSL_DPAA2_PTP_CLOCK) += rtc/
drivers/staging/fsl-dpaa2/ethernet/dpaa2-eth.c+107−4
@@ -38,8 +38,11 @@ · 37 unmodified lines
38#include <linux/msi.h>38#include <linux/msi.h>
39#include <linux/kthread.h>39#include <linux/kthread.h>
40#include <linux/iommu.h>40#include <linux/iommu.h>
41 41#include <linux/net_tstamp.h>
42#include <linux/fsl/mc.h>42#include <linux/fsl/mc.h>
43
44#include <net/sock.h>
45
43#include "dpaa2-eth.h"46#include "dpaa2-eth.h"
44 47
45/* CREATE_TRACE_POINTS only needs to be defined once. Other dpa files48/* CREATE_TRACE_POINTS only needs to be defined once. Other dpa files
@@ -275,6 +278,18 @@ static void dpaa2_eth_rx(struct dpaa2_eth_priv *priv, · 229 unmodified lines
275 278
276 prefetch(skb->data);279 prefetch(skb->data);
277 280
281 /* Get the timestamp value */
282 if (priv->rx_tstamp) {
283 struct skb_shared_hwtstamps *shhwtstamps = skb_hwtstamps(skb);
284 __le64 *ts = dpaa2_get_ts(vaddr, false);
285 u64 ns;
286
287 memset(shhwtstamps, 0, sizeof(*shhwtstamps));
288
289 ns = DPAA2_PTP_CLK_PERIOD_NS * le64_to_cpup(ts);
290 shhwtstamps->hwtstamp = ns_to_ktime(ns);
291 }
292
278 /* Check if we need to validate the L4 csum */293 /* Check if we need to validate the L4 csum */
279 if (likely(dpaa2_fd_get_frc(fd) & DPAA2_FD_FRC_FASV)) {294 if (likely(dpaa2_fd_get_frc(fd) & DPAA2_FD_FRC_FASV)) {
280 status = le32_to_cpu(fas->status);295 status = le32_to_cpu(fas->status);
@@ -334,6 +349,28 @@ static int consume_frames(struct dpaa2_eth_channel *ch) · 53 unmodified lines
334 return cleaned;349 return cleaned;
335}350}
336 351
352/* Configure the egress frame annotation for timestamp update */
353static void enable_tx_tstamp(struct dpaa2_fd *fd, void *buf_start)
354{
355 struct dpaa2_faead *faead;
356 u32 ctrl, frc;
357
358 /* Mark the egress frame annotation area as valid */
359 frc = dpaa2_fd_get_frc(fd);
360 dpaa2_fd_set_frc(fd, frc | DPAA2_FD_FRC_FAEADV);
361
362 /* Set hardware annotation size */
363 ctrl = dpaa2_fd_get_ctrl(fd);
364 dpaa2_fd_set_ctrl(fd, ctrl | DPAA2_FD_CTRL_ASAL);
365
366 /* enable UPD (update prepanded data) bit in FAEAD field of
367 * hardware frame annotation area
368 */
369 ctrl = DPAA2_FAEAD_A2V | DPAA2_FAEAD_UPDV | DPAA2_FAEAD_UPD;
370 faead = dpaa2_get_faead(buf_start, true);
371 faead->ctrl = cpu_to_le32(ctrl);
372}
373
337/* Create a frame descriptor based on a fragmented skb */374/* Create a frame descriptor based on a fragmented skb */
338static int build_sg_fd(struct dpaa2_eth_priv *priv,375static int build_sg_fd(struct dpaa2_eth_priv *priv,
339 struct sk_buff *skb,376 struct sk_buff *skb,
@@ -420,6 +457,9 @@ static int build_sg_fd(struct dpaa2_eth_priv *priv, · 80 unmodified lines
420 dpaa2_fd_set_len(fd, skb->len);457 dpaa2_fd_set_len(fd, skb->len);
421 dpaa2_fd_set_ctrl(fd, DPAA2_FD_CTRL_PTA | DPAA2_FD_CTRL_PTV1);458 dpaa2_fd_set_ctrl(fd, DPAA2_FD_CTRL_PTA | DPAA2_FD_CTRL_PTV1);
422 459
460 if (priv->tx_tstamp && skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)
461 enable_tx_tstamp(fd, sgt_buf);
462
423 return 0;463 return 0;
424 464
425dma_map_single_failed:465dma_map_single_failed:
@@ -470,6 +510,9 @@ static int build_single_fd(struct dpaa2_eth_priv *priv, · 44 unmodified lines
470 dpaa2_fd_set_format(fd, dpaa2_fd_single);510 dpaa2_fd_set_format(fd, dpaa2_fd_single);
471 dpaa2_fd_set_ctrl(fd, DPAA2_FD_CTRL_PTA | DPAA2_FD_CTRL_PTV1);511 dpaa2_fd_set_ctrl(fd, DPAA2_FD_CTRL_PTA | DPAA2_FD_CTRL_PTV1);
472 512
513 if (priv->tx_tstamp && skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)
514 enable_tx_tstamp(fd, buffer_start);
515
473 return 0;516 return 0;
474}517}
475 518
@@ -520,6 +563,19 @@ static void free_tx_fd(const struct dpaa2_eth_priv *priv, · 44 unmodified lines
520 return;563 return;
521 }564 }
522 565
566 /* Get the timestamp value */
567 if (priv->tx_tstamp && skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP) {
568 struct skb_shared_hwtstamps shhwtstamps;
569 __le64 *ts = dpaa2_get_ts(skbh, true);
570 u64 ns;
571
572 memset(&shhwtstamps, 0, sizeof(shhwtstamps));
573
574 ns = DPAA2_PTP_CLK_PERIOD_NS * le64_to_cpup(ts);
575 shhwtstamps.hwtstamp = ns_to_ktime(ns);
576 skb_tstamp_tx(skb, &shhwtstamps);
577 }
578
523 /* Free SGT buffer allocated on tx */579 /* Free SGT buffer allocated on tx */
524 if (fd_format != dpaa2_fd_single)580 if (fd_format != dpaa2_fd_single)
525 skb_free_frag(skbh);581 skb_free_frag(skbh);
@@ -552,6 +608,10 @@ static netdev_tx_t dpaa2_eth_tx(struct sk_buff *skb, struct net_device *net_dev) · 26 unmodified lines
552 goto err_alloc_headroom;608 goto err_alloc_headroom;
553 }609 }
554 percpu_extras->tx_reallocs++;610 percpu_extras->tx_reallocs++;
611
612 if (skb->sk)
613 skb_set_owner_w(ns, skb->sk);
614
555 dev_kfree_skb(skb);615 dev_kfree_skb(skb);
556 skb = ns;616 skb = ns;
557 }617 }
@@ -1365,6 +1425,45 @@ static int dpaa2_eth_set_features(struct net_device *net_dev, · 807 unmodified lines
1365 return 0;1425 return 0;
1366}1426}
1367 1427
1428static int dpaa2_eth_ts_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
1429{
1430 struct dpaa2_eth_priv *priv = netdev_priv(dev);
1431 struct hwtstamp_config config;
1432
1433 if (copy_from_user(&config, rq->ifr_data, sizeof(config)))
1434 return -EFAULT;
1435
1436 switch (config.tx_type) {
1437 case HWTSTAMP_TX_OFF:
1438 priv->tx_tstamp = false;
1439 break;
1440 case HWTSTAMP_TX_ON:
1441 priv->tx_tstamp = true;
1442 break;
1443 default:
1444 return -ERANGE;
1445 }
1446
1447 if (config.rx_filter == HWTSTAMP_FILTER_NONE) {
1448 priv->rx_tstamp = false;
1449 } else {
1450 priv->rx_tstamp = true;
1451 /* TS is set for all frame types, not only those requested */
1452 config.rx_filter = HWTSTAMP_FILTER_ALL;
1453 }
1454
1455 return copy_to_user(rq->ifr_data, &config, sizeof(config)) ?
1456 -EFAULT : 0;
1457}
1458
1459static int dpaa2_eth_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
1460{
1461 if (cmd == SIOCSHWTSTAMP)
1462 return dpaa2_eth_ts_ioctl(dev, rq, cmd);
1463
1464 return -EINVAL;
1465}
1466
1368static const struct net_device_ops dpaa2_eth_ops = {1467static const struct net_device_ops dpaa2_eth_ops = {
1369 .ndo_open = dpaa2_eth_open,1468 .ndo_open = dpaa2_eth_open,
1370 .ndo_start_xmit = dpaa2_eth_tx,1469 .ndo_start_xmit = dpaa2_eth_tx,
@@ -1375,6 +1474,7 @@ static const struct net_device_ops dpaa2_eth_ops = { · 4 unmodified lines
1375 .ndo_change_mtu = dpaa2_eth_change_mtu,1474 .ndo_change_mtu = dpaa2_eth_change_mtu,
1376 .ndo_set_rx_mode = dpaa2_eth_set_rx_mode,1475 .ndo_set_rx_mode = dpaa2_eth_set_rx_mode,
1377 .ndo_set_features = dpaa2_eth_set_features,1476 .ndo_set_features = dpaa2_eth_set_features,
1477 .ndo_do_ioctl = dpaa2_eth_ioctl,
1378};1478};
1379 1479
1380static void cdan_cb(struct dpaa2_io_notification_ctx *ctx)1480static void cdan_cb(struct dpaa2_io_notification_ctx *ctx)
@@ -1770,7 +1870,9 @@ static int set_buffer_layout(struct dpaa2_eth_priv *priv) · 389 unmodified lines
1770 1870
1771 /* tx buffer */1871 /* tx buffer */
1772 buf_layout.private_data_size = DPAA2_ETH_SWA_SIZE;1872 buf_layout.private_data_size = DPAA2_ETH_SWA_SIZE;
1773 buf_layout.options = DPNI_BUF_LAYOUT_OPT_PRIVATE_DATA_SIZE;1873 buf_layout.pass_timestamp = true;
1874 buf_layout.options = DPNI_BUF_LAYOUT_OPT_PRIVATE_DATA_SIZE |
1875 DPNI_BUF_LAYOUT_OPT_TIMESTAMP;
1774 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,1876 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,
1775 DPNI_QUEUE_TX, &buf_layout);1877 DPNI_QUEUE_TX, &buf_layout);
1776 if (err) {1878 if (err) {
@@ -1779,7 +1881,7 @@ static int set_buffer_layout(struct dpaa2_eth_priv *priv) · 2 unmodified lines
1779 }1881 }
1780 1882
1781 /* tx-confirm buffer */1883 /* tx-confirm buffer */
1782 buf_layout.options = 0;1884 buf_layout.options = DPNI_BUF_LAYOUT_OPT_TIMESTAMP;
1783 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,1885 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,
1784 DPNI_QUEUE_TX_CONFIRM, &buf_layout);1886 DPNI_QUEUE_TX_CONFIRM, &buf_layout);
1785 if (err) {1887 if (err) {
@@ -1810,7 +1912,8 @@ static int set_buffer_layout(struct dpaa2_eth_priv *priv) · 24 unmodified lines
1810 buf_layout.options = DPNI_BUF_LAYOUT_OPT_PARSER_RESULT |1912 buf_layout.options = DPNI_BUF_LAYOUT_OPT_PARSER_RESULT |
1811 DPNI_BUF_LAYOUT_OPT_FRAME_STATUS |1913 DPNI_BUF_LAYOUT_OPT_FRAME_STATUS |
1812 DPNI_BUF_LAYOUT_OPT_DATA_ALIGN |1914 DPNI_BUF_LAYOUT_OPT_DATA_ALIGN |
1813 DPNI_BUF_LAYOUT_OPT_DATA_HEAD_ROOM;1915 DPNI_BUF_LAYOUT_OPT_DATA_HEAD_ROOM |
1916 DPNI_BUF_LAYOUT_OPT_TIMESTAMP;
1814 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,1917 err = dpni_set_buffer_layout(priv->mc_io, 0, priv->mc_token,
1815 DPNI_QUEUE_RX, &buf_layout);1918 DPNI_QUEUE_RX, &buf_layout);
1816 if (err) {1919 if (err) {
drivers/staging/fsl-dpaa2/ethernet/dpaa2-eth.h+47−2
@@ -88,8 +88,12 @@ · 87 unmodified lines
88#define DPAA2_ETH_SKB_SIZE \88#define DPAA2_ETH_SKB_SIZE \
89 (DPAA2_ETH_RX_BUF_SIZE + SKB_DATA_ALIGN(sizeof(struct skb_shared_info)))89 (DPAA2_ETH_RX_BUF_SIZE + SKB_DATA_ALIGN(sizeof(struct skb_shared_info)))
90 90
91/* Hardware annotation area in RX buffers */91/* Hardware annotation area in RX/TX buffers */
92#define DPAA2_ETH_RX_HWA_SIZE 6492#define DPAA2_ETH_RX_HWA_SIZE 64
93#define DPAA2_ETH_TX_HWA_SIZE 128
94
95/* PTP nominal frequency 1GHz */
96#define DPAA2_PTP_CLK_PERIOD_NS 1
93 97
94/* Due to a limitation in WRIOP 1.0.0, the RX buffer data must be aligned98/* Due to a limitation in WRIOP 1.0.0, the RX buffer data must be aligned
95 * to 256B. For newer revisions, the requirement is only for 64B alignment99 * to 256B. For newer revisions, the requirement is only for 64B alignment
@@ -135,6 +139,7 @@ struct dpaa2_eth_swa { · 39 unmodified lines
135/* Annotation bits in FD CTRL */139/* Annotation bits in FD CTRL */
136#define DPAA2_FD_CTRL_PTA 0x00800000140#define DPAA2_FD_CTRL_PTA 0x00800000
137#define DPAA2_FD_CTRL_PTV1 0x00400000141#define DPAA2_FD_CTRL_PTV1 0x00400000
142#define DPAA2_FD_CTRL_ASAL 0x00020000 /* ASAL = 128B */
138 143
139/* Frame annotation status */144/* Frame annotation status */
140struct dpaa2_fas {145struct dpaa2_fas {
@@ -150,6 +155,23 @@ struct dpaa2_fas { · 9 unmodified lines
150#define DPAA2_FAS_OFFSET 0155#define DPAA2_FAS_OFFSET 0
151#define DPAA2_FAS_SIZE (sizeof(struct dpaa2_fas))156#define DPAA2_FAS_SIZE (sizeof(struct dpaa2_fas))
152 157
158/* Timestamp is located in the next 8 bytes of the buffer's
159 * hardware annotation area
160 */
161#define DPAA2_TS_OFFSET 0x8
162
163/* Frame annotation egress action descriptor */
164#define DPAA2_FAEAD_OFFSET 0x58
165
166struct dpaa2_faead {
167 __le32 conf_fqid;
168 __le32 ctrl;
169};
170
171#define DPAA2_FAEAD_A2V 0x20000000
172#define DPAA2_FAEAD_UPDV 0x00001000
173#define DPAA2_FAEAD_UPD 0x00000010
174
153/* Accessors for the hardware annotation fields that we use */175/* Accessors for the hardware annotation fields that we use */
154static inline void *dpaa2_get_hwa(void *buf_addr, bool swa)176static inline void *dpaa2_get_hwa(void *buf_addr, bool swa)
155{177{
@@ -161,6 +183,16 @@ static inline struct dpaa2_fas *dpaa2_get_fas(void *buf_addr, bool swa) · 5 unmodified lines
161 return dpaa2_get_hwa(buf_addr, swa) + DPAA2_FAS_OFFSET;183 return dpaa2_get_hwa(buf_addr, swa) + DPAA2_FAS_OFFSET;
162}184}
163 185
186static inline __le64 *dpaa2_get_ts(void *buf_addr, bool swa)
187{
188 return dpaa2_get_hwa(buf_addr, swa) + DPAA2_TS_OFFSET;
189}
190
191static inline struct dpaa2_faead *dpaa2_get_faead(void *buf_addr, bool swa)
192{
193 return dpaa2_get_hwa(buf_addr, swa) + DPAA2_FAEAD_OFFSET;
194}
195
164/* Error and status bits in the frame annotation status word */196/* Error and status bits in the frame annotation status word */
165/* Debug frame, otherwise supposed to be discarded */197/* Debug frame, otherwise supposed to be discarded */
166#define DPAA2_FAS_DISC 0x80000000198#define DPAA2_FAS_DISC 0x80000000
@@ -319,6 +351,9 @@ struct dpaa2_eth_priv { · 152 unmodified lines
319 u16 bpid;351 u16 bpid;
320 struct iommu_domain *iommu_domain;352 struct iommu_domain *iommu_domain;
321 353
354 bool tx_tstamp; /* Tx timestamping enabled */
355 bool rx_tstamp; /* Rx timestamping enabled */
356
322 u16 tx_qdid;357 u16 tx_qdid;
323 u16 rx_buf_align;358 u16 rx_buf_align;
324 struct fsl_mc_io *mc_io;359 struct fsl_mc_io *mc_io;
@@ -355,6 +390,7 @@ struct dpaa2_eth_priv { · 30 unmodified lines
355 390
356extern const struct ethtool_ops dpaa2_ethtool_ops;391extern const struct ethtool_ops dpaa2_ethtool_ops;
357extern const char dpaa2_eth_drv_version[];392extern const char dpaa2_eth_drv_version[];
393extern int dpaa2_phc_index;
358 394
359static inline int dpaa2_eth_cmp_dpni_ver(struct dpaa2_eth_priv *priv,395static inline int dpaa2_eth_cmp_dpni_ver(struct dpaa2_eth_priv *priv,
360 u16 ver_major, u16 ver_minor)396 u16 ver_major, u16 ver_minor)
@@ -377,10 +413,19 @@ static inline · 16 unmodified lines
377unsigned int dpaa2_eth_needed_headroom(struct dpaa2_eth_priv *priv,413unsigned int dpaa2_eth_needed_headroom(struct dpaa2_eth_priv *priv,
378 struct sk_buff *skb)414 struct sk_buff *skb)
379{415{
416 unsigned int headroom = DPAA2_ETH_SWA_SIZE;
417
418 /* For non-linear skbs we have no headroom requirement, as we build a
419 * SG frame with a newly allocated SGT buffer
420 */
380 if (skb_is_nonlinear(skb))421 if (skb_is_nonlinear(skb))
381 return 0;422 return 0;
382 423
383 return DPAA2_ETH_SWA_SIZE;424 /* If we have Tx timestamping, need 128B hardware annotation */
425 if (priv->tx_tstamp && skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)
426 headroom += DPAA2_ETH_TX_HWA_SIZE;
427
428 return headroom;
384}429}
385 430
386/* Extra headroom space requested to hardware, in order to make sure there's431/* Extra headroom space requested to hardware, in order to make sure there's
drivers/staging/fsl-dpaa2/ethernet/dpaa2-ethtool.c+23−0
@@ -30,6 +30,8 @@ · 29 unmodified lines
30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 */31 */
32 32
33#include <linux/net_tstamp.h>
34
33#include "dpni.h" /* DPNI_LINK_OPT_* */35#include "dpni.h" /* DPNI_LINK_OPT_* */
34#include "dpaa2-eth.h"36#include "dpaa2-eth.h"
35 37
@@ -274,6 +276,26 @@ static int dpaa2_eth_get_rxnfc(struct net_device *net_dev, · 238 unmodified lines
274 return 0;276 return 0;
275}277}
276 278
279int dpaa2_phc_index = -1;
280EXPORT_SYMBOL(dpaa2_phc_index);
281
282static int dpaa2_eth_get_ts_info(struct net_device *dev,
283 struct ethtool_ts_info *info)
284{
285 info->so_timestamping = SOF_TIMESTAMPING_TX_HARDWARE |
286 SOF_TIMESTAMPING_RX_HARDWARE |
287 SOF_TIMESTAMPING_RAW_HARDWARE;
288
289 info->phc_index = dpaa2_phc_index;
290
291 info->tx_types = (1 << HWTSTAMP_TX_OFF) |
292 (1 << HWTSTAMP_TX_ON);
293
294 info->rx_filters = (1 << HWTSTAMP_FILTER_NONE) |
295 (1 << HWTSTAMP_FILTER_ALL);
296 return 0;
297}
298
277const struct ethtool_ops dpaa2_ethtool_ops = {299const struct ethtool_ops dpaa2_ethtool_ops = {
278 .get_drvinfo = dpaa2_eth_get_drvinfo,300 .get_drvinfo = dpaa2_eth_get_drvinfo,
279 .get_link = ethtool_op_get_link,301 .get_link = ethtool_op_get_link,
@@ -283,4 +305,5 @@ const struct ethtool_ops dpaa2_ethtool_ops = { · 3 unmodified lines
283 .get_ethtool_stats = dpaa2_eth_get_ethtool_stats,305 .get_ethtool_stats = dpaa2_eth_get_ethtool_stats,
284 .get_strings = dpaa2_eth_get_strings,306 .get_strings = dpaa2_eth_get_strings,
285 .get_rxnfc = dpaa2_eth_get_rxnfc,307 .get_rxnfc = dpaa2_eth_get_rxnfc,
308 .get_ts_info = dpaa2_eth_get_ts_info,
286};309};
drivers/staging/fsl-dpaa2/ethsw/dpsw-cmd.h+13−0
@@ -49,6 +49,8 @@ · 48 unmodified lines
49#define DPSW_CMDID_IF_SET_FLOODING DPSW_CMD_ID(0x047)49#define DPSW_CMDID_IF_SET_FLOODING DPSW_CMD_ID(0x047)
50#define DPSW_CMDID_IF_SET_BROADCAST DPSW_CMD_ID(0x048)50#define DPSW_CMDID_IF_SET_BROADCAST DPSW_CMD_ID(0x048)
51 51
52#define DPSW_CMDID_IF_GET_TCI DPSW_CMD_ID(0x04A)
53
52#define DPSW_CMDID_IF_SET_LINK_CFG DPSW_CMD_ID(0x04C)54#define DPSW_CMDID_IF_SET_LINK_CFG DPSW_CMD_ID(0x04C)
53 55
54#define DPSW_CMDID_VLAN_ADD DPSW_CMD_ID(0x060)56#define DPSW_CMDID_VLAN_ADD DPSW_CMD_ID(0x060)
@@ -206,6 +208,17 @@ struct dpsw_cmd_if_set_tci { · 151 unmodified lines
206 __le16 conf;208 __le16 conf;
207};209};
208 210
211struct dpsw_cmd_if_get_tci {
212 __le16 if_id;
213};
214
215struct dpsw_rsp_if_get_tci {
216 __le16 pad;
217 __le16 vlan_id;
218 u8 dei;
219 u8 pcp;
220};
221
209#define DPSW_STATE_SHIFT 0222#define DPSW_STATE_SHIFT 0
210#define DPSW_STATE_SIZE 4223#define DPSW_STATE_SIZE 4
211 224
drivers/staging/fsl-dpaa2/ethsw/dpsw.c+42−0
@@ -528,6 +528,48 @@ int dpsw_if_set_tci(struct fsl_mc_io *mc_io, · 527 unmodified lines
528 return mc_send_command(mc_io, &cmd);528 return mc_send_command(mc_io, &cmd);
529}529}
530 530
531/**
532 * dpsw_if_get_tci() - Get default VLAN Tag Control Information (TCI)
533 * @mc_io: Pointer to MC portal's I/O object
534 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
535 * @token: Token of DPSW object
536 * @if_id: Interface Identifier
537 * @cfg: Tag Control Information Configuration
538 *
539 * Return: Completion status. '0' on Success; Error code otherwise.
540 */
541int dpsw_if_get_tci(struct fsl_mc_io *mc_io,
542 u32 cmd_flags,
543 u16 token,
544 u16 if_id,
545 struct dpsw_tci_cfg *cfg)
546{
547 struct fsl_mc_command cmd = { 0 };
548 struct dpsw_cmd_if_get_tci *cmd_params;
549 struct dpsw_rsp_if_get_tci *rsp_params;
550 int err;
551
552 /* prepare command */
553 cmd.header = mc_encode_cmd_header(DPSW_CMDID_IF_GET_TCI,
554 cmd_flags,
555 token);
556 cmd_params = (struct dpsw_cmd_if_get_tci *)cmd.params;
557 cmd_params->if_id = cpu_to_le16(if_id);
558
559 /* send command to mc*/
560 err = mc_send_command(mc_io, &cmd);
561 if (err)
562 return err;
563
564 /* retrieve response parameters */
565 rsp_params = (struct dpsw_rsp_if_get_tci *)cmd.params;
566 cfg->pcp = rsp_params->pcp;
567 cfg->dei = rsp_params->dei;
568 cfg->vlan_id = le16_to_cpu(rsp_params->vlan_id);
569
570 return 0;
571}
572
531/**573/**
532 * dpsw_if_set_stp() - Function sets Spanning Tree Protocol (STP) state.574 * dpsw_if_set_stp() - Function sets Spanning Tree Protocol (STP) state.
533 * @mc_io: Pointer to MC portal's I/O object575 * @mc_io: Pointer to MC portal's I/O object
drivers/staging/fsl-dpaa2/ethsw/dpsw.h+6−0
@@ -306,6 +306,12 @@ int dpsw_if_set_tci(struct fsl_mc_io *mc_io, · 305 unmodified lines
306 u16 if_id,306 u16 if_id,
307 const struct dpsw_tci_cfg *cfg);307 const struct dpsw_tci_cfg *cfg);
308 308
309int dpsw_if_get_tci(struct fsl_mc_io *mc_io,
310 u32 cmd_flags,
311 u16 token,
312 u16 if_id,
313 struct dpsw_tci_cfg *cfg);
314
309/**315/**
310 * enum dpsw_stp_state - Spanning Tree Protocol (STP) states316 * enum dpsw_stp_state - Spanning Tree Protocol (STP) states
311 * @DPSW_STP_STATE_BLOCKING: Blocking state317 * @DPSW_STP_STATE_BLOCKING: Blocking state
drivers/staging/fsl-dpaa2/ethsw/ethsw.c+18−21
@@ -50,14 +50,23 @@ static int ethsw_add_vlan(struct ethsw_core *ethsw, u16 vid) · 49 unmodified lines
50 return 0;50 return 0;
51}51}
52 52
53static int ethsw_port_set_tci(struct ethsw_port_priv *port_priv,53static int ethsw_port_set_pvid(struct ethsw_port_priv *port_priv, u16 pvid)
54 struct dpsw_tci_cfg *tci_cfg)
55{54{
56 struct ethsw_core *ethsw = port_priv->ethsw_data;55 struct ethsw_core *ethsw = port_priv->ethsw_data;
57 struct net_device *netdev = port_priv->netdev;56 struct net_device *netdev = port_priv->netdev;
57 struct dpsw_tci_cfg tci_cfg = { 0 };
58 bool is_oper;58 bool is_oper;
59 int err, ret;59 int err, ret;
60 60
61 err = dpsw_if_get_tci(ethsw->mc_io, 0, ethsw->dpsw_handle,
62 port_priv->idx, &tci_cfg);
63 if (err) {
64 netdev_err(netdev, "dpsw_if_get_tci err %d\n", err);
65 return err;
66 }
67
68 tci_cfg.vlan_id = pvid;
69
61 /* Interface needs to be down to change PVID */70 /* Interface needs to be down to change PVID */
62 is_oper = netif_oper_up(netdev);71 is_oper = netif_oper_up(netdev);
63 if (is_oper) {72 if (is_oper) {
@@ -71,17 +80,16 @@ static int ethsw_port_set_tci(struct ethsw_port_priv *port_priv, · 7 unmodified lines
71 }80 }
72 81
73 err = dpsw_if_set_tci(ethsw->mc_io, 0, ethsw->dpsw_handle,82 err = dpsw_if_set_tci(ethsw->mc_io, 0, ethsw->dpsw_handle,
74 port_priv->idx, tci_cfg);83 port_priv->idx, &tci_cfg);
75 if (err) {84 if (err) {
76 netdev_err(netdev, "dpsw_if_set_tci err %d\n", err);85 netdev_err(netdev, "dpsw_if_set_tci err %d\n", err);
77 goto set_tci_error;86 goto set_tci_error;
78 }87 }
79 88
80 /* Delete previous PVID info and mark the new one */89 /* Delete previous PVID info and mark the new one */
81 if (port_priv->pvid)90 port_priv->vlans[port_priv->pvid] &= ~ETHSW_VLAN_PVID;
82 port_priv->vlans[port_priv->pvid] &= ~ETHSW_VLAN_PVID;91 port_priv->vlans[pvid] |= ETHSW_VLAN_PVID;
83 port_priv->vlans[tci_cfg->vlan_id] |= ETHSW_VLAN_PVID;92 port_priv->pvid = pvid;
84 port_priv->pvid = tci_cfg->vlan_id;
85 93
86set_tci_error:94set_tci_error:
87 if (is_oper) {95 if (is_oper) {
@@ -133,13 +141,7 @@ static int ethsw_port_add_vlan(struct ethsw_port_priv *port_priv, · 45 unmodified lines
133 }141 }
134 142
135 if (flags & BRIDGE_VLAN_INFO_PVID) {143 if (flags & BRIDGE_VLAN_INFO_PVID) {
136 struct dpsw_tci_cfg tci_cfg = {144 err = ethsw_port_set_pvid(port_priv, vid);
137 .pcp = 0,
138 .dei = 0,
139 .vlan_id = vid,
140 };
141
142 err = ethsw_port_set_tci(port_priv, &tci_cfg);
143 if (err)145 if (err)
144 return err;146 return err;
145 }147 }
@@ -616,10 +618,8 @@ static void ethsw_teardown_irqs(struct fsl_mc_device *sw_dev) · 470 unmodified lines
616{618{
617 struct device *dev = &sw_dev->dev;619 struct device *dev = &sw_dev->dev;
618 struct ethsw_core *ethsw = dev_get_drvdata(dev);620 struct ethsw_core *ethsw = dev_get_drvdata(dev);
619 struct fsl_mc_device_irq *irq;
620 int err;621 int err;
621 622
622 irq = sw_dev->irqs[DPSW_IRQ_INDEX_IF];
623 err = dpsw_set_irq_enable(ethsw->mc_io, 0, ethsw->dpsw_handle,623 err = dpsw_set_irq_enable(ethsw->mc_io, 0, ethsw->dpsw_handle,
624 DPSW_IRQ_INDEX_IF, 0);624 DPSW_IRQ_INDEX_IF, 0);
625 if (err)625 if (err)
@@ -822,9 +822,7 @@ static int ethsw_port_del_vlan(struct ethsw_port_priv *port_priv, u16 vid) · 196 unmodified lines
822 return -ENOENT;822 return -ENOENT;
823 823
824 if (port_priv->vlans[vid] & ETHSW_VLAN_PVID) {824 if (port_priv->vlans[vid] & ETHSW_VLAN_PVID) {
825 struct dpsw_tci_cfg tci_cfg = { 0 };825 err = ethsw_port_set_pvid(port_priv, 0);
826
827 err = ethsw_port_set_tci(port_priv, &tci_cfg);
828 if (err)826 if (err)
829 return err;827 return err;
830 }828 }
@@ -1260,7 +1258,6 @@ static int ethsw_port_init(struct ethsw_port_priv *port_priv, u16 port) · 429 unmodified lines
1260 const char def_mcast[ETH_ALEN] = {0x01, 0x00, 0x5e, 0x00, 0x00, 0x01};1258 const char def_mcast[ETH_ALEN] = {0x01, 0x00, 0x5e, 0x00, 0x00, 0x01};
1261 struct net_device *netdev = port_priv->netdev;1259 struct net_device *netdev = port_priv->netdev;
1262 struct ethsw_core *ethsw = port_priv->ethsw_data;1260 struct ethsw_core *ethsw = port_priv->ethsw_data;
1263 struct dpsw_tci_cfg tci_cfg = {0};
1264 struct dpsw_vlan_if_cfg vcfg;1261 struct dpsw_vlan_if_cfg vcfg;
1265 int err;1262 int err;
1266 1263
@@ -1278,7 +1275,7 @@ static int ethsw_port_init(struct ethsw_port_priv *port_priv, u16 port) · 11 unmodified lines
1278 return err;1275 return err;
1279 }1276 }
1280 1277
1281 err = ethsw_port_set_tci(port_priv, &tci_cfg);1278 err = ethsw_port_set_pvid(port_priv, 0);
1282 if (err)1279 if (err)
1283 return err;1280 return err;
1284 1281
drivers/staging/fsl-dpaa2/rtc/Makefile+7−0
@@ -0,0 +1,7 @@
1#
2# Makefile for the Freescale DPAA2 PTP clock
3#
4
5obj-$(CONFIG_FSL_DPAA2_PTP_CLOCK) += dpaa2-rtc.o
6
7dpaa2-rtc-objs := rtc.o dprtc.o
drivers/staging/fsl-dpaa2/rtc/dprtc-cmd.h+137−0
@@ -0,0 +1,137 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright 2013-2016 Freescale Semiconductor Inc.
4 * Copyright 2016-2018 NXP
5 */
6
7#ifndef _FSL_DPRTC_CMD_H
8#define _FSL_DPRTC_CMD_H
9
10/* DPRTC Version */
11#define DPRTC_VER_MAJOR 2
12#define DPRTC_VER_MINOR 0
13
14/* Command versioning */
15#define DPRTC_CMD_BASE_VERSION 1
16#define DPRTC_CMD_ID_OFFSET 4
17
18#define DPRTC_CMD(id) (((id) << DPRTC_CMD_ID_OFFSET) | DPRTC_CMD_BASE_VERSION)
19
20/* Command IDs */
21#define DPRTC_CMDID_CLOSE DPRTC_CMD(0x800)
22#define DPRTC_CMDID_OPEN DPRTC_CMD(0x810)
23#define DPRTC_CMDID_CREATE DPRTC_CMD(0x910)
24#define DPRTC_CMDID_DESTROY DPRTC_CMD(0x990)
25#define DPRTC_CMDID_GET_API_VERSION DPRTC_CMD(0xa10)
26
27#define DPRTC_CMDID_ENABLE DPRTC_CMD(0x002)
28#define DPRTC_CMDID_DISABLE DPRTC_CMD(0x003)
29#define DPRTC_CMDID_GET_ATTR DPRTC_CMD(0x004)
30#define DPRTC_CMDID_RESET DPRTC_CMD(0x005)
31#define DPRTC_CMDID_IS_ENABLED DPRTC_CMD(0x006)
32
33#define DPRTC_CMDID_SET_IRQ_ENABLE DPRTC_CMD(0x012)
34#define DPRTC_CMDID_GET_IRQ_ENABLE DPRTC_CMD(0x013)
35#define DPRTC_CMDID_SET_IRQ_MASK DPRTC_CMD(0x014)
36#define DPRTC_CMDID_GET_IRQ_MASK DPRTC_CMD(0x015)
37#define DPRTC_CMDID_GET_IRQ_STATUS DPRTC_CMD(0x016)
38#define DPRTC_CMDID_CLEAR_IRQ_STATUS DPRTC_CMD(0x017)
39
40#define DPRTC_CMDID_SET_CLOCK_OFFSET DPRTC_CMD(0x1d0)
41#define DPRTC_CMDID_SET_FREQ_COMPENSATION DPRTC_CMD(0x1d1)
42#define DPRTC_CMDID_GET_FREQ_COMPENSATION DPRTC_CMD(0x1d2)
43#define DPRTC_CMDID_GET_TIME DPRTC_CMD(0x1d3)
44#define DPRTC_CMDID_SET_TIME DPRTC_CMD(0x1d4)
45#define DPRTC_CMDID_SET_ALARM DPRTC_CMD(0x1d5)
46#define DPRTC_CMDID_SET_PERIODIC_PULSE DPRTC_CMD(0x1d6)
47#define DPRTC_CMDID_CLEAR_PERIODIC_PULSE DPRTC_CMD(0x1d7)
48#define DPRTC_CMDID_SET_EXT_TRIGGER DPRTC_CMD(0x1d8)
49#define DPRTC_CMDID_CLEAR_EXT_TRIGGER DPRTC_CMD(0x1d9)
50#define DPRTC_CMDID_GET_EXT_TRIGGER_TIMESTAMP DPRTC_CMD(0x1dA)
51
52/* Macros for accessing command fields smaller than 1byte */
53#define DPRTC_MASK(field) \
54 GENMASK(DPRTC_##field##_SHIFT + DPRTC_##field##_SIZE - 1, \
55 DPRTC_##field##_SHIFT)
56#define dprtc_get_field(var, field) \
57 (((var) & DPRTC_MASK(field)) >> DPRTC_##field##_SHIFT)
58
59#pragma pack(push, 1)
60struct dprtc_cmd_open {
61 __le32 dprtc_id;
62};
63
64struct dprtc_cmd_destroy {
65 __le32 object_id;
66};
67
68#define DPRTC_ENABLE_SHIFT 0
69#define DPRTC_ENABLE_SIZE 1
70
71struct dprtc_rsp_is_enabled {
72 u8 en;
73};
74
75struct dprtc_cmd_get_irq {
76 __le32 pad;
77 u8 irq_index;
78};
79
80struct dprtc_cmd_set_irq_enable {
81 u8 en;
82 u8 pad[3];
83 u8 irq_index;
84};
85
86struct dprtc_rsp_get_irq_enable {
87 u8 en;
88};
89
90struct dprtc_cmd_set_irq_mask {
91 __le32 mask;
92 u8 irq_index;
93};
94
95struct dprtc_rsp_get_irq_mask {
96 __le32 mask;
97};
98
99struct dprtc_cmd_get_irq_status {
100 __le32 status;
101 u8 irq_index;
102};
103
104struct dprtc_rsp_get_irq_status {
105 __le32 status;
106};
107
108struct dprtc_cmd_clear_irq_status {
109 __le32 status;
110 u8 irq_index;
111};
112
113struct dprtc_rsp_get_attributes {
114 __le32 pad;
115 __le32 id;
116};
117
118struct dprtc_cmd_set_clock_offset {
119 __le64 offset;
120};
121
122struct dprtc_get_freq_compensation {
123 __le32 freq_compensation;
124};
125
126struct dprtc_time {
127 __le64 time;
128};
129
130struct dprtc_rsp_get_api_version {
131 __le16 major;
132 __le16 minor;
133};
134
135#pragma pack(pop)
136
137#endif /* _FSL_DPRTC_CMD_H */
drivers/staging/fsl-dpaa2/rtc/dprtc.c+701−0
@@ -0,0 +1,701 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright 2013-2016 Freescale Semiconductor Inc.
4 * Copyright 2016-2018 NXP
5 */
6
7#include <linux/fsl/mc.h>
8
9#include "dprtc.h"
10#include "dprtc-cmd.h"
11
12/**
13 * dprtc_open() - Open a control session for the specified object.
14 * @mc_io: Pointer to MC portal's I/O object
15 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
16 * @dprtc_id: DPRTC unique ID
17 * @token: Returned token; use in subsequent API calls
18 *
19 * This function can be used to open a control session for an
20 * already created object; an object may have been declared in
21 * the DPL or by calling the dprtc_create function.
22 * This function returns a unique authentication token,
23 * associated with the specific object ID and the specific MC
24 * portal; this token must be used in all subsequent commands for
25 * this specific object
26 *
27 * Return: '0' on Success; Error code otherwise.
28 */
29int dprtc_open(struct fsl_mc_io *mc_io,
30 u32 cmd_flags,
31 int dprtc_id,
32 u16 *token)
33{
34 struct dprtc_cmd_open *cmd_params;
35 struct fsl_mc_command cmd = { 0 };
36 int err;
37
38 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_OPEN,
39 cmd_flags,
40 0);
41 cmd_params = (struct dprtc_cmd_open *)cmd.params;
42 cmd_params->dprtc_id = cpu_to_le32(dprtc_id);
43
44 err = mc_send_command(mc_io, &cmd);
45 if (err)
46 return err;
47
48 *token = mc_cmd_hdr_read_token(&cmd);
49
50 return 0;
51}
52
53/**
54 * dprtc_close() - Close the control session of the object
55 * @mc_io: Pointer to MC portal's I/O object
56 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
57 * @token: Token of DPRTC object
58 *
59 * After this function is called, no further operations are
60 * allowed on the object without opening a new control session.
61 *
62 * Return: '0' on Success; Error code otherwise.
63 */
64int dprtc_close(struct fsl_mc_io *mc_io,
65 u32 cmd_flags,
66 u16 token)
67{
68 struct fsl_mc_command cmd = { 0 };
69
70 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_CLOSE, cmd_flags,
71 token);
72
73 return mc_send_command(mc_io, &cmd);
74}
75
76/**
77 * dprtc_create() - Create the DPRTC object.
78 * @mc_io: Pointer to MC portal's I/O object
79 * @dprc_token: Parent container token; '0' for default container
80 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
81 * @cfg: Configuration structure
82 * @obj_id: Returned object id
83 *
84 * Create the DPRTC object, allocate required resources and
85 * perform required initialization.
86 *
87 * The function accepts an authentication token of a parent
88 * container that this object should be assigned to. The token
89 * can be '0' so the object will be assigned to the default container.
90 * The newly created object can be opened with the returned
91 * object id and using the container's associated tokens and MC portals.
92 *
93 * Return: '0' on Success; Error code otherwise.
94 */
95int dprtc_create(struct fsl_mc_io *mc_io,
96 u16 dprc_token,
97 u32 cmd_flags,
98 const struct dprtc_cfg *cfg,
99 u32 *obj_id)
100{
101 struct fsl_mc_command cmd = { 0 };
102 int err;
103
104 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_CREATE,
105 cmd_flags,
106 dprc_token);
107
108 err = mc_send_command(mc_io, &cmd);
109 if (err)
110 return err;
111
112 *obj_id = mc_cmd_read_object_id(&cmd);
113
114 return 0;
115}
116
117/**
118 * dprtc_destroy() - Destroy the DPRTC object and release all its resources.
119 * @mc_io: Pointer to MC portal's I/O object
120 * @dprc_token: Parent container token; '0' for default container
121 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
122 * @object_id: The object id; it must be a valid id within the container that
123 * created this object;
124 *
125 * The function accepts the authentication token of the parent container that
126 * created the object (not the one that currently owns the object). The object
127 * is searched within parent using the provided 'object_id'.
128 * All tokens to the object must be closed before calling destroy.
129 *
130 * Return: '0' on Success; error code otherwise.
131 */
132int dprtc_destroy(struct fsl_mc_io *mc_io,
133 u16 dprc_token,
134 u32 cmd_flags,
135 u32 object_id)
136{
137 struct dprtc_cmd_destroy *cmd_params;
138 struct fsl_mc_command cmd = { 0 };
139
140 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_DESTROY,
141 cmd_flags,
142 dprc_token);
143 cmd_params = (struct dprtc_cmd_destroy *)cmd.params;
144 cmd_params->object_id = cpu_to_le32(object_id);
145
146 return mc_send_command(mc_io, &cmd);
147}
148
149/**
150 * dprtc_enable() - Enable the DPRTC.
151 * @mc_io: Pointer to MC portal's I/O object
152 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
153 * @token: Token of DPRTC object
154 *
155 * Return: '0' on Success; Error code otherwise.
156 */
157int dprtc_enable(struct fsl_mc_io *mc_io,
158 u32 cmd_flags,
159 u16 token)
160{
161 struct fsl_mc_command cmd = { 0 };
162
163 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_ENABLE, cmd_flags,
164 token);
165
166 return mc_send_command(mc_io, &cmd);
167}
168
169/**
170 * dprtc_disable() - Disable the DPRTC.
171 * @mc_io: Pointer to MC portal's I/O object
172 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
173 * @token: Token of DPRTC object
174 *
175 * Return: '0' on Success; Error code otherwise.
176 */
177int dprtc_disable(struct fsl_mc_io *mc_io,
178 u32 cmd_flags,
179 u16 token)
180{
181 struct fsl_mc_command cmd = { 0 };
182
183 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_DISABLE,
184 cmd_flags,
185 token);
186
187 return mc_send_command(mc_io, &cmd);
188}
189
190/**
191 * dprtc_is_enabled() - Check if the DPRTC is enabled.
192 * @mc_io: Pointer to MC portal's I/O object
193 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
194 * @token: Token of DPRTC object
195 * @en: Returns '1' if object is enabled; '0' otherwise
196 *
197 * Return: '0' on Success; Error code otherwise.
198 */
199int dprtc_is_enabled(struct fsl_mc_io *mc_io,
200 u32 cmd_flags,
201 u16 token,
202 int *en)
203{
204 struct dprtc_rsp_is_enabled *rsp_params;
205 struct fsl_mc_command cmd = { 0 };
206 int err;
207
208 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_IS_ENABLED, cmd_flags,
209 token);
210
211 err = mc_send_command(mc_io, &cmd);
212 if (err)
213 return err;
214
215 rsp_params = (struct dprtc_rsp_is_enabled *)cmd.params;
216 *en = dprtc_get_field(rsp_params->en, ENABLE);
217
218 return 0;
219}
220
221/**
222 * dprtc_reset() - Reset the DPRTC, returns the object to initial state.
223 * @mc_io: Pointer to MC portal's I/O object
224 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
225 * @token: Token of DPRTC object
226 *
227 * Return: '0' on Success; Error code otherwise.
228 */
229int dprtc_reset(struct fsl_mc_io *mc_io,
230 u32 cmd_flags,
231 u16 token)
232{
233 struct fsl_mc_command cmd = { 0 };
234
235 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_RESET,
236 cmd_flags,
237 token);
238
239 return mc_send_command(mc_io, &cmd);
240}
241
242/**
243 * dprtc_set_irq_enable() - Set overall interrupt state.
244 * @mc_io: Pointer to MC portal's I/O object
245 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
246 * @token: Token of DPRTC object
247 * @irq_index: The interrupt index to configure
248 * @en: Interrupt state - enable = 1, disable = 0
249 *
250 * Allows GPP software to control when interrupts are generated.
251 * Each interrupt can have up to 32 causes. The enable/disable control's the
252 * overall interrupt state. if the interrupt is disabled no causes will cause
253 * an interrupt.
254 *
255 * Return: '0' on Success; Error code otherwise.
256 */
257int dprtc_set_irq_enable(struct fsl_mc_io *mc_io,
258 u32 cmd_flags,
259 u16 token,
260 u8 irq_index,
261 u8 en)
262{
263 struct dprtc_cmd_set_irq_enable *cmd_params;
264 struct fsl_mc_command cmd = { 0 };
265
266 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_IRQ_ENABLE,
267 cmd_flags,
268 token);
269 cmd_params = (struct dprtc_cmd_set_irq_enable *)cmd.params;
270 cmd_params->irq_index = irq_index;
271 cmd_params->en = en;
272
273 return mc_send_command(mc_io, &cmd);
274}
275
276/**
277 * dprtc_get_irq_enable() - Get overall interrupt state
278 * @mc_io: Pointer to MC portal's I/O object
279 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
280 * @token: Token of DPRTC object
281 * @irq_index: The interrupt index to configure
282 * @en: Returned interrupt state - enable = 1, disable = 0
283 *
284 * Return: '0' on Success; Error code otherwise.
285 */
286int dprtc_get_irq_enable(struct fsl_mc_io *mc_io,
287 u32 cmd_flags,
288 u16 token,
289 u8 irq_index,
290 u8 *en)
291{
292 struct dprtc_rsp_get_irq_enable *rsp_params;
293 struct dprtc_cmd_get_irq *cmd_params;
294 struct fsl_mc_command cmd = { 0 };
295 int err;
296
297 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_IRQ_ENABLE,
298 cmd_flags,
299 token);
300 cmd_params = (struct dprtc_cmd_get_irq *)cmd.params;
301 cmd_params->irq_index = irq_index;
302
303 err = mc_send_command(mc_io, &cmd);
304 if (err)
305 return err;
306
307 rsp_params = (struct dprtc_rsp_get_irq_enable *)cmd.params;
308 *en = rsp_params->en;
309
310 return 0;
311}
312
313/**
314 * dprtc_set_irq_mask() - Set interrupt mask.
315 * @mc_io: Pointer to MC portal's I/O object
316 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
317 * @token: Token of DPRTC object
318 * @irq_index: The interrupt index to configure
319 * @mask: Event mask to trigger interrupt;
320 * each bit:
321 * 0 = ignore event
322 * 1 = consider event for asserting IRQ
323 *
324 * Every interrupt can have up to 32 causes and the interrupt model supports
325 * masking/unmasking each cause independently
326 *
327 * Return: '0' on Success; Error code otherwise.
328 */
329int dprtc_set_irq_mask(struct fsl_mc_io *mc_io,
330 u32 cmd_flags,
331 u16 token,
332 u8 irq_index,
333 u32 mask)
334{
335 struct dprtc_cmd_set_irq_mask *cmd_params;
336 struct fsl_mc_command cmd = { 0 };
337
338 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_IRQ_MASK,
339 cmd_flags,
340 token);
341 cmd_params = (struct dprtc_cmd_set_irq_mask *)cmd.params;
342 cmd_params->mask = cpu_to_le32(mask);
343 cmd_params->irq_index = irq_index;
344
345 return mc_send_command(mc_io, &cmd);
346}
347
348/**
349 * dprtc_get_irq_mask() - Get interrupt mask.
350 * @mc_io: Pointer to MC portal's I/O object
351 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
352 * @token: Token of DPRTC object
353 * @irq_index: The interrupt index to configure
354 * @mask: Returned event mask to trigger interrupt
355 *
356 * Every interrupt can have up to 32 causes and the interrupt model supports
357 * masking/unmasking each cause independently
358 *
359 * Return: '0' on Success; Error code otherwise.
360 */
361int dprtc_get_irq_mask(struct fsl_mc_io *mc_io,
362 u32 cmd_flags,
363 u16 token,
364 u8 irq_index,
365 u32 *mask)
366{
367 struct dprtc_rsp_get_irq_mask *rsp_params;
368 struct dprtc_cmd_get_irq *cmd_params;
369 struct fsl_mc_command cmd = { 0 };
370 int err;
371
372 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_IRQ_MASK,
373 cmd_flags,
374 token);
375 cmd_params = (struct dprtc_cmd_get_irq *)cmd.params;
376 cmd_params->irq_index = irq_index;
377
378 err = mc_send_command(mc_io, &cmd);
379 if (err)
380 return err;
381
382 rsp_params = (struct dprtc_rsp_get_irq_mask *)cmd.params;
383 *mask = le32_to_cpu(rsp_params->mask);
384
385 return 0;
386}
387
388/**
389 * dprtc_get_irq_status() - Get the current status of any pending interrupts.
390 *
391 * @mc_io: Pointer to MC portal's I/O object
392 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
393 * @token: Token of DPRTC object
394 * @irq_index: The interrupt index to configure
395 * @status: Returned interrupts status - one bit per cause:
396 * 0 = no interrupt pending
397 * 1 = interrupt pending
398 *
399 * Return: '0' on Success; Error code otherwise.
400 */
401int dprtc_get_irq_status(struct fsl_mc_io *mc_io,
402 u32 cmd_flags,
403 u16 token,
404 u8 irq_index,
405 u32 *status)
406{
407 struct dprtc_cmd_get_irq_status *cmd_params;
408 struct dprtc_rsp_get_irq_status *rsp_params;
409 struct fsl_mc_command cmd = { 0 };
410 int err;
411
412 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_IRQ_STATUS,
413 cmd_flags,
414 token);
415 cmd_params = (struct dprtc_cmd_get_irq_status *)cmd.params;
416 cmd_params->status = cpu_to_le32(*status);
417 cmd_params->irq_index = irq_index;
418
419 err = mc_send_command(mc_io, &cmd);
420 if (err)
421 return err;
422
423 rsp_params = (struct dprtc_rsp_get_irq_status *)cmd.params;
424 *status = le32_to_cpu(rsp_params->status);
425
426 return 0;
427}
428
429/**
430 * dprtc_clear_irq_status() - Clear a pending interrupt's status
431 *
432 * @mc_io: Pointer to MC portal's I/O object
433 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
434 * @token: Token of DPRTC object
435 * @irq_index: The interrupt index to configure
436 * @status: Bits to clear (W1C) - one bit per cause:
437 * 0 = don't change
438 * 1 = clear status bit
439 *
440 * Return: '0' on Success; Error code otherwise.
441 */
442int dprtc_clear_irq_status(struct fsl_mc_io *mc_io,
443 u32 cmd_flags,
444 u16 token,
445 u8 irq_index,
446 u32 status)
447{
448 struct dprtc_cmd_clear_irq_status *cmd_params;
449 struct fsl_mc_command cmd = { 0 };
450
451 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_CLEAR_IRQ_STATUS,
452 cmd_flags,
453 token);
454 cmd_params = (struct dprtc_cmd_clear_irq_status *)cmd.params;
455 cmd_params->irq_index = irq_index;
456 cmd_params->status = cpu_to_le32(status);
457
458 return mc_send_command(mc_io, &cmd);
459}
460
461/**
462 * dprtc_get_attributes - Retrieve DPRTC attributes.
463 *
464 * @mc_io: Pointer to MC portal's I/O object
465 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
466 * @token: Token of DPRTC object
467 * @attr: Returned object's attributes
468 *
469 * Return: '0' on Success; Error code otherwise.
470 */
471int dprtc_get_attributes(struct fsl_mc_io *mc_io,
472 u32 cmd_flags,
473 u16 token,
474 struct dprtc_attr *attr)
475{
476 struct dprtc_rsp_get_attributes *rsp_params;
477 struct fsl_mc_command cmd = { 0 };
478 int err;
479
480 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_ATTR,
481 cmd_flags,
482 token);
483
484 err = mc_send_command(mc_io, &cmd);
485 if (err)
486 return err;
487
488 rsp_params = (struct dprtc_rsp_get_attributes *)cmd.params;
489 attr->id = le32_to_cpu(rsp_params->id);
490
491 return 0;
492}
493
494/**
495 * dprtc_set_clock_offset() - Sets the clock's offset
496 * (usually relative to another clock).
497 *
498 * @mc_io: Pointer to MC portal's I/O object
499 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
500 * @token: Token of DPRTC object
501 * @offset: New clock offset (in nanoseconds).
502 *
503 * Return: '0' on Success; Error code otherwise.
504 */
505int dprtc_set_clock_offset(struct fsl_mc_io *mc_io,
506 u32 cmd_flags,
507 u16 token,
508 int64_t offset)
509{
510 struct dprtc_cmd_set_clock_offset *cmd_params;
511 struct fsl_mc_command cmd = { 0 };
512
513 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_CLOCK_OFFSET,
514 cmd_flags,
515 token);
516 cmd_params = (struct dprtc_cmd_set_clock_offset *)cmd.params;
517 cmd_params->offset = cpu_to_le64(offset);
518
519 return mc_send_command(mc_io, &cmd);
520}
521
522/**
523 * dprtc_set_freq_compensation() - Sets a new frequency compensation value.
524 *
525 * @mc_io: Pointer to MC portal's I/O object
526 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
527 * @token: Token of DPRTC object
528 * @freq_compensation: The new frequency compensation value to set.
529 *
530 * Return: '0' on Success; Error code otherwise.
531 */
532int dprtc_set_freq_compensation(struct fsl_mc_io *mc_io,
533 u32 cmd_flags,
534 u16 token,
535 u32 freq_compensation)
536{
537 struct dprtc_get_freq_compensation *cmd_params;
538 struct fsl_mc_command cmd = { 0 };
539
540 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_FREQ_COMPENSATION,
541 cmd_flags,
542 token);
543 cmd_params = (struct dprtc_get_freq_compensation *)cmd.params;
544 cmd_params->freq_compensation = cpu_to_le32(freq_compensation);
545
546 return mc_send_command(mc_io, &cmd);
547}
548
549/**
550 * dprtc_get_freq_compensation() - Retrieves the frequency compensation value
551 *
552 * @mc_io: Pointer to MC portal's I/O object
553 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
554 * @token: Token of DPRTC object
555 * @freq_compensation: Frequency compensation value
556 *
557 * Return: '0' on Success; Error code otherwise.
558 */
559int dprtc_get_freq_compensation(struct fsl_mc_io *mc_io,
560 u32 cmd_flags,
561 u16 token,
562 u32 *freq_compensation)
563{
564 struct dprtc_get_freq_compensation *rsp_params;
565 struct fsl_mc_command cmd = { 0 };
566 int err;
567
568 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_FREQ_COMPENSATION,
569 cmd_flags,
570 token);
571
572 err = mc_send_command(mc_io, &cmd);
573 if (err)
574 return err;
575
576 rsp_params = (struct dprtc_get_freq_compensation *)cmd.params;
577 *freq_compensation = le32_to_cpu(rsp_params->freq_compensation);
578
579 return 0;
580}
581
582/**
583 * dprtc_get_time() - Returns the current RTC time.
584 *
585 * @mc_io: Pointer to MC portal's I/O object
586 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
587 * @token: Token of DPRTC object
588 * @time: Current RTC time.
589 *
590 * Return: '0' on Success; Error code otherwise.
591 */
592int dprtc_get_time(struct fsl_mc_io *mc_io,
593 u32 cmd_flags,
594 u16 token,
595 uint64_t *time)
596{
597 struct dprtc_time *rsp_params;
598 struct fsl_mc_command cmd = { 0 };
599 int err;
600
601 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_TIME,
602 cmd_flags,
603 token);
604
605 err = mc_send_command(mc_io, &cmd);
606 if (err)
607 return err;
608
609 rsp_params = (struct dprtc_time *)cmd.params;
610 *time = le64_to_cpu(rsp_params->time);
611
612 return 0;
613}
614
615/**
616 * dprtc_set_time() - Updates current RTC time.
617 *
618 * @mc_io: Pointer to MC portal's I/O object
619 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
620 * @token: Token of DPRTC object
621 * @time: New RTC time.
622 *
623 * Return: '0' on Success; Error code otherwise.
624 */
625int dprtc_set_time(struct fsl_mc_io *mc_io,
626 u32 cmd_flags,
627 u16 token,
628 uint64_t time)
629{
630 struct dprtc_time *cmd_params;
631 struct fsl_mc_command cmd = { 0 };
632
633 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_TIME,
634 cmd_flags,
635 token);
636 cmd_params = (struct dprtc_time *)cmd.params;
637 cmd_params->time = cpu_to_le64(time);
638
639 return mc_send_command(mc_io, &cmd);
640}
641
642/**
643 * dprtc_set_alarm() - Defines and sets alarm.
644 *
645 * @mc_io: Pointer to MC portal's I/O object
646 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
647 * @token: Token of DPRTC object
648 * @time: In nanoseconds, the time when the alarm
649 * should go off - must be a multiple of
650 * 1 microsecond
651 *
652 * Return: '0' on Success; Error code otherwise.
653 */
654int dprtc_set_alarm(struct fsl_mc_io *mc_io,
655 u32 cmd_flags,
656 u16 token, uint64_t time)
657{
658 struct dprtc_time *cmd_params;
659 struct fsl_mc_command cmd = { 0 };
660
661 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_SET_ALARM,
662 cmd_flags,
663 token);
664 cmd_params = (struct dprtc_time *)cmd.params;
665 cmd_params->time = cpu_to_le64(time);
666
667 return mc_send_command(mc_io, &cmd);
668}
669
670/**
671 * dprtc_get_api_version() - Get Data Path Real Time Counter API version
672 * @mc_io: Pointer to MC portal's I/O object
673 * @cmd_flags: Command flags; one or more of 'MC_CMD_FLAG_'
674 * @major_ver: Major version of data path real time counter API
675 * @minor_ver: Minor version of data path real time counter API
676 *
677 * Return: '0' on Success; Error code otherwise.
678 */
679int dprtc_get_api_version(struct fsl_mc_io *mc_io,
680 u32 cmd_flags,
681 u16 *major_ver,
682 u16 *minor_ver)
683{
684 struct dprtc_rsp_get_api_version *rsp_params;
685 struct fsl_mc_command cmd = { 0 };
686 int err;
687
688 cmd.header = mc_encode_cmd_header(DPRTC_CMDID_GET_API_VERSION,
689 cmd_flags,
690 0);
691
692 err = mc_send_command(mc_io, &cmd);
693 if (err)
694 return err;
695
696 rsp_params = (struct dprtc_rsp_get_api_version *)cmd.params;
697 *major_ver = le16_to_cpu(rsp_params->major);
698 *minor_ver = le16_to_cpu(rsp_params->minor);
699
700 return 0;
701}
drivers/staging/fsl-dpaa2/rtc/dprtc.h+164−0
@@ -0,0 +1,164 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright 2013-2016 Freescale Semiconductor Inc.
4 * Copyright 2016-2018 NXP
5 */
6
7#ifndef __FSL_DPRTC_H
8#define __FSL_DPRTC_H
9
10/* Data Path Real Time Counter API
11 * Contains initialization APIs and runtime control APIs for RTC
12 */
13
14struct fsl_mc_io;
15
16/**
17 * Number of irq's
18 */
19#define DPRTC_MAX_IRQ_NUM 1
20#define DPRTC_IRQ_INDEX 0
21
22/**
23 * Interrupt event masks:
24 */
25
26/**
27 * Interrupt event mask indicating alarm event had occurred
28 */
29#define DPRTC_EVENT_ALARM 0x40000000
30/**
31 * Interrupt event mask indicating periodic pulse event had occurred
32 */
33#define DPRTC_EVENT_PPS 0x08000000
34
35int dprtc_open(struct fsl_mc_io *mc_io,
36 u32 cmd_flags,
37 int dprtc_id,
38 u16 *token);
39
40int dprtc_close(struct fsl_mc_io *mc_io,
41 u32 cmd_flags,
42 u16 token);
43
44/**
45 * struct dprtc_cfg - Structure representing DPRTC configuration
46 * @options: place holder
47 */
48struct dprtc_cfg {
49 u32 options;
50};
51
52int dprtc_create(struct fsl_mc_io *mc_io,
53 u16 dprc_token,
54 u32 cmd_flags,
55 const struct dprtc_cfg *cfg,
56 u32 *obj_id);
57
58int dprtc_destroy(struct fsl_mc_io *mc_io,
59 u16 dprc_token,
60 u32 cmd_flags,
61 u32 object_id);
62
63int dprtc_enable(struct fsl_mc_io *mc_io,
64 u32 cmd_flags,
65 u16 token);
66
67int dprtc_disable(struct fsl_mc_io *mc_io,
68 u32 cmd_flags,
69 u16 token);
70
71int dprtc_is_enabled(struct fsl_mc_io *mc_io,
72 u32 cmd_flags,
73 u16 token,
74 int *en);
75
76int dprtc_reset(struct fsl_mc_io *mc_io,
77 u32 cmd_flags,
78 u16 token);
79
80int dprtc_set_clock_offset(struct fsl_mc_io *mc_io,
81 u32 cmd_flags,
82 u16 token,
83 int64_t offset);
84
85int dprtc_set_freq_compensation(struct fsl_mc_io *mc_io,
86 u32 cmd_flags,
87 u16 token,
88 u32 freq_compensation);
89
90int dprtc_get_freq_compensation(struct fsl_mc_io *mc_io,
91 u32 cmd_flags,
92 u16 token,
93 u32 *freq_compensation);
94
95int dprtc_get_time(struct fsl_mc_io *mc_io,
96 u32 cmd_flags,
97 u16 token,
98 uint64_t *time);
99
100int dprtc_set_time(struct fsl_mc_io *mc_io,
101 u32 cmd_flags,
102 u16 token,
103 uint64_t time);
104
105int dprtc_set_alarm(struct fsl_mc_io *mc_io,
106 u32 cmd_flags,
107 u16 token,
108 uint64_t time);
109
110int dprtc_set_irq_enable(struct fsl_mc_io *mc_io,
111 u32 cmd_flags,
112 u16 token,
113 u8 irq_index,
114 u8 en);
115
116int dprtc_get_irq_enable(struct fsl_mc_io *mc_io,
117 u32 cmd_flags,
118 u16 token,
119 u8 irq_index,
120 u8 *en);
121
122int dprtc_set_irq_mask(struct fsl_mc_io *mc_io,
123 u32 cmd_flags,
124 u16 token,
125 u8 irq_index,
126 u32 mask);
127
128int dprtc_get_irq_mask(struct fsl_mc_io *mc_io,
129 u32 cmd_flags,
130 u16 token,
131 u8 irq_index,
132 u32 *mask);
133
134int dprtc_get_irq_status(struct fsl_mc_io *mc_io,
135 u32 cmd_flags,
136 u16 token,
137 u8 irq_index,
138 u32 *status);
139
140int dprtc_clear_irq_status(struct fsl_mc_io *mc_io,
141 u32 cmd_flags,
142 u16 token,
143 u8 irq_index,
144 u32 status);
145
146/**
147 * struct dprtc_attr - Structure representing DPRTC attributes
148 * @id: DPRTC object ID
149 */
150struct dprtc_attr {
151 int id;
152};
153
154int dprtc_get_attributes(struct fsl_mc_io *mc_io,
155 u32 cmd_flags,
156 u16 token,
157 struct dprtc_attr *attr);
158
159int dprtc_get_api_version(struct fsl_mc_io *mc_io,
160 u32 cmd_flags,
161 u16 *major_ver,
162 u16 *minor_ver);
163
164#endif /* __FSL_DPRTC_H */
drivers/staging/fsl-dpaa2/rtc/rtc.c+229−0
@@ -0,0 +1,229 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright 2013-2016 Freescale Semiconductor Inc.
4 * Copyright 2016-2018 NXP
5 */
6
7#include <linux/module.h>
8#include <linux/slab.h>
9#include <linux/ptp_clock_kernel.h>
10#include <linux/fsl/mc.h>
11
12#include "rtc.h"
13
14struct ptp_dpaa2_priv {
15 struct fsl_mc_device *rtc_mc_dev;
16 struct ptp_clock *clock;
17 struct ptp_clock_info caps;
18 u32 freq_comp;
19};
20
21/* PTP clock operations */
22static int ptp_dpaa2_adjfreq(struct ptp_clock_info *ptp, s32 ppb)
23{
24 struct ptp_dpaa2_priv *ptp_dpaa2 =
25 container_of(ptp, struct ptp_dpaa2_priv, caps);
26 struct fsl_mc_device *mc_dev = ptp_dpaa2->rtc_mc_dev;
27 struct device *dev = &mc_dev->dev;
28 u64 adj;
29 u32 diff, tmr_add;
30 int neg_adj = 0;
31 int err = 0;
32
33 if (ppb < 0) {
34 neg_adj = 1;
35 ppb = -ppb;
36 }
37
38 tmr_add = ptp_dpaa2->freq_comp;
39 adj = tmr_add;
40 adj *= ppb;
41 diff = div_u64(adj, 1000000000ULL);
42
43 tmr_add = neg_adj ? tmr_add - diff : tmr_add + diff;
44
45 err = dprtc_set_freq_compensation(mc_dev->mc_io, 0,
46 mc_dev->mc_handle, tmr_add);
47 if (err)
48 dev_err(dev, "dprtc_set_freq_compensation err %d\n", err);
49 return 0;
50}
51
52static int ptp_dpaa2_adjtime(struct ptp_clock_info *ptp, s64 delta)
53{
54 struct ptp_dpaa2_priv *ptp_dpaa2 =
55 container_of(ptp, struct ptp_dpaa2_priv, caps);
56 struct fsl_mc_device *mc_dev = ptp_dpaa2->rtc_mc_dev;
57 struct device *dev = &mc_dev->dev;
58 s64 now;
59 int err = 0;
60
61 err = dprtc_get_time(mc_dev->mc_io, 0, mc_dev->mc_handle, &now);
62 if (err) {
63 dev_err(dev, "dprtc_get_time err %d\n", err);
64 return 0;
65 }
66
67 now += delta;
68
69 err = dprtc_set_time(mc_dev->mc_io, 0, mc_dev->mc_handle, now);
70 if (err) {
71 dev_err(dev, "dprtc_set_time err %d\n", err);
72 return 0;
73 }
74 return 0;
75}
76
77static int ptp_dpaa2_gettime(struct ptp_clock_info *ptp, struct timespec64 *ts)
78{
79 struct ptp_dpaa2_priv *ptp_dpaa2 =
80 container_of(ptp, struct ptp_dpaa2_priv, caps);
81 struct fsl_mc_device *mc_dev = ptp_dpaa2->rtc_mc_dev;
82 struct device *dev = &mc_dev->dev;
83 u64 ns;
84 u32 remainder;
85 int err = 0;
86
87 err = dprtc_get_time(mc_dev->mc_io, 0, mc_dev->mc_handle, &ns);
88 if (err) {
89 dev_err(dev, "dprtc_get_time err %d\n", err);
90 return 0;
91 }
92
93 ts->tv_sec = div_u64_rem(ns, 1000000000, &remainder);
94 ts->tv_nsec = remainder;
95 return 0;
96}
97
98static int ptp_dpaa2_settime(struct ptp_clock_info *ptp,
99 const struct timespec64 *ts)
100{
101 struct ptp_dpaa2_priv *ptp_dpaa2 =
102 container_of(ptp, struct ptp_dpaa2_priv, caps);
103 struct fsl_mc_device *mc_dev = ptp_dpaa2->rtc_mc_dev;
104 struct device *dev = &mc_dev->dev;
105 u64 ns;
106 int err = 0;
107
108 ns = ts->tv_sec * 1000000000ULL;
109 ns += ts->tv_nsec;
110
111 err = dprtc_set_time(mc_dev->mc_io, 0, mc_dev->mc_handle, ns);
112 if (err)
113 dev_err(dev, "dprtc_set_time err %d\n", err);
114 return 0;
115}
116
117static struct ptp_clock_info ptp_dpaa2_caps = {
118 .owner = THIS_MODULE,
119 .name = "DPAA2 PTP Clock",
120 .max_adj = 512000,
121 .n_alarm = 2,
122 .n_ext_ts = 2,
123 .n_per_out = 3,
124 .n_pins = 0,
125 .pps = 1,
126 .adjfreq = ptp_dpaa2_adjfreq,
127 .adjtime = ptp_dpaa2_adjtime,
128 .gettime64 = ptp_dpaa2_gettime,
129 .settime64 = ptp_dpaa2_settime,
130};
131
132static int rtc_probe(struct fsl_mc_device *mc_dev)
133{
134 struct device *dev = &mc_dev->dev;
135 struct ptp_dpaa2_priv *ptp_dpaa2;
136 u32 tmr_add = 0;
137 int err;
138
139 ptp_dpaa2 = kzalloc(sizeof(*ptp_dpaa2), GFP_KERNEL);
140 if (!ptp_dpaa2)
141 return -ENOMEM;
142
143 err = fsl_mc_portal_allocate(mc_dev, 0, &mc_dev->mc_io);
144 if (err) {
145 dev_err(dev, "fsl_mc_portal_allocate err %d\n", err);
146 goto err_exit;
147 }
148
149 err = dprtc_open(mc_dev->mc_io, 0, mc_dev->obj_desc.id,
150 &mc_dev->mc_handle);
151 if (err) {
152 dev_err(dev, "dprtc_open err %d\n", err);
153 goto err_free_mcp;
154 }
155
156 ptp_dpaa2->rtc_mc_dev = mc_dev;
157
158 err = dprtc_get_freq_compensation(mc_dev->mc_io, 0,
159 mc_dev->mc_handle, &tmr_add);
160 if (err) {
161 dev_err(dev, "dprtc_get_freq_compensation err %d\n", err);
162 goto err_close;
163 }
164
165 ptp_dpaa2->freq_comp = tmr_add;
166 ptp_dpaa2->caps = ptp_dpaa2_caps;
167
168 ptp_dpaa2->clock = ptp_clock_register(&ptp_dpaa2->caps, dev);
169 if (IS_ERR(ptp_dpaa2->clock)) {
170 err = PTR_ERR(ptp_dpaa2->clock);
171 goto err_close;
172 }
173
174 dpaa2_phc_index = ptp_clock_index(ptp_dpaa2->clock);
175
176 dev_set_drvdata(dev, ptp_dpaa2);
177
178 return 0;
179
180err_close:
181 dprtc_close(mc_dev->mc_io, 0, mc_dev->mc_handle);
182err_free_mcp:
183 fsl_mc_portal_free(mc_dev->mc_io);
184err_exit:
185 kfree(ptp_dpaa2);
186 dev_set_drvdata(dev, NULL);
187 return err;
188}
189
190static int rtc_remove(struct fsl_mc_device *mc_dev)
191{
192 struct ptp_dpaa2_priv *ptp_dpaa2;
193 struct device *dev = &mc_dev->dev;
194
195 ptp_dpaa2 = dev_get_drvdata(dev);
196 ptp_clock_unregister(ptp_dpaa2->clock);
197
198 dprtc_close(mc_dev->mc_io, 0, mc_dev->mc_handle);
199 fsl_mc_portal_free(mc_dev->mc_io);
200
201 kfree(ptp_dpaa2);
202 dev_set_drvdata(dev, NULL);
203
204 return 0;
205}
206
207static const struct fsl_mc_device_id rtc_match_id_table[] = {
208 {
209 .vendor = FSL_MC_VENDOR_FREESCALE,
210 .obj_type = "dprtc",
211 },
212 {}
213};
214MODULE_DEVICE_TABLE(fslmc, rtc_match_id_table);
215
216static struct fsl_mc_driver rtc_drv = {
217 .driver = {
218 .name = KBUILD_MODNAME,
219 .owner = THIS_MODULE,
220 },
221 .probe = rtc_probe,
222 .remove = rtc_remove,
223 .match_id_table = rtc_match_id_table,
224};
225
226module_fsl_mc_driver(rtc_drv);
227
228MODULE_LICENSE("GPL v2");
229MODULE_DESCRIPTION("DPAA2 PTP Clock Driver");
drivers/staging/fsl-dpaa2/rtc/rtc.h+14−0
@@ -0,0 +1,14 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright 2018 NXP
4 */
5
6#ifndef __RTC_H
7#define __RTC_H
8
9#include "dprtc.h"
10#include "dprtc-cmd.h"
11
12extern int dpaa2_phc_index;
13
14#endif
drivers/staging/fsl-mc/bus/dpio/dpio-driver.c+19−9
@@ -13,6 +13,7 @@ · 12 unmodified lines
13#include <linux/msi.h>13#include <linux/msi.h>
14#include <linux/dma-mapping.h>14#include <linux/dma-mapping.h>
15#include <linux/delay.h>15#include <linux/delay.h>
16#include <linux/io.h>
16 17
17#include <linux/fsl/mc.h>18#include <linux/fsl/mc.h>
18#include "../../include/dpaa2-io.h"19#include "../../include/dpaa2-io.h"
@@ -100,7 +101,7 @@ static int dpaa2_dpio_probe(struct fsl_mc_device *dpio_dev) · 81 unmodified lines
100 if (err) {101 if (err) {
101 dev_dbg(dev, "MC portal allocation failed\n");102 dev_dbg(dev, "MC portal allocation failed\n");
102 err = -EPROBE_DEFER;103 err = -EPROBE_DEFER;
103 goto err_mcportal;104 goto err_priv_alloc;
104 }105 }
105 106
106 err = dpio_open(dpio_dev->mc_io, 0, dpio_dev->obj_desc.id,107 err = dpio_open(dpio_dev->mc_io, 0, dpio_dev->obj_desc.id,
@@ -146,10 +147,22 @@ static int dpaa2_dpio_probe(struct fsl_mc_device *dpio_dev) · 39 unmodified lines
146 * Set the CENA regs to be the cache inhibited area of the portal to147 * Set the CENA regs to be the cache inhibited area of the portal to
147 * avoid coherency issues if a user migrates to another core.148 * avoid coherency issues if a user migrates to another core.
148 */149 */
149 desc.regs_cena = ioremap_wc(dpio_dev->regions[1].start,150 desc.regs_cena = devm_memremap(dev, dpio_dev->regions[1].start,
150 resource_size(&dpio_dev->regions[1]));151 resource_size(&dpio_dev->regions[1]),
151 desc.regs_cinh = ioremap(dpio_dev->regions[1].start,152 MEMREMAP_WC);
152 resource_size(&dpio_dev->regions[1]));153 if (IS_ERR(desc.regs_cena)) {
154 dev_err(dev, "devm_memremap failed\n");
155 err = PTR_ERR(desc.regs_cena);
156 goto err_allocate_irqs;
157 }
158
159 desc.regs_cinh = devm_ioremap(dev, dpio_dev->regions[1].start,
160 resource_size(&dpio_dev->regions[1]));
161 if (!desc.regs_cinh) {
162 err = -ENOMEM;
163 dev_err(dev, "devm_ioremap failed\n");
164 goto err_allocate_irqs;
165 }
153 166
154 err = fsl_mc_allocate_irqs(dpio_dev);167 err = fsl_mc_allocate_irqs(dpio_dev);
155 if (err) {168 if (err) {
@@ -164,6 +177,7 @@ static int dpaa2_dpio_probe(struct fsl_mc_device *dpio_dev) · 8 unmodified lines
164 priv->io = dpaa2_io_create(&desc);177 priv->io = dpaa2_io_create(&desc);
165 if (!priv->io) {178 if (!priv->io) {
166 dev_err(dev, "dpaa2_io_create failed\n");179 dev_err(dev, "dpaa2_io_create failed\n");
180 err = -ENOMEM;
167 goto err_dpaa2_io_create;181 goto err_dpaa2_io_create;
168 }182 }
169 183
@@ -185,8 +199,6 @@ err_get_attr: · 15 unmodified lines
185 dpio_close(dpio_dev->mc_io, 0, dpio_dev->mc_handle);199 dpio_close(dpio_dev->mc_io, 0, dpio_dev->mc_handle);
186err_open:200err_open:
187 fsl_mc_portal_free(dpio_dev->mc_io);201 fsl_mc_portal_free(dpio_dev->mc_io);
188err_mcportal:
189 dev_set_drvdata(dev, NULL);
190err_priv_alloc:202err_priv_alloc:
191 return err;203 return err;
192}204}
@@ -230,8 +242,6 @@ static int dpaa2_dpio_remove(struct fsl_mc_device *dpio_dev) · 37 unmodified lines
230 242
231 fsl_mc_portal_free(dpio_dev->mc_io);243 fsl_mc_portal_free(dpio_dev->mc_io);
232 244
233 dev_set_drvdata(dev, NULL);
234
235 return 0;245 return 0;
236 246
237err_open:247err_open:
drivers/staging/fsl-mc/bus/dpio/qbman-portal.h+2−2
@@ -15,7 +15,7 @@ struct qbman_swp; · 14 unmodified lines
15/* qbman software portal descriptor structure */15/* qbman software portal descriptor structure */
16struct qbman_swp_desc {16struct qbman_swp_desc {
17 void *cena_bar; /* Cache-enabled portal base address */17 void *cena_bar; /* Cache-enabled portal base address */
18 void *cinh_bar; /* Cache-inhibited portal base address */18 void __iomem *cinh_bar; /* Cache-inhibited portal base address */
19 u32 qman_version;19 u32 qman_version;
20};20};
21 21
@@ -102,7 +102,7 @@ struct qbman_release_desc { · 80 unmodified lines
102/* portal data structure */102/* portal data structure */
103struct qbman_swp {103struct qbman_swp {
104 const struct qbman_swp_desc *desc;104 const struct qbman_swp_desc *desc;
105 void __iomem *addr_cena;105 void *addr_cena;
106 void __iomem *addr_cinh;106 void __iomem *addr_cinh;
107 107
108 /* Management commands */108 /* Management commands */
drivers/staging/fsl-mc/include/dpaa2-io.h+1−1
@@ -52,7 +52,7 @@ struct dpaa2_io_desc { · 51 unmodified lines
52 int has_8prio;52 int has_8prio;
53 int cpu;53 int cpu;
54 void *regs_cena;54 void *regs_cena;
55 void *regs_cinh;55 void __iomem *regs_cinh;
56 int dpio_id;56 int dpio_id;
57 u32 qman_version;57 u32 qman_version;
58};58};
drivers/staging/gdm724x/gdm_endian.c+2−12
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#include <linux/kernel.h>4#include <linux/kernel.h>
15#include "gdm_endian.h"5#include "gdm_endian.h"
drivers/staging/gdm724x/gdm_endian.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef __GDM_ENDIAN_H__4#ifndef __GDM_ENDIAN_H__
15#define __GDM_ENDIAN_H__5#define __GDM_ENDIAN_H__
drivers/staging/gdm724x/gdm_lte.c+3−13
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt4#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
15 5
@@ -408,7 +398,7 @@ static s32 gdm_lte_tx_nic_type(struct net_device *dev, struct sk_buff *skb) · 392 unmodified lines
408 return nic_type;398 return nic_type;
409}399}
410 400
411static int gdm_lte_tx(struct sk_buff *skb, struct net_device *dev)401static netdev_tx_t gdm_lte_tx(struct sk_buff *skb, struct net_device *dev)
412{402{
413 struct nic *nic = netdev_priv(dev);403 struct nic *nic = netdev_priv(dev);
414 u32 nic_type;404 u32 nic_type;
drivers/staging/gdm724x/gdm_lte.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _GDM_LTE_H_4#ifndef _GDM_LTE_H_
15#define _GDM_LTE_H_5#define _GDM_LTE_H_
drivers/staging/gdm724x/gdm_mux.c+2−12
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt4#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
15 5
drivers/staging/gdm724x/gdm_mux.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _GDM_MUX_H_4#ifndef _GDM_MUX_H_
15#define _GDM_MUX_H_5#define _GDM_MUX_H_
drivers/staging/gdm724x/gdm_tty.c+2−12
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt4#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
15 5
drivers/staging/gdm724x/gdm_tty.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _GDM_TTY_H_4#ifndef _GDM_TTY_H_
15#define _GDM_TTY_H_5#define _GDM_TTY_H_
drivers/staging/gdm724x/gdm_usb.c+2−12
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt4#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
15 5
drivers/staging/gdm724x/gdm_usb.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _GDM_USB_H_4#ifndef _GDM_USB_H_
15#define _GDM_USB_H_5#define _GDM_USB_H_
drivers/staging/gdm724x/hci.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _HCI_H_4#ifndef _HCI_H_
15#define _HCI_H_5#define _HCI_H_
drivers/staging/gdm724x/hci_packet.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _HCI_PACKET_H_4#ifndef _HCI_PACKET_H_
15#define _HCI_PACKET_H_5#define _HCI_PACKET_H_
drivers/staging/gdm724x/netlink_k.c+2−12
@@ -1,15 +1,5 @@
1/*1// SPDX-License-Identifier: GPL-2.0
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt4#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
15 5
drivers/staging/gdm724x/netlink_k.h+2−12
@@ -1,15 +1,5 @@
1/*1/* SPDX-License-Identifier: GPL-2.0 */
2 * Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved.2/* Copyright (c) 2012 GCT Semiconductor, Inc. All rights reserved. */
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13 3
14#ifndef _NETLINK_K_H4#ifndef _NETLINK_K_H
15#define _NETLINK_K_H5#define _NETLINK_K_H
drivers/staging/goldfish/Kconfig+1−8
@@ -1,13 +1,6 @@
1config GOLDFISH_AUDIO1config GOLDFISH_AUDIO
2 tristate "Goldfish AVD Audio Device"2 tristate "Goldfish AVD Audio Device"
3 depends on GOLDFISH3 depends on GOLDFISH
4 ---help---4 help
5 Emulated audio channel for the Goldfish Android Virtual Device5 Emulated audio channel for the Goldfish Android Virtual Device
6 6
7config MTD_GOLDFISH_NAND
8 tristate "Goldfish NAND device"
9 depends on GOLDFISH
10 depends on MTD
11 help
12 Drives the emulated NAND flash device on the Google Goldfish
13 Android virtual device.
drivers/staging/goldfish/Makefile+0−1
@@ -3,4 +3,3 @@ · 2 unmodified lines
3#3#
4 4
5obj-$(CONFIG_GOLDFISH_AUDIO) += goldfish_audio.o5obj-$(CONFIG_GOLDFISH_AUDIO) += goldfish_audio.o
6obj-$(CONFIG_MTD_GOLDFISH_NAND) += goldfish_nand.o
drivers/staging/goldfish/goldfish_nand.c+0−441
@@ -1,441 +0,0 @@
1/*
2 * drivers/mtd/devices/goldfish_nand.c
3 *
4 * Copyright (C) 2007 Google, Inc.
5 * Copyright (C) 2012 Intel, Inc.
6 * Copyright (C) 2013 Intel, Inc.
7 *
8 * This software is licensed under the terms of the GNU General Public
9 * License version 2, as published by the Free Software Foundation, and
10 * may be copied, distributed, and modified under those terms.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 */
18
19#include <linux/io.h>
20#include <linux/device.h>
21#include <linux/module.h>
22#include <linux/slab.h>
23#include <linux/ioport.h>
24#include <linux/vmalloc.h>
25#include <linux/mtd/mtd.h>
26#include <linux/platform_device.h>
27#include <linux/mutex.h>
28#include <linux/goldfish.h>
29#include <asm/div64.h>
30#include <linux/dma-mapping.h>
31
32#include "goldfish_nand_reg.h"
33
34struct goldfish_nand {
35 /* lock protects access to the device registers */
36 struct mutex lock;
37 unsigned char __iomem *base;
38 struct cmd_params *cmd_params;
39 size_t mtd_count;
40 struct mtd_info mtd[0];
41};
42
43static u32 goldfish_nand_cmd_with_params(struct mtd_info *mtd,
44 enum nand_cmd cmd, u64 addr, u32 len,
45 void *ptr, u32 *rv)
46{
47 u32 cmdp;
48 struct goldfish_nand *nand = mtd->priv;
49 struct cmd_params *cps = nand->cmd_params;
50 unsigned char __iomem *base = nand->base;
51
52 if (!cps)
53 return -1;
54
55 switch (cmd) {
56 case NAND_CMD_ERASE:
57 cmdp = NAND_CMD_ERASE_WITH_PARAMS;
58 break;
59 case NAND_CMD_READ:
60 cmdp = NAND_CMD_READ_WITH_PARAMS;
61 break;
62 case NAND_CMD_WRITE:
63 cmdp = NAND_CMD_WRITE_WITH_PARAMS;
64 break;
65 default:
66 return -1;
67 }
68 cps->dev = mtd - nand->mtd;
69 cps->addr_high = (u32)(addr >> 32);
70 cps->addr_low = (u32)addr;
71 cps->transfer_size = len;
72 cps->data = (unsigned long)ptr;
73 writel(cmdp, base + NAND_COMMAND);
74 *rv = cps->result;
75 return 0;
76}
77
78static u32 goldfish_nand_cmd(struct mtd_info *mtd, enum nand_cmd cmd,
79 u64 addr, u32 len, void *ptr)
80{
81 struct goldfish_nand *nand = mtd->priv;
82 u32 rv;
83 unsigned char __iomem *base = nand->base;
84
85 mutex_lock(&nand->lock);
86 if (goldfish_nand_cmd_with_params(mtd, cmd, addr, len, ptr, &rv)) {
87 writel(mtd - nand->mtd, base + NAND_DEV);
88 writel((u32)(addr >> 32), base + NAND_ADDR_HIGH);
89 writel((u32)addr, base + NAND_ADDR_LOW);
90 writel(len, base + NAND_TRANSFER_SIZE);
91 gf_write_ptr(ptr, base + NAND_DATA, base + NAND_DATA_HIGH);
92 writel(cmd, base + NAND_COMMAND);
93 rv = readl(base + NAND_RESULT);
94 }
95 mutex_unlock(&nand->lock);
96 return rv;
97}
98
99static int goldfish_nand_erase(struct mtd_info *mtd, struct erase_info *instr)
100{
101 loff_t ofs = instr->addr;
102 u32 len = instr->len;
103 s32 rem;
104
105 if (ofs + len > mtd->size)
106 goto invalid_arg;
107 ofs = div_s64_rem(ofs, mtd->writesize, &rem);
108 if (rem)
109 goto invalid_arg;
110 ofs *= (mtd->writesize + mtd->oobsize);
111
112 if (len % mtd->writesize)
113 goto invalid_arg;
114 len = len / mtd->writesize * (mtd->writesize + mtd->oobsize);
115
116 if (goldfish_nand_cmd(mtd, NAND_CMD_ERASE, ofs, len, NULL) != len) {
117 pr_err("%s: erase failed, start %llx, len %x, dev_size %llx, erase_size %x\n",
118 __func__, ofs, len, mtd->size, mtd->erasesize);
119 return -EIO;
120 }
121
122 return 0;
123
124invalid_arg:
125 pr_err("%s: invalid erase, start %llx, len %x, dev_size %llx, erase_size %x\n",
126 __func__, ofs, len, mtd->size, mtd->erasesize);
127 return -EINVAL;
128}
129
130static int goldfish_nand_read_oob(struct mtd_info *mtd, loff_t ofs,
131 struct mtd_oob_ops *ops)
132{
133 s32 rem;
134
135 if (ofs + ops->len > mtd->size)
136 goto invalid_arg;
137 if (ops->datbuf && ops->len && ops->len != mtd->writesize)
138 goto invalid_arg;
139 if (ops->ooblen + ops->ooboffs > mtd->oobsize)
140 goto invalid_arg;
141
142 ofs = div_s64_rem(ofs, mtd->writesize, &rem);
143 if (rem)
144 goto invalid_arg;
145 ofs *= (mtd->writesize + mtd->oobsize);
146
147 if (ops->datbuf)
148 ops->retlen = goldfish_nand_cmd(mtd, NAND_CMD_READ, ofs,
149 ops->len, ops->datbuf);
150 ofs += mtd->writesize + ops->ooboffs;
151 if (ops->oobbuf)
152 ops->oobretlen = goldfish_nand_cmd(mtd, NAND_CMD_READ, ofs,
153 ops->ooblen, ops->oobbuf);
154 return 0;
155
156invalid_arg:
157 pr_err("%s: invalid read, start %llx, len %zx, ooblen %zx, dev_size %llx, write_size %x\n",
158 __func__, ofs, ops->len, ops->ooblen, mtd->size, mtd->writesize);
159 return -EINVAL;
160}
161
162static int goldfish_nand_write_oob(struct mtd_info *mtd, loff_t ofs,
163 struct mtd_oob_ops *ops)
164{
165 s32 rem;
166
167 if (ofs + ops->len > mtd->size)
168 goto invalid_arg;
169 if (ops->len && ops->len != mtd->writesize)
170 goto invalid_arg;
171 if (ops->ooblen + ops->ooboffs > mtd->oobsize)
172 goto invalid_arg;
173
174 ofs = div_s64_rem(ofs, mtd->writesize, &rem);
175 if (rem)
176 goto invalid_arg;
177 ofs *= (mtd->writesize + mtd->oobsize);
178
179 if (ops->datbuf)
180 ops->retlen = goldfish_nand_cmd(mtd, NAND_CMD_WRITE, ofs,
181 ops->len, ops->datbuf);
182 ofs += mtd->writesize + ops->ooboffs;
183 if (ops->oobbuf)
184 ops->oobretlen = goldfish_nand_cmd(mtd, NAND_CMD_WRITE, ofs,
185 ops->ooblen, ops->oobbuf);
186 return 0;
187
188invalid_arg:
189 pr_err("%s: invalid write, start %llx, len %zx, ooblen %zx, dev_size %llx, write_size %x\n",
190 __func__, ofs, ops->len, ops->ooblen, mtd->size, mtd->writesize);
191 return -EINVAL;
192}
193
194static int goldfish_nand_read(struct mtd_info *mtd, loff_t from, size_t len,
195 size_t *retlen, u_char *buf)
196{
197 s32 rem;
198
199 if (from + len > mtd->size)
200 goto invalid_arg;
201
202 from = div_s64_rem(from, mtd->writesize, &rem);
203 if (rem)
204 goto invalid_arg;
205 from *= (mtd->writesize + mtd->oobsize);
206
207 *retlen = goldfish_nand_cmd(mtd, NAND_CMD_READ, from, len, buf);
208 return 0;
209
210invalid_arg:
211 pr_err("%s: invalid read, start %llx, len %zx, dev_size %llx, write_size %x\n",
212 __func__, from, len, mtd->size, mtd->writesize);
213 return -EINVAL;
214}
215
216static int goldfish_nand_write(struct mtd_info *mtd, loff_t to, size_t len,
217 size_t *retlen, const u_char *buf)
218{
219 s32 rem;
220
221 if (to + len > mtd->size)
222 goto invalid_arg;
223
224 to = div_s64_rem(to, mtd->writesize, &rem);
225 if (rem)
226 goto invalid_arg;
227 to *= (mtd->writesize + mtd->oobsize);
228
229 *retlen = goldfish_nand_cmd(mtd, NAND_CMD_WRITE, to, len, (void *)buf);
230 return 0;
231
232invalid_arg:
233 pr_err("%s: invalid write, start %llx, len %zx, dev_size %llx, write_size %x\n",
234 __func__, to, len, mtd->size, mtd->writesize);
235 return -EINVAL;
236}
237
238static int goldfish_nand_block_isbad(struct mtd_info *mtd, loff_t ofs)
239{
240 s32 rem;
241
242 if (ofs >= mtd->size)
243 goto invalid_arg;
244
245 ofs = div_s64_rem(ofs, mtd->writesize, &rem);
246 if (rem)
247 goto invalid_arg;
248 ofs *= mtd->erasesize / mtd->writesize;
249 ofs *= (mtd->writesize + mtd->oobsize);
250
251 return goldfish_nand_cmd(mtd, NAND_CMD_BLOCK_BAD_GET, ofs, 0, NULL);
252
253invalid_arg:
254 pr_err("%s: invalid arg, ofs %llx, dev_size %llx, write_size %x\n",
255 __func__, ofs, mtd->size, mtd->writesize);
256 return -EINVAL;
257}
258
259static int goldfish_nand_block_markbad(struct mtd_info *mtd, loff_t ofs)
260{
261 s32 rem;
262
263 if (ofs >= mtd->size)
264 goto invalid_arg;
265
266 ofs = div_s64_rem(ofs, mtd->writesize, &rem);
267 if (rem)
268 goto invalid_arg;
269 ofs *= mtd->erasesize / mtd->writesize;
270 ofs *= (mtd->writesize + mtd->oobsize);
271
272 if (goldfish_nand_cmd(mtd, NAND_CMD_BLOCK_BAD_SET, ofs, 0, NULL) != 1)
273 return -EIO;
274 return 0;
275
276invalid_arg:
277 pr_err("%s: invalid arg, ofs %llx, dev_size %llx, write_size %x\n",
278 __func__, ofs, mtd->size, mtd->writesize);
279 return -EINVAL;
280}
281
282static int nand_setup_cmd_params(struct platform_device *pdev,
283 struct goldfish_nand *nand)
284{
285 dma_addr_t dma_handle;
286 unsigned char __iomem *base = nand->base;
287
288 nand->cmd_params = dmam_alloc_coherent(&pdev->dev,
289 sizeof(struct cmd_params),
290 &dma_handle, GFP_KERNEL);
291 if (!nand->cmd_params) {
292 dev_err(&pdev->dev, "allocate buffer failed\n");
293 return -ENOMEM;
294 }
295 writel((u32)((u64)dma_handle >> 32), base + NAND_CMD_PARAMS_ADDR_HIGH);
296 writel((u32)dma_handle, base + NAND_CMD_PARAMS_ADDR_LOW);
297 return 0;
298}
299
300static int goldfish_nand_init_device(struct platform_device *pdev,
301 struct goldfish_nand *nand, int id)
302{
303 u32 name_len;
304 u32 result;
305 u32 flags;
306 unsigned char __iomem *base = nand->base;
307 struct mtd_info *mtd = &nand->mtd[id];
308 char *name;
309
310 mutex_lock(&nand->lock);
311 writel(id, base + NAND_DEV);
312 flags = readl(base + NAND_DEV_FLAGS);
313 name_len = readl(base + NAND_DEV_NAME_LEN);
314 mtd->writesize = readl(base + NAND_DEV_PAGE_SIZE);
315 mtd->size = readl(base + NAND_DEV_SIZE_LOW);
316 mtd->size |= (u64)readl(base + NAND_DEV_SIZE_HIGH) << 32;
317 mtd->oobsize = readl(base + NAND_DEV_EXTRA_SIZE);
318 mtd->oobavail = mtd->oobsize;
319 mtd->erasesize = readl(base + NAND_DEV_ERASE_SIZE) /
320 (mtd->writesize + mtd->oobsize) * mtd->writesize;
321 mtd->size = div_s64(mtd->size, mtd->writesize + mtd->oobsize);
322 mtd->size *= mtd->writesize;
323 dev_dbg(&pdev->dev,
324 "goldfish nand dev%d: size %llx, page %d, extra %d, erase %d\n",
325 id, mtd->size, mtd->writesize,
326 mtd->oobsize, mtd->erasesize);
327 mutex_unlock(&nand->lock);
328
329 mtd->priv = nand;
330
331 name = devm_kzalloc(&pdev->dev, name_len + 1, GFP_KERNEL);
332 if (!name)
333 return -ENOMEM;
334 mtd->name = name;
335
336 result = goldfish_nand_cmd(mtd, NAND_CMD_GET_DEV_NAME, 0, name_len,
337 name);
338 if (result != name_len) {
339 dev_err(&pdev->dev,
340 "%s: failed to get dev name %d != %d\n",
341 __func__, result, name_len);
342 return -ENODEV;
343 }
344 ((char *)mtd->name)[name_len] = '\0';
345
346 /* Setup the MTD structure */
347 mtd->type = MTD_NANDFLASH;
348 mtd->flags = MTD_CAP_NANDFLASH;
349 if (flags & NAND_DEV_FLAG_READ_ONLY)
350 mtd->flags &= ~MTD_WRITEABLE;
351 if (flags & NAND_DEV_FLAG_CMD_PARAMS_CAP)
352 nand_setup_cmd_params(pdev, nand);
353
354 mtd->owner = THIS_MODULE;
355 mtd->_erase = goldfish_nand_erase;
356 mtd->_read = goldfish_nand_read;
357 mtd->_write = goldfish_nand_write;
358 mtd->_read_oob = goldfish_nand_read_oob;
359 mtd->_write_oob = goldfish_nand_write_oob;
360 mtd->_block_isbad = goldfish_nand_block_isbad;
361 mtd->_block_markbad = goldfish_nand_block_markbad;
362
363 if (mtd_device_register(mtd, NULL, 0))
364 return -EIO;
365
366 return 0;
367}
368
369static int goldfish_nand_probe(struct platform_device *pdev)
370{
371 u32 num_dev;
372 int i;
373 int err;
374 u32 num_dev_working;
375 u32 version;
376 struct resource *r;
377 struct goldfish_nand *nand;
378 unsigned char __iomem *base;
379
380 r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
381 if (!r)
382 return -ENODEV;
383
384 base = devm_ioremap(&pdev->dev, r->start, PAGE_SIZE);
385 if (!base)
386 return -ENOMEM;
387
388 version = readl(base + NAND_VERSION);
389 if (version != NAND_VERSION_CURRENT) {
390 dev_err(&pdev->dev,
391 "goldfish_nand_init: version mismatch, got %d, expected %d\n",
392 version, NAND_VERSION_CURRENT);
393 return -ENODEV;
394 }
395 num_dev = readl(base + NAND_NUM_DEV);
396 if (num_dev == 0)
397 return -ENODEV;
398
399 nand = devm_kzalloc(&pdev->dev, sizeof(*nand) +
400 sizeof(struct mtd_info) * num_dev, GFP_KERNEL);
401 if (!nand)
402 return -ENOMEM;
403
404 mutex_init(&nand->lock);
405 nand->base = base;
406 nand->mtd_count = num_dev;
407 platform_set_drvdata(pdev, nand);
408
409 num_dev_working = 0;
410 for (i = 0; i < num_dev; i++) {
411 err = goldfish_nand_init_device(pdev, nand, i);
412 if (err == 0)
413 num_dev_working++;
414 }
415 if (num_dev_working == 0)
416 return -ENODEV;
417 return 0;
418}
419
420static int goldfish_nand_remove(struct platform_device *pdev)
421{
422 struct goldfish_nand *nand = platform_get_drvdata(pdev);
423 int i;
424
425 for (i = 0; i < nand->mtd_count; i++) {
426 if (nand->mtd[i].name)
427 mtd_device_unregister(&nand->mtd[i]);
428 }
429 return 0;
430}
431
432static struct platform_driver goldfish_nand_driver = {
433 .probe = goldfish_nand_probe,
434 .remove = goldfish_nand_remove,
435 .driver = {
436 .name = "goldfish_nand"
437 }
438};
439
440module_platform_driver(goldfish_nand_driver);
441MODULE_LICENSE("GPL");
drivers/staging/goldfish/goldfish_nand_reg.h+0−76
@@ -1,76 +0,0 @@
1/*
2 * drivers/mtd/devices/goldfish_nand_reg.h
3 *
4 * Copyright (C) 2007 Google, Inc.
5 *
6 * This software is licensed under the terms of the GNU General Public
7 * License version 2, as published by the Free Software Foundation, and
8 * may be copied, distributed, and modified under those terms.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 */
16
17#ifndef GOLDFISH_NAND_REG_H
18#define GOLDFISH_NAND_REG_H
19
20enum nand_cmd {
21 /* Write device name for NAND_DEV to NAND_DATA (vaddr) */
22 NAND_CMD_GET_DEV_NAME,
23 NAND_CMD_READ,
24 NAND_CMD_WRITE,
25 NAND_CMD_ERASE,
26 /* NAND_RESULT is 1 if block is bad, 0 if it is not */
27 NAND_CMD_BLOCK_BAD_GET,
28 NAND_CMD_BLOCK_BAD_SET,
29 NAND_CMD_READ_WITH_PARAMS,
30 NAND_CMD_WRITE_WITH_PARAMS,
31 NAND_CMD_ERASE_WITH_PARAMS
32};
33
34enum nand_dev_flags {
35 NAND_DEV_FLAG_READ_ONLY = 0x00000001,
36 NAND_DEV_FLAG_CMD_PARAMS_CAP = 0x00000002,
37};
38
39#define NAND_VERSION_CURRENT (1)
40
41enum nand_reg {
42 /* Global */
43 NAND_VERSION = 0x000,
44 NAND_NUM_DEV = 0x004,
45 NAND_DEV = 0x008,
46
47 /* Dev info */
48 NAND_DEV_FLAGS = 0x010,
49 NAND_DEV_NAME_LEN = 0x014,
50 NAND_DEV_PAGE_SIZE = 0x018,
51 NAND_DEV_EXTRA_SIZE = 0x01c,
52 NAND_DEV_ERASE_SIZE = 0x020,
53 NAND_DEV_SIZE_LOW = 0x028,
54 NAND_DEV_SIZE_HIGH = 0x02c,
55
56 /* Command */
57 NAND_RESULT = 0x040,
58 NAND_COMMAND = 0x044,
59 NAND_DATA = 0x048,
60 NAND_DATA_HIGH = 0x100,
61 NAND_TRANSFER_SIZE = 0x04c,
62 NAND_ADDR_LOW = 0x050,
63 NAND_ADDR_HIGH = 0x054,
64 NAND_CMD_PARAMS_ADDR_LOW = 0x058,
65 NAND_CMD_PARAMS_ADDR_HIGH = 0x05c,
66};
67
68struct cmd_params {
69 u32 dev;
70 u32 addr_low;
71 u32 addr_high;
72 u32 transfer_size;
73 unsigned long data;
74 u32 result;
75};
76#endif
drivers/staging/greybus/TODO+5−0
@@ -0,0 +1,5 @@
1* Convert all uses of the old GPIO API from <linux/gpio.h> to the
2 GPIO descriptor API in <linux/gpio/consumer.h> and look up GPIO
3 lines from device tree or ACPI.
4* Convert the GPIO driver to use the GPIO irqchip library
5 GPIOLIB_IRQCHIP instead of reimplementing the same.
drivers/staging/greybus/arche-platform.c+4−5
@@ -315,8 +315,7 @@ static ssize_t state_store(struct device *dev, · 314 unmodified lines
315 struct device_attribute *attr,315 struct device_attribute *attr,
316 const char *buf, size_t count)316 const char *buf, size_t count)
317{317{
318 struct platform_device *pdev = to_platform_device(dev);318 struct arche_platform_drvdata *arche_pdata = dev_get_drvdata(dev);
319 struct arche_platform_drvdata *arche_pdata = platform_get_drvdata(pdev);
320 int ret = 0;319 int ret = 0;
321 320
322 mutex_lock(&arche_pdata->platform_state_mutex);321 mutex_lock(&arche_pdata->platform_state_mutex);
@@ -448,7 +447,7 @@ static int arche_platform_probe(struct platform_device *pdev) · 125 unmodified lines
448 arche_pdata->svc_reset_gpio = of_get_named_gpio(np,447 arche_pdata->svc_reset_gpio = of_get_named_gpio(np,
449 "svc,reset-gpio",448 "svc,reset-gpio",
450 0);449 0);
451 if (arche_pdata->svc_reset_gpio < 0) {450 if (!gpio_is_valid(arche_pdata->svc_reset_gpio)) {
452 dev_err(dev, "failed to get reset-gpio\n");451 dev_err(dev, "failed to get reset-gpio\n");
453 return arche_pdata->svc_reset_gpio;452 return arche_pdata->svc_reset_gpio;
454 }453 }
@@ -468,7 +467,7 @@ static int arche_platform_probe(struct platform_device *pdev) · 13 unmodified lines
468 arche_pdata->svc_sysboot_gpio = of_get_named_gpio(np,467 arche_pdata->svc_sysboot_gpio = of_get_named_gpio(np,
469 "svc,sysboot-gpio",468 "svc,sysboot-gpio",
470 0);469 0);
471 if (arche_pdata->svc_sysboot_gpio < 0) {470 if (!gpio_is_valid(arche_pdata->svc_sysboot_gpio)) {
472 dev_err(dev, "failed to get sysboot gpio\n");471 dev_err(dev, "failed to get sysboot gpio\n");
473 return arche_pdata->svc_sysboot_gpio;472 return arche_pdata->svc_sysboot_gpio;
474 }473 }
@@ -487,7 +486,7 @@ static int arche_platform_probe(struct platform_device *pdev) · 12 unmodified lines
487 arche_pdata->svc_refclk_req = of_get_named_gpio(np,486 arche_pdata->svc_refclk_req = of_get_named_gpio(np,
488 "svc,refclk-req-gpio",487 "svc,refclk-req-gpio",
489 0);488 0);
490 if (arche_pdata->svc_refclk_req < 0) {489 if (!gpio_is_valid(arche_pdata->svc_refclk_req)) {
491 dev_err(dev, "failed to get svc clock-req gpio\n");490 dev_err(dev, "failed to get svc clock-req gpio\n");
492 return arche_pdata->svc_refclk_req;491 return arche_pdata->svc_refclk_req;
493 }492 }
drivers/staging/greybus/audio_codec.h+4−1
@@ -23,7 +23,10 @@ enum { · 22 unmodified lines
23 NUM_CODEC_DAIS,23 NUM_CODEC_DAIS,
24};24};
25 25
26/* device_type should be same as defined in audio.h (Android media layer) */26/*
27 * device_type should be same as defined in audio.h
28 * (Android media layer)
29 */
27enum {30enum {
28 GBAUDIO_DEVICE_NONE = 0x0,31 GBAUDIO_DEVICE_NONE = 0x0,
29 /* reserved bits */32 /* reserved bits */
drivers/staging/greybus/audio_topology.c+1−1
@@ -996,7 +996,7 @@ static int gbaudio_tplg_create_widget(struct gbaudio_module_info *module, · 995 unmodified lines
996 996
997 ret = gbaudio_validate_kcontrol_count(w);997 ret = gbaudio_validate_kcontrol_count(w);
998 if (ret) {998 if (ret) {
999 dev_err(module->dev, "Inavlid kcontrol count=%d for %s\n",999 dev_err(module->dev, "Invalid kcontrol count=%d for %s\n",
1000 w->ncontrols, w->name);1000 w->ncontrols, w->name);
1001 return ret;1001 return ret;
1002 }1002 }
drivers/staging/greybus/camera.c+3−14
@@ -1174,11 +1174,6 @@ static int gb_camera_debugfs_init(struct gb_camera *gcam) · 1173 unmodified lines
1174 gcam->bundle->id);1174 gcam->bundle->id);
1175 1175
1176 gcam->debugfs.root = debugfs_create_dir(dirname, gb_debugfs_get());1176 gcam->debugfs.root = debugfs_create_dir(dirname, gb_debugfs_get());
1177 if (IS_ERR(gcam->debugfs.root)) {
1178 gcam_err(gcam, "debugfs root create failed (%ld)\n",
1179 PTR_ERR(gcam->debugfs.root));
1180 return PTR_ERR(gcam->debugfs.root);
1181 }
1182 1177
1183 gcam->debugfs.buffers = vmalloc(sizeof(*gcam->debugfs.buffers) *1178 gcam->debugfs.buffers = vmalloc(sizeof(*gcam->debugfs.buffers) *
1184 GB_CAMERA_DEBUGFS_BUFFER_MAX);1179 GB_CAMERA_DEBUGFS_BUFFER_MAX);
@@ -1188,18 +1183,12 @@ static int gb_camera_debugfs_init(struct gb_camera *gcam) · 3 unmodified lines
1188 for (i = 0; i < ARRAY_SIZE(gb_camera_debugfs_entries); ++i) {1183 for (i = 0; i < ARRAY_SIZE(gb_camera_debugfs_entries); ++i) {
1189 const struct gb_camera_debugfs_entry *entry =1184 const struct gb_camera_debugfs_entry *entry =
1190 &gb_camera_debugfs_entries[i];1185 &gb_camera_debugfs_entries[i];
1191 struct dentry *dentry;
1192 1186
1193 gcam->debugfs.buffers[i].length = 0;1187 gcam->debugfs.buffers[i].length = 0;
1194 1188
1195 dentry = debugfs_create_file(entry->name, entry->mask,1189 debugfs_create_file(entry->name, entry->mask,
1196 gcam->debugfs.root, gcam,1190 gcam->debugfs.root, gcam,
1197 &gb_camera_debugfs_ops);1191 &gb_camera_debugfs_ops);
1198 if (IS_ERR(dentry)) {
1199 gcam_err(gcam,
1200 "debugfs operation %s create failed (%ld)\n",
1201 entry->name, PTR_ERR(dentry));
1202 return PTR_ERR(dentry);
1203 }1192 }
1204 }1193 }
1205 1194
drivers/staging/greybus/svc.c+0−3
@@ -1137,7 +1137,6 @@ static int gb_svc_intf_reset_recv(struct gb_operation *op) · 1136 unmodified lines
1137 struct gb_svc *svc = gb_connection_get_data(op->connection);1137 struct gb_svc *svc = gb_connection_get_data(op->connection);
1138 struct gb_message *request = op->request;1138 struct gb_message *request = op->request;
1139 struct gb_svc_intf_reset_request *reset;1139 struct gb_svc_intf_reset_request *reset;
1140 u8 intf_id;
1141 1140
1142 if (request->payload_size < sizeof(*reset)) {1141 if (request->payload_size < sizeof(*reset)) {
1143 dev_warn(&svc->dev, "short reset request received (%zu < %zu)\n",1142 dev_warn(&svc->dev, "short reset request received (%zu < %zu)\n",
@@ -1146,8 +1145,6 @@ static int gb_svc_intf_reset_recv(struct gb_operation *op) · 2 unmodified lines
1146 }1145 }
1147 reset = request->payload;1146 reset = request->payload;
1148 1147
1149 intf_id = reset->intf_id;
1150
1151 /* FIXME Reset the interface here */1148 /* FIXME Reset the interface here */
1152 1149
1153 return 0;1150 return 0;
drivers/staging/iio/Kconfig+0−1
@@ -11,7 +11,6 @@ source "drivers/staging/iio/cdc/Kconfig" · 10 unmodified lines
11source "drivers/staging/iio/frequency/Kconfig"11source "drivers/staging/iio/frequency/Kconfig"
12source "drivers/staging/iio/gyro/Kconfig"12source "drivers/staging/iio/gyro/Kconfig"
13source "drivers/staging/iio/impedance-analyzer/Kconfig"13source "drivers/staging/iio/impedance-analyzer/Kconfig"
14source "drivers/staging/iio/light/Kconfig"
15source "drivers/staging/iio/meter/Kconfig"14source "drivers/staging/iio/meter/Kconfig"
16source "drivers/staging/iio/resolver/Kconfig"15source "drivers/staging/iio/resolver/Kconfig"
17 16
drivers/staging/iio/Makefile+0−1
@@ -10,6 +10,5 @@ obj-y += cdc/ · 9 unmodified lines
10obj-y += frequency/10obj-y += frequency/
11obj-y += gyro/11obj-y += gyro/
12obj-y += impedance-analyzer/12obj-y += impedance-analyzer/
13obj-y += light/
14obj-y += meter/13obj-y += meter/
15obj-y += resolver/14obj-y += resolver/
drivers/staging/iio/TODO+8−1
@@ -1,4 +1,11 @@
12016 10/0912018-04-15
2
3All affected drivers:
4Convert all uses of the old GPIO API from <linux/gpio.h> to the
5GPIO descriptor API in <linux/gpio/consumer.h> and look up GPIO
6lines from device tree, ACPI or board files, board files should
7use <linux/gpio/machine.h>.
8
2 9
3ADI Drivers:10ADI Drivers:
4CC the device-drivers-devel@blackfin.uclinux.org mailing list when11CC the device-drivers-devel@blackfin.uclinux.org mailing list when
drivers/staging/iio/accel/Kconfig+0−24
@@ -3,18 +3,6 @@ · 2 unmodified lines
3#3#
4menu "Accelerometers"4menu "Accelerometers"
5 5
6config ADIS16201
7 tristate "Analog Devices ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer"
8 depends on SPI
9 select IIO_ADIS_LIB
10 select IIO_ADIS_LIB_BUFFER if IIO_BUFFER
11 help
12 Say Y here to build support for Analog Devices adis16201 dual-axis
13 digital inclinometer and accelerometer.
14
15 To compile this driver as a module, say M here: the module will
16 be called adis16201.
17
18config ADIS162036config ADIS16203
19 tristate "Analog Devices ADIS16203 Programmable 360 Degrees Inclinometer"7 tristate "Analog Devices ADIS16203 Programmable 360 Degrees Inclinometer"
20 depends on SPI8 depends on SPI
@@ -27,18 +15,6 @@ config ADIS16203 · 6 unmodified lines
27 To compile this driver as a module, say M here: the module will be15 To compile this driver as a module, say M here: the module will be
28 called adis16203.16 called adis16203.
29 17
30config ADIS16209
31 tristate "Analog Devices ADIS16209 Dual-Axis Digital Inclinometer and Accelerometer"
32 depends on SPI
33 select IIO_ADIS_LIB
34 select IIO_ADIS_LIB_BUFFER if IIO_BUFFER
35 help
36 Say Y here to build support for Analog Devices adis16209 dual-axis digital inclinometer
37 and accelerometer.
38
39 To compile this driver as a module, say M here: the module will be
40 called adis16209.
41
42config ADIS1624018config ADIS16240
43 tristate "Analog Devices ADIS16240 Programmable Impact Sensor and Recorder"19 tristate "Analog Devices ADIS16240 Programmable Impact Sensor and Recorder"
44 depends on SPI20 depends on SPI
drivers/staging/iio/accel/Makefile+0−2
@@ -2,7 +2,5 @@ · 1 unmodified line
2# Makefile for industrial I/O accelerometer drivers2# Makefile for industrial I/O accelerometer drivers
3#3#
4 4
5obj-$(CONFIG_ADIS16201) += adis16201.o
6obj-$(CONFIG_ADIS16203) += adis16203.o5obj-$(CONFIG_ADIS16203) += adis16203.o
7obj-$(CONFIG_ADIS16209) += adis16209.o
8obj-$(CONFIG_ADIS16240) += adis16240.o6obj-$(CONFIG_ADIS16240) += adis16240.o
drivers/staging/iio/accel/adis16201.c+0−385
@@ -1,385 +0,0 @@
1/*
2 * ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer
3 *
4 * Copyright 2010 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2 or later.
7 */
8
9#include <linux/delay.h>
10#include <linux/device.h>
11#include <linux/kernel.h>
12#include <linux/module.h>
13#include <linux/mutex.h>
14#include <linux/slab.h>
15#include <linux/spi/spi.h>
16#include <linux/sysfs.h>
17
18#include <linux/iio/iio.h>
19#include <linux/iio/sysfs.h>
20#include <linux/iio/buffer.h>
21#include <linux/iio/imu/adis.h>
22
23#define ADIS16201_STARTUP_DELAY 220 /* ms */
24
25/* Flash memory write count */
26#define ADIS16201_FLASH_CNT 0x00
27
28/* Output, power supply */
29#define ADIS16201_SUPPLY_OUT 0x02
30
31/* Output, x-axis accelerometer */
32#define ADIS16201_XACCL_OUT 0x04
33
34/* Output, y-axis accelerometer */
35#define ADIS16201_YACCL_OUT 0x06
36
37/* Output, auxiliary ADC input */
38#define ADIS16201_AUX_ADC 0x08
39
40/* Output, temperature */
41#define ADIS16201_TEMP_OUT 0x0A
42
43/* Output, x-axis inclination */
44#define ADIS16201_XINCL_OUT 0x0C
45
46/* Output, y-axis inclination */
47#define ADIS16201_YINCL_OUT 0x0E
48
49/* Calibration, x-axis acceleration offset */
50#define ADIS16201_XACCL_OFFS 0x10
51
52/* Calibration, y-axis acceleration offset */
53#define ADIS16201_YACCL_OFFS 0x12
54
55/* x-axis acceleration scale factor */
56#define ADIS16201_XACCL_SCALE 0x14
57
58/* y-axis acceleration scale factor */
59#define ADIS16201_YACCL_SCALE 0x16
60
61/* Calibration, x-axis inclination offset */
62#define ADIS16201_XINCL_OFFS 0x18
63
64/* Calibration, y-axis inclination offset */
65#define ADIS16201_YINCL_OFFS 0x1A
66
67/* x-axis inclination scale factor */
68#define ADIS16201_XINCL_SCALE 0x1C
69
70/* y-axis inclination scale factor */
71#define ADIS16201_YINCL_SCALE 0x1E
72
73/* Alarm 1 amplitude threshold */
74#define ADIS16201_ALM_MAG1 0x20
75
76/* Alarm 2 amplitude threshold */
77#define ADIS16201_ALM_MAG2 0x22
78
79/* Alarm 1, sample period */
80#define ADIS16201_ALM_SMPL1 0x24
81
82/* Alarm 2, sample period */
83#define ADIS16201_ALM_SMPL2 0x26
84
85/* Alarm control */
86#define ADIS16201_ALM_CTRL 0x28
87
88/* Auxiliary DAC data */
89#define ADIS16201_AUX_DAC 0x30
90
91/* General-purpose digital input/output control */
92#define ADIS16201_GPIO_CTRL 0x32
93
94/* Miscellaneous control */
95#define ADIS16201_MSC_CTRL 0x34
96
97/* Internal sample period (rate) control */
98#define ADIS16201_SMPL_PRD 0x36
99
100/* Operation, filter configuration */
101#define ADIS16201_AVG_CNT 0x38
102
103/* Operation, sleep mode control */
104#define ADIS16201_SLP_CNT 0x3A
105
106/* Diagnostics, system status register */
107#define ADIS16201_DIAG_STAT 0x3C
108
109/* Operation, system command register */
110#define ADIS16201_GLOB_CMD 0x3E
111
112/* MSC_CTRL */
113
114/* Self-test enable */
115#define ADIS16201_MSC_CTRL_SELF_TEST_EN BIT(8)
116
117/* Data-ready enable: 1 = enabled, 0 = disabled */
118#define ADIS16201_MSC_CTRL_DATA_RDY_EN BIT(2)
119
120/* Data-ready polarity: 1 = active high, 0 = active low */
121#define ADIS16201_MSC_CTRL_ACTIVE_HIGH BIT(1)
122
123/* Data-ready line selection: 1 = DIO1, 0 = DIO0 */
124#define ADIS16201_MSC_CTRL_DATA_RDY_DIO1 BIT(0)
125
126/* DIAG_STAT */
127
128/* Alarm 2 status: 1 = alarm active, 0 = alarm inactive */
129#define ADIS16201_DIAG_STAT_ALARM2 BIT(9)
130
131/* Alarm 1 status: 1 = alarm active, 0 = alarm inactive */
132#define ADIS16201_DIAG_STAT_ALARM1 BIT(8)
133
134/* SPI communications failure */
135#define ADIS16201_DIAG_STAT_SPI_FAIL_BIT 3
136
137/* Flash update failure */
138#define ADIS16201_DIAG_STAT_FLASH_UPT_BIT 2
139
140/* Power supply above 3.625 V */
141#define ADIS16201_DIAG_STAT_POWER_HIGH_BIT 1
142
143/* Power supply below 3.15 V */
144#define ADIS16201_DIAG_STAT_POWER_LOW_BIT 0
145
146/* GLOB_CMD */
147
148#define ADIS16201_GLOB_CMD_SW_RESET BIT(7)
149#define ADIS16201_GLOB_CMD_FACTORY_CAL BIT(1)
150
151#define ADIS16201_ERROR_ACTIVE BIT(14)
152
153enum adis16201_scan {
154 ADIS16201_SCAN_ACC_X,
155 ADIS16201_SCAN_ACC_Y,
156 ADIS16201_SCAN_INCLI_X,
157 ADIS16201_SCAN_INCLI_Y,
158 ADIS16201_SCAN_SUPPLY,
159 ADIS16201_SCAN_AUX_ADC,
160 ADIS16201_SCAN_TEMP,
161};
162
163static const u8 adis16201_addresses[] = {
164 [ADIS16201_SCAN_ACC_X] = ADIS16201_XACCL_OFFS,
165 [ADIS16201_SCAN_ACC_Y] = ADIS16201_YACCL_OFFS,
166 [ADIS16201_SCAN_INCLI_X] = ADIS16201_XINCL_OFFS,
167 [ADIS16201_SCAN_INCLI_Y] = ADIS16201_YINCL_OFFS,
168};
169
170static int adis16201_read_raw(struct iio_dev *indio_dev,
171 struct iio_chan_spec const *chan,
172 int *val, int *val2,
173 long mask)
174{
175 struct adis *st = iio_priv(indio_dev);
176 int ret;
177 int bits;
178 u8 addr;
179 s16 val16;
180
181 switch (mask) {
182 case IIO_CHAN_INFO_RAW:
183 return adis_single_conversion(indio_dev, chan,
184 ADIS16201_ERROR_ACTIVE, val);
185 case IIO_CHAN_INFO_SCALE:
186 switch (chan->type) {
187 case IIO_VOLTAGE:
188 if (chan->channel == 0) {
189 *val = 1;
190 *val2 = 220000; /* 1.22 mV */
191 } else {
192 *val = 0;
193 *val2 = 610000; /* 0.610 mV */
194 }
195 return IIO_VAL_INT_PLUS_MICRO;
196 case IIO_TEMP:
197 *val = -470; /* 0.47 C */
198 *val2 = 0;
199 return IIO_VAL_INT_PLUS_MICRO;
200 case IIO_ACCEL:
201 *val = 0;
202 *val2 = IIO_G_TO_M_S_2(462400); /* 0.4624 mg */
203 return IIO_VAL_INT_PLUS_NANO;
204 case IIO_INCLI:
205 *val = 0;
206 *val2 = 100000; /* 0.1 degree */
207 return IIO_VAL_INT_PLUS_MICRO;
208 default:
209 return -EINVAL;
210 }
211 break;
212 case IIO_CHAN_INFO_OFFSET:
213 *val = 25000 / -470 - 1278; /* 25 C = 1278 */
214 return IIO_VAL_INT;
215 case IIO_CHAN_INFO_CALIBBIAS:
216 switch (chan->type) {
217 case IIO_ACCEL:
218 bits = 12;
219 break;
220 case IIO_INCLI:
221 bits = 9;
222 break;
223 default:
224 return -EINVAL;
225 }
226 addr = adis16201_addresses[chan->scan_index];
227 ret = adis_read_reg_16(st, addr, &val16);
228 if (ret)
229 return ret;
230 val16 &= (1 << bits) - 1;
231 val16 = (s16)(val16 << (16 - bits)) >> (16 - bits);
232 *val = val16;
233 return IIO_VAL_INT;
234 }
235
236 return -EINVAL;
237}
238
239static int adis16201_write_raw(struct iio_dev *indio_dev,
240 struct iio_chan_spec const *chan,
241 int val,
242 int val2,
243 long mask)
244{
245 struct adis *st = iio_priv(indio_dev);
246 int bits;
247 s16 val16;
248 u8 addr;
249
250 switch (mask) {
251 case IIO_CHAN_INFO_CALIBBIAS:
252 switch (chan->type) {
253 case IIO_ACCEL:
254 bits = 12;
255 break;
256 case IIO_INCLI:
257 bits = 9;
258 break;
259 default:
260 return -EINVAL;
261 }
262 val16 = val & ((1 << bits) - 1);
263 addr = adis16201_addresses[chan->scan_index];
264 return adis_write_reg_16(st, addr, val16);
265 }
266
267 return -EINVAL;
268}
269
270static const struct iio_chan_spec adis16201_channels[] = {
271 ADIS_SUPPLY_CHAN(ADIS16201_SUPPLY_OUT, ADIS16201_SCAN_SUPPLY, 0, 12),
272 ADIS_TEMP_CHAN(ADIS16201_TEMP_OUT, ADIS16201_SCAN_TEMP, 0, 12),
273 ADIS_ACCEL_CHAN(X, ADIS16201_XACCL_OUT, ADIS16201_SCAN_ACC_X,
274 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
275 ADIS_ACCEL_CHAN(Y, ADIS16201_YACCL_OUT, ADIS16201_SCAN_ACC_Y,
276 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
277 ADIS_AUX_ADC_CHAN(ADIS16201_AUX_ADC, ADIS16201_SCAN_AUX_ADC, 0, 12),
278 ADIS_INCLI_CHAN(X, ADIS16201_XINCL_OUT, ADIS16201_SCAN_INCLI_X,
279 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
280 ADIS_INCLI_CHAN(X, ADIS16201_YINCL_OUT, ADIS16201_SCAN_INCLI_Y,
281 BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14),
282 IIO_CHAN_SOFT_TIMESTAMP(7)
283};
284
285static const struct iio_info adis16201_info = {
286 .read_raw = adis16201_read_raw,
287 .write_raw = adis16201_write_raw,
288 .update_scan_mode = adis_update_scan_mode,
289};
290
291static const char * const adis16201_status_error_msgs[] = {
292 [ADIS16201_DIAG_STAT_SPI_FAIL_BIT] = "SPI failure",
293 [ADIS16201_DIAG_STAT_FLASH_UPT_BIT] = "Flash update failed",
294 [ADIS16201_DIAG_STAT_POWER_HIGH_BIT] = "Power supply above 3.625V",
295 [ADIS16201_DIAG_STAT_POWER_LOW_BIT] = "Power supply below 3.15V",
296};
297
298static const struct adis_data adis16201_data = {
299 .read_delay = 20,
300 .msc_ctrl_reg = ADIS16201_MSC_CTRL,
301 .glob_cmd_reg = ADIS16201_GLOB_CMD,
302 .diag_stat_reg = ADIS16201_DIAG_STAT,
303
304 .self_test_mask = ADIS16201_MSC_CTRL_SELF_TEST_EN,
305 .self_test_no_autoclear = true,
306 .startup_delay = ADIS16201_STARTUP_DELAY,
307
308 .status_error_msgs = adis16201_status_error_msgs,
309 .status_error_mask = BIT(ADIS16201_DIAG_STAT_SPI_FAIL_BIT) |
310 BIT(ADIS16201_DIAG_STAT_FLASH_UPT_BIT) |
311 BIT(ADIS16201_DIAG_STAT_POWER_HIGH_BIT) |
312 BIT(ADIS16201_DIAG_STAT_POWER_LOW_BIT),
313};
314
315static int adis16201_probe(struct spi_device *spi)
316{
317 int ret;
318 struct adis *st;
319 struct iio_dev *indio_dev;
320
321 /* setup the industrialio driver allocated elements */
322 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
323 if (!indio_dev)
324 return -ENOMEM;
325
326 st = iio_priv(indio_dev);
327 /* this is only used for removal purposes */
328 spi_set_drvdata(spi, indio_dev);
329
330 indio_dev->name = spi->dev.driver->name;
331 indio_dev->dev.parent = &spi->dev;
332 indio_dev->info = &adis16201_info;
333
334 indio_dev->channels = adis16201_channels;
335 indio_dev->num_channels = ARRAY_SIZE(adis16201_channels);
336 indio_dev->modes = INDIO_DIRECT_MODE;
337
338 ret = adis_init(st, indio_dev, spi, &adis16201_data);
339 if (ret)
340 return ret;
341
342 ret = adis_setup_buffer_and_trigger(st, indio_dev, NULL);
343 if (ret)
344 return ret;
345
346 /* Get the device into a sane initial state */
347 ret = adis_initial_startup(st);
348 if (ret)
349 goto error_cleanup_buffer_trigger;
350
351 ret = iio_device_register(indio_dev);
352 if (ret < 0)
353 goto error_cleanup_buffer_trigger;
354
355 return 0;
356
357error_cleanup_buffer_trigger:
358 adis_cleanup_buffer_and_trigger(st, indio_dev);
359 return ret;
360}
361
362static int adis16201_remove(struct spi_device *spi)
363{
364 struct iio_dev *indio_dev = spi_get_drvdata(spi);
365 struct adis *st = iio_priv(indio_dev);
366
367 iio_device_unregister(indio_dev);
368 adis_cleanup_buffer_and_trigger(st, indio_dev);
369
370 return 0;
371}
372
373static struct spi_driver adis16201_driver = {
374 .driver = {
375 .name = "adis16201",
376 },
377 .probe = adis16201_probe,
378 .remove = adis16201_remove,
379};
380module_spi_driver(adis16201_driver);
381
382MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
383MODULE_DESCRIPTION("Analog Devices ADIS16201 Dual-Axis Digital Inclinometer and Accelerometer");
384MODULE_LICENSE("GPL v2");
385MODULE_ALIAS("spi:adis16201");
drivers/staging/iio/adc/ad7606_par.c+2−4
@@ -18,8 +18,7 @@ · 17 unmodified lines
18static int ad7606_par16_read_block(struct device *dev,18static int ad7606_par16_read_block(struct device *dev,
19 int count, void *buf)19 int count, void *buf)
20{20{
21 struct platform_device *pdev = to_platform_device(dev);21 struct iio_dev *indio_dev = dev_get_drvdata(dev);
22 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
23 struct ad7606_state *st = iio_priv(indio_dev);22 struct ad7606_state *st = iio_priv(indio_dev);
24 23
25 insw((unsigned long)st->base_address, buf, count);24 insw((unsigned long)st->base_address, buf, count);
@@ -34,8 +33,7 @@ static const struct ad7606_bus_ops ad7606_par16_bops = { · 8 unmodified lines
34static int ad7606_par8_read_block(struct device *dev,33static int ad7606_par8_read_block(struct device *dev,
35 int count, void *buf)34 int count, void *buf)
36{35{
37 struct platform_device *pdev = to_platform_device(dev);36 struct iio_dev *indio_dev = dev_get_drvdata(dev);
38 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
39 struct ad7606_state *st = iio_priv(indio_dev);37 struct ad7606_state *st = iio_priv(indio_dev);
40 38
41 insb((unsigned long)st->base_address, buf, count * 2);39 insb((unsigned long)st->base_address, buf, count * 2);
drivers/staging/iio/adc/ad7780.c+1−1
@@ -128,7 +128,7 @@ static const struct ad_sigma_delta_info ad7780_sigma_delta_info = { · 127 unmodified lines
128};128};
129 129
130#define AD7780_CHANNEL(bits, wordsize) \130#define AD7780_CHANNEL(bits, wordsize) \
131 AD_SD_CHANNEL(1, 0, 0, bits, 32, wordsize - bits)131 AD_SD_CHANNEL_NO_SAMP_FREQ(1, 0, 0, bits, 32, wordsize - bits)
132 132
133static const struct ad7780_chip_info ad7780_chip_info_tbl[] = {133static const struct ad7780_chip_info ad7780_chip_info_tbl[] = {
134 [ID_AD7170] = {134 [ID_AD7170] = {
drivers/staging/iio/cdc/ad7746.c+22−22
@@ -6,15 +6,15 @@ · 5 unmodified lines
6 * Licensed under the GPL-2.6 * Licensed under the GPL-2.
7 */7 */
8 8
9#include <linux/interrupt.h>9#include <linux/delay.h>
10#include <linux/device.h>10#include <linux/device.h>
11#include <linux/kernel.h>
12#include <linux/slab.h>
13#include <linux/sysfs.h>
14#include <linux/i2c.h>11#include <linux/i2c.h>
15#include <linux/delay.h>12#include <linux/interrupt.h>
13#include <linux/kernel.h>
16#include <linux/module.h>14#include <linux/module.h>
15#include <linux/slab.h>
17#include <linux/stat.h>16#include <linux/stat.h>
17#include <linux/sysfs.h>
18 18
19#include <linux/iio/iio.h>19#include <linux/iio/iio.h>
20#include <linux/iio/sysfs.h>20#include <linux/iio/sysfs.h>
@@ -220,8 +220,8 @@ static int ad7746_select_channel(struct iio_dev *indio_dev, · 199 unmodified lines
220 struct iio_chan_spec const *chan)220 struct iio_chan_spec const *chan)
221{221{
222 struct ad7746_chip_info *chip = iio_priv(indio_dev);222 struct ad7746_chip_info *chip = iio_priv(indio_dev);
223 int ret, delay, idx;
224 u8 vt_setup, cap_setup;223 u8 vt_setup, cap_setup;
224 int ret, delay, idx;
225 225
226 switch (chan->type) {226 switch (chan->type) {
227 case IIO_CAPACITANCE:227 case IIO_CAPACITANCE:
@@ -289,8 +289,8 @@ static inline ssize_t ad7746_start_calib(struct device *dev, · 61 unmodified lines
289{289{
290 struct iio_dev *indio_dev = dev_to_iio_dev(dev);290 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
291 struct ad7746_chip_info *chip = iio_priv(indio_dev);291 struct ad7746_chip_info *chip = iio_priv(indio_dev);
292 bool doit;
293 int ret, timeout = 10;292 int ret, timeout = 10;
293 bool doit;
294 294
295 ret = strtobool(buf, &doit);295 ret = strtobool(buf, &doit);
296 if (ret < 0)296 if (ret < 0)
@@ -410,8 +410,7 @@ static struct attribute *ad7746_attributes[] = { · 113 unmodified lines
410 &iio_dev_attr_in_capacitance1_calibbias_calibration.dev_attr.attr,410 &iio_dev_attr_in_capacitance1_calibbias_calibration.dev_attr.attr,
411 &iio_dev_attr_in_voltage0_calibscale_calibration.dev_attr.attr,411 &iio_dev_attr_in_voltage0_calibscale_calibration.dev_attr.attr,
412 &iio_const_attr_in_voltage_sampling_frequency_available.dev_attr.attr,412 &iio_const_attr_in_voltage_sampling_frequency_available.dev_attr.attr,
413 &iio_const_attr_in_capacitance_sampling_frequency_available.413 &iio_const_attr_in_capacitance_sampling_frequency_available.dev_attr.attr,
414 dev_attr.attr,
415 NULL,414 NULL,
416};415};
417 416
@@ -451,26 +450,26 @@ static int ad7746_write_raw(struct iio_dev *indio_dev, · 33 unmodified lines
451 goto out;450 goto out;
452 }451 }
453 452
454 ret = i2c_smbus_write_word_data(chip->client, reg, swab16(val));453 ret = i2c_smbus_write_word_swapped(chip->client, reg, val);
455 if (ret < 0)454 if (ret < 0)
456 goto out;455 goto out;
457 456
458 ret = 0;457 ret = 0;
459 break;458 break;
460 case IIO_CHAN_INFO_CALIBBIAS:459 case IIO_CHAN_INFO_CALIBBIAS:
461 if ((val < 0) | (val > 0xFFFF)) {460 if (val < 0 || val > 0xFFFF) {
462 ret = -EINVAL;461 ret = -EINVAL;
463 goto out;462 goto out;
464 }463 }
465 ret = i2c_smbus_write_word_data(chip->client,464 ret = i2c_smbus_write_word_swapped(chip->client,
466 AD7746_REG_CAP_OFFH, swab16(val));465 AD7746_REG_CAP_OFFH, val);
467 if (ret < 0)466 if (ret < 0)
468 goto out;467 goto out;
469 468
470 ret = 0;469 ret = 0;
471 break;470 break;
472 case IIO_CHAN_INFO_OFFSET:471 case IIO_CHAN_INFO_OFFSET:
473 if ((val < 0) | (val > 43008000)) { /* 21pF */472 if (val < 0 || val > 43008000) { /* 21pF */
474 ret = -EINVAL;473 ret = -EINVAL;
475 goto out;474 goto out;
476 }475 }
@@ -556,7 +555,8 @@ static int ad7746_read_raw(struct iio_dev *indio_dev, · 79 unmodified lines
556 /* Now read the actual register */555 /* Now read the actual register */
557 556
558 ret = i2c_smbus_read_i2c_block_data(chip->client,557 ret = i2c_smbus_read_i2c_block_data(chip->client,
559 chan->address >> 8, 3, &chip->data.d8[1]);558 chan->address >> 8, 3,
559 &chip->data.d8[1]);
560 560
561 if (ret < 0)561 if (ret < 0)
562 goto out;562 goto out;
@@ -594,27 +594,27 @@ static int ad7746_read_raw(struct iio_dev *indio_dev, · 31 unmodified lines
594 goto out;594 goto out;
595 }595 }
596 596
597 ret = i2c_smbus_read_word_data(chip->client, reg);597 ret = i2c_smbus_read_word_swapped(chip->client, reg);
598 if (ret < 0)598 if (ret < 0)
599 goto out;599 goto out;
600 /* 1 + gain_val / 2^16 */600 /* 1 + gain_val / 2^16 */
601 *val = 1;601 *val = 1;
602 *val2 = (15625 * swab16(ret)) / 1024;602 *val2 = (15625 * ret) / 1024;
603 603
604 ret = IIO_VAL_INT_PLUS_MICRO;604 ret = IIO_VAL_INT_PLUS_MICRO;
605 break;605 break;
606 case IIO_CHAN_INFO_CALIBBIAS:606 case IIO_CHAN_INFO_CALIBBIAS:
607 ret = i2c_smbus_read_word_data(chip->client,607 ret = i2c_smbus_read_word_swapped(chip->client,
608 AD7746_REG_CAP_OFFH);608 AD7746_REG_CAP_OFFH);
609 if (ret < 0)609 if (ret < 0)
610 goto out;610 goto out;
611 *val = swab16(ret);611 *val = ret;
612 612
613 ret = IIO_VAL_INT;613 ret = IIO_VAL_INT;
614 break;614 break;
615 case IIO_CHAN_INFO_OFFSET:615 case IIO_CHAN_INFO_OFFSET:
616 *val = AD7746_CAPDAC_DACP(chip->capdac[chan->channel]616 *val = AD7746_CAPDAC_DACP(chip->capdac[chan->channel]
617 [chan->differential]) * 338646;617 [chan->differential]) * 338646;
618 618
619 ret = IIO_VAL_INT;619 ret = IIO_VAL_INT;
620 break;620 break;
@@ -680,8 +680,8 @@ static int ad7746_probe(struct i2c_client *client, · 59 unmodified lines
680 struct ad7746_platform_data *pdata = client->dev.platform_data;680 struct ad7746_platform_data *pdata = client->dev.platform_data;
681 struct ad7746_chip_info *chip;681 struct ad7746_chip_info *chip;
682 struct iio_dev *indio_dev;682 struct iio_dev *indio_dev;
683 int ret = 0;
684 unsigned char regval = 0;683 unsigned char regval = 0;
684 int ret = 0;
685 685
686 indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*chip));686 indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*chip));
687 if (!indio_dev)687 if (!indio_dev)
drivers/staging/iio/light/Kconfig+0−14
@@ -1,14 +0,0 @@
1#
2# Light sensors
3#
4menu "Light sensors"
5
6config TSL2x7x
7 tristate "TAOS TSL/TMD2x71 and TSL/TMD2x72 Family of light and proximity sensors"
8 depends on I2C
9 help
10 Support for: tsl2571, tsl2671, tmd2671, tsl2771, tmd2771, tsl2572, tsl2672,
11 tmd2672, tsl2772, tmd2772 devices.
12 Provides iio_events and direct access via sysfs.
13
14endmenu
drivers/staging/iio/light/Makefile+0−5
@@ -1,5 +0,0 @@
1#
2# Makefile for industrial I/O Light sensors
3#
4
5obj-$(CONFIG_TSL2x7x) += tsl2x7x.o
drivers/staging/iio/light/tsl2x7x.c+0−1889
@@ -1,1889 +0,0 @@
1/*
2 * Device driver for monitoring ambient light intensity in (lux)
3 * and proximity detection (prox) within the TAOS TSL2X7X family of devices.
4 *
5 * Copyright (c) 2012, TAOS Corporation.
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful, but WITHOUT
13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15 * more details.
16 */
17
18#include <linux/delay.h>
19#include <linux/errno.h>
20#include <linux/i2c.h>
21#include <linux/interrupt.h>
22#include <linux/kernel.h>
23#include <linux/module.h>
24#include <linux/mutex.h>
25#include <linux/slab.h>
26#include <linux/iio/events.h>
27#include <linux/iio/iio.h>
28#include <linux/iio/sysfs.h>
29#include "tsl2x7x.h"
30
31/* Cal defs*/
32#define PROX_STAT_CAL 0
33#define PROX_STAT_SAMP 1
34#define MAX_SAMPLES_CAL 200
35
36/* TSL2X7X Device ID */
37#define TRITON_ID 0x00
38#define SWORDFISH_ID 0x30
39#define HALIBUT_ID 0x20
40
41/* Lux calculation constants */
42#define TSL2X7X_LUX_CALC_OVER_FLOW 65535
43
44/* TAOS Register definitions - note:
45 * depending on device, some of these register are not used and the
46 * register address is benign.
47 */
48/* 2X7X register offsets */
49#define TSL2X7X_MAX_CONFIG_REG 16
50
51/* Device Registers and Masks */
52#define TSL2X7X_CNTRL 0x00
53#define TSL2X7X_ALS_TIME 0X01
54#define TSL2X7X_PRX_TIME 0x02
55#define TSL2X7X_WAIT_TIME 0x03
56#define TSL2X7X_ALS_MINTHRESHLO 0X04
57#define TSL2X7X_ALS_MINTHRESHHI 0X05
58#define TSL2X7X_ALS_MAXTHRESHLO 0X06
59#define TSL2X7X_ALS_MAXTHRESHHI 0X07
60#define TSL2X7X_PRX_MINTHRESHLO 0X08
61#define TSL2X7X_PRX_MINTHRESHHI 0X09
62#define TSL2X7X_PRX_MAXTHRESHLO 0X0A
63#define TSL2X7X_PRX_MAXTHRESHHI 0X0B
64#define TSL2X7X_PERSISTENCE 0x0C
65#define TSL2X7X_PRX_CONFIG 0x0D
66#define TSL2X7X_PRX_COUNT 0x0E
67#define TSL2X7X_GAIN 0x0F
68#define TSL2X7X_NOTUSED 0x10
69#define TSL2X7X_REVID 0x11
70#define TSL2X7X_CHIPID 0x12
71#define TSL2X7X_STATUS 0x13
72#define TSL2X7X_ALS_CHAN0LO 0x14
73#define TSL2X7X_ALS_CHAN0HI 0x15
74#define TSL2X7X_ALS_CHAN1LO 0x16
75#define TSL2X7X_ALS_CHAN1HI 0x17
76#define TSL2X7X_PRX_LO 0x18
77#define TSL2X7X_PRX_HI 0x19
78
79/* tsl2X7X cmd reg masks */
80#define TSL2X7X_CMD_REG 0x80
81#define TSL2X7X_CMD_SPL_FN 0x60
82
83#define TSL2X7X_CMD_PROX_INT_CLR 0X05
84#define TSL2X7X_CMD_ALS_INT_CLR 0x06
85#define TSL2X7X_CMD_PROXALS_INT_CLR 0X07
86
87/* tsl2X7X cntrl reg masks */
88#define TSL2X7X_CNTL_ADC_ENBL 0x02
89#define TSL2X7X_CNTL_PWR_ON 0x01
90
91/* tsl2X7X status reg masks */
92#define TSL2X7X_STA_ADC_VALID 0x01
93#define TSL2X7X_STA_PRX_VALID 0x02
94#define TSL2X7X_STA_ADC_PRX_VALID (TSL2X7X_STA_ADC_VALID | \
95 TSL2X7X_STA_PRX_VALID)
96#define TSL2X7X_STA_ALS_INTR 0x10
97#define TSL2X7X_STA_PRX_INTR 0x20
98
99/* tsl2X7X cntrl reg masks */
100#define TSL2X7X_CNTL_REG_CLEAR 0x00
101#define TSL2X7X_CNTL_PROX_INT_ENBL 0X20
102#define TSL2X7X_CNTL_ALS_INT_ENBL 0X10
103#define TSL2X7X_CNTL_WAIT_TMR_ENBL 0X08
104#define TSL2X7X_CNTL_PROX_DET_ENBL 0X04
105#define TSL2X7X_CNTL_PWRON 0x01
106#define TSL2X7X_CNTL_ALSPON_ENBL 0x03
107#define TSL2X7X_CNTL_INTALSPON_ENBL 0x13
108#define TSL2X7X_CNTL_PROXPON_ENBL 0x0F
109#define TSL2X7X_CNTL_INTPROXPON_ENBL 0x2F
110
111/*Prox diode to use */
112#define TSL2X7X_DIODE0 0x01
113#define TSL2X7X_DIODE1 0x02
114#define TSL2X7X_DIODE_BOTH 0x03
115
116/* LED Power */
117#define TSL2X7X_100_mA 0x00
118#define TSL2X7X_50_mA 0x01
119#define TSL2X7X_25_mA 0x02
120#define TSL2X7X_13_mA 0x03
121#define TSL2X7X_MAX_TIMER_CNT 0xFF
122
123#define TSL2X7X_MIN_ITIME 3
124
125/* TAOS txx2x7x Device family members */
126enum {
127 tsl2571,
128 tsl2671,
129 tmd2671,
130 tsl2771,
131 tmd2771,
132 tsl2572,
133 tsl2672,
134 tmd2672,
135 tsl2772,
136 tmd2772
137};
138
139enum {
140 TSL2X7X_CHIP_UNKNOWN = 0,
141 TSL2X7X_CHIP_WORKING = 1,
142 TSL2X7X_CHIP_SUSPENDED = 2
143};
144
145/* Per-device data */
146struct tsl2x7x_als_info {
147 u16 als_ch0;
148 u16 als_ch1;
149 u16 lux;
150};
151
152struct tsl2x7x_prox_stat {
153 int min;
154 int max;
155 int mean;
156 unsigned long stddev;
157};
158
159struct tsl2x7x_chip_info {
160 int chan_table_elements;
161 struct iio_chan_spec channel[4];
162 const struct iio_info *info;
163};
164
165struct tsl2X7X_chip {
166 kernel_ulong_t id;
167 struct mutex prox_mutex;
168 struct mutex als_mutex;
169 struct i2c_client *client;
170 u16 prox_data;
171 struct tsl2x7x_als_info als_cur_info;
172 struct tsl2x7x_settings settings;
173 struct tsl2X7X_platform_data *pdata;
174 int als_time_scale;
175 int als_saturation;
176 int tsl2x7x_chip_status;
177 u8 tsl2x7x_config[TSL2X7X_MAX_CONFIG_REG];
178 const struct tsl2x7x_chip_info *chip_info;
179 const struct iio_info *info;
180 s64 event_timestamp;
181 /*
182 * This structure is intentionally large to accommodate
183 * updates via sysfs.
184 * Sized to 9 = max 8 segments + 1 termination segment
185 */
186 struct tsl2x7x_lux tsl2x7x_device_lux[TSL2X7X_MAX_LUX_TABLE_SIZE];
187};
188
189/* Different devices require different coefficents */
190static const struct tsl2x7x_lux tsl2x71_lux_table[TSL2X7X_DEF_LUX_TABLE_SZ] = {
191 { 14461, 611, 1211 },
192 { 18540, 352, 623 },
193 { 0, 0, 0 },
194};
195
196static const struct tsl2x7x_lux tmd2x71_lux_table[TSL2X7X_DEF_LUX_TABLE_SZ] = {
197 { 11635, 115, 256 },
198 { 15536, 87, 179 },
199 { 0, 0, 0 },
200};
201
202static const struct tsl2x7x_lux tsl2x72_lux_table[TSL2X7X_DEF_LUX_TABLE_SZ] = {
203 { 14013, 466, 917 },
204 { 18222, 310, 552 },
205 { 0, 0, 0 },
206};
207
208static const struct tsl2x7x_lux tmd2x72_lux_table[TSL2X7X_DEF_LUX_TABLE_SZ] = {
209 { 13218, 130, 262 },
210 { 17592, 92, 169 },
211 { 0, 0, 0 },
212};
213
214static const struct tsl2x7x_lux *tsl2x7x_default_lux_table_group[] = {
215 [tsl2571] = tsl2x71_lux_table,
216 [tsl2671] = tsl2x71_lux_table,
217 [tmd2671] = tmd2x71_lux_table,
218 [tsl2771] = tsl2x71_lux_table,
219 [tmd2771] = tmd2x71_lux_table,
220 [tsl2572] = tsl2x72_lux_table,
221 [tsl2672] = tsl2x72_lux_table,
222 [tmd2672] = tmd2x72_lux_table,
223 [tsl2772] = tsl2x72_lux_table,
224 [tmd2772] = tmd2x72_lux_table,
225};
226
227static const struct tsl2x7x_settings tsl2x7x_default_settings = {
228 .als_time = 219, /* 101 ms */
229 .als_gain = 0,
230 .prx_time = 254, /* 5.4 ms */
231 .prox_gain = 0,
232 .wait_time = 245,
233 .prox_config = 0,
234 .als_gain_trim = 1000,
235 .als_cal_target = 150,
236 .als_thresh_low = 200,
237 .als_thresh_high = 256,
238 .persistence = 255,
239 .interrupts_en = 0,
240 .prox_thres_low = 0,
241 .prox_thres_high = 512,
242 .prox_max_samples_cal = 30,
243 .prox_pulse_count = 8,
244 .prox_diode = TSL2X7X_DIODE1,
245 .prox_power = TSL2X7X_100_mA
246};
247
248static const s16 tsl2x7x_als_gain[] = {
249 1,
250 8,
251 16,
252 120
253};
254
255static const s16 tsl2x7x_prx_gain[] = {
256 1,
257 2,
258 4,
259 8
260};
261
262/* Channel variations */
263enum {
264 ALS,
265 PRX,
266 ALSPRX,
267 PRX2,
268 ALSPRX2,
269};
270
271static const u8 device_channel_config[] = {
272 ALS,
273 PRX,
274 PRX,
275 ALSPRX,
276 ALSPRX,
277 ALS,
278 PRX2,
279 PRX2,
280 ALSPRX2,
281 ALSPRX2
282};
283
284static int tsl2x7x_clear_interrupts(struct tsl2X7X_chip *chip, int reg)
285{
286 int ret;
287
288 ret = i2c_smbus_write_byte(chip->client,
289 TSL2X7X_CMD_REG | TSL2X7X_CMD_SPL_FN | reg);
290 if (ret < 0)
291 dev_err(&chip->client->dev,
292 "%s: failed to clear interrupt status %x: %d\n",
293 __func__, reg, ret);
294
295 return ret;
296}
297
298static int tsl2x7x_read_status(struct tsl2X7X_chip *chip)
299{
300 int ret;
301
302 ret = i2c_smbus_read_byte_data(chip->client,
303 TSL2X7X_CMD_REG | TSL2X7X_STATUS);
304 if (ret < 0)
305 dev_err(&chip->client->dev,
306 "%s: failed to read STATUS register: %d\n", __func__,
307 ret);
308
309 return ret;
310}
311
312static int tsl2x7x_write_control_reg(struct tsl2X7X_chip *chip, u8 data)
313{
314 int ret;
315
316 ret = i2c_smbus_write_byte_data(chip->client,
317 TSL2X7X_CMD_REG | TSL2X7X_CNTRL, data);
318 if (ret < 0) {
319 dev_err(&chip->client->dev,
320 "%s: failed to write to control register %x: %d\n",
321 __func__, data, ret);
322 }
323
324 return ret;
325}
326
327/**
328 * tsl2x7x_get_lux() - Reads and calculates current lux value.
329 * @indio_dev: pointer to IIO device
330 *
331 * The raw ch0 and ch1 values of the ambient light sensed in the last
332 * integration cycle are read from the device.
333 * Time scale factor array values are adjusted based on the integration time.
334 * The raw values are multiplied by a scale factor, and device gain is obtained
335 * using gain index. Limit checks are done next, then the ratio of a multiple
336 * of ch1 value, to the ch0 value, is calculated. Array tsl2x7x_device_lux[]
337 * is then scanned to find the first ratio value that is just above the ratio
338 * we just calculated. The ch0 and ch1 multiplier constants in the array are
339 * then used along with the time scale factor array values, to calculate the
340 * lux.
341 */
342static int tsl2x7x_get_lux(struct iio_dev *indio_dev)
343{
344 u16 ch0, ch1; /* separated ch0/ch1 data from device */
345 u32 lux; /* raw lux calculated from device data */
346 u64 lux64;
347 u32 ratio;
348 u8 buf[4];
349 struct tsl2x7x_lux *p;
350 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
351 int i, ret;
352 u32 ch0lux = 0;
353 u32 ch1lux = 0;
354
355 mutex_lock(&chip->als_mutex);
356
357 if (chip->tsl2x7x_chip_status != TSL2X7X_CHIP_WORKING) {
358 /* device is not enabled */
359 dev_err(&chip->client->dev, "%s: device is not enabled\n",
360 __func__);
361 ret = -EBUSY;
362 goto out_unlock;
363 }
364
365 ret = tsl2x7x_read_status(chip);
366 if (ret < 0)
367 goto out_unlock;
368
369 /* is data new & valid */
370 if (!(ret & TSL2X7X_STA_ADC_VALID)) {
371 dev_err(&chip->client->dev,
372 "%s: data not valid yet\n", __func__);
373 ret = chip->als_cur_info.lux; /* return LAST VALUE */
374 goto out_unlock;
375 }
376
377 for (i = 0; i < 4; i++) {
378 int reg = TSL2X7X_CMD_REG | (TSL2X7X_ALS_CHAN0LO + i);
379
380 ret = i2c_smbus_read_byte_data(chip->client, reg);
381 if (ret < 0) {
382 dev_err(&chip->client->dev,
383 "failed to read. err=%x\n", ret);
384 goto out_unlock;
385 }
386
387 buf[i] = ret;
388 }
389
390 ret = tsl2x7x_clear_interrupts(chip, TSL2X7X_CMD_ALS_INT_CLR);
391 if (ret < 0)
392 goto out_unlock;
393
394 /* extract ALS/lux data */
395 ch0 = le16_to_cpup((const __le16 *)&buf[0]);
396 ch1 = le16_to_cpup((const __le16 *)&buf[2]);
397
398 chip->als_cur_info.als_ch0 = ch0;
399 chip->als_cur_info.als_ch1 = ch1;
400
401 if (ch0 >= chip->als_saturation || ch1 >= chip->als_saturation) {
402 lux = TSL2X7X_LUX_CALC_OVER_FLOW;
403 goto return_max;
404 }
405
406 if (!ch0) {
407 /* have no data, so return LAST VALUE */
408 ret = chip->als_cur_info.lux;
409 goto out_unlock;
410 }
411 /* calculate ratio */
412 ratio = (ch1 << 15) / ch0;
413 /* convert to unscaled lux using the pointer to the table */
414 p = (struct tsl2x7x_lux *)chip->tsl2x7x_device_lux;
415 while (p->ratio != 0 && p->ratio < ratio)
416 p++;
417
418 if (p->ratio == 0) {
419 lux = 0;
420 } else {
421 lux = DIV_ROUND_UP(ch0 * p->ch0,
422 tsl2x7x_als_gain[chip->settings.als_gain]) -
423 DIV_ROUND_UP(ch1 * p->ch1,
424 tsl2x7x_als_gain[chip->settings.als_gain]);
425 }
426
427 /* note: lux is 31 bit max at this point */
428 if (ch1lux > ch0lux) {
429 dev_dbg(&chip->client->dev, "ch1lux > ch0lux-return last value\n");
430 ret = chip->als_cur_info.lux;
431 goto out_unlock;
432 }
433
434 /* adjust for active time scale */
435 if (chip->als_time_scale == 0)
436 lux = 0;
437 else
438 lux = (lux + (chip->als_time_scale >> 1)) /
439 chip->als_time_scale;
440
441 /* adjust for active gain scale
442 * The tsl2x7x_device_lux tables have a factor of 256 built-in.
443 * User-specified gain provides a multiplier.
444 * Apply user-specified gain before shifting right to retain precision.
445 * Use 64 bits to avoid overflow on multiplication.
446 * Then go back to 32 bits before division to avoid using div_u64().
447 */
448
449 lux64 = lux;
450 lux64 = lux64 * chip->settings.als_gain_trim;
451 lux64 >>= 8;
452 lux = lux64;
453 lux = (lux + 500) / 1000;
454
455 if (lux > TSL2X7X_LUX_CALC_OVER_FLOW) /* check for overflow */
456 lux = TSL2X7X_LUX_CALC_OVER_FLOW;
457
458 /* Update the structure with the latest lux. */
459return_max:
460 chip->als_cur_info.lux = lux;
461 ret = lux;
462
463out_unlock:
464 mutex_unlock(&chip->als_mutex);
465
466 return ret;
467}
468
469/**
470 * tsl2x7x_get_prox() - Reads proximity data registers and updates
471 * chip->prox_data.
472 *
473 * @indio_dev: pointer to IIO device
474 */
475static int tsl2x7x_get_prox(struct iio_dev *indio_dev)
476{
477 int i;
478 int ret;
479 u8 chdata[2];
480 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
481
482 mutex_lock(&chip->prox_mutex);
483
484 ret = tsl2x7x_read_status(chip);
485 if (ret < 0)
486 goto prox_poll_err;
487
488 switch (chip->id) {
489 case tsl2571:
490 case tsl2671:
491 case tmd2671:
492 case tsl2771:
493 case tmd2771:
494 if (!(ret & TSL2X7X_STA_ADC_VALID)) {
495 ret = -EINVAL;
496 goto prox_poll_err;
497 }
498 break;
499 case tsl2572:
500 case tsl2672:
501 case tmd2672:
502 case tsl2772:
503 case tmd2772:
504 if (!(ret & TSL2X7X_STA_PRX_VALID)) {
505 ret = -EINVAL;
506 goto prox_poll_err;
507 }
508 break;
509 }
510
511 for (i = 0; i < 2; i++) {
512 int reg = TSL2X7X_CMD_REG | (TSL2X7X_PRX_LO + i);
513
514 ret = i2c_smbus_read_byte_data(chip->client, reg);
515 if (ret < 0)
516 goto prox_poll_err;
517
518 chdata[i] = ret;
519 }
520
521 chip->prox_data = le16_to_cpup((const __le16 *)&chdata[0]);
522 ret = chip->prox_data;
523
524prox_poll_err:
525 mutex_unlock(&chip->prox_mutex);
526
527 return ret;
528}
529
530/**
531 * tsl2x7x_defaults() - Populates the device nominal operating parameters
532 * with those provided by a 'platform' data struct or
533 * with prefined defaults.
534 *
535 * @chip: pointer to device structure.
536 */
537static void tsl2x7x_defaults(struct tsl2X7X_chip *chip)
538{
539 /* If Operational settings defined elsewhere.. */
540 if (chip->pdata && chip->pdata->platform_default_settings)
541 memcpy(&chip->settings, chip->pdata->platform_default_settings,
542 sizeof(tsl2x7x_default_settings));
543 else
544 memcpy(&chip->settings, &tsl2x7x_default_settings,
545 sizeof(tsl2x7x_default_settings));
546
547 /* Load up the proper lux table. */
548 if (chip->pdata && chip->pdata->platform_lux_table[0].ratio != 0)
549 memcpy(chip->tsl2x7x_device_lux,
550 chip->pdata->platform_lux_table,
551 sizeof(chip->pdata->platform_lux_table));
552 else
553 memcpy(chip->tsl2x7x_device_lux,
554 tsl2x7x_default_lux_table_group[chip->id],
555 TSL2X7X_DEFAULT_TABLE_BYTES);
556}
557
558/**
559 * tsl2x7x_als_calibrate() - Obtain single reading and calculate
560 * the als_gain_trim.
561 *
562 * @indio_dev: pointer to IIO device
563 */
564static int tsl2x7x_als_calibrate(struct iio_dev *indio_dev)
565{
566 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
567 int ret, lux_val;
568
569 ret = i2c_smbus_read_byte_data(chip->client,
570 TSL2X7X_CMD_REG | TSL2X7X_CNTRL);
571 if (ret < 0) {
572 dev_err(&chip->client->dev,
573 "%s: failed to read from the CNTRL register\n",
574 __func__);
575 return ret;
576 }
577
578 if ((ret & (TSL2X7X_CNTL_ADC_ENBL | TSL2X7X_CNTL_PWR_ON))
579 != (TSL2X7X_CNTL_ADC_ENBL | TSL2X7X_CNTL_PWR_ON)) {
580 dev_err(&chip->client->dev,
581 "%s: Device is not powered on and/or ADC is not enabled\n",
582 __func__);
583 return -EINVAL;
584 } else if ((ret & TSL2X7X_STA_ADC_VALID) != TSL2X7X_STA_ADC_VALID) {
585 dev_err(&chip->client->dev,
586 "%s: The two ADC channels have not completed an integration cycle\n",
587 __func__);
588 return -ENODATA;
589 }
590
591 lux_val = tsl2x7x_get_lux(indio_dev);
592 if (lux_val < 0) {
593 dev_err(&chip->client->dev,
594 "%s: failed to get lux\n", __func__);
595 return lux_val;
596 }
597
598 ret = (chip->settings.als_cal_target * chip->settings.als_gain_trim) /
599 lux_val;
600 if (ret < 250 || ret > 4000)
601 return -ERANGE;
602
603 chip->settings.als_gain_trim = ret;
604 dev_info(&chip->client->dev,
605 "%s als_calibrate completed\n", chip->client->name);
606
607 return ret;
608}
609
610static int tsl2x7x_chip_on(struct iio_dev *indio_dev)
611{
612 int i;
613 int ret = 0;
614 u8 *dev_reg;
615 int als_count;
616 int als_time;
617 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
618 u8 reg_val = 0;
619
620 /* Non calculated parameters */
621 chip->tsl2x7x_config[TSL2X7X_PRX_TIME] = chip->settings.prx_time;
622 chip->tsl2x7x_config[TSL2X7X_WAIT_TIME] = chip->settings.wait_time;
623 chip->tsl2x7x_config[TSL2X7X_PRX_CONFIG] = chip->settings.prox_config;
624
625 chip->tsl2x7x_config[TSL2X7X_ALS_MINTHRESHLO] =
626 (chip->settings.als_thresh_low) & 0xFF;
627 chip->tsl2x7x_config[TSL2X7X_ALS_MINTHRESHHI] =
628 (chip->settings.als_thresh_low >> 8) & 0xFF;
629 chip->tsl2x7x_config[TSL2X7X_ALS_MAXTHRESHLO] =
630 (chip->settings.als_thresh_high) & 0xFF;
631 chip->tsl2x7x_config[TSL2X7X_ALS_MAXTHRESHHI] =
632 (chip->settings.als_thresh_high >> 8) & 0xFF;
633 chip->tsl2x7x_config[TSL2X7X_PERSISTENCE] = chip->settings.persistence;
634
635 chip->tsl2x7x_config[TSL2X7X_PRX_COUNT] =
636 chip->settings.prox_pulse_count;
637 chip->tsl2x7x_config[TSL2X7X_PRX_MINTHRESHLO] =
638 (chip->settings.prox_thres_low) & 0xFF;
639 chip->tsl2x7x_config[TSL2X7X_PRX_MINTHRESHHI] =
640 (chip->settings.prox_thres_low >> 8) & 0xFF;
641 chip->tsl2x7x_config[TSL2X7X_PRX_MAXTHRESHLO] =
642 (chip->settings.prox_thres_high) & 0xFF;
643 chip->tsl2x7x_config[TSL2X7X_PRX_MAXTHRESHHI] =
644 (chip->settings.prox_thres_high >> 8) & 0xFF;
645
646 /* and make sure we're not already on */
647 if (chip->tsl2x7x_chip_status == TSL2X7X_CHIP_WORKING) {
648 /* if forcing a register update - turn off, then on */
649 dev_info(&chip->client->dev, "device is already enabled\n");
650 return -EINVAL;
651 }
652
653 /* determine als integration register */
654 als_count = (chip->settings.als_time * 100 + 135) / 270;
655 if (!als_count)
656 als_count = 1; /* ensure at least one cycle */
657
658 /* convert back to time (encompasses overrides) */
659 als_time = (als_count * 27 + 5) / 10;
660 chip->tsl2x7x_config[TSL2X7X_ALS_TIME] = 256 - als_count;
661
662 /* Set the gain based on tsl2x7x_settings struct */
663 chip->tsl2x7x_config[TSL2X7X_GAIN] =
664 (chip->settings.als_gain & 0xFF) |
665 ((chip->settings.prox_gain & 0xFF) << 2) |
666 (chip->settings.prox_diode << 4) |
667 (chip->settings.prox_power << 6);
668
669 /* set chip struct re scaling and saturation */
670 chip->als_saturation = als_count * 922; /* 90% of full scale */
671 chip->als_time_scale = (als_time + 25) / 50;
672
673 /*
674 * TSL2X7X Specific power-on / adc enable sequence
675 * Power on the device 1st.
676 */
677 ret = tsl2x7x_write_control_reg(chip, TSL2X7X_CNTL_PWR_ON);
678 if (ret < 0)
679 return ret;
680
681 /*
682 * Use the following shadow copy for our delay before enabling ADC.
683 * Write all the registers.
684 */
685 for (i = 0, dev_reg = chip->tsl2x7x_config;
686 i < TSL2X7X_MAX_CONFIG_REG; i++) {
687 ret = i2c_smbus_write_byte_data(chip->client,
688 TSL2X7X_CMD_REG + i,
689 *dev_reg++);
690 if (ret < 0) {
691 dev_err(&chip->client->dev,
692 "failed on write to reg %d.\n", i);
693 return ret;
694 }
695 }
696
697 /* Power-on settling time */
698 usleep_range(3000, 3500);
699
700 /*
701 * NOW enable the ADC
702 * initialize the desired mode of operation
703 */
704 ret = tsl2x7x_write_control_reg(chip,
705 TSL2X7X_CNTL_PWR_ON |
706 TSL2X7X_CNTL_ADC_ENBL |
707 TSL2X7X_CNTL_PROX_DET_ENBL);
708 if (ret < 0)
709 return ret;
710
711 chip->tsl2x7x_chip_status = TSL2X7X_CHIP_WORKING;
712
713 if (chip->settings.interrupts_en != 0) {
714 dev_info(&chip->client->dev, "Setting Up Interrupt(s)\n");
715
716 reg_val = TSL2X7X_CNTL_PWR_ON | TSL2X7X_CNTL_ADC_ENBL;
717 if (chip->settings.interrupts_en == 0x20 ||
718 chip->settings.interrupts_en == 0x30)
719 reg_val |= TSL2X7X_CNTL_PROX_DET_ENBL;
720
721 reg_val |= chip->settings.interrupts_en;
722 ret = tsl2x7x_write_control_reg(chip, reg_val);
723 if (ret < 0)
724 return ret;
725
726 ret = tsl2x7x_clear_interrupts(chip,
727 TSL2X7X_CMD_PROXALS_INT_CLR);
728 if (ret < 0)
729 return ret;
730 }
731
732 return ret;
733}
734
735static int tsl2x7x_chip_off(struct iio_dev *indio_dev)
736{
737 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
738
739 /* turn device off */
740 chip->tsl2x7x_chip_status = TSL2X7X_CHIP_SUSPENDED;
741 return tsl2x7x_write_control_reg(chip, 0x00);
742}
743
744/**
745 * tsl2x7x_invoke_change
746 * @indio_dev: pointer to IIO device
747 *
748 * Obtain and lock both ALS and PROX resources,
749 * determine and save device state (On/Off),
750 * cycle device to implement updated parameter,
751 * put device back into proper state, and unlock
752 * resource.
753 */
754static int tsl2x7x_invoke_change(struct iio_dev *indio_dev)
755{
756 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
757 int device_status = chip->tsl2x7x_chip_status;
758 int ret;
759
760 mutex_lock(&chip->als_mutex);
761 mutex_lock(&chip->prox_mutex);
762
763 if (device_status == TSL2X7X_CHIP_WORKING) {
764 ret = tsl2x7x_chip_off(indio_dev);
765 if (ret < 0)
766 goto unlock;
767 }
768
769 ret = tsl2x7x_chip_on(indio_dev);
770
771unlock:
772 mutex_unlock(&chip->prox_mutex);
773 mutex_unlock(&chip->als_mutex);
774
775 return ret;
776}
777
778static void tsl2x7x_prox_calculate(int *data, int length,
779 struct tsl2x7x_prox_stat *stat)
780{
781 int i;
782 int sample_sum;
783 int tmp;
784
785 if (!length)
786 length = 1;
787
788 sample_sum = 0;
789 stat->min = INT_MAX;
790 stat->max = INT_MIN;
791 for (i = 0; i < length; i++) {
792 sample_sum += data[i];
793 stat->min = min(stat->min, data[i]);
794 stat->max = max(stat->max, data[i]);
795 }
796
797 stat->mean = sample_sum / length;
798 sample_sum = 0;
799 for (i = 0; i < length; i++) {
800 tmp = data[i] - stat->mean;
801 sample_sum += tmp * tmp;
802 }
803 stat->stddev = int_sqrt((long)sample_sum / length);
804}
805
806/**
807 * tsl2x7x_prox_cal() - Calculates std. and sets thresholds.
808 * @indio_dev: pointer to IIO device
809 *
810 * Calculates a standard deviation based on the samples,
811 * and sets the threshold accordingly.
812 */
813static int tsl2x7x_prox_cal(struct iio_dev *indio_dev)
814{
815 int prox_history[MAX_SAMPLES_CAL + 1];
816 int i, ret;
817 struct tsl2x7x_prox_stat prox_stat_data[2];
818 struct tsl2x7x_prox_stat *cal;
819 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
820 u8 tmp_irq_settings;
821 u8 current_state = chip->tsl2x7x_chip_status;
822
823 if (chip->settings.prox_max_samples_cal > MAX_SAMPLES_CAL) {
824 dev_err(&chip->client->dev,
825 "max prox samples cal is too big: %d\n",
826 chip->settings.prox_max_samples_cal);
827 chip->settings.prox_max_samples_cal = MAX_SAMPLES_CAL;
828 }
829
830 /* have to stop to change settings */
831 ret = tsl2x7x_chip_off(indio_dev);
832 if (ret < 0)
833 return ret;
834
835 /* Enable proximity detection save just in case prox not wanted yet*/
836 tmp_irq_settings = chip->settings.interrupts_en;
837 chip->settings.interrupts_en |= TSL2X7X_CNTL_PROX_INT_ENBL;
838
839 /*turn on device if not already on*/
840 ret = tsl2x7x_chip_on(indio_dev);
841 if (ret < 0)
842 return ret;
843
844 /*gather the samples*/
845 for (i = 0; i < chip->settings.prox_max_samples_cal; i++) {
846 usleep_range(15000, 17500);
847 ret = tsl2x7x_get_prox(indio_dev);
848 if (ret < 0)
849 return ret;
850 prox_history[i] = chip->prox_data;
851 dev_info(&chip->client->dev, "2 i=%d prox data= %d\n",
852 i, chip->prox_data);
853 }
854
855 ret = tsl2x7x_chip_off(indio_dev);
856 if (ret < 0)
857 return ret;
858 cal = &prox_stat_data[PROX_STAT_CAL];
859 tsl2x7x_prox_calculate(prox_history,
860 chip->settings.prox_max_samples_cal, cal);
861 chip->settings.prox_thres_high = (cal->max << 1) - cal->mean;
862
863 dev_info(&chip->client->dev, " cal min=%d mean=%d max=%d\n",
864 cal->min, cal->mean, cal->max);
865 dev_info(&chip->client->dev,
866 "%s proximity threshold set to %d\n",
867 chip->client->name, chip->settings.prox_thres_high);
868
869 /* back to the way they were */
870 chip->settings.interrupts_en = tmp_irq_settings;
871 if (current_state == TSL2X7X_CHIP_WORKING) {
872 ret = tsl2x7x_chip_on(indio_dev);
873 if (ret < 0)
874 return ret;
875 }
876
877 return 0;
878}
879
880static ssize_t
881in_illuminance0_calibscale_available_show(struct device *dev,
882 struct device_attribute *attr,
883 char *buf)
884{
885 struct tsl2X7X_chip *chip = iio_priv(dev_to_iio_dev(dev));
886
887 switch (chip->id) {
888 case tsl2571:
889 case tsl2671:
890 case tmd2671:
891 case tsl2771:
892 case tmd2771:
893 return snprintf(buf, PAGE_SIZE, "%s\n", "1 8 16 128");
894 }
895
896 return snprintf(buf, PAGE_SIZE, "%s\n", "1 8 16 120");
897}
898
899static IIO_CONST_ATTR(in_proximity0_calibscale_available, "1 2 4 8");
900
901static IIO_CONST_ATTR(in_illuminance0_integration_time_available,
902 ".00272 - .696");
903
904static ssize_t in_illuminance0_target_input_show(struct device *dev,
905 struct device_attribute *attr,
906 char *buf)
907{
908 struct tsl2X7X_chip *chip = iio_priv(dev_to_iio_dev(dev));
909
910 return snprintf(buf, PAGE_SIZE, "%d\n", chip->settings.als_cal_target);
911}
912
913static ssize_t in_illuminance0_target_input_store(struct device *dev,
914 struct device_attribute *attr,
915 const char *buf, size_t len)
916{
917 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
918 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
919 unsigned long value;
920 int ret;
921
922 if (kstrtoul(buf, 0, &value))
923 return -EINVAL;
924
925 if (value)
926 chip->settings.als_cal_target = value;
927
928 ret = tsl2x7x_invoke_change(indio_dev);
929 if (ret < 0)
930 return ret;
931
932 return len;
933}
934
935static ssize_t in_illuminance0_calibrate_store(struct device *dev,
936 struct device_attribute *attr,
937 const char *buf, size_t len)
938{
939 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
940 bool value;
941 int ret;
942
943 if (strtobool(buf, &value))
944 return -EINVAL;
945
946 if (value) {
947 ret = tsl2x7x_als_calibrate(indio_dev);
948 if (ret < 0)
949 return ret;
950 }
951
952 ret = tsl2x7x_invoke_change(indio_dev);
953 if (ret < 0)
954 return ret;
955
956 return len;
957}
958
959static ssize_t in_illuminance0_lux_table_show(struct device *dev,
960 struct device_attribute *attr,
961 char *buf)
962{
963 struct tsl2X7X_chip *chip = iio_priv(dev_to_iio_dev(dev));
964 int i = 0;
965 int offset = 0;
966
967 while (i < TSL2X7X_MAX_LUX_TABLE_SIZE) {
968 offset += snprintf(buf + offset, PAGE_SIZE, "%u,%u,%u,",
969 chip->tsl2x7x_device_lux[i].ratio,
970 chip->tsl2x7x_device_lux[i].ch0,
971 chip->tsl2x7x_device_lux[i].ch1);
972 if (chip->tsl2x7x_device_lux[i].ratio == 0) {
973 /*
974 * We just printed the first "0" entry.
975 * Now get rid of the extra "," and break.
976 */
977 offset--;
978 break;
979 }
980 i++;
981 }
982
983 offset += snprintf(buf + offset, PAGE_SIZE, "\n");
984 return offset;
985}
986
987static ssize_t in_illuminance0_lux_table_store(struct device *dev,
988 struct device_attribute *attr,
989 const char *buf, size_t len)
990{
991 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
992 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
993 int value[ARRAY_SIZE(chip->tsl2x7x_device_lux) * 3 + 1];
994 int n, ret;
995
996 get_options(buf, ARRAY_SIZE(value), value);
997
998 /* We now have an array of ints starting at value[1], and
999 * enumerated by value[0].
1000 * We expect each group of three ints is one table entry,
1001 * and the last table entry is all 0.
1002 */
1003 n = value[0];
1004 if ((n % 3) || n < 6 ||
1005 n > ((ARRAY_SIZE(chip->tsl2x7x_device_lux) - 1) * 3)) {
1006 dev_info(dev, "LUX TABLE INPUT ERROR 1 Value[0]=%d\n", n);
1007 return -EINVAL;
1008 }
1009
1010 if ((value[(n - 2)] | value[(n - 1)] | value[n]) != 0) {
1011 dev_info(dev, "LUX TABLE INPUT ERROR 2 Value[0]=%d\n", n);
1012 return -EINVAL;
1013 }
1014
1015 if (chip->tsl2x7x_chip_status == TSL2X7X_CHIP_WORKING) {
1016 ret = tsl2x7x_chip_off(indio_dev);
1017 if (ret < 0)
1018 return ret;
1019 }
1020
1021 /* Zero out the table */
1022 memset(chip->tsl2x7x_device_lux, 0, sizeof(chip->tsl2x7x_device_lux));
1023 memcpy(chip->tsl2x7x_device_lux, &value[1], (value[0] * 4));
1024
1025 ret = tsl2x7x_invoke_change(indio_dev);
1026 if (ret < 0)
1027 return ret;
1028
1029 return len;
1030}
1031
1032static ssize_t in_proximity0_calibrate_store(struct device *dev,
1033 struct device_attribute *attr,
1034 const char *buf, size_t len)
1035{
1036 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
1037 bool value;
1038 int ret;
1039
1040 if (strtobool(buf, &value))
1041 return -EINVAL;
1042
1043 if (value) {
1044 ret = tsl2x7x_prox_cal(indio_dev);
1045 if (ret < 0)
1046 return ret;
1047 }
1048
1049 ret = tsl2x7x_invoke_change(indio_dev);
1050 if (ret < 0)
1051 return ret;
1052
1053 return len;
1054}
1055
1056static int tsl2x7x_read_interrupt_config(struct iio_dev *indio_dev,
1057 const struct iio_chan_spec *chan,
1058 enum iio_event_type type,
1059 enum iio_event_direction dir)
1060{
1061 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1062 int ret;
1063
1064 if (chan->type == IIO_INTENSITY)
1065 ret = !!(chip->settings.interrupts_en & 0x10);
1066 else
1067 ret = !!(chip->settings.interrupts_en & 0x20);
1068
1069 return ret;
1070}
1071
1072static int tsl2x7x_write_interrupt_config(struct iio_dev *indio_dev,
1073 const struct iio_chan_spec *chan,
1074 enum iio_event_type type,
1075 enum iio_event_direction dir,
1076 int val)
1077{
1078 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1079 int ret;
1080
1081 if (chan->type == IIO_INTENSITY) {
1082 if (val)
1083 chip->settings.interrupts_en |= 0x10;
1084 else
1085 chip->settings.interrupts_en &= 0x20;
1086 } else {
1087 if (val)
1088 chip->settings.interrupts_en |= 0x20;
1089 else
1090 chip->settings.interrupts_en &= 0x10;
1091 }
1092
1093 ret = tsl2x7x_invoke_change(indio_dev);
1094 if (ret < 0)
1095 return ret;
1096
1097 return 0;
1098}
1099
1100static int tsl2x7x_write_event_value(struct iio_dev *indio_dev,
1101 const struct iio_chan_spec *chan,
1102 enum iio_event_type type,
1103 enum iio_event_direction dir,
1104 enum iio_event_info info,
1105 int val, int val2)
1106{
1107 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1108 int ret = -EINVAL, y, z, filter_delay;
1109 u8 time;
1110
1111 switch (info) {
1112 case IIO_EV_INFO_VALUE:
1113 if (chan->type == IIO_INTENSITY) {
1114 switch (dir) {
1115 case IIO_EV_DIR_RISING:
1116 chip->settings.als_thresh_high = val;
1117 ret = 0;
1118 break;
1119 case IIO_EV_DIR_FALLING:
1120 chip->settings.als_thresh_low = val;
1121 ret = 0;
1122 break;
1123 default:
1124 break;
1125 }
1126 } else {
1127 switch (dir) {
1128 case IIO_EV_DIR_RISING:
1129 chip->settings.prox_thres_high = val;
1130 ret = 0;
1131 break;
1132 case IIO_EV_DIR_FALLING:
1133 chip->settings.prox_thres_low = val;
1134 ret = 0;
1135 break;
1136 default:
1137 break;
1138 }
1139 }
1140 break;
1141 case IIO_EV_INFO_PERIOD:
1142 if (chan->type == IIO_INTENSITY)
1143 time = chip->settings.als_time;
1144 else
1145 time = chip->settings.prx_time;
1146
1147 y = (TSL2X7X_MAX_TIMER_CNT - time) + 1;
1148 z = y * TSL2X7X_MIN_ITIME;
1149
1150 filter_delay = DIV_ROUND_UP((val * 1000) + val2, z);
1151
1152 if (chan->type == IIO_INTENSITY) {
1153 chip->settings.persistence &= 0xF0;
1154 chip->settings.persistence |=
1155 (filter_delay & 0x0F);
1156 dev_info(&chip->client->dev, "%s: ALS persistence = %d",
1157 __func__, filter_delay);
1158 } else {
1159 chip->settings.persistence &= 0x0F;
1160 chip->settings.persistence |=
1161 ((filter_delay << 4) & 0xF0);
1162 dev_info(&chip->client->dev,
1163 "%s: Proximity persistence = %d",
1164 __func__, filter_delay);
1165 }
1166 ret = 0;
1167 break;
1168 default:
1169 break;
1170 }
1171
1172 if (ret < 0)
1173 return ret;
1174
1175 return tsl2x7x_invoke_change(indio_dev);
1176}
1177
1178static int tsl2x7x_read_event_value(struct iio_dev *indio_dev,
1179 const struct iio_chan_spec *chan,
1180 enum iio_event_type type,
1181 enum iio_event_direction dir,
1182 enum iio_event_info info,
1183 int *val, int *val2)
1184{
1185 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1186 int ret = -EINVAL, filter_delay, mult;
1187 u8 time;
1188
1189 switch (info) {
1190 case IIO_EV_INFO_VALUE:
1191 if (chan->type == IIO_INTENSITY) {
1192 switch (dir) {
1193 case IIO_EV_DIR_RISING:
1194 *val = chip->settings.als_thresh_high;
1195 ret = IIO_VAL_INT;
1196 break;
1197 case IIO_EV_DIR_FALLING:
1198 *val = chip->settings.als_thresh_low;
1199 ret = IIO_VAL_INT;
1200 break;
1201 default:
1202 break;
1203 }
1204 } else {
1205 switch (dir) {
1206 case IIO_EV_DIR_RISING:
1207 *val = chip->settings.prox_thres_high;
1208 ret = IIO_VAL_INT;
1209 break;
1210 case IIO_EV_DIR_FALLING:
1211 *val = chip->settings.prox_thres_low;
1212 ret = IIO_VAL_INT;
1213 break;
1214 default:
1215 break;
1216 }
1217 }
1218 break;
1219 case IIO_EV_INFO_PERIOD:
1220 if (chan->type == IIO_INTENSITY) {
1221 time = chip->settings.als_time;
1222 mult = chip->settings.persistence & 0x0F;
1223 } else {
1224 time = chip->settings.prx_time;
1225 mult = (chip->settings.persistence & 0xF0) >> 4;
1226 }
1227
1228 /* Determine integration time */
1229 *val = (TSL2X7X_MAX_TIMER_CNT - time) + 1;
1230 *val2 = *val * TSL2X7X_MIN_ITIME;
1231 filter_delay = *val2 * mult;
1232 *val = filter_delay / 1000;
1233 *val2 = filter_delay % 1000;
1234 ret = IIO_VAL_INT_PLUS_MICRO;
1235 break;
1236 default:
1237 break;
1238 }
1239
1240 return ret;
1241}
1242
1243static int tsl2x7x_read_raw(struct iio_dev *indio_dev,
1244 struct iio_chan_spec const *chan,
1245 int *val,
1246 int *val2,
1247 long mask)
1248{
1249 int ret = -EINVAL;
1250 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1251
1252 switch (mask) {
1253 case IIO_CHAN_INFO_PROCESSED:
1254 switch (chan->type) {
1255 case IIO_LIGHT:
1256 tsl2x7x_get_lux(indio_dev);
1257 *val = chip->als_cur_info.lux;
1258 ret = IIO_VAL_INT;
1259 break;
1260 default:
1261 return -EINVAL;
1262 }
1263 break;
1264 case IIO_CHAN_INFO_RAW:
1265 switch (chan->type) {
1266 case IIO_INTENSITY:
1267 tsl2x7x_get_lux(indio_dev);
1268 if (chan->channel == 0)
1269 *val = chip->als_cur_info.als_ch0;
1270 else
1271 *val = chip->als_cur_info.als_ch1;
1272 ret = IIO_VAL_INT;
1273 break;
1274 case IIO_PROXIMITY:
1275 tsl2x7x_get_prox(indio_dev);
1276 *val = chip->prox_data;
1277 ret = IIO_VAL_INT;
1278 break;
1279 default:
1280 return -EINVAL;
1281 }
1282 break;
1283 case IIO_CHAN_INFO_CALIBSCALE:
1284 if (chan->type == IIO_LIGHT)
1285 *val = tsl2x7x_als_gain[chip->settings.als_gain];
1286 else
1287 *val = tsl2x7x_prx_gain[chip->settings.prox_gain];
1288 ret = IIO_VAL_INT;
1289 break;
1290 case IIO_CHAN_INFO_CALIBBIAS:
1291 *val = chip->settings.als_gain_trim;
1292 ret = IIO_VAL_INT;
1293 break;
1294 case IIO_CHAN_INFO_INT_TIME:
1295 *val = (TSL2X7X_MAX_TIMER_CNT - chip->settings.als_time) + 1;
1296 *val2 = ((*val * TSL2X7X_MIN_ITIME) % 1000) / 1000;
1297 ret = IIO_VAL_INT_PLUS_MICRO;
1298 break;
1299 default:
1300 ret = -EINVAL;
1301 }
1302
1303 return ret;
1304}
1305
1306static int tsl2x7x_write_raw(struct iio_dev *indio_dev,
1307 struct iio_chan_spec const *chan,
1308 int val,
1309 int val2,
1310 long mask)
1311{
1312 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1313
1314 switch (mask) {
1315 case IIO_CHAN_INFO_CALIBSCALE:
1316 if (chan->type == IIO_INTENSITY) {
1317 switch (val) {
1318 case 1:
1319 chip->settings.als_gain = 0;
1320 break;
1321 case 8:
1322 chip->settings.als_gain = 1;
1323 break;
1324 case 16:
1325 chip->settings.als_gain = 2;
1326 break;
1327 case 120:
1328 switch (chip->id) {
1329 case tsl2572:
1330 case tsl2672:
1331 case tmd2672:
1332 case tsl2772:
1333 case tmd2772:
1334 return -EINVAL;
1335 }
1336 chip->settings.als_gain = 3;
1337 break;
1338 case 128:
1339 switch (chip->id) {
1340 case tsl2571:
1341 case tsl2671:
1342 case tmd2671:
1343 case tsl2771:
1344 case tmd2771:
1345 return -EINVAL;
1346 }
1347 chip->settings.als_gain = 3;
1348 break;
1349 default:
1350 return -EINVAL;
1351 }
1352 } else {
1353 switch (val) {
1354 case 1:
1355 chip->settings.prox_gain = 0;
1356 break;
1357 case 2:
1358 chip->settings.prox_gain = 1;
1359 break;
1360 case 4:
1361 chip->settings.prox_gain = 2;
1362 break;
1363 case 8:
1364 chip->settings.prox_gain = 3;
1365 break;
1366 default:
1367 return -EINVAL;
1368 }
1369 }
1370 break;
1371 case IIO_CHAN_INFO_CALIBBIAS:
1372 chip->settings.als_gain_trim = val;
1373 break;
1374 case IIO_CHAN_INFO_INT_TIME:
1375 chip->settings.als_time =
1376 TSL2X7X_MAX_TIMER_CNT - (val2 / TSL2X7X_MIN_ITIME);
1377
1378 dev_info(&chip->client->dev, "%s: als time = %d",
1379 __func__, chip->settings.als_time);
1380 break;
1381 default:
1382 return -EINVAL;
1383 }
1384
1385 return tsl2x7x_invoke_change(indio_dev);
1386}
1387
1388static DEVICE_ATTR_RO(in_illuminance0_calibscale_available);
1389
1390static DEVICE_ATTR_RW(in_illuminance0_target_input);
1391
1392static DEVICE_ATTR_WO(in_illuminance0_calibrate);
1393
1394static DEVICE_ATTR_WO(in_proximity0_calibrate);
1395
1396static DEVICE_ATTR_RW(in_illuminance0_lux_table);
1397
1398/* Use the default register values to identify the Taos device */
1399static int tsl2x7x_device_id(int *id, int target)
1400{
1401 switch (target) {
1402 case tsl2571:
1403 case tsl2671:
1404 case tsl2771:
1405 return (*id & 0xf0) == TRITON_ID;
1406 case tmd2671:
1407 case tmd2771:
1408 return (*id & 0xf0) == HALIBUT_ID;
1409 case tsl2572:
1410 case tsl2672:
1411 case tmd2672:
1412 case tsl2772:
1413 case tmd2772:
1414 return (*id & 0xf0) == SWORDFISH_ID;
1415 }
1416
1417 return -EINVAL;
1418}
1419
1420static irqreturn_t tsl2x7x_event_handler(int irq, void *private)
1421{
1422 struct iio_dev *indio_dev = private;
1423 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1424 s64 timestamp = iio_get_time_ns(indio_dev);
1425 int ret;
1426
1427 ret = tsl2x7x_read_status(chip);
1428 if (ret < 0)
1429 return ret;
1430
1431 /* What type of interrupt do we need to process */
1432 if (ret & TSL2X7X_STA_PRX_INTR) {
1433 tsl2x7x_get_prox(indio_dev); /* freshen data for ABI */
1434 iio_push_event(indio_dev,
1435 IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY,
1436 0,
1437 IIO_EV_TYPE_THRESH,
1438 IIO_EV_DIR_EITHER),
1439 timestamp);
1440 }
1441
1442 if (ret & TSL2X7X_STA_ALS_INTR) {
1443 tsl2x7x_get_lux(indio_dev); /* freshen data for ABI */
1444 iio_push_event(indio_dev,
1445 IIO_UNMOD_EVENT_CODE(IIO_LIGHT,
1446 0,
1447 IIO_EV_TYPE_THRESH,
1448 IIO_EV_DIR_EITHER),
1449 timestamp);
1450 }
1451
1452 ret = tsl2x7x_clear_interrupts(chip, TSL2X7X_CMD_PROXALS_INT_CLR);
1453 if (ret < 0)
1454 return ret;
1455
1456 return IRQ_HANDLED;
1457}
1458
1459static struct attribute *tsl2x7x_ALS_device_attrs[] = {
1460 &dev_attr_in_illuminance0_calibscale_available.attr,
1461 &iio_const_attr_in_illuminance0_integration_time_available
1462 .dev_attr.attr,
1463 &dev_attr_in_illuminance0_target_input.attr,
1464 &dev_attr_in_illuminance0_calibrate.attr,
1465 &dev_attr_in_illuminance0_lux_table.attr,
1466 NULL
1467};
1468
1469static struct attribute *tsl2x7x_PRX_device_attrs[] = {
1470 &dev_attr_in_proximity0_calibrate.attr,
1471 NULL
1472};
1473
1474static struct attribute *tsl2x7x_ALSPRX_device_attrs[] = {
1475 &dev_attr_in_illuminance0_calibscale_available.attr,
1476 &iio_const_attr_in_illuminance0_integration_time_available
1477 .dev_attr.attr,
1478 &dev_attr_in_illuminance0_target_input.attr,
1479 &dev_attr_in_illuminance0_calibrate.attr,
1480 &dev_attr_in_illuminance0_lux_table.attr,
1481 NULL
1482};
1483
1484static struct attribute *tsl2x7x_PRX2_device_attrs[] = {
1485 &dev_attr_in_proximity0_calibrate.attr,
1486 &iio_const_attr_in_proximity0_calibscale_available.dev_attr.attr,
1487 NULL
1488};
1489
1490static struct attribute *tsl2x7x_ALSPRX2_device_attrs[] = {
1491 &dev_attr_in_illuminance0_calibscale_available.attr,
1492 &iio_const_attr_in_illuminance0_integration_time_available
1493 .dev_attr.attr,
1494 &dev_attr_in_illuminance0_target_input.attr,
1495 &dev_attr_in_illuminance0_calibrate.attr,
1496 &dev_attr_in_illuminance0_lux_table.attr,
1497 &dev_attr_in_proximity0_calibrate.attr,
1498 &iio_const_attr_in_proximity0_calibscale_available.dev_attr.attr,
1499 NULL
1500};
1501
1502static const struct attribute_group tsl2X7X_device_attr_group_tbl[] = {
1503 [ALS] = {
1504 .attrs = tsl2x7x_ALS_device_attrs,
1505 },
1506 [PRX] = {
1507 .attrs = tsl2x7x_PRX_device_attrs,
1508 },
1509 [ALSPRX] = {
1510 .attrs = tsl2x7x_ALSPRX_device_attrs,
1511 },
1512 [PRX2] = {
1513 .attrs = tsl2x7x_PRX2_device_attrs,
1514 },
1515 [ALSPRX2] = {
1516 .attrs = tsl2x7x_ALSPRX2_device_attrs,
1517 },
1518};
1519
1520static const struct iio_info tsl2X7X_device_info[] = {
1521 [ALS] = {
1522 .attrs = &tsl2X7X_device_attr_group_tbl[ALS],
1523 .read_raw = &tsl2x7x_read_raw,
1524 .write_raw = &tsl2x7x_write_raw,
1525 .read_event_value = &tsl2x7x_read_event_value,
1526 .write_event_value = &tsl2x7x_write_event_value,
1527 .read_event_config = &tsl2x7x_read_interrupt_config,
1528 .write_event_config = &tsl2x7x_write_interrupt_config,
1529 },
1530 [PRX] = {
1531 .attrs = &tsl2X7X_device_attr_group_tbl[PRX],
1532 .read_raw = &tsl2x7x_read_raw,
1533 .write_raw = &tsl2x7x_write_raw,
1534 .read_event_value = &tsl2x7x_read_event_value,
1535 .write_event_value = &tsl2x7x_write_event_value,
1536 .read_event_config = &tsl2x7x_read_interrupt_config,
1537 .write_event_config = &tsl2x7x_write_interrupt_config,
1538 },
1539 [ALSPRX] = {
1540 .attrs = &tsl2X7X_device_attr_group_tbl[ALSPRX],
1541 .read_raw = &tsl2x7x_read_raw,
1542 .write_raw = &tsl2x7x_write_raw,
1543 .read_event_value = &tsl2x7x_read_event_value,
1544 .write_event_value = &tsl2x7x_write_event_value,
1545 .read_event_config = &tsl2x7x_read_interrupt_config,
1546 .write_event_config = &tsl2x7x_write_interrupt_config,
1547 },
1548 [PRX2] = {
1549 .attrs = &tsl2X7X_device_attr_group_tbl[PRX2],
1550 .read_raw = &tsl2x7x_read_raw,
1551 .write_raw = &tsl2x7x_write_raw,
1552 .read_event_value = &tsl2x7x_read_event_value,
1553 .write_event_value = &tsl2x7x_write_event_value,
1554 .read_event_config = &tsl2x7x_read_interrupt_config,
1555 .write_event_config = &tsl2x7x_write_interrupt_config,
1556 },
1557 [ALSPRX2] = {
1558 .attrs = &tsl2X7X_device_attr_group_tbl[ALSPRX2],
1559 .read_raw = &tsl2x7x_read_raw,
1560 .write_raw = &tsl2x7x_write_raw,
1561 .read_event_value = &tsl2x7x_read_event_value,
1562 .write_event_value = &tsl2x7x_write_event_value,
1563 .read_event_config = &tsl2x7x_read_interrupt_config,
1564 .write_event_config = &tsl2x7x_write_interrupt_config,
1565 },
1566};
1567
1568static const struct iio_event_spec tsl2x7x_events[] = {
1569 {
1570 .type = IIO_EV_TYPE_THRESH,
1571 .dir = IIO_EV_DIR_RISING,
1572 .mask_separate = BIT(IIO_EV_INFO_VALUE) |
1573 BIT(IIO_EV_INFO_ENABLE),
1574 }, {
1575 .type = IIO_EV_TYPE_THRESH,
1576 .dir = IIO_EV_DIR_FALLING,
1577 .mask_separate = BIT(IIO_EV_INFO_VALUE) |
1578 BIT(IIO_EV_INFO_ENABLE),
1579 }, {
1580 .type = IIO_EV_TYPE_THRESH,
1581 .dir = IIO_EV_DIR_EITHER,
1582 .mask_separate = BIT(IIO_EV_INFO_PERIOD),
1583 },
1584};
1585
1586static const struct tsl2x7x_chip_info tsl2x7x_chip_info_tbl[] = {
1587 [ALS] = {
1588 .channel = {
1589 {
1590 .type = IIO_LIGHT,
1591 .indexed = 1,
1592 .channel = 0,
1593 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED) |
1594 BIT(IIO_CHAN_INFO_INT_TIME),
1595 }, {
1596 .type = IIO_INTENSITY,
1597 .indexed = 1,
1598 .channel = 0,
1599 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1600 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1601 BIT(IIO_CHAN_INFO_CALIBBIAS),
1602 .event_spec = tsl2x7x_events,
1603 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1604 }, {
1605 .type = IIO_INTENSITY,
1606 .indexed = 1,
1607 .channel = 1,
1608 },
1609 },
1610 .chan_table_elements = 3,
1611 .info = &tsl2X7X_device_info[ALS],
1612 },
1613 [PRX] = {
1614 .channel = {
1615 {
1616 .type = IIO_PROXIMITY,
1617 .indexed = 1,
1618 .channel = 0,
1619 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1620 .event_spec = tsl2x7x_events,
1621 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1622 },
1623 },
1624 .chan_table_elements = 1,
1625 .info = &tsl2X7X_device_info[PRX],
1626 },
1627 [ALSPRX] = {
1628 .channel = {
1629 {
1630 .type = IIO_LIGHT,
1631 .indexed = 1,
1632 .channel = 0,
1633 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED) |
1634 BIT(IIO_CHAN_INFO_INT_TIME),
1635 }, {
1636 .type = IIO_INTENSITY,
1637 .indexed = 1,
1638 .channel = 0,
1639 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1640 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1641 BIT(IIO_CHAN_INFO_CALIBBIAS),
1642 .event_spec = tsl2x7x_events,
1643 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1644 }, {
1645 .type = IIO_INTENSITY,
1646 .indexed = 1,
1647 .channel = 1,
1648 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1649 }, {
1650 .type = IIO_PROXIMITY,
1651 .indexed = 1,
1652 .channel = 0,
1653 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1654 .event_spec = tsl2x7x_events,
1655 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1656 },
1657 },
1658 .chan_table_elements = 4,
1659 .info = &tsl2X7X_device_info[ALSPRX],
1660 },
1661 [PRX2] = {
1662 .channel = {
1663 {
1664 .type = IIO_PROXIMITY,
1665 .indexed = 1,
1666 .channel = 0,
1667 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1668 BIT(IIO_CHAN_INFO_CALIBSCALE),
1669 .event_spec = tsl2x7x_events,
1670 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1671 },
1672 },
1673 .chan_table_elements = 1,
1674 .info = &tsl2X7X_device_info[PRX2],
1675 },
1676 [ALSPRX2] = {
1677 .channel = {
1678 {
1679 .type = IIO_LIGHT,
1680 .indexed = 1,
1681 .channel = 0,
1682 .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED) |
1683 BIT(IIO_CHAN_INFO_INT_TIME),
1684 }, {
1685 .type = IIO_INTENSITY,
1686 .indexed = 1,
1687 .channel = 0,
1688 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1689 BIT(IIO_CHAN_INFO_CALIBSCALE) |
1690 BIT(IIO_CHAN_INFO_CALIBBIAS),
1691 .event_spec = tsl2x7x_events,
1692 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1693 }, {
1694 .type = IIO_INTENSITY,
1695 .indexed = 1,
1696 .channel = 1,
1697 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1698 }, {
1699 .type = IIO_PROXIMITY,
1700 .indexed = 1,
1701 .channel = 0,
1702 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1703 BIT(IIO_CHAN_INFO_CALIBSCALE),
1704 .event_spec = tsl2x7x_events,
1705 .num_event_specs = ARRAY_SIZE(tsl2x7x_events),
1706 },
1707 },
1708 .chan_table_elements = 4,
1709 .info = &tsl2X7X_device_info[ALSPRX2],
1710 },
1711};
1712
1713static int tsl2x7x_probe(struct i2c_client *clientp,
1714 const struct i2c_device_id *id)
1715{
1716 int ret;
1717 struct iio_dev *indio_dev;
1718 struct tsl2X7X_chip *chip;
1719
1720 indio_dev = devm_iio_device_alloc(&clientp->dev, sizeof(*chip));
1721 if (!indio_dev)
1722 return -ENOMEM;
1723
1724 chip = iio_priv(indio_dev);
1725 chip->client = clientp;
1726 i2c_set_clientdata(clientp, indio_dev);
1727
1728 ret = i2c_smbus_read_byte_data(chip->client,
1729 TSL2X7X_CMD_REG | TSL2X7X_CHIPID);
1730 if (ret < 0)
1731 return ret;
1732
1733 if ((!tsl2x7x_device_id(&ret, id->driver_data)) ||
1734 (tsl2x7x_device_id(&ret, id->driver_data) == -EINVAL)) {
1735 dev_info(&chip->client->dev,
1736 "%s: i2c device found does not match expected id\n",
1737 __func__);
1738 return -EINVAL;
1739 }
1740
1741 ret = i2c_smbus_write_byte(clientp, TSL2X7X_CMD_REG | TSL2X7X_CNTRL);
1742 if (ret < 0) {
1743 dev_err(&clientp->dev, "write to cmd reg failed. err = %d\n",
1744 ret);
1745 return ret;
1746 }
1747
1748 /*
1749 * ALS and PROX functions can be invoked via user space poll
1750 * or H/W interrupt. If busy return last sample.
1751 */
1752 mutex_init(&chip->als_mutex);
1753 mutex_init(&chip->prox_mutex);
1754
1755 chip->tsl2x7x_chip_status = TSL2X7X_CHIP_UNKNOWN;
1756 chip->pdata = dev_get_platdata(&clientp->dev);
1757 chip->id = id->driver_data;
1758 chip->chip_info =
1759 &tsl2x7x_chip_info_tbl[device_channel_config[id->driver_data]];
1760
1761 indio_dev->info = chip->chip_info->info;
1762 indio_dev->dev.parent = &clientp->dev;
1763 indio_dev->modes = INDIO_DIRECT_MODE;
1764 indio_dev->name = chip->client->name;
1765 indio_dev->channels = chip->chip_info->channel;
1766 indio_dev->num_channels = chip->chip_info->chan_table_elements;
1767
1768 if (clientp->irq) {
1769 ret = devm_request_threaded_irq(&clientp->dev, clientp->irq,
1770 NULL,
1771 &tsl2x7x_event_handler,
1772 IRQF_TRIGGER_RISING |
1773 IRQF_ONESHOT,
1774 "TSL2X7X_event",
1775 indio_dev);
1776 if (ret) {
1777 dev_err(&clientp->dev,
1778 "%s: irq request failed", __func__);
1779 return ret;
1780 }
1781 }
1782
1783 /* Load up the defaults */
1784 tsl2x7x_defaults(chip);
1785 /* Make sure the chip is on */
1786 tsl2x7x_chip_on(indio_dev);
1787
1788 ret = iio_device_register(indio_dev);
1789 if (ret) {
1790 dev_err(&clientp->dev,
1791 "%s: iio registration failed\n", __func__);
1792 return ret;
1793 }
1794
1795 dev_info(&clientp->dev, "%s Light sensor found.\n", id->name);
1796
1797 return 0;
1798}
1799
1800static int tsl2x7x_suspend(struct device *dev)
1801{
1802 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1803 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1804 int ret = 0;
1805
1806 if (chip->tsl2x7x_chip_status == TSL2X7X_CHIP_WORKING) {
1807 ret = tsl2x7x_chip_off(indio_dev);
1808 chip->tsl2x7x_chip_status = TSL2X7X_CHIP_SUSPENDED;
1809 }
1810
1811 return ret;
1812}
1813
1814static int tsl2x7x_resume(struct device *dev)
1815{
1816 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1817 struct tsl2X7X_chip *chip = iio_priv(indio_dev);
1818 int ret = 0;
1819
1820 if (chip->tsl2x7x_chip_status == TSL2X7X_CHIP_SUSPENDED)
1821 ret = tsl2x7x_chip_on(indio_dev);
1822
1823 return ret;
1824}
1825
1826static int tsl2x7x_remove(struct i2c_client *client)
1827{
1828 struct iio_dev *indio_dev = i2c_get_clientdata(client);
1829
1830 tsl2x7x_chip_off(indio_dev);
1831
1832 iio_device_unregister(indio_dev);
1833
1834 return 0;
1835}
1836
1837static const struct i2c_device_id tsl2x7x_idtable[] = {
1838 { "tsl2571", tsl2571 },
1839 { "tsl2671", tsl2671 },
1840 { "tmd2671", tmd2671 },
1841 { "tsl2771", tsl2771 },
1842 { "tmd2771", tmd2771 },
1843 { "tsl2572", tsl2572 },
1844 { "tsl2672", tsl2672 },
1845 { "tmd2672", tmd2672 },
1846 { "tsl2772", tsl2772 },
1847 { "tmd2772", tmd2772 },
1848 {}
1849};
1850
1851MODULE_DEVICE_TABLE(i2c, tsl2x7x_idtable);
1852
1853static const struct of_device_id tsl2x7x_of_match[] = {
1854 { .compatible = "amstaos,tsl2571" },
1855 { .compatible = "amstaos,tsl2671" },
1856 { .compatible = "amstaos,tmd2671" },
1857 { .compatible = "amstaos,tsl2771" },
1858 { .compatible = "amstaos,tmd2771" },
1859 { .compatible = "amstaos,tsl2572" },
1860 { .compatible = "amstaos,tsl2672" },
1861 { .compatible = "amstaos,tmd2672" },
1862 { .compatible = "amstaos,tsl2772" },
1863 { .compatible = "amstaos,tmd2772" },
1864 {}
1865};
1866MODULE_DEVICE_TABLE(of, tsl2x7x_of_match);
1867
1868static const struct dev_pm_ops tsl2x7x_pm_ops = {
1869 .suspend = tsl2x7x_suspend,
1870 .resume = tsl2x7x_resume,
1871};
1872
1873/* Driver definition */
1874static struct i2c_driver tsl2x7x_driver = {
1875 .driver = {
1876 .name = "tsl2x7x",
1877 .of_match_table = tsl2x7x_of_match,
1878 .pm = &tsl2x7x_pm_ops,
1879 },
1880 .id_table = tsl2x7x_idtable,
1881 .probe = tsl2x7x_probe,
1882 .remove = tsl2x7x_remove,
1883};
1884
1885module_i2c_driver(tsl2x7x_driver);
1886
1887MODULE_AUTHOR("J. August Brenner<jbrenner@taosinc.com>");
1888MODULE_DESCRIPTION("TAOS tsl2x7x ambient and proximity light sensor driver");
1889MODULE_LICENSE("GPL");
drivers/staging/iio/light/tsl2x7x.h+0−99
@@ -1,99 +0,0 @@
1/*
2 * Device driver for monitoring ambient light intensity (lux)
3 * and proximity (prox) within the TAOS TSL2X7X family of devices.
4 *
5 * Copyright (c) 2012, TAOS Corporation.
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful, but WITHOUT
13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15 * more details.
16 *
17 * You should have received a copy of the GNU General Public License along
18 * with this program; if not, write to the Free Software Foundation, Inc.,
19 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20 */
21
22#ifndef __TSL2X7X_H
23#define __TSL2X7X_H
24
25struct tsl2x7x_lux {
26 unsigned int ratio;
27 unsigned int ch0;
28 unsigned int ch1;
29};
30
31/* Max number of segments allowable in LUX table */
32#define TSL2X7X_MAX_LUX_TABLE_SIZE 9
33/* The default LUX tables all have 3 elements. */
34#define TSL2X7X_DEF_LUX_TABLE_SZ 3
35#define TSL2X7X_DEFAULT_TABLE_BYTES (sizeof(struct tsl2x7x_lux) * \
36 TSL2X7X_DEF_LUX_TABLE_SZ)
37
38/**
39 * struct tsl2x7x_default_settings - power on defaults unless
40 * overridden by platform data.
41 * @als_time: ALS Integration time - multiple of 50mS
42 * @als_gain: Index into the ALS gain table.
43 * @als_gain_trim: default gain trim to account for
44 * aperture effects.
45 * @wait_time: Time between PRX and ALS cycles
46 * in 2.7 periods
47 * @prx_time: 5.2ms prox integration time -
48 * decrease in 2.7ms periods
49 * @prx_gain: Proximity gain index
50 * @prox_config: Prox configuration filters.
51 * @als_cal_target: Known external ALS reading for
52 * calibration.
53 * @interrupts_en: Enable/Disable - 0x00 = none, 0x10 = als,
54 * 0x20 = prx, 0x30 = bth
55 * @persistence: H/W Filters, Number of 'out of limits'
56 * ADC readings PRX/ALS.
57 * @als_thresh_low: CH0 'low' count to trigger interrupt.
58 * @als_thresh_high: CH0 'high' count to trigger interrupt.
59 * @prox_thres_low: Low threshold proximity detection.
60 * @prox_thres_high: High threshold proximity detection
61 * @prox_pulse_count: Number if proximity emitter pulses
62 * @prox_max_samples_cal: Used for prox cal.
63 */
64struct tsl2x7x_settings {
65 int als_time;
66 int als_gain;
67 int als_gain_trim;
68 int wait_time;
69 int prx_time;
70 int prox_gain;
71 int prox_config;
72 int als_cal_target;
73 u8 interrupts_en;
74 u8 persistence;
75 int als_thresh_low;
76 int als_thresh_high;
77 int prox_thres_low;
78 int prox_thres_high;
79 int prox_pulse_count;
80 int prox_max_samples_cal;
81 int prox_diode;
82 int prox_power;
83};
84
85/**
86 * struct tsl2X7X_platform_data - Platform callback, glass and defaults
87 * @platform_power: Suspend/resume platform callback
88 * @power_on: Power on callback
89 * @power_off: Power off callback
90 * @platform_lux_table: Device specific glass coefficents
91 * @platform_default_settings: Device specific power on defaults
92 *
93 */
94struct tsl2X7X_platform_data {
95 struct tsl2x7x_lux platform_lux_table[TSL2X7X_MAX_LUX_TABLE_SIZE];
96 struct tsl2x7x_settings *platform_default_settings;
97};
98
99#endif /* __TSL2X7X_H */
drivers/staging/iio/meter/Kconfig+0−42
@@ -3,48 +3,6 @@ · 2 unmodified lines
3#3#
4menu "Active energy metering IC"4menu "Active energy metering IC"
5 5
6config ADE7753
7 tristate "Analog Devices ADE7753/6 Single-Phase Multifunction Metering IC Driver"
8 depends on SPI
9 help
10 Say yes here to build support for Analog Devices ADE7753 Single-Phase Multifunction
11 Metering IC with di/dt Sensor Interface.
12
13 To compile this driver as a module, choose M here: the
14 module will be called ade7753.
15
16config ADE7754
17 tristate "Analog Devices ADE7754 Polyphase Multifunction Energy Metering IC Driver"
18 depends on SPI
19 help
20 Say yes here to build support for Analog Devices ADE7754 Polyphase
21 Multifunction Energy Metering IC Driver.
22
23 To compile this driver as a module, choose M here: the
24 module will be called ade7754.
25
26config ADE7758
27 tristate "Analog Devices ADE7758 Poly Phase Multifunction Energy Metering IC Driver"
28 depends on SPI
29 select IIO_TRIGGER if IIO_BUFFER
30 select IIO_KFIFO_BUF if IIO_BUFFER
31 help
32 Say yes here to build support for Analog Devices ADE7758 Polyphase
33 Multifunction Energy Metering IC with Per Phase Information Driver.
34
35 To compile this driver as a module, choose M here: the
36 module will be called ade7758.
37
38config ADE7759
39 tristate "Analog Devices ADE7759 Active Energy Metering IC Driver"
40 depends on SPI
41 help
42 Say yes here to build support for Analog Devices ADE7758 Active Energy
43 Metering IC with di/dt Sensor Interface.
44
45 To compile this driver as a module, choose M here: the
46 module will be called ade7759.
47
48config ADE78546config ADE7854
49 tristate "Analog Devices ADE7854/58/68/78 Polyphase Multifunction Energy Metering IC Driver"7 tristate "Analog Devices ADE7854/58/68/78 Polyphase Multifunction Energy Metering IC Driver"
50 depends on SPI || I2C8 depends on SPI || I2C
drivers/staging/iio/meter/Makefile+0−8
@@ -3,14 +3,6 @@ · 2 unmodified lines
3# Makefile for metering ic drivers3# Makefile for metering ic drivers
4#4#
5 5
6obj-$(CONFIG_ADE7753) += ade7753.o
7obj-$(CONFIG_ADE7754) += ade7754.o
8
9ade7758-y := ade7758_core.o
10ade7758-$(CONFIG_IIO_BUFFER) += ade7758_ring.o ade7758_trigger.o
11obj-$(CONFIG_ADE7758) += ade7758.o
12
13obj-$(CONFIG_ADE7759) += ade7759.o
14obj-$(CONFIG_ADE7854) += ade7854.o6obj-$(CONFIG_ADE7854) += ade7854.o
15obj-$(CONFIG_ADE7854_I2C) += ade7854-i2c.o7obj-$(CONFIG_ADE7854_I2C) += ade7854-i2c.o
16obj-$(CONFIG_ADE7854_SPI) += ade7854-spi.o8obj-$(CONFIG_ADE7854_SPI) += ade7854-spi.o
drivers/staging/iio/meter/ade7753.c+0−630
@@ -1,630 +0,0 @@
1/*
2 * ADE7753 Single-Phase Multifunction Metering IC with di/dt Sensor Interface
3 *
4 * Copyright 2010 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2 or later.
7 */
8
9#include <linux/delay.h>
10#include <linux/device.h>
11#include <linux/interrupt.h>
12#include <linux/irq.h>
13#include <linux/kernel.h>
14#include <linux/list.h>
15#include <linux/module.h>
16#include <linux/mutex.h>
17#include <linux/slab.h>
18#include <linux/sysfs.h>
19#include <linux/iio/iio.h>
20#include <linux/iio/sysfs.h>
21#include <linux/spi/spi.h>
22#include "meter.h"
23
24#define ADE7753_WAVEFORM 0x01
25#define ADE7753_AENERGY 0x02
26#define ADE7753_RAENERGY 0x03
27#define ADE7753_LAENERGY 0x04
28#define ADE7753_VAENERGY 0x05
29#define ADE7753_RVAENERGY 0x06
30#define ADE7753_LVAENERGY 0x07
31#define ADE7753_LVARENERGY 0x08
32#define ADE7753_MODE 0x09
33#define ADE7753_IRQEN 0x0A
34#define ADE7753_STATUS 0x0B
35#define ADE7753_RSTSTATUS 0x0C
36#define ADE7753_CH1OS 0x0D
37#define ADE7753_CH2OS 0x0E
38#define ADE7753_GAIN 0x0F
39#define ADE7753_PHCAL 0x10
40#define ADE7753_APOS 0x11
41#define ADE7753_WGAIN 0x12
42#define ADE7753_WDIV 0x13
43#define ADE7753_CFNUM 0x14
44#define ADE7753_CFDEN 0x15
45#define ADE7753_IRMS 0x16
46#define ADE7753_VRMS 0x17
47#define ADE7753_IRMSOS 0x18
48#define ADE7753_VRMSOS 0x19
49#define ADE7753_VAGAIN 0x1A
50#define ADE7753_VADIV 0x1B
51#define ADE7753_LINECYC 0x1C
52#define ADE7753_ZXTOUT 0x1D
53#define ADE7753_SAGCYC 0x1E
54#define ADE7753_SAGLVL 0x1F
55#define ADE7753_IPKLVL 0x20
56#define ADE7753_VPKLVL 0x21
57#define ADE7753_IPEAK 0x22
58#define ADE7753_RSTIPEAK 0x23
59#define ADE7753_VPEAK 0x24
60#define ADE7753_RSTVPEAK 0x25
61#define ADE7753_TEMP 0x26
62#define ADE7753_PERIOD 0x27
63#define ADE7753_TMODE 0x3D
64#define ADE7753_CHKSUM 0x3E
65#define ADE7753_DIEREV 0x3F
66
67#define ADE7753_READ_REG(a) a
68#define ADE7753_WRITE_REG(a) ((a) | 0x80)
69
70#define ADE7753_MAX_TX 4
71#define ADE7753_MAX_RX 4
72#define ADE7753_STARTUP_DELAY 1000
73
74#define ADE7753_SPI_SLOW (u32)(300 * 1000)
75#define ADE7753_SPI_BURST (u32)(1000 * 1000)
76#define ADE7753_SPI_FAST (u32)(2000 * 1000)
77
78/**
79 * struct ade7753_state - device instance specific data
80 * @us: actual spi_device
81 * @tx: transmit buffer
82 * @rx: receive buffer
83 * @buf_lock: mutex to protect tx, rx and write frequency
84 **/
85struct ade7753_state {
86 struct spi_device *us;
87 struct mutex buf_lock;
88 u8 tx[ADE7753_MAX_TX] ____cacheline_aligned;
89 u8 rx[ADE7753_MAX_RX];
90};
91
92static int ade7753_spi_write_reg_8(struct device *dev,
93 u8 reg_address,
94 u8 val)
95{
96 int ret;
97 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
98 struct ade7753_state *st = iio_priv(indio_dev);
99
100 mutex_lock(&st->buf_lock);
101 st->tx[0] = ADE7753_WRITE_REG(reg_address);
102 st->tx[1] = val;
103
104 ret = spi_write(st->us, st->tx, 2);
105 mutex_unlock(&st->buf_lock);
106
107 return ret;
108}
109
110static int __ade7753_spi_write_reg_16(struct device *dev, u8 reg_address,
111 u16 value)
112{
113 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
114 struct ade7753_state *st = iio_priv(indio_dev);
115
116 st->tx[0] = ADE7753_WRITE_REG(reg_address);
117 st->tx[1] = (value >> 8) & 0xFF;
118 st->tx[2] = value & 0xFF;
119
120 return spi_write(st->us, st->tx, 3);
121}
122
123static int ade7753_spi_write_reg_16(struct device *dev, u8 reg_address,
124 u16 value)
125{
126 int ret;
127 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
128 struct ade7753_state *st = iio_priv(indio_dev);
129
130 mutex_lock(&st->buf_lock);
131 ret = __ade7753_spi_write_reg_16(dev, reg_address, value);
132 mutex_unlock(&st->buf_lock);
133
134 return ret;
135}
136
137static int ade7753_spi_read_reg_8(struct device *dev,
138 u8 reg_address,
139 u8 *val)
140{
141 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
142 struct ade7753_state *st = iio_priv(indio_dev);
143 ssize_t ret;
144
145 ret = spi_w8r8(st->us, ADE7753_READ_REG(reg_address));
146 if (ret < 0) {
147 dev_err(&st->us->dev, "problem when reading 8 bit register 0x%02X",
148 reg_address);
149 return ret;
150 }
151 *val = ret;
152
153 return 0;
154}
155
156static int ade7753_spi_read_reg_16(struct device *dev,
157 u8 reg_address,
158 u16 *val)
159{
160 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
161 struct ade7753_state *st = iio_priv(indio_dev);
162 ssize_t ret;
163
164 ret = spi_w8r16be(st->us, ADE7753_READ_REG(reg_address));
165 if (ret < 0) {
166 dev_err(&st->us->dev, "problem when reading 16 bit register 0x%02X",
167 reg_address);
168 return ret;
169 }
170
171 *val = ret;
172
173 return 0;
174}
175
176static int ade7753_spi_read_reg_24(struct device *dev,
177 u8 reg_address,
178 u32 *val)
179{
180 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
181 struct ade7753_state *st = iio_priv(indio_dev);
182 int ret;
183 struct spi_transfer xfers[] = {
184 {
185 .tx_buf = st->tx,
186 .bits_per_word = 8,
187 .len = 1,
188 }, {
189 .rx_buf = st->tx,
190 .bits_per_word = 8,
191 .len = 3,
192 }
193 };
194
195 mutex_lock(&st->buf_lock);
196 st->tx[0] = ADE7753_READ_REG(reg_address);
197
198 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
199 if (ret) {
200 dev_err(&st->us->dev, "problem when reading 24 bit register 0x%02X",
201 reg_address);
202 goto error_ret;
203 }
204 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
205
206error_ret:
207 mutex_unlock(&st->buf_lock);
208 return ret;
209}
210
211static ssize_t ade7753_read_8bit(struct device *dev,
212 struct device_attribute *attr,
213 char *buf)
214{
215 int ret;
216 u8 val;
217 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
218
219 ret = ade7753_spi_read_reg_8(dev, this_attr->address, &val);
220 if (ret)
221 return ret;
222
223 return sprintf(buf, "%u\n", val);
224}
225
226static ssize_t ade7753_read_16bit(struct device *dev,
227 struct device_attribute *attr,
228 char *buf)
229{
230 int ret;
231 u16 val;
232 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
233
234 ret = ade7753_spi_read_reg_16(dev, this_attr->address, &val);
235 if (ret)
236 return ret;
237
238 return sprintf(buf, "%u\n", val);
239}
240
241static ssize_t ade7753_read_24bit(struct device *dev,
242 struct device_attribute *attr,
243 char *buf)
244{
245 int ret;
246 u32 val;
247 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
248
249 ret = ade7753_spi_read_reg_24(dev, this_attr->address, &val);
250 if (ret)
251 return ret;
252
253 return sprintf(buf, "%u\n", val);
254}
255
256static ssize_t ade7753_write_8bit(struct device *dev,
257 struct device_attribute *attr,
258 const char *buf,
259 size_t len)
260{
261 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
262 int ret;
263 u8 val;
264
265 ret = kstrtou8(buf, 10, &val);
266 if (ret)
267 goto error_ret;
268 ret = ade7753_spi_write_reg_8(dev, this_attr->address, val);
269
270error_ret:
271 return ret ? ret : len;
272}
273
274static ssize_t ade7753_write_16bit(struct device *dev,
275 struct device_attribute *attr,
276 const char *buf,
277 size_t len)
278{
279 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
280 int ret;
281 u16 val;
282
283 ret = kstrtou16(buf, 10, &val);
284 if (ret)
285 goto error_ret;
286 ret = ade7753_spi_write_reg_16(dev, this_attr->address, val);
287
288error_ret:
289 return ret ? ret : len;
290}
291
292static int ade7753_reset(struct device *dev)
293{
294 u16 val;
295 int ret;
296
297 ret = ade7753_spi_read_reg_16(dev, ADE7753_MODE, &val);
298 if (ret)
299 return ret;
300
301 val |= BIT(6); /* Software Chip Reset */
302
303 return ade7753_spi_write_reg_16(dev, ADE7753_MODE, val);
304}
305
306static IIO_DEV_ATTR_AENERGY(ade7753_read_24bit, ADE7753_AENERGY);
307static IIO_DEV_ATTR_LAENERGY(ade7753_read_24bit, ADE7753_LAENERGY);
308static IIO_DEV_ATTR_VAENERGY(ade7753_read_24bit, ADE7753_VAENERGY);
309static IIO_DEV_ATTR_LVAENERGY(ade7753_read_24bit, ADE7753_LVAENERGY);
310static IIO_DEV_ATTR_CFDEN(0644,
311 ade7753_read_16bit,
312 ade7753_write_16bit,
313 ADE7753_CFDEN);
314static IIO_DEV_ATTR_CFNUM(0644,
315 ade7753_read_8bit,
316 ade7753_write_8bit,
317 ADE7753_CFNUM);
318static IIO_DEV_ATTR_CHKSUM(ade7753_read_8bit, ADE7753_CHKSUM);
319static IIO_DEV_ATTR_PHCAL(0644,
320 ade7753_read_16bit,
321 ade7753_write_16bit,
322 ADE7753_PHCAL);
323static IIO_DEV_ATTR_APOS(0644,
324 ade7753_read_16bit,
325 ade7753_write_16bit,
326 ADE7753_APOS);
327static IIO_DEV_ATTR_SAGCYC(0644,
328 ade7753_read_8bit,
329 ade7753_write_8bit,
330 ADE7753_SAGCYC);
331static IIO_DEV_ATTR_SAGLVL(0644,
332 ade7753_read_8bit,
333 ade7753_write_8bit,
334 ADE7753_SAGLVL);
335static IIO_DEV_ATTR_LINECYC(0644,
336 ade7753_read_8bit,
337 ade7753_write_8bit,
338 ADE7753_LINECYC);
339static IIO_DEV_ATTR_WDIV(0644,
340 ade7753_read_8bit,
341 ade7753_write_8bit,
342 ADE7753_WDIV);
343static IIO_DEV_ATTR_IRMS(0644,
344 ade7753_read_24bit,
345 NULL,
346 ADE7753_IRMS);
347static IIO_DEV_ATTR_VRMS(0444,
348 ade7753_read_24bit,
349 NULL,
350 ADE7753_VRMS);
351static IIO_DEV_ATTR_IRMSOS(0644,
352 ade7753_read_16bit,
353 ade7753_write_16bit,
354 ADE7753_IRMSOS);
355static IIO_DEV_ATTR_VRMSOS(0644,
356 ade7753_read_16bit,
357 ade7753_write_16bit,
358 ADE7753_VRMSOS);
359static IIO_DEV_ATTR_WGAIN(0644,
360 ade7753_read_16bit,
361 ade7753_write_16bit,
362 ADE7753_WGAIN);
363static IIO_DEV_ATTR_VAGAIN(0644,
364 ade7753_read_16bit,
365 ade7753_write_16bit,
366 ADE7753_VAGAIN);
367static IIO_DEV_ATTR_PGA_GAIN(0644,
368 ade7753_read_16bit,
369 ade7753_write_16bit,
370 ADE7753_GAIN);
371static IIO_DEV_ATTR_IPKLVL(0644,
372 ade7753_read_8bit,
373 ade7753_write_8bit,
374 ADE7753_IPKLVL);
375static IIO_DEV_ATTR_VPKLVL(0644,
376 ade7753_read_8bit,
377 ade7753_write_8bit,
378 ADE7753_VPKLVL);
379static IIO_DEV_ATTR_IPEAK(0444,
380 ade7753_read_24bit,
381 NULL,
382 ADE7753_IPEAK);
383static IIO_DEV_ATTR_VPEAK(0444,
384 ade7753_read_24bit,
385 NULL,
386 ADE7753_VPEAK);
387static IIO_DEV_ATTR_VPERIOD(0444,
388 ade7753_read_16bit,
389 NULL,
390 ADE7753_PERIOD);
391
392static IIO_DEVICE_ATTR(choff_1, 0644,
393 ade7753_read_8bit,
394 ade7753_write_8bit,
395 ADE7753_CH1OS);
396
397static IIO_DEVICE_ATTR(choff_2, 0644,
398 ade7753_read_8bit,
399 ade7753_write_8bit,
400 ADE7753_CH2OS);
401
402static int ade7753_set_irq(struct device *dev, bool enable)
403{
404 int ret;
405 u8 irqen;
406
407 ret = ade7753_spi_read_reg_8(dev, ADE7753_IRQEN, &irqen);
408 if (ret)
409 goto error_ret;
410
411 if (enable)
412 irqen |= BIT(3); /* Enables an interrupt when a data is
413 * present in the waveform register
414 */
415 else
416 irqen &= ~BIT(3);
417
418 ret = ade7753_spi_write_reg_8(dev, ADE7753_IRQEN, irqen);
419
420error_ret:
421 return ret;
422}
423
424/* Power down the device */
425static int ade7753_stop_device(struct device *dev)
426{
427 u16 val;
428 int ret;
429
430 ret = ade7753_spi_read_reg_16(dev, ADE7753_MODE, &val);
431 if (ret)
432 return ret;
433
434 val |= BIT(4); /* AD converters can be turned off */
435
436 return ade7753_spi_write_reg_16(dev, ADE7753_MODE, val);
437}
438
439static int ade7753_initial_setup(struct iio_dev *indio_dev)
440{
441 int ret;
442 struct device *dev = &indio_dev->dev;
443 struct ade7753_state *st = iio_priv(indio_dev);
444
445 /* use low spi speed for init */
446 st->us->mode = SPI_MODE_3;
447 spi_setup(st->us);
448
449 /* Disable IRQ */
450 ret = ade7753_set_irq(dev, false);
451 if (ret) {
452 dev_err(dev, "disable irq failed");
453 goto err_ret;
454 }
455
456 ade7753_reset(dev);
457 usleep_range(ADE7753_STARTUP_DELAY, ADE7753_STARTUP_DELAY + 100);
458
459err_ret:
460 return ret;
461}
462
463static ssize_t ade7753_read_frequency(struct device *dev,
464 struct device_attribute *attr,
465 char *buf)
466{
467 int ret;
468 u16 t;
469 int sps;
470
471 ret = ade7753_spi_read_reg_16(dev, ADE7753_MODE, &t);
472 if (ret)
473 return ret;
474
475 t = (t >> 11) & 0x3;
476 sps = 27900 / (1 + t);
477
478 return sprintf(buf, "%d\n", sps);
479}
480
481static ssize_t ade7753_write_frequency(struct device *dev,
482 struct device_attribute *attr,
483 const char *buf,
484 size_t len)
485{
486 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
487 struct ade7753_state *st = iio_priv(indio_dev);
488 u16 val;
489 int ret;
490 u16 reg, t;
491
492 ret = kstrtou16(buf, 10, &val);
493 if (ret)
494 return ret;
495 if (!val)
496 return -EINVAL;
497
498 mutex_lock(&st->buf_lock);
499
500 t = 27900 / val;
501 if (t > 0)
502 t--;
503
504 if (t > 1)
505 st->us->max_speed_hz = ADE7753_SPI_SLOW;
506 else
507 st->us->max_speed_hz = ADE7753_SPI_FAST;
508
509 ret = ade7753_spi_read_reg_16(dev, ADE7753_MODE, &reg);
510 if (ret)
511 goto out;
512
513 reg &= ~(3 << 11);
514 reg |= t << 11;
515
516 ret = __ade7753_spi_write_reg_16(dev, ADE7753_MODE, reg);
517
518out:
519 mutex_unlock(&st->buf_lock);
520
521 return ret ? ret : len;
522}
523
524static IIO_DEV_ATTR_TEMP_RAW(ade7753_read_8bit);
525static IIO_CONST_ATTR(in_temp_offset, "-25 C");
526static IIO_CONST_ATTR(in_temp_scale, "0.67 C");
527
528static IIO_DEV_ATTR_SAMP_FREQ(0644,
529 ade7753_read_frequency,
530 ade7753_write_frequency);
531
532static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("27900 14000 7000 3500");
533
534static struct attribute *ade7753_attributes[] = {
535 &iio_dev_attr_in_temp_raw.dev_attr.attr,
536 &iio_const_attr_in_temp_offset.dev_attr.attr,
537 &iio_const_attr_in_temp_scale.dev_attr.attr,
538 &iio_dev_attr_sampling_frequency.dev_attr.attr,
539 &iio_const_attr_sampling_frequency_available.dev_attr.attr,
540 &iio_dev_attr_phcal.dev_attr.attr,
541 &iio_dev_attr_cfden.dev_attr.attr,
542 &iio_dev_attr_aenergy.dev_attr.attr,
543 &iio_dev_attr_laenergy.dev_attr.attr,
544 &iio_dev_attr_vaenergy.dev_attr.attr,
545 &iio_dev_attr_lvaenergy.dev_attr.attr,
546 &iio_dev_attr_cfnum.dev_attr.attr,
547 &iio_dev_attr_apos.dev_attr.attr,
548 &iio_dev_attr_sagcyc.dev_attr.attr,
549 &iio_dev_attr_saglvl.dev_attr.attr,
550 &iio_dev_attr_linecyc.dev_attr.attr,
551 &iio_dev_attr_chksum.dev_attr.attr,
552 &iio_dev_attr_pga_gain.dev_attr.attr,
553 &iio_dev_attr_wgain.dev_attr.attr,
554 &iio_dev_attr_choff_1.dev_attr.attr,
555 &iio_dev_attr_choff_2.dev_attr.attr,
556 &iio_dev_attr_wdiv.dev_attr.attr,
557 &iio_dev_attr_irms.dev_attr.attr,
558 &iio_dev_attr_vrms.dev_attr.attr,
559 &iio_dev_attr_irmsos.dev_attr.attr,
560 &iio_dev_attr_vrmsos.dev_attr.attr,
561 &iio_dev_attr_vagain.dev_attr.attr,
562 &iio_dev_attr_ipklvl.dev_attr.attr,
563 &iio_dev_attr_vpklvl.dev_attr.attr,
564 &iio_dev_attr_ipeak.dev_attr.attr,
565 &iio_dev_attr_vpeak.dev_attr.attr,
566 &iio_dev_attr_vperiod.dev_attr.attr,
567 NULL,
568};
569
570static const struct attribute_group ade7753_attribute_group = {
571 .attrs = ade7753_attributes,
572};
573
574static const struct iio_info ade7753_info = {
575 .attrs = &ade7753_attribute_group,
576};
577
578static int ade7753_probe(struct spi_device *spi)
579{
580 int ret;
581 struct ade7753_state *st;
582 struct iio_dev *indio_dev;
583
584 /* setup the industrialio driver allocated elements */
585 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
586 if (!indio_dev)
587 return -ENOMEM;
588 /* this is only used for removal purposes */
589 spi_set_drvdata(spi, indio_dev);
590
591 st = iio_priv(indio_dev);
592 st->us = spi;
593 mutex_init(&st->buf_lock);
594
595 indio_dev->name = spi->dev.driver->name;
596 indio_dev->dev.parent = &spi->dev;
597 indio_dev->info = &ade7753_info;
598 indio_dev->modes = INDIO_DIRECT_MODE;
599
600 /* Get the device into a sane initial state */
601 ret = ade7753_initial_setup(indio_dev);
602 if (ret)
603 return ret;
604
605 return iio_device_register(indio_dev);
606}
607
608static int ade7753_remove(struct spi_device *spi)
609{
610 struct iio_dev *indio_dev = spi_get_drvdata(spi);
611
612 iio_device_unregister(indio_dev);
613 ade7753_stop_device(&indio_dev->dev);
614
615 return 0;
616}
617
618static struct spi_driver ade7753_driver = {
619 .driver = {
620 .name = "ade7753",
621 },
622 .probe = ade7753_probe,
623 .remove = ade7753_remove,
624};
625module_spi_driver(ade7753_driver);
626
627MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
628MODULE_DESCRIPTION("Analog Devices ADE7753/6 Single-Phase Multifunction Meter");
629MODULE_LICENSE("GPL v2");
630MODULE_ALIAS("spi:ade7753");
drivers/staging/iio/meter/ade7754.c+0−664
@@ -1,664 +0,0 @@
1/*
2 * ADE7754 Polyphase Multifunction Energy Metering IC Driver
3 *
4 * Copyright 2010 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2 or later.
7 */
8
9#include <linux/delay.h>
10#include <linux/device.h>
11#include <linux/interrupt.h>
12#include <linux/irq.h>
13#include <linux/kernel.h>
14#include <linux/list.h>
15#include <linux/module.h>
16#include <linux/mutex.h>
17#include <linux/spi/spi.h>
18#include <linux/slab.h>
19#include <linux/sysfs.h>
20#include <linux/iio/iio.h>
21#include <linux/iio/sysfs.h>
22#include "meter.h"
23
24#define ADE7754_AENERGY 0x01
25#define ADE7754_RAENERGY 0x02
26#define ADE7754_LAENERGY 0x03
27#define ADE7754_VAENERGY 0x04
28#define ADE7754_RVAENERGY 0x05
29#define ADE7754_LVAENERGY 0x06
30#define ADE7754_PERIOD 0x07
31#define ADE7754_TEMP 0x08
32#define ADE7754_WFORM 0x09
33#define ADE7754_OPMODE 0x0A
34#define ADE7754_MMODE 0x0B
35#define ADE7754_WAVMODE 0x0C
36#define ADE7754_WATMODE 0x0D
37#define ADE7754_VAMODE 0x0E
38#define ADE7754_IRQEN 0x0F
39#define ADE7754_STATUS 0x10
40#define ADE7754_RSTATUS 0x11
41#define ADE7754_ZXTOUT 0x12
42#define ADE7754_LINCYC 0x13
43#define ADE7754_SAGCYC 0x14
44#define ADE7754_SAGLVL 0x15
45#define ADE7754_VPEAK 0x16
46#define ADE7754_IPEAK 0x17
47#define ADE7754_GAIN 0x18
48#define ADE7754_AWG 0x19
49#define ADE7754_BWG 0x1A
50#define ADE7754_CWG 0x1B
51#define ADE7754_AVAG 0x1C
52#define ADE7754_BVAG 0x1D
53#define ADE7754_CVAG 0x1E
54#define ADE7754_APHCAL 0x1F
55#define ADE7754_BPHCAL 0x20
56#define ADE7754_CPHCAL 0x21
57#define ADE7754_AAPOS 0x22
58#define ADE7754_BAPOS 0x23
59#define ADE7754_CAPOS 0x24
60#define ADE7754_CFNUM 0x25
61#define ADE7754_CFDEN 0x26
62#define ADE7754_WDIV 0x27
63#define ADE7754_VADIV 0x28
64#define ADE7754_AIRMS 0x29
65#define ADE7754_BIRMS 0x2A
66#define ADE7754_CIRMS 0x2B
67#define ADE7754_AVRMS 0x2C
68#define ADE7754_BVRMS 0x2D
69#define ADE7754_CVRMS 0x2E
70#define ADE7754_AIRMSOS 0x2F
71#define ADE7754_BIRMSOS 0x30
72#define ADE7754_CIRMSOS 0x31
73#define ADE7754_AVRMSOS 0x32
74#define ADE7754_BVRMSOS 0x33
75#define ADE7754_CVRMSOS 0x34
76#define ADE7754_AAPGAIN 0x35
77#define ADE7754_BAPGAIN 0x36
78#define ADE7754_CAPGAIN 0x37
79#define ADE7754_AVGAIN 0x38
80#define ADE7754_BVGAIN 0x39
81#define ADE7754_CVGAIN 0x3A
82#define ADE7754_CHKSUM 0x3E
83#define ADE7754_VERSION 0x3F
84
85#define ADE7754_READ_REG(a) a
86#define ADE7754_WRITE_REG(a) ((a) | 0x80)
87
88#define ADE7754_MAX_TX 4
89#define ADE7754_MAX_RX 4
90#define ADE7754_STARTUP_DELAY 1000
91
92#define ADE7754_SPI_SLOW (u32)(300 * 1000)
93#define ADE7754_SPI_BURST (u32)(1000 * 1000)
94#define ADE7754_SPI_FAST (u32)(2000 * 1000)
95
96/**
97 * struct ade7754_state - device instance specific data
98 * @us: actual spi_device
99 * @buf_lock: mutex to protect tx, rx and write frequency
100 * @tx: transmit buffer
101 * @rx: receive buffer
102 **/
103struct ade7754_state {
104 struct spi_device *us;
105 struct mutex buf_lock;
106 u8 tx[ADE7754_MAX_TX] ____cacheline_aligned;
107 u8 rx[ADE7754_MAX_RX];
108};
109
110/* Unlocked version of ade7754_spi_write_reg_8 function */
111static int __ade7754_spi_write_reg_8(struct device *dev, u8 reg_address, u8 val)
112{
113 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
114 struct ade7754_state *st = iio_priv(indio_dev);
115
116 st->tx[0] = ADE7754_WRITE_REG(reg_address);
117 st->tx[1] = val;
118 return spi_write(st->us, st->tx, 2);
119}
120
121static int ade7754_spi_write_reg_8(struct device *dev, u8 reg_address, u8 val)
122{
123 int ret;
124 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
125 struct ade7754_state *st = iio_priv(indio_dev);
126
127 mutex_lock(&st->buf_lock);
128 ret = __ade7754_spi_write_reg_8(dev, reg_address, val);
129 mutex_unlock(&st->buf_lock);
130
131 return ret;
132}
133
134static int ade7754_spi_write_reg_16(struct device *dev,
135 u8 reg_address, u16 val)
136{
137 int ret;
138 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
139 struct ade7754_state *st = iio_priv(indio_dev);
140
141 mutex_lock(&st->buf_lock);
142 st->tx[0] = ADE7754_WRITE_REG(reg_address);
143 st->tx[1] = (val >> 8) & 0xFF;
144 st->tx[2] = val & 0xFF;
145 ret = spi_write(st->us, st->tx, 3);
146 mutex_unlock(&st->buf_lock);
147
148 return ret;
149}
150
151static int ade7754_spi_read_reg_8(struct device *dev, u8 reg_address, u8 *val)
152{
153 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
154 struct ade7754_state *st = iio_priv(indio_dev);
155 int ret;
156
157 ret = spi_w8r8(st->us, ADE7754_READ_REG(reg_address));
158 if (ret < 0) {
159 dev_err(&st->us->dev, "problem when reading 8 bit register 0x%02X",
160 reg_address);
161 return ret;
162 }
163 *val = ret;
164
165 return 0;
166}
167
168static int ade7754_spi_read_reg_16(struct device *dev,
169 u8 reg_address, u16 *val)
170{
171 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
172 struct ade7754_state *st = iio_priv(indio_dev);
173 int ret;
174
175 ret = spi_w8r16be(st->us, ADE7754_READ_REG(reg_address));
176 if (ret < 0) {
177 dev_err(&st->us->dev, "problem when reading 16 bit register 0x%02X",
178 reg_address);
179 return ret;
180 }
181
182 *val = ret;
183
184 return 0;
185}
186
187static int ade7754_spi_read_reg_24(struct device *dev,
188 u8 reg_address, u32 *val)
189{
190 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
191 struct ade7754_state *st = iio_priv(indio_dev);
192 int ret;
193 struct spi_transfer xfers[] = {
194 {
195 .tx_buf = st->tx,
196 .rx_buf = st->rx,
197 .bits_per_word = 8,
198 .len = 4,
199 },
200 };
201
202 mutex_lock(&st->buf_lock);
203 st->tx[0] = ADE7754_READ_REG(reg_address);
204 st->tx[1] = 0;
205 st->tx[2] = 0;
206 st->tx[3] = 0;
207
208 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
209 if (ret) {
210 dev_err(&st->us->dev, "problem when reading 24 bit register 0x%02X",
211 reg_address);
212 goto error_ret;
213 }
214 *val = (st->rx[1] << 16) | (st->rx[2] << 8) | st->rx[3];
215
216error_ret:
217 mutex_unlock(&st->buf_lock);
218 return ret;
219}
220
221static ssize_t ade7754_read_8bit(struct device *dev,
222 struct device_attribute *attr,
223 char *buf)
224{
225 int ret;
226 u8 val = 0;
227 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
228
229 ret = ade7754_spi_read_reg_8(dev, this_attr->address, &val);
230 if (ret)
231 return ret;
232
233 return sprintf(buf, "%u\n", val);
234}
235
236static ssize_t ade7754_read_16bit(struct device *dev,
237 struct device_attribute *attr,
238 char *buf)
239{
240 int ret;
241 u16 val = 0;
242 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
243
244 ret = ade7754_spi_read_reg_16(dev, this_attr->address, &val);
245 if (ret)
246 return ret;
247
248 return sprintf(buf, "%u\n", val);
249}
250
251static ssize_t ade7754_read_24bit(struct device *dev,
252 struct device_attribute *attr,
253 char *buf)
254{
255 int ret;
256 u32 val = 0;
257 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
258
259 ret = ade7754_spi_read_reg_24(dev, this_attr->address, &val);
260 if (ret)
261 return ret;
262
263 return sprintf(buf, "%u\n", val & 0xFFFFFF);
264}
265
266static ssize_t ade7754_write_8bit(struct device *dev,
267 struct device_attribute *attr,
268 const char *buf,
269 size_t len)
270{
271 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
272 int ret;
273 u8 val;
274
275 ret = kstrtou8(buf, 10, &val);
276 if (ret)
277 goto error_ret;
278 ret = ade7754_spi_write_reg_8(dev, this_attr->address, val);
279
280error_ret:
281 return ret ? ret : len;
282}
283
284static ssize_t ade7754_write_16bit(struct device *dev,
285 struct device_attribute *attr,
286 const char *buf,
287 size_t len)
288{
289 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
290 int ret;
291 u16 val;
292
293 ret = kstrtou16(buf, 10, &val);
294 if (ret)
295 goto error_ret;
296 ret = ade7754_spi_write_reg_16(dev, this_attr->address, val);
297
298error_ret:
299 return ret ? ret : len;
300}
301
302static int ade7754_reset(struct device *dev)
303{
304 int ret;
305 u8 val;
306
307 ret = ade7754_spi_read_reg_8(dev, ADE7754_OPMODE, &val);
308 if (ret < 0)
309 return ret;
310
311 val |= BIT(6); /* Software Chip Reset */
312 return ade7754_spi_write_reg_8(dev, ADE7754_OPMODE, val);
313}
314
315static IIO_DEV_ATTR_AENERGY(ade7754_read_24bit, ADE7754_AENERGY);
316static IIO_DEV_ATTR_LAENERGY(ade7754_read_24bit, ADE7754_LAENERGY);
317static IIO_DEV_ATTR_VAENERGY(ade7754_read_24bit, ADE7754_VAENERGY);
318static IIO_DEV_ATTR_LVAENERGY(ade7754_read_24bit, ADE7754_LVAENERGY);
319static IIO_DEV_ATTR_VPEAK(0644,
320 ade7754_read_8bit,
321 ade7754_write_8bit,
322 ADE7754_VPEAK);
323static IIO_DEV_ATTR_IPEAK(0644,
324 ade7754_read_8bit,
325 ade7754_write_8bit,
326 ADE7754_VPEAK);
327static IIO_DEV_ATTR_APHCAL(0644,
328 ade7754_read_8bit,
329 ade7754_write_8bit,
330 ADE7754_APHCAL);
331static IIO_DEV_ATTR_BPHCAL(0644,
332 ade7754_read_8bit,
333 ade7754_write_8bit,
334 ADE7754_BPHCAL);
335static IIO_DEV_ATTR_CPHCAL(0644,
336 ade7754_read_8bit,
337 ade7754_write_8bit,
338 ADE7754_CPHCAL);
339static IIO_DEV_ATTR_AAPOS(0644,
340 ade7754_read_16bit,
341 ade7754_write_16bit,
342 ADE7754_AAPOS);
343static IIO_DEV_ATTR_BAPOS(0644,
344 ade7754_read_16bit,
345 ade7754_write_16bit,
346 ADE7754_BAPOS);
347static IIO_DEV_ATTR_CAPOS(0644,
348 ade7754_read_16bit,
349 ade7754_write_16bit,
350 ADE7754_CAPOS);
351static IIO_DEV_ATTR_WDIV(0644,
352 ade7754_read_8bit,
353 ade7754_write_8bit,
354 ADE7754_WDIV);
355static IIO_DEV_ATTR_VADIV(0644,
356 ade7754_read_8bit,
357 ade7754_write_8bit,
358 ADE7754_VADIV);
359static IIO_DEV_ATTR_CFNUM(0644,
360 ade7754_read_16bit,
361 ade7754_write_16bit,
362 ADE7754_CFNUM);
363static IIO_DEV_ATTR_CFDEN(0644,
364 ade7754_read_16bit,
365 ade7754_write_16bit,
366 ADE7754_CFDEN);
367static IIO_DEV_ATTR_ACTIVE_POWER_A_GAIN(0644,
368 ade7754_read_16bit,
369 ade7754_write_16bit,
370 ADE7754_AAPGAIN);
371static IIO_DEV_ATTR_ACTIVE_POWER_B_GAIN(0644,
372 ade7754_read_16bit,
373 ade7754_write_16bit,
374 ADE7754_BAPGAIN);
375static IIO_DEV_ATTR_ACTIVE_POWER_C_GAIN(0644,
376 ade7754_read_16bit,
377 ade7754_write_16bit,
378 ADE7754_CAPGAIN);
379static IIO_DEV_ATTR_AIRMS(0444,
380 ade7754_read_24bit,
381 NULL,
382 ADE7754_AIRMS);
383static IIO_DEV_ATTR_BIRMS(0444,
384 ade7754_read_24bit,
385 NULL,
386 ADE7754_BIRMS);
387static IIO_DEV_ATTR_CIRMS(0444,
388 ade7754_read_24bit,
389 NULL,
390 ADE7754_CIRMS);
391static IIO_DEV_ATTR_AVRMS(0444,
392 ade7754_read_24bit,
393 NULL,
394 ADE7754_AVRMS);
395static IIO_DEV_ATTR_BVRMS(0444,
396 ade7754_read_24bit,
397 NULL,
398 ADE7754_BVRMS);
399static IIO_DEV_ATTR_CVRMS(0444,
400 ade7754_read_24bit,
401 NULL,
402 ADE7754_CVRMS);
403static IIO_DEV_ATTR_AIRMSOS(0444,
404 ade7754_read_16bit,
405 ade7754_write_16bit,
406 ADE7754_AIRMSOS);
407static IIO_DEV_ATTR_BIRMSOS(0444,
408 ade7754_read_16bit,
409 ade7754_write_16bit,
410 ADE7754_BIRMSOS);
411static IIO_DEV_ATTR_CIRMSOS(0444,
412 ade7754_read_16bit,
413 ade7754_write_16bit,
414 ADE7754_CIRMSOS);
415static IIO_DEV_ATTR_AVRMSOS(0444,
416 ade7754_read_16bit,
417 ade7754_write_16bit,
418 ADE7754_AVRMSOS);
419static IIO_DEV_ATTR_BVRMSOS(0444,
420 ade7754_read_16bit,
421 ade7754_write_16bit,
422 ADE7754_BVRMSOS);
423static IIO_DEV_ATTR_CVRMSOS(0444,
424 ade7754_read_16bit,
425 ade7754_write_16bit,
426 ADE7754_CVRMSOS);
427
428static int ade7754_set_irq(struct device *dev, bool enable)
429{
430 int ret;
431 u16 irqen;
432
433 ret = ade7754_spi_read_reg_16(dev, ADE7754_IRQEN, &irqen);
434 if (ret)
435 return ret;
436
437 if (enable)
438 irqen |= BIT(14); /* Enables an interrupt when a data is
439 * present in the waveform register
440 */
441 else
442 irqen &= ~BIT(14);
443
444 return ade7754_spi_write_reg_16(dev, ADE7754_IRQEN, irqen);
445}
446
447/* Power down the device */
448static int ade7754_stop_device(struct device *dev)
449{
450 int ret;
451 u8 val;
452
453 ret = ade7754_spi_read_reg_8(dev, ADE7754_OPMODE, &val);
454 if (ret < 0) {
455 dev_err(dev, "unable to power down the device, error: %d",
456 ret);
457 return ret;
458 }
459
460 val |= 7 << 3; /* ADE7754 powered down */
461 return ade7754_spi_write_reg_8(dev, ADE7754_OPMODE, val);
462}
463
464static int ade7754_initial_setup(struct iio_dev *indio_dev)
465{
466 int ret;
467 struct ade7754_state *st = iio_priv(indio_dev);
468 struct device *dev = &indio_dev->dev;
469
470 /* use low spi speed for init */
471 st->us->mode = SPI_MODE_3;
472 spi_setup(st->us);
473
474 /* Disable IRQ */
475 ret = ade7754_set_irq(dev, false);
476 if (ret) {
477 dev_err(dev, "disable irq failed");
478 goto err_ret;
479 }
480
481 ade7754_reset(dev);
482 usleep_range(ADE7754_STARTUP_DELAY, ADE7754_STARTUP_DELAY + 100);
483
484err_ret:
485 return ret;
486}
487
488static ssize_t ade7754_read_frequency(struct device *dev,
489 struct device_attribute *attr,
490 char *buf)
491{
492 int ret;
493 u8 t;
494 int sps;
495
496 ret = ade7754_spi_read_reg_8(dev, ADE7754_WAVMODE, &t);
497 if (ret)
498 return ret;
499
500 t = (t >> 3) & 0x3;
501 sps = 26000 / (1 + t);
502
503 return sprintf(buf, "%d\n", sps);
504}
505
506static ssize_t ade7754_write_frequency(struct device *dev,
507 struct device_attribute *attr,
508 const char *buf,
509 size_t len)
510{
511 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
512 struct ade7754_state *st = iio_priv(indio_dev);
513 u16 val;
514 int ret;
515 u8 reg, t;
516
517 ret = kstrtou16(buf, 10, &val);
518 if (ret)
519 return ret;
520 if (!val)
521 return -EINVAL;
522
523 mutex_lock(&st->buf_lock);
524
525 t = 26000 / val;
526 if (t > 0)
527 t--;
528
529 if (t > 1)
530 st->us->max_speed_hz = ADE7754_SPI_SLOW;
531 else
532 st->us->max_speed_hz = ADE7754_SPI_FAST;
533
534 ret = ade7754_spi_read_reg_8(dev, ADE7754_WAVMODE, &reg);
535 if (ret)
536 goto out;
537
538 reg &= ~(3 << 3);
539 reg |= t << 3;
540
541 ret = __ade7754_spi_write_reg_8(dev, ADE7754_WAVMODE, reg);
542
543out:
544 mutex_unlock(&st->buf_lock);
545
546 return ret ? ret : len;
547}
548static IIO_DEV_ATTR_TEMP_RAW(ade7754_read_8bit);
549static IIO_CONST_ATTR(in_temp_offset, "129 C");
550static IIO_CONST_ATTR(in_temp_scale, "4 C");
551
552static IIO_DEV_ATTR_SAMP_FREQ(0644,
553 ade7754_read_frequency,
554 ade7754_write_frequency);
555
556static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("26000 13000 65000 33000");
557
558static struct attribute *ade7754_attributes[] = {
559 &iio_dev_attr_in_temp_raw.dev_attr.attr,
560 &iio_const_attr_in_temp_offset.dev_attr.attr,
561 &iio_const_attr_in_temp_scale.dev_attr.attr,
562 &iio_dev_attr_sampling_frequency.dev_attr.attr,
563 &iio_const_attr_sampling_frequency_available.dev_attr.attr,
564 &iio_dev_attr_aenergy.dev_attr.attr,
565 &iio_dev_attr_laenergy.dev_attr.attr,
566 &iio_dev_attr_vaenergy.dev_attr.attr,
567 &iio_dev_attr_lvaenergy.dev_attr.attr,
568 &iio_dev_attr_vpeak.dev_attr.attr,
569 &iio_dev_attr_ipeak.dev_attr.attr,
570 &iio_dev_attr_aphcal.dev_attr.attr,
571 &iio_dev_attr_bphcal.dev_attr.attr,
572 &iio_dev_attr_cphcal.dev_attr.attr,
573 &iio_dev_attr_aapos.dev_attr.attr,
574 &iio_dev_attr_bapos.dev_attr.attr,
575 &iio_dev_attr_capos.dev_attr.attr,
576 &iio_dev_attr_wdiv.dev_attr.attr,
577 &iio_dev_attr_vadiv.dev_attr.attr,
578 &iio_dev_attr_cfnum.dev_attr.attr,
579 &iio_dev_attr_cfden.dev_attr.attr,
580 &iio_dev_attr_active_power_a_gain.dev_attr.attr,
581 &iio_dev_attr_active_power_b_gain.dev_attr.attr,
582 &iio_dev_attr_active_power_c_gain.dev_attr.attr,
583 &iio_dev_attr_airms.dev_attr.attr,
584 &iio_dev_attr_birms.dev_attr.attr,
585 &iio_dev_attr_cirms.dev_attr.attr,
586 &iio_dev_attr_avrms.dev_attr.attr,
587 &iio_dev_attr_bvrms.dev_attr.attr,
588 &iio_dev_attr_cvrms.dev_attr.attr,
589 &iio_dev_attr_airmsos.dev_attr.attr,
590 &iio_dev_attr_birmsos.dev_attr.attr,
591 &iio_dev_attr_cirmsos.dev_attr.attr,
592 &iio_dev_attr_avrmsos.dev_attr.attr,
593 &iio_dev_attr_bvrmsos.dev_attr.attr,
594 &iio_dev_attr_cvrmsos.dev_attr.attr,
595 NULL,
596};
597
598static const struct attribute_group ade7754_attribute_group = {
599 .attrs = ade7754_attributes,
600};
601
602static const struct iio_info ade7754_info = {
603 .attrs = &ade7754_attribute_group,
604};
605
606static int ade7754_probe(struct spi_device *spi)
607{
608 int ret;
609 struct ade7754_state *st;
610 struct iio_dev *indio_dev;
611
612 /* setup the industrialio driver allocated elements */
613 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
614 if (!indio_dev)
615 return -ENOMEM;
616 /* this is only used for removal purposes */
617 spi_set_drvdata(spi, indio_dev);
618
619 st = iio_priv(indio_dev);
620 st->us = spi;
621 mutex_init(&st->buf_lock);
622
623 indio_dev->name = spi->dev.driver->name;
624 indio_dev->dev.parent = &spi->dev;
625 indio_dev->info = &ade7754_info;
626 indio_dev->modes = INDIO_DIRECT_MODE;
627
628 /* Get the device into a sane initial state */
629 ret = ade7754_initial_setup(indio_dev);
630 if (ret)
631 goto powerdown_on_error;
632 ret = iio_device_register(indio_dev);
633 if (ret)
634 goto powerdown_on_error;
635 return ret;
636
637powerdown_on_error:
638 ade7754_stop_device(&indio_dev->dev);
639 return ret;
640}
641
642static int ade7754_remove(struct spi_device *spi)
643{
644 struct iio_dev *indio_dev = spi_get_drvdata(spi);
645
646 iio_device_unregister(indio_dev);
647 ade7754_stop_device(&indio_dev->dev);
648
649 return 0;
650}
651
652static struct spi_driver ade7754_driver = {
653 .driver = {
654 .name = "ade7754",
655 },
656 .probe = ade7754_probe,
657 .remove = ade7754_remove,
658};
659module_spi_driver(ade7754_driver);
660
661MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
662MODULE_DESCRIPTION("Analog Devices ADE7754 Polyphase Multifunction Energy Metering IC Driver");
663MODULE_LICENSE("GPL v2");
664MODULE_ALIAS("spi:ad7754");
drivers/staging/iio/meter/ade7758.h+0−183
@@ -1,183 +0,0 @@
1/*
2 * ADE7758 Poly Phase Multifunction Energy Metering IC driver
3 *
4 * Copyright 2010-2011 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2.
7 */
8
9#ifndef _ADE7758_H
10#define _ADE7758_H
11
12#define ADE7758_AWATTHR 0x01
13#define ADE7758_BWATTHR 0x02
14#define ADE7758_CWATTHR 0x03
15#define ADE7758_AVARHR 0x04
16#define ADE7758_BVARHR 0x05
17#define ADE7758_CVARHR 0x06
18#define ADE7758_AVAHR 0x07
19#define ADE7758_BVAHR 0x08
20#define ADE7758_CVAHR 0x09
21#define ADE7758_AIRMS 0x0A
22#define ADE7758_BIRMS 0x0B
23#define ADE7758_CIRMS 0x0C
24#define ADE7758_AVRMS 0x0D
25#define ADE7758_BVRMS 0x0E
26#define ADE7758_CVRMS 0x0F
27#define ADE7758_FREQ 0x10
28#define ADE7758_TEMP 0x11
29#define ADE7758_WFORM 0x12
30#define ADE7758_OPMODE 0x13
31#define ADE7758_MMODE 0x14
32#define ADE7758_WAVMODE 0x15
33#define ADE7758_COMPMODE 0x16
34#define ADE7758_LCYCMODE 0x17
35#define ADE7758_MASK 0x18
36#define ADE7758_STATUS 0x19
37#define ADE7758_RSTATUS 0x1A
38#define ADE7758_ZXTOUT 0x1B
39#define ADE7758_LINECYC 0x1C
40#define ADE7758_SAGCYC 0x1D
41#define ADE7758_SAGLVL 0x1E
42#define ADE7758_VPINTLVL 0x1F
43#define ADE7758_IPINTLVL 0x20
44#define ADE7758_VPEAK 0x21
45#define ADE7758_IPEAK 0x22
46#define ADE7758_GAIN 0x23
47#define ADE7758_AVRMSGAIN 0x24
48#define ADE7758_BVRMSGAIN 0x25
49#define ADE7758_CVRMSGAIN 0x26
50#define ADE7758_AIGAIN 0x27
51#define ADE7758_BIGAIN 0x28
52#define ADE7758_CIGAIN 0x29
53#define ADE7758_AWG 0x2A
54#define ADE7758_BWG 0x2B
55#define ADE7758_CWG 0x2C
56#define ADE7758_AVARG 0x2D
57#define ADE7758_BVARG 0x2E
58#define ADE7758_CVARG 0x2F
59#define ADE7758_AVAG 0x30
60#define ADE7758_BVAG 0x31
61#define ADE7758_CVAG 0x32
62#define ADE7758_AVRMSOS 0x33
63#define ADE7758_BVRMSOS 0x34
64#define ADE7758_CVRMSOS 0x35
65#define ADE7758_AIRMSOS 0x36
66#define ADE7758_BIRMSOS 0x37
67#define ADE7758_CIRMSOS 0x38
68#define ADE7758_AWAITOS 0x39
69#define ADE7758_BWAITOS 0x3A
70#define ADE7758_CWAITOS 0x3B
71#define ADE7758_AVAROS 0x3C
72#define ADE7758_BVAROS 0x3D
73#define ADE7758_CVAROS 0x3E
74#define ADE7758_APHCAL 0x3F
75#define ADE7758_BPHCAL 0x40
76#define ADE7758_CPHCAL 0x41
77#define ADE7758_WDIV 0x42
78#define ADE7758_VADIV 0x44
79#define ADE7758_VARDIV 0x43
80#define ADE7758_APCFNUM 0x45
81#define ADE7758_APCFDEN 0x46
82#define ADE7758_VARCFNUM 0x47
83#define ADE7758_VARCFDEN 0x48
84#define ADE7758_CHKSUM 0x7E
85#define ADE7758_VERSION 0x7F
86
87#define ADE7758_READ_REG(a) a
88#define ADE7758_WRITE_REG(a) ((a) | 0x80)
89
90#define ADE7758_MAX_TX 8
91#define ADE7758_MAX_RX 4
92#define ADE7758_STARTUP_DELAY 1000
93
94#define AD7758_NUM_WAVSEL 5
95#define AD7758_NUM_PHSEL 3
96#define AD7758_NUM_WAVESRC (AD7758_NUM_WAVSEL * AD7758_NUM_PHSEL)
97
98#define AD7758_PHASE_A 0
99#define AD7758_PHASE_B 1
100#define AD7758_PHASE_C 2
101#define AD7758_CURRENT 0
102#define AD7758_VOLTAGE 1
103#define AD7758_ACT_PWR 2
104#define AD7758_REACT_PWR 3
105#define AD7758_APP_PWR 4
106#define AD7758_WT(p, w) (((w) << 2) | (p))
107
108/**
109 * struct ade7758_state - device instance specific data
110 * @us: actual spi_device
111 * @trig: data ready trigger registered with iio
112 * @tx: transmit buffer
113 * @rx: receive buffer
114 * @buf_lock: mutex to protect tx, rx, read and write frequency
115 **/
116struct ade7758_state {
117 struct spi_device *us;
118 struct iio_trigger *trig;
119 u8 *tx;
120 u8 *rx;
121 struct mutex buf_lock;
122 struct spi_transfer ring_xfer[4];
123 struct spi_message ring_msg;
124 /*
125 * DMA (thus cache coherency maintenance) requires the
126 * transfer buffers to live in their own cache lines.
127 */
128 unsigned char rx_buf[8] ____cacheline_aligned;
129 unsigned char tx_buf[8];
130
131};
132
133#ifdef CONFIG_IIO_BUFFER
134/* At the moment triggers are only used for ring buffer
135 * filling. This may change!
136 */
137
138void ade7758_remove_trigger(struct iio_dev *indio_dev);
139int ade7758_probe_trigger(struct iio_dev *indio_dev);
140
141ssize_t ade7758_read_data_from_ring(struct device *dev,
142 struct device_attribute *attr, char *buf);
143
144int ade7758_configure_ring(struct iio_dev *indio_dev);
145void ade7758_unconfigure_ring(struct iio_dev *indio_dev);
146
147int ade7758_set_irq(struct device *dev, bool enable);
148
149int ade7758_spi_write_reg_8(struct device *dev, u8 reg_address, u8 val);
150int ade7758_spi_read_reg_8(struct device *dev, u8 reg_address, u8 *val);
151
152#else /* CONFIG_IIO_BUFFER */
153
154static inline void ade7758_remove_trigger(struct iio_dev *indio_dev)
155{
156}
157
158static inline int ade7758_probe_trigger(struct iio_dev *indio_dev)
159{
160 return 0;
161}
162
163static int ade7758_configure_ring(struct iio_dev *indio_dev)
164{
165 return 0;
166}
167
168static inline void ade7758_unconfigure_ring(struct iio_dev *indio_dev)
169{
170}
171
172static inline int ade7758_initialize_ring(struct iio_ring_buffer *ring)
173{
174 return 0;
175}
176
177static inline void ade7758_uninitialize_ring(struct iio_dev *indio_dev)
178{
179}
180
181#endif /* CONFIG_IIO_BUFFER */
182
183#endif
drivers/staging/iio/meter/ade7758_core.c+0−955
@@ -1,955 +0,0 @@
1/*
2 * ADE7758 Poly Phase Multifunction Energy Metering IC driver
3 *
4 * Copyright 2010-2011 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2.
7 */
8
9#include <linux/interrupt.h>
10#include <linux/irq.h>
11#include <linux/delay.h>
12#include <linux/mutex.h>
13#include <linux/device.h>
14#include <linux/kernel.h>
15#include <linux/spi/spi.h>
16#include <linux/slab.h>
17#include <linux/sysfs.h>
18#include <linux/list.h>
19#include <linux/module.h>
20
21#include <linux/iio/iio.h>
22#include <linux/iio/sysfs.h>
23#include <linux/iio/buffer.h>
24#include "meter.h"
25#include "ade7758.h"
26
27static int __ade7758_spi_write_reg_8(struct device *dev, u8 reg_address, u8 val)
28{
29 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
30 struct ade7758_state *st = iio_priv(indio_dev);
31
32 st->tx[0] = ADE7758_WRITE_REG(reg_address);
33 st->tx[1] = val;
34
35 return spi_write(st->us, st->tx, 2);
36}
37
38int ade7758_spi_write_reg_8(struct device *dev, u8 reg_address, u8 val)
39{
40 int ret;
41 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
42 struct ade7758_state *st = iio_priv(indio_dev);
43
44 mutex_lock(&st->buf_lock);
45 ret = __ade7758_spi_write_reg_8(dev, reg_address, val);
46 mutex_unlock(&st->buf_lock);
47
48 return ret;
49}
50
51static int ade7758_spi_write_reg_16(struct device *dev, u8 reg_address,
52 u16 value)
53{
54 int ret;
55 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
56 struct ade7758_state *st = iio_priv(indio_dev);
57 struct spi_transfer xfers[] = {
58 {
59 .tx_buf = st->tx,
60 .bits_per_word = 8,
61 .len = 3,
62 }
63 };
64
65 mutex_lock(&st->buf_lock);
66 st->tx[0] = ADE7758_WRITE_REG(reg_address);
67 st->tx[1] = (value >> 8) & 0xFF;
68 st->tx[2] = value & 0xFF;
69
70 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
71 mutex_unlock(&st->buf_lock);
72
73 return ret;
74}
75
76static int ade7758_spi_write_reg_24(struct device *dev, u8 reg_address,
77 u32 value)
78{
79 int ret;
80 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
81 struct ade7758_state *st = iio_priv(indio_dev);
82 struct spi_transfer xfers[] = {
83 {
84 .tx_buf = st->tx,
85 .bits_per_word = 8,
86 .len = 4,
87 }
88 };
89
90 mutex_lock(&st->buf_lock);
91 st->tx[0] = ADE7758_WRITE_REG(reg_address);
92 st->tx[1] = (value >> 16) & 0xFF;
93 st->tx[2] = (value >> 8) & 0xFF;
94 st->tx[3] = value & 0xFF;
95
96 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
97 mutex_unlock(&st->buf_lock);
98
99 return ret;
100}
101
102static int __ade7758_spi_read_reg_8(struct device *dev, u8 reg_address, u8 *val)
103{
104 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
105 struct ade7758_state *st = iio_priv(indio_dev);
106 int ret;
107 struct spi_transfer xfers[] = {
108 {
109 .tx_buf = st->tx,
110 .bits_per_word = 8,
111 .len = 1,
112 .delay_usecs = 4,
113 },
114 {
115 .tx_buf = &st->tx[1],
116 .rx_buf = st->rx,
117 .bits_per_word = 8,
118 .len = 1,
119 },
120 };
121
122 st->tx[0] = ADE7758_READ_REG(reg_address);
123 st->tx[1] = 0;
124
125 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
126 if (ret) {
127 dev_err(&st->us->dev, "problem when reading 8 bit register 0x%02X",
128 reg_address);
129 goto error_ret;
130 }
131 *val = st->rx[0];
132
133error_ret:
134 return ret;
135}
136
137int ade7758_spi_read_reg_8(struct device *dev, u8 reg_address, u8 *val)
138{
139 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
140 struct ade7758_state *st = iio_priv(indio_dev);
141 int ret;
142
143 mutex_lock(&st->buf_lock);
144 ret = __ade7758_spi_read_reg_8(dev, reg_address, val);
145 mutex_unlock(&st->buf_lock);
146
147 return ret;
148}
149
150static int ade7758_spi_read_reg_16(struct device *dev, u8 reg_address,
151 u16 *val)
152{
153 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
154 struct ade7758_state *st = iio_priv(indio_dev);
155 int ret;
156 struct spi_transfer xfers[] = {
157 {
158 .tx_buf = st->tx,
159 .bits_per_word = 8,
160 .len = 1,
161 .delay_usecs = 4,
162 },
163 {
164 .tx_buf = &st->tx[1],
165 .rx_buf = st->rx,
166 .bits_per_word = 8,
167 .len = 2,
168 },
169 };
170
171 mutex_lock(&st->buf_lock);
172 st->tx[0] = ADE7758_READ_REG(reg_address);
173 st->tx[1] = 0;
174 st->tx[2] = 0;
175
176 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
177 if (ret) {
178 dev_err(&st->us->dev, "problem when reading 16 bit register 0x%02X",
179 reg_address);
180 goto error_ret;
181 }
182
183 *val = (st->rx[0] << 8) | st->rx[1];
184
185error_ret:
186 mutex_unlock(&st->buf_lock);
187 return ret;
188}
189
190static int ade7758_spi_read_reg_24(struct device *dev, u8 reg_address,
191 u32 *val)
192{
193 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
194 struct ade7758_state *st = iio_priv(indio_dev);
195 int ret;
196 struct spi_transfer xfers[] = {
197 {
198 .tx_buf = st->tx,
199 .bits_per_word = 8,
200 .len = 1,
201 .delay_usecs = 4,
202 },
203 {
204 .tx_buf = &st->tx[1],
205 .rx_buf = st->rx,
206 .bits_per_word = 8,
207 .len = 3,
208 },
209 };
210
211 mutex_lock(&st->buf_lock);
212 st->tx[0] = ADE7758_READ_REG(reg_address);
213 st->tx[1] = 0;
214 st->tx[2] = 0;
215 st->tx[3] = 0;
216
217 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
218 if (ret) {
219 dev_err(&st->us->dev, "problem when reading 24 bit register 0x%02X",
220 reg_address);
221 goto error_ret;
222 }
223 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
224
225error_ret:
226 mutex_unlock(&st->buf_lock);
227 return ret;
228}
229
230static ssize_t ade7758_read_8bit(struct device *dev,
231 struct device_attribute *attr, char *buf)
232{
233 int ret;
234 u8 val = 0;
235 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
236
237 ret = ade7758_spi_read_reg_8(dev, this_attr->address, &val);
238 if (ret)
239 return ret;
240
241 return sprintf(buf, "%u\n", val);
242}
243
244static ssize_t ade7758_read_16bit(struct device *dev,
245 struct device_attribute *attr, char *buf)
246{
247 int ret;
248 u16 val = 0;
249 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
250
251 ret = ade7758_spi_read_reg_16(dev, this_attr->address, &val);
252 if (ret)
253 return ret;
254
255 return sprintf(buf, "%u\n", val);
256}
257
258static ssize_t ade7758_read_24bit(struct device *dev,
259 struct device_attribute *attr, char *buf)
260{
261 int ret;
262 u32 val = 0;
263 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
264
265 ret = ade7758_spi_read_reg_24(dev, this_attr->address, &val);
266 if (ret)
267 return ret;
268
269 return sprintf(buf, "%u\n", val & 0xFFFFFF);
270}
271
272static ssize_t ade7758_write_8bit(struct device *dev,
273 struct device_attribute *attr,
274 const char *buf, size_t len)
275{
276 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
277 int ret;
278 u8 val;
279
280 ret = kstrtou8(buf, 10, &val);
281 if (ret)
282 goto error_ret;
283 ret = ade7758_spi_write_reg_8(dev, this_attr->address, val);
284
285error_ret:
286 return ret ? ret : len;
287}
288
289static ssize_t ade7758_write_16bit(struct device *dev,
290 struct device_attribute *attr,
291 const char *buf, size_t len)
292{
293 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
294 int ret;
295 u16 val;
296
297 ret = kstrtou16(buf, 10, &val);
298 if (ret)
299 goto error_ret;
300 ret = ade7758_spi_write_reg_16(dev, this_attr->address, val);
301
302error_ret:
303 return ret ? ret : len;
304}
305
306static int ade7758_reset(struct device *dev)
307{
308 int ret;
309 u8 val;
310
311 ret = ade7758_spi_read_reg_8(dev, ADE7758_OPMODE, &val);
312 if (ret < 0) {
313 dev_err(dev, "Failed to read opmode reg\n");
314 return ret;
315 }
316 val |= BIT(6); /* Software Chip Reset */
317 ret = ade7758_spi_write_reg_8(dev, ADE7758_OPMODE, val);
318 if (ret < 0)
319 dev_err(dev, "Failed to write opmode reg\n");
320 return ret;
321}
322
323static IIO_DEV_ATTR_VPEAK(0644,
324 ade7758_read_8bit,
325 ade7758_write_8bit,
326 ADE7758_VPEAK);
327static IIO_DEV_ATTR_IPEAK(0644,
328 ade7758_read_8bit,
329 ade7758_write_8bit,
330 ADE7758_VPEAK);
331static IIO_DEV_ATTR_APHCAL(0644,
332 ade7758_read_8bit,
333 ade7758_write_8bit,
334 ADE7758_APHCAL);
335static IIO_DEV_ATTR_BPHCAL(0644,
336 ade7758_read_8bit,
337 ade7758_write_8bit,
338 ADE7758_BPHCAL);
339static IIO_DEV_ATTR_CPHCAL(0644,
340 ade7758_read_8bit,
341 ade7758_write_8bit,
342 ADE7758_CPHCAL);
343static IIO_DEV_ATTR_WDIV(0644,
344 ade7758_read_8bit,
345 ade7758_write_8bit,
346 ADE7758_WDIV);
347static IIO_DEV_ATTR_VADIV(0644,
348 ade7758_read_8bit,
349 ade7758_write_8bit,
350 ADE7758_VADIV);
351static IIO_DEV_ATTR_AIRMS(0444,
352 ade7758_read_24bit,
353 NULL,
354 ADE7758_AIRMS);
355static IIO_DEV_ATTR_BIRMS(0444,
356 ade7758_read_24bit,
357 NULL,
358 ADE7758_BIRMS);
359static IIO_DEV_ATTR_CIRMS(0444,
360 ade7758_read_24bit,
361 NULL,
362 ADE7758_CIRMS);
363static IIO_DEV_ATTR_AVRMS(0444,
364 ade7758_read_24bit,
365 NULL,
366 ADE7758_AVRMS);
367static IIO_DEV_ATTR_BVRMS(0444,
368 ade7758_read_24bit,
369 NULL,
370 ADE7758_BVRMS);
371static IIO_DEV_ATTR_CVRMS(0444,
372 ade7758_read_24bit,
373 NULL,
374 ADE7758_CVRMS);
375static IIO_DEV_ATTR_AIRMSOS(0644,
376 ade7758_read_16bit,
377 ade7758_write_16bit,
378 ADE7758_AIRMSOS);
379static IIO_DEV_ATTR_BIRMSOS(0644,
380 ade7758_read_16bit,
381 ade7758_write_16bit,
382 ADE7758_BIRMSOS);
383static IIO_DEV_ATTR_CIRMSOS(0644,
384 ade7758_read_16bit,
385 ade7758_write_16bit,
386 ADE7758_CIRMSOS);
387static IIO_DEV_ATTR_AVRMSOS(0644,
388 ade7758_read_16bit,
389 ade7758_write_16bit,
390 ADE7758_AVRMSOS);
391static IIO_DEV_ATTR_BVRMSOS(0644,
392 ade7758_read_16bit,
393 ade7758_write_16bit,
394 ADE7758_BVRMSOS);
395static IIO_DEV_ATTR_CVRMSOS(0644,
396 ade7758_read_16bit,
397 ade7758_write_16bit,
398 ADE7758_CVRMSOS);
399static IIO_DEV_ATTR_AIGAIN(0644,
400 ade7758_read_16bit,
401 ade7758_write_16bit,
402 ADE7758_AIGAIN);
403static IIO_DEV_ATTR_BIGAIN(0644,
404 ade7758_read_16bit,
405 ade7758_write_16bit,
406 ADE7758_BIGAIN);
407static IIO_DEV_ATTR_CIGAIN(0644,
408 ade7758_read_16bit,
409 ade7758_write_16bit,
410 ADE7758_CIGAIN);
411static IIO_DEV_ATTR_AVRMSGAIN(0644,
412 ade7758_read_16bit,
413 ade7758_write_16bit,
414 ADE7758_AVRMSGAIN);
415static IIO_DEV_ATTR_BVRMSGAIN(0644,
416 ade7758_read_16bit,
417 ade7758_write_16bit,
418 ADE7758_BVRMSGAIN);
419static IIO_DEV_ATTR_CVRMSGAIN(0644,
420 ade7758_read_16bit,
421 ade7758_write_16bit,
422 ADE7758_CVRMSGAIN);
423
424int ade7758_set_irq(struct device *dev, bool enable)
425{
426 int ret;
427 u32 irqen;
428
429 ret = ade7758_spi_read_reg_24(dev, ADE7758_MASK, &irqen);
430 if (ret)
431 return ret;
432
433 if (enable)
434 irqen |= BIT(16); /* Enables an interrupt when a data is
435 * present in the waveform register
436 */
437 else
438 irqen &= ~BIT(16);
439
440 ret = ade7758_spi_write_reg_24(dev, ADE7758_MASK, irqen);
441
442 return ret;
443}
444
445/* Power down the device */
446static int ade7758_stop_device(struct device *dev)
447{
448 int ret;
449 u8 val;
450
451 ret = ade7758_spi_read_reg_8(dev, ADE7758_OPMODE, &val);
452 if (ret < 0) {
453 dev_err(dev, "Failed to read opmode reg\n");
454 return ret;
455 }
456 val |= 7 << 3; /* ADE7758 powered down */
457 ret = ade7758_spi_write_reg_8(dev, ADE7758_OPMODE, val);
458 if (ret < 0)
459 dev_err(dev, "Failed to write opmode reg\n");
460 return ret;
461}
462
463static int ade7758_initial_setup(struct iio_dev *indio_dev)
464{
465 struct ade7758_state *st = iio_priv(indio_dev);
466 struct device *dev = &indio_dev->dev;
467 int ret;
468
469 /* use low spi speed for init */
470 st->us->mode = SPI_MODE_1;
471 spi_setup(st->us);
472
473 /* Disable IRQ */
474 ret = ade7758_set_irq(dev, false);
475 if (ret) {
476 dev_err(dev, "disable irq failed");
477 goto err_ret;
478 }
479
480 ade7758_reset(dev);
481 usleep_range(ADE7758_STARTUP_DELAY, ADE7758_STARTUP_DELAY + 100);
482
483err_ret:
484 return ret;
485}
486
487static int ade7758_read_samp_freq(struct device *dev, int *val)
488{
489 int ret;
490 u8 t;
491
492 ret = ade7758_spi_read_reg_8(dev, ADE7758_WAVMODE, &t);
493 if (ret)
494 return ret;
495
496 t = (t >> 5) & 0x3;
497 *val = 26040 / (1 << t);
498
499 return 0;
500}
501
502static int ade7758_write_samp_freq(struct device *dev, int val)
503{
504 int ret;
505 u8 reg, t;
506 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
507 struct ade7758_state *st = iio_priv(indio_dev);
508
509 switch (val) {
510 case 26040:
511 t = 0;
512 break;
513 case 13020:
514 t = 1;
515 break;
516 case 6510:
517 t = 2;
518 break;
519 case 3255:
520 t = 3;
521 break;
522 default:
523 return -EINVAL;
524 }
525
526 mutex_lock(&st->buf_lock);
527
528 ret = __ade7758_spi_read_reg_8(dev, ADE7758_WAVMODE, &reg);
529 if (ret)
530 goto out;
531
532 reg &= ~(5 << 3);
533 reg |= t << 5;
534
535 ret = __ade7758_spi_write_reg_8(dev, ADE7758_WAVMODE, reg);
536
537out:
538 mutex_unlock(&st->buf_lock);
539
540 return ret;
541}
542
543static int ade7758_read_raw(struct iio_dev *indio_dev,
544 struct iio_chan_spec const *chan,
545 int *val,
546 int *val2,
547 long mask)
548{
549 int ret;
550
551 switch (mask) {
552 case IIO_CHAN_INFO_SAMP_FREQ:
553
554 ret = ade7758_read_samp_freq(&indio_dev->dev, val);
555
556 return ret;
557 default:
558 return -EINVAL;
559 }
560
561 return ret;
562}
563
564static int ade7758_write_raw(struct iio_dev *indio_dev,
565 struct iio_chan_spec const *chan,
566 int val, int val2, long mask)
567{
568 int ret;
569
570 switch (mask) {
571 case IIO_CHAN_INFO_SAMP_FREQ:
572 if (val2)
573 return -EINVAL;
574
575 ret = ade7758_write_samp_freq(&indio_dev->dev, val);
576
577 return ret;
578 default:
579 return -EINVAL;
580 }
581
582 return ret;
583}
584
585static IIO_DEV_ATTR_TEMP_RAW(ade7758_read_8bit);
586static IIO_CONST_ATTR(in_temp_offset, "129 C");
587static IIO_CONST_ATTR(in_temp_scale, "4 C");
588
589static IIO_DEV_ATTR_AWATTHR(ade7758_read_16bit,
590 ADE7758_AWATTHR);
591static IIO_DEV_ATTR_BWATTHR(ade7758_read_16bit,
592 ADE7758_BWATTHR);
593static IIO_DEV_ATTR_CWATTHR(ade7758_read_16bit,
594 ADE7758_CWATTHR);
595static IIO_DEV_ATTR_AVARHR(ade7758_read_16bit,
596 ADE7758_AVARHR);
597static IIO_DEV_ATTR_BVARHR(ade7758_read_16bit,
598 ADE7758_BVARHR);
599static IIO_DEV_ATTR_CVARHR(ade7758_read_16bit,
600 ADE7758_CVARHR);
601static IIO_DEV_ATTR_AVAHR(ade7758_read_16bit,
602 ADE7758_AVAHR);
603static IIO_DEV_ATTR_BVAHR(ade7758_read_16bit,
604 ADE7758_BVAHR);
605static IIO_DEV_ATTR_CVAHR(ade7758_read_16bit,
606 ADE7758_CVAHR);
607
608static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("26040 13020 6510 3255");
609
610static struct attribute *ade7758_attributes[] = {
611 &iio_dev_attr_in_temp_raw.dev_attr.attr,
612 &iio_const_attr_in_temp_offset.dev_attr.attr,
613 &iio_const_attr_in_temp_scale.dev_attr.attr,
614 &iio_const_attr_sampling_frequency_available.dev_attr.attr,
615 &iio_dev_attr_awatthr.dev_attr.attr,
616 &iio_dev_attr_bwatthr.dev_attr.attr,
617 &iio_dev_attr_cwatthr.dev_attr.attr,
618 &iio_dev_attr_avarhr.dev_attr.attr,
619 &iio_dev_attr_bvarhr.dev_attr.attr,
620 &iio_dev_attr_cvarhr.dev_attr.attr,
621 &iio_dev_attr_avahr.dev_attr.attr,
622 &iio_dev_attr_bvahr.dev_attr.attr,
623 &iio_dev_attr_cvahr.dev_attr.attr,
624 &iio_dev_attr_vpeak.dev_attr.attr,
625 &iio_dev_attr_ipeak.dev_attr.attr,
626 &iio_dev_attr_aphcal.dev_attr.attr,
627 &iio_dev_attr_bphcal.dev_attr.attr,
628 &iio_dev_attr_cphcal.dev_attr.attr,
629 &iio_dev_attr_wdiv.dev_attr.attr,
630 &iio_dev_attr_vadiv.dev_attr.attr,
631 &iio_dev_attr_airms.dev_attr.attr,
632 &iio_dev_attr_birms.dev_attr.attr,
633 &iio_dev_attr_cirms.dev_attr.attr,
634 &iio_dev_attr_avrms.dev_attr.attr,
635 &iio_dev_attr_bvrms.dev_attr.attr,
636 &iio_dev_attr_cvrms.dev_attr.attr,
637 &iio_dev_attr_aigain.dev_attr.attr,
638 &iio_dev_attr_bigain.dev_attr.attr,
639 &iio_dev_attr_cigain.dev_attr.attr,
640 &iio_dev_attr_avrmsgain.dev_attr.attr,
641 &iio_dev_attr_bvrmsgain.dev_attr.attr,
642 &iio_dev_attr_cvrmsgain.dev_attr.attr,
643 &iio_dev_attr_airmsos.dev_attr.attr,
644 &iio_dev_attr_birmsos.dev_attr.attr,
645 &iio_dev_attr_cirmsos.dev_attr.attr,
646 &iio_dev_attr_avrmsos.dev_attr.attr,
647 &iio_dev_attr_bvrmsos.dev_attr.attr,
648 &iio_dev_attr_cvrmsos.dev_attr.attr,
649 NULL,
650};
651
652static const struct attribute_group ade7758_attribute_group = {
653 .attrs = ade7758_attributes,
654};
655
656static const struct iio_chan_spec ade7758_channels[] = {
657 {
658 .type = IIO_VOLTAGE,
659 .indexed = 1,
660 .channel = 0,
661 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
662 .address = AD7758_WT(AD7758_PHASE_A, AD7758_VOLTAGE),
663 .scan_index = 0,
664 .scan_type = {
665 .sign = 's',
666 .realbits = 24,
667 .storagebits = 32,
668 },
669 }, {
670 .type = IIO_CURRENT,
671 .indexed = 1,
672 .channel = 0,
673 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
674 .address = AD7758_WT(AD7758_PHASE_A, AD7758_CURRENT),
675 .scan_index = 1,
676 .scan_type = {
677 .sign = 's',
678 .realbits = 24,
679 .storagebits = 32,
680 },
681 }, {
682 .type = IIO_POWER,
683 .indexed = 1,
684 .channel = 0,
685 .extend_name = "apparent",
686 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
687 .address = AD7758_WT(AD7758_PHASE_A, AD7758_APP_PWR),
688 .scan_index = 2,
689 .scan_type = {
690 .sign = 's',
691 .realbits = 24,
692 .storagebits = 32,
693 },
694 }, {
695 .type = IIO_POWER,
696 .indexed = 1,
697 .channel = 0,
698 .extend_name = "active",
699 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
700 .address = AD7758_WT(AD7758_PHASE_A, AD7758_ACT_PWR),
701 .scan_index = 3,
702 .scan_type = {
703 .sign = 's',
704 .realbits = 24,
705 .storagebits = 32,
706 },
707 }, {
708 .type = IIO_POWER,
709 .indexed = 1,
710 .channel = 0,
711 .extend_name = "reactive",
712 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
713 .address = AD7758_WT(AD7758_PHASE_A, AD7758_REACT_PWR),
714 .scan_index = 4,
715 .scan_type = {
716 .sign = 's',
717 .realbits = 24,
718 .storagebits = 32,
719 },
720 }, {
721 .type = IIO_VOLTAGE,
722 .indexed = 1,
723 .channel = 1,
724 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
725 .address = AD7758_WT(AD7758_PHASE_B, AD7758_VOLTAGE),
726 .scan_index = 5,
727 .scan_type = {
728 .sign = 's',
729 .realbits = 24,
730 .storagebits = 32,
731 },
732 }, {
733 .type = IIO_CURRENT,
734 .indexed = 1,
735 .channel = 1,
736 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
737 .address = AD7758_WT(AD7758_PHASE_B, AD7758_CURRENT),
738 .scan_index = 6,
739 .scan_type = {
740 .sign = 's',
741 .realbits = 24,
742 .storagebits = 32,
743 },
744 }, {
745 .type = IIO_POWER,
746 .indexed = 1,
747 .channel = 1,
748 .extend_name = "apparent",
749 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
750 .address = AD7758_WT(AD7758_PHASE_B, AD7758_APP_PWR),
751 .scan_index = 7,
752 .scan_type = {
753 .sign = 's',
754 .realbits = 24,
755 .storagebits = 32,
756 },
757 }, {
758 .type = IIO_POWER,
759 .indexed = 1,
760 .channel = 1,
761 .extend_name = "active",
762 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
763 .address = AD7758_WT(AD7758_PHASE_B, AD7758_ACT_PWR),
764 .scan_index = 8,
765 .scan_type = {
766 .sign = 's',
767 .realbits = 24,
768 .storagebits = 32,
769 },
770 }, {
771 .type = IIO_POWER,
772 .indexed = 1,
773 .channel = 1,
774 .extend_name = "reactive",
775 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
776 .address = AD7758_WT(AD7758_PHASE_B, AD7758_REACT_PWR),
777 .scan_index = 9,
778 .scan_type = {
779 .sign = 's',
780 .realbits = 24,
781 .storagebits = 32,
782 },
783 }, {
784 .type = IIO_VOLTAGE,
785 .indexed = 1,
786 .channel = 2,
787 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
788 .address = AD7758_WT(AD7758_PHASE_C, AD7758_VOLTAGE),
789 .scan_index = 10,
790 .scan_type = {
791 .sign = 's',
792 .realbits = 24,
793 .storagebits = 32,
794 },
795 }, {
796 .type = IIO_CURRENT,
797 .indexed = 1,
798 .channel = 2,
799 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
800 .address = AD7758_WT(AD7758_PHASE_C, AD7758_CURRENT),
801 .scan_index = 11,
802 .scan_type = {
803 .sign = 's',
804 .realbits = 24,
805 .storagebits = 32,
806 },
807 }, {
808 .type = IIO_POWER,
809 .indexed = 1,
810 .channel = 2,
811 .extend_name = "apparent",
812 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
813 .address = AD7758_WT(AD7758_PHASE_C, AD7758_APP_PWR),
814 .scan_index = 12,
815 .scan_type = {
816 .sign = 's',
817 .realbits = 24,
818 .storagebits = 32,
819 },
820 }, {
821 .type = IIO_POWER,
822 .indexed = 1,
823 .channel = 2,
824 .extend_name = "active",
825 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
826 .address = AD7758_WT(AD7758_PHASE_C, AD7758_ACT_PWR),
827 .scan_index = 13,
828 .scan_type = {
829 .sign = 's',
830 .realbits = 24,
831 .storagebits = 32,
832 },
833 }, {
834 .type = IIO_POWER,
835 .indexed = 1,
836 .channel = 2,
837 .extend_name = "reactive",
838 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_SAMP_FREQ),
839 .address = AD7758_WT(AD7758_PHASE_C, AD7758_REACT_PWR),
840 .scan_index = 14,
841 .scan_type = {
842 .sign = 's',
843 .realbits = 24,
844 .storagebits = 32,
845 },
846 },
847 IIO_CHAN_SOFT_TIMESTAMP(15),
848};
849
850static const struct iio_info ade7758_info = {
851 .attrs = &ade7758_attribute_group,
852 .read_raw = &ade7758_read_raw,
853 .write_raw = &ade7758_write_raw,
854};
855
856static int ade7758_probe(struct spi_device *spi)
857{
858 int ret;
859 struct ade7758_state *st;
860 struct iio_dev *indio_dev;
861
862 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
863 if (!indio_dev)
864 return -ENOMEM;
865
866 st = iio_priv(indio_dev);
867 /* this is only used for removal purposes */
868 spi_set_drvdata(spi, indio_dev);
869
870 /* Allocate the comms buffers */
871 st->rx = kcalloc(ADE7758_MAX_RX, sizeof(*st->rx), GFP_KERNEL);
872 if (!st->rx)
873 return -ENOMEM;
874 st->tx = kcalloc(ADE7758_MAX_TX, sizeof(*st->tx), GFP_KERNEL);
875 if (!st->tx) {
876 ret = -ENOMEM;
877 goto error_free_rx;
878 }
879 st->us = spi;
880 mutex_init(&st->buf_lock);
881
882 indio_dev->name = spi->dev.driver->name;
883 indio_dev->dev.parent = &spi->dev;
884 indio_dev->info = &ade7758_info;
885 indio_dev->modes = INDIO_DIRECT_MODE;
886 indio_dev->channels = ade7758_channels;
887 indio_dev->num_channels = ARRAY_SIZE(ade7758_channels);
888
889 ret = ade7758_configure_ring(indio_dev);
890 if (ret)
891 goto error_free_tx;
892
893 /* Get the device into a sane initial state */
894 ret = ade7758_initial_setup(indio_dev);
895 if (ret)
896 goto error_unreg_ring_funcs;
897
898 if (spi->irq) {
899 ret = ade7758_probe_trigger(indio_dev);
900 if (ret)
901 goto error_unreg_ring_funcs;
902 }
903
904 ret = iio_device_register(indio_dev);
905 if (ret)
906 goto error_remove_trigger;
907
908 return 0;
909
910error_remove_trigger:
911 if (spi->irq)
912 ade7758_remove_trigger(indio_dev);
913error_unreg_ring_funcs:
914 ade7758_unconfigure_ring(indio_dev);
915error_free_tx:
916 kfree(st->tx);
917error_free_rx:
918 kfree(st->rx);
919 return ret;
920}
921
922static int ade7758_remove(struct spi_device *spi)
923{
924 struct iio_dev *indio_dev = spi_get_drvdata(spi);
925 struct ade7758_state *st = iio_priv(indio_dev);
926
927 iio_device_unregister(indio_dev);
928 ade7758_stop_device(&indio_dev->dev);
929 ade7758_remove_trigger(indio_dev);
930 ade7758_unconfigure_ring(indio_dev);
931 kfree(st->tx);
932 kfree(st->rx);
933
934 return 0;
935}
936
937static const struct spi_device_id ade7758_id[] = {
938 {"ade7758", 0},
939 {}
940};
941MODULE_DEVICE_TABLE(spi, ade7758_id);
942
943static struct spi_driver ade7758_driver = {
944 .driver = {
945 .name = "ade7758",
946 },
947 .probe = ade7758_probe,
948 .remove = ade7758_remove,
949 .id_table = ade7758_id,
950};
951module_spi_driver(ade7758_driver);
952
953MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
954MODULE_DESCRIPTION("Analog Devices ADE7758 Polyphase Multifunction Energy Metering IC Driver");
955MODULE_LICENSE("GPL v2");
drivers/staging/iio/meter/ade7758_ring.c+0−177
@@ -1,177 +0,0 @@
1/*
2 * ADE7758 Poly Phase Multifunction Energy Metering IC driver
3 *
4 * Copyright 2010-2011 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2.
7 */
8#include <linux/export.h>
9#include <linux/interrupt.h>
10#include <linux/kernel.h>
11#include <linux/spi/spi.h>
12#include <linux/slab.h>
13#include <asm/unaligned.h>
14
15#include <linux/iio/iio.h>
16#include <linux/iio/buffer.h>
17#include <linux/iio/kfifo_buf.h>
18#include <linux/iio/trigger_consumer.h>
19#include "ade7758.h"
20
21/**
22 * ade7758_spi_read_burst() - read data registers
23 * @indio_dev: the IIO device
24 **/
25static int ade7758_spi_read_burst(struct iio_dev *indio_dev)
26{
27 struct ade7758_state *st = iio_priv(indio_dev);
28 int ret;
29
30 ret = spi_sync(st->us, &st->ring_msg);
31 if (ret)
32 dev_err(&st->us->dev, "problem when reading WFORM value\n");
33
34 return ret;
35}
36
37static int ade7758_write_waveform_type(struct device *dev, unsigned int type)
38{
39 int ret;
40 u8 reg;
41
42 ret = ade7758_spi_read_reg_8(dev, ADE7758_WAVMODE, &reg);
43 if (ret)
44 goto out;
45
46 reg &= ~0x1F;
47 reg |= type & 0x1F;
48
49 ret = ade7758_spi_write_reg_8(dev, ADE7758_WAVMODE, reg);
50out:
51 return ret;
52}
53
54/* Whilst this makes a lot of calls to iio_sw_ring functions - it is too device
55 * specific to be rolled into the core.
56 */
57static irqreturn_t ade7758_trigger_handler(int irq, void *p)
58{
59 struct iio_poll_func *pf = p;
60 struct iio_dev *indio_dev = pf->indio_dev;
61 struct ade7758_state *st = iio_priv(indio_dev);
62 s64 dat64[2];
63 u32 *dat32 = (u32 *)dat64;
64
65 if (!bitmap_empty(indio_dev->active_scan_mask, indio_dev->masklength))
66 if (ade7758_spi_read_burst(indio_dev) >= 0)
67 *dat32 = get_unaligned_be32(&st->rx_buf[5]) & 0xFFFFFF;
68
69 iio_push_to_buffers_with_timestamp(indio_dev, dat64, pf->timestamp);
70
71 iio_trigger_notify_done(indio_dev->trig);
72
73 return IRQ_HANDLED;
74}
75
76/**
77 * ade7758_ring_preenable() setup the parameters of the ring before enabling
78 *
79 * The complex nature of the setting of the number of bytes per datum is due
80 * to this driver currently ensuring that the timestamp is stored at an 8
81 * byte boundary.
82 **/
83static int ade7758_ring_preenable(struct iio_dev *indio_dev)
84{
85 unsigned int channel;
86
87 if (bitmap_empty(indio_dev->active_scan_mask, indio_dev->masklength))
88 return -EINVAL;
89
90 channel = find_first_bit(indio_dev->active_scan_mask,
91 indio_dev->masklength);
92
93 ade7758_write_waveform_type(&indio_dev->dev,
94 indio_dev->channels[channel].address);
95
96 return 0;
97}
98
99static const struct iio_buffer_setup_ops ade7758_ring_setup_ops = {
100 .preenable = &ade7758_ring_preenable,
101 .postenable = &iio_triggered_buffer_postenable,
102 .predisable = &iio_triggered_buffer_predisable,
103 .validate_scan_mask = &iio_validate_scan_mask_onehot,
104};
105
106void ade7758_unconfigure_ring(struct iio_dev *indio_dev)
107{
108 iio_dealloc_pollfunc(indio_dev->pollfunc);
109 iio_kfifo_free(indio_dev->buffer);
110}
111
112int ade7758_configure_ring(struct iio_dev *indio_dev)
113{
114 struct ade7758_state *st = iio_priv(indio_dev);
115 struct iio_buffer *buffer;
116 int ret = 0;
117
118 buffer = iio_kfifo_allocate();
119 if (!buffer)
120 return -ENOMEM;
121
122 iio_device_attach_buffer(indio_dev, buffer);
123
124 indio_dev->setup_ops = &ade7758_ring_setup_ops;
125
126 indio_dev->pollfunc = iio_alloc_pollfunc(&iio_pollfunc_store_time,
127 &ade7758_trigger_handler,
128 0,
129 indio_dev,
130 "ade7759_consumer%d",
131 indio_dev->id);
132 if (!indio_dev->pollfunc) {
133 ret = -ENOMEM;
134 goto error_iio_kfifo_free;
135 }
136
137 indio_dev->modes |= INDIO_BUFFER_TRIGGERED;
138
139 st->tx_buf[0] = ADE7758_READ_REG(ADE7758_RSTATUS);
140 st->tx_buf[1] = 0;
141 st->tx_buf[2] = 0;
142 st->tx_buf[3] = 0;
143 st->tx_buf[4] = ADE7758_READ_REG(ADE7758_WFORM);
144 st->tx_buf[5] = 0;
145 st->tx_buf[6] = 0;
146 st->tx_buf[7] = 0;
147
148 /* build spi ring message */
149 st->ring_xfer[0].tx_buf = &st->tx_buf[0];
150 st->ring_xfer[0].len = 1;
151 st->ring_xfer[0].bits_per_word = 8;
152 st->ring_xfer[0].delay_usecs = 4;
153 st->ring_xfer[1].rx_buf = &st->rx_buf[1];
154 st->ring_xfer[1].len = 3;
155 st->ring_xfer[1].bits_per_word = 8;
156 st->ring_xfer[1].cs_change = 1;
157
158 st->ring_xfer[2].tx_buf = &st->tx_buf[4];
159 st->ring_xfer[2].len = 1;
160 st->ring_xfer[2].bits_per_word = 8;
161 st->ring_xfer[2].delay_usecs = 1;
162 st->ring_xfer[3].rx_buf = &st->rx_buf[5];
163 st->ring_xfer[3].len = 3;
164 st->ring_xfer[3].bits_per_word = 8;
165
166 spi_message_init(&st->ring_msg);
167 spi_message_add_tail(&st->ring_xfer[0], &st->ring_msg);
168 spi_message_add_tail(&st->ring_xfer[1], &st->ring_msg);
169 spi_message_add_tail(&st->ring_xfer[2], &st->ring_msg);
170 spi_message_add_tail(&st->ring_xfer[3], &st->ring_msg);
171
172 return 0;
173
174error_iio_kfifo_free:
175 iio_kfifo_free(indio_dev->buffer);
176 return ret;
177}
drivers/staging/iio/meter/ade7758_trigger.c+0−108
@@ -1,108 +0,0 @@
1/*
2 * ADE7758 Poly Phase Multifunction Energy Metering IC driver
3 *
4 * Copyright 2010-2011 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2.
7 */
8
9#include <linux/interrupt.h>
10#include <linux/kernel.h>
11#include <linux/spi/spi.h>
12#include <linux/export.h>
13
14#include <linux/iio/iio.h>
15#include <linux/iio/trigger.h>
16#include "ade7758.h"
17
18/**
19 * ade7758_data_rdy_trig_poll() the event handler for the data rdy trig
20 **/
21static irqreturn_t ade7758_data_rdy_trig_poll(int irq, void *private)
22{
23 disable_irq_nosync(irq);
24 iio_trigger_poll(private);
25
26 return IRQ_HANDLED;
27}
28
29/**
30 * ade7758_data_rdy_trigger_set_state() set datardy interrupt state
31 **/
32static int ade7758_data_rdy_trigger_set_state(struct iio_trigger *trig,
33 bool state)
34{
35 struct iio_dev *indio_dev = iio_trigger_get_drvdata(trig);
36
37 dev_dbg(&indio_dev->dev, "(%d)\n", state);
38 return ade7758_set_irq(&indio_dev->dev, state);
39}
40
41/**
42 * ade7758_trig_try_reen() try renabling irq for data rdy trigger
43 * @trig: the datardy trigger
44 **/
45static int ade7758_trig_try_reen(struct iio_trigger *trig)
46{
47 struct iio_dev *indio_dev = iio_trigger_get_drvdata(trig);
48 struct ade7758_state *st = iio_priv(indio_dev);
49
50 enable_irq(st->us->irq);
51 /* irq reenabled so success! */
52 return 0;
53}
54
55static const struct iio_trigger_ops ade7758_trigger_ops = {
56 .set_trigger_state = &ade7758_data_rdy_trigger_set_state,
57 .try_reenable = &ade7758_trig_try_reen,
58};
59
60int ade7758_probe_trigger(struct iio_dev *indio_dev)
61{
62 struct ade7758_state *st = iio_priv(indio_dev);
63 int ret;
64
65 st->trig = iio_trigger_alloc("%s-dev%d",
66 spi_get_device_id(st->us)->name,
67 indio_dev->id);
68 if (!st->trig) {
69 ret = -ENOMEM;
70 goto error_ret;
71 }
72
73 ret = request_irq(st->us->irq,
74 ade7758_data_rdy_trig_poll,
75 IRQF_TRIGGER_LOW,
76 spi_get_device_id(st->us)->name,
77 st->trig);
78 if (ret)
79 goto error_free_trig;
80
81 st->trig->dev.parent = &st->us->dev;
82 st->trig->ops = &ade7758_trigger_ops;
83 iio_trigger_set_drvdata(st->trig, indio_dev);
84 ret = iio_trigger_register(st->trig);
85
86 /* select default trigger */
87 indio_dev->trig = iio_trigger_get(st->trig);
88 if (ret)
89 goto error_free_irq;
90
91 return 0;
92
93error_free_irq:
94 free_irq(st->us->irq, st->trig);
95error_free_trig:
96 iio_trigger_free(st->trig);
97error_ret:
98 return ret;
99}
100
101void ade7758_remove_trigger(struct iio_dev *indio_dev)
102{
103 struct ade7758_state *st = iio_priv(indio_dev);
104
105 iio_trigger_unregister(st->trig);
106 free_irq(st->us->irq, st->trig);
107 iio_trigger_free(st->trig);
108}
drivers/staging/iio/meter/ade7759.c+0−558
@@ -1,558 +0,0 @@
1/*
2 * ADE7759 Active Energy Metering IC with di/dt Sensor Interface Driver
3 *
4 * Copyright 2010 Analog Devices Inc.
5 *
6 * Licensed under the GPL-2 or later.
7 */
8
9#include <linux/interrupt.h>
10#include <linux/irq.h>
11#include <linux/delay.h>
12#include <linux/mutex.h>
13#include <linux/device.h>
14#include <linux/kernel.h>
15#include <linux/spi/spi.h>
16#include <linux/slab.h>
17#include <linux/sysfs.h>
18#include <linux/list.h>
19#include <linux/module.h>
20
21#include <linux/iio/iio.h>
22#include <linux/iio/sysfs.h>
23#include "meter.h"
24
25#define ADE7759_WAVEFORM 0x01
26#define ADE7759_AENERGY 0x02
27#define ADE7759_RSTENERGY 0x03
28#define ADE7759_STATUS 0x04
29#define ADE7759_RSTSTATUS 0x05
30#define ADE7759_MODE 0x06
31#define ADE7759_CFDEN 0x07
32#define ADE7759_CH1OS 0x08
33#define ADE7759_CH2OS 0x09
34#define ADE7759_GAIN 0x0A
35#define ADE7759_APGAIN 0x0B
36#define ADE7759_PHCAL 0x0C
37#define ADE7759_APOS 0x0D
38#define ADE7759_ZXTOUT 0x0E
39#define ADE7759_SAGCYC 0x0F
40#define ADE7759_IRQEN 0x10
41#define ADE7759_SAGLVL 0x11
42#define ADE7759_TEMP 0x12
43#define ADE7759_LINECYC 0x13
44#define ADE7759_LENERGY 0x14
45#define ADE7759_CFNUM 0x15
46#define ADE7759_CHKSUM 0x1E
47#define ADE7759_DIEREV 0x1F
48
49#define ADE7759_READ_REG(a) a
50#define ADE7759_WRITE_REG(a) ((a) | 0x80)
51
52#define ADE7759_MAX_TX 6
53#define ADE7759_MAX_RX 6
54#define ADE7759_STARTUP_DELAY 1000
55
56#define ADE7759_SPI_SLOW (u32)(300 * 1000)
57#define ADE7759_SPI_BURST (u32)(1000 * 1000)
58#define ADE7759_SPI_FAST (u32)(2000 * 1000)
59
60/**
61 * struct ade7759_state - device instance specific data
62 * @us: actual spi_device
63 * @buf_lock: mutex to protect tx and rx and write frequency
64 * @tx: transmit buffer
65 * @rx: receive buffer
66 **/
67struct ade7759_state {
68 struct spi_device *us;
69 struct mutex buf_lock;
70 u8 tx[ADE7759_MAX_TX] ____cacheline_aligned;
71 u8 rx[ADE7759_MAX_RX];
72};
73
74static int ade7759_spi_write_reg_8(struct device *dev,
75 u8 reg_address,
76 u8 val)
77{
78 int ret;
79 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
80 struct ade7759_state *st = iio_priv(indio_dev);
81
82 mutex_lock(&st->buf_lock);
83 st->tx[0] = ADE7759_WRITE_REG(reg_address);
84 st->tx[1] = val;
85
86 ret = spi_write(st->us, st->tx, 2);
87 mutex_unlock(&st->buf_lock);
88
89 return ret;
90}
91
92/*Unlocked version of ade7759_spi_write_reg_16 function */
93static int __ade7759_spi_write_reg_16(struct device *dev,
94 u8 reg_address,
95 u16 value)
96{
97 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
98 struct ade7759_state *st = iio_priv(indio_dev);
99
100 st->tx[0] = ADE7759_WRITE_REG(reg_address);
101 st->tx[1] = (value >> 8) & 0xFF;
102 st->tx[2] = value & 0xFF;
103 return spi_write(st->us, st->tx, 3);
104}
105
106static int ade7759_spi_write_reg_16(struct device *dev,
107 u8 reg_address,
108 u16 value)
109{
110 int ret;
111 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
112 struct ade7759_state *st = iio_priv(indio_dev);
113
114 mutex_lock(&st->buf_lock);
115 ret = __ade7759_spi_write_reg_16(dev, reg_address, value);
116 mutex_unlock(&st->buf_lock);
117
118 return ret;
119}
120
121static int ade7759_spi_read_reg_8(struct device *dev,
122 u8 reg_address,
123 u8 *val)
124{
125 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
126 struct ade7759_state *st = iio_priv(indio_dev);
127 int ret;
128
129 ret = spi_w8r8(st->us, ADE7759_READ_REG(reg_address));
130 if (ret < 0) {
131 dev_err(&st->us->dev,
132 "problem when reading 8 bit register 0x%02X",
133 reg_address);
134 return ret;
135 }
136 *val = ret;
137
138 return 0;
139}
140
141static int ade7759_spi_read_reg_16(struct device *dev,
142 u8 reg_address,
143 u16 *val)
144{
145 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
146 struct ade7759_state *st = iio_priv(indio_dev);
147 int ret;
148
149 ret = spi_w8r16be(st->us, ADE7759_READ_REG(reg_address));
150 if (ret < 0) {
151 dev_err(&st->us->dev, "problem when reading 16 bit register 0x%02X",
152 reg_address);
153 return ret;
154 }
155
156 *val = ret;
157
158 return 0;
159}
160
161static int ade7759_spi_read_reg_40(struct device *dev,
162 u8 reg_address,
163 u64 *val)
164{
165 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
166 struct ade7759_state *st = iio_priv(indio_dev);
167 int ret;
168 struct spi_transfer xfers[] = {
169 {
170 .tx_buf = st->tx,
171 .rx_buf = st->rx,
172 .bits_per_word = 8,
173 .len = 6,
174 },
175 };
176
177 mutex_lock(&st->buf_lock);
178 st->tx[0] = ADE7759_READ_REG(reg_address);
179 memset(&st->tx[1], 0, 5);
180
181 ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
182 if (ret) {
183 dev_err(&st->us->dev,
184 "problem when reading 40 bit register 0x%02X",
185 reg_address);
186 goto error_ret;
187 }
188 *val = ((u64)st->rx[1] << 32) | ((u64)st->rx[2] << 24) |
189 (st->rx[3] << 16) | (st->rx[4] << 8) | st->rx[5];
190
191error_ret:
192 mutex_unlock(&st->buf_lock);
193 return ret;
194}
195
196static ssize_t ade7759_read_8bit(struct device *dev,
197 struct device_attribute *attr,
198 char *buf)
199{
200 int ret;
201 u8 val = 0;
202 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
203
204 ret = ade7759_spi_read_reg_8(dev, this_attr->address, &val);
205 if (ret)
206 return ret;
207
208 return sprintf(buf, "%u\n", val);
209}
210
211static ssize_t ade7759_read_16bit(struct device *dev,
212 struct device_attribute *attr,
213 char *buf)
214{
215 int ret;
216 u16 val = 0;
217 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
218
219 ret = ade7759_spi_read_reg_16(dev, this_attr->address, &val);
220 if (ret)
221 return ret;
222
223 return sprintf(buf, "%u\n", val);
224}
225
226static ssize_t ade7759_read_40bit(struct device *dev,
227 struct device_attribute *attr,
228 char *buf)
229{
230 int ret;
231 u64 val = 0;
232 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
233
234 ret = ade7759_spi_read_reg_40(dev, this_attr->address, &val);
235 if (ret)
236 return ret;
237
238 return sprintf(buf, "%llu\n", val);
239}
240
241static ssize_t ade7759_write_8bit(struct device *dev,
242 struct device_attribute *attr,
243 const char *buf,
244 size_t len)
245{
246 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
247 int ret;
248 u8 val;
249
250 ret = kstrtou8(buf, 10, &val);
251 if (ret)
252 goto error_ret;
253 ret = ade7759_spi_write_reg_8(dev, this_attr->address, val);
254
255error_ret:
256 return ret ? ret : len;
257}
258
259static ssize_t ade7759_write_16bit(struct device *dev,
260 struct device_attribute *attr,
261 const char *buf,
262 size_t len)
263{
264 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
265 int ret;
266 u16 val;
267
268 ret = kstrtou16(buf, 10, &val);
269 if (ret)
270 goto error_ret;
271 ret = ade7759_spi_write_reg_16(dev, this_attr->address, val);
272
273error_ret:
274 return ret ? ret : len;
275}
276
277static int ade7759_reset(struct device *dev)
278{
279 int ret;
280 u16 val;
281
282 ret = ade7759_spi_read_reg_16(dev, ADE7759_MODE, &val);
283 if (ret < 0)
284 return ret;
285
286 val |= BIT(6); /* Software Chip Reset */
287 return ade7759_spi_write_reg_16(dev,
288 ADE7759_MODE,
289 val);
290}
291
292static IIO_DEV_ATTR_AENERGY(ade7759_read_40bit, ADE7759_AENERGY);
293static IIO_DEV_ATTR_CFDEN(0644,
294 ade7759_read_16bit,
295 ade7759_write_16bit,
296 ADE7759_CFDEN);
297static IIO_DEV_ATTR_CFNUM(0644,
298 ade7759_read_8bit,
299 ade7759_write_8bit,
300 ADE7759_CFNUM);
301static IIO_DEV_ATTR_CHKSUM(ade7759_read_8bit, ADE7759_CHKSUM);
302static IIO_DEV_ATTR_PHCAL(0644,
303 ade7759_read_16bit,
304 ade7759_write_16bit,
305 ADE7759_PHCAL);
306static IIO_DEV_ATTR_APOS(0644,
307 ade7759_read_16bit,
308 ade7759_write_16bit,
309 ADE7759_APOS);
310static IIO_DEV_ATTR_SAGCYC(0644,
311 ade7759_read_8bit,
312 ade7759_write_8bit,
313 ADE7759_SAGCYC);
314static IIO_DEV_ATTR_SAGLVL(0644,
315 ade7759_read_8bit,
316 ade7759_write_8bit,
317 ADE7759_SAGLVL);
318static IIO_DEV_ATTR_LINECYC(0644,
319 ade7759_read_8bit,
320 ade7759_write_8bit,
321 ADE7759_LINECYC);
322static IIO_DEV_ATTR_LENERGY(ade7759_read_40bit, ADE7759_LENERGY);
323static IIO_DEV_ATTR_PGA_GAIN(0644,
324 ade7759_read_8bit,
325 ade7759_write_8bit,
326 ADE7759_GAIN);
327static IIO_DEV_ATTR_ACTIVE_POWER_GAIN(0644,
328 ade7759_read_16bit,
329 ade7759_write_16bit,
330 ADE7759_APGAIN);
331
332static IIO_DEVICE_ATTR(choff_1, 0644,
333 ade7759_read_8bit,
334 ade7759_write_8bit,
335 ADE7759_CH1OS);
336
337static IIO_DEVICE_ATTR(choff_2, 0644,
338 ade7759_read_8bit,
339 ade7759_write_8bit,
340 ADE7759_CH2OS);
341
342static int ade7759_set_irq(struct device *dev, bool enable)
343{
344 int ret;
345 u8 irqen;
346
347 ret = ade7759_spi_read_reg_8(dev, ADE7759_IRQEN, &irqen);
348 if (ret)
349 goto error_ret;
350
351 if (enable)
352 irqen |= BIT(3); /* Enables an interrupt when a data is
353 * present in the waveform register
354 */
355 else
356 irqen &= ~BIT(3);
357
358 ret = ade7759_spi_write_reg_8(dev, ADE7759_IRQEN, irqen);
359
360error_ret:
361 return ret;
362}
363
364/* Power down the device */
365static int ade7759_stop_device(struct device *dev)
366{
367 int ret;
368 u16 val;
369
370 ret = ade7759_spi_read_reg_16(dev, ADE7759_MODE, &val);
371 if (ret < 0) {
372 dev_err(dev, "unable to power down the device, error: %d\n",
373 ret);
374 return ret;
375 }
376
377 val |= BIT(4); /* AD converters can be turned off */
378
379 return ade7759_spi_write_reg_16(dev, ADE7759_MODE, val);
380}
381
382static int ade7759_initial_setup(struct iio_dev *indio_dev)
383{
384 int ret;
385 struct ade7759_state *st = iio_priv(indio_dev);
386 struct device *dev = &indio_dev->dev;
387
388 /* use low spi speed for init */
389 st->us->mode = SPI_MODE_3;
390 spi_setup(st->us);
391
392 /* Disable IRQ */
393 ret = ade7759_set_irq(dev, false);
394 if (ret) {
395 dev_err(dev, "disable irq failed");
396 goto err_ret;
397 }
398
399 ade7759_reset(dev);
400 usleep_range(ADE7759_STARTUP_DELAY, ADE7759_STARTUP_DELAY + 100);
401
402err_ret:
403 return ret;
404}
405
406static ssize_t ade7759_read_frequency(struct device *dev,
407 struct device_attribute *attr,
408 char *buf)
409{
410 int ret;
411 u16 t;
412 int sps;
413
414 ret = ade7759_spi_read_reg_16(dev, ADE7759_MODE, &t);
415 if (ret)
416 return ret;
417
418 t = (t >> 3) & 0x3;
419 sps = 27900 / (1 + t);
420
421 return sprintf(buf, "%d\n", sps);
422}
423
424static ssize_t ade7759_write_frequency(struct device *dev,
425 struct device_attribute *attr,
426 const char *buf,
427 size_t len)
428{
429 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
430 struct ade7759_state *st = iio_priv(indio_dev);
431 u16 val;
432 int ret;
433 u16 reg, t;
434
435 ret = kstrtou16(buf, 10, &val);
436 if (ret)
437 return ret;
438 if (!val)
439 return -EINVAL;
440
441 mutex_lock(&st->buf_lock);
442
443 t = 27900 / val;
444 if (t > 0)
445 t--;
446
447 if (t > 1)
448 st->us->max_speed_hz = ADE7759_SPI_SLOW;
449 else
450 st->us->max_speed_hz = ADE7759_SPI_FAST;
451
452 ret = ade7759_spi_read_reg_16(dev, ADE7759_MODE, &reg);
453 if (ret)
454 goto out;
455
456 reg &= ~(3 << 13);
457 reg |= t << 13;
458
459 ret = __ade7759_spi_write_reg_16(dev, ADE7759_MODE, reg);
460
461out:
462 mutex_unlock(&st->buf_lock);
463
464 return ret ? ret : len;
465}
466static IIO_DEV_ATTR_TEMP_RAW(ade7759_read_8bit);
467static IIO_CONST_ATTR(in_temp_offset, "70 C");
468static IIO_CONST_ATTR(in_temp_scale, "1 C");
469
470static IIO_DEV_ATTR_SAMP_FREQ(0644,
471 ade7759_read_frequency,
472 ade7759_write_frequency);
473
474static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("27900 14000 7000 3500");
475
476static struct attribute *ade7759_attributes[] = {
477 &iio_dev_attr_in_temp_raw.dev_attr.attr,
478 &iio_const_attr_in_temp_offset.dev_attr.attr,
479 &iio_const_attr_in_temp_scale.dev_attr.attr,
480 &iio_dev_attr_sampling_frequency.dev_attr.attr,
481 &iio_const_attr_sampling_frequency_available.dev_attr.attr,
482 &iio_dev_attr_phcal.dev_attr.attr,
483 &iio_dev_attr_cfden.dev_attr.attr,
484 &iio_dev_attr_aenergy.dev_attr.attr,
485 &iio_dev_attr_cfnum.dev_attr.attr,
486 &iio_dev_attr_apos.dev_attr.attr,
487 &iio_dev_attr_sagcyc.dev_attr.attr,
488 &iio_dev_attr_saglvl.dev_attr.attr,
489 &iio_dev_attr_linecyc.dev_attr.attr,
490 &iio_dev_attr_lenergy.dev_attr.attr,
491 &iio_dev_attr_chksum.dev_attr.attr,
492 &iio_dev_attr_pga_gain.dev_attr.attr,
493 &iio_dev_attr_active_power_gain.dev_attr.attr,
494 &iio_dev_attr_choff_1.dev_attr.attr,
495 &iio_dev_attr_choff_2.dev_attr.attr,
496 NULL,
497};
498
499static const struct attribute_group ade7759_attribute_group = {
500 .attrs = ade7759_attributes,
501};
502
503static const struct iio_info ade7759_info = {
504 .attrs = &ade7759_attribute_group,
505};
506
507static int ade7759_probe(struct spi_device *spi)
508{
509 int ret;
510 struct ade7759_state *st;
511 struct iio_dev *indio_dev;
512
513 /* setup the industrialio driver allocated elements */
514 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
515 if (!indio_dev)
516 return -ENOMEM;
517 /* this is only used for removal purposes */
518 spi_set_drvdata(spi, indio_dev);
519
520 st = iio_priv(indio_dev);
521 st->us = spi;
522 mutex_init(&st->buf_lock);
523 indio_dev->name = spi->dev.driver->name;
524 indio_dev->dev.parent = &spi->dev;
525 indio_dev->info = &ade7759_info;
526 indio_dev->modes = INDIO_DIRECT_MODE;
527
528 /* Get the device into a sane initial state */
529 ret = ade7759_initial_setup(indio_dev);
530 if (ret)
531 return ret;
532
533 return iio_device_register(indio_dev);
534}
535
536static int ade7759_remove(struct spi_device *spi)
537{
538 struct iio_dev *indio_dev = spi_get_drvdata(spi);
539
540 iio_device_unregister(indio_dev);
541 ade7759_stop_device(&indio_dev->dev);
542
543 return 0;
544}
545
546static struct spi_driver ade7759_driver = {
547 .driver = {
548 .name = "ade7759",
549 },
550 .probe = ade7759_probe,
551 .remove = ade7759_remove,
552};
553module_spi_driver(ade7759_driver);
554
555MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
556MODULE_DESCRIPTION("Analog Devices ADE7759 Active Energy Metering IC Driver");
557MODULE_LICENSE("GPL v2");
558MODULE_ALIAS("spi:ad7759");
drivers/staging/iio/meter/ade7854-i2c.c+70−168
@@ -15,91 +15,60 @@ · 14 unmodified lines
15#include <linux/iio/iio.h>15#include <linux/iio/iio.h>
16#include "ade7854.h"16#include "ade7854.h"
17 17
18static int ade7854_i2c_write_reg_8(struct device *dev,18static int ade7854_i2c_write_reg(struct device *dev,
19 u16 reg_address,19 u16 reg_address,
20 u8 val)20 u32 val,
21 int bits)
21{22{
22 int ret;23 int ret;
24 int count;
23 struct iio_dev *indio_dev = dev_to_iio_dev(dev);25 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
24 struct ade7854_state *st = iio_priv(indio_dev);26 struct ade7854_state *st = iio_priv(indio_dev);
25 27
26 mutex_lock(&st->buf_lock);28 mutex_lock(&st->buf_lock);
27 st->tx[0] = (reg_address >> 8) & 0xFF;29 st->tx[0] = (reg_address >> 8) & 0xFF;
28 st->tx[1] = reg_address & 0xFF;30 st->tx[1] = reg_address & 0xFF;
29 st->tx[2] = val;
30 31
31 ret = i2c_master_send(st->i2c, st->tx, 3);32 switch (bits) {
33 case 8:
34 st->tx[2] = val & 0xFF;
35 count = 3;
36 break;
37 case 16:
38 st->tx[2] = (val >> 8) & 0xFF;
39 st->tx[3] = val & 0xFF;
40 count = 4;
41 break;
42 case 24:
43 st->tx[2] = (val >> 16) & 0xFF;
44 st->tx[3] = (val >> 8) & 0xFF;
45 st->tx[4] = val & 0xFF;
46 count = 5;
47 break;
48 case 32:
49 st->tx[2] = (val >> 24) & 0xFF;
50 st->tx[3] = (val >> 16) & 0xFF;
51 st->tx[4] = (val >> 8) & 0xFF;
52 st->tx[5] = val & 0xFF;
53 count = 6;
54 break;
55 default:
56 ret = -EINVAL;
57 goto unlock;
58 }
59
60 ret = i2c_master_send(st->i2c, st->tx, count);
61
62unlock:
32 mutex_unlock(&st->buf_lock);63 mutex_unlock(&st->buf_lock);
33 64
34 return ret;65 return ret < 0 ? ret : 0;
35}66}
36 67
37static int ade7854_i2c_write_reg_16(struct device *dev,68static int ade7854_i2c_read_reg(struct device *dev,
38 u16 reg_address,69 u16 reg_address,
39 u16 val)70 u32 *val,
40{71 int bits)
41 int ret;
42 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
43 struct ade7854_state *st = iio_priv(indio_dev);
44
45 mutex_lock(&st->buf_lock);
46 st->tx[0] = (reg_address >> 8) & 0xFF;
47 st->tx[1] = reg_address & 0xFF;
48 st->tx[2] = (val >> 8) & 0xFF;
49 st->tx[3] = val & 0xFF;
50
51 ret = i2c_master_send(st->i2c, st->tx, 4);
52 mutex_unlock(&st->buf_lock);
53
54 return ret;
55}
56
57static int ade7854_i2c_write_reg_24(struct device *dev,
58 u16 reg_address,
59 u32 val)
60{
61 int ret;
62 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
63 struct ade7854_state *st = iio_priv(indio_dev);
64
65 mutex_lock(&st->buf_lock);
66 st->tx[0] = (reg_address >> 8) & 0xFF;
67 st->tx[1] = reg_address & 0xFF;
68 st->tx[2] = (val >> 16) & 0xFF;
69 st->tx[3] = (val >> 8) & 0xFF;
70 st->tx[4] = val & 0xFF;
71
72 ret = i2c_master_send(st->i2c, st->tx, 5);
73 mutex_unlock(&st->buf_lock);
74
75 return ret;
76}
77
78static int ade7854_i2c_write_reg_32(struct device *dev,
79 u16 reg_address,
80 u32 val)
81{
82 int ret;
83 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
84 struct ade7854_state *st = iio_priv(indio_dev);
85
86 mutex_lock(&st->buf_lock);
87 st->tx[0] = (reg_address >> 8) & 0xFF;
88 st->tx[1] = reg_address & 0xFF;
89 st->tx[2] = (val >> 24) & 0xFF;
90 st->tx[3] = (val >> 16) & 0xFF;
91 st->tx[4] = (val >> 8) & 0xFF;
92 st->tx[5] = val & 0xFF;
93
94 ret = i2c_master_send(st->i2c, st->tx, 6);
95 mutex_unlock(&st->buf_lock);
96
97 return ret;
98}
99
100static int ade7854_i2c_read_reg_8(struct device *dev,
101 u16 reg_address,
102 u8 *val)
103{72{
104 struct iio_dev *indio_dev = dev_to_iio_dev(dev);73 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
105 struct ade7854_state *st = iio_priv(indio_dev);74 struct ade7854_state *st = iio_priv(indio_dev);
@@ -110,94 +79,33 @@ static int ade7854_i2c_read_reg_8(struct device *dev, · 4 unmodified lines
110 st->tx[1] = reg_address & 0xFF;79 st->tx[1] = reg_address & 0xFF;
111 80
112 ret = i2c_master_send(st->i2c, st->tx, 2);81 ret = i2c_master_send(st->i2c, st->tx, 2);
113 if (ret)82 if (ret < 0)
114 goto out;83 goto unlock;
115 84
116 ret = i2c_master_recv(st->i2c, st->rx, 1);85 ret = i2c_master_recv(st->i2c, st->rx, bits);
117 if (ret)86 if (ret < 0)
118 goto out;87 goto unlock;
119 88
120 *val = st->rx[0];89 switch (bits) {
121out:90 case 8:
122 mutex_unlock(&st->buf_lock);91 *val = st->rx[0];
123 return ret;92 break;
124}93 case 16:
125 94 *val = (st->rx[0] << 8) | st->rx[1];
126static int ade7854_i2c_read_reg_16(struct device *dev,95 break;
127 u16 reg_address,96 case 24:
128 u16 *val)97 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
129{98 break;
130 struct iio_dev *indio_dev = dev_to_iio_dev(dev);99 case 32:
131 struct ade7854_state *st = iio_priv(indio_dev);100 *val = (st->rx[0] << 24) | (st->rx[1] << 16) |
132 int ret;101 (st->rx[2] << 8) | st->rx[3];
133 102 break;
134 mutex_lock(&st->buf_lock);103 default:
135 st->tx[0] = (reg_address >> 8) & 0xFF;104 ret = -EINVAL;
136 st->tx[1] = reg_address & 0xFF;105 goto unlock;
137 106 }
138 ret = i2c_master_send(st->i2c, st->tx, 2);107
139 if (ret)108unlock:
140 goto out;
141
142 ret = i2c_master_recv(st->i2c, st->rx, 2);
143 if (ret)
144 goto out;
145
146 *val = (st->rx[0] << 8) | st->rx[1];
147out:
148 mutex_unlock(&st->buf_lock);
149 return ret;
150}
151
152static int ade7854_i2c_read_reg_24(struct device *dev,
153 u16 reg_address,
154 u32 *val)
155{
156 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
157 struct ade7854_state *st = iio_priv(indio_dev);
158 int ret;
159
160 mutex_lock(&st->buf_lock);
161 st->tx[0] = (reg_address >> 8) & 0xFF;
162 st->tx[1] = reg_address & 0xFF;
163
164 ret = i2c_master_send(st->i2c, st->tx, 2);
165 if (ret)
166 goto out;
167
168 ret = i2c_master_recv(st->i2c, st->rx, 3);
169 if (ret)
170 goto out;
171
172 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
173out:
174 mutex_unlock(&st->buf_lock);
175 return ret;
176}
177
178static int ade7854_i2c_read_reg_32(struct device *dev,
179 u16 reg_address,
180 u32 *val)
181{
182 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
183 struct ade7854_state *st = iio_priv(indio_dev);
184 int ret;
185
186 mutex_lock(&st->buf_lock);
187 st->tx[0] = (reg_address >> 8) & 0xFF;
188 st->tx[1] = reg_address & 0xFF;
189
190 ret = i2c_master_send(st->i2c, st->tx, 2);
191 if (ret)
192 goto out;
193
194 ret = i2c_master_recv(st->i2c, st->rx, 3);
195 if (ret)
196 goto out;
197
198 *val = (st->rx[0] << 24) | (st->rx[1] << 16) |
199 (st->rx[2] << 8) | st->rx[3];
200out:
201 mutex_unlock(&st->buf_lock);109 mutex_unlock(&st->buf_lock);
202 return ret;110 return ret;
203}111}
@@ -213,14 +121,8 @@ static int ade7854_i2c_probe(struct i2c_client *client, · 9 unmodified lines
213 return -ENOMEM;121 return -ENOMEM;
214 st = iio_priv(indio_dev);122 st = iio_priv(indio_dev);
215 i2c_set_clientdata(client, indio_dev);123 i2c_set_clientdata(client, indio_dev);
216 st->read_reg_8 = ade7854_i2c_read_reg_8;124 st->read_reg = ade7854_i2c_read_reg;
217 st->read_reg_16 = ade7854_i2c_read_reg_16;125 st->write_reg = ade7854_i2c_write_reg;
218 st->read_reg_24 = ade7854_i2c_read_reg_24;
219 st->read_reg_32 = ade7854_i2c_read_reg_32;
220 st->write_reg_8 = ade7854_i2c_write_reg_8;
221 st->write_reg_16 = ade7854_i2c_write_reg_16;
222 st->write_reg_24 = ade7854_i2c_write_reg_24;
223 st->write_reg_32 = ade7854_i2c_write_reg_32;
224 st->i2c = client;126 st->i2c = client;
225 st->irq = client->irq;127 st->irq = client->irq;
226 128
drivers/staging/iio/meter/ade7854-spi.c+55−213
@@ -15,9 +15,10 @@ · 14 unmodified lines
15#include <linux/iio/iio.h>15#include <linux/iio/iio.h>
16#include "ade7854.h"16#include "ade7854.h"
17 17
18static int ade7854_spi_write_reg_8(struct device *dev,18static int ade7854_spi_write_reg(struct device *dev,
19 u16 reg_address,19 u16 reg_address,
20 u8 val)20 u32 val,
21 int bits)
21{22{
22 int ret;23 int ret;
23 struct iio_dev *indio_dev = dev_to_iio_dev(dev);24 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
@@ -32,173 +33,44 @@ static int ade7854_spi_write_reg_8(struct device *dev, · 8 unmodified lines
32 st->tx[0] = ADE7854_WRITE_REG;33 st->tx[0] = ADE7854_WRITE_REG;
33 st->tx[1] = (reg_address >> 8) & 0xFF;34 st->tx[1] = (reg_address >> 8) & 0xFF;
34 st->tx[2] = reg_address & 0xFF;35 st->tx[2] = reg_address & 0xFF;
35 st->tx[3] = val & 0xFF;36 switch (bits) {
36 37 case 8:
37 ret = spi_sync_transfer(st->spi, &xfer, 1);38 st->tx[3] = val & 0xFF;
38 mutex_unlock(&st->buf_lock);39 break;
39 40 case 16:
40 return ret;41 xfer.len = 5;
41}42 st->tx[3] = (val >> 8) & 0xFF;
42 43 st->tx[4] = val & 0xFF;
43static int ade7854_spi_write_reg_16(struct device *dev,44 break;
44 u16 reg_address,45 case 24:
45 u16 val)46 xfer.len = 6;
46{47 st->tx[3] = (val >> 16) & 0xFF;
47 int ret;48 st->tx[4] = (val >> 8) & 0xFF;
48 struct iio_dev *indio_dev = dev_to_iio_dev(dev);49 st->tx[5] = val & 0xFF;
49 struct ade7854_state *st = iio_priv(indio_dev);50 break;
50 struct spi_transfer xfer = {51 case 32:
51 .tx_buf = st->tx,52 xfer.len = 7;
52 .bits_per_word = 8,53 st->tx[3] = (val >> 24) & 0xFF;
53 .len = 5,54 st->tx[4] = (val >> 16) & 0xFF;
54 };55 st->tx[5] = (val >> 8) & 0xFF;
55 56 st->tx[6] = val & 0xFF;
56 mutex_lock(&st->buf_lock);57 break;
57 st->tx[0] = ADE7854_WRITE_REG;58 default:
58 st->tx[1] = (reg_address >> 8) & 0xFF;59 ret = -EINVAL;
59 st->tx[2] = reg_address & 0xFF;60 goto unlock;
60 st->tx[3] = (val >> 8) & 0xFF;
61 st->tx[4] = val & 0xFF;
62
63 ret = spi_sync_transfer(st->spi, &xfer, 1);
64 mutex_unlock(&st->buf_lock);
65
66 return ret;
67}
68
69static int ade7854_spi_write_reg_24(struct device *dev,
70 u16 reg_address,
71 u32 val)
72{
73 int ret;
74 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
75 struct ade7854_state *st = iio_priv(indio_dev);
76 struct spi_transfer xfer = {
77 .tx_buf = st->tx,
78 .bits_per_word = 8,
79 .len = 6,
80 };
81
82 mutex_lock(&st->buf_lock);
83 st->tx[0] = ADE7854_WRITE_REG;
84 st->tx[1] = (reg_address >> 8) & 0xFF;
85 st->tx[2] = reg_address & 0xFF;
86 st->tx[3] = (val >> 16) & 0xFF;
87 st->tx[4] = (val >> 8) & 0xFF;
88 st->tx[5] = val & 0xFF;
89
90 ret = spi_sync_transfer(st->spi, &xfer, 1);
91 mutex_unlock(&st->buf_lock);
92
93 return ret;
94}
95
96static int ade7854_spi_write_reg_32(struct device *dev,
97 u16 reg_address,
98 u32 val)
99{
100 int ret;
101 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
102 struct ade7854_state *st = iio_priv(indio_dev);
103 struct spi_transfer xfer = {
104 .tx_buf = st->tx,
105 .bits_per_word = 8,
106 .len = 7,
107 };
108
109 mutex_lock(&st->buf_lock);
110 st->tx[0] = ADE7854_WRITE_REG;
111 st->tx[1] = (reg_address >> 8) & 0xFF;
112 st->tx[2] = reg_address & 0xFF;
113 st->tx[3] = (val >> 24) & 0xFF;
114 st->tx[4] = (val >> 16) & 0xFF;
115 st->tx[5] = (val >> 8) & 0xFF;
116 st->tx[6] = val & 0xFF;
117
118 ret = spi_sync_transfer(st->spi, &xfer, 1);
119 mutex_unlock(&st->buf_lock);
120
121 return ret;
122}
123
124static int ade7854_spi_read_reg_8(struct device *dev,
125 u16 reg_address,
126 u8 *val)
127{
128 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
129 struct ade7854_state *st = iio_priv(indio_dev);
130 int ret;
131 struct spi_transfer xfers[] = {
132 {
133 .tx_buf = st->tx,
134 .bits_per_word = 8,
135 .len = 3,
136 }, {
137 .rx_buf = st->rx,
138 .bits_per_word = 8,
139 .len = 1,
140 }
141 };
142
143 mutex_lock(&st->buf_lock);
144
145 st->tx[0] = ADE7854_READ_REG;
146 st->tx[1] = (reg_address >> 8) & 0xFF;
147 st->tx[2] = reg_address & 0xFF;
148
149 ret = spi_sync_transfer(st->spi, xfers, ARRAY_SIZE(xfers));
150 if (ret) {
151 dev_err(&st->spi->dev, "problem when reading 8 bit register 0x%02X",
152 reg_address);
153 goto error_ret;
154 }61 }
155 *val = st->rx[0];
156 62
157error_ret:63 ret = spi_sync_transfer(st->spi, &xfer, 1);
64unlock:
158 mutex_unlock(&st->buf_lock);65 mutex_unlock(&st->buf_lock);
159 return ret;
160}
161
162static int ade7854_spi_read_reg_16(struct device *dev,
163 u16 reg_address,
164 u16 *val)
165{
166 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
167 struct ade7854_state *st = iio_priv(indio_dev);
168 int ret;
169 struct spi_transfer xfers[] = {
170 {
171 .tx_buf = st->tx,
172 .bits_per_word = 8,
173 .len = 3,
174 }, {
175 .rx_buf = st->rx,
176 .bits_per_word = 8,
177 .len = 2,
178 }
179 };
180 66
181 mutex_lock(&st->buf_lock);
182 st->tx[0] = ADE7854_READ_REG;
183 st->tx[1] = (reg_address >> 8) & 0xFF;
184 st->tx[2] = reg_address & 0xFF;
185
186 ret = spi_sync_transfer(st->spi, xfers, ARRAY_SIZE(xfers));
187 if (ret) {
188 dev_err(&st->spi->dev, "problem when reading 16 bit register 0x%02X",
189 reg_address);
190 goto error_ret;
191 }
192 *val = be16_to_cpup((const __be16 *)st->rx);
193
194error_ret:
195 mutex_unlock(&st->buf_lock);
196 return ret;67 return ret;
197}68}
198 69
199static int ade7854_spi_read_reg_24(struct device *dev,70static int ade7854_spi_read_reg(struct device *dev,
200 u16 reg_address,71 u16 reg_address,
201 u32 *val)72 u32 *val,
73 int bits)
202{74{
203 struct iio_dev *indio_dev = dev_to_iio_dev(dev);75 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
204 struct ade7854_state *st = iio_priv(indio_dev);76 struct ade7854_state *st = iio_priv(indio_dev);
@@ -211,7 +83,7 @@ static int ade7854_spi_read_reg_24(struct device *dev, · 6 unmodified lines
211 }, {83 }, {
212 .rx_buf = st->rx,84 .rx_buf = st->rx,
213 .bits_per_word = 8,85 .bits_per_word = 8,
214 .len = 3,86 .len = bits,
215 }87 }
216 };88 };
217 89
@@ -222,52 +94,28 @@ static int ade7854_spi_read_reg_24(struct device *dev, · 4 unmodified lines
222 st->tx[2] = reg_address & 0xFF;94 st->tx[2] = reg_address & 0xFF;
223 95
224 ret = spi_sync_transfer(st->spi, xfers, ARRAY_SIZE(xfers));96 ret = spi_sync_transfer(st->spi, xfers, ARRAY_SIZE(xfers));
225 if (ret) {97 if (ret < 0) {
226 dev_err(&st->spi->dev, "problem when reading 24 bit register 0x%02X",98 dev_err(&st->spi->dev, "problem when reading register 0x%02X",
227 reg_address);99 reg_address);
228 goto error_ret;100 goto unlock;
229 }101 }
230 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
231
232error_ret:
233 mutex_unlock(&st->buf_lock);
234 return ret;
235}
236
237static int ade7854_spi_read_reg_32(struct device *dev,
238 u16 reg_address,
239 u32 *val)
240{
241 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
242 struct ade7854_state *st = iio_priv(indio_dev);
243 int ret;
244 struct spi_transfer xfers[] = {
245 {
246 .tx_buf = st->tx,
247 .bits_per_word = 8,
248 .len = 3,
249 }, {
250 .rx_buf = st->rx,
251 .bits_per_word = 8,
252 .len = 4,
253 }
254 };
255
256 mutex_lock(&st->buf_lock);
257 102
258 st->tx[0] = ADE7854_READ_REG;103 switch (bits) {
259 st->tx[1] = (reg_address >> 8) & 0xFF;104 case 8:
260 st->tx[2] = reg_address & 0xFF;105 *val = st->rx[0];
261 106 break;
262 ret = spi_sync_transfer(st->spi, xfers, ARRAY_SIZE(xfers));107 case 16:
263 if (ret) {108 *val = be16_to_cpup((const __be16 *)st->rx);
264 dev_err(&st->spi->dev, "problem when reading 32 bit register 0x%02X",109 break;
265 reg_address);110 case 24:
266 goto error_ret;111 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
112 break;
113 case 32:
114 *val = be32_to_cpup((const __be32 *)st->rx);
115 break;
267 }116 }
268 *val = be32_to_cpup((const __be32 *)st->rx);
269 117
270error_ret:118unlock:
271 mutex_unlock(&st->buf_lock);119 mutex_unlock(&st->buf_lock);
272 return ret;120 return ret;
273}121}
@@ -282,14 +130,8 @@ static int ade7854_spi_probe(struct spi_device *spi) · 8 unmodified lines
282 return -ENOMEM;130 return -ENOMEM;
283 st = iio_priv(indio_dev);131 st = iio_priv(indio_dev);
284 spi_set_drvdata(spi, indio_dev);132 spi_set_drvdata(spi, indio_dev);
285 st->read_reg_8 = ade7854_spi_read_reg_8;133 st->read_reg = ade7854_spi_read_reg;
286 st->read_reg_16 = ade7854_spi_read_reg_16;134 st->write_reg = ade7854_spi_write_reg;
287 st->read_reg_24 = ade7854_spi_read_reg_24;
288 st->read_reg_32 = ade7854_spi_read_reg_32;
289 st->write_reg_8 = ade7854_spi_write_reg_8;
290 st->write_reg_16 = ade7854_spi_write_reg_16;
291 st->write_reg_24 = ade7854_spi_write_reg_24;
292 st->write_reg_32 = ade7854_spi_write_reg_32;
293 st->irq = spi->irq;135 st->irq = spi->irq;
294 st->spi = spi;136 st->spi = spi;
295 137
drivers/staging/iio/meter/ade7854.c+20−20
@@ -27,13 +27,13 @@ static ssize_t ade7854_read_8bit(struct device *dev, · 26 unmodified lines
27 char *buf)27 char *buf)
28{28{
29 int ret;29 int ret;
30 u8 val = 0;30 u32 val = 0;
31 struct iio_dev *indio_dev = dev_to_iio_dev(dev);31 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
32 struct ade7854_state *st = iio_priv(indio_dev);32 struct ade7854_state *st = iio_priv(indio_dev);
33 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);33 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
34 34
35 ret = st->read_reg_8(dev, this_attr->address, &val);35 ret = st->read_reg(dev, this_attr->address, &val, 8);
36 if (ret)36 if (ret < 0)
37 return ret;37 return ret;
38 38
39 return sprintf(buf, "%u\n", val);39 return sprintf(buf, "%u\n", val);
@@ -44,13 +44,13 @@ static ssize_t ade7854_read_16bit(struct device *dev, · 4 unmodified lines
44 char *buf)44 char *buf)
45{45{
46 int ret;46 int ret;
47 u16 val = 0;47 u32 val = 0;
48 struct iio_dev *indio_dev = dev_to_iio_dev(dev);48 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
49 struct ade7854_state *st = iio_priv(indio_dev);49 struct ade7854_state *st = iio_priv(indio_dev);
50 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);50 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
51 51
52 ret = st->read_reg_16(dev, this_attr->address, &val);52 ret = st->read_reg(dev, this_attr->address, &val, 16);
53 if (ret)53 if (ret < 0)
54 return ret;54 return ret;
55 55
56 return sprintf(buf, "%u\n", val);56 return sprintf(buf, "%u\n", val);
@@ -66,8 +66,8 @@ static ssize_t ade7854_read_24bit(struct device *dev, · 9 unmodified lines
66 struct ade7854_state *st = iio_priv(indio_dev);66 struct ade7854_state *st = iio_priv(indio_dev);
67 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);67 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
68 68
69 ret = st->read_reg_24(dev, this_attr->address, &val);69 ret = st->read_reg(dev, this_attr->address, &val, 24);
70 if (ret)70 if (ret < 0)
71 return ret;71 return ret;
72 72
73 return sprintf(buf, "%u\n", val);73 return sprintf(buf, "%u\n", val);
@@ -83,8 +83,8 @@ static ssize_t ade7854_read_32bit(struct device *dev, · 9 unmodified lines
83 struct iio_dev *indio_dev = dev_to_iio_dev(dev);83 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
84 struct ade7854_state *st = iio_priv(indio_dev);84 struct ade7854_state *st = iio_priv(indio_dev);
85 85
86 ret = st->read_reg_32(dev, this_attr->address, &val);86 ret = st->read_reg(dev, this_attr->address, &val, 32);
87 if (ret)87 if (ret < 0)
88 return ret;88 return ret;
89 89
90 return sprintf(buf, "%u\n", val);90 return sprintf(buf, "%u\n", val);
@@ -105,7 +105,7 @@ static ssize_t ade7854_write_8bit(struct device *dev, · 14 unmodified lines
105 ret = kstrtou8(buf, 10, &val);105 ret = kstrtou8(buf, 10, &val);
106 if (ret)106 if (ret)
107 goto error_ret;107 goto error_ret;
108 ret = st->write_reg_8(dev, this_attr->address, val);108 ret = st->write_reg(dev, this_attr->address, val, 8);
109 109
110error_ret:110error_ret:
111 return ret ? ret : len;111 return ret ? ret : len;
@@ -126,7 +126,7 @@ static ssize_t ade7854_write_16bit(struct device *dev, · 14 unmodified lines
126 ret = kstrtou16(buf, 10, &val);126 ret = kstrtou16(buf, 10, &val);
127 if (ret)127 if (ret)
128 goto error_ret;128 goto error_ret;
129 ret = st->write_reg_16(dev, this_attr->address, val);129 ret = st->write_reg(dev, this_attr->address, val, 16);
130 130
131error_ret:131error_ret:
132 return ret ? ret : len;132 return ret ? ret : len;
@@ -147,7 +147,7 @@ static ssize_t ade7854_write_24bit(struct device *dev, · 14 unmodified lines
147 ret = kstrtou32(buf, 10, &val);147 ret = kstrtou32(buf, 10, &val);
148 if (ret)148 if (ret)
149 goto error_ret;149 goto error_ret;
150 ret = st->write_reg_24(dev, this_attr->address, val);150 ret = st->write_reg(dev, this_attr->address, val, 24);
151 151
152error_ret:152error_ret:
153 return ret ? ret : len;153 return ret ? ret : len;
@@ -168,7 +168,7 @@ static ssize_t ade7854_write_32bit(struct device *dev, · 14 unmodified lines
168 ret = kstrtou32(buf, 10, &val);168 ret = kstrtou32(buf, 10, &val);
169 if (ret)169 if (ret)
170 goto error_ret;170 goto error_ret;
171 ret = st->write_reg_32(dev, this_attr->address, val);171 ret = st->write_reg(dev, this_attr->address, val, 32);
172 172
173error_ret:173error_ret:
174 return ret ? ret : len;174 return ret ? ret : len;
@@ -178,12 +178,12 @@ static int ade7854_reset(struct device *dev) · 3 unmodified lines
178{178{
179 struct iio_dev *indio_dev = dev_to_iio_dev(dev);179 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
180 struct ade7854_state *st = iio_priv(indio_dev);180 struct ade7854_state *st = iio_priv(indio_dev);
181 u16 val;181 u32 val;
182 182
183 st->read_reg_16(dev, ADE7854_CONFIG, &val);183 st->read_reg(dev, ADE7854_CONFIG, &val, 16);
184 val |= BIT(7); /* Software Chip Reset */184 val |= BIT(7); /* Software Chip Reset */
185 185
186 return st->write_reg_16(dev, ADE7854_CONFIG, val);186 return st->write_reg(dev, ADE7854_CONFIG, val, 16);
187}187}
188 188
189static IIO_DEV_ATTR_AIGAIN(0644,189static IIO_DEV_ATTR_AIGAIN(0644,
@@ -415,8 +415,8 @@ static int ade7854_set_irq(struct device *dev, bool enable) · 225 unmodified lines
415 int ret;415 int ret;
416 u32 irqen;416 u32 irqen;
417 417
418 ret = st->read_reg_32(dev, ADE7854_MASK0, &irqen);418 ret = st->read_reg(dev, ADE7854_MASK0, &irqen, 32);
419 if (ret)419 if (ret < 0)
420 return ret;420 return ret;
421 421
422 if (enable)422 if (enable)
@@ -426,7 +426,7 @@ static int ade7854_set_irq(struct device *dev, bool enable) · 3 unmodified lines
426 else426 else
427 irqen &= ~BIT(17);427 irqen &= ~BIT(17);
428 428
429 return st->write_reg_32(dev, ADE7854_MASK0, irqen);429 return st->write_reg(dev, ADE7854_MASK0, irqen, 32);
430}430}
431 431
432static int ade7854_initial_setup(struct iio_dev *indio_dev)432static int ade7854_initial_setup(struct iio_dev *indio_dev)
drivers/staging/iio/meter/ade7854.h+7−9
@@ -145,7 +145,9 @@ · 144 unmodified lines
145 145
146/**146/**
147 * struct ade7854_state - device instance specific data147 * struct ade7854_state - device instance specific data
148 * @spi: actual spi_device148 * @spi: actual spi_device
149 * @read_reg Wrapper function for I2C and SPI read
150 * @write_reg Wrapper function for I2C and SPI write
149 * @indio_dev: industrial I/O device structure151 * @indio_dev: industrial I/O device structure
150 * @buf_lock: mutex to protect tx and rx152 * @buf_lock: mutex to protect tx and rx
151 * @tx: transmit buffer153 * @tx: transmit buffer
@@ -154,14 +156,10 @@ · 2 unmodified lines
154struct ade7854_state {156struct ade7854_state {
155 struct spi_device *spi;157 struct spi_device *spi;
156 struct i2c_client *i2c;158 struct i2c_client *i2c;
157 int (*read_reg_8)(struct device *dev, u16 reg_address, u8 *val);159 int (*read_reg)(struct device *dev, u16 reg_address, u32 *val,
158 int (*read_reg_16)(struct device *dev, u16 reg_address, u16 *val);160 int bits);
159 int (*read_reg_24)(struct device *dev, u16 reg_address, u32 *val);161 int (*write_reg)(struct device *dev, u16 reg_address, u32 val,
160 int (*read_reg_32)(struct device *dev, u16 reg_address, u32 *val);162 int bits);
161 int (*write_reg_8)(struct device *dev, u16 reg_address, u8 val);
162 int (*write_reg_16)(struct device *dev, u16 reg_address, u16 val);
163 int (*write_reg_24)(struct device *dev, u16 reg_address, u32 val);
164 int (*write_reg_32)(struct device *dev, u16 reg_address, u32 val);
165 int irq;163 int irq;
166 struct mutex buf_lock;164 struct mutex buf_lock;
167 u8 tx[ADE7854_MAX_TX] ____cacheline_aligned;165 u8 tx[ADE7854_MAX_TX] ____cacheline_aligned;
drivers/staging/iio/resolver/Kconfig+0−12
@@ -13,18 +13,6 @@ config AD2S90 · 12 unmodified lines
13 To compile this driver as a module, choose M here: the13 To compile this driver as a module, choose M here: the
14 module will be called ad2s90.14 module will be called ad2s90.
15 15
16config AD2S1200
17 tristate "Analog Devices ad2s1200/ad2s1205 driver"
18 depends on SPI
19 depends on GPIOLIB || COMPILE_TEST
20 help
21 Say yes here to build support for Analog Devices spi resolver
22 to digital converters, ad2s1200 and ad2s1205, provides direct access
23 via sysfs.
24
25 To compile this driver as a module, choose M here: the
26 module will be called ad2s1200.
27
28config AD2S121016config AD2S1210
29 tristate "Analog Devices ad2s1210 driver"17 tristate "Analog Devices ad2s1210 driver"
30 depends on SPI18 depends on SPI
drivers/staging/iio/resolver/Makefile+0−1
@@ -3,5 +3,4 @@ · 2 unmodified lines
3#3#
4 4
5obj-$(CONFIG_AD2S90) += ad2s90.o5obj-$(CONFIG_AD2S90) += ad2s90.o
6obj-$(CONFIG_AD2S1200) += ad2s1200.o
7obj-$(CONFIG_AD2S1210) += ad2s1210.o6obj-$(CONFIG_AD2S1210) += ad2s1210.o
drivers/staging/ipx/Kconfig+0−61
@@ -1,61 +0,0 @@
1#
2# IPX configuration
3#
4config IPX
5 tristate "The IPX protocol"
6 depends on NET
7 select LLC
8 ---help---
9 This is support for the Novell networking protocol, IPX, commonly
10 used for local networks of Windows machines. You need it if you
11 want to access Novell NetWare file or print servers using the Linux
12 Novell client ncpfs (available from
13 <ftp://platan.vc.cvut.cz/pub/linux/ncpfs/>) or from
14 within the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO,
15 available from <http://www.tldp.org/docs.html#howto>). In order
16 to do the former, you'll also have to say Y to "NCP file system
17 support", below.
18
19 IPX is similar in scope to IP, while SPX, which runs on top of IPX,
20 is similar to TCP.
21
22 To turn your Linux box into a fully featured NetWare file server and
23 IPX router, say Y here and fetch either lwared from
24 <ftp://ibiblio.org/pub/Linux/system/network/daemons/> or
25 mars_nwe from <ftp://www.compu-art.de/mars_nwe/>. For more
26 information, read the IPX-HOWTO available from
27 <http://www.tldp.org/docs.html#howto>.
28
29 The IPX driver would enlarge your kernel by about 16 KB. To compile
30 this driver as a module, choose M here: the module will be called ipx.
31 Unless you want to integrate your Linux box with a local Novell
32 network, say N.
33
34config IPX_INTERN
35 bool "IPX: Full internal IPX network"
36 depends on IPX
37 ---help---
38 Every IPX network has an address that identifies it. Sometimes it is
39 useful to give an IPX "network" address to your Linux box as well
40 (for example if your box is acting as a file server for different
41 IPX networks: it will then be accessible from everywhere using the
42 same address). The way this is done is to create a virtual internal
43 "network" inside your box and to assign an IPX address to this
44 network. Say Y here if you want to do this; read the IPX-HOWTO at
45 <http://www.tldp.org/docs.html#howto> for details.
46
47 The full internal IPX network enables you to allocate sockets on
48 different virtual nodes of the internal network. This is done by
49 evaluating the field sipx_node of the socket address given to the
50 bind call. So applications should always initialize the node field
51 to 0 when binding a socket on the primary network. In this case the
52 socket is assigned the default node that has been given to the
53 kernel when the internal network was created. By enabling the full
54 internal IPX network the cross-forwarding of packets targeted at
55 'special' sockets to sockets listening on the primary network is
56 disabled. This might break existing applications, especially RIP/SAP
57 daemons. A RIP/SAP daemon that works well with the full internal net
58 can be found on <ftp://ftp.gwdg.de/pub/linux/misc/ncpfs/>.
59
60 If you don't know what you are doing, say N.
61
drivers/staging/ipx/Makefile+0−8
@@ -1,8 +0,0 @@
1#
2# Makefile for the Linux IPX layer.
3#
4
5obj-$(CONFIG_IPX) += ipx.o
6
7ipx-y := af_ipx.o ipx_route.o ipx_proc.o pe2.o
8ipx-$(CONFIG_SYSCTL) += sysctl_net_ipx.o
drivers/staging/ipx/TODO+0−4
@@ -1,4 +0,0 @@
1The ipx code will be removed soon from the kernel tree as it is old and
2obsolete and broken.
3
4Don't worry about fixing up anything here, it's not needed.
drivers/staging/ipx/af_ipx.c+0−2082
@@ -1,2082 +0,0 @@
1/*
2 * Implements an IPX socket layer.
3 *
4 * This code is derived from work by
5 * Ross Biro : Writing the original IP stack
6 * Fred Van Kempen : Tidying up the TCP/IP
7 *
8 * Many thanks go to Keith Baker, Institute For Industrial Information
9 * Technology Ltd, Swansea University for allowing me to work on this
10 * in my own time even though it was in some ways related to commercial
11 * work I am currently employed to do there.
12 *
13 * All the material in this file is subject to the Gnu license version 2.
14 * Neither Alan Cox nor the Swansea University Computer Society admit
15 * liability nor provide warranty for any of this software. This material
16 * is provided as is and at no charge.
17 *
18 * Portions Copyright (c) 2000-2003 Conectiva, Inc. <acme@conectiva.com.br>
19 * Neither Arnaldo Carvalho de Melo nor Conectiva, Inc. admit liability nor
20 * provide warranty for any of this software. This material is provided
21 * "AS-IS" and at no charge.
22 *
23 * Portions Copyright (c) 1995 Caldera, Inc. <greg@caldera.com>
24 * Neither Greg Page nor Caldera, Inc. admit liability nor provide
25 * warranty for any of this software. This material is provided
26 * "AS-IS" and at no charge.
27 *
28 * See net/ipx/ChangeLog.
29 */
30
31#include <linux/capability.h>
32#include <linux/errno.h>
33#include <linux/if_arp.h>
34#include <linux/if_ether.h>
35#include <linux/init.h>
36#include <linux/ipx.h>
37#include <linux/kernel.h>
38#include <linux/list.h>
39#include <linux/module.h>
40#include <linux/net.h>
41#include <linux/netdevice.h>
42#include <linux/uio.h>
43#include <linux/slab.h>
44#include <linux/skbuff.h>
45#include <linux/socket.h>
46#include <linux/sockios.h>
47#include <linux/string.h>
48#include <linux/types.h>
49#include <linux/termios.h>
50
51#include <net/ipx.h>
52#include <net/p8022.h>
53#include <net/psnap.h>
54#include <net/sock.h>
55#include <net/datalink.h>
56#include <net/tcp_states.h>
57#include <net/net_namespace.h>
58
59#include <linux/uaccess.h>
60
61/* Configuration Variables */
62static unsigned char ipxcfg_max_hops = 16;
63static char ipxcfg_auto_select_primary;
64static char ipxcfg_auto_create_interfaces;
65int sysctl_ipx_pprop_broadcasting = 1;
66
67/* Global Variables */
68static struct datalink_proto *p8022_datalink;
69static struct datalink_proto *pEII_datalink;
70static struct datalink_proto *p8023_datalink;
71static struct datalink_proto *pSNAP_datalink;
72
73static const struct proto_ops ipx_dgram_ops;
74
75LIST_HEAD(ipx_interfaces);
76DEFINE_SPINLOCK(ipx_interfaces_lock);
77
78struct ipx_interface *ipx_primary_net;
79struct ipx_interface *ipx_internal_net;
80
81struct ipx_interface *ipx_interfaces_head(void)
82{
83 struct ipx_interface *rc = NULL;
84
85 if (!list_empty(&ipx_interfaces))
86 rc = list_entry(ipx_interfaces.next,
87 struct ipx_interface, node);
88 return rc;
89}
90
91static void ipxcfg_set_auto_select(char val)
92{
93 ipxcfg_auto_select_primary = val;
94 if (val && !ipx_primary_net)
95 ipx_primary_net = ipx_interfaces_head();
96}
97
98static int ipxcfg_get_config_data(struct ipx_config_data __user *arg)
99{
100 struct ipx_config_data vals;
101
102 vals.ipxcfg_auto_create_interfaces = ipxcfg_auto_create_interfaces;
103 vals.ipxcfg_auto_select_primary = ipxcfg_auto_select_primary;
104
105 return copy_to_user(arg, &vals, sizeof(vals)) ? -EFAULT : 0;
106}
107
108/*
109 * Note: Sockets may not be removed _during_ an interrupt or inet_bh
110 * handler using this technique. They can be added although we do not
111 * use this facility.
112 */
113
114static void ipx_remove_socket(struct sock *sk)
115{
116 /* Determine interface with which socket is associated */
117 struct ipx_interface *intrfc = ipx_sk(sk)->intrfc;
118
119 if (!intrfc)
120 goto out;
121
122 ipxitf_hold(intrfc);
123 spin_lock_bh(&intrfc->if_sklist_lock);
124 sk_del_node_init(sk);
125 spin_unlock_bh(&intrfc->if_sklist_lock);
126 ipxitf_put(intrfc);
127out:
128 return;
129}
130
131static void ipx_destroy_socket(struct sock *sk)
132{
133 ipx_remove_socket(sk);
134 skb_queue_purge(&sk->sk_receive_queue);
135 sk_refcnt_debug_dec(sk);
136}
137
138/*
139 * The following code is used to support IPX Interfaces (IPXITF). An
140 * IPX interface is defined by a physical device and a frame type.
141 */
142
143/* ipxitf_clear_primary_net has to be called with ipx_interfaces_lock held */
144
145static void ipxitf_clear_primary_net(void)
146{
147 ipx_primary_net = NULL;
148 if (ipxcfg_auto_select_primary)
149 ipx_primary_net = ipx_interfaces_head();
150}
151
152static struct ipx_interface *__ipxitf_find_using_phys(struct net_device *dev,
153 __be16 datalink)
154{
155 struct ipx_interface *i;
156
157 list_for_each_entry(i, &ipx_interfaces, node)
158 if (i->if_dev == dev && i->if_dlink_type == datalink)
159 goto out;
160 i = NULL;
161out:
162 return i;
163}
164
165static struct ipx_interface *ipxitf_find_using_phys(struct net_device *dev,
166 __be16 datalink)
167{
168 struct ipx_interface *i;
169
170 spin_lock_bh(&ipx_interfaces_lock);
171 i = __ipxitf_find_using_phys(dev, datalink);
172 if (i)
173 ipxitf_hold(i);
174 spin_unlock_bh(&ipx_interfaces_lock);
175 return i;
176}
177
178struct ipx_interface *ipxitf_find_using_net(__be32 net)
179{
180 struct ipx_interface *i;
181
182 spin_lock_bh(&ipx_interfaces_lock);
183 if (net) {
184 list_for_each_entry(i, &ipx_interfaces, node)
185 if (i->if_netnum == net)
186 goto hold;
187 i = NULL;
188 goto unlock;
189 }
190
191 i = ipx_primary_net;
192 if (i)
193hold:
194 ipxitf_hold(i);
195unlock:
196 spin_unlock_bh(&ipx_interfaces_lock);
197 return i;
198}
199
200/* Sockets are bound to a particular IPX interface. */
201static void ipxitf_insert_socket(struct ipx_interface *intrfc, struct sock *sk)
202{
203 ipxitf_hold(intrfc);
204 spin_lock_bh(&intrfc->if_sklist_lock);
205 ipx_sk(sk)->intrfc = intrfc;
206 sk_add_node(sk, &intrfc->if_sklist);
207 spin_unlock_bh(&intrfc->if_sklist_lock);
208 ipxitf_put(intrfc);
209}
210
211/* caller must hold intrfc->if_sklist_lock */
212static struct sock *__ipxitf_find_socket(struct ipx_interface *intrfc,
213 __be16 port)
214{
215 struct sock *s;
216
217 sk_for_each(s, &intrfc->if_sklist)
218 if (ipx_sk(s)->port == port)
219 goto found;
220 s = NULL;
221found:
222 return s;
223}
224
225/* caller must hold a reference to intrfc */
226static struct sock *ipxitf_find_socket(struct ipx_interface *intrfc,
227 __be16 port)
228{
229 struct sock *s;
230
231 spin_lock_bh(&intrfc->if_sklist_lock);
232 s = __ipxitf_find_socket(intrfc, port);
233 if (s)
234 sock_hold(s);
235 spin_unlock_bh(&intrfc->if_sklist_lock);
236
237 return s;
238}
239
240#ifdef CONFIG_IPX_INTERN
241static struct sock *ipxitf_find_internal_socket(struct ipx_interface *intrfc,
242 unsigned char *ipx_node,
243 __be16 port)
244{
245 struct sock *s;
246
247 ipxitf_hold(intrfc);
248 spin_lock_bh(&intrfc->if_sklist_lock);
249
250 sk_for_each(s, &intrfc->if_sklist) {
251 struct ipx_sock *ipxs = ipx_sk(s);
252
253 if (ipxs->port == port &&
254 !memcmp(ipx_node, ipxs->node, IPX_NODE_LEN))
255 goto found;
256 }
257 s = NULL;
258found:
259 spin_unlock_bh(&intrfc->if_sklist_lock);
260 ipxitf_put(intrfc);
261 return s;
262}
263#endif
264
265static void __ipxitf_down(struct ipx_interface *intrfc)
266{
267 struct sock *s;
268 struct hlist_node *t;
269
270 /* Delete all routes associated with this interface */
271 ipxrtr_del_routes(intrfc);
272
273 spin_lock_bh(&intrfc->if_sklist_lock);
274 /* error sockets */
275 sk_for_each_safe(s, t, &intrfc->if_sklist) {
276 struct ipx_sock *ipxs = ipx_sk(s);
277
278 s->sk_err = ENOLINK;
279 s->sk_error_report(s);
280 ipxs->intrfc = NULL;
281 ipxs->port = 0;
282 sock_set_flag(s, SOCK_ZAPPED); /* Indicates it is no longer bound */
283 sk_del_node_init(s);
284 }
285 INIT_HLIST_HEAD(&intrfc->if_sklist);
286 spin_unlock_bh(&intrfc->if_sklist_lock);
287
288 /* remove this interface from list */
289 list_del(&intrfc->node);
290
291 /* remove this interface from *special* networks */
292 if (intrfc == ipx_primary_net)
293 ipxitf_clear_primary_net();
294 if (intrfc == ipx_internal_net)
295 ipx_internal_net = NULL;
296
297 if (intrfc->if_dev)
298 dev_put(intrfc->if_dev);
299 kfree(intrfc);
300}
301
302void ipxitf_down(struct ipx_interface *intrfc)
303{
304 spin_lock_bh(&ipx_interfaces_lock);
305 __ipxitf_down(intrfc);
306 spin_unlock_bh(&ipx_interfaces_lock);
307}
308
309static void __ipxitf_put(struct ipx_interface *intrfc)
310{
311 if (refcount_dec_and_test(&intrfc->refcnt))
312 __ipxitf_down(intrfc);
313}
314
315static int ipxitf_device_event(struct notifier_block *notifier,
316 unsigned long event, void *ptr)
317{
318 struct net_device *dev = netdev_notifier_info_to_dev(ptr);
319 struct ipx_interface *i, *tmp;
320
321 if (!net_eq(dev_net(dev), &init_net))
322 return NOTIFY_DONE;
323
324 if (event != NETDEV_DOWN && event != NETDEV_UP)
325 goto out;
326
327 spin_lock_bh(&ipx_interfaces_lock);
328 list_for_each_entry_safe(i, tmp, &ipx_interfaces, node)
329 if (i->if_dev == dev) {
330 if (event == NETDEV_UP)
331 ipxitf_hold(i);
332 else
333 __ipxitf_put(i);
334 }
335 spin_unlock_bh(&ipx_interfaces_lock);
336out:
337 return NOTIFY_DONE;
338}
339
340
341static __exit void ipxitf_cleanup(void)
342{
343 struct ipx_interface *i, *tmp;
344
345 spin_lock_bh(&ipx_interfaces_lock);
346 list_for_each_entry_safe(i, tmp, &ipx_interfaces, node)
347 __ipxitf_put(i);
348 spin_unlock_bh(&ipx_interfaces_lock);
349}
350
351static void ipxitf_def_skb_handler(struct sock *sock, struct sk_buff *skb)
352{
353 if (sock_queue_rcv_skb(sock, skb) < 0)
354 kfree_skb(skb);
355}
356
357/*
358 * On input skb->sk is NULL. Nobody is charged for the memory.
359 */
360
361/* caller must hold a reference to intrfc */
362
363#ifdef CONFIG_IPX_INTERN
364static int ipxitf_demux_socket(struct ipx_interface *intrfc,
365 struct sk_buff *skb, int copy)
366{
367 struct ipxhdr *ipx = ipx_hdr(skb);
368 int is_broadcast = !memcmp(ipx->ipx_dest.node, ipx_broadcast_node,
369 IPX_NODE_LEN);
370 struct sock *s;
371 int rc;
372
373 spin_lock_bh(&intrfc->if_sklist_lock);
374
375 sk_for_each(s, &intrfc->if_sklist) {
376 struct ipx_sock *ipxs = ipx_sk(s);
377
378 if (ipxs->port == ipx->ipx_dest.sock &&
379 (is_broadcast || !memcmp(ipx->ipx_dest.node,
380 ipxs->node, IPX_NODE_LEN))) {
381 /* We found a socket to which to send */
382 struct sk_buff *skb1;
383
384 if (copy) {
385 skb1 = skb_clone(skb, GFP_ATOMIC);
386 rc = -ENOMEM;
387 if (!skb1)
388 goto out;
389 } else {
390 skb1 = skb;
391 copy = 1; /* skb may only be used once */
392 }
393 ipxitf_def_skb_handler(s, skb1);
394
395 /* On an external interface, one socket can listen */
396 if (intrfc != ipx_internal_net)
397 break;
398 }
399 }
400
401 /* skb was solely for us, and we did not make a copy, so free it. */
402 if (!copy)
403 kfree_skb(skb);
404
405 rc = 0;
406out:
407 spin_unlock_bh(&intrfc->if_sklist_lock);
408 return rc;
409}
410#else
411static struct sock *ncp_connection_hack(struct ipx_interface *intrfc,
412 struct ipxhdr *ipx)
413{
414 /* The packet's target is a NCP connection handler. We want to hand it
415 * to the correct socket directly within the kernel, so that the
416 * mars_nwe packet distribution process does not have to do it. Here we
417 * only care about NCP and BURST packets.
418 *
419 * You might call this a hack, but believe me, you do not want a
420 * complete NCP layer in the kernel, and this is VERY fast as well. */
421 struct sock *sk = NULL;
422 int connection = 0;
423 u8 *ncphdr = (u8 *)(ipx + 1);
424
425 if (*ncphdr == 0x22 && *(ncphdr + 1) == 0x22) /* NCP request */
426 connection = (((int) *(ncphdr + 5)) << 8) | (int) *(ncphdr + 3);
427 else if (*ncphdr == 0x77 && *(ncphdr + 1) == 0x77) /* BURST packet */
428 connection = (((int) *(ncphdr + 9)) << 8) | (int) *(ncphdr + 8);
429
430 if (connection) {
431 /* Now we have to look for a special NCP connection handling
432 * socket. Only these sockets have ipx_ncp_conn != 0, set by
433 * SIOCIPXNCPCONN. */
434 spin_lock_bh(&intrfc->if_sklist_lock);
435 sk_for_each(sk, &intrfc->if_sklist)
436 if (ipx_sk(sk)->ipx_ncp_conn == connection) {
437 sock_hold(sk);
438 goto found;
439 }
440 sk = NULL;
441 found:
442 spin_unlock_bh(&intrfc->if_sklist_lock);
443 }
444 return sk;
445}
446
447static int ipxitf_demux_socket(struct ipx_interface *intrfc,
448 struct sk_buff *skb, int copy)
449{
450 struct ipxhdr *ipx = ipx_hdr(skb);
451 struct sock *sock1 = NULL, *sock2 = NULL;
452 struct sk_buff *skb1 = NULL, *skb2 = NULL;
453 int rc;
454
455 if (intrfc == ipx_primary_net && ntohs(ipx->ipx_dest.sock) == 0x451)
456 sock1 = ncp_connection_hack(intrfc, ipx);
457 if (!sock1)
458 /* No special socket found, forward the packet the normal way */
459 sock1 = ipxitf_find_socket(intrfc, ipx->ipx_dest.sock);
460
461 /*
462 * We need to check if there is a primary net and if
463 * this is addressed to one of the *SPECIAL* sockets because
464 * these need to be propagated to the primary net.
465 * The *SPECIAL* socket list contains: 0x452(SAP), 0x453(RIP) and
466 * 0x456(Diagnostic).
467 */
468
469 if (ipx_primary_net && intrfc != ipx_primary_net) {
470 const int dsock = ntohs(ipx->ipx_dest.sock);
471
472 if (dsock == 0x452 || dsock == 0x453 || dsock == 0x456)
473 /* The appropriate thing to do here is to dup the
474 * packet and route to the primary net interface via
475 * ipxitf_send; however, we'll cheat and just demux it
476 * here. */
477 sock2 = ipxitf_find_socket(ipx_primary_net,
478 ipx->ipx_dest.sock);
479 }
480
481 /*
482 * If there is nothing to do return. The kfree will cancel any charging.
483 */
484 rc = 0;
485 if (!sock1 && !sock2) {
486 if (!copy)
487 kfree_skb(skb);
488 goto out;
489 }
490
491 /*
492 * This next segment of code is a little awkward, but it sets it up
493 * so that the appropriate number of copies of the SKB are made and
494 * that skb1 and skb2 point to it (them) so that it (they) can be
495 * demuxed to sock1 and/or sock2. If we are unable to make enough
496 * copies, we do as much as is possible.
497 */
498
499 if (copy)
500 skb1 = skb_clone(skb, GFP_ATOMIC);
501 else
502 skb1 = skb;
503
504 rc = -ENOMEM;
505 if (!skb1)
506 goto out_put;
507
508 /* Do we need 2 SKBs? */
509 if (sock1 && sock2)
510 skb2 = skb_clone(skb1, GFP_ATOMIC);
511 else
512 skb2 = skb1;
513
514 if (sock1)
515 ipxitf_def_skb_handler(sock1, skb1);
516
517 if (!skb2)
518 goto out_put;
519
520 if (sock2)
521 ipxitf_def_skb_handler(sock2, skb2);
522
523 rc = 0;
524out_put:
525 if (sock1)
526 sock_put(sock1);
527 if (sock2)
528 sock_put(sock2);
529out:
530 return rc;
531}
532#endif /* CONFIG_IPX_INTERN */
533
534static struct sk_buff *ipxitf_adjust_skbuff(struct ipx_interface *intrfc,
535 struct sk_buff *skb)
536{
537 struct sk_buff *skb2;
538 int in_offset = (unsigned char *)ipx_hdr(skb) - skb->head;
539 int out_offset = intrfc->if_ipx_offset;
540 int len;
541
542 /* Hopefully, most cases */
543 if (in_offset >= out_offset)
544 return skb;
545
546 /* Need new SKB */
547 len = skb->len + out_offset;
548 skb2 = alloc_skb(len, GFP_ATOMIC);
549 if (skb2) {
550 skb_reserve(skb2, out_offset);
551 skb_reset_network_header(skb2);
552 skb_reset_transport_header(skb2);
553 skb_put(skb2, skb->len);
554 memcpy(ipx_hdr(skb2), ipx_hdr(skb), skb->len);
555 memcpy(skb2->cb, skb->cb, sizeof(skb->cb));
556 }
557 kfree_skb(skb);
558 return skb2;
559}
560
561/* caller must hold a reference to intrfc and the skb has to be unshared */
562int ipxitf_send(struct ipx_interface *intrfc, struct sk_buff *skb, char *node)
563{
564 struct ipxhdr *ipx = ipx_hdr(skb);
565 struct net_device *dev = intrfc->if_dev;
566 struct datalink_proto *dl = intrfc->if_dlink;
567 char dest_node[IPX_NODE_LEN];
568 int send_to_wire = 1;
569 int addr_len;
570
571 ipx->ipx_tctrl = IPX_SKB_CB(skb)->ipx_tctrl;
572 ipx->ipx_dest.net = IPX_SKB_CB(skb)->ipx_dest_net;
573 ipx->ipx_source.net = IPX_SKB_CB(skb)->ipx_source_net;
574
575 /* see if we need to include the netnum in the route list */
576 if (IPX_SKB_CB(skb)->last_hop.index >= 0) {
577 __be32 *last_hop = (__be32 *)(((u8 *) skb->data) +
578 sizeof(struct ipxhdr) +
579 IPX_SKB_CB(skb)->last_hop.index *
580 sizeof(__be32));
581 *last_hop = IPX_SKB_CB(skb)->last_hop.netnum;
582 IPX_SKB_CB(skb)->last_hop.index = -1;
583 }
584
585 /*
586 * We need to know how many skbuffs it will take to send out this
587 * packet to avoid unnecessary copies.
588 */
589
590 if (!dl || !dev || dev->flags & IFF_LOOPBACK)
591 send_to_wire = 0; /* No non looped */
592
593 /*
594 * See if this should be demuxed to sockets on this interface
595 *
596 * We want to ensure the original was eaten or that we only use
597 * up clones.
598 */
599
600 if (ipx->ipx_dest.net == intrfc->if_netnum) {
601 /*
602 * To our own node, loop and free the original.
603 * The internal net will receive on all node address.
604 */
605 if (intrfc == ipx_internal_net ||
606 !memcmp(intrfc->if_node, node, IPX_NODE_LEN)) {
607 /* Don't charge sender */
608 skb_orphan(skb);
609
610 /* Will charge receiver */
611 return ipxitf_demux_socket(intrfc, skb, 0);
612 }
613
614 /* Broadcast, loop and possibly keep to send on. */
615 if (!memcmp(ipx_broadcast_node, node, IPX_NODE_LEN)) {
616 if (!send_to_wire)
617 skb_orphan(skb);
618 ipxitf_demux_socket(intrfc, skb, send_to_wire);
619 if (!send_to_wire)
620 goto out;
621 }
622 }
623
624 /*
625 * If the originating net is not equal to our net; this is routed
626 * We are still charging the sender. Which is right - the driver
627 * free will handle this fairly.
628 */
629 if (ipx->ipx_source.net != intrfc->if_netnum) {
630 /*
631 * Unshare the buffer before modifying the count in
632 * case it's a flood or tcpdump
633 */
634 skb = skb_unshare(skb, GFP_ATOMIC);
635 if (!skb)
636 goto out;
637 if (++ipx->ipx_tctrl > ipxcfg_max_hops)
638 send_to_wire = 0;
639 }
640
641 if (!send_to_wire) {
642 kfree_skb(skb);
643 goto out;
644 }
645
646 /* Determine the appropriate hardware address */
647 addr_len = dev->addr_len;
648 if (!memcmp(ipx_broadcast_node, node, IPX_NODE_LEN))
649 memcpy(dest_node, dev->broadcast, addr_len);
650 else
651 memcpy(dest_node, &(node[IPX_NODE_LEN-addr_len]), addr_len);
652
653 /* Make any compensation for differing physical/data link size */
654 skb = ipxitf_adjust_skbuff(intrfc, skb);
655 if (!skb)
656 goto out;
657
658 /* set up data link and physical headers */
659 skb->dev = dev;
660 skb->protocol = htons(ETH_P_IPX);
661
662 /* Send it out */
663 dl->request(dl, skb, dest_node);
664out:
665 return 0;
666}
667

1415 more lines aren’t shown here.

drivers/staging/ipx/ipx_proc.c+0−303

This diff is large: its 304 lines aren’t shown here.

drivers/staging/ipx/ipx_route.c+0−293

This diff is large: its 294 lines aren’t shown here.

drivers/staging/ipx/pe2.c+0−36

This diff is large: its 37 lines aren’t shown here.

drivers/staging/ipx/sysctl_net_ipx.c+0−40

This diff is large: its 41 lines aren’t shown here.

drivers/staging/ks7010/eap_packet.h+4−72

This diff is large: its 108 lines aren’t shown here.

drivers/staging/ks7010/ks7010_sdio.c+368−264

This diff is large: its 1107 lines aren’t shown here.

drivers/staging/ks7010/ks7010_sdio.h+0−164

This diff is large: its 165 lines aren’t shown here.

drivers/staging/ks7010/ks_hostif.c+431−612

This diff is large: its 1933 lines aren’t shown here.

drivers/staging/ks7010/ks_hostif.h+220−245

This diff is large: its 736 lines aren’t shown here.

drivers/staging/ks7010/ks_wlan.h+173−105

This diff is large: its 479 lines aren’t shown here.

drivers/staging/ks7010/ks_wlan_ioctl.h+1−6

This diff is large: its 26 lines aren’t shown here.

drivers/staging/ks7010/ks_wlan_net.c+424−694

This diff is large: its 2089 lines aren’t shown here.

drivers/staging/ks7010/michael_mic.c+12−16

This diff is large: its 81 lines aren’t shown here.

drivers/staging/ks7010/michael_mic.h+4−7

This diff is large: its 27 lines aren’t shown here.

drivers/staging/lustre/Kconfig+0−3

This diff is large: its 4 lines aren’t shown here.

drivers/staging/lustre/Makefile+0−2

This diff is large: its 3 lines aren’t shown here.

drivers/staging/lustre/README.txt+0−83

This diff is large: its 84 lines aren’t shown here.

drivers/staging/lustre/TODO+0−302

This diff is large: its 303 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/curproc.h+0−85

This diff is large: its 86 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs.h+0−135

This diff is large: its 136 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_cpu.h+0−295

This diff is large: its 296 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_crypto.h+0−205

This diff is large: its 206 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_debug.h+0−167

This diff is large: its 168 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_fail.h+0−191

This diff is large: its 192 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_hash.h+0−866

This diff is large: its 867 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_prim.h+0−82

This diff is large: its 83 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_private.h+0−200

This diff is large: its 201 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_string.h+0−100

This diff is large: its 101 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/libcfs_time.h+0−79

This diff is large: its 80 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/linux/libcfs.h+0−133

This diff is large: its 134 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/linux/linux-cpu.h+0−78

This diff is large: its 79 lines aren’t shown here.

drivers/staging/lustre/include/linux/libcfs/linux/linux-time.h+0−103

This diff is large: its 104 lines aren’t shown here.

drivers/staging/lustre/include/linux/lnet/api.h+0−212

This diff is large: its 213 lines aren’t shown here.

drivers/staging/lustre/include/linux/lnet/lib-lnet.h+0−644

This diff is large: its 645 lines aren’t shown here.

drivers/staging/lustre/include/linux/lnet/lib-types.h+0−666

This diff is large: its 667 lines aren’t shown here.

drivers/staging/lustre/include/linux/lnet/socklnd.h+0−87

This diff is large: its 88 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/libcfs_debug.h+0−149

This diff is large: its 150 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/libcfs_ioctl.h+0−141

This diff is large: its 142 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/lnet-dlc.h+0−149

This diff is large: its 150 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/lnet-types.h+0−669

This diff is large: its 670 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/lnetctl.h+0−134

This diff is large: its 135 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/lnetst.h+0−556

This diff is large: its 557 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/nidstr.h+0−119

This diff is large: its 120 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lnet/socklnd.h+0−44

This diff is large: its 45 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_cfg.h+0−261

This diff is large: its 262 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_fid.h+0−293

This diff is large: its 294 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_fiemap.h+0−72

This diff is large: its 73 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_idl.h+0−2688

This diff is large: its 2689 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_ioctl.h+0−231

This diff is large: its 232 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_kernelcomm.h+0−94

This diff is large: its 95 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_ostid.h+0−236

This diff is large: its 237 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_param.h+0−94

This diff is large: its 95 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_user.h+0−1325

This diff is large: its 1326 lines aren’t shown here.

drivers/staging/lustre/include/uapi/linux/lustre/lustre_ver.h+0−27

This diff is large: its 28 lines aren’t shown here.

drivers/staging/lustre/lnet/Kconfig+0−46

This diff is large: its 47 lines aren’t shown here.

drivers/staging/lustre/lnet/Makefile+0−1

This diff is large: its 2 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/Makefile+0−1

This diff is large: its 2 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/o2iblnd/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd.c+0−2952

This diff is large: its 2953 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd.h+0−1038

This diff is large: its 1039 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd_cb.c+0−3751

This diff is large: its 3752 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/o2iblnd/o2iblnd_modparams.c+0−287

This diff is large: its 288 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/Makefile+0−6

This diff is large: its 7 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd.c+0−2918

This diff is large: its 2919 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd.h+0−705

This diff is large: its 706 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd_cb.c+0−2592

This diff is large: its 2593 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd_lib.c+0−533

This diff is large: its 534 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd_modparams.c+0−184

This diff is large: its 185 lines aren’t shown here.

drivers/staging/lustre/lnet/klnds/socklnd/socklnd_proto.c+0−810

This diff is large: its 811 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/Makefile+0−19

This diff is large: its 20 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/debug.c+0−458

This diff is large: its 459 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/fail.c+0−142

This diff is large: its 143 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/hash.c+0−2064

This diff is large: its 2065 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/libcfs_cpu.c+0−228

This diff is large: its 229 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/libcfs_lock.c+0−152

This diff is large: its 153 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/libcfs_mem.c+0−167

This diff is large: its 168 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/libcfs_string.c+0−556

This diff is large: its 557 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-cpu.c+0−1079

This diff is large: its 1080 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-crypto-adler.c+0−139

This diff is large: its 140 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-crypto.c+0−443

This diff is large: its 444 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-crypto.h+0−30

This diff is large: its 31 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-debug.c+0−145

This diff is large: its 146 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-module.c+0−197

This diff is large: its 198 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/linux/linux-tracefile.c+0−257

This diff is large: its 258 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/module.c+0−604

This diff is large: its 605 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/tracefile.c+0−1191

This diff is large: its 1192 lines aren’t shown here.

drivers/staging/lustre/lnet/libcfs/tracefile.h+0−263

This diff is large: its 264 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/Makefile+0−10

This diff is large: its 11 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/acceptor.c+0−501

This diff is large: its 502 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/api-ni.c+0−2307

This diff is large: its 2308 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/config.c+0−1234

This diff is large: its 1235 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-eq.c+0−426

This diff is large: its 427 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-md.c+0−463

This diff is large: its 464 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-me.c+0−274

This diff is large: its 275 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-move.c+0−2388

This diff is large: its 2389 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-msg.c+0−625

This diff is large: its 626 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-ptl.c+0−987

This diff is large: its 988 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lib-socket.c+0−586

This diff is large: its 587 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/lo.c+0−105

This diff is large: its 106 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/module.c+0−223

This diff is large: its 224 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/net_fault.c+0−1023

This diff is large: its 1024 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/nidstrings.c+0−1258

This diff is large: its 1259 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/peer.c+0−456

This diff is large: its 457 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/router.c+0−1800

This diff is large: its 1801 lines aren’t shown here.

drivers/staging/lustre/lnet/lnet/router_proc.c+0−909

This diff is large: its 910 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/Makefile+0−7

This diff is large: its 8 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/brw_test.c+0−526

This diff is large: its 527 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/conctl.c+0−799

This diff is large: its 800 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/conrpc.c+0−1397

This diff is large: its 1398 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/conrpc.h+0−143

This diff is large: its 144 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/console.c+0−2101

This diff is large: its 2102 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/console.h+0−244

This diff is large: its 245 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/framework.c+0−1786

This diff is large: its 1787 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/module.c+0−165

This diff is large: its 166 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/ping_test.c+0−228

This diff is large: its 229 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/rpc.c+0−1682

This diff is large: its 1683 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/rpc.h+0−295

This diff is large: its 296 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/selftest.h+0−623

This diff is large: its 624 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/timer.c+0−244

This diff is large: its 245 lines aren’t shown here.

drivers/staging/lustre/lnet/selftest/timer.h+0−50

This diff is large: its 51 lines aren’t shown here.

drivers/staging/lustre/lustre/Kconfig+0−45

This diff is large: its 46 lines aren’t shown here.

drivers/staging/lustre/lustre/Makefile+0−2

This diff is large: its 3 lines aren’t shown here.

drivers/staging/lustre/lustre/fid/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/fid/fid_internal.h+0−47

This diff is large: its 48 lines aren’t shown here.

drivers/staging/lustre/lustre/fid/fid_lib.c+0−88

This diff is large: its 89 lines aren’t shown here.

drivers/staging/lustre/lustre/fid/fid_request.c+0−440

This diff is large: its 441 lines aren’t shown here.

drivers/staging/lustre/lustre/fid/lproc_fid.c+0−226

This diff is large: its 227 lines aren’t shown here.

drivers/staging/lustre/lustre/fld/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/fld/fld_cache.c+0−517

This diff is large: its 518 lines aren’t shown here.

drivers/staging/lustre/lustre/fld/fld_internal.h+0−171

This diff is large: its 172 lines aren’t shown here.

drivers/staging/lustre/lustre/fld/fld_request.c+0−471

This diff is large: its 472 lines aren’t shown here.

drivers/staging/lustre/lustre/fld/lproc_fld.c+0−155

This diff is large: its 156 lines aren’t shown here.

drivers/staging/lustre/lustre/include/cl_object.h+0−2463

This diff is large: its 2464 lines aren’t shown here.

drivers/staging/lustre/lustre/include/interval_tree.h+0−119

This diff is large: its 120 lines aren’t shown here.

drivers/staging/lustre/lustre/include/llog_swab.h+0−67

This diff is large: its 68 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lprocfs_status.h+0−672

This diff is large: its 673 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lu_object.h+0−1335

This diff is large: its 1336 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lu_ref.h+0−178

This diff is large: its 179 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_acl.h+0−46

This diff is large: its 47 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_compat.h+0−81

This diff is large: its 82 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_debug.h+0−52

This diff is large: its 53 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_disk.h+0−153

This diff is large: its 154 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_dlm.h+0−1354

This diff is large: its 1355 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_dlm_flags.h+0−402

This diff is large: its 403 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_errno.h+0−198

This diff is large: its 199 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_export.h+0−257

This diff is large: its 258 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_fid.h+0−676

This diff is large: its 677 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_fld.h+0−138

This diff is large: its 139 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_ha.h+0−61

This diff is large: its 62 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_handles.h+0−93

This diff is large: its 94 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_import.h+0−368

This diff is large: its 369 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_intent.h+0−69

This diff is large: its 70 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_kernelcomm.h+0−56

This diff is large: its 57 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_lib.h+0−124

This diff is large: its 125 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_linkea.h+0−93

This diff is large: its 94 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_lmv.h+0−174

This diff is large: its 175 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_log.h+0−382

This diff is large: its 383 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_mdc.h+0−229

This diff is large: its 230 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_mds.h+0−63

This diff is large: its 64 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_net.h+0−2359

This diff is large: its 2360 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_nrs.h+0−718

This diff is large: its 719 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_nrs_fifo.h+0−71

This diff is large: its 72 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_obdo.h+0−55

This diff is large: its 56 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_patchless_compat.h+0−67

This diff is large: its 68 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_req_layout.h+0−307

This diff is large: its 308 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_sec.h+0−1070

This diff is large: its 1071 lines aren’t shown here.

drivers/staging/lustre/lustre/include/lustre_swab.h+0−109

This diff is large: its 110 lines aren’t shown here.

drivers/staging/lustre/lustre/include/obd.h+0−1101

This diff is large: its 1102 lines aren’t shown here.

drivers/staging/lustre/lustre/include/obd_cksum.h+0−153

This diff is large: its 154 lines aren’t shown here.

drivers/staging/lustre/lustre/include/obd_class.h+0−1607

This diff is large: its 1608 lines aren’t shown here.

drivers/staging/lustre/lustre/include/obd_support.h+0−545

This diff is large: its 546 lines aren’t shown here.

drivers/staging/lustre/lustre/include/seq_range.h+0−200

This diff is large: its 201 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/interval_tree.c+0−599

This diff is large: its 600 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/l_lock.c+0−74

This diff is large: its 75 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_extent.c+0−259

This diff is large: its 260 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_flock.c+0−495

This diff is large: its 496 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_inodebits.c+0−69

This diff is large: its 70 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_internal.h+0−342

This diff is large: its 343 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_lib.c+0−843

This diff is large: its 844 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_lock.c+0−2146

This diff is large: its 2147 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_lockd.c+0−1163

This diff is large: its 1164 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_plain.c+0−68

This diff is large: its 69 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_pool.c+0−1023

This diff is large: its 1024 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_request.c+0−2080

This diff is large: its 2081 lines aren’t shown here.

drivers/staging/lustre/lustre/ldlm/ldlm_resource.c+0−1369

This diff is large: its 1370 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/Makefile+0−11

This diff is large: its 12 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/dcache.c+0−300

This diff is large: its 301 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/dir.c+0−1706

This diff is large: its 1707 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/file.c+0−3600

This diff is large: its 3601 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/glimpse.c+0−206

This diff is large: its 207 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/lcommon_cl.c+0−293

This diff is large: its 294 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/lcommon_misc.c+0−186

This diff is large: its 187 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/llite_internal.h+0−1337

This diff is large: its 1338 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/llite_lib.c+0−2666

This diff is large: its 2667 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/llite_mmap.c+0−478

This diff is large: its 479 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/llite_nfs.c+0−375

This diff is large: its 376 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/lproc_llite.c+0−1684

This diff is large: its 1685 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/namei.c+0−1202

This diff is large: its 1203 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/range_lock.c+0−240

This diff is large: its 241 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/range_lock.h+0−83

This diff is large: its 84 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/rw.c+0−1214

This diff is large: its 1215 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/rw26.c+0−641

This diff is large: its 642 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/statahead.c+0−1577

This diff is large: its 1578 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/super25.c+0−185

This diff is large: its 186 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/symlink.c+0−159

This diff is large: its 160 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_dev.c+0−659

This diff is large: its 660 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_internal.h+0−321

This diff is large: its 322 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_io.c+0−1374

This diff is large: its 1375 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_lock.c+0−87

This diff is large: its 88 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_object.c+0−305

This diff is large: its 306 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/vvp_page.c+0−523

This diff is large: its 524 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/xattr.c+0−638

This diff is large: its 639 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/xattr_cache.c+0−523

This diff is large: its 524 lines aren’t shown here.

drivers/staging/lustre/lustre/llite/xattr_security.c+0−96

This diff is large: its 97 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/lmv_fld.c+0−82

This diff is large: its 83 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/lmv_intent.c+0−517

This diff is large: its 518 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/lmv_internal.h+0−164

This diff is large: its 165 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/lmv_obd.c+0−3131

This diff is large: its 3132 lines aren’t shown here.

drivers/staging/lustre/lustre/lmv/lproc_lmv.c+0−173

This diff is large: its 174 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/Makefile+0−9

This diff is large: its 10 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_cl_internal.h+0−641

This diff is large: its 642 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_dev.c+0−384

This diff is large: its 385 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_ea.c+0−332

This diff is large: its 333 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_internal.h+0−283

This diff is large: its 284 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_io.c+0−1023

This diff is large: its 1024 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_lock.c+0−348

This diff is large: its 349 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_merge.c+0−107

This diff is large: its 108 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_obd.c+0−1448

This diff is large: its 1449 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_object.c+0−1625

This diff is large: its 1626 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_offset.c+0−271

This diff is large: its 272 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_pack.c+0−400

This diff is large: its 401 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_page.c+0−136

This diff is large: its 137 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_pool.c+0−586

This diff is large: its 587 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lov_request.c+0−356

This diff is large: its 357 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lovsub_dev.c+0−147

This diff is large: its 148 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lovsub_lock.c+0−81

This diff is large: its 82 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lovsub_object.c+0−180

This diff is large: its 181 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lovsub_page.c+0−68

This diff is large: its 69 lines aren’t shown here.

drivers/staging/lustre/lustre/lov/lproc_lov.c+0−299

This diff is large: its 300 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/lproc_mdc.c+0−231

This diff is large: its 232 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/mdc_internal.h+0−144

This diff is large: its 145 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/mdc_lib.c+0−497

This diff is large: its 498 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/mdc_locks.c+0−1202

This diff is large: its 1203 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/mdc_reint.c+0−419

This diff is large: its 420 lines aren’t shown here.

drivers/staging/lustre/lustre/mdc/mdc_request.c+0−2754

This diff is large: its 2755 lines aren’t shown here.

drivers/staging/lustre/lustre/mgc/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/mgc/lproc_mgc.c+0−69

This diff is large: its 70 lines aren’t shown here.

drivers/staging/lustre/lustre/mgc/mgc_internal.h+0−58

This diff is large: its 59 lines aren’t shown here.

drivers/staging/lustre/lustre/mgc/mgc_request.c+0−1844

This diff is large: its 1845 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/Makefile+0−12

This diff is large: its 13 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/cl_internal.h+0−95

This diff is large: its 96 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/cl_io.c+0−1152

This diff is large: its 1153 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/cl_lock.c+0−275

This diff is large: its 276 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/cl_object.c+0−1061

This diff is large: its 1062 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/cl_page.c+0−1046

This diff is large: its 1047 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/class_obd.c+0−535

This diff is large: its 536 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/debug.c+0−96

This diff is large: its 97 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/genops.c+0−1514

This diff is large: its 1515 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/kernelcomm.c+0−238

This diff is large: its 239 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/linkea.c+0−249

This diff is large: its 250 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/linux/linux-module.c+0−531

This diff is large: its 532 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/linux/linux-sysctl.c+0−162

This diff is large: its 163 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/llog.c+0−523

This diff is large: its 524 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/llog_cat.c+0−236

This diff is large: its 237 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/llog_internal.h+0−79

This diff is large: its 80 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/llog_obd.c+0−225

This diff is large: its 226 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/llog_swab.c+0−412

This diff is large: its 413 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lprocfs_counters.c+0−133

This diff is large: its 134 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lprocfs_status.c+0−1810

This diff is large: its 1811 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lu_object.c+0−2058

This diff is large: its 2059 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lu_ref.c+0−47

This diff is large: its 48 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lustre_handles.c+0−240

This diff is large: its 241 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/lustre_peer.c+0−214

This diff is large: its 215 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/obd_config.c+0−1559

This diff is large: its 1560 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/obd_mount.c+0−1244

This diff is large: its 1245 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/obdo.c+0−181

This diff is large: its 182 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/statfs_pack.c+0−58

This diff is large: its 59 lines aren’t shown here.

drivers/staging/lustre/lustre/obdclass/uuid.c+0−47

This diff is large: its 48 lines aren’t shown here.

drivers/staging/lustre/lustre/obdecho/Makefile+0−5

This diff is large: its 6 lines aren’t shown here.

drivers/staging/lustre/lustre/obdecho/echo_client.c+0−1724

This diff is large: its 1725 lines aren’t shown here.

drivers/staging/lustre/lustre/obdecho/echo_internal.h+0−42

This diff is large: its 43 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/Makefile+0−6

This diff is large: its 7 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/lproc_osc.c+0−843

This diff is large: its 844 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_cache.c+0−3306

This diff is large: its 3307 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_cl_internal.h+0−683

This diff is large: its 684 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_dev.c+0−246

This diff is large: its 247 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_internal.h+0−236

This diff is large: its 237 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_io.c+0−918

This diff is large: its 919 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_lock.c+0−1231

This diff is large: its 1232 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_object.c+0−474

This diff is large: its 475 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_page.c+0−1094

This diff is large: its 1095 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_quota.c+0−284

This diff is large: its 285 lines aren’t shown here.

drivers/staging/lustre/lustre/osc/osc_request.c+0−2899

This diff is large: its 2900 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/Makefile+0−23

This diff is large: its 24 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/client.c+0−3269

This diff is large: its 3270 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/connection.c+0−234

This diff is large: its 235 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/errno.c+0−381

This diff is large: its 382 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/events.c+0−585

This diff is large: its 586 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/import.c+0−1676

This diff is large: its 1677 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/layout.c+0−2234

This diff is large: its 2235 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/llog_client.c+0−340

This diff is large: its 341 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/llog_net.c+0−69

This diff is large: its 70 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/lproc_ptlrpc.c+0−1332

This diff is large: its 1333 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/niobuf.c+0−770

This diff is large: its 771 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/nrs.c+0−1612

This diff is large: its 1613 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/nrs_fifo.c+0−269

This diff is large: its 270 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/pack_generic.c+0−2313

This diff is large: its 2314 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/pers.c+0−72

This diff is large: its 73 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/pinger.c+0−477

This diff is large: its 478 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/ptlrpc_internal.h+0−371

This diff is large: its 372 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/ptlrpc_module.c+0−182

This diff is large: its 183 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/ptlrpcd.c+0−912

This diff is large: its 913 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/recover.c+0−374

This diff is large: its 375 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec.c+0−2383

This diff is large: its 2384 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_bulk.c+0−572

This diff is large: its 573 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_config.c+0−850

This diff is large: its 851 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_gc.c+0−190

This diff is large: its 191 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_lproc.c+0−195

This diff is large: its 196 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_null.c+0−459

This diff is large: its 460 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/sec_plain.c+0−1023

This diff is large: its 1024 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/service.c+0−2804

This diff is large: its 2805 lines aren’t shown here.

drivers/staging/lustre/lustre/ptlrpc/wiretest.c+0−4210

This diff is large: its 4211 lines aren’t shown here.

drivers/staging/lustre/sysfs-fs-lustre+0−654

This diff is large: its 655 lines aren’t shown here.

drivers/staging/most/cdev/cdev.c+10−6

This diff is large: its 63 lines aren’t shown here.

drivers/staging/most/core.c+48−20

This diff is large: its 124 lines aren’t shown here.

drivers/staging/most/core.h+4−0

This diff is large: its 23 lines aren’t shown here.

drivers/staging/most/dim2/Kconfig+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/most/dim2/dim2.c+296−101

This diff is large: its 585 lines aren’t shown here.

drivers/staging/most/dim2/dim2.h+0−21

This diff is large: its 22 lines aren’t shown here.

drivers/staging/most/dim2/hal.c+6−3

This diff is large: its 30 lines aren’t shown here.

drivers/staging/most/dim2/reg.h+42−42

This diff is large: its 91 lines aren’t shown here.

drivers/staging/most/i2c/i2c.c+49−91

This diff is large: its 284 lines aren’t shown here.

drivers/staging/most/sound/sound.c+63−60

This diff is large: its 170 lines aren’t shown here.

drivers/staging/most/usb/usb.c+42−13

This diff is large: its 136 lines aren’t shown here.

drivers/staging/most/video/video.c+0−32

This diff is large: its 116 lines aren’t shown here.

drivers/staging/mt7621-dts/gbpc1.dts+1−2

This diff is large: its 17 lines aren’t shown here.

drivers/staging/mt7621-dts/mt7621.dtsi+15−9

This diff is large: its 57 lines aren’t shown here.

drivers/staging/mt7621-eth/ethtool.c+39−15

This diff is large: its 116 lines aren’t shown here.

drivers/staging/mt7621-eth/gsw_mt7620.h+2−2

This diff is large: its 11 lines aren’t shown here.

drivers/staging/mt7621-eth/gsw_mt7621.c+5−5

This diff is large: its 40 lines aren’t shown here.

drivers/staging/mt7621-eth/mdio.c+5−1

This diff is large: its 27 lines aren’t shown here.

drivers/staging/mt7621-eth/mtk_eth_soc.c+20−24

This diff is large: its 123 lines aren’t shown here.

drivers/staging/mt7621-eth/mtk_eth_soc.h+14−19

This diff is large: its 55 lines aren’t shown here.

drivers/staging/mt7621-eth/soc_mt7621.c+4−3

This diff is large: its 26 lines aren’t shown here.

drivers/staging/mt7621-gpio/TODO+0−2

This diff is large: its 6 lines aren’t shown here.

drivers/staging/mt7621-gpio/gpio-mt7621.c+109−91

This diff is large: its 393 lines aren’t shown here.

drivers/staging/mt7621-gpio/mediatek,mt7621-gpio.txt+68−0

This diff is large: its 69 lines aren’t shown here.

drivers/staging/mt7621-mmc/board.h+4−78

This diff is large: its 104 lines aren’t shown here.

drivers/staging/mt7621-mmc/dbg.c+179−219

This diff is large: its 483 lines aren’t shown here.

drivers/staging/mt7621-mmc/dbg.h+48−49

This diff is large: its 143 lines aren’t shown here.

drivers/staging/mt7621-mmc/mt6575_sd.h+536−551

This diff is large: its 1180 lines aren’t shown here.

drivers/staging/mt7621-mmc/sd.c+1920−2538

This diff is large: its 4941 lines aren’t shown here.

drivers/staging/mt7621-pci/pci-mt7621.c+170−311

This diff is large: its 742 lines aren’t shown here.

drivers/staging/mt7621-pinctrl/pinctrl-rt2880.c+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/staging/mt7621-spi/spi-mt7621.c+0−4

This diff is large: its 32 lines aren’t shown here.

drivers/staging/ncpfs/Kconfig+0−108

This diff is large: its 109 lines aren’t shown here.

drivers/staging/ncpfs/Makefile+0−17

This diff is large: its 18 lines aren’t shown here.

drivers/staging/ncpfs/TODO+0−4

This diff is large: its 5 lines aren’t shown here.

drivers/staging/ncpfs/dir.c+0−1220

This diff is large: its 1221 lines aren’t shown here.

drivers/staging/ncpfs/file.c+0−263

This diff is large: its 264 lines aren’t shown here.

drivers/staging/ncpfs/getopt.c+0−76

This diff is large: its 77 lines aren’t shown here.

drivers/staging/ncpfs/getopt.h+0−17

This diff is large: its 18 lines aren’t shown here.

drivers/staging/ncpfs/inode.c+0−1067

This diff is large: its 1068 lines aren’t shown here.

drivers/staging/ncpfs/ioctl.c+0−923

This diff is large: its 924 lines aren’t shown here.

drivers/staging/ncpfs/mmap.c+0−125

This diff is large: its 126 lines aren’t shown here.

drivers/staging/ncpfs/ncp_fs.h+0−101

This diff is large: its 102 lines aren’t shown here.

drivers/staging/ncpfs/ncp_fs_i.h+0−31

This diff is large: its 32 lines aren’t shown here.

drivers/staging/ncpfs/ncp_fs_sb.h+0−174

This diff is large: its 175 lines aren’t shown here.

drivers/staging/ncpfs/ncplib_kernel.c+0−1326

This diff is large: its 1327 lines aren’t shown here.

drivers/staging/ncpfs/ncplib_kernel.h+0−215

This diff is large: its 216 lines aren’t shown here.

drivers/staging/ncpfs/ncpsign_kernel.c+0−128

This diff is large: its 129 lines aren’t shown here.

drivers/staging/ncpfs/ncpsign_kernel.h+0−27

This diff is large: its 28 lines aren’t shown here.

drivers/staging/ncpfs/sock.c+0−855

This diff is large: its 856 lines aren’t shown here.

drivers/staging/ncpfs/symlink.c+0−182

This diff is large: its 183 lines aren’t shown here.

drivers/staging/nvec/nvec.c+29−52

This diff is large: its 181 lines aren’t shown here.

drivers/staging/nvec/nvec.h+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/olpc_dcon/TODO+4−0

This diff is large: its 11 lines aren’t shown here.

drivers/staging/pi433/Documentation/devicetree/pi433.txt+3−3

This diff is large: its 14 lines aren’t shown here.

drivers/staging/pi433/Documentation/pi433.txt+5−5

This diff is large: its 36 lines aren’t shown here.

drivers/staging/pi433/Kconfig+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/pi433/pi433_if.c+26−13

This diff is large: its 102 lines aren’t shown here.

drivers/staging/pi433/rf69.c+129−53

This diff is large: its 358 lines aren’t shown here.

drivers/staging/pi433/rf69.h+19−9

This diff is large: its 56 lines aren’t shown here.

drivers/staging/rtl8188eu/TODO+0−5

This diff is large: its 12 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_ap.c+36−36

This diff is large: its 286 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_cmd.c+13−13

This diff is large: its 67 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_ieee80211.c+10−10

This diff is large: its 83 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_ioctl_set.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_mlme.c+19−19

This diff is large: its 114 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_mlme_ext.c+50−50

This diff is large: its 323 lines aren’t shown here.

drivers/staging/rtl8188eu/core/rtw_wlan_util.c+17−17

This diff is large: its 117 lines aren’t shown here.

drivers/staging/rtl8188eu/hal/rtl8188e_cmd.c+8−8

This diff is large: its 42 lines aren’t shown here.

drivers/staging/rtl8188eu/include/wlan_bssdef.h+5−5

This diff is large: its 31 lines aren’t shown here.

drivers/staging/rtl8188eu/os_dep/ioctl_linux.c+6−6

This diff is large: its 48 lines aren’t shown here.

drivers/staging/rtl8188eu/os_dep/recv_linux.c+0−4

This diff is large: its 11 lines aren’t shown here.

drivers/staging/rtl8192e/dot11d.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192e/rtllib_tx.c+7−7

This diff is large: its 63 lines aren’t shown here.

drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_ccmp.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_wep.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192u/ieee80211/ieee80211_softmac.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192u/ieee80211/rtl819x_HTProc.c+204−263

This diff is large: its 926 lines aren’t shown here.

drivers/staging/rtl8192u/r8192U_core.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8192u/r8192U_dm.c+2−2

This diff is large: its 16 lines aren’t shown here.

drivers/staging/rtl8723bs/Makefile+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_ap.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_btcoex.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_cmd.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_debug.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_eeprom.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_efuse.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_ieee80211.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_io.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_ioctl_set.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_mlme.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_mlme_ext.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_odm.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_pwrctrl.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_recv.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_rf.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_security.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_sta_mgt.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_wlan_util.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/core/rtw_xmit.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalBtc8723b1Ant.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalBtc8723b1Ant.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalBtc8723b2Ant.c+2−10

This diff is large: its 27 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalBtc8723b2Ant.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalBtcOutSrc.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_BB.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_BB.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_MAC.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_MAC.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_RF.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalHWImg8723B_RF.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalPhyRf.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalPhyRf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalPhyRf_8723B.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalPhyRf_8723B.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/HalPwrSeqCmd.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/Mp_Precomp.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_btcoex.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_com.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_com_phycfg.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_intf.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_phy.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_pwr_seq.crenamed from drivers/staging/rtl8723bs/hal/Hal8723BPwrSeq.c+2−10

This diff is large: its 27 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/hal_sdio.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_AntDiv.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_AntDiv.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_CfoTracking.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_CfoTracking.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DIG.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DIG.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DynamicBBPowerSaving.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DynamicBBPowerSaving.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DynamicTxPower.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_DynamicTxPower.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_EdcaTurboCheck.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_EdcaTurboCheck.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_HWConfig.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_HWConfig.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_NoiseMonitor.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_NoiseMonitor.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_PathDiv.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_PathDiv.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_RTL8723B.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_RTL8723B.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_RegConfig8723B.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_RegConfig8723B.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_RegDefine11N.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_debug.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_debug.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_interface.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_precomp.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_reg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/odm_types.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_cmd.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_dm.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_hal_init.c+16−24

This diff is large: its 82 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_phycfg.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_rf6052.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723b_rxdesc.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723bs_recv.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/rtl8723bs_xmit.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/sdio_halinit.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/hal/sdio_ops.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/Hal8192CPhyReg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/HalPwrSeqCmd.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/HalVerDef.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/autoconf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/basic_types.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/cmd_osdep.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/drv_conf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/drv_types.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/drv_types_sdio.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/ethernet.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_btcoex.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_com.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_com_h2c.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_com_phycfg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_com_reg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_data.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_intf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_pg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_phy.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_phy_cfg.hrenamed from drivers/staging/rtl8723bs/include/Hal8723BPhyCfg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_phy_reg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_phy_reg_8723b.hrenamed from drivers/staging/rtl8723bs/include/Hal8723BPhyReg.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/hal_pwr_seq.hrenamed from drivers/staging/rtl8723bs/include/Hal8723BPwrSeq.h+0−0

File renamed without changes.

drivers/staging/rtl8723bs/include/hal_sdio.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/ieee80211.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/ioctl_cfg80211.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/mlme_osdep.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/osdep_intf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/osdep_service.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/osdep_service_linux.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/recv_osdep.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8192c_recv.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8192c_rf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_cmd.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_dm.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_hal.h+151−132

This diff is large: its 413 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_recv.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_rf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_spec.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtl8723b_xmit.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_ap.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_beamforming.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_br_ext.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_btcoex.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_byteorder.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_cmd.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_debug.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_eeprom.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_efuse.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_event.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_ht.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_io.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_ioctl.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_ioctl_set.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_mlme.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_mlme_ext.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_mp.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_odm.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_pwrctrl.h+13−22

This diff is large: its 50 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_qos.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_recv.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_rf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_security.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_version.h+1−0

This diff is large: its 4 lines aren’t shown here.

drivers/staging/rtl8723bs/include/rtw_xmit.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/sdio_hal.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/sdio_ops.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/sdio_ops_linux.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/sdio_osintf.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/sta_info.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/wifi.h+7−15

This diff is large: its 48 lines aren’t shown here.

drivers/staging/rtl8723bs/include/wlan_bssdef.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/include/xmit_osdep.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/ioctl_cfg80211.c+2−10

This diff is large: its 27 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/ioctl_linux.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/mlme_linux.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/os_intfs.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/osdep_service.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/recv_linux.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/rtw_proc.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/rtw_proc.h+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/sdio_intf.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/sdio_ops_linux.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtl8723bs/os_dep/xmit_linux.c+1−9

This diff is large: its 18 lines aren’t shown here.

drivers/staging/rtlwifi/base.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/base.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbt_precomp.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822b1ant.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822b1ant.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822b2ant.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822b2ant.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822bwifionly.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtc8822bwifionly.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtcoutsrc.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/halbtcoutsrc.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/rtl_btc.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/btcoexist/rtl_btc.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/cam.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/cam.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/core.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/core.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/debug.c+10−22

This diff is large: its 70 lines aren’t shown here.

drivers/staging/rtlwifi/debug.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/efuse.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/efuse.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_2_platform.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_cfg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_phy.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_pwr_seq.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_8822b_pwr_seq.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_pcie.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_pcie.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_sdio.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_sdio.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_usb.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_api_8822b_usb.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_func_8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_8822b/halmac_func_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_88xx_cfg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_pcie.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_pcie.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_sdio.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_sdio.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_usb.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_api_88xx_usb.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_func_88xx.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_88xx/halmac_func_88xx.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_api.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_api.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_bit2.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_bit_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_fw_info.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_fw_offload_c2h_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_fw_offload_h2c_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_h2c_extra_info_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_intf_phy_cmd.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_original_c2h_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_original_h2c_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_pcie_reg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_pwr_seq_cmd.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_reg2.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_reg_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_rx_bd_chip.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_rx_bd_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_rx_desc_chip.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_rx_desc_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_sdio_reg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_tx_bd_chip.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_tx_bd_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_tx_desc_chip.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_tx_desc_nic.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_type.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/halmac_usb_reg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/rtl_halmac.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/halmac/rtl_halmac.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/pci.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/pci.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/halphyrf_ce.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/halphyrf_ce.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/mp_precomp.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_acs.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_acs.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_adaptivity.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_adaptivity.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_adc_sampling.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_adc_sampling.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_antdiv.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_antdiv.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_beamforming.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_ccx.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_ccx.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_cfotracking.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_cfotracking.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_debug.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_debug.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dfs.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dig.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dig.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dynamic_rx_path.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dynamicbbpowersaving.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dynamicbbpowersaving.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dynamictxpower.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_dynamictxpower.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_edcaturbocheck.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_edcaturbocheck.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_features.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_hwconfig.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_hwconfig.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_interface.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_interface.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_iqk.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_kfree.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_kfree.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_noisemonitor.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_noisemonitor.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_powertracking_ce.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_powertracking_ce.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_pre_define.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_precomp.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_psd.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_psd.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_rainfo.c+3−14

This diff is large: its 39 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_rainfo.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_reg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_regdefine11ac.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_regdefine11n.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/phydm_types.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_bb.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_bb.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_mac.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_mac.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_rf.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halhwimg8822b_rf.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halphyrf_8822b.c+18−29

This diff is large: its 117 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/halphyrf_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_hal_api8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_hal_api8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_iqk_8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_iqk_8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_regconfig8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_regconfig8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_rtl8822b.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/phydm_rtl8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl8822b/version_rtl8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl_phydm.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/rtl_phydm.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/txbf/halcomtxbf.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/txbf/haltxbf8822b.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/txbf/haltxbfinterface.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/txbf/haltxbfjaguar.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/phydm/txbf/phydm_hal_txbf_api.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/ps.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/ps.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/pwrseqcmd.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rc.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rc.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/regd.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/regd.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/def.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/fw.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/fw.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/hw.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/hw.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/led.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/led.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/phy.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/phy.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/reg.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/sw.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/sw.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/trx.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/rtl8822be/trx.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/stats.c+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/stats.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/rtlwifi/wifi.h+1−12

This diff is large: its 21 lines aren’t shown here.

drivers/staging/sm750fb/TODO+4−1

This diff is large: its 13 lines aren’t shown here.

drivers/staging/speakup/buffers.c+4−0

This diff is large: its 11 lines aren’t shown here.

drivers/staging/speakup/main.c+6−0

This diff is large: its 20 lines aren’t shown here.

drivers/staging/speakup/speakup.h+2−1

This diff is large: its 10 lines aren’t shown here.

drivers/staging/speakup/speakup_dummy.c+1−0

This diff is large: its 8 lines aren’t shown here.

drivers/staging/speakup/speakup_soft.c+2−1

This diff is large: its 17 lines aren’t shown here.

drivers/staging/speakup/spk_types.h+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/speakup/varhandlers.c+1−0

This diff is large: its 8 lines aren’t shown here.

drivers/staging/unisys/visornic/visornic_main.c+7−18

This diff is large: its 46 lines aren’t shown here.

drivers/staging/vboxvideo/vbox_main.c+2−1

This diff is large: its 10 lines aren’t shown here.

drivers/staging/vboxvideo/vbox_mode.c+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/vc04_services/Kconfig+0−1

This diff is large: its 7 lines aren’t shown here.

drivers/staging/vc04_services/Makefile+1−1

This diff is large: its 7 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-audio/bcm2835-vchiq.c+38−26

This diff is large: its 90 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-audio/bcm2835.c+41−2

This diff is large: its 71 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-audio/bcm2835.h+12−0

This diff is large: its 40 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/TODO+0−11

This diff is large: its 15 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/bcm2835-camera.c+222−180

This diff is large: its 599 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/mmal-common.h+8−1

This diff is large: its 30 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/mmal-msg-port.h+1−1

This diff is large: its 9 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/mmal-parameters.h+13−0

This diff is large: its 31 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/mmal-vchiq.c+83−262

This diff is large: its 565 lines aren’t shown here.

drivers/staging/vc04_services/bcm2835-camera/mmal-vchiq.h+3−12

This diff is large: its 34 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchi/TODO+2−7

This diff is large: its 20 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchi/vchi_common.h+0−2

This diff is large: its 13 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_2835_arm.c+3−3

This diff is large: its 20 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_arm.c+51−45

This diff is large: its 266 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_core.c+36−19

This diff is large: its 165 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_core.h+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_debugfs.c+24−113

This diff is large: its 206 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_debugfs.h+2−2

This diff is large: its 14 lines aren’t shown here.

drivers/staging/vc04_services/interface/vchiq_arm/vchiq_shim.c+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/staging/vt6655/card.c+1−4

This diff is large: its 12 lines aren’t shown here.

drivers/staging/vt6655/device_main.c+123−27

This diff is large: its 296 lines aren’t shown here.

drivers/staging/wilc1000/TODO+4−8

This diff is large: its 23 lines aren’t shown here.

drivers/staging/wilc1000/coreconfigurator.c+46−94

This diff is large: its 208 lines aren’t shown here.

drivers/staging/wilc1000/coreconfigurator.h+1−36

This diff is large: its 73 lines aren’t shown here.

drivers/staging/wilc1000/host_interface.c+241−308

This diff is large: its 973 lines aren’t shown here.

drivers/staging/wilc1000/host_interface.h+2−4

This diff is large: its 34 lines aren’t shown here.

drivers/staging/wilc1000/linux_mon.c+21−69

This diff is large: its 188 lines aren’t shown here.

drivers/staging/wilc1000/linux_wlan.c+140−238

This diff is large: its 731 lines aren’t shown here.

drivers/staging/wilc1000/wilc_debugfs.c+0−2

This diff is large: its 9 lines aren’t shown here.

drivers/staging/wilc1000/wilc_sdio.c+52−57

This diff is large: its 410 lines aren’t shown here.

drivers/staging/wilc1000/wilc_spi.c+36−63

This diff is large: its 251 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wfi_cfgoperations.c+524−525

This diff is large: its 1548 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wfi_cfgoperations.h+6−12

This diff is large: its 30 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wfi_netdevice.h+19−64

This diff is large: its 150 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wlan.c+9−17

This diff is large: its 81 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wlan.h+15−22

This diff is large: its 66 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wlan_cfg.c+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/staging/wilc1000/wilc_wlan_if.h+4−12

This diff is large: its 44 lines aren’t shown here.

drivers/staging/wlan-ng/hfa384x.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/hfa384x_usb.c+3−4

This diff is large: its 28 lines aren’t shown here.

drivers/staging/wlan-ng/p80211conv.c+4−4

This diff is large: its 36 lines aren’t shown here.

drivers/staging/wlan-ng/p80211conv.h+15−11

This diff is large: its 44 lines aren’t shown here.

drivers/staging/wlan-ng/p80211hdr.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211ioctl.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211metadef.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211metastruct.h+45−45

This diff is large: its 95 lines aren’t shown here.

drivers/staging/wlan-ng/p80211mgmt.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211msg.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211netdev.c+4−4

This diff is large: its 22 lines aren’t shown here.

drivers/staging/wlan-ng/p80211netdev.h+4−4

This diff is large: its 21 lines aren’t shown here.

drivers/staging/wlan-ng/p80211req.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/p80211types.h+1−32

This diff is large: its 49 lines aren’t shown here.

drivers/staging/wlan-ng/prism2mgmt.h+1−1

This diff is large: its 6 lines aren’t shown here.

drivers/staging/wlan-ng/prism2sta.c+24−28

This diff is large: its 127 lines aren’t shown here.

fs/compat.c+1−71

This diff is large: its 99 lines aren’t shown here.

include/linux/iio/adc/ad_sigma_delta.h+17−7

This diff is large: its 59 lines aren’t shown here.

include/linux/iio/adc/stm32-dfsdm-adc.h+2−0

This diff is large: its 9 lines aren’t shown here.

include/linux/iio/common/cros_ec_sensors_core.hrenamed from drivers/iio/common/cros_ec_sensors/cros_ec_sensors_core.h+3−0

This diff is large: its 18 lines aren’t shown here.

include/linux/iio/iio.h+12−12

This diff is large: its 31 lines aren’t shown here.

include/linux/kernel.h+16−0

This diff is large: its 23 lines aren’t shown here.

include/linux/platform_data/tsl2772.h+101−0

This diff is large: its 102 lines aren’t shown here.

include/uapi/linux/ncp.h+0−202

This diff is large: its 203 lines aren’t shown here.

include/uapi/linux/ncp_fs.h+0−147

This diff is large: its 148 lines aren’t shown here.

include/uapi/linux/ncp_mount.h+0−72

This diff is large: its 73 lines aren’t shown here.

include/uapi/linux/ncp_no.h+0−20

This diff is large: its 21 lines aren’t shown here.

scripts/selinux/mdp/mdp.c+0−1

This diff is large: its 8 lines aren’t shown here.

tools/iio/iio_generic_buffer.c+8−5

This diff is large: its 44 lines aren’t shown here.

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t