History

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

Pull staging tree update from Greg Kroah-Hartman: "Here is the big staging tree update for the 3.7-rc1 merge window. There are a few patches in here that are outside of the staging area, namely HID and IIO patches, but all of them have been acked by the relevant subsystem maintainers. The IIO stuff is still coming in through this tree as it hasn't entirely moved out of the staging tree, but is almost there. Other than that, there wa a ton of work on the comedi drivers to make them more readable and the correct style. Doing that removed a lot of code, but we added a new driver to the staging tree, so we didn't end up with a net reduction this time around: 662 files changed, 51649 insertions(+), 26582 deletions(-) All of these patches have been in the linux-next tree already. Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>" * tag 'staging-3.6' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging: (1094 commits) staging: comedi: jr3_pci: fix iomem dereference staging: comedi: drivers: use comedi_fc.h cmdtest helpers Staging: winbond: usb_free_urb(NULL) is safe Staging: winbond: checkpatch cleanup Staging: winbond: Removed undesired spaces, lines and tabs Staging: winbond: Typo corrections in comments Staging: winbond: Changed c99 comments to c89 comments staging: r8712u: Do not queue cloned skb staging: comedi: ni_mio_common: always lock in ni_ai_poll() staging: comedi: s626: add FIXME comment staging: comedi: s626: don't dereference insn->data staging: comedi: s526: fix if() check in s526_gpct_winsn() staging: comedi: s626: cleanup comments in s626_initialize() staging: comedi: s626: remove clear of kzalloc'ed data staging: comedi: s626: remove 'WDInterval' from private data staging: comedi: s626: remove 'ChargeEnabled' from private data staging: comedi: s626: remove 'IsBoardRevA' comment staging: comedi: s626: #if 0 out the "SAA7146 BUG WORKAROUND" staging: comedi: s626: remove 'allocatedBuf' from private data staging: comedi: s626: add final attach message ...

Linus Torvalds committed 14 years ago

Commit def7cb82 parents 06d2fe1 e187895662 files · +51649 −26582Browse files

Unified · Split

662 files
  1. Documentation/devicetree/bindings/staging/iio/adc/mxs-lradc.txt +15 −0
  2. Documentation/devicetree/bindings/staging/imx-drm/fsl-imx-drm.txt +41 −0
  3. Documentation/hid/hid-sensor.txt +140 −0
  4. drivers/hid/Kconfig +14 −0
  5. drivers/hid/Makefile +1 −0
  6. drivers/hid/hid-core.c +5 −0
  7. drivers/hid/hid-ids.h +6 −0
  8. drivers/hid/hid-sensor-hub.c +680 −0
  9. drivers/iio/Kconfig +6 −1
  10. drivers/iio/Makefile +5 −0
  11. drivers/iio/accel/Kconfig +16 −0
  12. drivers/iio/accel/Makefile +5 −0
  13. drivers/iio/accel/hid-sensor-accel-3d.c +418 −0
  14. drivers/iio/adc/Kconfig +38 −0
  15. drivers/iio/adc/Makefile +4 −0
  16. drivers/iio/adc/ad7266.c +1 −1
  17. drivers/iio/adc/ad7476.c +149 −61
  18. drivers/iio/adc/ad7791.c +460 −0
  19. drivers/iio/adc/ad_sigma_delta.c +558 −0
  20. drivers/iio/adc/at91_adc.c +18 −59
  21. drivers/iio/adc/lp8788_adc.c +264 −0
  22. drivers/iio/common/Kconfig +5 −0
  23. drivers/iio/common/Makefile +9 −0
  24. drivers/iio/common/hid-sensors/Kconfig +26 −0
  25. drivers/iio/common/hid-sensors/Makefile +6 −0
  26. drivers/iio/common/hid-sensors/hid-sensor-attributes.c +250 −0
  27. drivers/iio/common/hid-sensors/hid-sensor-attributes.h +57 −0
  28. drivers/iio/common/hid-sensors/hid-sensor-trigger.c +103 −0
  29. drivers/iio/common/hid-sensors/hid-sensor-trigger.h +26 −0
  30. drivers/iio/dac/Kconfig +16 −4
  31. drivers/iio/dac/Makefile +1 −0
  32. drivers/iio/dac/ad5446.c +338 −112
  33. drivers/iio/dac/ad5446.h +0 −91
  34. drivers/iio/dac/ad5755.c +650 −0
  35. drivers/iio/gyro/Kconfig +16 −0
  36. drivers/iio/gyro/Makefile +5 −0
  37. drivers/iio/gyro/hid-sensor-gyro-3d.c +418 −0
  38. drivers/iio/industrialio-buffer.c +7 −8
  39. drivers/iio/industrialio-core.c +10 −3
  40. drivers/iio/inkern.c +128 −11
  41. drivers/iio/kfifo_buf.c +23 −8
  42. drivers/iio/light/Kconfig +10 −0
  43. drivers/iio/light/Makefile +1 −0
  44. drivers/iio/light/adjd_s311.c +1 −1
  45. drivers/iio/light/hid-sensor-als.c +385 −0
  46. drivers/iio/magnetometer/Kconfig +16 −0
  47. drivers/iio/magnetometer/Makefile +5 −0
  48. drivers/iio/magnetometer/hid-sensor-magn-3d.c +419 −0
  49. drivers/power/Kconfig +7 −0
  50. drivers/power/Makefile +1 −0
  51. drivers/power/generic-adc-battery.c +422 −0
  52. drivers/staging/Kconfig +8 −2
  53. drivers/staging/Makefile +4 −1
  54. drivers/staging/android/alarm-dev.c +7 −10
  55. drivers/staging/android/ashmem.c +16 −16
  56. drivers/staging/android/binder.c +3 −3
  57. drivers/staging/android/logger.c +26 −14
  58. drivers/staging/android/logger.h +17 −7
  59. drivers/staging/android/timed_gpio.c +1 −12
  60. drivers/staging/asus_oled/asus_oled.c +45 −11
  61. drivers/staging/bcm/Bcmchar.c +2 −0
  62. drivers/staging/bcm/CmHost.c +68 −82
  63. drivers/staging/bcm/CmHost.h +19 −35
  64. drivers/staging/bcm/InterfaceInit.c +13 −4
  65. drivers/staging/bcm/InterfaceInit.h +16 −17
  66. drivers/staging/bcm/Kconfig +1 −1
  67. drivers/staging/bcm/Misc.c +4 −1
  68. drivers/staging/bcm/PHSModule.c +2 −2
  69. drivers/staging/bcm/Prototypes.h +1 −1
  70. drivers/staging/bcm/Transmit.c +106 −128
  71. drivers/staging/bcm/cntrl_SignalingInterface.h +296 −408
  72. drivers/staging/bcm/hostmibs.c +1 −1
  73. drivers/staging/bcm/nvm.c +2 −2
  74. drivers/staging/bcm/target_params.h +1 −1
  75. drivers/staging/ccg/Kconfig +1 −1
  76. drivers/staging/ccg/ccg.c +5 −9
  77. drivers/staging/ced1401/Kconfig +6 −0
  78. drivers/staging/ced1401/Makefile +3 −0
  79. drivers/staging/ced1401/TODO +10 −0
  80. drivers/staging/ced1401/ced_ioc.c +1515 −0
  81. drivers/staging/ced1401/ced_ioctl.h +345 −0
  82. drivers/staging/ced1401/machine.h +127 −0
  83. drivers/staging/ced1401/usb1401.c +1637 −0
  84. drivers/staging/ced1401/usb1401.h +249 −0
  85. drivers/staging/ced1401/use1401.h +287 −0
  86. drivers/staging/ced1401/use14_ioc.h +301 −0
  87. drivers/staging/ced1401/userspace/use1401.c +3035 −0
  88. drivers/staging/comedi/Kconfig +28 −38
  89. drivers/staging/comedi/comedi.h +554 −555
  90. drivers/staging/comedi/comedi_fops.c +73 −79
  91. drivers/staging/comedi/comedidev.h +1 −1
  92. drivers/staging/comedi/drivers.c +45 −37
  93. drivers/staging/comedi/drivers/8253.h +9 −6
  94. drivers/staging/comedi/drivers/8255.c +12 −29
  95. drivers/staging/comedi/drivers/8255_pci.c +353 −0
  96. drivers/staging/comedi/drivers/Makefile +2 −4
  97. drivers/staging/comedi/drivers/acl7225b.c +3 −3
  98. drivers/staging/comedi/drivers/addi-data/addi_amcc_S5920.c +0 −195
  99. drivers/staging/comedi/drivers/addi-data/addi_amcc_S5920.h +0 −27
  100. drivers/staging/comedi/drivers/addi-data/addi_common.c +7 −7
  101. drivers/staging/comedi/drivers/addi-data/amcc_s5933_58.h +0 −453
  102. drivers/staging/comedi/drivers/addi-data/hwdrv_APCI1710.c +9 −9
  103. drivers/staging/comedi/drivers/addi-data/hwdrv_apci3120.c +15 −46
  104. drivers/staging/comedi/drivers/addi-data/hwdrv_apci3200.c +29 −52
  105. drivers/staging/comedi/drivers/addi_apci_all.c +0 −18
  106. drivers/staging/comedi/drivers/adl_pci6208.c +87 −96
  107. drivers/staging/comedi/drivers/adl_pci7230.c +0 −190
  108. drivers/staging/comedi/drivers/adl_pci7296.c +0 −183
  109. drivers/staging/comedi/drivers/adl_pci7432.c +0 −200
  110. drivers/staging/comedi/drivers/adl_pci7x3x.c +332 −0
  111. drivers/staging/comedi/drivers/adl_pci8164.c +17 −56
  112. drivers/staging/comedi/drivers/adl_pci9111.c +278 −695
  113. drivers/staging/comedi/drivers/adl_pci9118.c +410 −649
  114. drivers/staging/comedi/drivers/adq12b.c +14 −15
  115. drivers/staging/comedi/drivers/adv_pci1710.c +316 −450
  116. drivers/staging/comedi/drivers/adv_pci1723.c +58 −164
  117. drivers/staging/comedi/drivers/adv_pci_dio.c +225 −248
  118. drivers/staging/comedi/drivers/aio_aio12_8.c +137 −81
  119. drivers/staging/comedi/drivers/aio_iiro_16.c +2 −2
  120. drivers/staging/comedi/drivers/amplc_dio200.c +49 −65
  121. drivers/staging/comedi/drivers/amplc_pc236.c +53 −55
  122. drivers/staging/comedi/drivers/amplc_pc263.c +34 −20
  123. drivers/staging/comedi/drivers/amplc_pci224.c +21 −43
  124. drivers/staging/comedi/drivers/amplc_pci230.c +45 −109
  125. drivers/staging/comedi/drivers/c6xdigio.c +3 −3
  126. drivers/staging/comedi/drivers/cb_das16_cs.c +18 −38
  127. drivers/staging/comedi/drivers/cb_pcidas.c +66 −136
  128. drivers/staging/comedi/drivers/cb_pcidas64.c +41 −87
  129. drivers/staging/comedi/drivers/cb_pcidda.c +175 −266
  130. drivers/staging/comedi/drivers/cb_pcidio.c +0 −211
  131. drivers/staging/comedi/drivers/cb_pcimdas.c +119 −160
  132. drivers/staging/comedi/drivers/cb_pcimdda.c +92 −301
  133. drivers/staging/comedi/drivers/comedi_bond.c +31 −79
  134. drivers/staging/comedi/drivers/comedi_fc.h +32 −0
  135. drivers/staging/comedi/drivers/comedi_parport.c +39 −47
  136. drivers/staging/comedi/drivers/comedi_test.c +40 −68
  137. drivers/staging/comedi/drivers/contec_pci_dio.c +45 −101
  138. drivers/staging/comedi/drivers/daqboard2000.c +202 −264
  139. drivers/staging/comedi/drivers/das08.c +149 −333
  140. drivers/staging/comedi/drivers/das08.h +4 −11
  141. drivers/staging/comedi/drivers/das08_cs.c +26 −0
  142. drivers/staging/comedi/drivers/das16.c +31 −51
  143. drivers/staging/comedi/drivers/das16m1.c +18 −36
  144. drivers/staging/comedi/drivers/das1800.c +63 −82
  145. drivers/staging/comedi/drivers/das6402.c +2 −2
  146. drivers/staging/comedi/drivers/das800.c +16 −36
  147. drivers/staging/comedi/drivers/dmm32at.c +19 −38
  148. drivers/staging/comedi/drivers/dt2801.c +6 −6
  149. drivers/staging/comedi/drivers/dt2811.c +4 −4
  150. drivers/staging/comedi/drivers/dt2814.c +14 −32
  151. drivers/staging/comedi/drivers/dt2815.c +1 −1
  152. drivers/staging/comedi/drivers/dt2817.c +1 −1
  153. drivers/staging/comedi/drivers/dt282x.c +29 −74
  154. drivers/staging/comedi/drivers/dt3000.c +16 −32
  155. drivers/staging/comedi/drivers/dt9812.c +4 −4
  156. drivers/staging/comedi/drivers/dyna_pci10xx.c +36 −125
  157. drivers/staging/comedi/drivers/fl512.c +2 −2
  158. drivers/staging/comedi/drivers/gsc_hpdi.c +11 −32
  159. drivers/staging/comedi/drivers/icp_multi.c +140 −552
  160. drivers/staging/comedi/drivers/icp_multi.h +0 −297
  161. drivers/staging/comedi/drivers/ii_pci20kc.c +2 −2
  162. drivers/staging/comedi/drivers/jr3_pci.c +5 −4
  163. drivers/staging/comedi/drivers/jr3_pci.h +2 −2
  164. drivers/staging/comedi/drivers/ke_counter.c +35 −68
  165. drivers/staging/comedi/drivers/me4000.c +618 −1018
  166. drivers/staging/comedi/drivers/me4000.h +0 −409
  167. drivers/staging/comedi/drivers/me_daq.c +99 −122
  168. drivers/staging/comedi/drivers/mite.c +135 −150
  169. drivers/staging/comedi/drivers/mite.h +16 −50
  170. drivers/staging/comedi/drivers/mpc624.c +1 −1
  171. drivers/staging/comedi/drivers/mpc8260cpm.c +1 −1
  172. drivers/staging/comedi/drivers/multiq3.c +8 −6
  173. drivers/staging/comedi/drivers/ni_6527.c +61 −110
  174. drivers/staging/comedi/drivers/ni_65xx.c +63 −118
  175. drivers/staging/comedi/drivers/ni_660x.c +46 −87
  176. drivers/staging/comedi/drivers/ni_670x.c +24 −38
  177. drivers/staging/comedi/drivers/ni_at_a2150.c +12 −34
  178. drivers/staging/comedi/drivers/ni_at_ao.c +4 −4
  179. drivers/staging/comedi/drivers/ni_atmio.c +1 −1
  180. drivers/staging/comedi/drivers/ni_atmio16d.c +26 −41
  181. drivers/staging/comedi/drivers/ni_daq_700.c +164 −48
  182. drivers/staging/comedi/drivers/ni_daq_dio24.c +8 −4
  183. drivers/staging/comedi/drivers/ni_labpc.c +198 −269
  184. drivers/staging/comedi/drivers/ni_labpc_cs.c +3 −3
  185. drivers/staging/comedi/drivers/ni_mio_common.c +88 −152
  186. drivers/staging/comedi/drivers/ni_mio_cs.c +2 −2
  187. drivers/staging/comedi/drivers/ni_pcidio.c +169 −303
  188. drivers/staging/comedi/drivers/ni_pcimio.c +30 −40
  189. drivers/staging/comedi/drivers/ni_tiocmd.c +18 −43
  190. drivers/staging/comedi/drivers/pcl711.c +18 −35
  191. drivers/staging/comedi/drivers/pcl724.c +9 −6
  192. drivers/staging/comedi/drivers/pcl725.c +2 −2
  193. drivers/staging/comedi/drivers/pcl726.c +3 −3
  194. drivers/staging/comedi/drivers/pcl730.c +4 −4
  195. drivers/staging/comedi/drivers/pcl812.c +20 −37
  196. drivers/staging/comedi/drivers/pcl816.c +14 −38
  197. drivers/staging/comedi/drivers/pcl818.c +20 −39
  198. drivers/staging/comedi/drivers/pcm3724.c +17 −9
  199. drivers/staging/comedi/drivers/pcm3730.c +6 −6
  200. drivers/staging/comedi/drivers/pcm_common.c +13 −43
  201. drivers/staging/comedi/drivers/pcmad.c +1 −1
  202. drivers/staging/comedi/drivers/pcmda12.c +1 −1
  203. drivers/staging/comedi/drivers/pcmmio.c +10 −22
  204. drivers/staging/comedi/drivers/pcmuio.c +7 −7
  205. drivers/staging/comedi/drivers/poc.c +1 −1
  206. drivers/staging/comedi/drivers/quatech_daqp_cs.c +20 −43
  207. drivers/staging/comedi/drivers/rtd520.c +21 −46
  208. drivers/staging/comedi/drivers/rti800.c +5 −5
  209. drivers/staging/comedi/drivers/rti802.c +1 −1
  210. drivers/staging/comedi/drivers/s526.c +153 −449
  211. drivers/staging/comedi/drivers/s626.c +303 −452
  212. drivers/staging/comedi/drivers/s626.h +0 −1
  213. drivers/staging/comedi/drivers/serial2002.c +8 −6
  214. drivers/staging/comedi/drivers/skel.c +28 −46
  215. drivers/staging/comedi/drivers/ssv_dnp.c +2 −5
  216. drivers/staging/comedi/drivers/usbdux.c +52 −149
  217. drivers/staging/comedi/drivers/usbduxfast.c +23 −97
  218. drivers/staging/comedi/drivers/usbduxsigma.c +45 −147
  219. drivers/staging/comedi/drivers/vmk80xx.c +8 −6
  220. drivers/staging/comedi/kcomedilib/kcomedilib_main.c +13 −10
  221. drivers/staging/comedi/range.c +10 −8
  222. drivers/staging/cptm1217/clearpad_tm1217.c +1 −12
  223. drivers/staging/crystalhd/crystalhd_lnx.c +5 −1
  224. drivers/staging/csr/Makefile +0 −1
  225. drivers/staging/csr/bh.c +90 −83
  226. drivers/staging/csr/csr_formatted_io.c +0 −27
  227. drivers/staging/csr/csr_formatted_io.h +0 −25
  228. drivers/staging/csr/csr_framework_ext.c +1 −12
  229. drivers/staging/csr/csr_panic.c +0 −1
  230. drivers/staging/csr/csr_time.c +9 −18
  231. drivers/staging/csr/csr_wifi_hip_card_sdio.c +4 −4
  232. drivers/staging/csr/csr_wifi_hip_download.c +2 −0
  233. drivers/staging/csr/csr_wifi_hip_send.c +2 −7
  234. drivers/staging/csr/csr_wifi_hip_udi.c +47 −47
  235. drivers/staging/csr/csr_wifi_hip_unifi.h +0 −1
  236. drivers/staging/csr/drv.c +9 −37
  237. drivers/staging/csr/firmware.c +2 −4
  238. drivers/staging/csr/io.c +17 −36
  239. drivers/staging/csr/monitor.c +1 −6
  240. drivers/staging/csr/netdev.c +6 −624
  241. drivers/staging/csr/sdio_events.c +2 −2
  242. drivers/staging/csr/sdio_mmc.c +21 −44
  243. drivers/staging/csr/sme_blocking.c +2 −2
  244. drivers/staging/csr/sme_native.c +1 −5
  245. drivers/staging/csr/sme_sys.c +8 −14
  246. drivers/staging/csr/sme_wext.c +3 −5
  247. drivers/staging/csr/ul_int.c +1 −4
  248. drivers/staging/csr/unifi_pdu_processing.c +1 −4
  249. drivers/staging/csr/unifi_priv.h +0 −40
  250. drivers/staging/csr/unifi_wext.h +6 −21
  251. drivers/staging/csr/wext_events.c +3 −5
  252. drivers/staging/cxt1e1/linux.c +6 −6
  253. drivers/staging/cxt1e1/musycc.c +5 −5
  254. drivers/staging/et131x/et131x.c +1 −6
  255. drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c +17 −17
  256. drivers/staging/ft1000/ft1000-usb/ft1000_hw.c +7 −7
  257. drivers/staging/ft1000/ft1000-usb/ft1000_usb.h +0 −2
  258. drivers/staging/gdm72xx/gdm_qos.c +59 −59
  259. drivers/staging/gdm72xx/gdm_qos.h +29 −29
  260. drivers/staging/gdm72xx/gdm_sdio.c +11 −26
  261. drivers/staging/gdm72xx/gdm_usb.c +24 −38
  262. drivers/staging/gdm72xx/gdm_usb.h +8 −8
  263. drivers/staging/gdm72xx/gdm_wimax.c +10 −6
  264. drivers/staging/gdm72xx/usb_boot.c +100 −120
  265. drivers/staging/iio/Documentation/generic_buffer.c +10 −0
  266. drivers/staging/iio/Documentation/inkernel.txt +3 −3
  267. drivers/staging/iio/Kconfig +1 −1
  268. drivers/staging/iio/TODO +1 −1
  269. drivers/staging/iio/accel/adis16201_core.c +2 −2
  270. drivers/staging/iio/accel/adis16201_ring.c +1 −2
  271. drivers/staging/iio/accel/adis16203_core.c +2 −2
  272. drivers/staging/iio/accel/adis16203_ring.c +1 −4
  273. drivers/staging/iio/accel/adis16204_core.c +2 −2
  274. drivers/staging/iio/accel/adis16204_ring.c +1 −2
  275. drivers/staging/iio/accel/adis16209_core.c +2 −2
  276. drivers/staging/iio/accel/adis16209_ring.c +1 −2
  277. drivers/staging/iio/accel/adis16220_core.c +4 −7
  278. drivers/staging/iio/accel/adis16240_core.c +2 −2
  279. drivers/staging/iio/accel/adis16240_ring.c +1 −2
  280. drivers/staging/iio/accel/kxsd9.c +3 −3
  281. drivers/staging/iio/accel/lis3l02dq.h +7 −7
  282. drivers/staging/iio/accel/lis3l02dq_core.c +10 −16
  283. drivers/staging/iio/accel/lis3l02dq_ring.c +15 −16
  284. drivers/staging/iio/accel/sca3000.h +1 −1
  285. drivers/staging/iio/accel/sca3000_core.c +6 −8
  286. drivers/staging/iio/accel/sca3000_ring.c +1 −1
  287. drivers/staging/iio/adc/Kconfig +20 −23
  288. drivers/staging/iio/adc/Makefile +1 −4
  289. drivers/staging/iio/adc/ad7192.c +67 −456
  290. drivers/staging/iio/adc/ad7298_core.c +1 −1
  291. drivers/staging/iio/adc/ad7298_ring.c +1 −2
  292. drivers/staging/iio/adc/ad7476.h +0 −66
  293. drivers/staging/iio/adc/ad7476_ring.c +0 −64
  294. drivers/staging/iio/adc/ad7606.h +1 −1
  295. drivers/staging/iio/adc/ad7606_core.c +3 −3
  296. drivers/staging/iio/adc/ad7606_ring.c +1 −2
  297. drivers/staging/iio/adc/ad7780.c +109 −128
  298. drivers/staging/iio/adc/ad7793.c +121 −567
  299. drivers/staging/iio/adc/ad7793.h +9 −1
  300. drivers/staging/iio/adc/ad7887_core.c +1 −1
  301. drivers/staging/iio/adc/ad7887_ring.c +1 −1
  302. drivers/staging/iio/adc/ad799x_ring.c +1 −2
  303. drivers/staging/iio/adc/lpc32xx_adc.c +1 −1
  304. drivers/staging/iio/adc/max1363.h +1 −1
  305. drivers/staging/iio/adc/max1363_core.c +16 −16
  306. drivers/staging/iio/adc/max1363_ring.c +1 −1
  307. drivers/staging/iio/adc/mxs-lradc.c +590 −0
  308. drivers/staging/iio/adc/spear_adc.c +9 −18
  309. drivers/staging/iio/gyro/adis16060_core.c +2 −2
  310. drivers/staging/iio/gyro/adis16080_core.c +1 −1
  311. drivers/staging/iio/gyro/adis16130_core.c +1 −1
  312. drivers/staging/iio/gyro/adis16260_core.c +3 −9
  313. drivers/staging/iio/gyro/adis16260_ring.c +1 −2
  314. drivers/staging/iio/gyro/adxrs450_core.c +1 −1
  315. drivers/staging/iio/iio_dummy_evgen.c +1 −1
  316. drivers/staging/iio/iio_hwmon.c +7 −40
  317. drivers/staging/iio/iio_simple_dummy.c +9 −15
  318. drivers/staging/iio/iio_simple_dummy.h +4 −2
  319. drivers/staging/iio/iio_simple_dummy_buffer.c +11 −2
  320. drivers/staging/iio/impedance-analyzer/ad5933.c +2 −2
  321. drivers/staging/iio/imu/adis16400.h +1 −1
  322. drivers/staging/iio/imu/adis16400_core.c +6 −12
  323. drivers/staging/iio/imu/adis16400_ring.c +1 −1
  324. drivers/staging/iio/light/isl29018.c +15 −2
  325. drivers/staging/iio/light/tsl2563.c +1 −1
  326. drivers/staging/iio/magnetometer/hmc5843.c +1 −1
  327. drivers/staging/iio/meter/ade7753.c +4 −9
  328. drivers/staging/iio/meter/ade7754.c +3 −9
  329. drivers/staging/iio/meter/ade7758.h +1 −1
  330. drivers/staging/iio/meter/ade7758_core.c +4 −9
  331. drivers/staging/iio/meter/ade7758_ring.c +1 −2
  332. drivers/staging/iio/meter/ade7759.c +3 −8
  333. drivers/staging/iio/meter/ade7854-spi.c +1 −1
  334. drivers/staging/iio/resolver/ad2s1210.c +1 −1
  335. drivers/staging/iio/ring_hw.h +1 −1
  336. drivers/staging/iio/ring_sw.c +3 −4
  337. drivers/staging/iio/trigger/Kconfig +2 −0
  338. drivers/staging/iio/trigger/iio-trig-bfin-timer.c +88 −21
  339. drivers/staging/iio/trigger/iio-trig-bfin-timer.h +24 −0
  340. drivers/staging/iio/trigger/iio-trig-gpio.c +4 −4
  341. drivers/staging/iio/trigger/iio-trig-periodic-rtc.c +4 −4
  342. drivers/staging/iio/trigger/iio-trig-sysfs.c +16 −1
  343. drivers/staging/imx-drm/Kconfig +35 −0
  344. drivers/staging/imx-drm/Makefile +9 −0
  345. drivers/staging/imx-drm/TODO +22 −0
  346. drivers/staging/imx-drm/imx-drm-core.c +884 −0
  347. drivers/staging/imx-drm/imx-drm.h +58 −0
  348. drivers/staging/imx-drm/imx-fb.c +47 −0
  349. drivers/staging/imx-drm/imx-fbdev.c +74 −0
  350. drivers/staging/imx-drm/ipu-v3/Makefile +3 −0
  351. drivers/staging/imx-drm/ipu-v3/imx-ipu-v3.h +318 −0
  352. drivers/staging/imx-drm/ipu-v3/ipu-common.c +1143 −0
  353. drivers/staging/imx-drm/ipu-v3/ipu-dc.c +372 −0
  354. drivers/staging/imx-drm/ipu-v3/ipu-di.c +700 −0
  355. drivers/staging/imx-drm/ipu-v3/ipu-dmfc.c +408 −0
  356. drivers/staging/imx-drm/ipu-v3/ipu-dp.c +336 −0
  357. drivers/staging/imx-drm/ipu-v3/ipu-prv.h +206 −0
  358. drivers/staging/imx-drm/ipuv3-crtc.c +579 −0
  359. drivers/staging/imx-drm/parallel-display.c +261 −0
  360. drivers/staging/ipack/Kconfig +1 −0
  361. drivers/staging/ipack/TODO +2 −23
  362. drivers/staging/ipack/bridges/tpci200.c +306 −429
  363. drivers/staging/ipack/bridges/tpci200.h +27 −12
  364. drivers/staging/ipack/devices/ipoctal.c +321 −417
  365. drivers/staging/ipack/devices/scc2698.h +58 −59
  366. drivers/staging/ipack/ipack.c +350 −22
  367. drivers/staging/ipack/ipack.h +61 −27
  368. drivers/staging/ipack/ipack_ids.h +32 −0
  369. drivers/staging/keucr/smcommon.h +0 −2
  370. drivers/staging/line6/pcm.c +7 −1
  371. drivers/staging/line6/variax.c +4 −4
  372. drivers/staging/nvec/Kconfig +1 −1
  373. drivers/staging/nvec/nvec.c +13 −12
  374. drivers/staging/olpc_dcon/olpc_dcon.c +24 −29
  375. drivers/staging/olpc_dcon/olpc_dcon_xo_1.c +9 −6
  376. drivers/staging/olpc_dcon/olpc_dcon_xo_1_5.c +4 −2
  377. drivers/staging/omap-thermal/omap-bandgap.c +12 −11
  378. drivers/staging/omap-thermal/omap-thermal-common.c +36 −6
  379. drivers/staging/omap-thermal/omap4-thermal.c +27 −27
  380. drivers/staging/omap-thermal/omap5-thermal.c +19 −19
  381. drivers/staging/omapdrm/omap_crtc.c +31 −2
  382. drivers/staging/omapdrm/omap_dmm_tiler.c +43 −8
  383. drivers/staging/omapdrm/omap_dmm_tiler.h +15 −2
  384. drivers/staging/omapdrm/omap_drv.c +18 −3
  385. drivers/staging/omapdrm/omap_drv.h +31 −2
  386. drivers/staging/omapdrm/omap_fb.c +85 −14
  387. drivers/staging/omapdrm/omap_gem.c +58 −2
  388. drivers/staging/omapdrm/omap_plane.c +90 −21
  389. drivers/staging/ozwpan/ozcdev.c +7 −7
  390. drivers/staging/ozwpan/ozevent.c +3 −3
  391. drivers/staging/ozwpan/ozhcd.c +80 −24
  392. drivers/staging/ozwpan/ozmain.c +1 −1
  393. drivers/staging/ozwpan/ozpd.c +2 −9
  394. drivers/staging/ozwpan/ozpd.h +1 −0
  395. drivers/staging/ozwpan/ozproto.c +13 −0
  396. drivers/staging/ozwpan/ozproto.h +7 −1
  397. drivers/staging/ozwpan/ozprotocol.h +5 −1
  398. drivers/staging/panel/panel.c +26 −26
  399. drivers/staging/ramster/Kconfig +21 −4
  400. drivers/staging/ramster/Makefile +6 −1
  401. drivers/staging/ramster/TODO +0 −13
  402. drivers/staging/ramster/cluster/Makefile +0 −3
  403. drivers/staging/ramster/ramster.h +27 −86
  404. drivers/staging/ramster/ramster/heartbeat.c +2 −4
  405. drivers/staging/ramster/ramster/heartbeat.h +0 −0
  406. drivers/staging/ramster/ramster/masklog.c +0 −0
  407. drivers/staging/ramster/ramster/masklog.h +0 −0
  408. drivers/staging/ramster/ramster/nodemanager.c +9 −6
  409. drivers/staging/ramster/ramster/nodemanager.h +0 −0
  410. drivers/staging/ramster/ramster/r2net.c +46 −33
  411. drivers/staging/ramster/ramster/ramster.c +985 −0
  412. drivers/staging/ramster/ramster/ramster.h +161 −0
  413. drivers/staging/ramster/ramster/ramster_nodemanager.h +0 −0
  414. drivers/staging/ramster/ramster/tcp.c +25 −28
  415. drivers/staging/ramster/ramster/tcp.h +0 −0
  416. drivers/staging/ramster/ramster/tcp_internal.h +0 −0
  417. drivers/staging/ramster/tmem.c +178 −135
  418. drivers/staging/ramster/tmem.h +62 −47
  419. drivers/staging/ramster/xvmalloc.c +0 −509
  420. drivers/staging/ramster/xvmalloc.h +0 −30
  421. drivers/staging/ramster/xvmalloc_int.h +0 −95
  422. drivers/staging/ramster/zbud.c +1060 −0
  423. drivers/staging/ramster/zbud.h +33 −0
  424. drivers/staging/ramster/zcache-main.c +1033 −2533
  425. drivers/staging/ramster/zcache.h +43 −12
  426. drivers/staging/rtl8187se/ieee80211/ieee80211.h +1 −1
  427. drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c +3 −10
  428. drivers/staging/rtl8187se/ieee80211/ieee80211_softmac_wx.c +3 −2
  429. drivers/staging/rtl8187se/r8180_core.c +2 −2
  430. drivers/staging/rtl8187se/r8180_hw.h +7 −2
  431. drivers/staging/rtl8187se/r8185b_init.c +1 −1
  432. drivers/staging/rtl8192e/rtl8192e/r8192E_firmware.c +5 −4
  433. drivers/staging/rtl8192e/rtl8192e/r8192E_firmware.h +4 −0
  434. drivers/staging/rtl8192e/rtl8192e/rtl_core.c +4 −2
  435. drivers/staging/rtl8192e/rtl8192e/rtl_dm.c +1 −1
  436. drivers/staging/rtl8192e/rtllib.h +4 −4
  437. drivers/staging/rtl8192e/rtllib_softmac.c +8 −16
  438. drivers/staging/rtl8192e/rtllib_softmac_wx.c +4 −3
  439. drivers/staging/rtl8192u/ieee80211/ieee80211.h +2 −2
  440. drivers/staging/rtl8192u/ieee80211/ieee80211_softmac.c +7 −13
  441. drivers/staging/rtl8192u/ieee80211/ieee80211_softmac_wx.c +3 −2
  442. drivers/staging/rtl8192u/ieee80211/rtl819x_BAProc.c +1 −1
  443. drivers/staging/rtl8192u/ieee80211/rtl819x_HT.h +2 −2
  444. drivers/staging/rtl8192u/ieee80211/rtl819x_HTProc.c +1 −1
  445. drivers/staging/rtl8192u/r8192U_core.c +8 −19
  446. drivers/staging/rtl8192u/r819xU_HTType.h +1 −1
  447. drivers/staging/rtl8192u/r819xU_phyreg.h +1 −1
  448. drivers/staging/rtl8712/drv_types.h +0 −9
  449. drivers/staging/rtl8712/ethernet.h +0 −8
  450. drivers/staging/rtl8712/os_intfs.c +1 −1
  451. drivers/staging/rtl8712/rtl8712_recv.c +8 −1
  452. drivers/staging/rtl8712/rtl8712_recv.h +1 −1
  453. drivers/staging/rtl8712/rtl8712_xmit.c +1 −1
  454. drivers/staging/rtl8712/rtl871x_ioctl_linux.c +1 −3
  455. drivers/staging/rtl8712/rtl871x_ioctl_set.c +1 −4
  456. drivers/staging/rtl8712/rtl871x_mlme.c +3 −2
  457. drivers/staging/rtl8712/rtl871x_pwrctrl.h +0 −20
  458. drivers/staging/rtl8712/rtl871x_recv.c +5 −4
  459. drivers/staging/rtl8712/rtl871x_security.c +4 −4
  460. drivers/staging/rtl8712/usb_intf.c +0 −1
  461. drivers/staging/rtl8712/usb_osintf.h +0 −3
  462. drivers/staging/rtl8712/usb_vendor_req.h +0 −58
  463. drivers/staging/rts5139/rts51x_fop.c +1 −1
  464. drivers/staging/rts5139/trace.h +3 −29
  465. drivers/staging/rts_pstor/ms.c +340 −532
  466. drivers/staging/rts_pstor/rtsx.c +54 −58
  467. drivers/staging/rts_pstor/rtsx_card.c +81 −105
  468. drivers/staging/rts_pstor/rtsx_chip.c +246 −317
  469. drivers/staging/rts_pstor/rtsx_scsi.c +169 −236
  470. drivers/staging/rts_pstor/rtsx_transport.c +45 −55
  471. drivers/staging/rts_pstor/sd.c +415 −640
  472. drivers/staging/rts_pstor/trace.h +3 −27
  473. drivers/staging/sbe-2t3e3/2t3e3.h +0 −1
  474. drivers/staging/sbe-2t3e3/dc.c +6 −4
  475. drivers/staging/sbe-2t3e3/module.c +11 −4
  476. drivers/staging/sbe-2t3e3/netdev.c +4 −4
  477. drivers/staging/sep/sep_main.c +1 −1
  478. drivers/staging/serqt_usb2/serqt_usb2.c +3 −8
  479. drivers/staging/silicom/Kconfig +46 −0
  480. drivers/staging/silicom/Makefile +9 −0
  481. drivers/staging/silicom/README +14 −0
  482. drivers/staging/silicom/TODO +8 −0
  483. drivers/staging/silicom/bits.h +56 −0
  484. drivers/staging/silicom/bp_ioctl.h +140 −0
  485. drivers/staging/silicom/bp_mod.c +8931 −0
  486. drivers/staging/silicom/bp_mod.h +704 −0
  487. drivers/staging/silicom/bp_proc.c +1350 −0
  488. drivers/staging/silicom/bypass.h +202 −0
  489. drivers/staging/silicom/bypasslib/Makefile +6 −0
  490. drivers/staging/silicom/bypasslib/bp_ioctl.h +198 −0
  491. drivers/staging/silicom/bypasslib/bplibk.h +47 −0
  492. drivers/staging/silicom/bypasslib/bypass.c +529 −0
  493. drivers/staging/silicom/bypasslib/libbp_sd.h +509 −0
  494. drivers/staging/silicom/libbp_sd.h +550 −0
  495. drivers/staging/slicoss/slicoss.c +14 −26
  496. drivers/staging/sm7xxfb/sm7xx.h +1 −1
  497. drivers/staging/sm7xxfb/sm7xxfb.c +49 −70
  498. drivers/staging/speakup/i18n.c +1 −0
  499. drivers/staging/speakup/speakup_soft.c +5 −10
  500. drivers/staging/telephony/ixj.c +2 −2
  501. drivers/staging/tidspbridge/Documentation/error-codes +1 −1
  502. drivers/staging/tidspbridge/core/_tiomap.h +1 −1
  503. drivers/staging/tidspbridge/core/chnl_sm.c +5 −4
  504. drivers/staging/tidspbridge/core/dsp-clock.c +2 −0
  505. drivers/staging/tidspbridge/core/io_sm.c +5 −5
  506. drivers/staging/tidspbridge/core/sync.c +1 −1
  507. drivers/staging/tidspbridge/core/tiomap3430.c +4 −4
  508. drivers/staging/tidspbridge/core/tiomap3430_pwr.c +1 −1
  509. drivers/staging/tidspbridge/core/wdt.c +4 −3
  510. drivers/staging/tidspbridge/dynload/tramp.c +4 −4
  511. drivers/staging/tidspbridge/gen/uuidutil.c +0 −21
  512. drivers/staging/tidspbridge/hw/hw_mmu.c +3 −3
  513. drivers/staging/tidspbridge/include/dspbridge/dspioctl.h +1 −1
  514. drivers/staging/tidspbridge/include/dspbridge/mbx_sh.h +1 −1
  515. drivers/staging/tidspbridge/include/dspbridge/node.h +1 −1
  516. drivers/staging/tidspbridge/include/dspbridge/ntfy.h +1 −1
  517. drivers/staging/tidspbridge/include/dspbridge/proc.h +1 −1
  518. drivers/staging/tidspbridge/include/dspbridge/strm.h +1 −1
  519. drivers/staging/tidspbridge/include/dspbridge/sync.h +2 −2
  520. drivers/staging/tidspbridge/include/dspbridge/uuidutil.h +0 −20
  521. drivers/staging/tidspbridge/rmgr/dbdcd.c +23 −6
  522. drivers/staging/tidspbridge/rmgr/drv_interface.c +1 −13
  523. drivers/staging/tidspbridge/rmgr/dspdrv.c +2 −2
  524. drivers/staging/tidspbridge/rmgr/mgr.c +2 −2
  525. drivers/staging/tidspbridge/rmgr/nldr.c +1 −1
  526. drivers/staging/tidspbridge/rmgr/node.c +2 −3
  527. drivers/staging/tidspbridge/rmgr/proc.c +1 −1
  528. drivers/staging/usbip/Kconfig +2 −2
  529. drivers/staging/usbip/stub_dev.c +6 −2
  530. drivers/staging/usbip/stub_rx.c +1 −1
  531. drivers/staging/usbip/usbip_common.c +4 −0
  532. drivers/staging/usbip/userspace/configure.ac +6 −6
  533. drivers/staging/usbip/userspace/doc/usbip.8 +42 −24
  534. drivers/staging/usbip/userspace/doc/usbip_bind_driver.8 +0 −42
  535. drivers/staging/usbip/userspace/doc/usbipd.8 +10 −6
  536. drivers/staging/usbip/vhci_hcd.c +22 −9
  537. drivers/staging/vme/devices/vme_pio2_core.c +5 −5
  538. drivers/staging/vme/devices/vme_user.c +5 −5
  539. drivers/staging/vt6655/80211mgr.h +1 −1
  540. drivers/staging/vt6655/baseband.c +86 −86
  541. drivers/staging/vt6655/baseband.h +5 −5
  542. drivers/staging/vt6655/bssdb.c +2 −2
  543. drivers/staging/vt6655/card.c +51 −50
  544. drivers/staging/vt6655/datarate.c +1 −1
  545. drivers/staging/vt6655/device.h +2 −2
  546. drivers/staging/vt6655/device_main.c +48 −56
  547. drivers/staging/vt6655/dpc.c +1 −1
  548. drivers/staging/vt6655/hostap.c +2 −6
  549. drivers/staging/vt6655/ioctl.c +3 −6
  550. drivers/staging/vt6655/iwctl.c +3 −3
  551. drivers/staging/vt6655/key.c +1 −1
  552. drivers/staging/vt6655/mac.c +6 −6
  553. drivers/staging/vt6655/mac.h +1 −1
  554. drivers/staging/vt6655/mib.c +1 −1
  555. drivers/staging/vt6655/power.c +1 −1
  556. drivers/staging/vt6655/rf.c +41 −41
  557. drivers/staging/vt6655/rf.h +1 −1
  558. drivers/staging/vt6655/rxtx.c +21 −21
  559. drivers/staging/vt6655/tcrc.c +1 −1
  560. drivers/staging/vt6655/tcrc.h +1 −1
  561. drivers/staging/vt6655/tether.c +2 −2
  562. drivers/staging/vt6655/tkip.c +1 −1
  563. drivers/staging/vt6655/vntwifi.c +1 −1
  564. drivers/staging/vt6655/wcmd.c +3 −3
  565. drivers/staging/vt6655/wmgr.c +28 −28
  566. drivers/staging/vt6655/wmgr.h +2 −2
  567. drivers/staging/vt6655/wpa.c +1 −1
  568. drivers/staging/vt6655/wpa2.c +4 −4
  569. drivers/staging/vt6655/wpactl.c +3 −3
  570. drivers/staging/vt6655/wroute.c +1 −1
  571. drivers/staging/vt6656/80211mgr.h +2 −2
  572. drivers/staging/vt6656/baseband.c +3 −3
  573. drivers/staging/vt6656/baseband.h +1 −1
  574. drivers/staging/vt6656/bssdb.c +9 −9
  575. drivers/staging/vt6656/card.c +19 −19
  576. drivers/staging/vt6656/device.h +1 −1
  577. drivers/staging/vt6656/dpc.c +1 −1
  578. drivers/staging/vt6656/hostap.c +13 −17
  579. drivers/staging/vt6656/int.c +1 −1
  580. drivers/staging/vt6656/ioctl.c +4 −7
  581. drivers/staging/vt6656/iwctl.c +1 −1
  582. drivers/staging/vt6656/key.c +2 −2
  583. drivers/staging/vt6656/main_usb.c +10 −10
  584. drivers/staging/vt6656/power.c +1 −1
  585. drivers/staging/vt6656/rf.c +29 −29
  586. drivers/staging/vt6656/rf.h +1 −1
  587. drivers/staging/vt6656/rxtx.c +26 −26
  588. drivers/staging/vt6656/tcrc.c +1 −1
  589. drivers/staging/vt6656/tcrc.h +1 −1
  590. drivers/staging/vt6656/tether.c +2 −2
  591. drivers/staging/vt6656/tkip.c +1 −1
  592. drivers/staging/vt6656/wcmd.c +4 −4
  593. drivers/staging/vt6656/wctl.c +1 −1
  594. drivers/staging/vt6656/wmgr.c +13 −13
  595. drivers/staging/vt6656/wpa.c +1 −1
  596. drivers/staging/vt6656/wpa2.c +3 −3
  597. drivers/staging/vt6656/wpactl.c +3 −3
  598. drivers/staging/winbond/Kconfig +1 −1
  599. drivers/staging/winbond/localpara.h +2 −2
  600. drivers/staging/winbond/mds.c +1 −1
  601. drivers/staging/winbond/mto.c +1 −1
  602. drivers/staging/winbond/phy_calibration.c +7 −7
  603. drivers/staging/winbond/reg.c +1 −1
  604. drivers/staging/winbond/sme_api.h +5 −6
  605. drivers/staging/winbond/wb35reg.c +2 −2
  606. drivers/staging/winbond/wb35tx.c +74 −80
  607. drivers/staging/winbond/wb35tx_s.h +19 −27
  608. drivers/staging/wlags49_h2/README.ubuntu +6 −6
  609. drivers/staging/wlags49_h2/TODO +5 −5
  610. drivers/staging/wlags49_h2/hcf.c +10 −10
  611. drivers/staging/wlags49_h2/hcfcfg.h +1 −1
  612. drivers/staging/wlags49_h2/hcfdef.h +3 −3
  613. drivers/staging/wlags49_h2/mdd.h +4 −4
  614. drivers/staging/wlags49_h2/sta_h2.c +1 −1
  615. drivers/staging/wlags49_h2/sta_h25.c +1 −1
  616. drivers/staging/wlags49_h2/wl_enc.h +1 −1
  617. drivers/staging/wlags49_h2/wl_if.h +1 −1
  618. drivers/staging/wlags49_h2/wl_internal.h +2 −2
  619. drivers/staging/wlags49_h2/wl_main.c +9 −9
  620. drivers/staging/wlags49_h2/wl_netdev.c +19 −40
  621. drivers/staging/wlags49_h2/wl_pci.c +4 −4
  622. drivers/staging/wlags49_h2/wl_priv.c +1 −1
  623. drivers/staging/wlags49_h2/wl_profile.c +1 −1
  624. drivers/staging/wlags49_h2/wl_version.h +1 −1
  625. drivers/staging/wlags49_h2/wl_wext.c +14 −13
  626. drivers/staging/wlags49_h25/Kconfig +1 −1
  627. drivers/staging/wlags49_h25/TODO +4 −4
  628. drivers/staging/wlan-ng/cfg80211.c +7 −4
  629. drivers/staging/wlan-ng/hfa384x_usb.c +11 −26
  630. drivers/staging/wlan-ng/p80211conv.c +3 −6
  631. drivers/staging/wlan-ng/p80211netdev.c +4 −17
  632. drivers/staging/wlan-ng/p80211netdev.h +1 −1
  633. drivers/staging/wlan-ng/p80211req.c +69 −83
  634. drivers/staging/wlan-ng/p80211types.h +1 −1
  635. drivers/staging/wlan-ng/p80211wep.c +6 −12
  636. drivers/staging/wlan-ng/prism2fw.c +28 −28
  637. drivers/staging/wlan-ng/prism2sta.c +13 −40
  638. drivers/staging/xgifb/XGI_main_26.c +25 −20
  639. drivers/staging/xgifb/vb_def.h +0 −21
  640. drivers/staging/xgifb/vb_init.c +1 −4
  641. drivers/staging/xgifb/vb_setmode.c +170 −431
  642. drivers/staging/xgifb/vb_struct.h +6 −43
  643. drivers/staging/xgifb/vb_table.h +46 −148
  644. drivers/staging/zcache/tmem.c +1 −1
  645. drivers/staging/zsmalloc/zsmalloc-main.c +273 −49
  646. drivers/staging/zsmalloc/zsmalloc_int.h +0 −155
  647. include/linux/hid-sensor-hub.h +160 −0
  648. include/linux/hid-sensor-ids.h +112 −0
  649. include/linux/iio/adc/ad_sigma_delta.h +173 −0
  650. include/linux/iio/buffer.h +2 −4
  651. include/linux/iio/consumer.h +41 −3
  652. include/linux/iio/iio.h +58 −7
  653. include/linux/iio/kfifo_buf.h +3 −0
  654. include/linux/iio/machine.h +5 −0
  655. include/linux/iio/trigger.h +7 −6
  656. include/linux/iio/trigger_consumer.h +11 −0
  657. include/linux/iio/types.h +1 −0
  658. include/linux/mod_devicetable.h +8 −0
  659. include/linux/platform_data/ad5755.h +103 −0
  660. include/linux/platform_data/ad7791.h +17 −0
  661. include/linux/power/generic-adc-battery.h +29 −0
  662. scripts/mod/file2alias.c +15 −0
Documentation/devicetree/bindings/staging/iio/adc/mxs-lradc.txt+15−0
@@ -0,0 +1,15 @@
1+* Freescale i.MX28 LRADC device driver
2+
3+Required properties:
4+- compatible: Should be "fsl,imx28-lradc"
5+- reg: Address and length of the register set for the device
6+- interrupts: Should contain the LRADC interrupts
7+
8+Examples:
9+
10+ lradc@80050000 {
11+ compatible = "fsl,imx28-lradc";
12+ reg = <0x80050000 0x2000>;
13+ interrupts = <10 14 15 16 17 18 19
14+ 20 21 22 23 24 25>;
15+ };
Documentation/devicetree/bindings/staging/imx-drm/fsl-imx-drm.txt+41−0
@@ -0,0 +1,41 @@
1+Freescale i.MX IPUv3
2+====================
3+
4+Required properties:
5+- compatible: Should be "fsl,<chip>-ipu"
6+- reg: should be register base and length as documented in the
7+ datasheet
8+- interrupts: Should contain sync interrupt and error interrupt,
9+ in this order.
10+- #crtc-cells: 1, See below
11+
12+example:
13+
14+ipu: ipu@18000000 {
15+ #crtc-cells = <1>;
16+ compatible = "fsl,imx53-ipu";
17+ reg = <0x18000000 0x080000000>;
18+ interrupts = <11 10>;
19+};
20+
21+Parallel display support
22+========================
23+
24+Required properties:
25+- compatible: Should be "fsl,imx-parallel-display"
26+- crtc: the crtc this display is connected to, see below
27+Optional properties:
28+- interface_pix_fmt: How this display is connected to the
29+ crtc. Currently supported types: "rgb24", "rgb565"
30+- edid: verbatim EDID data block describing attached display.
31+- ddc: phandle describing the i2c bus handling the display data
32+ channel
33+
34+example:
35+
36+display@di0 {
37+ compatible = "fsl,imx-parallel-display";
38+ edid = [edid-data];
39+ crtc = <&ipu 0>;
40+ interface-pix-fmt = "rgb24";
41+};
Documentation/hid/hid-sensor.txt+140−0
@@ -0,0 +1,140 @@
1+
2+HID Sensors Framework
3+======================
4+HID sensor framework provides necessary interfaces to implement sensor drivers,
5+which are connected to a sensor hub. The sensor hub is a HID device and it provides
6+a report descriptor conforming to HID 1.12 sensor usage tables.
7+
8+Description from the HID 1.12 "HID Sensor Usages" specification:
9+"Standardization of HID usages for sensors would allow (but not require) sensor
10+hardware vendors to provide a consistent Plug And Play interface at the USB boundary,
11+thereby enabling some operating systems to incorporate common device drivers that
12+could be reused between vendors, alleviating any need for the vendors to provide
13+the drivers themselves."
14+
15+This specification describes many usage IDs, which describe the type of sensor
16+and also the individual data fields. Each sensor can have variable number of
17+data fields. The length and order is specified in the report descriptor. For
18+example a part of report descriptor can look like:
19+
20+ INPUT(1)[INPUT]
21+ ..
22+ Field(2)
23+ Physical(0020.0073)
24+ Usage(1)
25+ 0020.045f
26+ Logical Minimum(-32767)
27+ Logical Maximum(32767)
28+ Report Size(8)
29+ Report Count(1)
30+ Report Offset(16)
31+ Flags(Variable Absolute)
32+..
33+..
34+
35+The report is indicating "sensor page (0x20)" contains an accelerometer-3D (0x73).
36+This accelerometer-3D has some fields. Here for example field 2 is motion intensity
37+(0x045f) with a logical minimum value of -32767 and logical maximum of 32767. The
38+order of fields and length of each field is important as the input event raw
39+data will use this format.
40+
41+
42+Implementation
43+=================
44+
45+This specification defines many different types of sensors with different sets of
46+data fields. It is difficult to have a common input event to user space applications,
47+for different sensors. For example an accelerometer can send X,Y and Z data, whereas
48+an ambient light sensor can send illumination data.
49+So the implementation has two parts:
50+- Core hid driver
51+- Individual sensor processing part (sensor drivers)
52+
53+Core driver
54+-----------
55+The core driver registers (hid-sensor-hub) registers as a HID driver. It parses
56+report descriptors and identifies all the sensors present. It adds an MFD device
57+with name HID-SENSOR-xxxx (where xxxx is usage id from the specification).
58+For example
59+HID-SENSOR-200073 is registered for an Accelerometer 3D driver.
60+So if any driver with this name is inserted, then the probe routine for that
61+function will be called. So an accelerometer processing driver can register
62+with this name and will be probed if there is an accelerometer-3D detected.
63+
64+The core driver provides a set of APIs which can be used by the processing
65+drivers to register and get events for that usage id. Also it provides parsing
66+functions, which get and set each input/feature/output report.
67+
68+Individual sensor processing part (sensor drivers)
69+-----------
70+The processing driver will use an interface provided by the core driver to parse
71+the report and get the indexes of the fields and also can get events. This driver
72+can use IIO interface to use the standard ABI defined for a type of sensor.
73+
74+
75+Core driver Interface
76+=====================
77+
78+Callback structure:
79+Each processing driver can use this structure to set some callbacks.
80+ int (*suspend)(..): Callback when HID suspend is received
81+ int (*resume)(..): Callback when HID resume is received
82+ int (*capture_sample)(..): Capture a sample for one of its data fields
83+ int (*send_event)(..): One complete event is received which can have
84+ multiple data fields.
85+
86+Registration functions:
87+int sensor_hub_register_callback(struct hid_sensor_hub_device *hsdev,
88+ u32 usage_id,
89+ struct hid_sensor_hub_callbacks *usage_callback):
90+
91+Registers callbacks for an usage id. The callback functions are not allowed
92+to sleep.
93+
94+
95+int sensor_hub_remove_callback(struct hid_sensor_hub_device *hsdev,
96+ u32 usage_id):
97+
98+Removes callbacks for an usage id.
99+
100+
101+Parsing function:
102+int sensor_hub_input_get_attribute_info(struct hid_sensor_hub_device *hsdev,
103+ u8 type,
104+ u32 usage_id, u32 attr_usage_id,
105+ struct hid_sensor_hub_attribute_info *info);
106+
107+A processing driver can look for some field of interest and check if it exists
108+in a report descriptor. If it exists it will store necessary information
109+so that fields can be set or get individually.
110+These indexes avoid searching every time and getting field index to get or set.
111+
112+
113+Set Feature report
114+int sensor_hub_set_feature(struct hid_sensor_hub_device *hsdev, u32 report_id,
115+ u32 field_index, s32 value);
116+
117+This interface is used to set a value for a field in feature report. For example
118+if there is a field report_interval, which is parsed by a call to
119+sensor_hub_input_get_attribute_info before, then it can directly set that individual
120+field.
121+
122+
123+int sensor_hub_get_feature(struct hid_sensor_hub_device *hsdev, u32 report_id,
124+ u32 field_index, s32 *value);
125+
126+This interface is used to get a value for a field in input report. For example
127+if there is a field report_interval, which is parsed by a call to
128+sensor_hub_input_get_attribute_info before, then it can directly get that individual
129+field value.
130+
131+
132+int sensor_hub_input_attr_get_raw_value(struct hid_sensor_hub_device *hsdev,
133+ u32 usage_id,
134+ u32 attr_usage_id, u32 report_id);
135+
136+This is used to get a particular field value through input reports. For example
137+accelerometer wants to poll X axis value, then it can call this function with
138+the usage id of X axis. HID sensors can provide events, so this is not necessary
139+to poll for any field. If there is some new sample, the core driver will call
140+registered callback function to process the sample.
drivers/hid/Kconfig+14−0
@@ -708,6 +708,20 @@ config HID_ZYDACRON · 707 unmodified lines
708708 ---help---
709709 Support for Zydacron remote control.
710710
711+config HID_SENSOR_HUB
712+ tristate "HID Sensors framework support"
713+ depends on USB_HID
714+ select MFD_CORE
715+ default n
716+ -- help---
717+ Support for HID Sensor framework. This creates a MFD instance
718+ for a sensor hub and identifies all the sensors connected to it.
719+ Each sensor is registered as a MFD cell, so that sensor specific
720+ processing can be done in a separate driver. Each sensor
721+ drivers can use the service provided by this driver to register
722+ for events and handle data streams. Each sensor driver can format
723+ data and present to user mode using input or IIO interface.
724+
711725 endmenu
712726
713727 endif # HID
drivers/hid/Makefile+1−0
@@ -112,6 +112,7 @@ obj-$(CONFIG_HID_ZYDACRON) += hid-zydacron.o · 111 unmodified lines
112112 obj-$(CONFIG_HID_WACOM) += hid-wacom.o
113113 obj-$(CONFIG_HID_WALTOP) += hid-waltop.o
114114 obj-$(CONFIG_HID_WIIMOTE) += hid-wiimote.o
115+obj-$(CONFIG_HID_SENSOR_HUB) += hid-sensor-hub.o
115116
116117 obj-$(CONFIG_USB_HID) += usbhid/
117118 obj-$(CONFIG_USB_MOUSE) += usbhid/
drivers/hid/hid-core.c+5−0
@@ -1568,6 +1568,10 @@ static const struct hid_device_id hid_have_special_driver[] = { · 1567 unmodified lines
15681568 { HID_USB_DEVICE(USB_VENDOR_ID_GYRATION, USB_DEVICE_ID_GYRATION_REMOTE_3) },
15691569 { HID_USB_DEVICE(USB_VENDOR_ID_HOLTEK, USB_DEVICE_ID_HOLTEK_ON_LINE_GRIP) },
15701570 { HID_USB_DEVICE(USB_VENDOR_ID_HOLTEK_ALT, USB_DEVICE_ID_HOLTEK_ALT_KEYBOARD) },
1571+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8086, USB_DEVICE_ID_SENSOR_HUB_1020) },
1572+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8086, USB_DEVICE_ID_SENSOR_HUB_09FA) },
1573+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8087, USB_DEVICE_ID_SENSOR_HUB_1020) },
1574+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8087, USB_DEVICE_ID_SENSOR_HUB_09FA) },
15711575 { HID_USB_DEVICE(USB_VENDOR_ID_KENSINGTON, USB_DEVICE_ID_KS_SLIMBLADE) },
15721576 { HID_USB_DEVICE(USB_VENDOR_ID_KEYTOUCH, USB_DEVICE_ID_KEYTOUCH_IEC) },
15731577 { HID_USB_DEVICE(USB_VENDOR_ID_KYE, USB_DEVICE_ID_KYE_ERGO_525V) },
@@ -1665,6 +1669,7 @@ static const struct hid_device_id hid_have_special_driver[] = { · 91 unmodified lines
16651669 { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_PS3_CONTROLLER) },
16661670 { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE) },
16671671 { HID_USB_DEVICE(USB_VENDOR_ID_SUNPLUS, USB_DEVICE_ID_SUNPLUS_WDESKTOP) },
1672+ { HID_USB_DEVICE(USB_VENDOR_ID_STANTUM_STM, USB_DEVICE_ID_SENSOR_HUB_7014) },
16681673 { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb300) },
16691674 { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb304) },
16701675 { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb323) },
drivers/hid/hid-ids.h+6−0
@@ -429,6 +429,11 @@ · 428 unmodified lines
429429 #define USB_VENDOR_ID_IMATION 0x0718
430430 #define USB_DEVICE_ID_DISC_STAKKA 0xd000
431431
432+#define USB_VENDOR_ID_INTEL_8086 0x8086
433+#define USB_VENDOR_ID_INTEL_8087 0x8087
434+#define USB_DEVICE_ID_SENSOR_HUB_1020 0x1020
435+#define USB_DEVICE_ID_SENSOR_HUB_09FA 0x09FA
436+
432437 #define USB_VENDOR_ID_IRTOUCHSYSTEMS 0x6615
433438 #define USB_DEVICE_ID_IRTOUCH_INFRARED_USB 0x0070
434439
@@ -706,6 +711,7 @@ · 271 unmodified lines
706711
707712 #define USB_VENDOR_ID_STANTUM_STM 0x0483
708713 #define USB_DEVICE_ID_MTP_STM 0x3261
714+#define USB_DEVICE_ID_SENSOR_HUB_7014 0x7014
709715
710716 #define USB_VENDOR_ID_STANTUM_SITRONIX 0x1403
711717 #define USB_DEVICE_ID_MTP_SITRONIX 0x5001
drivers/hid/hid-sensor-hub.c+680−0
@@ -0,0 +1,680 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/hid.h>
21+#include <linux/usb.h>
22+#include "usbhid/usbhid.h"
23+#include <linux/module.h>
24+#include <linux/slab.h>
25+#include <linux/mfd/core.h>
26+#include <linux/list.h>
27+#include <linux/hid-sensor-ids.h>
28+#include <linux/hid-sensor-hub.h>
29+#include "hid-ids.h"
30+
31+/**
32+ * struct sensor_hub_pending - Synchronous read pending information
33+ * @status: Pending status true/false.
34+ * @ready: Completion synchronization data.
35+ * @usage_id: Usage id for physical device, E.g. Gyro usage id.
36+ * @attr_usage_id: Usage Id of a field, E.g. X-AXIS for a gyro.
37+ * @raw_size: Response size for a read request.
38+ * @raw_data: Place holder for received response.
39+ */
40+struct sensor_hub_pending {
41+ bool status;
42+ struct completion ready;
43+ u32 usage_id;
44+ u32 attr_usage_id;
45+ int raw_size;
46+ u8 *raw_data;
47+};
48+
49+/**
50+ * struct sensor_hub_data - Hold a instance data for a HID hub device
51+ * @hsdev: Stored hid instance for current hub device.
52+ * @mutex: Mutex to serialize synchronous request.
53+ * @lock: Spin lock to protect pending request structure.
54+ * @pending: Holds information of pending sync read request.
55+ * @dyn_callback_list: Holds callback function
56+ * @dyn_callback_lock: spin lock to protect callback list
57+ * @hid_sensor_hub_client_devs: Stores all MFD cells for a hub instance.
58+ * @hid_sensor_client_cnt: Number of MFD cells, (no of sensors attached).
59+ */
60+struct sensor_hub_data {
61+ struct hid_sensor_hub_device *hsdev;
62+ struct mutex mutex;
63+ spinlock_t lock;
64+ struct sensor_hub_pending pending;
65+ struct list_head dyn_callback_list;
66+ spinlock_t dyn_callback_lock;
67+ struct mfd_cell *hid_sensor_hub_client_devs;
68+ int hid_sensor_client_cnt;
69+};
70+
71+/**
72+ * struct hid_sensor_hub_callbacks_list - Stores callback list
73+ * @list: list head.
74+ * @usage_id: usage id for a physical device.
75+ * @usage_callback: Stores registered callback functions.
76+ * @priv: Private data for a physical device.
77+ */
78+struct hid_sensor_hub_callbacks_list {
79+ struct list_head list;
80+ u32 usage_id;
81+ struct hid_sensor_hub_callbacks *usage_callback;
82+ void *priv;
83+};
84+
85+static int sensor_hub_check_for_sensor_page(struct hid_device *hdev)
86+{
87+ int i;
88+ int ret = -EINVAL;
89+
90+ for (i = 0; i < hdev->maxcollection; i++) {
91+ struct hid_collection *col = &hdev->collection[i];
92+ if (col->type == HID_COLLECTION_PHYSICAL &&
93+ (col->usage & HID_USAGE_PAGE) == HID_UP_SENSOR) {
94+ ret = 0;
95+ break;
96+ }
97+ }
98+
99+ return ret;
100+}
101+
102+static struct hid_report *sensor_hub_report(int id, struct hid_device *hdev,
103+ int dir)
104+{
105+ struct hid_report *report;
106+
107+ list_for_each_entry(report, &hdev->report_enum[dir].report_list, list) {
108+ if (report->id == id)
109+ return report;
110+ }
111+ hid_warn(hdev, "No report with id 0x%x found\n", id);
112+
113+ return NULL;
114+}
115+
116+static int sensor_hub_get_physical_device_count(
117+ struct hid_report_enum *report_enum)
118+{
119+ struct hid_report *report;
120+ struct hid_field *field;
121+ int cnt = 0;
122+
123+ list_for_each_entry(report, &report_enum->report_list, list) {
124+ field = report->field[0];
125+ if (report->maxfield && field &&
126+ field->physical)
127+ cnt++;
128+ }
129+
130+ return cnt;
131+}
132+
133+static void sensor_hub_fill_attr_info(
134+ struct hid_sensor_hub_attribute_info *info,
135+ s32 index, s32 report_id, s32 units, s32 unit_expo, s32 size)
136+{
137+ info->index = index;
138+ info->report_id = report_id;
139+ info->units = units;
140+ info->unit_expo = unit_expo;
141+ info->size = size/8;
142+}
143+
144+static struct hid_sensor_hub_callbacks *sensor_hub_get_callback(
145+ struct hid_device *hdev,
146+ u32 usage_id, void **priv)
147+{
148+ struct hid_sensor_hub_callbacks_list *callback;
149+ struct sensor_hub_data *pdata = hid_get_drvdata(hdev);
150+
151+ spin_lock(&pdata->dyn_callback_lock);
152+ list_for_each_entry(callback, &pdata->dyn_callback_list, list)
153+ if (callback->usage_id == usage_id) {
154+ *priv = callback->priv;
155+ spin_unlock(&pdata->dyn_callback_lock);
156+ return callback->usage_callback;
157+ }
158+ spin_unlock(&pdata->dyn_callback_lock);
159+
160+ return NULL;
161+}
162+
163+int sensor_hub_register_callback(struct hid_sensor_hub_device *hsdev,
164+ u32 usage_id,
165+ struct hid_sensor_hub_callbacks *usage_callback)
166+{
167+ struct hid_sensor_hub_callbacks_list *callback;
168+ struct sensor_hub_data *pdata = hid_get_drvdata(hsdev->hdev);
169+
170+ spin_lock(&pdata->dyn_callback_lock);
171+ list_for_each_entry(callback, &pdata->dyn_callback_list, list)
172+ if (callback->usage_id == usage_id) {
173+ spin_unlock(&pdata->dyn_callback_lock);
174+ return -EINVAL;
175+ }
176+ callback = kzalloc(sizeof(*callback), GFP_ATOMIC);
177+ if (!callback) {
178+ spin_unlock(&pdata->dyn_callback_lock);
179+ return -ENOMEM;
180+ }
181+ callback->usage_callback = usage_callback;
182+ callback->usage_id = usage_id;
183+ callback->priv = NULL;
184+ list_add_tail(&callback->list, &pdata->dyn_callback_list);
185+ spin_unlock(&pdata->dyn_callback_lock);
186+
187+ return 0;
188+}
189+EXPORT_SYMBOL_GPL(sensor_hub_register_callback);
190+
191+int sensor_hub_remove_callback(struct hid_sensor_hub_device *hsdev,
192+ u32 usage_id)
193+{
194+ struct hid_sensor_hub_callbacks_list *callback;
195+ struct sensor_hub_data *pdata = hid_get_drvdata(hsdev->hdev);
196+
197+ spin_lock(&pdata->dyn_callback_lock);
198+ list_for_each_entry(callback, &pdata->dyn_callback_list, list)
199+ if (callback->usage_id == usage_id) {
200+ list_del(&callback->list);
201+ kfree(callback);
202+ break;
203+ }
204+ spin_unlock(&pdata->dyn_callback_lock);
205+
206+ return 0;
207+}
208+EXPORT_SYMBOL_GPL(sensor_hub_remove_callback);
209+
210+int sensor_hub_set_feature(struct hid_sensor_hub_device *hsdev, u32 report_id,
211+ u32 field_index, s32 value)
212+{
213+ struct hid_report *report;
214+ struct sensor_hub_data *data = hid_get_drvdata(hsdev->hdev);
215+ int ret = 0;
216+
217+ mutex_lock(&data->mutex);
218+ report = sensor_hub_report(report_id, hsdev->hdev, HID_FEATURE_REPORT);
219+ if (!report || (field_index >= report->maxfield)) {
220+ ret = -EINVAL;
221+ goto done_proc;
222+ }
223+ hid_set_field(report->field[field_index], 0, value);
224+ usbhid_submit_report(hsdev->hdev, report, USB_DIR_OUT);
225+ usbhid_wait_io(hsdev->hdev);
226+
227+done_proc:
228+ mutex_unlock(&data->mutex);
229+
230+ return ret;
231+}
232+EXPORT_SYMBOL_GPL(sensor_hub_set_feature);
233+
234+int sensor_hub_get_feature(struct hid_sensor_hub_device *hsdev, u32 report_id,
235+ u32 field_index, s32 *value)
236+{
237+ struct hid_report *report;
238+ struct sensor_hub_data *data = hid_get_drvdata(hsdev->hdev);
239+ int ret = 0;
240+
241+ mutex_lock(&data->mutex);
242+ report = sensor_hub_report(report_id, hsdev->hdev, HID_FEATURE_REPORT);
243+ if (!report || (field_index >= report->maxfield)) {
244+ ret = -EINVAL;
245+ goto done_proc;
246+ }
247+ usbhid_submit_report(hsdev->hdev, report, USB_DIR_IN);
248+ usbhid_wait_io(hsdev->hdev);
249+ *value = report->field[field_index]->value[0];
250+
251+done_proc:
252+ mutex_unlock(&data->mutex);
253+
254+ return ret;
255+}
256+EXPORT_SYMBOL_GPL(sensor_hub_get_feature);
257+
258+
259+int sensor_hub_input_attr_get_raw_value(struct hid_sensor_hub_device *hsdev,
260+ u32 usage_id,
261+ u32 attr_usage_id, u32 report_id)
262+{
263+ struct sensor_hub_data *data = hid_get_drvdata(hsdev->hdev);
264+ unsigned long flags;
265+ struct hid_report *report;
266+ int ret_val = 0;
267+
268+ mutex_lock(&data->mutex);
269+ memset(&data->pending, 0, sizeof(data->pending));
270+ init_completion(&data->pending.ready);
271+ data->pending.usage_id = usage_id;
272+ data->pending.attr_usage_id = attr_usage_id;
273+ data->pending.raw_size = 0;
274+
275+ spin_lock_irqsave(&data->lock, flags);
276+ data->pending.status = true;
277+ report = sensor_hub_report(report_id, hsdev->hdev, HID_INPUT_REPORT);
278+ if (!report) {
279+ spin_unlock_irqrestore(&data->lock, flags);
280+ goto err_free;
281+ }
282+ usbhid_submit_report(hsdev->hdev, report, USB_DIR_IN);
283+ spin_unlock_irqrestore(&data->lock, flags);
284+ wait_for_completion_interruptible_timeout(&data->pending.ready, HZ*5);
285+ switch (data->pending.raw_size) {
286+ case 1:
287+ ret_val = *(u8 *)data->pending.raw_data;
288+ break;
289+ case 2:
290+ ret_val = *(u16 *)data->pending.raw_data;
291+ break;
292+ case 4:
293+ ret_val = *(u32 *)data->pending.raw_data;
294+ break;
295+ default:
296+ ret_val = 0;
297+ }
298+ kfree(data->pending.raw_data);
299+
300+err_free:
301+ data->pending.status = false;
302+ mutex_unlock(&data->mutex);
303+
304+ return ret_val;
305+}
306+EXPORT_SYMBOL_GPL(sensor_hub_input_attr_get_raw_value);
307+
308+int sensor_hub_input_get_attribute_info(struct hid_sensor_hub_device *hsdev,
309+ u8 type,
310+ u32 usage_id,
311+ u32 attr_usage_id,
312+ struct hid_sensor_hub_attribute_info *info)
313+{
314+ int ret = -1;
315+ int i, j;
316+ int collection_index = -1;
317+ struct hid_report *report;
318+ struct hid_field *field;
319+ struct hid_report_enum *report_enum;
320+ struct hid_device *hdev = hsdev->hdev;
321+
322+ /* Initialize with defaults */
323+ info->usage_id = usage_id;
324+ info->attrib_id = attr_usage_id;
325+ info->report_id = -1;
326+ info->index = -1;
327+ info->units = -1;
328+ info->unit_expo = -1;
329+
330+ for (i = 0; i < hdev->maxcollection; ++i) {
331+ struct hid_collection *collection = &hdev->collection[i];
332+ if (usage_id == collection->usage) {
333+ collection_index = i;
334+ break;
335+ }
336+ }
337+ if (collection_index == -1)
338+ goto err_ret;
339+
340+ report_enum = &hdev->report_enum[type];
341+ list_for_each_entry(report, &report_enum->report_list, list) {
342+ for (i = 0; i < report->maxfield; ++i) {
343+ field = report->field[i];
344+ if (field->physical == usage_id &&
345+ field->logical == attr_usage_id) {
346+ sensor_hub_fill_attr_info(info, i, report->id,
347+ field->unit, field->unit_exponent,
348+ field->report_size);
349+ ret = 0;
350+ } else {
351+ for (j = 0; j < field->maxusage; ++j) {
352+ if (field->usage[j].hid ==
353+ attr_usage_id &&
354+ field->usage[j].collection_index ==
355+ collection_index) {
356+ sensor_hub_fill_attr_info(info,
357+ i, report->id,
358+ field->unit,
359+ field->unit_exponent,
360+ field->report_size);
361+ ret = 0;
362+ break;
363+ }
364+ }
365+ }
366+ if (ret == 0)
367+ break;
368+ }
369+ }
370+
371+err_ret:
372+ return ret;
373+}
374+EXPORT_SYMBOL_GPL(sensor_hub_input_get_attribute_info);
375+
376+#ifdef CONFIG_PM
377+static int sensor_hub_suspend(struct hid_device *hdev, pm_message_t message)
378+{
379+ struct sensor_hub_data *pdata = hid_get_drvdata(hdev);
380+ struct hid_sensor_hub_callbacks_list *callback;
381+
382+ hid_dbg(hdev, " sensor_hub_suspend\n");
383+ spin_lock(&pdata->dyn_callback_lock);
384+ list_for_each_entry(callback, &pdata->dyn_callback_list, list) {
385+ if (callback->usage_callback->suspend)
386+ callback->usage_callback->suspend(
387+ pdata->hsdev, callback->priv);
388+ }
389+ spin_unlock(&pdata->dyn_callback_lock);
390+
391+ return 0;
392+}
393+
394+static int sensor_hub_resume(struct hid_device *hdev)
395+{
396+ struct sensor_hub_data *pdata = hid_get_drvdata(hdev);
397+ struct hid_sensor_hub_callbacks_list *callback;
398+
399+ hid_dbg(hdev, " sensor_hub_resume\n");
400+ spin_lock(&pdata->dyn_callback_lock);
401+ list_for_each_entry(callback, &pdata->dyn_callback_list, list) {
402+ if (callback->usage_callback->resume)
403+ callback->usage_callback->resume(
404+ pdata->hsdev, callback->priv);
405+ }
406+ spin_unlock(&pdata->dyn_callback_lock);
407+
408+ return 0;
409+}
410+
411+static int sensor_hub_reset_resume(struct hid_device *hdev)
412+{
413+ return 0;
414+}
415+#endif
416+/*
417+ * Handle raw report as sent by device
418+ */
419+static int sensor_hub_raw_event(struct hid_device *hdev,
420+ struct hid_report *report, u8 *raw_data, int size)
421+{
422+ int i;
423+ u8 *ptr;
424+ int sz;
425+ struct sensor_hub_data *pdata = hid_get_drvdata(hdev);
426+ unsigned long flags;
427+ struct hid_sensor_hub_callbacks *callback = NULL;
428+ struct hid_collection *collection = NULL;
429+ void *priv = NULL;
430+
431+ hid_dbg(hdev, "sensor_hub_raw_event report id:0x%x size:%d type:%d\n",
432+ report->id, size, report->type);
433+ hid_dbg(hdev, "maxfield:%d\n", report->maxfield);
434+ if (report->type != HID_INPUT_REPORT)
435+ return 1;
436+
437+ ptr = raw_data;
438+ ptr++; /*Skip report id*/
439+
440+ if (!report)
441+ goto err_report;
442+
443+ spin_lock_irqsave(&pdata->lock, flags);
444+
445+ for (i = 0; i < report->maxfield; ++i) {
446+
447+ hid_dbg(hdev, "%d collection_index:%x hid:%x sz:%x\n",
448+ i, report->field[i]->usage->collection_index,
449+ report->field[i]->usage->hid,
450+ report->field[i]->report_size/8);
451+
452+ sz = report->field[i]->report_size/8;
453+ if (pdata->pending.status && pdata->pending.attr_usage_id ==
454+ report->field[i]->usage->hid) {
455+ hid_dbg(hdev, "data was pending ...\n");
456+ pdata->pending.raw_data = kmalloc(sz, GFP_ATOMIC);
457+ if (pdata->pending.raw_data) {
458+ memcpy(pdata->pending.raw_data, ptr, sz);
459+ pdata->pending.raw_size = sz;
460+ } else
461+ pdata->pending.raw_size = 0;
462+ complete(&pdata->pending.ready);
463+ }
464+ collection = &hdev->collection[
465+ report->field[i]->usage->collection_index];
466+ hid_dbg(hdev, "collection->usage %x\n",
467+ collection->usage);
468+ callback = sensor_hub_get_callback(pdata->hsdev->hdev,
469+ report->field[i]->physical,
470+ &priv);
471+ if (callback && callback->capture_sample) {
472+ if (report->field[i]->logical)
473+ callback->capture_sample(pdata->hsdev,
474+ report->field[i]->logical, sz, ptr,
475+ callback->pdev);
476+ else
477+ callback->capture_sample(pdata->hsdev,
478+ report->field[i]->usage->hid, sz, ptr,
479+ callback->pdev);
480+ }
481+ ptr += sz;
482+ }
483+ if (callback && collection && callback->send_event)
484+ callback->send_event(pdata->hsdev, collection->usage,
485+ callback->pdev);
486+ spin_unlock_irqrestore(&pdata->lock, flags);
487+
488+err_report:
489+ return 1;
490+}
491+
492+static int sensor_hub_probe(struct hid_device *hdev,
493+ const struct hid_device_id *id)
494+{
495+ int ret;
496+ struct sensor_hub_data *sd;
497+ int i;
498+ char *name;
499+ struct hid_report *report;
500+ struct hid_report_enum *report_enum;
501+ struct hid_field *field;
502+ int dev_cnt;
503+
504+ sd = kzalloc(sizeof(struct sensor_hub_data), GFP_KERNEL);
505+ if (!sd) {
506+ hid_err(hdev, "cannot allocate Sensor data\n");
507+ return -ENOMEM;
508+ }
509+ sd->hsdev = kzalloc(sizeof(struct hid_sensor_hub_device), GFP_KERNEL);
510+ if (!sd->hsdev) {
511+ hid_err(hdev, "cannot allocate hid_sensor_hub_device\n");
512+ ret = -ENOMEM;
513+ goto err_free_hub;
514+ }
515+ hid_set_drvdata(hdev, sd);
516+ sd->hsdev->hdev = hdev;
517+ sd->hsdev->vendor_id = hdev->vendor;
518+ sd->hsdev->product_id = hdev->product;
519+ spin_lock_init(&sd->lock);
520+ spin_lock_init(&sd->dyn_callback_lock);
521+ mutex_init(&sd->mutex);
522+ ret = hid_parse(hdev);
523+ if (ret) {
524+ hid_err(hdev, "parse failed\n");
525+ goto err_free;
526+ }
527+ if (sensor_hub_check_for_sensor_page(hdev) < 0) {
528+ hid_err(hdev, "sensor page not found\n");
529+ goto err_free;
530+ }
531+ INIT_LIST_HEAD(&hdev->inputs);
532+
533+ ret = hid_hw_start(hdev, 0);
534+ if (ret) {
535+ hid_err(hdev, "hw start failed\n");
536+ goto err_free;
537+ }
538+ ret = hid_hw_open(hdev);
539+ if (ret) {
540+ hid_err(hdev, "failed to open input interrupt pipe\n");
541+ goto err_stop_hw;
542+ }
543+
544+ INIT_LIST_HEAD(&sd->dyn_callback_list);
545+ sd->hid_sensor_client_cnt = 0;
546+ report_enum = &hdev->report_enum[HID_INPUT_REPORT];
547+
548+ dev_cnt = sensor_hub_get_physical_device_count(report_enum);
549+ if (dev_cnt > HID_MAX_PHY_DEVICES) {
550+ hid_err(hdev, "Invalid Physical device count\n");
551+ ret = -EINVAL;
552+ goto err_close;
553+ }
554+ sd->hid_sensor_hub_client_devs = kzalloc(dev_cnt *
555+ sizeof(struct mfd_cell),
556+ GFP_KERNEL);
557+ if (sd->hid_sensor_hub_client_devs == NULL) {
558+ hid_err(hdev, "Failed to allocate memory for mfd cells\n");
559+ ret = -ENOMEM;
560+ goto err_close;
561+ }
562+ list_for_each_entry(report, &report_enum->report_list, list) {
563+ hid_dbg(hdev, "Report id:%x\n", report->id);
564+ field = report->field[0];
565+ if (report->maxfield && field &&
566+ field->physical) {
567+ name = kasprintf(GFP_KERNEL, "HID-SENSOR-%x",
568+ field->physical);
569+ if (name == NULL) {
570+ hid_err(hdev, "Failed MFD device name\n");
571+ ret = -ENOMEM;
572+ goto err_free_names;
573+ }
574+ sd->hid_sensor_hub_client_devs[
575+ sd->hid_sensor_client_cnt].name = name;
576+ sd->hid_sensor_hub_client_devs[
577+ sd->hid_sensor_client_cnt].platform_data =
578+ sd->hsdev;
579+ sd->hid_sensor_hub_client_devs[
580+ sd->hid_sensor_client_cnt].pdata_size =
581+ sizeof(*sd->hsdev);
582+ hid_dbg(hdev, "Adding %s:%p\n", name, sd);
583+ sd->hid_sensor_client_cnt++;
584+ }
585+ }
586+ ret = mfd_add_devices(&hdev->dev, 0, sd->hid_sensor_hub_client_devs,
587+ sd->hid_sensor_client_cnt, NULL, 0, NULL);
588+ if (ret < 0)
589+ goto err_free_names;
590+
591+ return ret;
592+
593+err_free_names:
594+ for (i = 0; i < sd->hid_sensor_client_cnt ; ++i)
595+ kfree(sd->hid_sensor_hub_client_devs[i].name);
596+ kfree(sd->hid_sensor_hub_client_devs);
597+err_close:
598+ hid_hw_close(hdev);
599+err_stop_hw:
600+ hid_hw_stop(hdev);
601+err_free:
602+ kfree(sd->hsdev);
603+err_free_hub:
604+ kfree(sd);
605+
606+ return ret;
607+}
608+
609+static void sensor_hub_remove(struct hid_device *hdev)
610+{
611+ struct sensor_hub_data *data = hid_get_drvdata(hdev);
612+ unsigned long flags;
613+ int i;
614+
615+ hid_dbg(hdev, " hardware removed\n");
616+ hid_hw_close(hdev);
617+ hid_hw_stop(hdev);
618+ spin_lock_irqsave(&data->lock, flags);
619+ if (data->pending.status)
620+ complete(&data->pending.ready);
621+ spin_unlock_irqrestore(&data->lock, flags);
622+ mfd_remove_devices(&hdev->dev);
623+ for (i = 0; i < data->hid_sensor_client_cnt ; ++i)
624+ kfree(data->hid_sensor_hub_client_devs[i].name);
625+ kfree(data->hid_sensor_hub_client_devs);
626+ hid_set_drvdata(hdev, NULL);
627+ mutex_destroy(&data->mutex);
628+ kfree(data->hsdev);
629+ kfree(data);
630+}
631+
632+static const struct hid_device_id sensor_hub_devices[] = {
633+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8086,
634+ USB_DEVICE_ID_SENSOR_HUB_1020) },
635+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8087,
636+ USB_DEVICE_ID_SENSOR_HUB_1020) },
637+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8086,
638+ USB_DEVICE_ID_SENSOR_HUB_09FA) },
639+ { HID_USB_DEVICE(USB_VENDOR_ID_INTEL_8087,
640+ USB_DEVICE_ID_SENSOR_HUB_09FA) },
641+ { HID_USB_DEVICE(USB_VENDOR_ID_STANTUM_STM,
642+ USB_DEVICE_ID_SENSOR_HUB_7014) },
643+ { }
644+};
645+MODULE_DEVICE_TABLE(hid, sensor_hub_devices);
646+
647+static const struct hid_usage_id sensor_hub_grabbed_usages[] = {
648+ { HID_ANY_ID, HID_ANY_ID, HID_ANY_ID },
649+ { HID_ANY_ID - 1, HID_ANY_ID - 1, HID_ANY_ID - 1 }
650+};
651+
652+static struct hid_driver sensor_hub_driver = {
653+ .name = "hid-sensor-hub",
654+ .id_table = sensor_hub_devices,
655+ .probe = sensor_hub_probe,
656+ .remove = sensor_hub_remove,
657+ .raw_event = sensor_hub_raw_event,
658+#ifdef CONFIG_PM
659+ .suspend = sensor_hub_suspend,
660+ .resume = sensor_hub_resume,
661+ .reset_resume = sensor_hub_reset_resume,
662+#endif
663+};
664+
665+static int __init sensor_hub_init(void)
666+{
667+ return hid_register_driver(&sensor_hub_driver);
668+}
669+
670+static void __exit sensor_hub_exit(void)
671+{
672+ hid_unregister_driver(&sensor_hub_driver);
673+}
674+
675+module_init(sensor_hub_init);
676+module_exit(sensor_hub_exit);
677+
678+MODULE_DESCRIPTION("HID Sensor Hub driver");
679+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
680+MODULE_LICENSE("GPL");
drivers/iio/Kconfig+6−1
@@ -1,5 +1,5 @@
11 #
2−# Industrial I/O subsytem configuration
2+# Industrial I/O subsystem configuration
33 #
44
55 menuconfig IIO
@@ -54,10 +54,15 @@ config IIO_CONSUMERS_PER_TRIGGER · 48 unmodified lines
5454 This value controls the maximum number of consumers that a
5555 given trigger may handle. Default is 2.
5656
57+source "drivers/iio/accel/Kconfig"
5758 source "drivers/iio/adc/Kconfig"
5859 source "drivers/iio/amplifiers/Kconfig"
5960 source "drivers/iio/light/Kconfig"
6061 source "drivers/iio/frequency/Kconfig"
6162 source "drivers/iio/dac/Kconfig"
63+source "drivers/iio/common/Kconfig"
64+source "drivers/iio/gyro/Kconfig"
65+source "drivers/iio/light/Kconfig"
66+source "drivers/iio/magnetometer/Kconfig"
6267
6368 endif # IIO
drivers/iio/Makefile+5−0
@@ -10,8 +10,13 @@ industrialio-$(CONFIG_IIO_TRIGGER) += industrialio-trigger.o · 9 unmodified lines
1010 obj-$(CONFIG_IIO_TRIGGERED_BUFFER) += industrialio-triggered-buffer.o
1111 obj-$(CONFIG_IIO_KFIFO_BUF) += kfifo_buf.o
1212
13+obj-y += accel/
1314 obj-y += adc/
1415 obj-y += amplifiers/
1516 obj-y += light/
1617 obj-y += frequency/
1718 obj-y += dac/
19+obj-y += common/
20+obj-y += gyro/
21+obj-y += light/
22+obj-y += magnetometer/
drivers/iio/accel/Kconfig+16−0
@@ -0,0 +1,16 @@
1+#
2+# Accelerometer drivers
3+#
4+menu "Accelerometers"
5+
6+config HID_SENSOR_ACCEL_3D
7+ depends on HID_SENSOR_HUB
8+ select IIO_BUFFER
9+ select IIO_TRIGGERED_BUFFER
10+ select HID_SENSOR_IIO_COMMON
11+ tristate "HID Acelerometers 3D"
12+ help
13+ Say yes here to build support for the HID SENSOR
14+ accelerometers 3D.
15+
16+endmenu
drivers/iio/accel/Makefile+5−0
@@ -0,0 +1,5 @@
1+#
2+# Makefile for industrial I/O accelerometer drivers
3+#
4+
5+obj-$(CONFIG_HID_SENSOR_ACCEL_3D) += hid-sensor-accel-3d.o
drivers/iio/accel/hid-sensor-accel-3d.c+418−0
@@ -0,0 +1,418 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/sysfs.h>
28+#include <linux/iio/buffer.h>
29+#include <linux/iio/trigger_consumer.h>
30+#include <linux/iio/triggered_buffer.h>
31+#include "../common/hid-sensors/hid-sensor-attributes.h"
32+#include "../common/hid-sensors/hid-sensor-trigger.h"
33+
34+/*Format: HID-SENSOR-usage_id_in_hex*/
35+/*Usage ID from spec for Accelerometer-3D: 0x200073*/
36+#define DRIVER_NAME "HID-SENSOR-200073"
37+
38+enum accel_3d_channel {
39+ CHANNEL_SCAN_INDEX_X,
40+ CHANNEL_SCAN_INDEX_Y,
41+ CHANNEL_SCAN_INDEX_Z,
42+ ACCEL_3D_CHANNEL_MAX,
43+};
44+
45+struct accel_3d_state {
46+ struct hid_sensor_hub_callbacks callbacks;
47+ struct hid_sensor_iio_common common_attributes;
48+ struct hid_sensor_hub_attribute_info accel[ACCEL_3D_CHANNEL_MAX];
49+ u32 accel_val[ACCEL_3D_CHANNEL_MAX];
50+};
51+
52+static const u32 accel_3d_addresses[ACCEL_3D_CHANNEL_MAX] = {
53+ HID_USAGE_SENSOR_ACCEL_X_AXIS,
54+ HID_USAGE_SENSOR_ACCEL_Y_AXIS,
55+ HID_USAGE_SENSOR_ACCEL_Z_AXIS
56+};
57+
58+/* Channel definitions */
59+static const struct iio_chan_spec accel_3d_channels[] = {
60+ {
61+ .type = IIO_ACCEL,
62+ .modified = 1,
63+ .channel2 = IIO_MOD_X,
64+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
65+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
66+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
67+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
68+ .scan_index = CHANNEL_SCAN_INDEX_X,
69+ }, {
70+ .type = IIO_ACCEL,
71+ .modified = 1,
72+ .channel2 = IIO_MOD_Y,
73+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
74+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
75+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
76+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
77+ .scan_index = CHANNEL_SCAN_INDEX_Y,
78+ }, {
79+ .type = IIO_ACCEL,
80+ .modified = 1,
81+ .channel2 = IIO_MOD_Z,
82+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
83+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
84+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
85+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
86+ .scan_index = CHANNEL_SCAN_INDEX_Z,
87+ }
88+};
89+
90+/* Adjust channel real bits based on report descriptor */
91+static void accel_3d_adjust_channel_bit_mask(struct iio_chan_spec *channels,
92+ int channel, int size)
93+{
94+ channels[channel].scan_type.sign = 's';
95+ /* Real storage bits will change based on the report desc. */
96+ channels[channel].scan_type.realbits = size * 8;
97+ /* Maximum size of a sample to capture is u32 */
98+ channels[channel].scan_type.storagebits = sizeof(u32) * 8;
99+}
100+
101+/* Channel read_raw handler */
102+static int accel_3d_read_raw(struct iio_dev *indio_dev,
103+ struct iio_chan_spec const *chan,
104+ int *val, int *val2,
105+ long mask)
106+{
107+ struct accel_3d_state *accel_state = iio_priv(indio_dev);
108+ int report_id = -1;
109+ u32 address;
110+ int ret;
111+ int ret_type;
112+
113+ *val = 0;
114+ *val2 = 0;
115+ switch (mask) {
116+ case 0:
117+ report_id = accel_state->accel[chan->scan_index].report_id;
118+ address = accel_3d_addresses[chan->scan_index];
119+ if (report_id >= 0)
120+ *val = sensor_hub_input_attr_get_raw_value(
121+ accel_state->common_attributes.hsdev,
122+ HID_USAGE_SENSOR_ACCEL_3D, address,
123+ report_id);
124+ else {
125+ *val = 0;
126+ return -EINVAL;
127+ }
128+ ret_type = IIO_VAL_INT;
129+ break;
130+ case IIO_CHAN_INFO_SCALE:
131+ *val = accel_state->accel[CHANNEL_SCAN_INDEX_X].units;
132+ ret_type = IIO_VAL_INT;
133+ break;
134+ case IIO_CHAN_INFO_OFFSET:
135+ *val = hid_sensor_convert_exponent(
136+ accel_state->accel[CHANNEL_SCAN_INDEX_X].unit_expo);
137+ ret_type = IIO_VAL_INT;
138+ break;
139+ case IIO_CHAN_INFO_SAMP_FREQ:
140+ ret = hid_sensor_read_samp_freq_value(
141+ &accel_state->common_attributes, val, val2);
142+ ret_type = IIO_VAL_INT_PLUS_MICRO;
143+ break;
144+ case IIO_CHAN_INFO_HYSTERESIS:
145+ ret = hid_sensor_read_raw_hyst_value(
146+ &accel_state->common_attributes, val, val2);
147+ ret_type = IIO_VAL_INT_PLUS_MICRO;
148+ break;
149+ default:
150+ ret_type = -EINVAL;
151+ break;
152+ }
153+
154+ return ret_type;
155+}
156+
157+/* Channel write_raw handler */
158+static int accel_3d_write_raw(struct iio_dev *indio_dev,
159+ struct iio_chan_spec const *chan,
160+ int val,
161+ int val2,
162+ long mask)
163+{
164+ struct accel_3d_state *accel_state = iio_priv(indio_dev);
165+ int ret = 0;
166+
167+ switch (mask) {
168+ case IIO_CHAN_INFO_SAMP_FREQ:
169+ ret = hid_sensor_write_samp_freq_value(
170+ &accel_state->common_attributes, val, val2);
171+ break;
172+ case IIO_CHAN_INFO_HYSTERESIS:
173+ ret = hid_sensor_write_raw_hyst_value(
174+ &accel_state->common_attributes, val, val2);
175+ break;
176+ default:
177+ ret = -EINVAL;
178+ }
179+
180+ return ret;
181+}
182+
183+static int accel_3d_write_raw_get_fmt(struct iio_dev *indio_dev,
184+ struct iio_chan_spec const *chan,
185+ long mask)
186+{
187+ return IIO_VAL_INT_PLUS_MICRO;
188+}
189+
190+static const struct iio_info accel_3d_info = {
191+ .driver_module = THIS_MODULE,
192+ .read_raw = &accel_3d_read_raw,
193+ .write_raw = &accel_3d_write_raw,
194+ .write_raw_get_fmt = &accel_3d_write_raw_get_fmt,
195+};
196+
197+/* Function to push data to buffer */
198+static void hid_sensor_push_data(struct iio_dev *indio_dev, u8 *data, int len)
199+{
200+ struct iio_buffer *buffer = indio_dev->buffer;
201+ int datum_sz;
202+
203+ dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n");
204+ if (!buffer) {
205+ dev_err(&indio_dev->dev, "Buffer == NULL\n");
206+ return;
207+ }
208+ datum_sz = buffer->access->get_bytes_per_datum(buffer);
209+ if (len > datum_sz) {
210+ dev_err(&indio_dev->dev, "Datum size mismatch %d:%d\n", len,
211+ datum_sz);
212+ return;
213+ }
214+ iio_push_to_buffer(buffer, (u8 *)data);
215+}
216+
217+/* Callback handler to send event after all samples are received and captured */
218+static int accel_3d_proc_event(struct hid_sensor_hub_device *hsdev,
219+ unsigned usage_id,
220+ void *priv)
221+{
222+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
223+ struct accel_3d_state *accel_state = iio_priv(indio_dev);
224+
225+ dev_dbg(&indio_dev->dev, "accel_3d_proc_event [%d]\n",
226+ accel_state->common_attributes.data_ready);
227+ if (accel_state->common_attributes.data_ready)
228+ hid_sensor_push_data(indio_dev,
229+ (u8 *)accel_state->accel_val,
230+ sizeof(accel_state->accel_val));
231+
232+ return 0;
233+}
234+
235+/* Capture samples in local storage */
236+static int accel_3d_capture_sample(struct hid_sensor_hub_device *hsdev,
237+ unsigned usage_id,
238+ size_t raw_len, char *raw_data,
239+ void *priv)
240+{
241+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
242+ struct accel_3d_state *accel_state = iio_priv(indio_dev);
243+ int offset;
244+ int ret = -EINVAL;
245+
246+ switch (usage_id) {
247+ case HID_USAGE_SENSOR_ACCEL_X_AXIS:
248+ case HID_USAGE_SENSOR_ACCEL_Y_AXIS:
249+ case HID_USAGE_SENSOR_ACCEL_Z_AXIS:
250+ offset = usage_id - HID_USAGE_SENSOR_ACCEL_X_AXIS;
251+ accel_state->accel_val[CHANNEL_SCAN_INDEX_X + offset] =
252+ *(u32 *)raw_data;
253+ ret = 0;
254+ break;
255+ default:
256+ break;
257+ }
258+
259+ return ret;
260+}
261+
262+/* Parse report which is specific to an usage id*/
263+static int accel_3d_parse_report(struct platform_device *pdev,
264+ struct hid_sensor_hub_device *hsdev,
265+ struct iio_chan_spec *channels,
266+ unsigned usage_id,
267+ struct accel_3d_state *st)
268+{
269+ int ret;
270+ int i;
271+
272+ for (i = 0; i <= CHANNEL_SCAN_INDEX_Z; ++i) {
273+ ret = sensor_hub_input_get_attribute_info(hsdev,
274+ HID_INPUT_REPORT,
275+ usage_id,
276+ HID_USAGE_SENSOR_ACCEL_X_AXIS + i,
277+ &st->accel[CHANNEL_SCAN_INDEX_X + i]);
278+ if (ret < 0)
279+ break;
280+ accel_3d_adjust_channel_bit_mask(channels,
281+ CHANNEL_SCAN_INDEX_X + i,
282+ st->accel[CHANNEL_SCAN_INDEX_X + i].size);
283+ }
284+ dev_dbg(&pdev->dev, "accel_3d %x:%x, %x:%x, %x:%x\n",
285+ st->accel[0].index,
286+ st->accel[0].report_id,
287+ st->accel[1].index, st->accel[1].report_id,
288+ st->accel[2].index, st->accel[2].report_id);
289+
290+ return ret;
291+}
292+
293+/* Function to initialize the processing for usage id */
294+static int __devinit hid_accel_3d_probe(struct platform_device *pdev)
295+{
296+ int ret = 0;
297+ static const char *name = "accel_3d";
298+ struct iio_dev *indio_dev;
299+ struct accel_3d_state *accel_state;
300+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
301+ struct iio_chan_spec *channels;
302+
303+ indio_dev = iio_device_alloc(sizeof(struct accel_3d_state));
304+ if (indio_dev == NULL) {
305+ ret = -ENOMEM;
306+ goto error_ret;
307+ }
308+ platform_set_drvdata(pdev, indio_dev);
309+
310+ accel_state = iio_priv(indio_dev);
311+ accel_state->common_attributes.hsdev = hsdev;
312+ accel_state->common_attributes.pdev = pdev;
313+
314+ ret = hid_sensor_parse_common_attributes(hsdev,
315+ HID_USAGE_SENSOR_ACCEL_3D,
316+ &accel_state->common_attributes);
317+ if (ret) {
318+ dev_err(&pdev->dev, "failed to setup common attributes\n");
319+ goto error_free_dev;
320+ }
321+
322+ channels = kmemdup(accel_3d_channels,
323+ sizeof(accel_3d_channels),
324+ GFP_KERNEL);
325+ if (!channels) {
326+ dev_err(&pdev->dev, "failed to duplicate channels\n");
327+ goto error_free_dev;
328+ }
329+
330+ ret = accel_3d_parse_report(pdev, hsdev, channels,
331+ HID_USAGE_SENSOR_ACCEL_3D, accel_state);
332+ if (ret) {
333+ dev_err(&pdev->dev, "failed to setup attributes\n");
334+ goto error_free_dev_mem;
335+ }
336+
337+ indio_dev->channels = channels;
338+ indio_dev->num_channels = ARRAY_SIZE(accel_3d_channels);
339+ indio_dev->dev.parent = &pdev->dev;
340+ indio_dev->info = &accel_3d_info;
341+ indio_dev->name = name;
342+ indio_dev->modes = INDIO_DIRECT_MODE;
343+
344+ ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time,
345+ NULL, NULL);
346+ if (ret) {
347+ dev_err(&pdev->dev, "failed to initialize trigger buffer\n");
348+ goto error_free_dev_mem;
349+ }
350+ accel_state->common_attributes.data_ready = false;
351+ ret = hid_sensor_setup_trigger(indio_dev, name,
352+ &accel_state->common_attributes);
353+ if (ret < 0) {
354+ dev_err(&pdev->dev, "trigger setup failed\n");
355+ goto error_unreg_buffer_funcs;
356+ }
357+
358+ ret = iio_device_register(indio_dev);
359+ if (ret) {
360+ dev_err(&pdev->dev, "device register failed\n");
361+ goto error_remove_trigger;
362+ }
363+
364+ accel_state->callbacks.send_event = accel_3d_proc_event;
365+ accel_state->callbacks.capture_sample = accel_3d_capture_sample;
366+ accel_state->callbacks.pdev = pdev;
367+ ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_ACCEL_3D,
368+ &accel_state->callbacks);
369+ if (ret < 0) {
370+ dev_err(&pdev->dev, "callback reg failed\n");
371+ goto error_iio_unreg;
372+ }
373+
374+ return ret;
375+
376+error_iio_unreg:
377+ iio_device_unregister(indio_dev);
378+error_remove_trigger:
379+ hid_sensor_remove_trigger(indio_dev);
380+error_unreg_buffer_funcs:
381+ iio_triggered_buffer_cleanup(indio_dev);
382+error_free_dev_mem:
383+ kfree(indio_dev->channels);
384+error_free_dev:
385+ iio_device_free(indio_dev);
386+error_ret:
387+ return ret;
388+}
389+
390+/* Function to deinitialize the processing for usage id */
391+static int __devinit hid_accel_3d_remove(struct platform_device *pdev)
392+{
393+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
394+ struct iio_dev *indio_dev = platform_get_drvdata(pdev);
395+
396+ sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_ACCEL_3D);
397+ iio_device_unregister(indio_dev);
398+ hid_sensor_remove_trigger(indio_dev);
399+ iio_triggered_buffer_cleanup(indio_dev);
400+ kfree(indio_dev->channels);
401+ iio_device_free(indio_dev);
402+
403+ return 0;
404+}
405+
406+static struct platform_driver hid_accel_3d_platform_driver = {
407+ .driver = {
408+ .name = DRIVER_NAME,
409+ .owner = THIS_MODULE,
410+ },
411+ .probe = hid_accel_3d_probe,
412+ .remove = hid_accel_3d_remove,
413+};
414+module_platform_driver(hid_accel_3d_platform_driver);
415+
416+MODULE_DESCRIPTION("HID Sensor Accel 3D");
417+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
418+MODULE_LICENSE("GPL");
drivers/iio/adc/Kconfig+38−0
@@ -3,6 +3,11 @@ · 2 unmodified lines
33 #
44 menu "Analog to digital converters"
55
6+config AD_SIGMA_DELTA
7+ tristate
8+ select IIO_BUFFER
9+ select IIO_TRIGGERED_BUFFER
10+
611 config AD7266
712 tristate "Analog Devices AD7265/AD7266 ADC driver"
813 depends on SPI_MASTER
@@ -13,6 +18,33 @@ config AD7266 · 4 unmodified lines
1318 Say yes here to build support for Analog Devices AD7265 and AD7266
1419 ADCs.
1520
21+config AD7791
22+ tristate "Analog Devices AD7791 ADC driver"
23+ depends on SPI
24+ select AD_SIGMA_DELTA
25+ help
26+ Say yes here to build support for Analog Devices AD7787, AD7788, AD7789,
27+ AD7790 and AD7791 SPI analog to digital converters (ADC). If unsure, say
28+ N (but it is safe to say "Y").
29+
30+ To compile this driver as a module, choose M here: the module will be
31+ called ad7791.
32+
33+config AD7476
34+ tristate "Analog Devices AD7476 and similar 1-channel ADCs driver"
35+ depends on SPI
36+ select IIO_BUFFER
37+ select IIO_TRIGGERED_BUFFER
38+ help
39+ Say yes here to build support for Analog Devices AD7273, AD7274, AD7276,
40+ AD7277, AD7278, AD7475, AD7476, AD7477, AD7478, AD7466, AD7467, AD7468,
41+ AD7495, AD7910, AD7920, AD7920 SPI analog to digital converters (ADC).
42+
43+ If unsure, say N (but it's safe to say "Y").
44+
45+ To compile this driver as a module, choose M here: the
46+ module will be called ad7476.
47+
1648 config AT91_ADC
1749 tristate "Atmel AT91 ADC"
1850 depends on ARCH_AT91
@@ -22,4 +54,10 @@ config AT91_ADC · 3 unmodified lines
2254 help
2355 Say yes here to build support for Atmel AT91 ADC.
2456
57+config LP8788_ADC
58+ bool "LP8788 ADC driver"
59+ depends on MFD_LP8788
60+ help
61+ Say yes here to build support for TI LP8788 ADC.
62+
2563 endmenu
drivers/iio/adc/Makefile+4−0
@@ -2,5 +2,9 @@ · 1 unmodified line
22 # Makefile for IIO ADC drivers
33 #
44
5+obj-$(CONFIG_AD_SIGMA_DELTA) += ad_sigma_delta.o
56 obj-$(CONFIG_AD7266) += ad7266.o
7+obj-$(CONFIG_AD7476) += ad7476.o
8+obj-$(CONFIG_AD7791) += ad7791.o
69 obj-$(CONFIG_AT91_ADC) += at91_adc.o
10+obj-$(CONFIG_LP8788_ADC) += lp8788_adc.o
drivers/iio/adc/ad7266.c+1−1
@@ -99,7 +99,7 @@ static irqreturn_t ad7266_trigger_handler(int irq, void *p) · 98 unmodified lines
9999 if (ret == 0) {
100100 if (indio_dev->scan_timestamp)
101101 ((s64 *)st->data)[1] = pf->timestamp;
102− iio_push_to_buffer(buffer, (u8 *)st->data, pf->timestamp);
102+ iio_push_to_buffer(buffer, (u8 *)st->data);
103103 }
104104
105105 iio_trigger_notify_done(indio_dev->trig);
drivers/iio/adc/ad7476.crenamed from drivers/staging/iio/adc/ad7476_core.c+149−61
@@ -18,8 +18,76 @@ · 17 unmodified lines
1818 #include <linux/iio/iio.h>
1919 #include <linux/iio/sysfs.h>
2020 #include <linux/iio/buffer.h>
21+#include <linux/iio/trigger_consumer.h>
22+#include <linux/iio/triggered_buffer.h>
2123
22−#include "ad7476.h"
24+#define RES_MASK(bits) ((1 << (bits)) - 1)
25+
26+struct ad7476_state;
27+
28+struct ad7476_chip_info {
29+ unsigned int int_vref_uv;
30+ struct iio_chan_spec channel[2];
31+ void (*reset)(struct ad7476_state *);
32+};
33+
34+struct ad7476_state {
35+ struct spi_device *spi;
36+ const struct ad7476_chip_info *chip_info;
37+ struct regulator *reg;
38+ struct spi_transfer xfer;
39+ struct spi_message msg;
40+ /*
41+ * DMA (thus cache coherency maintenance) requires the
42+ * transfer buffers to live in their own cache lines.
43+ * Make the buffer large enough for one 16 bit sample and one 64 bit
44+ * aligned 64 bit timestamp.
45+ */
46+ unsigned char data[ALIGN(2, sizeof(s64)) + sizeof(s64)]
47+ ____cacheline_aligned;
48+};
49+
50+enum ad7476_supported_device_ids {
51+ ID_AD7091R,
52+ ID_AD7276,
53+ ID_AD7277,
54+ ID_AD7278,
55+ ID_AD7466,
56+ ID_AD7467,
57+ ID_AD7468,
58+ ID_AD7495,
59+ ID_AD7940,
60+};
61+
62+static irqreturn_t ad7476_trigger_handler(int irq, void *p)
63+{
64+ struct iio_poll_func *pf = p;
65+ struct iio_dev *indio_dev = pf->indio_dev;
66+ struct ad7476_state *st = iio_priv(indio_dev);
67+ s64 time_ns;
68+ int b_sent;
69+
70+ b_sent = spi_sync(st->spi, &st->msg);
71+ if (b_sent < 0)
72+ goto done;
73+
74+ time_ns = iio_get_time_ns();
75+
76+ if (indio_dev->scan_timestamp)
77+ ((s64 *)st->data)[1] = time_ns;
78+
79+ iio_push_to_buffer(indio_dev->buffer, st->data);
80+done:
81+ iio_trigger_notify_done(indio_dev->trig);
82+
83+ return IRQ_HANDLED;
84+}
85+
86+static void ad7091_reset(struct ad7476_state *st)
87+{
88+ /* Any transfers with 8 scl cycles will reset the device */
89+ spi_read(st->spi, st->data, 1);
90+}
2391
2492 static int ad7476_scan_direct(struct ad7476_state *st)
2593 {
@@ -29,7 +97,7 @@ static int ad7476_scan_direct(struct ad7476_state *st) · 3 unmodified lines
2997 if (ret)
3098 return ret;
3199
32− return (st->data[0] << 8) | st->data[1];
100+ return be16_to_cpup((__be16 *)st->data);
33101 }
34102
35103 static int ad7476_read_raw(struct iio_dev *indio_dev,
@@ -40,7 +108,7 @@ static int ad7476_read_raw(struct iio_dev *indio_dev, · 4 unmodified lines
40108 {
41109 int ret;
42110 struct ad7476_state *st = iio_priv(indio_dev);
43− unsigned int scale_uv;
111+ int scale_uv;
44112
45113 switch (m) {
46114 case IIO_CHAN_INFO_RAW:
@@ -57,62 +125,80 @@ static int ad7476_read_raw(struct iio_dev *indio_dev, · 10 unmodified lines
57125 RES_MASK(st->chip_info->channel[0].scan_type.realbits);
58126 return IIO_VAL_INT;
59127 case IIO_CHAN_INFO_SCALE:
60− scale_uv = (st->int_vref_mv * 1000)
61− >> st->chip_info->channel[0].scan_type.realbits;
62− *val = scale_uv/1000;
63− *val2 = (scale_uv%1000)*1000;
128+ if (!st->chip_info->int_vref_uv) {
129+ scale_uv = regulator_get_voltage(st->reg);
130+ if (scale_uv < 0)
131+ return scale_uv;
132+ } else {
133+ scale_uv = st->chip_info->int_vref_uv;
134+ }
135+ scale_uv >>= chan->scan_type.realbits;
136+ *val = scale_uv / 1000;
137+ *val2 = (scale_uv % 1000) * 1000;
64138 return IIO_VAL_INT_PLUS_MICRO;
65139 }
66140 return -EINVAL;
67141 }
68142
69−#define AD7476_CHAN(bits) \
143+#define _AD7476_CHAN(bits, _shift, _info_mask) \
70144 { \
71145 .type = IIO_VOLTAGE, \
72146 .indexed = 1, \
73− .info_mask = IIO_CHAN_INFO_RAW_SEPARATE_BIT | \
147+ .info_mask = _info_mask | \
74148 IIO_CHAN_INFO_SCALE_SHARED_BIT, \
75149 .scan_type = { \
76150 .sign = 'u', \
77− .realbits = bits, \
151+ .realbits = (bits), \
78152 .storagebits = 16, \
79− .shift = 12 - bits, \
153+ .shift = (_shift), \
154+ .endianness = IIO_BE, \
80155 }, \
81156 }
82157
158+#define AD7476_CHAN(bits) _AD7476_CHAN((bits), 13 - (bits), \
159+ IIO_CHAN_INFO_RAW_SEPARATE_BIT)
160+#define AD7940_CHAN(bits) _AD7476_CHAN((bits), 15 - (bits), \
161+ IIO_CHAN_INFO_RAW_SEPARATE_BIT)
162+#define AD7091R_CHAN(bits) _AD7476_CHAN((bits), 16 - (bits), 0)
163+
83164 static const struct ad7476_chip_info ad7476_chip_info_tbl[] = {
84− [ID_AD7466] = {
85− .channel[0] = AD7476_CHAN(12),
165+ [ID_AD7091R] = {
166+ .channel[0] = AD7091R_CHAN(12),
86167 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
168+ .reset = ad7091_reset,
87169 },
88− [ID_AD7467] = {
89− .channel[0] = AD7476_CHAN(10),
170+ [ID_AD7276] = {
171+ .channel[0] = AD7940_CHAN(12),
90172 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
91173 },
92− [ID_AD7468] = {
93− .channel[0] = AD7476_CHAN(8),
174+ [ID_AD7277] = {
175+ .channel[0] = AD7940_CHAN(10),
94176 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
95177 },
96− [ID_AD7475] = {
97− .channel[0] = AD7476_CHAN(12),
178+ [ID_AD7278] = {
179+ .channel[0] = AD7940_CHAN(8),
98180 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
99181 },
100− [ID_AD7476] = {
182+ [ID_AD7466] = {
101183 .channel[0] = AD7476_CHAN(12),
102184 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
103185 },
104− [ID_AD7477] = {
186+ [ID_AD7467] = {
105187 .channel[0] = AD7476_CHAN(10),
106188 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
107189 },
108− [ID_AD7478] = {
190+ [ID_AD7468] = {
109191 .channel[0] = AD7476_CHAN(8),
110192 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
111193 },
112194 [ID_AD7495] = {
113195 .channel[0] = AD7476_CHAN(12),
114196 .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
115− .int_vref_mv = 2500,
197+ .int_vref_uv = 2500000,
198+ },
199+ [ID_AD7940] = {
200+ .channel[0] = AD7940_CHAN(14),
201+ .channel[1] = IIO_CHAN_SOFT_TIMESTAMP(1),
116202 },
117203 };
118204
@@ -123,10 +209,9 @@ static const struct iio_info ad7476_info = { · 4 unmodified lines
123209
124210 static int __devinit ad7476_probe(struct spi_device *spi)
125211 {
126− struct ad7476_platform_data *pdata = spi->dev.platform_data;
127212 struct ad7476_state *st;
128213 struct iio_dev *indio_dev;
129− int ret, voltage_uv = 0;
214+ int ret;
130215
131216 indio_dev = iio_device_alloc(sizeof(*st));
132217 if (indio_dev == NULL) {
@@ -134,25 +219,18 @@ static int __devinit ad7476_probe(struct spi_device *spi) · 1 unmodified line
134219 goto error_ret;
135220 }
136221 st = iio_priv(indio_dev);
137− st->reg = regulator_get(&spi->dev, "vcc");
138− if (!IS_ERR(st->reg)) {
139− ret = regulator_enable(st->reg);
140− if (ret)
141− goto error_put_reg;
142−
143− voltage_uv = regulator_get_voltage(st->reg);
144− }
145222 st->chip_info =
146223 &ad7476_chip_info_tbl[spi_get_device_id(spi)->driver_data];
147224
148− if (st->chip_info->int_vref_mv)
149− st->int_vref_mv = st->chip_info->int_vref_mv;
150− else if (pdata && pdata->vref_mv)
151− st->int_vref_mv = pdata->vref_mv;
152− else if (voltage_uv)
153− st->int_vref_mv = voltage_uv / 1000;
154− else
155− dev_warn(&spi->dev, "reference voltage unspecified\n");
225+ st->reg = regulator_get(&spi->dev, "vcc");
226+ if (IS_ERR(st->reg)) {
227+ ret = PTR_ERR(st->reg);
228+ goto error_free_dev;
229+ }
230+
231+ ret = regulator_enable(st->reg);
232+ if (ret)
233+ goto error_put_reg;
156234
157235 spi_set_drvdata(spi, indio_dev);
158236
@@ -173,57 +251,67 @@ static int __devinit ad7476_probe(struct spi_device *spi) · 14 unmodified lines
173251 spi_message_init(&st->msg);
174252 spi_message_add_tail(&st->xfer, &st->msg);
175253
176− ret = ad7476_register_ring_funcs_and_init(indio_dev);
254+ ret = iio_triggered_buffer_setup(indio_dev, NULL,
255+ &ad7476_trigger_handler, NULL);
177256 if (ret)
178257 goto error_disable_reg;
179258
259+ if (st->chip_info->reset)
260+ st->chip_info->reset(st);
261+
180262 ret = iio_device_register(indio_dev);
181263 if (ret)
182264 goto error_ring_unregister;
183265 return 0;
184266
185267 error_ring_unregister:
186− ad7476_ring_cleanup(indio_dev);
268+ iio_triggered_buffer_cleanup(indio_dev);
187269 error_disable_reg:
188− if (!IS_ERR(st->reg))
189− regulator_disable(st->reg);
270+ regulator_disable(st->reg);
190271 error_put_reg:
191− if (!IS_ERR(st->reg))
192− regulator_put(st->reg);
272+ regulator_put(st->reg);
273+error_free_dev:
193274 iio_device_free(indio_dev);
194275
195276 error_ret:
196277 return ret;
197278 }
198279
199−static int ad7476_remove(struct spi_device *spi)
280+static int __devexit ad7476_remove(struct spi_device *spi)
200281 {
201282 struct iio_dev *indio_dev = spi_get_drvdata(spi);
202283 struct ad7476_state *st = iio_priv(indio_dev);
203284
204285 iio_device_unregister(indio_dev);
205− ad7476_ring_cleanup(indio_dev);
206− if (!IS_ERR(st->reg)) {
207− regulator_disable(st->reg);
208− regulator_put(st->reg);
209− }
286+ iio_triggered_buffer_cleanup(indio_dev);
287+ regulator_disable(st->reg);
288+ regulator_put(st->reg);
210289 iio_device_free(indio_dev);
211290
212291 return 0;
213292 }
214293
215294 static const struct spi_device_id ad7476_id[] = {
295+ {"ad7091r", ID_AD7091R},
296+ {"ad7273", ID_AD7277},
297+ {"ad7274", ID_AD7276},
298+ {"ad7276", ID_AD7276},
299+ {"ad7277", ID_AD7277},
300+ {"ad7278", ID_AD7278},
216301 {"ad7466", ID_AD7466},
217302 {"ad7467", ID_AD7467},
218303 {"ad7468", ID_AD7468},
219− {"ad7475", ID_AD7475},
220− {"ad7476", ID_AD7476},
221− {"ad7476a", ID_AD7476},
222− {"ad7477", ID_AD7477},
223− {"ad7477a", ID_AD7477},
224− {"ad7478", ID_AD7478},
225− {"ad7478a", ID_AD7478},
304+ {"ad7475", ID_AD7466},
305+ {"ad7476", ID_AD7466},
306+ {"ad7476a", ID_AD7466},
307+ {"ad7477", ID_AD7467},
308+ {"ad7477a", ID_AD7467},
309+ {"ad7478", ID_AD7468},
310+ {"ad7478a", ID_AD7468},
226311 {"ad7495", ID_AD7495},
312+ {"ad7910", ID_AD7467},
313+ {"ad7920", ID_AD7466},
314+ {"ad7940", ID_AD7940},
227315 {}
228316 };
229317 MODULE_DEVICE_TABLE(spi, ad7476_id);
@@ -240,5 +328,5 @@ static struct spi_driver ad7476_driver = { · 10 unmodified lines
240328 module_spi_driver(ad7476_driver);
241329
242330 MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
243−MODULE_DESCRIPTION("Analog Devices AD7475/6/7/8(A) AD7466/7/8 ADC");
331+MODULE_DESCRIPTION("Analog Devices AD7476 and similar 1-channel ADCs");
244332 MODULE_LICENSE("GPL v2");
drivers/iio/adc/ad7791.c+460−0
@@ -0,0 +1,460 @@
1+/*
2+ * AD7787/AD7788/AD7789/AD7790/AD7791 SPI ADC driver
3+ *
4+ * Copyright 2012 Analog Devices Inc.
5+ * Author: Lars-Peter Clausen <lars@metafoo.de>
6+ *
7+ * Licensed under the GPL-2.
8+ */
9+
10+#include <linux/interrupt.h>
11+#include <linux/device.h>
12+#include <linux/kernel.h>
13+#include <linux/slab.h>
14+#include <linux/sysfs.h>
15+#include <linux/spi/spi.h>
16+#include <linux/regulator/consumer.h>
17+#include <linux/err.h>
18+#include <linux/sched.h>
19+#include <linux/delay.h>
20+#include <linux/module.h>
21+
22+#include <linux/iio/iio.h>
23+#include <linux/iio/sysfs.h>
24+#include <linux/iio/buffer.h>
25+#include <linux/iio/trigger.h>
26+#include <linux/iio/trigger_consumer.h>
27+#include <linux/iio/triggered_buffer.h>
28+#include <linux/iio/adc/ad_sigma_delta.h>
29+
30+#include <linux/platform_data/ad7791.h>
31+
32+#define AD7791_REG_COMM 0x0 /* For writes */
33+#define AD7791_REG_STATUS 0x0 /* For reads */
34+#define AD7791_REG_MODE 0x1
35+#define AD7791_REG_FILTER 0x2
36+#define AD7791_REG_DATA 0x3
37+
38+#define AD7791_MODE_CONTINUOUS 0x00
39+#define AD7791_MODE_SINGLE 0x02
40+#define AD7791_MODE_POWERDOWN 0x03
41+
42+#define AD7791_CH_AIN1P_AIN1N 0x00
43+#define AD7791_CH_AIN2 0x01
44+#define AD7791_CH_AIN1N_AIN1N 0x02
45+#define AD7791_CH_AVDD_MONITOR 0x03
46+
47+#define AD7791_FILTER_CLK_DIV_1 (0x0 << 4)
48+#define AD7791_FILTER_CLK_DIV_2 (0x1 << 4)
49+#define AD7791_FILTER_CLK_DIV_4 (0x2 << 4)
50+#define AD7791_FILTER_CLK_DIV_8 (0x3 << 4)
51+#define AD7791_FILTER_CLK_MASK (0x3 << 4)
52+#define AD7791_FILTER_RATE_120 0x0
53+#define AD7791_FILTER_RATE_100 0x1
54+#define AD7791_FILTER_RATE_33_3 0x2
55+#define AD7791_FILTER_RATE_20 0x3
56+#define AD7791_FILTER_RATE_16_6 0x4
57+#define AD7791_FILTER_RATE_16_7 0x5
58+#define AD7791_FILTER_RATE_13_3 0x6
59+#define AD7791_FILTER_RATE_9_5 0x7
60+#define AD7791_FILTER_RATE_MASK 0x7
61+
62+#define AD7791_MODE_BUFFER BIT(1)
63+#define AD7791_MODE_UNIPOLAR BIT(2)
64+#define AD7791_MODE_BURNOUT BIT(3)
65+#define AD7791_MODE_SEL_MASK (0x3 << 6)
66+#define AD7791_MODE_SEL(x) ((x) << 6)
67+
68+#define DECLARE_AD7787_CHANNELS(name, bits, storagebits) \
69+const struct iio_chan_spec name[] = { \
70+ AD_SD_DIFF_CHANNEL(0, 0, 0, AD7791_CH_AIN1P_AIN1N, \
71+ (bits), (storagebits), 0), \
72+ AD_SD_CHANNEL(1, 1, AD7791_CH_AIN2, (bits), (storagebits), 0), \
73+ AD_SD_SHORTED_CHANNEL(2, 0, AD7791_CH_AIN1N_AIN1N, \
74+ (bits), (storagebits), 0), \
75+ AD_SD_SUPPLY_CHANNEL(3, 2, AD7791_CH_AVDD_MONITOR, \
76+ (bits), (storagebits), 0), \
77+ IIO_CHAN_SOFT_TIMESTAMP(4), \
78+}
79+
80+#define DECLARE_AD7791_CHANNELS(name, bits, storagebits) \
81+const struct iio_chan_spec name[] = { \
82+ AD_SD_DIFF_CHANNEL(0, 0, 0, AD7791_CH_AIN1P_AIN1N, \
83+ (bits), (storagebits), 0), \
84+ AD_SD_SHORTED_CHANNEL(1, 0, AD7791_CH_AIN1N_AIN1N, \
85+ (bits), (storagebits), 0), \
86+ AD_SD_SUPPLY_CHANNEL(2, 1, AD7791_CH_AVDD_MONITOR, \
87+ (bits), (storagebits), 0), \
88+ IIO_CHAN_SOFT_TIMESTAMP(3), \
89+}
90+
91+static DECLARE_AD7787_CHANNELS(ad7787_channels, 24, 32);
92+static DECLARE_AD7791_CHANNELS(ad7790_channels, 16, 16);
93+static DECLARE_AD7791_CHANNELS(ad7791_channels, 24, 32);
94+
95+enum {
96+ AD7787,
97+ AD7788,
98+ AD7789,
99+ AD7790,
100+ AD7791,
101+};
102+
103+enum ad7791_chip_info_flags {
104+ AD7791_FLAG_HAS_FILTER = (1 << 0),
105+ AD7791_FLAG_HAS_BUFFER = (1 << 1),
106+ AD7791_FLAG_HAS_UNIPOLAR = (1 << 2),
107+ AD7791_FLAG_HAS_BURNOUT = (1 << 3),
108+};
109+
110+struct ad7791_chip_info {
111+ const struct iio_chan_spec *channels;
112+ unsigned int num_channels;
113+ enum ad7791_chip_info_flags flags;
114+};
115+
116+static const struct ad7791_chip_info ad7791_chip_infos[] = {
117+ [AD7787] = {
118+ .channels = ad7787_channels,
119+ .num_channels = ARRAY_SIZE(ad7787_channels),
120+ .flags = AD7791_FLAG_HAS_FILTER | AD7791_FLAG_HAS_BUFFER |
121+ AD7791_FLAG_HAS_UNIPOLAR | AD7791_FLAG_HAS_BURNOUT,
122+ },
123+ [AD7788] = {
124+ .channels = ad7790_channels,
125+ .num_channels = ARRAY_SIZE(ad7790_channels),
126+ .flags = AD7791_FLAG_HAS_UNIPOLAR,
127+ },
128+ [AD7789] = {
129+ .channels = ad7791_channels,
130+ .num_channels = ARRAY_SIZE(ad7791_channels),
131+ .flags = AD7791_FLAG_HAS_UNIPOLAR,
132+ },
133+ [AD7790] = {
134+ .channels = ad7790_channels,
135+ .num_channels = ARRAY_SIZE(ad7790_channels),
136+ .flags = AD7791_FLAG_HAS_FILTER | AD7791_FLAG_HAS_BUFFER |
137+ AD7791_FLAG_HAS_BURNOUT,
138+ },
139+ [AD7791] = {
140+ .channels = ad7791_channels,
141+ .num_channels = ARRAY_SIZE(ad7791_channels),
142+ .flags = AD7791_FLAG_HAS_FILTER | AD7791_FLAG_HAS_BUFFER |
143+ AD7791_FLAG_HAS_UNIPOLAR | AD7791_FLAG_HAS_BURNOUT,
144+ },
145+};
146+
147+struct ad7791_state {
148+ struct ad_sigma_delta sd;
149+ uint8_t mode;
150+ uint8_t filter;
151+
152+ struct regulator *reg;
153+ const struct ad7791_chip_info *info;
154+};
155+
156+static struct ad7791_state *ad_sigma_delta_to_ad7791(struct ad_sigma_delta *sd)
157+{
158+ return container_of(sd, struct ad7791_state, sd);
159+}
160+
161+static int ad7791_set_channel(struct ad_sigma_delta *sd, unsigned int channel)
162+{
163+ ad_sd_set_comm(sd, channel);
164+
165+ return 0;
166+}
167+
168+static int ad7791_set_mode(struct ad_sigma_delta *sd,
169+ enum ad_sigma_delta_mode mode)
170+{
171+ struct ad7791_state *st = ad_sigma_delta_to_ad7791(sd);
172+
173+ switch (mode) {
174+ case AD_SD_MODE_CONTINUOUS:
175+ mode = AD7791_MODE_CONTINUOUS;
176+ break;
177+ case AD_SD_MODE_SINGLE:
178+ mode = AD7791_MODE_SINGLE;
179+ break;
180+ case AD_SD_MODE_IDLE:
181+ case AD_SD_MODE_POWERDOWN:
182+ mode = AD7791_MODE_POWERDOWN;
183+ break;
184+ }
185+
186+ st->mode &= ~AD7791_MODE_SEL_MASK;
187+ st->mode |= AD7791_MODE_SEL(mode);
188+
189+ return ad_sd_write_reg(sd, AD7791_REG_MODE, sizeof(st->mode), st->mode);
190+}
191+
192+static const struct ad_sigma_delta_info ad7791_sigma_delta_info = {
193+ .set_channel = ad7791_set_channel,
194+ .set_mode = ad7791_set_mode,
195+ .has_registers = true,
196+ .addr_shift = 4,
197+ .read_mask = BIT(3),
198+};
199+
200+static int ad7791_read_raw(struct iio_dev *indio_dev,
201+ const struct iio_chan_spec *chan, int *val, int *val2, long info)
202+{
203+ struct ad7791_state *st = iio_priv(indio_dev);
204+ bool unipolar = !!(st->mode & AD7791_MODE_UNIPOLAR);
205+ unsigned long long scale_pv;
206+
207+ switch (info) {
208+ case IIO_CHAN_INFO_RAW:
209+ return ad_sigma_delta_single_conversion(indio_dev, chan, val);
210+ case IIO_CHAN_INFO_OFFSET:
211+ /**
212+ * Unipolar: 0 to VREF
213+ * Bipolar -VREF to VREF
214+ **/
215+ if (unipolar)
216+ *val = 0;
217+ else
218+ *val = -(1 << (chan->scan_type.realbits - 1));
219+ return IIO_VAL_INT;
220+ case IIO_CHAN_INFO_SCALE:
221+ /* The monitor channel uses an internal reference. */
222+ if (chan->address == AD7791_CH_AVDD_MONITOR) {
223+ scale_pv = 5850000000000ULL;
224+ } else {
225+ int voltage_uv;
226+
227+ voltage_uv = regulator_get_voltage(st->reg);
228+ if (voltage_uv < 0)
229+ return voltage_uv;
230+ scale_pv = (unsigned long long)voltage_uv * 1000000;
231+ }
232+ if (unipolar)
233+ scale_pv >>= chan->scan_type.realbits;
234+ else
235+ scale_pv >>= chan->scan_type.realbits - 1;
236+ *val2 = do_div(scale_pv, 1000000000);
237+ *val = scale_pv;
238+
239+ return IIO_VAL_INT_PLUS_NANO;
240+ }
241+
242+ return -EINVAL;
243+}
244+
245+static const char * const ad7791_sample_freq_avail[] = {
246+ [AD7791_FILTER_RATE_120] = "120",
247+ [AD7791_FILTER_RATE_100] = "100",
248+ [AD7791_FILTER_RATE_33_3] = "33.3",
249+ [AD7791_FILTER_RATE_20] = "20",
250+ [AD7791_FILTER_RATE_16_6] = "16.6",
251+ [AD7791_FILTER_RATE_16_7] = "16.7",
252+ [AD7791_FILTER_RATE_13_3] = "13.3",
253+ [AD7791_FILTER_RATE_9_5] = "9.5",
254+};
255+
256+static ssize_t ad7791_read_frequency(struct device *dev,
257+ struct device_attribute *attr, char *buf)
258+{
259+ struct iio_dev *indio_dev = dev_to_iio_dev(dev);
260+ struct ad7791_state *st = iio_priv(indio_dev);
261+ unsigned int rate = st->filter & AD7791_FILTER_RATE_MASK;
262+
263+ return sprintf(buf, "%s\n", ad7791_sample_freq_avail[rate]);
264+}
265+
266+static ssize_t ad7791_write_frequency(struct device *dev,
267+ struct device_attribute *attr, const char *buf, size_t len)
268+{
269+ struct iio_dev *indio_dev = dev_to_iio_dev(dev);
270+ struct ad7791_state *st = iio_priv(indio_dev);
271+ int i, ret;
272+
273+ mutex_lock(&indio_dev->mlock);
274+ if (iio_buffer_enabled(indio_dev)) {
275+ mutex_unlock(&indio_dev->mlock);
276+ return -EBUSY;
277+ }
278+ mutex_unlock(&indio_dev->mlock);
279+
280+ ret = -EINVAL;
281+
282+ for (i = 0; i < ARRAY_SIZE(ad7791_sample_freq_avail); i++) {
283+ if (sysfs_streq(ad7791_sample_freq_avail[i], buf)) {
284+
285+ mutex_lock(&indio_dev->mlock);
286+ st->filter &= ~AD7791_FILTER_RATE_MASK;
287+ st->filter |= i;
288+ ad_sd_write_reg(&st->sd, AD7791_REG_FILTER,
289+ sizeof(st->filter), st->filter);
290+ mutex_unlock(&indio_dev->mlock);
291+ ret = 0;
292+ break;
293+ }
294+ }
295+
296+ return ret ? ret : len;
297+}
298+
299+static IIO_DEV_ATTR_SAMP_FREQ(S_IWUSR | S_IRUGO,
300+ ad7791_read_frequency,
301+ ad7791_write_frequency);
302+
303+static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("120 100 33.3 20 16.7 16.6 13.3 9.5");
304+
305+static struct attribute *ad7791_attributes[] = {
306+ &iio_dev_attr_sampling_frequency.dev_attr.attr,
307+ &iio_const_attr_sampling_frequency_available.dev_attr.attr,
308+ NULL
309+};
310+
311+static const struct attribute_group ad7791_attribute_group = {
312+ .attrs = ad7791_attributes,
313+};
314+
315+static const struct iio_info ad7791_info = {
316+ .read_raw = &ad7791_read_raw,
317+ .attrs = &ad7791_attribute_group,
318+ .validate_trigger = ad_sd_validate_trigger,
319+ .driver_module = THIS_MODULE,
320+};
321+
322+static const struct iio_info ad7791_no_filter_info = {
323+ .read_raw = &ad7791_read_raw,
324+ .validate_trigger = ad_sd_validate_trigger,
325+ .driver_module = THIS_MODULE,
326+};
327+
328+static int __devinit ad7791_setup(struct ad7791_state *st,
329+ struct ad7791_platform_data *pdata)
330+{
331+ /* Set to poweron-reset default values */
332+ st->mode = AD7791_MODE_BUFFER;
333+ st->filter = AD7791_FILTER_RATE_16_6;
334+
335+ if (!pdata)
336+ return 0;
337+
338+ if ((st->info->flags & AD7791_FLAG_HAS_BUFFER) && !pdata->buffered)
339+ st->mode &= ~AD7791_MODE_BUFFER;
340+
341+ if ((st->info->flags & AD7791_FLAG_HAS_BURNOUT) &&
342+ pdata->burnout_current)
343+ st->mode |= AD7791_MODE_BURNOUT;
344+
345+ if ((st->info->flags & AD7791_FLAG_HAS_UNIPOLAR) && pdata->unipolar)
346+ st->mode |= AD7791_MODE_UNIPOLAR;
347+
348+ return ad_sd_write_reg(&st->sd, AD7791_REG_MODE, sizeof(st->mode),
349+ st->mode);
350+}
351+
352+static int __devinit ad7791_probe(struct spi_device *spi)
353+{
354+ struct ad7791_platform_data *pdata = spi->dev.platform_data;
355+ struct iio_dev *indio_dev;
356+ struct ad7791_state *st;
357+ int ret;
358+
359+ if (!spi->irq) {
360+ dev_err(&spi->dev, "Missing IRQ.\n");
361+ return -ENXIO;
362+ }
363+
364+ indio_dev = iio_device_alloc(sizeof(*st));
365+ if (!indio_dev)
366+ return -ENOMEM;
367+
368+ st = iio_priv(indio_dev);
369+
370+ st->reg = regulator_get(&spi->dev, "refin");
371+ if (IS_ERR(st->reg)) {
372+ ret = PTR_ERR(st->reg);
373+ goto err_iio_free;
374+ }
375+
376+ ret = regulator_enable(st->reg);
377+ if (ret)
378+ goto error_put_reg;
379+
380+ st->info = &ad7791_chip_infos[spi_get_device_id(spi)->driver_data];
381+ ad_sd_init(&st->sd, indio_dev, spi, &ad7791_sigma_delta_info);
382+
383+ spi_set_drvdata(spi, indio_dev);
384+
385+ indio_dev->dev.parent = &spi->dev;
386+ indio_dev->name = spi_get_device_id(spi)->name;
387+ indio_dev->modes = INDIO_DIRECT_MODE;
388+ indio_dev->channels = st->info->channels;
389+ indio_dev->num_channels = st->info->num_channels;
390+ if (st->info->flags & AD7791_FLAG_HAS_FILTER)
391+ indio_dev->info = &ad7791_info;
392+ else
393+ indio_dev->info = &ad7791_no_filter_info;
394+
395+ ret = ad_sd_setup_buffer_and_trigger(indio_dev);
396+ if (ret)
397+ goto error_disable_reg;
398+
399+ ret = ad7791_setup(st, pdata);
400+ if (ret)
401+ goto error_remove_trigger;
402+
403+ ret = iio_device_register(indio_dev);
404+ if (ret)
405+ goto error_remove_trigger;
406+
407+ return 0;
408+
409+error_remove_trigger:
410+ ad_sd_cleanup_buffer_and_trigger(indio_dev);
411+error_disable_reg:
412+ regulator_disable(st->reg);
413+error_put_reg:
414+ regulator_put(st->reg);
415+err_iio_free:
416+ iio_device_free(indio_dev);
417+
418+ return ret;
419+}
420+
421+static int __devexit ad7791_remove(struct spi_device *spi)
422+{
423+ struct iio_dev *indio_dev = spi_get_drvdata(spi);
424+ struct ad7791_state *st = iio_priv(indio_dev);
425+
426+ iio_device_unregister(indio_dev);
427+ ad_sd_cleanup_buffer_and_trigger(indio_dev);
428+
429+ regulator_disable(st->reg);
430+ regulator_put(st->reg);
431+
432+ iio_device_free(indio_dev);
433+
434+ return 0;
435+}
436+
437+static const struct spi_device_id ad7791_spi_ids[] = {
438+ { "ad7787", AD7787 },
439+ { "ad7788", AD7788 },
440+ { "ad7789", AD7789 },
441+ { "ad7790", AD7790 },
442+ { "ad7791", AD7791 },
443+ {}
444+};
445+MODULE_DEVICE_TABLE(spi, ad7791_spi_ids);
446+
447+static struct spi_driver ad7791_driver = {
448+ .driver = {
449+ .name = "ad7791",
450+ .owner = THIS_MODULE,
451+ },
452+ .probe = ad7791_probe,
453+ .remove = __devexit_p(ad7791_remove),
454+ .id_table = ad7791_spi_ids,
455+};
456+module_spi_driver(ad7791_driver);
457+
458+MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
459+MODULE_DESCRIPTION("Analog Device AD7787/AD7788/AD7789/AD7790/AD7791 ADC driver");
460+MODULE_LICENSE("GPL v2");
drivers/iio/adc/ad_sigma_delta.c+558−0
@@ -0,0 +1,558 @@
1+/*
2+ * Support code for Analog Devices Sigma-Delta ADCs
3+ *
4+ * Copyright 2012 Analog Devices Inc.
5+ * Author: Lars-Peter Clausen <lars@metafoo.de>
6+ *
7+ * Licensed under the GPL-2.
8+ */
9+
10+#include <linux/interrupt.h>
11+#include <linux/device.h>
12+#include <linux/kernel.h>
13+#include <linux/slab.h>
14+#include <linux/spi/spi.h>
15+#include <linux/err.h>
16+#include <linux/module.h>
17+
18+#include <linux/iio/iio.h>
19+#include <linux/iio/sysfs.h>
20+#include <linux/iio/buffer.h>
21+#include <linux/iio/trigger.h>
22+#include <linux/iio/trigger_consumer.h>
23+#include <linux/iio/triggered_buffer.h>
24+#include <linux/iio/adc/ad_sigma_delta.h>
25+
26+#include <asm/unaligned.h>
27+
28+
29+#define AD_SD_COMM_CHAN_MASK 0x3
30+
31+#define AD_SD_REG_COMM 0x00
32+#define AD_SD_REG_DATA 0x03
33+
34+/**
35+ * ad_sd_set_comm() - Set communications register
36+ *
37+ * @sigma_delta: The sigma delta device
38+ * @comm: New value for the communications register
39+ */
40+void ad_sd_set_comm(struct ad_sigma_delta *sigma_delta, uint8_t comm)
41+{
42+ /* Some variants use the lower two bits of the communications register
43+ * to select the channel */
44+ sigma_delta->comm = comm & AD_SD_COMM_CHAN_MASK;
45+}
46+EXPORT_SYMBOL_GPL(ad_sd_set_comm);
47+
48+/**
49+ * ad_sd_write_reg() - Write a register
50+ *
51+ * @sigma_delta: The sigma delta device
52+ * @reg: Address of the register
53+ * @size: Size of the register (0-3)
54+ * @val: Value to write to the register
55+ *
56+ * Returns 0 on success, an error code otherwise.
57+ **/
58+int ad_sd_write_reg(struct ad_sigma_delta *sigma_delta, unsigned int reg,
59+ unsigned int size, unsigned int val)
60+{
61+ uint8_t *data = sigma_delta->data;
62+ struct spi_transfer t = {
63+ .tx_buf = data,
64+ .len = size + 1,
65+ .cs_change = sigma_delta->bus_locked,
66+ };
67+ struct spi_message m;
68+ int ret;
69+
70+ data[0] = (reg << sigma_delta->info->addr_shift) | sigma_delta->comm;
71+
72+ switch (size) {
73+ case 3:
74+ data[1] = val >> 16;
75+ data[2] = val >> 8;
76+ data[3] = val;
77+ break;
78+ case 2:
79+ put_unaligned_be16(val, &data[1]);
80+ break;
81+ case 1:
82+ data[1] = val;
83+ break;
84+ case 0:
85+ break;
86+ default:
87+ return -EINVAL;
88+ }
89+
90+ spi_message_init(&m);
91+ spi_message_add_tail(&t, &m);
92+
93+ if (sigma_delta->bus_locked)
94+ ret = spi_sync_locked(sigma_delta->spi, &m);
95+ else
96+ ret = spi_sync(sigma_delta->spi, &m);
97+
98+ return ret;
99+}
100+EXPORT_SYMBOL_GPL(ad_sd_write_reg);
101+
102+static int ad_sd_read_reg_raw(struct ad_sigma_delta *sigma_delta,
103+ unsigned int reg, unsigned int size, uint8_t *val)
104+{
105+ uint8_t *data = sigma_delta->data;
106+ int ret;
107+ struct spi_transfer t[] = {
108+ {
109+ .tx_buf = data,
110+ .len = 1,
111+ }, {
112+ .rx_buf = val,
113+ .len = size,
114+ .cs_change = sigma_delta->bus_locked,
115+ },
116+ };
117+ struct spi_message m;
118+
119+ spi_message_init(&m);
120+
121+ if (sigma_delta->info->has_registers) {
122+ data[0] = reg << sigma_delta->info->addr_shift;
123+ data[0] |= sigma_delta->info->read_mask;
124+ spi_message_add_tail(&t[0], &m);
125+ }
126+ spi_message_add_tail(&t[1], &m);
127+
128+ if (sigma_delta->bus_locked)
129+ ret = spi_sync_locked(sigma_delta->spi, &m);
130+ else
131+ ret = spi_sync(sigma_delta->spi, &m);
132+
133+ return ret;
134+}
135+
136+/**
137+ * ad_sd_read_reg() - Read a register
138+ *
139+ * @sigma_delta: The sigma delta device
140+ * @reg: Address of the register
141+ * @size: Size of the register (1-4)
142+ * @val: Read value
143+ *
144+ * Returns 0 on success, an error code otherwise.
145+ **/
146+int ad_sd_read_reg(struct ad_sigma_delta *sigma_delta,
147+ unsigned int reg, unsigned int size, unsigned int *val)
148+{
149+ int ret;
150+
151+ ret = ad_sd_read_reg_raw(sigma_delta, reg, size, sigma_delta->data);
152+ if (ret < 0)
153+ goto out;
154+
155+ switch (size) {
156+ case 4:
157+ *val = get_unaligned_be32(sigma_delta->data);
158+ break;
159+ case 3:
160+ *val = (sigma_delta->data[0] << 16) |
161+ (sigma_delta->data[1] << 8) |
162+ sigma_delta->data[2];
163+ break;
164+ case 2:
165+ *val = get_unaligned_be16(sigma_delta->data);
166+ break;
167+ case 1:
168+ *val = sigma_delta->data[0];
169+ break;
170+ default:
171+ ret = -EINVAL;
172+ break;
173+ }
174+
175+out:
176+ return ret;
177+}
178+EXPORT_SYMBOL_GPL(ad_sd_read_reg);
179+
180+static int ad_sd_calibrate(struct ad_sigma_delta *sigma_delta,
181+ unsigned int mode, unsigned int channel)
182+{
183+ int ret;
184+
185+ ret = ad_sigma_delta_set_channel(sigma_delta, channel);
186+ if (ret)
187+ return ret;
188+
189+ spi_bus_lock(sigma_delta->spi->master);
190+ sigma_delta->bus_locked = true;
191+ INIT_COMPLETION(sigma_delta->completion);
192+
193+ ret = ad_sigma_delta_set_mode(sigma_delta, mode);
194+ if (ret < 0)
195+ goto out;
196+
197+ sigma_delta->irq_dis = false;
198+ enable_irq(sigma_delta->spi->irq);
199+ ret = wait_for_completion_timeout(&sigma_delta->completion, 2*HZ);
200+ if (ret == 0) {
201+ sigma_delta->irq_dis = true;
202+ disable_irq_nosync(sigma_delta->spi->irq);
203+ ret = -EIO;
204+ } else {
205+ ret = 0;
206+ }
207+out:
208+ sigma_delta->bus_locked = false;
209+ spi_bus_unlock(sigma_delta->spi->master);
210+ ad_sigma_delta_set_mode(sigma_delta, AD_SD_MODE_IDLE);
211+
212+ return ret;
213+}
214+
215+/**
216+ * ad_sd_calibrate_all() - Performs channel calibration
217+ * @sigma_delta: The sigma delta device
218+ * @cb: Array of channels and calibration type to perform
219+ * @n: Number of items in cb
220+ *
221+ * Returns 0 on success, an error code otherwise.
222+ **/
223+int ad_sd_calibrate_all(struct ad_sigma_delta *sigma_delta,
224+ const struct ad_sd_calib_data *cb, unsigned int n)
225+{
226+ unsigned int i;
227+ int ret;
228+
229+ for (i = 0; i < n; i++) {
230+ ret = ad_sd_calibrate(sigma_delta, cb[i].mode, cb[i].channel);
231+ if (ret)
232+ return ret;
233+ }
234+
235+ return 0;
236+}
237+EXPORT_SYMBOL_GPL(ad_sd_calibrate_all);
238+
239+/**
240+ * ad_sigma_delta_single_conversion() - Performs a single data conversion
241+ * @indio_dev: The IIO device
242+ * @chan: The conversion is done for this channel
243+ * @val: Pointer to the location where to store the read value
244+ *
245+ * Returns: 0 on success, an error value otherwise.
246+ */
247+int ad_sigma_delta_single_conversion(struct iio_dev *indio_dev,
248+ const struct iio_chan_spec *chan, int *val)
249+{
250+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
251+ unsigned int sample, raw_sample;
252+ int ret = 0;
253+
254+ if (iio_buffer_enabled(indio_dev))
255+ return -EBUSY;
256+
257+ mutex_lock(&indio_dev->mlock);
258+ ad_sigma_delta_set_channel(sigma_delta, chan->address);
259+
260+ spi_bus_lock(sigma_delta->spi->master);
261+ sigma_delta->bus_locked = true;
262+ INIT_COMPLETION(sigma_delta->completion);
263+
264+ ad_sigma_delta_set_mode(sigma_delta, AD_SD_MODE_SINGLE);
265+
266+ sigma_delta->irq_dis = false;
267+ enable_irq(sigma_delta->spi->irq);
268+ ret = wait_for_completion_interruptible_timeout(
269+ &sigma_delta->completion, HZ);
270+
271+ sigma_delta->bus_locked = false;
272+ spi_bus_unlock(sigma_delta->spi->master);
273+
274+ if (ret == 0)
275+ ret = -EIO;
276+ if (ret < 0)
277+ goto out;
278+
279+ ret = ad_sd_read_reg(sigma_delta, AD_SD_REG_DATA,
280+ DIV_ROUND_UP(chan->scan_type.realbits + chan->scan_type.shift, 8),
281+ &raw_sample);
282+
283+out:
284+ if (!sigma_delta->irq_dis) {
285+ disable_irq_nosync(sigma_delta->spi->irq);
286+ sigma_delta->irq_dis = true;
287+ }
288+
289+ ad_sigma_delta_set_mode(sigma_delta, AD_SD_MODE_IDLE);
290+ mutex_unlock(&indio_dev->mlock);
291+
292+ if (ret)
293+ return ret;
294+
295+ sample = raw_sample >> chan->scan_type.shift;
296+ sample &= (1 << chan->scan_type.realbits) - 1;
297+ *val = sample;
298+
299+ ret = ad_sigma_delta_postprocess_sample(sigma_delta, raw_sample);
300+ if (ret)
301+ return ret;
302+
303+ return IIO_VAL_INT;
304+}
305+EXPORT_SYMBOL_GPL(ad_sigma_delta_single_conversion);
306+
307+static int ad_sd_buffer_postenable(struct iio_dev *indio_dev)
308+{
309+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
310+ unsigned int channel;
311+ int ret;
312+
313+ ret = iio_triggered_buffer_postenable(indio_dev);
314+ if (ret < 0)
315+ return ret;
316+
317+ channel = find_first_bit(indio_dev->active_scan_mask,
318+ indio_dev->masklength);
319+ ret = ad_sigma_delta_set_channel(sigma_delta,
320+ indio_dev->channels[channel].address);
321+ if (ret)
322+ goto err_predisable;
323+
324+ spi_bus_lock(sigma_delta->spi->master);
325+ sigma_delta->bus_locked = true;
326+ ret = ad_sigma_delta_set_mode(sigma_delta, AD_SD_MODE_CONTINUOUS);
327+ if (ret)
328+ goto err_unlock;
329+
330+ sigma_delta->irq_dis = false;
331+ enable_irq(sigma_delta->spi->irq);
332+
333+ return 0;
334+
335+err_unlock:
336+ spi_bus_unlock(sigma_delta->spi->master);
337+err_predisable:
338+
339+ return ret;
340+}
341+
342+static int ad_sd_buffer_postdisable(struct iio_dev *indio_dev)
343+{
344+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
345+
346+ INIT_COMPLETION(sigma_delta->completion);
347+ wait_for_completion_timeout(&sigma_delta->completion, HZ);
348+
349+ if (!sigma_delta->irq_dis) {
350+ disable_irq_nosync(sigma_delta->spi->irq);
351+ sigma_delta->irq_dis = true;
352+ }
353+
354+ ad_sigma_delta_set_mode(sigma_delta, AD_SD_MODE_IDLE);
355+
356+ sigma_delta->bus_locked = false;
357+ return spi_bus_unlock(sigma_delta->spi->master);
358+}
359+
360+static irqreturn_t ad_sd_trigger_handler(int irq, void *p)
361+{
362+ struct iio_poll_func *pf = p;
363+ struct iio_dev *indio_dev = pf->indio_dev;
364+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
365+ unsigned int reg_size;
366+ uint8_t data[16];
367+ int ret;
368+
369+ memset(data, 0x00, 16);
370+
371+ /* Guaranteed to be aligned with 8 byte boundary */
372+ if (indio_dev->scan_timestamp)
373+ ((s64 *)data)[1] = pf->timestamp;
374+
375+ reg_size = indio_dev->channels[0].scan_type.realbits +
376+ indio_dev->channels[0].scan_type.shift;
377+ reg_size = DIV_ROUND_UP(reg_size, 8);
378+
379+ switch (reg_size) {
380+ case 4:
381+ case 2:
382+ case 1:
383+ ret = ad_sd_read_reg_raw(sigma_delta, AD_SD_REG_DATA,
384+ reg_size, &data[0]);
385+ break;
386+ case 3:
387+ /* We store 24 bit samples in a 32 bit word. Keep the upper
388+ * byte set to zero. */
389+ ret = ad_sd_read_reg_raw(sigma_delta, AD_SD_REG_DATA,
390+ reg_size, &data[1]);
391+ break;
392+ }
393+
394+ iio_push_to_buffer(indio_dev->buffer, (uint8_t *)data);
395+
396+ iio_trigger_notify_done(indio_dev->trig);
397+ sigma_delta->irq_dis = false;
398+ enable_irq(sigma_delta->spi->irq);
399+
400+ return IRQ_HANDLED;
401+}
402+
403+static const struct iio_buffer_setup_ops ad_sd_buffer_setup_ops = {
404+ .preenable = &iio_sw_buffer_preenable,
405+ .postenable = &ad_sd_buffer_postenable,
406+ .predisable = &iio_triggered_buffer_predisable,
407+ .postdisable = &ad_sd_buffer_postdisable,
408+ .validate_scan_mask = &iio_validate_scan_mask_onehot,
409+};
410+
411+static irqreturn_t ad_sd_data_rdy_trig_poll(int irq, void *private)
412+{
413+ struct ad_sigma_delta *sigma_delta = private;
414+
415+ complete(&sigma_delta->completion);
416+ disable_irq_nosync(irq);
417+ sigma_delta->irq_dis = true;
418+ iio_trigger_poll(sigma_delta->trig, iio_get_time_ns());
419+
420+ return IRQ_HANDLED;
421+}
422+
423+/**
424+ * ad_sd_validate_trigger() - validate_trigger callback for ad_sigma_delta devices
425+ * @indio_dev: The IIO device
426+ * @trig: The new trigger
427+ *
428+ * Returns: 0 if the 'trig' matches the trigger registered by the ad_sigma_delta
429+ * device, -EINVAL otherwise.
430+ */
431+int ad_sd_validate_trigger(struct iio_dev *indio_dev, struct iio_trigger *trig)
432+{
433+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
434+
435+ if (sigma_delta->trig != trig)
436+ return -EINVAL;
437+
438+ return 0;
439+}
440+EXPORT_SYMBOL_GPL(ad_sd_validate_trigger);
441+
442+static const struct iio_trigger_ops ad_sd_trigger_ops = {
443+ .owner = THIS_MODULE,
444+};
445+
446+static int ad_sd_probe_trigger(struct iio_dev *indio_dev)
447+{
448+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
449+ int ret;
450+
451+ sigma_delta->trig = iio_trigger_alloc("%s-dev%d", indio_dev->name,
452+ indio_dev->id);
453+ if (sigma_delta->trig == NULL) {
454+ ret = -ENOMEM;
455+ goto error_ret;
456+ }
457+ sigma_delta->trig->ops = &ad_sd_trigger_ops;
458+ init_completion(&sigma_delta->completion);
459+
460+ ret = request_irq(sigma_delta->spi->irq,
461+ ad_sd_data_rdy_trig_poll,
462+ IRQF_TRIGGER_LOW,
463+ indio_dev->name,
464+ sigma_delta);
465+ if (ret)
466+ goto error_free_trig;
467+
468+ if (!sigma_delta->irq_dis) {
469+ sigma_delta->irq_dis = true;
470+ disable_irq_nosync(sigma_delta->spi->irq);
471+ }
472+ sigma_delta->trig->dev.parent = &sigma_delta->spi->dev;
473+ sigma_delta->trig->private_data = sigma_delta;
474+
475+ ret = iio_trigger_register(sigma_delta->trig);
476+ if (ret)
477+ goto error_free_irq;
478+
479+ /* select default trigger */
480+ indio_dev->trig = sigma_delta->trig;
481+
482+ return 0;
483+
484+error_free_irq:
485+ free_irq(sigma_delta->spi->irq, sigma_delta);
486+error_free_trig:
487+ iio_trigger_free(sigma_delta->trig);
488+error_ret:
489+ return ret;
490+}
491+
492+static void ad_sd_remove_trigger(struct iio_dev *indio_dev)
493+{
494+ struct ad_sigma_delta *sigma_delta = iio_device_get_drvdata(indio_dev);
495+
496+ iio_trigger_unregister(sigma_delta->trig);
497+ free_irq(sigma_delta->spi->irq, sigma_delta);
498+ iio_trigger_free(sigma_delta->trig);
499+}
500+
501+/**
502+ * ad_sd_setup_buffer_and_trigger() -
503+ * @indio_dev: The IIO device
504+ */
505+int ad_sd_setup_buffer_and_trigger(struct iio_dev *indio_dev)
506+{
507+ int ret;
508+
509+ ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time,
510+ &ad_sd_trigger_handler, &ad_sd_buffer_setup_ops);
511+ if (ret)
512+ return ret;
513+
514+ ret = ad_sd_probe_trigger(indio_dev);
515+ if (ret) {
516+ iio_triggered_buffer_cleanup(indio_dev);
517+ return ret;
518+ }
519+
520+ return 0;
521+}
522+EXPORT_SYMBOL_GPL(ad_sd_setup_buffer_and_trigger);
523+
524+/**
525+ * ad_sd_cleanup_buffer_and_trigger() -
526+ * @indio_dev: The IIO device
527+ */
528+void ad_sd_cleanup_buffer_and_trigger(struct iio_dev *indio_dev)
529+{
530+ ad_sd_remove_trigger(indio_dev);
531+ iio_triggered_buffer_cleanup(indio_dev);
532+}
533+EXPORT_SYMBOL_GPL(ad_sd_cleanup_buffer_and_trigger);
534+
535+/**
536+ * ad_sd_init() - Initializes a ad_sigma_delta struct
537+ * @sigma_delta: The ad_sigma_delta device
538+ * @indio_dev: The IIO device which the Sigma Delta device is used for
539+ * @spi: The SPI device for the ad_sigma_delta device
540+ * @info: Device specific callbacks and options
541+ *
542+ * This function needs to be called before any other operations are performed on
543+ * the ad_sigma_delta struct.
544+ */
545+int ad_sd_init(struct ad_sigma_delta *sigma_delta, struct iio_dev *indio_dev,
546+ struct spi_device *spi, const struct ad_sigma_delta_info *info)
547+{
548+ sigma_delta->spi = spi;
549+ sigma_delta->info = info;
550+ iio_device_set_drvdata(indio_dev, sigma_delta);
551+
552+ return 0;
553+}
554+EXPORT_SYMBOL_GPL(ad_sd_init);
555+
556+MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
557+MODULE_DESCRIPTION("Analog Devices Sigma-Delta ADCs");
558+MODULE_LICENSE("GPL v2");
drivers/iio/adc/at91_adc.c+18−59
@@ -82,7 +82,7 @@ static irqreturn_t at91_adc_trigger_handler(int irq, void *p) · 81 unmodified lines
8282 *timestamp = pf->timestamp;
8383 }
8484
85− buffer->access->store_to(buffer, (u8 *)st->buffer, pf->timestamp);
85+ buffer->access->store_to(buffer, (u8 *)st->buffer);
8686
8787 iio_trigger_notify_done(idev->trig);
8888 st->irq_enabled = true;
@@ -545,13 +545,6 @@ static int __devinit at91_adc_probe(struct platform_device *pdev) · 456 unmodified lines
545545 goto error_free_device;
546546 }
547547
548− res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
549− if (!res) {
550− dev_err(&pdev->dev, "No resource defined\n");
551− ret = -ENXIO;
552− goto error_ret;
553− }
554−
555548 platform_set_drvdata(pdev, idev);
556549
557550 idev->dev.parent = &pdev->dev;
@@ -566,18 +559,12 @@ static int __devinit at91_adc_probe(struct platform_device *pdev) · 8 unmodified lines
566559 goto error_free_device;
567560 }
568561
569− if (!request_mem_region(res->start, resource_size(res),
570− "AT91 adc registers")) {
571− dev_err(&pdev->dev, "Resources are unavailable.\n");
572− ret = -EBUSY;
573− goto error_free_device;
574− }
562+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
575563
576− st->reg_base = ioremap(res->start, resource_size(res));
564+ st->reg_base = devm_request_and_ioremap(&pdev->dev, res);
577565 if (!st->reg_base) {
578− dev_err(&pdev->dev, "Failed to map registers.\n");
579566 ret = -ENOMEM;
580− goto error_release_mem;
567+ goto error_free_device;
581568 }
582569
583570 /*
@@ -592,45 +579,35 @@ static int __devinit at91_adc_probe(struct platform_device *pdev) · 8 unmodified lines
592579 idev);
593580 if (ret) {
594581 dev_err(&pdev->dev, "Failed to allocate IRQ.\n");
595− goto error_unmap_reg;
582+ goto error_free_device;
596583 }
597584
598− st->clk = clk_get(&pdev->dev, "adc_clk");
585+ st->clk = devm_clk_get(&pdev->dev, "adc_clk");
599586 if (IS_ERR(st->clk)) {
600587 dev_err(&pdev->dev, "Failed to get the clock.\n");
601588 ret = PTR_ERR(st->clk);
602589 goto error_free_irq;
603590 }
604591
605− ret = clk_prepare(st->clk);
592+ ret = clk_prepare_enable(st->clk);
606593 if (ret) {
607− dev_err(&pdev->dev, "Could not prepare the clock.\n");
608− goto error_free_clk;
609− }
610−
611− ret = clk_enable(st->clk);
612− if (ret) {
613− dev_err(&pdev->dev, "Could not enable the clock.\n");
614− goto error_unprepare_clk;
594+ dev_err(&pdev->dev,
595+ "Could not prepare or enable the clock.\n");
596+ goto error_free_irq;
615597 }
616598
617− st->adc_clk = clk_get(&pdev->dev, "adc_op_clk");
599+ st->adc_clk = devm_clk_get(&pdev->dev, "adc_op_clk");
618600 if (IS_ERR(st->adc_clk)) {
619601 dev_err(&pdev->dev, "Failed to get the ADC clock.\n");
620602 ret = PTR_ERR(st->adc_clk);
621603 goto error_disable_clk;
622604 }
623605
624− ret = clk_prepare(st->adc_clk);
606+ ret = clk_prepare_enable(st->adc_clk);
625607 if (ret) {
626− dev_err(&pdev->dev, "Could not prepare the ADC clock.\n");
627− goto error_free_adc_clk;
628− }
629−
630− ret = clk_enable(st->adc_clk);
631− if (ret) {
632− dev_err(&pdev->dev, "Could not enable the ADC clock.\n");
633− goto error_unprepare_adc_clk;
608+ dev_err(&pdev->dev,
609+ "Could not prepare or enable the ADC clock.\n");
610+ goto error_disable_clk;
634611 }
635612
636613 /*
@@ -694,23 +671,11 @@ error_remove_triggers: · 57 unmodified lines
694671 error_unregister_buffer:
695672 at91_adc_buffer_remove(idev);
696673 error_disable_adc_clk:
697− clk_disable(st->adc_clk);
698−error_unprepare_adc_clk:
699− clk_unprepare(st->adc_clk);
700−error_free_adc_clk:
701− clk_put(st->adc_clk);
674+ clk_disable_unprepare(st->adc_clk);
702675 error_disable_clk:
703− clk_disable(st->clk);
704−error_unprepare_clk:
705− clk_unprepare(st->clk);
706−error_free_clk:
707− clk_put(st->clk);
676+ clk_disable_unprepare(st->clk);
708677 error_free_irq:
709678 free_irq(st->irq, idev);
710−error_unmap_reg:
711− iounmap(st->reg_base);
712−error_release_mem:
713− release_mem_region(res->start, resource_size(res));
714679 error_free_device:
715680 iio_device_free(idev);
716681 error_ret:
@@ -720,20 +685,14 @@ error_ret: · 3 unmodified lines
720685 static int __devexit at91_adc_remove(struct platform_device *pdev)
721686 {
722687 struct iio_dev *idev = platform_get_drvdata(pdev);
723− struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
724688 struct at91_adc_state *st = iio_priv(idev);
725689
726690 iio_device_unregister(idev);
727691 at91_adc_trigger_remove(idev);
728692 at91_adc_buffer_remove(idev);
729693 clk_disable_unprepare(st->adc_clk);
730− clk_put(st->adc_clk);
731− clk_disable(st->clk);
732− clk_unprepare(st->clk);
733− clk_put(st->clk);
694+ clk_disable_unprepare(st->clk);
734695 free_irq(st->irq, idev);
735− iounmap(st->reg_base);
736− release_mem_region(res->start, resource_size(res));
737696 iio_device_free(idev);
738697
739698 return 0;
drivers/iio/adc/lp8788_adc.c+264−0
@@ -0,0 +1,264 @@
1+/*
2+ * TI LP8788 MFD - ADC driver
3+ *
4+ * Copyright 2012 Texas Instruments
5+ *
6+ * Author: Milo(Woogyom) Kim <milo.kim@ti.com>
7+ *
8+ * This program is free software; you can redistribute it and/or modify
9+ * it under the terms of the GNU General Public License version 2 as
10+ * published by the Free Software Foundation.
11+ */
12+
13+#include <linux/delay.h>
14+#include <linux/iio/iio.h>
15+#include <linux/iio/driver.h>
16+#include <linux/iio/machine.h>
17+#include <linux/mfd/lp8788.h>
18+#include <linux/module.h>
19+#include <linux/mutex.h>
20+#include <linux/platform_device.h>
21+#include <linux/slab.h>
22+
23+/* register address */
24+#define LP8788_ADC_CONF 0x60
25+#define LP8788_ADC_RAW 0x61
26+#define LP8788_ADC_DONE 0x63
27+
28+#define ADC_CONV_START 1
29+
30+struct lp8788_adc {
31+ struct lp8788 *lp;
32+ struct iio_map *map;
33+ struct mutex lock;
34+};
35+
36+static const int lp8788_scale[LPADC_MAX] = {
37+ [LPADC_VBATT_5P5] = 1343101,
38+ [LPADC_VIN_CHG] = 3052503,
39+ [LPADC_IBATT] = 610500,
40+ [LPADC_IC_TEMP] = 61050,
41+ [LPADC_VBATT_6P0] = 1465201,
42+ [LPADC_VBATT_5P0] = 1221001,
43+ [LPADC_ADC1] = 610500,
44+ [LPADC_ADC2] = 610500,
45+ [LPADC_VDD] = 1025641,
46+ [LPADC_VCOIN] = 757020,
47+ [LPADC_ADC3] = 610500,
48+ [LPADC_ADC4] = 610500,
49+};
50+
51+static int lp8788_get_adc_result(struct lp8788_adc *adc, enum lp8788_adc_id id,
52+ int *val)
53+{
54+ unsigned int msb;
55+ unsigned int lsb;
56+ unsigned int result;
57+ u8 data;
58+ u8 rawdata[2];
59+ int size = ARRAY_SIZE(rawdata);
60+ int retry = 5;
61+ int ret;
62+
63+ data = (id << 1) | ADC_CONV_START;
64+ ret = lp8788_write_byte(adc->lp, LP8788_ADC_CONF, data);
65+ if (ret)
66+ goto err_io;
67+
68+ /* retry until adc conversion is done */
69+ data = 0;
70+ while (retry--) {
71+ usleep_range(100, 200);
72+
73+ ret = lp8788_read_byte(adc->lp, LP8788_ADC_DONE, &data);
74+ if (ret)
75+ goto err_io;
76+
77+ /* conversion done */
78+ if (data)
79+ break;
80+ }
81+
82+ ret = lp8788_read_multi_bytes(adc->lp, LP8788_ADC_RAW, rawdata, size);
83+ if (ret)
84+ goto err_io;
85+
86+ msb = (rawdata[0] << 4) & 0x00000ff0;
87+ lsb = (rawdata[1] >> 4) & 0x0000000f;
88+ result = msb | lsb;
89+ *val = result;
90+
91+ return 0;
92+
93+err_io:
94+ return ret;
95+}
96+
97+static int lp8788_adc_read_raw(struct iio_dev *indio_dev,
98+ struct iio_chan_spec const *chan,
99+ int *val, int *val2, long mask)
100+{
101+ struct lp8788_adc *adc = iio_priv(indio_dev);
102+ enum lp8788_adc_id id = chan->channel;
103+ int ret;
104+
105+ mutex_lock(&adc->lock);
106+
107+ switch (mask) {
108+ case IIO_CHAN_INFO_RAW:
109+ ret = lp8788_get_adc_result(adc, id, val) ? -EIO : IIO_VAL_INT;
110+ break;
111+ case IIO_CHAN_INFO_SCALE:
112+ *val = lp8788_scale[id] / 1000000;
113+ *val2 = lp8788_scale[id] % 1000000;
114+ ret = IIO_VAL_INT_PLUS_MICRO;
115+ break;
116+ default:
117+ ret = -EINVAL;
118+ break;
119+ }
120+
121+ mutex_unlock(&adc->lock);
122+
123+ return ret;
124+}
125+
126+static const struct iio_info lp8788_adc_info = {
127+ .read_raw = &lp8788_adc_read_raw,
128+ .driver_module = THIS_MODULE,
129+};
130+
131+#define LP8788_CHAN(_id, _type) { \
132+ .type = _type, \
133+ .indexed = 1, \
134+ .channel = LPADC_##_id, \
135+ .info_mask = IIO_CHAN_INFO_RAW_SEPARATE_BIT | \
136+ IIO_CHAN_INFO_SCALE_SEPARATE_BIT, \
137+ .datasheet_name = #_id, \
138+}
139+
140+static const struct iio_chan_spec lp8788_adc_channels[] = {
141+ [LPADC_VBATT_5P5] = LP8788_CHAN(VBATT_5P5, IIO_VOLTAGE),
142+ [LPADC_VIN_CHG] = LP8788_CHAN(VIN_CHG, IIO_VOLTAGE),
143+ [LPADC_IBATT] = LP8788_CHAN(IBATT, IIO_CURRENT),
144+ [LPADC_IC_TEMP] = LP8788_CHAN(IC_TEMP, IIO_TEMP),
145+ [LPADC_VBATT_6P0] = LP8788_CHAN(VBATT_6P0, IIO_VOLTAGE),
146+ [LPADC_VBATT_5P0] = LP8788_CHAN(VBATT_5P0, IIO_VOLTAGE),
147+ [LPADC_ADC1] = LP8788_CHAN(ADC1, IIO_VOLTAGE),
148+ [LPADC_ADC2] = LP8788_CHAN(ADC2, IIO_VOLTAGE),
149+ [LPADC_VDD] = LP8788_CHAN(VDD, IIO_VOLTAGE),
150+ [LPADC_VCOIN] = LP8788_CHAN(VCOIN, IIO_VOLTAGE),
151+ [LPADC_ADC3] = LP8788_CHAN(ADC3, IIO_VOLTAGE),
152+ [LPADC_ADC4] = LP8788_CHAN(ADC4, IIO_VOLTAGE),
153+};
154+
155+/* default maps used by iio consumer (lp8788-charger driver) */
156+static struct iio_map lp8788_default_iio_maps[] = {
157+ {
158+ .consumer_dev_name = "lp8788-charger",
159+ .consumer_channel = "lp8788_vbatt_5p0",
160+ .adc_channel_label = "VBATT_5P0",
161+ },
162+ {
163+ .consumer_dev_name = "lp8788-charger",
164+ .consumer_channel = "lp8788_adc1",
165+ .adc_channel_label = "ADC1",
166+ },
167+ { }
168+};
169+
170+static int lp8788_iio_map_register(struct iio_dev *indio_dev,
171+ struct lp8788_platform_data *pdata,
172+ struct lp8788_adc *adc)
173+{
174+ struct iio_map *map;
175+ int ret;
176+
177+ map = (!pdata || !pdata->adc_pdata) ?
178+ lp8788_default_iio_maps : pdata->adc_pdata;
179+
180+ ret = iio_map_array_register(indio_dev, map);
181+ if (ret) {
182+ dev_err(adc->lp->dev, "iio map err: %d\n", ret);
183+ return ret;
184+ }
185+
186+ adc->map = map;
187+ return 0;
188+}
189+
190+static inline void lp8788_iio_map_unregister(struct iio_dev *indio_dev,
191+ struct lp8788_adc *adc)
192+{
193+ iio_map_array_unregister(indio_dev, adc->map);
194+}
195+
196+static int __devinit lp8788_adc_probe(struct platform_device *pdev)
197+{
198+ struct lp8788 *lp = dev_get_drvdata(pdev->dev.parent);
199+ struct iio_dev *indio_dev;
200+ struct lp8788_adc *adc;
201+ int ret;
202+
203+ indio_dev = iio_device_alloc(sizeof(*adc));
204+ if (!indio_dev)
205+ return -ENOMEM;
206+
207+ adc = iio_priv(indio_dev);
208+ adc->lp = lp;
209+ platform_set_drvdata(pdev, indio_dev);
210+
211+ ret = lp8788_iio_map_register(indio_dev, lp->pdata, adc);
212+ if (ret)
213+ goto err_iio_map;
214+
215+ mutex_init(&adc->lock);
216+
217+ indio_dev->dev.parent = lp->dev;
218+ indio_dev->name = pdev->name;
219+ indio_dev->modes = INDIO_DIRECT_MODE;
220+ indio_dev->info = &lp8788_adc_info;
221+ indio_dev->channels = lp8788_adc_channels;
222+ indio_dev->num_channels = ARRAY_SIZE(lp8788_adc_channels);
223+
224+ ret = iio_device_register(indio_dev);
225+ if (ret) {
226+ dev_err(lp->dev, "iio dev register err: %d\n", ret);
227+ goto err_iio_device;
228+ }
229+
230+ return 0;
231+
232+err_iio_device:
233+ lp8788_iio_map_unregister(indio_dev, adc);
234+err_iio_map:
235+ iio_device_free(indio_dev);
236+ return ret;
237+}
238+
239+static int __devexit lp8788_adc_remove(struct platform_device *pdev)
240+{
241+ struct iio_dev *indio_dev = platform_get_drvdata(pdev);
242+ struct lp8788_adc *adc = iio_priv(indio_dev);
243+
244+ iio_device_unregister(indio_dev);
245+ lp8788_iio_map_unregister(indio_dev, adc);
246+ iio_device_free(indio_dev);
247+
248+ return 0;
249+}
250+
251+static struct platform_driver lp8788_adc_driver = {
252+ .probe = lp8788_adc_probe,
253+ .remove = __devexit_p(lp8788_adc_remove),
254+ .driver = {
255+ .name = LP8788_DEV_ADC,
256+ .owner = THIS_MODULE,
257+ },
258+};
259+module_platform_driver(lp8788_adc_driver);
260+
261+MODULE_DESCRIPTION("Texas Instruments LP8788 ADC Driver");
262+MODULE_AUTHOR("Milo Kim");
263+MODULE_LICENSE("GPL");
264+MODULE_ALIAS("platform:lp8788-adc");
drivers/iio/common/Kconfig+5−0
@@ -0,0 +1,5 @@
1+#
2+# IIO common modules
3+#
4+
5+source "drivers/iio/common/hid-sensors/Kconfig"
drivers/iio/common/Makefile+9−0
@@ -0,0 +1,9 @@
1+#
2+# Makefile for the IIO common modules.
3+# Common modules contains modules, which can be shared among multiple
4+# IIO modules. For example if the trigger processing is common for
5+# multiple IIO modules then this can be moved to a common module
6+# instead of duplicating in each module.
7+#
8+
9+obj-y += hid-sensors/
drivers/iio/common/hid-sensors/Kconfig+26−0
@@ -0,0 +1,26 @@
1+#
2+# Hid Sensor common modules
3+#
4+menu "Hid Sensor IIO Common"
5+
6+config HID_SENSOR_IIO_COMMON
7+ tristate "Common modules for all HID Sensor IIO drivers"
8+ depends on HID_SENSOR_HUB
9+ select IIO_TRIGGER if IIO_BUFFER
10+ help
11+ Say yes here to build support for HID sensor to use
12+ HID sensor common processing for attributes and IIO triggers.
13+ There are many attributes which can be shared among multiple
14+ HID sensor drivers, this module contains processing for those
15+ attributes.
16+
17+config HID_SENSOR_ENUM_BASE_QUIRKS
18+ tristate "ENUM base quirks for HID Sensor IIO drivers"
19+ depends on HID_SENSOR_IIO_COMMON
20+ help
21+ Say yes here to build support for sensor hub FW using
22+ enumeration, which is using 1 as base instead of 0.
23+ Since logical minimum is still set 0 instead of 1,
24+ there is no easy way to differentiate.
25+
26+endmenu
drivers/iio/common/hid-sensors/Makefile+6−0
@@ -0,0 +1,6 @@
1+#
2+# Makefile for the Hid sensor common modules.
3+#
4+
5+obj-$(CONFIG_HID_SENSOR_IIO_COMMON) += hid-sensor-iio-common.o
6+hid-sensor-iio-common-y := hid-sensor-attributes.o hid-sensor-trigger.o
drivers/iio/common/hid-sensors/hid-sensor-attributes.c+250−0
@@ -0,0 +1,250 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/sysfs.h>
28+#include "hid-sensor-attributes.h"
29+
30+static int pow_10(unsigned power)
31+{
32+ int i;
33+ int ret = 1;
34+ for (i = 0; i < power; ++i)
35+ ret = ret * 10;
36+
37+ return ret;
38+}
39+
40+static void simple_div(int dividend, int divisor, int *whole,
41+ int *micro_frac)
42+{
43+ int rem;
44+ int exp = 0;
45+
46+ *micro_frac = 0;
47+ if (divisor == 0) {
48+ *whole = 0;
49+ return;
50+ }
51+ *whole = dividend/divisor;
52+ rem = dividend % divisor;
53+ if (rem) {
54+ while (rem <= divisor) {
55+ rem *= 10;
56+ exp++;
57+ }
58+ *micro_frac = (rem / divisor) * pow_10(6-exp);
59+ }
60+}
61+
62+static void split_micro_fraction(unsigned int no, int exp, int *val1, int *val2)
63+{
64+ *val1 = no/pow_10(exp);
65+ *val2 = no%pow_10(exp) * pow_10(6-exp);
66+}
67+
68+/*
69+VTF format uses exponent and variable size format.
70+For example if the size is 2 bytes
71+0x0067 with VTF16E14 format -> +1.03
72+To convert just change to 0x67 to decimal and use two decimal as E14 stands
73+for 10^-2.
74+Negative numbers are 2's complement
75+*/
76+static void convert_from_vtf_format(u32 value, int size, int exp,
77+ int *val1, int *val2)
78+{
79+ int sign = 1;
80+
81+ if (value & BIT(size*8 - 1)) {
82+ value = ((1LL << (size * 8)) - value);
83+ sign = -1;
84+ }
85+ exp = hid_sensor_convert_exponent(exp);
86+ if (exp >= 0) {
87+ *val1 = sign * value * pow_10(exp);
88+ *val2 = 0;
89+ } else {
90+ split_micro_fraction(value, -exp, val1, val2);
91+ if (*val1)
92+ *val1 = sign * (*val1);
93+ else
94+ *val2 = sign * (*val2);
95+ }
96+}
97+
98+static u32 convert_to_vtf_format(int size, int exp, int val1, int val2)
99+{
100+ u32 value;
101+ int sign = 1;
102+
103+ if (val1 < 0 || val2 < 0)
104+ sign = -1;
105+ exp = hid_sensor_convert_exponent(exp);
106+ if (exp < 0) {
107+ value = abs(val1) * pow_10(-exp);
108+ value += abs(val2) / pow_10(6+exp);
109+ } else
110+ value = abs(val1) / pow_10(exp);
111+ if (sign < 0)
112+ value = ((1LL << (size * 8)) - value);
113+
114+ return value;
115+}
116+
117+int hid_sensor_read_samp_freq_value(struct hid_sensor_iio_common *st,
118+ int *val1, int *val2)
119+{
120+ s32 value;
121+ int ret;
122+
123+ ret = sensor_hub_get_feature(st->hsdev,
124+ st->poll.report_id,
125+ st->poll.index, &value);
126+ if (ret < 0 || value < 0) {
127+ *val1 = *val2 = 0;
128+ return -EINVAL;
129+ } else {
130+ if (st->poll.units == HID_USAGE_SENSOR_UNITS_MILLISECOND)
131+ simple_div(1000, value, val1, val2);
132+ else if (st->poll.units == HID_USAGE_SENSOR_UNITS_SECOND)
133+ simple_div(1, value, val1, val2);
134+ else {
135+ *val1 = *val2 = 0;
136+ return -EINVAL;
137+ }
138+ }
139+
140+ return IIO_VAL_INT_PLUS_MICRO;
141+}
142+EXPORT_SYMBOL(hid_sensor_read_samp_freq_value);
143+
144+int hid_sensor_write_samp_freq_value(struct hid_sensor_iio_common *st,
145+ int val1, int val2)
146+{
147+ s32 value;
148+ int ret;
149+
150+ if (val1 < 0 || val2 < 0)
151+ ret = -EINVAL;
152+
153+ value = val1 * pow_10(6) + val2;
154+ if (value) {
155+ if (st->poll.units == HID_USAGE_SENSOR_UNITS_MILLISECOND)
156+ value = pow_10(9)/value;
157+ else if (st->poll.units == HID_USAGE_SENSOR_UNITS_SECOND)
158+ value = pow_10(6)/value;
159+ else
160+ value = 0;
161+ }
162+ ret = sensor_hub_set_feature(st->hsdev,
163+ st->poll.report_id,
164+ st->poll.index, value);
165+ if (ret < 0 || value < 0)
166+ ret = -EINVAL;
167+
168+ return ret;
169+}
170+EXPORT_SYMBOL(hid_sensor_write_samp_freq_value);
171+
172+int hid_sensor_read_raw_hyst_value(struct hid_sensor_iio_common *st,
173+ int *val1, int *val2)
174+{
175+ s32 value;
176+ int ret;
177+
178+ ret = sensor_hub_get_feature(st->hsdev,
179+ st->sensitivity.report_id,
180+ st->sensitivity.index, &value);
181+ if (ret < 0 || value < 0) {
182+ *val1 = *val2 = 0;
183+ return -EINVAL;
184+ } else {
185+ convert_from_vtf_format(value, st->sensitivity.size,
186+ st->sensitivity.unit_expo,
187+ val1, val2);
188+ }
189+
190+ return IIO_VAL_INT_PLUS_MICRO;
191+}
192+EXPORT_SYMBOL(hid_sensor_read_raw_hyst_value);
193+
194+int hid_sensor_write_raw_hyst_value(struct hid_sensor_iio_common *st,
195+ int val1, int val2)
196+{
197+ s32 value;
198+ int ret;
199+
200+ value = convert_to_vtf_format(st->sensitivity.size,
201+ st->sensitivity.unit_expo,
202+ val1, val2);
203+ ret = sensor_hub_set_feature(st->hsdev,
204+ st->sensitivity.report_id,
205+ st->sensitivity.index, value);
206+ if (ret < 0 || value < 0)
207+ ret = -EINVAL;
208+
209+ return ret;
210+}
211+EXPORT_SYMBOL(hid_sensor_write_raw_hyst_value);
212+
213+int hid_sensor_parse_common_attributes(struct hid_sensor_hub_device *hsdev,
214+ u32 usage_id,
215+ struct hid_sensor_iio_common *st)
216+{
217+
218+ sensor_hub_input_get_attribute_info(hsdev,
219+ HID_FEATURE_REPORT, usage_id,
220+ HID_USAGE_SENSOR_PROP_REPORT_INTERVAL,
221+ &st->poll);
222+
223+ sensor_hub_input_get_attribute_info(hsdev,
224+ HID_FEATURE_REPORT, usage_id,
225+ HID_USAGE_SENSOR_PROP_REPORT_STATE,
226+ &st->report_state);
227+
228+ sensor_hub_input_get_attribute_info(hsdev,
229+ HID_FEATURE_REPORT, usage_id,
230+ HID_USAGE_SENSOR_PROY_POWER_STATE,
231+ &st->power_state);
232+
233+ sensor_hub_input_get_attribute_info(hsdev,
234+ HID_FEATURE_REPORT, usage_id,
235+ HID_USAGE_SENSOR_PROP_SENSITIVITY_ABS,
236+ &st->sensitivity);
237+
238+ hid_dbg(hsdev->hdev, "common attributes: %x:%x, %x:%x, %x:%x %x:%x\n",
239+ st->poll.index, st->poll.report_id,
240+ st->report_state.index, st->report_state.report_id,
241+ st->power_state.index, st->power_state.report_id,
242+ st->sensitivity.index, st->sensitivity.report_id);
243+
244+ return 0;
245+}
246+EXPORT_SYMBOL(hid_sensor_parse_common_attributes);
247+
248+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
249+MODULE_DESCRIPTION("HID Sensor common attribute processing");
250+MODULE_LICENSE("GPL");
drivers/iio/common/hid-sensors/hid-sensor-attributes.h+57−0
@@ -0,0 +1,57 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#ifndef _HID_SENSORS_ATTRIBUTES_H
20+#define _HID_SENSORS_ATTRIBUTES_H
21+
22+/* Common hid sensor iio structure */
23+struct hid_sensor_iio_common {
24+ struct hid_sensor_hub_device *hsdev;
25+ struct platform_device *pdev;
26+ unsigned usage_id;
27+ bool data_ready;
28+ struct hid_sensor_hub_attribute_info poll;
29+ struct hid_sensor_hub_attribute_info report_state;
30+ struct hid_sensor_hub_attribute_info power_state;
31+ struct hid_sensor_hub_attribute_info sensitivity;
32+};
33+
34+/*Convert from hid unit expo to regular exponent*/
35+static inline int hid_sensor_convert_exponent(int unit_expo)
36+{
37+ if (unit_expo < 0x08)
38+ return unit_expo;
39+ else if (unit_expo <= 0x0f)
40+ return -(0x0f-unit_expo+1);
41+ else
42+ return 0;
43+}
44+
45+int hid_sensor_parse_common_attributes(struct hid_sensor_hub_device *hsdev,
46+ u32 usage_id,
47+ struct hid_sensor_iio_common *st);
48+int hid_sensor_write_raw_hyst_value(struct hid_sensor_iio_common *st,
49+ int val1, int val2);
50+int hid_sensor_read_raw_hyst_value(struct hid_sensor_iio_common *st,
51+ int *val1, int *val2);
52+int hid_sensor_write_samp_freq_value(struct hid_sensor_iio_common *st,
53+ int val1, int val2);
54+int hid_sensor_read_samp_freq_value(struct hid_sensor_iio_common *st,
55+ int *val1, int *val2);
56+
57+#endif
drivers/iio/common/hid-sensors/hid-sensor-trigger.c+103−0
@@ -0,0 +1,103 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/trigger.h>
28+#include <linux/iio/sysfs.h>
29+#include "hid-sensor-attributes.h"
30+#include "hid-sensor-trigger.h"
31+
32+static int hid_sensor_data_rdy_trigger_set_state(struct iio_trigger *trig,
33+ bool state)
34+{
35+ struct hid_sensor_iio_common *st = trig->private_data;
36+ int state_val;
37+
38+ state_val = state ? 1 : 0;
39+#if (defined CONFIG_HID_SENSOR_ENUM_BASE_QUIRKS) || \
40+ (defined CONFIG_HID_SENSOR_ENUM_BASE_QUIRKS_MODULE)
41+ ++state_val;
42+#endif
43+ st->data_ready = state;
44+ sensor_hub_set_feature(st->hsdev, st->power_state.report_id,
45+ st->power_state.index,
46+ (s32)state_val);
47+
48+ sensor_hub_set_feature(st->hsdev, st->report_state.report_id,
49+ st->report_state.index,
50+ (s32)state_val);
51+
52+ return 0;
53+}
54+
55+void hid_sensor_remove_trigger(struct iio_dev *indio_dev)
56+{
57+ iio_trigger_unregister(indio_dev->trig);
58+ iio_trigger_free(indio_dev->trig);
59+ indio_dev->trig = NULL;
60+}
61+EXPORT_SYMBOL(hid_sensor_remove_trigger);
62+
63+static const struct iio_trigger_ops hid_sensor_trigger_ops = {
64+ .owner = THIS_MODULE,
65+ .set_trigger_state = &hid_sensor_data_rdy_trigger_set_state,
66+};
67+
68+int hid_sensor_setup_trigger(struct iio_dev *indio_dev, const char *name,
69+ struct hid_sensor_iio_common *attrb)
70+{
71+ int ret;
72+ struct iio_trigger *trig;
73+
74+ trig = iio_trigger_alloc("%s-dev%d", name, indio_dev->id);
75+ if (trig == NULL) {
76+ dev_err(&indio_dev->dev, "Trigger Allocate Failed\n");
77+ ret = -ENOMEM;
78+ goto error_ret;
79+ }
80+
81+ trig->dev.parent = indio_dev->dev.parent;
82+ trig->private_data = attrb;
83+ trig->ops = &hid_sensor_trigger_ops;
84+ ret = iio_trigger_register(trig);
85+
86+ if (ret) {
87+ dev_err(&indio_dev->dev, "Trigger Register Failed\n");
88+ goto error_free_trig;
89+ }
90+ indio_dev->trig = trig;
91+
92+ return ret;
93+
94+error_free_trig:
95+ iio_trigger_free(trig);
96+error_ret:
97+ return ret;
98+}
99+EXPORT_SYMBOL(hid_sensor_setup_trigger);
100+
101+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
102+MODULE_DESCRIPTION("HID Sensor trigger processing");
103+MODULE_LICENSE("GPL");
drivers/iio/common/hid-sensors/hid-sensor-trigger.h+26−0
@@ -0,0 +1,26 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#ifndef _HID_SENSOR_TRIGGER_H
20+#define _HID_SENSOR_TRIGGER_H
21+
22+int hid_sensor_setup_trigger(struct iio_dev *indio_dev, const char *name,
23+ struct hid_sensor_iio_common *attrb);
24+void hid_sensor_remove_trigger(struct iio_dev *indio_dev);
25+
26+#endif
drivers/iio/dac/Kconfig+16−4
@@ -57,11 +57,12 @@ config AD5624R_SPI · 56 unmodified lines
5757
5858 config AD5446
5959 tristate "Analog Devices AD5446 and similar single channel DACs driver"
60− depends on SPI
60+ depends on (SPI_MASTER || I2C)
6161 help
62− Say yes here to build support for Analog Devices AD5444, AD5446, AD5450,
63− AD5451, AD5452, AD5453, AD5512A, AD5541A, AD5542A, AD5543, AD5553, AD5601,
64− AD5611, AD5620, AD5621, AD5640, AD5660, AD5662 DACs.
62+ Say yes here to build support for Analog Devices AD5300, AD5301, AD5310,
63+ AD5311, AD5320, AD5321, AD5444, AD5446, AD5450, AD5451, AD5452, AD5453,
64+ AD5512A, AD5541A, AD5542A, AD5543, AD5553, AD5601, AD5602, AD5611, AD5612,
65+ AD5620, AD5621, AD5622, AD5640, AD5660, AD5662 DACs.
6566
6667 To compile this driver as a module, choose M here: the
6768 module will be called ad5446.
@@ -76,6 +77,17 @@ config AD5504 · 8 unmodified lines
7677 To compile this driver as a module, choose M here: the
7778 module will be called ad5504.
7879
80+config AD5755
81+ tristate "Analog Devices AD5755/AD5755-1/AD5757/AD5735/AD5737 DAC driver"
82+ depends on SPI_MASTER
83+ help
84+ Say yes here to build support for Analog Devices AD5755, AD5755-1,
85+ AD5757, AD5735, AD5737 quad channel Digital to
86+ Analog Converter.
87+
88+ To compile this driver as a module, choose M here: the
89+ module will be called ad5755.
90+
7991 config AD5764
8092 tristate "Analog Devices AD5764/64R/44/44R DAC driver"
8193 depends on SPI_MASTER
drivers/iio/dac/Makefile+1−0
@@ -9,6 +9,7 @@ obj-$(CONFIG_AD5624R_SPI) += ad5624r_spi.o · 8 unmodified lines
99 obj-$(CONFIG_AD5064) += ad5064.o
1010 obj-$(CONFIG_AD5504) += ad5504.o
1111 obj-$(CONFIG_AD5446) += ad5446.o
12+obj-$(CONFIG_AD5755) += ad5755.o
1213 obj-$(CONFIG_AD5764) += ad5764.o
1314 obj-$(CONFIG_AD5791) += ad5791.o
1415 obj-$(CONFIG_AD5686) += ad5686.o
drivers/iio/dac/ad5446.c+338−112
@@ -14,6 +14,7 @@ · 13 unmodified lines
1414 #include <linux/sysfs.h>
1515 #include <linux/list.h>
1616 #include <linux/spi/spi.h>
17+#include <linux/i2c.h>
1718 #include <linux/regulator/consumer.h>
1819 #include <linux/err.h>
1920 #include <linux/module.h>
@@ -21,24 +22,40 @@ · 1 unmodified line
2122 #include <linux/iio/iio.h>
2223 #include <linux/iio/sysfs.h>
2324
24−#include "ad5446.h"
25+#define MODE_PWRDWN_1k 0x1
26+#define MODE_PWRDWN_100k 0x2
27+#define MODE_PWRDWN_TRISTATE 0x3
2528
26−static int ad5446_write(struct ad5446_state *st, unsigned val)
27−{
28− __be16 data = cpu_to_be16(val);
29− return spi_write(st->spi, &data, sizeof(data));
30−}
29+/**
30+ * struct ad5446_state - driver instance specific data
31+ * @spi: spi_device
32+ * @chip_info: chip model specific constants, available modes etc
33+ * @reg: supply regulator
34+ * @vref_mv: actual reference voltage used
35+ */
3136
32−static int ad5660_write(struct ad5446_state *st, unsigned val)
33−{
34− uint8_t data[3];
37+struct ad5446_state {
38+ struct device *dev;
39+ const struct ad5446_chip_info *chip_info;
40+ struct regulator *reg;
41+ unsigned short vref_mv;
42+ unsigned cached_val;
43+ unsigned pwr_down_mode;
44+ unsigned pwr_down;
45+};
3546
36− data[0] = (val >> 16) & 0xFF;
37− data[1] = (val >> 8) & 0xFF;
38− data[2] = val & 0xFF;
47+/**
48+ * struct ad5446_chip_info - chip specific information
49+ * @channel: channel spec for the DAC
50+ * @int_vref_mv: AD5620/40/60: the internal reference voltage
51+ * @write: chip specific helper function to write to the register
52+ */
3953
40− return spi_write(st->spi, data, sizeof(data));
41−}
54+struct ad5446_chip_info {
55+ struct iio_chan_spec channel;
56+ u16 int_vref_mv;
57+ int (*write)(struct ad5446_state *st, unsigned val);
58+};
4259
4360 static const char * const ad5446_powerdown_modes[] = {
4461 "1kohm_to_gnd", "100kohm_to_gnd", "three_state"
@@ -110,7 +127,7 @@ static ssize_t ad5446_write_dac_powerdown(struct iio_dev *indio_dev, · 65 unmodified lines
110127 return ret ? ret : len;
111128 }
112129
113−static const struct iio_chan_spec_ext_info ad5064_ext_info_powerdown[] = {
130+static const struct iio_chan_spec_ext_info ad5446_ext_info_powerdown[] = {
114131 {
115132 .name = "powerdown",
116133 .read = ad5446_read_dac_powerdown,
@@ -136,84 +153,7 @@ static const struct iio_chan_spec_ext_info ad5064_ext_info_powerdown[] = { · 19 unmodified lines
136153 _AD5446_CHANNEL(bits, storage, shift, NULL)
137154
138155 #define AD5446_CHANNEL_POWERDOWN(bits, storage, shift) \
139− _AD5446_CHANNEL(bits, storage, shift, ad5064_ext_info_powerdown)
140−
141−static const struct ad5446_chip_info ad5446_chip_info_tbl[] = {
142− [ID_AD5444] = {
143− .channel = AD5446_CHANNEL(12, 16, 2),
144− .write = ad5446_write,
145− },
146− [ID_AD5446] = {
147− .channel = AD5446_CHANNEL(14, 16, 0),
148− .write = ad5446_write,
149− },
150− [ID_AD5450] = {
151− .channel = AD5446_CHANNEL(8, 16, 6),
152− .write = ad5446_write,
153− },
154− [ID_AD5451] = {
155− .channel = AD5446_CHANNEL(10, 16, 4),
156− .write = ad5446_write,
157− },
158− [ID_AD5541A] = {
159− .channel = AD5446_CHANNEL(16, 16, 0),
160− .write = ad5446_write,
161− },
162− [ID_AD5512A] = {
163− .channel = AD5446_CHANNEL(12, 16, 4),
164− .write = ad5446_write,
165− },
166− [ID_AD5553] = {
167− .channel = AD5446_CHANNEL(14, 16, 0),
168− .write = ad5446_write,
169− },
170− [ID_AD5601] = {
171− .channel = AD5446_CHANNEL_POWERDOWN(8, 16, 6),
172− .write = ad5446_write,
173− },
174− [ID_AD5611] = {
175− .channel = AD5446_CHANNEL_POWERDOWN(10, 16, 4),
176− .write = ad5446_write,
177− },
178− [ID_AD5621] = {
179− .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
180− .write = ad5446_write,
181− },
182− [ID_AD5620_2500] = {
183− .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
184− .int_vref_mv = 2500,
185− .write = ad5446_write,
186− },
187− [ID_AD5620_1250] = {
188− .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
189− .int_vref_mv = 1250,
190− .write = ad5446_write,
191− },
192− [ID_AD5640_2500] = {
193− .channel = AD5446_CHANNEL_POWERDOWN(14, 16, 0),
194− .int_vref_mv = 2500,
195− .write = ad5446_write,
196− },
197− [ID_AD5640_1250] = {
198− .channel = AD5446_CHANNEL_POWERDOWN(14, 16, 0),
199− .int_vref_mv = 1250,
200− .write = ad5446_write,
201− },
202− [ID_AD5660_2500] = {
203− .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
204− .int_vref_mv = 2500,
205− .write = ad5660_write,
206− },
207− [ID_AD5660_1250] = {
208− .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
209− .int_vref_mv = 1250,
210− .write = ad5660_write,
211− },
212− [ID_AD5662] = {
213− .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
214− .write = ad5660_write,
215− },
216−};
156+ _AD5446_CHANNEL(bits, storage, shift, ad5446_ext_info_powerdown)
217157
218158 static int ad5446_read_raw(struct iio_dev *indio_dev,
219159 struct iio_chan_spec const *chan,
@@ -272,14 +212,15 @@ static const struct iio_info ad5446_info = { · 52 unmodified lines
272212 .driver_module = THIS_MODULE,
273213 };
274214
275−static int __devinit ad5446_probe(struct spi_device *spi)
215+static int __devinit ad5446_probe(struct device *dev, const char *name,
216+ const struct ad5446_chip_info *chip_info)
276217 {
277218 struct ad5446_state *st;
278219 struct iio_dev *indio_dev;
279220 struct regulator *reg;
280221 int ret, voltage_uv = 0;
281222
282− reg = regulator_get(&spi->dev, "vcc");
223+ reg = regulator_get(dev, "vcc");
283224 if (!IS_ERR(reg)) {
284225 ret = regulator_enable(reg);
285226 if (ret)
@@ -294,16 +235,15 @@ static int __devinit ad5446_probe(struct spi_device *spi) · 8 unmodified lines
294235 goto error_disable_reg;
295236 }
296237 st = iio_priv(indio_dev);
297− st->chip_info =
298− &ad5446_chip_info_tbl[spi_get_device_id(spi)->driver_data];
238+ st->chip_info = chip_info;
299239
300− spi_set_drvdata(spi, indio_dev);
240+ dev_set_drvdata(dev, indio_dev);
301241 st->reg = reg;
302− st->spi = spi;
242+ st->dev = dev;
303243
304− /* Establish that the iio_dev is a child of the spi device */
305− indio_dev->dev.parent = &spi->dev;
306− indio_dev->name = spi_get_device_id(spi)->name;
244+ /* Establish that the iio_dev is a child of the device */
245+ indio_dev->dev.parent = dev;
246+ indio_dev->name = name;
307247 indio_dev->info = &ad5446_info;
308248 indio_dev->modes = INDIO_DIRECT_MODE;
309249 indio_dev->channels = &st->chip_info->channel;
@@ -316,7 +256,7 @@ static int __devinit ad5446_probe(struct spi_device *spi) · 6 unmodified lines
316256 else if (voltage_uv)
317257 st->vref_mv = voltage_uv / 1000;
318258 else
319− dev_warn(&spi->dev, "reference voltage unspecified\n");
259+ dev_warn(dev, "reference voltage unspecified\n");
320260
321261 ret = iio_device_register(indio_dev);
322262 if (ret)
@@ -336,9 +276,9 @@ error_put_reg: · 13 unmodified lines
336276 return ret;
337277 }
338278
339−static int ad5446_remove(struct spi_device *spi)
279+static int ad5446_remove(struct device *dev)
340280 {
341− struct iio_dev *indio_dev = spi_get_drvdata(spi);
281+ struct iio_dev *indio_dev = dev_get_drvdata(dev);
342282 struct ad5446_state *st = iio_priv(indio_dev);
343283
344284 iio_device_unregister(indio_dev);
@@ -351,7 +291,151 @@ static int ad5446_remove(struct spi_device *spi) · 6 unmodified lines
351291 return 0;
352292 }
353293
354−static const struct spi_device_id ad5446_id[] = {
294+#if IS_ENABLED(CONFIG_SPI_MASTER)
295+
296+static int ad5446_write(struct ad5446_state *st, unsigned val)
297+{
298+ struct spi_device *spi = to_spi_device(st->dev);
299+ __be16 data = cpu_to_be16(val);
300+
301+ return spi_write(spi, &data, sizeof(data));
302+}
303+
304+static int ad5660_write(struct ad5446_state *st, unsigned val)
305+{
306+ struct spi_device *spi = to_spi_device(st->dev);
307+ uint8_t data[3];
308+
309+ data[0] = (val >> 16) & 0xFF;
310+ data[1] = (val >> 8) & 0xFF;
311+ data[2] = val & 0xFF;
312+
313+ return spi_write(spi, data, sizeof(data));
314+}
315+
316+/**
317+ * ad5446_supported_spi_device_ids:
318+ * The AD5620/40/60 parts are available in different fixed internal reference
319+ * voltage options. The actual part numbers may look differently
320+ * (and a bit cryptic), however this style is used to make clear which
321+ * parts are supported here.
322+ */
323+enum ad5446_supported_spi_device_ids {
324+ ID_AD5300,
325+ ID_AD5310,
326+ ID_AD5320,
327+ ID_AD5444,
328+ ID_AD5446,
329+ ID_AD5450,
330+ ID_AD5451,
331+ ID_AD5541A,
332+ ID_AD5512A,
333+ ID_AD5553,
334+ ID_AD5601,
335+ ID_AD5611,
336+ ID_AD5621,
337+ ID_AD5620_2500,
338+ ID_AD5620_1250,
339+ ID_AD5640_2500,
340+ ID_AD5640_1250,
341+ ID_AD5660_2500,
342+ ID_AD5660_1250,
343+ ID_AD5662,
344+};
345+
346+static const struct ad5446_chip_info ad5446_spi_chip_info[] = {
347+ [ID_AD5300] = {
348+ .channel = AD5446_CHANNEL_POWERDOWN(8, 16, 4),
349+ .write = ad5446_write,
350+ },
351+ [ID_AD5310] = {
352+ .channel = AD5446_CHANNEL_POWERDOWN(10, 16, 2),
353+ .write = ad5446_write,
354+ },
355+ [ID_AD5320] = {
356+ .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 0),
357+ .write = ad5446_write,
358+ },
359+ [ID_AD5444] = {
360+ .channel = AD5446_CHANNEL(12, 16, 2),
361+ .write = ad5446_write,
362+ },
363+ [ID_AD5446] = {
364+ .channel = AD5446_CHANNEL(14, 16, 0),
365+ .write = ad5446_write,
366+ },
367+ [ID_AD5450] = {
368+ .channel = AD5446_CHANNEL(8, 16, 6),
369+ .write = ad5446_write,
370+ },
371+ [ID_AD5451] = {
372+ .channel = AD5446_CHANNEL(10, 16, 4),
373+ .write = ad5446_write,
374+ },
375+ [ID_AD5541A] = {
376+ .channel = AD5446_CHANNEL(16, 16, 0),
377+ .write = ad5446_write,
378+ },
379+ [ID_AD5512A] = {
380+ .channel = AD5446_CHANNEL(12, 16, 4),
381+ .write = ad5446_write,
382+ },
383+ [ID_AD5553] = {
384+ .channel = AD5446_CHANNEL(14, 16, 0),
385+ .write = ad5446_write,
386+ },
387+ [ID_AD5601] = {
388+ .channel = AD5446_CHANNEL_POWERDOWN(8, 16, 6),
389+ .write = ad5446_write,
390+ },
391+ [ID_AD5611] = {
392+ .channel = AD5446_CHANNEL_POWERDOWN(10, 16, 4),
393+ .write = ad5446_write,
394+ },
395+ [ID_AD5621] = {
396+ .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
397+ .write = ad5446_write,
398+ },
399+ [ID_AD5620_2500] = {
400+ .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
401+ .int_vref_mv = 2500,
402+ .write = ad5446_write,
403+ },
404+ [ID_AD5620_1250] = {
405+ .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 2),
406+ .int_vref_mv = 1250,
407+ .write = ad5446_write,
408+ },
409+ [ID_AD5640_2500] = {
410+ .channel = AD5446_CHANNEL_POWERDOWN(14, 16, 0),
411+ .int_vref_mv = 2500,
412+ .write = ad5446_write,
413+ },
414+ [ID_AD5640_1250] = {
415+ .channel = AD5446_CHANNEL_POWERDOWN(14, 16, 0),
416+ .int_vref_mv = 1250,
417+ .write = ad5446_write,
418+ },
419+ [ID_AD5660_2500] = {
420+ .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
421+ .int_vref_mv = 2500,
422+ .write = ad5660_write,
423+ },
424+ [ID_AD5660_1250] = {
425+ .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
426+ .int_vref_mv = 1250,
427+ .write = ad5660_write,
428+ },
429+ [ID_AD5662] = {
430+ .channel = AD5446_CHANNEL_POWERDOWN(16, 16, 0),
431+ .write = ad5660_write,
432+ },
433+};
434+
435+static const struct spi_device_id ad5446_spi_ids[] = {
436+ {"ad5300", ID_AD5300},
437+ {"ad5310", ID_AD5310},
438+ {"ad5320", ID_AD5320},
355439 {"ad5444", ID_AD5444},
356440 {"ad5446", ID_AD5446},
357441 {"ad5450", ID_AD5450},
@@ -375,18 +459,160 @@ static const struct spi_device_id ad5446_id[] = { · 17 unmodified lines
375459 {"ad5662", ID_AD5662},
376460 {}
377461 };
378−MODULE_DEVICE_TABLE(spi, ad5446_id);
462+MODULE_DEVICE_TABLE(spi, ad5446_spi_ids);
463+
464+static int __devinit ad5446_spi_probe(struct spi_device *spi)
465+{
466+ const struct spi_device_id *id = spi_get_device_id(spi);
379467
380−static struct spi_driver ad5446_driver = {
468+ return ad5446_probe(&spi->dev, id->name,
469+ &ad5446_spi_chip_info[id->driver_data]);
470+}
471+
472+static int __devexit ad5446_spi_remove(struct spi_device *spi)
473+{
474+ return ad5446_remove(&spi->dev);
475+}
476+
477+static struct spi_driver ad5446_spi_driver = {
381478 .driver = {
382479 .name = "ad5446",
383480 .owner = THIS_MODULE,
384481 },
385− .probe = ad5446_probe,
386− .remove = __devexit_p(ad5446_remove),
387− .id_table = ad5446_id,
482+ .probe = ad5446_spi_probe,
483+ .remove = __devexit_p(ad5446_spi_remove),
484+ .id_table = ad5446_spi_ids,
388485 };
389−module_spi_driver(ad5446_driver);
486+
487+static int __init ad5446_spi_register_driver(void)
488+{
489+ return spi_register_driver(&ad5446_spi_driver);
490+}
491+
492+static void ad5446_spi_unregister_driver(void)
493+{
494+ spi_unregister_driver(&ad5446_spi_driver);
495+}
496+
497+#else
498+
499+static inline int ad5446_spi_register_driver(void) { return 0; }
500+static inline void ad5446_spi_unregister_driver(void) { }
501+
502+#endif
503+
504+#if IS_ENABLED(CONFIG_I2C)
505+
506+static int ad5622_write(struct ad5446_state *st, unsigned val)
507+{
508+ struct i2c_client *client = to_i2c_client(st->dev);
509+ __be16 data = cpu_to_be16(val);
510+
511+ return i2c_master_send(client, (char *)&data, sizeof(data));
512+}
513+
514+/**
515+ * ad5446_supported_i2c_device_ids:
516+ * The AD5620/40/60 parts are available in different fixed internal reference
517+ * voltage options. The actual part numbers may look differently
518+ * (and a bit cryptic), however this style is used to make clear which
519+ * parts are supported here.
520+ */
521+enum ad5446_supported_i2c_device_ids {
522+ ID_AD5602,
523+ ID_AD5612,
524+ ID_AD5622,
525+};
526+
527+static const struct ad5446_chip_info ad5446_i2c_chip_info[] = {
528+ [ID_AD5602] = {
529+ .channel = AD5446_CHANNEL_POWERDOWN(8, 16, 4),
530+ .write = ad5622_write,
531+ },
532+ [ID_AD5612] = {
533+ .channel = AD5446_CHANNEL_POWERDOWN(10, 16, 2),
534+ .write = ad5622_write,
535+ },
536+ [ID_AD5622] = {
537+ .channel = AD5446_CHANNEL_POWERDOWN(12, 16, 0),
538+ .write = ad5622_write,
539+ },
540+};
541+
542+static int __devinit ad5446_i2c_probe(struct i2c_client *i2c,
543+ const struct i2c_device_id *id)
544+{
545+ return ad5446_probe(&i2c->dev, id->name,
546+ &ad5446_i2c_chip_info[id->driver_data]);
547+}
548+
549+static int __devexit ad5446_i2c_remove(struct i2c_client *i2c)
550+{
551+ return ad5446_remove(&i2c->dev);
552+}
553+
554+static const struct i2c_device_id ad5446_i2c_ids[] = {
555+ {"ad5301", ID_AD5602},
556+ {"ad5311", ID_AD5612},
557+ {"ad5321", ID_AD5622},
558+ {"ad5602", ID_AD5602},
559+ {"ad5612", ID_AD5612},
560+ {"ad5622", ID_AD5622},
561+ {}
562+};
563+MODULE_DEVICE_TABLE(i2c, ad5446_i2c_ids);
564+
565+static struct i2c_driver ad5446_i2c_driver = {
566+ .driver = {
567+ .name = "ad5446",
568+ .owner = THIS_MODULE,
569+ },
570+ .probe = ad5446_i2c_probe,
571+ .remove = __devexit_p(ad5446_i2c_remove),
572+ .id_table = ad5446_i2c_ids,
573+};
574+
575+static int __init ad5446_i2c_register_driver(void)
576+{
577+ return i2c_add_driver(&ad5446_i2c_driver);
578+}
579+
580+static void __exit ad5446_i2c_unregister_driver(void)
581+{
582+ i2c_del_driver(&ad5446_i2c_driver);
583+}
584+
585+#else
586+
587+static inline int ad5446_i2c_register_driver(void) { return 0; }
588+static inline void ad5446_i2c_unregister_driver(void) { }
589+
590+#endif
591+
592+static int __init ad5446_init(void)
593+{
594+ int ret;
595+
596+ ret = ad5446_spi_register_driver();
597+ if (ret)
598+ return ret;
599+
600+ ret = ad5446_i2c_register_driver();
601+ if (ret) {
602+ ad5446_spi_unregister_driver();
603+ return ret;
604+ }
605+
606+ return 0;
607+}
608+module_init(ad5446_init);
609+
610+static void __exit ad5446_exit(void)
611+{
612+ ad5446_i2c_unregister_driver();
613+ ad5446_spi_unregister_driver();
614+}
615+module_exit(ad5446_exit);
390616
391617 MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
392618 MODULE_DESCRIPTION("Analog Devices AD5444/AD5446 DAC");
drivers/iio/dac/ad5446.h+0−91
@@ -1,91 +0,0 @@
1−/*
2− * AD5446 SPI DAC driver
3− *
4− * Copyright 2010 Analog Devices Inc.
5− *
6− * Licensed under the GPL-2 or later.
7− */
8−#ifndef IIO_DAC_AD5446_H_
9−#define IIO_DAC_AD5446_H_
10−
11−/* DAC Control Bits */
12−
13−#define AD5446_LOAD (0x0 << 14) /* Load and update */
14−#define AD5446_SDO_DIS (0x1 << 14) /* Disable SDO */
15−#define AD5446_NOP (0x2 << 14) /* No operation */
16−#define AD5446_CLK_RISING (0x3 << 14) /* Clock data on rising edge */
17−
18−#define AD5620_LOAD (0x0 << 14) /* Load and update Norm Operation*/
19−#define AD5620_PWRDWN_1k (0x1 << 14) /* Power-down: 1kOhm to GND */
20−#define AD5620_PWRDWN_100k (0x2 << 14) /* Power-down: 100kOhm to GND */
21−#define AD5620_PWRDWN_TRISTATE (0x3 << 14) /* Power-down: Three-state */
22−
23−#define AD5660_LOAD (0x0 << 16) /* Load and update Norm Operation*/
24−#define AD5660_PWRDWN_1k (0x1 << 16) /* Power-down: 1kOhm to GND */
25−#define AD5660_PWRDWN_100k (0x2 << 16) /* Power-down: 100kOhm to GND */
26−#define AD5660_PWRDWN_TRISTATE (0x3 << 16) /* Power-down: Three-state */
27−
28−#define MODE_PWRDWN_1k 0x1
29−#define MODE_PWRDWN_100k 0x2
30−#define MODE_PWRDWN_TRISTATE 0x3
31−
32−/**
33− * struct ad5446_state - driver instance specific data
34− * @spi: spi_device
35− * @chip_info: chip model specific constants, available modes etc
36− * @reg: supply regulator
37− * @vref_mv: actual reference voltage used
38− */
39−
40−struct ad5446_state {
41− struct spi_device *spi;
42− const struct ad5446_chip_info *chip_info;
43− struct regulator *reg;
44− unsigned short vref_mv;
45− unsigned cached_val;
46− unsigned pwr_down_mode;
47− unsigned pwr_down;
48−};
49−
50−/**
51− * struct ad5446_chip_info - chip specific information
52− * @channel: channel spec for the DAC
53− * @int_vref_mv: AD5620/40/60: the internal reference voltage
54− * @write: chip specific helper function to write to the register
55− */
56−
57−struct ad5446_chip_info {
58− struct iio_chan_spec channel;
59− u16 int_vref_mv;
60− int (*write)(struct ad5446_state *st, unsigned val);
61−};
62−
63−/**
64− * ad5446_supported_device_ids:
65− * The AD5620/40/60 parts are available in different fixed internal reference
66− * voltage options. The actual part numbers may look differently
67− * (and a bit cryptic), however this style is used to make clear which
68− * parts are supported here.
69− */
70−
71−enum ad5446_supported_device_ids {
72− ID_AD5444,
73− ID_AD5446,
74− ID_AD5450,
75− ID_AD5451,
76− ID_AD5541A,
77− ID_AD5512A,
78− ID_AD5553,
79− ID_AD5601,
80− ID_AD5611,
81− ID_AD5621,
82− ID_AD5620_2500,
83− ID_AD5620_1250,
84− ID_AD5640_2500,
85− ID_AD5640_1250,
86− ID_AD5660_2500,
87− ID_AD5660_1250,
88− ID_AD5662,
89−};
90−
91−#endif /* IIO_DAC_AD5446_H_ */
drivers/iio/dac/ad5755.c+650−0
@@ -0,0 +1,650 @@
1+/*
2+ * AD5755, AD5755-1, AD5757, AD5735, AD5737 Digital to analog converters driver
3+ *
4+ * Copyright 2012 Analog Devices Inc.
5+ *
6+ * Licensed under the GPL-2.
7+ */
8+
9+#include <linux/device.h>
10+#include <linux/err.h>
11+#include <linux/module.h>
12+#include <linux/kernel.h>
13+#include <linux/spi/spi.h>
14+#include <linux/slab.h>
15+#include <linux/sysfs.h>
16+#include <linux/delay.h>
17+#include <linux/iio/iio.h>
18+#include <linux/iio/sysfs.h>
19+#include <linux/platform_data/ad5755.h>
20+
21+#define AD5755_NUM_CHANNELS 4
22+
23+#define AD5755_ADDR(x) ((x) << 16)
24+
25+#define AD5755_WRITE_REG_DATA(chan) (chan)
26+#define AD5755_WRITE_REG_GAIN(chan) (0x08 | (chan))
27+#define AD5755_WRITE_REG_OFFSET(chan) (0x10 | (chan))
28+#define AD5755_WRITE_REG_CTRL(chan) (0x1c | (chan))
29+
30+#define AD5755_READ_REG_DATA(chan) (chan)
31+#define AD5755_READ_REG_CTRL(chan) (0x4 | (chan))
32+#define AD5755_READ_REG_GAIN(chan) (0x8 | (chan))
33+#define AD5755_READ_REG_OFFSET(chan) (0xc | (chan))
34+#define AD5755_READ_REG_CLEAR(chan) (0x10 | (chan))
35+#define AD5755_READ_REG_SLEW(chan) (0x14 | (chan))
36+#define AD5755_READ_REG_STATUS 0x18
37+#define AD5755_READ_REG_MAIN 0x19
38+#define AD5755_READ_REG_DC_DC 0x1a
39+
40+#define AD5755_CTRL_REG_SLEW 0x0
41+#define AD5755_CTRL_REG_MAIN 0x1
42+#define AD5755_CTRL_REG_DAC 0x2
43+#define AD5755_CTRL_REG_DC_DC 0x3
44+#define AD5755_CTRL_REG_SW 0x4
45+
46+#define AD5755_READ_FLAG 0x800000
47+
48+#define AD5755_NOOP 0x1CE000
49+
50+#define AD5755_DAC_INT_EN BIT(8)
51+#define AD5755_DAC_CLR_EN BIT(7)
52+#define AD5755_DAC_OUT_EN BIT(6)
53+#define AD5755_DAC_INT_CURRENT_SENSE_RESISTOR BIT(5)
54+#define AD5755_DAC_DC_DC_EN BIT(4)
55+#define AD5755_DAC_VOLTAGE_OVERRANGE_EN BIT(3)
56+
57+#define AD5755_DC_DC_MAXV 0
58+#define AD5755_DC_DC_FREQ_SHIFT 2
59+#define AD5755_DC_DC_PHASE_SHIFT 4
60+#define AD5755_EXT_DC_DC_COMP_RES BIT(6)
61+
62+#define AD5755_SLEW_STEP_SIZE_SHIFT 0
63+#define AD5755_SLEW_RATE_SHIFT 3
64+#define AD5755_SLEW_ENABLE BIT(12)
65+
66+/**
67+ * struct ad5755_chip_info - chip specific information
68+ * @channel_template: channel specification
69+ * @calib_shift: shift for the calibration data registers
70+ * @has_voltage_out: whether the chip has voltage outputs
71+ */
72+struct ad5755_chip_info {
73+ const struct iio_chan_spec channel_template;
74+ unsigned int calib_shift;
75+ bool has_voltage_out;
76+};
77+
78+/**
79+ * struct ad5755_state - driver instance specific data
80+ * @spi: spi device the driver is attached to
81+ * @chip_info: chip model specific constants, available modes etc
82+ * @pwr_down: bitmask which contains hether a channel is powered down or not
83+ * @ctrl: software shadow of the channel ctrl registers
84+ * @channels: iio channel spec for the device
85+ * @data: spi transfer buffers
86+ */
87+struct ad5755_state {
88+ struct spi_device *spi;
89+ const struct ad5755_chip_info *chip_info;
90+ unsigned int pwr_down;
91+ unsigned int ctrl[AD5755_NUM_CHANNELS];
92+ struct iio_chan_spec channels[AD5755_NUM_CHANNELS];
93+
94+ /*
95+ * DMA (thus cache coherency maintenance) requires the
96+ * transfer buffers to live in their own cache lines.
97+ */
98+
99+ union {
100+ u32 d32;
101+ u8 d8[4];
102+ } data[2] ____cacheline_aligned;
103+};
104+
105+enum ad5755_type {
106+ ID_AD5755,
107+ ID_AD5757,
108+ ID_AD5735,
109+ ID_AD5737,
110+};
111+
112+static int ad5755_write_unlocked(struct iio_dev *indio_dev,
113+ unsigned int reg, unsigned int val)
114+{
115+ struct ad5755_state *st = iio_priv(indio_dev);
116+
117+ st->data[0].d32 = cpu_to_be32((reg << 16) | val);
118+
119+ return spi_write(st->spi, &st->data[0].d8[1], 3);
120+}
121+
122+static int ad5755_write_ctrl_unlocked(struct iio_dev *indio_dev,
123+ unsigned int channel, unsigned int reg, unsigned int val)
124+{
125+ return ad5755_write_unlocked(indio_dev,
126+ AD5755_WRITE_REG_CTRL(channel), (reg << 13) | val);
127+}
128+
129+static int ad5755_write(struct iio_dev *indio_dev, unsigned int reg,
130+ unsigned int val)
131+{
132+ int ret;
133+
134+ mutex_lock(&indio_dev->mlock);
135+ ret = ad5755_write_unlocked(indio_dev, reg, val);
136+ mutex_unlock(&indio_dev->mlock);
137+
138+ return ret;
139+}
140+
141+static int ad5755_write_ctrl(struct iio_dev *indio_dev, unsigned int channel,
142+ unsigned int reg, unsigned int val)
143+{
144+ int ret;
145+
146+ mutex_lock(&indio_dev->mlock);
147+ ret = ad5755_write_ctrl_unlocked(indio_dev, channel, reg, val);
148+ mutex_unlock(&indio_dev->mlock);
149+
150+ return ret;
151+}
152+
153+static int ad5755_read(struct iio_dev *indio_dev, unsigned int addr)
154+{
155+ struct ad5755_state *st = iio_priv(indio_dev);
156+ struct spi_message m;
157+ int ret;
158+ struct spi_transfer t[] = {
159+ {
160+ .tx_buf = &st->data[0].d8[1],
161+ .len = 3,
162+ .cs_change = 1,
163+ }, {
164+ .tx_buf = &st->data[1].d8[1],
165+ .rx_buf = &st->data[1].d8[1],
166+ .len = 3,
167+ },
168+ };
169+
170+ spi_message_init(&m);
171+ spi_message_add_tail(&t[0], &m);
172+ spi_message_add_tail(&t[1], &m);
173+
174+ mutex_lock(&indio_dev->mlock);
175+
176+ st->data[0].d32 = cpu_to_be32(AD5755_READ_FLAG | (addr << 16));
177+ st->data[1].d32 = cpu_to_be32(AD5755_NOOP);
178+
179+ ret = spi_sync(st->spi, &m);
180+ if (ret >= 0)
181+ ret = be32_to_cpu(st->data[1].d32) & 0xffff;
182+
183+ mutex_unlock(&indio_dev->mlock);
184+
185+ return ret;
186+}
187+
188+static int ad5755_update_dac_ctrl(struct iio_dev *indio_dev,
189+ unsigned int channel, unsigned int set, unsigned int clr)
190+{
191+ struct ad5755_state *st = iio_priv(indio_dev);
192+ int ret;
193+
194+ st->ctrl[channel] |= set;
195+ st->ctrl[channel] &= ~clr;
196+
197+ ret = ad5755_write_ctrl_unlocked(indio_dev, channel,
198+ AD5755_CTRL_REG_DAC, st->ctrl[channel]);
199+
200+ return ret;
201+}
202+
203+static int ad5755_set_channel_pwr_down(struct iio_dev *indio_dev,
204+ unsigned int channel, bool pwr_down)
205+{
206+ struct ad5755_state *st = iio_priv(indio_dev);
207+ unsigned int mask = BIT(channel);
208+
209+ mutex_lock(&indio_dev->mlock);
210+
211+ if ((bool)(st->pwr_down & mask) == pwr_down)
212+ goto out_unlock;
213+
214+ if (!pwr_down) {
215+ st->pwr_down &= ~mask;
216+ ad5755_update_dac_ctrl(indio_dev, channel,
217+ AD5755_DAC_INT_EN | AD5755_DAC_DC_DC_EN, 0);
218+ udelay(200);
219+ ad5755_update_dac_ctrl(indio_dev, channel,
220+ AD5755_DAC_OUT_EN, 0);
221+ } else {
222+ st->pwr_down |= mask;
223+ ad5755_update_dac_ctrl(indio_dev, channel,
224+ 0, AD5755_DAC_INT_EN | AD5755_DAC_OUT_EN |
225+ AD5755_DAC_DC_DC_EN);
226+ }
227+
228+out_unlock:
229+ mutex_unlock(&indio_dev->mlock);
230+
231+ return 0;
232+}
233+
234+static const int ad5755_min_max_table[][2] = {
235+ [AD5755_MODE_VOLTAGE_0V_5V] = { 0, 5000 },
236+ [AD5755_MODE_VOLTAGE_0V_10V] = { 0, 10000 },
237+ [AD5755_MODE_VOLTAGE_PLUSMINUS_5V] = { -5000, 5000 },
238+ [AD5755_MODE_VOLTAGE_PLUSMINUS_10V] = { -10000, 10000 },
239+ [AD5755_MODE_CURRENT_4mA_20mA] = { 4, 20 },
240+ [AD5755_MODE_CURRENT_0mA_20mA] = { 0, 20 },
241+ [AD5755_MODE_CURRENT_0mA_24mA] = { 0, 24 },
242+};
243+
244+static void ad5755_get_min_max(struct ad5755_state *st,
245+ struct iio_chan_spec const *chan, int *min, int *max)
246+{
247+ enum ad5755_mode mode = st->ctrl[chan->channel] & 7;
248+ *min = ad5755_min_max_table[mode][0];
249+ *max = ad5755_min_max_table[mode][1];
250+}
251+
252+static inline int ad5755_get_offset(struct ad5755_state *st,
253+ struct iio_chan_spec const *chan)
254+{
255+ int min, max;
256+
257+ ad5755_get_min_max(st, chan, &min, &max);
258+ return (min * (1 << chan->scan_type.realbits)) / (max - min);
259+}
260+
261+static inline int ad5755_get_scale(struct ad5755_state *st,
262+ struct iio_chan_spec const *chan)
263+{
264+ int min, max;
265+
266+ ad5755_get_min_max(st, chan, &min, &max);
267+ return ((max - min) * 1000000000ULL) >> chan->scan_type.realbits;
268+}
269+
270+static int ad5755_chan_reg_info(struct ad5755_state *st,
271+ struct iio_chan_spec const *chan, long info, bool write,
272+ unsigned int *reg, unsigned int *shift, unsigned int *offset)
273+{
274+ switch (info) {
275+ case IIO_CHAN_INFO_RAW:
276+ if (write)
277+ *reg = AD5755_WRITE_REG_DATA(chan->address);
278+ else
279+ *reg = AD5755_READ_REG_DATA(chan->address);
280+ *shift = chan->scan_type.shift;
281+ *offset = 0;
282+ break;
283+ case IIO_CHAN_INFO_CALIBBIAS:
284+ if (write)
285+ *reg = AD5755_WRITE_REG_OFFSET(chan->address);
286+ else
287+ *reg = AD5755_READ_REG_OFFSET(chan->address);
288+ *shift = st->chip_info->calib_shift;
289+ *offset = 32768;
290+ break;
291+ case IIO_CHAN_INFO_CALIBSCALE:
292+ if (write)
293+ *reg = AD5755_WRITE_REG_GAIN(chan->address);
294+ else
295+ *reg = AD5755_READ_REG_GAIN(chan->address);
296+ *shift = st->chip_info->calib_shift;
297+ *offset = 0;
298+ break;
299+ default:
300+ return -EINVAL;
301+ }
302+
303+ return 0;
304+}
305+
306+static int ad5755_read_raw(struct iio_dev *indio_dev,
307+ const struct iio_chan_spec *chan, int *val, int *val2, long info)
308+{
309+ struct ad5755_state *st = iio_priv(indio_dev);
310+ unsigned int reg, shift, offset;
311+ int ret;
312+
313+ switch (info) {
314+ case IIO_CHAN_INFO_SCALE:
315+ *val = 0;
316+ *val2 = ad5755_get_scale(st, chan);
317+ return IIO_VAL_INT_PLUS_NANO;
318+ case IIO_CHAN_INFO_OFFSET:
319+ *val = ad5755_get_offset(st, chan);
320+ return IIO_VAL_INT;
321+ default:
322+ ret = ad5755_chan_reg_info(st, chan, info, false,
323+ &reg, &shift, &offset);
324+ if (ret)
325+ return ret;
326+
327+ ret = ad5755_read(indio_dev, reg);
328+ if (ret < 0)
329+ return ret;
330+
331+ *val = (ret - offset) >> shift;
332+
333+ return IIO_VAL_INT;
334+ }
335+
336+ return -EINVAL;
337+}
338+
339+static int ad5755_write_raw(struct iio_dev *indio_dev,
340+ const struct iio_chan_spec *chan, int val, int val2, long info)
341+{
342+ struct ad5755_state *st = iio_priv(indio_dev);
343+ unsigned int shift, reg, offset;
344+ int ret;
345+
346+ ret = ad5755_chan_reg_info(st, chan, info, true,
347+ &reg, &shift, &offset);
348+ if (ret)
349+ return ret;
350+
351+ val <<= shift;
352+ val += offset;
353+
354+ if (val < 0 || val > 0xffff)
355+ return -EINVAL;
356+
357+ return ad5755_write(indio_dev, reg, val);
358+}
359+
360+static ssize_t ad5755_read_powerdown(struct iio_dev *indio_dev, uintptr_t priv,
361+ const struct iio_chan_spec *chan, char *buf)
362+{
363+ struct ad5755_state *st = iio_priv(indio_dev);
364+
365+ return sprintf(buf, "%d\n",
366+ (bool)(st->pwr_down & (1 << chan->channel)));
367+}
368+
369+static ssize_t ad5755_write_powerdown(struct iio_dev *indio_dev, uintptr_t priv,
370+ struct iio_chan_spec const *chan, const char *buf, size_t len)
371+{
372+ bool pwr_down;
373+ int ret;
374+
375+ ret = strtobool(buf, &pwr_down);
376+ if (ret)
377+ return ret;
378+
379+ ret = ad5755_set_channel_pwr_down(indio_dev, chan->channel, pwr_down);
380+ return ret ? ret : len;
381+}
382+
383+static const struct iio_info ad5755_info = {
384+ .read_raw = ad5755_read_raw,
385+ .write_raw = ad5755_write_raw,
386+ .driver_module = THIS_MODULE,
387+};
388+
389+static const struct iio_chan_spec_ext_info ad5755_ext_info[] = {
390+ {
391+ .name = "powerdown",
392+ .read = ad5755_read_powerdown,
393+ .write = ad5755_write_powerdown,
394+ },
395+ { },
396+};
397+
398+#define AD5755_CHANNEL(_bits) { \
399+ .indexed = 1, \
400+ .output = 1, \
401+ .info_mask = IIO_CHAN_INFO_RAW_SEPARATE_BIT | \
402+ IIO_CHAN_INFO_SCALE_SEPARATE_BIT | \
403+ IIO_CHAN_INFO_OFFSET_SEPARATE_BIT | \
404+ IIO_CHAN_INFO_CALIBSCALE_SEPARATE_BIT | \
405+ IIO_CHAN_INFO_CALIBBIAS_SEPARATE_BIT, \
406+ .scan_type = IIO_ST('u', (_bits), 16, 16 - (_bits)), \
407+ .ext_info = ad5755_ext_info, \
408+}
409+
410+static const struct ad5755_chip_info ad5755_chip_info_tbl[] = {
411+ [ID_AD5735] = {
412+ .channel_template = AD5755_CHANNEL(14),
413+ .has_voltage_out = true,
414+ .calib_shift = 4,
415+ },
416+ [ID_AD5737] = {
417+ .channel_template = AD5755_CHANNEL(14),
418+ .has_voltage_out = false,
419+ .calib_shift = 4,
420+ },
421+ [ID_AD5755] = {
422+ .channel_template = AD5755_CHANNEL(16),
423+ .has_voltage_out = true,
424+ .calib_shift = 0,
425+ },
426+ [ID_AD5757] = {
427+ .channel_template = AD5755_CHANNEL(16),
428+ .has_voltage_out = false,
429+ .calib_shift = 0,
430+ },
431+};
432+
433+static bool ad5755_is_valid_mode(struct ad5755_state *st, enum ad5755_mode mode)
434+{
435+ switch (mode) {
436+ case AD5755_MODE_VOLTAGE_0V_5V:
437+ case AD5755_MODE_VOLTAGE_0V_10V:
438+ case AD5755_MODE_VOLTAGE_PLUSMINUS_5V:
439+ case AD5755_MODE_VOLTAGE_PLUSMINUS_10V:
440+ return st->chip_info->has_voltage_out;
441+ case AD5755_MODE_CURRENT_4mA_20mA:
442+ case AD5755_MODE_CURRENT_0mA_20mA:
443+ case AD5755_MODE_CURRENT_0mA_24mA:
444+ return true;
445+ default:
446+ return false;
447+ }
448+}
449+
450+static int __devinit ad5755_setup_pdata(struct iio_dev *indio_dev,
451+ const struct ad5755_platform_data *pdata)
452+{
453+ struct ad5755_state *st = iio_priv(indio_dev);
454+ unsigned int val;
455+ unsigned int i;
456+ int ret;
457+
458+ if (pdata->dc_dc_phase > AD5755_DC_DC_PHASE_90_DEGREE ||
459+ pdata->dc_dc_freq > AD5755_DC_DC_FREQ_650kHZ ||
460+ pdata->dc_dc_maxv > AD5755_DC_DC_MAXV_29V5)
461+ return -EINVAL;
462+
463+ val = pdata->dc_dc_maxv << AD5755_DC_DC_MAXV;
464+ val |= pdata->dc_dc_freq << AD5755_DC_DC_FREQ_SHIFT;
465+ val |= pdata->dc_dc_phase << AD5755_DC_DC_PHASE_SHIFT;
466+ if (pdata->ext_dc_dc_compenstation_resistor)
467+ val |= AD5755_EXT_DC_DC_COMP_RES;
468+
469+ ret = ad5755_write_ctrl(indio_dev, 0, AD5755_CTRL_REG_DC_DC, val);
470+ if (ret < 0)
471+ return ret;
472+
473+ for (i = 0; i < ARRAY_SIZE(pdata->dac); ++i) {
474+ val = pdata->dac[i].slew.step_size <<
475+ AD5755_SLEW_STEP_SIZE_SHIFT;
476+ val |= pdata->dac[i].slew.rate <<
477+ AD5755_SLEW_RATE_SHIFT;
478+ if (pdata->dac[i].slew.enable)
479+ val |= AD5755_SLEW_ENABLE;
480+
481+ ret = ad5755_write_ctrl(indio_dev, i,
482+ AD5755_CTRL_REG_SLEW, val);
483+ if (ret < 0)
484+ return ret;
485+ }
486+
487+ for (i = 0; i < ARRAY_SIZE(pdata->dac); ++i) {
488+ if (!ad5755_is_valid_mode(st, pdata->dac[i].mode))
489+ return -EINVAL;
490+
491+ val = 0;
492+ if (!pdata->dac[i].ext_current_sense_resistor)
493+ val |= AD5755_DAC_INT_CURRENT_SENSE_RESISTOR;
494+ if (pdata->dac[i].enable_voltage_overrange)
495+ val |= AD5755_DAC_VOLTAGE_OVERRANGE_EN;
496+ val |= pdata->dac[i].mode;
497+
498+ ret = ad5755_update_dac_ctrl(indio_dev, i, val, 0);
499+ if (ret < 0)
500+ return ret;
501+ }
502+
503+ return 0;
504+}
505+
506+static bool __devinit ad5755_is_voltage_mode(enum ad5755_mode mode)
507+{
508+ switch (mode) {
509+ case AD5755_MODE_VOLTAGE_0V_5V:
510+ case AD5755_MODE_VOLTAGE_0V_10V:
511+ case AD5755_MODE_VOLTAGE_PLUSMINUS_5V:
512+ case AD5755_MODE_VOLTAGE_PLUSMINUS_10V:
513+ return true;
514+ default:
515+ return false;
516+ }
517+}
518+
519+static int __devinit ad5755_init_channels(struct iio_dev *indio_dev,
520+ const struct ad5755_platform_data *pdata)
521+{
522+ struct ad5755_state *st = iio_priv(indio_dev);
523+ struct iio_chan_spec *channels = st->channels;
524+ unsigned int i;
525+
526+ for (i = 0; i < AD5755_NUM_CHANNELS; ++i) {
527+ channels[i] = st->chip_info->channel_template;
528+ channels[i].channel = i;
529+ channels[i].address = i;
530+ if (pdata && ad5755_is_voltage_mode(pdata->dac[i].mode))
531+ channels[i].type = IIO_VOLTAGE;
532+ else
533+ channels[i].type = IIO_CURRENT;
534+ }
535+
536+ indio_dev->channels = channels;
537+
538+ return 0;
539+}
540+
541+#define AD5755_DEFAULT_DAC_PDATA { \
542+ .mode = AD5755_MODE_CURRENT_4mA_20mA, \
543+ .ext_current_sense_resistor = true, \
544+ .enable_voltage_overrange = false, \
545+ .slew = { \
546+ .enable = false, \
547+ .rate = AD5755_SLEW_RATE_64k, \
548+ .step_size = AD5755_SLEW_STEP_SIZE_1, \
549+ }, \
550+ }
551+
552+static const struct ad5755_platform_data ad5755_default_pdata = {
553+ .ext_dc_dc_compenstation_resistor = false,
554+ .dc_dc_phase = AD5755_DC_DC_PHASE_ALL_SAME_EDGE,
555+ .dc_dc_freq = AD5755_DC_DC_FREQ_410kHZ,
556+ .dc_dc_maxv = AD5755_DC_DC_MAXV_23V,
557+ .dac = {
558+ [0] = AD5755_DEFAULT_DAC_PDATA,
559+ [1] = AD5755_DEFAULT_DAC_PDATA,
560+ [2] = AD5755_DEFAULT_DAC_PDATA,
561+ [3] = AD5755_DEFAULT_DAC_PDATA,
562+ },
563+};
564+
565+static int __devinit ad5755_probe(struct spi_device *spi)
566+{
567+ enum ad5755_type type = spi_get_device_id(spi)->driver_data;
568+ const struct ad5755_platform_data *pdata = dev_get_platdata(&spi->dev);
569+ struct iio_dev *indio_dev;
570+ struct ad5755_state *st;
571+ int ret;
572+
573+ indio_dev = iio_device_alloc(sizeof(*st));
574+ if (indio_dev == NULL) {
575+ dev_err(&spi->dev, "Failed to allocate iio device\n");
576+ return -ENOMEM;
577+ }
578+
579+ st = iio_priv(indio_dev);
580+ spi_set_drvdata(spi, indio_dev);
581+
582+ st->chip_info = &ad5755_chip_info_tbl[type];
583+ st->spi = spi;
584+ st->pwr_down = 0xf;
585+
586+ indio_dev->dev.parent = &spi->dev;
587+ indio_dev->name = spi_get_device_id(spi)->name;
588+ indio_dev->info = &ad5755_info;
589+ indio_dev->modes = INDIO_DIRECT_MODE;
590+ indio_dev->num_channels = AD5755_NUM_CHANNELS;
591+
592+ if (!pdata)
593+ pdata = &ad5755_default_pdata;
594+
595+ ret = ad5755_init_channels(indio_dev, pdata);
596+ if (ret)
597+ goto error_free;
598+
599+ ret = ad5755_setup_pdata(indio_dev, pdata);
600+ if (ret)
601+ goto error_free;
602+
603+ ret = iio_device_register(indio_dev);
604+ if (ret) {
605+ dev_err(&spi->dev, "Failed to register iio device: %d\n", ret);
606+ goto error_free;
607+ }
608+
609+ return 0;
610+
611+error_free:
612+ iio_device_free(indio_dev);
613+
614+ return ret;
615+}
616+
617+static int __devexit ad5755_remove(struct spi_device *spi)
618+{
619+ struct iio_dev *indio_dev = spi_get_drvdata(spi);
620+
621+ iio_device_unregister(indio_dev);
622+ iio_device_free(indio_dev);
623+
624+ return 0;
625+}
626+
627+static const struct spi_device_id ad5755_id[] = {
628+ { "ad5755", ID_AD5755 },
629+ { "ad5755-1", ID_AD5755 },
630+ { "ad5757", ID_AD5757 },
631+ { "ad5735", ID_AD5735 },
632+ { "ad5737", ID_AD5737 },
633+ {}
634+};
635+MODULE_DEVICE_TABLE(spi, ad5755_id);
636+
637+static struct spi_driver ad5755_driver = {
638+ .driver = {
639+ .name = "ad5755",
640+ .owner = THIS_MODULE,
641+ },
642+ .probe = ad5755_probe,
643+ .remove = __devexit_p(ad5755_remove),
644+ .id_table = ad5755_id,
645+};
646+module_spi_driver(ad5755_driver);
647+
648+MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
649+MODULE_DESCRIPTION("Analog Devices AD5755/55-1/57/35/37 DAC");
650+MODULE_LICENSE("GPL v2");
drivers/iio/gyro/Kconfig+16−0
@@ -0,0 +1,16 @@
1+#
2+# IIO Digital Gyroscope Sensor drivers configuration
3+#
4+menu "Digital gyroscope sensors"
5+
6+config HID_SENSOR_GYRO_3D
7+ depends on HID_SENSOR_HUB
8+ select IIO_BUFFER
9+ select IIO_TRIGGERED_BUFFER
10+ select HID_SENSOR_IIO_COMMON
11+ tristate "HID Gyroscope 3D"
12+ help
13+ Say yes here to build support for the HID SENSOR
14+ Gyroscope 3D.
15+
16+endmenu
drivers/iio/gyro/Makefile+5−0
@@ -0,0 +1,5 @@
1+#
2+# Makefile for industrial I/O gyroscope sensor drivers
3+#
4+
5+obj-$(CONFIG_HID_SENSOR_GYRO_3D) += hid-sensor-gyro-3d.o
drivers/iio/gyro/hid-sensor-gyro-3d.c+418−0
@@ -0,0 +1,418 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/sysfs.h>
28+#include <linux/iio/buffer.h>
29+#include <linux/iio/trigger_consumer.h>
30+#include <linux/iio/triggered_buffer.h>
31+#include "../common/hid-sensors/hid-sensor-attributes.h"
32+#include "../common/hid-sensors/hid-sensor-trigger.h"
33+
34+/*Format: HID-SENSOR-usage_id_in_hex*/
35+/*Usage ID from spec for Gyro-3D: 0x200076*/
36+#define DRIVER_NAME "HID-SENSOR-200076"
37+
38+enum gyro_3d_channel {
39+ CHANNEL_SCAN_INDEX_X,
40+ CHANNEL_SCAN_INDEX_Y,
41+ CHANNEL_SCAN_INDEX_Z,
42+ GYRO_3D_CHANNEL_MAX,
43+};
44+
45+struct gyro_3d_state {
46+ struct hid_sensor_hub_callbacks callbacks;
47+ struct hid_sensor_iio_common common_attributes;
48+ struct hid_sensor_hub_attribute_info gyro[GYRO_3D_CHANNEL_MAX];
49+ u32 gyro_val[GYRO_3D_CHANNEL_MAX];
50+};
51+
52+static const u32 gyro_3d_addresses[GYRO_3D_CHANNEL_MAX] = {
53+ HID_USAGE_SENSOR_ANGL_VELOCITY_X_AXIS,
54+ HID_USAGE_SENSOR_ANGL_VELOCITY_Y_AXIS,
55+ HID_USAGE_SENSOR_ANGL_VELOCITY_Z_AXIS
56+};
57+
58+/* Channel definitions */
59+static const struct iio_chan_spec gyro_3d_channels[] = {
60+ {
61+ .type = IIO_ANGL_VEL,
62+ .modified = 1,
63+ .channel2 = IIO_MOD_X,
64+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
65+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
66+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
67+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
68+ .scan_index = CHANNEL_SCAN_INDEX_X,
69+ }, {
70+ .type = IIO_ANGL_VEL,
71+ .modified = 1,
72+ .channel2 = IIO_MOD_Y,
73+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
74+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
75+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
76+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
77+ .scan_index = CHANNEL_SCAN_INDEX_Y,
78+ }, {
79+ .type = IIO_ANGL_VEL,
80+ .modified = 1,
81+ .channel2 = IIO_MOD_Z,
82+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
83+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
84+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
85+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
86+ .scan_index = CHANNEL_SCAN_INDEX_Z,
87+ }
88+};
89+
90+/* Adjust channel real bits based on report descriptor */
91+static void gyro_3d_adjust_channel_bit_mask(struct iio_chan_spec *channels,
92+ int channel, int size)
93+{
94+ channels[channel].scan_type.sign = 's';
95+ /* Real storage bits will change based on the report desc. */
96+ channels[channel].scan_type.realbits = size * 8;
97+ /* Maximum size of a sample to capture is u32 */
98+ channels[channel].scan_type.storagebits = sizeof(u32) * 8;
99+}
100+
101+/* Channel read_raw handler */
102+static int gyro_3d_read_raw(struct iio_dev *indio_dev,
103+ struct iio_chan_spec const *chan,
104+ int *val, int *val2,
105+ long mask)
106+{
107+ struct gyro_3d_state *gyro_state = iio_priv(indio_dev);
108+ int report_id = -1;
109+ u32 address;
110+ int ret;
111+ int ret_type;
112+
113+ *val = 0;
114+ *val2 = 0;
115+ switch (mask) {
116+ case 0:
117+ report_id = gyro_state->gyro[chan->scan_index].report_id;
118+ address = gyro_3d_addresses[chan->scan_index];
119+ if (report_id >= 0)
120+ *val = sensor_hub_input_attr_get_raw_value(
121+ gyro_state->common_attributes.hsdev,
122+ HID_USAGE_SENSOR_GYRO_3D, address,
123+ report_id);
124+ else {
125+ *val = 0;
126+ return -EINVAL;
127+ }
128+ ret_type = IIO_VAL_INT;
129+ break;
130+ case IIO_CHAN_INFO_SCALE:
131+ *val = gyro_state->gyro[CHANNEL_SCAN_INDEX_X].units;
132+ ret_type = IIO_VAL_INT;
133+ break;
134+ case IIO_CHAN_INFO_OFFSET:
135+ *val = hid_sensor_convert_exponent(
136+ gyro_state->gyro[CHANNEL_SCAN_INDEX_X].unit_expo);
137+ ret_type = IIO_VAL_INT;
138+ break;
139+ case IIO_CHAN_INFO_SAMP_FREQ:
140+ ret = hid_sensor_read_samp_freq_value(
141+ &gyro_state->common_attributes, val, val2);
142+ ret_type = IIO_VAL_INT_PLUS_MICRO;
143+ break;
144+ case IIO_CHAN_INFO_HYSTERESIS:
145+ ret = hid_sensor_read_raw_hyst_value(
146+ &gyro_state->common_attributes, val, val2);
147+ ret_type = IIO_VAL_INT_PLUS_MICRO;
148+ break;
149+ default:
150+ ret_type = -EINVAL;
151+ break;
152+ }
153+
154+ return ret_type;
155+}
156+
157+/* Channel write_raw handler */
158+static int gyro_3d_write_raw(struct iio_dev *indio_dev,
159+ struct iio_chan_spec const *chan,
160+ int val,
161+ int val2,
162+ long mask)
163+{
164+ struct gyro_3d_state *gyro_state = iio_priv(indio_dev);
165+ int ret = 0;
166+
167+ switch (mask) {
168+ case IIO_CHAN_INFO_SAMP_FREQ:
169+ ret = hid_sensor_write_samp_freq_value(
170+ &gyro_state->common_attributes, val, val2);
171+ break;
172+ case IIO_CHAN_INFO_HYSTERESIS:
173+ ret = hid_sensor_write_raw_hyst_value(
174+ &gyro_state->common_attributes, val, val2);
175+ break;
176+ default:
177+ ret = -EINVAL;
178+ }
179+
180+ return ret;
181+}
182+
183+static int gyro_3d_write_raw_get_fmt(struct iio_dev *indio_dev,
184+ struct iio_chan_spec const *chan,
185+ long mask)
186+{
187+ return IIO_VAL_INT_PLUS_MICRO;
188+}
189+
190+static const struct iio_info gyro_3d_info = {
191+ .driver_module = THIS_MODULE,
192+ .read_raw = &gyro_3d_read_raw,
193+ .write_raw = &gyro_3d_write_raw,
194+ .write_raw_get_fmt = &gyro_3d_write_raw_get_fmt,
195+};
196+
197+/* Function to push data to buffer */
198+static void hid_sensor_push_data(struct iio_dev *indio_dev, u8 *data, int len)
199+{
200+ struct iio_buffer *buffer = indio_dev->buffer;
201+ int datum_sz;
202+
203+ dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n");
204+ if (!buffer) {
205+ dev_err(&indio_dev->dev, "Buffer == NULL\n");
206+ return;
207+ }
208+ datum_sz = buffer->access->get_bytes_per_datum(buffer);
209+ if (len > datum_sz) {
210+ dev_err(&indio_dev->dev, "Datum size mismatch %d:%d\n", len,
211+ datum_sz);
212+ return;
213+ }
214+ iio_push_to_buffer(buffer, (u8 *)data);
215+}
216+
217+/* Callback handler to send event after all samples are received and captured */
218+static int gyro_3d_proc_event(struct hid_sensor_hub_device *hsdev,
219+ unsigned usage_id,
220+ void *priv)
221+{
222+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
223+ struct gyro_3d_state *gyro_state = iio_priv(indio_dev);
224+
225+ dev_dbg(&indio_dev->dev, "gyro_3d_proc_event [%d]\n",
226+ gyro_state->common_attributes.data_ready);
227+ if (gyro_state->common_attributes.data_ready)
228+ hid_sensor_push_data(indio_dev,
229+ (u8 *)gyro_state->gyro_val,
230+ sizeof(gyro_state->gyro_val));
231+
232+ return 0;
233+}
234+
235+/* Capture samples in local storage */
236+static int gyro_3d_capture_sample(struct hid_sensor_hub_device *hsdev,
237+ unsigned usage_id,
238+ size_t raw_len, char *raw_data,
239+ void *priv)
240+{
241+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
242+ struct gyro_3d_state *gyro_state = iio_priv(indio_dev);
243+ int offset;
244+ int ret = -EINVAL;
245+
246+ switch (usage_id) {
247+ case HID_USAGE_SENSOR_ANGL_VELOCITY_X_AXIS:
248+ case HID_USAGE_SENSOR_ANGL_VELOCITY_Y_AXIS:
249+ case HID_USAGE_SENSOR_ANGL_VELOCITY_Z_AXIS:
250+ offset = usage_id - HID_USAGE_SENSOR_ANGL_VELOCITY_X_AXIS;
251+ gyro_state->gyro_val[CHANNEL_SCAN_INDEX_X + offset] =
252+ *(u32 *)raw_data;
253+ ret = 0;
254+ break;
255+ default:
256+ break;
257+ }
258+
259+ return ret;
260+}
261+
262+/* Parse report which is specific to an usage id*/
263+static int gyro_3d_parse_report(struct platform_device *pdev,
264+ struct hid_sensor_hub_device *hsdev,
265+ struct iio_chan_spec *channels,
266+ unsigned usage_id,
267+ struct gyro_3d_state *st)
268+{
269+ int ret;
270+ int i;
271+
272+ for (i = 0; i <= CHANNEL_SCAN_INDEX_Z; ++i) {
273+ ret = sensor_hub_input_get_attribute_info(hsdev,
274+ HID_INPUT_REPORT,
275+ usage_id,
276+ HID_USAGE_SENSOR_ANGL_VELOCITY_X_AXIS + i,
277+ &st->gyro[CHANNEL_SCAN_INDEX_X + i]);
278+ if (ret < 0)
279+ break;
280+ gyro_3d_adjust_channel_bit_mask(channels,
281+ CHANNEL_SCAN_INDEX_X + i,
282+ st->gyro[CHANNEL_SCAN_INDEX_X + i].size);
283+ }
284+ dev_dbg(&pdev->dev, "gyro_3d %x:%x, %x:%x, %x:%x\n",
285+ st->gyro[0].index,
286+ st->gyro[0].report_id,
287+ st->gyro[1].index, st->gyro[1].report_id,
288+ st->gyro[2].index, st->gyro[2].report_id);
289+
290+ return ret;
291+}
292+
293+/* Function to initialize the processing for usage id */
294+static int __devinit hid_gyro_3d_probe(struct platform_device *pdev)
295+{
296+ int ret = 0;
297+ static const char *name = "gyro_3d";
298+ struct iio_dev *indio_dev;
299+ struct gyro_3d_state *gyro_state;
300+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
301+ struct iio_chan_spec *channels;
302+
303+ indio_dev = iio_device_alloc(sizeof(struct gyro_3d_state));
304+ if (indio_dev == NULL) {
305+ ret = -ENOMEM;
306+ goto error_ret;
307+ }
308+ platform_set_drvdata(pdev, indio_dev);
309+
310+ gyro_state = iio_priv(indio_dev);
311+ gyro_state->common_attributes.hsdev = hsdev;
312+ gyro_state->common_attributes.pdev = pdev;
313+
314+ ret = hid_sensor_parse_common_attributes(hsdev,
315+ HID_USAGE_SENSOR_GYRO_3D,
316+ &gyro_state->common_attributes);
317+ if (ret) {
318+ dev_err(&pdev->dev, "failed to setup common attributes\n");
319+ goto error_free_dev;
320+ }
321+
322+ channels = kmemdup(gyro_3d_channels,
323+ sizeof(gyro_3d_channels),
324+ GFP_KERNEL);
325+ if (!channels) {
326+ dev_err(&pdev->dev, "failed to duplicate channels\n");
327+ goto error_free_dev;
328+ }
329+
330+ ret = gyro_3d_parse_report(pdev, hsdev, channels,
331+ HID_USAGE_SENSOR_GYRO_3D, gyro_state);
332+ if (ret) {
333+ dev_err(&pdev->dev, "failed to setup attributes\n");
334+ goto error_free_dev_mem;
335+ }
336+
337+ indio_dev->channels = channels;
338+ indio_dev->num_channels = ARRAY_SIZE(gyro_3d_channels);
339+ indio_dev->dev.parent = &pdev->dev;
340+ indio_dev->info = &gyro_3d_info;
341+ indio_dev->name = name;
342+ indio_dev->modes = INDIO_DIRECT_MODE;
343+
344+ ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time,
345+ NULL, NULL);
346+ if (ret) {
347+ dev_err(&pdev->dev, "failed to initialize trigger buffer\n");
348+ goto error_free_dev_mem;
349+ }
350+ gyro_state->common_attributes.data_ready = false;
351+ ret = hid_sensor_setup_trigger(indio_dev, name,
352+ &gyro_state->common_attributes);
353+ if (ret < 0) {
354+ dev_err(&pdev->dev, "trigger setup failed\n");
355+ goto error_unreg_buffer_funcs;
356+ }
357+
358+ ret = iio_device_register(indio_dev);
359+ if (ret) {
360+ dev_err(&pdev->dev, "device register failed\n");
361+ goto error_remove_trigger;
362+ }
363+
364+ gyro_state->callbacks.send_event = gyro_3d_proc_event;
365+ gyro_state->callbacks.capture_sample = gyro_3d_capture_sample;
366+ gyro_state->callbacks.pdev = pdev;
367+ ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_GYRO_3D,
368+ &gyro_state->callbacks);
369+ if (ret < 0) {
370+ dev_err(&pdev->dev, "callback reg failed\n");
371+ goto error_iio_unreg;
372+ }
373+
374+ return ret;
375+
376+error_iio_unreg:
377+ iio_device_unregister(indio_dev);
378+error_remove_trigger:
379+ hid_sensor_remove_trigger(indio_dev);
380+error_unreg_buffer_funcs:
381+ iio_triggered_buffer_cleanup(indio_dev);
382+error_free_dev_mem:
383+ kfree(indio_dev->channels);
384+error_free_dev:
385+ iio_device_free(indio_dev);
386+error_ret:
387+ return ret;
388+}
389+
390+/* Function to deinitialize the processing for usage id */
391+static int __devinit hid_gyro_3d_remove(struct platform_device *pdev)
392+{
393+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
394+ struct iio_dev *indio_dev = platform_get_drvdata(pdev);
395+
396+ sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_GYRO_3D);
397+ iio_device_unregister(indio_dev);
398+ hid_sensor_remove_trigger(indio_dev);
399+ iio_triggered_buffer_cleanup(indio_dev);
400+ kfree(indio_dev->channels);
401+ iio_device_free(indio_dev);
402+
403+ return 0;
404+}
405+
406+static struct platform_driver hid_gyro_3d_platform_driver = {
407+ .driver = {
408+ .name = DRIVER_NAME,
409+ .owner = THIS_MODULE,
410+ },
411+ .probe = hid_gyro_3d_probe,
412+ .remove = hid_gyro_3d_remove,
413+};
414+module_platform_driver(hid_gyro_3d_platform_driver);
415+
416+MODULE_DESCRIPTION("HID Sensor Gyroscope 3D");
417+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
418+MODULE_LICENSE("GPL");
drivers/iio/industrialio-buffer.c+7−8
@@ -422,7 +422,7 @@ ssize_t iio_buffer_store_enable(struct device *dev, · 421 unmodified lines
422422 ret = indio_dev->setup_ops->preenable(indio_dev);
423423 if (ret) {
424424 printk(KERN_ERR
425− "Buffer not started:"
425+ "Buffer not started: "
426426 "buffer preenable failed\n");
427427 goto error_ret;
428428 }
@@ -431,12 +431,12 @@ ssize_t iio_buffer_store_enable(struct device *dev, · 2 unmodified lines
431431 ret = buffer->access->request_update(buffer);
432432 if (ret) {
433433 printk(KERN_INFO
434− "Buffer not started:"
434+ "Buffer not started: "
435435 "buffer parameter update failed\n");
436436 goto error_ret;
437437 }
438438 }
439− /* Definitely possible for devices to support both of these.*/
439+ /* Definitely possible for devices to support both of these. */
440440 if (indio_dev->modes & INDIO_BUFFER_TRIGGERED) {
441441 if (!indio_dev->trig) {
442442 printk(KERN_INFO
@@ -456,7 +456,7 @@ ssize_t iio_buffer_store_enable(struct device *dev, · 13 unmodified lines
456456 ret = indio_dev->setup_ops->postenable(indio_dev);
457457 if (ret) {
458458 printk(KERN_INFO
459− "Buffer not started:"
459+ "Buffer not started: "
460460 "postenable failed\n");
461461 indio_dev->currentmode = previous_mode;
462462 if (indio_dev->setup_ops->postdisable)
@@ -657,7 +657,7 @@ EXPORT_SYMBOL_GPL(iio_scan_mask_query); · 194 unmodified lines
657657 /**
658658 * struct iio_demux_table() - table describing demux memcpy ops
659659 * @from: index to copy from
660− * @to: index to copy to
660+ * @to: index to copy to
661661 * @length: how many bytes to copy
662662 * @l: list head used for management
663663 */
@@ -682,12 +682,11 @@ static unsigned char *iio_demux(struct iio_buffer *buffer, · 18 unmodified lines
682682 return buffer->demux_bounce;
683683 }
684684
685−int iio_push_to_buffer(struct iio_buffer *buffer, unsigned char *data,
686− s64 timestamp)
685+int iio_push_to_buffer(struct iio_buffer *buffer, unsigned char *data)
687686 {
688687 unsigned char *dataout = iio_demux(buffer, data);
689688
690− return buffer->access->store_to(buffer, dataout, timestamp);
689+ return buffer->access->store_to(buffer, dataout);
691690 }
692691 EXPORT_SYMBOL_GPL(iio_push_to_buffer);
693692
drivers/iio/industrialio-core.c+10−3
@@ -29,7 +29,7 @@ · 28 unmodified lines
2929 #include <linux/iio/sysfs.h>
3030 #include <linux/iio/events.h>
3131
32−/* IDA to assign each registered device a unique id*/
32+/* IDA to assign each registered device a unique id */
3333 static DEFINE_IDA(iio_ida);
3434
3535 static dev_t iio_devt;
@@ -99,6 +99,7 @@ static const char * const iio_chan_info_postfix[] = { · 63 unmodified lines
9999 [IIO_CHAN_INFO_FREQUENCY] = "frequency",
100100 [IIO_CHAN_INFO_PHASE] = "phase",
101101 [IIO_CHAN_INFO_HARDWAREGAIN] = "hardwaregain",
102+ [IIO_CHAN_INFO_HYSTERESIS] = "hysteresis",
102103 };
103104
104105 const struct iio_chan_spec
@@ -365,6 +366,7 @@ static ssize_t iio_read_channel_info(struct device *dev, · 260 unmodified lines
365366 {
366367 struct iio_dev *indio_dev = dev_to_iio_dev(dev);
367368 struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
369+ unsigned long long tmp;
368370 int val, val2;
369371 bool scale_db = false;
370372 int ret = indio_dev->info->read_raw(indio_dev, this_attr->c,
@@ -390,6 +392,11 @@ static ssize_t iio_read_channel_info(struct device *dev, · 19 unmodified lines
390392 return sprintf(buf, "-%d.%09u\n", val, -val2);
391393 else
392394 return sprintf(buf, "%d.%09u\n", val, val2);
395+ case IIO_VAL_FRACTIONAL:
396+ tmp = div_s64((s64)val * 1000000000LL, val2);
397+ val2 = do_div(tmp, 1000000000LL);
398+ val = tmp;
399+ return sprintf(buf, "%d.%09u\n", val, val2);
393400 default:
394401 return 0;
395402 }
@@ -729,7 +736,7 @@ static int iio_device_register_sysfs(struct iio_dev *indio_dev) · 333 unmodified lines
729736 attrcount = attrcount_orig;
730737 /*
731738 * New channel registration method - relies on the fact a group does
732− * not need to be initialized if it is name is NULL.
739+ * not need to be initialized if its name is NULL.
733740 */
734741 if (indio_dev->channels)
735742 for (i = 0; i < indio_dev->num_channels; i++) {
@@ -980,6 +987,6 @@ EXPORT_SYMBOL(iio_device_unregister); · 244 unmodified lines
980987 subsys_initcall(iio_init);
981988 module_exit(iio_exit);
982989
983−MODULE_AUTHOR("Jonathan Cameron <jic23@cam.ac.uk>");
990+MODULE_AUTHOR("Jonathan Cameron <jic23@kernel.org>");
984991 MODULE_DESCRIPTION("Industrial I/O core");
985992 MODULE_LICENSE("GPL");
drivers/iio/inkern.c+128−11
@@ -111,6 +111,7 @@ struct iio_channel *iio_channel_get(const char *name, const char *channel_name) · 110 unmodified lines
111111 {
112112 struct iio_map_internal *c_i = NULL, *c = NULL;
113113 struct iio_channel *channel;
114+ int err;
114115
115116 if (name == NULL && channel_name == NULL)
116117 return ERR_PTR(-ENODEV);
@@ -130,18 +131,32 @@ struct iio_channel *iio_channel_get(const char *name, const char *channel_name) · 13 unmodified lines
130131 if (c == NULL)
131132 return ERR_PTR(-ENODEV);
132133
133− channel = kmalloc(sizeof(*channel), GFP_KERNEL);
134− if (channel == NULL)
135− return ERR_PTR(-ENOMEM);
134+ channel = kzalloc(sizeof(*channel), GFP_KERNEL);
135+ if (channel == NULL) {
136+ err = -ENOMEM;
137+ goto error_no_mem;
138+ }
136139
137140 channel->indio_dev = c->indio_dev;
138141
139− if (c->map->adc_channel_label)
142+ if (c->map->adc_channel_label) {
140143 channel->channel =
141144 iio_chan_spec_from_name(channel->indio_dev,
142145 c->map->adc_channel_label);
143146
147+ if (channel->channel == NULL) {
148+ err = -EINVAL;
149+ goto error_no_chan;
150+ }
151+ }
152+
144153 return channel;
154+
155+error_no_chan:
156+ kfree(channel);
157+error_no_mem:
158+ iio_device_put(c->indio_dev);
159+ return ERR_PTR(err);
145160 }
146161 EXPORT_SYMBOL_GPL(iio_channel_get);
147162
@@ -229,9 +244,21 @@ void iio_channel_release_all(struct iio_channel *channels) · 81 unmodified lines
229244 }
230245 EXPORT_SYMBOL_GPL(iio_channel_release_all);
231246
247+static int iio_channel_read(struct iio_channel *chan, int *val, int *val2,
248+ enum iio_chan_info_enum info)
249+{
250+ int unused;
251+
252+ if (val2 == NULL)
253+ val2 = &unused;
254+
255+ return chan->indio_dev->info->read_raw(chan->indio_dev, chan->channel,
256+ val, val2, info);
257+}
258+
232259 int iio_read_channel_raw(struct iio_channel *chan, int *val)
233260 {
234− int val2, ret;
261+ int ret;
235262
236263 mutex_lock(&chan->indio_dev->info_exist_lock);
237264 if (chan->indio_dev->info == NULL) {
@@ -239,8 +266,7 @@ int iio_read_channel_raw(struct iio_channel *chan, int *val) · 1 unmodified line
239266 goto err_unlock;
240267 }
241268
242− ret = chan->indio_dev->info->read_raw(chan->indio_dev, chan->channel,
243− val, &val2, 0);
269+ ret = iio_channel_read(chan, val, NULL, IIO_CHAN_INFO_RAW);
244270 err_unlock:
245271 mutex_unlock(&chan->indio_dev->info_exist_lock);
246272
@@ -248,6 +274,100 @@ err_unlock: · 1 unmodified line
248274 }
249275 EXPORT_SYMBOL_GPL(iio_read_channel_raw);
250276
277+static int iio_convert_raw_to_processed_unlocked(struct iio_channel *chan,
278+ int raw, int *processed, unsigned int scale)
279+{
280+ int scale_type, scale_val, scale_val2, offset;
281+ s64 raw64 = raw;
282+ int ret;
283+
284+ ret = iio_channel_read(chan, &offset, NULL, IIO_CHAN_INFO_SCALE);
285+ if (ret == 0)
286+ raw64 += offset;
287+
288+ scale_type = iio_channel_read(chan, &scale_val, &scale_val2,
289+ IIO_CHAN_INFO_SCALE);
290+ if (scale_type < 0)
291+ return scale_type;
292+
293+ switch (scale_type) {
294+ case IIO_VAL_INT:
295+ *processed = raw64 * scale_val;
296+ break;
297+ case IIO_VAL_INT_PLUS_MICRO:
298+ if (scale_val2 < 0)
299+ *processed = -raw64 * scale_val;
300+ else
301+ *processed = raw64 * scale_val;
302+ *processed += div_s64(raw64 * (s64)scale_val2 * scale,
303+ 1000000LL);
304+ break;
305+ case IIO_VAL_INT_PLUS_NANO:
306+ if (scale_val2 < 0)
307+ *processed = -raw64 * scale_val;
308+ else
309+ *processed = raw64 * scale_val;
310+ *processed += div_s64(raw64 * (s64)scale_val2 * scale,
311+ 1000000000LL);
312+ break;
313+ case IIO_VAL_FRACTIONAL:
314+ *processed = div_s64(raw64 * (s64)scale_val * scale,
315+ scale_val2);
316+ break;
317+ default:
318+ return -EINVAL;
319+ }
320+
321+ return 0;
322+}
323+
324+int iio_convert_raw_to_processed(struct iio_channel *chan, int raw,
325+ int *processed, unsigned int scale)
326+{
327+ int ret;
328+
329+ mutex_lock(&chan->indio_dev->info_exist_lock);
330+ if (chan->indio_dev->info == NULL) {
331+ ret = -ENODEV;
332+ goto err_unlock;
333+ }
334+
335+ ret = iio_convert_raw_to_processed_unlocked(chan, raw, processed,
336+ scale);
337+err_unlock:
338+ mutex_unlock(&chan->indio_dev->info_exist_lock);
339+
340+ return ret;
341+}
342+EXPORT_SYMBOL_GPL(iio_convert_raw_to_processed);
343+
344+int iio_read_channel_processed(struct iio_channel *chan, int *val)
345+{
346+ int ret;
347+
348+ mutex_lock(&chan->indio_dev->info_exist_lock);
349+ if (chan->indio_dev->info == NULL) {
350+ ret = -ENODEV;
351+ goto err_unlock;
352+ }
353+
354+ if (iio_channel_has_info(chan->channel, IIO_CHAN_INFO_PROCESSED)) {
355+ ret = iio_channel_read(chan, val, NULL,
356+ IIO_CHAN_INFO_PROCESSED);
357+ } else {
358+ ret = iio_channel_read(chan, val, NULL, IIO_CHAN_INFO_RAW);
359+ if (ret < 0)
360+ goto err_unlock;
361+ ret = iio_convert_raw_to_processed_unlocked(chan, *val, val, 1);
362+ }
363+
364+err_unlock:
365+ mutex_unlock(&chan->indio_dev->info_exist_lock);
366+
367+ return ret;
368+}
369+EXPORT_SYMBOL_GPL(iio_read_channel_processed);
370+
251371 int iio_read_channel_scale(struct iio_channel *chan, int *val, int *val2)
252372 {
253373 int ret;
@@ -258,10 +378,7 @@ int iio_read_channel_scale(struct iio_channel *chan, int *val, int *val2) · 4 unmodified lines
258378 goto err_unlock;
259379 }
260380
261− ret = chan->indio_dev->info->read_raw(chan->indio_dev,
262− chan->channel,
263− val, val2,
264− IIO_CHAN_INFO_SCALE);
381+ ret = iio_channel_read(chan, val, val2, IIO_CHAN_INFO_SCALE);
265382 err_unlock:
266383 mutex_unlock(&chan->indio_dev->info_exist_lock);
267384
drivers/iio/kfifo_buf.c+23−8
@@ -6,6 +6,7 @@ · 5 unmodified lines
66 #include <linux/kfifo.h>
77 #include <linux/mutex.h>
88 #include <linux/iio/kfifo_buf.h>
9+#include <linux/sched.h>
910
1011 struct iio_kfifo {
1112 struct iio_buffer buffer;
@@ -22,7 +23,8 @@ static inline int __iio_allocate_kfifo(struct iio_kfifo *buf, · 10 unmodified lines
2223 return -EINVAL;
2324
2425 __iio_update_buffer(&buf->buffer, bytes_per_datum, length);
25− return kfifo_alloc(&buf->kf, bytes_per_datum*length, GFP_KERNEL);
26+ return __kfifo_alloc((struct __kfifo *)&buf->kf, length,
27+ bytes_per_datum, GFP_KERNEL);
2628 }
2729
2830 static int iio_request_update_kfifo(struct iio_buffer *r)
@@ -35,6 +37,7 @@ static int iio_request_update_kfifo(struct iio_buffer *r) · 6 unmodified lines
3537 kfifo_free(&buf->kf);
3638 ret = __iio_allocate_kfifo(buf, buf->buffer.bytes_per_datum,
3739 buf->buffer.length);
40+ r->stufftoread = false;
3841 error_ret:
3942 return ret;
4043 }
@@ -81,6 +84,9 @@ static int iio_set_bytes_per_datum_kfifo(struct iio_buffer *r, size_t bpd) · 40 unmodified lines
8184
8285 static int iio_set_length_kfifo(struct iio_buffer *r, int length)
8386 {
87+ /* Avoid an invalid state */
88+ if (length < 2)
89+ length = 2;
8490 if (r->length != length) {
8591 r->length = length;
8692 iio_mark_update_needed_kfifo(r);
@@ -89,14 +95,16 @@ static int iio_set_length_kfifo(struct iio_buffer *r, int length) · 2 unmodified lines
8995 }
9096
9197 static int iio_store_to_kfifo(struct iio_buffer *r,
92− u8 *data,
93− s64 timestamp)
98+ u8 *data)
9499 {
95100 int ret;
96101 struct iio_kfifo *kf = iio_to_kfifo(r);
97− ret = kfifo_in(&kf->kf, data, r->bytes_per_datum);
98− if (ret != r->bytes_per_datum)
102+ ret = kfifo_in(&kf->kf, data, 1);
103+ if (ret != 1)
99104 return -EBUSY;
105+ r->stufftoread = true;
106+ wake_up_interruptible(&r->pollq);
107+
100108 return 0;
101109 }
102110
@@ -106,11 +114,18 @@ static int iio_read_first_n_kfifo(struct iio_buffer *r, · 3 unmodified lines
106114 int ret, copied;
107115 struct iio_kfifo *kf = iio_to_kfifo(r);
108116
109− if (n < r->bytes_per_datum)
117+ if (n < r->bytes_per_datum || r->bytes_per_datum == 0)
110118 return -EINVAL;
111119
112− n = rounddown(n, r->bytes_per_datum);
113120 ret = kfifo_to_user(&kf->kf, buf, n, &copied);
121+ if (ret < 0)
122+ return ret;
123+
124+ if (kfifo_is_empty(&kf->kf))
125+ r->stufftoread = false;
126+ /* verify it is still empty to avoid race */
127+ if (!kfifo_is_empty(&kf->kf))
128+ r->stufftoread = true;
114129
115130 return copied;
116131 }
@@ -136,7 +151,7 @@ struct iio_buffer *iio_kfifo_allocate(struct iio_dev *indio_dev) · 19 unmodified lines
136151 iio_buffer_init(&kf->buffer);
137152 kf->buffer.attrs = &iio_kfifo_attribute_group;
138153 kf->buffer.access = &kfifo_access_funcs;
139−
154+ kf->buffer.length = 2;
140155 return &kf->buffer;
141156 }
142157 EXPORT_SYMBOL(iio_kfifo_allocate);
drivers/iio/light/Kconfig+10−0
@@ -42,4 +42,14 @@ config VCNL4000 · 41 unmodified lines
4242 To compile this driver as a module, choose M here: the
4343 module will be called vcnl4000.
4444
45+config HID_SENSOR_ALS
46+ depends on HID_SENSOR_HUB
47+ select IIO_BUFFER
48+ select IIO_TRIGGERED_BUFFER
49+ select HID_SENSOR_IIO_COMMON
50+ tristate "HID ALS"
51+ help
52+ Say yes here to build support for the HID SENSOR
53+ Ambient light sensor.
54+
4555 endmenu
drivers/iio/light/Makefile+1−0
@@ -5,3 +5,4 @@ · 4 unmodified lines
55 obj-$(CONFIG_ADJD_S311) += adjd_s311.o
66 obj-$(CONFIG_SENSORS_LM3533) += lm3533-als.o
77 obj-$(CONFIG_VCNL4000) += vcnl4000.o
8+obj-$(CONFIG_HID_SENSOR_ALS) += hid-sensor-als.o
drivers/iio/light/adjd_s311.c+1−1
@@ -187,7 +187,7 @@ static irqreturn_t adjd_s311_trigger_handler(int irq, void *p) · 186 unmodified lines
187187 if (indio_dev->scan_timestamp)
188188 *(s64 *)((u8 *)data->buffer + ALIGN(len, sizeof(s64)))
189189 = time_ns;
190− iio_push_to_buffer(buffer, (u8 *)data->buffer, time_ns);
190+ iio_push_to_buffer(buffer, (u8 *)data->buffer);
191191
192192 done:
193193 iio_trigger_notify_done(indio_dev->trig);
drivers/iio/light/hid-sensor-als.c+385−0
@@ -0,0 +1,385 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/sysfs.h>
28+#include <linux/iio/buffer.h>
29+#include <linux/iio/trigger_consumer.h>
30+#include <linux/iio/triggered_buffer.h>
31+#include "../common/hid-sensors/hid-sensor-attributes.h"
32+#include "../common/hid-sensors/hid-sensor-trigger.h"
33+
34+/*Format: HID-SENSOR-usage_id_in_hex*/
35+/*Usage ID from spec for Accelerometer-3D: 0x200041*/
36+#define DRIVER_NAME "HID-SENSOR-200041"
37+
38+#define CHANNEL_SCAN_INDEX_ILLUM 0
39+
40+struct als_state {
41+ struct hid_sensor_hub_callbacks callbacks;
42+ struct hid_sensor_iio_common common_attributes;
43+ struct hid_sensor_hub_attribute_info als_illum;
44+ u32 illum;
45+};
46+
47+/* Channel definitions */
48+static const struct iio_chan_spec als_channels[] = {
49+ {
50+ .type = IIO_INTENSITY,
51+ .modified = 1,
52+ .channel2 = IIO_MOD_LIGHT_BOTH,
53+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
54+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
55+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
56+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
57+ .scan_index = CHANNEL_SCAN_INDEX_ILLUM,
58+ }
59+};
60+
61+/* Adjust channel real bits based on report descriptor */
62+static void als_adjust_channel_bit_mask(struct iio_chan_spec *channels,
63+ int channel, int size)
64+{
65+ channels[channel].scan_type.sign = 's';
66+ /* Real storage bits will change based on the report desc. */
67+ channels[channel].scan_type.realbits = size * 8;
68+ /* Maximum size of a sample to capture is u32 */
69+ channels[channel].scan_type.storagebits = sizeof(u32) * 8;
70+}
71+
72+/* Channel read_raw handler */
73+static int als_read_raw(struct iio_dev *indio_dev,
74+ struct iio_chan_spec const *chan,
75+ int *val, int *val2,
76+ long mask)
77+{
78+ struct als_state *als_state = iio_priv(indio_dev);
79+ int report_id = -1;
80+ u32 address;
81+ int ret;
82+ int ret_type;
83+
84+ *val = 0;
85+ *val2 = 0;
86+ switch (mask) {
87+ case 0:
88+ switch (chan->scan_index) {
89+ case CHANNEL_SCAN_INDEX_ILLUM:
90+ report_id = als_state->als_illum.report_id;
91+ address =
92+ HID_USAGE_SENSOR_LIGHT_ILLUM;
93+ break;
94+ default:
95+ report_id = -1;
96+ break;
97+ }
98+ if (report_id >= 0)
99+ *val = sensor_hub_input_attr_get_raw_value(
100+ als_state->common_attributes.hsdev,
101+ HID_USAGE_SENSOR_ALS, address,
102+ report_id);
103+ else {
104+ *val = 0;
105+ return -EINVAL;
106+ }
107+ ret_type = IIO_VAL_INT;
108+ break;
109+ case IIO_CHAN_INFO_SCALE:
110+ *val = als_state->als_illum.units;
111+ ret_type = IIO_VAL_INT;
112+ break;
113+ case IIO_CHAN_INFO_OFFSET:
114+ *val = hid_sensor_convert_exponent(
115+ als_state->als_illum.unit_expo);
116+ ret_type = IIO_VAL_INT;
117+ break;
118+ case IIO_CHAN_INFO_SAMP_FREQ:
119+ ret = hid_sensor_read_samp_freq_value(
120+ &als_state->common_attributes, val, val2);
121+ ret_type = IIO_VAL_INT_PLUS_MICRO;
122+ break;
123+ case IIO_CHAN_INFO_HYSTERESIS:
124+ ret = hid_sensor_read_raw_hyst_value(
125+ &als_state->common_attributes, val, val2);
126+ ret_type = IIO_VAL_INT_PLUS_MICRO;
127+ break;
128+ default:
129+ ret_type = -EINVAL;
130+ break;
131+ }
132+
133+ return ret_type;
134+}
135+
136+/* Channel write_raw handler */
137+static int als_write_raw(struct iio_dev *indio_dev,
138+ struct iio_chan_spec const *chan,
139+ int val,
140+ int val2,
141+ long mask)
142+{
143+ struct als_state *als_state = iio_priv(indio_dev);
144+ int ret = 0;
145+
146+ switch (mask) {
147+ case IIO_CHAN_INFO_SAMP_FREQ:
148+ ret = hid_sensor_write_samp_freq_value(
149+ &als_state->common_attributes, val, val2);
150+ break;
151+ case IIO_CHAN_INFO_HYSTERESIS:
152+ ret = hid_sensor_write_raw_hyst_value(
153+ &als_state->common_attributes, val, val2);
154+ break;
155+ default:
156+ ret = -EINVAL;
157+ }
158+
159+ return ret;
160+}
161+
162+static int als_write_raw_get_fmt(struct iio_dev *indio_dev,
163+ struct iio_chan_spec const *chan,
164+ long mask)
165+{
166+ return IIO_VAL_INT_PLUS_MICRO;
167+}
168+
169+static const struct iio_info als_info = {
170+ .driver_module = THIS_MODULE,
171+ .read_raw = &als_read_raw,
172+ .write_raw = &als_write_raw,
173+ .write_raw_get_fmt = &als_write_raw_get_fmt,
174+};
175+
176+/* Function to push data to buffer */
177+static void hid_sensor_push_data(struct iio_dev *indio_dev, u8 *data, int len)
178+{
179+ struct iio_buffer *buffer = indio_dev->buffer;
180+ int datum_sz;
181+
182+ dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n");
183+ if (!buffer) {
184+ dev_err(&indio_dev->dev, "Buffer == NULL\n");
185+ return;
186+ }
187+ datum_sz = buffer->access->get_bytes_per_datum(buffer);
188+ if (len > datum_sz) {
189+ dev_err(&indio_dev->dev, "Datum size mismatch %d:%d\n", len,
190+ datum_sz);
191+ return;
192+ }
193+ iio_push_to_buffer(buffer, (u8 *)data);
194+}
195+
196+/* Callback handler to send event after all samples are received and captured */
197+static int als_proc_event(struct hid_sensor_hub_device *hsdev,
198+ unsigned usage_id,
199+ void *priv)
200+{
201+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
202+ struct als_state *als_state = iio_priv(indio_dev);
203+
204+ dev_dbg(&indio_dev->dev, "als_proc_event [%d]\n",
205+ als_state->common_attributes.data_ready);
206+ if (als_state->common_attributes.data_ready)
207+ hid_sensor_push_data(indio_dev,
208+ (u8 *)&als_state->illum,
209+ sizeof(als_state->illum));
210+
211+ return 0;
212+}
213+
214+/* Capture samples in local storage */
215+static int als_capture_sample(struct hid_sensor_hub_device *hsdev,
216+ unsigned usage_id,
217+ size_t raw_len, char *raw_data,
218+ void *priv)
219+{
220+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
221+ struct als_state *als_state = iio_priv(indio_dev);
222+ int ret = -EINVAL;
223+
224+ switch (usage_id) {
225+ case HID_USAGE_SENSOR_LIGHT_ILLUM:
226+ als_state->illum = *(u32 *)raw_data;
227+ ret = 0;
228+ break;
229+ default:
230+ break;
231+ }
232+
233+ return ret;
234+}
235+
236+/* Parse report which is specific to an usage id*/
237+static int als_parse_report(struct platform_device *pdev,
238+ struct hid_sensor_hub_device *hsdev,
239+ struct iio_chan_spec *channels,
240+ unsigned usage_id,
241+ struct als_state *st)
242+{
243+ int ret;
244+
245+ ret = sensor_hub_input_get_attribute_info(hsdev, HID_INPUT_REPORT,
246+ usage_id,
247+ HID_USAGE_SENSOR_LIGHT_ILLUM,
248+ &st->als_illum);
249+ if (ret < 0)
250+ return ret;
251+ als_adjust_channel_bit_mask(channels, CHANNEL_SCAN_INDEX_ILLUM,
252+ st->als_illum.size);
253+
254+ dev_dbg(&pdev->dev, "als %x:%x\n", st->als_illum.index,
255+ st->als_illum.report_id);
256+
257+ return ret;
258+}
259+
260+/* Function to initialize the processing for usage id */
261+static int __devinit hid_als_probe(struct platform_device *pdev)
262+{
263+ int ret = 0;
264+ static const char *name = "als";
265+ struct iio_dev *indio_dev;
266+ struct als_state *als_state;
267+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
268+ struct iio_chan_spec *channels;
269+
270+ indio_dev = iio_device_alloc(sizeof(struct als_state));
271+ if (indio_dev == NULL) {
272+ ret = -ENOMEM;
273+ goto error_ret;
274+ }
275+ platform_set_drvdata(pdev, indio_dev);
276+
277+ als_state = iio_priv(indio_dev);
278+ als_state->common_attributes.hsdev = hsdev;
279+ als_state->common_attributes.pdev = pdev;
280+
281+ ret = hid_sensor_parse_common_attributes(hsdev, HID_USAGE_SENSOR_ALS,
282+ &als_state->common_attributes);
283+ if (ret) {
284+ dev_err(&pdev->dev, "failed to setup common attributes\n");
285+ goto error_free_dev;
286+ }
287+
288+ channels = kmemdup(als_channels,
289+ sizeof(als_channels),
290+ GFP_KERNEL);
291+ if (!channels) {
292+ dev_err(&pdev->dev, "failed to duplicate channels\n");
293+ goto error_free_dev;
294+ }
295+
296+ ret = als_parse_report(pdev, hsdev, channels,
297+ HID_USAGE_SENSOR_ALS, als_state);
298+ if (ret) {
299+ dev_err(&pdev->dev, "failed to setup attributes\n");
300+ goto error_free_dev_mem;
301+ }
302+
303+ indio_dev->channels = channels;
304+ indio_dev->num_channels =
305+ ARRAY_SIZE(als_channels);
306+ indio_dev->dev.parent = &pdev->dev;
307+ indio_dev->info = &als_info;
308+ indio_dev->name = name;
309+ indio_dev->modes = INDIO_DIRECT_MODE;
310+
311+ ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time,
312+ NULL, NULL);
313+ if (ret) {
314+ dev_err(&pdev->dev, "failed to initialize trigger buffer\n");
315+ goto error_free_dev_mem;
316+ }
317+ als_state->common_attributes.data_ready = false;
318+ ret = hid_sensor_setup_trigger(indio_dev, name,
319+ &als_state->common_attributes);
320+ if (ret < 0) {
321+ dev_err(&pdev->dev, "trigger setup failed\n");
322+ goto error_unreg_buffer_funcs;
323+ }
324+
325+ ret = iio_device_register(indio_dev);
326+ if (ret) {
327+ dev_err(&pdev->dev, "device register failed\n");
328+ goto error_remove_trigger;
329+ }
330+
331+ als_state->callbacks.send_event = als_proc_event;
332+ als_state->callbacks.capture_sample = als_capture_sample;
333+ als_state->callbacks.pdev = pdev;
334+ ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_ALS,
335+ &als_state->callbacks);
336+ if (ret < 0) {
337+ dev_err(&pdev->dev, "callback reg failed\n");
338+ goto error_iio_unreg;
339+ }
340+
341+ return ret;
342+
343+error_iio_unreg:
344+ iio_device_unregister(indio_dev);
345+error_remove_trigger:
346+ hid_sensor_remove_trigger(indio_dev);
347+error_unreg_buffer_funcs:
348+ iio_triggered_buffer_cleanup(indio_dev);
349+error_free_dev_mem:
350+ kfree(indio_dev->channels);
351+error_free_dev:
352+ iio_device_free(indio_dev);
353+error_ret:
354+ return ret;
355+}
356+
357+/* Function to deinitialize the processing for usage id */
358+static int __devinit hid_als_remove(struct platform_device *pdev)
359+{
360+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
361+ struct iio_dev *indio_dev = platform_get_drvdata(pdev);
362+
363+ sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_ALS);
364+ iio_device_unregister(indio_dev);
365+ hid_sensor_remove_trigger(indio_dev);
366+ iio_triggered_buffer_cleanup(indio_dev);
367+ kfree(indio_dev->channels);
368+ iio_device_free(indio_dev);
369+
370+ return 0;
371+}
372+
373+static struct platform_driver hid_als_platform_driver = {
374+ .driver = {
375+ .name = DRIVER_NAME,
376+ .owner = THIS_MODULE,
377+ },
378+ .probe = hid_als_probe,
379+ .remove = hid_als_remove,
380+};
381+module_platform_driver(hid_als_platform_driver);
382+
383+MODULE_DESCRIPTION("HID Sensor ALS");
384+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
385+MODULE_LICENSE("GPL");
drivers/iio/magnetometer/Kconfig+16−0
@@ -0,0 +1,16 @@
1+#
2+# Magnetometer sensors
3+#
4+menu "Magnetometer sensors"
5+
6+config HID_SENSOR_MAGNETOMETER_3D
7+ depends on HID_SENSOR_HUB
8+ select IIO_BUFFER
9+ select IIO_TRIGGERED_BUFFER
10+ select HID_SENSOR_IIO_COMMON
11+ tristate "HID Magenetometer 3D"
12+ help
13+ Say yes here to build support for the HID SENSOR
14+ Magnetometer 3D.
15+
16+endmenu
drivers/iio/magnetometer/Makefile+5−0
@@ -0,0 +1,5 @@
1+#
2+# Makefile for industrial I/O Magnetometer sensor drivers
3+#
4+
5+obj-$(CONFIG_HID_SENSOR_MAGNETOMETER_3D) += hid-sensor-magn-3d.o
drivers/iio/magnetometer/hid-sensor-magn-3d.c+419−0
@@ -0,0 +1,419 @@
1+/*
2+ * HID Sensors Driver
3+ * Copyright (c) 2012, Intel Corporation.
4+ *
5+ * This program is free software; you can redistribute it and/or modify it
6+ * under the terms and conditions of the GNU General Public License,
7+ * version 2, as published by the Free Software Foundation.
8+ *
9+ * This program is distributed in the hope it will be useful, but WITHOUT
10+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12+ * more details.
13+ *
14+ * You should have received a copy of the GNU General Public License along with
15+ * this program; if not, write to the Free Software Foundation, Inc.,
16+ * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17+ *
18+ */
19+#include <linux/device.h>
20+#include <linux/platform_device.h>
21+#include <linux/module.h>
22+#include <linux/interrupt.h>
23+#include <linux/irq.h>
24+#include <linux/slab.h>
25+#include <linux/hid-sensor-hub.h>
26+#include <linux/iio/iio.h>
27+#include <linux/iio/sysfs.h>
28+#include <linux/iio/buffer.h>
29+#include <linux/iio/trigger_consumer.h>
30+#include <linux/iio/triggered_buffer.h>
31+#include "../common/hid-sensors/hid-sensor-attributes.h"
32+#include "../common/hid-sensors/hid-sensor-trigger.h"
33+
34+/*Format: HID-SENSOR-usage_id_in_hex*/
35+/*Usage ID from spec for Magnetometer-3D: 0x200083*/
36+#define DRIVER_NAME "HID-SENSOR-200083"
37+
38+enum magn_3d_channel {
39+ CHANNEL_SCAN_INDEX_X,
40+ CHANNEL_SCAN_INDEX_Y,
41+ CHANNEL_SCAN_INDEX_Z,
42+ MAGN_3D_CHANNEL_MAX,
43+};
44+
45+struct magn_3d_state {
46+ struct hid_sensor_hub_callbacks callbacks;
47+ struct hid_sensor_iio_common common_attributes;
48+ struct hid_sensor_hub_attribute_info magn[MAGN_3D_CHANNEL_MAX];
49+ u32 magn_val[MAGN_3D_CHANNEL_MAX];
50+};
51+
52+static const u32 magn_3d_addresses[MAGN_3D_CHANNEL_MAX] = {
53+ HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_X_AXIS,
54+ HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_Y_AXIS,
55+ HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_Z_AXIS
56+};
57+
58+/* Channel definitions */
59+static const struct iio_chan_spec magn_3d_channels[] = {
60+ {
61+ .type = IIO_MAGN,
62+ .modified = 1,
63+ .channel2 = IIO_MOD_X,
64+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
65+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
66+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
67+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
68+ .scan_index = CHANNEL_SCAN_INDEX_X,
69+ }, {
70+ .type = IIO_MAGN,
71+ .modified = 1,
72+ .channel2 = IIO_MOD_Y,
73+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
74+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
75+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
76+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
77+ .scan_index = CHANNEL_SCAN_INDEX_Y,
78+ }, {
79+ .type = IIO_MAGN,
80+ .modified = 1,
81+ .channel2 = IIO_MOD_Z,
82+ .info_mask = IIO_CHAN_INFO_OFFSET_SHARED_BIT |
83+ IIO_CHAN_INFO_SCALE_SHARED_BIT |
84+ IIO_CHAN_INFO_SAMP_FREQ_SHARED_BIT |
85+ IIO_CHAN_INFO_HYSTERESIS_SHARED_BIT,
86+ .scan_index = CHANNEL_SCAN_INDEX_Z,
87+ }
88+};
89+
90+/* Adjust channel real bits based on report descriptor */
91+static void magn_3d_adjust_channel_bit_mask(struct iio_chan_spec *channels,
92+ int channel, int size)
93+{
94+ channels[channel].scan_type.sign = 's';
95+ /* Real storage bits will change based on the report desc. */
96+ channels[channel].scan_type.realbits = size * 8;
97+ /* Maximum size of a sample to capture is u32 */
98+ channels[channel].scan_type.storagebits = sizeof(u32) * 8;
99+}
100+
101+/* Channel read_raw handler */
102+static int magn_3d_read_raw(struct iio_dev *indio_dev,
103+ struct iio_chan_spec const *chan,
104+ int *val, int *val2,
105+ long mask)
106+{
107+ struct magn_3d_state *magn_state = iio_priv(indio_dev);
108+ int report_id = -1;
109+ u32 address;
110+ int ret;
111+ int ret_type;
112+
113+ *val = 0;
114+ *val2 = 0;
115+ switch (mask) {
116+ case 0:
117+ report_id =
118+ magn_state->magn[chan->scan_index].report_id;
119+ address = magn_3d_addresses[chan->scan_index];
120+ if (report_id >= 0)
121+ *val = sensor_hub_input_attr_get_raw_value(
122+ magn_state->common_attributes.hsdev,
123+ HID_USAGE_SENSOR_COMPASS_3D, address,
124+ report_id);
125+ else {
126+ *val = 0;
127+ return -EINVAL;
128+ }
129+ ret_type = IIO_VAL_INT;
130+ break;
131+ case IIO_CHAN_INFO_SCALE:
132+ *val = magn_state->magn[CHANNEL_SCAN_INDEX_X].units;
133+ ret_type = IIO_VAL_INT;
134+ break;
135+ case IIO_CHAN_INFO_OFFSET:
136+ *val = hid_sensor_convert_exponent(
137+ magn_state->magn[CHANNEL_SCAN_INDEX_X].unit_expo);
138+ ret_type = IIO_VAL_INT;
139+ break;
140+ case IIO_CHAN_INFO_SAMP_FREQ:
141+ ret = hid_sensor_read_samp_freq_value(
142+ &magn_state->common_attributes, val, val2);
143+ ret_type = IIO_VAL_INT_PLUS_MICRO;
144+ break;
145+ case IIO_CHAN_INFO_HYSTERESIS:
146+ ret = hid_sensor_read_raw_hyst_value(
147+ &magn_state->common_attributes, val, val2);
148+ ret_type = IIO_VAL_INT_PLUS_MICRO;
149+ break;
150+ default:
151+ ret_type = -EINVAL;
152+ break;
153+ }
154+
155+ return ret_type;
156+}
157+
158+/* Channel write_raw handler */
159+static int magn_3d_write_raw(struct iio_dev *indio_dev,
160+ struct iio_chan_spec const *chan,
161+ int val,
162+ int val2,
163+ long mask)
164+{
165+ struct magn_3d_state *magn_state = iio_priv(indio_dev);
166+ int ret = 0;
167+
168+ switch (mask) {
169+ case IIO_CHAN_INFO_SAMP_FREQ:
170+ ret = hid_sensor_write_samp_freq_value(
171+ &magn_state->common_attributes, val, val2);
172+ break;
173+ case IIO_CHAN_INFO_HYSTERESIS:
174+ ret = hid_sensor_write_raw_hyst_value(
175+ &magn_state->common_attributes, val, val2);
176+ break;
177+ default:
178+ ret = -EINVAL;
179+ }
180+
181+ return ret;
182+}
183+
184+static int magn_3d_write_raw_get_fmt(struct iio_dev *indio_dev,
185+ struct iio_chan_spec const *chan,
186+ long mask)
187+{
188+ return IIO_VAL_INT_PLUS_MICRO;
189+}
190+
191+static const struct iio_info magn_3d_info = {
192+ .driver_module = THIS_MODULE,
193+ .read_raw = &magn_3d_read_raw,
194+ .write_raw = &magn_3d_write_raw,
195+ .write_raw_get_fmt = &magn_3d_write_raw_get_fmt,
196+};
197+
198+/* Function to push data to buffer */
199+static void hid_sensor_push_data(struct iio_dev *indio_dev, u8 *data, int len)
200+{
201+ struct iio_buffer *buffer = indio_dev->buffer;
202+ int datum_sz;
203+
204+ dev_dbg(&indio_dev->dev, "hid_sensor_push_data\n");
205+ if (!buffer) {
206+ dev_err(&indio_dev->dev, "Buffer == NULL\n");
207+ return;
208+ }
209+ datum_sz = buffer->access->get_bytes_per_datum(buffer);
210+ if (len > datum_sz) {
211+ dev_err(&indio_dev->dev, "Datum size mismatch %d:%d\n", len,
212+ datum_sz);
213+ return;
214+ }
215+ iio_push_to_buffer(buffer, (u8 *)data);
216+}
217+
218+/* Callback handler to send event after all samples are received and captured */
219+static int magn_3d_proc_event(struct hid_sensor_hub_device *hsdev,
220+ unsigned usage_id,
221+ void *priv)
222+{
223+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
224+ struct magn_3d_state *magn_state = iio_priv(indio_dev);
225+
226+ dev_dbg(&indio_dev->dev, "magn_3d_proc_event [%d]\n",
227+ magn_state->common_attributes.data_ready);
228+ if (magn_state->common_attributes.data_ready)
229+ hid_sensor_push_data(indio_dev,
230+ (u8 *)magn_state->magn_val,
231+ sizeof(magn_state->magn_val));
232+
233+ return 0;
234+}
235+
236+/* Capture samples in local storage */
237+static int magn_3d_capture_sample(struct hid_sensor_hub_device *hsdev,
238+ unsigned usage_id,
239+ size_t raw_len, char *raw_data,
240+ void *priv)
241+{
242+ struct iio_dev *indio_dev = platform_get_drvdata(priv);
243+ struct magn_3d_state *magn_state = iio_priv(indio_dev);
244+ int offset;
245+ int ret = -EINVAL;
246+
247+ switch (usage_id) {
248+ case HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_X_AXIS:
249+ case HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_Y_AXIS:
250+ case HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_Z_AXIS:
251+ offset = usage_id - HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_X_AXIS;
252+ magn_state->magn_val[CHANNEL_SCAN_INDEX_X + offset] =
253+ *(u32 *)raw_data;
254+ ret = 0;
255+ break;
256+ default:
257+ break;
258+ }
259+
260+ return ret;
261+}
262+
263+/* Parse report which is specific to an usage id*/
264+static int magn_3d_parse_report(struct platform_device *pdev,
265+ struct hid_sensor_hub_device *hsdev,
266+ struct iio_chan_spec *channels,
267+ unsigned usage_id,
268+ struct magn_3d_state *st)
269+{
270+ int ret;
271+ int i;
272+
273+ for (i = 0; i <= CHANNEL_SCAN_INDEX_Z; ++i) {
274+ ret = sensor_hub_input_get_attribute_info(hsdev,
275+ HID_INPUT_REPORT,
276+ usage_id,
277+ HID_USAGE_SENSOR_ORIENT_MAGN_FLUX_X_AXIS + i,
278+ &st->magn[CHANNEL_SCAN_INDEX_X + i]);
279+ if (ret < 0)
280+ break;
281+ magn_3d_adjust_channel_bit_mask(channels,
282+ CHANNEL_SCAN_INDEX_X + i,
283+ st->magn[CHANNEL_SCAN_INDEX_X + i].size);
284+ }
285+ dev_dbg(&pdev->dev, "magn_3d %x:%x, %x:%x, %x:%x\n",
286+ st->magn[0].index,
287+ st->magn[0].report_id,
288+ st->magn[1].index, st->magn[1].report_id,
289+ st->magn[2].index, st->magn[2].report_id);
290+
291+ return ret;
292+}
293+
294+/* Function to initialize the processing for usage id */
295+static int __devinit hid_magn_3d_probe(struct platform_device *pdev)
296+{
297+ int ret = 0;
298+ static char *name = "magn_3d";
299+ struct iio_dev *indio_dev;
300+ struct magn_3d_state *magn_state;
301+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
302+ struct iio_chan_spec *channels;
303+
304+ indio_dev = iio_device_alloc(sizeof(struct magn_3d_state));
305+ if (indio_dev == NULL) {
306+ ret = -ENOMEM;
307+ goto error_ret;
308+ }
309+ platform_set_drvdata(pdev, indio_dev);
310+
311+ magn_state = iio_priv(indio_dev);
312+ magn_state->common_attributes.hsdev = hsdev;
313+ magn_state->common_attributes.pdev = pdev;
314+
315+ ret = hid_sensor_parse_common_attributes(hsdev,
316+ HID_USAGE_SENSOR_COMPASS_3D,
317+ &magn_state->common_attributes);
318+ if (ret) {
319+ dev_err(&pdev->dev, "failed to setup common attributes\n");
320+ goto error_free_dev;
321+ }
322+
323+ channels = kmemdup(magn_3d_channels,
324+ sizeof(magn_3d_channels),
325+ GFP_KERNEL);
326+ if (!channels) {
327+ dev_err(&pdev->dev, "failed to duplicate channels\n");
328+ goto error_free_dev;
329+ }
330+
331+ ret = magn_3d_parse_report(pdev, hsdev, channels,
332+ HID_USAGE_SENSOR_COMPASS_3D, magn_state);
333+ if (ret) {
334+ dev_err(&pdev->dev, "failed to setup attributes\n");
335+ goto error_free_dev_mem;
336+ }
337+
338+ indio_dev->channels = channels;
339+ indio_dev->num_channels = ARRAY_SIZE(magn_3d_channels);
340+ indio_dev->dev.parent = &pdev->dev;
341+ indio_dev->info = &magn_3d_info;
342+ indio_dev->name = name;
343+ indio_dev->modes = INDIO_DIRECT_MODE;
344+
345+ ret = iio_triggered_buffer_setup(indio_dev, &iio_pollfunc_store_time,
346+ NULL, NULL);
347+ if (ret) {
348+ dev_err(&pdev->dev, "failed to initialize trigger buffer\n");
349+ goto error_free_dev_mem;
350+ }
351+ magn_state->common_attributes.data_ready = false;
352+ ret = hid_sensor_setup_trigger(indio_dev, name,
353+ &magn_state->common_attributes);
354+ if (ret < 0) {
355+ dev_err(&pdev->dev, "trigger setup failed\n");
356+ goto error_unreg_buffer_funcs;
357+ }
358+
359+ ret = iio_device_register(indio_dev);
360+ if (ret) {
361+ dev_err(&pdev->dev, "device register failed\n");
362+ goto error_remove_trigger;
363+ }
364+
365+ magn_state->callbacks.send_event = magn_3d_proc_event;
366+ magn_state->callbacks.capture_sample = magn_3d_capture_sample;
367+ magn_state->callbacks.pdev = pdev;
368+ ret = sensor_hub_register_callback(hsdev, HID_USAGE_SENSOR_COMPASS_3D,
369+ &magn_state->callbacks);
370+ if (ret < 0) {
371+ dev_err(&pdev->dev, "callback reg failed\n");
372+ goto error_iio_unreg;
373+ }
374+
375+ return ret;
376+
377+error_iio_unreg:
378+ iio_device_unregister(indio_dev);
379+error_remove_trigger:
380+ hid_sensor_remove_trigger(indio_dev);
381+error_unreg_buffer_funcs:
382+ iio_triggered_buffer_cleanup(indio_dev);
383+error_free_dev_mem:
384+ kfree(indio_dev->channels);
385+error_free_dev:
386+ iio_device_free(indio_dev);
387+error_ret:
388+ return ret;
389+}
390+
391+/* Function to deinitialize the processing for usage id */
392+static int __devinit hid_magn_3d_remove(struct platform_device *pdev)
393+{
394+ struct hid_sensor_hub_device *hsdev = pdev->dev.platform_data;
395+ struct iio_dev *indio_dev = platform_get_drvdata(pdev);
396+
397+ sensor_hub_remove_callback(hsdev, HID_USAGE_SENSOR_COMPASS_3D);
398+ iio_device_unregister(indio_dev);
399+ hid_sensor_remove_trigger(indio_dev);
400+ iio_triggered_buffer_cleanup(indio_dev);
401+ kfree(indio_dev->channels);
402+ iio_device_free(indio_dev);
403+
404+ return 0;
405+}
406+
407+static struct platform_driver hid_magn_3d_platform_driver = {
408+ .driver = {
409+ .name = DRIVER_NAME,
410+ .owner = THIS_MODULE,
411+ },
412+ .probe = hid_magn_3d_probe,
413+ .remove = hid_magn_3d_remove,
414+};
415+module_platform_driver(hid_magn_3d_platform_driver);
416+
417+MODULE_DESCRIPTION("HID Sensor Magnetometer 3D");
418+MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@intel.com>");
419+MODULE_LICENSE("GPL");
drivers/power/Kconfig+7−0
@@ -29,6 +29,13 @@ config APM_POWER · 28 unmodified lines
2929 Say Y here to enable support APM status emulation using
3030 battery class devices.
3131
32+config GENERIC_ADC_BATTERY
33+ tristate "Generic battery support using IIO"
34+ depends on IIO
35+ help
36+ Say Y here to enable support for the generic battery driver
37+ which uses IIO framework to read adc.
38+
3239 config MAX8925_POWER
3340 tristate "MAX8925 battery charger support"
3441 depends on MFD_MAX8925
drivers/power/Makefile+1−0
@@ -5,6 +5,7 @@ power_supply-$(CONFIG_SYSFS) += power_supply_sysfs.o · 4 unmodified lines
55 power_supply-$(CONFIG_LEDS_TRIGGERS) += power_supply_leds.o
66
77 obj-$(CONFIG_POWER_SUPPLY) += power_supply.o
8+obj-$(CONFIG_GENERIC_ADC_BATTERY) += generic-adc-battery.o
89
910 obj-$(CONFIG_PDA_POWER) += pda_power.o
1011 obj-$(CONFIG_APM_POWER) += apm_power.o
drivers/power/generic-adc-battery.c+422−0
@@ -0,0 +1,422 @@
1+/*
2+ * Generic battery driver code using IIO
3+ * Copyright (C) 2012, Anish Kumar <anish198519851985@gmail.com>
4+ * based on jz4740-battery.c
5+ * based on s3c_adc_battery.c
6+ *
7+ * This file is subject to the terms and conditions of the GNU General Public
8+ * License. See the file COPYING in the main directory of this archive for
9+ * more details.
10+ *
11+ */
12+#include <linux/interrupt.h>
13+#include <linux/platform_device.h>
14+#include <linux/power_supply.h>
15+#include <linux/gpio.h>
16+#include <linux/err.h>
17+#include <linux/timer.h>
18+#include <linux/jiffies.h>
19+#include <linux/errno.h>
20+#include <linux/init.h>
21+#include <linux/module.h>
22+#include <linux/slab.h>
23+#include <linux/iio/consumer.h>
24+#include <linux/iio/types.h>
25+#include <linux/power/generic-adc-battery.h>
26+
27+#define JITTER_DEFAULT 10 /* hope 10ms is enough */
28+
29+enum gab_chan_type {
30+ GAB_VOLTAGE = 0,
31+ GAB_CURRENT,
32+ GAB_POWER,
33+ GAB_MAX_CHAN_TYPE
34+};
35+
36+/*
37+ * gab_chan_name suggests the standard channel names for commonly used
38+ * channel types.
39+ */
40+static const char *const gab_chan_name[] = {
41+ [GAB_VOLTAGE] = "voltage",
42+ [GAB_CURRENT] = "current",
43+ [GAB_POWER] = "power",
44+};
45+
46+struct gab {
47+ struct power_supply psy;
48+ struct iio_channel *channel[GAB_MAX_CHAN_TYPE];
49+ struct gab_platform_data *pdata;
50+ struct delayed_work bat_work;
51+ int level;
52+ int status;
53+ bool cable_plugged;
54+};
55+
56+static struct gab *to_generic_bat(struct power_supply *psy)
57+{
58+ return container_of(psy, struct gab, psy);
59+}
60+
61+static void gab_ext_power_changed(struct power_supply *psy)
62+{
63+ struct gab *adc_bat = to_generic_bat(psy);
64+
65+ schedule_delayed_work(&adc_bat->bat_work, msecs_to_jiffies(0));
66+}
67+
68+static const enum power_supply_property gab_props[] = {
69+ POWER_SUPPLY_PROP_STATUS,
70+ POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN,
71+ POWER_SUPPLY_PROP_CHARGE_EMPTY_DESIGN,
72+ POWER_SUPPLY_PROP_CHARGE_NOW,
73+ POWER_SUPPLY_PROP_VOLTAGE_NOW,
74+ POWER_SUPPLY_PROP_CURRENT_NOW,
75+ POWER_SUPPLY_PROP_TECHNOLOGY,
76+ POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN,
77+ POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN,
78+ POWER_SUPPLY_PROP_MODEL_NAME,
79+};
80+
81+/*
82+ * This properties are set based on the received platform data and this
83+ * should correspond one-to-one with enum chan_type.
84+ */
85+static const enum power_supply_property gab_dyn_props[] = {
86+ POWER_SUPPLY_PROP_VOLTAGE_NOW,
87+ POWER_SUPPLY_PROP_CURRENT_NOW,
88+ POWER_SUPPLY_PROP_POWER_NOW,
89+};
90+
91+static bool gab_charge_finished(struct gab *adc_bat)
92+{
93+ struct gab_platform_data *pdata = adc_bat->pdata;
94+ bool ret = gpio_get_value(pdata->gpio_charge_finished);
95+ bool inv = pdata->gpio_inverted;
96+
97+ if (!gpio_is_valid(pdata->gpio_charge_finished))
98+ return false;
99+ return ret ^ inv;
100+}
101+
102+static int gab_get_status(struct gab *adc_bat)
103+{
104+ struct gab_platform_data *pdata = adc_bat->pdata;
105+ struct power_supply_info *bat_info;
106+
107+ bat_info = &pdata->battery_info;
108+ if (adc_bat->level == bat_info->charge_full_design)
109+ return POWER_SUPPLY_STATUS_FULL;
110+ return adc_bat->status;
111+}
112+
113+static enum gab_chan_type gab_prop_to_chan(enum power_supply_property psp)
114+{
115+ switch (psp) {
116+ case POWER_SUPPLY_PROP_POWER_NOW:
117+ return GAB_POWER;
118+ case POWER_SUPPLY_PROP_VOLTAGE_NOW:
119+ return GAB_VOLTAGE;
120+ case POWER_SUPPLY_PROP_CURRENT_NOW:
121+ return GAB_CURRENT;
122+ default:
123+ WARN_ON(1);
124+ break;
125+ }
126+ return GAB_POWER;
127+}
128+
129+static int read_channel(struct gab *adc_bat, enum power_supply_property psp,
130+ int *result)
131+{
132+ int ret;
133+ int chan_index;
134+
135+ chan_index = gab_prop_to_chan(psp);
136+ ret = iio_read_channel_processed(adc_bat->channel[chan_index],
137+ result);
138+ if (ret < 0)
139+ pr_err("read channel error\n");
140+ return ret;
141+}
142+
143+static int gab_get_property(struct power_supply *psy,
144+ enum power_supply_property psp, union power_supply_propval *val)
145+{
146+ struct gab *adc_bat;
147+ struct gab_platform_data *pdata;
148+ struct power_supply_info *bat_info;
149+ int result = 0;
150+ int ret = 0;
151+
152+ adc_bat = to_generic_bat(psy);
153+ if (!adc_bat) {
154+ dev_err(psy->dev, "no battery infos ?!\n");
155+ return -EINVAL;
156+ }
157+ pdata = adc_bat->pdata;
158+ bat_info = &pdata->battery_info;
159+
160+ switch (psp) {
161+ case POWER_SUPPLY_PROP_STATUS:
162+ gab_get_status(adc_bat);
163+ break;
164+ case POWER_SUPPLY_PROP_CHARGE_EMPTY_DESIGN:
165+ val->intval = 0;
166+ break;
167+ case POWER_SUPPLY_PROP_CHARGE_NOW:
168+ val->intval = pdata->cal_charge(result);
169+ break;
170+ case POWER_SUPPLY_PROP_VOLTAGE_NOW:
171+ case POWER_SUPPLY_PROP_CURRENT_NOW:
172+ case POWER_SUPPLY_PROP_POWER_NOW:
173+ ret = read_channel(adc_bat, psp, &result);
174+ if (ret < 0)
175+ goto err;
176+ val->intval = result;
177+ break;
178+ case POWER_SUPPLY_PROP_TECHNOLOGY:
179+ val->intval = bat_info->technology;
180+ break;
181+ case POWER_SUPPLY_PROP_VOLTAGE_MIN_DESIGN:
182+ val->intval = bat_info->voltage_min_design;
183+ break;
184+ case POWER_SUPPLY_PROP_VOLTAGE_MAX_DESIGN:
185+ val->intval = bat_info->voltage_max_design;
186+ break;
187+ case POWER_SUPPLY_PROP_CHARGE_FULL_DESIGN:
188+ val->intval = bat_info->charge_full_design;
189+ break;
190+ case POWER_SUPPLY_PROP_MODEL_NAME:
191+ val->strval = bat_info->name;
192+ break;
193+ default:
194+ return -EINVAL;
195+ }
196+err:
197+ return ret;
198+}
199+
200+static void gab_work(struct work_struct *work)
201+{
202+ struct gab *adc_bat;
203+ struct gab_platform_data *pdata;
204+ struct delayed_work *delayed_work;
205+ bool is_plugged;
206+ int status;
207+
208+ delayed_work = container_of(work, struct delayed_work, work);
209+ adc_bat = container_of(delayed_work, struct gab, bat_work);
210+ pdata = adc_bat->pdata;
211+ status = adc_bat->status;
212+
213+ is_plugged = power_supply_am_i_supplied(&adc_bat->psy);
214+ adc_bat->cable_plugged = is_plugged;
215+
216+ if (!is_plugged)
217+ adc_bat->status = POWER_SUPPLY_STATUS_DISCHARGING;
218+ else if (gab_charge_finished(adc_bat))
219+ adc_bat->status = POWER_SUPPLY_STATUS_NOT_CHARGING;
220+ else
221+ adc_bat->status = POWER_SUPPLY_STATUS_CHARGING;
222+
223+ if (status != adc_bat->status)
224+ power_supply_changed(&adc_bat->psy);
225+}
226+
227+static irqreturn_t gab_charged(int irq, void *dev_id)
228+{
229+ struct gab *adc_bat = dev_id;
230+ struct gab_platform_data *pdata = adc_bat->pdata;
231+ int delay;
232+
233+ delay = pdata->jitter_delay ? pdata->jitter_delay : JITTER_DEFAULT;
234+ schedule_delayed_work(&adc_bat->bat_work,
235+ msecs_to_jiffies(delay));
236+ return IRQ_HANDLED;
237+}
238+
239+static int __devinit gab_probe(struct platform_device *pdev)
240+{
241+ struct gab *adc_bat;
242+ struct power_supply *psy;
243+ struct gab_platform_data *pdata = pdev->dev.platform_data;
244+ enum power_supply_property *properties;
245+ int ret = 0;
246+ int chan;
247+ int index = 0;
248+
249+ adc_bat = devm_kzalloc(&pdev->dev, sizeof(*adc_bat), GFP_KERNEL);
250+ if (!adc_bat) {
251+ dev_err(&pdev->dev, "failed to allocate memory\n");
252+ return -ENOMEM;
253+ }
254+
255+ psy = &adc_bat->psy;
256+ psy->name = pdata->battery_info.name;
257+
258+ /* bootup default values for the battery */
259+ adc_bat->cable_plugged = false;
260+ adc_bat->status = POWER_SUPPLY_STATUS_DISCHARGING;
261+ psy->type = POWER_SUPPLY_TYPE_BATTERY;
262+ psy->get_property = gab_get_property;
263+ psy->external_power_changed = gab_ext_power_changed;
264+ adc_bat->pdata = pdata;
265+
266+ /* calculate the total number of channels */
267+ chan = ARRAY_SIZE(gab_chan_name);
268+
269+ /*
270+ * copying the static properties and allocating extra memory for holding
271+ * the extra configurable properties received from platform data.
272+ */
273+ psy->properties = kcalloc(ARRAY_SIZE(gab_props) +
274+ ARRAY_SIZE(gab_chan_name),
275+ sizeof(*psy->properties), GFP_KERNEL);
276+ if (!psy->properties) {
277+ ret = -ENOMEM;
278+ goto first_mem_fail;
279+ }
280+
281+ memcpy(psy->properties, gab_props, sizeof(gab_props));
282+ properties = psy->properties + sizeof(gab_props);
283+
284+ /*
285+ * getting channel from iio and copying the battery properties
286+ * based on the channel supported by consumer device.
287+ */
288+ for (chan = 0; chan < ARRAY_SIZE(gab_chan_name); chan++) {
289+ adc_bat->channel[chan] = iio_channel_get(dev_name(&pdev->dev),
290+ gab_chan_name[chan]);
291+ if (IS_ERR(adc_bat->channel[chan])) {
292+ ret = PTR_ERR(adc_bat->channel[chan]);
293+ } else {
294+ /* copying properties for supported channels only */
295+ memcpy(properties + sizeof(*(psy->properties)) * index,
296+ &gab_dyn_props[chan],
297+ sizeof(gab_dyn_props[chan]));
298+ index++;
299+ }
300+ }
301+
302+ /* none of the channels are supported so let's bail out */
303+ if (index == ARRAY_SIZE(gab_chan_name))
304+ goto second_mem_fail;
305+
306+ /*
307+ * Total number of properties is equal to static properties
308+ * plus the dynamic properties.Some properties may not be set
309+ * as come channels may be not be supported by the device.So
310+ * we need to take care of that.
311+ */
312+ psy->num_properties = ARRAY_SIZE(gab_props) + index;
313+
314+ ret = power_supply_register(&pdev->dev, psy);
315+ if (ret)
316+ goto err_reg_fail;
317+
318+ INIT_DELAYED_WORK(&adc_bat->bat_work, gab_work);
319+
320+ if (gpio_is_valid(pdata->gpio_charge_finished)) {
321+ int irq;
322+ ret = gpio_request(pdata->gpio_charge_finished, "charged");
323+ if (ret)
324+ goto gpio_req_fail;
325+
326+ irq = gpio_to_irq(pdata->gpio_charge_finished);
327+ ret = request_any_context_irq(irq, gab_charged,
328+ IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
329+ "battery charged", adc_bat);
330+ if (ret)
331+ goto err_gpio;
332+ }
333+
334+ platform_set_drvdata(pdev, adc_bat);
335+
336+ /* Schedule timer to check current status */
337+ schedule_delayed_work(&adc_bat->bat_work,
338+ msecs_to_jiffies(0));
339+ return 0;
340+
341+err_gpio:
342+ gpio_free(pdata->gpio_charge_finished);
343+gpio_req_fail:
344+ power_supply_unregister(psy);
345+err_reg_fail:
346+ for (chan = 0; ARRAY_SIZE(gab_chan_name); chan++)
347+ iio_channel_release(adc_bat->channel[chan]);
348+second_mem_fail:
349+ kfree(psy->properties);
350+first_mem_fail:
351+ return ret;
352+}
353+
354+static int __devexit gab_remove(struct platform_device *pdev)
355+{
356+ int chan;
357+ struct gab *adc_bat = platform_get_drvdata(pdev);
358+ struct gab_platform_data *pdata = adc_bat->pdata;
359+
360+ power_supply_unregister(&adc_bat->psy);
361+
362+ if (gpio_is_valid(pdata->gpio_charge_finished)) {
363+ free_irq(gpio_to_irq(pdata->gpio_charge_finished), adc_bat);
364+ gpio_free(pdata->gpio_charge_finished);
365+ }
366+
367+ for (chan = 0; ARRAY_SIZE(gab_chan_name); chan++)
368+ iio_channel_release(adc_bat->channel[chan]);
369+
370+ kfree(adc_bat->psy.properties);
371+ cancel_delayed_work(&adc_bat->bat_work);
372+ return 0;
373+}
374+
375+#ifdef CONFIG_PM
376+static int gab_suspend(struct device *dev)
377+{
378+ struct gab *adc_bat = dev_get_drvdata(dev);
379+
380+ cancel_delayed_work_sync(&adc_bat->bat_work);
381+ adc_bat->status = POWER_SUPPLY_STATUS_UNKNOWN;
382+ return 0;
383+}
384+
385+static int gab_resume(struct device *dev)
386+{
387+ struct gab *adc_bat = dev_get_drvdata(dev);
388+ struct gab_platform_data *pdata = adc_bat->pdata;
389+ int delay;
390+
391+ delay = pdata->jitter_delay ? pdata->jitter_delay : JITTER_DEFAULT;
392+
393+ /* Schedule timer to check current status */
394+ schedule_delayed_work(&adc_bat->bat_work,
395+ msecs_to_jiffies(delay));
396+ return 0;
397+}
398+
399+static const struct dev_pm_ops gab_pm_ops = {
400+ .suspend = gab_suspend,
401+ .resume = gab_resume,
402+};
403+
404+#define GAB_PM_OPS (&gab_pm_ops)
405+#else
406+#define GAB_PM_OPS (NULL)
407+#endif
408+
409+static struct platform_driver gab_driver = {
410+ .driver = {
411+ .name = "generic-adc-battery",
412+ .owner = THIS_MODULE,
413+ .pm = GAB_PM_OPS
414+ },
415+ .probe = gab_probe,
416+ .remove = __devexit_p(gab_remove),
417+};
418+module_platform_driver(gab_driver);
419+
420+MODULE_AUTHOR("anish kumar <anish198519851985@gmail.com>");
421+MODULE_DESCRIPTION("generic battery driver using IIO");
422+MODULE_LICENSE("GPL");
drivers/staging/Kconfig+8−2
@@ -122,8 +122,6 @@ source "drivers/staging/android/Kconfig" · 121 unmodified lines
122122
123123 source "drivers/staging/telephony/Kconfig"
124124
125−source "drivers/staging/ramster/Kconfig"
126−
127125 source "drivers/staging/ozwpan/Kconfig"
128126
129127 source "drivers/staging/ccg/Kconfig"
@@ -136,4 +134,12 @@ source "drivers/staging/csr/Kconfig" · 6 unmodified lines
136134
137135 source "drivers/staging/omap-thermal/Kconfig"
138136
137+source "drivers/staging/ramster/Kconfig"
138+
139+source "drivers/staging/silicom/Kconfig"
140+
141+source "drivers/staging/ced1401/Kconfig"
142+
143+source "drivers/staging/imx-drm/Kconfig"
144+
139145 endif # STAGING
drivers/staging/Makefile+4−1
@@ -54,9 +54,12 @@ obj-$(CONFIG_MFD_NVEC) += nvec/ · 53 unmodified lines
5454 obj-$(CONFIG_DRM_OMAP) += omapdrm/
5555 obj-$(CONFIG_ANDROID) += android/
5656 obj-$(CONFIG_PHONE) += telephony/
57−obj-$(CONFIG_RAMSTER) += ramster/
5857 obj-$(CONFIG_USB_WPAN_HCD) += ozwpan/
5958 obj-$(CONFIG_USB_G_CCG) += ccg/
6059 obj-$(CONFIG_WIMAX_GDM72XX) += gdm72xx/
6160 obj-$(CONFIG_CSR_WIFI) += csr/
6261 obj-$(CONFIG_OMAP_BANDGAP) += omap-thermal/
62+obj-$(CONFIG_ZCACHE2) += ramster/
63+obj-$(CONFIG_NET_VENDOR_SILICOM) += silicom/
64+obj-$(CONFIG_CED1401) += ced1401/
65+obj-$(CONFIG_DRM_IMX) += imx-drm/
drivers/staging/android/alarm-dev.c+7−10
@@ -67,10 +67,8 @@ static struct devalarm alarms[ANDROID_ALARM_TYPE_COUNT]; · 66 unmodified lines
6767
6868 static int is_wakeup(enum android_alarm_type type)
6969 {
70− if (type == ANDROID_ALARM_RTC_WAKEUP ||
71− type == ANDROID_ALARM_ELAPSED_REALTIME_WAKEUP)
72− return 1;
73− return 0;
70+ return (type == ANDROID_ALARM_RTC_WAKEUP ||
71+ type == ANDROID_ALARM_ELAPSED_REALTIME_WAKEUP);
7472 }
7573
7674
@@ -85,12 +83,9 @@ static void devalarm_start(struct devalarm *alrm, ktime_t exp) · 8 unmodified lines
8583
8684 static int devalarm_try_to_cancel(struct devalarm *alrm)
8785 {
88− int ret;
8986 if (is_wakeup(alrm->type))
90− ret = alarm_try_to_cancel(&alrm->u.alrm);
91− else
92− ret = hrtimer_try_to_cancel(&alrm->u.hrt);
93− return ret;
87+ return alarm_try_to_cancel(&alrm->u.alrm);
88+ return hrtimer_try_to_cancel(&alrm->u.hrt);
9489 }
9590
9691 static void devalarm_cancel(struct devalarm *alrm)
@@ -223,10 +218,12 @@ from_old_alarm_set: · 126 unmodified lines
223218 case ANDROID_ALARM_ELAPSED_REALTIME:
224219 get_monotonic_boottime(&tmp_time);
225220 break;
226− case ANDROID_ALARM_TYPE_COUNT:
227221 case ANDROID_ALARM_SYSTEMTIME:
228222 ktime_get_ts(&tmp_time);
229223 break;
224+ default:
225+ rv = -EINVAL;
226+ goto err1;
230227 }
231228 if (copy_to_user((void __user *)arg, &tmp_time,
232229 sizeof(tmp_time))) {
drivers/staging/android/ashmem.c+16−16
@@ -1,20 +1,20 @@
11 /* mm/ashmem.c
2−**
3−** Anonymous Shared Memory Subsystem, ashmem
4−**
5−** Copyright (C) 2008 Google, Inc.
6−**
7−** Robert Love <rlove@google.com>
8−**
9−** This software is licensed under the terms of the GNU General Public
10−** License version 2, as published by the Free Software Foundation, and
11−** may be copied, distributed, and modified under those terms.
12−**
13−** This program is distributed in the hope that it will be useful,
14−** but WITHOUT ANY WARRANTY; without even the implied warranty of
15−** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16−** GNU General Public License for more details.
17−*/
2+ *
3+ * Anonymous Shared Memory Subsystem, ashmem
4+ *
5+ * Copyright (C) 2008 Google, Inc.
6+ *
7+ * Robert Love <rlove@google.com>
8+ *
9+ * This software is licensed under the terms of the GNU General Public
10+ * License version 2, as published by the Free Software Foundation, and
11+ * may be copied, distributed, and modified under those terms.
12+ *
13+ * This program is distributed in the hope that it will be useful,
14+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
15+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16+ * GNU General Public License for more details.
17+ */
1818
1919 #define pr_fmt(fmt) "ashmem: " fmt
2020
drivers/staging/android/binder.c+3−3
@@ -365,7 +365,7 @@ binder_defer_work(struct binder_proc *proc, enum binder_deferred_state defer); · 364 unmodified lines
365365 /*
366366 * copied from get_unused_fd_flags
367367 */
368−int task_get_unused_fd_flags(struct binder_proc *proc, int flags)
368+static int task_get_unused_fd_flags(struct binder_proc *proc, int flags)
369369 {
370370 struct files_struct *files = proc->files;
371371 int fd, error;
@@ -415,13 +415,13 @@ repeat: · 43 unmodified lines
415415 else
416416 __clear_close_on_exec(fd, fdt);
417417 files->next_fd = fd + 1;
418−#if 1
418+
419419 /* Sanity check */
420420 if (fdt->fd[fd] != NULL) {
421421 pr_warn("get_unused_fd: slot %d not NULL!\n", fd);
422422 fdt->fd[fd] = NULL;
423423 }
424−#endif
424+
425425 error = fd;
426426
427427 out:
drivers/staging/android/logger.c+26−14
@@ -32,38 +32,50 @@ · 31 unmodified lines
3232
3333 #include <asm/ioctls.h>
3434
35−/*
35+/**
3636 * struct logger_log - represents a specific log, such as 'main' or 'radio'
37+ * @buffer: The actual ring buffer
38+ * @misc: The "misc" device representing the log
39+ * @wq: The wait queue for @readers
40+ * @readers: This log's readers
41+ * @mutex: The mutex that protects the @buffer
42+ * @w_off: The current write head offset
43+ * @head: The head, or location that readers start reading at.
44+ * @size: The size of the log
45+ * @logs: The list of log channels
3746 *
3847 * This structure lives from module insertion until module removal, so it does
3948 * not need additional reference counting. The structure is protected by the
4049 * mutex 'mutex'.
4150 */
4251 struct logger_log {
43− unsigned char *buffer;/* the ring buffer itself */
44− struct miscdevice misc; /* misc device representing the log */
45− wait_queue_head_t wq; /* wait queue for readers */
46− struct list_head readers; /* this log's readers */
47− struct mutex mutex; /* mutex protecting buffer */
48− size_t w_off; /* current write head offset */
49− size_t head; /* new readers start here */
50− size_t size; /* size of the log */
51− struct list_head logs; /* list of log channels (myself)*/
52+ unsigned char *buffer;
53+ struct miscdevice misc;
54+ wait_queue_head_t wq;
55+ struct list_head readers;
56+ struct mutex mutex;
57+ size_t w_off;
58+ size_t head;
59+ size_t size;
60+ struct list_head logs;
5261 };
5362
5463 static LIST_HEAD(log_list);
5564
5665
57−/*
66+/**
5867 * struct logger_reader - a logging device open for reading
68+ * @log: The associated log
69+ * @list: The associated entry in @logger_log's list
70+ * @r_off: The current read head offset.
5971 *
6072 * This object lives from open to release, so we don't need additional
6173 * reference counting. The structure is protected by log->mutex.
6274 */
6375 struct logger_reader {
64− struct logger_log *log; /* associated log */
65− struct list_head list; /* entry in logger_log's list */
66− size_t r_off; /* current read head offset */
76+ struct logger_log *log;
77+ struct list_head list;
78+ size_t r_off;
6779 };
6880
6981 /* logger_offset - returns index 'n' into the log via (optimized) modulus */
drivers/staging/android/logger.h+17−7
@@ -20,14 +20,24 @@ · 19 unmodified lines
2020 #include <linux/types.h>
2121 #include <linux/ioctl.h>
2222
23+/**
24+ * struct logger_entry - defines a single entry that is given to a logger
25+ * @len: The length of the payload
26+ * @__pad: Two bytes of padding that appear to be required
27+ * @pid: The generating process' process ID
28+ * @tid: The generating process' thread ID
29+ * @sec: The number of seconds that have elapsed since the Epoch
30+ * @nsec: The number of nanoseconds that have elapsed since @sec
31+ * @msg: The message that is to be logged
32+ */
2333 struct logger_entry {
24− __u16 len; /* length of the payload */
25− __u16 __pad; /* no matter what, we get 2 bytes of padding */
26− __s32 pid; /* generating process's pid */
27− __s32 tid; /* generating process's tid */
28− __s32 sec; /* seconds since Epoch */
29− __s32 nsec; /* nanoseconds */
30− char msg[0]; /* the entry's payload */
34+ __u16 len;
35+ __u16 __pad;
36+ __s32 pid;
37+ __s32 tid;
38+ __s32 sec;
39+ __s32 nsec;
40+ char msg[0];
3141 };
3242
3343 #define LOGGER_LOG_RADIO "log_radio" /* radio-related messages */
drivers/staging/android/timed_gpio.c+1−12
@@ -161,18 +161,7 @@ static struct platform_driver timed_gpio_driver = { · 160 unmodified lines
161161 },
162162 };
163163
164−static int __init timed_gpio_init(void)
165−{
166− return platform_driver_register(&timed_gpio_driver);
167−}
168−
169−static void __exit timed_gpio_exit(void)
170−{
171− platform_driver_unregister(&timed_gpio_driver);
172−}
173−
174−module_init(timed_gpio_init);
175−module_exit(timed_gpio_exit);
164+module_platform_driver(timed_gpio_driver);
176165
177166 MODULE_AUTHOR("Mike Lockwood <lockwood@android.com>");
178167 MODULE_DESCRIPTION("timed gpio driver");
drivers/staging/asus_oled/asus_oled.c+45−11
@@ -42,8 +42,6 @@ · 41 unmodified lines
4242 #define ASUS_OLED_NAME "asus-oled"
4343 #define ASUS_OLED_UNDERSCORE_NAME "asus_oled"
4444
45−#define ASUS_OLED_ERROR "Asus OLED Display Error: "
46−
4745 #define ASUS_OLED_STATIC 's'
4846 #define ASUS_OLED_ROLL 'r'
4947 #define ASUS_OLED_FLASH 'f'
@@ -57,8 +55,9 @@ · 7 unmodified lines
5755 #define USB_DEVICE_ID_ASUS_LCM2 0x175b
5856
5957 MODULE_AUTHOR("Jakub Schmidtke, sjakub@gmail.com");
60−MODULE_DESCRIPTION("Asus OLED Driver v" ASUS_OLED_VERSION);
58+MODULE_DESCRIPTION("Asus OLED Driver");
6159 MODULE_LICENSE("GPL");
60+MODULE_VERSION(ASUS_OLED_VERSION);
6261
6362 static struct class *oled_class;
6463 static int oled_num;
@@ -138,6 +137,7 @@ struct asus_oled_dev { · 73 unmodified lines
138137 size_t buf_size;
139138 char *buf;
140139 uint8_t enabled;
140+ uint8_t enabled_post_resume;
141141 struct device *dev;
142142 };
143143
@@ -383,13 +383,13 @@ static int append_values(struct asus_oled_dev *odev, uint8_t val, size_t count) · 239 unmodified lines
383383
384384 default:
385385 i = 0;
386− printk(ASUS_OLED_ERROR "Unknown OLED Pack Mode: %d!\n",
386+ dev_err(odev->dev, "Unknown OLED Pack Mode: %d!\n",
387387 odev->pack_mode);
388388 break;
389389 }
390390
391391 if (i >= odev->buf_size) {
392− printk(ASUS_OLED_ERROR "Buffer overflow! Report a bug:"
392+ dev_err(odev->dev, "Buffer overflow! Report a bug:"
393393 "offs: %d >= %d i: %d (x: %d y: %d)\n",
394394 (int) odev->buf_offs, (int) odev->buf_size,
395395 (int) i, (int) x, (int) y);
@@ -435,7 +435,7 @@ static ssize_t odev_set_picture(struct asus_oled_dev *odev, · 39 unmodified lines
435435 odev->buf = kmalloc(odev->buf_size, GFP_KERNEL);
436436 if (odev->buf == NULL) {
437437 odev->buf_size = 0;
438− printk(ASUS_OLED_ERROR "Out of memory!\n");
438+ dev_err(odev->dev, "Out of memory!\n");
439439 return -ENOMEM;
440440 }
441441
@@ -473,7 +473,7 @@ static ssize_t odev_set_picture(struct asus_oled_dev *odev, · 31 unmodified lines
473473 odev->pic_mode = buf[1];
474474 break;
475475 default:
476− printk(ASUS_OLED_ERROR "Wrong picture mode: '%c'.\n",
476+ dev_err(odev->dev, "Wrong picture mode: '%c'.\n",
477477 buf[1]);
478478 return -EIO;
479479 break;
@@ -533,7 +533,7 @@ static ssize_t odev_set_picture(struct asus_oled_dev *odev, · 53 unmodified lines
533533
534534 if (odev->buf == NULL) {
535535 odev->buf_size = 0;
536− printk(ASUS_OLED_ERROR "Out of memory!\n");
536+ dev_err(odev->dev, "Out of memory!\n");
537537 return -ENOMEM;
538538 }
539539
@@ -593,15 +593,15 @@ static ssize_t odev_set_picture(struct asus_oled_dev *odev, · 53 unmodified lines
593593 return count;
594594
595595 error_width:
596− printk(ASUS_OLED_ERROR "Wrong picture width specified.\n");
596+ dev_err(odev->dev, "Wrong picture width specified.\n");
597597 return -EIO;
598598
599599 error_height:
600− printk(ASUS_OLED_ERROR "Wrong picture height specified.\n");
600+ dev_err(odev->dev, "Wrong picture height specified.\n");
601601 return -EIO;
602602
603603 error_header:
604− printk(ASUS_OLED_ERROR "Wrong picture header.\n");
604+ dev_err(odev->dev, "Wrong picture header.\n");
605605 return -EIO;
606606 }
607607
@@ -766,11 +766,45 @@ static void asus_oled_disconnect(struct usb_interface *interface) · 158 unmodified lines
766766 dev_info(&interface->dev, "Disconnected Asus OLED device\n");
767767 }
768768
769+#ifdef CONFIG_PM
770+static int asus_oled_suspend(struct usb_interface *intf, pm_message_t message)
771+{
772+ struct asus_oled_dev *odev;
773+
774+ odev = usb_get_intfdata(intf);
775+ if (!odev)
776+ return -ENODEV;
777+
778+ odev->enabled_post_resume = odev->enabled;
779+ enable_oled(odev, 0);
780+
781+ return 0;
782+}
783+
784+static int asus_oled_resume(struct usb_interface *intf)
785+{
786+ struct asus_oled_dev *odev;
787+
788+ odev = usb_get_intfdata(intf);
789+ if (!odev)
790+ return -ENODEV;
791+
792+ enable_oled(odev, odev->enabled_post_resume);
793+
794+ return 0;
795+}
796+#else
797+#define asus_oled_suspend NULL
798+#define asus_oled_resume NULL
799+#endif
800+
769801 static struct usb_driver oled_driver = {
770802 .name = ASUS_OLED_NAME,
771803 .probe = asus_oled_probe,
772804 .disconnect = asus_oled_disconnect,
773805 .id_table = id_table,
806+ .suspend = asus_oled_suspend,
807+ .resume = asus_oled_resume,
774808 };
775809
776810 static CLASS_ATTR_STRING(version, S_IRUGO,
drivers/staging/bcm/Bcmchar.c+2−0
@@ -820,6 +820,7 @@ cntrlEnd: · 819 unmodified lines
820820
821821 if (copy_from_user(psFwInfo, IoBuffer.InputBuffer, IoBuffer.InputLength)) {
822822 up(&Adapter->fw_download_sema);
823+ kfree(psFwInfo);
823824 return -EFAULT;
824825 }
825826
@@ -829,6 +830,7 @@ cntrlEnd: · 3 unmodified lines
829830 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Something else is wrong %lu\n",
830831 psFwInfo->u32FirmwareLength);
831832 up(&Adapter->fw_download_sema);
833+ kfree(psFwInfo);
832834 Status = -EINVAL;
833835 return Status;
834836 }
drivers/staging/bcm/CmHost.c+68−82
@@ -235,7 +235,7 @@ void ClearTargetDSXBuffer(struct bcm_mini_adapter *Adapter, B_UINT16 TID, BOOLEA · 234 unmodified lines
235235 * @ingroup ctrl_pkt_functions
236236 * copy classifier rule into the specified SF index
237237 */
238−static inline VOID CopyClassifierRuleToSF(struct bcm_mini_adapter *Adapter, stConvergenceSLTypes *psfCSType, UINT uiSearchRuleIndex, UINT nClassifierIndex)
238+static inline VOID CopyClassifierRuleToSF(struct bcm_mini_adapter *Adapter, struct bcm_convergence_types *psfCSType, UINT uiSearchRuleIndex, UINT nClassifierIndex)
239239 {
240240 struct bcm_classifier_rule *pstClassifierEntry = NULL;
241241 /* VOID *pvPhsContext = NULL; */
@@ -428,7 +428,7 @@ VOID DeleteAllClassifiersForSF(struct bcm_mini_adapter *Adapter, UINT uiSearchRu · 186 unmodified lines
428428 * @ingroup ctrl_pkt_functions
429429 */
430430 static VOID CopyToAdapter(register struct bcm_mini_adapter *Adapter, /* <Pointer to the Adapter structure */
431− register pstServiceFlowParamSI psfLocalSet, /* <Pointer to the ServiceFlowParamSI structure */
431+ register struct bcm_connect_mgr_params *psfLocalSet, /* Pointer to the connection manager parameters structure */
432432 register UINT uiSearchRuleIndex, /* <Index of Queue, to which this data belongs */
433433 register UCHAR ucDsxType,
434434 stLocalSFAddIndicationAlt *pstAddIndication) {
@@ -439,7 +439,7 @@ static VOID CopyToAdapter(register struct bcm_mini_adapter *Adapter, /* <Pointer · 4 unmodified lines
439439 enum E_CLASSIFIER_ACTION eClassifierAction = eInvalidClassifierAction;
440440 B_UINT16 u16PacketClassificationRuleIndex = 0;
441441 int i;
442− stConvergenceSLTypes *psfCSType = NULL;
442+ struct bcm_convergence_types *psfCSType = NULL;
443443 S_PHS_RULE sPhsRule;
444444 USHORT uVCID = Adapter->PackInfo[uiSearchRuleIndex].usVCID_Value;
445445 UINT UGIValue = 0;
@@ -915,7 +915,7 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 469 unmodified lines
915915 if (!pstAddIndication->sfAuthorizedSet.bValid)
916916 pstAddIndication->sfAuthorizedSet.bValid = 1;
917917 for (nIndex = 0; nIndex < nCurClassifierCnt; nIndex++) {
918− stConvergenceSLTypes *psfCSType = NULL;
918+ struct bcm_convergence_types *psfCSType = NULL;
919919 psfCSType = &pstAddIndication->sfAuthorizedSet.cConvergenceSLTypes[nIndex];
920920
921921 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "psfCSType = %p", psfCSType);
@@ -999,13 +999,10 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 77 unmodified lines
999999 #ifdef VERSION_D5
10001000 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPv6FlowLableLength: 0x%X ",
10011001 psfCSType->cCPacketClassificationRule.u8IPv6FlowLableLength);
1002− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPv6FlowLable[6]: 0x %02X %02X %02X %02X %02X %02X ",
1003− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[0],
1004− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[1],
1005− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[2],
1006− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[3],
1007− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[4],
1008− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[5]);
1002+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1003+ DBG_LVL_ALL, "u8IPv6FlowLable[6]: 0x%*ph ",
1004+ 6, psfCSType->cCPacketClassificationRule.
1005+ u8IPv6FlowLable);
10091006 #endif
10101007 }
10111008
@@ -1015,13 +1012,9 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 3 unmodified lines
10151012 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u16CID: 0x%X", pstAddIndication->sfAdmittedSet.u16CID);
10161013 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ServiceClassNameLength: 0x%X",
10171014 pstAddIndication->sfAdmittedSet.u8ServiceClassNameLength);
1018− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ServiceClassName: 0x %02X %02X %02X %02X %02X %02X",
1019− pstAddIndication->sfAdmittedSet.u8ServiceClassName[0],
1020− pstAddIndication->sfAdmittedSet.u8ServiceClassName[1],
1021− pstAddIndication->sfAdmittedSet.u8ServiceClassName[2],
1022− pstAddIndication->sfAdmittedSet.u8ServiceClassName[3],
1023− pstAddIndication->sfAdmittedSet.u8ServiceClassName[4],
1024− pstAddIndication->sfAdmittedSet.u8ServiceClassName[5]);
1015+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL,
1016+ "u8ServiceClassName: 0x%*ph",
1017+ 6, pstAddIndication->sfAdmittedSet.u8ServiceClassName);
10251018
10261019 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8MBSService: 0x%02X", pstAddIndication->sfAdmittedSet.u8MBSService);
10271020 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8QosParamSet: 0x%02X", pstAddIndication->sfAdmittedSet.u8QosParamSet);
@@ -1066,7 +1059,7 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 38 unmodified lines
10661059 nCurClassifierCnt = MAX_CLASSIFIERS_IN_SF;
10671060
10681061 for (nIndex = 0; nIndex < nCurClassifierCnt; nIndex++) {
1069− stConvergenceSLTypes *psfCSType = NULL;
1062+ struct bcm_convergence_types *psfCSType = NULL;
10701063
10711064 psfCSType = &pstAddIndication->sfAdmittedSet.cConvergenceSLTypes[nIndex];
10721065 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, " CCPacketClassificationRuleSI====>");
@@ -1074,10 +1067,10 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 1 unmodified line
10741067 psfCSType->cCPacketClassificationRule.u8ClassifierRulePriority);
10751068 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPTypeOfServiceLength: 0x%02X",
10761069 psfCSType->cCPacketClassificationRule.u8IPTypeOfServiceLength);
1077− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPTypeOfService[3]: 0x%02X %02X %02X",
1078− psfCSType->cCPacketClassificationRule.u8IPTypeOfService[0],
1079− psfCSType->cCPacketClassificationRule.u8IPTypeOfService[1],
1080− psfCSType->cCPacketClassificationRule.u8IPTypeOfService[2]);
1070+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1071+ DBG_LVL_ALL, "u8IPTypeOfService[3]: 0x%*ph",
1072+ 3, psfCSType->cCPacketClassificationRule.
1073+ u8IPTypeOfService);
10811074 for (uiLoopIndex = 0; uiLoopIndex < 1; uiLoopIndex++)
10821075 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8Protocol: 0x%02X ", psfCSType->cCPacketClassificationRule.u8Protocol);
10831076
@@ -1098,20 +1091,20 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 14 unmodified lines
10981091 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ProtocolSourcePortRangeLength: 0x%02X ",
10991092 psfCSType->cCPacketClassificationRule.u8ProtocolSourcePortRangeLength);
11001093
1101− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ProtocolSourcePortRange[4]: 0x %02X %02X %02X %02X ",
1102− psfCSType->cCPacketClassificationRule.u8ProtocolSourcePortRange[0],
1103− psfCSType->cCPacketClassificationRule.u8ProtocolSourcePortRange[1],
1104− psfCSType->cCPacketClassificationRule.u8ProtocolSourcePortRange[2],
1105− psfCSType->cCPacketClassificationRule.u8ProtocolSourcePortRange[3]);
1094+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1095+ DBG_LVL_ALL, "u8ProtocolSourcePortRange[4]: "
1096+ "0x%*ph ", 4, psfCSType->
1097+ cCPacketClassificationRule.
1098+ u8ProtocolSourcePortRange);
11061099
11071100 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ProtocolDestPortRangeLength: 0x%02X ",
11081101 psfCSType->cCPacketClassificationRule.u8ProtocolDestPortRangeLength);
11091102
1110− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ProtocolDestPortRange[4]: 0x %02X %02X %02X %02X ",
1111− psfCSType->cCPacketClassificationRule.u8ProtocolDestPortRange[0],
1112− psfCSType->cCPacketClassificationRule.u8ProtocolDestPortRange[1],
1113− psfCSType->cCPacketClassificationRule.u8ProtocolDestPortRange[2],
1114− psfCSType->cCPacketClassificationRule.u8ProtocolDestPortRange[3]);
1103+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1104+ DBG_LVL_ALL, "u8ProtocolDestPortRange[4]: "
1105+ "0x%*ph ", 4, psfCSType->
1106+ cCPacketClassificationRule.
1107+ u8ProtocolDestPortRange);
11151108
11161109 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8EthernetDestMacAddressLength: 0x%02X ",
11171110 psfCSType->cCPacketClassificationRule.u8EthernetDestMacAddressLength);
@@ -1130,10 +1123,10 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 12 unmodified lines
11301123 u8EthernetSourceMACAddress);
11311124
11321125 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8EthertypeLength: 0x%02X ", psfCSType->cCPacketClassificationRule.u8EthertypeLength);
1133− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8Ethertype[3]: 0x%02X %02X %02X",
1134− psfCSType->cCPacketClassificationRule.u8Ethertype[0],
1135− psfCSType->cCPacketClassificationRule.u8Ethertype[1],
1136− psfCSType->cCPacketClassificationRule.u8Ethertype[2]);
1126+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1127+ DBG_LVL_ALL, "u8Ethertype[3]: 0x%*ph",
1128+ 3, psfCSType->cCPacketClassificationRule.
1129+ u8Ethertype);
11371130
11381131 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u16UserPriority: 0x%X ", psfCSType->cCPacketClassificationRule.u16UserPriority);
11391132 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u16VLANID: 0x%X ", psfCSType->cCPacketClassificationRule.u16VLANID);
@@ -1147,13 +1140,10 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 7 unmodified lines
11471140 #ifdef VERSION_D5
11481141 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPv6FlowLableLength: 0x%X ",
11491142 psfCSType->cCPacketClassificationRule.u8IPv6FlowLableLength);
1150− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8IPv6FlowLable[6]: 0x %02X %02X %02X %02X %02X %02X ",
1151− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[0],
1152− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[1],
1153− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[2],
1154− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[3],
1155− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[4],
1156− psfCSType->cCPacketClassificationRule.u8IPv6FlowLable[5]);
1143+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL,
1144+ DBG_LVL_ALL, "u8IPv6FlowLable[6]: 0x%*ph ",
1145+ 6, psfCSType->cCPacketClassificationRule.
1146+ u8IPv6FlowLable);
11571147 #endif
11581148 }
11591149
@@ -1162,13 +1152,9 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 2 unmodified lines
11621152 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u32SFID: 0x%X", pstAddIndication->sfActiveSet.u32SFID);
11631153 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u16CID: 0x%X", pstAddIndication->sfActiveSet.u16CID);
11641154 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ServiceClassNameLength: 0x%X", pstAddIndication->sfActiveSet.u8ServiceClassNameLength);
1165− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8ServiceClassName: 0x %02X %02X %02X %02X %02X %02X",
1166− pstAddIndication->sfActiveSet.u8ServiceClassName[0],
1167− pstAddIndication->sfActiveSet.u8ServiceClassName[1],
1168− pstAddIndication->sfActiveSet.u8ServiceClassName[2],
1169− pstAddIndication->sfActiveSet.u8ServiceClassName[3],
1170− pstAddIndication->sfActiveSet.u8ServiceClassName[4],
1171− pstAddIndication->sfActiveSet.u8ServiceClassName[5]);
1155+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL,
1156+ "u8ServiceClassName: 0x%*ph",
1157+ 6, pstAddIndication->sfActiveSet.u8ServiceClassName);
11721158
11731159 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8MBSService: 0x%02X", pstAddIndication->sfActiveSet.u8MBSService);
11741160 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, "u8QosParamSet: 0x%02X", pstAddIndication->sfActiveSet.u8QosParamSet);
@@ -1212,7 +1198,7 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 37 unmodified lines
12121198 nCurClassifierCnt = MAX_CLASSIFIERS_IN_SF;
12131199
12141200 for (nIndex = 0; nIndex < nCurClassifierCnt; nIndex++) {
1215− stConvergenceSLTypes *psfCSType = NULL;
1201+ struct bcm_convergence_types *psfCSType = NULL;
12161202
12171203 psfCSType = &pstAddIndication->sfActiveSet.cConvergenceSLTypes[nIndex];
12181204 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_CONTROL, DBG_LVL_ALL, " CCPacketClassificationRuleSI====>");
@@ -1314,7 +1300,7 @@ static VOID DumpCmControlPacket(PVOID pvBuffer) · 95 unmodified lines
13141300
13151301 static inline ULONG RestoreSFParam(struct bcm_mini_adapter *Adapter, ULONG ulAddrSFParamSet, PUCHAR pucDestBuffer)
13161302 {
1317− UINT nBytesToRead = sizeof(stServiceFlowParamSI);
1303+ UINT nBytesToRead = sizeof(struct bcm_connect_mgr_params);
13181304
13191305 if (ulAddrSFParamSet == 0 || NULL == pucDestBuffer) {
13201306 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Got Param address as 0!!");
@@ -1331,7 +1317,7 @@ static inline ULONG RestoreSFParam(struct bcm_mini_adapter *Adapter, ULONG ulAdd · 10 unmodified lines
13311317
13321318 static ULONG StoreSFParam(struct bcm_mini_adapter *Adapter, PUCHAR pucSrcBuffer, ULONG ulAddrSFParamSet)
13331319 {
1334− UINT nBytesToWrite = sizeof(stServiceFlowParamSI);
1320+ UINT nBytesToWrite = sizeof(struct bcm_connect_mgr_params);
13351321 int ret = 0;
13361322
13371323 if (ulAddrSFParamSet == 0 || NULL == pucSrcBuffer)
@@ -1348,8 +1334,8 @@ static ULONG StoreSFParam(struct bcm_mini_adapter *Adapter, PUCHAR pucSrcBuffer, · 10 unmodified lines
13481334 ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBuffer, UINT *puBufferLength)
13491335 {
13501336 stLocalSFAddIndicationAlt *pstAddIndicationAlt = NULL;
1351− stLocalSFAddIndication *pstAddIndication = NULL;
1352− stLocalSFDeleteRequest *pstDeletionRequest;
1337+ struct bcm_add_indication *pstAddIndication = NULL;
1338+ struct bcm_del_request *pstDeletionRequest;
13531339 UINT uiSearchRuleIndex;
13541340 ULONG ulSFID;
13551341
@@ -1360,7 +1346,7 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 4 unmodified lines
13601346 * we can stop the further classifying the pkt for this SF.
13611347 */
13621348 if (pstAddIndicationAlt->u8Type == DSD_REQ) {
1363− pstDeletionRequest = (stLocalSFDeleteRequest *)pvBuffer;
1349+ pstDeletionRequest = (struct bcm_del_request *)pvBuffer;
13641350
13651351 ulSFID = ntohl(pstDeletionRequest->u32SFID);
13661352 uiSearchRuleIndex = SearchSfid(Adapter, ulSFID);
@@ -1379,12 +1365,12 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 12 unmodified lines
13791365 }
13801366 /* For DSA_REQ, only up to "psfAuthorizedSet" parameter should be accessed by driver! */
13811367
1382− pstAddIndication = kmalloc(sizeof(*pstAddIndication), GFP_KERNEL);
1368+ pstAddIndication = kmalloc(sizeof(struct bcm_add_indication), GFP_KERNEL);
13831369 if (pstAddIndication == NULL)
13841370 return 0;
13851371
13861372 /* AUTHORIZED SET */
1387− pstAddIndication->psfAuthorizedSet = (stServiceFlowParamSI *)
1373+ pstAddIndication->psfAuthorizedSet = (struct bcm_connect_mgr_params *)
13881374 GetNextTargetBufferLocation(Adapter, pstAddIndicationAlt->u16TID);
13891375 if (!pstAddIndication->psfAuthorizedSet) {
13901376 kfree(pstAddIndication);
@@ -1398,10 +1384,10 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 7 unmodified lines
13981384 }
13991385
14001386 /* this can't possibly be right */
1401− pstAddIndication->psfAuthorizedSet = (stServiceFlowParamSI *)ntohl((ULONG)pstAddIndication->psfAuthorizedSet);
1387+ pstAddIndication->psfAuthorizedSet = (struct bcm_connect_mgr_params *)ntohl((ULONG)pstAddIndication->psfAuthorizedSet);
14021388
14031389 if (pstAddIndicationAlt->u8Type == DSA_REQ) {
1404− stLocalSFAddRequest AddRequest;
1390+ struct bcm_add_request AddRequest;
14051391
14061392 AddRequest.u8Type = pstAddIndicationAlt->u8Type;
14071393 AddRequest.eConnectionDir = pstAddIndicationAlt->u8Direction;
@@ -1409,8 +1395,8 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 1 unmodified line
14091395 AddRequest.u16CID = pstAddIndicationAlt->u16CID;
14101396 AddRequest.u16VCID = pstAddIndicationAlt->u16VCID;
14111397 AddRequest.psfParameterSet = pstAddIndication->psfAuthorizedSet;
1412− (*puBufferLength) = sizeof(stLocalSFAddRequest);
1413− memcpy(pvBuffer, &AddRequest, sizeof(stLocalSFAddRequest));
1398+ (*puBufferLength) = sizeof(struct bcm_add_request);
1399+ memcpy(pvBuffer, &AddRequest, sizeof(struct bcm_add_request));
14141400 kfree(pstAddIndication);
14151401 return 1;
14161402 }
@@ -1426,7 +1412,7 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 9 unmodified lines
14261412 pstAddIndication->u8CC = pstAddIndicationAlt->u8CC;
14271413
14281414 /* ADMITTED SET */
1429− pstAddIndication->psfAdmittedSet = (stServiceFlowParamSI *)
1415+ pstAddIndication->psfAdmittedSet = (struct bcm_connect_mgr_params *)
14301416 GetNextTargetBufferLocation(Adapter, pstAddIndicationAlt->u16TID);
14311417 if (!pstAddIndication->psfAdmittedSet) {
14321418 kfree(pstAddIndication);
@@ -1437,10 +1423,10 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 4 unmodified lines
14371423 return 0;
14381424 }
14391425
1440− pstAddIndication->psfAdmittedSet = (stServiceFlowParamSI *)ntohl((ULONG)pstAddIndication->psfAdmittedSet);
1426+ pstAddIndication->psfAdmittedSet = (struct bcm_connect_mgr_params *)ntohl((ULONG)pstAddIndication->psfAdmittedSet);
14411427
14421428 /* ACTIVE SET */
1443− pstAddIndication->psfActiveSet = (stServiceFlowParamSI *)
1429+ pstAddIndication->psfActiveSet = (struct bcm_connect_mgr_params *)
14441430 GetNextTargetBufferLocation(Adapter, pstAddIndicationAlt->u16TID);
14451431 if (!pstAddIndication->psfActiveSet) {
14461432 kfree(pstAddIndication);
@@ -1451,10 +1437,10 @@ ULONG StoreCmControlResponseMessage(struct bcm_mini_adapter *Adapter, PVOID pvBu · 4 unmodified lines
14511437 return 0;
14521438 }
14531439
1454− pstAddIndication->psfActiveSet = (stServiceFlowParamSI *)ntohl((ULONG)pstAddIndication->psfActiveSet);
1440+ pstAddIndication->psfActiveSet = (struct bcm_connect_mgr_params *)ntohl((ULONG)pstAddIndication->psfActiveSet);
14551441
1456− (*puBufferLength) = sizeof(stLocalSFAddIndication);
1457− *(stLocalSFAddIndication *)pvBuffer = *pstAddIndication;
1442+ (*puBufferLength) = sizeof(struct bcm_add_indication);
1443+ *(struct bcm_add_indication *)pvBuffer = *pstAddIndication;
14581444 kfree(pstAddIndication);
14591445 return 1;
14601446 }
@@ -1463,10 +1449,10 @@ static inline stLocalSFAddIndicationAlt · 2 unmodified lines
14631449 *RestoreCmControlResponseMessage(register struct bcm_mini_adapter *Adapter, register PVOID pvBuffer)
14641450 {
14651451 ULONG ulStatus = 0;
1466− stLocalSFAddIndication *pstAddIndication = NULL;
1452+ struct bcm_add_indication *pstAddIndication = NULL;
14671453 stLocalSFAddIndicationAlt *pstAddIndicationDest = NULL;
14681454
1469− pstAddIndication = (stLocalSFAddIndication *)(pvBuffer);
1455+ pstAddIndication = (struct bcm_add_indication *)(pvBuffer);
14701456 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "=====>");
14711457 if ((pstAddIndication->u8Type == DSD_REQ) ||
14721458 (pstAddIndication->u8Type == DSD_RSP) ||
@@ -1553,7 +1539,7 @@ ULONG SetUpTargetDsxBuffers(struct bcm_mini_adapter *Adapter) · 80 unmodified lines
15531539 if (Adapter->astTargetDsxBuffer[0].ulTargetDsxBuffer)
15541540 return 1;
15551541
1556− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Size of Each DSX Buffer(Also size of ServiceFlowParamSI): %zx ", sizeof(stServiceFlowParamSI));
1542+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Size of Each DSX Buffer(Also size of connection manager parameters): %zx ", sizeof(struct bcm_connect_mgr_params));
15571543 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Reading DSX buffer From Target location %x ", DSX_MESSAGE_EXCHANGE_BUFFER);
15581544
15591545 Status = rdmalt(Adapter, DSX_MESSAGE_EXCHANGE_BUFFER, (PUINT)&ulTargetDsxBuffersBase, sizeof(UINT));
@@ -1564,7 +1550,7 @@ ULONG SetUpTargetDsxBuffers(struct bcm_mini_adapter *Adapter) · 4 unmodified lines
15641550
15651551 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Base Address Of DSX Target Buffer : 0x%lx", ulTargetDsxBuffersBase);
15661552 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "Tgt Buffer is Now %lx :", ulTargetDsxBuffersBase);
1567− ulCntTargetBuffers = DSX_MESSAGE_EXCHANGE_BUFFER_SIZE / sizeof(stServiceFlowParamSI);
1553+ ulCntTargetBuffers = DSX_MESSAGE_EXCHANGE_BUFFER_SIZE / sizeof(struct bcm_connect_mgr_params);
15681554
15691555 Adapter->ulTotalTargetBuffersAvailable =
15701556 ulCntTargetBuffers > MAX_TARGET_DSX_BUFFERS ?
@@ -1576,7 +1562,7 @@ ULONG SetUpTargetDsxBuffers(struct bcm_mini_adapter *Adapter) · 5 unmodified lines
15761562 Adapter->astTargetDsxBuffer[i].ulTargetDsxBuffer = ulTargetDsxBuffersBase;
15771563 Adapter->astTargetDsxBuffer[i].valid = 1;
15781564 Adapter->astTargetDsxBuffer[i].tid = 0;
1579− ulTargetDsxBuffersBase += sizeof(stServiceFlowParamSI);
1565+ ulTargetDsxBuffersBase += sizeof(struct bcm_connect_mgr_params);
15801566 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, " Target DSX Buffer %lx setup at 0x%lx",
15811567 i, Adapter->astTargetDsxBuffer[i].ulTargetDsxBuffer);
15821568 }
@@ -1647,7 +1633,7 @@ int FreeAdapterDsxBuffer(struct bcm_mini_adapter *Adapter) · 64 unmodified lines
16471633 BOOLEAN CmControlResponseMessage(struct bcm_mini_adapter *Adapter, /* <Pointer to the Adapter structure */
16481634 PVOID pvBuffer /* Starting Address of the Buffer, that contains the AddIndication Data */)
16491635 {
1650− stServiceFlowParamSI *psfLocalSet = NULL;
1636+ struct bcm_connect_mgr_params *psfLocalSet = NULL;
16511637 stLocalSFAddIndicationAlt *pstAddIndication = NULL;
16521638 stLocalSFChangeIndicationAlt *pstChangeIndication = NULL;
16531639 struct bcm_leader *pLeader = NULL;
@@ -1658,7 +1644,7 @@ BOOLEAN CmControlResponseMessage(struct bcm_mini_adapter *Adapter, /* <Pointer · 4 unmodified lines
16581644 */
16591645 pstAddIndication = RestoreCmControlResponseMessage(Adapter, pvBuffer);
16601646 if (pstAddIndication == NULL) {
1661− ClearTargetDSXBuffer(Adapter, ((stLocalSFAddIndication *)pvBuffer)->u16TID, FALSE);
1647+ ClearTargetDSXBuffer(Adapter, ((struct bcm_add_indication *)pvBuffer)->u16TID, FALSE);
16621648 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_PRINTK, 0, 0, "Error in restoring Service Flow param structure from DSx message");
16631649 return FALSE;
16641650 }
@@ -1870,10 +1856,10 @@ BOOLEAN CmControlResponseMessage(struct bcm_mini_adapter *Adapter, /* <Pointer · 205 unmodified lines
18701856 UINT uiSearchRuleIndex;
18711857 ULONG ulSFID;
18721858
1873− pLeader->PLength = sizeof(stLocalSFDeleteIndication);
1874− *((stLocalSFDeleteIndication *)&(Adapter->caDsxReqResp[LEADER_SIZE])) = *((stLocalSFDeleteIndication *)pstAddIndication);
1859+ pLeader->PLength = sizeof(struct bcm_del_indication);
1860+ *((struct bcm_del_indication *)&(Adapter->caDsxReqResp[LEADER_SIZE])) = *((struct bcm_del_indication *)pstAddIndication);
18751861
1876− ulSFID = ntohl(((stLocalSFDeleteIndication *)pstAddIndication)->u32SFID);
1862+ ulSFID = ntohl(((struct bcm_del_indication *)pstAddIndication)->u32SFID);
18771863 uiSearchRuleIndex = SearchSfid(Adapter, ulSFID);
18781864 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "DSD - Removing connection %x", uiSearchRuleIndex);
18791865
@@ -1884,7 +1870,7 @@ BOOLEAN CmControlResponseMessage(struct bcm_mini_adapter *Adapter, /* <Pointer · 4 unmodified lines
18841870 }
18851871
18861872 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, CONN_MSG, DBG_LVL_ALL, "SENDING DSD RESPONSE TO MAC");
1887− ((stLocalSFDeleteIndication *)&(Adapter->caDsxReqResp[LEADER_SIZE]))->u8Type = DSD_RSP;
1873+ ((struct bcm_del_indication *)&(Adapter->caDsxReqResp[LEADER_SIZE]))->u8Type = DSD_RSP;
18881874 CopyBufferToControlPacket(Adapter, (PVOID)Adapter->caDsxReqResp);
18891875 }
18901876 case DSD_RSP:
@@ -1927,7 +1913,7 @@ int get_dsx_sf_data_to_application(struct bcm_mini_adapter *Adapter, UINT uiSFId · 36 unmodified lines
19271913 VOID OverrideServiceFlowParams(struct bcm_mini_adapter *Adapter, PUINT puiBuffer)
19281914 {
19291915 B_UINT32 u32NumofSFsinMsg = ntohl(*(puiBuffer + 1));
1930− stIM_SFHostNotify *pHostInfo = NULL;
1916+ struct bcm_stim_sfhostnotify *pHostInfo = NULL;
19311917 UINT uiSearchRuleIndex = 0;
19321918 ULONG ulSFID = 0;
19331919
@@ -1936,7 +1922,7 @@ VOID OverrideServiceFlowParams(struct bcm_mini_adapter *Adapter, PUINT puiBuffer · 2 unmodified lines
19361922
19371923 while (u32NumofSFsinMsg != 0 && u32NumofSFsinMsg < NO_OF_QUEUES) {
19381924 u32NumofSFsinMsg--;
1939− pHostInfo = (stIM_SFHostNotify *)puiBuffer;
1925+ pHostInfo = (struct bcm_stim_sfhostnotify *)puiBuffer;
19401926 puiBuffer = (PUINT)(pHostInfo + 1);
19411927
19421928 ulSFID = ntohl(pHostInfo->SFID);
drivers/staging/bcm/CmHost.h+19−35
@@ -35,8 +35,7 @@ typedef struct stLocalSFAddRequestAlt{ · 34 unmodified lines
3535 B_UINT16 u16VCID;
3636
3737
38− /// \brief structure ParameterSet
39− stServiceFlowParamSI sfParameterSet;
38+ struct bcm_connect_mgr_params sfParameterSet;
4039
4140 //USE_MEMORY_MANAGER();
4241 }stLocalSFAddRequestAlt;
@@ -50,12 +49,9 @@ typedef struct stLocalSFAddIndicationAlt{ · 7 unmodified lines
5049 B_UINT16 u16CID;
5150 /// \brief 16bitVCID
5251 B_UINT16 u16VCID;
53− /// \brief structure AuthorizedSet
54− stServiceFlowParamSI sfAuthorizedSet;
55− /// \brief structure AdmittedSet
56− stServiceFlowParamSI sfAdmittedSet;
57− /// \brief structure ActiveSet
58− stServiceFlowParamSI sfActiveSet;
52+ struct bcm_connect_mgr_params sfAuthorizedSet;
53+ struct bcm_connect_mgr_params sfAdmittedSet;
54+ struct bcm_connect_mgr_params sfActiveSet;
5955
6056 B_UINT8 u8CC; /**< Confirmation Code*/
6157 B_UINT8 u8Padd; /**< 8-bit Padding */
@@ -72,12 +68,9 @@ typedef struct stLocalSFAddConfirmationAlt{ · 10 unmodified lines
7268 B_UINT16 u16CID;
7369 /// \brief 16bitVCID
7470 B_UINT16 u16VCID;
75− /// \brief structure AuthorizedSet
76− stServiceFlowParamSI sfAuthorizedSet;
77− /// \brief structure AdmittedSet
78− stServiceFlowParamSI sfAdmittedSet;
79− /// \brief structure ActiveSet
80− stServiceFlowParamSI sfActiveSet;
71+ struct bcm_connect_mgr_params sfAuthorizedSet;
72+ struct bcm_connect_mgr_params sfAdmittedSet;
73+ struct bcm_connect_mgr_params sfActiveSet;
8174 }stLocalSFAddConfirmationAlt;
8275
8376
@@ -91,16 +84,13 @@ typedef struct stLocalSFChangeRequestAlt{ · 7 unmodified lines
9184 /// \brief 16bitVCID
9285 B_UINT16 u16VCID;
9386 /*
94− //Pointer location at which following Service Flow param Structure can be read
95− //from the target. We get only the address location and we need to read out the
96− //entire SF param structure at the given location on target
87+ //Pointer location at which following connection manager param Structure can be read
88+ //from the target. We only get the address location and we need to read out the
89+ //entire connection manager param structure at the given location on target
9790 */
98− /// \brief structure AuthorizedSet
99− stServiceFlowParamSI sfAuthorizedSet;
100− /// \brief structure AdmittedSet
101− stServiceFlowParamSI sfAdmittedSet;
102− /// \brief structure ParameterSet
103− stServiceFlowParamSI sfActiveSet;
91+ struct bcm_connect_mgr_params sfAuthorizedSet;
92+ struct bcm_connect_mgr_params sfAdmittedSet;
93+ struct bcm_connect_mgr_params sfActiveSet;
10494
10595 B_UINT8 u8CC; /**< Confirmation Code*/
10696 B_UINT8 u8Padd; /**< 8-bit Padding */
@@ -117,12 +107,9 @@ typedef struct stLocalSFChangeConfirmationAlt{ · 10 unmodified lines
117107 B_UINT16 u16CID;
118108 /// \brief 16bitVCID
119109 B_UINT16 u16VCID;
120− /// \brief structure AuthorizedSet
121− stServiceFlowParamSI sfAuthorizedSet;
122− /// \brief structure AdmittedSet
123− stServiceFlowParamSI sfAdmittedSet;
124− /// \brief structure ActiveSet
125− stServiceFlowParamSI sfActiveSet;
110+ struct bcm_connect_mgr_params sfAuthorizedSet;
111+ struct bcm_connect_mgr_params sfAdmittedSet;
112+ struct bcm_connect_mgr_params sfActiveSet;
126113
127114 }stLocalSFChangeConfirmationAlt;
128115
@@ -135,12 +122,9 @@ typedef struct stLocalSFChangeIndicationAlt{ · 6 unmodified lines
135122 B_UINT16 u16CID;
136123 /// \brief 16bitVCID
137124 B_UINT16 u16VCID;
138− /// \brief structure AuthorizedSet
139− stServiceFlowParamSI sfAuthorizedSet;
140− /// \brief structure AdmittedSet
141− stServiceFlowParamSI sfAdmittedSet;
142− /// \brief structure ActiveSet
143− stServiceFlowParamSI sfActiveSet;
125+ struct bcm_connect_mgr_params sfAuthorizedSet;
126+ struct bcm_connect_mgr_params sfAdmittedSet;
127+ struct bcm_connect_mgr_params sfActiveSet;
144128
145129 B_UINT8 u8CC; /**< Confirmation Code*/
146130 B_UINT8 u8Padd; /**< 8-bit Padding */
drivers/staging/bcm/InterfaceInit.c+13−4
@@ -8,6 +8,7 @@ static struct usb_device_id InterfaceUsbtable[] = { · 7 unmodified lines
88 { USB_DEVICE(BCM_USB_VENDOR_ID_ZTE, BCM_USB_PRODUCT_ID_226) },
99 { USB_DEVICE(BCM_USB_VENDOR_ID_FOXCONN, BCM_USB_PRODUCT_ID_1901) },
1010 { USB_DEVICE(BCM_USB_VENDOR_ID_ZTE, BCM_USB_PRODUCT_ID_ZTE_TU25) },
11+ { USB_DEVICE(BCM_USB_VENDOR_ID_ZTE, BCM_USB_PRODUCT_ID_ZTE_226) },
1112 { }
1213 };
1314 MODULE_DEVICE_TABLE(usb, InterfaceUsbtable);
@@ -669,16 +670,24 @@ struct class *bcm_class; · 655 unmodified lines
669670
670671 static __init int bcm_init(void)
671672 {
672− printk(KERN_INFO "%s: %s, %s\n", DRV_NAME, DRV_DESCRIPTION, DRV_VERSION);
673− printk(KERN_INFO "%s\n", DRV_COPYRIGHT);
673+ int retval;
674+
675+ pr_info("%s: %s, %s\n", DRV_NAME, DRV_DESCRIPTION, DRV_VERSION);
676+ pr_info("%s\n", DRV_COPYRIGHT);
674677
675678 bcm_class = class_create(THIS_MODULE, DRV_NAME);
676679 if (IS_ERR(bcm_class)) {
677− printk(KERN_ERR DRV_NAME ": could not create class\n");
680+ pr_err(DRV_NAME ": could not create class\n");
678681 return PTR_ERR(bcm_class);
679682 }
680683
681− return usb_register(&usbbcm_driver);
684+ retval = usb_register(&usbbcm_driver);
685+ if (retval < 0) {
686+ pr_err(DRV_NAME ": could not register usb driver\n");
687+ class_destroy(bcm_class);
688+ return retval;
689+ }
690+ return 0;
682691 }
683692
684693 static __exit void bcm_exit(void)
drivers/staging/bcm/InterfaceInit.h+16−17
@@ -1,27 +1,26 @@
11 #ifndef _INTERFACE_INIT_H
22 #define _INTERFACE_INIT_H
33
4−#define BCM_USB_VENDOR_ID_T3 0x198f
5−#define BCM_USB_VENDOR_ID_FOXCONN 0x0489
6−#define BCM_USB_VENDOR_ID_ZTE 0x19d2
4+#define BCM_USB_VENDOR_ID_T3 0x198f
5+#define BCM_USB_VENDOR_ID_FOXCONN 0x0489
6+#define BCM_USB_VENDOR_ID_ZTE 0x19d2
77
8−#define BCM_USB_PRODUCT_ID_T3 0x0300
9−#define BCM_USB_PRODUCT_ID_T3B 0x0210
10−#define BCM_USB_PRODUCT_ID_T3L 0x0220
11−#define BCM_USB_PRODUCT_ID_SM250 0xbccd
12−#define BCM_USB_PRODUCT_ID_SYM 0x15E
13−#define BCM_USB_PRODUCT_ID_1901 0xe017
14−#define BCM_USB_PRODUCT_ID_226 0x0132
15−#define BCM_USB_PRODUCT_ID_ZTE_TU25 0x0007
8+#define BCM_USB_PRODUCT_ID_T3 0x0300
9+#define BCM_USB_PRODUCT_ID_T3B 0x0210
10+#define BCM_USB_PRODUCT_ID_T3L 0x0220
11+#define BCM_USB_PRODUCT_ID_SM250 0xbccd
12+#define BCM_USB_PRODUCT_ID_SYM 0x15E
13+#define BCM_USB_PRODUCT_ID_1901 0xe017
14+#define BCM_USB_PRODUCT_ID_226 0x0132 /* not sure if this is valid */
15+#define BCM_USB_PRODUCT_ID_ZTE_226 0x172
16+#define BCM_USB_PRODUCT_ID_ZTE_TU25 0x0007
1617
17−#define BCM_USB_MINOR_BASE 192
18+#define BCM_USB_MINOR_BASE 192
1819
20+int InterfaceInitialize(void);
1921
20−INT InterfaceInitialize(void);
22+int InterfaceExit(void);
2123
22−INT InterfaceExit(void);
23−
24−INT usbbcm_worker_thread(PS_INTERFACE_ADAPTER psIntfAdapter);
24+int usbbcm_worker_thread(PS_INTERFACE_ADAPTER psIntfAdapter);
2525
2626 #endif
27−
drivers/staging/bcm/Kconfig+1−1
@@ -1,6 +1,6 @@
11 config BCM_WIMAX
22 tristate "Beceem BCS200/BCS220-3 and BCSM250 wimax support"
3− depends on USB && NET && EXPERIMENTAL
3+ depends on USB && NET
44 default N
55 help
66 This is an experimental driver for the Beceem WIMAX chipset used
drivers/staging/bcm/Misc.c+4−1
@@ -752,7 +752,10 @@ VOID DumpPackInfo(struct bcm_mini_adapter *Adapter) · 751 unmodified lines
752752 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "AuthzSet: %x\n", Adapter->PackInfo[uiLoopIndex].bAuthorizedSet);
753753 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "ClassifyPrority: %x\n", Adapter->PackInfo[uiLoopIndex].bClassifierPriority);
754754 BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "uiMaxLatency: %x\n", Adapter->PackInfo[uiLoopIndex].uiMaxLatency);
755− BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "ServiceClassName: %x %x %x %x\n", Adapter->PackInfo[uiLoopIndex].ucServiceClassName[0], Adapter->PackInfo[uiLoopIndex].ucServiceClassName[1], Adapter->PackInfo[uiLoopIndex].ucServiceClassName[2], Adapter->PackInfo[uiLoopIndex].ucServiceClassName[3]);
755+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_OTHERS, DUMP_INFO,
756+ DBG_LVL_ALL, "ServiceClassName: %*ph\n",
757+ 4, Adapter->PackInfo[uiLoopIndex].
758+ ucServiceClassName);
756759 /* BCM_DEBUG_PRINT (Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "bHeaderSuppressionEnabled :%X\n", Adapter->PackInfo[uiLoopIndex].bHeaderSuppressionEnabled);
757760 * BCM_DEBUG_PRINT (Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "uiTotalTxBytes:%X\n", Adapter->PackInfo[uiLoopIndex].uiTotalTxBytes);
758761 * BCM_DEBUG_PRINT (Adapter, DBG_TYPE_OTHERS, DUMP_INFO, DBG_LVL_ALL, "uiTotalRxBytes:%X\n", Adapter->PackInfo[uiLoopIndex].uiTotalRxBytes);
drivers/staging/bcm/PHSModule.c+2−2
@@ -66,7 +66,7 @@ Input parameters: IN struct bcm_mini_adapter *Adapter - Miniport Adapte · 65 unmodified lines
6666 BOOLEAN bHeaderSuppressionEnabled - indicates if header suprression is enabled for SF.
6767
6868 Return: STATUS_SUCCESS - If the send was successful.
69− Other - If an error occured.
69+ Other - If an error occurred.
7070 */
7171
7272 int PHSTransmit(struct bcm_mini_adapter *Adapter,
@@ -346,7 +346,7 @@ int phs_init(PPHS_DEVICE_EXTENSION pPhsdeviceExtension, struct bcm_mini_adapter · 273 unmodified lines
346346
347347
348348
349− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, PHS_DISPATCH, DBG_LVL_ALL, "\n phs_init Successfull");
349+ BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, PHS_DISPATCH, DBG_LVL_ALL, "\n phs_init Successful");
350350 return STATUS_SUCCESS;
351351 }
352352
drivers/staging/bcm/Prototypes.h+1−1
@@ -95,7 +95,7 @@ void beceem_parse_target_struct(struct bcm_mini_adapter *Adapter); · 94 unmodified lines
9595 int bcm_ioctl_fw_download(struct bcm_mini_adapter *Adapter, struct bcm_firmware_info *psFwInfo);
9696
9797 void CopyMIBSExtendedSFParameters(struct bcm_mini_adapter *Adapter,
98− CServiceFlowParamSI *psfLocalSet, UINT uiSearchRuleIndex);
98+ struct bcm_connect_mgr_params *psfLocalSet, UINT uiSearchRuleIndex);
9999
100100 VOID ResetCounters(struct bcm_mini_adapter *Adapter);
101101
drivers/staging/bcm/Transmit.c+106−128
@@ -1,162 +1,149 @@
11 /**
2−@file Transmit.c
3−@defgroup tx_functions Transmission
4−@section Queueing
5−@dot
6−digraph transmit1 {
7−node[shape=box]
8−edge[weight=5;color=red]
9−
10−bcm_transmit->GetPacketQueueIndex[label="IP Packet"]
11−GetPacketQueueIndex->IpVersion4[label="IPV4"]
12−GetPacketQueueIndex->IpVersion6[label="IPV6"]
13−}
14−
15−@enddot
16−
17−@section De-Queueing
18−@dot
19−digraph transmit2 {
20−node[shape=box]
21−edge[weight=5;color=red]
22−interrupt_service_thread->transmit_packets
23−tx_pkt_hdler->transmit_packets
24−transmit_packets->CheckAndSendPacketFromIndex
25−transmit_packets->UpdateTokenCount
26−CheckAndSendPacketFromIndex->PruneQueue
27−CheckAndSendPacketFromIndex->IsPacketAllowedForFlow
28−CheckAndSendPacketFromIndex->SendControlPacket[label="control pkt"]
29−SendControlPacket->bcm_cmd53
30−CheckAndSendPacketFromIndex->SendPacketFromQueue[label="data pkt"]
31−SendPacketFromQueue->SetupNextSend->bcm_cmd53
32−}
33−@enddot
34−*/
2+ * @file Transmit.c
3+ * @defgroup tx_functions Transmission
4+ * @section Queueing
5+ * @dot
6+ * digraph transmit1 {
7+ * node[shape=box]
8+ * edge[weight=5;color=red]
9+ *
10+ * bcm_transmit->GetPacketQueueIndex[label="IP Packet"]
11+ * GetPacketQueueIndex->IpVersion4[label="IPV4"]
12+ * GetPacketQueueIndex->IpVersion6[label="IPV6"]
13+ * }
14+ *
15+ * @enddot
16+ *
17+ * @section De-Queueing
18+ * @dot
19+ * digraph transmit2 {
20+ * node[shape=box]
21+ * edge[weight=5;color=red]
22+ * interrupt_service_thread->transmit_packets
23+ * tx_pkt_hdler->transmit_packets
24+ * transmit_packets->CheckAndSendPacketFromIndex
25+ * transmit_packets->UpdateTokenCount
26+ * CheckAndSendPacketFromIndex->PruneQueue
27+ * CheckAndSendPacketFromIndex->IsPacketAllowedForFlow
28+ * CheckAndSendPacketFromIndex->SendControlPacket[label="control pkt"]
29+ * SendControlPacket->bcm_cmd53
30+ * CheckAndSendPacketFromIndex->SendPacketFromQueue[label="data pkt"]
31+ * SendPacketFromQueue->SetupNextSend->bcm_cmd53
32+ * }
33+ * @enddot
34+ */
3535
3636 #include "headers.h"
3737
38−
3938 /**
40−@ingroup ctrl_pkt_functions
41−This function dispatches control packet to the h/w interface
42−@return zero(success) or -ve value(failure)
43−*/
44−INT SendControlPacket(struct bcm_mini_adapter *Adapter, char *pControlPacket)
39+ * @ingroup ctrl_pkt_functions
40+ * This function dispatches control packet to the h/w interface
41+ * @return zero(success) or -ve value(failure)
42+ */
43+int SendControlPacket(struct bcm_mini_adapter *Adapter, char *pControlPacket)
4544 {
4645 struct bcm_leader *PLeader = (struct bcm_leader *)pControlPacket;
4746
48− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Tx");
49− if(!pControlPacket || !Adapter)
50− {
51− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Got NULL Control Packet or Adapter");
47+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Tx");
48+ if (!pControlPacket || !Adapter) {
49+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Got NULL Control Packet or Adapter");
50+ return STATUS_FAILURE;
51+ }
52+ if ((atomic_read(&Adapter->CurrNumFreeTxDesc) <
53+ ((PLeader->PLength-1)/MAX_DEVICE_DESC_SIZE)+1)) {
54+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "NO FREE DESCRIPTORS TO SEND CONTROL PACKET");
5255 return STATUS_FAILURE;
5356 }
54− if((atomic_read( &Adapter->CurrNumFreeTxDesc ) <
55− ((PLeader->PLength-1)/MAX_DEVICE_DESC_SIZE)+1))
56− {
57− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "NO FREE DESCRIPTORS TO SEND CONTROL PACKET");
58− return STATUS_FAILURE;
59− }
6057
6158 /* Update the netdevice statistics */
6259 /* Dump Packet */
63− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader Status: %x", PLeader->Status);
64− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader VCID: %x",PLeader->Vcid);
65− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader Length: %x",PLeader->PLength);
66− if(Adapter->device_removed)
60+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader Status: %x", PLeader->Status);
61+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader VCID: %x", PLeader->Vcid);
62+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "Leader Length: %x", PLeader->PLength);
63+ if (Adapter->device_removed)
6764 return 0;
6865
6966 if (netif_msg_pktdata(Adapter))
7067 print_hex_dump(KERN_DEBUG, PFX "tx control: ", DUMP_PREFIX_NONE,
71− 16, 1, pControlPacket, PLeader->PLength + LEADER_SIZE, 0);
68+ 16, 1, pControlPacket, PLeader->PLength + LEADER_SIZE, 0);
7269
7370 Adapter->interface_transmit(Adapter->pvInterfaceAdapter,
74− pControlPacket, (PLeader->PLength + LEADER_SIZE));
71+ pControlPacket, (PLeader->PLength + LEADER_SIZE));
7572
7673 atomic_dec(&Adapter->CurrNumFreeTxDesc);
77− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "<=========");
74+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_CONTROL, DBG_LVL_ALL, "<=========");
7875 return STATUS_SUCCESS;
7976 }
8077
8178 /**
82−@ingroup tx_functions
83−This function despatches the IP packets with the given vcid
84−to the target via the host h/w interface.
85−@return zero(success) or -ve value(failure)
86−*/
87−INT SetupNextSend(struct bcm_mini_adapter *Adapter, struct sk_buff *Packet, USHORT Vcid)
79+ * @ingroup tx_functions
80+ * This function despatches the IP packets with the given vcid
81+ * to the target via the host h/w interface.
82+ * @return zero(success) or -ve value(failure)
83+ */
84+int SetupNextSend(struct bcm_mini_adapter *Adapter, struct sk_buff *Packet, USHORT Vcid)
8885 {
89− int status=0;
90− BOOLEAN bHeaderSupressionEnabled = FALSE;
91− B_UINT16 uiClassifierRuleID;
86+ int status = 0;
87+ BOOLEAN bHeaderSupressionEnabled = FALSE;
88+ B_UINT16 uiClassifierRuleID;
9289 u16 QueueIndex = skb_get_queue_mapping(Packet);
93− struct bcm_leader Leader={0};
90+ struct bcm_leader Leader = {0};
9491
95− if(Packet->len > MAX_DEVICE_DESC_SIZE)
96− {
92+ if (Packet->len > MAX_DEVICE_DESC_SIZE) {
9793 status = STATUS_FAILURE;
9894 goto errExit;
9995 }
10096
10197 /* Get the Classifier Rule ID */
102− uiClassifierRuleID = *((UINT32*) (Packet->cb)+SKB_CB_CLASSIFICATION_OFFSET);
98+ uiClassifierRuleID = *((UINT32 *) (Packet->cb) + SKB_CB_CLASSIFICATION_OFFSET);
10399
104100 bHeaderSupressionEnabled = Adapter->PackInfo[QueueIndex].bHeaderSuppressionEnabled
105101 & Adapter->bPHSEnabled;
106102
107− if(Adapter->device_removed)
108− {
103+ if (Adapter->device_removed) {
109104 status = STATUS_FAILURE;
110105 goto errExit;
111− }
106+ }
112107
113108 status = PHSTransmit(Adapter, &Packet, Vcid, uiClassifierRuleID, bHeaderSupressionEnabled,
114− (UINT *)&Packet->len, Adapter->PackInfo[QueueIndex].bEthCSSupport);
109+ (UINT *)&Packet->len, Adapter->PackInfo[QueueIndex].bEthCSSupport);
115110
116− if(status != STATUS_SUCCESS)
117− {
118− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "PHS Transmit failed..\n");
111+ if (status != STATUS_SUCCESS) {
112+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "PHS Transmit failed..\n");
119113 goto errExit;
120114 }
121115
122− Leader.Vcid = Vcid;
116+ Leader.Vcid = Vcid;
123117
124− if(TCP_ACK == *((UINT32*) (Packet->cb) + SKB_CB_TCPACK_OFFSET ))
118+ if (TCP_ACK == *((UINT32 *) (Packet->cb) + SKB_CB_TCPACK_OFFSET))
125119 Leader.Status = LEADER_STATUS_TCP_ACK;
126120 else
127121 Leader.Status = LEADER_STATUS;
128122
129− if(Adapter->PackInfo[QueueIndex].bEthCSSupport)
130− {
123+ if (Adapter->PackInfo[QueueIndex].bEthCSSupport) {
131124 Leader.PLength = Packet->len;
132− if(skb_headroom(Packet) < LEADER_SIZE)
133− {
134− if((status = skb_cow(Packet,LEADER_SIZE)))
135− {
136− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"bcm_transmit : Failed To Increase headRoom\n");
125+ if (skb_headroom(Packet) < LEADER_SIZE) {
126+ status = skb_cow(Packet, LEADER_SIZE);
127+ if (status) {
128+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "bcm_transmit : Failed To Increase headRoom\n");
137129 goto errExit;
138130 }
139131 }
140132 skb_push(Packet, LEADER_SIZE);
141133 memcpy(Packet->data, &Leader, LEADER_SIZE);
142− }
143− else
144− {
134+ } else {
145135 Leader.PLength = Packet->len - ETH_HLEN;
146136 memcpy((struct bcm_leader *)skb_pull(Packet, (ETH_HLEN - LEADER_SIZE)), &Leader, LEADER_SIZE);
147137 }
148138
149139 status = Adapter->interface_transmit(Adapter->pvInterfaceAdapter,
150− Packet->data, (Leader.PLength + LEADER_SIZE));
151− if(status)
152− {
140+ Packet->data, (Leader.PLength + LEADER_SIZE));
141+ if (status) {
153142 ++Adapter->dev->stats.tx_errors;
154143 if (netif_msg_tx_err(Adapter))
155144 pr_info(PFX "%s: transmit error %d\n", Adapter->dev->name,
156145 status);
157− }
158− else
159− {
146+ } else {
160147 struct net_device_stats *netstats = &Adapter->dev->stats;
161148 Adapter->PackInfo[QueueIndex].uiTotalTxBytes += Leader.PLength;
162149
@@ -175,7 +162,6 @@ INT SetupNextSend(struct bcm_mini_adapter *Adapter, struct sk_buff *Packet, USH · 12 unmodified lines
175162 atomic_dec(&Adapter->CurrNumFreeTxDesc);
176163
177164 errExit:
178−
179165 dev_kfree_skb(Packet);
180166 return status;
181167 }
@@ -188,73 +174,65 @@ static int tx_pending(struct bcm_mini_adapter *Adapter) · 6 unmodified lines
188174 }
189175
190176 /**
191−@ingroup tx_functions
192−Transmit thread
193−*/
194−int tx_pkt_handler(struct bcm_mini_adapter *Adapter /**< pointer to adapter object*/
195− )
177+ * @ingroup tx_functions
178+ * Transmit thread
179+ */
180+int tx_pkt_handler(struct bcm_mini_adapter *Adapter /**< pointer to adapter object*/)
196181 {
197182 int status = 0;
198183
199− while(! kthread_should_stop()) {
184+ while (!kthread_should_stop()) {
200185 /* FIXME - the timeout looks like workaround for racey usage of TxPktAvail */
201− if(Adapter->LinkUpStatus)
186+ if (Adapter->LinkUpStatus)
202187 wait_event_timeout(Adapter->tx_packet_wait_queue,
203− tx_pending(Adapter), msecs_to_jiffies(10));
188+ tx_pending(Adapter), msecs_to_jiffies(10));
204189 else
205190 wait_event_interruptible(Adapter->tx_packet_wait_queue,
206− tx_pending(Adapter));
191+ tx_pending(Adapter));
207192
208193 if (Adapter->device_removed)
209194 break;
210195
211− if(Adapter->downloadDDR == 1)
212− {
213− Adapter->downloadDDR +=1;
196+ if (Adapter->downloadDDR == 1) {
197+ Adapter->downloadDDR += 1;
214198 status = download_ddr_settings(Adapter);
215− if(status)
199+ if (status)
216200 pr_err(PFX "DDR DOWNLOAD FAILED! %d\n", status);
217201 continue;
218202 }
219203
220− //Check end point for halt/stall.
221− if(Adapter->bEndPointHalted == TRUE)
222− {
204+ /* Check end point for halt/stall. */
205+ if (Adapter->bEndPointHalted == TRUE) {
223206 Bcm_clear_halt_of_endpoints(Adapter);
224207 Adapter->bEndPointHalted = FALSE;
225208 StartInterruptUrb((PS_INTERFACE_ADAPTER)(Adapter->pvInterfaceAdapter));
226209 }
227210
228− if(Adapter->LinkUpStatus && !Adapter->IdleMode)
229− {
230− if(atomic_read(&Adapter->TotalPacketCount))
231− {
211+ if (Adapter->LinkUpStatus && !Adapter->IdleMode) {
212+ if (atomic_read(&Adapter->TotalPacketCount))
232213 update_per_sf_desc_cnts(Adapter);
233− }
234214 }
235215
236− if( atomic_read(&Adapter->CurrNumFreeTxDesc) &&
216+ if (atomic_read(&Adapter->CurrNumFreeTxDesc) &&
237217 Adapter->LinkStatus == SYNC_UP_REQUEST &&
238− !Adapter->bSyncUpRequestSent)
239− {
240− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Calling LinkMessage");
218+ !Adapter->bSyncUpRequestSent) {
219+
220+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Calling LinkMessage");
241221 LinkMessage(Adapter);
242222 }
243223
244− if((Adapter->IdleMode || Adapter->bShutStatus) && atomic_read(&Adapter->TotalPacketCount))
245− {
246− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Device in Low Power mode...waking up");
247− Adapter->usIdleModePattern = ABORT_IDLE_MODE;
248− Adapter->bWakeUpDevice = TRUE;
249− wake_up(&Adapter->process_rx_cntrlpkt);
224+ if ((Adapter->IdleMode || Adapter->bShutStatus) && atomic_read(&Adapter->TotalPacketCount)) {
225+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Device in Low Power mode...waking up");
226+ Adapter->usIdleModePattern = ABORT_IDLE_MODE;
227+ Adapter->bWakeUpDevice = TRUE;
228+ wake_up(&Adapter->process_rx_cntrlpkt);
250229 }
251230
252231 transmit_packets(Adapter);
253−
254232 atomic_set(&Adapter->TxPktAvail, 0);
255233 }
256234
257− BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Exiting the tx thread..\n");
235+ BCM_DEBUG_PRINT(Adapter, DBG_TYPE_TX, TX_PACKETS, DBG_LVL_ALL, "Exiting the tx thread..\n");
258236 Adapter->transmit_packet_thread = NULL;
259237 return 0;
260238 }
drivers/staging/bcm/cntrl_SignalingInterface.h+296−408
@@ -1,423 +1,311 @@
11 #ifndef CNTRL_SIGNALING_INTERFACE_
22 #define CNTRL_SIGNALING_INTERFACE_
33
4−
5−
6−
7−#define DSA_REQ 11
8−#define DSA_RSP 12
9−#define DSA_ACK 13
10−#define DSC_REQ 14
11−#define DSC_RSP 15
12−#define DSC_ACK 16
13−#define DSD_REQ 17
14−#define DSD_RSP 18
15−#define DSD_ACK 19
16−#define MAX_CLASSIFIERS_IN_SF 4
17−
18−
19−#define MAX_STRING_LEN 20
20−#define MAX_PHS_LENGTHS 255
21−#define VENDOR_PHS_PARAM_LENGTH 10
22−#define MAX_NUM_ACTIVE_BS 10
23−#define AUTH_TOKEN_LENGTH 10
24−#define NUM_HARQ_CHANNELS 16 //Changed from 10 to 16 to accommodate all HARQ channels
25−#define VENDOR_CLASSIFIER_PARAM_LENGTH 1 //Changed the size to 1 byte since we dnt use it
26−#define VENDOR_SPECIF_QOS_PARAM 1
27−#define VENDOR_PHS_PARAM_LENGTH 10
28−#define MBS_CONTENTS_ID_LENGTH 10
29−#define GLOBAL_SF_CLASSNAME_LENGTH 6
30−
31−#define TYPE_OF_SERVICE_LENGTH 3
32−#define IP_MASKED_SRC_ADDRESS_LENGTH 32
33−#define IP_MASKED_DEST_ADDRESS_LENGTH 32
34−#define PROTOCOL_SRC_PORT_RANGE_LENGTH 4
35−#define PROTOCOL_DEST_PORT_RANGE_LENGTH 4
36−#define ETHERNET_DEST_MAC_ADDR_LENGTH 12
37−#define ETHERNET_SRC_MAC_ADDR_LENGTH 12
38−#define NUM_ETHERTYPE_BYTES 3
39−#define NUM_IPV6_FLOWLABLE_BYTES 3
40−
41−
42−////////////////////////////////////////////////////////////////////////////////
43−////////////////////////structure Definitions///////////////////////////////////
44−////////////////////////////////////////////////////////////////////////////////
45−/// \brief class cCPacketClassificationRule
46−struct _stCPacketClassificationRuleSI{
47−
48− /** 16bit UserPriority Of The Service Flow*/
49− B_UINT16 u16UserPriority;
50− /** 16bit VLANID Of The Service Flow*/
51− B_UINT16 u16VLANID;
52− /** 16bit Packet Classification RuleIndex Of The Service Flow*/
53− B_UINT16 u16PacketClassificationRuleIndex;
54− /** 8bit Classifier Rule Priority Of The Service Flow*/
55− B_UINT8 u8ClassifierRulePriority;
56− /** Length of IP TypeOfService field*/
57− B_UINT8 u8IPTypeOfServiceLength;
58− /** 3bytes IP TypeOfService */
59− B_UINT8 u8IPTypeOfService[TYPE_OF_SERVICE_LENGTH];
60− /** Protocol used in classification of Service Flow*/
61− B_UINT8 u8Protocol;
62− /** Length of IP Masked Source Address */
63− B_UINT8 u8IPMaskedSourceAddressLength;
64− /** IP Masked Source Address used in classification for the Service Flow*/
65− B_UINT8 u8IPMaskedSourceAddress[IP_MASKED_SRC_ADDRESS_LENGTH];
66− /** Length of IP Destination Address */
67− B_UINT8 u8IPDestinationAddressLength;
68− /** IP Destination Address used in classification for the Service Flow*/
69− B_UINT8 u8IPDestinationAddress[IP_MASKED_DEST_ADDRESS_LENGTH];
70− /** Length of Protocol Source Port Range */
71− B_UINT8 u8ProtocolSourcePortRangeLength;
72− /** Protocol Source Port Range used in the Service Flow*/
73− B_UINT8 u8ProtocolSourcePortRange[PROTOCOL_SRC_PORT_RANGE_LENGTH];
74− /** Length of Protocol Dest Port Range */
75− B_UINT8 u8ProtocolDestPortRangeLength;
76− /** Protocol Dest Port Range used in the Service Flow*/
77− B_UINT8 u8ProtocolDestPortRange[PROTOCOL_DEST_PORT_RANGE_LENGTH];
78− /** Length of Ethernet Destination MAC Address */
79− B_UINT8 u8EthernetDestMacAddressLength;
80− /** Ethernet Destination MAC Address used in classification of the Service Flow*/
81− B_UINT8 u8EthernetDestMacAddress[ETHERNET_DEST_MAC_ADDR_LENGTH];
82− /** Length of Ethernet Source MAC Address */
83− B_UINT8 u8EthernetSourceMACAddressLength;
84− /** Ethernet Source MAC Address used in classification of the Service Flow*/
85− B_UINT8 u8EthernetSourceMACAddress[ETHERNET_SRC_MAC_ADDR_LENGTH];
86− /** Length of Ethertype */
87− B_UINT8 u8EthertypeLength;
88− /** 3bytes Ethertype Of The Service Flow*/
89− B_UINT8 u8Ethertype[NUM_ETHERTYPE_BYTES];
90− /** 8bit Associated PHSI Of The Service Flow*/
91− B_UINT8 u8AssociatedPHSI;
92− /** Length of Vendor Specific Classifier Param length Of The Service Flow*/
93− B_UINT8 u8VendorSpecificClassifierParamLength;
94− /** Vendor Specific Classifier Param Of The Service Flow*/
95− B_UINT8 u8VendorSpecificClassifierParam[VENDOR_CLASSIFIER_PARAM_LENGTH];
96− /** Length Of IPv6 Flow Lable of the Service Flow*/
97− B_UINT8 u8IPv6FlowLableLength;
98− /** IPv6 Flow Lable Of The Service Flow*/
99− B_UINT8 u8IPv6FlowLable[NUM_IPV6_FLOWLABLE_BYTES];
100− /** Action associated with the classifier rule*/
101− B_UINT8 u8ClassifierActionRule;
102− B_UINT16 u16ValidityBitMap;
4+#define DSA_REQ 11
5+#define DSA_RSP 12
6+#define DSA_ACK 13
7+#define DSC_REQ 14
8+#define DSC_RSP 15
9+#define DSC_ACK 16
10+#define DSD_REQ 17
11+#define DSD_RSP 18
12+#define DSD_ACK 19
13+#define MAX_CLASSIFIERS_IN_SF 4
14+
15+#define MAX_STRING_LEN 20
16+#define MAX_PHS_LENGTHS 255
17+#define VENDOR_PHS_PARAM_LENGTH 10
18+#define MAX_NUM_ACTIVE_BS 10
19+#define AUTH_TOKEN_LENGTH 10
20+#define NUM_HARQ_CHANNELS 16 /* Changed from 10 to 16 to accommodate all HARQ channels */
21+#define VENDOR_CLASSIFIER_PARAM_LENGTH 1 /* Changed the size to 1 byte since we dnt use it */
22+#define VENDOR_SPECIF_QOS_PARAM 1
23+#define VENDOR_PHS_PARAM_LENGTH 10
24+#define MBS_CONTENTS_ID_LENGTH 10
25+#define GLOBAL_SF_CLASSNAME_LENGTH 6
26+
27+#define TYPE_OF_SERVICE_LENGTH 3
28+#define IP_MASKED_SRC_ADDRESS_LENGTH 32
29+#define IP_MASKED_DEST_ADDRESS_LENGTH 32
30+#define PROTOCOL_SRC_PORT_RANGE_LENGTH 4
31+#define PROTOCOL_DEST_PORT_RANGE_LENGTH 4
32+#define ETHERNET_DEST_MAC_ADDR_LENGTH 12
33+#define ETHERNET_SRC_MAC_ADDR_LENGTH 12
34+#define NUM_ETHERTYPE_BYTES 3
35+#define NUM_IPV6_FLOWLABLE_BYTES 3
36+
37+struct bcm_packet_class_rules {
38+ /* 16bit UserPriority Of The Service Flow */
39+ B_UINT16 u16UserPriority;
40+ /* 16bit VLANID Of The Service Flow */
41+ B_UINT16 u16VLANID;
42+ /* 16bit Packet Classification RuleIndex Of The Service Flow */
43+ B_UINT16 u16PacketClassificationRuleIndex;
44+ /* 8bit Classifier Rule Priority Of The Service Flow */
45+ B_UINT8 u8ClassifierRulePriority;
46+ /* Length of IP TypeOfService field */
47+ B_UINT8 u8IPTypeOfServiceLength;
48+ /* 3bytes IP TypeOfService */
49+ B_UINT8 u8IPTypeOfService[TYPE_OF_SERVICE_LENGTH];
50+ /* Protocol used in classification of Service Flow */
51+ B_UINT8 u8Protocol;
52+ /* Length of IP Masked Source Address */
53+ B_UINT8 u8IPMaskedSourceAddressLength;
54+ /* IP Masked Source Address used in classification for the Service Flow */
55+ B_UINT8 u8IPMaskedSourceAddress[IP_MASKED_SRC_ADDRESS_LENGTH];
56+ /* Length of IP Destination Address */
57+ B_UINT8 u8IPDestinationAddressLength;
58+ /* IP Destination Address used in classification for the Service Flow */
59+ B_UINT8 u8IPDestinationAddress[IP_MASKED_DEST_ADDRESS_LENGTH];
60+ /* Length of Protocol Source Port Range */
61+ B_UINT8 u8ProtocolSourcePortRangeLength;
62+ /* Protocol Source Port Range used in the Service Flow */
63+ B_UINT8 u8ProtocolSourcePortRange[PROTOCOL_SRC_PORT_RANGE_LENGTH];
64+ /* Length of Protocol Dest Port Range */
65+ B_UINT8 u8ProtocolDestPortRangeLength;
66+ /* Protocol Dest Port Range used in the Service Flow */
67+ B_UINT8 u8ProtocolDestPortRange[PROTOCOL_DEST_PORT_RANGE_LENGTH];
68+ /* Length of Ethernet Destination MAC Address */
69+ B_UINT8 u8EthernetDestMacAddressLength;
70+ /* Ethernet Destination MAC Address used in classification of the Service Flow */
71+ B_UINT8 u8EthernetDestMacAddress[ETHERNET_DEST_MAC_ADDR_LENGTH];
72+ /* Length of Ethernet Source MAC Address */
73+ B_UINT8 u8EthernetSourceMACAddressLength;
74+ /* Ethernet Source MAC Address used in classification of the Service Flow */
75+ B_UINT8 u8EthernetSourceMACAddress[ETHERNET_SRC_MAC_ADDR_LENGTH];
76+ /* Length of Ethertype */
77+ B_UINT8 u8EthertypeLength;
78+ /* 3bytes Ethertype Of The Service Flow */
79+ B_UINT8 u8Ethertype[NUM_ETHERTYPE_BYTES];
80+ /* 8bit Associated PHSI Of The Service Flow */
81+ B_UINT8 u8AssociatedPHSI;
82+ /* Length of Vendor Specific Classifier Param length Of The Service Flow */
83+ B_UINT8 u8VendorSpecificClassifierParamLength;
84+ /* Vendor Specific Classifier Param Of The Service Flow */
85+ B_UINT8 u8VendorSpecificClassifierParam[VENDOR_CLASSIFIER_PARAM_LENGTH];
86+ /* Length Of IPv6 Flow Lable of the Service Flow */
87+ B_UINT8 u8IPv6FlowLableLength;
88+ /* IPv6 Flow Lable Of The Service Flow */
89+ B_UINT8 u8IPv6FlowLable[NUM_IPV6_FLOWLABLE_BYTES];
90+ /* Action associated with the classifier rule */
91+ B_UINT8 u8ClassifierActionRule;
92+ B_UINT16 u16ValidityBitMap;
10393 };
104−typedef struct _stCPacketClassificationRuleSI CCPacketClassificationRuleSI,stCPacketClassificationRuleSI, *pstCPacketClassificationRuleSI;
105−
106−/// \brief class CPhsRuleSI
107−typedef struct _stPhsRuleSI {
108− /** 8bit PHS Index Of The Service Flow*/
109− B_UINT8 u8PHSI;
110− /** PHSF Length Of The Service Flow*/
111− B_UINT8 u8PHSFLength;
112− /** String of bytes containing header information to be suppressed by the sending CS and reconstructed by the receiving CS*/
113− B_UINT8 u8PHSF[MAX_PHS_LENGTHS];
114− /** PHSM Length Of The Service Flow*/
115− B_UINT8 u8PHSMLength;
116− /** PHS Mask for the SF*/
117− B_UINT8 u8PHSM[MAX_PHS_LENGTHS];
118− /** 8bit Total number of bytes to be suppressed for the Service Flow*/
119− B_UINT8 u8PHSS;
120− /** 8bit Indicates whether or not Packet Header contents need to be verified prior to suppression */
121− B_UINT8 u8PHSV;
122− /** Vendor Specific PHS param Length Of The Service Flow*/
123− B_UINT8 u8VendorSpecificPHSParamsLength;
124− /** Vendor Specific PHS param Of The Service Flow*/
125− B_UINT8 u8VendorSpecificPHSParams[VENDOR_PHS_PARAM_LENGTH];
126−
127− B_UINT8 u8Padding[2];
128−}stPhsRuleSI,*pstPhsRuleSI;
129−typedef stPhsRuleSI CPhsRuleSI;
13094
131−/// \brief structure cConvergenceSLTypes
132−struct _stConvergenceSLTypes{
133− /** 8bit Phs Classfier Action Of The Service Flow*/
134− B_UINT8 u8ClassfierDSCAction;
135− /** 8bit Phs DSC Action Of The Service Flow*/
136− B_UINT8 u8PhsDSCAction;
137− /** 16bit Padding */
138− B_UINT8 u8Padding[2];
139− /// \brief class cCPacketClassificationRule
140− stCPacketClassificationRuleSI cCPacketClassificationRule;
141− /// \brief class CPhsRuleSI
142− struct _stPhsRuleSI cPhsRule;
95+struct bcm_phs_rules {
96+ /* 8bit PHS Index Of The Service Flow */
97+ B_UINT8 u8PHSI;
98+ /* PHSF Length Of The Service Flow */
99+ B_UINT8 u8PHSFLength;
100+ /* String of bytes containing header information to be suppressed by the sending CS and reconstructed by the receiving CS */
101+ B_UINT8 u8PHSF[MAX_PHS_LENGTHS];
102+ /* PHSM Length Of The Service Flow */
103+ B_UINT8 u8PHSMLength;
104+ /* PHS Mask for the SF */
105+ B_UINT8 u8PHSM[MAX_PHS_LENGTHS];
106+ /* 8bit Total number of bytes to be suppressed for the Service Flow */
107+ B_UINT8 u8PHSS;
108+ /* 8bit Indicates whether or not Packet Header contents need to be verified prior to suppression */
109+ B_UINT8 u8PHSV;
110+ /* Vendor Specific PHS param Length Of The Service Flow */
111+ B_UINT8 u8VendorSpecificPHSParamsLength;
112+ /* Vendor Specific PHS param Of The Service Flow */
113+ B_UINT8 u8VendorSpecificPHSParams[VENDOR_PHS_PARAM_LENGTH];
114+ B_UINT8 u8Padding[2];
143115 };
144−typedef struct _stConvergenceSLTypes stConvergenceSLTypes,CConvergenceSLTypes, *pstConvergenceSLTypes;
145−
146−
147−/// \brief structure CServiceFlowParamSI
148−typedef struct _stServiceFlowParamSI{
149−
150− /** 32bitSFID Of The Service Flow*/
151− B_UINT32 u32SFID;
152−
153− /** 32bit Maximum Sustained Traffic Rate of the Service Flow*/
154− B_UINT32 u32MaxSustainedTrafficRate;
155−
156− /** 32bit Maximum Traffic Burst allowed for the Service Flow*/
157− B_UINT32 u32MaxTrafficBurst;
158−
159− /** 32bit Minimum Reserved Traffic Rate of the Service Flow*/
160− B_UINT32 u32MinReservedTrafficRate;
161−
162− /** 32bit Tolerated Jitter of the Service Flow*/
163− B_UINT32 u32ToleratedJitter;
164−
165− /** 32bit Maximum Latency of the Service Flow*/
166− B_UINT32 u32MaximumLatency;
167−
168− /** 16bitCID Of The Service Flow*/
169− B_UINT16 u16CID;
170−
171− /** 16bit SAID on which the service flow being set up shall be mapped*/
172− B_UINT16 u16TargetSAID;
173−
174− /** 16bit ARQ window size negotiated*/
175− B_UINT16 u16ARQWindowSize;
176−
177− /** 16bit Total Tx delay incl sending, receiving & processing delays */
178− B_UINT16 u16ARQRetryTxTimeOut;
179−
180− /** 16bit Total Rx delay incl sending, receiving & processing delays */
181− B_UINT16 u16ARQRetryRxTimeOut;
182−
183− /** 16bit ARQ block lifetime */
184− B_UINT16 u16ARQBlockLifeTime;
185−
186− /** 16bit ARQ Sync loss timeout*/
187− B_UINT16 u16ARQSyncLossTimeOut;
188−
189− /** 16bit ARQ Purge timeout */
190− B_UINT16 u16ARQRxPurgeTimeOut;
191−//TODO::Remove this once we move to a new CORR2 driver
192− /// \brief Size of an ARQ block
193− B_UINT16 u16ARQBlockSize;
194−
195−//#endif
196− /** 16bit Nominal interval b/w consecutive SDU arrivals at MAC SAP*/
197− B_UINT16 u16SDUInterArrivalTime;
198−
199− /** 16bit Specifies the time base for rate measurement */
200− B_UINT16 u16TimeBase;
201−
202− /** 16bit Interval b/w Successive Grant oppurtunities*/
203− B_UINT16 u16UnsolicitedGrantInterval;
204−
205− /** 16bit Interval b/w Successive Polling grant oppurtunities*/
206− B_UINT16 u16UnsolicitedPollingInterval;
207−
208− /** internal var to get the overhead */
209− B_UINT16 u16MacOverhead;
210−
211− /** MBS contents Identifier*/
212− B_UINT16 u16MBSContentsID[MBS_CONTENTS_ID_LENGTH];
213−
214− /** MBS contents Identifier length*/
215− B_UINT8 u8MBSContentsIDLength;
216−
217− /** ServiceClassName Length Of The Service Flow*/
218− B_UINT8 u8ServiceClassNameLength;
219−
220− /** 32bytes ServiceClassName Of The Service Flow*/
221− B_UINT8 u8ServiceClassName[32];
222−
223− /** 8bit Indicates whether or not MBS service is requested for this Serivce Flow*/
224− B_UINT8 u8MBSService;
225−
226− /** 8bit QOS Parameter Set specifies proper application of QoS paramters to Provisioned, Admitted and Active sets*/
227− B_UINT8 u8QosParamSet;
228−
229− /** 8bit Traffic Priority Of the Service Flow */
230− B_UINT8 u8TrafficPriority;
231−
232− /** 8bit Uplink Grant Scheduling Type of The Service Flow */
233− B_UINT8 u8ServiceFlowSchedulingType;
234−
235− /** 8bit Request transmission Policy of the Service Flow*/
236− B_UINT8 u8RequesttransmissionPolicy;
237−
238− /** 8bit Specifies whether SDUs for this Service flow are of FixedLength or Variable length */
239− B_UINT8 u8FixedLengthVSVariableLengthSDUIndicator;
240−
241− /** 8bit Length of the SDU for a fixed length SDU service flow*/
242− B_UINT8 u8SDUSize;
243116
244− /** 8bit Indicates whether or not ARQ is requested for this connection*/
245− B_UINT8 u8ARQEnable;
246−
247− /**< 8bit Indicates whether or not data has tobe delivered in order to higher layer*/
248− B_UINT8 u8ARQDeliverInOrder;
249−
250− /** 8bit Receiver ARQ ACK processing time */
251− B_UINT8 u8RxARQAckProcessingTime;
252−
253− /** 8bit Convergence Sublayer Specification Of The Service Flow*/
254− B_UINT8 u8CSSpecification;
255−
256− /** 8 bit Type of data delivery service*/
257− B_UINT8 u8TypeOfDataDeliveryService;
258−
259− /** 8bit Specifies whether a service flow may generate Paging */
260− B_UINT8 u8PagingPreference;
261−
262− /** 8bit Indicates the MBS Zone through which the connection or virtual connection is valid */
263− B_UINT8 u8MBSZoneIdentifierassignment;
264−
265− /** 8bit Specifies whether traffic on SF should generate MOB_TRF_IND to MS in sleep mode*/
266− B_UINT8 u8TrafficIndicationPreference;
267−
268− /** 8bit Speciifes the length of predefined Global QoS parameter set encoding for this SF */
269− B_UINT8 u8GlobalServicesClassNameLength;
270−
271− /** 6 byte Speciifes the predefined Global QoS parameter set encoding for this SF */
272− B_UINT8 u8GlobalServicesClassName[GLOBAL_SF_CLASSNAME_LENGTH];
273−
274− /** 8bit Indicates whether or not SN feedback is enabled for the conn */
275− B_UINT8 u8SNFeedbackEnabled;
276−
277− /** Indicates the size of the Fragment Sequence Number for the connection */
278− B_UINT8 u8FSNSize;
279−
280− /** 8bit Number of CIDs in active BS list */
281− B_UINT8 u8CIDAllocation4activeBSsLength;
282−
283− /** CIDs of BS in the active list */
284− B_UINT8 u8CIDAllocation4activeBSs[MAX_NUM_ACTIVE_BS];
285−
286− /** Specifies if PDU extended subheader should be applied on every PDU on this conn*/
287− B_UINT8 u8PDUSNExtendedSubheader4HarqReordering;
288−
289− /** 8bit Specifies whether the connection uses HARQ or not */
290− B_UINT8 u8HARQServiceFlows;
291−
292− /** Specifies the length of Authorization token*/
293− B_UINT8 u8AuthTokenLength;
294−
295− /** Specifies the Authorization token*/
296− B_UINT8 u8AuthToken[AUTH_TOKEN_LENGTH];
297−
298− /** specifes Number of HARQ channels used to carry data length*/
299− B_UINT8 u8HarqChannelMappingLength;
300−
301− /** specifes HARQ channels used to carry data*/
302− B_UINT8 u8HARQChannelMapping[NUM_HARQ_CHANNELS];
303−
304− /** 8bit Length of Vendor Specific QoS Params */
305− B_UINT8 u8VendorSpecificQoSParamLength;
306−
307− /** 1byte Vendor Specific QoS Param Of The Service Flow*/
308− B_UINT8 u8VendorSpecificQoSParam[VENDOR_SPECIF_QOS_PARAM];
309−
310− // indicates total classifiers in the SF
311− B_UINT8 u8TotalClassifiers; /**< Total number of valid classifiers*/
312− B_UINT8 bValid; /**< Validity flag */
313− B_UINT8 u8Padding; /**< Padding byte*/
314−
315−/**
316−Structure for Convergence SubLayer Types with a maximum of 4 classifiers
317−*/
318− stConvergenceSLTypes cConvergenceSLTypes[MAX_CLASSIFIERS_IN_SF];
319−
320−} stServiceFlowParamSI, *pstServiceFlowParamSI;
321−typedef stServiceFlowParamSI CServiceFlowParamSI;
322−
323−/**
324−structure stLocalSFAddRequest
325−*/
326−typedef struct _stLocalSFAddRequest{
327−
328− B_UINT8 u8Type; /**< Type*/
329− B_UINT8 eConnectionDir; /**< Connection direction*/
330− /// \brief 16 bit TID
331− B_UINT16 u16TID; /**< 16bit TID*/
332− /// \brief 16bitCID
333− B_UINT16 u16CID; /**< 16bit CID*/
334− /// \brief 16bitVCID
335− B_UINT16 u16VCID; /**< 16bit VCID*/
336− /// \brief structure ParameterSet
337−
338− stServiceFlowParamSI *psfParameterSet; /**< structure ParameterSet*/
339−
340−}stLocalSFAddRequest, *pstLocalSFAddRequest;
341−
342−
343−/**
344−structure stLocalSFAddIndication
345−*/
346−typedef struct _stLocalSFAddIndication{
347−
348− B_UINT8 u8Type; /**< Type*/
349− B_UINT8 eConnectionDir; /**< Connection Direction*/
350− /// \brief 16 bit TID
351− B_UINT16 u16TID; /**< TID*/
352− /// \brief 16bitCID
353− B_UINT16 u16CID; /**< 16bitCID*/
354− /// \brief 16bitVCID
355− B_UINT16 u16VCID; /**< 16bitVCID*/
356−
357−
358− /// \brief structure AuthorizedSet
359− /// \brief structure AuthorizedSet
360− stServiceFlowParamSI *psfAuthorizedSet; /**< AuthorizedSet of type stServiceFlowParamSI*/
361− /// \brief structure AdmittedSet
362− stServiceFlowParamSI *psfAdmittedSet; /**< AdmittedSet of type stServiceFlowParamSI*/
363− /// \brief structure ActiveSet
364− stServiceFlowParamSI *psfActiveSet; /**< sfActiveSet of type stServiceFlowParamSI*/
365− B_UINT8 u8CC; /**< Confirmation Code*/
366− B_UINT8 u8Padd; /**< 8-bit Padding */
367−
368− B_UINT16 u16Padd; /**< 16 bit Padding */
369−
370−}stLocalSFAddIndication;
117+struct bcm_convergence_types {
118+ /* 8bit Phs Classfier Action Of The Service Flow */
119+ B_UINT8 u8ClassfierDSCAction;
120+ /* 8bit Phs DSC Action Of The Service Flow */
121+ B_UINT8 u8PhsDSCAction;
122+ /* 16bit Padding */
123+ B_UINT8 u8Padding[2];
124+ /* Packet classification rules structure */
125+ struct bcm_packet_class_rules cCPacketClassificationRule;
126+ /* Payload header suppression rules structure */
127+ struct bcm_phs_rules cPhsRule;
128+};
371129
130+struct bcm_connect_mgr_params {
131+ /* 32bitSFID Of The Service Flow */
132+ B_UINT32 u32SFID;
133+ /* 32bit Maximum Sustained Traffic Rate of the Service Flow */
134+ B_UINT32 u32MaxSustainedTrafficRate;
135+ /* 32bit Maximum Traffic Burst allowed for the Service Flow */
136+ B_UINT32 u32MaxTrafficBurst;
137+ /* 32bit Minimum Reserved Traffic Rate of the Service Flow */
138+ B_UINT32 u32MinReservedTrafficRate;
139+ /* 32bit Tolerated Jitter of the Service Flow */
140+ B_UINT32 u32ToleratedJitter;
141+ /* 32bit Maximum Latency of the Service Flow */
142+ B_UINT32 u32MaximumLatency;
143+ /* 16bitCID Of The Service Flow */
144+ B_UINT16 u16CID;
145+ /* 16bit SAID on which the service flow being set up shall be mapped */
146+ B_UINT16 u16TargetSAID;
147+ /* 16bit ARQ window size negotiated */
148+ B_UINT16 u16ARQWindowSize;
149+ /* 16bit Total Tx delay incl sending, receiving & processing delays */
150+ B_UINT16 u16ARQRetryTxTimeOut;
151+ /* 16bit Total Rx delay incl sending, receiving & processing delays */
152+ B_UINT16 u16ARQRetryRxTimeOut;
153+ /* 16bit ARQ block lifetime */
154+ B_UINT16 u16ARQBlockLifeTime;
155+ /* 16bit ARQ Sync loss timeout */
156+ B_UINT16 u16ARQSyncLossTimeOut;
157+ /* 16bit ARQ Purge timeout */
158+ B_UINT16 u16ARQRxPurgeTimeOut;
159+ /* TODO::Remove this once we move to a new CORR2 driver
160+ * brief Size of an ARQ block
161+ */
162+ B_UINT16 u16ARQBlockSize;
163+ /* #endif */
164+ /* 16bit Nominal interval b/w consecutive SDU arrivals at MAC SAP */
165+ B_UINT16 u16SDUInterArrivalTime;
166+ /* 16bit Specifies the time base for rate measurement */
167+ B_UINT16 u16TimeBase;
168+ /* 16bit Interval b/w Successive Grant oppurtunities */
169+ B_UINT16 u16UnsolicitedGrantInterval;
170+ /* 16bit Interval b/w Successive Polling grant oppurtunities */
171+ B_UINT16 u16UnsolicitedPollingInterval;
172+ /* internal var to get the overhead */
173+ B_UINT16 u16MacOverhead;
174+ /* MBS contents Identifier */
175+ B_UINT16 u16MBSContentsID[MBS_CONTENTS_ID_LENGTH];
176+ /* MBS contents Identifier length */
177+ B_UINT8 u8MBSContentsIDLength;
178+ /* ServiceClassName Length Of The Service Flow */
179+ B_UINT8 u8ServiceClassNameLength;
180+ /* 32bytes ServiceClassName Of The Service Flow */
181+ B_UINT8 u8ServiceClassName[32];
182+ /* 8bit Indicates whether or not MBS service is requested for this Serivce Flow */
183+ B_UINT8 u8MBSService;
184+ /* 8bit QOS Parameter Set specifies proper application of QoS parameters to Provisioned, Admitted and Active sets */
185+ B_UINT8 u8QosParamSet;
186+ /* 8bit Traffic Priority Of the Service Flow */
187+ B_UINT8 u8TrafficPriority;
188+ /* 8bit Uplink Grant Scheduling Type of The Service Flow */
189+ B_UINT8 u8ServiceFlowSchedulingType;
190+ /* 8bit Request transmission Policy of the Service Flow */
191+ B_UINT8 u8RequesttransmissionPolicy;
192+ /* 8bit Specifies whether SDUs for this Service flow are of FixedLength or Variable length */
193+ B_UINT8 u8FixedLengthVSVariableLengthSDUIndicator;
194+ /* 8bit Length of the SDU for a fixed length SDU service flow */
195+ B_UINT8 u8SDUSize;
196+ /* 8bit Indicates whether or not ARQ is requested for this connection */
197+ B_UINT8 u8ARQEnable;
198+ /* < 8bit Indicates whether or not data has tobe delivered in order to higher layer */
199+ B_UINT8 u8ARQDeliverInOrder;
200+ /* 8bit Receiver ARQ ACK processing time */
201+ B_UINT8 u8RxARQAckProcessingTime;
202+ /* 8bit Convergence Sublayer Specification Of The Service Flow */
203+ B_UINT8 u8CSSpecification;
204+ /* 8 bit Type of data delivery service */
205+ B_UINT8 u8TypeOfDataDeliveryService;
206+ /* 8bit Specifies whether a service flow may generate Paging */
207+ B_UINT8 u8PagingPreference;
208+ /* 8bit Indicates the MBS Zone through which the connection or virtual connection is valid */
209+ B_UINT8 u8MBSZoneIdentifierassignment;
210+ /* 8bit Specifies whether traffic on SF should generate MOB_TRF_IND to MS in sleep mode */
211+ B_UINT8 u8TrafficIndicationPreference;
212+ /* 8bit Speciifes the length of predefined Global QoS parameter set encoding for this SF */
213+ B_UINT8 u8GlobalServicesClassNameLength;
214+ /* 6 byte Speciifes the predefined Global QoS parameter set encoding for this SF */
215+ B_UINT8 u8GlobalServicesClassName[GLOBAL_SF_CLASSNAME_LENGTH];
216+ /* 8bit Indicates whether or not SN feedback is enabled for the conn */
217+ B_UINT8 u8SNFeedbackEnabled;
218+ /* Indicates the size of the Fragment Sequence Number for the connection */
219+ B_UINT8 u8FSNSize;
220+ /* 8bit Number of CIDs in active BS list */
221+ B_UINT8 u8CIDAllocation4activeBSsLength;
222+ /* CIDs of BS in the active list */
223+ B_UINT8 u8CIDAllocation4activeBSs[MAX_NUM_ACTIVE_BS];
224+ /* Specifies if PDU extended subheader should be applied on every PDU on this conn */
225+ B_UINT8 u8PDUSNExtendedSubheader4HarqReordering;
226+ /* 8bit Specifies whether the connection uses HARQ or not */
227+ B_UINT8 u8HARQServiceFlows;
228+ /* Specifies the length of Authorization token */
229+ B_UINT8 u8AuthTokenLength;
230+ /* Specifies the Authorization token */
231+ B_UINT8 u8AuthToken[AUTH_TOKEN_LENGTH];
232+ /* specifes Number of HARQ channels used to carry data length */
233+ B_UINT8 u8HarqChannelMappingLength;
234+ /* specifes HARQ channels used to carry data */
235+ B_UINT8 u8HARQChannelMapping[NUM_HARQ_CHANNELS];
236+ /* 8bit Length of Vendor Specific QoS Params */
237+ B_UINT8 u8VendorSpecificQoSParamLength;
238+ /* 1byte Vendor Specific QoS Param Of The Service Flow */
239+ B_UINT8 u8VendorSpecificQoSParam[VENDOR_SPECIF_QOS_PARAM];
240+ /* indicates total classifiers in the SF */
241+ B_UINT8 u8TotalClassifiers; /* < Total number of valid classifiers */
242+ B_UINT8 bValid; /* < Validity flag */
243+ B_UINT8 u8Padding; /* < Padding byte */
244+ /*
245+ * Structure for Convergence SubLayer Types with a maximum of 4 classifiers
246+ */
247+ struct bcm_convergence_types cConvergenceSLTypes[MAX_CLASSIFIERS_IN_SF];
248+};
372249
373−typedef struct _stLocalSFAddIndication *pstLocalSFAddIndication;
374−/**
375−structure stLocalSFChangeRequest is same as structure stLocalSFAddIndication
376−*/
377−typedef struct _stLocalSFAddIndication stLocalSFChangeRequest, *pstLocalSFChangeRequest;
378−/**
379−structure stLocalSFChangeIndication is same as structure stLocalSFAddIndication
380−*/
381−typedef struct _stLocalSFAddIndication stLocalSFChangeIndication, *pstLocalSFChangeIndication;
250+struct bcm_add_request {
251+ B_UINT8 u8Type; /* < Type */
252+ B_UINT8 eConnectionDir; /* < Connection direction */
253+ /* brief 16 bit TID */
254+ B_UINT16 u16TID; /* < 16bit TID */
255+ /* brief 16bitCID */
256+ B_UINT16 u16CID; /* < 16bit CID */
257+ /* brief 16bitVCID */
258+ B_UINT16 u16VCID; /* < 16bit VCID */
259+ struct bcm_connect_mgr_params *psfParameterSet; /* < connection manager parameters */
260+};
382261
383−/**
384−structure stLocalSFDeleteRequest
385−*/
386−typedef struct _stLocalSFDeleteRequest{
387− B_UINT8 u8Type; /**< Type*/
388− B_UINT8 u8Padding; /**< Padding byte*/
389− B_UINT16 u16TID; /**< TID*/
390− /// \brief 32bitSFID
391− B_UINT32 u32SFID; /**< SFID*/
392−}stLocalSFDeleteRequest, *pstLocalSFDeleteRequest;
262+struct bcm_add_indication {
263+ B_UINT8 u8Type; /* < Type */
264+ B_UINT8 eConnectionDir; /* < Connection Direction */
265+ /* brief 16 bit TID */
266+ B_UINT16 u16TID; /* < TID */
267+ /* brief 16bitCID */
268+ B_UINT16 u16CID; /* < 16bitCID */
269+ /* brief 16bitVCID */
270+ B_UINT16 u16VCID; /* < 16bitVCID */
271+ struct bcm_connect_mgr_params *psfAuthorizedSet; /* Authorized set of connection manager parameters */
272+ struct bcm_connect_mgr_params *psfAdmittedSet; /* Admitted set of connection manager parameters */
273+ struct bcm_connect_mgr_params *psfActiveSet; /* Activeset of connection manager parameters */
274+ B_UINT8 u8CC; /* <Confirmation Code */
275+ B_UINT8 u8Padd; /* < 8-bit Padding */
276+ B_UINT16 u16Padd; /* < 16 bit Padding */
277+};
393278
394−/**
395−structure stLocalSFDeleteIndication
396−*/
397−typedef struct stLocalSFDeleteIndication{
398− B_UINT8 u8Type; /**< Type */
399− B_UINT8 u8Padding; /**< Padding */
400− B_UINT16 u16TID; /**< TID */
401− /// \brief 16bitCID
402− B_UINT16 u16CID; /**< CID */
403− /// \brief 16bitVCID
404− B_UINT16 u16VCID; /**< VCID */
405− /// \brief 32bitSFID
406− B_UINT32 u32SFID; /**< SFID */
407− /// \brief 8bit Confirmation code
408− B_UINT8 u8ConfirmationCode; /**< Confirmation code */
409− B_UINT8 u8Padding1[3]; /**< 3 byte Padding */
410−}stLocalSFDeleteIndication;
279+struct bcm_del_request {
280+ B_UINT8 u8Type; /* < Type */
281+ B_UINT8 u8Padding; /* < Padding byte */
282+ B_UINT16 u16TID; /* < TID */
283+ /* brief 32bitSFID */
284+ B_UINT32 u32SFID; /* < SFID */
285+};
411286
412−typedef struct _stIM_SFHostNotify
413−{
414− B_UINT32 SFID; //SFID of the service flow
415− B_UINT16 newCID; //the new/changed CID
416− B_UINT16 VCID; //Get new Vcid if the flow has been made active in CID update TLV, but was inactive earlier or the orig vcid
417− B_UINT8 RetainSF; //Indication to Host if the SF is to be retained or deleted; if TRUE-retain else delete
418− B_UINT8 QoSParamSet; //QoS paramset of the retained SF
419− B_UINT16 u16reserved; //For byte alignment
287+struct bcm_del_indication {
288+ B_UINT8 u8Type; /* < Type */
289+ B_UINT8 u8Padding; /* < Padding */
290+ B_UINT16 u16TID; /* < TID */
291+ /* brief 16bitCID */
292+ B_UINT16 u16CID; /* < CID */
293+ /* brief 16bitVCID */
294+ B_UINT16 u16VCID; /* < VCID */
295+ /* brief 32bitSFID */
296+ B_UINT32 u32SFID; /* < SFID */
297+ /* brief 8bit Confirmation code */
298+ B_UINT8 u8ConfirmationCode; /* < Confirmation code */
299+ B_UINT8 u8Padding1[3]; /* < 3 byte Padding */
300+};
420301
421−} stIM_SFHostNotify;
302+struct bcm_stim_sfhostnotify {
303+ B_UINT32 SFID; /* SFID of the service flow */
304+ B_UINT16 newCID; /* the new/changed CID */
305+ B_UINT16 VCID; /* Get new Vcid if the flow has been made active in CID update TLV, but was inactive earlier or the orig vcid */
306+ B_UINT8 RetainSF; /* Indication to Host if the SF is to be retained or deleted; if TRUE-retain else delete */
307+ B_UINT8 QoSParamSet; /* QoS paramset of the retained SF */
308+ B_UINT16 u16reserved; /* For byte alignment */
309+};
422310
423311 #endif
drivers/staging/bcm/hostmibs.c+1−1
@@ -101,7 +101,7 @@ VOID GetDroppedAppCntrlPktMibs(S_MIBS_HOST_STATS_MIBS *pstHostMibs, struct bcm_t · 100 unmodified lines
101101 sizeof(S_MIBS_DROPPED_APP_CNTRL_MESSAGES));
102102 }
103103
104−VOID CopyMIBSExtendedSFParameters(struct bcm_mini_adapter *Adapter, CServiceFlowParamSI *psfLocalSet, UINT uiSearchRuleIndex)
104+VOID CopyMIBSExtendedSFParameters(struct bcm_mini_adapter *Adapter, struct bcm_connect_mgr_params *psfLocalSet, UINT uiSearchRuleIndex)
105105 {
106106 S_MIBS_EXTSERVICEFLOW_PARAMETERS *t = &Adapter->PackInfo[uiSearchRuleIndex].stMibsExtServiceFlowTable;
107107
drivers/staging/bcm/nvm.c+2−2
@@ -577,7 +577,7 @@ static int FlashSectorErase(struct bcm_mini_adapter *Adapter, · 576 unmodified lines
577577 * the sector erase cycle is 500 ms to 40000 msec. hence sleeping 10 ms
578578 * won't hamper performance in any case.
579579 */
580− udelay(10000);
580+ mdelay(10);
581581 } while ((uiStatus & 0x1) && (iRetries < 400));
582582
583583 if (uiStatus & 0x1) {
@@ -3932,7 +3932,7 @@ int validateFlash2xReadWrite(struct bcm_mini_adapter *Adapter, PFLASH2X_READWRIT · 3348 unmodified lines
39323932 BcmGetSectionValStartOffset(Adapter, ISO_IMAGE2_PART3);
39333933 }
39343934
3935− /* since this uiSectEndoffset is the size of iso Image. hence for calculating the vitual endoffset
3935+ /* since this uiSectEndoffset is the size of iso Image. hence for calculating the virtual endoffset
39363936 * it should be added in startoffset. so that check done in last of this function can be valued.
39373937 */
39383938 uiSectEndOffset = uiSectStartOffset + uiSectEndOffset;
drivers/staging/bcm/target_params.h+1−1
@@ -32,7 +32,7 @@ typedef struct _TARGET_PARAMS · 31 unmodified lines
3232 B_UINT32 m_u32PowerSavingModesEnable; //bit 1: 1 Idlemode enable; bit2: 1 Sleepmode Enable
3333 /* PowerSaving Mode Options:
3434 bit 0 = 1: CPE mode - to keep pcmcia if alive;
35− bit 1 = 1: CINR reporing in Idlemode Msg
35+ bit 1 = 1: CINR reporting in Idlemode Msg
3636 bit 2 = 1: Default PSC Enable in sleepmode*/
3737 B_UINT32 m_u32PowerSavingModeOptions;
3838
drivers/staging/ccg/Kconfig+1−1
@@ -2,7 +2,7 @@ if USB_GADGET · 1 unmodified line
22
33 config USB_G_CCG
44 tristate "Configurable Composite Gadget (STAGING)"
5− depends on STAGING && BLOCK && !USB_ZERO && !USB_ZERO_HNPTEST && !USB_AUDIO && !GADGET_UAC1 && !USB_ETH && !USB_ETH_RNDIS && !USB_ETH_EEM && !USB_G_NCM && !USB_GADGETFS && !USB_FUNCTIONFS && !USB_FUNCTIONFS_ETH && !USB_FUNCTIONFS_RNDIS && !USB_FUNCTIONFS_GENERIC && !USB_FILE_STORAGE && !USB_FILE_STORAGE_TEST && !USB_MASS_STORAGE && !USB_G_SERIAL && !USB_MIDI_GADGET && !USB_G_PRINTER && !USB_CDC_COMPOSITE && !USB_G_NOKIA && !USB_G_ACM_MS && !USB_G_MULTI && !USB_G_MULTI_RNDIS && !USB_G_MULTI_CDC && !USB_G_HID && !USB_G_DBGP && !USB_G_WEBCAM
5+ depends on STAGING && BLOCK && NET && !USB_ZERO && !USB_ZERO_HNPTEST && !USB_AUDIO && !GADGET_UAC1 && !USB_ETH && !USB_ETH_RNDIS && !USB_ETH_EEM && !USB_G_NCM && !USB_GADGETFS && !USB_FUNCTIONFS && !USB_FUNCTIONFS_ETH && !USB_FUNCTIONFS_RNDIS && !USB_FUNCTIONFS_GENERIC && !USB_FILE_STORAGE && !USB_FILE_STORAGE_TEST && !USB_MASS_STORAGE && !USB_G_SERIAL && !USB_MIDI_GADGET && !USB_G_PRINTER && !USB_CDC_COMPOSITE && !USB_G_NOKIA && !USB_G_ACM_MS && !USB_G_MULTI && !USB_G_MULTI_RNDIS && !USB_G_MULTI_CDC && !USB_G_HID && !USB_G_DBGP && !USB_G_WEBCAM
66 help
77 The Configurable Composite Gadget supports multiple USB
88 functions: acm, mass storage, rndis and FunctionFS.
drivers/staging/ccg/ccg.c+5−9
@@ -728,7 +728,7 @@ static int mass_storage_function_init(struct ccg_usb_function *f, · 727 unmodified lines
728728 struct fsg_common *common;
729729 int err;
730730
731− memset(&fsg, 0, sizeof fsg);
731+ memset(&fsg, 0, sizeof(fsg));
732732 fsg.nluns = 1;
733733 fsg.luns[0].removable = 1;
734734 fsg.vendor_name = iManufacturer;
@@ -1101,13 +1101,7 @@ static struct device_attribute *ccg_usb_attributes[] = { · 366 unmodified lines
11011101 static int ccg_bind_config(struct usb_configuration *c)
11021102 {
11031103 struct ccg_dev *dev = _ccg_dev;
1104− int ret = 0;
1105−
1106− ret = ccg_bind_enabled_functions(dev, c);
1107− if (ret)
1108− return ret;
1109−
1110− return 0;
1104+ return ccg_bind_enabled_functions(dev, c);
11111105 }
11121106
11131107 static void ccg_unbind_config(struct usb_configuration *c)
@@ -1254,8 +1248,10 @@ static int __init init(void) · 140 unmodified lines
12541248 return PTR_ERR(ccg_class);
12551249
12561250 dev = kzalloc(sizeof(*dev), GFP_KERNEL);
1257− if (!dev)
1251+ if (!dev) {
1252+ class_destroy(ccg_class);
12581253 return -ENOMEM;
1254+ }
12591255
12601256 dev->functions = supported_functions;
12611257 INIT_LIST_HEAD(&dev->enabled_functions);
drivers/staging/ced1401/Kconfig+6−0
@@ -0,0 +1,6 @@
1+config CED1401
2+ tristate "Cambridge Electronic Design 1401 USB support"
3+ depends on USB
4+ help
5+ This driver supports the Cambridge Electronic Design 1401 USB device
6+ (whatever that is.)
drivers/staging/ced1401/Makefile+3−0
@@ -0,0 +1,3 @@
1+
2+obj-$(CONFIG_CED1401) := cedusb.o
3+cedusb-objs := usb1401.o ced_ioc.o
drivers/staging/ced1401/TODO+10−0
@@ -0,0 +1,10 @@
1+TODO:
2+ - coding syle fixes
3+ - build warning fixups
4+ - ioctl auditing
5+ - usb api auditing
6+ - proper USB minor number (it's stomping on an existing one right now.)
7+
8+Please send patches to Greg Kroah-Hartman <gregkh@linuxfoundation.org> and Cc:
9+Alois Schlögl <alois.schloegl@ist.ac.at>
10+
drivers/staging/ced1401/ced_ioc.c+1515−0
@@ -0,0 +1,1515 @@
1+/* ced_ioc.c
2+ ioctl part of the 1401 usb device driver for linux.
3+ Copyright (C) 2010 Cambridge Electronic Design Ltd
4+ Author Greg P Smith (greg@ced.co.uk)
5+
6+ This program is free software; you can redistribute it and/or
7+ modify it under the terms of the GNU General Public License
8+ as published by the Free Software Foundation; either version 2
9+ of the License, or (at your option) any later version.
10+
11+ This program is distributed in the hope that it will be useful,
12+ but WITHOUT ANY WARRANTY; without even the implied warranty of
13+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+ GNU General Public License for more details.
15+
16+ You should have received a copy of the GNU General Public License
17+ along with this program; if not, write to the Free Software
18+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19+*/
20+#include <linux/kernel.h>
21+#include <linux/errno.h>
22+#include <linux/init.h>
23+#include <linux/slab.h>
24+#include <linux/module.h>
25+#include <linux/kref.h>
26+#include <linux/uaccess.h>
27+#include <linux/usb.h>
28+#include <linux/mutex.h>
29+#include <linux/page-flags.h>
30+#include <linux/pagemap.h>
31+#include <linux/jiffies.h>
32+
33+#include "usb1401.h"
34+
35+/****************************************************************************
36+** FlushOutBuff
37+**
38+** Empties the Output buffer and sets int lines. Used from user level only
39+****************************************************************************/
40+void FlushOutBuff(DEVICE_EXTENSION * pdx)
41+{
42+ dev_dbg(&pdx->interface->dev, "%s currentState=%d", __func__,
43+ pdx->sCurrentState);
44+ if (pdx->sCurrentState == U14ERR_TIME) /* Do nothing if hardware in trouble */
45+ return;
46+// CharSend_Cancel(pdx); /* Kill off any pending I/O */
47+ spin_lock_irq(&pdx->charOutLock);
48+ pdx->dwNumOutput = 0;
49+ pdx->dwOutBuffGet = 0;
50+ pdx->dwOutBuffPut = 0;
51+ spin_unlock_irq(&pdx->charOutLock);
52+}
53+
54+/****************************************************************************
55+**
56+** FlushInBuff
57+**
58+** Empties the input buffer and sets int lines
59+****************************************************************************/
60+void FlushInBuff(DEVICE_EXTENSION * pdx)
61+{
62+ dev_dbg(&pdx->interface->dev, "%s currentState=%d", __func__,
63+ pdx->sCurrentState);
64+ if (pdx->sCurrentState == U14ERR_TIME) /* Do nothing if hardware in trouble */
65+ return;
66+// CharRead_Cancel(pDevObject); /* Kill off any pending I/O */
67+ spin_lock_irq(&pdx->charInLock);
68+ pdx->dwNumInput = 0;
69+ pdx->dwInBuffGet = 0;
70+ pdx->dwInBuffPut = 0;
71+ spin_unlock_irq(&pdx->charInLock);
72+}
73+
74+/****************************************************************************
75+** PutChars
76+**
77+** Utility routine to copy chars into the output buffer and fire them off.
78+** called from user mode, holds charOutLock.
79+****************************************************************************/
80+static int PutChars(DEVICE_EXTENSION * pdx, const char *pCh,
81+ unsigned int uCount)
82+{
83+ int iReturn;
84+ spin_lock_irq(&pdx->charOutLock); // get the output spin lock
85+ if ((OUTBUF_SZ - pdx->dwNumOutput) >= uCount) {
86+ unsigned int u;
87+ for (u = 0; u < uCount; u++) {
88+ pdx->outputBuffer[pdx->dwOutBuffPut++] = pCh[u];
89+ if (pdx->dwOutBuffPut >= OUTBUF_SZ)
90+ pdx->dwOutBuffPut = 0;
91+ }
92+ pdx->dwNumOutput += uCount;
93+ spin_unlock_irq(&pdx->charOutLock);
94+ iReturn = SendChars(pdx); // ...give a chance to transmit data
95+ } else {
96+ iReturn = U14ERR_NOOUT; // no room at the out (ha-ha)
97+ spin_unlock_irq(&pdx->charOutLock);
98+ }
99+ return iReturn;
100+}
101+
102+/*****************************************************************************
103+** Add the data in pData (local pointer) of length n to the output buffer, and
104+** trigger an output transfer if this is appropriate. User mode.
105+** Holds the io_mutex
106+*****************************************************************************/
107+int SendString(DEVICE_EXTENSION * pdx, const char __user * pData,
108+ unsigned int n)
109+{
110+ int iReturn = U14ERR_NOERROR; // assume all will be well
111+ char buffer[OUTBUF_SZ + 1]; // space in our address space for characters
112+ if (n > OUTBUF_SZ) // check space in local buffer...
113+ return U14ERR_NOOUT; // ...too many characters
114+ if (copy_from_user(buffer, pData, n))
115+ return -EFAULT;
116+ buffer[n] = 0; // terminate for debug purposes
117+
118+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
119+ if (n > 0) // do nothing if nowt to do!
120+ {
121+ dev_dbg(&pdx->interface->dev, "%s n=%d>%s<", __func__, n,
122+ buffer);
123+ iReturn = PutChars(pdx, buffer, n);
124+ }
125+
126+ Allowi(pdx, false); // make sure we have input int
127+ mutex_unlock(&pdx->io_mutex);
128+
129+ return iReturn;
130+}
131+
132+/****************************************************************************
133+** SendChar
134+**
135+** Sends a single character to the 1401. User mode, holds io_mutex.
136+****************************************************************************/
137+int SendChar(DEVICE_EXTENSION * pdx, char c)
138+{
139+ int iReturn;
140+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
141+ iReturn = PutChars(pdx, &c, 1);
142+ dev_dbg(&pdx->interface->dev, "SendChar >%c< (0x%02x)", c, c);
143+ Allowi(pdx, false); // Make sure char reads are running
144+ mutex_unlock(&pdx->io_mutex);
145+ return iReturn;
146+}
147+
148+/***************************************************************************
149+**
150+** Get1401State
151+**
152+** Retrieves state information from the 1401, adjusts the 1401 state held
153+** in the device extension to indicate the current 1401 type.
154+**
155+** *state is updated with information about the 1401 state as returned by the
156+** 1401. The low byte is a code for what 1401 is doing:
157+**
158+** 0 normal 1401 operation
159+** 1 sending chars to host
160+** 2 sending block data to host
161+** 3 reading block data from host
162+** 4 sending an escape sequence to the host
163+** 0x80 1401 is executing self-test, in which case the upper word
164+** is the last error code seen (or zero for no new error).
165+**
166+** *error is updated with error information if a self-test error code
167+** is returned in the upper word of state.
168+**
169+** both state and error are set to -1 if there are comms problems, and
170+** to zero if there is a simple failure.
171+**
172+** return error code (U14ERR_NOERROR for OK)
173+*/
174+int Get1401State(DEVICE_EXTENSION * pdx, __u32 * state, __u32 * error)
175+{
176+ int nGot;
177+ dev_dbg(&pdx->interface->dev, "Get1401State() entry");
178+
179+ *state = 0xFFFFFFFF; // Start off with invalid state
180+ nGot = usb_control_msg(pdx->udev, usb_rcvctrlpipe(pdx->udev, 0),
181+ GET_STATUS, (D_TO_H | VENDOR | DEVREQ), 0, 0,
182+ pdx->statBuf, sizeof(pdx->statBuf), HZ);
183+ if (nGot != sizeof(pdx->statBuf)) {
184+ dev_err(&pdx->interface->dev,
185+ "Get1401State() FAILED, return code %d", nGot);
186+ pdx->sCurrentState = U14ERR_TIME; // Indicate that things are very wrong indeed
187+ *state = 0; // Force status values to a known state
188+ *error = 0;
189+ } else {
190+ int nDevice;
191+ dev_dbg(&pdx->interface->dev,
192+ "Get1401State() Success, state: 0x%x, 0x%x",
193+ pdx->statBuf[0], pdx->statBuf[1]);
194+
195+ *state = pdx->statBuf[0]; // Return the state values to the calling code
196+ *error = pdx->statBuf[1];
197+
198+ nDevice = pdx->udev->descriptor.bcdDevice >> 8; // 1401 type code value
199+ switch (nDevice) // so we can clean up current state
200+ {
201+ case 0:
202+ pdx->sCurrentState = U14ERR_U1401;
203+ break;
204+
205+ default: // allow lots of device codes for future 1401s
206+ if ((nDevice >= 1) && (nDevice <= 23))
207+ pdx->sCurrentState = (short)(nDevice + 6);
208+ else
209+ pdx->sCurrentState = U14ERR_ILL;
210+ break;
211+ }
212+ }
213+
214+ return pdx->sCurrentState >= 0 ? U14ERR_NOERROR : pdx->sCurrentState;
215+}
216+
217+/****************************************************************************
218+** ReadWrite_Cancel
219+**
220+** Kills off staged read\write request from the USB if one is pending.
221+****************************************************************************/
222+int ReadWrite_Cancel(DEVICE_EXTENSION * pdx)
223+{
224+ dev_dbg(&pdx->interface->dev, "ReadWrite_Cancel entry %d",
225+ pdx->bStagedUrbPending);
226+#ifdef NOT_WRITTEN_YET
227+ int ntStatus = STATUS_SUCCESS;
228+ bool bResult = false;
229+ unsigned int i;
230+ // We can fill this in when we know how we will implement the staged transfer stuff
231+ spin_lock_irq(&pdx->stagedLock);
232+
233+ if (pdx->bStagedUrbPending) // anything to be cancelled? May need more...
234+ {
235+ dev_info(&pdx->interface - dev,
236+ "ReadWrite_Cancel about to cancel Urb");
237+
238+ // KeClearEvent(&pdx->StagingDoneEvent); // Clear the staging done flag
239+ USB_ASSERT(pdx->pStagedIrp != NULL);
240+
241+ // Release the spinlock first otherwise the completion routine may hang
242+ // on the spinlock while this function hands waiting for the event.
243+ spin_unlock_irq(&pdx->stagedLock);
244+ bResult = IoCancelIrp(pdx->pStagedIrp); // Actually do the cancel
245+ if (bResult) {
246+ LARGE_INTEGER timeout;
247+ timeout.QuadPart = -10000000; // Use a timeout of 1 second
248+ dev_info(&pdx->interface - dev,
249+ "ReadWrite_Cancel about to wait till done");
250+ ntStatus =
251+ KeWaitForSingleObject(&pdx->StagingDoneEvent,
252+ Executive, KernelMode, FALSE,
253+ &timeout);
254+ } else {
255+ dev_info(&pdx->interface - dev,
256+ "ReadWrite_Cancel, cancellation failed");
257+ ntStatus = U14ERR_FAIL;
258+ }
259+ USB_KdPrint(DBGLVL_DEFAULT,
260+ ("ReadWrite_Cancel ntStatus = 0x%x decimal %d\n",
261+ ntStatus, ntStatus));
262+ } else
263+ spin_unlock_irq(&pdx->stagedLock);
264+
265+ dev_info(&pdx->interface - dev, "ReadWrite_Cancel done");
266+ return ntStatus;
267+#else
268+ return U14ERR_NOERROR;
269+#endif
270+
271+}
272+
273+/***************************************************************************
274+** InSelfTest - utility to check in self test. Return 1 for ST, 0 for not or
275+** a -ve error code if we failed for some reason.
276+***************************************************************************/
277+static int InSelfTest(DEVICE_EXTENSION * pdx, unsigned int *pState)
278+{
279+ unsigned int state, error;
280+ int iReturn = Get1401State(pdx, &state, &error); // see if in self-test
281+ if (iReturn == U14ERR_NOERROR) // if all still OK
282+ iReturn = (state == (unsigned int)-1) || // TX problem or...
283+ ((state & 0xff) == 0x80); // ...self test
284+ *pState = state; // return actual state
285+ return iReturn;
286+}
287+
288+/***************************************************************************
289+** Is1401 - ALWAYS CALLED HOLDING THE io_mutex
290+**
291+** Tests for the current state of the 1401. Sets sCurrentState:
292+**
293+** U14ERR_NOIF 1401 i/f card not installed (not done here)
294+** U14ERR_OFF 1401 apparently not switched on
295+** U14ERR_NC 1401 appears to be not connected
296+** U14ERR_ILL 1401 if it is there its not very well at all
297+** U14ERR_TIME 1401 appears OK, but doesn't communicate - very bad
298+** U14ERR_STD 1401 OK and ready for use
299+** U14ERR_PLUS 1401+ OK and ready for use
300+** U14ERR_U1401 Micro1401 OK and ready for use
301+** U14ERR_POWER Power1401 OK and ready for use
302+** U14ERR_U14012 Micro1401 mkII OK and ready for use
303+**
304+** Returns TRUE if a 1401 detected and OK, else FALSE
305+****************************************************************************/
306+bool Is1401(DEVICE_EXTENSION * pdx)
307+{
308+ int iReturn;
309+ dev_dbg(&pdx->interface->dev, "%s", __func__);
310+
311+ ced_draw_down(pdx); // wait for, then kill outstanding Urbs
312+ FlushInBuff(pdx); // Clear out input buffer & pipe
313+ FlushOutBuff(pdx); // Clear output buffer & pipe
314+
315+ // The next call returns 0 if OK, but has returned 1 in the past, meaning that
316+ // usb_unlock_device() is needed... now it always is
317+ iReturn = usb_lock_device_for_reset(pdx->udev, pdx->interface);
318+
319+ // release the io_mutex because if we don't, we will deadlock due to system
320+ // calls back into the driver.
321+ mutex_unlock(&pdx->io_mutex); // locked, so we will not get system calls
322+ if (iReturn >= 0) // if we failed
323+ {
324+ iReturn = usb_reset_device(pdx->udev); // try to do the reset
325+ usb_unlock_device(pdx->udev); // undo the lock
326+ }
327+
328+ mutex_lock(&pdx->io_mutex); // hold stuff off while we wait
329+ pdx->dwDMAFlag = MODE_CHAR; // Clear DMA mode flag regardless!
330+ if (iReturn == 0) // if all is OK still
331+ {
332+ unsigned int state;
333+ iReturn = InSelfTest(pdx, &state); // see if likely in self test
334+ if (iReturn > 0) // do we need to wait for self-test?
335+ {
336+ unsigned long ulTimeOut = jiffies + 30 * HZ; // when to give up
337+ while ((iReturn > 0) && time_before(jiffies, ulTimeOut)) {
338+ schedule(); // let other stuff run
339+ iReturn = InSelfTest(pdx, &state); // see if done yet
340+ }
341+ }
342+
343+ if (iReturn == 0) // if all is OK...
344+ iReturn = state == 0; // then sucess is that the state is 0
345+ } else
346+ iReturn = 0; // we failed
347+ pdx->bForceReset = false; // Clear forced reset flag now
348+
349+ return iReturn > 0;
350+}
351+
352+/****************************************************************************
353+** QuickCheck - ALWAYS CALLED HOLDING THE io_mutex
354+** This is used to test for a 1401. It will try to do a quick check if all is
355+** OK, that is the 1401 was OK the last time it was asked, and there is no DMA
356+** in progress, and if the bTestBuff flag is set, the character buffers must be
357+** empty too. If the quick check shows that the state is still the same, then
358+** all is OK.
359+**
360+** If any of the above conditions are not met, or if the state or type of the
361+** 1401 has changed since the previous test, the full Is1401 test is done, but
362+** only if bCanReset is also TRUE.
363+**
364+** The return value is TRUE if a useable 1401 is found, FALSE if not
365+*/
366+bool QuickCheck(DEVICE_EXTENSION * pdx, bool bTestBuff, bool bCanReset)
367+{
368+ bool bRet = false; // assume it will fail and we will reset
369+ bool bShortTest;
370+
371+ bShortTest = ((pdx->dwDMAFlag == MODE_CHAR) && // no DMA running
372+ (!pdx->bForceReset) && // Not had a real reset forced
373+ (pdx->sCurrentState >= U14ERR_STD)); // No 1401 errors stored
374+
375+ dev_dbg(&pdx->interface->dev,
376+ "%s DMAFlag:%d, state:%d, force:%d, testBuff:%d, short:%d",
377+ __func__, pdx->dwDMAFlag, pdx->sCurrentState, pdx->bForceReset,
378+ bTestBuff, bShortTest);
379+
380+ if ((bTestBuff) && // Buffer check requested, and...
381+ (pdx->dwNumInput || pdx->dwNumOutput)) // ...characters were in the buffer?
382+ {
383+ bShortTest = false; // Then do the full test
384+ dev_dbg(&pdx->interface->dev,
385+ "%s will reset as buffers not empty", __func__);
386+ }
387+
388+ if (bShortTest || !bCanReset) // Still OK to try the short test?
389+ { // Always test if no reset - we want state update
390+ unsigned int state, error;
391+ dev_dbg(&pdx->interface->dev, "%s->Get1401State", __func__);
392+ if (Get1401State(pdx, &state, &error) == U14ERR_NOERROR) // Check on the 1401 state
393+ {
394+ if ((state & 0xFF) == 0) // If call worked, check the status value
395+ bRet = true; // If that was zero, all is OK, no reset needed
396+ }
397+ }
398+
399+ if (!bRet && bCanReset) // If all not OK, then
400+ {
401+ dev_info(&pdx->interface->dev, "%s->Is1401 %d %d %d %d",
402+ __func__, bShortTest, pdx->sCurrentState, bTestBuff,
403+ pdx->bForceReset);
404+ bRet = Is1401(pdx); // do full test
405+ }
406+
407+ return bRet;
408+}
409+
410+/****************************************************************************
411+** Reset1401
412+**
413+** Resets the 1401 and empties the i/o buffers
414+*****************************************************************************/
415+int Reset1401(DEVICE_EXTENSION * pdx)
416+{
417+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
418+ dev_dbg(&pdx->interface->dev, "ABout to call QuickCheck");
419+ QuickCheck(pdx, true, true); // Check 1401, reset if not OK
420+ mutex_unlock(&pdx->io_mutex);
421+ return U14ERR_NOERROR;
422+}
423+
424+/****************************************************************************
425+** GetChar
426+**
427+** Gets a single character from the 1401
428+****************************************************************************/
429+int GetChar(DEVICE_EXTENSION * pdx)
430+{
431+ int iReturn = U14ERR_NOIN; // assume we will get nothing
432+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
433+
434+ dev_dbg(&pdx->interface->dev, "GetChar");
435+
436+ Allowi(pdx, false); // Make sure char reads are running
437+ SendChars(pdx); // and send any buffered chars
438+
439+ spin_lock_irq(&pdx->charInLock);
440+ if (pdx->dwNumInput > 0) // worth looking
441+ {
442+ iReturn = pdx->inputBuffer[pdx->dwInBuffGet++];
443+ if (pdx->dwInBuffGet >= INBUF_SZ)
444+ pdx->dwInBuffGet = 0;
445+ pdx->dwNumInput--;
446+ } else
447+ iReturn = U14ERR_NOIN; // no input data to read
448+ spin_unlock_irq(&pdx->charInLock);
449+
450+ Allowi(pdx, false); // Make sure char reads are running
451+
452+ mutex_unlock(&pdx->io_mutex); // Protect disconnect from new i/o
453+ return iReturn;
454+}
455+
456+/****************************************************************************
457+** GetString
458+**
459+** Gets a string from the 1401. Returns chars up to the next CR or when
460+** there are no more to read or nowhere to put them. CR is translated to
461+** 0 and counted as a character. If the string does not end in a 0, we will
462+** add one, if there is room, but it is not counted as a character.
463+**
464+** returns the count of characters (including the terminator, or 0 if none
465+** or a negative error code.
466+****************************************************************************/
467+int GetString(DEVICE_EXTENSION * pdx, char __user * pUser, int n)
468+{
469+ int nAvailable; // character in the buffer
470+ int iReturn = U14ERR_NOIN;
471+ if (n <= 0)
472+ return -ENOMEM;
473+
474+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
475+ Allowi(pdx, false); // Make sure char reads are running
476+ SendChars(pdx); // and send any buffered chars
477+
478+ spin_lock_irq(&pdx->charInLock);
479+ nAvailable = pdx->dwNumInput; // characters available now
480+ if (nAvailable > n) // read max of space in pUser...
481+ nAvailable = n; // ...or input characters
482+
483+ if (nAvailable > 0) // worth looking?
484+ {
485+ char buffer[INBUF_SZ + 1]; // space for a linear copy of data
486+ int nGot = 0;
487+ int nCopyToUser; // number to copy to user
488+ char cData;
489+ do {
490+ cData = pdx->inputBuffer[pdx->dwInBuffGet++];
491+ if (cData == CR_CHAR) // replace CR with zero
492+ cData = (char)0;
493+
494+ if (pdx->dwInBuffGet >= INBUF_SZ)
495+ pdx->dwInBuffGet = 0; // wrap buffer pointer
496+
497+ buffer[nGot++] = cData; // save the output
498+ }
499+ while ((nGot < nAvailable) && cData);
500+
501+ nCopyToUser = nGot; // what to copy...
502+ if (cData) // do we need null
503+ {
504+ buffer[nGot] = (char)0; // make it tidy
505+ if (nGot < n) // if space in user buffer...
506+ ++nCopyToUser; // ...copy the 0 as well.
507+ }
508+
509+ pdx->dwNumInput -= nGot;
510+ spin_unlock_irq(&pdx->charInLock);
511+
512+ dev_dbg(&pdx->interface->dev,
513+ "GetString read %d characters >%s<", nGot, buffer);
514+ if (copy_to_user(pUser, buffer, nCopyToUser))
515+ iReturn = -EFAULT;
516+ else
517+ iReturn = nGot; // report characters read
518+ } else
519+ spin_unlock_irq(&pdx->charInLock);
520+
521+ Allowi(pdx, false); // Make sure char reads are running
522+ mutex_unlock(&pdx->io_mutex); // Protect disconnect from new i/o
523+
524+ return iReturn;
525+}
526+
527+/*******************************************************************************
528+** Get count of characters in the inout buffer.
529+*******************************************************************************/
530+int Stat1401(DEVICE_EXTENSION * pdx)
531+{
532+ int iReturn;
533+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
534+ Allowi(pdx, false); // make sure we allow pending chars
535+ SendChars(pdx); // in both directions
536+ iReturn = pdx->dwNumInput; // no lock as single read
537+ mutex_unlock(&pdx->io_mutex); // Protect disconnect from new i/o
538+ return iReturn;
539+}
540+
541+/****************************************************************************
542+** LineCount
543+**
544+** Returns the number of newline chars in the buffer. There is no need for
545+** any fancy interlocks as we only read the interrupt routine data, and the
546+** system is arranged so nothing can be destroyed.
547+****************************************************************************/
548+int LineCount(DEVICE_EXTENSION * pdx)
549+{
550+ int iReturn = 0; // will be count of line ends
551+
552+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
553+ Allowi(pdx, false); // Make sure char reads are running
554+ SendChars(pdx); // and send any buffered chars
555+ spin_lock_irq(&pdx->charInLock); // Get protection
556+
557+ if (pdx->dwNumInput > 0) // worth looking?
558+ {
559+ unsigned int dwIndex = pdx->dwInBuffGet; // start at first available
560+ unsigned int dwEnd = pdx->dwInBuffPut; // Position for search end
561+ do {
562+ if (pdx->inputBuffer[dwIndex++] == CR_CHAR)
563+ ++iReturn; // inc count if CR
564+
565+ if (dwIndex >= INBUF_SZ) // see if we fall off buff
566+ dwIndex = 0;
567+ }
568+ while (dwIndex != dwEnd); // go to last avaliable
569+ }
570+
571+ spin_unlock_irq(&pdx->charInLock);
572+ dev_dbg(&pdx->interface->dev, "LineCount returned %d", iReturn);
573+ mutex_unlock(&pdx->io_mutex); // Protect disconnect from new i/o
574+ return iReturn;
575+}
576+
577+/****************************************************************************
578+** GetOutBufSpace
579+**
580+** Gets the space in the output buffer. Called from user code.
581+*****************************************************************************/
582+int GetOutBufSpace(DEVICE_EXTENSION * pdx)
583+{
584+ int iReturn;
585+ mutex_lock(&pdx->io_mutex); // Protect disconnect from new i/o
586+ SendChars(pdx); // send any buffered chars
587+ iReturn = (int)(OUTBUF_SZ - pdx->dwNumOutput); // no lock needed for single read
588+ dev_dbg(&pdx->interface->dev, "OutBufSpace %d", iReturn);
589+ mutex_unlock(&pdx->io_mutex); // Protect disconnect from new i/o
590+ return iReturn;
591+}
592+
593+/****************************************************************************
594+**
595+** ClearArea
596+**
597+** Clears up a transfer area. This is always called in the context of a user
598+** request, never from a call-back.
599+****************************************************************************/
600+int ClearArea(DEVICE_EXTENSION * pdx, int nArea)
601+{
602+ int iReturn = U14ERR_NOERROR;
603+
604+ if ((nArea < 0) || (nArea >= MAX_TRANSAREAS)) {
605+ iReturn = U14ERR_BADAREA;
606+ dev_err(&pdx->interface->dev, "%s Attempt to clear area %d",
607+ __func__, nArea);
608+ } else {
609+ TRANSAREA *pTA = &pdx->rTransDef[nArea]; // to save typing
610+ if (!pTA->bUsed) // if not used...
611+ iReturn = U14ERR_NOTSET; // ...nothing to be done
612+ else {
613+ // We must save the memory we return as we shouldn't mess with memory while
614+ // holding a spin lock.
615+ struct page **pPages = 0; // save page address list
616+ int nPages = 0; // and number of pages
617+ int np;
618+
619+ dev_dbg(&pdx->interface->dev, "%s area %d", __func__,
620+ nArea);
621+ spin_lock_irq(&pdx->stagedLock);
622+ if ((pdx->StagedId == nArea)
623+ && (pdx->dwDMAFlag > MODE_CHAR)) {
624+ iReturn = U14ERR_UNLOCKFAIL; // cannot delete as in use
625+ dev_err(&pdx->interface->dev,
626+ "%s call on area %d while active",
627+ __func__, nArea);
628+ } else {
629+ pPages = pTA->pPages; // save page address list
630+ nPages = pTA->nPages; // and page count
631+ if (pTA->dwEventSz) // if events flagging in use
632+ wake_up_interruptible(&pTA->wqEvent); // release anything that was waiting
633+
634+ if (pdx->bXFerWaiting
635+ && (pdx->rDMAInfo.wIdent == nArea))
636+ pdx->bXFerWaiting = false; // Cannot have pending xfer if area cleared
637+
638+ // Clean out the TRANSAREA except for the wait queue, which is at the end
639+ // This sets bUsed to false and dwEventSz to 0 to say area not used and no events.
640+ memset(pTA, 0,
641+ sizeof(TRANSAREA) -
642+ sizeof(wait_queue_head_t));
643+ }
644+ spin_unlock_irq(&pdx->stagedLock);
645+
646+ if (pPages) // if we decided to release the memory
647+ {
648+ // Now we must undo the pinning down of the pages. We will assume the worst and mark
649+ // all the pages as dirty. Don't be tempted to move this up above as you must not be
650+ // holding a spin lock to do this stuff as it is not atomic.
651+ dev_dbg(&pdx->interface->dev, "%s nPages=%d",
652+ __func__, nPages);
653+
654+ for (np = 0; np < nPages; ++np) {
655+ if (pPages[np]) {
656+ SetPageDirty(pPages[np]);
657+ page_cache_release(pPages[np]);
658+ }
659+ }
660+
661+ kfree(pPages);
662+ dev_dbg(&pdx->interface->dev,
663+ "%s kfree(pPages) done", __func__);
664+ }
665+ }
666+ }
667+
668+ return iReturn;
669+}
670+
671+/****************************************************************************
672+** SetArea
673+**
674+** Sets up a transfer area - the functional part. Called by both
675+** SetTransfer and SetCircular.
676+****************************************************************************/
677+static int SetArea(DEVICE_EXTENSION * pdx, int nArea, char __user * puBuf,
678+ unsigned int dwLength, bool bCircular, bool bCircToHost)
679+{
680+ // Start by working out the page aligned start of the area and the size
681+ // of the area in pages, allowing for the start not being aligned and the
682+ // end needing to be rounded up to a page boundary.
683+ unsigned long ulStart = ((unsigned long)puBuf) & PAGE_MASK;
684+ unsigned int ulOffset = ((unsigned long)puBuf) & (PAGE_SIZE - 1);
685+ int len = (dwLength + ulOffset + PAGE_SIZE - 1) >> PAGE_SHIFT;
686+
687+ TRANSAREA *pTA = &pdx->rTransDef[nArea]; // to save typing
688+ struct page **pPages = 0; // space for page tables
689+ int nPages = 0; // and number of pages
690+
691+ int iReturn = ClearArea(pdx, nArea); // see if OK to use this area
692+ if ((iReturn != U14ERR_NOTSET) && // if not area unused and...
693+ (iReturn != U14ERR_NOERROR)) // ...not all OK, then...
694+ return iReturn; // ...we cannot use this area
695+
696+ if (!access_ok(VERIFY_WRITE, puBuf, dwLength)) // if we cannot access the memory...
697+ return -EFAULT; // ...then we are done
698+
699+ // Now allocate space to hold the page pointer and virtual address pointer tables
700+ pPages =
701+ (struct page **)kmalloc(len * sizeof(struct page *), GFP_KERNEL);
702+ if (!pPages) {
703+ iReturn = U14ERR_NOMEMORY;
704+ goto error;
705+ }
706+ dev_dbg(&pdx->interface->dev, "%s %p, length=%06x, circular %d",
707+ __func__, puBuf, dwLength, bCircular);
708+
709+ // To pin down user pages we must first acquire the mapping semaphore.
710+ down_read(&current->mm->mmap_sem); // get memory map semaphore
711+ nPages =
712+ get_user_pages(current, current->mm, ulStart, len, 1, 0, pPages, 0);
713+ up_read(&current->mm->mmap_sem); // release the semaphore
714+ dev_dbg(&pdx->interface->dev, "%s nPages = %d", __func__, nPages);
715+
716+ if (nPages > 0) // if we succeeded
717+ {
718+ // If you are tempted to use page_address (form LDD3), forget it. You MUST use
719+ // kmap() or kmap_atomic() to get a virtual address. page_address will give you
720+ // (null) or at least it does in this context with an x86 machine.
721+ spin_lock_irq(&pdx->stagedLock);
722+ pTA->lpvBuff = puBuf; // keep start of region (user address)
723+ pTA->dwBaseOffset = ulOffset; // save offset in first page to start of xfer
724+ pTA->dwLength = dwLength; // Size if the region in bytes
725+ pTA->pPages = pPages; // list of pages that are used by buffer
726+ pTA->nPages = nPages; // number of pages
727+
728+ pTA->bCircular = bCircular;
729+ pTA->bCircToHost = bCircToHost;
730+
731+ pTA->aBlocks[0].dwOffset = 0;
732+ pTA->aBlocks[0].dwSize = 0;
733+ pTA->aBlocks[1].dwOffset = 0;
734+ pTA->aBlocks[1].dwSize = 0;
735+ pTA->bUsed = true; // This is now a used block
736+
737+ spin_unlock_irq(&pdx->stagedLock);
738+ iReturn = U14ERR_NOERROR; // say all was well
739+ } else {
740+ iReturn = U14ERR_LOCKFAIL;
741+ goto error;
742+ }
743+
744+ return iReturn;
745+
746+error:
747+ kfree(pPages);
748+ return iReturn;
749+}
750+
751+/****************************************************************************
752+** SetTransfer
753+**
754+** Sets up a transfer area record. If the area is already set, we attempt to
755+** unset it. Unsetting will fail if the area is booked, and a transfer to that
756+** area is in progress. Otherwise, we will release the area and re-assign it.
757+****************************************************************************/
758+int SetTransfer(DEVICE_EXTENSION * pdx, TRANSFERDESC __user * pTD)
759+{
760+ int iReturn;
761+ TRANSFERDESC td;
762+
763+ if (copy_from_user(&td, pTD, sizeof(td)))
764+ return -EFAULT;
765+
766+ mutex_lock(&pdx->io_mutex);
767+ dev_dbg(&pdx->interface->dev, "%s area:%d, size:%08x", __func__,
768+ td.wAreaNum, td.dwLength);
769+ // The strange cast is done so that we don't get warnings in 32-bit linux about the size of the
770+ // pointer. The pointer is always passed as a 64-bit object so that we don't have problems using
771+ // a 32-bit program on a 64-bit system. unsigned long is 64-bits on a 64-bit system.
772+ iReturn =
773+ SetArea(pdx, td.wAreaNum,
774+ (char __user *)((unsigned long)td.lpvBuff), td.dwLength,
775+ false, false);
776+ mutex_unlock(&pdx->io_mutex);
777+ return iReturn;
778+}
779+
780+/****************************************************************************
781+** UnSetTransfer
782+** Erases a transfer area record
783+****************************************************************************/
784+int UnsetTransfer(DEVICE_EXTENSION * pdx, int nArea)
785+{
786+ int iReturn;
787+ mutex_lock(&pdx->io_mutex);
788+ iReturn = ClearArea(pdx, nArea);
789+ mutex_unlock(&pdx->io_mutex);
790+ return iReturn;
791+}
792+
793+/****************************************************************************
794+** SetEvent
795+** Creates an event that we can test for based on a transfer to/from an area.
796+** The area must be setup for a transfer. We attempt to simulate the Windows
797+** driver behavior for events (as we don't actually use them), which is to
798+** pretend that whatever the user asked for was achieved, so we return 1 if
799+** try to create one, and 0 if they ask to remove (assuming all else was OK).
800+****************************************************************************/
801+int SetEvent(DEVICE_EXTENSION * pdx, TRANSFEREVENT __user * pTE)
802+{
803+ int iReturn = U14ERR_NOERROR;
804+ TRANSFEREVENT te;
805+
806+ // get a local copy of the data
807+ if (copy_from_user(&te, pTE, sizeof(te)))
808+ return -EFAULT;
809+
810+ if (te.wAreaNum >= MAX_TRANSAREAS) // the area must exist
811+ return U14ERR_BADAREA;
812+ else {
813+ TRANSAREA *pTA = &pdx->rTransDef[te.wAreaNum];
814+ mutex_lock(&pdx->io_mutex); // make sure we have no competitor
815+ spin_lock_irq(&pdx->stagedLock);
816+ if (pTA->bUsed) // area must be in use
817+ {
818+ pTA->dwEventSt = te.dwStart; // set area regions
819+ pTA->dwEventSz = te.dwLength; // set size (0 cancels it)
820+ pTA->bEventToHost = te.wFlags & 1; // set the direction
821+ pTA->iWakeUp = 0; // zero the wake up count
822+ } else
823+ iReturn = U14ERR_NOTSET;
824+ spin_unlock_irq(&pdx->stagedLock);
825+ mutex_unlock(&pdx->io_mutex);
826+ }
827+ return iReturn ==
828+ U14ERR_NOERROR ? (te.iSetEvent ? 1 : U14ERR_NOERROR) : iReturn;
829+}
830+
831+/****************************************************************************
832+** WaitEvent
833+** Sleep the process with a timeout waiting for an event. Returns the number
834+** of times that a block met the event condition since we last cleared it or
835+** 0 if timed out, or -ve error (bad area or not set, or signal).
836+****************************************************************************/
837+int WaitEvent(DEVICE_EXTENSION * pdx, int nArea, int msTimeOut)
838+{
839+ int iReturn;
840+ if ((unsigned)nArea >= MAX_TRANSAREAS)
841+ return U14ERR_BADAREA;
842+ else {
843+ int iWait;
844+ TRANSAREA *pTA = &pdx->rTransDef[nArea];
845+ msTimeOut = (msTimeOut * HZ + 999) / 1000; // convert timeout to jiffies
846+
847+ // We cannot wait holding the mutex, but we check the flags while holding
848+ // it. This may well be pointless as another thread could get in between
849+ // releasing it and the wait call. However, this would have to clear the
850+ // iWakeUp flag. However, the !pTA-bUsed may help us in this case.
851+ mutex_lock(&pdx->io_mutex); // make sure we have no competitor
852+ if (!pTA->bUsed || !pTA->dwEventSz) // check something to wait for...
853+ return U14ERR_NOTSET; // ...else we do nothing
854+ mutex_unlock(&pdx->io_mutex);
855+
856+ if (msTimeOut)
857+ iWait =
858+ wait_event_interruptible_timeout(pTA->wqEvent,
859+ pTA->iWakeUp
860+ || !pTA->bUsed,
861+ msTimeOut);
862+ else
863+ iWait =
864+ wait_event_interruptible(pTA->wqEvent, pTA->iWakeUp
865+ || !pTA->bUsed);
866+ if (iWait)
867+ iReturn = -ERESTARTSYS; // oops - we have had a SIGNAL
868+ else
869+ iReturn = pTA->iWakeUp; // else the wakeup count
870+
871+ spin_lock_irq(&pdx->stagedLock);
872+ pTA->iWakeUp = 0; // clear the flag
873+ spin_unlock_irq(&pdx->stagedLock);
874+ }
875+ return iReturn;
876+}
877+
878+/****************************************************************************
879+** TestEvent
880+** Test the event to see if a WaitEvent would return immediately. Returns the
881+** number of times a block completed since the last call, or 0 if none or a
882+** negative error.
883+****************************************************************************/
884+int TestEvent(DEVICE_EXTENSION * pdx, int nArea)
885+{
886+ int iReturn;
887+ if ((unsigned)nArea >= MAX_TRANSAREAS)
888+ iReturn = U14ERR_BADAREA;
889+ else {
890+ TRANSAREA *pTA = &pdx->rTransDef[nArea];
891+ mutex_lock(&pdx->io_mutex); // make sure we have no competitor
892+ spin_lock_irq(&pdx->stagedLock);
893+ iReturn = pTA->iWakeUp; // get wakeup count since last call
894+ pTA->iWakeUp = 0; // clear the count
895+ spin_unlock_irq(&pdx->stagedLock);
896+ mutex_unlock(&pdx->io_mutex);
897+ }
898+ return iReturn;
899+}
900+
901+/****************************************************************************
902+** GetTransferInfo
903+** Puts the current state of the 1401 in a TGET_TX_BLOCK.
904+*****************************************************************************/
905+int GetTransfer(DEVICE_EXTENSION * pdx, TGET_TX_BLOCK __user * pTX)
906+{
907+ int iReturn = U14ERR_NOERROR;
908+ unsigned int dwIdent;
909+
910+ mutex_lock(&pdx->io_mutex);
911+ dwIdent = pdx->StagedId; // area ident for last xfer
912+ if (dwIdent >= MAX_TRANSAREAS)
913+ iReturn = U14ERR_BADAREA;
914+ else {
915+ // Return the best information we have - we don't have physical addresses
916+ TGET_TX_BLOCK tx;
917+ memset(&tx, 0, sizeof(tx)); // clean out local work structure
918+ tx.size = pdx->rTransDef[dwIdent].dwLength;
919+ tx.linear = (long long)((long)pdx->rTransDef[dwIdent].lpvBuff);
920+ tx.avail = GET_TX_MAXENTRIES; // how many blocks we could return
921+ tx.used = 1; // number we actually return
922+ tx.entries[0].physical =
923+ (long long)(tx.linear + pdx->StagedOffset);
924+ tx.entries[0].size = tx.size;
925+
926+ if (copy_to_user(pTX, &tx, sizeof(tx)))
927+ iReturn = -EFAULT;
928+ }
929+ mutex_unlock(&pdx->io_mutex);
930+ return iReturn;
931+}
932+
933+/****************************************************************************
934+** KillIO1401
935+**
936+** Empties the host i/o buffers
937+****************************************************************************/
938+int KillIO1401(DEVICE_EXTENSION * pdx)
939+{
940+ dev_dbg(&pdx->interface->dev, "%s", __func__);
941+ mutex_lock(&pdx->io_mutex);
942+ FlushOutBuff(pdx);
943+ FlushInBuff(pdx);
944+ mutex_unlock(&pdx->io_mutex);
945+ return U14ERR_NOERROR;
946+}
947+
948+/****************************************************************************
949+** BlkTransState
950+** Returns a 0 or a 1 for whether DMA is happening. No point holding a mutex
951+** for this as it only does one read.
952+*****************************************************************************/
953+int BlkTransState(DEVICE_EXTENSION * pdx)
954+{
955+ int iReturn = pdx->dwDMAFlag != MODE_CHAR;
956+ dev_dbg(&pdx->interface->dev, "%s = %d", __func__, iReturn);
957+ return iReturn;
958+}
959+
960+/****************************************************************************
961+** StateOf1401
962+**
963+** Puts the current state of the 1401 in the Irp return buffer.
964+*****************************************************************************/
965+int StateOf1401(DEVICE_EXTENSION * pdx)
966+{
967+ int iReturn;
968+ mutex_lock(&pdx->io_mutex);
969+
970+ QuickCheck(pdx, false, false); // get state up to date, no reset
971+ iReturn = pdx->sCurrentState;
972+
973+ mutex_unlock(&pdx->io_mutex);
974+ dev_dbg(&pdx->interface->dev, "%s = %d", __func__, iReturn);
975+
976+ return iReturn;
977+}
978+
979+/****************************************************************************
980+** StartSelfTest
981+**
982+** Initiates a self-test cycle. The assumption is that we have no interrupts
983+** active, so we should make sure that this is the case.
984+*****************************************************************************/
985+int StartSelfTest(DEVICE_EXTENSION * pdx)
986+{
987+ int nGot;
988+ mutex_lock(&pdx->io_mutex);
989+ dev_dbg(&pdx->interface->dev, "%s", __func__);
990+
991+ ced_draw_down(pdx); // wait for, then kill outstanding Urbs
992+ FlushInBuff(pdx); // Clear out input buffer & pipe
993+ FlushOutBuff(pdx); // Clear output buffer & pipe
994+// ReadWrite_Cancel(pDeviceObject); /* so things stay tidy */
995+ pdx->dwDMAFlag = MODE_CHAR; /* Clear DMA mode flags here */
996+
997+ nGot = usb_control_msg(pdx->udev, usb_rcvctrlpipe(pdx->udev, 0), DB_SELFTEST, (H_TO_D | VENDOR | DEVREQ), 0, 0, 0, 0, HZ); // allow 1 second timeout
998+ pdx->ulSelfTestTime = jiffies + HZ * 30; // 30 seconds into the future
999+
1000+ mutex_unlock(&pdx->io_mutex);
1001+ if (nGot < 0)
1002+ dev_err(&pdx->interface->dev, "%s err=%d", __func__, nGot);
1003+ return nGot < 0 ? U14ERR_FAIL : U14ERR_NOERROR;
1004+}
1005+
1006+/****************************************************************************
1007+** CheckSelfTest
1008+**
1009+** Check progress of a self-test cycle
1010+****************************************************************************/
1011+int CheckSelfTest(DEVICE_EXTENSION * pdx, TGET_SELFTEST __user * pGST)
1012+{
1013+ unsigned int state, error;
1014+ int iReturn;
1015+ TGET_SELFTEST gst; // local work space
1016+ memset(&gst, 0, sizeof(gst)); // clear out the space (sets code 0)
1017+
1018+ mutex_lock(&pdx->io_mutex);
1019+
1020+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1021+ iReturn = Get1401State(pdx, &state, &error);
1022+ if (iReturn == U14ERR_NOERROR) // Only accept zero if it happens twice
1023+ iReturn = Get1401State(pdx, &state, &error);
1024+
1025+ if (iReturn != U14ERR_NOERROR) // Self-test can cause comms errors
1026+ { // so we assume still testing
1027+ dev_err(&pdx->interface->dev,
1028+ "%s Get1401State=%d, assuming still testing", __func__,
1029+ iReturn);
1030+ state = 0x80; // Force still-testing, no error
1031+ error = 0;
1032+ iReturn = U14ERR_NOERROR;
1033+ }
1034+
1035+ if ((state == -1) && (error == -1)) // If Get1401State had problems
1036+ {
1037+ dev_err(&pdx->interface->dev,
1038+ "%s Get1401State failed, assuming still testing",
1039+ __func__);
1040+ state = 0x80; // Force still-testing, no error
1041+ error = 0;
1042+ }
1043+
1044+ if ((state & 0xFF) == 0x80) // If we are still in self-test
1045+ {
1046+ if (state & 0x00FF0000) // Have we got an error?
1047+ {
1048+ gst.code = (state & 0x00FF0000) >> 16; // read the error code
1049+ gst.x = error & 0x0000FFFF; // Error data X
1050+ gst.y = (error & 0xFFFF0000) >> 16; // and data Y
1051+ dev_dbg(&pdx->interface->dev, "Self-test error code %d",
1052+ gst.code);
1053+ } else // No error, check for timeout
1054+ {
1055+ unsigned long ulNow = jiffies; // get current time
1056+ if (time_after(ulNow, pdx->ulSelfTestTime)) {
1057+ gst.code = -2; // Flag the timeout
1058+ dev_dbg(&pdx->interface->dev,
1059+ "Self-test timed-out");
1060+ } else
1061+ dev_dbg(&pdx->interface->dev,
1062+ "Self-test on-going");
1063+ }
1064+ } else {
1065+ gst.code = -1; // Flag the test is done
1066+ dev_dbg(&pdx->interface->dev, "Self-test done");
1067+ }
1068+
1069+ if (gst.code < 0) // If we have a problem or finished
1070+ { // If using the 2890 we should reset properly
1071+ if ((pdx->nPipes == 4) && (pdx->s1401Type <= TYPEPOWER))
1072+ Is1401(pdx); // Get 1401 reset and OK
1073+ else
1074+ QuickCheck(pdx, true, true); // Otherwise check without reset unless problems
1075+ }
1076+ mutex_unlock(&pdx->io_mutex);
1077+
1078+ if (copy_to_user(pGST, &gst, sizeof(gst)))
1079+ return -EFAULT;
1080+
1081+ return iReturn;
1082+}
1083+
1084+/****************************************************************************
1085+** TypeOf1401
1086+**
1087+** Returns code for standard, plus, micro1401, power1401 or none
1088+****************************************************************************/
1089+int TypeOf1401(DEVICE_EXTENSION * pdx)
1090+{
1091+ int iReturn = TYPEUNKNOWN;
1092+ mutex_lock(&pdx->io_mutex);
1093+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1094+
1095+ switch (pdx->s1401Type) {
1096+ case TYPE1401:
1097+ iReturn = U14ERR_STD;
1098+ break; // Handle these types directly
1099+ case TYPEPLUS:
1100+ iReturn = U14ERR_PLUS;
1101+ break;
1102+ case TYPEU1401:
1103+ iReturn = U14ERR_U1401;
1104+ break;
1105+ default:
1106+ if ((pdx->s1401Type >= TYPEPOWER) && (pdx->s1401Type <= 25))
1107+ iReturn = pdx->s1401Type + 4; // We can calculate types
1108+ else // for up-coming 1401 designs
1109+ iReturn = TYPEUNKNOWN; // Don't know or not there
1110+ }
1111+ dev_dbg(&pdx->interface->dev, "%s %d", __func__, iReturn);
1112+ mutex_unlock(&pdx->io_mutex);
1113+
1114+ return iReturn;
1115+}
1116+
1117+/****************************************************************************
1118+** TransferFlags
1119+**
1120+** Returns flags on block transfer abilities
1121+****************************************************************************/
1122+int TransferFlags(DEVICE_EXTENSION * pdx)
1123+{
1124+ int iReturn = U14TF_MULTIA | U14TF_DIAG | // we always have multiple DMA area
1125+ U14TF_NOTIFY | U14TF_CIRCTH; // diagnostics, notify and circular
1126+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1127+ mutex_lock(&pdx->io_mutex);
1128+ if (pdx->bIsUSB2) // Set flag for USB2 if appropriate
1129+ iReturn |= U14TF_USB2;
1130+ mutex_unlock(&pdx->io_mutex);
1131+
1132+ return iReturn;
1133+}
1134+
1135+/***************************************************************************
1136+** DbgCmd1401
1137+** Issues a debug\diagnostic command to the 1401 along with a 32-bit datum
1138+** This is a utility command used for dbg operations.
1139+*/
1140+static int DbgCmd1401(DEVICE_EXTENSION * pdx, unsigned char cmd,
1141+ unsigned int data)
1142+{
1143+ int iReturn;
1144+ dev_dbg(&pdx->interface->dev, "%s entry", __func__);
1145+ iReturn = usb_control_msg(pdx->udev, usb_sndctrlpipe(pdx->udev, 0), cmd, (H_TO_D | VENDOR | DEVREQ), (unsigned short)data, (unsigned short)(data >> 16), 0, 0, HZ); // allow 1 second timeout
1146+ if (iReturn < 0)
1147+ dev_err(&pdx->interface->dev, "%s fail code=%d", __func__,
1148+ iReturn);
1149+
1150+ return iReturn;
1151+}
1152+
1153+/****************************************************************************
1154+** DbgPeek
1155+**
1156+** Execute the diagnostic peek operation. Uses address, width and repeats.
1157+****************************************************************************/
1158+int DbgPeek(DEVICE_EXTENSION * pdx, TDBGBLOCK __user * pDB)
1159+{
1160+ int iReturn;
1161+ TDBGBLOCK db;
1162+
1163+ if (copy_from_user(&db, pDB, sizeof(db)))
1164+ return -EFAULT;
1165+
1166+ mutex_lock(&pdx->io_mutex);
1167+ dev_dbg(&pdx->interface->dev, "%s @ %08x", __func__, db.iAddr);
1168+
1169+ iReturn = DbgCmd1401(pdx, DB_SETADD, db.iAddr);
1170+ if (iReturn == U14ERR_NOERROR)
1171+ iReturn = DbgCmd1401(pdx, DB_WIDTH, db.iWidth);
1172+ if (iReturn == U14ERR_NOERROR)
1173+ iReturn = DbgCmd1401(pdx, DB_REPEATS, db.iRepeats);
1174+ if (iReturn == U14ERR_NOERROR)
1175+ iReturn = DbgCmd1401(pdx, DB_PEEK, 0);
1176+ mutex_unlock(&pdx->io_mutex);
1177+
1178+ return iReturn;
1179+}
1180+
1181+/****************************************************************************
1182+** DbgPoke
1183+**
1184+** Execute the diagnostic poke operation. Parameters are in the CSBLOCK struct
1185+** in order address, size, repeats and value to poke.
1186+****************************************************************************/
1187+int DbgPoke(DEVICE_EXTENSION * pdx, TDBGBLOCK __user * pDB)
1188+{
1189+ int iReturn;
1190+ TDBGBLOCK db;
1191+
1192+ if (copy_from_user(&db, pDB, sizeof(db)))
1193+ return -EFAULT;
1194+
1195+ mutex_lock(&pdx->io_mutex);
1196+ dev_dbg(&pdx->interface->dev, "%s @ %08x", __func__, db.iAddr);
1197+
1198+ iReturn = DbgCmd1401(pdx, DB_SETADD, db.iAddr);
1199+ if (iReturn == U14ERR_NOERROR)
1200+ iReturn = DbgCmd1401(pdx, DB_WIDTH, db.iWidth);
1201+ if (iReturn == U14ERR_NOERROR)
1202+ iReturn = DbgCmd1401(pdx, DB_REPEATS, db.iRepeats);
1203+ if (iReturn == U14ERR_NOERROR)
1204+ iReturn = DbgCmd1401(pdx, DB_POKE, db.iData);
1205+ mutex_unlock(&pdx->io_mutex);
1206+
1207+ return iReturn;
1208+}
1209+
1210+/****************************************************************************
1211+** DbgRampData
1212+**
1213+** Execute the diagnostic ramp data operation. Parameters are in the CSBLOCK struct
1214+** in order address, default, enable mask, size and repeats.
1215+****************************************************************************/
1216+int DbgRampData(DEVICE_EXTENSION * pdx, TDBGBLOCK __user * pDB)
1217+{
1218+ int iReturn;
1219+ TDBGBLOCK db;
1220+
1221+ if (copy_from_user(&db, pDB, sizeof(db)))
1222+ return -EFAULT;
1223+
1224+ mutex_lock(&pdx->io_mutex);
1225+ dev_dbg(&pdx->interface->dev, "%s @ %08x", __func__, db.iAddr);
1226+
1227+ iReturn = DbgCmd1401(pdx, DB_SETADD, db.iAddr);
1228+ if (iReturn == U14ERR_NOERROR)
1229+ iReturn = DbgCmd1401(pdx, DB_SETDEF, db.iDefault);
1230+ if (iReturn == U14ERR_NOERROR)
1231+ iReturn = DbgCmd1401(pdx, DB_SETMASK, db.iMask);
1232+ if (iReturn == U14ERR_NOERROR)
1233+ iReturn = DbgCmd1401(pdx, DB_WIDTH, db.iWidth);
1234+ if (iReturn == U14ERR_NOERROR)
1235+ iReturn = DbgCmd1401(pdx, DB_REPEATS, db.iRepeats);
1236+ if (iReturn == U14ERR_NOERROR)
1237+ iReturn = DbgCmd1401(pdx, DB_RAMPD, 0);
1238+ mutex_unlock(&pdx->io_mutex);
1239+
1240+ return iReturn;
1241+}
1242+
1243+/****************************************************************************
1244+** DbgRampAddr
1245+**
1246+** Execute the diagnostic ramp address operation
1247+****************************************************************************/
1248+int DbgRampAddr(DEVICE_EXTENSION * pdx, TDBGBLOCK __user * pDB)
1249+{
1250+ int iReturn;
1251+ TDBGBLOCK db;
1252+
1253+ if (copy_from_user(&db, pDB, sizeof(db)))
1254+ return -EFAULT;
1255+
1256+ mutex_lock(&pdx->io_mutex);
1257+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1258+
1259+ iReturn = DbgCmd1401(pdx, DB_SETDEF, db.iDefault);
1260+ if (iReturn == U14ERR_NOERROR)
1261+ iReturn = DbgCmd1401(pdx, DB_SETMASK, db.iMask);
1262+ if (iReturn == U14ERR_NOERROR)
1263+ iReturn = DbgCmd1401(pdx, DB_WIDTH, db.iWidth);
1264+ if (iReturn == U14ERR_NOERROR)
1265+ iReturn = DbgCmd1401(pdx, DB_REPEATS, db.iRepeats);
1266+ if (iReturn == U14ERR_NOERROR)
1267+ iReturn = DbgCmd1401(pdx, DB_RAMPA, 0);
1268+ mutex_unlock(&pdx->io_mutex);
1269+
1270+ return iReturn;
1271+}
1272+
1273+/****************************************************************************
1274+** DbgGetData
1275+**
1276+** Retrieve the data resulting from the last debug Peek operation
1277+****************************************************************************/
1278+int DbgGetData(DEVICE_EXTENSION * pdx, TDBGBLOCK __user * pDB)
1279+{
1280+ int iReturn;
1281+ TDBGBLOCK db;
1282+ memset(&db, 0, sizeof(db)); // fill returned block with 0s
1283+
1284+ mutex_lock(&pdx->io_mutex);
1285+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1286+
1287+ // Read back the last peeked value from the 1401.
1288+ iReturn = usb_control_msg(pdx->udev, usb_rcvctrlpipe(pdx->udev, 0),
1289+ DB_DATA, (D_TO_H | VENDOR | DEVREQ), 0, 0,
1290+ &db.iData, sizeof(db.iData), HZ);
1291+ if (iReturn == sizeof(db.iData)) {
1292+ if (copy_to_user(pDB, &db, sizeof(db)))
1293+ iReturn = -EFAULT;
1294+ else
1295+ iReturn = U14ERR_NOERROR;
1296+ } else
1297+ dev_err(&pdx->interface->dev, "%s failed, code %d", __func__,
1298+ iReturn);
1299+
1300+ mutex_unlock(&pdx->io_mutex);
1301+
1302+ return iReturn;
1303+}
1304+
1305+/****************************************************************************
1306+** DbgStopLoop
1307+**
1308+** Stop any never-ending debug loop, we just call Get1401State for USB
1309+**
1310+****************************************************************************/
1311+int DbgStopLoop(DEVICE_EXTENSION * pdx)
1312+{
1313+ int iReturn;
1314+ unsigned int uState, uErr;
1315+
1316+ mutex_lock(&pdx->io_mutex);
1317+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1318+ iReturn = Get1401State(pdx, &uState, &uErr);
1319+ mutex_unlock(&pdx->io_mutex);
1320+
1321+ return iReturn;
1322+}
1323+
1324+/****************************************************************************
1325+** SetCircular
1326+**
1327+** Sets up a transfer area record for circular transfers. If the area is
1328+** already set, we attempt to unset it. Unsetting will fail if the area is
1329+** booked and a transfer to that area is in progress. Otherwise, we will
1330+** release the area and re-assign it.
1331+****************************************************************************/
1332+int SetCircular(DEVICE_EXTENSION * pdx, TRANSFERDESC __user * pTD)
1333+{
1334+ int iReturn;
1335+ bool bToHost;
1336+ TRANSFERDESC td;
1337+
1338+ if (copy_from_user(&td, pTD, sizeof(td)))
1339+ return -EFAULT;
1340+
1341+ mutex_lock(&pdx->io_mutex);
1342+ dev_dbg(&pdx->interface->dev, "%s area:%d, size:%08x", __func__,
1343+ td.wAreaNum, td.dwLength);
1344+ bToHost = td.eSize != 0; // this is used as the tohost flag
1345+
1346+ // The strange cast is done so that we don't get warnings in 32-bit linux about the size of the
1347+ // pointer. The pointer is always passed as a 64-bit object so that we don't have problems using
1348+ // a 32-bit program on a 64-bit system. unsigned long is 64-bits on a 64-bit system.
1349+ iReturn =
1350+ SetArea(pdx, td.wAreaNum,
1351+ (char __user *)((unsigned long)td.lpvBuff), td.dwLength,
1352+ true, bToHost);
1353+ mutex_unlock(&pdx->io_mutex);
1354+ return iReturn;
1355+}
1356+
1357+/****************************************************************************
1358+** GetCircBlock
1359+**
1360+** Return the next available block of circularly-transferred data.
1361+****************************************************************************/
1362+int GetCircBlock(DEVICE_EXTENSION * pdx, TCIRCBLOCK __user * pCB)
1363+{
1364+ int iReturn = U14ERR_NOERROR;
1365+ unsigned int nArea;
1366+ TCIRCBLOCK cb;
1367+
1368+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1369+
1370+ if (copy_from_user(&cb, pCB, sizeof(cb)))
1371+ return -EFAULT;
1372+
1373+ mutex_lock(&pdx->io_mutex);
1374+
1375+ nArea = cb.nArea; // Retrieve parameters first
1376+ cb.dwOffset = 0; // set default result (nothing)
1377+ cb.dwSize = 0;
1378+
1379+ if (nArea < MAX_TRANSAREAS) // The area number must be OK
1380+ {
1381+ TRANSAREA *pArea = &pdx->rTransDef[nArea]; // Pointer to relevant info
1382+ spin_lock_irq(&pdx->stagedLock); // Lock others out
1383+
1384+ if ((pArea->bUsed) && (pArea->bCircular) && // Must be circular area
1385+ (pArea->bCircToHost)) // For now at least must be to host
1386+ {
1387+ if (pArea->aBlocks[0].dwSize > 0) // Got anything?
1388+ {
1389+ cb.dwOffset = pArea->aBlocks[0].dwOffset;
1390+ cb.dwSize = pArea->aBlocks[0].dwSize;
1391+ dev_dbg(&pdx->interface->dev,
1392+ "%s return block 0: %d bytes at %d",
1393+ __func__, cb.dwSize, cb.dwOffset);
1394+ }
1395+ } else
1396+ iReturn = U14ERR_NOTSET;
1397+
1398+ spin_unlock_irq(&pdx->stagedLock);
1399+ } else
1400+ iReturn = U14ERR_BADAREA;
1401+
1402+ if (copy_to_user(pCB, &cb, sizeof(cb)))
1403+ iReturn = -EFAULT;
1404+
1405+ mutex_unlock(&pdx->io_mutex);
1406+ return iReturn;
1407+}
1408+
1409+/****************************************************************************
1410+** FreeCircBlock
1411+**
1412+** Frees a block of circularly-transferred data and returns the next one.
1413+****************************************************************************/
1414+int FreeCircBlock(DEVICE_EXTENSION * pdx, TCIRCBLOCK __user * pCB)
1415+{
1416+ int iReturn = U14ERR_NOERROR;
1417+ unsigned int nArea, uStart, uSize;
1418+ TCIRCBLOCK cb;
1419+
1420+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1421+
1422+ if (copy_from_user(&cb, pCB, sizeof(cb)))
1423+ return -EFAULT;
1424+
1425+ mutex_lock(&pdx->io_mutex);
1426+
1427+ nArea = cb.nArea; // Retrieve parameters first
1428+ uStart = cb.dwOffset;
1429+ uSize = cb.dwSize;
1430+ cb.dwOffset = 0; // then set default result (nothing)
1431+ cb.dwSize = 0;
1432+
1433+ if (nArea < MAX_TRANSAREAS) // The area number must be OK
1434+ {
1435+ TRANSAREA *pArea = &pdx->rTransDef[nArea]; // Pointer to relevant info
1436+ spin_lock_irq(&pdx->stagedLock); // Lock others out
1437+
1438+ if ((pArea->bUsed) && (pArea->bCircular) && // Must be circular area
1439+ (pArea->bCircToHost)) // For now at least must be to host
1440+ {
1441+ bool bWaiting = false;
1442+
1443+ if ((pArea->aBlocks[0].dwSize >= uSize) && // Got anything?
1444+ (pArea->aBlocks[0].dwOffset == uStart)) // Must be legal data
1445+ {
1446+ pArea->aBlocks[0].dwSize -= uSize;
1447+ pArea->aBlocks[0].dwOffset += uSize;
1448+ if (pArea->aBlocks[0].dwSize == 0) // Have we emptied this block?
1449+ {
1450+ if (pArea->aBlocks[1].dwSize) // Is there a second block?
1451+ {
1452+ pArea->aBlocks[0] = pArea->aBlocks[1]; // Copy down block 2 data
1453+ pArea->aBlocks[1].dwSize = 0; // and mark the second block as unused
1454+ pArea->aBlocks[1].dwOffset = 0;
1455+ } else
1456+ pArea->aBlocks[0].dwOffset = 0;
1457+ }
1458+
1459+ dev_dbg(&pdx->interface->dev,
1460+ "%s free %d bytes at %d, return %d bytes at %d, wait=%d",
1461+ __func__, uSize, uStart,
1462+ pArea->aBlocks[0].dwSize,
1463+ pArea->aBlocks[0].dwOffset,
1464+ pdx->bXFerWaiting);
1465+
1466+ // Return the next available block of memory as well
1467+ if (pArea->aBlocks[0].dwSize > 0) // Got anything?
1468+ {
1469+ cb.dwOffset =
1470+ pArea->aBlocks[0].dwOffset;
1471+ cb.dwSize = pArea->aBlocks[0].dwSize;
1472+ }
1473+
1474+ bWaiting = pdx->bXFerWaiting;
1475+ if (bWaiting && pdx->bStagedUrbPending) {
1476+ dev_err(&pdx->interface->dev,
1477+ "%s ERROR: waiting xfer and staged Urb pending!",
1478+ __func__);
1479+ bWaiting = false;
1480+ }
1481+ } else {
1482+ dev_err(&pdx->interface->dev,
1483+ "%s ERROR: freeing %d bytes at %d, block 0 is %d bytes at %d",
1484+ __func__, uSize, uStart,
1485+ pArea->aBlocks[0].dwSize,
1486+ pArea->aBlocks[0].dwOffset);
1487+ iReturn = U14ERR_NOMEMORY;
1488+ }
1489+
1490+ // If we have one, kick off pending transfer
1491+ if (bWaiting) // Got a block xfer waiting?
1492+ {
1493+ int RWMStat =
1494+ ReadWriteMem(pdx, !pdx->rDMAInfo.bOutWard,
1495+ pdx->rDMAInfo.wIdent,
1496+ pdx->rDMAInfo.dwOffset,
1497+ pdx->rDMAInfo.dwSize);
1498+ if (RWMStat != U14ERR_NOERROR)
1499+ dev_err(&pdx->interface->dev,
1500+ "%s rw setup failed %d",
1501+ __func__, RWMStat);
1502+ }
1503+ } else
1504+ iReturn = U14ERR_NOTSET;
1505+
1506+ spin_unlock_irq(&pdx->stagedLock);
1507+ } else
1508+ iReturn = U14ERR_BADAREA;
1509+
1510+ if (copy_to_user(pCB, &cb, sizeof(cb)))
1511+ return -EFAULT;
1512+
1513+ mutex_unlock(&pdx->io_mutex);
1514+ return iReturn;
1515+}
drivers/staging/ced1401/ced_ioctl.h+345−0
@@ -0,0 +1,345 @@
1+/*
2+ * IOCTL calls for the CED1401 driver
3+ * Copyright (C) 2010 Cambridge Electronic Design Ltd
4+ * Author Greg P Smith (greg@ced.co.uk)
5+ *
6+ * This program is free software; you can redistribute it and/or
7+ * modify it under the terms of the GNU General Public License
8+ * as published by the Free Software Foundation; either version 2
9+ * of the License, or (at your option) any later version.
10+ *
11+ * This program is distributed in the hope that it will be useful,
12+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+ * GNU General Public License for more details.
15+ */
16+#ifndef __CED_IOCTL_H__
17+#define __CED_IOCTL_H__
18+
19+#include <linux/ioctl.h>
20+
21+/* dma modes, only MODE_CHAR and MODE_LINEAR are used in this driver */
22+#define MODE_CHAR 0
23+#define MODE_LINEAR 1
24+
25+/****************************************************************************
26+** TypeDefs
27+*****************************************************************************/
28+
29+typedef unsigned short TBLOCKENTRY; /* index the blk transfer table 0-7 */
30+
31+typedef struct TransferDesc {
32+ long long lpvBuff; /* address of transfer area (for 64 or 32 bit) */
33+ unsigned int dwLength; /* length of the area */
34+ TBLOCKENTRY wAreaNum; /* number of transfer area to set up */
35+ short eSize; /* element size - is tohost flag for circular */
36+} TRANSFERDESC;
37+
38+typedef TRANSFERDESC * LPTRANSFERDESC;
39+
40+typedef struct TransferEvent {
41+ unsigned int dwStart; /* offset into the area */
42+ unsigned int dwLength; /* length of the region */
43+ unsigned short wAreaNum; /* the area number */
44+ unsigned short wFlags; /* bit 0 set for toHost */
45+ int iSetEvent; /* could be dummy in LINUX */
46+} TRANSFEREVENT;
47+
48+#define MAX_TRANSFER_SIZE 0x4000 /* Maximum data bytes per IRP */
49+#define MAX_AREA_LENGTH 0x100000 /* Maximum size of transfer area */
50+#define MAX_TRANSAREAS 8 /* definitions for dma set up */
51+
52+typedef struct TGetSelfTest {
53+ int code; /* self-test error code */
54+ int x, y; /* additional information */
55+} TGET_SELFTEST;
56+
57+/* Debug block used for several commands. Not all fields are used for all commands. */
58+typedef struct TDbgBlock {
59+ int iAddr; /* the address in the 1401 */
60+ int iRepeats; /* number of repeats */
61+ int iWidth; /* width in bytes 1, 2, 4 */
62+ int iDefault; /* default value */
63+ int iMask; /* mask to apply */
64+ int iData; /* data for poke, result for peek */
65+} TDBGBLOCK;
66+
67+/* Used to collect information about a circular block from the device driver */
68+typedef struct TCircBlock {
69+ unsigned int nArea; /* the area to collect information from */
70+ unsigned int dwOffset; /* offset into the area to the available block */
71+ unsigned int dwSize; /* size of the area */
72+} TCIRCBLOCK;
73+
74+/* Used to clollect the 1401 status */
75+typedef struct TCSBlock {
76+ unsigned int uiState;
77+ unsigned int uiError;
78+} TCSBLOCK;
79+
80+/*
81+ * As seen by the user, an ioctl call looks like: int ioctl(int fd, unsigned
82+ * long cmd, char* argp); We will then have all sorts of variants on this that
83+ * can be used to pass stuff to our driver. We will generate macros for each
84+ * type of call so as to provide some sort of type safety in the calling:
85+ */
86+#define CED_MAGIC_IOC 0xce
87+
88+/* NBNB: READ and WRITE are from the point of view of the device, not user. */
89+typedef struct ced_ioc_string {
90+ int nChars;
91+ char buffer[256];
92+} CED_IOC_STRING;
93+
94+#define IOCTL_CED_SENDSTRING(n) _IOC(_IOC_WRITE, CED_MAGIC_IOC, 2, n)
95+
96+#define IOCTL_CED_RESET1401 _IO(CED_MAGIC_IOC, 3)
97+#define IOCTL_CED_GETCHAR _IO(CED_MAGIC_IOC, 4)
98+#define IOCTL_CED_SENDCHAR _IO(CED_MAGIC_IOC, 5)
99+#define IOCTL_CED_STAT1401 _IO(CED_MAGIC_IOC, 6)
100+#define IOCTL_CED_LINECOUNT _IO(CED_MAGIC_IOC, 7)
101+#define IOCTL_CED_GETSTRING(nMax) _IOC(_IOC_READ, CED_MAGIC_IOC, 8, nMax)
102+
103+#define IOCTL_CED_SETTRANSFER _IOW(CED_MAGIC_IOC, 11, TRANSFERDESC)
104+#define IOCTL_CED_UNSETTRANSFER _IO(CED_MAGIC_IOC, 12)
105+#define IOCTL_CED_SETEVENT _IOW(CED_MAGIC_IOC, 13, TRANSFEREVENT)
106+#define IOCTL_CED_GETOUTBUFSPACE _IO(CED_MAGIC_IOC, 14)
107+#define IOCTL_CED_GETBASEADDRESS _IO(CED_MAGIC_IOC, 15)
108+#define IOCTL_CED_GETDRIVERREVISION _IO(CED_MAGIC_IOC, 16)
109+
110+#define IOCTL_CED_GETTRANSFER _IOR(CED_MAGIC_IOC, 17, TGET_TX_BLOCK)
111+#define IOCTL_CED_KILLIO1401 _IO(CED_MAGIC_IOC, 18)
112+#define IOCTL_CED_BLKTRANSSTATE _IO(CED_MAGIC_IOC, 19)
113+
114+#define IOCTL_CED_STATEOF1401 _IO(CED_MAGIC_IOC, 23)
115+#define IOCTL_CED_GRAB1401 _IO(CED_MAGIC_IOC, 25)
116+#define IOCTL_CED_FREE1401 _IO(CED_MAGIC_IOC, 26)
117+#define IOCTL_CED_STARTSELFTEST _IO(CED_MAGIC_IOC, 31)
118+#define IOCTL_CED_CHECKSELFTEST _IOR(CED_MAGIC_IOC, 32, TGET_SELFTEST)
119+#define IOCTL_CED_TYPEOF1401 _IO(CED_MAGIC_IOC, 33)
120+#define IOCTL_CED_TRANSFERFLAGS _IO(CED_MAGIC_IOC, 34)
121+
122+#define IOCTL_CED_DBGPEEK _IOW(CED_MAGIC_IOC, 35, TDBGBLOCK)
123+#define IOCTL_CED_DBGPOKE _IOW(CED_MAGIC_IOC, 36, TDBGBLOCK)
124+#define IOCTL_CED_DBGRAMPDATA _IOW(CED_MAGIC_IOC, 37, TDBGBLOCK)
125+#define IOCTL_CED_DBGRAMPADDR _IOW(CED_MAGIC_IOC, 38, TDBGBLOCK)
126+#define IOCTL_CED_DBGGETDATA _IOR(CED_MAGIC_IOC, 39, TDBGBLOCK)
127+#define IOCTL_CED_DBGSTOPLOOP _IO(CED_MAGIC_IOC, 40)
128+#define IOCTL_CED_FULLRESET _IO(CED_MAGIC_IOC, 41)
129+#define IOCTL_CED_SETCIRCULAR _IOW(CED_MAGIC_IOC, 42, TRANSFERDESC)
130+#define IOCTL_CED_GETCIRCBLOCK _IOWR(CED_MAGIC_IOC, 43, TCIRCBLOCK)
131+#define IOCTL_CED_FREECIRCBLOCK _IOWR(CED_MAGIC_IOC, 44, TCIRCBLOCK)
132+#define IOCTL_CED_WAITEVENT _IO(CED_MAGIC_IOC, 45)
133+#define IOCTL_CED_TESTEVENT _IO(CED_MAGIC_IOC, 46)
134+
135+#ifndef __KERNEL__
136+/*
137+ * If nothing said about return value, it is a U14ERR_... error code
138+ * (U14ERR_NOERROR for none)
139+ */
140+inline int CED_SendString(int fh, const char *szText, int n)
141+{
142+ return ioctl(fh, IOCTL_CED_SENDSTRING(n), szText);
143+}
144+
145+inline int CED_Reset1401(int fh)
146+{
147+ return ioctl(fh, IOCTL_CED_RESET1401);
148+}
149+
150+/* Return the singe character or a -ve error code. */
151+inline int CED_GetChar(int fh)
152+{
153+ return ioctl(fh, IOCTL_CED_GETCHAR);
154+}
155+
156+/* Return character count in input buffer */
157+inline int CED_Stat1401(int fh)
158+{
159+ return ioctl(fh, IOCTL_CED_STAT1401);
160+}
161+
162+inline int CED_SendChar(int fh, char c)
163+{
164+ return ioctl(fh, IOCTL_CED_SENDCHAR, c);
165+}
166+
167+inline int CED_LineCount(int fh)
168+{
169+ return ioctl(fh, IOCTL_CED_LINECOUNT);
170+}
171+
172+/*
173+ * return the count of characters returned. If the string was terminated by CR
174+ * or 0, then the 0 is part of the count. Otherwise, we will add a zero if
175+ * there is room, but it is not included in the count. The return value is 0
176+ * if there was nothing to read.
177+ */
178+inline int CED_GetString(int fh, char *szText, int nMax)
179+{
180+ return ioctl(fh, IOCTL_CED_GETSTRING(nMax), szText);
181+}
182+
183+/* returns space in the output buffer. */
184+inline int CED_GetOutBufSpace(int fh)
185+{
186+ return ioctl(fh, IOCTL_CED_GETOUTBUFSPACE);
187+}
188+
189+/* This always returns -1 as not implemented. */
190+inline int CED_GetBaseAddress(int fh)
191+{
192+ return ioctl(fh, IOCTL_CED_GETBASEADDRESS);
193+}
194+
195+/* returns the major revision <<16 | minor revision. */
196+inline int CED_GetDriverRevision(int fh)
197+{
198+ return ioctl(fh, IOCTL_CED_GETDRIVERREVISION);
199+}
200+
201+inline int CED_SetTransfer(int fh, TRANSFERDESC *pTD)
202+{
203+ return ioctl(fh, IOCTL_CED_SETTRANSFER, pTD);
204+}
205+
206+inline int CED_UnsetTransfer(int fh, int nArea)
207+{
208+ return ioctl(fh, IOCTL_CED_UNSETTRANSFER, nArea);
209+}
210+
211+inline int CED_SetEvent(int fh, TRANSFEREVENT *pTE)
212+{
213+ return ioctl(fh, IOCTL_CED_SETEVENT, pTE);
214+}
215+
216+inline int CED_GetTransfer(int fh, TGET_TX_BLOCK *pTX)
217+{
218+ return ioctl(fh, IOCTL_CED_GETTRANSFER, pTX);
219+}
220+
221+inline int CED_KillIO1401(int fh)
222+{
223+ return ioctl(fh, IOCTL_CED_KILLIO1401);
224+}
225+
226+/* returns 0 if no active DMA, 1 if active */
227+inline int CED_BlkTransState(int fh)
228+{
229+ return ioctl(fh, IOCTL_CED_BLKTRANSSTATE);
230+}
231+
232+inline int CED_StateOf1401(int fh)
233+{
234+ return ioctl(fh, IOCTL_CED_STATEOF1401);
235+}
236+
237+inline int CED_Grab1401(int fh)
238+{
239+ return ioctl(fh, IOCTL_CED_GRAB1401);
240+}
241+
242+inline int CED_Free1401(int fh)
243+{
244+ return ioctl(fh, IOCTL_CED_FREE1401);
245+}
246+
247+inline int CED_StartSelfTest(int fh)
248+{
249+ return ioctl(fh, IOCTL_CED_STARTSELFTEST);
250+}
251+
252+inline int CED_CheckSelfTest(int fh, TGET_SELFTEST *pGST)
253+{
254+ return ioctl(fh, IOCTL_CED_CHECKSELFTEST, pGST);
255+}
256+
257+inline int CED_TypeOf1401(int fh)
258+{
259+ return ioctl(fh, IOCTL_CED_TYPEOF1401);
260+}
261+
262+inline int CED_TransferFlags(int fh)
263+{
264+ return ioctl(fh, IOCTL_CED_TRANSFERFLAGS);
265+}
266+
267+inline int CED_DbgPeek(int fh, TDBGBLOCK *pDB)
268+{
269+ return ioctl(fh, IOCTL_CED_DBGPEEK, pDB);
270+}
271+
272+inline int CED_DbgPoke(int fh, TDBGBLOCK *pDB)
273+{
274+ return ioctl(fh, IOCTL_CED_DBGPOKE, pDB);
275+}
276+
277+inline int CED_DbgRampData(int fh, TDBGBLOCK *pDB)
278+{
279+ return ioctl(fh, IOCTL_CED_DBGRAMPDATA, pDB);
280+}
281+
282+inline int CED_DbgRampAddr(int fh, TDBGBLOCK *pDB)
283+{
284+ return ioctl(fh, IOCTL_CED_DBGRAMPADDR, pDB);
285+}
286+
287+inline int CED_DbgGetData(int fh, TDBGBLOCK *pDB)
288+{
289+ return ioctl(fh, IOCTL_CED_DBGGETDATA, pDB);
290+}
291+
292+inline int CED_DbgStopLoop(int fh)
293+{
294+ return ioctl(fh, IOCTL_CED_DBGSTOPLOOP);
295+}
296+
297+inline int CED_FullReset(int fh)
298+{
299+ return ioctl(fh, IOCTL_CED_FULLRESET);
300+}
301+
302+inline int CED_SetCircular(int fh, TRANSFERDESC *pTD)
303+{
304+ return ioctl(fh, IOCTL_CED_SETCIRCULAR, pTD);
305+}
306+
307+inline int CED_GetCircBlock(int fh, TCIRCBLOCK *pCB)
308+{
309+ return ioctl(fh, IOCTL_CED_GETCIRCBLOCK, pCB);
310+}
311+
312+inline int CED_FreeCircBlock(int fh, TCIRCBLOCK *pCB)
313+{
314+ return ioctl(fh, IOCTL_CED_FREECIRCBLOCK, pCB);
315+}
316+
317+inline int CED_WaitEvent(int fh, int nArea, int msTimeOut)
318+{
319+ return ioctl(fh, IOCTL_CED_WAITEVENT, (nArea & 0xff)|(msTimeOut << 8));
320+}
321+
322+inline int CED_TestEvent(int fh, int nArea)
323+{
324+ return ioctl(fh, IOCTL_CED_TESTEVENT, nArea);
325+}
326+#endif
327+
328+#ifdef NOTWANTEDYET
329+#define IOCTL_CED_REGCALLBACK _IO(CED_MAGIC_IOC, 9) /* Not used */
330+#define IOCTL_CED_GETMONITORBUF _IO(CED_MAGIC_IOC, 10) /* Not used */
331+
332+#define IOCTL_CED_BYTECOUNT _IO(CED_MAGIC_IOC, 20) /* Not used */
333+#define IOCTL_CED_ZEROBLOCKCOUNT _IO(CED_MAGIC_IOC, 21) /* Not used */
334+#define IOCTL_CED_STOPCIRCULAR _IO(CED_MAGIC_IOC, 22) /* Not used */
335+
336+#define IOCTL_CED_REGISTERS1401 _IO(CED_MAGIC_IOC, 24) /* Not used */
337+#define IOCTL_CED_STEP1401 _IO(CED_MAGIC_IOC, 27) /* Not used */
338+#define IOCTL_CED_SET1401REGISTERS _IO(CED_MAGIC_IOC, 28) /* Not used */
339+#define IOCTL_CED_STEPTILL1401 _IO(CED_MAGIC_IOC, 29) /* Not used */
340+#define IOCTL_CED_SETORIN _IO(CED_MAGIC_IOC, 30) /* Not used */
341+
342+#endif
343+
344+/* __CED_IOCTL_H__ */
345+#endif
drivers/staging/ced1401/machine.h+127−0
@@ -0,0 +1,127 @@
1+/*****************************************************************************
2+**
3+** machine.h
4+**
5+** Copyright (c) Cambridge Electronic Design Limited 1991,1992,2010
6+**
7+** This program is free software; you can redistribute it and/or
8+** modify it under the terms of the GNU General Public License
9+** as published by the Free Software Foundation; either version 2
10+** of the License, or (at your option) any later version.
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+** You should have received a copy of the GNU General Public License
18+** along with this program; if not, write to the Free Software
19+** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20+**
21+** Contact CED: Cambridge Electronic Design Limited, Science Park, Milton Road
22+** Cambridge, CB6 0FE.
23+** www.ced.co.uk
24+** greg@ced.co.uk
25+**
26+** This file is included at the start of 'C' or 'C++' source file to define
27+** things for cross-platform/compiler interoperability. This used to deal with
28+** MSDOS/16-bit stuff, but this was all removed in Decemeber 2010. There are
29+** three things to consider: Windows, LINUX, mac OSX (BSD Unix) and 32 vs 64
30+** bit. At the time of writing (DEC 2010) there is a consensus on the following
31+** and their unsigned equivalents:
32+**
33+** type bits
34+** char 8
35+** short 16
36+** int 32
37+** long long 64
38+**
39+** long is a problem as it is always 64 bits on linux/unix and is always 32 bits
40+** on windows.
41+** On windows, we define _IS_WINDOWS_ and one of WIN32 or WIN64.
42+** On linux we define LINUX
43+** On Max OSX we define MACOSX
44+**
45+*/
46+
47+#ifndef __MACHINE_H__
48+#define __MACHINE_H__
49+#ifndef __KERNEL__
50+#include <float.h>
51+#include <limits.h>
52+#endif
53+
54+/*
55+** The initial section is to identify the operating system
56+*/
57+#if (defined(__linux__) || defined(_linux) || defined(__linux)) && !defined(LINUX)
58+#define LINUX 1
59+#endif
60+
61+#if (defined(__WIN32__) || defined(_WIN32)) && !defined(WIN32)
62+#define WIN32 1
63+#endif
64+
65+#if defined(__APPLE__)
66+#define MACOSX
67+#endif
68+
69+#if defined(_WIN64)
70+#undef WIN32
71+#undef WIN64
72+#define WIN64 1
73+#endif
74+
75+#if defined(WIN32) || defined(WIN64)
76+#define _IS_WINDOWS_ 1
77+#endif
78+
79+#if defined(LINUX) || defined(MAXOSX)
80+ #define FAR
81+
82+ typedef int BOOL; // To match Windows
83+ typedef char * LPSTR;
84+ typedef const char * LPCSTR;
85+ typedef unsigned short WORD;
86+ typedef unsigned int DWORD;
87+ typedef unsigned char BYTE;
88+ typedef BYTE BOOLEAN;
89+ typedef unsigned char UCHAR;
90+ #define __packed __attribute__((packed))
91+ typedef BYTE * LPBYTE;
92+ #define HIWORD(x) (WORD)(((x)>>16) & 0xffff)
93+ #define LOWORD(x) (WORD)((x) & 0xffff)
94+#endif
95+
96+#ifdef _IS_WINDOWS_
97+#include <windows.h>
98+#define __packed
99+#endif
100+
101+/*
102+** Sort out the DllExport and DllImport macros. The GCC compiler has its own
103+** syntax for this, though it also supports the MS specific __declspec() as
104+** a synonym.
105+*/
106+#ifdef GNUC
107+ #define DllExport __attribute__((dllexport))
108+ #define DllImport __attribute__((dllimport))
109+#endif
110+
111+#ifndef DllExport
112+#ifdef _IS_WINDOWS_
113+ #define DllExport __declspec(dllexport)
114+ #define DllImport __declspec(dllimport)
115+#else
116+ #define DllExport
117+ #define DllImport
118+#endif
119+#endif /* _IS_WINDOWS_ */
120+
121+
122+#ifndef TRUE
123+ #define TRUE 1
124+ #define FALSE 0
125+#endif
126+
127+#endif
drivers/staging/ced1401/usb1401.c+1637−0
@@ -0,0 +1,1637 @@
1+/***********************************************************************************
2+ CED1401 usb driver. This basic loading is based on the usb-skeleton.c code that is:
3+ Copyright (C) 2001-2004 Greg Kroah-Hartman (greg@kroah.com)
4+ Copyright (C) 2012 Alois Schloegl <alois.schloegl@ist.ac.at>
5+ There is not a great deal of the skeleton left.
6+
7+ All the remainder dealing specifically with the CED1401 is based on drivers written
8+ by CED for other systems (mainly Windows) and is:
9+ Copyright (C) 2010 Cambridge Electronic Design Ltd
10+ Author Greg P Smith (greg@ced.co.uk)
11+
12+ This program is free software; you can redistribute it and/or
13+ modify it under the terms of the GNU General Public License
14+ as published by the Free Software Foundation; either version 2
15+ of the License, or (at your option) any later version.
16+
17+ This program is distributed in the hope that it will be useful,
18+ but WITHOUT ANY WARRANTY; without even the implied warranty of
19+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20+ GNU General Public License for more details.
21+
22+ You should have received a copy of the GNU General Public License
23+ along with this program; if not, write to the Free Software
24+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
25+
26+Endpoints
27+*********
28+There are 4 endpoints plus the control endpoint in the standard interface
29+provided by most 1401s. The control endpoint is used for standard USB requests,
30+plus various CED-specific transactions such as start self test, debug and get
31+the 1401 status. The other endpoints are:
32+
33+ 1 Characters to the 1401
34+ 2 Characters from the 1401
35+ 3 Block data to the 1401
36+ 4 Block data to the host.
37+
38+inside the driver these are indexed as an array from 0 to 3, transactions
39+over the control endpoint are carried out using a separate mechanism. The
40+use of the endpoints is mostly straightforward, with the driver issuing
41+IO request packets (IRPs) as required to transfer data to and from the 1401.
42+The handling of endpoint 2 is different because it is used for characters
43+from the 1401, which can appear spontaneously and without any other driver
44+activity - for example to repeatedly request DMA transfers in Spike2. The
45+desired effect is achieved by using an interrupt endpoint which can be
46+polled to see if it has data available, and writing the driver so that it
47+always maintains a pending read IRP from that endpoint which will read the
48+character data and terminate as soon as the 1401 makes data available. This
49+works very well, some care is taken with when you kick off this character
50+read IRP to avoid it being active when it is not wanted but generally it
51+is running all the time.
52+
53+In the 2270, there are only three endpoints plus the control endpoint. In
54+addition to the transactions mentioned above, the control endpoint is used
55+to transfer character data to the 1401. The other endpoints are used as:
56+
57+ 1 Characters from the 1401
58+ 2 Block data to the 1401
59+ 3 Block data to the host.
60+
61+The type of interface available is specified by the interface subclass field
62+in the interface descriptor provided by the 1401. See the USB_INT_ constants
63+for the values that this field can hold.
64+
65+****************************************************************************
66+Linux implementation
67+
68+Although Linux Device Drivers (3rd Edition) was a major source of information,
69+it is very out of date. A lot of information was gleaned from the latest
70+usb_skeleton.c code (you need to download the kernel sources to get this).
71+
72+To match the Windows version, everything is done using ioctl calls. All the
73+device state is held in the DEVICE_EXTENSION (named to match Windows use).
74+Block transfers are done by using get_user_pages() to pin down a list of
75+pages that we hold a pointer to in the device driver. We also allocate a
76+coherent transfer buffer of size STAGED_SZ (this must be a multiple of the
77+bulk endpoint size so that the 1401 does not realise that we break large
78+transfers down into smaller pieces). We use kmap_atomic() to get a kernel
79+va for each page, as it is required, for copying; see CopyUserSpace().
80+
81+All character and data transfers are done using asynchronous IO. All Urbs are
82+tracked by anchoring them. Status and debug ioctls are implemented with the
83+synchronous non-Urb based transfers.
84+*/
85+
86+#include <linux/kernel.h>
87+#include <linux/errno.h>
88+#include <linux/usb.h>
89+#include <linux/mutex.h>
90+#include <linux/mm.h>
91+#include <linux/highmem.h>
92+#include <linux/version.h>
93+#if ( LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35) )
94+#include <linux/init.h>
95+#include <linux/slab.h>
96+#include <linux/module.h>
97+#include <linux/kref.h>
98+#include <linux/uaccess.h>
99+#endif
100+
101+#include "usb1401.h"
102+
103+/* Define these values to match your devices */
104+#define USB_CED_VENDOR_ID 0x0525
105+#define USB_CED_PRODUCT_ID 0xa0f0
106+
107+/* table of devices that work with this driver */
108+static const struct usb_device_id ced_table[] = {
109+ {USB_DEVICE(USB_CED_VENDOR_ID, USB_CED_PRODUCT_ID)},
110+ {} /* Terminating entry */
111+};
112+
113+MODULE_DEVICE_TABLE(usb, ced_table);
114+
115+/* Get a minor range for your devices from the usb maintainer */
116+#define USB_CED_MINOR_BASE 192
117+
118+/* our private defines. if this grows any larger, use your own .h file */
119+#define MAX_TRANSFER (PAGE_SIZE - 512)
120+/* MAX_TRANSFER is chosen so that the VM is not stressed by
121+ allocations > PAGE_SIZE and the number of packets in a page
122+ is an integer 512 is the largest possible packet on EHCI */
123+#define WRITES_IN_FLIGHT 8
124+/* arbitrarily chosen */
125+
126+/*
127+The cause for these errors is that the driver makes use of the functions usb_buffer_alloc() and usb_buffer_free() which got renamed in kernel 2.6.35. This is stated in the Changelog: USB: rename usb_buffer_alloc() and usb_buffer_free() users
128+ For more clearance what the functions actually do,
129+ usb_buffer_alloc() is renamed to usb_alloc_coherent()
130+ usb_buffer_free() is renamed to usb_free_coherent()
131+ This is needed on Debian 2.6.32-5-amd64
132+*/
133+#if ( LINUX_VERSION_CODE < KERNEL_VERSION(2,6,35) )
134+#define usb_alloc_coherent usb_buffer_alloc
135+#define usb_free_coherent usb_buffer_free
136+#define noop_llseek NULL
137+#endif
138+
139+static struct usb_driver ced_driver;
140+
141+static void ced_delete(struct kref *kref)
142+{
143+ DEVICE_EXTENSION *pdx = to_DEVICE_EXTENSION(kref);
144+
145+ // Free up the output buffer, then free the output urb. Note that the interface member
146+ // of pdx will probably be NULL, so cannot be used to get to dev.
147+ usb_free_coherent(pdx->udev, OUTBUF_SZ, pdx->pCoherCharOut,
148+ pdx->pUrbCharOut->transfer_dma);
149+ usb_free_urb(pdx->pUrbCharOut);
150+
151+ // Do the same for chan input
152+ usb_free_coherent(pdx->udev, INBUF_SZ, pdx->pCoherCharIn,
153+ pdx->pUrbCharIn->transfer_dma);
154+ usb_free_urb(pdx->pUrbCharIn);
155+
156+ // Do the same for the block transfers
157+ usb_free_coherent(pdx->udev, STAGED_SZ, pdx->pCoherStagedIO,
158+ pdx->pStagedUrb->transfer_dma);
159+ usb_free_urb(pdx->pStagedUrb);
160+
161+ usb_put_dev(pdx->udev);
162+ kfree(pdx);
163+}
164+
165+// This is the driver end of the open() call from user space.
166+static int ced_open(struct inode *inode, struct file *file)
167+{
168+ DEVICE_EXTENSION *pdx;
169+ int retval = 0;
170+ int subminor = iminor(inode);
171+ struct usb_interface *interface =
172+ usb_find_interface(&ced_driver, subminor);
173+ if (!interface) {
174+ pr_err("%s - error, can't find device for minor %d", __func__,
175+ subminor);
176+ retval = -ENODEV;
177+ goto exit;
178+ }
179+
180+ pdx = usb_get_intfdata(interface);
181+ if (!pdx) {
182+ retval = -ENODEV;
183+ goto exit;
184+ }
185+
186+ dev_dbg(&interface->dev, "%s got pdx", __func__);
187+
188+ /* increment our usage count for the device */
189+ kref_get(&pdx->kref);
190+
191+ /* lock the device to allow correctly handling errors
192+ * in resumption */
193+ mutex_lock(&pdx->io_mutex);
194+
195+ if (!pdx->open_count++) {
196+ retval = usb_autopm_get_interface(interface);
197+ if (retval) {
198+ pdx->open_count--;
199+ mutex_unlock(&pdx->io_mutex);
200+ kref_put(&pdx->kref, ced_delete);
201+ goto exit;
202+ }
203+ } else { //uncomment this block if you want exclusive open
204+ dev_err(&interface->dev, "%s fail: already open", __func__);
205+ retval = -EBUSY;
206+ pdx->open_count--;
207+ mutex_unlock(&pdx->io_mutex);
208+ kref_put(&pdx->kref, ced_delete);
209+ goto exit;
210+ }
211+ /* prevent the device from being autosuspended */
212+
213+ /* save our object in the file's private structure */
214+ file->private_data = pdx;
215+ mutex_unlock(&pdx->io_mutex);
216+
217+exit:
218+ return retval;
219+}
220+
221+static int ced_release(struct inode *inode, struct file *file)
222+{
223+ DEVICE_EXTENSION *pdx = file->private_data;
224+ if (pdx == NULL)
225+ return -ENODEV;
226+
227+ dev_dbg(&pdx->interface->dev, "%s called", __func__);
228+ mutex_lock(&pdx->io_mutex);
229+ if (!--pdx->open_count && pdx->interface) // Allow autosuspend
230+ usb_autopm_put_interface(pdx->interface);
231+ mutex_unlock(&pdx->io_mutex);
232+
233+ kref_put(&pdx->kref, ced_delete); // decrement the count on our device
234+ return 0;
235+}
236+
237+static int ced_flush(struct file *file, fl_owner_t id)
238+{
239+ int res;
240+ DEVICE_EXTENSION *pdx = file->private_data;
241+ if (pdx == NULL)
242+ return -ENODEV;
243+
244+ dev_dbg(&pdx->interface->dev, "%s char in pend=%d", __func__,
245+ pdx->bReadCharsPending);
246+
247+ /* wait for io to stop */
248+ mutex_lock(&pdx->io_mutex);
249+ dev_dbg(&pdx->interface->dev, "%s got io_mutex", __func__);
250+ ced_draw_down(pdx);
251+
252+ /* read out errors, leave subsequent opens a clean slate */
253+ spin_lock_irq(&pdx->err_lock);
254+ res = pdx->errors ? (pdx->errors == -EPIPE ? -EPIPE : -EIO) : 0;
255+ pdx->errors = 0;
256+ spin_unlock_irq(&pdx->err_lock);
257+
258+ mutex_unlock(&pdx->io_mutex);
259+ dev_dbg(&pdx->interface->dev, "%s exit reached", __func__);
260+
261+ return res;
262+}
263+
264+/***************************************************************************
265+** CanAcceptIoRequests
266+** If the device is removed, interface is set NULL. We also clear our pointer
267+** from the interface, so we should make sure that pdx is not NULL. This will
268+** not help with a device extension held by a file.
269+** return true if can accept new io requests, else false
270+*/
271+static bool CanAcceptIoRequests(DEVICE_EXTENSION * pdx)
272+{
273+ return pdx && pdx->interface; // Can we accept IO requests
274+}
275+
276+/****************************************************************************
277+** Callback routine to complete writes. This may need to fire off another
278+** urb to complete the transfer.
279+****************************************************************************/
280+static void ced_writechar_callback(struct urb *pUrb)
281+{
282+ DEVICE_EXTENSION *pdx = pUrb->context;
283+ int nGot = pUrb->actual_length; // what we transferred
284+
285+ if (pUrb->status) { // sync/async unlink faults aren't errors
286+ if (!
287+ (pUrb->status == -ENOENT || pUrb->status == -ECONNRESET
288+ || pUrb->status == -ESHUTDOWN)) {
289+ dev_err(&pdx->interface->dev,
290+ "%s - nonzero write bulk status received: %d",
291+ __func__, pUrb->status);
292+ }
293+
294+ spin_lock(&pdx->err_lock);
295+ pdx->errors = pUrb->status;
296+ spin_unlock(&pdx->err_lock);
297+ nGot = 0; // and tidy up again if so
298+
299+ spin_lock(&pdx->charOutLock); // already at irq level
300+ pdx->dwOutBuffGet = 0; // Reset the output buffer
301+ pdx->dwOutBuffPut = 0;
302+ pdx->dwNumOutput = 0; // Clear the char count
303+ pdx->bPipeError[0] = 1; // Flag an error for later
304+ pdx->bSendCharsPending = false; // Allow other threads again
305+ spin_unlock(&pdx->charOutLock); // already at irq level
306+ dev_dbg(&pdx->interface->dev,
307+ "%s - char out done, 0 chars sent", __func__);
308+ } else {
309+ dev_dbg(&pdx->interface->dev,
310+ "%s - char out done, %d chars sent", __func__, nGot);
311+ spin_lock(&pdx->charOutLock); // already at irq level
312+ pdx->dwNumOutput -= nGot; // Now adjust the char send buffer
313+ pdx->dwOutBuffGet += nGot; // to match what we did
314+ if (pdx->dwOutBuffGet >= OUTBUF_SZ) // Can't do this any earlier as data could be overwritten
315+ pdx->dwOutBuffGet = 0;
316+
317+ if (pdx->dwNumOutput > 0) // if more to be done...
318+ {
319+ int nPipe = 0; // The pipe number to use
320+ int iReturn;
321+ char *pDat = &pdx->outputBuffer[pdx->dwOutBuffGet];
322+ unsigned int dwCount = pdx->dwNumOutput; // maximum to send
323+ if ((pdx->dwOutBuffGet + dwCount) > OUTBUF_SZ) // does it cross buffer end?
324+ dwCount = OUTBUF_SZ - pdx->dwOutBuffGet;
325+ spin_unlock(&pdx->charOutLock); // we are done with stuff that changes
326+ memcpy(pdx->pCoherCharOut, pDat, dwCount); // copy output data to the buffer
327+ usb_fill_bulk_urb(pdx->pUrbCharOut, pdx->udev,
328+ usb_sndbulkpipe(pdx->udev,
329+ pdx->epAddr[0]),
330+ pdx->pCoherCharOut, dwCount,
331+ ced_writechar_callback, pdx);
332+ pdx->pUrbCharOut->transfer_flags |=
333+ URB_NO_TRANSFER_DMA_MAP;
334+ usb_anchor_urb(pdx->pUrbCharOut, &pdx->submitted); // in case we need to kill it
335+ iReturn = usb_submit_urb(pdx->pUrbCharOut, GFP_ATOMIC);
336+ dev_dbg(&pdx->interface->dev, "%s n=%d>%s<", __func__,
337+ dwCount, pDat);
338+ spin_lock(&pdx->charOutLock); // grab lock for errors
339+ if (iReturn) {
340+ pdx->bPipeError[nPipe] = 1; // Flag an error to be handled later
341+ pdx->bSendCharsPending = false; // Allow other threads again
342+ usb_unanchor_urb(pdx->pUrbCharOut);
343+ dev_err(&pdx->interface->dev,
344+ "%s usb_submit_urb() returned %d",
345+ __func__, iReturn);
346+ }
347+ } else
348+ pdx->bSendCharsPending = false; // Allow other threads again
349+ spin_unlock(&pdx->charOutLock); // already at irq level
350+ }
351+}
352+
353+/****************************************************************************
354+** SendChars
355+** Transmit the characters in the output buffer to the 1401. This may need
356+** breaking down into multiple transfers.
357+****************************************************************************/
358+int SendChars(DEVICE_EXTENSION * pdx)
359+{
360+ int iReturn = U14ERR_NOERROR;
361+
362+ spin_lock_irq(&pdx->charOutLock); // Protect ourselves
363+
364+ if ((!pdx->bSendCharsPending) && // Not currently sending
365+ (pdx->dwNumOutput > 0) && // has characters to output
366+ (CanAcceptIoRequests(pdx))) // and current activity is OK
367+ {
368+ unsigned int dwCount = pdx->dwNumOutput; // Get a copy of the character count
369+ pdx->bSendCharsPending = true; // Set flag to lock out other threads
370+
371+ dev_dbg(&pdx->interface->dev,
372+ "Send %d chars to 1401, EP0 flag %d\n", dwCount,
373+ pdx->nPipes == 3);
374+ // If we have only 3 end points we must send the characters to the 1401 using EP0.
375+ if (pdx->nPipes == 3) {
376+ // For EP0 character transmissions to the 1401, we have to hang about until they
377+ // are gone, as otherwise without more character IO activity they will never go.
378+ unsigned int count = dwCount; // Local char counter
379+ unsigned int index = 0; // The index into the char buffer
380+
381+ spin_unlock_irq(&pdx->charOutLock); // Free spinlock as we call USBD
382+
383+ while ((count > 0) && (iReturn == U14ERR_NOERROR)) {
384+ // We have to break the transfer up into 64-byte chunks because of a 2270 problem
385+ int n = count > 64 ? 64 : count; // Chars for this xfer, max of 64
386+ int nSent = usb_control_msg(pdx->udev,
387+ usb_sndctrlpipe(pdx->udev, 0), // use end point 0
388+ DB_CHARS, // bRequest
389+ (H_TO_D | VENDOR | DEVREQ), // to the device, vendor request to the device
390+ 0, 0, // value and index are both 0
391+ &pdx->outputBuffer[index], // where to send from
392+ n, // how much to send
393+ 1000); // timeout in jiffies
394+ if (nSent <= 0) {
395+ iReturn = nSent ? nSent : -ETIMEDOUT; // if 0 chars says we timed out
396+ dev_err(&pdx->interface->dev,
397+ "Send %d chars by EP0 failed: %d",
398+ n, iReturn);
399+ } else {
400+ dev_dbg(&pdx->interface->dev,
401+ "Sent %d chars by EP0", n);
402+ count -= nSent;
403+ index += nSent;
404+ }
405+ }
406+
407+ spin_lock_irq(&pdx->charOutLock); // Protect pdx changes, released by general code
408+ pdx->dwOutBuffGet = 0; // so reset the output buffer
409+ pdx->dwOutBuffPut = 0;
410+ pdx->dwNumOutput = 0; // and clear the buffer count
411+ pdx->bSendCharsPending = false; // Allow other threads again
412+ } else { // Here for sending chars normally - we hold the spin lock
413+ int nPipe = 0; // The pipe number to use
414+ char *pDat = &pdx->outputBuffer[pdx->dwOutBuffGet];
415+
416+ if ((pdx->dwOutBuffGet + dwCount) > OUTBUF_SZ) // does it cross buffer end?
417+ dwCount = OUTBUF_SZ - pdx->dwOutBuffGet;
418+ spin_unlock_irq(&pdx->charOutLock); // we are done with stuff that changes
419+ memcpy(pdx->pCoherCharOut, pDat, dwCount); // copy output data to the buffer
420+ usb_fill_bulk_urb(pdx->pUrbCharOut, pdx->udev,
421+ usb_sndbulkpipe(pdx->udev,
422+ pdx->epAddr[0]),
423+ pdx->pCoherCharOut, dwCount,
424+ ced_writechar_callback, pdx);
425+ pdx->pUrbCharOut->transfer_flags |=
426+ URB_NO_TRANSFER_DMA_MAP;
427+ usb_anchor_urb(pdx->pUrbCharOut, &pdx->submitted);
428+ iReturn = usb_submit_urb(pdx->pUrbCharOut, GFP_KERNEL);
429+ spin_lock_irq(&pdx->charOutLock); // grab lock for errors
430+ if (iReturn) {
431+ pdx->bPipeError[nPipe] = 1; // Flag an error to be handled later
432+ pdx->bSendCharsPending = false; // Allow other threads again
433+ usb_unanchor_urb(pdx->pUrbCharOut); // remove from list of active urbs
434+ }
435+ }
436+ } else if (pdx->bSendCharsPending && (pdx->dwNumOutput > 0))
437+ dev_dbg(&pdx->interface->dev,
438+ "SendChars bSendCharsPending:true");
439+
440+ dev_dbg(&pdx->interface->dev, "SendChars exit code: %d", iReturn);
441+ spin_unlock_irq(&pdx->charOutLock); // Now let go of the spinlock
442+ return iReturn;
443+}
444+
445+/***************************************************************************
446+** CopyUserSpace
447+** This moves memory between pinned down user space and the pCoherStagedIO
448+** memory buffer we use for transfers. Copy n bytes in the directions that
449+** is defined by pdx->StagedRead. The user space is determined by the area
450+** in pdx->StagedId and the offset in pdx->StagedDone. The user
451+** area may well not start on a page boundary, so allow for that.
452+**
453+** We have a table of physical pages that describe the area, so we can use
454+** this to get a virtual address that the kernel can use.
455+**
456+** pdx Is our device extension which holds all we know about the transfer.
457+** n The number of bytes to move one way or the other.
458+***************************************************************************/
459+static void CopyUserSpace(DEVICE_EXTENSION * pdx, int n)
460+{
461+ unsigned int nArea = pdx->StagedId;
462+ if (nArea < MAX_TRANSAREAS) {
463+ TRANSAREA *pArea = &pdx->rTransDef[nArea]; // area to be used
464+ unsigned int dwOffset =
465+ pdx->StagedDone + pdx->StagedOffset + pArea->dwBaseOffset;
466+ char *pCoherBuf = pdx->pCoherStagedIO; // coherent buffer
467+ if (!pArea->bUsed) {
468+ dev_err(&pdx->interface->dev, "%s area %d unused",
469+ __func__, nArea);
470+ return;
471+ }
472+
473+ while (n) {
474+ int nPage = dwOffset >> PAGE_SHIFT; // page number in table
475+ if (nPage < pArea->nPages) {
476+ char *pvAddress =
477+ (char *)kmap_atomic(pArea->pPages[nPage]);
478+ if (pvAddress) {
479+ unsigned int uiPageOff = dwOffset & (PAGE_SIZE - 1); // offset into the page
480+ size_t uiXfer = PAGE_SIZE - uiPageOff; // max to transfer on this page
481+ if (uiXfer > n) // limit byte count if too much
482+ uiXfer = n; // for the page
483+ if (pdx->StagedRead)
484+ memcpy(pvAddress + uiPageOff,
485+ pCoherBuf, uiXfer);
486+ else
487+ memcpy(pCoherBuf,
488+ pvAddress + uiPageOff,
489+ uiXfer);
490+ kunmap_atomic(pvAddress);
491+ dwOffset += uiXfer;
492+ pCoherBuf += uiXfer;
493+ n -= uiXfer;
494+ } else {
495+ dev_err(&pdx->interface->dev,
496+ "%s did not map page %d",
497+ __func__, nPage);
498+ return;
499+ }
500+
501+ } else {
502+ dev_err(&pdx->interface->dev,
503+ "%s exceeded pages %d", __func__,
504+ nPage);
505+ return;
506+ }
507+ }
508+ } else
509+ dev_err(&pdx->interface->dev, "%s bad area %d", __func__,
510+ nArea);
511+}
512+
513+// Forward declarations for stuff used circularly
514+static int StageChunk(DEVICE_EXTENSION * pdx);
515+/***************************************************************************
516+** ReadWrite_Complete
517+**
518+** Completion routine for our staged read/write Irps
519+*/
520+static void staged_callback(struct urb *pUrb)
521+{
522+ DEVICE_EXTENSION *pdx = pUrb->context;
523+ unsigned int nGot = pUrb->actual_length; // what we transferred
524+ bool bCancel = false;
525+ bool bRestartCharInput; // used at the end
526+
527+ spin_lock(&pdx->stagedLock); // stop ReadWriteMem() action while this routine is running
528+ pdx->bStagedUrbPending = false; // clear the flag for staged IRP pending
529+
530+ if (pUrb->status) { // sync/async unlink faults aren't errors
531+ if (!
532+ (pUrb->status == -ENOENT || pUrb->status == -ECONNRESET
533+ || pUrb->status == -ESHUTDOWN)) {
534+ dev_err(&pdx->interface->dev,
535+ "%s - nonzero write bulk status received: %d",
536+ __func__, pUrb->status);
537+ } else
538+ dev_info(&pdx->interface->dev,
539+ "%s - staged xfer cancelled", __func__);
540+
541+ spin_lock(&pdx->err_lock);
542+ pdx->errors = pUrb->status;
543+ spin_unlock(&pdx->err_lock);
544+ nGot = 0; // and tidy up again if so
545+ bCancel = true;
546+ } else {
547+ dev_dbg(&pdx->interface->dev, "%s %d chars xferred", __func__,
548+ nGot);
549+ if (pdx->StagedRead) // if reading, save to user space
550+ CopyUserSpace(pdx, nGot); // copy from buffer to user
551+ if (nGot == 0)
552+ dev_dbg(&pdx->interface->dev, "%s ZLP", __func__);
553+ }
554+
555+ // Update the transfer length based on the TransferBufferLength value in the URB
556+ pdx->StagedDone += nGot;
557+
558+ dev_dbg(&pdx->interface->dev, "%s, done %d bytes of %d", __func__,
559+ pdx->StagedDone, pdx->StagedLength);
560+
561+ if ((pdx->StagedDone == pdx->StagedLength) || // If no more to do
562+ (bCancel)) // or this IRP was cancelled
563+ {
564+ TRANSAREA *pArea = &pdx->rTransDef[pdx->StagedId]; // Transfer area info
565+ dev_dbg(&pdx->interface->dev,
566+ "%s transfer done, bytes %d, cancel %d", __func__,
567+ pdx->StagedDone, bCancel);
568+
569+ // Here is where we sort out what to do with this transfer if using a circular buffer. We have
570+ // a completed transfer that can be assumed to fit into the transfer area. We should be able to
571+ // add this to the end of a growing block or to use it to start a new block unless the code
572+ // that calculates the offset to use (in ReadWriteMem) is totally duff.
573+ if ((pArea->bCircular) && (pArea->bCircToHost) && (!bCancel) && // Time to sort out circular buffer info?
574+ (pdx->StagedRead)) // Only for tohost transfers for now
575+ {
576+ if (pArea->aBlocks[1].dwSize > 0) // If block 1 is in use we must append to it
577+ {
578+ if (pdx->StagedOffset ==
579+ (pArea->aBlocks[1].dwOffset +
580+ pArea->aBlocks[1].dwSize)) {
581+ pArea->aBlocks[1].dwSize +=
582+ pdx->StagedLength;
583+ dev_dbg(&pdx->interface->dev,
584+ "RWM_Complete, circ block 1 now %d bytes at %d",
585+ pArea->aBlocks[1].dwSize,
586+ pArea->aBlocks[1].dwOffset);
587+ } else {
588+ // Here things have gone very, very, wrong, but I cannot see how this can actually be achieved
589+ pArea->aBlocks[1].dwOffset =
590+ pdx->StagedOffset;
591+ pArea->aBlocks[1].dwSize =
592+ pdx->StagedLength;
593+ dev_err(&pdx->interface->dev,
594+ "%s ERROR, circ block 1 re-started %d bytes at %d",
595+ __func__,
596+ pArea->aBlocks[1].dwSize,
597+ pArea->aBlocks[1].dwOffset);
598+ }
599+ } else // If block 1 is not used, we try to add to block 0
600+ {
601+ if (pArea->aBlocks[0].dwSize > 0) // Got stored block 0 information?
602+ { // Must append onto the existing block 0
603+ if (pdx->StagedOffset ==
604+ (pArea->aBlocks[0].dwOffset +
605+ pArea->aBlocks[0].dwSize)) {
606+ pArea->aBlocks[0].dwSize += pdx->StagedLength; // Just add this transfer in
607+ dev_dbg(&pdx->interface->dev,
608+ "RWM_Complete, circ block 0 now %d bytes at %d",
609+ pArea->aBlocks[0].
610+ dwSize,
611+ pArea->aBlocks[0].
612+ dwOffset);
613+ } else // If it doesn't append, put into new block 1
614+ {
615+ pArea->aBlocks[1].dwOffset =
616+ pdx->StagedOffset;
617+ pArea->aBlocks[1].dwSize =
618+ pdx->StagedLength;
619+ dev_dbg(&pdx->interface->dev,
620+ "RWM_Complete, circ block 1 started %d bytes at %d",
621+ pArea->aBlocks[1].
622+ dwSize,
623+ pArea->aBlocks[1].
624+ dwOffset);
625+ }
626+ } else // No info stored yet, just save in block 0
627+ {
628+ pArea->aBlocks[0].dwOffset =
629+ pdx->StagedOffset;
630+ pArea->aBlocks[0].dwSize =
631+ pdx->StagedLength;
632+ dev_dbg(&pdx->interface->dev,
633+ "RWM_Complete, circ block 0 started %d bytes at %d",
634+ pArea->aBlocks[0].dwSize,
635+ pArea->aBlocks[0].dwOffset);
636+ }
637+ }
638+ }
639+
640+ if (!bCancel) // Don't generate an event if cancelled
641+ {
642+ dev_dbg(&pdx->interface->dev,
643+ "RWM_Complete, bCircular %d, bToHost %d, eStart %d, eSize %d",
644+ pArea->bCircular, pArea->bEventToHost,
645+ pArea->dwEventSt, pArea->dwEventSz);
646+ if ((pArea->dwEventSz) && // Set a user-mode event...
647+ (pdx->StagedRead == pArea->bEventToHost)) // ...on transfers in this direction?
648+ {
649+ int iWakeUp = 0; // assume
650+ // If we have completed the right sort of DMA transfer then set the event to notify
651+ // the user code to wake up anyone that is waiting.
652+ if ((pArea->bCircular) && // Circular areas use a simpler test
653+ (pArea->bCircToHost)) // only in supported direction
654+ { // Is total data waiting up to size limit?
655+ unsigned int dwTotal =
656+ pArea->aBlocks[0].dwSize +
657+ pArea->aBlocks[1].dwSize;
658+ iWakeUp = (dwTotal >= pArea->dwEventSz);
659+ } else {
660+ unsigned int transEnd =
661+ pdx->StagedOffset +
662+ pdx->StagedLength;
663+ unsigned int eventEnd =
664+ pArea->dwEventSt + pArea->dwEventSz;
665+ iWakeUp = (pdx->StagedOffset < eventEnd)
666+ && (transEnd > pArea->dwEventSt);
667+ }
668+
669+ if (iWakeUp) {
670+ dev_dbg(&pdx->interface->dev,
671+ "About to set event to notify app");
672+ wake_up_interruptible(&pArea->wqEvent); // wake up waiting processes
673+ ++pArea->iWakeUp; // increment wakeup count
674+ }
675+ }
676+ }
677+
678+ pdx->dwDMAFlag = MODE_CHAR; // Switch back to char mode before ReadWriteMem call
679+
680+ if (!bCancel) // Don't look for waiting transfer if cancelled
681+ {
682+ // If we have a transfer waiting, kick it off
683+ if (pdx->bXFerWaiting) // Got a block xfer waiting?
684+ {
685+ int iReturn;
686+ dev_info(&pdx->interface->dev,
687+ "*** RWM_Complete *** pending transfer will now be set up!!!");
688+ iReturn =
689+ ReadWriteMem(pdx, !pdx->rDMAInfo.bOutWard,
690+ pdx->rDMAInfo.wIdent,
691+ pdx->rDMAInfo.dwOffset,
692+ pdx->rDMAInfo.dwSize);
693+
694+ if (iReturn)
695+ dev_err(&pdx->interface->dev,
696+ "RWM_Complete rw setup failed %d",
697+ iReturn);
698+ }
699+ }
700+
701+ } else // Here for more to do
702+ StageChunk(pdx); // fire off the next bit
703+
704+ // While we hold the stagedLock, see if we should reallow character input ints
705+ // Don't allow if cancelled, or if a new block has started or if there is a waiting block.
706+ // This feels wrong as we should ask which spin lock protects dwDMAFlag.
707+ bRestartCharInput = !bCancel && (pdx->dwDMAFlag == MODE_CHAR)
708+ && !pdx->bXFerWaiting;
709+
710+ spin_unlock(&pdx->stagedLock); // Finally release the lock again
711+
712+ // This is not correct as dwDMAFlag is protected by the staged lock, but it is treated
713+ // in Allowi as if it were protected by the char lock. In any case, most systems will
714+ // not be upset by char input during DMA... sigh. Needs sorting out.
715+ if (bRestartCharInput) // may be out of date, but...
716+ Allowi(pdx, true); // ...Allowi tests a lock too.
717+ dev_dbg(&pdx->interface->dev, "%s done", __func__);
718+}
719+
720+/****************************************************************************
721+** StageChunk
722+**
723+** Generates the next chunk of data making up a staged transfer.
724+**
725+** The calling code must have acquired the staging spinlock before calling
726+** this function, and is responsible for releasing it. We are at callback level.
727+****************************************************************************/
728+static int StageChunk(DEVICE_EXTENSION * pdx)
729+{
730+ int iReturn = U14ERR_NOERROR;
731+ unsigned int ChunkSize;
732+ int nPipe = pdx->StagedRead ? 3 : 2; // The pipe number to use for reads or writes
733+ if (pdx->nPipes == 3)
734+ nPipe--; // Adjust for the 3-pipe case
735+ if (nPipe < 0) // and trap case that should never happen
736+ return U14ERR_FAIL;
737+
738+ if (!CanAcceptIoRequests(pdx)) // got sudden remove?
739+ {
740+ dev_info(&pdx->interface->dev, "%s sudden remove, giving up",
741+ __func__);
742+ return U14ERR_FAIL; // could do with a better error
743+ }
744+
745+ ChunkSize = (pdx->StagedLength - pdx->StagedDone); // transfer length remaining
746+ if (ChunkSize > STAGED_SZ) // make sure to keep legal
747+ ChunkSize = STAGED_SZ; // limit to max allowed
748+
749+ if (!pdx->StagedRead) // if writing...
750+ CopyUserSpace(pdx, ChunkSize); // ...copy data into the buffer
751+
752+ usb_fill_bulk_urb(pdx->pStagedUrb, pdx->udev,
753+ pdx->StagedRead ? usb_rcvbulkpipe(pdx->udev,
754+ pdx->
755+ epAddr[nPipe]) :
756+ usb_sndbulkpipe(pdx->udev, pdx->epAddr[nPipe]),
757+ pdx->pCoherStagedIO, ChunkSize, staged_callback, pdx);
758+ pdx->pStagedUrb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
759+ usb_anchor_urb(pdx->pStagedUrb, &pdx->submitted); // in case we need to kill it
760+ iReturn = usb_submit_urb(pdx->pStagedUrb, GFP_ATOMIC);
761+ if (iReturn) {
762+ usb_unanchor_urb(pdx->pStagedUrb); // kill it
763+ pdx->bPipeError[nPipe] = 1; // Flag an error to be handled later
764+ dev_err(&pdx->interface->dev, "%s submit urb failed, code %d",
765+ __func__, iReturn);
766+ } else
767+ pdx->bStagedUrbPending = true; // Set the flag for staged URB pending
768+ dev_dbg(&pdx->interface->dev, "%s done so far:%d, this size:%d",
769+ __func__, pdx->StagedDone, ChunkSize);
770+
771+ return iReturn;
772+}
773+
774+/***************************************************************************
775+** ReadWriteMem
776+**
777+** This routine is used generally for block read and write operations.
778+** Breaks up a read or write in to specified sized chunks, as specified by pipe
779+** information on maximum transfer size.
780+**
781+** Any code that calls this must be holding the stagedLock
782+**
783+** Arguments:
784+** DeviceObject - pointer to our FDO (Functional Device Object)
785+** Read - TRUE for read, FALSE for write. This is from POV of the driver
786+** wIdent - the transfer area number - defines memory area and more.
787+** dwOffs - the start offset within the transfer area of the start of this
788+** transfer.
789+** dwLen - the number of bytes to transfer.
790+*/
791+int ReadWriteMem(DEVICE_EXTENSION * pdx, bool Read, unsigned short wIdent,
792+ unsigned int dwOffs, unsigned int dwLen)
793+{
794+ TRANSAREA *pArea = &pdx->rTransDef[wIdent]; // Transfer area info
795+
796+ if (!CanAcceptIoRequests(pdx)) // Are we in a state to accept new requests?
797+ {
798+ dev_err(&pdx->interface->dev, "%s can't accept requests",
799+ __func__);
800+ return U14ERR_FAIL;
801+ }
802+
803+ dev_dbg(&pdx->interface->dev,
804+ "%s xfer %d bytes to %s, offset %d, area %d", __func__, dwLen,
805+ Read ? "host" : "1401", dwOffs, wIdent);
806+
807+ // Amazingly, we can get an escape sequence back before the current staged Urb is done, so we
808+ // have to check for this situation and, if so, wait until all is OK.
809+ if (pdx->bStagedUrbPending) {
810+ pdx->bXFerWaiting = true; // Flag we are waiting
811+ dev_info(&pdx->interface->dev,
812+ "%s xfer is waiting, as previous staged pending",
813+ __func__);
814+ return U14ERR_NOERROR;
815+ }
816+
817+ if (dwLen == 0) // allow 0-len read or write; just return success
818+ {
819+ dev_dbg(&pdx->interface->dev,
820+ "%s OK; zero-len read/write request", __func__);
821+ return U14ERR_NOERROR;
822+ }
823+
824+ if ((pArea->bCircular) && // Circular transfer?
825+ (pArea->bCircToHost) && (Read)) // In a supported direction
826+ { // If so, we sort out offset ourself
827+ bool bWait = false; // Flag for transfer having to wait
828+
829+ dev_dbg(&pdx->interface->dev,
830+ "Circular buffers are %d at %d and %d at %d",
831+ pArea->aBlocks[0].dwSize, pArea->aBlocks[0].dwOffset,
832+ pArea->aBlocks[1].dwSize, pArea->aBlocks[1].dwOffset);
833+ if (pArea->aBlocks[1].dwSize > 0) // Using the second block already?
834+ {
835+ dwOffs = pArea->aBlocks[1].dwOffset + pArea->aBlocks[1].dwSize; // take offset from that
836+ bWait = (dwOffs + dwLen) > pArea->aBlocks[0].dwOffset; // Wait if will overwrite block 0?
837+ bWait |= (dwOffs + dwLen) > pArea->dwLength; // or if it overflows the buffer
838+ } else // Area 1 not in use, try to use area 0
839+ {
840+ if (pArea->aBlocks[0].dwSize == 0) // Reset block 0 if not in use
841+ pArea->aBlocks[0].dwOffset = 0;
842+ dwOffs =
843+ pArea->aBlocks[0].dwOffset +
844+ pArea->aBlocks[0].dwSize;
845+ if ((dwOffs + dwLen) > pArea->dwLength) // Off the end of the buffer?
846+ {
847+ pArea->aBlocks[1].dwOffset = 0; // Set up to use second block
848+ dwOffs = 0;
849+ bWait = (dwOffs + dwLen) > pArea->aBlocks[0].dwOffset; // Wait if will overwrite block 0?
850+ bWait |= (dwOffs + dwLen) > pArea->dwLength; // or if it overflows the buffer
851+ }
852+ }
853+
854+ if (bWait) // This transfer will have to wait?
855+ {
856+ pdx->bXFerWaiting = true; // Flag we are waiting
857+ dev_dbg(&pdx->interface->dev,
858+ "%s xfer waiting for circular buffer space",
859+ __func__);
860+ return U14ERR_NOERROR;
861+ }
862+
863+ dev_dbg(&pdx->interface->dev,
864+ "%s circular xfer, %d bytes starting at %d", __func__,
865+ dwLen, dwOffs);
866+ }
867+ // Save the parameters for the read\write transfer
868+ pdx->StagedRead = Read; // Save the parameters for this read
869+ pdx->StagedId = wIdent; // ID allows us to get transfer area info
870+ pdx->StagedOffset = dwOffs; // The area within the transfer area
871+ pdx->StagedLength = dwLen;
872+ pdx->StagedDone = 0; // Initialise the byte count
873+ pdx->dwDMAFlag = MODE_LINEAR; // Set DMA mode flag at this point
874+ pdx->bXFerWaiting = false; // Clearly not a transfer waiting now
875+
876+// KeClearEvent(&pdx->StagingDoneEvent); // Clear the transfer done event
877+ StageChunk(pdx); // fire off the first chunk
878+
879+ return U14ERR_NOERROR;
880+}
881+
882+/****************************************************************************
883+**
884+** ReadChar
885+**
886+** Reads a character a buffer. If there is no more
887+** data we return FALSE. Used as part of decoding a DMA request.
888+**
889+****************************************************************************/
890+static bool ReadChar(unsigned char *pChar, char *pBuf, unsigned int *pdDone,
891+ unsigned int dGot)
892+{
893+ bool bRead = false;
894+ unsigned int dDone = *pdDone;
895+
896+ if (dDone < dGot) // If there is more data
897+ {
898+ *pChar = (unsigned char)pBuf[dDone]; // Extract the next char
899+ dDone++; // Increment the done count
900+ *pdDone = dDone;
901+ bRead = true; // and flag success
902+ }
903+
904+ return bRead;
905+}
906+
907+#ifdef NOTUSED
908+/****************************************************************************
909+**
910+** ReadWord
911+**
912+** Reads a word from the 1401, just uses ReadChar twice; passes on any error
913+**
914+*****************************************************************************/
915+static bool ReadWord(unsigned short *pWord, char *pBuf, unsigned int *pdDone,
916+ unsigned int dGot)
917+{
918+ if (ReadChar((unsigned char *)pWord, pBuf, pdDone, dGot))
919+ return ReadChar(((unsigned char *)pWord) + 1, pBuf, pdDone,
920+ dGot);
921+ else
922+ return false;
923+}
924+#endif
925+
926+/****************************************************************************
927+** ReadHuff
928+**
929+** Reads a coded number in and returns it, Code is:
930+** If data is in range 0..127 we recieve 1 byte. If data in range 128-16383
931+** we recieve two bytes, top bit of first indicates another on its way. If
932+** data in range 16383-4194303 we get three bytes, top two bits of first set
933+** to indicate three byte total.
934+**
935+*****************************************************************************/
936+static bool ReadHuff(volatile unsigned int *pDWord, char *pBuf,
937+ unsigned int *pdDone, unsigned int dGot)
938+{
939+ unsigned char ucData; /* for each read to ReadChar */
940+ bool bReturn = true; /* assume we will succeed */
941+ unsigned int dwData = 0; /* Accumulator for the data */
942+
943+ if (ReadChar(&ucData, pBuf, pdDone, dGot)) {
944+ dwData = ucData; /* copy the data */
945+ if ((dwData & 0x00000080) != 0) { /* Bit set for more data ? */
946+ dwData &= 0x0000007F; /* Clear the relevant bit */
947+ if (ReadChar(&ucData, pBuf, pdDone, dGot)) {
948+ dwData = (dwData << 8) | ucData;
949+ if ((dwData & 0x00004000) != 0) { /* three byte sequence ? */
950+ dwData &= 0x00003FFF; /* Clear the relevant bit */
951+ if (ReadChar
952+ (&ucData, pBuf, pdDone, dGot))
953+ dwData = (dwData << 8) | ucData;
954+ else
955+ bReturn = false;
956+ }
957+ } else
958+ bReturn = false; /* couldn't read data */
959+ }
960+ } else
961+ bReturn = false;
962+
963+ *pDWord = dwData; /* return the data */
964+ return bReturn;
965+}
966+
967+/***************************************************************************
968+**
969+** ReadDMAInfo
970+**
971+** Tries to read info about the dma request from the 1401 and decode it into
972+** the dma descriptor block. We have at this point had the escape character
973+** from the 1401 and now we must read in the rest of the information about
974+** the transfer request. Returns FALSE if 1401 fails to respond or obselete
975+** code from 1401 or bad parameters.
976+**
977+** The pBuf char pointer does not include the initial escape character, so
978+** we start handling the data at offset zero.
979+**
980+*****************************************************************************/
981+static bool ReadDMAInfo(volatile DMADESC * pDmaDesc, DEVICE_EXTENSION * pdx,
982+ char *pBuf, unsigned int dwCount)
983+{
984+ bool bResult = false; // assume we won't succeed
985+ unsigned char ucData;
986+ unsigned int dDone = 0; // We haven't parsed anything so far
987+
988+ dev_dbg(&pdx->interface->dev, "%s", __func__);
989+
990+ if (ReadChar(&ucData, pBuf, &dDone, dwCount)) {
991+ unsigned char ucTransCode = (ucData & 0x0F); // get code for transfer type
992+ unsigned short wIdent = ((ucData >> 4) & 0x07); // and area identifier
993+
994+ // fill in the structure we were given
995+ pDmaDesc->wTransType = ucTransCode; // type of transfer
996+ pDmaDesc->wIdent = wIdent; // area to use
997+ pDmaDesc->dwSize = 0; // initialise other bits
998+ pDmaDesc->dwOffset = 0;
999+
1000+ dev_dbg(&pdx->interface->dev, "%s type: %d ident: %d", __func__,
1001+ pDmaDesc->wTransType, pDmaDesc->wIdent);
1002+
1003+ pDmaDesc->bOutWard = (ucTransCode != TM_EXTTOHOST); // set transfer direction
1004+
1005+ switch (ucTransCode) {
1006+ case TM_EXTTOHOST: // Extended linear transfer modes (the only ones!)
1007+ case TM_EXTTO1401:
1008+ {
1009+ bResult =
1010+ ReadHuff(&(pDmaDesc->dwOffset), pBuf,
1011+ &dDone, dwCount)
1012+ && ReadHuff(&(pDmaDesc->dwSize), pBuf,
1013+ &dDone, dwCount);
1014+ if (bResult) {
1015+ dev_dbg(&pdx->interface->dev,
1016+ "%s xfer offset & size %d %d",
1017+ __func__, pDmaDesc->dwOffset,
1018+ pDmaDesc->dwSize);
1019+
1020+ if ((wIdent >= MAX_TRANSAREAS) || // Illegal area number, or...
1021+ (!pdx->rTransDef[wIdent].bUsed) || // area not set up, or...
1022+ (pDmaDesc->dwOffset > pdx->rTransDef[wIdent].dwLength) || // range/size
1023+ ((pDmaDesc->dwOffset +
1024+ pDmaDesc->dwSize) >
1025+ (pdx->rTransDef[wIdent].
1026+ dwLength))) {
1027+ bResult = false; // bad parameter(s)
1028+ dev_dbg(&pdx->interface->dev,
1029+ "%s bad param - id %d, bUsed %d, offset %d, size %d, area length %d",
1030+ __func__, wIdent,
1031+ pdx->rTransDef[wIdent].
1032+ bUsed,
1033+ pDmaDesc->dwOffset,
1034+ pDmaDesc->dwSize,
1035+ pdx->rTransDef[wIdent].
1036+ dwLength);
1037+ }
1038+ }
1039+ break;
1040+ }
1041+ default:
1042+ break;
1043+ }
1044+ } else
1045+ bResult = false;
1046+
1047+ if (!bResult) // now check parameters for validity
1048+ dev_err(&pdx->interface->dev, "%s error reading Esc sequence",
1049+ __func__);
1050+
1051+ return bResult;
1052+}
1053+
1054+/****************************************************************************
1055+**
1056+** Handle1401Esc
1057+**
1058+** Deals with an escape sequence coming from the 1401. This can either be
1059+** a DMA transfer request of various types or a response to an escape sequence
1060+** sent to the 1401. This is called from a callback.
1061+**
1062+** Parameters are
1063+**
1064+** dwCount - the number of characters in the device extension char in buffer,
1065+** this is known to be at least 2 or we will not be called.
1066+**
1067+****************************************************************************/
1068+static int Handle1401Esc(DEVICE_EXTENSION * pdx, char *pCh,
1069+ unsigned int dwCount)
1070+{
1071+ int iReturn = U14ERR_FAIL;
1072+
1073+ // I have no idea what this next test is about. '?' is 0x3f, which is area 3, code
1074+ // 15. At the moment, this is not used, so it does no harm, but unless someone can
1075+ // tell me what this is for, it should be removed from this and the Windows driver.
1076+ if (pCh[0] == '?') // Is this an information response
1077+ { // Parse and save the information
1078+ } else {
1079+ spin_lock(&pdx->stagedLock); // Lock others out
1080+
1081+ if (ReadDMAInfo(&pdx->rDMAInfo, pdx, pCh, dwCount)) // Get DMA parameters
1082+ {
1083+ unsigned short wTransType = pdx->rDMAInfo.wTransType; // check transfer type
1084+
1085+ dev_dbg(&pdx->interface->dev,
1086+ "%s xfer to %s, offset %d, length %d", __func__,
1087+ pdx->rDMAInfo.bOutWard ? "1401" : "host",
1088+ pdx->rDMAInfo.dwOffset, pdx->rDMAInfo.dwSize);
1089+
1090+ if (pdx->bXFerWaiting) // Check here for badly out of kilter...
1091+ { // This can never happen, really
1092+ dev_err(&pdx->interface->dev,
1093+ "ERROR: DMA setup while transfer still waiting");
1094+ spin_unlock(&pdx->stagedLock);
1095+ } else {
1096+ if ((wTransType == TM_EXTTOHOST)
1097+ || (wTransType == TM_EXTTO1401)) {
1098+ iReturn =
1099+ ReadWriteMem(pdx,
1100+ !pdx->rDMAInfo.
1101+ bOutWard,
1102+ pdx->rDMAInfo.wIdent,
1103+ pdx->rDMAInfo.dwOffset,
1104+ pdx->rDMAInfo.dwSize);
1105+ if (iReturn != U14ERR_NOERROR)
1106+ dev_err(&pdx->interface->dev,
1107+ "%s ReadWriteMem() failed %d",
1108+ __func__, iReturn);
1109+ } else // This covers non-linear transfer setup
1110+ dev_err(&pdx->interface->dev,
1111+ "%s Unknown block xfer type %d",
1112+ __func__, wTransType);
1113+ }
1114+ } else // Failed to read parameters
1115+ dev_err(&pdx->interface->dev, "%s ReadDMAInfo() fail",
1116+ __func__);
1117+
1118+ spin_unlock(&pdx->stagedLock); // OK here
1119+ }
1120+
1121+ dev_dbg(&pdx->interface->dev, "%s returns %d", __func__, iReturn);
1122+
1123+ return iReturn;
1124+}
1125+
1126+/****************************************************************************
1127+** Callback for the character read complete or error
1128+****************************************************************************/
1129+static void ced_readchar_callback(struct urb *pUrb)
1130+{
1131+ DEVICE_EXTENSION *pdx = pUrb->context;
1132+ int nGot = pUrb->actual_length; // what we transferred
1133+
1134+ if (pUrb->status) // Do we have a problem to handle?
1135+ {
1136+ int nPipe = pdx->nPipes == 4 ? 1 : 0; // The pipe number to use for error
1137+ // sync/async unlink faults aren't errors... just saying device removed or stopped
1138+ if (!
1139+ (pUrb->status == -ENOENT || pUrb->status == -ECONNRESET
1140+ || pUrb->status == -ESHUTDOWN)) {
1141+ dev_err(&pdx->interface->dev,
1142+ "%s - nonzero write bulk status received: %d",
1143+ __func__, pUrb->status);
1144+ } else
1145+ dev_dbg(&pdx->interface->dev,
1146+ "%s - 0 chars pUrb->status=%d (shutdown?)",
1147+ __func__, pUrb->status);
1148+
1149+ spin_lock(&pdx->err_lock);
1150+ pdx->errors = pUrb->status;
1151+ spin_unlock(&pdx->err_lock);
1152+ nGot = 0; // and tidy up again if so
1153+
1154+ spin_lock(&pdx->charInLock); // already at irq level
1155+ pdx->bPipeError[nPipe] = 1; // Flag an error for later
1156+ } else {
1157+ if ((nGot > 1) && ((pdx->pCoherCharIn[0] & 0x7f) == 0x1b)) // Esc sequence?
1158+ {
1159+ Handle1401Esc(pdx, &pdx->pCoherCharIn[1], nGot - 1); // handle it
1160+ spin_lock(&pdx->charInLock); // already at irq level
1161+ } else {
1162+ spin_lock(&pdx->charInLock); // already at irq level
1163+ if (nGot > 0) {
1164+ unsigned int i;
1165+ if (nGot < INBUF_SZ) {
1166+ pdx->pCoherCharIn[nGot] = 0; // tidy the string
1167+ dev_dbg(&pdx->interface->dev,
1168+ "%s got %d chars >%s<",
1169+ __func__, nGot,
1170+ pdx->pCoherCharIn);
1171+ }
1172+ // We know that whatever we read must fit in the input buffer
1173+ for (i = 0; i < nGot; i++) {
1174+ pdx->inputBuffer[pdx->dwInBuffPut++] =
1175+ pdx->pCoherCharIn[i] & 0x7F;
1176+ if (pdx->dwInBuffPut >= INBUF_SZ)
1177+ pdx->dwInBuffPut = 0;
1178+ }
1179+
1180+ if ((pdx->dwNumInput + nGot) <= INBUF_SZ)
1181+ pdx->dwNumInput += nGot; // Adjust the buffer count accordingly
1182+ } else
1183+ dev_dbg(&pdx->interface->dev, "%s read ZLP",
1184+ __func__);
1185+ }
1186+ }
1187+
1188+ pdx->bReadCharsPending = false; // No longer have a pending read
1189+ spin_unlock(&pdx->charInLock); // already at irq level
1190+
1191+ Allowi(pdx, true); // see if we can do the next one
1192+}
1193+
1194+/****************************************************************************
1195+** Allowi
1196+**
1197+** This is used to make sure that there is always a pending input transfer so
1198+** we can pick up any inward transfers. This can be called in multiple contexts
1199+** so we use the irqsave version of the spinlock.
1200+****************************************************************************/
1201+int Allowi(DEVICE_EXTENSION * pdx, bool bInCallback)
1202+{
1203+ int iReturn = U14ERR_NOERROR;
1204+ unsigned long flags;
1205+ spin_lock_irqsave(&pdx->charInLock, flags); // can be called in multiple contexts
1206+
1207+ // We don't want char input running while DMA is in progress as we know that this
1208+ // can cause sequencing problems for the 2270. So don't. It will also allow the
1209+ // ERR response to get back to the host code too early on some PCs, even if there
1210+ // is no actual driver failure, so we don't allow this at all.
1211+ if (!pdx->bInDrawDown && // stop input if
1212+ !pdx->bReadCharsPending && // If no read request outstanding
1213+ (pdx->dwNumInput < (INBUF_SZ / 2)) && // and there is some space
1214+ (pdx->dwDMAFlag == MODE_CHAR) && // not doing any DMA
1215+ (!pdx->bXFerWaiting) && // no xfer waiting to start
1216+ (CanAcceptIoRequests(pdx))) // and activity is generally OK
1217+ { // then off we go
1218+ unsigned int nMax = INBUF_SZ - pdx->dwNumInput; // max we could read
1219+ int nPipe = pdx->nPipes == 4 ? 1 : 0; // The pipe number to use
1220+
1221+ dev_dbg(&pdx->interface->dev, "%s %d chars in input buffer",
1222+ __func__, pdx->dwNumInput);
1223+
1224+ usb_fill_int_urb(pdx->pUrbCharIn, pdx->udev,
1225+ usb_rcvintpipe(pdx->udev, pdx->epAddr[nPipe]),
1226+ pdx->pCoherCharIn, nMax, ced_readchar_callback,
1227+ pdx, pdx->bInterval);
1228+ pdx->pUrbCharIn->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; // short xfers are OK by default
1229+ usb_anchor_urb(pdx->pUrbCharIn, &pdx->submitted); // in case we need to kill it
1230+ iReturn =
1231+ usb_submit_urb(pdx->pUrbCharIn,
1232+ bInCallback ? GFP_ATOMIC : GFP_KERNEL);
1233+ if (iReturn) {
1234+ usb_unanchor_urb(pdx->pUrbCharIn); // remove from list of active Urbs
1235+ pdx->bPipeError[nPipe] = 1; // Flag an error to be handled later
1236+ dev_err(&pdx->interface->dev,
1237+ "%s submit urb failed: %d", __func__, iReturn);
1238+ } else
1239+ pdx->bReadCharsPending = true; // Flag that we are active here
1240+ }
1241+
1242+ spin_unlock_irqrestore(&pdx->charInLock, flags);
1243+
1244+ return iReturn;
1245+
1246+}
1247+
1248+/*****************************************************************************
1249+** The ioctl entry point to the driver that is used by us to talk to it.
1250+** inode The device node (no longer in 3.0.0 kernels)
1251+** file The file that is open, which holds our pdx pointer
1252+** ulArg The argument passed in. Note that long is 64-bits in 64-bit system, i.e. it is big
1253+** enough for a 64-bit pointer.
1254+*****************************************************************************/
1255+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36)
1256+static long ced_ioctl(struct file *file, unsigned int cmd, unsigned long ulArg)
1257+#else
1258+static int ced_ioctl(struct inode *node, struct file *file, unsigned int cmd,
1259+ unsigned long ulArg)
1260+#endif
1261+{
1262+ int err = 0;
1263+ DEVICE_EXTENSION *pdx = file->private_data;
1264+ if (!CanAcceptIoRequests(pdx)) // check we still exist
1265+ return -ENODEV;
1266+
1267+ // Check that access is allowed, where is is needed. Anything that would have an indeterminate
1268+ // size will be checked by the specific command.
1269+ if (_IOC_DIR(cmd) & _IOC_READ) // read from point of view of user...
1270+ err = !access_ok(VERIFY_WRITE, (void __user *)ulArg, _IOC_SIZE(cmd)); // is kernel write
1271+ else if (_IOC_DIR(cmd) & _IOC_WRITE) // and write from point of view of user...
1272+ err = !access_ok(VERIFY_READ, (void __user *)ulArg, _IOC_SIZE(cmd)); // is kernel read
1273+ if (err)
1274+ return -EFAULT;
1275+
1276+ switch (_IOC_NR(cmd)) {
1277+ case _IOC_NR(IOCTL_CED_SENDSTRING(0)):
1278+ return SendString(pdx, (const char __user *)ulArg,
1279+ _IOC_SIZE(cmd));
1280+
1281+ case _IOC_NR(IOCTL_CED_RESET1401):
1282+ return Reset1401(pdx);
1283+
1284+ case _IOC_NR(IOCTL_CED_GETCHAR):
1285+ return GetChar(pdx);
1286+
1287+ case _IOC_NR(IOCTL_CED_SENDCHAR):
1288+ return SendChar(pdx, (char)ulArg);
1289+
1290+ case _IOC_NR(IOCTL_CED_STAT1401):
1291+ return Stat1401(pdx);
1292+
1293+ case _IOC_NR(IOCTL_CED_LINECOUNT):
1294+ return LineCount(pdx);
1295+
1296+ case _IOC_NR(IOCTL_CED_GETSTRING(0)):
1297+ return GetString(pdx, (char __user *)ulArg, _IOC_SIZE(cmd));
1298+
1299+ case _IOC_NR(IOCTL_CED_SETTRANSFER):
1300+ return SetTransfer(pdx, (TRANSFERDESC __user *) ulArg);
1301+
1302+ case _IOC_NR(IOCTL_CED_UNSETTRANSFER):
1303+ return UnsetTransfer(pdx, (int)ulArg);
1304+
1305+ case _IOC_NR(IOCTL_CED_SETEVENT):
1306+ return SetEvent(pdx, (TRANSFEREVENT __user *) ulArg);
1307+
1308+ case _IOC_NR(IOCTL_CED_GETOUTBUFSPACE):
1309+ return GetOutBufSpace(pdx);
1310+
1311+ case _IOC_NR(IOCTL_CED_GETBASEADDRESS):
1312+ return -1;
1313+
1314+ case _IOC_NR(IOCTL_CED_GETDRIVERREVISION):
1315+ return (2 << 24) | (DRIVERMAJREV << 16) | DRIVERMINREV; // USB | MAJOR | MINOR
1316+
1317+ case _IOC_NR(IOCTL_CED_GETTRANSFER):
1318+ return GetTransfer(pdx, (TGET_TX_BLOCK __user *) ulArg);
1319+
1320+ case _IOC_NR(IOCTL_CED_KILLIO1401):
1321+ return KillIO1401(pdx);
1322+
1323+ case _IOC_NR(IOCTL_CED_STATEOF1401):
1324+ return StateOf1401(pdx);
1325+
1326+ case _IOC_NR(IOCTL_CED_GRAB1401):
1327+ case _IOC_NR(IOCTL_CED_FREE1401):
1328+ return U14ERR_NOERROR;
1329+
1330+ case _IOC_NR(IOCTL_CED_STARTSELFTEST):
1331+ return StartSelfTest(pdx);
1332+
1333+ case _IOC_NR(IOCTL_CED_CHECKSELFTEST):
1334+ return CheckSelfTest(pdx, (TGET_SELFTEST __user *) ulArg);
1335+
1336+ case _IOC_NR(IOCTL_CED_TYPEOF1401):
1337+ return TypeOf1401(pdx);
1338+
1339+ case _IOC_NR(IOCTL_CED_TRANSFERFLAGS):
1340+ return TransferFlags(pdx);
1341+
1342+ case _IOC_NR(IOCTL_CED_DBGPEEK):
1343+ return DbgPeek(pdx, (TDBGBLOCK __user *) ulArg);
1344+
1345+ case _IOC_NR(IOCTL_CED_DBGPOKE):
1346+ return DbgPoke(pdx, (TDBGBLOCK __user *) ulArg);
1347+
1348+ case _IOC_NR(IOCTL_CED_DBGRAMPDATA):
1349+ return DbgRampData(pdx, (TDBGBLOCK __user *) ulArg);
1350+
1351+ case _IOC_NR(IOCTL_CED_DBGRAMPADDR):
1352+ return DbgRampAddr(pdx, (TDBGBLOCK __user *) ulArg);
1353+
1354+ case _IOC_NR(IOCTL_CED_DBGGETDATA):
1355+ return DbgGetData(pdx, (TDBGBLOCK __user *) ulArg);
1356+
1357+ case _IOC_NR(IOCTL_CED_DBGSTOPLOOP):
1358+ return DbgStopLoop(pdx);
1359+
1360+ case _IOC_NR(IOCTL_CED_FULLRESET):
1361+ pdx->bForceReset = true; // Set a flag for a full reset
1362+ break;
1363+
1364+ case _IOC_NR(IOCTL_CED_SETCIRCULAR):
1365+ return SetCircular(pdx, (TRANSFERDESC __user *) ulArg);
1366+
1367+ case _IOC_NR(IOCTL_CED_GETCIRCBLOCK):
1368+ return GetCircBlock(pdx, (TCIRCBLOCK __user *) ulArg);
1369+
1370+ case _IOC_NR(IOCTL_CED_FREECIRCBLOCK):
1371+ return FreeCircBlock(pdx, (TCIRCBLOCK __user *) ulArg);
1372+
1373+ case _IOC_NR(IOCTL_CED_WAITEVENT):
1374+ return WaitEvent(pdx, (int)(ulArg & 0xff), (int)(ulArg >> 8));
1375+
1376+ case _IOC_NR(IOCTL_CED_TESTEVENT):
1377+ return TestEvent(pdx, (int)ulArg);
1378+
1379+ default:
1380+ return U14ERR_NO_SUCH_FN;
1381+ }
1382+ return U14ERR_NOERROR;
1383+}
1384+
1385+static const struct file_operations ced_fops = {
1386+ .owner = THIS_MODULE,
1387+ .open = ced_open,
1388+ .release = ced_release,
1389+ .flush = ced_flush,
1390+ .llseek = noop_llseek,
1391+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36)
1392+ .unlocked_ioctl = ced_ioctl,
1393+#else
1394+ .ioctl = ced_ioctl,
1395+#endif
1396+};
1397+
1398+/*
1399+ * usb class driver info in order to get a minor number from the usb core,
1400+ * and to have the device registered with the driver core
1401+ */
1402+static struct usb_class_driver ced_class = {
1403+ .name = "cedusb%d",
1404+ .fops = &ced_fops,
1405+ .minor_base = USB_CED_MINOR_BASE,
1406+};
1407+
1408+// Check that the device that matches a 1401 vendor and product ID is OK to use and
1409+// initialise our DEVICE_EXTENSION.
1410+static int ced_probe(struct usb_interface *interface,
1411+ const struct usb_device_id *id)
1412+{
1413+ DEVICE_EXTENSION *pdx;
1414+ struct usb_host_interface *iface_desc;
1415+ struct usb_endpoint_descriptor *endpoint;
1416+ int i, bcdDevice;
1417+ int retval = -ENOMEM;
1418+
1419+ // allocate memory for our device extension and initialize it
1420+ pdx = kzalloc(sizeof(*pdx), GFP_KERNEL);
1421+ if (!pdx) {
1422+ dev_err(&interface->dev, "Out of memory\n");
1423+ goto error;
1424+ }
1425+
1426+ for (i = 0; i < MAX_TRANSAREAS; ++i) // Initialise the wait queues
1427+ {
1428+ init_waitqueue_head(&pdx->rTransDef[i].wqEvent);
1429+ }
1430+
1431+ // Put initialises for our stuff here. Note that all of *pdx is zero, so
1432+ // no need to explicitly zero it.
1433+ spin_lock_init(&pdx->charOutLock);
1434+ spin_lock_init(&pdx->charInLock);
1435+ spin_lock_init(&pdx->stagedLock);
1436+
1437+ // Initialises from the skeleton stuff
1438+ kref_init(&pdx->kref);
1439+ mutex_init(&pdx->io_mutex);
1440+ spin_lock_init(&pdx->err_lock);
1441+ init_usb_anchor(&pdx->submitted);
1442+
1443+ pdx->udev = usb_get_dev(interface_to_usbdev(interface));
1444+ pdx->interface = interface;
1445+
1446+ // Attempt to identify the device
1447+ bcdDevice = pdx->udev->descriptor.bcdDevice;
1448+ i = (bcdDevice >> 8);
1449+ if (i == 0)
1450+ pdx->s1401Type = TYPEU1401;
1451+ else if ((i >= 1) && (i <= 23))
1452+ pdx->s1401Type = i + 2;
1453+ else {
1454+ dev_err(&interface->dev, "%s Unknown device. bcdDevice = %d",
1455+ __func__, bcdDevice);
1456+ goto error;
1457+ }
1458+ // set up the endpoint information. We only care about the number of EP as
1459+ // we know that we are dealing with a 1401 device.
1460+ iface_desc = interface->cur_altsetting;
1461+ pdx->nPipes = iface_desc->desc.bNumEndpoints;
1462+ dev_info(&interface->dev, "1401Type=%d with %d End Points",
1463+ pdx->s1401Type, pdx->nPipes);
1464+ if ((pdx->nPipes < 3) || (pdx->nPipes > 4))
1465+ goto error;
1466+
1467+ // Allocate the URBs we hold for performing transfers
1468+ pdx->pUrbCharOut = usb_alloc_urb(0, GFP_KERNEL); // character output URB
1469+ pdx->pUrbCharIn = usb_alloc_urb(0, GFP_KERNEL); // character input URB
1470+ pdx->pStagedUrb = usb_alloc_urb(0, GFP_KERNEL); // block transfer URB
1471+ if (!pdx->pUrbCharOut || !pdx->pUrbCharIn || !pdx->pStagedUrb) {
1472+ dev_err(&interface->dev, "%s URB alloc failed", __func__);
1473+ goto error;
1474+ }
1475+
1476+ pdx->pCoherStagedIO =
1477+ usb_alloc_coherent(pdx->udev, STAGED_SZ, GFP_KERNEL,
1478+ &pdx->pStagedUrb->transfer_dma);
1479+ pdx->pCoherCharOut =
1480+ usb_alloc_coherent(pdx->udev, OUTBUF_SZ, GFP_KERNEL,
1481+ &pdx->pUrbCharOut->transfer_dma);
1482+ pdx->pCoherCharIn =
1483+ usb_alloc_coherent(pdx->udev, INBUF_SZ, GFP_KERNEL,
1484+ &pdx->pUrbCharIn->transfer_dma);
1485+ if (!pdx->pCoherCharOut || !pdx->pCoherCharIn || !pdx->pCoherStagedIO) {
1486+ dev_err(&interface->dev, "%s Coherent buffer alloc failed",
1487+ __func__);
1488+ goto error;
1489+ }
1490+
1491+ for (i = 0; i < pdx->nPipes; ++i) {
1492+ endpoint = &iface_desc->endpoint[i].desc;
1493+ pdx->epAddr[i] = endpoint->bEndpointAddress;
1494+ dev_info(&interface->dev, "Pipe %d, ep address %02x", i,
1495+ pdx->epAddr[i]);
1496+ if (((pdx->nPipes == 3) && (i == 0)) || // if char input end point
1497+ ((pdx->nPipes == 4) && (i == 1))) {
1498+ pdx->bInterval = endpoint->bInterval; // save the endpoint interrupt interval
1499+ dev_info(&interface->dev, "Pipe %d, bInterval = %d", i,
1500+ pdx->bInterval);
1501+ }
1502+ // Detect USB2 by checking last ep size (64 if USB1)
1503+ if (i == pdx->nPipes - 1) // if this is the last ep (bulk)
1504+ {
1505+ pdx->bIsUSB2 =
1506+ le16_to_cpu(endpoint->wMaxPacketSize) > 64;
1507+ dev_info(&pdx->interface->dev, "USB%d",
1508+ pdx->bIsUSB2 + 1);
1509+ }
1510+ }
1511+
1512+ /* save our data pointer in this interface device */
1513+ usb_set_intfdata(interface, pdx);
1514+
1515+ /* we can register the device now, as it is ready */
1516+ retval = usb_register_dev(interface, &ced_class);
1517+ if (retval) {
1518+ /* something prevented us from registering this driver */
1519+ dev_err(&interface->dev,
1520+ "Not able to get a minor for this device.\n");
1521+ usb_set_intfdata(interface, NULL);
1522+ goto error;
1523+ }
1524+
1525+ /* let the user know what node this device is now attached to */
1526+ dev_info(&interface->dev,
1527+ "USB CEDUSB device now attached to cedusb #%d",
1528+ interface->minor);
1529+ return 0;
1530+
1531+error:
1532+ if (pdx)
1533+ kref_put(&pdx->kref, ced_delete); // frees allocated memory
1534+ return retval;
1535+}
1536+
1537+static void ced_disconnect(struct usb_interface *interface)
1538+{
1539+ DEVICE_EXTENSION *pdx = usb_get_intfdata(interface);
1540+ int minor = interface->minor; // save for message at the end
1541+ int i;
1542+
1543+ usb_set_intfdata(interface, NULL); // remove the pdx from the interface
1544+ usb_deregister_dev(interface, &ced_class); // give back our minor device number
1545+
1546+ mutex_lock(&pdx->io_mutex); // stop more I/O starting while...
1547+ ced_draw_down(pdx); // ...wait for then kill any io
1548+ for (i = 0; i < MAX_TRANSAREAS; ++i) {
1549+ int iErr = ClearArea(pdx, i); // ...release any used memory
1550+ if (iErr == U14ERR_UNLOCKFAIL)
1551+ dev_err(&pdx->interface->dev, "%s Area %d was in used",
1552+ __func__, i);
1553+ }
1554+ pdx->interface = NULL; // ...we kill off link to interface
1555+ mutex_unlock(&pdx->io_mutex);
1556+
1557+ usb_kill_anchored_urbs(&pdx->submitted);
1558+
1559+ kref_put(&pdx->kref, ced_delete); // decrement our usage count
1560+
1561+ dev_info(&interface->dev, "USB cedusb #%d now disconnected", minor);
1562+}
1563+
1564+// Wait for all the urbs we know of to be done with, then kill off any that
1565+// are left. NBNB we will need to have a mechanism to stop circular xfers
1566+// from trying to fire off more urbs. We will wait up to 3 seconds for Urbs
1567+// to be done.
1568+void ced_draw_down(DEVICE_EXTENSION * pdx)
1569+{
1570+ int time;
1571+ dev_dbg(&pdx->interface->dev, "%s called", __func__);
1572+
1573+ pdx->bInDrawDown = true;
1574+ time = usb_wait_anchor_empty_timeout(&pdx->submitted, 3000);
1575+ if (!time) // if we timed out we kill the urbs
1576+ {
1577+ usb_kill_anchored_urbs(&pdx->submitted);
1578+ dev_err(&pdx->interface->dev, "%s timed out", __func__);
1579+ }
1580+ pdx->bInDrawDown = false;
1581+}
1582+
1583+static int ced_suspend(struct usb_interface *intf, pm_message_t message)
1584+{
1585+ DEVICE_EXTENSION *pdx = usb_get_intfdata(intf);
1586+ if (!pdx)
1587+ return 0;
1588+ ced_draw_down(pdx);
1589+
1590+ dev_dbg(&pdx->interface->dev, "%s called", __func__);
1591+ return 0;
1592+}
1593+
1594+static int ced_resume(struct usb_interface *intf)
1595+{
1596+ DEVICE_EXTENSION *pdx = usb_get_intfdata(intf);
1597+ if (!pdx)
1598+ return 0;
1599+ dev_dbg(&pdx->interface->dev, "%s called", __func__);
1600+ return 0;
1601+}
1602+
1603+static int ced_pre_reset(struct usb_interface *intf)
1604+{
1605+ DEVICE_EXTENSION *pdx = usb_get_intfdata(intf);
1606+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1607+ mutex_lock(&pdx->io_mutex);
1608+ ced_draw_down(pdx);
1609+ return 0;
1610+}
1611+
1612+static int ced_post_reset(struct usb_interface *intf)
1613+{
1614+ DEVICE_EXTENSION *pdx = usb_get_intfdata(intf);
1615+ dev_dbg(&pdx->interface->dev, "%s", __func__);
1616+
1617+ /* we are sure no URBs are active - no locking needed */
1618+ pdx->errors = -EPIPE;
1619+ mutex_unlock(&pdx->io_mutex);
1620+
1621+ return 0;
1622+}
1623+
1624+static struct usb_driver ced_driver = {
1625+ .name = "cedusb",
1626+ .probe = ced_probe,
1627+ .disconnect = ced_disconnect,
1628+ .suspend = ced_suspend,
1629+ .resume = ced_resume,
1630+ .pre_reset = ced_pre_reset,
1631+ .post_reset = ced_post_reset,
1632+ .id_table = ced_table,
1633+ .supports_autosuspend = 1,
1634+};
1635+
1636+module_usb_driver(ced_driver);
1637+MODULE_LICENSE("GPL");
drivers/staging/ced1401/usb1401.h+249−0
@@ -0,0 +1,249 @@
1+/* usb1401.h
2+ Header file for the CED 1401 USB device driver for Linux
3+ Copyright (C) 2010 Cambridge Electronic Design Ltd
4+ Author Greg P Smith (greg@ced.co.uk)
5+
6+ This program is free software; you can redistribute it and/or
7+ modify it under the terms of the GNU General Public License
8+ as published by the Free Software Foundation; either version 2
9+ of the License, or (at your option) any later version.
10+
11+ This program is distributed in the hope that it will be useful,
12+ but WITHOUT ANY WARRANTY; without even the implied warranty of
13+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+ GNU General Public License for more details.
15+
16+ You should have received a copy of the GNU General Public License
17+ along with this program; if not, write to the Free Software
18+ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19+*/
20+#ifndef __USB1401_H__
21+#define __USB1401_H__
22+#include "use1401.h"
23+#include "ced_ioctl.h"
24+
25+#ifndef UINT
26+#define UINT unsigned int
27+#endif
28+
29+/// Device type codes, but these don't need to be extended - a succession is assumed
30+/// These are set for usb from the bcdDevice field (suitably mangled). Future devices
31+/// will be added in order of device creation to the list, so the names here are just
32+/// to help use remember which device is which. The U14ERR_... values follow the same
33+/// pattern for modern devices.
34+#define TYPEUNKNOWN -1 // dont know
35+#define TYPE1401 0 // standard 1401
36+#define TYPEPLUS 1 // 1401 plus
37+#define TYPEU1401 2 // u1401
38+#define TYPEPOWER 3 // Power1401
39+#define TYPEU14012 4 // u1401 mkII
40+#define TYPEPOWER2 5 // Power1401 mk II
41+#define TYPEMICRO3 6 // Micro1401-3
42+#define TYPEPOWER3 7 // Power1401-3
43+
44+/// Some useful defines of constants. DONT FORGET to change the version in the
45+/// resources whenever you change it here!.
46+#define DRIVERMAJREV 2 // driver revision level major (match windows)
47+#define DRIVERMINREV 0 // driver revision level minor
48+
49+/// Definitions of the various block transfer command codes
50+#define TM_EXTTOHOST 8 // extended tohost
51+#define TM_EXTTO1401 9 // extended to1401
52+
53+/// Definitions of values in usbReqtype. Used in sorting out setup actions
54+#define H_TO_D 0x00
55+#define D_TO_H 0x80
56+#define VENDOR 0x40
57+#define DEVREQ 0x00
58+#define INTREQ 0x01
59+#define ENDREQ 0x02
60+
61+/// Definition of values in usbRequest, again used to sort out setup
62+#define GET_STATUS 0x00
63+#define CLEAR_FEATURE 0x01
64+#define SET_FEATURE 0x03
65+#define SET_ADDRESS 0x05
66+#define GET_DESC 0x06
67+#define SET_DESC 0x07
68+#define GET_CONF 0x08
69+#define SET_CONF 0x09
70+#define GET_INTERFACE 0x0a
71+#define SET_INTERFACE 0x0b
72+#define SYNCH_FRAME 0x0c
73+
74+/// Definitions of the various debug command codes understood by the 1401. These
75+/// are used in various vendor-specific commands to achieve the desired effect
76+#define DB_GRAB 0x50 /* Grab is a NOP for USB */
77+#define DB_FREE 0x51 /* Free is a NOP for the USB */
78+#define DB_SETADD 0x52 /* Set debug address (double) */
79+#define DB_SELFTEST 0x53 /* Start self test */
80+#define DB_SETMASK 0x54 /* Set enable mask (double) */
81+#define DB_SETDEF 0x55 /* Set default mask (double) */
82+#define DB_PEEK 0x56 /* Peek address, save result */
83+#define DB_POKE 0x57 /* Poke address with data (double) */
84+#define DB_RAMPD 0x58 /* Ramp data at debug address */
85+#define DB_RAMPA 0x59 /* Ramp address bus */
86+#define DB_REPEATS 0x5A /* Set repeats for operations (double) */
87+#define DB_WIDTH 0x5B /* Set width for operations (byte) */
88+#define DB_DATA 0x5C /* Get 4-byte data read by PEEK */
89+#define DB_CHARS 0x5D /* Send chars via EP0 control write */
90+
91+#define CR_CHAR 0x0D /* The carriage return character */
92+#define CR_CHAR_80 0x8d /* and with bit 7 set */
93+
94+/// A structure holding information about a block of memory for use in circular transfers
95+typedef struct circBlk
96+{
97+ volatile UINT dwOffset; /* Offset within area of block start */
98+ volatile UINT dwSize; /* Size of the block, in bytes (0 = unused) */
99+} CIRCBLK;
100+
101+/// A structure holding all of the information about a transfer area - an area of
102+/// memory set up for use either as a source or destination in DMA transfers.
103+typedef struct transarea
104+{
105+ void* lpvBuff; // User address of xfer area saved for completeness
106+ UINT dwBaseOffset; // offset to start of xfer area in first page
107+ UINT dwLength; // Length of xfer area, in bytes
108+ struct page **pPages; // Points at array of locked down pages
109+ int nPages; // number of pages that are locked down
110+ bool bUsed; // Is this structure in use?
111+ bool bCircular; // Is this area for circular transfers?
112+ bool bCircToHost; // Flag for direction of circular transfer
113+ bool bEventToHost; // Set event on transfer to host?
114+ int iWakeUp; // Set 1 on event, cleared by TestEvent()
115+ UINT dwEventSt; // Defines section within xfer area for...
116+ UINT dwEventSz; // ...notification by the event SZ is 0 if unset
117+ CIRCBLK aBlocks[2]; // Info on a pair of circular blocks
118+ wait_queue_head_t wqEvent; // The wait queue for events in this area MUST BE LAST
119+} TRANSAREA;
120+
121+/// The DMADESC structure is used to hold information on the transfer in progress. It
122+/// is set up by ReadDMAInfo, using information sent by the 1401 in an escape sequence.
123+typedef struct dmadesc
124+{
125+ unsigned short wTransType; /* transfer type as TM_xxx above */
126+ unsigned short wIdent; /* identifier word */
127+ unsigned int dwSize; /* bytes to transfer */
128+ unsigned int dwOffset; /* offset into transfer area for trans */
129+ bool bOutWard; /* true when data is going TO 1401 */
130+} DMADESC;
131+
132+#define INBUF_SZ 256 /* input buffer size */
133+#define OUTBUF_SZ 256 /* output buffer size */
134+#define STAGED_SZ 0x10000 // size of coherent buffer for staged transfers
135+
136+/// Structure to hold all of our device specific stuff. We are making this as similar as we
137+/// can to the Windows driver to help in our understanding of what is going on.
138+typedef struct _DEVICE_EXTENSION
139+{
140+ char inputBuffer[INBUF_SZ]; /* The two buffers */
141+ char outputBuffer[OUTBUF_SZ]; /* accessed by the host functions */
142+ volatile unsigned int dwNumInput; /* num of chars in input buffer */
143+ volatile unsigned int dwInBuffGet; /* where to get from input buffer */
144+ volatile unsigned int dwInBuffPut; /* where to put into input buffer */
145+ volatile unsigned int dwNumOutput; /* num of chars in output buffer */
146+ volatile unsigned int dwOutBuffGet; /* where to get from output buffer*/
147+ volatile unsigned int dwOutBuffPut; /* where to put into output buffer*/
148+
149+ volatile bool bSendCharsPending; /* Flag to indicate sendchar active */
150+ volatile bool bReadCharsPending; /* Flag to indicate a read is primed */
151+ char* pCoherCharOut; /* special aligned buffer for chars to 1401 */
152+ struct urb* pUrbCharOut; /* urb used for chars to 1401 */
153+ char* pCoherCharIn; /* special aligned buffer for chars to host */
154+ struct urb* pUrbCharIn; /* urb used for chars to host */
155+
156+ spinlock_t charOutLock; /* to protect the outputBuffer and outputting */
157+ spinlock_t charInLock; /* to protect the inputBuffer and char reads */
158+ __u8 bInterval; /* Interrupt end point interval */
159+
160+ volatile unsigned int dwDMAFlag; /* state of DMA */
161+ TRANSAREA rTransDef[MAX_TRANSAREAS];/* transfer area info */
162+ volatile DMADESC rDMAInfo; // info on current DMA transfer
163+ volatile bool bXFerWaiting; // Flag set if DMA transfer stalled
164+ volatile bool bInDrawDown; // Flag that we want to halt transfers
165+
166+ // Parameters relating to a block read\write that is in progress. Some of these values
167+ // are equivalent to values in rDMAInfo. The values here are those in use, while those
168+ // in rDMAInfo are those recieved from the 1401 via an escape sequence. If another
169+ // escape sequence arrives before the previous xfer ends, rDMAInfo values are updated while these
170+ // are used to finish off the current transfer.
171+ volatile short StagedId; // The transfer area id for this transfer
172+ volatile bool StagedRead; // Flag TRUE for read from 1401, FALSE for write
173+ volatile unsigned int StagedLength; // Total length of this transfer
174+ volatile unsigned int StagedOffset; // Offset within memory area for transfer start
175+ volatile unsigned int StagedDone; // Bytes transferred so far
176+ volatile bool bStagedUrbPending; // Flag to indicate active
177+ char* pCoherStagedIO; // buffer used for block transfers
178+ struct urb* pStagedUrb; // The URB to use
179+ spinlock_t stagedLock; // protects ReadWriteMem() and circular buffer stuff
180+
181+ short s1401Type; // type of 1401 attached
182+ short sCurrentState; // current error state
183+ bool bIsUSB2; // type of the interface we connect to
184+ bool bForceReset; // Flag to make sure we get a real reset
185+ __u32 statBuf[2]; // buffer for 1401 state info
186+
187+ unsigned long ulSelfTestTime; // used to timeout self test
188+
189+ int nPipes; // Should be 3 or 4 depending on 1401 usb chip
190+ int bPipeError[4]; // set non-zero if an error on one of the pipe
191+ __u8 epAddr[4]; // addresses of the 3/4 end points
192+
193+ struct usb_device *udev; // the usb device for this device
194+ struct usb_interface *interface; // the interface for this device, NULL if removed
195+ struct usb_anchor submitted; // in case we need to retract our submissions
196+ struct mutex io_mutex; // synchronize I/O with disconnect, one user-mode caller at a time
197+
198+ int errors; // the last request tanked
199+ int open_count; // count the number of openers
200+ spinlock_t err_lock; // lock for errors
201+ struct kref kref;
202+}DEVICE_EXTENSION, *PDEVICE_EXTENSION;
203+#define to_DEVICE_EXTENSION(d) container_of(d, DEVICE_EXTENSION, kref)
204+
205+/// Definitions of routimes used between compilation object files
206+// in usb1401.c
207+extern int Allowi(DEVICE_EXTENSION* pdx, bool bInCallback);
208+extern int SendChars(DEVICE_EXTENSION* pdx);
209+extern void ced_draw_down(DEVICE_EXTENSION *pdx);
210+extern int ReadWriteMem(DEVICE_EXTENSION *pdx, bool Read, unsigned short wIdent,
211+ unsigned int dwOffs, unsigned int dwLen);
212+
213+// in ced_ioc.c
214+extern int ClearArea(DEVICE_EXTENSION *pdx, int nArea);
215+extern int SendString(DEVICE_EXTENSION* pdx, const char __user* pData, unsigned int n);
216+extern int SendChar(DEVICE_EXTENSION *pdx, char c);
217+extern int Get1401State(DEVICE_EXTENSION* pdx, __u32* state, __u32* error);
218+extern int ReadWrite_Cancel(DEVICE_EXTENSION *pdx);
219+extern bool Is1401(DEVICE_EXTENSION* pdx);
220+extern bool QuickCheck(DEVICE_EXTENSION* pdx, bool bTestBuff, bool bCanReset);
221+extern int Reset1401(DEVICE_EXTENSION *pdx);
222+extern int GetChar(DEVICE_EXTENSION *pdx);
223+extern int GetString(DEVICE_EXTENSION *pdx, char __user* pUser, int n);
224+extern int SetTransfer(DEVICE_EXTENSION *pdx, TRANSFERDESC __user *pTD);
225+extern int UnsetTransfer(DEVICE_EXTENSION *pdx, int nArea);
226+extern int SetEvent(DEVICE_EXTENSION *pdx, TRANSFEREVENT __user*pTE);
227+extern int Stat1401(DEVICE_EXTENSION *pdx);
228+extern int LineCount(DEVICE_EXTENSION *pdx);
229+extern int GetOutBufSpace(DEVICE_EXTENSION *pdx);
230+extern int GetTransfer(DEVICE_EXTENSION *pdx, TGET_TX_BLOCK __user *pGTB);
231+extern int KillIO1401(DEVICE_EXTENSION *pdx);
232+extern int BlkTransState(DEVICE_EXTENSION *pdx);
233+extern int StateOf1401(DEVICE_EXTENSION *pdx);
234+extern int StartSelfTest(DEVICE_EXTENSION *pdx);
235+extern int CheckSelfTest(DEVICE_EXTENSION *pdx, TGET_SELFTEST __user *pGST);
236+extern int TypeOf1401(DEVICE_EXTENSION *pdx);
237+extern int TransferFlags(DEVICE_EXTENSION *pdx);
238+extern int DbgPeek(DEVICE_EXTENSION *pdx, TDBGBLOCK __user* pDB);
239+extern int DbgPoke(DEVICE_EXTENSION *pdx, TDBGBLOCK __user *pDB);
240+extern int DbgRampData(DEVICE_EXTENSION *pdx, TDBGBLOCK __user *pDB);
241+extern int DbgRampAddr(DEVICE_EXTENSION *pdx, TDBGBLOCK __user *pDB);
242+extern int DbgGetData(DEVICE_EXTENSION *pdx, TDBGBLOCK __user *pDB);
243+extern int DbgStopLoop(DEVICE_EXTENSION *pdx);
244+extern int SetCircular(DEVICE_EXTENSION *pdx, TRANSFERDESC __user *pTD);
245+extern int GetCircBlock(DEVICE_EXTENSION *pdx, TCIRCBLOCK __user* pCB);
246+extern int FreeCircBlock(DEVICE_EXTENSION *pdx, TCIRCBLOCK __user* pCB);
247+extern int WaitEvent(DEVICE_EXTENSION *pdx, int nArea, int msTimeOut);
248+extern int TestEvent(DEVICE_EXTENSION *pdx, int nArea);
249+#endif
drivers/staging/ced1401/use1401.h+287−0
@@ -0,0 +1,287 @@
1+/****************************************************************************
2+** use1401.h
3+** Copyright (C) Cambridge Electronic Design Ltd, 1992-2010
4+** Authors: Paul Cox, Tim Bergel, Greg Smith
5+** See CVS for revisions.
6+**
7+** Because the size of a long is different between 32-bit and 64-bit on some
8+** systems, we avoid this in this interface.
9+****************************************************************************/
10+#ifndef __USE1401_H__
11+#define __USE1401_H__
12+#include "machine.h"
13+
14+// Some definitions to make things compatible. If you want to use Use1401 directly
15+// from a Windows program you should define U14_NOT_DLL, in which case you also
16+// MUST make sure that your application startup code calls U14InitLib().
17+// DLL_USE1401 is defined when you are building the Use1401 dll, not otherwise.
18+#ifdef _IS_WINDOWS_
19+#ifndef U14_NOT_DLL
20+#ifdef DLL_USE1401
21+#define U14API(retType) retType DllExport __stdcall
22+#else
23+#define U14API(retType) retType DllImport __stdcall
24+#endif
25+#endif
26+
27+#define U14ERRBASE -500
28+#define U14LONG long
29+#endif
30+
31+#ifdef LINUX
32+#define U14ERRBASE -1000
33+#define U14LONG int
34+#endif
35+
36+#ifdef _QT
37+#ifndef U14_NOT_DLL
38+#undef U14API
39+#define U14API(retType) retType __declspec(dllimport) __stdcall
40+#endif
41+#undef U14LONG
42+#define U14LONG int
43+#endif
44+
45+#ifndef U14API
46+#define U14API(retType) retType
47+#endif
48+
49+#ifndef U14LONG
50+#define U14LONG long
51+#endif
52+
53+/// Error codes: We need them here as user space can see them.
54+#define U14ERR_NOERROR 0 // no problems
55+
56+/// Device error codes, but these don't need to be extended - a succession is assumed
57+#define U14ERR_STD 4 // standard 1401 connected
58+#define U14ERR_U1401 5 // u1401 connected
59+#define U14ERR_PLUS 6 // 1401 plus connected
60+#define U14ERR_POWER 7 // Power1401 connected
61+#define U14ERR_U14012 8 // u1401 mkII connected
62+#define U14ERR_POWER2 9
63+#define U14ERR_U14013 10
64+#define U14ERR_POWER3 11
65+
66+/// NBNB Error numbers need shifting as some linux error codes start at 512
67+#define U14ERR(n) (n+U14ERRBASE)
68+#define U14ERR_OFF U14ERR(0) /* 1401 there but switched off */
69+#define U14ERR_NC U14ERR(-1) /* 1401 not connected */
70+#define U14ERR_ILL U14ERR(-2) /* if present it is ill */
71+#define U14ERR_NOIF U14ERR(-3) /* I/F card missing */
72+#define U14ERR_TIME U14ERR(-4) /* 1401 failed to come ready */
73+#define U14ERR_BADSW U14ERR(-5) /* I/F card bad switches */
74+#define U14ERR_PTIME U14ERR(-6) /* 1401plus failed to come ready */
75+#define U14ERR_NOINT U14ERR(-7) /* couldn't grab the int vector */
76+#define U14ERR_INUSE U14ERR(-8) /* 1401 is already in use */
77+#define U14ERR_NODMA U14ERR(-9) /* couldn't get DMA channel */
78+#define U14ERR_BADHAND U14ERR(-10) /* handle provided was bad */
79+#define U14ERR_BAD1401NUM U14ERR(-11) /* 1401 number provided was bad */
80+
81+#define U14ERR_NO_SUCH_FN U14ERR(-20) /* no such function */
82+#define U14ERR_NO_SUCH_SUBFN U14ERR(-21) /* no such sub function */
83+#define U14ERR_NOOUT U14ERR(-22) /* no room in output buffer */
84+#define U14ERR_NOIN U14ERR(-23) /* no input in buffer */
85+#define U14ERR_STRLEN U14ERR(-24) /* string longer than buffer */
86+#define U14ERR_ERR_STRLEN U14ERR(-24) /* string longer than buffer */
87+#define U14ERR_LOCKFAIL U14ERR(-25) /* failed to lock memory */
88+#define U14ERR_UNLOCKFAIL U14ERR(-26) /* failed to unlock memory */
89+#define U14ERR_ALREADYSET U14ERR(-27) /* area already set up */
90+#define U14ERR_NOTSET U14ERR(-28) /* area not set up */
91+#define U14ERR_BADAREA U14ERR(-29) /* illegal area number */
92+#define U14ERR_FAIL U14ERR(-30) /* we failed for some other reason*/
93+
94+#define U14ERR_NOFILE U14ERR(-40) /* command file not found */
95+#define U14ERR_READERR U14ERR(-41) /* error reading command file */
96+#define U14ERR_UNKNOWN U14ERR(-42) /* unknown command */
97+#define U14ERR_HOSTSPACE U14ERR(-43) /* not enough host space to load */
98+#define U14ERR_LOCKERR U14ERR(-44) /* could not lock resource/command*/
99+#define U14ERR_CLOADERR U14ERR(-45) /* CLOAD command failed */
100+
101+#define U14ERR_TOXXXERR U14ERR(-60) /* tohost/1401 failed */
102+#define U14ERR_NO386ENH U14ERR(-80) /* not 386 enhanced mode */
103+#define U14ERR_NO1401DRIV U14ERR(-81) /* no device driver */
104+#define U14ERR_DRIVTOOOLD U14ERR(-82) /* device driver too old */
105+
106+#define U14ERR_TIMEOUT U14ERR(-90) /* timeout occurred */
107+
108+#define U14ERR_BUFF_SMALL U14ERR(-100) /* buffer for getstring too small */
109+#define U14ERR_CBALREADY U14ERR(-101) /* there is already a callback */
110+#define U14ERR_BADDEREG U14ERR(-102) /* bad parameter to deregcallback */
111+#define U14ERR_NOMEMORY U14ERR(-103) /* no memory for allocation */
112+
113+#define U14ERR_DRIVCOMMS U14ERR(-110) /* failed talking to driver */
114+#define U14ERR_OUTOFMEMORY U14ERR(-111) /* needed memory and couldnt get it*/
115+
116+/// 1401 type codes.
117+#define U14TYPE1401 0 /* standard 1401 */
118+#define U14TYPEPLUS 1 /* 1401 plus */
119+#define U14TYPEU1401 2 /* u1401 */
120+#define U14TYPEPOWER 3 /* power1401 */
121+#define U14TYPEU14012 4 /* u1401 mk II */
122+#define U14TYPEPOWER2 5 /* power1401 mk II */
123+#define U14TYPEU14013 6 /* u1401-3 */
124+#define U14TYPEPOWER3 7 /* power1401-3 */
125+#define U14TYPEUNKNOWN -1 /* dont know */
126+
127+/// Transfer flags to allow driver capabilities to be interrogated
128+
129+/// Constants for transfer flags
130+#define U14TF_USEDMA 1 /* Transfer flag for use DMA */
131+#define U14TF_MULTIA 2 /* Transfer flag for multi areas */
132+#define U14TF_FIFO 4 /* for FIFO interface card */
133+#define U14TF_USB2 8 /* for USB2 interface and 1401 */
134+#define U14TF_NOTIFY 16 /* for event notifications */
135+#define U14TF_SHORT 32 /* for PCI can short cycle */
136+#define U14TF_PCI2 64 /* for new PCI card 1401-70 */
137+#define U14TF_CIRCTH 128 /* Circular-mode to host */
138+#define U14TF_DIAG 256 /* Diagnostics/debug functions */
139+#define U14TF_CIRC14 512 /* Circular-mode to 1401 */
140+
141+/// Definitions of element sizes for DMA transfers - to allow byte-swapping
142+#define ESZBYTES 0 /* BYTE element size value */
143+#define ESZWORDS 1 /* WORD element size value */
144+#define ESZLONGS 2 /* long element size value */
145+#define ESZUNKNOWN 0 /* unknown element size value */
146+
147+/// These define required access types for the debug/diagnostics function
148+#define BYTE_SIZE 1 /* 8-bit access */
149+#define WORD_SIZE 2 /* 16-bit access */
150+#define LONG_SIZE 3 /* 32-bit access */
151+
152+/// Stuff used by U14_GetTransfer
153+#define GET_TX_MAXENTRIES 257 /* (max length / page size + 1) */
154+
155+#ifdef _IS_WINDOWS_
156+#pragma pack(1)
157+
158+typedef struct /* used for U14_GetTransfer results */
159+{ /* Info on a single mapped block */
160+ U14LONG physical;
161+ U14LONG size;
162+} TXENTRY;
163+
164+typedef struct TGetTxBlock /* used for U14_GetTransfer results */
165+{ /* matches structure in VXD */
166+ U14LONG size;
167+ U14LONG linear;
168+ short seg;
169+ short reserved;
170+ short avail; /* number of available entries */
171+ short used; /* number of used entries */
172+ TXENTRY entries[GET_TX_MAXENTRIES]; /* Array of mapped block info */
173+} TGET_TX_BLOCK;
174+
175+typedef TGET_TX_BLOCK *LPGET_TX_BLOCK;
176+
177+#pragma pack()
178+#endif
179+
180+#ifdef LINUX
181+typedef struct /* used for U14_GetTransfer results */
182+{ /* Info on a single mapped block */
183+ long long physical;
184+ long size;
185+} TXENTRY;
186+
187+typedef struct TGetTxBlock /* used for U14_GetTransfer results */
188+{ /* matches structure in VXD */
189+ long long linear; /* linear address */
190+ long size; /* total size of the mapped area, holds id when called */
191+ short seg; /* segment of the address for Win16 */
192+ short reserved;
193+ short avail; /* number of available entries */
194+ short used; /* number of used entries */
195+ TXENTRY entries[GET_TX_MAXENTRIES]; /* Array of mapped block info */
196+} TGET_TX_BLOCK;
197+#endif
198+
199+#ifdef __cplusplus
200+extern "C" {
201+#endif
202+
203+U14API(int) U14WhenToTimeOut(short hand); // when to timeout in ms
204+U14API(short) U14PassedTime(int iTime); // non-zero if iTime passed
205+
206+U14API(short) U14LastErrCode(short hand);
207+
208+U14API(short) U14Open1401(short n1401);
209+U14API(short) U14Close1401(short hand);
210+U14API(short) U14Reset1401(short hand);
211+U14API(short) U14ForceReset(short hand);
212+U14API(short) U14TypeOf1401(short hand);
213+U14API(short) U14NameOf1401(short hand, char* pBuf, WORD wMax);
214+
215+U14API(short) U14Stat1401(short hand);
216+U14API(short) U14CharCount(short hand);
217+U14API(short) U14LineCount(short hand);
218+
219+U14API(short) U14SendString(short hand, const char* pString);
220+U14API(short) U14GetString(short hand, char* pBuffer, WORD wMaxLen);
221+U14API(short) U14SendChar(short hand, char cChar);
222+U14API(short) U14GetChar(short hand, char* pcChar);
223+
224+U14API(short) U14LdCmd(short hand, const char* command);
225+U14API(DWORD) U14Ld(short hand, const char* vl, const char* str);
226+
227+U14API(short) U14SetTransArea(short hand, WORD wArea, void *pvBuff,
228+ DWORD dwLength, short eSz);
229+U14API(short) U14UnSetTransfer(short hand, WORD wArea);
230+U14API(short) U14SetTransferEvent(short hand, WORD wArea, BOOL bEvent,
231+ BOOL bToHost, DWORD dwStart, DWORD dwLength);
232+U14API(int) U14TestTransferEvent(short hand, WORD wArea);
233+U14API(int) U14WaitTransferEvent(short hand, WORD wArea, int msTimeOut);
234+U14API(short) U14GetTransfer(short hand, TGET_TX_BLOCK *pTransBlock);
235+
236+U14API(short) U14ToHost(short hand, char* pAddrHost,DWORD dwSize,DWORD dw1401,
237+ short eSz);
238+U14API(short) U14To1401(short hand, const char* pAddrHost,DWORD dwSize,DWORD dw1401,
239+ short eSz);
240+
241+U14API(short) U14SetCircular(short hand, WORD wArea, BOOL bToHost, void *pvBuff,
242+ DWORD dwLength);
243+
244+U14API(int) U14GetCircBlk(short hand, WORD wArea, DWORD *pdwOffs);
245+U14API(int) U14FreeCircBlk(short hand, WORD wArea, DWORD dwOffs, DWORD dwSize,
246+ DWORD *pdwOffs);
247+
248+U14API(short) U14StrToLongs(const char* pszBuff, U14LONG *palNums, short sMaxLongs);
249+U14API(short) U14LongsFrom1401(short hand, U14LONG *palBuff, short sMaxLongs);
250+
251+U14API(void) U14SetTimeout(short hand, int lTimeout);
252+U14API(int) U14GetTimeout(short hand);
253+U14API(short) U14OutBufSpace(short hand);
254+U14API(int) U14BaseAddr1401(short hand);
255+U14API(int) U14DriverVersion(short hand);
256+U14API(int) U14DriverType(short hand);
257+U14API(short) U14DriverName(short hand, char* pBuf, WORD wMax);
258+U14API(short) U14GetUserMemorySize(short hand, DWORD *pMemorySize);
259+U14API(short) U14KillIO1401(short hand);
260+
261+U14API(short) U14BlkTransState(short hand);
262+U14API(short) U14StateOf1401(short hand);
263+
264+U14API(short) U14Grab1401(short hand);
265+U14API(short) U14Free1401(short hand);
266+U14API(short) U14Peek1401(short hand, DWORD dwAddr, int nSize, int nRepeats);
267+U14API(short) U14Poke1401(short hand, DWORD dwAddr, DWORD dwValue, int nSize, int nRepeats);
268+U14API(short) U14Ramp1401(short hand, DWORD dwAddr, DWORD dwDef, DWORD dwEnable, int nSize, int nRepeats);
269+U14API(short) U14RampAddr(short hand, DWORD dwDef, DWORD dwEnable, int nSize, int nRepeats);
270+U14API(short) U14StopDebugLoop(short hand);
271+U14API(short) U14GetDebugData(short hand, U14LONG *plValue);
272+
273+U14API(short) U14StartSelfTest(short hand);
274+U14API(short) U14CheckSelfTest(short hand, U14LONG *pData);
275+U14API(short) U14TransferFlags(short hand);
276+U14API(void) U14GetErrorString(short nErr, char* pStr, WORD wMax);
277+U14API(int) U14MonitorRev(short hand);
278+U14API(void) U14CloseAll(void);
279+
280+U14API(short) U14WorkingSet(DWORD dwMinKb, DWORD dwMaxKb);
281+U14API(int) U14InitLib(void);
282+
283+#ifdef __cplusplus
284+}
285+#endif
286+
287+#endif /* End of ifndef __USE1401_H__ */
drivers/staging/ced1401/use14_ioc.h+301−0
@@ -0,0 +1,301 @@
1+/* use14_ioc.h
2+** definitions of use1401 module stuff that is shared between use1401 and the driver.
3+** Copyright (C) Cambridge Electronic Design Limited 2010
4+** Author Greg P Smith
5+************************************************************************************/
6+#ifndef __USE14_IOC_H__
7+#define __USE14_IOC_H__
8+
9+#define MAX_TRANSAREAS 8 /* The number of transfer areas supported by driver */
10+
11+#define i386
12+#include "winioctl.h" /* needed so we can access driver */
13+
14+/*
15+** Defines for IOCTL functions to ask driver to perform. These must be matched
16+** in both use1401 and in the driver. The IOCTL code contains a command
17+** identifier, plus other information about the device, the type of access
18+** with which the file must have been opened, and the type of buffering.
19+** The IOCTL function codes from 0x80 to 0xFF are for developer use.
20+*/
21+#define FILE_DEVICE_CED1401 0x8001
22+#define FNNUMBASE 0x800
23+
24+#define U14_OPEN1401 CTL_CODE( FILE_DEVICE_CED1401, \
25+ FNNUMBASE, \
26+ METHOD_BUFFERED, \
27+ FILE_ANY_ACCESS)
28+
29+#define U14_CLOSE1401 CTL_CODE( FILE_DEVICE_CED1401, \
30+ FNNUMBASE+1, \
31+ METHOD_BUFFERED, \
32+ FILE_ANY_ACCESS)
33+
34+#define U14_SENDSTRING CTL_CODE( FILE_DEVICE_CED1401, \
35+ FNNUMBASE+2, \
36+ METHOD_BUFFERED, \
37+ FILE_ANY_ACCESS)
38+
39+#define U14_RESET1401 CTL_CODE( FILE_DEVICE_CED1401, \
40+ FNNUMBASE+3, \
41+ METHOD_BUFFERED, \
42+ FILE_ANY_ACCESS)
43+
44+#define U14_GETCHAR CTL_CODE( FILE_DEVICE_CED1401, \
45+ FNNUMBASE+4, \
46+ METHOD_BUFFERED, \
47+ FILE_ANY_ACCESS)
48+
49+#define U14_SENDCHAR CTL_CODE( FILE_DEVICE_CED1401, \
50+ FNNUMBASE+5, \
51+ METHOD_BUFFERED, \
52+ FILE_ANY_ACCESS)
53+
54+#define U14_STAT1401 CTL_CODE( FILE_DEVICE_CED1401, \
55+ FNNUMBASE+6, \
56+ METHOD_BUFFERED, \
57+ FILE_ANY_ACCESS)
58+
59+#define U14_LINECOUNT CTL_CODE( FILE_DEVICE_CED1401, \
60+ FNNUMBASE+7, \
61+ METHOD_BUFFERED, \
62+ FILE_ANY_ACCESS)
63+
64+#define U14_GETSTRING CTL_CODE( FILE_DEVICE_CED1401, \
65+ FNNUMBASE+8, \
66+ METHOD_BUFFERED, \
67+ FILE_ANY_ACCESS)
68+
69+#define U14_REGCALLBACK CTL_CODE( FILE_DEVICE_CED1401, \
70+ FNNUMBASE+9, \
71+ METHOD_BUFFERED, \
72+ FILE_ANY_ACCESS)
73+
74+#define U14_GETMONITORBUF CTL_CODE( FILE_DEVICE_CED1401, \
75+ FNNUMBASE+10, \
76+ METHOD_BUFFERED, \
77+ FILE_ANY_ACCESS)
78+
79+#define U14_SETTRANSFER CTL_CODE( FILE_DEVICE_CED1401, \
80+ FNNUMBASE+11, \
81+ METHOD_BUFFERED, \
82+ FILE_ANY_ACCESS)
83+
84+#define U14_UNSETTRANSFER CTL_CODE( FILE_DEVICE_CED1401, \
85+ FNNUMBASE+12, \
86+ METHOD_BUFFERED, \
87+ FILE_ANY_ACCESS)
88+
89+#define U14_SETTRANSEVENT CTL_CODE( FILE_DEVICE_CED1401, \
90+ FNNUMBASE+13, \
91+ METHOD_BUFFERED, \
92+ FILE_ANY_ACCESS)
93+
94+#define U14_GETOUTBUFSPACE CTL_CODE( FILE_DEVICE_CED1401, \
95+ FNNUMBASE+14, \
96+ METHOD_BUFFERED, \
97+ FILE_ANY_ACCESS)
98+
99+#define U14_GETBASEADDRESS CTL_CODE( FILE_DEVICE_CED1401, \
100+ FNNUMBASE+15, \
101+ METHOD_BUFFERED, \
102+ FILE_ANY_ACCESS)
103+
104+#define U14_GETDRIVERREVISION CTL_CODE( FILE_DEVICE_CED1401, \
105+ FNNUMBASE+16, \
106+ METHOD_BUFFERED, \
107+ FILE_ANY_ACCESS)
108+
109+#define U14_GETTRANSFER CTL_CODE( FILE_DEVICE_CED1401, \
110+ FNNUMBASE+17, \
111+ METHOD_BUFFERED, \
112+ FILE_ANY_ACCESS)
113+
114+#define U14_KILLIO1401 CTL_CODE( FILE_DEVICE_CED1401, \
115+ FNNUMBASE+18, \
116+ METHOD_BUFFERED, \
117+ FILE_ANY_ACCESS)
118+
119+#define U14_BLKTRANSSTATE CTL_CODE( FILE_DEVICE_CED1401, \
120+ FNNUMBASE+19, \
121+ METHOD_BUFFERED, \
122+ FILE_ANY_ACCESS)
123+
124+#define U14_BYTECOUNT CTL_CODE( FILE_DEVICE_CED1401, \
125+ FNNUMBASE+20, \
126+ METHOD_BUFFERED, \
127+ FILE_ANY_ACCESS)
128+
129+#define U14_ZEROBLOCKCOUNT CTL_CODE( FILE_DEVICE_CED1401, \
130+ FNNUMBASE+21, \
131+ METHOD_BUFFERED, \
132+ FILE_ANY_ACCESS)
133+
134+#define U14_STOPCIRCULAR CTL_CODE( FILE_DEVICE_CED1401, \
135+ FNNUMBASE+22, \
136+ METHOD_BUFFERED, \
137+ FILE_ANY_ACCESS)
138+
139+#define U14_STATEOF1401 CTL_CODE( FILE_DEVICE_CED1401, \
140+ FNNUMBASE+23, \
141+ METHOD_BUFFERED, \
142+ FILE_ANY_ACCESS)
143+
144+#define U14_REGISTERS1401 CTL_CODE( FILE_DEVICE_CED1401, \
145+ FNNUMBASE+24, \
146+ METHOD_BUFFERED, \
147+ FILE_ANY_ACCESS)
148+
149+#define U14_GRAB1401 CTL_CODE( FILE_DEVICE_CED1401, \
150+ FNNUMBASE+25, \
151+ METHOD_BUFFERED, \
152+ FILE_ANY_ACCESS)
153+
154+#define U14_FREE1401 CTL_CODE( FILE_DEVICE_CED1401, \
155+ FNNUMBASE+26, \
156+ METHOD_BUFFERED, \
157+ FILE_ANY_ACCESS)
158+
159+#define U14_STEP1401 CTL_CODE( FILE_DEVICE_CED1401, \
160+ FNNUMBASE+27, \
161+ METHOD_BUFFERED, \
162+ FILE_ANY_ACCESS)
163+
164+#define U14_SET1401REGISTERS CTL_CODE( FILE_DEVICE_CED1401, \
165+ FNNUMBASE+28, \
166+ METHOD_BUFFERED, \
167+ FILE_ANY_ACCESS)
168+
169+#define U14_STEPTILL1401 CTL_CODE( FILE_DEVICE_CED1401, \
170+ FNNUMBASE+29, \
171+ METHOD_BUFFERED, \
172+ FILE_ANY_ACCESS)
173+
174+#define U14_SETORIN CTL_CODE( FILE_DEVICE_CED1401, \
175+ FNNUMBASE+30, \
176+ METHOD_BUFFERED, \
177+ FILE_ANY_ACCESS)
178+
179+#define U14_STARTSELFTEST CTL_CODE( FILE_DEVICE_CED1401, \
180+ FNNUMBASE+31, \
181+ METHOD_BUFFERED, \
182+ FILE_ANY_ACCESS)
183+
184+#define U14_CHECKSELFTEST CTL_CODE( FILE_DEVICE_CED1401, \
185+ FNNUMBASE+32, \
186+ METHOD_BUFFERED, \
187+ FILE_ANY_ACCESS)
188+
189+#define U14_TYPEOF1401 CTL_CODE( FILE_DEVICE_CED1401, \
190+ FNNUMBASE+33, \
191+ METHOD_BUFFERED, \
192+ FILE_ANY_ACCESS)
193+
194+#define U14_TRANSFERFLAGS CTL_CODE( FILE_DEVICE_CED1401, \
195+ FNNUMBASE+34, \
196+ METHOD_BUFFERED, \
197+ FILE_ANY_ACCESS)
198+
199+#define U14_DBGPEEK CTL_CODE( FILE_DEVICE_CED1401, \
200+ FNNUMBASE+35, \
201+ METHOD_BUFFERED, \
202+ FILE_ANY_ACCESS)
203+
204+#define U14_DBGPOKE CTL_CODE( FILE_DEVICE_CED1401, \
205+ FNNUMBASE+36, \
206+ METHOD_BUFFERED, \
207+ FILE_ANY_ACCESS)
208+
209+#define U14_DBGRAMPDATA CTL_CODE( FILE_DEVICE_CED1401, \
210+ FNNUMBASE+37, \
211+ METHOD_BUFFERED, \
212+ FILE_ANY_ACCESS)
213+
214+#define U14_DBGRAMPADDR CTL_CODE( FILE_DEVICE_CED1401, \
215+ FNNUMBASE+38, \
216+ METHOD_BUFFERED, \
217+ FILE_ANY_ACCESS)
218+
219+#define U14_DBGGETDATA CTL_CODE( FILE_DEVICE_CED1401, \
220+ FNNUMBASE+39, \
221+ METHOD_BUFFERED, \
222+ FILE_ANY_ACCESS)
223+
224+#define U14_DBGSTOPLOOP CTL_CODE( FILE_DEVICE_CED1401, \
225+ FNNUMBASE+40, \
226+ METHOD_BUFFERED, \
227+ FILE_ANY_ACCESS)
228+
229+#define U14_FULLRESET CTL_CODE( FILE_DEVICE_CED1401, \
230+ FNNUMBASE+41, \
231+ METHOD_BUFFERED, \
232+ FILE_ANY_ACCESS)
233+
234+#define U14_SETCIRCULAR CTL_CODE( FILE_DEVICE_CED1401, \
235+ FNNUMBASE+42, \
236+ METHOD_BUFFERED, \
237+ FILE_ANY_ACCESS)
238+
239+#define U14_GETCIRCBLK CTL_CODE( FILE_DEVICE_CED1401, \
240+ FNNUMBASE+43, \
241+ METHOD_BUFFERED, \
242+ FILE_ANY_ACCESS)
243+
244+#define U14_FREECIRCBLK CTL_CODE( FILE_DEVICE_CED1401, \
245+ FNNUMBASE+44, \
246+ METHOD_BUFFERED, \
247+ FILE_ANY_ACCESS)
248+
249+//--------------- Structures that are shared with the driver -------------
250+#pragma pack(1)
251+
252+typedef struct /* used for get/set standard 1401 registers */
253+{
254+ short sPC;
255+ char A;
256+ char X;
257+ char Y;
258+ char stat;
259+ char rubbish;
260+} T1401REGISTERS;
261+
262+typedef union /* to communicate with 1401 driver status & control funcs */
263+{
264+ char chrs[22];
265+ short ints[11];
266+ long longs[5];
267+ T1401REGISTERS registers;
268+} TCSBLOCK;
269+
270+typedef TCSBLOCK* LPTCSBLOCK;
271+
272+typedef struct paramBlk
273+{
274+ short sState;
275+ TCSBLOCK csBlock;
276+} PARAMBLK;
277+
278+typedef PARAMBLK* PPARAMBLK;
279+
280+typedef struct TransferDesc /* Structure and type for SetTransArea */
281+{
282+ WORD wArea; /* number of transfer area to set up */
283+ void FAR * lpvBuff; /* address of transfer area */
284+ DWORD dwLength; /* length of area to set up */
285+ short eSize; /* size to move (for swapping on MAC) */
286+} TRANSFERDESC;
287+
288+typedef TRANSFERDESC FAR * LPTRANSFERDESC;
289+
290+/* This is the structure used to set up a transfer area */
291+typedef struct VXTransferDesc /* use1401.c and use1432x.x use only */
292+{
293+ WORD wArea; /* number of transfer area to set up */
294+ WORD wAddrSel; /* 16 bit selector for area */
295+ DWORD dwAddrOfs; /* 32 bit offset for area start */
296+ DWORD dwLength; /* length of area to set up */
297+} VXTRANSFERDESC;
298+
299+#pragma pack()
300+
301+#endif
drivers/staging/ced1401/userspace/use1401.c+3035−0
@@ -0,0 +1,3035 @@
1+/****************************************************************************
2+** use1401.c
3+** Copyright (C) Cambridge Electronic Design Ltd, 1992-2010
4+**
5+** This program is free software; you can redistribute it and/or
6+** modify it under the terms of the GNU General Public License
7+** as published by the Free Software Foundation; either version 2
8+** of the License, or (at your option) any later version.
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+** You should have received a copy of the GNU General Public License
16+** along with this program; if not, write to the Free Software
17+** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18+**
19+** Contact CED: Cambridge Electronic Design Limited, Science Park, Milton Road
20+** Cambridge, CB6 0FE.
21+** www.ced.co.uk
22+** greg@ced.co.uk
23+**
24+** Title: USE1401.C
25+** Version: 4.00
26+** Author: Paul Cox, Tim Bergel, Greg Smith
27+**
28+** The code was vigorously pruned in DEC 2010 to remove the macintosh options
29+** and to get rid of the 16-bit support. It has also been aligned with the
30+** Linux version. See CVS for revisions. This will work for Win 9x onwards.
31+****************************************************************************
32+**
33+** Notes on Windows interface to driver
34+** ************************************
35+**
36+** Under Windows 9x and NT, Use1401 uses DeviceIoControl to get access to
37+** the 1401 driver. This has parameters for the device handle, the function
38+** code, an input pointer and byte count, an output pointer and byte count
39+** and a pointer to a DWORD to hold the output byte count. Note that input
40+** and output are from the point-of-view of the driver, so the output stuff
41+** is used to read values from the 1401, not send to the 1401. The use of
42+** these parameters varies with the function in use and the operating
43+** system; there are five separate DIOC calls SendString, GetString and
44+** SetTransferArea all have their own specialised calls, the rest use the
45+** Status1401 or Control1401 functions.
46+**
47+** There are two basic styles of DIOC call used, one for Win9x VxD drivers
48+** and one for NT Kernel-mode and WDM drivers (see below for tables showing
49+** the different parameters used. The array bUseNTDIOC[] selects between
50+** these two calling styles.
51+**
52+** Function codes
53+** In Win3.x, simple function codes from 0 to 40 were used, shifted left 8
54+** bits with a sub-function code in the lower 8 bits. These were also used
55+** in the Windows 95 driver, though we had to add 1 to the code value to
56+** avoid problems (Open from CreateFile is zero), and the sub-function code
57+** is now unused. We found that this gave some problems with Windows 98
58+** as the function code values are reserved by microsoft, so we switched to
59+** using the NT function codes instead. The NT codes are generated using the
60+** CTL_CODE macro, essentially this gives 0x80012000 | (func << 2), where
61+** func is the original 0 to 34 value. The driver will handle both types of
62+** code and Use1432 only uses the NT codes if it knows the driver is new
63+** enough. The array bUseNTCodes[] holds flags on the type of codes required.
64+** GPS/TDB Dec 2010: we removed the bUseNTCodes array as this is always true
65+** as we no longer support ancient versions.
66+**
67+** The CreateFile and CloseFile function calls are also handled
68+** by DIOC, using the special function codes 0 and -1 respectively.
69+**
70+** Input pointer and buffer size
71+** These are intended for data sent to the device driver. In nearly all cases
72+** they are unused in calls to the Win95 driver, the NT driver uses them
73+** for all information sent to the driver. The table below shows the pointer
74+** and byte count used for the various calls:
75+**
76+** Win 95 Win NT
77+** SendString NULL, 0 pStr, nStr
78+** GetString NULL, 0 NULL, 0
79+** SetTransferArea pBuf, nBuf (unused?) pDesc, nDesc
80+** GetTransfer NULL, 0 NULL, 0
81+** Status1401 NULL, 0 NULL, 0
82+** Control1401 NULL, 0 pBlk, nBlk
83+**
84+** pStr and nStr are pointers to a char buffer and the buffer length for
85+** string I/O, note that these are temporary buffers owned by the DLL, not
86+** application memory, pBuf and nBuf are the transfer area buffer (I think
87+** these are unused), pDesc and nDesc are the TRANSFERDESC structure, pBlk
88+** and nBlk are the TCSBLOCK structure.
89+**
90+**
91+** Output pointer and buffer size
92+** These are intended for data read from the device driver. These are used
93+** for almost all information sent to the Win95 driver, the NT driver uses
94+** them for information read from the driver, chiefly the error code. The
95+** table below shows the pointer and byte count used for the various calls:
96+**
97+** Win 95 Win NT
98+** SendString pStr, nStr pPar, nPar
99+** GetString pStr, nStr+2 pStr, nStr+2
100+** SetTransferArea pDesc, nDesc pPar, nPar
101+** GetTransfer pGet, nGet pGet, nGet
102+** Status1401 pBlk, nBlk pPar, nPar
103+** Control1401 pBlk, nBlk pPar, nPar
104+**
105+** pStr and nStr are pointers to a char buffer and the buffer length for
106+** string I/O, the +2 for GetString refers to two spare bytes at the start
107+** used to hold the string length and returning an error code for NT. Note
108+** again that these are (and must be) DLL-owned temporary buffers. pPar
109+** and nPar are a PARAM structure used in NT (it holds an error code and a
110+** TCSBLOCK structure). pDesc and nDesc are the VXTRANSFERDESC structure,
111+** pBlk and nBlk are the TCSBLOCK structure. pGet and nGet indicate the
112+** TGET_TX_BLOCK structure used for GetTransfer.
113+**
114+**
115+** The output byte count
116+** Both drivers return the output buffer size here, regardless of the actual
117+** bytes output. This is used to check that we did get through to the driver.
118+**
119+** Multiple 1401s
120+** **************
121+**
122+** We have code that tries to support the use of multiple 1401s, but there
123+** are problems: The lDriverVersion and lDriverType variables are global, not
124+** per-1401 (a particular problem as the U14 functions that use them don't
125+** have a hand parameter). In addition, the mechansim for finding a free
126+** 1401 depends upon the 1401 device driver open operation failing if it's
127+** already in use, which doesn't always happen, particularly with the VxDs.
128+** The code in TryToOpen tries to fix this by relying on TYPEOF1401 to detect
129+** the 1401-in-use state - the VxDs contain special code to help this. This is
130+** working OK but multiple 1401 support works better with the Win2000 drivers.
131+**
132+** USB driver
133+** **********
134+**
135+** The USB driver, which runs on both Win98 and NT2000, uses the NT-style
136+** calling convention, both for the DIOC codes and the DIOC parameters. The
137+** TryToOpen function has been altered to look for an NT driver first in
138+** the appropriate circumstances, and to set the driver DIOC flags up in
139+** the correct state.
140+**
141+** Adding a new 1401 type - now almost nothing to do
142+** *************************************************
143+**
144+** The 1401 types are defined by a set of U14TYPExxxx codes in USE1401.H.
145+** You should add a new one of these to keep things tidy for applications.
146+**
147+** DRIVERET_MAX (below) specifies the maximum allowed type code from the
148+** 1401 driver; I have set this high to accomodate as yet undesigned 1401
149+** types. Similarly, as long as the command file names follow the ARM,
150+** ARN, ARO sequence, these are calculated by the ExtForType function, so
151+** you don't need to do anything here either.
152+**
153+** Version number
154+** **************
155+** The new U14InitLib() function returns 0 if the OS is incapable of use,
156+** otherwise is returns the version of the USE1401 library. This is done
157+** in three parts: Major(31-24).Minor(23-16).Revision.(15-0) (brackets are
158+** the bits used). The Major number starts at 2 for the first revision with
159+** the U14InitLib() function. Changes to the Major version means that we
160+** have broken backwards compatibility. Minor number changes mean that we
161+** have added new functionality that does not break backwards compatibility.
162+** we starts at 0. Revision changes mean we have fixed something. Each index
163+** returns to 0 when a higer one changes.
164+*/
165+#define U14LIB_MAJOR 4
166+#define U14LIB_MINOR 0
167+#define U14LIB_REVISION 0
168+#define U14LIB_VERSION ((U14LIB_MAJOR<<24) | (U14LIB_MINOR<<16) | U14LIB_REVISION)
169+
170+#include <stdlib.h>
171+#include <string.h>
172+#include <stdio.h>
173+
174+#include "USE1401.H"
175+
176+#ifdef _IS_WINDOWS_
177+#include <io.h>
178+#include <windows.h>
179+#pragma warning(disable: 4100) /* Disable "Unused formal parameter" warning */
180+#include <assert.h>
181+#include "process.h"
182+
183+
184+#define sprintf wsprintf
185+#define PATHSEP '\\'
186+#define PATHSEPSTR "\\"
187+#define DEFCMDPATH "\\1401\\" // default command path if all else fails
188+#define MINDRIVERMAJREV 1 // minimum driver revision level we need
189+#define __packed // does nothing in Windows
190+
191+#include "use14_ioc.h" // links to device driver stuff
192+#endif
193+
194+#ifdef LINUX
195+#include <fcntl.h>
196+#include <unistd.h>
197+#include <sys/ioctl.h>
198+#include <errno.h>
199+#include <sys/time.h>
200+#include <sched.h>
201+#include <libgen.h>
202+#define PATHSEP '/'
203+#define PATHSEPSTR "/"
204+#define DEFCMDPATH "/var/1401/" // default command path if all else fails
205+#define MINDRIVERMAJREV 2 // minimum driver revision level we need
206+
207+#include "ced_ioctl.h" // links to device driver stuff
208+#endif
209+
210+#define MAX1401 8 // The number of 1401s that can be supported
211+
212+/*
213+** These are the 1401 type codes returned by the driver, they are a slightly
214+** odd sequence & start for reasons of compatability with the DOS driver.
215+** The maximum code value is the upper limit of 1401 device types.
216+*/
217+#define DRIVRET_STD 4 // Codes for 1401 types matching driver values
218+#define DRIVRET_U1401 5 // This table does not need extending, as
219+#define DRIVRET_PLUS 6 // we can calculate values now.
220+#define DRIVRET_POWER 7 // but we need all of these values still
221+#define DRIVRET_MAX 26 // Maximum tolerated code - future designs
222+
223+/*
224+** These variables store data that will be used to generate the last
225+** error string. For now, a string will hold the 1401 command file name.
226+*/
227+static char szLastName[20]; // additional text information
228+
229+/*
230+** Information stored per handle. NBNB, driverType and DriverVersion used to be
231+** only stored once for all handles... i.e. nonsensical. This change means that
232+** three U14...() calls now include handles that were previously void. We have
233+** set a constructor and a destructor call for the library (see the end) to
234+** initialise important structures, or call use1401_load().
235+*/
236+static short asDriverType[MAX1401] = {0};
237+static int lLastDriverVersion = U14ERR_NO1401DRIV;
238+static int lLastDriverType = U14TYPEUNKNOWN;
239+static int alDriverVersion[MAX1401]; // version/type of each driver
240+static int alTimeOutPeriod[MAX1401]; // timeout time in milliseconds
241+static short asLastRetCode[MAX1401]; // last code from a fn call
242+static short asType1401[MAX1401] = {0}; // The type of the 1401
243+static BOOL abGrabbed[MAX1401] = {0}; // Flag for grabbed, set true by grab1401
244+static int iAttached = 0; // counts process attaches so can let go
245+
246+#ifdef _IS_WINDOWS_
247+/****************************************************************************
248+** Windows NT Specific Variables and internal types
249+****************************************************************************/
250+static HANDLE aHand1401[MAX1401] = {0}; // handles for 1401s
251+static HANDLE aXferEvent[MAX1401] = {0}; // transfer events for the 1401s
252+static LPVOID apAreas[MAX1401][MAX_TRANSAREAS]; // Locked areas
253+static DWORD auAreas[MAX1401][MAX_TRANSAREAS]; // Size of locked areas
254+static BOOL bWindows9x = FALSE; // if we are Windows 95 or better
255+#ifdef _WIN64
256+#define USE_NT_DIOC(ind) TRUE
257+#else
258+static BOOL abUseNTDIOC[MAX1401]; // Use NT-style DIOC parameters */
259+#define USE_NT_DIOC(ind) abUseNTDIOC[ind]
260+#endif
261+
262+#endif
263+
264+#ifdef LINUX
265+static int aHand1401[MAX1401] = {0}; // handles for 1401s
266+#define INVALID_HANDLE_VALUE 0 // to avoid code differences
267+#endif
268+
269+
270+/*
271+** The CmdHead relates to backwards compatibility with ancient Microsoft (and Sperry!)
272+** versions of BASIC, where this header was needed so we could load a command into
273+** memory.
274+*/
275+#pragma pack(1) // pack our structure
276+typedef struct CmdHead // defines header block on command
277+{ // for PC commands
278+ char acBasic[5]; // BASIC information - needed to align things
279+ WORD wBasicSz; // size as seen by BASIC
280+ WORD wCmdSize; // size of the following info
281+} __packed CMDHEAD;
282+#pragma pack() // back to normal
283+
284+/*
285+** The rest of the header looks like this...
286+** int iRelPnt; relocation pointer... actual start
287+** char acName[8]; string holding the command name
288+** BYTE bMonRev; monitor revision level
289+** BYTE bCmdRev; command revision level
290+*/
291+
292+typedef CMDHEAD *LPCMDHEAD; // pointer to a command header
293+
294+#define MAXSTRLEN 255 // maximum string length we use
295+#define TOHOST FALSE
296+#define TO1401 TRUE
297+
298+static short CheckHandle(short h)
299+{
300+ if ((h < 0) || (h >= MAX1401)) // must be legal range...
301+ return U14ERR_BADHAND;
302+ if (aHand1401[h] <= 0) // must be open
303+ return U14ERR_BADHAND;
304+ return U14ERR_NOERROR;
305+}
306+
307+#ifdef _IS_WINDOWS_
308+/****************************************************************************
309+** U14Status1401 Used for functions which do not pass any data in but
310+** get data back
311+****************************************************************************/
312+static short U14Status1401(short sHand, LONG lCode, TCSBLOCK* pBlk)
313+{
314+ DWORD dwBytes = 0;
315+
316+ if ((sHand < 0) || (sHand >= MAX1401)) /* Check parameters */
317+ return U14ERR_BADHAND;
318+#ifndef _WIN64
319+ if (!USE_NT_DIOC(sHand))
320+ { /* Windows 9x DIOC methods? */
321+ if (DeviceIoControl(aHand1401[sHand], lCode, NULL, 0, pBlk,sizeof(TCSBLOCK),&dwBytes,NULL))
322+ return (short)((dwBytes>=sizeof(TCSBLOCK)) ? U14ERR_NOERROR : U14ERR_DRIVCOMMS);
323+ else
324+ return (short)GetLastError();
325+ }
326+ else
327+#endif
328+ { /* Windows NT or USB driver */
329+ PARAMBLK rWork;
330+ rWork.sState = U14ERR_DRIVCOMMS;
331+ if (DeviceIoControl(aHand1401[sHand], lCode, NULL, 0, &rWork,sizeof(PARAMBLK),&dwBytes,NULL) &&
332+ (dwBytes >= sizeof(PARAMBLK)))
333+ {
334+ *pBlk = rWork.csBlock;
335+ return rWork.sState;
336+ }
337+ }
338+
339+ return U14ERR_DRIVCOMMS;
340+}
341+
342+/****************************************************************************
343+** U14Control1401 Used for functions which pass data in and only expect
344+** an error code back
345+****************************************************************************/
346+static short U14Control1401(short sHand, LONG lCode, TCSBLOCK* pBlk)
347+{
348+ DWORD dwBytes = 0;
349+
350+ if ((sHand < 0) || (sHand >= MAX1401)) /* Check parameters */
351+ return U14ERR_BADHAND;
352+
353+#ifndef _WIN64
354+ if (!USE_NT_DIOC(sHand))
355+ { /* Windows 9x DIOC methods */
356+ if (DeviceIoControl(aHand1401[sHand], lCode, NULL, 0, pBlk, sizeof(TCSBLOCK), &dwBytes, NULL))
357+ return (short)(dwBytes >= sizeof(TCSBLOCK) ? U14ERR_NOERROR : U14ERR_DRIVCOMMS);
358+ else
359+ return (short)GetLastError();
360+ }
361+ else
362+#endif
363+ { /* Windows NT or later */
364+ PARAMBLK rWork;
365+ rWork.sState = U14ERR_DRIVCOMMS;
366+ if (DeviceIoControl(aHand1401[sHand], lCode, pBlk, sizeof(TCSBLOCK), &rWork, sizeof(PARAMBLK), &dwBytes, NULL) &&
367+ (dwBytes >= sizeof(PARAMBLK)))
368+ return rWork.sState;
369+ }
370+
371+ return U14ERR_DRIVCOMMS;
372+}
373+#endif
374+
375+/****************************************************************************
376+** SafeTickCount
377+** Gets time in approximately units of a millisecond.
378+*****************************************************************************/
379+static long SafeTickCount()
380+{
381+#ifdef _IS_WINDOWS_
382+ return GetTickCount();
383+#endif
384+#ifdef LINUX
385+ struct timeval tv;
386+ gettimeofday(&tv, NULL);
387+ return (tv.tv_sec*1000 + tv.tv_usec/1000);
388+#endif
389+}
390+
391+/****************************************************************************
392+** A utility routine to get the command file extension for a given type
393+** of 1401. We assume the type code is vaguely legal.
394+****************************************************************************/
395+static int ExtForType(short sType, char* szExt)
396+{
397+ szExt[0] = 0; /* Default return is a blank string */
398+ switch (sType)
399+ {
400+ case U14TYPE1401: strcpy(szExt, ".CMD"); break; // Standard 1401
401+ case U14TYPEPLUS: strcpy(szExt, ".GXC"); break; // 1401 plus
402+ default: // All others are in a predictable sequence
403+ strcpy(szExt, ".ARM");
404+ szExt[3] = (char)('M' + sType - U14TYPEU1401);
405+ if (szExt[3] > 'Z') // Wrap round to ARA after ARZ
406+ szExt[3] = (char)(szExt[3] - 26);
407+ }
408+ return 0;
409+}
410+
411+/****************************************************************************
412+** U14WhenToTimeOut
413+** Returns the time to time out in time units suitable for the machine
414+** we are running on ie millsecs for pc/linux, or Mac/
415+****************************************************************************/
416+U14API(int) U14WhenToTimeOut(short hand)
417+{
418+ int iNow = SafeTickCount();
419+ if ((hand >= 0) && (hand < MAX1401))
420+ iNow += alTimeOutPeriod[hand];
421+ return iNow;
422+}
423+
424+/****************************************************************************
425+** U14PassedTime
426+** Returns non zero if the timed passed in has been passed 0 if not
427+****************************************************************************/
428+U14API(short) U14PassedTime(int lCheckTime)
429+{
430+ return (short)((SafeTickCount()-lCheckTime) > 0);
431+}
432+
433+/****************************************************************************
434+** TranslateString
435+** Tidies up string that U14GetString returns. Converts all the commas in a
436+** string to spaces. Removes terminating CR character. May do more in future.
437+****************************************************************************/
438+static void TranslateString(char* pStr)
439+{
440+ int i = 0;
441+ while (pStr[i])
442+ {
443+ if (pStr[i] == ',')
444+ pStr[i] = ' '; /* convert comma to space */
445+ ++i;
446+ }
447+
448+ if ((i > 0) && (pStr[i-1] == '\n')) /* kill terminating LF */
449+ pStr[i-1] = (char)0;
450+}
451+
452+/****************************************************************************
453+** U14StrToLongs
454+** Converts a string to an array of longs and returns the number of values
455+****************************************************************************/
456+U14API(short) U14StrToLongs(const char* pszBuff, U14LONG *palNums, short sMaxLongs)
457+{
458+ WORD wChInd = 0; // index into source
459+ short sLgInd = 0; // index into result longs
460+
461+ while (pszBuff[wChInd] && // until we get to end of string...
462+ (sLgInd < sMaxLongs)) // ...or filled the buffer
463+ {
464+ // Why not use a C Library converter?
465+ switch (pszBuff[wChInd])
466+ {
467+ case '-':
468+ case '0': case '1': case '2': case '3': case '4':
469+ case '5': case '6': case '7': case '8': case '9':
470+ {
471+ BOOL bDone = FALSE; // true at end of number
472+ int iSign = 1; // sign of number
473+ long lValue = 0;
474+
475+ while ((!bDone) && pszBuff[wChInd])
476+ {
477+ switch (pszBuff[wChInd])
478+ {
479+ case '-':
480+ iSign = -1; // swap sign
481+ break;
482+
483+ case '0': case '1': case '2': case '3': case '4':
484+ case '5': case '6': case '7': case '8': case '9':
485+ lValue *= 10; // move to next digit base 10
486+ lValue += ((int)pszBuff[wChInd]-(int)'0');
487+ break;
488+
489+ default: // end of number
490+ bDone = TRUE;
491+ break;
492+ }
493+ wChInd++; // move onto next character
494+ }
495+ palNums[sLgInd] = lValue * iSign;
496+ sLgInd++;
497+ }
498+ break;
499+
500+ default:
501+ wChInd++; // look at next char
502+ break;
503+ }
504+ }
505+ return (sLgInd);
506+}
507+
508+
509+/****************************************************************************
510+** U14LongsFrom1401
511+** Gets the next waiting line from the 1401 and converts it longs
512+** Returns the number of numbers read or an error.
513+****************************************************************************/
514+U14API(short) U14LongsFrom1401(short hand, U14LONG *palBuff, short sMaxLongs)
515+{
516+ char szWork[MAXSTRLEN];
517+ short sResult = U14GetString(hand, szWork, MAXSTRLEN);/* get reply from 1401 */
518+ if (sResult == U14ERR_NOERROR) /* if no error convert */
519+ sResult = U14StrToLongs(szWork, palBuff, sMaxLongs);
520+ return sResult;
521+}
522+
523+/****************************************************************************
524+** U14CheckErr
525+** Sends the ERR command to the 1401 and gets the result. Returns 0, a
526+** negative error code, or the first error value.
527+****************************************************************************/
528+U14API(short) U14CheckErr(short hand)
529+{
530+ short sResult = U14SendString(hand, ";ERR;");
531+ if (sResult == U14ERR_NOERROR)
532+ {
533+ U14LONG er[3];
534+ sResult = U14LongsFrom1401(hand, er, 3);
535+ if (sResult > 0)
536+ {
537+ sResult = (short)er[0]; /* Either zero or an error value */
538+#ifdef _DEBUG
539+ if (er[0] != 0)
540+ {
541+ char szMsg[50];
542+ sprintf(szMsg, "U14CheckErr returned %d,%d\n", er[0], er[1]);
543+ OutputDebugString(szMsg);
544+ }
545+#endif
546+ }
547+ else
548+ {
549+ if (sResult == 0)
550+ sResult = U14ERR_TIMEOUT; /* No numbers equals timeout */
551+ }
552+ }
553+
554+ return sResult;
555+}
556+
557+/****************************************************************************
558+** U14LastErrCode
559+** Returns the last code from the driver. This is for Windows where all calls
560+** go through the Control and Status routines, so we can save any error.
561+****************************************************************************/
562+U14API(short) U14LastErrCode(short hand)
563+{
564+ if ((hand < 0) || (hand >= MAX1401))
565+ return U14ERR_BADHAND;
566+ return asLastRetCode[hand];
567+}
568+
569+/****************************************************************************
570+** U14SetTimeout
571+** Set the timeout period for 1401 comms in milliseconds
572+****************************************************************************/
573+U14API(void) U14SetTimeout(short hand, int lTimeOut)
574+{
575+ if ((hand < 0) || (hand >= MAX1401))
576+ return;
577+ alTimeOutPeriod[hand] = lTimeOut;
578+}
579+
580+/****************************************************************************
581+** U14GetTimeout
582+** Get the timeout period for 1401 comms in milliseconds
583+****************************************************************************/
584+U14API(int) U14GetTimeout(short hand)
585+{
586+ if ((hand < 0) || (hand >= MAX1401))
587+ return U14ERR_BADHAND;
588+ return alTimeOutPeriod[hand];
589+}
590+
591+/****************************************************************************
592+** U14OutBufSpace
593+** Return the space in the output buffer, or an error.
594+****************************************************************************/
595+U14API(short) U14OutBufSpace(short hand)
596+{
597+#ifdef _IS_WINDOWS_
598+ TCSBLOCK csBlock;
599+ short sErr = U14Status1401(hand, U14_GETOUTBUFSPACE,&csBlock);
600+ if (sErr == U14ERR_NOERROR)
601+ sErr = csBlock.ints[0];
602+ return sErr;
603+#endif
604+#ifdef LINUX
605+ short sErr = CheckHandle(hand);
606+ return (sErr == U14ERR_NOERROR) ? CED_GetOutBufSpace(aHand1401[hand]) : sErr;
607+#endif
608+}
609+
610+
611+/****************************************************************************
612+** U14BaseAddr1401
613+** Returns the 1401 base address or an error code. Meaningless nowadays
614+****************************************************************************/
615+U14API(int) U14BaseAddr1401(short hand)
616+{
617+#ifdef _IS_WINDOWS_
618+ TCSBLOCK csBlock;
619+ int iError = U14Status1401(hand, U14_GETBASEADDRESS,&csBlock);
620+ if (iError == U14ERR_NOERROR)
621+ iError = csBlock.longs[0];
622+ return iError;
623+#endif
624+#ifdef LINUX
625+ short sErr = CheckHandle(hand);
626+ return (sErr == U14ERR_NOERROR) ? CED_GetBaseAddress(aHand1401[hand]) : sErr;
627+#endif
628+}
629+
630+/****************************************************************************
631+** U14StateOf1401
632+** Return error state, either NOERROR or a negative code.
633+****************************************************************************/
634+U14API(short) U14StateOf1401(short hand)
635+{
636+#ifdef _IS_WINDOWS_
637+ TCSBLOCK csBlock;
638+ short sErr = U14Status1401(hand, U14_STATEOF1401, &csBlock);
639+ if (sErr == U14ERR_NOERROR)
640+ {
641+ sErr = csBlock.ints[0]; // returned 1401 state
642+ if ((sErr >= DRIVRET_STD) && (sErr <= DRIVRET_MAX))
643+ sErr = U14ERR_NOERROR;
644+ }
645+#endif
646+#ifdef LINUX
647+ short sErr = CheckHandle(hand);
648+ if (sErr == U14ERR_NOERROR)
649+ {
650+ sErr = (short)CED_StateOf1401(aHand1401[hand]);
651+ if ((sErr >= DRIVRET_STD) && (sErr <= DRIVRET_MAX))
652+ sErr = U14ERR_NOERROR;
653+ }
654+#endif
655+ return sErr;
656+}
657+
658+/****************************************************************************
659+** U14DriverVersion
660+** Returns the driver version. Hi word is major revision, low word is minor.
661+** If you pass in a silly handle (like -1), we return the version of the last
662+** driver we know of (to cope with PCI and no 1401 attached).
663+****************************************************************************/
664+U14API(int) U14DriverVersion(short hand)
665+{
666+ return CheckHandle(hand) != U14ERR_NOERROR ? lLastDriverVersion : alDriverVersion[hand];
667+}
668+
669+/****************************************************************************
670+** U14DriverType
671+** Returns the driver type. The type, 0=ISA/NU-Bus, 1=PCI, 2=USB, 3=HSS
672+** If you pass in a silly handle (like -1), we return the type of the last
673+** driver we know of (to cope with PCI and no 1401 attached).
674+****************************************************************************/
675+U14API(int) U14DriverType(short hand)
676+{
677+ return CheckHandle(hand) != U14ERR_NOERROR ? lLastDriverType : asDriverType[hand];
678+}
679+
680+/****************************************************************************
681+** U14DriverName
682+** Returns the driver type as 3 character (ISA, PCI, USB or HSS))
683+****************************************************************************/
684+U14API(short) U14DriverName(short hand, char* pBuf, WORD wMax)
685+{
686+ char* pName;
687+ *pBuf = 0; // Start off with a blank string
688+ switch (U14DriverType(hand)) // Results according to type
689+ {
690+ case 0: pName = "ISA"; break;
691+ case 1: pName = "PCI"; break;
692+ case 2: pName = "USB"; break;
693+ case 3: pName = "HSS"; break;
694+ default: pName = "???"; break;
695+ }
696+ strncpy(pBuf, pName, wMax); // Copy the correct name to return
697+
698+ return U14ERR_NOERROR;
699+}
700+
701+/****************************************************************************
702+** U14BlkTransState
703+** Returns 0 no transfer in progress, 1 transfer in progress or an error code
704+****************************************************************************/
705+U14API(short) U14BlkTransState(short hand)
706+{
707+#ifdef _IS_WINDOWS_
708+ TCSBLOCK csBlock;
709+ short sErr = U14Status1401(hand, U14_BLKTRANSSTATE, &csBlock);
710+ if (sErr == U14ERR_NOERROR)
711+ sErr = csBlock.ints[0];
712+ return sErr;
713+#endif
714+#ifdef LINUX
715+ short sErr = CheckHandle(hand);
716+ return (sErr == U14ERR_NOERROR) ? CED_BlkTransState(aHand1401[hand]) : sErr;
717+#endif
718+}
719+
720+/****************************************************************************
721+** U14Grab1401
722+** Take control of the 1401 for diagnostics purposes. USB does nothing.
723+****************************************************************************/
724+U14API(short) U14Grab1401(short hand)
725+{
726+ short sErr = CheckHandle(hand);
727+ if (sErr == U14ERR_NOERROR)
728+ {
729+#ifdef _IS_WINDOWS_
730+ if (abGrabbed[hand]) // 1401 should not have been grabbed
731+ sErr = U14ERR_ALREADYSET; // Error code defined for this
732+ else
733+ {
734+ TCSBLOCK csBlock;
735+ sErr = U14Control1401(hand, U14_GRAB1401, &csBlock);
736+ }
737+#endif
738+#ifdef LINUX
739+ // 1401 should not have been grabbed
740+ sErr = abGrabbed[hand] ? U14ERR_ALREADYSET : CED_Grab1401(aHand1401[hand]);
741+#endif
742+ if (sErr == U14ERR_NOERROR)
743+ abGrabbed[hand] = TRUE;
744+ }
745+ return sErr;
746+}
747+
748+/****************************************************************************
749+** U14Free1401
750+****************************************************************************/
751+U14API(short) U14Free1401(short hand)
752+{
753+ short sErr = CheckHandle(hand);
754+ if (sErr == U14ERR_NOERROR)
755+ {
756+#ifdef _IS_WINDOWS_
757+ if (abGrabbed[hand]) // 1401 should have been grabbed
758+ {
759+ TCSBLOCK csBlock;
760+ sErr = U14Control1401(hand, U14_FREE1401, &csBlock);
761+ }
762+ else
763+ sErr = U14ERR_NOTSET;
764+#endif
765+#ifdef LINUX
766+ // 1401 should not have been grabbed
767+ sErr = abGrabbed[hand] ? CED_Free1401(aHand1401[hand]) : U14ERR_NOTSET;
768+#endif
769+ if (sErr == U14ERR_NOERROR)
770+ abGrabbed[hand] = FALSE;
771+ }
772+ return sErr;
773+}
774+
775+/****************************************************************************
776+** U14Peek1401
777+** DESCRIPTION Cause the 1401 to do one or more peek operations.
778+** If lRepeats is zero, the loop will continue until U14StopDebugLoop
779+** is called. After the peek is done, use U14GetDebugData to retrieve
780+** the results of the peek.
781+****************************************************************************/
782+U14API(short) U14Peek1401(short hand, DWORD dwAddr, int nSize, int nRepeats)
783+{
784+ short sErr = CheckHandle(hand);
785+ if (sErr == U14ERR_NOERROR)
786+ {
787+ if (abGrabbed[hand]) // 1401 should have been grabbed
788+ {
789+#ifdef _IS_WINDOWS_
790+ TCSBLOCK csBlock;
791+ csBlock.longs[0] = (long)dwAddr;
792+ csBlock.longs[1] = nSize;
793+ csBlock.longs[2] = nRepeats;
794+ sErr = U14Control1401(hand, U14_DBGPEEK, &csBlock);
795+#endif
796+#ifdef LINUX
797+ TDBGBLOCK dbb;
798+ dbb.iAddr = (int)dwAddr;
799+ dbb.iWidth = nSize;
800+ dbb.iRepeats = nRepeats;
801+ sErr = CED_DbgPeek(aHand1401[hand], &dbb);
802+#endif
803+ }
804+ else
805+ sErr = U14ERR_NOTSET;
806+ }
807+ return sErr;
808+}
809+
810+/****************************************************************************
811+** U14Poke1401
812+** DESCRIPTION Cause the 1401 to do one or more poke operations.
813+** If lRepeats is zero, the loop will continue until U14StopDebugLoop
814+** is called.
815+****************************************************************************/
816+U14API(short) U14Poke1401(short hand, DWORD dwAddr, DWORD dwValue,
817+ int nSize, int nRepeats)
818+{
819+ short sErr = CheckHandle(hand);
820+ if (sErr == U14ERR_NOERROR)
821+ {
822+ if (abGrabbed[hand]) // 1401 should have been grabbed
823+ {
824+#ifdef _IS_WINDOWS_
825+ TCSBLOCK csBlock;
826+ csBlock.longs[0] = (long)dwAddr;
827+ csBlock.longs[1] = nSize;
828+ csBlock.longs[2] = nRepeats;
829+ csBlock.longs[3] = (long)dwValue;
830+ sErr = U14Control1401(hand, U14_DBGPOKE, &csBlock);
831+#endif
832+#ifdef LINUX
833+ TDBGBLOCK dbb;
834+ dbb.iAddr = (int)dwAddr;
835+ dbb.iWidth = nSize;
836+ dbb.iRepeats= nRepeats;
837+ dbb.iData = (int)dwValue;
838+ sErr = CED_DbgPoke(aHand1401[hand], &dbb);
839+#endif
840+ }
841+ else
842+ sErr = U14ERR_NOTSET;
843+ }
844+ return sErr;
845+}
846+
847+/****************************************************************************
848+** U14Ramp1401
849+** DESCRIPTION Cause the 1401 to loop, writing a ramp to a location.
850+** If lRepeats is zero, the loop will continue until U14StopDebugLoop.
851+****************************************************************************/
852+U14API(short) U14Ramp1401(short hand, DWORD dwAddr, DWORD dwDef, DWORD dwEnable,
853+ int nSize, int nRepeats)
854+{
855+ short sErr = CheckHandle(hand);
856+ if (sErr == U14ERR_NOERROR)
857+ {
858+ if (abGrabbed[hand]) // 1401 should have been grabbed
859+ {
860+#ifdef _IS_WINDOWS_
861+ TCSBLOCK csBlock;
862+ csBlock.longs[0] = (long)dwAddr;
863+ csBlock.longs[1] = (long)dwDef;
864+ csBlock.longs[2] = (long)dwEnable;
865+ csBlock.longs[3] = nSize;
866+ csBlock.longs[4] = nRepeats;
867+ sErr = U14Control1401(hand, U14_DBGRAMPDATA, &csBlock);
868+#endif
869+#ifdef LINUX
870+ TDBGBLOCK dbb;
871+ dbb.iAddr = (int)dwAddr;
872+ dbb.iDefault = (int)dwDef;
873+ dbb.iMask = (int)dwEnable;
874+ dbb.iWidth = nSize;
875+ dbb.iRepeats = nRepeats;
876+ sErr = CED_DbgRampAddr(aHand1401[hand], &dbb);
877+#endif
878+ }
879+ else
880+ sErr = U14ERR_NOTSET;
881+ }
882+ return sErr;
883+}
884+
885+/****************************************************************************
886+** U14RampAddr
887+** DESCRIPTION Cause the 1401 to loop, reading from a ramping location.
888+** If lRepeats is zero, the loop will continue until U14StopDebugLoop
889+****************************************************************************/
890+U14API(short) U14RampAddr(short hand, DWORD dwDef, DWORD dwEnable,
891+ int nSize, int nRepeats)
892+{
893+ short sErr = CheckHandle(hand);
894+ if (sErr == U14ERR_NOERROR)
895+ {
896+ if (abGrabbed[hand]) // 1401 should have been grabbed
897+ {
898+#ifdef _IS_WINDOWS_
899+ TCSBLOCK csBlock;
900+ csBlock.longs[0] = (long)dwDef;
901+ csBlock.longs[1] = (long)dwEnable;
902+ csBlock.longs[2] = nSize;
903+ csBlock.longs[3] = nRepeats;
904+ sErr = U14Control1401(hand, U14_DBGRAMPADDR, &csBlock);
905+#endif
906+#ifdef LINUX
907+ TDBGBLOCK dbb;
908+ dbb.iDefault = (int)dwDef;
909+ dbb.iMask = (int)dwEnable;
910+ dbb.iWidth = nSize;
911+ dbb.iRepeats = nRepeats;
912+ sErr = CED_DbgRampAddr(aHand1401[hand], &dbb);
913+#endif
914+ }
915+ else
916+ sErr = U14ERR_NOTSET;
917+ }
918+ return sErr;
919+}
920+
921+/****************************************************************************
922+** U14StopDebugLoop
923+** DESCRIPTION Stops a peek\poke\ramp that, with repeats set to zero,
924+** will otherwise continue forever.
925+****************************************************************************/
926+U14API(short) U14StopDebugLoop(short hand)
927+{
928+ short sErr = CheckHandle(hand);
929+ if (sErr == U14ERR_NOERROR)
930+#ifdef _IS_WINDOWS_
931+ {
932+ if (abGrabbed[hand]) // 1401 should have been grabbed
933+ {
934+ TCSBLOCK csBlock;
935+ sErr = U14Control1401(hand, U14_DBGSTOPLOOP, &csBlock);
936+ }
937+ else
938+ sErr = U14ERR_NOTSET;
939+ }
940+#endif
941+#ifdef LINUX
942+ sErr = abGrabbed[hand] ? CED_DbgStopLoop(aHand1401[hand]) : U14ERR_NOTSET;
943+#endif
944+ return sErr;
945+}
946+
947+/****************************************************************************
948+** U14GetDebugData
949+** DESCRIPTION Returns the result from a previous peek operation.
950+****************************************************************************/
951+U14API(short) U14GetDebugData(short hand, U14LONG* plValue)
952+{
953+ short sErr = CheckHandle(hand);
954+ if (sErr == U14ERR_NOERROR)
955+ {
956+ if (abGrabbed[hand]) // 1401 should have been grabbed
957+ {
958+#ifdef _IS_WINDOWS_
959+ TCSBLOCK csBlock;
960+ sErr = U14Status1401(hand, U14_DBGGETDATA, &csBlock);
961+ if (sErr == U14ERR_NOERROR)
962+ *plValue = csBlock.longs[0]; // Return the data
963+#endif
964+#ifdef LINUX
965+ TDBGBLOCK dbb;
966+ sErr = CED_DbgGetData(aHand1401[hand], &dbb);
967+ if (sErr == U14ERR_NOERROR)
968+ *plValue = dbb.iData; /* Return the data */
969+#endif
970+ }
971+ else
972+ sErr = U14ERR_NOTSET;
973+ }
974+ return sErr;
975+}
976+
977+/****************************************************************************
978+** U14StartSelfTest
979+****************************************************************************/
980+U14API(short) U14StartSelfTest(short hand)
981+{
982+#ifdef _IS_WINDOWS_
983+ TCSBLOCK csBlock;
984+ return U14Control1401(hand, U14_STARTSELFTEST, &csBlock);
985+#endif
986+#ifdef LINUX
987+ short sErr = CheckHandle(hand);
988+ return (sErr == U14ERR_NOERROR) ? CED_StartSelfTest(aHand1401[hand]) : sErr;
989+#endif
990+}
991+
992+/****************************************************************************
993+** U14CheckSelfTest
994+****************************************************************************/
995+U14API(short) U14CheckSelfTest(short hand, U14LONG *pData)
996+{
997+#ifdef _IS_WINDOWS_
998+ TCSBLOCK csBlock;
999+ short sErr = U14Status1401(hand, U14_CHECKSELFTEST, &csBlock);
1000+ if (sErr == U14ERR_NOERROR)
1001+ {
1002+ pData[0] = csBlock.longs[0]; /* Return the results to user */
1003+ pData[1] = csBlock.longs[1];
1004+ pData[2] = csBlock.longs[2];
1005+ }
1006+#endif
1007+#ifdef LINUX
1008+ short sErr = CheckHandle(hand);
1009+ if (sErr == U14ERR_NOERROR) /* Check parameters */
1010+ {
1011+ TGET_SELFTEST gst;
1012+ sErr = CED_CheckSelfTest(aHand1401[hand], &gst);
1013+ if (sErr == U14ERR_NOERROR)
1014+ {
1015+ pData[0] = gst.code; /* Return the results to user */
1016+ pData[1] = gst.x;
1017+ pData[2] = gst.y;
1018+ }
1019+ }
1020+#endif
1021+ return sErr;
1022+}
1023+
1024+/****************************************************************************
1025+** U14GetUserMemorySize
1026+****************************************************************************/
1027+U14API(short) U14GetUserMemorySize(short hand, DWORD *pMemorySize)
1028+{
1029+ // The original 1401 used a different command for getting the size
1030+ short sErr = U14SendString(hand, (asType1401[hand] == U14TYPE1401) ? "MEMTOP;" : "MEMTOP,?;");
1031+ *pMemorySize = 0; /* if we get error then leave size set at 0 */
1032+ if (sErr == U14ERR_NOERROR)
1033+ {
1034+ U14LONG alLimits[4];
1035+ sErr = U14LongsFrom1401(hand, alLimits, 4);
1036+ if (sErr > 0) /* +ve sErr is the number of values read */
1037+ {
1038+ sErr = U14ERR_NOERROR; /* All OK, flag success */
1039+ if (asType1401[hand] == U14TYPE1401) /* result for standard */
1040+ *pMemorySize = alLimits[0] - alLimits[1]; /* memtop-membot */
1041+ else
1042+ *pMemorySize = alLimits[0]; /* result for plus or u1401 */
1043+ }
1044+ }
1045+ return sErr;
1046+}
1047+
1048+/****************************************************************************
1049+** U14TypeOf1401
1050+** Returns the type of the 1401, maybe unknown
1051+****************************************************************************/
1052+U14API(short) U14TypeOf1401(short hand)
1053+{
1054+ if ((hand < 0) || (hand >= MAX1401)) /* Check parameters */
1055+ return U14ERR_BADHAND;
1056+ else
1057+ return asType1401[hand];
1058+}
1059+
1060+/****************************************************************************
1061+** U14NameOf1401
1062+** Returns the type of the 1401 as a string, blank if unknown
1063+****************************************************************************/
1064+U14API(short) U14NameOf1401(short hand, char* pBuf, WORD wMax)
1065+{
1066+ short sErr = CheckHandle(hand);
1067+ if (sErr == U14ERR_NOERROR)
1068+ {
1069+ char* pName;
1070+ switch (asType1401[hand]) // Results according to type
1071+ {
1072+ case U14TYPE1401: pName = "Std 1401"; break;
1073+ case U14TYPEPLUS: pName = "1401plus"; break;
1074+ case U14TYPEU1401: pName = "micro1401"; break;
1075+ case U14TYPEPOWER: pName = "Power1401"; break;
1076+ case U14TYPEU14012:pName = "Micro1401 mk II"; break;
1077+ case U14TYPEPOWER2:pName = "Power1401 mk II"; break;
1078+ case U14TYPEU14013:pName = "Micro1401-3"; break;
1079+ case U14TYPEPOWER3:pName = "Power1401-3"; break;
1080+ default: pName = "Unknown";
1081+ }
1082+ strncpy(pBuf, pName, wMax);
1083+ }
1084+ return sErr;
1085+}
1086+
1087+/****************************************************************************
1088+** U14TransferFlags
1089+** Returns the driver block transfer flags.
1090+** Bits can be set - see U14TF_ constants in use1401.h
1091+*****************************************************************************/
1092+U14API(short) U14TransferFlags(short hand)
1093+{
1094+#ifdef _IS_WINDOWS_
1095+ TCSBLOCK csBlock;
1096+ short sErr = U14Status1401(hand, U14_TRANSFERFLAGS, &csBlock);
1097+ return (sErr == U14ERR_NOERROR) ? (short)csBlock.ints[0] : sErr;
1098+#endif
1099+#ifdef LINUX
1100+ short sErr = CheckHandle(hand);
1101+ return (sErr == U14ERR_NOERROR) ? CED_TransferFlags(aHand1401[hand]) : sErr;
1102+#endif
1103+}
1104+
1105+/****************************************************************************
1106+** GetDriverVersion
1107+** Actually reads driver version from the device driver.
1108+** Hi word is major revision, low word is minor revision.
1109+** Assumes that hand has been checked. Also codes driver type in bits 24 up.
1110+*****************************************************************************/
1111+static int GetDriverVersion(short hand)
1112+{
1113+#ifdef _IS_WINDOWS_
1114+ TCSBLOCK csBlock;
1115+ int iErr = U14Status1401(hand, U14_GETDRIVERREVISION, &csBlock);
1116+ if (iErr == U14ERR_NOERROR)
1117+ iErr = csBlock.longs[0];
1118+ return iErr;
1119+#endif
1120+#ifdef LINUX
1121+ return CED_GetDriverRevision(aHand1401[hand]);
1122+#endif
1123+}
1124+
1125+/****************************************************************************
1126+** U14MonitorRev
1127+** Returns the 1401 monitor revision number.
1128+** The number returned is the minor revision - the part after the
1129+** decimal point - plus the major revision times 1000.
1130+*****************************************************************************/
1131+U14API(int) U14MonitorRev(short hand)
1132+{
1133+ int iRev = 0;
1134+ int iErr = CheckHandle(hand);
1135+ if (iErr != U14ERR_NOERROR) // Check open and in use
1136+ return iErr;
1137+
1138+ if (asType1401[hand] >= U14TYPEPOWER2) // The Power2 onwards can give us the monitor
1139+ { // revision directly for all versions
1140+ iErr = U14SendString(hand, "INFO,S,28;");
1141+ if (iErr == U14ERR_NOERROR)
1142+ {
1143+ U14LONG lVals[2]; // Read a single number being the revision
1144+ iErr = U14LongsFrom1401(hand, lVals, 1);
1145+ if (iErr > 0)
1146+ {
1147+ iErr = U14ERR_NOERROR;
1148+ iRev = lVals[0]; // This is the minor part of the revision
1149+ iRev += asType1401[hand] * 10000;
1150+ }
1151+ }
1152+ }
1153+ else
1154+ { /* Do it the hard way for older hardware */
1155+ iErr = U14SendString(hand, ";CLIST;"); /* ask for command levels */
1156+ if (iErr == U14ERR_NOERROR)
1157+ {
1158+ while (iErr == U14ERR_NOERROR)
1159+ {
1160+ char wstr[50];
1161+ iErr = U14GetString(hand, wstr, 45);
1162+ if (iErr == U14ERR_NOERROR)
1163+ {
1164+ char *pstr = strstr(wstr,"RESET"); /* Is this the RESET command? */
1165+ if ((pstr == wstr) && (wstr[5] == ' '))
1166+ {
1167+ char *pstr2;
1168+ size_t l;
1169+ pstr += 6; /* Move past RESET and followinmg char */
1170+ l = strlen(pstr); /* The length of text remaining */
1171+ while (((pstr[l-1] == ' ') || (pstr[l-1] == 13)) && (l > 0))
1172+ {
1173+ pstr[l-1] = 0; /* Tidy up string at the end */
1174+ l--; /* by removing spaces and CRs */
1175+ }
1176+ pstr2 = strchr(pstr, '.'); /* Find the decimal point */
1177+ if (pstr2 != NULL) /* If we found the DP */
1178+ {
1179+ *pstr2 = 0; /* End pstr string at DP */
1180+ pstr2++; /* Now past the decimal point */
1181+ iRev = atoi(pstr2); /* Get the number after point */
1182+ }
1183+ iRev += (atoi(pstr) * 1000); /* Add first bit * 1000 */
1184+ }
1185+ if ((strlen(wstr) < 3) && (wstr[0] == ' '))
1186+ break; /* Spot the last line of results */
1187+ }
1188+ }
1189+ }
1190+ }
1191+ if (iErr == U14ERR_NOERROR) /* Return revision if no error */
1192+ iErr = iRev;
1193+
1194+ return iErr;
1195+}
1196+
1197+/****************************************************************************
1198+** U14TryToOpen Tries to open the 1401 number passed
1199+** Note : This will succeed with NT driver even if no I/F card or
1200+** 1401 switched off, so we check state and close the driver
1201+** if the state is unsatisfactory in U14Open1401.
1202+****************************************************************************/
1203+#ifdef _IS_WINDOWS_
1204+#define U14NAMEOLD "\\\\.\\CED_140%d"
1205+#define U14NAMENEW "\\\\.\\CED%d"
1206+static short U14TryToOpen(int n1401, long* plRetVal, short* psHandle)
1207+{
1208+ short sErr = U14ERR_NOERROR;
1209+ HANDLE hDevice = INVALID_HANDLE_VALUE;
1210+ DWORD dwErr = 0;
1211+ int nFirst, nLast, nDev = 0; /* Used for the search for a 1401 */
1212+ BOOL bOldName = FALSE; /* start by looking for a modern driver */
1213+
1214+ if (n1401 == 0) /* If we need to look for a 1401 */
1215+ {
1216+ nFirst = 1; /* Set the search range */
1217+ nLast = MAX1401; /* through all the possible 1401s */
1218+ }
1219+ else
1220+ nFirst = nLast = n1401; /* Otherwise just one 1401 */
1221+
1222+ while (hDevice == INVALID_HANDLE_VALUE) /* Loop to try for a 1401 */
1223+ {
1224+ for (nDev = nFirst; nDev <= nLast; nDev++)
1225+ {
1226+ char szDevName[40]; /* name of the device to open */
1227+ sprintf(szDevName, bOldName ? U14NAMEOLD : U14NAMENEW, nDev);
1228+ hDevice = CreateFile(szDevName, GENERIC_WRITE | GENERIC_READ,
1229+ 0, 0, /* Unshared mode does nothing as this is a device */
1230+ OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
1231+
1232+ if (hDevice != INVALID_HANDLE_VALUE)/* Check 1401 if opened */
1233+ {
1234+ TCSBLOCK csBlock;
1235+ assert(aHand1401[nDev-1] == INVALID_HANDLE_VALUE); // assert if already open
1236+ aHand1401[nDev-1] = hDevice; /* Save handle for now */
1237+
1238+#ifndef _WIN64
1239+ // Use DIOC method if not windows 9x or if using new device name
1240+ abUseNTDIOC[nDev-1] = (BOOL)(!bWindows9x || !bOldName);
1241+#endif
1242+ sErr = U14Status1401((short)(nDev-1), U14_TYPEOF1401, &csBlock);
1243+ if (sErr == U14ERR_NOERROR)
1244+ {
1245+ *plRetVal = csBlock.ints[0];
1246+ if (csBlock.ints[0] == U14ERR_INUSE)/* Prevent multi opens */
1247+ {
1248+ CloseHandle(hDevice); /* treat as open failure */
1249+ hDevice = INVALID_HANDLE_VALUE;
1250+ aHand1401[nDev-1] = INVALID_HANDLE_VALUE;
1251+ sErr = U14ERR_INUSE;
1252+ }
1253+ else
1254+ break; /* Exit from for loop on success */
1255+ }
1256+ else
1257+ {
1258+ CloseHandle(hDevice); /* Give up if func fails */
1259+ hDevice = INVALID_HANDLE_VALUE;
1260+ aHand1401[nDev-1] = INVALID_HANDLE_VALUE;
1261+ }
1262+ }
1263+ else
1264+ {
1265+ DWORD dwe = GetLastError(); /* Get error code otherwise */
1266+ if ((dwe != ERROR_FILE_NOT_FOUND) || (dwErr == 0))
1267+ dwErr = dwe; /* Ignore repeats of 'not found' */
1268+ }
1269+ }
1270+
1271+ if ((hDevice == INVALID_HANDLE_VALUE) &&/* No device found, and... */
1272+ (bWindows9x) && /* ...old names are allowed, and... */
1273+ (bOldName == FALSE)) /* ...not tried old names yet */
1274+ bOldName = TRUE; /* Set flag and go round again */
1275+ else
1276+ break; /* otherwise that's all folks */
1277+ }
1278+
1279+ if (hDevice != INVALID_HANDLE_VALUE) /* If we got our device open */
1280+ *psHandle = (short)(nDev-1); /* return 1401 number opened */
1281+ else
1282+ {
1283+ if (dwErr == ERROR_FILE_NOT_FOUND) /* Sort out the error codes */
1284+ sErr = U14ERR_NO1401DRIV; /* if file not found */
1285+ else if (dwErr == ERROR_NOT_SUPPORTED)
1286+ sErr = U14ERR_DRIVTOOOLD; /* if DIOC not supported */
1287+ else if (dwErr == ERROR_ACCESS_DENIED)
1288+ sErr = U14ERR_INUSE;
1289+ else
1290+ sErr = U14ERR_DRIVCOMMS; /* otherwise assume comms problem */
1291+ }
1292+ return sErr;
1293+}
1294+#endif
1295+#ifdef LINUX
1296+static short U14TryToOpen(int n1401, long* plRetVal, short* psHandle)
1297+{
1298+ short sErr = U14ERR_NOERROR;
1299+ int fh = 0; // will be 1401 handle
1300+ int iErr = 0;
1301+ int nFirst, nLast, nDev = 0; // Used for the search for a 1401
1302+
1303+ if (n1401 == 0) // If we need to look for a 1401
1304+ {
1305+ nFirst = 1; /* Set the search range */
1306+ nLast = MAX1401; /* through all the possible 1401s */
1307+ }
1308+ else
1309+ nFirst = nLast = n1401; /* Otherwise just one 1401 */
1310+
1311+ for (nDev = nFirst; nDev <= nLast; nDev++)
1312+ {
1313+ char szDevName[40]; // name of the device to open
1314+ sprintf(szDevName,"/dev/cedusb/%d", nDev-1);
1315+ fh = open(szDevName, O_RDWR); // can only be opened once at a time
1316+ if (fh > 0) // Check 1401 if opened
1317+ {
1318+ int iType1401 = CED_TypeOf1401(fh); // get 1401 type
1319+ aHand1401[nDev-1] = fh; // Save handle for now
1320+ if (iType1401 >= 0)
1321+ {
1322+ *plRetVal = iType1401;
1323+ break; // Exit from for loop on success
1324+ }
1325+ else
1326+ {
1327+ close(fh); // Give up if func fails
1328+ fh = 0;
1329+ aHand1401[nDev-1] = 0;
1330+ }
1331+ }
1332+ else
1333+ {
1334+ if (((errno != ENODEV) && (errno != ENOENT)) || (iErr == 0))
1335+ iErr = errno; // Ignore repeats of 'not found'
1336+ }
1337+ }
1338+
1339+
1340+ if (fh) // If we got our device open
1341+ *psHandle = (short)(nDev-1); // return 1401 number opened
1342+ else
1343+ {
1344+ if ((iErr == ENODEV) || (iErr == ENOENT)) // Sort out the error codes
1345+ sErr = U14ERR_NO1401DRIV; // if file not found
1346+ else if (iErr == EBUSY)
1347+ sErr = U14ERR_INUSE;
1348+ else
1349+ sErr = U14ERR_DRIVCOMMS; // otherwise assume comms problem
1350+ }
1351+
1352+ return sErr;
1353+}
1354+#endif
1355+/****************************************************************************
1356+** U14Open1401
1357+** Tries to get the 1401 for use by this application
1358+*****************************************************************************/
1359+U14API(short) U14Open1401(short n1401)
1360+{
1361+ long lRetVal = -1;
1362+ short sErr;
1363+ short hand = 0;
1364+
1365+ if ((n1401 < 0) || (n1401 > MAX1401)) // must check the 1401 number
1366+ return U14ERR_BAD1401NUM;
1367+
1368+ szLastName[0] = 0; /* initialise the error info string */
1369+
1370+ sErr = U14TryToOpen(n1401, &lRetVal, &hand);
1371+ if (sErr == U14ERR_NOERROR)
1372+ {
1373+ long lDriverVersion = GetDriverVersion(hand); /* get driver revision */
1374+ long lDriverRev = -1;
1375+ if (lDriverVersion >= 0) /* can use it if all OK */
1376+ {
1377+ lLastDriverType = (lDriverVersion >> 24) & 0x000000FF;
1378+ asDriverType[hand] = (short)lLastDriverType; /* Drv type */
1379+ lLastDriverVersion = lDriverVersion & 0x00FFFFFF;
1380+ alDriverVersion[hand] = lLastDriverVersion; /* Actual version */
1381+ lDriverRev = ((lDriverVersion>>16) & 0x00FF); /* use hi word */
1382+ }
1383+ else
1384+ {
1385+ U14Close1401(hand); /* If there is a problem we should close */
1386+ return (short)lDriverVersion; /* and return the error code */
1387+ }
1388+
1389+ if (lDriverRev < MINDRIVERMAJREV) /* late enough version? */
1390+ {
1391+ U14Close1401(hand); /* If there is a problem we should close */
1392+ return U14ERR_DRIVTOOOLD; /* too old */
1393+ }
1394+
1395+ asLastRetCode[hand] = U14ERR_NOERROR; /* Initialise this 1401s info */
1396+ abGrabbed[hand] = FALSE; /* we are not in single step mode */
1397+ U14SetTimeout(hand, 3000); /* set 3 seconds as default timeout */
1398+
1399+ switch (lRetVal)
1400+ {
1401+ case DRIVRET_STD: asType1401[hand] = U14TYPE1401; break; /* Some we do by hand */
1402+ case DRIVRET_U1401:asType1401[hand] = U14TYPEU1401; break;
1403+ case DRIVRET_PLUS: asType1401[hand] = U14TYPEPLUS; break;
1404+ default: // For the power upwards, we can calculate the codes
1405+ if ((lRetVal >= DRIVRET_POWER) && (lRetVal <= DRIVRET_MAX))
1406+ asType1401[hand] = (short)(lRetVal - (DRIVRET_POWER - U14TYPEPOWER));
1407+ else
1408+ asType1401[hand] = U14TYPEUNKNOWN;
1409+ break;
1410+ }
1411+ U14KillIO1401(hand); /* resets the 1401 buffers */
1412+
1413+ if (asType1401[hand] != U14TYPEUNKNOWN) /* If all seems OK so far */
1414+ {
1415+ sErr = U14CheckErr(hand); /* we can check 1401 comms now */
1416+ if (sErr != 0) /* If this failed to go OK */
1417+ U14Reset1401(hand); /* Reset the 1401 to try to sort it out */
1418+ }
1419+
1420+ sErr = U14StateOf1401(hand);/* Get the state of the 1401 for return */
1421+ if (sErr == U14ERR_NOERROR)
1422+ sErr = hand; /* return the handle if no problem */
1423+ else
1424+ U14Close1401(hand); /* If there is a problem we should close */
1425+ }
1426+
1427+ return sErr;
1428+}
1429+
1430+
1431+/****************************************************************************
1432+** U14Close1401
1433+** Closes the 1401 so someone else can use it.
1434+****************************************************************************/
1435+U14API(short) U14Close1401(short hand)
1436+{
1437+ int j;
1438+ int iAreaMask = 0; // Mask for active areas
1439+ short sErr = CheckHandle(hand);
1440+ if (sErr != U14ERR_NOERROR) // Check open and in use
1441+ return sErr;
1442+
1443+ for (j = 0; j<MAX_TRANSAREAS; ++j)
1444+ {
1445+ TGET_TX_BLOCK gtb;
1446+ int iReturn = U14GetTransfer(hand, &gtb); // get area information
1447+ if (iReturn == U14ERR_NOERROR) // ignore if any problem
1448+ if (gtb.used)
1449+ iAreaMask |= (1 << j); // set a bit for each used area
1450+ }
1451+
1452+ if (iAreaMask) // if any areas are in use
1453+ {
1454+ U14Reset1401(hand); // in case an active transfer running
1455+ for (j = 0; j < MAX_TRANSAREAS; ++j) // Locate locked areas
1456+ if (iAreaMask & (1 << j)) // And kill off any transfers
1457+ U14UnSetTransfer(hand, (WORD)j);
1458+ }
1459+
1460+#ifdef _IS_WINDOWS_
1461+ if (aXferEvent[hand]) // if this 1401 has an open event handle
1462+ {
1463+ CloseHandle(aXferEvent[hand]); // close down the handle
1464+ aXferEvent[hand] = NULL; // and mark it as gone
1465+ }
1466+
1467+ if (CloseHandle(aHand1401[hand]))
1468+#endif
1469+#ifdef LINUX
1470+ if (close(aHand1401[hand]) == 0) // make sure that close works
1471+#endif
1472+ {
1473+ aHand1401[hand] = INVALID_HANDLE_VALUE;
1474+ asType1401[hand] = U14TYPEUNKNOWN;
1475+ return U14ERR_NOERROR;
1476+ }
1477+ else
1478+ return U14ERR_BADHAND; /* BUGBUG GetLastError() ? */
1479+}
1480+
1481+/**************************************************************************
1482+**
1483+** Look for open 1401s and attempt to close them down. 32-bit windows only.
1484+**************************************************************************/
1485+U14API(void) U14CloseAll(void)
1486+{
1487+ int i;
1488+ for (i = 0; i < MAX1401; i++) // Tidy up and make safe
1489+ if (aHand1401[i] != INVALID_HANDLE_VALUE)
1490+ U14Close1401((short)i); // Last ditch close 1401
1491+}
1492+
1493+/****************************************************************************
1494+** U14Reset1401
1495+** Resets the 1401
1496+****************************************************************************/
1497+U14API(short) U14Reset1401(short hand)
1498+{
1499+#ifdef _IS_WINDOWS_
1500+ TCSBLOCK csBlock;
1501+ return U14Control1401(hand, U14_RESET1401, &csBlock);
1502+#endif
1503+#ifdef LINUX
1504+ short sErr = CheckHandle(hand);
1505+ return (sErr == U14ERR_NOERROR) ? CED_Reset1401(aHand1401[hand]) : sErr;
1506+#endif
1507+}
1508+
1509+/****************************************************************************
1510+** U14ForceReset
1511+** Sets the 1401 full reset flag, so that next call to Reset1401 will
1512+** always cause a genuine reset.
1513+*****************************************************************************/
1514+U14API(short) U14ForceReset(short hand)
1515+{
1516+#ifdef _IS_WINDOWS_
1517+ TCSBLOCK csBlock;
1518+ return U14Control1401(hand, U14_FULLRESET, &csBlock);
1519+#endif
1520+#ifdef LINUX
1521+ short sErr = CheckHandle(hand);
1522+ return (sErr == U14ERR_NOERROR) ? CED_FullReset(aHand1401[hand]) : sErr;
1523+#endif
1524+}
1525+
1526+/****************************************************************************
1527+** U14KillIO1401
1528+** Removes any pending IO from the buffers.
1529+*****************************************************************************/
1530+U14API(short) U14KillIO1401(short hand)
1531+{
1532+#ifdef _IS_WINDOWS_
1533+ TCSBLOCK csBlock;
1534+ return U14Control1401(hand, U14_KILLIO1401, &csBlock);
1535+#endif
1536+#ifdef LINUX
1537+ short sErr = CheckHandle(hand);
1538+ return (sErr == U14ERR_NOERROR) ? CED_KillIO1401(aHand1401[hand]) : sErr;
1539+#endif
1540+}
1541+
1542+
1543+/****************************************************************************
1544+** U14SendString
1545+** Send characters to the 1401
1546+*****************************************************************************/
1547+U14API(short) U14SendString(short hand, const char* pString)
1548+{
1549+ int nChars; // length we are sending
1550+ long lTimeOutTicks; // when to time out
1551+ BOOL bSpaceToSend; // space to send yet
1552+ short sErr = CheckHandle(hand);
1553+ if (sErr != U14ERR_NOERROR)
1554+ return sErr;
1555+
1556+ nChars = (int)strlen(pString); // get string length we want to send
1557+ if (nChars > MAXSTRLEN)
1558+ return U14ERR_STRLEN; // String too long
1559+
1560+#ifdef _IS_WINDOWS_
1561+ // To get here we must wait for the buffer to have some space
1562+ lTimeOutTicks = U14WhenToTimeOut(hand);
1563+ do
1564+ {
1565+ bSpaceToSend = (BOOL)((long)U14OutBufSpace(hand) >= nChars);
1566+ }
1567+ while (!bSpaceToSend && !U14PassedTime(lTimeOutTicks));
1568+
1569+ if (!bSpaceToSend) /* Last-ditch attempt to avoid timeout */
1570+ { /* This can happen with anti-virus or network activity! */
1571+ int i;
1572+ for (i = 0; (i < 4) && (!bSpaceToSend); ++i)
1573+ {
1574+ Sleep(25); /* Give other threads a chance for a while */
1575+ bSpaceToSend = (BOOL)((long)U14OutBufSpace(hand) >= nChars);
1576+ }
1577+ }
1578+
1579+ if (asLastRetCode[hand] == U14ERR_NOERROR) /* no errors? */
1580+ {
1581+ if (bSpaceToSend)
1582+ {
1583+ PARAMBLK rData;
1584+ DWORD dwBytes;
1585+ char tstr[MAXSTRLEN+5]; /* Buffer for chars */
1586+
1587+ if ((hand < 0) || (hand >= MAX1401))
1588+ sErr = U14ERR_BADHAND;
1589+ else
1590+ {
1591+ strcpy(tstr, pString); /* Into local buf */
1592+#ifndef _WIN64
1593+ if (!USE_NT_DIOC(hand)) /* Using WIN 95 driver access? */
1594+ {
1595+ int iOK = DeviceIoControl(aHand1401[hand], (DWORD)U14_SENDSTRING,
1596+ NULL, 0, tstr, nChars,
1597+ &dwBytes, NULL);
1598+ if (iOK)
1599+ sErr = (dwBytes >= (DWORD)nChars) ? U14ERR_NOERROR : U14ERR_DRIVCOMMS;
1600+ else
1601+ sErr = (short)GetLastError();
1602+ }
1603+ else
1604+#endif
1605+ {
1606+ int iOK = DeviceIoControl(aHand1401[hand],(DWORD)U14_SENDSTRING,
1607+ tstr, nChars,
1608+ &rData,sizeof(PARAMBLK),&dwBytes,NULL);
1609+ if (iOK && (dwBytes >= sizeof(PARAMBLK)))
1610+ sErr = rData.sState;
1611+ else
1612+ sErr = U14ERR_DRIVCOMMS;
1613+ }
1614+
1615+ if (sErr != U14ERR_NOERROR) // If we have had a comms error
1616+ U14ForceReset(hand); // make sure we get real reset
1617+ }
1618+
1619+ return sErr;
1620+
1621+ }
1622+ else
1623+ {
1624+ U14ForceReset(hand); // make sure we get real reset
1625+ return U14ERR_TIMEOUT;
1626+ }
1627+ }
1628+ else
1629+ return asLastRetCode[hand];
1630+#endif
1631+#ifdef LINUX
1632+ // Just try to send it and see what happens!
1633+ sErr = CED_SendString(aHand1401[hand], pString, nChars);
1634+ if (sErr != U14ERR_NOOUT) // if any result except "no room in output"...
1635+ {
1636+ if (sErr != U14ERR_NOERROR) // if a problem...
1637+ U14ForceReset(hand); // ...make sure we get real reset next time
1638+ return sErr; // ... we are done as nothing we can do
1639+ }
1640+
1641+ // To get here we must wait for the buffer to have some space
1642+ lTimeOutTicks = U14WhenToTimeOut(hand);
1643+ do
1644+ {
1645+ bSpaceToSend = (BOOL)((long)U14OutBufSpace(hand) >= nChars);
1646+ if (!bSpaceToSend)
1647+ sched_yield(); // let others have fun while we wait
1648+ }
1649+ while (!bSpaceToSend && !U14PassedTime(lTimeOutTicks));
1650+
1651+ if (asLastRetCode[hand] == U14ERR_NOERROR) /* no errors? */
1652+ {
1653+ if (bSpaceToSend)
1654+ {
1655+ sErr = CED_SendString(aHand1401[hand], pString, nChars);
1656+ if (sErr != U14ERR_NOERROR) // If we have had a comms error
1657+ U14ForceReset(hand); // make sure we get real reset
1658+ return sErr;
1659+ }
1660+ else
1661+ {
1662+ U14ForceReset(hand); // make sure we get real reset
1663+ return U14ERR_TIMEOUT;
1664+ }
1665+ }
1666+ else
1667+ return asLastRetCode[hand];
1668+#endif
1669+}
1670+
1671+/****************************************************************************
1672+** U14SendChar
1673+** Send character to the 1401
1674+*****************************************************************************/
1675+U14API(short) U14SendChar(short hand, char cChar)
1676+{
1677+#ifdef _IS_WINDOWS_
1678+ char sz[2]=" "; // convert to a string and send
1679+ sz[0] = cChar;
1680+ sz[1] = 0;
1681+ return(U14SendString(hand, sz)); // String routines are better
1682+#endif
1683+#ifdef LINUX
1684+ short sErr = CheckHandle(hand);
1685+ return (sErr == U14ERR_NOERROR) ? CED_SendChar(aHand1401[hand], cChar) : sErr;
1686+#endif
1687+}
1688+
1689+/****************************************************************************
1690+** U14GetString
1691+** Get a string from the 1401. Returns a null terminated string.
1692+** The string is all the characters up to the next CR in the buffer
1693+** or the end of the buffer if that comes first. This only returns text
1694+** if there is a CR in the buffer. The terminating CR character is removed.
1695+** wMaxLen Is the size of the buffer and must be at least 2 or an error.
1696+** Returns U14ERR_NOERR if OK with the result in the string or a negative
1697+** error code. Any error from the device causes us to set up for
1698+** a full reset.
1699+****************************************************************************/
1700+U14API(short) U14GetString(short hand, char* pBuffer, WORD wMaxLen)
1701+{
1702+ short sErr = CheckHandle(hand);
1703+ if (sErr != U14ERR_NOERROR) // If an error...
1704+ return sErr; // ...bail out!
1705+
1706+#ifdef _IS_WINDOWS_
1707+ if (wMaxLen>1) // we need space for terminating 0
1708+ {
1709+ BOOL bLineToGet; // true when a line to get
1710+ long lTimeOutTicks = U14WhenToTimeOut(hand);
1711+ do
1712+ bLineToGet = (BOOL)(U14LineCount(hand) != 0);
1713+ while (!bLineToGet && !U14PassedTime(lTimeOutTicks));
1714+
1715+ if (!bLineToGet) /* Last-ditch attempt to avoid timeout */
1716+ { /* This can happen with anti-virus or network activity! */
1717+ int i;
1718+ for (i = 0; (i < 4) && (!bLineToGet); ++i)
1719+ {
1720+ Sleep(25); /* Give other threads a chance for a while */
1721+ bLineToGet = (BOOL)(U14LineCount(hand) != 0);
1722+ }
1723+ }
1724+
1725+ if (bLineToGet)
1726+ {
1727+ if (asLastRetCode[hand] == U14ERR_NOERROR) /* all ok so far */
1728+ {
1729+ DWORD dwBytes = 0;
1730+ *((WORD *)pBuffer) = wMaxLen; /* set up length */
1731+#ifndef _WIN64
1732+ if (!USE_NT_DIOC(hand)) /* Win 95 DIOC here ? */
1733+ {
1734+ char tstr[MAXSTRLEN+5]; /* Buffer for Win95 chars */
1735+ int iOK;
1736+
1737+ if (wMaxLen > MAXSTRLEN) /* Truncate length */
1738+ wMaxLen = MAXSTRLEN;
1739+
1740+ *((WORD *)tstr) = wMaxLen; /* set len */
1741+
1742+ iOK = DeviceIoControl(aHand1401[hand],(DWORD)U14_GETSTRING,
1743+ NULL, 0, tstr, wMaxLen+sizeof(short),
1744+ &dwBytes, NULL);
1745+ if (iOK) /* Device IO control OK ? */
1746+ {
1747+ if (dwBytes >= 0) /* If driver OK */
1748+ {
1749+ strcpy(pBuffer, tstr);
1750+ sErr = U14ERR_NOERROR;
1751+ }
1752+ else
1753+ sErr = U14ERR_DRIVCOMMS;
1754+ }
1755+ else
1756+ {
1757+ sErr = (short)GetLastError();
1758+ if (sErr > 0) /* Errors are -ve */
1759+ sErr = (short)-sErr;
1760+ }
1761+ }
1762+ else
1763+#endif
1764+ { /* Here for NT, the DLL must own the buffer */
1765+ HANDLE hMem = GlobalAlloc(GMEM_MOVEABLE,wMaxLen+sizeof(short));
1766+ if (hMem)
1767+ {
1768+ char* pMem = (char*)GlobalLock(hMem);
1769+ if (pMem)
1770+ {
1771+ int iOK = DeviceIoControl(aHand1401[hand],(DWORD)U14_GETSTRING,
1772+ NULL, 0, pMem, wMaxLen+sizeof(short),
1773+ &dwBytes, NULL);
1774+ if (iOK) /* Device IO control OK ? */
1775+ {
1776+ if (dwBytes >= wMaxLen)
1777+ {
1778+ strcpy(pBuffer, pMem+sizeof(short));
1779+ sErr = *((SHORT*)pMem);
1780+ }
1781+ else
1782+ sErr = U14ERR_DRIVCOMMS;
1783+ }
1784+ else
1785+ sErr = U14ERR_DRIVCOMMS;
1786+
1787+ GlobalUnlock(hMem);
1788+ }
1789+ else
1790+ sErr = U14ERR_OUTOFMEMORY;
1791+
1792+ GlobalFree(hMem);
1793+ }
1794+ else
1795+ sErr = U14ERR_OUTOFMEMORY;
1796+ }
1797+
1798+ if (sErr == U14ERR_NOERROR) // If all OK...
1799+ TranslateString(pBuffer); // ...convert any commas to spaces
1800+ else // If we have had a comms error...
1801+ U14ForceReset(hand); // ...make sure we get real reset
1802+
1803+ }
1804+ else
1805+ sErr = asLastRetCode[hand];
1806+ }
1807+ else
1808+ {
1809+ sErr = U14ERR_TIMEOUT;
1810+ U14ForceReset(hand); // make sure we get real reset
1811+ }
1812+ }
1813+ else
1814+ sErr = U14ERR_BUFF_SMALL;
1815+ return sErr;
1816+#endif
1817+#ifdef LINUX
1818+ if (wMaxLen>1) // we need space for terminating 0
1819+ {
1820+ BOOL bLineToGet; // true when a line to get
1821+ long lTimeOutTicks = U14WhenToTimeOut(hand);
1822+ do
1823+ {
1824+ bLineToGet = (BOOL)(U14LineCount(hand) != 0);
1825+ if (!bLineToGet)
1826+ sched_yield();
1827+
1828+ }
1829+ while (!bLineToGet && !U14PassedTime(lTimeOutTicks));
1830+
1831+ if (bLineToGet)
1832+ {
1833+ sErr = CED_GetString(aHand1401[hand], pBuffer, wMaxLen-1); // space for terminator
1834+ if (sErr >=0) // if we were OK...
1835+ {
1836+ if (sErr >= wMaxLen) // this should NOT happen unless
1837+ sErr = U14ERR_DRIVCOMMS; // ...driver Comms are very bad
1838+ else
1839+ {
1840+ pBuffer[sErr] = 0; // OK, so terminate the string...
1841+ TranslateString(pBuffer); // ...and convert commas to spaces.
1842+ }
1843+ }
1844+
1845+ if (sErr < U14ERR_NOERROR) // If we have had a comms error
1846+ U14ForceReset(hand); // make sure we get real reset
1847+ }
1848+ else
1849+ {
1850+ sErr = U14ERR_TIMEOUT;
1851+ U14ForceReset(hand); // make sure we get real reset
1852+ }
1853+ }
1854+ else
1855+ sErr = U14ERR_BUFF_SMALL;
1856+
1857+ return sErr >= U14ERR_NOERROR ? U14ERR_NOERROR : sErr;
1858+#endif
1859+}
1860+
1861+/****************************************************************************
1862+** U14GetChar
1863+** Get a character from the 1401. CR returned as CR.
1864+*****************************************************************************/
1865+U14API(short) U14GetChar(short hand, char* pcChar)
1866+{
1867+#ifdef _IS_WINDOWS_
1868+ char sz[2]; // read a very short string
1869+ short sErr = U14GetString(hand, sz, 2); // read one char and nul terminate it
1870+ *pcChar = sz[0]; // copy to result, NB char translate done by GetString
1871+ if (sErr == U14ERR_NOERROR)
1872+ { // undo translate of CR to zero
1873+ if (*pcChar == '\0') // by converting back
1874+ *pcChar = '\n'; // What a nasty thing to have to do
1875+ }
1876+ return sErr;
1877+#endif
1878+#ifdef LINUX
1879+ short sErr = CheckHandle(hand);
1880+ if (sErr != U14ERR_NOERROR) // Check parameters
1881+ return sErr;
1882+ sErr = CED_GetChar(aHand1401[hand]); // get one char, if available
1883+ if (sErr >= 0)
1884+ {
1885+ *pcChar = (char)sErr; // return if it we have one
1886+ return U14ERR_NOERROR; // say all OK
1887+ }
1888+ else
1889+ return sErr;
1890+#endif
1891+}
1892+
1893+/****************************************************************************
1894+** U14Stat1401
1895+** Returns 0 for no lines or error or non zero for something waiting
1896+****************************************************************************/
1897+U14API(short) U14Stat1401(short hand)
1898+{
1899+ return ((short)(U14LineCount(hand) > 0));
1900+}
1901+
1902+/****************************************************************************
1903+** U14CharCount
1904+** Returns the number of characters in the input buffer
1905+*****************************************************************************/
1906+U14API(short) U14CharCount(short hand)
1907+{
1908+#ifdef _IS_WINDOWS_
1909+ TCSBLOCK csBlock;
1910+ short sErr = U14Status1401(hand, U14_STAT1401, &csBlock);
1911+ if (sErr == U14ERR_NOERROR)
1912+ sErr = csBlock.ints[0];
1913+ return sErr;
1914+#endif
1915+#ifdef LINUX
1916+ short sErr = CheckHandle(hand);
1917+ return (sErr == U14ERR_NOERROR) ? CED_Stat1401(aHand1401[hand]) : sErr;
1918+#endif
1919+}
1920+
1921+/****************************************************************************
1922+** U14LineCount
1923+** Returns the number of CR characters in the input buffer
1924+*****************************************************************************/
1925+U14API(short) U14LineCount(short hand)
1926+{
1927+#ifdef _IS_WINDOWS_
1928+ TCSBLOCK csBlock;
1929+ short sErr = U14Status1401(hand, U14_LINECOUNT, &csBlock);
1930+ if (sErr == U14ERR_NOERROR)
1931+ sErr = csBlock.ints[0];
1932+ return sErr;
1933+#endif
1934+#ifdef LINUX
1935+ short sErr = CheckHandle(hand);
1936+ return (sErr == U14ERR_NOERROR) ? CED_LineCount(aHand1401[hand]) : sErr;
1937+#endif
1938+}
1939+
1940+/****************************************************************************
1941+** U14GetErrorString
1942+** Converts error code supplied to a decent descriptive string.
1943+** NOTE: This function may use some extra information stored
1944+** internally in the DLL. This information is stored on a
1945+** per-process basis, but it might be altered if you call
1946+** other functions after getting an error and before using
1947+** this function.
1948+****************************************************************************/
1949+U14API(void) U14GetErrorString(short nErr, char* pStr, WORD wMax)
1950+{
1951+ char wstr[150];
1952+
1953+ switch (nErr) /* Basically, we do this with a switch block */
1954+ {
1955+ case U14ERR_OFF:
1956+ sprintf(wstr, "The 1401 is apparently switched off (code %d)", nErr);
1957+ break;
1958+
1959+ case U14ERR_NC:
1960+ sprintf(wstr, "The 1401 is not connected to the interface card (code %d)", nErr);
1961+ break;
1962+
1963+ case U14ERR_ILL:
1964+ sprintf(wstr, "The 1401 is not working correctly (code %d)", nErr);
1965+ break;
1966+
1967+ case U14ERR_NOIF:
1968+ sprintf(wstr, "The 1401 interface card was not detected (code %d)", nErr);
1969+ break;
1970+
1971+ case U14ERR_TIME:
1972+ sprintf(wstr, "The 1401 fails to become ready for use (code %d)", nErr);
1973+ break;
1974+
1975+ case U14ERR_BADSW:
1976+ sprintf(wstr, "The 1401 interface card jumpers are incorrect (code %d)", nErr);
1977+ break;
1978+
1979+ case U14ERR_NOINT:
1980+ sprintf(wstr, "The 1401 interrupt is not available for use (code %d)", nErr);
1981+ break;
1982+
1983+ case U14ERR_INUSE:
1984+ sprintf(wstr, "The 1401 is already in use by another program (code %d)", nErr);
1985+ break;
1986+
1987+ case U14ERR_NODMA:
1988+ sprintf(wstr, "The 1401 DMA channel is not available for use (code %d)", nErr);
1989+ break;
1990+
1991+ case U14ERR_BADHAND:
1992+ sprintf(wstr, "The application supplied an incorrect 1401 handle (code %d)", nErr);
1993+ break;
1994+
1995+ case U14ERR_BAD1401NUM:
1996+ sprintf(wstr, "The application used an incorrect 1401 number (code %d)", nErr);
1997+ break;
1998+
1999+ case U14ERR_NO_SUCH_FN:
2000+ sprintf(wstr, "The code passed to the 1401 driver is invalid (code %d)", nErr);
2001+ break;
2002+
2003+ case U14ERR_NO_SUCH_SUBFN:
2004+ sprintf(wstr, "The sub-code passed to the 1401 driver is invalid (code %d)", nErr);
2005+ break;
2006+
2007+ case U14ERR_NOOUT:
2008+ sprintf(wstr, "No room in buffer for characters for the 1401 (code %d)", nErr);
2009+ break;
2010+
2011+ case U14ERR_NOIN:
2012+ sprintf(wstr, "No characters from the 1401 are available (code %d)", nErr);
2013+ break;
2014+
2015+ case U14ERR_STRLEN:
2016+ sprintf(wstr, "A string sent to or read from the 1401 was too long (code %d)", nErr);
2017+ break;
2018+
2019+ case U14ERR_LOCKFAIL:
2020+ sprintf(wstr, "Failed to lock host memory for data transfer (code %d)", nErr);
2021+ break;
2022+
2023+ case U14ERR_UNLOCKFAIL:
2024+ sprintf(wstr, "Failed to unlock host memory after data transfer (code %d)", nErr);
2025+ break;
2026+
2027+ case U14ERR_ALREADYSET:
2028+ sprintf(wstr, "The transfer area used is already set up (code %d)", nErr);
2029+ break;
2030+
2031+ case U14ERR_NOTSET:
2032+ sprintf(wstr, "The transfer area used has not been set up (code %d)", nErr);
2033+ break;
2034+
2035+ case U14ERR_BADAREA:
2036+ sprintf(wstr, "The transfer area number is incorrect (code %d)", nErr);
2037+ break;
2038+
2039+ case U14ERR_NOFILE:
2040+ sprintf(wstr, "The command file %s could not be opened (code %d)", szLastName, nErr);
2041+ break;
2042+
2043+ case U14ERR_READERR:
2044+ sprintf(wstr, "The command file %s could not be read (code %d)", szLastName, nErr);
2045+ break;
2046+
2047+ case U14ERR_UNKNOWN:
2048+ sprintf(wstr, "The %s command resource could not be found (code %d)", szLastName, nErr);
2049+ break;
2050+
2051+ case U14ERR_HOSTSPACE:
2052+ sprintf(wstr, "Unable to allocate memory for loading command %s (code %d)", szLastName, nErr);
2053+ break;
2054+
2055+ case U14ERR_LOCKERR:
2056+ sprintf(wstr, "Unable to lock memory for loading command %s (code %d)", szLastName, nErr);
2057+ break;
2058+
2059+ case U14ERR_CLOADERR:
2060+ sprintf(wstr, "Error in loading command %s, bad command format (code %d)", szLastName, nErr);
2061+ break;
2062+
2063+ case U14ERR_TOXXXERR:
2064+ sprintf(wstr, "Error detected after data transfer to or from the 1401 (code %d)", nErr);
2065+ break;
2066+
2067+ case U14ERR_NO386ENH:
2068+ sprintf(wstr, "Windows 3.1 is not running in 386 enhanced mode (code %d)", nErr);
2069+ break;
2070+
2071+ case U14ERR_NO1401DRIV:
2072+ sprintf(wstr, "The 1401 device driver cannot be found (code %d)\nUSB: check plugged in and powered\nOther: not installed?", nErr);
2073+ break;
2074+
2075+ case U14ERR_DRIVTOOOLD:
2076+ sprintf(wstr, "The 1401 device driver is too old for use (code %d)", nErr);
2077+ break;
2078+
2079+ case U14ERR_TIMEOUT:
2080+ sprintf(wstr, "Character transmissions to the 1401 timed-out (code %d)", nErr);
2081+ break;
2082+
2083+ case U14ERR_BUFF_SMALL:
2084+ sprintf(wstr, "Buffer for text from the 1401 was too small (code %d)", nErr);
2085+ break;
2086+
2087+ case U14ERR_CBALREADY:
2088+ sprintf(wstr, "1401 monitor callback already set up (code %d)", nErr);
2089+ break;
2090+
2091+ case U14ERR_BADDEREG:
2092+ sprintf(wstr, "1401 monitor callback deregister invalid (code %d)", nErr);
2093+ break;
2094+
2095+ case U14ERR_DRIVCOMMS:
2096+ sprintf(wstr, "1401 device driver communications failed (code %d)", nErr);
2097+ break;
2098+
2099+ case U14ERR_OUTOFMEMORY:
2100+ sprintf(wstr, "Failed to allocate or lock memory for text from the 1401 (code %d)", nErr);
2101+ break;
2102+
2103+ default:
2104+ sprintf(wstr, "1401 error code %d returned; this code is unknown", nErr);
2105+ break;
2106+
2107+ }
2108+ if ((WORD)strlen(wstr) >= wMax-1) /* Check for string being too long */
2109+ wstr[wMax-1] = 0; /* and truncate it if so */
2110+ strcpy(pStr, wstr); /* Return the error string */
2111+}
2112+
2113+/***************************************************************************
2114+** U14GetTransfer
2115+** Get a TGET_TX_BLOCK describing a transfer area (held in the block)
2116+***************************************************************************/
2117+U14API(short) U14GetTransfer(short hand, TGET_TX_BLOCK *pTransBlock)
2118+{
2119+ short sErr = CheckHandle(hand);
2120+#ifdef _IS_WINDOWS_
2121+ if (sErr == U14ERR_NOERROR)
2122+ {
2123+ DWORD dwBytes = 0;
2124+ BOOL bOK = DeviceIoControl(aHand1401[hand], (DWORD)U14_GETTRANSFER, NULL, 0, pTransBlock,
2125+ sizeof(TGET_TX_BLOCK), &dwBytes, NULL);
2126+
2127+ if (bOK && (dwBytes >= sizeof(TGET_TX_BLOCK)))
2128+ sErr = U14ERR_NOERROR;
2129+ else
2130+ sErr = U14ERR_DRIVCOMMS;
2131+ }
2132+ return sErr;
2133+#endif
2134+#ifdef LINUX
2135+ return (sErr == U14ERR_NOERROR) ? CED_GetTransfer(aHand1401[hand], pTransBlock) : sErr;
2136+#endif
2137+}
2138+/////////////////////////////////////////////////////////////////////////////
2139+// U14WorkingSet
2140+// For Win32 only, adjusts process working set so that minimum is at least
2141+// dwMinKb and maximum is at least dwMaxKb.
2142+// Return value is zero if all went OK, or a code from 1 to 3 indicating the
2143+// cause of the failure:
2144+//
2145+// 1 unable to access process (insufficient rights?)
2146+// 2 unable to read process working set
2147+// 3 unable to set process working set - bad parameters?
2148+U14API(short) U14WorkingSet(DWORD dwMinKb, DWORD dwMaxKb)
2149+{
2150+#ifdef _IS_WINDOWS_
2151+ short sRetVal = 0; // 0 means all is OK
2152+ HANDLE hProcess;
2153+ DWORD dwVer = GetVersion();
2154+ if (dwVer & 0x80000000) // is this not NT?
2155+ return 0; // then give up right now
2156+
2157+ // Now attempt to get information on working set size
2158+ hProcess = OpenProcess(STANDARD_RIGHTS_REQUIRED |
2159+ PROCESS_QUERY_INFORMATION |
2160+ PROCESS_SET_QUOTA,
2161+ FALSE, _getpid());
2162+ if (hProcess)
2163+ {
2164+ SIZE_T dwMinSize,dwMaxSize;
2165+ if (GetProcessWorkingSetSize(hProcess, &dwMinSize, &dwMaxSize))
2166+ {
2167+ DWORD dwMin = dwMinKb << 10; // convert from kb to bytes
2168+ DWORD dwMax = dwMaxKb << 10;
2169+
2170+ // if we get here, we have managed to read the current size
2171+ if (dwMin > dwMinSize) // need to change sizes?
2172+ dwMinSize = dwMin;
2173+
2174+ if (dwMax > dwMaxSize)
2175+ dwMaxSize = dwMax;
2176+
2177+ if (!SetProcessWorkingSetSize(hProcess, dwMinSize, dwMaxSize))
2178+ sRetVal = 3; // failed to change size
2179+ }
2180+ else
2181+ sRetVal = 2; // failed to read original size
2182+
2183+ CloseHandle(hProcess);
2184+ }
2185+ else
2186+ sRetVal = 1; // failed to get handle
2187+
2188+ return sRetVal;
2189+#endif
2190+#ifdef LINUX
2191+ if (dwMinKb | dwMaxKb)
2192+ {
2193+ // to stop compiler moaning
2194+ }
2195+ return U14ERR_NOERROR;
2196+#endif
2197+}
2198+
2199+/****************************************************************************
2200+** U14UnSetTransfer Cancels a transfer area
2201+** wArea The index of a block previously used in by SetTransfer
2202+*****************************************************************************/
2203+U14API(short) U14UnSetTransfer(short hand, WORD wArea)
2204+{
2205+ short sErr = CheckHandle(hand);
2206+#ifdef _IS_WINDOWS_
2207+ if (sErr == U14ERR_NOERROR)
2208+ {
2209+ TCSBLOCK csBlock;
2210+ csBlock.ints[0] = (short)wArea; /* Area number into control block */
2211+ sErr = U14Control1401(hand, U14_UNSETTRANSFER, &csBlock); /* Free area */
2212+
2213+ VirtualUnlock(apAreas[hand][wArea], auAreas[hand][wArea]);/* Unlock */
2214+ apAreas[hand][wArea] = NULL; /* Clear locations */
2215+ auAreas[hand][wArea] = 0;
2216+ }
2217+ return sErr;
2218+#endif
2219+#ifdef LINUX
2220+ return (sErr == U14ERR_NOERROR) ? CED_UnsetTransfer(aHand1401[hand], wArea) : sErr;
2221+#endif
2222+}
2223+
2224+/****************************************************************************
2225+** U14SetTransArea Sets an area up to be used for transfers
2226+** WORD wArea The area number to set up
2227+** void *pvBuff The address of the buffer for the data.
2228+** DWORD dwLength The length of the buffer for the data
2229+** short eSz The element size (used for byte swapping on the Mac)
2230+****************************************************************************/
2231+U14API(short) U14SetTransArea(short hand, WORD wArea, void *pvBuff,
2232+ DWORD dwLength, short eSz)
2233+{
2234+ TRANSFERDESC td;
2235+ short sErr = CheckHandle(hand);
2236+ if (sErr != U14ERR_NOERROR)
2237+ return sErr;
2238+ if (wArea >= MAX_TRANSAREAS) // Is this a valid area number
2239+ return U14ERR_BADAREA;
2240+
2241+#ifdef _IS_WINDOWS_
2242+ assert(apAreas[hand][wArea] == NULL);
2243+ assert(auAreas[hand][wArea] == 0);
2244+
2245+ apAreas[hand][wArea] = pvBuff; /* Save data for later */
2246+ auAreas[hand][wArea] = dwLength;
2247+
2248+ if (!VirtualLock(pvBuff, dwLength)) /* Lock using WIN32 calls */
2249+ {
2250+ apAreas[hand][wArea] = NULL; /* Clear locations */
2251+ auAreas[hand][wArea] = 0;
2252+ return U14ERR_LOCKERR; /* VirtualLock failed */
2253+ }
2254+#ifndef _WIN64
2255+ if (!USE_NT_DIOC(hand)) /* Use Win 9x DIOC? */
2256+ {
2257+ DWORD dwBytes;
2258+ VXTRANSFERDESC vxDesc; /* Structure to pass to VXD */
2259+ vxDesc.wArea = wArea; /* Copy across simple params */
2260+ vxDesc.dwLength = dwLength;
2261+
2262+ // Check we are not asking an old driver for more than area 0
2263+ if ((wArea != 0) && (U14DriverVersion(hand) < 0x00010002L))
2264+ sErr = U14ERR_DRIVTOOOLD;
2265+ else
2266+ {
2267+ vxDesc.dwAddrOfs = (DWORD)pvBuff; /* 32 bit offset */
2268+ vxDesc.wAddrSel = 0;
2269+
2270+ if (DeviceIoControl(aHand1401[hand], (DWORD)U14_SETTRANSFER,
2271+ pvBuff,dwLength, /* Will translate pointer */
2272+ &vxDesc,sizeof(VXTRANSFERDESC),
2273+ &dwBytes,NULL))
2274+ {
2275+ if (dwBytes >= sizeof(VXTRANSFERDESC)) /* Driver OK ? */
2276+ sErr = U14ERR_NOERROR;
2277+ else
2278+ sErr = U14ERR_DRIVCOMMS; /* Else never got there */
2279+ }
2280+ else
2281+ sErr = (short)GetLastError();
2282+ }
2283+ }
2284+ else
2285+#endif
2286+ {
2287+ PARAMBLK rWork;
2288+ DWORD dwBytes;
2289+ td.wArea = wArea; /* Pure NT - put data into struct */
2290+ td.lpvBuff = pvBuff;
2291+ td.dwLength = dwLength;
2292+ td.eSize = 0; // Dummy element size
2293+
2294+ if (DeviceIoControl(aHand1401[hand],(DWORD)U14_SETTRANSFER,
2295+ &td,sizeof(TRANSFERDESC),
2296+ &rWork,sizeof(PARAMBLK),&dwBytes,NULL))
2297+ {
2298+ if (dwBytes >= sizeof(PARAMBLK)) // maybe error from driver?
2299+ sErr = rWork.sState; // will report any error
2300+ else
2301+ sErr = U14ERR_DRIVCOMMS; // Else never got there
2302+ }
2303+ else
2304+ sErr = U14ERR_DRIVCOMMS;
2305+ }
2306+
2307+ if (sErr != U14ERR_NOERROR)
2308+ {
2309+ if (sErr != U14ERR_LOCKERR) // unless lock failed...
2310+ VirtualUnlock(pvBuff, dwLength); // ...release the lock
2311+ apAreas[hand][wArea] = NULL; // Clear locations
2312+ auAreas[hand][wArea] = 0;
2313+ }
2314+
2315+ return sErr;
2316+#endif
2317+#ifdef LINUX
2318+ // The strange cast is so that it works in 64 and 32-bit linux as long is 64-bits
2319+ // in the 64 bit version.
2320+ td.lpvBuff = (long long)((unsigned long)pvBuff);
2321+ td.wAreaNum = wArea;
2322+ td.dwLength = dwLength;
2323+ td.eSize = eSz; // Dummy element size
2324+ return CED_SetTransfer(aHand1401[hand], &td);
2325+#endif
2326+}
2327+
2328+/****************************************************************************
2329+** U14SetTransferEvent Sets an event for notification of application
2330+** wArea The tranfer area index, from 0 to MAXAREAS-1
2331+** bEvent True to create an event, false to remove it
2332+** bToHost Set 0 for notification on to1401 tranfers, 1 for
2333+** notification of transfers to the host PC
2334+** dwStart The offset of the sub-area of interest
2335+** dwLength The size of the sub-area of interest
2336+**
2337+** The device driver will set the event supplied to the signalled state
2338+** whenever a DMA transfer to/from the specified area is completed. The
2339+** transfer has to be in the direction specified by bToHost, and overlap
2340+** that part of the whole transfer area specified by dwStart and dwLength.
2341+** It is important that this function is called with bEvent false to release
2342+** the event once 1401 activity is finished.
2343+**
2344+** Returns 1 if an event handle exists, 0 if all OK and no event handle or
2345+** a negative code for an error.
2346+****************************************************************************/
2347+U14API(short) U14SetTransferEvent(short hand, WORD wArea, BOOL bEvent,
2348+ BOOL bToHost, DWORD dwStart, DWORD dwLength)
2349+{
2350+#ifdef _IS_WINDOWS_
2351+ TCSBLOCK csBlock;
2352+ short sErr = U14TransferFlags(hand); // see if we can handle events
2353+ if (sErr >= U14ERR_NOERROR) // check handle is OK
2354+ {
2355+ bEvent = bEvent && ((sErr & U14TF_NOTIFY) != 0); // remove request if we cannot do events
2356+ if (wArea >= MAX_TRANSAREAS) // Check a valid area...
2357+ return U14ERR_BADAREA; // ...and bail of not
2358+
2359+ // We can hold an event for each area, so see if we need to change the
2360+ // state of the event.
2361+ if ((bEvent != 0) != (aXferEvent[hand] != 0)) // change of event state?
2362+ {
2363+ if (bEvent) // want one and none present
2364+ aXferEvent[hand] = CreateEvent(NULL, FALSE, FALSE, NULL);
2365+ else
2366+ {
2367+ CloseHandle(aXferEvent[hand]); // clear the existing event
2368+ aXferEvent[hand] = NULL; // and clear handle
2369+ }
2370+ }
2371+
2372+ // We have to store the parameters differently for 64-bit operations
2373+ // because a handle is 64 bits long. The drivers know of this and
2374+ // handle the information appropriately.
2375+#ifdef _WIN64
2376+ csBlock.longs[0] = wArea; // Pass paramaters into the driver...
2377+ if (bToHost != 0) // The direction flag is held in the
2378+ csBlock.longs[0] |= 0x10000; // upper word of the transfer area value
2379+ *((HANDLE*)&csBlock.longs[1]) = aXferEvent[hand]; // The event handle is 64-bits
2380+ csBlock.longs[3] = dwStart; // Thankfully these two remain
2381+ csBlock.longs[4] = dwLength; // as unsigned 32-bit values
2382+#else
2383+ csBlock.longs[0] = wArea; // pass paramaters into the driver...
2384+ csBlock.longs[1] = (long)aXferEvent[hand]; // ...especially the event handle
2385+ csBlock.longs[2] = bToHost;
2386+ csBlock.longs[3] = dwStart;
2387+ csBlock.longs[4] = dwLength;
2388+#endif
2389+ sErr = U14Control1401(hand, U14_SETTRANSEVENT, &csBlock);
2390+ if (sErr == U14ERR_NOERROR)
2391+ sErr = (short)(aXferEvent[hand] != NULL); // report if we have a flag
2392+ }
2393+
2394+ return sErr;
2395+#endif
2396+#ifdef LINUX
2397+ TRANSFEREVENT te;
2398+ short sErr = CheckHandle(hand);
2399+ if (sErr != U14ERR_NOERROR)
2400+ return sErr;
2401+
2402+ if (wArea >= MAX_TRANSAREAS) // Is this a valid area number
2403+ return U14ERR_BADAREA;
2404+
2405+ te.wAreaNum = wArea; // copy parameters to the control block
2406+ te.wFlags = bToHost ? 1 : 0; // bit 0 sets the direction
2407+ te.dwStart = dwStart; // start offset of the event area
2408+ te.dwLength = dwLength; // size of the event area
2409+ te.iSetEvent = bEvent; // in Windows, this creates/destroys the event
2410+ return CED_SetEvent(aHand1401[hand], &te);
2411+#endif
2412+}
2413+
2414+/****************************************************************************
2415+** U14TestTransferEvent
2416+** Would a U14WaitTransferEvent() call return immediately? return 1 if so,
2417+** 0 if not or a negative code if a problem.
2418+****************************************************************************/
2419+U14API(int) U14TestTransferEvent(short hand, WORD wArea)
2420+{
2421+#ifdef _IS_WINDOWS_
2422+ int iErr = CheckHandle(hand);
2423+ if (iErr == U14ERR_NOERROR)
2424+ {
2425+ if (aXferEvent[hand]) // if a handle is set...
2426+ iErr = WaitForSingleObject(aXferEvent[hand], 0) == WAIT_OBJECT_0;
2427+ }
2428+ return iErr;
2429+#endif
2430+#ifdef LINUX
2431+ short sErr = CheckHandle(hand);
2432+ return (sErr == U14ERR_NOERROR) ? CED_TestEvent(aHand1401[hand], wArea) : sErr;
2433+#endif
2434+}
2435+
2436+/****************************************************************************
2437+** U14WaitTransferEvent
2438+** Wait for a transfer event with a timeout.
2439+** msTimeOut is 0 for an infinite wait, else it is the maximum time to wait
2440+** in milliseconds in range 0-0x00ffffff.
2441+** Returns If no event handle then return immediately. Else return 1 if
2442+** timed out or 0=event, and a negative code if a problem.
2443+****************************************************************************/
2444+U14API(int) U14WaitTransferEvent(short hand, WORD wArea, int msTimeOut)
2445+{
2446+#ifdef _IS_WINDOWS_
2447+ int iErr = CheckHandle(hand);
2448+ if (iErr == U14ERR_NOERROR)
2449+ {
2450+ if (aXferEvent[hand])
2451+ {
2452+ if (msTimeOut == 0)
2453+ msTimeOut = INFINITE;
2454+ iErr = WaitForSingleObject(aXferEvent[hand], msTimeOut) != WAIT_OBJECT_0;
2455+ }
2456+ else
2457+ iErr = TRUE; // say we timed out if no event
2458+ }
2459+ return iErr;
2460+#endif
2461+#ifdef LINUX
2462+ short sErr = CheckHandle(hand);
2463+ return (sErr == U14ERR_NOERROR) ? CED_WaitEvent(aHand1401[hand], wArea, msTimeOut) : sErr;
2464+#endif
2465+}
2466+
2467+/****************************************************************************
2468+** U14SetCircular Sets an area up for circular DMA transfers
2469+** WORD wArea The area number to set up
2470+** BOOL bToHost Sets the direction of data transfer
2471+** void *pvBuff The address of the buffer for the data
2472+** DWORD dwLength The length of the buffer for the data
2473+****************************************************************************/
2474+U14API(short) U14SetCircular(short hand, WORD wArea, BOOL bToHost,
2475+ void *pvBuff, DWORD dwLength)
2476+{
2477+ short sErr = CheckHandle(hand);
2478+ if (sErr != U14ERR_NOERROR)
2479+ return sErr;
2480+
2481+ if (wArea >= MAX_TRANSAREAS) /* Is this a valid area number */
2482+ return U14ERR_BADAREA;
2483+
2484+ if (!bToHost) /* For now, support tohost transfers only */
2485+ return U14ERR_BADAREA; /* best error code I can find */
2486+#ifdef _IS_WINDOWS_
2487+ assert(apAreas[hand][wArea] == NULL);
2488+ assert(auAreas[hand][wArea] == 0);
2489+
2490+ apAreas[hand][wArea] = pvBuff; /* Save data for later */
2491+ auAreas[hand][wArea] = dwLength;
2492+
2493+ if (!VirtualLock(pvBuff, dwLength)) /* Lock using WIN32 calls */
2494+ sErr = U14ERR_LOCKERR; /* VirtualLock failed */
2495+ else
2496+ {
2497+ PARAMBLK rWork;
2498+ DWORD dwBytes;
2499+ TRANSFERDESC txDesc;
2500+ txDesc.wArea = wArea; /* Pure NT - put data into struct */
2501+ txDesc.lpvBuff = pvBuff;
2502+ txDesc.dwLength = dwLength;
2503+ txDesc.eSize = (short)bToHost; /* Use this for direction flag */
2504+
2505+ if (DeviceIoControl(aHand1401[hand],(DWORD)U14_SETCIRCULAR,
2506+ &txDesc, sizeof(TRANSFERDESC),
2507+ &rWork, sizeof(PARAMBLK),&dwBytes,NULL))
2508+ {
2509+ if (dwBytes >= sizeof(PARAMBLK)) /* error from driver? */
2510+ sErr = rWork.sState; /* No, just return driver data */
2511+ else
2512+ sErr = U14ERR_DRIVCOMMS; /* Else never got there */
2513+ }
2514+ else
2515+ sErr = U14ERR_DRIVCOMMS;
2516+ }
2517+
2518+ if (sErr != U14ERR_NOERROR)
2519+ {
2520+ if (sErr != U14ERR_LOCKERR)
2521+ VirtualUnlock(pvBuff, dwLength); /* Release NT lock */
2522+ apAreas[hand][wArea] = NULL; /* Clear locations */
2523+ auAreas[hand][wArea] = 0;
2524+ }
2525+
2526+ return sErr;
2527+#endif
2528+#ifdef LINUX
2529+ else
2530+ {
2531+ TRANSFERDESC td;
2532+ td.lpvBuff = (long long)((unsigned long)pvBuff);
2533+ td.wAreaNum = wArea;
2534+ td.dwLength = dwLength;
2535+ td.eSize = (short)bToHost; /* Use this for direction flag */
2536+ return CED_SetCircular(aHand1401[hand], &td);
2537+ }
2538+#endif
2539+}
2540+
2541+/****************************************************************************
2542+** Function GetCircBlk returns the size (& start offset) of the next
2543+** available block of circular data.
2544+****************************************************************************/
2545+U14API(int) U14GetCircBlk(short hand, WORD wArea, DWORD *pdwOffs)
2546+{
2547+ int lErr = CheckHandle(hand);
2548+ if (lErr != U14ERR_NOERROR)
2549+ return lErr;
2550+
2551+ if (wArea >= MAX_TRANSAREAS) // Is this a valid area number?
2552+ return U14ERR_BADAREA;
2553+ else
2554+ {
2555+#ifdef _IS_WINDOWS_
2556+ PARAMBLK rWork;
2557+ TCSBLOCK csBlock;
2558+ DWORD dwBytes;
2559+ csBlock.longs[0] = wArea; // Area number into control block
2560+ rWork.sState = U14ERR_DRIVCOMMS;
2561+ if (DeviceIoControl(aHand1401[hand], (DWORD)U14_GETCIRCBLK, &csBlock, sizeof(TCSBLOCK), &rWork, sizeof(PARAMBLK), &dwBytes, NULL) &&
2562+ (dwBytes >= sizeof(PARAMBLK)))
2563+ lErr = rWork.sState;
2564+ else
2565+ lErr = U14ERR_DRIVCOMMS;
2566+
2567+ if (lErr == U14ERR_NOERROR) // Did everything go OK?
2568+ { // Yes, we can pass the results back
2569+ lErr = rWork.csBlock.longs[1]; // Return the block information
2570+ *pdwOffs = rWork.csBlock.longs[0]; // Offset is first in array
2571+ }
2572+#endif
2573+#ifdef LINUX
2574+ TCIRCBLOCK cb;
2575+ cb.nArea = wArea; // Area number into control block
2576+ cb.dwOffset = 0;
2577+ cb.dwSize = 0;
2578+ lErr = CED_GetCircBlock(aHand1401[hand], &cb);
2579+ if (lErr == U14ERR_NOERROR) // Did everything go OK?
2580+ { // Yes, we can pass the results back
2581+ lErr = cb.dwSize; // return the size
2582+ *pdwOffs = cb.dwOffset; // and the offset
2583+ }
2584+#endif
2585+ }
2586+ return lErr;
2587+}
2588+
2589+/****************************************************************************
2590+** Function FreeCircBlk marks the specified area of memory as free for
2591+** resuse for circular transfers and returns the size (& start
2592+** offset) of the next available block of circular data.
2593+****************************************************************************/
2594+U14API(int) U14FreeCircBlk(short hand, WORD wArea, DWORD dwOffs, DWORD dwSize,
2595+ DWORD *pdwOffs)
2596+{
2597+ int lErr = CheckHandle(hand);
2598+ if (lErr != U14ERR_NOERROR)
2599+ return lErr;
2600+
2601+ if (wArea < MAX_TRANSAREAS) // Is this a valid area number
2602+ {
2603+#ifdef _IS_WINDOWS_
2604+ PARAMBLK rWork;
2605+ TCSBLOCK csBlock;
2606+ DWORD dwBytes;
2607+ csBlock.longs[0] = wArea; // Area number into control block
2608+ csBlock.longs[1] = dwOffs;
2609+ csBlock.longs[2] = dwSize;
2610+ rWork.sState = U14ERR_DRIVCOMMS;
2611+ if (DeviceIoControl(aHand1401[hand], (DWORD)U14_FREECIRCBLK, &csBlock, sizeof(TCSBLOCK),
2612+ &rWork, sizeof(PARAMBLK), &dwBytes, NULL) &&
2613+ (dwBytes >= sizeof(PARAMBLK)))
2614+ lErr = rWork.sState;
2615+ else
2616+ lErr = U14ERR_DRIVCOMMS;
2617+ if (lErr == U14ERR_NOERROR) // Did everything work OK?
2618+ { // Yes, we can pass the results back
2619+ lErr = rWork.csBlock.longs[1]; // Return the block information
2620+ *pdwOffs = rWork.csBlock.longs[0]; // Offset is first in array
2621+ }
2622+#endif
2623+#ifdef LINUX
2624+ TCIRCBLOCK cb;
2625+ cb.nArea = wArea; // Area number into control block
2626+ cb.dwOffset = dwOffs;
2627+ cb.dwSize = dwSize;
2628+
2629+ lErr = CED_FreeCircBlock(aHand1401[hand], &cb);
2630+ if (lErr == U14ERR_NOERROR) // Did everything work OK?
2631+ { // Yes, we can pass the results back
2632+ lErr = cb.dwSize; // Return the block information
2633+ *pdwOffs = cb.dwOffset; // Offset is first in array
2634+ }
2635+#endif
2636+ }
2637+ else
2638+ lErr = U14ERR_BADAREA;
2639+
2640+ return lErr;
2641+}
2642+
2643+/****************************************************************************
2644+** Transfer
2645+** Transfer moves data to 1401 or to host
2646+** Assumes memory is allocated and locked,
2647+** which it should be to get a pointer
2648+*****************************************************************************/
2649+static short Transfer(short hand, BOOL bTo1401, char* pData,
2650+ DWORD dwSize, DWORD dw1401, short eSz)
2651+{
2652+ char strcopy[MAXSTRLEN+1]; // to hold copy of work string
2653+ short sResult = U14SetTransArea(hand, 0, (void *)pData, dwSize, eSz);
2654+ if (sResult == U14ERR_NOERROR) // no error
2655+ {
2656+ sprintf(strcopy, // data offset is always 0
2657+ "TO%s,$%X,$%X,0;", bTo1401 ? "1401" : "HOST", dw1401, dwSize);
2658+
2659+ U14SendString(hand, strcopy); // send transfer string
2660+
2661+ sResult = U14CheckErr(hand); // Use ERR command to check for done
2662+ if (sResult > 0)
2663+ sResult = U14ERR_TOXXXERR; // If a 1401 error, use this code
2664+
2665+ U14UnSetTransfer(hand, 0);
2666+ }
2667+ return sResult;
2668+}
2669+
2670+/****************************************************************************
2671+** Function ToHost transfers data into the host from the 1401
2672+****************************************************************************/
2673+U14API(short) U14ToHost(short hand, char* pAddrHost, DWORD dwSize,
2674+ DWORD dw1401, short eSz)
2675+{
2676+ short sErr = CheckHandle(hand);
2677+ if ((sErr == U14ERR_NOERROR) && dwSize) // TOHOST is a constant
2678+ sErr = Transfer(hand, TOHOST, pAddrHost, dwSize, dw1401, eSz);
2679+ return sErr;
2680+}
2681+
2682+/****************************************************************************
2683+** Function To1401 transfers data into the 1401 from the host
2684+****************************************************************************/
2685+U14API(short) U14To1401(short hand, const char* pAddrHost,DWORD dwSize,
2686+ DWORD dw1401, short eSz)
2687+{
2688+ short sErr = CheckHandle(hand);
2689+ if ((sErr == U14ERR_NOERROR) && dwSize) // TO1401 is a constant
2690+ sErr = Transfer(hand, TO1401, (char*)pAddrHost, dwSize, dw1401, eSz);
2691+ return sErr;
2692+}
2693+
2694+/****************************************************************************
2695+** Function LdCmd Loads a command from a full path or just a file
2696+*****************************************************************************/
2697+#ifdef _IS_WINDOWS_
2698+#define file_exist(name) (_access(name, 0) != -1)
2699+#define file_open(name) _lopen(name, OF_READ)
2700+#define file_close(h) _lclose(h)
2701+#define file_seek(h, pos) _llseek(h, pos, FILE_BEGIN)
2702+#define file_read(h, buffer, size) (_lread(h, buffer, size) == size)
2703+#endif
2704+#ifdef LINUX
2705+#define file_exist(name) (access(name, F_OK) != -1)
2706+#define file_open(name) open(name, O_RDONLY)
2707+#define file_close(h) close(h)
2708+#define file_seek(h, pos) lseek(h, pos, SEEK_SET)
2709+#define file_read(h, buffer, size) (read(h, buffer, size) == (ssize_t)size)
2710+static DWORD GetModuleFileName(void* dummy, char* buffer, int max)
2711+{
2712+ // The following works for Linux systems with a /proc file system.
2713+ char szProcPath[32];
2714+ sprintf(szProcPath, "/proc/%d/exe", getpid()); // attempt to read link
2715+ if (readlink(szProcPath, buffer, max) != -1)
2716+ {
2717+ dirname (buffer);
2718+ strcat (buffer, "/");
2719+ return strlen(buffer);
2720+ }
2721+ return 0;
2722+}
2723+#endif
2724+
2725+U14API(short) U14LdCmd(short hand, const char* command)
2726+{
2727+ char strcopy[MAXSTRLEN+1]; // to hold copy of work string
2728+ BOOL bGotIt = FALSE; // have we found the command file?
2729+ int iFHandle; // file handle of command
2730+#define FNSZ 260
2731+ char filnam[FNSZ]; // space to build name in
2732+ char szCmd[25]; // just the command name with extension
2733+
2734+ short sErr = CheckHandle(hand);
2735+ if (sErr != U14ERR_NOERROR)
2736+ return sErr;
2737+
2738+ if (strchr(command, '.') != NULL) // see if we have full name
2739+ {
2740+ if (file_exist(command)) // If the file exists
2741+ {
2742+ strcpy(filnam, command); // use name as is
2743+ bGotIt = TRUE; // Flag no more searching
2744+ }
2745+ else // not found, get file name for search
2746+ {
2747+ char* pStr = strrchr(command, PATHSEP); // Point to last separator
2748+ if (pStr != NULL) // Check we got it
2749+ {
2750+ pStr++; // move past the backslash
2751+ strcpy(szCmd, pStr); // copy file name as is
2752+ }
2753+ else
2754+ strcpy(szCmd, command); // use as is
2755+ }
2756+ }
2757+ else // File extension not supplied, so build the command file name
2758+ {
2759+ char szExt[8];
2760+ strcpy(szCmd, command); // Build command file name
2761+ ExtForType(asType1401[hand], szExt);// File extension string
2762+ strcat(szCmd, szExt); // add it to the end
2763+ }
2764+
2765+ // Next place to look is in the 1401 folder in the same place as the
2766+ // application was run from.
2767+ if (!bGotIt) // Still not got it?
2768+ {
2769+ DWORD dwLen = GetModuleFileName(NULL, filnam, FNSZ); // Get app path
2770+ if (dwLen > 0) // and use it as path if found
2771+ {
2772+ char* pStr = strrchr(filnam, PATHSEP); // Point to last separator
2773+ if (pStr != NULL)
2774+ {
2775+ *(++pStr) = 0; // Terminate string there
2776+ if (strlen(filnam) < FNSZ-6) // make sure we have space
2777+ {
2778+ strcat(filnam, "1401" PATHSEPSTR); // add in 1401 subdir
2779+ strcat(filnam,szCmd);
2780+ bGotIt = (BOOL)file_exist(filnam); // See if file exists
2781+ }
2782+ }
2783+ }
2784+ }
2785+
2786+ // Next place to look is in whatever path is set by the 1401DIR environment
2787+ // variable, if it exists.
2788+ if (!bGotIt) // Need to do more searches?/
2789+ {
2790+ char* pStr = getenv("1401DIR"); // Try to find environment var
2791+ if (pStr != NULL) // and use it as path if found
2792+ {
2793+ strcpy(filnam, pStr); // Use path in environment
2794+ if (filnam[strlen(filnam)-1] != PATHSEP)// We need separator
2795+ strcat(filnam, PATHSEPSTR);
2796+ strcat(filnam, szCmd);
2797+ bGotIt = (BOOL)file_exist(filnam); // Got this one?
2798+ }
2799+ }
2800+
2801+ // Last place to look is the default location.
2802+ if (!bGotIt) // Need to do more searches?
2803+ {
2804+ strcpy(filnam, DEFCMDPATH); // Use default path
2805+ strcat(filnam, szCmd);
2806+ bGotIt = file_exist(filnam); // Got this one?
2807+ }
2808+
2809+ iFHandle = file_open(filnam);
2810+ if (iFHandle == -1)
2811+ sErr = U14ERR_NOFILE;
2812+ else
2813+ { // first read in the header block
2814+ CMDHEAD rCmdHead; // to hold the command header
2815+ if (file_read(iFHandle, &rCmdHead, sizeof(CMDHEAD)))
2816+ {
2817+ size_t nComSize = rCmdHead.wCmdSize;
2818+ char* pMem = malloc(nComSize);
2819+ if (pMem != NULL)
2820+ {
2821+ file_seek(iFHandle, sizeof(CMDHEAD));
2822+ if (file_read(iFHandle, pMem, (UINT)nComSize))
2823+ {
2824+ sErr = U14SetTransArea(hand, 0, (void *)pMem, (DWORD)nComSize, ESZBYTES);
2825+ if (sErr == U14ERR_NOERROR)
2826+ {
2827+ sprintf(strcopy, "CLOAD,0,$%X;", (int)nComSize);
2828+ sErr = U14SendString(hand, strcopy);
2829+ if (sErr == U14ERR_NOERROR)
2830+ {
2831+ sErr = U14CheckErr(hand); // Use ERR to check for done
2832+ if (sErr > 0)
2833+ sErr = U14ERR_CLOADERR; // If an error, this code
2834+ }
2835+ U14UnSetTransfer(hand, 0); // release transfer area
2836+ }
2837+ }
2838+ else
2839+ sErr = U14ERR_READERR;
2840+ free(pMem);
2841+ }
2842+ else
2843+ sErr = U14ERR_HOSTSPACE; // memory allocate failed
2844+ }
2845+ else
2846+ sErr = U14ERR_READERR;
2847+
2848+ file_close(iFHandle); // close the file
2849+ }
2850+
2851+ return sErr;
2852+}
2853+
2854+
2855+/****************************************************************************
2856+** Ld
2857+** Loads a command into the 1401
2858+** Returns NOERROR code or a long with error in lo word and index of
2859+** command that failed in high word
2860+****************************************************************************/
2861+U14API(DWORD) U14Ld(short hand, const char* vl, const char* str)
2862+{
2863+ DWORD dwIndex = 0; // index to current command
2864+ long lErr = U14ERR_NOERROR; // what the error was that went wrong
2865+ char strcopy[MAXSTRLEN+1]; // stores unmodified str parameter
2866+ char szFExt[8]; // The command file extension
2867+ short sErr = CheckHandle(hand);
2868+ if (sErr != U14ERR_NOERROR)
2869+ return sErr;
2870+
2871+ ExtForType(asType1401[hand], szFExt); // File extension string
2872+ strcpy(strcopy, str); // to avoid changing original
2873+
2874+ // now break out one command at a time and see if loaded
2875+ if (*str) // if anything there
2876+ {
2877+ BOOL bDone = FALSE; // true when finished all commands
2878+ int iLoop1 = 0; // Point at start of string for command name
2879+ int iLoop2 = 0; // and at start of str parameter
2880+ do // repeat until end of str
2881+ {
2882+ char filnam[MAXSTRLEN+1]; // filename to use
2883+ char szFName[MAXSTRLEN+1]; // filename work string
2884+
2885+ if (!strcopy[iLoop1]) // at the end of the string?
2886+ bDone = TRUE; // set the finish flag
2887+
2888+ if (bDone || (strcopy[iLoop1] == ',')) // end of cmd?
2889+ {
2890+ U14LONG er[5]; // Used to read back error results
2891+ ++dwIndex; // Keep count of command number, first is 1
2892+ szFName[iLoop2]=(char)0; // null terminate name of command
2893+
2894+ strncpy(szLastName, szFName, sizeof(szLastName)); // Save for error info
2895+ szLastName[sizeof(szLastName)-1] = 0;
2896+ strncat(szLastName, szFExt, sizeof(szLastName)); // with extension included
2897+ szLastName[sizeof(szLastName)-1] = 0;
2898+
2899+ U14SendString(hand, szFName); // ask if loaded
2900+ U14SendString(hand, ";ERR;"); // add err return
2901+
2902+ lErr = U14LongsFrom1401(hand, er, 5);
2903+ if (lErr > 0)
2904+ {
2905+ lErr = U14ERR_NOERROR;
2906+ if (er[0] == 255) // if command not loaded at all
2907+ {
2908+ if (vl && *vl) // if we have a path name
2909+ {
2910+ strcpy(filnam, vl);
2911+ if (strchr("\\/:", filnam[strlen(filnam)-1]) == NULL)
2912+ strcat(filnam, PATHSEPSTR); // add separator if none found
2913+ strcat(filnam, szFName); // add the file name
2914+ strcat(filnam, szFExt); // and extension
2915+ }
2916+ else
2917+ strcpy(filnam, szFName); // simple name
2918+
2919+ lErr = U14LdCmd(hand, filnam); // load cmd
2920+ if (lErr != U14ERR_NOERROR) // spot any errors
2921+ bDone = TRUE; // give up if an error
2922+ }
2923+ }
2924+ else
2925+ bDone = TRUE; // give up if an error
2926+
2927+ iLoop2 = 0; // Reset pointer to command name string
2928+ ++iLoop1; // and move on through str parameter
2929+ }
2930+ else
2931+ szFName[iLoop2++] = strcopy[iLoop1++]; // no command end, so copy 1 char
2932+ }
2933+ while (!bDone);
2934+ }
2935+
2936+ if (lErr == U14ERR_NOERROR)
2937+ {
2938+ szLastName[0] = 0; // No error, so clean out command name here
2939+ return lErr;
2940+ }
2941+ else
2942+ return ((dwIndex<<16) | ((DWORD)lErr & 0x0000FFFF));
2943+}
2944+
2945+// Initialise the library (if not initialised) and return the library version
2946+U14API(int) U14InitLib(void)
2947+{
2948+ int iRetVal = U14LIB_VERSION;
2949+ if (iAttached == 0) // only do this the first time please
2950+ {
2951+ int i;
2952+#ifdef _IS_WINDOWS_
2953+ int j;
2954+ DWORD dwVersion = GetVersion();
2955+ bWindows9x = FALSE; // Assume not Win9x
2956+
2957+ if (dwVersion & 0x80000000) // if not windows NT
2958+ {
2959+ if ((LOBYTE(LOWORD(dwVersion)) < 4) && // if Win32s or...
2960+ (HIBYTE(LOWORD(dwVersion)) < 95)) // ...below Windows 95
2961+ iRetVal = 0; // We do not support this
2962+ else
2963+ bWindows9x = TRUE; // Flag we have Win9x
2964+ }
2965+#endif
2966+
2967+ for (i = 0; i < MAX1401; i++) // initialise the device area
2968+ {
2969+ aHand1401[i] = INVALID_HANDLE_VALUE; // Clear handle values
2970+ asType1401[i] = U14TYPEUNKNOWN; // and 1401 type codes
2971+ alTimeOutPeriod[i] = 3000; // 3 second timeouts
2972+#ifdef _IS_WINDOWS_
2973+#ifndef _WIN64
2974+ abUseNTDIOC[i] = (BOOL)!bWindows9x;
2975+#endif
2976+ aXferEvent[i] = NULL; // there are no Xfer events
2977+ for (j = 0; j < MAX_TRANSAREAS; j++) // Clear out locked area info
2978+ {
2979+ apAreas[i][j] = NULL;
2980+ auAreas[i][j] = 0;
2981+ }
2982+#endif
2983+ }
2984+ }
2985+ return iRetVal;
2986+}
2987+
2988+///--------------------------------------------------------------------------------
2989+/// Functions called when the library is loaded and unloaded to give us a chance to
2990+/// setup the library.
2991+
2992+
2993+#ifdef _IS_WINDOWS_
2994+#ifndef U14_NOT_DLL
2995+/****************************************************************************
2996+** FUNCTION: DllMain(HANDLE, DWORD, LPVOID)
2997+** LibMain is called by Windows when the DLL is initialized, Thread Attached,
2998+** and other times. Refer to SDK documentation, as to the different ways this
2999+** may be called.
3000+****************************************************************************/
3001+INT APIENTRY DllMain(HANDLE hInst, DWORD ul_reason_being_called, LPVOID lpReserved)
3002+{
3003+ int iRetVal = 1;
3004+
3005+ switch (ul_reason_being_called)
3006+ {
3007+ case DLL_PROCESS_ATTACH:
3008+ iRetVal = U14InitLib() > 0; // does nothing if iAttached != 0
3009+ ++iAttached; // count times attached
3010+ break;
3011+
3012+ case DLL_PROCESS_DETACH:
3013+ if (--iAttached == 0) // last man out?
3014+ U14CloseAll(); // release all open handles
3015+ break;
3016+ }
3017+ return iRetVal;
3018+
3019+ UNREFERENCED_PARAMETER(lpReserved);
3020+}
3021+#endif
3022+#endif
3023+#ifdef LINUX
3024+void __attribute__((constructor)) use1401_load(void)
3025+{
3026+ U14InitLib();
3027+ ++iAttached;
3028+}
3029+
3030+void __attribute__((destructor)) use1401_unload(void)
3031+{
3032+ if (--iAttached == 0) // last man out?
3033+ U14CloseAll(); // release all open handles
3034+}
3035+#endif
drivers/staging/comedi/Kconfig+28−38
@@ -549,6 +549,23 @@ menuconfig COMEDI_PCI_DRIVERS · 548 unmodified lines
549549
550550 if COMEDI_PCI_DRIVERS
551551
552+config COMEDI_8255_PCI
553+ tristate "Generic PCI based 8255 digital i/o board support"
554+ select COMEDI_8255
555+ ---help---
556+ Enable support for PCI based 8255 digital i/o boards. This driver
557+ provides a PCI wrapper around the generic 8255 driver.
558+
559+ Supported boards:
560+ ADlink - PCI-7224, PCI-7248, and PCI-7296
561+ Measurement Computing - PCI-DIO24, PCI-DIO24H, PCI-DIO48H and
562+ PCI-DIO96H
563+ National Instruments - PCI-DIO-96, PCI-DIO-96B, PXI-6508, PCI-6503,
564+ PCI-6503B, PCI-6503X, and PXI-6503
565+
566+ To compile this driver as a module, choose M here: the module will
567+ be called 8255_pci.
568+
552569 config COMEDI_ADDI_APCI_035
553570 tristate "ADDI-DATA APCI_035 support"
554571 depends on VIRT_TO_BUS
@@ -676,30 +693,16 @@ config COMEDI_ADL_PCI6208 · 121 unmodified lines
676693 To compile this driver as a module, choose M here: the module will be
677694 called adl_pci6208.
678695
679−config COMEDI_ADL_PCI7230
680− tristate "ADLink PCI-7230 digital io board support"
681− ---help---
682− Enable support for ADlink PCI-7230 digital io board support
683−
684− To compile this driver as a module, choose M here: the module will be
685− called adl_pci7230.
686−
687−config COMEDI_ADL_PCI7296
688− tristate "ADLink PCI-7296 96 ch. digital io board support"
689− select COMEDI_8255
696+config COMEDI_ADL_PCI7X3X
697+ tristate "ADLink PCI-723X/743X isolated digital i/o board support"
690698 ---help---
691− Enable support for ADlink PCI-7296 96 ch. digital io board support
699+ Enable support for ADlink PCI-723X/743X isolated digital i/o boards.
700+ Supported boards include the 32-channel PCI-7230 (16 in/16 out),
701+ PCI-7233 (32 in), and PCI-7234 (32 out) as well as the 64-channel
702+ PCI-7432 (32 in/32 out), PCI-7433 (64 in), and PCI-7434 (64 out).
692703
693704 To compile this driver as a module, choose M here: the module will be
694− called adl_pci7296.
695−
696−config COMEDI_ADL_PCI7432
697− tristate "ADLink PCI-7432 64 ch. isolated digital io board support"
698− ---help---
699− Enable support for ADlink PCI-7432 64 ch. isolated digital io board
700−
701− To compile this driver as a module, choose M here: the module will be
702− called adl_pci7432.
705+ called adl_pci7x3x.
703706
704707 config COMEDI_ADL_PCI8164
705708 tristate "ADLink PCI-8164 4 Axes Motion Control board support"
@@ -935,16 +938,6 @@ config COMEDI_CB_PCIDDA · 229 unmodified lines
935938 To compile this driver as a module, choose M here: the module will be
936939 called cb_pcidda.
937940
938−config COMEDI_CB_PCIDIO
939− tristate "MeasurementComputing PCI-DIO series support"
940− select COMEDI_8255
941− ---help---
942− Enable support for ComputerBoards/MeasurementComputing PCI-DIO series
943− PCI-DIO24, PCI-DIO24H and PCI-DIO48H
944−
945− To compile this driver as a module, choose M here: the module will be
946− called cb_pcidio.
947−
948941 config COMEDI_CB_PCIMDAS
949942 tristate "MeasurementComputing PCIM-DAS1602/16 support"
950943 select COMEDI_8255
@@ -1039,15 +1032,12 @@ config COMEDI_NI_LABPC · 88 unmodified lines
10391032 called ni_labpc.
10401033
10411034 config COMEDI_NI_PCIDIO
1042− tristate "NI PCI-DIO32HS, PCI-DIO96, PCI-6533, PCI-6503 support"
1035+ tristate "NI PCI-DIO32HS, PCI-6533, PCI-6534 support"
10431036 select COMEDI_MITE
10441037 select COMEDI_8255
10451038 ---help---
10461039 Enable support for National Instruments PCI-DIO-32HS, PXI-6533,
1047− PCI-DIO-96, PCI-DIO-96B, PXI-6508, PCI-6503, PCI-6503B, PCI-6503X,
1048− PXI-6503, PCI-6533 and PCI-6534
1049− The DIO-96 appears as four 8255 subdevices. See the 8255
1050− driver notes for details.
1040+ PCI-6533 and PCI-6534
10511041
10521042 To compile this driver as a module, choose M here: the module will be
10531043 called ni_pcidio.
@@ -1262,8 +1252,8 @@ config COMEDI_8255 · 208 unmodified lines
12621252 that has an 8255 chip. For multifunction boards, the main driver will
12631253 configure the 8255 subdevice automatically.
12641254
1265− Note that most PCI 8255 boards do NOT work with this driver, and
1266− need a separate driver as a wrapper.
1255+ Note that most PCI based 8255 boards use the 8255_pci driver as a
1256+ wrapper around this driver.
12671257
12681258 To compile this driver as a module, choose M here: the module will be
12691259 called 8255.
drivers/staging/comedi/comedi.h+554−555
@@ -208,92 +208,92 @@ · 207 unmodified lines
208208
209209 /* subdevice types */
210210
211− enum comedi_subdevice_type {
212− COMEDI_SUBD_UNUSED, /* unused by driver */
213− COMEDI_SUBD_AI, /* analog input */
214− COMEDI_SUBD_AO, /* analog output */
215− COMEDI_SUBD_DI, /* digital input */
216− COMEDI_SUBD_DO, /* digital output */
217− COMEDI_SUBD_DIO, /* digital input/output */
218− COMEDI_SUBD_COUNTER, /* counter */
219− COMEDI_SUBD_TIMER, /* timer */
220− COMEDI_SUBD_MEMORY, /* memory, EEPROM, DPRAM */
221− COMEDI_SUBD_CALIB, /* calibration DACs */
222− COMEDI_SUBD_PROC, /* processor, DSP */
223− COMEDI_SUBD_SERIAL, /* serial IO */
224− COMEDI_SUBD_PWM /* PWM */
225− };
211+enum comedi_subdevice_type {
212+ COMEDI_SUBD_UNUSED, /* unused by driver */
213+ COMEDI_SUBD_AI, /* analog input */
214+ COMEDI_SUBD_AO, /* analog output */
215+ COMEDI_SUBD_DI, /* digital input */
216+ COMEDI_SUBD_DO, /* digital output */
217+ COMEDI_SUBD_DIO, /* digital input/output */
218+ COMEDI_SUBD_COUNTER, /* counter */
219+ COMEDI_SUBD_TIMER, /* timer */
220+ COMEDI_SUBD_MEMORY, /* memory, EEPROM, DPRAM */
221+ COMEDI_SUBD_CALIB, /* calibration DACs */
222+ COMEDI_SUBD_PROC, /* processor, DSP */
223+ COMEDI_SUBD_SERIAL, /* serial IO */
224+ COMEDI_SUBD_PWM /* PWM */
225+};
226226
227227 /* configuration instructions */
228228
229− enum configuration_ids {
230− INSN_CONFIG_DIO_INPUT = 0,
231− INSN_CONFIG_DIO_OUTPUT = 1,
232− INSN_CONFIG_DIO_OPENDRAIN = 2,
233− INSN_CONFIG_ANALOG_TRIG = 16,
229+enum configuration_ids {
230+ INSN_CONFIG_DIO_INPUT = 0,
231+ INSN_CONFIG_DIO_OUTPUT = 1,
232+ INSN_CONFIG_DIO_OPENDRAIN = 2,
233+ INSN_CONFIG_ANALOG_TRIG = 16,
234234 /* INSN_CONFIG_WAVEFORM = 17, */
235235 /* INSN_CONFIG_TRIG = 18, */
236236 /* INSN_CONFIG_COUNTER = 19, */
237− INSN_CONFIG_ALT_SOURCE = 20,
238− INSN_CONFIG_DIGITAL_TRIG = 21,
239− INSN_CONFIG_BLOCK_SIZE = 22,
240− INSN_CONFIG_TIMER_1 = 23,
241− INSN_CONFIG_FILTER = 24,
242− INSN_CONFIG_CHANGE_NOTIFY = 25,
243−
244− /*ALPHA*/ INSN_CONFIG_SERIAL_CLOCK = 26,
245− INSN_CONFIG_BIDIRECTIONAL_DATA = 27,
246− INSN_CONFIG_DIO_QUERY = 28,
247− INSN_CONFIG_PWM_OUTPUT = 29,
248− INSN_CONFIG_GET_PWM_OUTPUT = 30,
249− INSN_CONFIG_ARM = 31,
250− INSN_CONFIG_DISARM = 32,
251− INSN_CONFIG_GET_COUNTER_STATUS = 33,
252− INSN_CONFIG_RESET = 34,
253− /* Use CTR as single pulsegenerator */
254− INSN_CONFIG_GPCT_SINGLE_PULSE_GENERATOR = 1001,
255− /* Use CTR as pulsetraingenerator */
256− INSN_CONFIG_GPCT_PULSE_TRAIN_GENERATOR = 1002,
257− /* Use the counter as encoder */
258− INSN_CONFIG_GPCT_QUADRATURE_ENCODER = 1003,
259− INSN_CONFIG_SET_GATE_SRC = 2001, /* Set gate source */
260− INSN_CONFIG_GET_GATE_SRC = 2002, /* Get gate source */
261− /* Set master clock source */
262− INSN_CONFIG_SET_CLOCK_SRC = 2003,
263− INSN_CONFIG_GET_CLOCK_SRC = 2004, /* Get master clock source */
264− INSN_CONFIG_SET_OTHER_SRC = 2005, /* Set other source */
265− /* INSN_CONFIG_GET_OTHER_SRC = 2006,*//* Get other source */
266− /* Get size in bytes of subdevice's on-board fifos used during
267− * streaming input/output */
268− INSN_CONFIG_GET_HARDWARE_BUFFER_SIZE = 2006,
269− INSN_CONFIG_SET_COUNTER_MODE = 4097,
270− /* INSN_CONFIG_8254_SET_MODE is deprecated */
271− INSN_CONFIG_8254_SET_MODE = INSN_CONFIG_SET_COUNTER_MODE,
272− INSN_CONFIG_8254_READ_STATUS = 4098,
273− INSN_CONFIG_SET_ROUTING = 4099,
274− INSN_CONFIG_GET_ROUTING = 4109,
275−/* PWM */
276− INSN_CONFIG_PWM_SET_PERIOD = 5000, /* sets frequency */
277− INSN_CONFIG_PWM_GET_PERIOD = 5001, /* gets frequency */
278− INSN_CONFIG_GET_PWM_STATUS = 5002, /* is it running? */
279− /* sets H bridge: duty cycle and sign bit for a relay at the
280− * same time */
281− INSN_CONFIG_PWM_SET_H_BRIDGE = 5003,
282− /* gets H bridge data: duty cycle and the sign bit */
283− INSN_CONFIG_PWM_GET_H_BRIDGE = 5004
284− };
285−
286− enum comedi_io_direction {
287− COMEDI_INPUT = 0,
288− COMEDI_OUTPUT = 1,
289− COMEDI_OPENDRAIN = 2
290− };
291−
292− enum comedi_support_level {
293− COMEDI_UNKNOWN_SUPPORT = 0,
294− COMEDI_SUPPORTED,
295− COMEDI_UNSUPPORTED
296− };
237+ INSN_CONFIG_ALT_SOURCE = 20,
238+ INSN_CONFIG_DIGITAL_TRIG = 21,
239+ INSN_CONFIG_BLOCK_SIZE = 22,
240+ INSN_CONFIG_TIMER_1 = 23,
241+ INSN_CONFIG_FILTER = 24,
242+ INSN_CONFIG_CHANGE_NOTIFY = 25,
243+
244+ INSN_CONFIG_SERIAL_CLOCK = 26, /*ALPHA*/
245+ INSN_CONFIG_BIDIRECTIONAL_DATA = 27,
246+ INSN_CONFIG_DIO_QUERY = 28,
247+ INSN_CONFIG_PWM_OUTPUT = 29,
248+ INSN_CONFIG_GET_PWM_OUTPUT = 30,
249+ INSN_CONFIG_ARM = 31,
250+ INSN_CONFIG_DISARM = 32,
251+ INSN_CONFIG_GET_COUNTER_STATUS = 33,
252+ INSN_CONFIG_RESET = 34,
253+ /* Use CTR as single pulsegenerator */
254+ INSN_CONFIG_GPCT_SINGLE_PULSE_GENERATOR = 1001,
255+ /* Use CTR as pulsetraingenerator */
256+ INSN_CONFIG_GPCT_PULSE_TRAIN_GENERATOR = 1002,
257+ /* Use the counter as encoder */
258+ INSN_CONFIG_GPCT_QUADRATURE_ENCODER = 1003,
259+ INSN_CONFIG_SET_GATE_SRC = 2001, /* Set gate source */
260+ INSN_CONFIG_GET_GATE_SRC = 2002, /* Get gate source */
261+ /* Set master clock source */
262+ INSN_CONFIG_SET_CLOCK_SRC = 2003,
263+ INSN_CONFIG_GET_CLOCK_SRC = 2004, /* Get master clock source */
264+ INSN_CONFIG_SET_OTHER_SRC = 2005, /* Set other source */
265+ /* INSN_CONFIG_GET_OTHER_SRC = 2006,*//* Get other source */
266+ /* Get size in bytes of subdevice's on-board fifos used during
267+ * streaming input/output */
268+ INSN_CONFIG_GET_HARDWARE_BUFFER_SIZE = 2006,
269+ INSN_CONFIG_SET_COUNTER_MODE = 4097,
270+ /* INSN_CONFIG_8254_SET_MODE is deprecated */
271+ INSN_CONFIG_8254_SET_MODE = INSN_CONFIG_SET_COUNTER_MODE,
272+ INSN_CONFIG_8254_READ_STATUS = 4098,
273+ INSN_CONFIG_SET_ROUTING = 4099,
274+ INSN_CONFIG_GET_ROUTING = 4109,
275+ /* PWM */
276+ INSN_CONFIG_PWM_SET_PERIOD = 5000, /* sets frequency */
277+ INSN_CONFIG_PWM_GET_PERIOD = 5001, /* gets frequency */
278+ INSN_CONFIG_GET_PWM_STATUS = 5002, /* is it running? */
279+ /* sets H bridge: duty cycle and sign bit for a relay at the
280+ * same time */
281+ INSN_CONFIG_PWM_SET_H_BRIDGE = 5003,
282+ /* gets H bridge data: duty cycle and the sign bit */
283+ INSN_CONFIG_PWM_GET_H_BRIDGE = 5004
284+};
285+
286+enum comedi_io_direction {
287+ COMEDI_INPUT = 0,
288+ COMEDI_OUTPUT = 1,
289+ COMEDI_OPENDRAIN = 2
290+};
291+
292+enum comedi_support_level {
293+ COMEDI_UNKNOWN_SUPPORT = 0,
294+ COMEDI_SUPPORTED,
295+ COMEDI_UNSUPPORTED
296+};
297297
298298 /* ioctls */
299299
@@ -317,133 +317,133 @@ · 17 unmodified lines
317317
318318 /* structures */
319319
320− struct comedi_trig {
321− unsigned int subdev; /* subdevice */
322− unsigned int mode; /* mode */
323− unsigned int flags;
324− unsigned int n_chan; /* number of channels */
325− unsigned int *chanlist; /* channel/range list */
326− short *data; /* data list, size depends on subd flags */
327− unsigned int n; /* number of scans */
328− unsigned int trigsrc;
329− unsigned int trigvar;
330− unsigned int trigvar1;
331− unsigned int data_len;
332− unsigned int unused[3];
333− };
334−
335− struct comedi_insn {
336− unsigned int insn;
337− unsigned int n;
338− unsigned int __user *data;
339− unsigned int subdev;
340− unsigned int chanspec;
341− unsigned int unused[3];
342− };
343−
344− struct comedi_insnlist {
345− unsigned int n_insns;
346− struct comedi_insn __user *insns;
347− };
348−
349− struct comedi_cmd {
350− unsigned int subdev;
351− unsigned int flags;
352−
353− unsigned int start_src;
354− unsigned int start_arg;
355−
356− unsigned int scan_begin_src;
357− unsigned int scan_begin_arg;
358−
359− unsigned int convert_src;
360− unsigned int convert_arg;
361−
362− unsigned int scan_end_src;
363− unsigned int scan_end_arg;
364−
365− unsigned int stop_src;
366− unsigned int stop_arg;
367−
368− unsigned int __user *chanlist; /* channel/range list */
369− unsigned int chanlist_len;
370−
371− short __user *data; /* data list, size depends on subd flags */
372− unsigned int data_len;
373− };
374−
375− struct comedi_chaninfo {
376− unsigned int subdev;
377− unsigned int __user *maxdata_list;
378− unsigned int __user *flaglist;
379− unsigned int __user *rangelist;
380− unsigned int unused[4];
381− };
382−
383− struct comedi_rangeinfo {
384− unsigned int range_type;
385− void __user *range_ptr;
386− };
387−
388− struct comedi_krange {
389− int min; /* fixed point, multiply by 1e-6 */
390− int max; /* fixed point, multiply by 1e-6 */
391− unsigned int flags;
392− };
393−
394− struct comedi_subdinfo {
395− unsigned int type;
396− unsigned int n_chan;
397− unsigned int subd_flags;
398− unsigned int timer_type;
399− unsigned int len_chanlist;
400− unsigned int maxdata;
401− unsigned int flags; /* channel flags */
402− unsigned int range_type; /* lookup in kernel */
403− unsigned int settling_time_0;
404− /* see support_level enum for values */
405− unsigned insn_bits_support;
406− unsigned int unused[8];
407− };
408−
409− struct comedi_devinfo {
410− unsigned int version_code;
411− unsigned int n_subdevs;
412− char driver_name[COMEDI_NAMELEN];
413− char board_name[COMEDI_NAMELEN];
414− int read_subdevice;
415− int write_subdevice;
416− int unused[30];
417− };
418−
419− struct comedi_devconfig {
420− char board_name[COMEDI_NAMELEN];
421− int options[COMEDI_NDEVCONFOPTS];
422− };
423−
424− struct comedi_bufconfig {
425− unsigned int subdevice;
426− unsigned int flags;
427−
428− unsigned int maximum_size;
429− unsigned int size;
430−
431− unsigned int unused[4];
432− };
433−
434− struct comedi_bufinfo {
435− unsigned int subdevice;
436− unsigned int bytes_read;
437−
438− unsigned int buf_write_ptr;
439− unsigned int buf_read_ptr;
440− unsigned int buf_write_count;
441− unsigned int buf_read_count;
442−
443− unsigned int bytes_written;
444−
445− unsigned int unused[4];
446− };
320+struct comedi_trig {
321+ unsigned int subdev; /* subdevice */
322+ unsigned int mode; /* mode */
323+ unsigned int flags;
324+ unsigned int n_chan; /* number of channels */
325+ unsigned int *chanlist; /* channel/range list */
326+ short *data; /* data list, size depends on subd flags */
327+ unsigned int n; /* number of scans */
328+ unsigned int trigsrc;
329+ unsigned int trigvar;
330+ unsigned int trigvar1;
331+ unsigned int data_len;
332+ unsigned int unused[3];
333+};
334+
335+struct comedi_insn {
336+ unsigned int insn;
337+ unsigned int n;
338+ unsigned int __user *data;
339+ unsigned int subdev;
340+ unsigned int chanspec;
341+ unsigned int unused[3];
342+};
343+
344+struct comedi_insnlist {
345+ unsigned int n_insns;
346+ struct comedi_insn __user *insns;
347+};
348+
349+struct comedi_cmd {
350+ unsigned int subdev;
351+ unsigned int flags;
352+
353+ unsigned int start_src;
354+ unsigned int start_arg;
355+
356+ unsigned int scan_begin_src;
357+ unsigned int scan_begin_arg;
358+
359+ unsigned int convert_src;
360+ unsigned int convert_arg;
361+
362+ unsigned int scan_end_src;
363+ unsigned int scan_end_arg;
364+
365+ unsigned int stop_src;
366+ unsigned int stop_arg;
367+
368+ unsigned int *chanlist; /* channel/range list */
369+ unsigned int chanlist_len;
370+
371+ short __user *data; /* data list, size depends on subd flags */
372+ unsigned int data_len;
373+};
374+
375+struct comedi_chaninfo {
376+ unsigned int subdev;
377+ unsigned int __user *maxdata_list;
378+ unsigned int __user *flaglist;
379+ unsigned int __user *rangelist;
380+ unsigned int unused[4];
381+};
382+
383+struct comedi_rangeinfo {
384+ unsigned int range_type;
385+ void __user *range_ptr;
386+};
387+
388+struct comedi_krange {
389+ int min; /* fixed point, multiply by 1e-6 */
390+ int max; /* fixed point, multiply by 1e-6 */
391+ unsigned int flags;
392+};
393+
394+struct comedi_subdinfo {
395+ unsigned int type;
396+ unsigned int n_chan;
397+ unsigned int subd_flags;
398+ unsigned int timer_type;
399+ unsigned int len_chanlist;
400+ unsigned int maxdata;
401+ unsigned int flags; /* channel flags */
402+ unsigned int range_type; /* lookup in kernel */
403+ unsigned int settling_time_0;
404+ /* see support_level enum for values */
405+ unsigned insn_bits_support;
406+ unsigned int unused[8];
407+};
408+
409+struct comedi_devinfo {
410+ unsigned int version_code;
411+ unsigned int n_subdevs;
412+ char driver_name[COMEDI_NAMELEN];
413+ char board_name[COMEDI_NAMELEN];
414+ int read_subdevice;
415+ int write_subdevice;
416+ int unused[30];
417+};
418+
419+struct comedi_devconfig {
420+ char board_name[COMEDI_NAMELEN];
421+ int options[COMEDI_NDEVCONFOPTS];
422+};
423+
424+struct comedi_bufconfig {
425+ unsigned int subdevice;
426+ unsigned int flags;
427+
428+ unsigned int maximum_size;
429+ unsigned int size;
430+
431+ unsigned int unused[4];
432+};
433+
434+struct comedi_bufinfo {
435+ unsigned int subdevice;
436+ unsigned int bytes_read;
437+
438+ unsigned int buf_write_ptr;
439+ unsigned int buf_read_ptr;
440+ unsigned int buf_write_count;
441+ unsigned int buf_read_count;
442+
443+ unsigned int bytes_written;
444+
445+ unsigned int unused[4];
446+};
447447
448448 /* range stuff */
449449
@@ -495,306 +495,306 @@ · 45 unmodified lines
495495
496496 */
497497
498− enum i8254_mode {
499− I8254_MODE0 = (0 << 1), /* Interrupt on terminal count */
500− I8254_MODE1 = (1 << 1), /* Hardware retriggerable one-shot */
501− I8254_MODE2 = (2 << 1), /* Rate generator */
502− I8254_MODE3 = (3 << 1), /* Square wave mode */
503− I8254_MODE4 = (4 << 1), /* Software triggered strobe */
504− I8254_MODE5 = (5 << 1), /* Hardware triggered strobe
505− * (retriggerable) */
506− I8254_BCD = 1, /* use binary-coded decimal instead of binary
498+enum i8254_mode {
499+ I8254_MODE0 = (0 << 1), /* Interrupt on terminal count */
500+ I8254_MODE1 = (1 << 1), /* Hardware retriggerable one-shot */
501+ I8254_MODE2 = (2 << 1), /* Rate generator */
502+ I8254_MODE3 = (3 << 1), /* Square wave mode */
503+ I8254_MODE4 = (4 << 1), /* Software triggered strobe */
504+ I8254_MODE5 = (5 << 1), /* Hardware triggered strobe
505+ * (retriggerable) */
506+ I8254_BCD = 1, /* use binary-coded decimal instead of binary
507507 * (pretty useless) */
508− I8254_BINARY = 0
509− };
510−
511− static inline unsigned NI_USUAL_PFI_SELECT(unsigned pfi_channel)
512− {
513− if (pfi_channel < 10)
514− return 0x1 + pfi_channel;
515− else
516− return 0xb + pfi_channel;
517− }
518−
519− static inline unsigned NI_USUAL_RTSI_SELECT(unsigned rtsi_channel)
520− {
521− if (rtsi_channel < 7)
522− return 0xb + rtsi_channel;
523− else
524− return 0x1b;
525− }
508+ I8254_BINARY = 0
509+};
510+
511+static inline unsigned NI_USUAL_PFI_SELECT(unsigned pfi_channel)
512+{
513+ if (pfi_channel < 10)
514+ return 0x1 + pfi_channel;
515+ else
516+ return 0xb + pfi_channel;
517+}
518+
519+static inline unsigned NI_USUAL_RTSI_SELECT(unsigned rtsi_channel)
520+{
521+ if (rtsi_channel < 7)
522+ return 0xb + rtsi_channel;
523+ else
524+ return 0x1b;
525+}
526526
527527 /* mode bits for NI general-purpose counters, set with
528528 * INSN_CONFIG_SET_COUNTER_MODE */
529529 #define NI_GPCT_COUNTING_MODE_SHIFT 16
530530 #define NI_GPCT_INDEX_PHASE_BITSHIFT 20
531531 #define NI_GPCT_COUNTING_DIRECTION_SHIFT 24
532− enum ni_gpct_mode_bits {
533− NI_GPCT_GATE_ON_BOTH_EDGES_BIT = 0x4,
534− NI_GPCT_EDGE_GATE_MODE_MASK = 0x18,
535− NI_GPCT_EDGE_GATE_STARTS_STOPS_BITS = 0x0,
536− NI_GPCT_EDGE_GATE_STOPS_STARTS_BITS = 0x8,
537− NI_GPCT_EDGE_GATE_STARTS_BITS = 0x10,
538− NI_GPCT_EDGE_GATE_NO_STARTS_NO_STOPS_BITS = 0x18,
539− NI_GPCT_STOP_MODE_MASK = 0x60,
540− NI_GPCT_STOP_ON_GATE_BITS = 0x00,
541− NI_GPCT_STOP_ON_GATE_OR_TC_BITS = 0x20,
542− NI_GPCT_STOP_ON_GATE_OR_SECOND_TC_BITS = 0x40,
543− NI_GPCT_LOAD_B_SELECT_BIT = 0x80,
544− NI_GPCT_OUTPUT_MODE_MASK = 0x300,
545− NI_GPCT_OUTPUT_TC_PULSE_BITS = 0x100,
546− NI_GPCT_OUTPUT_TC_TOGGLE_BITS = 0x200,
547− NI_GPCT_OUTPUT_TC_OR_GATE_TOGGLE_BITS = 0x300,
548− NI_GPCT_HARDWARE_DISARM_MASK = 0xc00,
549− NI_GPCT_NO_HARDWARE_DISARM_BITS = 0x000,
550− NI_GPCT_DISARM_AT_TC_BITS = 0x400,
551− NI_GPCT_DISARM_AT_GATE_BITS = 0x800,
552− NI_GPCT_DISARM_AT_TC_OR_GATE_BITS = 0xc00,
553− NI_GPCT_LOADING_ON_TC_BIT = 0x1000,
554− NI_GPCT_LOADING_ON_GATE_BIT = 0x4000,
555− NI_GPCT_COUNTING_MODE_MASK = 0x7 << NI_GPCT_COUNTING_MODE_SHIFT,
556− NI_GPCT_COUNTING_MODE_NORMAL_BITS =
557− 0x0 << NI_GPCT_COUNTING_MODE_SHIFT,
558− NI_GPCT_COUNTING_MODE_QUADRATURE_X1_BITS =
559− 0x1 << NI_GPCT_COUNTING_MODE_SHIFT,
560− NI_GPCT_COUNTING_MODE_QUADRATURE_X2_BITS =
561− 0x2 << NI_GPCT_COUNTING_MODE_SHIFT,
562− NI_GPCT_COUNTING_MODE_QUADRATURE_X4_BITS =
563− 0x3 << NI_GPCT_COUNTING_MODE_SHIFT,
564− NI_GPCT_COUNTING_MODE_TWO_PULSE_BITS =
565− 0x4 << NI_GPCT_COUNTING_MODE_SHIFT,
566− NI_GPCT_COUNTING_MODE_SYNC_SOURCE_BITS =
567− 0x6 << NI_GPCT_COUNTING_MODE_SHIFT,
568− NI_GPCT_INDEX_PHASE_MASK = 0x3 << NI_GPCT_INDEX_PHASE_BITSHIFT,
569− NI_GPCT_INDEX_PHASE_LOW_A_LOW_B_BITS =
570− 0x0 << NI_GPCT_INDEX_PHASE_BITSHIFT,
571− NI_GPCT_INDEX_PHASE_LOW_A_HIGH_B_BITS =
572− 0x1 << NI_GPCT_INDEX_PHASE_BITSHIFT,
573− NI_GPCT_INDEX_PHASE_HIGH_A_LOW_B_BITS =
574− 0x2 << NI_GPCT_INDEX_PHASE_BITSHIFT,
575− NI_GPCT_INDEX_PHASE_HIGH_A_HIGH_B_BITS =
576− 0x3 << NI_GPCT_INDEX_PHASE_BITSHIFT,
577− NI_GPCT_INDEX_ENABLE_BIT = 0x400000,
578− NI_GPCT_COUNTING_DIRECTION_MASK =
579− 0x3 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
580− NI_GPCT_COUNTING_DIRECTION_DOWN_BITS =
581− 0x00 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
582− NI_GPCT_COUNTING_DIRECTION_UP_BITS =
583− 0x1 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
584− NI_GPCT_COUNTING_DIRECTION_HW_UP_DOWN_BITS =
585− 0x2 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
586− NI_GPCT_COUNTING_DIRECTION_HW_GATE_BITS =
587− 0x3 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
588− NI_GPCT_RELOAD_SOURCE_MASK = 0xc000000,
589− NI_GPCT_RELOAD_SOURCE_FIXED_BITS = 0x0,
590− NI_GPCT_RELOAD_SOURCE_SWITCHING_BITS = 0x4000000,
591− NI_GPCT_RELOAD_SOURCE_GATE_SELECT_BITS = 0x8000000,
592− NI_GPCT_OR_GATE_BIT = 0x10000000,
593− NI_GPCT_INVERT_OUTPUT_BIT = 0x20000000
594− };
532+enum ni_gpct_mode_bits {
533+ NI_GPCT_GATE_ON_BOTH_EDGES_BIT = 0x4,
534+ NI_GPCT_EDGE_GATE_MODE_MASK = 0x18,
535+ NI_GPCT_EDGE_GATE_STARTS_STOPS_BITS = 0x0,
536+ NI_GPCT_EDGE_GATE_STOPS_STARTS_BITS = 0x8,
537+ NI_GPCT_EDGE_GATE_STARTS_BITS = 0x10,
538+ NI_GPCT_EDGE_GATE_NO_STARTS_NO_STOPS_BITS = 0x18,
539+ NI_GPCT_STOP_MODE_MASK = 0x60,
540+ NI_GPCT_STOP_ON_GATE_BITS = 0x00,
541+ NI_GPCT_STOP_ON_GATE_OR_TC_BITS = 0x20,
542+ NI_GPCT_STOP_ON_GATE_OR_SECOND_TC_BITS = 0x40,
543+ NI_GPCT_LOAD_B_SELECT_BIT = 0x80,
544+ NI_GPCT_OUTPUT_MODE_MASK = 0x300,
545+ NI_GPCT_OUTPUT_TC_PULSE_BITS = 0x100,
546+ NI_GPCT_OUTPUT_TC_TOGGLE_BITS = 0x200,
547+ NI_GPCT_OUTPUT_TC_OR_GATE_TOGGLE_BITS = 0x300,
548+ NI_GPCT_HARDWARE_DISARM_MASK = 0xc00,
549+ NI_GPCT_NO_HARDWARE_DISARM_BITS = 0x000,
550+ NI_GPCT_DISARM_AT_TC_BITS = 0x400,
551+ NI_GPCT_DISARM_AT_GATE_BITS = 0x800,
552+ NI_GPCT_DISARM_AT_TC_OR_GATE_BITS = 0xc00,
553+ NI_GPCT_LOADING_ON_TC_BIT = 0x1000,
554+ NI_GPCT_LOADING_ON_GATE_BIT = 0x4000,
555+ NI_GPCT_COUNTING_MODE_MASK = 0x7 << NI_GPCT_COUNTING_MODE_SHIFT,
556+ NI_GPCT_COUNTING_MODE_NORMAL_BITS =
557+ 0x0 << NI_GPCT_COUNTING_MODE_SHIFT,
558+ NI_GPCT_COUNTING_MODE_QUADRATURE_X1_BITS =
559+ 0x1 << NI_GPCT_COUNTING_MODE_SHIFT,
560+ NI_GPCT_COUNTING_MODE_QUADRATURE_X2_BITS =
561+ 0x2 << NI_GPCT_COUNTING_MODE_SHIFT,
562+ NI_GPCT_COUNTING_MODE_QUADRATURE_X4_BITS =
563+ 0x3 << NI_GPCT_COUNTING_MODE_SHIFT,
564+ NI_GPCT_COUNTING_MODE_TWO_PULSE_BITS =
565+ 0x4 << NI_GPCT_COUNTING_MODE_SHIFT,
566+ NI_GPCT_COUNTING_MODE_SYNC_SOURCE_BITS =
567+ 0x6 << NI_GPCT_COUNTING_MODE_SHIFT,
568+ NI_GPCT_INDEX_PHASE_MASK = 0x3 << NI_GPCT_INDEX_PHASE_BITSHIFT,
569+ NI_GPCT_INDEX_PHASE_LOW_A_LOW_B_BITS =
570+ 0x0 << NI_GPCT_INDEX_PHASE_BITSHIFT,
571+ NI_GPCT_INDEX_PHASE_LOW_A_HIGH_B_BITS =
572+ 0x1 << NI_GPCT_INDEX_PHASE_BITSHIFT,
573+ NI_GPCT_INDEX_PHASE_HIGH_A_LOW_B_BITS =
574+ 0x2 << NI_GPCT_INDEX_PHASE_BITSHIFT,
575+ NI_GPCT_INDEX_PHASE_HIGH_A_HIGH_B_BITS =
576+ 0x3 << NI_GPCT_INDEX_PHASE_BITSHIFT,
577+ NI_GPCT_INDEX_ENABLE_BIT = 0x400000,
578+ NI_GPCT_COUNTING_DIRECTION_MASK =
579+ 0x3 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
580+ NI_GPCT_COUNTING_DIRECTION_DOWN_BITS =
581+ 0x00 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
582+ NI_GPCT_COUNTING_DIRECTION_UP_BITS =
583+ 0x1 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
584+ NI_GPCT_COUNTING_DIRECTION_HW_UP_DOWN_BITS =
585+ 0x2 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
586+ NI_GPCT_COUNTING_DIRECTION_HW_GATE_BITS =
587+ 0x3 << NI_GPCT_COUNTING_DIRECTION_SHIFT,
588+ NI_GPCT_RELOAD_SOURCE_MASK = 0xc000000,
589+ NI_GPCT_RELOAD_SOURCE_FIXED_BITS = 0x0,
590+ NI_GPCT_RELOAD_SOURCE_SWITCHING_BITS = 0x4000000,
591+ NI_GPCT_RELOAD_SOURCE_GATE_SELECT_BITS = 0x8000000,
592+ NI_GPCT_OR_GATE_BIT = 0x10000000,
593+ NI_GPCT_INVERT_OUTPUT_BIT = 0x20000000
594+};
595595
596596 /* Bits for setting a clock source with
597597 * INSN_CONFIG_SET_CLOCK_SRC when using NI general-purpose counters. */
598− enum ni_gpct_clock_source_bits {
599− NI_GPCT_CLOCK_SRC_SELECT_MASK = 0x3f,
600− NI_GPCT_TIMEBASE_1_CLOCK_SRC_BITS = 0x0,
601− NI_GPCT_TIMEBASE_2_CLOCK_SRC_BITS = 0x1,
602− NI_GPCT_TIMEBASE_3_CLOCK_SRC_BITS = 0x2,
603− NI_GPCT_LOGIC_LOW_CLOCK_SRC_BITS = 0x3,
604− NI_GPCT_NEXT_GATE_CLOCK_SRC_BITS = 0x4,
605− NI_GPCT_NEXT_TC_CLOCK_SRC_BITS = 0x5,
606− /* NI 660x-specific */
607− NI_GPCT_SOURCE_PIN_i_CLOCK_SRC_BITS = 0x6,
608− NI_GPCT_PXI10_CLOCK_SRC_BITS = 0x7,
609− NI_GPCT_PXI_STAR_TRIGGER_CLOCK_SRC_BITS = 0x8,
610− NI_GPCT_ANALOG_TRIGGER_OUT_CLOCK_SRC_BITS = 0x9,
611− NI_GPCT_PRESCALE_MODE_CLOCK_SRC_MASK = 0x30000000,
612− NI_GPCT_NO_PRESCALE_CLOCK_SRC_BITS = 0x0,
613− /* divide source by 2 */
614− NI_GPCT_PRESCALE_X2_CLOCK_SRC_BITS = 0x10000000,
615− /* divide source by 8 */
616− NI_GPCT_PRESCALE_X8_CLOCK_SRC_BITS = 0x20000000,
617− NI_GPCT_INVERT_CLOCK_SRC_BIT = 0x80000000
618− };
619− static inline unsigned NI_GPCT_SOURCE_PIN_CLOCK_SRC_BITS(unsigned n)
620− {
621− /* NI 660x-specific */
622− return 0x10 + n;
623− }
624− static inline unsigned NI_GPCT_RTSI_CLOCK_SRC_BITS(unsigned n)
625− {
626− return 0x18 + n;
627− }
628− static inline unsigned NI_GPCT_PFI_CLOCK_SRC_BITS(unsigned n)
629− {
630− /* no pfi on NI 660x */
631− return 0x20 + n;
632− }
598+enum ni_gpct_clock_source_bits {
599+ NI_GPCT_CLOCK_SRC_SELECT_MASK = 0x3f,
600+ NI_GPCT_TIMEBASE_1_CLOCK_SRC_BITS = 0x0,
601+ NI_GPCT_TIMEBASE_2_CLOCK_SRC_BITS = 0x1,
602+ NI_GPCT_TIMEBASE_3_CLOCK_SRC_BITS = 0x2,
603+ NI_GPCT_LOGIC_LOW_CLOCK_SRC_BITS = 0x3,
604+ NI_GPCT_NEXT_GATE_CLOCK_SRC_BITS = 0x4,
605+ NI_GPCT_NEXT_TC_CLOCK_SRC_BITS = 0x5,
606+ /* NI 660x-specific */
607+ NI_GPCT_SOURCE_PIN_i_CLOCK_SRC_BITS = 0x6,
608+ NI_GPCT_PXI10_CLOCK_SRC_BITS = 0x7,
609+ NI_GPCT_PXI_STAR_TRIGGER_CLOCK_SRC_BITS = 0x8,
610+ NI_GPCT_ANALOG_TRIGGER_OUT_CLOCK_SRC_BITS = 0x9,
611+ NI_GPCT_PRESCALE_MODE_CLOCK_SRC_MASK = 0x30000000,
612+ NI_GPCT_NO_PRESCALE_CLOCK_SRC_BITS = 0x0,
613+ /* divide source by 2 */
614+ NI_GPCT_PRESCALE_X2_CLOCK_SRC_BITS = 0x10000000,
615+ /* divide source by 8 */
616+ NI_GPCT_PRESCALE_X8_CLOCK_SRC_BITS = 0x20000000,
617+ NI_GPCT_INVERT_CLOCK_SRC_BIT = 0x80000000
618+};
619+static inline unsigned NI_GPCT_SOURCE_PIN_CLOCK_SRC_BITS(unsigned n)
620+{
621+ /* NI 660x-specific */
622+ return 0x10 + n;
623+}
624+static inline unsigned NI_GPCT_RTSI_CLOCK_SRC_BITS(unsigned n)
625+{
626+ return 0x18 + n;
627+}
628+static inline unsigned NI_GPCT_PFI_CLOCK_SRC_BITS(unsigned n)
629+{
630+ /* no pfi on NI 660x */
631+ return 0x20 + n;
632+}
633633
634634 /* Possibilities for setting a gate source with
635635 INSN_CONFIG_SET_GATE_SRC when using NI general-purpose counters.
636636 May be bitwise-or'd with CR_EDGE or CR_INVERT. */
637− enum ni_gpct_gate_select {
638− /* m-series gates */
639− NI_GPCT_TIMESTAMP_MUX_GATE_SELECT = 0x0,
640− NI_GPCT_AI_START2_GATE_SELECT = 0x12,
641− NI_GPCT_PXI_STAR_TRIGGER_GATE_SELECT = 0x13,
642− NI_GPCT_NEXT_OUT_GATE_SELECT = 0x14,
643− NI_GPCT_AI_START1_GATE_SELECT = 0x1c,
644− NI_GPCT_NEXT_SOURCE_GATE_SELECT = 0x1d,
645− NI_GPCT_ANALOG_TRIGGER_OUT_GATE_SELECT = 0x1e,
646− NI_GPCT_LOGIC_LOW_GATE_SELECT = 0x1f,
647− /* more gates for 660x */
648− NI_GPCT_SOURCE_PIN_i_GATE_SELECT = 0x100,
649− NI_GPCT_GATE_PIN_i_GATE_SELECT = 0x101,
650− /* more gates for 660x "second gate" */
651− NI_GPCT_UP_DOWN_PIN_i_GATE_SELECT = 0x201,
652− NI_GPCT_SELECTED_GATE_GATE_SELECT = 0x21e,
653− /* m-series "second gate" sources are unknown,
654− * we should add them here with an offset of 0x300 when
655− * known. */
656− NI_GPCT_DISABLED_GATE_SELECT = 0x8000,
657− };
658− static inline unsigned NI_GPCT_GATE_PIN_GATE_SELECT(unsigned n)
659− {
660− return 0x102 + n;
661− }
662− static inline unsigned NI_GPCT_RTSI_GATE_SELECT(unsigned n)
663− {
664− return NI_USUAL_RTSI_SELECT(n);
665− }
666− static inline unsigned NI_GPCT_PFI_GATE_SELECT(unsigned n)
667− {
668− return NI_USUAL_PFI_SELECT(n);
669− }
670− static inline unsigned NI_GPCT_UP_DOWN_PIN_GATE_SELECT(unsigned n)
671− {
672− return 0x202 + n;
673− }
637+enum ni_gpct_gate_select {
638+ /* m-series gates */
639+ NI_GPCT_TIMESTAMP_MUX_GATE_SELECT = 0x0,
640+ NI_GPCT_AI_START2_GATE_SELECT = 0x12,
641+ NI_GPCT_PXI_STAR_TRIGGER_GATE_SELECT = 0x13,
642+ NI_GPCT_NEXT_OUT_GATE_SELECT = 0x14,
643+ NI_GPCT_AI_START1_GATE_SELECT = 0x1c,
644+ NI_GPCT_NEXT_SOURCE_GATE_SELECT = 0x1d,
645+ NI_GPCT_ANALOG_TRIGGER_OUT_GATE_SELECT = 0x1e,
646+ NI_GPCT_LOGIC_LOW_GATE_SELECT = 0x1f,
647+ /* more gates for 660x */
648+ NI_GPCT_SOURCE_PIN_i_GATE_SELECT = 0x100,
649+ NI_GPCT_GATE_PIN_i_GATE_SELECT = 0x101,
650+ /* more gates for 660x "second gate" */
651+ NI_GPCT_UP_DOWN_PIN_i_GATE_SELECT = 0x201,
652+ NI_GPCT_SELECTED_GATE_GATE_SELECT = 0x21e,
653+ /* m-series "second gate" sources are unknown,
654+ * we should add them here with an offset of 0x300 when
655+ * known. */
656+ NI_GPCT_DISABLED_GATE_SELECT = 0x8000,
657+};
658+static inline unsigned NI_GPCT_GATE_PIN_GATE_SELECT(unsigned n)
659+{
660+ return 0x102 + n;
661+}
662+static inline unsigned NI_GPCT_RTSI_GATE_SELECT(unsigned n)
663+{
664+ return NI_USUAL_RTSI_SELECT(n);
665+}
666+static inline unsigned NI_GPCT_PFI_GATE_SELECT(unsigned n)
667+{
668+ return NI_USUAL_PFI_SELECT(n);
669+}
670+static inline unsigned NI_GPCT_UP_DOWN_PIN_GATE_SELECT(unsigned n)
671+{
672+ return 0x202 + n;
673+}
674674
675675 /* Possibilities for setting a source with
676676 INSN_CONFIG_SET_OTHER_SRC when using NI general-purpose counters. */
677− enum ni_gpct_other_index {
678− NI_GPCT_SOURCE_ENCODER_A,
679− NI_GPCT_SOURCE_ENCODER_B,
680− NI_GPCT_SOURCE_ENCODER_Z
681− };
682− enum ni_gpct_other_select {
683− /* m-series gates */
684− /* Still unknown, probably only need NI_GPCT_PFI_OTHER_SELECT */
685− NI_GPCT_DISABLED_OTHER_SELECT = 0x8000,
686− };
687− static inline unsigned NI_GPCT_PFI_OTHER_SELECT(unsigned n)
688− {
689− return NI_USUAL_PFI_SELECT(n);
690− }
677+enum ni_gpct_other_index {
678+ NI_GPCT_SOURCE_ENCODER_A,
679+ NI_GPCT_SOURCE_ENCODER_B,
680+ NI_GPCT_SOURCE_ENCODER_Z
681+};
682+enum ni_gpct_other_select {
683+ /* m-series gates */
684+ /* Still unknown, probably only need NI_GPCT_PFI_OTHER_SELECT */
685+ NI_GPCT_DISABLED_OTHER_SELECT = 0x8000,
686+};
687+static inline unsigned NI_GPCT_PFI_OTHER_SELECT(unsigned n)
688+{
689+ return NI_USUAL_PFI_SELECT(n);
690+}
691691
692692 /* start sources for ni general-purpose counters for use with
693693 INSN_CONFIG_ARM */
694− enum ni_gpct_arm_source {
695− NI_GPCT_ARM_IMMEDIATE = 0x0,
696− NI_GPCT_ARM_PAIRED_IMMEDIATE = 0x1, /* Start both the counter
697− * and the adjacent paired
698− * counter simultaneously */
699− /* NI doesn't document bits for selecting hardware arm triggers.
700− * If the NI_GPCT_ARM_UNKNOWN bit is set, we will pass the least
701− * significant bits (3 bits for 660x or 5 bits for m-series)
702− * through to the hardware. This will at least allow someone to
703− * figure out what the bits do later. */
704− NI_GPCT_ARM_UNKNOWN = 0x1000,
705− };
694+enum ni_gpct_arm_source {
695+ NI_GPCT_ARM_IMMEDIATE = 0x0,
696+ NI_GPCT_ARM_PAIRED_IMMEDIATE = 0x1, /* Start both the counter
697+ * and the adjacent paired
698+ * counter simultaneously */
699+ /* NI doesn't document bits for selecting hardware arm triggers.
700+ * If the NI_GPCT_ARM_UNKNOWN bit is set, we will pass the least
701+ * significant bits (3 bits for 660x or 5 bits for m-series)
702+ * through to the hardware. This will at least allow someone to
703+ * figure out what the bits do later. */
704+ NI_GPCT_ARM_UNKNOWN = 0x1000,
705+};
706706
707707 /* digital filtering options for ni 660x for use with INSN_CONFIG_FILTER. */
708− enum ni_gpct_filter_select {
709− NI_GPCT_FILTER_OFF = 0x0,
710− NI_GPCT_FILTER_TIMEBASE_3_SYNC = 0x1,
711− NI_GPCT_FILTER_100x_TIMEBASE_1 = 0x2,
712− NI_GPCT_FILTER_20x_TIMEBASE_1 = 0x3,
713− NI_GPCT_FILTER_10x_TIMEBASE_1 = 0x4,
714− NI_GPCT_FILTER_2x_TIMEBASE_1 = 0x5,
715− NI_GPCT_FILTER_2x_TIMEBASE_3 = 0x6
716− };
708+enum ni_gpct_filter_select {
709+ NI_GPCT_FILTER_OFF = 0x0,
710+ NI_GPCT_FILTER_TIMEBASE_3_SYNC = 0x1,
711+ NI_GPCT_FILTER_100x_TIMEBASE_1 = 0x2,
712+ NI_GPCT_FILTER_20x_TIMEBASE_1 = 0x3,
713+ NI_GPCT_FILTER_10x_TIMEBASE_1 = 0x4,
714+ NI_GPCT_FILTER_2x_TIMEBASE_1 = 0x5,
715+ NI_GPCT_FILTER_2x_TIMEBASE_3 = 0x6
716+};
717717
718718 /* PFI digital filtering options for ni m-series for use with
719719 * INSN_CONFIG_FILTER. */
720− enum ni_pfi_filter_select {
721− NI_PFI_FILTER_OFF = 0x0,
722− NI_PFI_FILTER_125ns = 0x1,
723− NI_PFI_FILTER_6425ns = 0x2,
724− NI_PFI_FILTER_2550us = 0x3
725− };
720+enum ni_pfi_filter_select {
721+ NI_PFI_FILTER_OFF = 0x0,
722+ NI_PFI_FILTER_125ns = 0x1,
723+ NI_PFI_FILTER_6425ns = 0x2,
724+ NI_PFI_FILTER_2550us = 0x3
725+};
726726
727727 /* master clock sources for ni mio boards and INSN_CONFIG_SET_CLOCK_SRC */
728− enum ni_mio_clock_source {
729− NI_MIO_INTERNAL_CLOCK = 0,
730− NI_MIO_RTSI_CLOCK = 1, /* doesn't work for m-series, use
731− NI_MIO_PLL_RTSI_CLOCK() */
732− /* the NI_MIO_PLL_* sources are m-series only */
733− NI_MIO_PLL_PXI_STAR_TRIGGER_CLOCK = 2,
734− NI_MIO_PLL_PXI10_CLOCK = 3,
735− NI_MIO_PLL_RTSI0_CLOCK = 4
736− };
737− static inline unsigned NI_MIO_PLL_RTSI_CLOCK(unsigned rtsi_channel)
738− {
739− return NI_MIO_PLL_RTSI0_CLOCK + rtsi_channel;
740− }
728+enum ni_mio_clock_source {
729+ NI_MIO_INTERNAL_CLOCK = 0,
730+ NI_MIO_RTSI_CLOCK = 1, /* doesn't work for m-series, use
731+ NI_MIO_PLL_RTSI_CLOCK() */
732+ /* the NI_MIO_PLL_* sources are m-series only */
733+ NI_MIO_PLL_PXI_STAR_TRIGGER_CLOCK = 2,
734+ NI_MIO_PLL_PXI10_CLOCK = 3,
735+ NI_MIO_PLL_RTSI0_CLOCK = 4
736+};
737+static inline unsigned NI_MIO_PLL_RTSI_CLOCK(unsigned rtsi_channel)
738+{
739+ return NI_MIO_PLL_RTSI0_CLOCK + rtsi_channel;
740+}
741741
742742 /* Signals which can be routed to an NI RTSI pin with INSN_CONFIG_SET_ROUTING.
743743 The numbers assigned are not arbitrary, they correspond to the bits required
744744 to program the board. */
745− enum ni_rtsi_routing {
746− NI_RTSI_OUTPUT_ADR_START1 = 0,
747− NI_RTSI_OUTPUT_ADR_START2 = 1,
748− NI_RTSI_OUTPUT_SCLKG = 2,
749− NI_RTSI_OUTPUT_DACUPDN = 3,
750− NI_RTSI_OUTPUT_DA_START1 = 4,
751− NI_RTSI_OUTPUT_G_SRC0 = 5,
752− NI_RTSI_OUTPUT_G_GATE0 = 6,
753− NI_RTSI_OUTPUT_RGOUT0 = 7,
754− NI_RTSI_OUTPUT_RTSI_BRD_0 = 8,
755− NI_RTSI_OUTPUT_RTSI_OSC = 12 /* pre-m-series always have RTSI
756− * clock on line 7 */
757− };
758− static inline unsigned NI_RTSI_OUTPUT_RTSI_BRD(unsigned n)
759− {
760− return NI_RTSI_OUTPUT_RTSI_BRD_0 + n;
761− }
745+enum ni_rtsi_routing {
746+ NI_RTSI_OUTPUT_ADR_START1 = 0,
747+ NI_RTSI_OUTPUT_ADR_START2 = 1,
748+ NI_RTSI_OUTPUT_SCLKG = 2,
749+ NI_RTSI_OUTPUT_DACUPDN = 3,
750+ NI_RTSI_OUTPUT_DA_START1 = 4,
751+ NI_RTSI_OUTPUT_G_SRC0 = 5,
752+ NI_RTSI_OUTPUT_G_GATE0 = 6,
753+ NI_RTSI_OUTPUT_RGOUT0 = 7,
754+ NI_RTSI_OUTPUT_RTSI_BRD_0 = 8,
755+ NI_RTSI_OUTPUT_RTSI_OSC = 12 /* pre-m-series always have RTSI
756+ * clock on line 7 */
757+};
758+static inline unsigned NI_RTSI_OUTPUT_RTSI_BRD(unsigned n)
759+{
760+ return NI_RTSI_OUTPUT_RTSI_BRD_0 + n;
761+}
762762
763763 /* Signals which can be routed to an NI PFI pin on an m-series board with
764764 * INSN_CONFIG_SET_ROUTING. These numbers are also returned by
765765 * INSN_CONFIG_GET_ROUTING on pre-m-series boards, even though their routing
766766 * cannot be changed. The numbers assigned are not arbitrary, they correspond
767767 * to the bits required to program the board. */
768− enum ni_pfi_routing {
769− NI_PFI_OUTPUT_PFI_DEFAULT = 0,
770− NI_PFI_OUTPUT_AI_START1 = 1,
771− NI_PFI_OUTPUT_AI_START2 = 2,
772− NI_PFI_OUTPUT_AI_CONVERT = 3,
773− NI_PFI_OUTPUT_G_SRC1 = 4,
774− NI_PFI_OUTPUT_G_GATE1 = 5,
775− NI_PFI_OUTPUT_AO_UPDATE_N = 6,
776− NI_PFI_OUTPUT_AO_START1 = 7,
777− NI_PFI_OUTPUT_AI_START_PULSE = 8,
778− NI_PFI_OUTPUT_G_SRC0 = 9,
779− NI_PFI_OUTPUT_G_GATE0 = 10,
780− NI_PFI_OUTPUT_EXT_STROBE = 11,
781− NI_PFI_OUTPUT_AI_EXT_MUX_CLK = 12,
782− NI_PFI_OUTPUT_GOUT0 = 13,
783− NI_PFI_OUTPUT_GOUT1 = 14,
784− NI_PFI_OUTPUT_FREQ_OUT = 15,
785− NI_PFI_OUTPUT_PFI_DO = 16,
786− NI_PFI_OUTPUT_I_ATRIG = 17,
787− NI_PFI_OUTPUT_RTSI0 = 18,
788− NI_PFI_OUTPUT_PXI_STAR_TRIGGER_IN = 26,
789− NI_PFI_OUTPUT_SCXI_TRIG1 = 27,
790− NI_PFI_OUTPUT_DIO_CHANGE_DETECT_RTSI = 28,
791− NI_PFI_OUTPUT_CDI_SAMPLE = 29,
792− NI_PFI_OUTPUT_CDO_UPDATE = 30
793− };
794− static inline unsigned NI_PFI_OUTPUT_RTSI(unsigned rtsi_channel)
795− {
796− return NI_PFI_OUTPUT_RTSI0 + rtsi_channel;
797− }
768+enum ni_pfi_routing {
769+ NI_PFI_OUTPUT_PFI_DEFAULT = 0,
770+ NI_PFI_OUTPUT_AI_START1 = 1,
771+ NI_PFI_OUTPUT_AI_START2 = 2,
772+ NI_PFI_OUTPUT_AI_CONVERT = 3,
773+ NI_PFI_OUTPUT_G_SRC1 = 4,
774+ NI_PFI_OUTPUT_G_GATE1 = 5,
775+ NI_PFI_OUTPUT_AO_UPDATE_N = 6,
776+ NI_PFI_OUTPUT_AO_START1 = 7,
777+ NI_PFI_OUTPUT_AI_START_PULSE = 8,
778+ NI_PFI_OUTPUT_G_SRC0 = 9,
779+ NI_PFI_OUTPUT_G_GATE0 = 10,
780+ NI_PFI_OUTPUT_EXT_STROBE = 11,
781+ NI_PFI_OUTPUT_AI_EXT_MUX_CLK = 12,
782+ NI_PFI_OUTPUT_GOUT0 = 13,
783+ NI_PFI_OUTPUT_GOUT1 = 14,
784+ NI_PFI_OUTPUT_FREQ_OUT = 15,
785+ NI_PFI_OUTPUT_PFI_DO = 16,
786+ NI_PFI_OUTPUT_I_ATRIG = 17,
787+ NI_PFI_OUTPUT_RTSI0 = 18,
788+ NI_PFI_OUTPUT_PXI_STAR_TRIGGER_IN = 26,
789+ NI_PFI_OUTPUT_SCXI_TRIG1 = 27,
790+ NI_PFI_OUTPUT_DIO_CHANGE_DETECT_RTSI = 28,
791+ NI_PFI_OUTPUT_CDI_SAMPLE = 29,
792+ NI_PFI_OUTPUT_CDO_UPDATE = 30
793+};
794+static inline unsigned NI_PFI_OUTPUT_RTSI(unsigned rtsi_channel)
795+{
796+ return NI_PFI_OUTPUT_RTSI0 + rtsi_channel;
797+}
798798
799799 /* Signals which can be routed to output on a NI PFI pin on a 660x board
800800 with INSN_CONFIG_SET_ROUTING. The numbers assigned are
@@ -802,113 +802,112 @@ INSN_CONFIG_ARM */ · 1 unmodified line
802802 to program the board. Lines 0 to 7 can only be set to
803803 NI_660X_PFI_OUTPUT_DIO. Lines 32 to 39 can only be set to
804804 NI_660X_PFI_OUTPUT_COUNTER. */
805− enum ni_660x_pfi_routing {
806− NI_660X_PFI_OUTPUT_COUNTER = 1, /* counter */
807− NI_660X_PFI_OUTPUT_DIO = 2, /* static digital output */
808− };
805+enum ni_660x_pfi_routing {
806+ NI_660X_PFI_OUTPUT_COUNTER = 1, /* counter */
807+ NI_660X_PFI_OUTPUT_DIO = 2, /* static digital output */
808+};
809809
810810 /* NI External Trigger lines. These values are not arbitrary, but are related
811811 * to the bits required to program the board (offset by 1 for historical
812812 * reasons). */
813− static inline unsigned NI_EXT_PFI(unsigned pfi_channel)
814− {
815− return NI_USUAL_PFI_SELECT(pfi_channel) - 1;
816− }
817− static inline unsigned NI_EXT_RTSI(unsigned rtsi_channel)
818− {
819− return NI_USUAL_RTSI_SELECT(rtsi_channel) - 1;
820− }
813+static inline unsigned NI_EXT_PFI(unsigned pfi_channel)
814+{
815+ return NI_USUAL_PFI_SELECT(pfi_channel) - 1;
816+}
817+static inline unsigned NI_EXT_RTSI(unsigned rtsi_channel)
818+{
819+ return NI_USUAL_RTSI_SELECT(rtsi_channel) - 1;
820+}
821821
822822 /* status bits for INSN_CONFIG_GET_COUNTER_STATUS */
823− enum comedi_counter_status_flags {
824− COMEDI_COUNTER_ARMED = 0x1,
825− COMEDI_COUNTER_COUNTING = 0x2,
826− COMEDI_COUNTER_TERMINAL_COUNT = 0x4,
827− };
823+enum comedi_counter_status_flags {
824+ COMEDI_COUNTER_ARMED = 0x1,
825+ COMEDI_COUNTER_COUNTING = 0x2,
826+ COMEDI_COUNTER_TERMINAL_COUNT = 0x4,
827+};
828828
829829 /* Clock sources for CDIO subdevice on NI m-series boards. Used as the
830830 * scan_begin_arg for a comedi_command. These sources may also be bitwise-or'd
831831 * with CR_INVERT to change polarity. */
832− enum ni_m_series_cdio_scan_begin_src {
833− NI_CDIO_SCAN_BEGIN_SRC_GROUND = 0,
834− NI_CDIO_SCAN_BEGIN_SRC_AI_START = 18,
835− NI_CDIO_SCAN_BEGIN_SRC_AI_CONVERT = 19,
836− NI_CDIO_SCAN_BEGIN_SRC_PXI_STAR_TRIGGER = 20,
837− NI_CDIO_SCAN_BEGIN_SRC_G0_OUT = 28,
838− NI_CDIO_SCAN_BEGIN_SRC_G1_OUT = 29,
839− NI_CDIO_SCAN_BEGIN_SRC_ANALOG_TRIGGER = 30,
840− NI_CDIO_SCAN_BEGIN_SRC_AO_UPDATE = 31,
841− NI_CDIO_SCAN_BEGIN_SRC_FREQ_OUT = 32,
842− NI_CDIO_SCAN_BEGIN_SRC_DIO_CHANGE_DETECT_IRQ = 33
843− };
844− static inline unsigned NI_CDIO_SCAN_BEGIN_SRC_PFI(unsigned pfi_channel)
845− {
846− return NI_USUAL_PFI_SELECT(pfi_channel);
847− }
848− static inline unsigned
849− NI_CDIO_SCAN_BEGIN_SRC_RTSI(unsigned rtsi_channel)
850− {
851− return NI_USUAL_RTSI_SELECT(rtsi_channel);
852− }
832+enum ni_m_series_cdio_scan_begin_src {
833+ NI_CDIO_SCAN_BEGIN_SRC_GROUND = 0,
834+ NI_CDIO_SCAN_BEGIN_SRC_AI_START = 18,
835+ NI_CDIO_SCAN_BEGIN_SRC_AI_CONVERT = 19,
836+ NI_CDIO_SCAN_BEGIN_SRC_PXI_STAR_TRIGGER = 20,
837+ NI_CDIO_SCAN_BEGIN_SRC_G0_OUT = 28,
838+ NI_CDIO_SCAN_BEGIN_SRC_G1_OUT = 29,
839+ NI_CDIO_SCAN_BEGIN_SRC_ANALOG_TRIGGER = 30,
840+ NI_CDIO_SCAN_BEGIN_SRC_AO_UPDATE = 31,
841+ NI_CDIO_SCAN_BEGIN_SRC_FREQ_OUT = 32,
842+ NI_CDIO_SCAN_BEGIN_SRC_DIO_CHANGE_DETECT_IRQ = 33
843+};
844+static inline unsigned NI_CDIO_SCAN_BEGIN_SRC_PFI(unsigned pfi_channel)
845+{
846+ return NI_USUAL_PFI_SELECT(pfi_channel);
847+}
848+static inline unsigned NI_CDIO_SCAN_BEGIN_SRC_RTSI(unsigned rtsi_channel)
849+{
850+ return NI_USUAL_RTSI_SELECT(rtsi_channel);
851+}
853852
854853 /* scan_begin_src for scan_begin_arg==TRIG_EXT with analog output command on NI
855854 * boards. These scan begin sources can also be bitwise-or'd with CR_INVERT to
856855 * change polarity. */
857− static inline unsigned NI_AO_SCAN_BEGIN_SRC_PFI(unsigned pfi_channel)
858− {
859− return NI_USUAL_PFI_SELECT(pfi_channel);
860− }
861− static inline unsigned NI_AO_SCAN_BEGIN_SRC_RTSI(unsigned rtsi_channel)
862− {
863− return NI_USUAL_RTSI_SELECT(rtsi_channel);
864− }
856+static inline unsigned NI_AO_SCAN_BEGIN_SRC_PFI(unsigned pfi_channel)
857+{
858+ return NI_USUAL_PFI_SELECT(pfi_channel);
859+}
860+static inline unsigned NI_AO_SCAN_BEGIN_SRC_RTSI(unsigned rtsi_channel)
861+{
862+ return NI_USUAL_RTSI_SELECT(rtsi_channel);
863+}
865864
866865 /* Bits for setting a clock source with
867866 * INSN_CONFIG_SET_CLOCK_SRC when using NI frequency output subdevice. */
868− enum ni_freq_out_clock_source_bits {
869− NI_FREQ_OUT_TIMEBASE_1_DIV_2_CLOCK_SRC, /* 10 MHz */
870− NI_FREQ_OUT_TIMEBASE_2_CLOCK_SRC /* 100 KHz */
871− };
867+enum ni_freq_out_clock_source_bits {
868+ NI_FREQ_OUT_TIMEBASE_1_DIV_2_CLOCK_SRC, /* 10 MHz */
869+ NI_FREQ_OUT_TIMEBASE_2_CLOCK_SRC /* 100 KHz */
870+};
872871
873872 /* Values for setting a clock source with INSN_CONFIG_SET_CLOCK_SRC for
874873 * 8254 counter subdevices on Amplicon DIO boards (amplc_dio200 driver). */
875− enum amplc_dio_clock_source {
876− AMPLC_DIO_CLK_CLKN, /* per channel external clock
877− input/output pin (pin is only an
878− input when clock source set to this
879− value, otherwise it is an output) */
880− AMPLC_DIO_CLK_10MHZ, /* 10 MHz internal clock */
881− AMPLC_DIO_CLK_1MHZ, /* 1 MHz internal clock */
882− AMPLC_DIO_CLK_100KHZ, /* 100 kHz internal clock */
883− AMPLC_DIO_CLK_10KHZ, /* 10 kHz internal clock */
884− AMPLC_DIO_CLK_1KHZ, /* 1 kHz internal clock */
885− AMPLC_DIO_CLK_OUTNM1, /* output of preceding counter channel
886− (for channel 0, preceding counter
887− channel is channel 2 on preceding
888− counter subdevice, for first counter
889− subdevice, preceding counter
890− subdevice is the last counter
891− subdevice) */
892− AMPLC_DIO_CLK_EXT /* per chip external input pin */
893− };
874+enum amplc_dio_clock_source {
875+ AMPLC_DIO_CLK_CLKN, /* per channel external clock
876+ input/output pin (pin is only an
877+ input when clock source set to this
878+ value, otherwise it is an output) */
879+ AMPLC_DIO_CLK_10MHZ, /* 10 MHz internal clock */
880+ AMPLC_DIO_CLK_1MHZ, /* 1 MHz internal clock */
881+ AMPLC_DIO_CLK_100KHZ, /* 100 kHz internal clock */
882+ AMPLC_DIO_CLK_10KHZ, /* 10 kHz internal clock */
883+ AMPLC_DIO_CLK_1KHZ, /* 1 kHz internal clock */
884+ AMPLC_DIO_CLK_OUTNM1, /* output of preceding counter channel
885+ (for channel 0, preceding counter
886+ channel is channel 2 on preceding
887+ counter subdevice, for first counter
888+ subdevice, preceding counter
889+ subdevice is the last counter
890+ subdevice) */
891+ AMPLC_DIO_CLK_EXT /* per chip external input pin */
892+};
894893
895894 /* Values for setting a gate source with INSN_CONFIG_SET_GATE_SRC for
896895 * 8254 counter subdevices on Amplicon DIO boards (amplc_dio200 driver). */
897− enum amplc_dio_gate_source {
898− AMPLC_DIO_GAT_VCC, /* internal high logic level */
899− AMPLC_DIO_GAT_GND, /* internal low logic level */
900− AMPLC_DIO_GAT_GATN, /* per channel external gate input */
901− AMPLC_DIO_GAT_NOUTNM2, /* negated output of counter channel
902− minus 2 (for channels 0 or 1,
903− channel minus 2 is channel 1 or 2 on
904− the preceding counter subdevice, for
905− the first counter subdevice the
906− preceding counter subdevice is the
907− last counter subdevice) */
908− AMPLC_DIO_GAT_RESERVED4,
909− AMPLC_DIO_GAT_RESERVED5,
910− AMPLC_DIO_GAT_RESERVED6,
911− AMPLC_DIO_GAT_RESERVED7
912− };
896+enum amplc_dio_gate_source {
897+ AMPLC_DIO_GAT_VCC, /* internal high logic level */
898+ AMPLC_DIO_GAT_GND, /* internal low logic level */
899+ AMPLC_DIO_GAT_GATN, /* per channel external gate input */
900+ AMPLC_DIO_GAT_NOUTNM2, /* negated output of counter channel
901+ minus 2 (for channels 0 or 1,
902+ channel minus 2 is channel 1 or 2 on
903+ the preceding counter subdevice, for
904+ the first counter subdevice the
905+ preceding counter subdevice is the
906+ last counter subdevice) */
907+ AMPLC_DIO_GAT_RESERVED4,
908+ AMPLC_DIO_GAT_RESERVED5,
909+ AMPLC_DIO_GAT_RESERVED6,
910+ AMPLC_DIO_GAT_RESERVED7
911+};
913912
914913 #endif /* _COMEDI_H */
drivers/staging/comedi/comedi_fops.c+73−79
@@ -370,7 +370,8 @@ static int do_devconfig_ioctl(struct comedi_device *dev, · 369 unmodified lines
370370 return -ENOMEM;
371371
372372 if (copy_from_user(aux_data,
373− comedi_aux_data(it.options, 0), aux_len)) {
373+ (unsigned char __user *
374+ )comedi_aux_data(it.options, 0), aux_len)) {
374375 vfree(aux_data);
375376 return -EFAULT;
376377 }
@@ -426,7 +427,7 @@ static int do_bufconfig_ioctl(struct comedi_device *dev, · 49 unmodified lines
426427 if (bc.subdevice >= dev->n_subdevices || bc.subdevice < 0)
427428 return -EINVAL;
428429
429− s = dev->subdevices + bc.subdevice;
430+ s = &dev->subdevices[bc.subdevice];
430431 async = s->async;
431432
432433 if (!async) {
@@ -539,7 +540,7 @@ static int do_subdinfo_ioctl(struct comedi_device *dev, · 106 unmodified lines
539540
540541 /* fill subdinfo structs */
541542 for (i = 0; i < dev->n_subdevices; i++) {
542− s = dev->subdevices + i;
543+ s = &dev->subdevices[i];
543544 us = tmp + i;
544545
545546 us->type = s->type;
@@ -617,7 +618,7 @@ static int do_chaninfo_ioctl(struct comedi_device *dev, · 71 unmodified lines
617618
618619 if (it.subdev >= dev->n_subdevices)
619620 return -EINVAL;
620− s = dev->subdevices + it.subdev;
621+ s = &dev->subdevices[it.subdev];
621622
622623 if (it.maxdata_list) {
623624 if (s->maxdata || !s->maxdata_list)
@@ -685,7 +686,7 @@ static int do_bufinfo_ioctl(struct comedi_device *dev, · 61 unmodified lines
685686 if (bi.subdevice >= dev->n_subdevices || bi.subdevice < 0)
686687 return -EINVAL;
687688
688− s = dev->subdevices + bi.subdevice;
689+ s = &dev->subdevices[bi.subdevice];
689690
690691 if (s->lock && s->lock != file)
691692 return -EACCES;
@@ -882,14 +883,12 @@ static int check_insn_config_length(struct comedi_insn *insn, · 190 unmodified lines
882883 /* by default we allow the insn since we don't have checks for
883884 * all possible cases yet */
884885 default:
885− printk(KERN_WARNING
886− "comedi: no check for data length of config insn id "
887− "%i is implemented.\n"
888− " Add a check to %s in %s.\n"
889− " Assuming n=%i is correct.\n", data[0], __func__,
890− __FILE__, insn->n);
886+ pr_warn("comedi: No check for data length of config insn id %i is implemented.\n",
887+ data[0]);
888+ pr_warn("comedi: Add a check to %s in %s.\n",
889+ __func__, __FILE__);
890+ pr_warn("comedi: Assuming n=%i is correct.\n", insn->n);
891891 return 0;
892− break;
893892 }
894893 return -EINVAL;
895894 }
@@ -940,7 +939,7 @@ static int parse_insn(struct comedi_device *dev, struct comedi_insn *insn, · 44 unmodified lines
940939 ret = -EINVAL;
941940 break;
942941 }
943− s = dev->subdevices + insn->subdev;
942+ s = &dev->subdevices[insn->subdev];
944943 if (!s->async) {
945944 DPRINTK("no async\n");
946945 ret = -EINVAL;
@@ -951,7 +950,7 @@ static int parse_insn(struct comedi_device *dev, struct comedi_insn *insn, · 4 unmodified lines
951950 ret = -EAGAIN;
952951 break;
953952 }
954− ret = s->async->inttrig(dev, s, insn->data[0]);
953+ ret = s->async->inttrig(dev, s, data[0]);
955954 if (ret >= 0)
956955 ret = 1;
957956 break;
@@ -969,7 +968,7 @@ static int parse_insn(struct comedi_device *dev, struct comedi_insn *insn, · 11 unmodified lines
969968 ret = -EINVAL;
970969 goto out;
971970 }
972− s = dev->subdevices + insn->subdev;
971+ s = &dev->subdevices[insn->subdev];
973972
974973 if (s->type == COMEDI_SUBD_UNUSED) {
975974 DPRINTK("%d not usable subdevice\n", insn->subdev);
@@ -1133,37 +1132,37 @@ static void comedi_set_subdevice_runflags(struct comedi_subdevice *s, · 157 unmodified lines
11331132 }
11341133
11351134 static int do_cmd_ioctl(struct comedi_device *dev,
1136− struct comedi_cmd __user *cmd, void *file)
1135+ struct comedi_cmd __user *arg, void *file)
11371136 {
1138− struct comedi_cmd user_cmd;
1137+ struct comedi_cmd cmd;
11391138 struct comedi_subdevice *s;
11401139 struct comedi_async *async;
11411140 int ret = 0;
1142− unsigned int __user *chanlist_saver = NULL;
1141+ unsigned int __user *user_chanlist;
11431142
1144− if (copy_from_user(&user_cmd, cmd, sizeof(struct comedi_cmd))) {
1143+ if (copy_from_user(&cmd, arg, sizeof(struct comedi_cmd))) {
11451144 DPRINTK("bad cmd address\n");
11461145 return -EFAULT;
11471146 }
11481147 /* save user's chanlist pointer so it can be restored later */
1149− chanlist_saver = user_cmd.chanlist;
1148+ user_chanlist = (unsigned int __user *)cmd.chanlist;
11501149
1151− if (user_cmd.subdev >= dev->n_subdevices) {
1152− DPRINTK("%d no such subdevice\n", user_cmd.subdev);
1150+ if (cmd.subdev >= dev->n_subdevices) {
1151+ DPRINTK("%d no such subdevice\n", cmd.subdev);
11531152 return -ENODEV;
11541153 }
11551154
1156− s = dev->subdevices + user_cmd.subdev;
1155+ s = &dev->subdevices[cmd.subdev];
11571156 async = s->async;
11581157
11591158 if (s->type == COMEDI_SUBD_UNUSED) {
1160− DPRINTK("%d not valid subdevice\n", user_cmd.subdev);
1159+ DPRINTK("%d not valid subdevice\n", cmd.subdev);
11611160 return -EIO;
11621161 }
11631162
11641163 if (!s->do_cmd || !s->do_cmdtest || !s->async) {
11651164 DPRINTK("subdevice %i does not support commands\n",
1166− user_cmd.subdev);
1165+ cmd.subdev);
11671166 return -EIO;
11681167 }
11691168
@@ -1181,23 +1180,22 @@ static int do_cmd_ioctl(struct comedi_device *dev, · 11 unmodified lines
11811180 s->busy = file;
11821181
11831182 /* make sure channel/gain list isn't too long */
1184− if (user_cmd.chanlist_len > s->len_chanlist) {
1183+ if (cmd.chanlist_len > s->len_chanlist) {
11851184 DPRINTK("channel/gain list too long %u > %d\n",
1186− user_cmd.chanlist_len, s->len_chanlist);
1185+ cmd.chanlist_len, s->len_chanlist);
11871186 ret = -EINVAL;
11881187 goto cleanup;
11891188 }
11901189
11911190 /* make sure channel/gain list isn't too short */
1192− if (user_cmd.chanlist_len < 1) {
1191+ if (cmd.chanlist_len < 1) {
11931192 DPRINTK("channel/gain list too short %u < 1\n",
1194− user_cmd.chanlist_len);
1193+ cmd.chanlist_len);
11951194 ret = -EINVAL;
11961195 goto cleanup;
11971196 }
11981197
1199− kfree(async->cmd.chanlist);
1200− async->cmd = user_cmd;
1198+ async->cmd = cmd;
12011199 async->cmd.data = NULL;
12021200 /* load channel/gain list */
12031201 async->cmd.chanlist =
@@ -1208,7 +1206,7 @@ static int do_cmd_ioctl(struct comedi_device *dev, · 4 unmodified lines
12081206 goto cleanup;
12091207 }
12101208
1211− if (copy_from_user(async->cmd.chanlist, user_cmd.chanlist,
1209+ if (copy_from_user(async->cmd.chanlist, user_chanlist,
12121210 async->cmd.chanlist_len * sizeof(int))) {
12131211 DPRINTK("fault reading chanlist\n");
12141212 ret = -EFAULT;
@@ -1228,11 +1226,11 @@ static int do_cmd_ioctl(struct comedi_device *dev, · 13 unmodified lines
12281226
12291227 if (async->cmd.flags & TRIG_BOGUS || ret) {
12301228 DPRINTK("test returned %d\n", ret);
1231− user_cmd = async->cmd;
1229+ cmd = async->cmd;
12321230 /* restore chanlist pointer before copying back */
1233− user_cmd.chanlist = chanlist_saver;
1234− user_cmd.data = NULL;
1235− if (copy_to_user(cmd, &user_cmd, sizeof(struct comedi_cmd))) {
1231+ cmd.chanlist = (unsigned int __force *)user_chanlist;
1232+ cmd.data = NULL;
1233+ if (copy_to_user(arg, &cmd, sizeof(struct comedi_cmd))) {
12361234 DPRINTK("fault writing cmd\n");
12371235 ret = -EFAULT;
12381236 goto cleanup;
@@ -1285,77 +1283,77 @@ cleanup: · 46 unmodified lines
12851283 static int do_cmdtest_ioctl(struct comedi_device *dev,
12861284 struct comedi_cmd __user *arg, void *file)
12871285 {
1288− struct comedi_cmd user_cmd;
1286+ struct comedi_cmd cmd;
12891287 struct comedi_subdevice *s;
12901288 int ret = 0;
12911289 unsigned int *chanlist = NULL;
1292− unsigned int __user *chanlist_saver = NULL;
1290+ unsigned int __user *user_chanlist;
12931291
1294− if (copy_from_user(&user_cmd, arg, sizeof(struct comedi_cmd))) {
1292+ if (copy_from_user(&cmd, arg, sizeof(struct comedi_cmd))) {
12951293 DPRINTK("bad cmd address\n");
12961294 return -EFAULT;
12971295 }
12981296 /* save user's chanlist pointer so it can be restored later */
1299− chanlist_saver = user_cmd.chanlist;
1297+ user_chanlist = (unsigned int __user *)cmd.chanlist;
13001298
1301− if (user_cmd.subdev >= dev->n_subdevices) {
1302− DPRINTK("%d no such subdevice\n", user_cmd.subdev);
1299+ if (cmd.subdev >= dev->n_subdevices) {
1300+ DPRINTK("%d no such subdevice\n", cmd.subdev);
13031301 return -ENODEV;
13041302 }
13051303
1306− s = dev->subdevices + user_cmd.subdev;
1304+ s = &dev->subdevices[cmd.subdev];
13071305 if (s->type == COMEDI_SUBD_UNUSED) {
1308− DPRINTK("%d not valid subdevice\n", user_cmd.subdev);
1306+ DPRINTK("%d not valid subdevice\n", cmd.subdev);
13091307 return -EIO;
13101308 }
13111309
13121310 if (!s->do_cmd || !s->do_cmdtest) {
13131311 DPRINTK("subdevice %i does not support commands\n",
1314− user_cmd.subdev);
1312+ cmd.subdev);
13151313 return -EIO;
13161314 }
13171315
13181316 /* make sure channel/gain list isn't too long */
1319− if (user_cmd.chanlist_len > s->len_chanlist) {
1317+ if (cmd.chanlist_len > s->len_chanlist) {
13201318 DPRINTK("channel/gain list too long %d > %d\n",
1321− user_cmd.chanlist_len, s->len_chanlist);
1319+ cmd.chanlist_len, s->len_chanlist);
13221320 ret = -EINVAL;
13231321 goto cleanup;
13241322 }
13251323
13261324 /* load channel/gain list */
1327− if (user_cmd.chanlist) {
1325+ if (cmd.chanlist) {
13281326 chanlist =
1329− kmalloc(user_cmd.chanlist_len * sizeof(int), GFP_KERNEL);
1327+ kmalloc(cmd.chanlist_len * sizeof(int), GFP_KERNEL);
13301328 if (!chanlist) {
13311329 DPRINTK("allocation failed\n");
13321330 ret = -ENOMEM;
13331331 goto cleanup;
13341332 }
13351333
1336− if (copy_from_user(chanlist, user_cmd.chanlist,
1337− user_cmd.chanlist_len * sizeof(int))) {
1334+ if (copy_from_user(chanlist, user_chanlist,
1335+ cmd.chanlist_len * sizeof(int))) {
13381336 DPRINTK("fault reading chanlist\n");
13391337 ret = -EFAULT;
13401338 goto cleanup;
13411339 }
13421340
13431341 /* make sure each element in channel/gain list is valid */
1344− ret = comedi_check_chanlist(s, user_cmd.chanlist_len, chanlist);
1342+ ret = comedi_check_chanlist(s, cmd.chanlist_len, chanlist);
13451343 if (ret < 0) {
13461344 DPRINTK("bad chanlist\n");
13471345 goto cleanup;
13481346 }
13491347
1350− user_cmd.chanlist = chanlist;
1348+ cmd.chanlist = chanlist;
13511349 }
13521350
1353− ret = s->do_cmdtest(dev, s, &user_cmd);
1351+ ret = s->do_cmdtest(dev, s, &cmd);
13541352
13551353 /* restore chanlist pointer before copying back */
1356− user_cmd.chanlist = chanlist_saver;
1354+ cmd.chanlist = (unsigned int __force *)user_chanlist;
13571355
1358− if (copy_to_user(arg, &user_cmd, sizeof(struct comedi_cmd))) {
1356+ if (copy_to_user(arg, &cmd, sizeof(struct comedi_cmd))) {
13591357 DPRINTK("bad cmd address\n");
13601358 ret = -EFAULT;
13611359 goto cleanup;
@@ -1390,7 +1388,7 @@ static int do_lock_ioctl(struct comedi_device *dev, unsigned int arg, · 28 unmodified lines
13901388
13911389 if (arg >= dev->n_subdevices)
13921390 return -EINVAL;
1393− s = dev->subdevices + arg;
1391+ s = &dev->subdevices[arg];
13941392
13951393 spin_lock_irqsave(&s->spin_lock, flags);
13961394 if (s->busy || s->lock)
@@ -1433,7 +1431,7 @@ static int do_unlock_ioctl(struct comedi_device *dev, unsigned int arg, · 36 unmodified lines
14331431
14341432 if (arg >= dev->n_subdevices)
14351433 return -EINVAL;
1436− s = dev->subdevices + arg;
1434+ s = &dev->subdevices[arg];
14371435
14381436 if (s->busy)
14391437 return -EBUSY;
@@ -1474,7 +1472,7 @@ static int do_cancel_ioctl(struct comedi_device *dev, unsigned int arg, · 34 unmodified lines
14741472
14751473 if (arg >= dev->n_subdevices)
14761474 return -EINVAL;
1477− s = dev->subdevices + arg;
1475+ s = &dev->subdevices[arg];
14781476 if (s->async == NULL)
14791477 return -EINVAL;
14801478
@@ -1511,7 +1509,7 @@ static int do_poll_ioctl(struct comedi_device *dev, unsigned int arg, · 30 unmodified lines
15111509
15121510 if (arg >= dev->n_subdevices)
15131511 return -EINVAL;
1514− s = dev->subdevices + arg;
1512+ s = &dev->subdevices[arg];
15151513
15161514 if (s->lock && s->lock != file)
15171515 return -EACCES;
@@ -2025,7 +2023,8 @@ done: · 507 unmodified lines
20252023 /*
20262024 This function restores a subdevice to an idle state.
20272025 */
2028−void do_become_nonbusy(struct comedi_device *dev, struct comedi_subdevice *s)
2026+static void do_become_nonbusy(struct comedi_device *dev,
2027+ struct comedi_subdevice *s)
20292028 {
20302029 struct comedi_async *async = s->async;
20312030
@@ -2033,9 +2032,11 @@ void do_become_nonbusy(struct comedi_device *dev, struct comedi_subdevice *s) · 1 unmodified line
20332032 if (async) {
20342033 comedi_reset_async_buf(async);
20352034 async->inttrig = NULL;
2035+ kfree(async->cmd.chanlist);
2036+ async->cmd.chanlist = NULL;
20362037 } else {
2037− printk(KERN_ERR
2038− "BUG: (?) do_become_nonbusy called with async=0\n");
2038+ dev_err(dev->class_dev,
2039+ "BUG: (?) do_become_nonbusy called with async=NULL\n");
20392040 }
20402041
20412042 s->busy = NULL;
@@ -2140,7 +2141,7 @@ static int comedi_close(struct inode *inode, struct file *file) · 98 unmodified lines
21402141
21412142 if (dev->subdevices) {
21422143 for (i = 0; i < dev->n_subdevices; i++) {
2143− s = dev->subdevices + i;
2144+ s = &dev->subdevices[i];
21442145
21452146 if (s->busy == file)
21462147 do_cancel(dev, s);
@@ -2211,14 +2212,12 @@ static int __init comedi_init(void) · 64 unmodified lines
22112212 int i;
22122213 int retval;
22132214
2214− printk(KERN_INFO "comedi: version " COMEDI_RELEASE
2215− " - http://www.comedi.org\n");
2215+ pr_info("comedi: version " COMEDI_RELEASE " - http://www.comedi.org\n");
22162216
22172217 if (comedi_num_legacy_minors < 0 ||
22182218 comedi_num_legacy_minors > COMEDI_NUM_BOARD_MINORS) {
2219− printk(KERN_ERR "comedi: error: invalid value for module "
2220− "parameter \"comedi_num_legacy_minors\". Valid values "
2221− "are 0 through %i.\n", COMEDI_NUM_BOARD_MINORS);
2219+ pr_err("comedi: error: invalid value for module parameter \"comedi_num_legacy_minors\". Valid values are 0 through %i.\n",
2220+ COMEDI_NUM_BOARD_MINORS);
22222221 return -EINVAL;
22232222 }
22242223
@@ -2247,7 +2246,7 @@ static int __init comedi_init(void) · 22 unmodified lines
22472246 }
22482247 comedi_class = class_create(THIS_MODULE, "comedi");
22492248 if (IS_ERR(comedi_class)) {
2250− printk(KERN_ERR "comedi: failed to create class");
2249+ pr_err("comedi: failed to create class\n");
22512250 cdev_del(&comedi_cdev);
22522251 unregister_chrdev_region(MKDEV(COMEDI_MAJOR, 0),
22532252 COMEDI_NUM_MINORS);
@@ -2295,8 +2294,7 @@ module_exit(comedi_cleanup); · 41 unmodified lines
22952294
22962295 void comedi_error(const struct comedi_device *dev, const char *s)
22972296 {
2298− printk(KERN_ERR "comedi%d: %s: %s\n", dev->minor,
2299− dev->driver->driver_name, s);
2297+ dev_err(dev->class_dev, "%s: %s\n", dev->driver->driver_name, s);
23002298 }
23012299 EXPORT_SYMBOL(comedi_error);
23022300
@@ -2364,7 +2362,7 @@ static int is_device_busy(struct comedi_device *dev) · 61 unmodified lines
23642362 return 0;
23652363
23662364 for (i = 0; i < dev->n_subdevices; i++) {
2367− s = dev->subdevices + i;
2365+ s = &dev->subdevices[i];
23682366 if (s->busy)
23692367 return 1;
23702368 if (s->async && s->async->mmap_count)
@@ -2420,9 +2418,7 @@ int comedi_alloc_board_minor(struct device *hardware_device) · 49 unmodified lines
24202418 comedi_device_cleanup(info->device);
24212419 kfree(info->device);
24222420 kfree(info);
2423− printk(KERN_ERR
2424− "comedi: error: "
2425− "ran out of minor numbers for board device files.\n");
2421+ pr_err("comedi: error: ran out of minor numbers for board device files.\n");
24262422 return -EBUSY;
24272423 }
24282424 info->device->minor = i;
@@ -2499,9 +2495,7 @@ int comedi_alloc_subdevice_minor(struct comedi_device *dev, · 70 unmodified lines
24992495 spin_unlock(&comedi_file_info_table_lock);
25002496 if (i == COMEDI_NUM_MINORS) {
25012497 kfree(info);
2502− printk(KERN_ERR
2503− "comedi: error: "
2504− "ran out of minor numbers for board device files.\n");
2498+ pr_err("comedi: error: ran out of minor numbers for board device files.\n");
25052499 return -EBUSY;
25062500 }
25072501 s->minor = i;
drivers/staging/comedi/comedidev.h+1−1
@@ -46,7 +46,7 @@ · 45 unmodified lines
4646
4747 #define DPRINTK(format, args...) do { \
4848 if (comedi_debug) \
49− printk(KERN_DEBUG "comedi: " format , ## args); \
49+ pr_debug("comedi: " format, ## args); \
5050 } while (0)
5151
5252 #define COMEDI_VERSION(a, b, c) (((a) << 16) + ((b) << 8) + (c))
drivers/staging/comedi/drivers.c+45−37
@@ -71,7 +71,7 @@ int comedi_alloc_subdevices(struct comedi_device *dev, int num_subdevices) · 70 unmodified lines
7171 dev->n_subdevices = num_subdevices;
7272
7373 for (i = 0; i < num_subdevices; ++i) {
74− s = dev->subdevices + i;
74+ s = &dev->subdevices[i];
7575 s->device = dev;
7676 s->async_dma_dir = DMA_NONE;
7777 spin_lock_init(&s->spin_lock);
@@ -88,7 +88,7 @@ static void cleanup_device(struct comedi_device *dev) · 10 unmodified lines
8888
8989 if (dev->subdevices) {
9090 for (i = 0; i < dev->n_subdevices; i++) {
91− s = dev->subdevices + i;
91+ s = &dev->subdevices[i];
9292 comedi_free_subdevice_minor(s);
9393 if (s->async) {
9494 comedi_buf_alloc(dev, s, 0);
@@ -119,8 +119,8 @@ static void __comedi_device_detach(struct comedi_device *dev) · 24 unmodified lines
119119 if (dev->driver)
120120 dev->driver->detach(dev);
121121 else
122− printk(KERN_WARNING
123− "BUG: dev->driver=NULL in comedi_device_detach()\n");
122+ dev_warn(dev->class_dev,
123+ "BUG: dev->driver=NULL in comedi_device_detach()\n");
124124 cleanup_device(dev);
125125 }
126126
@@ -142,8 +142,7 @@ static int comedi_device_postconfig(struct comedi_device *dev) · 15 unmodified lines
142142 return ret;
143143 }
144144 if (!dev->board_name) {
145− printk(KERN_WARNING "BUG: dev->board_name=<%p>\n",
146− dev->board_name);
145+ dev_warn(dev->class_dev, "BUG: dev->board_name=NULL\n");
147146 dev->board_name = "BUG";
148147 }
149148 smp_wmb();
@@ -160,10 +159,8 @@ int comedi_device_attach(struct comedi_device *dev, struct comedi_devconfig *it) · 10 unmodified lines
160159 return -EBUSY;
161160
162161 for (driv = comedi_drivers; driv; driv = driv->next) {
163− if (!try_module_get(driv->module)) {
164− printk(KERN_INFO "comedi: failed to increment module count, skipping\n");
162+ if (!try_module_get(driv->module))
165163 continue;
166− }
167164 if (driv->num_names) {
168165 dev->board_ptr = comedi_recognize(driv, it->board_name);
169166 if (dev->board_ptr)
@@ -176,16 +173,21 @@ int comedi_device_attach(struct comedi_device *dev, struct comedi_devconfig *it) · 6 unmodified lines
176173 /* recognize has failed if we get here */
177174 /* report valid board names before returning error */
178175 for (driv = comedi_drivers; driv; driv = driv->next) {
179− if (!try_module_get(driv->module)) {
180− printk(KERN_INFO
181− "comedi: failed to increment module count\n");
176+ if (!try_module_get(driv->module))
182177 continue;
183− }
184178 comedi_report_boards(driv);
185179 module_put(driv->module);
186180 }
187181 return -EIO;
188182 }
183+ if (driv->attach == NULL) {
184+ /* driver does not support manual configuration */
185+ dev_warn(dev->class_dev,
186+ "driver '%s' does not support attach using comedi_config\n",
187+ driv->driver_name);
188+ module_put(driv->module);
189+ return -ENOSYS;
190+ }
189191 /* initialize dev->driver here so
190192 * comedi_error() can be called from attach */
191193 dev->driver = driv;
@@ -225,8 +227,9 @@ int comedi_driver_unregister(struct comedi_driver *driver) · 33 unmodified lines
225227 mutex_lock(&dev->mutex);
226228 if (dev->attached && dev->driver == driver) {
227229 if (dev->use_count)
228− printk(KERN_WARNING "BUG! detaching device with use_count=%d\n",
229− dev->use_count);
230+ dev_warn(dev->class_dev,
231+ "BUG! detaching device with use_count=%d\n",
232+ dev->use_count);
230233 comedi_device_detach(dev);
231234 }
232235 mutex_unlock(&dev->mutex);
@@ -255,7 +258,7 @@ static int postconfig(struct comedi_device *dev) · 22 unmodified lines
255258 int ret;
256259
257260 for (i = 0; i < dev->n_subdevices; i++) {
258− s = dev->subdevices + i;
261+ s = &dev->subdevices[i];
259262
260263 if (s->type == COMEDI_SUBD_UNUSED)
261264 continue;
@@ -273,8 +276,8 @@ static int postconfig(struct comedi_device *dev) · 11 unmodified lines
273276 async =
274277 kzalloc(sizeof(struct comedi_async), GFP_KERNEL);
275278 if (async == NULL) {
276− printk(KERN_INFO
277− "failed to allocate async struct\n");
279+ dev_warn(dev->class_dev,
280+ "failed to allocate async struct\n");
278281 return -ENOMEM;
279282 }
280283 init_waitqueue_head(&async->wait_head);
@@ -290,7 +293,8 @@ static int postconfig(struct comedi_device *dev) · 9 unmodified lines
290293 async->prealloc_buf = NULL;
291294 async->prealloc_bufsz = 0;
292295 if (comedi_buf_alloc(dev, s, buf_size) < 0) {
293− printk(KERN_INFO "Buffer allocation failed\n");
296+ dev_warn(dev->class_dev,
297+ "Buffer allocation failed\n");
294298 return -ENOMEM;
295299 }
296300 if (s->buf_change) {
@@ -370,17 +374,17 @@ static void comedi_report_boards(struct comedi_driver *driv) · 73 unmodified lines
370374 unsigned int i;
371375 const char *const *name_ptr;
372376
373− printk(KERN_INFO "comedi: valid board names for %s driver are:\n",
374− driv->driver_name);
377+ pr_info("comedi: valid board names for %s driver are:\n",
378+ driv->driver_name);
375379
376380 name_ptr = driv->board_name;
377381 for (i = 0; i < driv->num_names; i++) {
378− printk(KERN_INFO " %s\n", *name_ptr);
382+ pr_info(" %s\n", *name_ptr);
379383 name_ptr = (const char **)((char *)name_ptr + driv->offset);
380384 }
381385
382386 if (driv->num_names == 0)
383− printk(KERN_INFO " %s\n", driv->driver_name);
387+ pr_info(" %s\n", driv->driver_name);
384388 }
385389
386390 static int poll_invalid(struct comedi_device *dev, struct comedi_subdevice *s)
@@ -411,7 +415,6 @@ static int insn_rw_emulate_bits(struct comedi_device *dev, · 24 unmodified lines
411415 new_insn.insn = INSN_BITS;
412416 new_insn.chanspec = base_bitfield_channel;
413417 new_insn.n = 2;
414− new_insn.data = new_data;
415418 new_insn.subdev = insn->subdev;
416419
417420 if (insn->insn == INSN_WRITE) {
@@ -584,9 +587,9 @@ static unsigned int comedi_buf_munge(struct comedi_async *async, · 166 unmodified lines
584587
585588 block_size = num_bytes - count;
586589 if (block_size < 0) {
587− printk(KERN_WARNING
588− "%s: %s: bug! block_size is negative\n",
589− __FILE__, __func__);
590+ dev_warn(s->device->class_dev,
591+ "%s: %s: bug! block_size is negative\n",
592+ __FILE__, __func__);
590593 break;
591594 }
592595 if ((int)(async->munge_ptr + block_size -
@@ -667,7 +670,8 @@ unsigned comedi_buf_write_free(struct comedi_async *async, unsigned int nbytes) · 74 unmodified lines
667670 {
668671 if ((int)(async->buf_write_count + nbytes -
669672 async->buf_write_alloc_count) > 0) {
670− printk(KERN_INFO "comedi: attempted to write-free more bytes than have been write-allocated.\n");
673+ dev_info(async->subdevice->device->class_dev,
674+ "attempted to write-free more bytes than have been write-allocated.\n");
671675 nbytes = async->buf_write_alloc_count - async->buf_write_count;
672676 }
673677 async->buf_write_count += nbytes;
@@ -703,8 +707,8 @@ unsigned comedi_buf_read_free(struct comedi_async *async, unsigned int nbytes) · 29 unmodified lines
703707 smp_mb();
704708 if ((int)(async->buf_read_count + nbytes -
705709 async->buf_read_alloc_count) > 0) {
706− printk(KERN_INFO
707− "comedi: attempted to read-free more bytes than have been read-allocated.\n");
710+ dev_info(async->subdevice->device->class_dev,
711+ "attempted to read-free more bytes than have been read-allocated.\n");
708712 nbytes = async->buf_read_alloc_count - async->buf_read_count;
709713 }
710714 async->buf_read_count += nbytes;
@@ -853,10 +857,9 @@ comedi_auto_config_helper(struct device *hardware_device, · 142 unmodified lines
853857 mutex_lock(&comedi_dev->mutex);
854858 if (comedi_dev->attached)
855859 ret = -EBUSY;
856− else if (!try_module_get(driver->module)) {
857− printk(KERN_INFO "comedi: failed to increment module count\n");
860+ else if (!try_module_get(driver->module))
858861 ret = -EIO;
859− } else {
862+ else {
860863 /* set comedi_dev->driver here for attach wrapper */
861864 comedi_dev->driver = driver;
862865 ret = (*attach_wrapper)(comedi_dev, context);
@@ -884,14 +887,19 @@ static int comedi_auto_config_wrapper(struct comedi_device *dev, void *context) · 21 unmodified lines
884887 * has already been copied to it->board_name */
885888 dev->board_ptr = comedi_recognize(driv, it->board_name);
886889 if (dev->board_ptr == NULL) {
887− printk(KERN_WARNING
888− "comedi: auto config failed to find board entry"
889− " '%s' for driver '%s'\n", it->board_name,
890− driv->driver_name);
890+ dev_warn(dev->class_dev,
891+ "auto config failed to find board entry '%s' for driver '%s'\n",
892+ it->board_name, driv->driver_name);
891893 comedi_report_boards(driv);
892894 return -EINVAL;
893895 }
894896 }
897+ if (!driv->attach) {
898+ dev_warn(dev->class_dev,
899+ "BUG! driver '%s' using old-style auto config but has no attach handler\n",
900+ driv->driver_name);
901+ return -EINVAL;
902+ }
895903 return driv->attach(dev, it);
896904 }
897905
drivers/staging/comedi/drivers/8253.h+9−6
@@ -262,8 +262,10 @@ static inline int i8254_load(unsigned long base_address, unsigned int regshift, · 261 unmodified lines
262262 return 0;
263263 }
264264
265−static inline int i8254_mm_load(void *base_address, unsigned int regshift,
266− unsigned int counter_number, unsigned int count,
265+static inline int i8254_mm_load(void __iomem *base_address,
266+ unsigned int regshift,
267+ unsigned int counter_number,
268+ unsigned int count,
267269 unsigned int mode)
268270 {
269271 unsigned int byte;
@@ -311,7 +313,8 @@ static inline int i8254_read(unsigned long base_address, unsigned int regshift, · 41 unmodified lines
311313 return ret;
312314 }
313315
314−static inline int i8254_mm_read(void *base_address, unsigned int regshift,
316+static inline int i8254_mm_read(void __iomem *base_address,
317+ unsigned int regshift,
315318 unsigned int counter_number)
316319 {
317320 unsigned int byte;
@@ -348,7 +351,7 @@ static inline void i8254_write(unsigned long base_address, · 30 unmodified lines
348351 outb(byte, base_address + (counter_number << regshift));
349352 }
350353
351−static inline void i8254_mm_write(void *base_address,
354+static inline void i8254_mm_write(void __iomem *base_address,
352355 unsigned int regshift,
353356 unsigned int counter_number,
354357 unsigned int count)
@@ -390,7 +393,7 @@ static inline int i8254_set_mode(unsigned long base_address, · 35 unmodified lines
390393 return 0;
391394 }
392395
393−static inline int i8254_mm_set_mode(void *base_address,
396+static inline int i8254_mm_set_mode(void __iomem *base_address,
394397 unsigned int regshift,
395398 unsigned int counter_number,
396399 unsigned int mode)
@@ -419,7 +422,7 @@ static inline int i8254_status(unsigned long base_address, · 22 unmodified lines
419422 return inb(base_address + (counter_number << regshift));
420423 }
421424
422−static inline int i8254_mm_status(void *base_address,
425+static inline int i8254_mm_status(void __iomem *base_address,
423426 unsigned int regshift,
424427 unsigned int counter_number)
425428 {
drivers/staging/comedi/drivers/8255.c+12−29
@@ -82,6 +82,8 @@ I/O port base address can be found in the output of 'lspci -v'. · 81 unmodified lines
8282
8383 #include <linux/ioport.h>
8484 #include <linux/slab.h>
85+
86+#include "comedi_fc.h"
8587 #include "8255.h"
8688
8789 #define _8255_SIZE 4
@@ -229,39 +231,20 @@ static int subdev_8255_cmdtest(struct comedi_device *dev, · 141 unmodified lines
229231 struct comedi_cmd *cmd)
230232 {
231233 int err = 0;
232− unsigned int tmp;
233−
234− /* step 1 */
235−
236− tmp = cmd->start_src;
237− cmd->start_src &= TRIG_NOW;
238− if (!cmd->start_src || tmp != cmd->start_src)
239− err++;
240−
241− tmp = cmd->scan_begin_src;
242− cmd->scan_begin_src &= TRIG_EXT;
243− if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src)
244− err++;
245234
246− tmp = cmd->convert_src;
247− cmd->convert_src &= TRIG_FOLLOW;
248− if (!cmd->convert_src || tmp != cmd->convert_src)
249− err++;
235+ /* Step 1 : check if triggers are trivially valid */
250236
251− tmp = cmd->scan_end_src;
252− cmd->scan_end_src &= TRIG_COUNT;
253− if (!cmd->scan_end_src || tmp != cmd->scan_end_src)
254− err++;
255−
256− tmp = cmd->stop_src;
257− cmd->stop_src &= TRIG_NONE;
258− if (!cmd->stop_src || tmp != cmd->stop_src)
259− err++;
237+ err |= cfc_check_trigger_src(&cmd->start_src, TRIG_NOW);
238+ err |= cfc_check_trigger_src(&cmd->scan_begin_src, TRIG_EXT);
239+ err |= cfc_check_trigger_src(&cmd->convert_src, TRIG_FOLLOW);
240+ err |= cfc_check_trigger_src(&cmd->scan_end_src, TRIG_COUNT);
241+ err |= cfc_check_trigger_src(&cmd->stop_src, TRIG_NONE);
260242
261243 if (err)
262244 return 1;
263245
264− /* step 2 */
246+ /* Step 2a : make sure trigger sources are unique */
247+ /* Step 2b : and mutually compatible */
265248
266249 if (err)
267250 return 2;
@@ -403,7 +386,7 @@ static int dev_8255_attach(struct comedi_device *dev, · 135 unmodified lines
403386 return ret;
404387
405388 for (i = 0; i < dev->n_subdevices; i++) {
406− s = dev->subdevices + i;
389+ s = &dev->subdevices[i];
407390 iobase = it->options[i];
408391
409392 if (!request_region(iobase, _8255_SIZE, "8255")) {
@@ -429,7 +412,7 @@ static void dev_8255_detach(struct comedi_device *dev) · 19 unmodified lines
429412 int i;
430413
431414 for (i = 0; i < dev->n_subdevices; i++) {
432− s = dev->subdevices + i;
415+ s = &dev->subdevices[i];
433416 if (s->type != COMEDI_SUBD_UNUSED) {
434417 spriv = s->private;
435418 release_region(spriv->iobase, _8255_SIZE);
drivers/staging/comedi/drivers/8255_pci.c+353−0
@@ -0,0 +1,353 @@
1+/*
2+ * COMEDI driver for generic PCI based 8255 digital i/o boards
3+ * Copyright (C) 2012 H Hartley Sweeten <hsweeten@visionengravers.com>
4+ *
5+ * Based on the tested adl_pci7296 driver written by:
6+ * Jon Grierson <jd@renko.co.uk>
7+ * and the experimental cb_pcidio driver written by:
8+ * Yoshiya Matsuzaka
9+ *
10+ * COMEDI - Linux Control and Measurement Device Interface
11+ * Copyright (C) 2000 David A. Schleef <ds@schleef.org>
12+ *
13+ * This program is free software; you can redistribute it and/or modify
14+ * it under the terms of the GNU General Public License as published by
15+ * the Free Software Foundation; either version 2 of the License, or
16+ * (at your option) any later version.
17+ *
18+ * This program is distributed in the hope that it will be useful,
19+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
20+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21+ * GNU General Public License for more details.
22+ *
23+ * You should have received a copy of the GNU General Public License
24+ * along with this program; if not, write to the Free Software
25+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
26+ */
27+
28+/*
29+Driver: 8255_pci
30+Description: Generic PCI based 8255 Digital I/O boards
31+Devices: (ADLink) PCI-7224 [adl_pci-7224] - 24 channels
32+ (ADLink) PCI-7248 [adl_pci-7248] - 48 channels
33+ (ADLink) PCI-7296 [adl_pci-7296] - 96 channels
34+ (Measurement Computing) PCI-DIO24 [cb_pci-dio24] - 24 channels
35+ (Measurement Computing) PCI-DIO24H [cb_pci-dio24h] - 24 channels
36+ (Measurement Computing) PCI-DIO48H [cb_pci-dio48h] - 48 channels
37+ (Measurement Computing) PCI-DIO96H [cb_pci-dio96h] - 96 channels
38+ (National Instruments) PCI-DIO-96 [ni_pci-dio-96] - 96 channels
39+ (National Instruments) PCI-DIO-96B [ni_pci-dio-96b] - 96 channels
40+ (National Instruments) PXI-6508 [ni_pxi-6508] - 96 channels
41+ (National Instruments) PCI-6503 [ni_pci-6503] - 24 channels
42+ (National Instruments) PCI-6503B [ni_pci-6503b] - 24 channels
43+ (National Instruments) PCI-6503X [ni_pci-6503x] - 24 channels
44+ (National Instruments) PXI-6503 [ni_pxi-6503] - 24 channels
45+Author: H Hartley Sweeten <hsweeten@visionengravers.com>
46+Updated: Wed, 12 Sep 2012 11:52:01 -0700
47+Status: untested
48+
49+Some of these boards also have an 8254 programmable timer/counter
50+chip. This chip is not currently supported by this driver.
51+
52+Interrupt support for these boards is also not currently supported.
53+
54+Configuration Options: not applicable, uses PCI auto config
55+*/
56+
57+#include "../comedidev.h"
58+
59+#include "8255.h"
60+
61+/*
62+ * PCI Device ID's supported by this driver
63+ */
64+#define PCI_DEVICE_ID_ADLINK_PCI7224 0x7224
65+#define PCI_DEVICE_ID_ADLINK_PCI7248 0x7248
66+#define PCI_DEVICE_ID_ADLINK_PCI7296 0x7296
67+
68+/* ComputerBoards is now known as Measurement Computing */
69+#define PCI_VENDOR_ID_CB 0x1307
70+
71+#define PCI_DEVICE_ID_CB_PCIDIO48H 0x000b
72+#define PCI_DEVICE_ID_CB_PCIDIO24H 0x0014
73+#define PCI_DEVICE_ID_CB_PCIDIO96H 0x0017
74+#define PCI_DEVICE_ID_CB_PCIDIO24 0x0028
75+
76+#define PCI_DEVICE_ID_NI_PCIDIO96 0x0160
77+#define PCI_DEVICE_ID_NI_PCI6503 0x0400
78+#define PCI_DEVICE_ID_NI_PCI6503B 0x1250
79+#define PCI_DEVICE_ID_NI_PXI6508 0x13c0
80+#define PCI_DEVICE_ID_NI_PCIDIO96B 0x1630
81+#define PCI_DEVICE_ID_NI_PCI6503X 0x17d0
82+#define PCI_DEVICE_ID_NI_PXI_6503 0x1800
83+
84+struct pci_8255_boardinfo {
85+ const char *name;
86+ unsigned short vendor;
87+ unsigned short device;
88+ int dio_badr;
89+ int is_mmio;
90+ int n_8255;
91+};
92+
93+static const struct pci_8255_boardinfo pci_8255_boards[] = {
94+ {
95+ .name = "adl_pci-7224",
96+ .vendor = PCI_VENDOR_ID_ADLINK,
97+ .device = PCI_DEVICE_ID_ADLINK_PCI7224,
98+ .dio_badr = 2,
99+ .n_8255 = 1,
100+ }, {
101+ .name = "adl_pci-7248",
102+ .vendor = PCI_VENDOR_ID_ADLINK,
103+ .device = PCI_DEVICE_ID_ADLINK_PCI7248,
104+ .dio_badr = 2,
105+ .n_8255 = 2,
106+ }, {
107+ .name = "adl_pci-7296",
108+ .vendor = PCI_VENDOR_ID_ADLINK,
109+ .device = PCI_DEVICE_ID_ADLINK_PCI7296,
110+ .dio_badr = 2,
111+ .n_8255 = 4,
112+ }, {
113+ .name = "cb_pci-dio24",
114+ .vendor = PCI_VENDOR_ID_CB,
115+ .device = PCI_DEVICE_ID_CB_PCIDIO24,
116+ .dio_badr = 2,
117+ .n_8255 = 1,
118+ }, {
119+ .name = "cb_pci-dio24h",
120+ .vendor = PCI_VENDOR_ID_CB,
121+ .device = PCI_DEVICE_ID_CB_PCIDIO24H,
122+ .dio_badr = 2,
123+ .n_8255 = 1,
124+ }, {
125+ .name = "cb_pci-dio48h",
126+ .vendor = PCI_VENDOR_ID_CB,
127+ .device = PCI_DEVICE_ID_CB_PCIDIO48H,
128+ .dio_badr = 1,
129+ .n_8255 = 2,
130+ }, {
131+ .name = "cb_pci-dio96h",
132+ .vendor = PCI_VENDOR_ID_CB,
133+ .device = PCI_DEVICE_ID_CB_PCIDIO96H,
134+ .dio_badr = 2,
135+ .n_8255 = 4,
136+ }, {
137+ .name = "ni_pci-dio-96",
138+ .vendor = PCI_VENDOR_ID_NI,
139+ .device = PCI_DEVICE_ID_NI_PCIDIO96,
140+ .dio_badr = 1,
141+ .is_mmio = 1,
142+ .n_8255 = 4,
143+ }, {
144+ .name = "ni_pci-dio-96b",
145+ .vendor = PCI_VENDOR_ID_NI,
146+ .device = PCI_DEVICE_ID_NI_PCIDIO96B,
147+ .dio_badr = 1,
148+ .is_mmio = 1,
149+ .n_8255 = 4,
150+ }, {
151+ .name = "ni_pxi-6508",
152+ .vendor = PCI_VENDOR_ID_NI,
153+ .device = PCI_DEVICE_ID_NI_PXI6508,
154+ .dio_badr = 1,
155+ .is_mmio = 1,
156+ .n_8255 = 4,
157+ }, {
158+ .name = "ni_pci-6503",
159+ .vendor = PCI_VENDOR_ID_NI,
160+ .device = PCI_DEVICE_ID_NI_PCI6503,
161+ .dio_badr = 1,
162+ .is_mmio = 1,
163+ .n_8255 = 1,
164+ }, {
165+ .name = "ni_pci-6503b",
166+ .vendor = PCI_VENDOR_ID_NI,
167+ .device = PCI_DEVICE_ID_NI_PCI6503B,
168+ .dio_badr = 1,
169+ .is_mmio = 1,
170+ .n_8255 = 1,
171+ }, {
172+ .name = "ni_pci-6503x",
173+ .vendor = PCI_VENDOR_ID_NI,
174+ .device = PCI_DEVICE_ID_NI_PCI6503X,
175+ .dio_badr = 1,
176+ .is_mmio = 1,
177+ .n_8255 = 1,
178+ }, {
179+ .name = "ni_pxi-6503",
180+ .vendor = PCI_VENDOR_ID_NI,
181+ .device = PCI_DEVICE_ID_NI_PXI_6503,
182+ .dio_badr = 1,
183+ .is_mmio = 1,
184+ .n_8255 = 1,
185+ },
186+};
187+
188+struct pci_8255_private {
189+ void __iomem *mmio_base;
190+};
191+
192+static int pci_8255_mmio(int dir, int port, int data, unsigned long iobase)
193+{
194+ void __iomem *mmio_base = (void __iomem *)iobase;
195+
196+ if (dir) {
197+ writeb(data, mmio_base + port);
198+ return 0;
199+ } else {
200+ return readb(mmio_base + port);
201+ }
202+}
203+
204+static const void *pci_8255_find_boardinfo(struct comedi_device *dev,
205+ struct pci_dev *pcidev)
206+{
207+ const struct pci_8255_boardinfo *board;
208+ int i;
209+
210+ for (i = 0; i < ARRAY_SIZE(pci_8255_boards); i++) {
211+ board = &pci_8255_boards[i];
212+ if (pcidev->vendor == board->vendor &&
213+ pcidev->device == board->device)
214+ return board;
215+ }
216+ return NULL;
217+}
218+
219+static int pci_8255_attach_pci(struct comedi_device *dev,
220+ struct pci_dev *pcidev)
221+{
222+ const struct pci_8255_boardinfo *board;
223+ struct pci_8255_private *devpriv;
224+ struct comedi_subdevice *s;
225+ resource_size_t iobase;
226+ unsigned long len;
227+ int ret;
228+ int i;
229+
230+ comedi_set_hw_dev(dev, &pcidev->dev);
231+
232+ board = pci_8255_find_boardinfo(dev, pcidev);
233+ if (!board)
234+ return -ENODEV;
235+ dev->board_ptr = board;
236+ dev->board_name = board->name;
237+
238+ ret = alloc_private(dev, sizeof(*devpriv));
239+ if (ret < 0)
240+ return ret;
241+ devpriv = dev->private;
242+
243+ ret = comedi_pci_enable(pcidev, dev->board_name);
244+ if (ret)
245+ return ret;
246+ iobase = pci_resource_start(pcidev, board->dio_badr);
247+ len = pci_resource_len(pcidev, board->dio_badr);
248+
249+ if (board->is_mmio) {
250+ devpriv->mmio_base = ioremap(iobase, len);
251+ if (!devpriv->mmio_base)
252+ return -ENOMEM;
253+ }
254+ dev->iobase = iobase;
255+
256+ /*
257+ * One, two, or four subdevices are setup by this driver depending
258+ * on the number of channels provided by the board. Each subdevice
259+ * has 24 channels supported by the 8255 module.
260+ */
261+ ret = comedi_alloc_subdevices(dev, board->n_8255);
262+ if (ret)
263+ return ret;
264+
265+ for (i = 0; i < board->n_8255; i++) {
266+ s = &dev->subdevices[i];
267+ if (board->is_mmio) {
268+ iobase = (unsigned long)(devpriv->mmio_base + (i * 4));
269+ ret = subdev_8255_init(dev, s, pci_8255_mmio, iobase);
270+ } else {
271+ iobase = dev->iobase + (i * 4);
272+ ret = subdev_8255_init(dev, s, NULL, iobase);
273+ }
274+ if (ret)
275+ return ret;
276+ }
277+
278+ dev_info(dev->class_dev, "%s attached (%d digital i/o channels)\n",
279+ dev->board_name, board->n_8255 * 24);
280+
281+ return 0;
282+}
283+
284+static void pci_8255_detach(struct comedi_device *dev)
285+{
286+ struct pci_dev *pcidev = comedi_to_pci_dev(dev);
287+ const struct pci_8255_boardinfo *board = comedi_board(dev);
288+ struct pci_8255_private *devpriv = dev->private;
289+ struct comedi_subdevice *s;
290+ int i;
291+
292+ if (dev->subdevices) {
293+ for (i = 0; i < board->n_8255; i++) {
294+ s = &dev->subdevices[i];
295+ subdev_8255_cleanup(dev, s);
296+ }
297+ }
298+ if (pcidev) {
299+ if (devpriv->mmio_base)
300+ iounmap(devpriv->mmio_base);
301+ if (dev->iobase)
302+ comedi_pci_disable(pcidev);
303+ }
304+}
305+
306+static struct comedi_driver pci_8255_driver = {
307+ .driver_name = "8255_pci",
308+ .module = THIS_MODULE,
309+ .attach_pci = pci_8255_attach_pci,
310+ .detach = pci_8255_detach,
311+};
312+
313+static int __devinit pci_8255_pci_probe(struct pci_dev *dev,
314+ const struct pci_device_id *ent)
315+{
316+ return comedi_pci_auto_config(dev, &pci_8255_driver);
317+}
318+
319+static void __devexit pci_8255_pci_remove(struct pci_dev *dev)
320+{
321+ comedi_pci_auto_unconfig(dev);
322+}
323+
324+static DEFINE_PCI_DEVICE_TABLE(pci_8255_pci_table) = {
325+ { PCI_DEVICE(PCI_VENDOR_ID_ADLINK, PCI_DEVICE_ID_ADLINK_PCI7224) },
326+ { PCI_DEVICE(PCI_VENDOR_ID_ADLINK, PCI_DEVICE_ID_ADLINK_PCI7248) },
327+ { PCI_DEVICE(PCI_VENDOR_ID_ADLINK, PCI_DEVICE_ID_ADLINK_PCI7296) },
328+ { PCI_DEVICE(PCI_VENDOR_ID_CB, PCI_DEVICE_ID_CB_PCIDIO24) },
329+ { PCI_DEVICE(PCI_VENDOR_ID_CB, PCI_DEVICE_ID_CB_PCIDIO24H) },
330+ { PCI_DEVICE(PCI_VENDOR_ID_CB, PCI_DEVICE_ID_CB_PCIDIO48H) },
331+ { PCI_DEVICE(PCI_VENDOR_ID_CB, PCI_DEVICE_ID_CB_PCIDIO96H) },
332+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PCIDIO96) },
333+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PCIDIO96B) },
334+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PXI6508) },
335+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PCI6503) },
336+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PCI6503B) },
337+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PCI6503X) },
338+ { PCI_DEVICE(PCI_VENDOR_ID_NI, PCI_DEVICE_ID_NI_PXI_6503) },
339+ { 0 }
340+};
341+MODULE_DEVICE_TABLE(pci, pci_8255_pci_table);
342+
343+static struct pci_driver pci_8255_pci_driver = {
344+ .name = "8255_pci",
345+ .id_table = pci_8255_pci_table,
346+ .probe = pci_8255_pci_probe,
347+ .remove = __devexit_p(pci_8255_pci_remove),
348+};
349+module_comedi_pci_driver(pci_8255_driver, pci_8255_pci_driver);
350+
351+MODULE_DESCRIPTION("COMEDI - Generic PCI based 8255 Digital I/O boards");
352+MODULE_AUTHOR("Comedi http://www.comedi.org");
353+MODULE_LICENSE("GPL");
drivers/staging/comedi/drivers/Makefile+2−4
@@ -55,6 +55,7 @@ obj-$(CONFIG_COMEDI_MULTIQ3) += multiq3.o · 54 unmodified lines
5555 obj-$(CONFIG_COMEDI_POC) += poc.o
5656
5757 # Comedi PCI drivers
58+obj-$(CONFIG_COMEDI_8255_PCI) += 8255_pci.o
5859 obj-$(CONFIG_COMEDI_ADDI_APCI_035) += addi_apci_035.o
5960 obj-$(CONFIG_COMEDI_ADDI_APCI_1032) += addi_apci_1032.o
6061 obj-$(CONFIG_COMEDI_ADDI_APCI_1500) += addi_apci_1500.o
@@ -69,9 +70,7 @@ obj-$(CONFIG_COMEDI_ADDI_APCI_3120) += addi_apci_3120.o · 8 unmodified lines
6970 obj-$(CONFIG_COMEDI_ADDI_APCI_3501) += addi_apci_3501.o
7071 obj-$(CONFIG_COMEDI_ADDI_APCI_3XXX) += addi_apci_3xxx.o
7172 obj-$(CONFIG_COMEDI_ADL_PCI6208) += adl_pci6208.o
72−obj-$(CONFIG_COMEDI_ADL_PCI7230) += adl_pci7230.o
73−obj-$(CONFIG_COMEDI_ADL_PCI7296) += adl_pci7296.o
74−obj-$(CONFIG_COMEDI_ADL_PCI7432) += adl_pci7432.o
73+obj-$(CONFIG_COMEDI_ADL_PCI7X3X) += adl_pci7x3x.o
7574 obj-$(CONFIG_COMEDI_ADL_PCI8164) += adl_pci8164.o
7675 obj-$(CONFIG_COMEDI_ADL_PCI9111) += adl_pci9111.o
7776 obj-$(CONFIG_COMEDI_ADL_PCI9118) += adl_pci9118.o
@@ -96,7 +95,6 @@ obj-$(CONFIG_COMEDI_KE_COUNTER) += ke_counter.o · 18 unmodified lines
9695 obj-$(CONFIG_COMEDI_CB_PCIDAS64) += cb_pcidas64.o
9796 obj-$(CONFIG_COMEDI_CB_PCIDAS) += cb_pcidas.o
9897 obj-$(CONFIG_COMEDI_CB_PCIDDA) += cb_pcidda.o
99−obj-$(CONFIG_COMEDI_CB_PCIDIO) += cb_pcidio.o
10098 obj-$(CONFIG_COMEDI_CB_PCIMDAS) += cb_pcimdas.o
10199 obj-$(CONFIG_COMEDI_CB_PCIMDDA) += cb_pcimdda.o
102100 obj-$(CONFIG_COMEDI_ME4000) += me4000.o
drivers/staging/comedi/drivers/acl7225b.c+3−3
@@ -81,7 +81,7 @@ static int acl7225b_attach(struct comedi_device *dev, · 80 unmodified lines
8181 if (ret)
8282 return ret;
8383
84− s = dev->subdevices + 0;
84+ s = &dev->subdevices[0];
8585 /* Relays outputs */
8686 s->type = COMEDI_SUBD_DO;
8787 s->subdev_flags = SDF_WRITABLE;
@@ -91,7 +91,7 @@ static int acl7225b_attach(struct comedi_device *dev, · 3 unmodified lines
9191 s->range_table = &range_digital;
9292 s->private = (void *)ACL7225_RIO_LO;
9393
94− s = dev->subdevices + 1;
94+ s = &dev->subdevices[1];
9595 /* Relays status */
9696 s->type = COMEDI_SUBD_DI;
9797 s->subdev_flags = SDF_READABLE;
@@ -101,7 +101,7 @@ static int acl7225b_attach(struct comedi_device *dev, · 3 unmodified lines
101101 s->range_table = &range_digital;
102102 s->private = (void *)ACL7225_RIO_LO;
103103
104− s = dev->subdevices + 2;
104+ s = &dev->subdevices[2];
105105 /* Isolated digital inputs */
106106 s->type = COMEDI_SUBD_DI;
107107 s->subdev_flags = SDF_READABLE;
drivers/staging/comedi/drivers/addi-data/addi_amcc_S5920.c+0−195
@@ -1,195 +0,0 @@
1−/**
2−@verbatim
3−
4−Copyright (C) 2004,2005 ADDI-DATA GmbH for the source code of this module.
5−
6− ADDI-DATA GmbH
7− Dieselstrasse 3
8− D-77833 Ottersweier
9− Tel: +19(0)7223/9493-0
10− Fax: +49(0)7223/9493-92
11− http://www.addi-data.com
12− info@addi-data.com
13−
14−This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
15−
16−This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
17−
18−You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19−
20−You should also find the complete GPL in the COPYING file accompanying this source code.
21−
22−@endverbatim
23−*/
24−/*
25− +-----------------------------------------------------------------------+
26− | (C) ADDI-DATA GmbH Dieselstraße 3 D-77833 Ottersweier |
27− +-----------------------------------------------------------------------+
28− | Tel : +49 (0) 7223/9493-0 | email : info@addi-data.com |
29− | Fax : +49 (0) 7223/9493-92 | Internet : http://www.addi-data.com |
30− +-------------------------------+---------------------------------------+
31− | Project : ADDI HEADER READ WRITER | Compiler : Visual C++ |
32− | Module name : S5920.cpp | Version : 6.0 |
33− +-------------------------------+---------------------------------------+
34− | Author : E. LIBS Date : 02/05/2002 |
35− +-----------------------------------------------------------------------+
36− | Description : DLL with the S5920 PCI Controller functions |
37− +-----------------------------------------------------------------------+
38− | UPDATE'S |
39− +-----------------------------------------------------------------------+
40− | Date | Author | Description of updates |
41− +----------+-----------+------------------------------------------------+
42− | 28/08/02 | LIBS Eric | Add return codes each time a function of the |
43− | | | Addi Library is called |
44− +-----------------------------------------------------------------------+
45− | 31/07/03 | KRAUTH J. | Changes for the MSX-Box |
46− +-----------------------------------------------------------------------+
47−*/
48−
49−#include "addi_amcc_S5920.h"
50−
51−/*+----------------------------------------------------------------------------+*/
52−/*| Function Name : int i_AddiHeaderRW_ReadEeprom |*/
53−/*| (int i_NbOfWordsToRead, |*/
54−/*| unsigned int dw_PCIBoardEepromAddress, |*/
55−/*| unsigned short w_EepromStartAddress, |*/
56−/*| unsigned short * pw_DataRead) |*/
57−/*+----------------------------------------------------------------------------+*/
58−/*| Task : Read word from the 5920 eeprom. |*/
59−/*+----------------------------------------------------------------------------+*/
60−/*| Input Parameters : int i_NbOfWordsToRead : Nbr. of word to read |*/
61−/*| unsigned int dw_PCIBoardEepromAddress : Address of the eeprom |*/
62−/*| unsigned short w_EepromStartAddress : Eeprom start address |*/
63−/*+----------------------------------------------------------------------------+*/
64−/*| Output Parameters : unsigned short * pw_DataRead : Read data |*/
65−/*+----------------------------------------------------------------------------+*/
66−/*| Return Value : - |*/
67−/*+----------------------------------------------------------------------------+*/
68−
69−int i_AddiHeaderRW_ReadEeprom(int i_NbOfWordsToRead,
70− unsigned int dw_PCIBoardEepromAddress,
71− unsigned short w_EepromStartAddress, unsigned short *pw_DataRead)
72−{
73− unsigned int dw_eeprom_busy = 0;
74− int i_Counter = 0;
75− int i_WordCounter;
76− int i;
77− unsigned char pb_ReadByte[1];
78− unsigned char b_ReadLowByte = 0;
79− unsigned char b_ReadHighByte = 0;
80− unsigned char b_SelectedAddressLow = 0;
81− unsigned char b_SelectedAddressHigh = 0;
82− unsigned short w_ReadWord = 0;
83−
84− for (i_WordCounter = 0; i_WordCounter < i_NbOfWordsToRead;
85− i_WordCounter++) {
86− do {
87− dw_eeprom_busy =
88− inl(dw_PCIBoardEepromAddress +
89− AMCC_OP_REG_MCSR);
90− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
91− } while (dw_eeprom_busy == EEPROM_BUSY);
92−
93− for (i_Counter = 0; i_Counter < 2; i_Counter++) {
94− b_SelectedAddressLow = (w_EepromStartAddress + i_Counter) % 256; /* Read the low 8 bit part */
95− b_SelectedAddressHigh = (w_EepromStartAddress + i_Counter) / 256; /* Read the high 8 bit part */
96−
97− /* Select the load low address mode */
98− outb(NVCMD_LOAD_LOW,
99− dw_PCIBoardEepromAddress + AMCC_OP_REG_MCSR +
100− 3);
101−
102− /* Wait on busy */
103− do {
104− dw_eeprom_busy =
105− inl(dw_PCIBoardEepromAddress +
106− AMCC_OP_REG_MCSR);
107− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
108− } while (dw_eeprom_busy == EEPROM_BUSY);
109−
110− /* Load the low address */
111− outb(b_SelectedAddressLow,
112− dw_PCIBoardEepromAddress + AMCC_OP_REG_MCSR +
113− 2);
114−
115− /* Wait on busy */
116− do {
117− dw_eeprom_busy =
118− inl(dw_PCIBoardEepromAddress +
119− AMCC_OP_REG_MCSR);
120− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
121− } while (dw_eeprom_busy == EEPROM_BUSY);
122−
123− /* Select the load high address mode */
124− outb(NVCMD_LOAD_HIGH,
125− dw_PCIBoardEepromAddress + AMCC_OP_REG_MCSR +
126− 3);
127−
128− /* Wait on busy */
129− do {
130− dw_eeprom_busy =
131− inl(dw_PCIBoardEepromAddress +
132− AMCC_OP_REG_MCSR);
133− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
134− } while (dw_eeprom_busy == EEPROM_BUSY);
135−
136− /* Load the high address */
137− outb(b_SelectedAddressHigh,
138− dw_PCIBoardEepromAddress + AMCC_OP_REG_MCSR +
139− 2);
140−
141− /* Wait on busy */
142− do {
143− dw_eeprom_busy =
144− inl(dw_PCIBoardEepromAddress +
145− AMCC_OP_REG_MCSR);
146− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
147− } while (dw_eeprom_busy == EEPROM_BUSY);
148−
149− /* Select the READ mode */
150− outb(NVCMD_BEGIN_READ,
151− dw_PCIBoardEepromAddress + AMCC_OP_REG_MCSR +
152− 3);
153−
154− /* Wait on busy */
155− do {
156− dw_eeprom_busy =
157− inl(dw_PCIBoardEepromAddress +
158− AMCC_OP_REG_MCSR);
159− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
160− } while (dw_eeprom_busy == EEPROM_BUSY);
161−
162− /* Read data into the EEPROM */
163− *pb_ReadByte =
164− inb(dw_PCIBoardEepromAddress +
165− AMCC_OP_REG_MCSR + 2);
166−
167− /* Wait on busy */
168− do {
169− dw_eeprom_busy =
170− inl(dw_PCIBoardEepromAddress +
171− AMCC_OP_REG_MCSR);
172− dw_eeprom_busy = dw_eeprom_busy & EEPROM_BUSY;
173− } while (dw_eeprom_busy == EEPROM_BUSY);
174−
175− /* Select the upper address part */
176− if (i_Counter == 0)
177− b_ReadLowByte = pb_ReadByte[0];
178− else
179− b_ReadHighByte = pb_ReadByte[0];
180−
181− /* Sleep */
182− msleep(1);
183−
184− }
185− w_ReadWord =
186− (b_ReadLowByte | (((unsigned short)b_ReadHighByte) *
187− 256));
188−
189− pw_DataRead[i_WordCounter] = w_ReadWord;
190−
191− w_EepromStartAddress += 2; /* to read the next word */
192−
193− } /* for (...) i_NbOfWordsToRead */
194− return 0;
195−}
drivers/staging/comedi/drivers/addi-data/addi_amcc_S5920.h+0−27
@@ -1,27 +0,0 @@
1−/*
2− * Copyright (C) 2004,2005 ADDI-DATA GmbH for the source code of this module.
3− *
4− * ADDI-DATA GmbH
5− * Dieselstrasse 3
6− * D-77833 Ottersweier
7− * Tel: +19(0)7223/9493-0
8− * Fax: +49(0)7223/9493-92
9− * http://www.addi-data.com
10− * info@addi-data.com
11− *
12− * This program is free software; you can redistribute it and/or modify it
13− * under the terms of the GNU General Public License as published by the Free
14− * Software Foundation; either version 2 of the License, or (at your option)
15− * any later version.
16− */
17−
18−#define AMCC_OP_REG_MCSR 0x3c
19−#define EEPROM_BUSY 0x80000000
20−#define NVCMD_LOAD_LOW (0x4 << 5) /* nvRam load low command */
21−#define NVCMD_LOAD_HIGH (0x5 << 5) /* nvRam load high command */
22−#define NVCMD_BEGIN_READ (0x7 << 5) /* nvRam begin read command */
23−#define NVCMD_BEGIN_WRITE (0x6 << 5) /* EEPROM begin write command */
24−
25−int i_AddiHeaderRW_ReadEeprom(int i_NbOfWordsToRead,
26− unsigned int dw_PCIBoardEepromAddress,
27− unsigned short w_EepromStartAddress, unsigned short *pw_DataRead);
drivers/staging/comedi/drivers/addi-data/addi_common.c+7−7
@@ -1669,7 +1669,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 1668 unmodified lines
16691669 return ret;
16701670
16711671 /* Allocate and Initialise AI Subdevice Structures */
1672− s = dev->subdevices + 0;
1672+ s = &dev->subdevices[0];
16731673 if ((devpriv->s_EeParameters.i_NbrAiChannel)
16741674 || (this_board->i_NbrAiChannelDiff)) {
16751675 dev->read_subdev = s;
@@ -1705,7 +1705,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 29 unmodified lines
17051705 }
17061706
17071707 /* Allocate and Initialise AO Subdevice Structures */
1708− s = dev->subdevices + 1;
1708+ s = &dev->subdevices[1];
17091709 if (devpriv->s_EeParameters.i_NbrAoChannel) {
17101710 s->type = COMEDI_SUBD_AO;
17111711 s->subdev_flags = SDF_WRITEABLE | SDF_GROUND | SDF_COMMON;
@@ -1720,7 +1720,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 8 unmodified lines
17201720 s->type = COMEDI_SUBD_UNUSED;
17211721 }
17221722 /* Allocate and Initialise DI Subdevice Structures */
1723− s = dev->subdevices + 2;
1723+ s = &dev->subdevices[2];
17241724 if (devpriv->s_EeParameters.i_NbrDiChannel) {
17251725 s->type = COMEDI_SUBD_DI;
17261726 s->subdev_flags = SDF_READABLE | SDF_GROUND | SDF_COMMON;
@@ -1738,7 +1738,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 11 unmodified lines
17381738 s->type = COMEDI_SUBD_UNUSED;
17391739 }
17401740 /* Allocate and Initialise DO Subdevice Structures */
1741− s = dev->subdevices + 3;
1741+ s = &dev->subdevices[3];
17421742 if (devpriv->s_EeParameters.i_NbrDoChannel) {
17431743 s->type = COMEDI_SUBD_DO;
17441744 s->subdev_flags =
@@ -1760,7 +1760,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 15 unmodified lines
17601760 }
17611761
17621762 /* Allocate and Initialise Timer Subdevice Structures */
1763− s = dev->subdevices + 4;
1763+ s = &dev->subdevices[4];
17641764 if (devpriv->s_EeParameters.i_Timer) {
17651765 s->type = COMEDI_SUBD_TIMER;
17661766 s->subdev_flags = SDF_WRITEABLE | SDF_GROUND | SDF_COMMON;
@@ -1778,7 +1778,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 11 unmodified lines
17781778 }
17791779
17801780 /* Allocate and Initialise TTL */
1781− s = dev->subdevices + 5;
1781+ s = &dev->subdevices[5];
17821782 if (this_board->i_NbrTTLChannel) {
17831783 s->type = COMEDI_SUBD_TTLIO;
17841784 s->subdev_flags =
@@ -1797,7 +1797,7 @@ static int i_ADDI_Attach(struct comedi_device *dev, struct comedi_devconfig *it) · 12 unmodified lines
17971797 }
17981798
17991799 /* EEPROM */
1800− s = dev->subdevices + 6;
1800+ s = &dev->subdevices[6];
18011801 if (this_board->i_PCIEeprom) {
18021802 s->type = COMEDI_SUBD_MEMORY;
18031803 s->subdev_flags = SDF_READABLE | SDF_INTERNAL;
drivers/staging/comedi/drivers/addi-data/amcc_s5933_58.h+0−453
@@ -1,453 +0,0 @@
1−/*
2− Modified by umesh on 16th may 2001
3− Modified by sarath on 22nd may 2001
4−*/
5−
6−/*
7− comedi/drivers/amcc_s5933_v_58.h
8−
9− Stuff for AMCC S5933 PCI Controller
10−
11− Author: Michal Dobes <majkl@tesnet.cz>
12−
13− Inspirated from general-purpose AMCC S5933 PCI Matchmaker driver
14− made by Andrea Cisternino <acister@pcape1.pi.infn.it>
15− and as result of espionage from MITE code made by David A. Schleef.
16− Thanks to AMCC for their on-line documentation and bus master DMA
17− example.
18−*/
19−
20−#ifndef _AMCC_S5933_H_
21−#define _AMCC_S5933_H_
22−
23−#include <linux/pci.h>
24−#include "../../comedidev.h"
25−
26−/***********Added by sarath for compatibility with APCI3120
27−
28−*************************/
29−
30−#define FIFO_ADVANCE_ON_BYTE_2 0x20000000 /* written on base0 */
31−
32−#define AMWEN_ENABLE 0x02 /* added for step 6 dma written on base2 */
33−#define A2P_FIFO_WRITE_ENABLE 0x01
34−
35−#define AGCSTS_TC_ENABLE 0x10000000 /* Added for transfer count enable bit */
36−
37−/* ADDON RELATED ADDITIONS */
38−/* Constant */
39−#define APCI3120_ENABLE_TRANSFER_ADD_ON_LOW 0x00
40−#define APCI3120_ENABLE_TRANSFER_ADD_ON_HIGH 0x1200
41−#define APCI3120_A2P_FIFO_MANAGEMENT 0x04000400L
42−#define APCI3120_AMWEN_ENABLE 0x02
43−#define APCI3120_A2P_FIFO_WRITE_ENABLE 0x01
44−#define APCI3120_FIFO_ADVANCE_ON_BYTE_2 0x20000000L
45−#define APCI3120_ENABLE_WRITE_TC_INT 0x00004000L
46−#define APCI3120_CLEAR_WRITE_TC_INT 0x00040000L
47−#define APCI3120_DISABLE_AMWEN_AND_A2P_FIFO_WRITE 0x0
48−#define APCI3120_DISABLE_BUS_MASTER_ADD_ON 0x0
49−#define APCI3120_DISABLE_BUS_MASTER_PCI 0x0
50−
51− /* ADD_ON ::: this needed since apci supports 16 bit interface to add on */
52−#define APCI3120_ADD_ON_AGCSTS_LOW 0x3C
53−#define APCI3120_ADD_ON_AGCSTS_HIGH APCI3120_ADD_ON_AGCSTS_LOW + 2
54−#define APCI3120_ADD_ON_MWAR_LOW 0x24
55−#define APCI3120_ADD_ON_MWAR_HIGH APCI3120_ADD_ON_MWAR_LOW + 2
56−#define APCI3120_ADD_ON_MWTC_LOW 0x058
57−#define APCI3120_ADD_ON_MWTC_HIGH APCI3120_ADD_ON_MWTC_LOW + 2
58−
59−/* AMCC */
60−#define APCI3120_AMCC_OP_MCSR 0x3C
61−#define APCI3120_AMCC_OP_REG_INTCSR 0x38
62−
63−/*******from here all upward definitions are added by sarath */
64−
65−/****************************************************************************/
66−/* AMCC Operation Register Offsets - PCI */
67−/****************************************************************************/
68−
69−#define AMCC_OP_REG_OMB1 0x00
70−#define AMCC_OP_REG_OMB2 0x04
71−#define AMCC_OP_REG_OMB3 0x08
72−#define AMCC_OP_REG_OMB4 0x0c
73−#define AMCC_OP_REG_IMB1 0x10
74−#define AMCC_OP_REG_IMB2 0x14
75−#define AMCC_OP_REG_IMB3 0x18
76−#define AMCC_OP_REG_IMB4 0x1c
77−#define AMCC_OP_REG_FIFO 0x20
78−#define AMCC_OP_REG_MWAR 0x24
79−#define AMCC_OP_REG_MWTC 0x28
80−#define AMCC_OP_REG_MRAR 0x2c
81−#define AMCC_OP_REG_MRTC 0x30
82−#define AMCC_OP_REG_MBEF 0x34
83−#define AMCC_OP_REG_INTCSR 0x38
84−#define AMCC_OP_REG_INTCSR_SRC (AMCC_OP_REG_INTCSR + 2) /* int source */
85−#define AMCC_OP_REG_INTCSR_FEC (AMCC_OP_REG_INTCSR + 3) /* FIFO ctrl */
86−#define AMCC_OP_REG_MCSR 0x3c
87−#define AMCC_OP_REG_MCSR_NVDATA (AMCC_OP_REG_MCSR + 2) /* Data in byte 2 */
88−#define AMCC_OP_REG_MCSR_NVCMD (AMCC_OP_REG_MCSR + 3) /* Command in byte 3 */
89−
90−#define AMCC_FIFO_DEPTH_DWORD 8
91−#define AMCC_FIFO_DEPTH_BYTES (8 * sizeof (u32))
92−
93−/****************************************************************************/
94−/* AMCC Operation Registers Size - PCI */
95−/****************************************************************************/
96−
97−#define AMCC_OP_REG_SIZE 64 /* in bytes */
98−
99−/****************************************************************************/
100−/* AMCC Operation Register Offsets - Add-on */
101−/****************************************************************************/
102−
103−#define AMCC_OP_REG_AIMB1 0x00
104−#define AMCC_OP_REG_AIMB2 0x04
105−#define AMCC_OP_REG_AIMB3 0x08
106−#define AMCC_OP_REG_AIMB4 0x0c
107−#define AMCC_OP_REG_AOMB1 0x10
108−#define AMCC_OP_REG_AOMB2 0x14
109−#define AMCC_OP_REG_AOMB3 0x18
110−#define AMCC_OP_REG_AOMB4 0x1c
111−#define AMCC_OP_REG_AFIFO 0x20
112−#define AMCC_OP_REG_AMWAR 0x24
113−#define AMCC_OP_REG_APTA 0x28
114−#define AMCC_OP_REG_APTD 0x2c
115−#define AMCC_OP_REG_AMRAR 0x30
116−#define AMCC_OP_REG_AMBEF 0x34
117−#define AMCC_OP_REG_AINT 0x38
118−#define AMCC_OP_REG_AGCSTS 0x3c
119−#define AMCC_OP_REG_AMWTC 0x58
120−#define AMCC_OP_REG_AMRTC 0x5c
121−
122−/****************************************************************************/
123−/* AMCC - Add-on General Control/Status Register */
124−/****************************************************************************/
125−
126−#define AGCSTS_CONTROL_MASK 0xfffff000
127−#define AGCSTS_NV_ACC_MASK 0xe0000000
128−#define AGCSTS_RESET_MASK 0x0e000000
129−#define AGCSTS_NV_DA_MASK 0x00ff0000
130−#define AGCSTS_BIST_MASK 0x0000f000
131−#define AGCSTS_STATUS_MASK 0x000000ff
132−#define AGCSTS_TCZERO_MASK 0x000000c0
133−#define AGCSTS_FIFO_ST_MASK 0x0000003f
134−
135−#define AGCSTS_RESET_MBFLAGS 0x08000000
136−#define AGCSTS_RESET_P2A_FIFO 0x04000000
137−#define AGCSTS_RESET_A2P_FIFO 0x02000000
138−#define AGCSTS_RESET_FIFOS (AGCSTS_RESET_A2P_FIFO | AGCSTS_RESET_P2A_FIFO)
139−
140−#define AGCSTS_A2P_TCOUNT 0x00000080
141−#define AGCSTS_P2A_TCOUNT 0x00000040
142−
143−#define AGCSTS_FS_P2A_EMPTY 0x00000020
144−#define AGCSTS_FS_P2A_HALF 0x00000010
145−#define AGCSTS_FS_P2A_FULL 0x00000008
146−
147−#define AGCSTS_FS_A2P_EMPTY 0x00000004
148−#define AGCSTS_FS_A2P_HALF 0x00000002
149−#define AGCSTS_FS_A2P_FULL 0x00000001
150−
151−/****************************************************************************/
152−/* AMCC - Add-on Interrupt Control/Status Register */
153−/****************************************************************************/
154−
155−#define AINT_INT_MASK 0x00ff0000
156−#define AINT_SEL_MASK 0x0000ffff
157−#define AINT_IS_ENSEL_MASK 0x00001f1f
158−
159−#define AINT_INT_ASSERTED 0x00800000
160−#define AINT_BM_ERROR 0x00200000
161−#define AINT_BIST_INT 0x00100000
162−
163−#define AINT_RT_COMPLETE 0x00080000
164−#define AINT_WT_COMPLETE 0x00040000
165−
166−#define AINT_OUT_MB_INT 0x00020000
167−#define AINT_IN_MB_INT 0x00010000
168−
169−#define AINT_READ_COMPL 0x00008000
170−#define AINT_WRITE_COMPL 0x00004000
171−
172−#define AINT_OMB_ENABLE 0x00001000
173−#define AINT_OMB_SELECT 0x00000c00
174−#define AINT_OMB_BYTE 0x00000300
175−
176−#define AINT_IMB_ENABLE 0x00000010
177−#define AINT_IMB_SELECT 0x0000000c
178−#define AINT_IMB_BYTE 0x00000003
179−
180−/* Enable Bus Mastering */
181−#define EN_A2P_TRANSFERS 0x00000400
182−/* FIFO Flag Reset */
183−#define RESET_A2P_FLAGS 0x04000000L
184−/* FIFO Relative Priority */
185−#define A2P_HI_PRIORITY 0x00000100L
186−/* Identify Interrupt Sources */
187−#define ANY_S593X_INT 0x00800000L
188−#define READ_TC_INT 0x00080000L
189−#define WRITE_TC_INT 0x00040000L
190−#define IN_MB_INT 0x00020000L
191−#define MASTER_ABORT_INT 0x00100000L
192−#define TARGET_ABORT_INT 0x00200000L
193−#define BUS_MASTER_INT 0x00200000L
194−
195−/****************************************************************************/
196−
197−struct pcilst_struct {
198− struct pcilst_struct *next;
199− int used;
200− struct pci_dev *pcidev;
201− unsigned short vendor;
202− unsigned short device;
203− unsigned int master;
204− unsigned char pci_bus;
205− unsigned char pci_slot;
206− unsigned char pci_func;
207− unsigned int io_addr[5];
208− unsigned int irq;
209−};
210−
211−struct pcilst_struct *amcc_devices; /* ptr to root list of all amcc devices */
212−
213−/****************************************************************************/
214−
215−void v_pci_card_list_init(unsigned short pci_vendor, char display);
216−void v_pci_card_list_cleanup(unsigned short pci_vendor);
217−struct pcilst_struct *ptr_find_free_pci_card_by_device(unsigned short vendor_id,
218− unsigned short
219− device_id);
220−int i_find_free_pci_card_by_position(unsigned short vendor_id,
221− unsigned short device_id,
222− unsigned short pci_bus,
223− unsigned short pci_slot,
224− struct pcilst_struct **card);
225−struct pcilst_struct *ptr_select_and_alloc_pci_card(unsigned short vendor_id,
226− unsigned short device_id,
227− unsigned short pci_bus,
228− unsigned short pci_slot);
229−
230−int i_pci_card_alloc(struct pcilst_struct *amcc);
231−int i_pci_card_free(struct pcilst_struct *amcc);
232−void v_pci_card_list_display(void);
233−int i_pci_card_data(struct pcilst_struct *amcc,
234− unsigned char *pci_bus, unsigned char *pci_slot,
235− unsigned char *pci_func, unsigned short *io_addr,
236− unsigned short *irq, unsigned short *master);
237−
238−/****************************************************************************/
239−
240−/* build list of amcc cards in this system */
241−void v_pci_card_list_init(unsigned short pci_vendor, char display)
242−{
243− struct pci_dev *pcidev;
244− struct pcilst_struct *amcc, *last;
245− int i;
246−
247− amcc_devices = NULL;
248− last = NULL;
249−
250− pci_for_each_dev(pcidev) {
251− if (pcidev->vendor == pci_vendor) {
252− amcc = kzalloc(sizeof(*amcc), GFP_KERNEL);
253− if (amcc == NULL)
254− continue;
255−
256− amcc->pcidev = pcidev;
257− if (last) {
258− last->next = amcc;
259− } else {
260− amcc_devices = amcc;
261− }
262− last = amcc;
263−
264− amcc->vendor = pcidev->vendor;
265− amcc->device = pcidev->device;
266−#if 0
267− amcc->master = pcidev->master; /* how get this information under 2.4 kernels? */
268−#endif
269− amcc->pci_bus = pcidev->bus->number;
270− amcc->pci_slot = PCI_SLOT(pcidev->devfn);
271− amcc->pci_func = PCI_FUNC(pcidev->devfn);
272− for (i = 0; i < 5; i++)
273− amcc->io_addr[i] =
274− pcidev->resource[i].start & ~3UL;
275− amcc->irq = pcidev->irq;

178 more lines aren’t shown here.

drivers/staging/comedi/drivers/addi-data/hwdrv_APCI1710.c+9−9

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

drivers/staging/comedi/drivers/addi-data/hwdrv_apci3120.c+15−46

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

drivers/staging/comedi/drivers/addi-data/hwdrv_apci3200.c+29−52

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

drivers/staging/comedi/drivers/addi_apci_all.c+0−18

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

drivers/staging/comedi/drivers/adl_pci6208.c+87−96

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

drivers/staging/comedi/drivers/adl_pci7230.c+0−190

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

drivers/staging/comedi/drivers/adl_pci7296.c+0−183

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

drivers/staging/comedi/drivers/adl_pci7432.c+0−200

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

drivers/staging/comedi/drivers/adl_pci7x3x.c+332−0

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

drivers/staging/comedi/drivers/adl_pci8164.c+17−56

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

drivers/staging/comedi/drivers/adl_pci9111.c+278−695

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

drivers/staging/comedi/drivers/adl_pci9118.c+410−649

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

drivers/staging/comedi/drivers/adq12b.c+14−15

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

drivers/staging/comedi/drivers/adv_pci1710.c+316−450

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

drivers/staging/comedi/drivers/adv_pci1723.c+58−164

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

drivers/staging/comedi/drivers/adv_pci_dio.c+225−248

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

drivers/staging/comedi/drivers/aio_aio12_8.c+137−81

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

drivers/staging/comedi/drivers/aio_iiro_16.c+2−2

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

drivers/staging/comedi/drivers/amplc_dio200.c+49−65

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

drivers/staging/comedi/drivers/amplc_pc236.c+53−55

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

drivers/staging/comedi/drivers/amplc_pc263.c+34−20

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

drivers/staging/comedi/drivers/amplc_pci224.c+21−43

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

drivers/staging/comedi/drivers/amplc_pci230.c+45−109

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

drivers/staging/comedi/drivers/c6xdigio.c+3−3

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

drivers/staging/comedi/drivers/cb_das16_cs.c+18−38

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

drivers/staging/comedi/drivers/cb_pcidas.c+66−136

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

drivers/staging/comedi/drivers/cb_pcidas64.c+41−87

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

drivers/staging/comedi/drivers/cb_pcidda.c+175−266

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

drivers/staging/comedi/drivers/cb_pcidio.c+0−211

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

drivers/staging/comedi/drivers/cb_pcimdas.c+119−160

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

drivers/staging/comedi/drivers/cb_pcimdda.c+92−301

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

drivers/staging/comedi/drivers/comedi_bond.c+31−79

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

drivers/staging/comedi/drivers/comedi_fc.h+32−0

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

drivers/staging/comedi/drivers/comedi_parport.c+39−47

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

drivers/staging/comedi/drivers/comedi_test.c+40−68

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

drivers/staging/comedi/drivers/contec_pci_dio.c+45−101

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

drivers/staging/comedi/drivers/daqboard2000.c+202−264

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

drivers/staging/comedi/drivers/das08.c+149−333

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

drivers/staging/comedi/drivers/das08.h+4−11

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

drivers/staging/comedi/drivers/das08_cs.c+26−0

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

drivers/staging/comedi/drivers/das16.c+31−51

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

drivers/staging/comedi/drivers/das16m1.c+18−36

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

drivers/staging/comedi/drivers/das1800.c+63−82

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

drivers/staging/comedi/drivers/das6402.c+2−2

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

drivers/staging/comedi/drivers/das800.c+16−36

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

drivers/staging/comedi/drivers/dmm32at.c+19−38

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

drivers/staging/comedi/drivers/dt2801.c+6−6

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

drivers/staging/comedi/drivers/dt2811.c+4−4

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

drivers/staging/comedi/drivers/dt2814.c+14−32

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

drivers/staging/comedi/drivers/dt2815.c+1−1

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

drivers/staging/comedi/drivers/dt2817.c+1−1

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

drivers/staging/comedi/drivers/dt282x.c+29−74

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

drivers/staging/comedi/drivers/dt3000.c+16−32

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

drivers/staging/comedi/drivers/dt9812.c+4−4

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

drivers/staging/comedi/drivers/dyna_pci10xx.c+36−125

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

drivers/staging/comedi/drivers/fl512.c+2−2

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

drivers/staging/comedi/drivers/gsc_hpdi.c+11−32

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

drivers/staging/comedi/drivers/icp_multi.c+140−552

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

drivers/staging/comedi/drivers/icp_multi.h+0−297

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

drivers/staging/comedi/drivers/ii_pci20kc.c+2−2

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

drivers/staging/comedi/drivers/jr3_pci.c+5−4

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

drivers/staging/comedi/drivers/jr3_pci.h+2−2

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

drivers/staging/comedi/drivers/ke_counter.c+35−68

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

drivers/staging/comedi/drivers/me4000.c+618−1018

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

drivers/staging/comedi/drivers/me4000.h+0−409

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

drivers/staging/comedi/drivers/me_daq.c+99−122

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

drivers/staging/comedi/drivers/mite.c+135−150

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

drivers/staging/comedi/drivers/mite.h+16−50

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

drivers/staging/comedi/drivers/mpc624.c+1−1

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

drivers/staging/comedi/drivers/mpc8260cpm.c+1−1

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

drivers/staging/comedi/drivers/multiq3.c+8−6

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

drivers/staging/comedi/drivers/ni_6527.c+61−110

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

drivers/staging/comedi/drivers/ni_65xx.c+63−118

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

drivers/staging/comedi/drivers/ni_660x.c+46−87

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

drivers/staging/comedi/drivers/ni_670x.c+24−38

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

drivers/staging/comedi/drivers/ni_at_a2150.c+12−34

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

drivers/staging/comedi/drivers/ni_at_ao.c+4−4

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

drivers/staging/comedi/drivers/ni_atmio.c+1−1

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

drivers/staging/comedi/drivers/ni_atmio16d.c+26−41

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

drivers/staging/comedi/drivers/ni_daq_700.c+164−48

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

drivers/staging/comedi/drivers/ni_daq_dio24.c+8−4

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

drivers/staging/comedi/drivers/ni_labpc.c+198−269

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

drivers/staging/comedi/drivers/ni_labpc_cs.c+3−3

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

drivers/staging/comedi/drivers/ni_mio_common.c+88−152

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

drivers/staging/comedi/drivers/ni_mio_cs.c+2−2

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

drivers/staging/comedi/drivers/ni_pcidio.c+169−303

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

drivers/staging/comedi/drivers/ni_pcimio.c+30−40

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

drivers/staging/comedi/drivers/ni_tiocmd.c+18−43

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

drivers/staging/comedi/drivers/pcl711.c+18−35

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

drivers/staging/comedi/drivers/pcl724.c+9−6

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

drivers/staging/comedi/drivers/pcl725.c+2−2

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

drivers/staging/comedi/drivers/pcl726.c+3−3

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

drivers/staging/comedi/drivers/pcl730.c+4−4

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

drivers/staging/comedi/drivers/pcl812.c+20−37

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

drivers/staging/comedi/drivers/pcl816.c+14−38

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

drivers/staging/comedi/drivers/pcl818.c+20−39

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

drivers/staging/comedi/drivers/pcm3724.c+17−9

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

drivers/staging/comedi/drivers/pcm3730.c+6−6

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

drivers/staging/comedi/drivers/pcm_common.c+13−43

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

drivers/staging/comedi/drivers/pcmad.c+1−1

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

drivers/staging/comedi/drivers/pcmda12.c+1−1

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

drivers/staging/comedi/drivers/pcmmio.c+10−22

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

drivers/staging/comedi/drivers/pcmuio.c+7−7

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

drivers/staging/comedi/drivers/poc.c+1−1

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

drivers/staging/comedi/drivers/quatech_daqp_cs.c+20−43

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

drivers/staging/comedi/drivers/rtd520.c+21−46

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

drivers/staging/comedi/drivers/rti800.c+5−5

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

drivers/staging/comedi/drivers/rti802.c+1−1

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

drivers/staging/comedi/drivers/s526.c+153−449

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

drivers/staging/comedi/drivers/s626.c+303−452

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

drivers/staging/comedi/drivers/s626.h+0−1

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

drivers/staging/comedi/drivers/serial2002.c+8−6

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

drivers/staging/comedi/drivers/skel.c+28−46

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

drivers/staging/comedi/drivers/ssv_dnp.c+2−5

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

drivers/staging/comedi/drivers/usbdux.c+52−149

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

drivers/staging/comedi/drivers/usbduxfast.c+23−97

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

drivers/staging/comedi/drivers/usbduxsigma.c+45−147

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

drivers/staging/comedi/drivers/vmk80xx.c+8−6

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

drivers/staging/comedi/kcomedilib/kcomedilib_main.c+13−10

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

drivers/staging/comedi/range.c+10−8

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

drivers/staging/cptm1217/clearpad_tm1217.c+1−12

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

drivers/staging/crystalhd/crystalhd_lnx.c+5−1

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

drivers/staging/csr/Makefile+0−1

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

drivers/staging/csr/bh.c+90−83

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

drivers/staging/csr/csr_formatted_io.c+0−27

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

drivers/staging/csr/csr_formatted_io.h+0−25

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

drivers/staging/csr/csr_framework_ext.c+1−12

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

drivers/staging/csr/csr_panic.c+0−1

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

drivers/staging/csr/csr_time.c+9−18

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

drivers/staging/csr/csr_wifi_hip_card_sdio.c+4−4

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

drivers/staging/csr/csr_wifi_hip_download.c+2−0

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

drivers/staging/csr/csr_wifi_hip_send.c+2−7

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

drivers/staging/csr/csr_wifi_hip_udi.c+47−47

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

drivers/staging/csr/csr_wifi_hip_unifi.h+0−1

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

drivers/staging/csr/drv.c+9−37

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

drivers/staging/csr/firmware.c+2−4

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

drivers/staging/csr/io.c+17−36

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

drivers/staging/csr/monitor.c+1−6

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

drivers/staging/csr/netdev.c+6−624

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

drivers/staging/csr/sdio_events.c+2−2

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

drivers/staging/csr/sdio_mmc.c+21−44

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

drivers/staging/csr/sme_blocking.c+2−2

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

drivers/staging/csr/sme_native.c+1−5

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

drivers/staging/csr/sme_sys.c+8−14

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

drivers/staging/csr/sme_wext.c+3−5

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

drivers/staging/csr/ul_int.c+1−4

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

drivers/staging/csr/unifi_pdu_processing.c+1−4

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

drivers/staging/csr/unifi_priv.h+0−40

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

drivers/staging/csr/unifi_wext.h+6−21

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

drivers/staging/csr/wext_events.c+3−5

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

drivers/staging/cxt1e1/linux.c+6−6

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

drivers/staging/cxt1e1/musycc.c+5−5

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

drivers/staging/et131x/et131x.c+1−6

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

drivers/staging/ft1000/ft1000-pcmcia/ft1000_dnld.c+17−17

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

drivers/staging/ft1000/ft1000-usb/ft1000_hw.c+7−7

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

drivers/staging/ft1000/ft1000-usb/ft1000_usb.h+0−2

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

drivers/staging/gdm72xx/gdm_qos.c+59−59

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

drivers/staging/gdm72xx/gdm_qos.h+29−29

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

drivers/staging/gdm72xx/gdm_sdio.c+11−26

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

drivers/staging/gdm72xx/gdm_usb.c+24−38

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

drivers/staging/gdm72xx/gdm_usb.h+8−8

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

drivers/staging/gdm72xx/gdm_wimax.c+10−6

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

drivers/staging/gdm72xx/usb_boot.c+100−120

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

drivers/staging/iio/Documentation/generic_buffer.c+10−0

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

drivers/staging/iio/Documentation/inkernel.txt+3−3

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

drivers/staging/iio/Kconfig+1−1

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

drivers/staging/iio/TODO+1−1

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

drivers/staging/iio/accel/adis16201_core.c+2−2

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

drivers/staging/iio/accel/adis16201_ring.c+1−2

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

drivers/staging/iio/accel/adis16203_core.c+2−2

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

drivers/staging/iio/accel/adis16203_ring.c+1−4

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

drivers/staging/iio/accel/adis16204_core.c+2−2

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

drivers/staging/iio/accel/adis16204_ring.c+1−2

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

drivers/staging/iio/accel/adis16209_core.c+2−2

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

drivers/staging/iio/accel/adis16209_ring.c+1−2

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

drivers/staging/iio/accel/adis16220_core.c+4−7

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

drivers/staging/iio/accel/adis16240_core.c+2−2

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

drivers/staging/iio/accel/adis16240_ring.c+1−2

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

drivers/staging/iio/accel/kxsd9.c+3−3

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

drivers/staging/iio/accel/lis3l02dq.h+7−7

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

drivers/staging/iio/accel/lis3l02dq_core.c+10−16

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

drivers/staging/iio/accel/lis3l02dq_ring.c+15−16

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

drivers/staging/iio/accel/sca3000.h+1−1

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

drivers/staging/iio/accel/sca3000_core.c+6−8

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

drivers/staging/iio/accel/sca3000_ring.c+1−1

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

drivers/staging/iio/adc/Kconfig+20−23

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

drivers/staging/iio/adc/Makefile+1−4

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

drivers/staging/iio/adc/ad7192.c+67−456

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

drivers/staging/iio/adc/ad7298_core.c+1−1

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

drivers/staging/iio/adc/ad7298_ring.c+1−2

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

drivers/staging/iio/adc/ad7476.h+0−66

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

drivers/staging/iio/adc/ad7476_ring.c+0−64

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

drivers/staging/iio/adc/ad7606.h+1−1

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

drivers/staging/iio/adc/ad7606_core.c+3−3

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

drivers/staging/iio/adc/ad7606_ring.c+1−2

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

drivers/staging/iio/adc/ad7780.c+109−128

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

drivers/staging/iio/adc/ad7793.c+121−567

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

drivers/staging/iio/adc/ad7793.h+9−1

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

drivers/staging/iio/adc/ad7887_core.c+1−1

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

drivers/staging/iio/adc/ad7887_ring.c+1−1

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

drivers/staging/iio/adc/ad799x_ring.c+1−2

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

drivers/staging/iio/adc/lpc32xx_adc.c+1−1

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

drivers/staging/iio/adc/max1363.h+1−1

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

drivers/staging/iio/adc/max1363_core.c+16−16

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

drivers/staging/iio/adc/max1363_ring.c+1−1

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

drivers/staging/iio/adc/mxs-lradc.c+590−0

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

drivers/staging/iio/adc/spear_adc.c+9−18

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

drivers/staging/iio/gyro/adis16060_core.c+2−2

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

drivers/staging/iio/gyro/adis16080_core.c+1−1

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

drivers/staging/iio/gyro/adis16130_core.c+1−1

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

drivers/staging/iio/gyro/adis16260_core.c+3−9

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

drivers/staging/iio/gyro/adis16260_ring.c+1−2

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

drivers/staging/iio/gyro/adxrs450_core.c+1−1

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

drivers/staging/iio/iio_dummy_evgen.c+1−1

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

drivers/staging/iio/iio_hwmon.c+7−40

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

drivers/staging/iio/iio_simple_dummy.c+9−15

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

drivers/staging/iio/iio_simple_dummy.h+4−2

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

drivers/staging/iio/iio_simple_dummy_buffer.c+11−2

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

drivers/staging/iio/impedance-analyzer/ad5933.c+2−2

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

drivers/staging/iio/imu/adis16400.h+1−1

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

drivers/staging/iio/imu/adis16400_core.c+6−12

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

drivers/staging/iio/imu/adis16400_ring.c+1−1

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

drivers/staging/iio/light/isl29018.c+15−2

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

drivers/staging/iio/light/tsl2563.c+1−1

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

drivers/staging/iio/magnetometer/hmc5843.c+1−1

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

drivers/staging/iio/meter/ade7753.c+4−9

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

drivers/staging/iio/meter/ade7754.c+3−9

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

drivers/staging/iio/meter/ade7758.h+1−1

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

drivers/staging/iio/meter/ade7758_core.c+4−9

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

drivers/staging/iio/meter/ade7758_ring.c+1−2

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

drivers/staging/iio/meter/ade7759.c+3−8

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

drivers/staging/iio/meter/ade7854-spi.c+1−1

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

drivers/staging/iio/resolver/ad2s1210.c+1−1

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

drivers/staging/iio/ring_hw.h+1−1

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

drivers/staging/iio/ring_sw.c+3−4

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

drivers/staging/iio/trigger/Kconfig+2−0

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

drivers/staging/iio/trigger/iio-trig-bfin-timer.c+88−21

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

drivers/staging/iio/trigger/iio-trig-bfin-timer.h+24−0

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

drivers/staging/iio/trigger/iio-trig-gpio.c+4−4

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

drivers/staging/iio/trigger/iio-trig-periodic-rtc.c+4−4

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

drivers/staging/iio/trigger/iio-trig-sysfs.c+16−1

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

drivers/staging/imx-drm/Kconfig+35−0

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

drivers/staging/imx-drm/Makefile+9−0

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

drivers/staging/imx-drm/TODO+22−0

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

drivers/staging/imx-drm/imx-drm-core.c+884−0

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

drivers/staging/imx-drm/imx-drm.h+58−0

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

drivers/staging/imx-drm/imx-fb.c+47−0

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

drivers/staging/imx-drm/imx-fbdev.c+74−0

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

drivers/staging/imx-drm/ipu-v3/Makefile+3−0

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

drivers/staging/imx-drm/ipu-v3/imx-ipu-v3.h+318−0

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

drivers/staging/imx-drm/ipu-v3/ipu-common.c+1143−0

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

drivers/staging/imx-drm/ipu-v3/ipu-dc.c+372−0

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

drivers/staging/imx-drm/ipu-v3/ipu-di.c+700−0

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

drivers/staging/imx-drm/ipu-v3/ipu-dmfc.c+408−0

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

drivers/staging/imx-drm/ipu-v3/ipu-dp.c+336−0

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

drivers/staging/imx-drm/ipu-v3/ipu-prv.h+206−0

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

drivers/staging/imx-drm/ipuv3-crtc.c+579−0

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

drivers/staging/imx-drm/parallel-display.c+261−0

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

drivers/staging/ipack/Kconfig+1−0

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

drivers/staging/ipack/TODO+2−23

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

drivers/staging/ipack/bridges/tpci200.c+306−429

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

drivers/staging/ipack/bridges/tpci200.h+27−12

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

drivers/staging/ipack/devices/ipoctal.c+321−417

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

drivers/staging/ipack/devices/scc2698.h+58−59

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

drivers/staging/ipack/ipack.c+350−22

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

drivers/staging/ipack/ipack.h+61−27

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

drivers/staging/ipack/ipack_ids.h+32−0

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

drivers/staging/keucr/smcommon.h+0−2

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

drivers/staging/line6/pcm.c+7−1

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

drivers/staging/line6/variax.c+4−4

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

drivers/staging/nvec/Kconfig+1−1

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

drivers/staging/nvec/nvec.c+13−12

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

drivers/staging/olpc_dcon/olpc_dcon.c+24−29

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

drivers/staging/olpc_dcon/olpc_dcon_xo_1.c+9−6

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

drivers/staging/olpc_dcon/olpc_dcon_xo_1_5.c+4−2

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

drivers/staging/omap-thermal/omap-bandgap.c+12−11

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

drivers/staging/omap-thermal/omap-thermal-common.c+36−6

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

drivers/staging/omap-thermal/omap4-thermal.c+27−27

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

drivers/staging/omap-thermal/omap5-thermal.c+19−19

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

drivers/staging/omapdrm/omap_crtc.c+31−2

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

drivers/staging/omapdrm/omap_dmm_tiler.c+43−8

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

drivers/staging/omapdrm/omap_dmm_tiler.h+15−2

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

drivers/staging/omapdrm/omap_drv.c+18−3

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

drivers/staging/omapdrm/omap_drv.h+31−2

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

drivers/staging/omapdrm/omap_fb.c+85−14

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

drivers/staging/omapdrm/omap_gem.c+58−2

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

drivers/staging/omapdrm/omap_plane.c+90−21

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

drivers/staging/ozwpan/ozcdev.c+7−7

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

drivers/staging/ozwpan/ozevent.c+3−3

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

drivers/staging/ozwpan/ozhcd.c+80−24

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

drivers/staging/ozwpan/ozmain.c+1−1

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

drivers/staging/ozwpan/ozpd.c+2−9

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

drivers/staging/ozwpan/ozpd.h+1−0

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

drivers/staging/ozwpan/ozproto.c+13−0

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

drivers/staging/ozwpan/ozproto.h+7−1

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

drivers/staging/ozwpan/ozprotocol.h+5−1

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

drivers/staging/panel/panel.c+26−26

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

drivers/staging/ramster/Kconfig+21−4

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

drivers/staging/ramster/Makefile+6−1

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

drivers/staging/ramster/TODO+0−13

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

drivers/staging/ramster/cluster/Makefile+0−3

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

drivers/staging/ramster/ramster.h+27−86

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

drivers/staging/ramster/ramster/heartbeat.crenamed from drivers/staging/ramster/cluster/heartbeat.c+2−4

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

drivers/staging/ramster/ramster/heartbeat.hrenamed from drivers/staging/ramster/cluster/heartbeat.h+0−0

File renamed without changes.

drivers/staging/ramster/ramster/masklog.crenamed from drivers/staging/ramster/cluster/masklog.c+0−0

File renamed without changes.

drivers/staging/ramster/ramster/masklog.hrenamed from drivers/staging/ramster/cluster/masklog.h+0−0

File renamed without changes.

drivers/staging/ramster/ramster/nodemanager.crenamed from drivers/staging/ramster/cluster/nodemanager.c+9−6

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

drivers/staging/ramster/ramster/nodemanager.hrenamed from drivers/staging/ramster/cluster/nodemanager.h+0−0

File renamed without changes.

drivers/staging/ramster/ramster/r2net.crenamed from drivers/staging/ramster/r2net.c+46−33

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

drivers/staging/ramster/ramster/ramster.c+985−0

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

drivers/staging/ramster/ramster/ramster.h+161−0

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

drivers/staging/ramster/ramster/ramster_nodemanager.hrenamed from drivers/staging/ramster/cluster/ramster_nodemanager.h+0−0

File renamed without changes.

drivers/staging/ramster/ramster/tcp.crenamed from drivers/staging/ramster/cluster/tcp.c+25−28

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

drivers/staging/ramster/ramster/tcp.hrenamed from drivers/staging/ramster/cluster/tcp.h+0−0

File renamed without changes.

drivers/staging/ramster/ramster/tcp_internal.hrenamed from drivers/staging/ramster/cluster/tcp_internal.h+0−0

File renamed without changes.

drivers/staging/ramster/tmem.c+178−135

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

drivers/staging/ramster/tmem.h+62−47

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

drivers/staging/ramster/xvmalloc.c+0−509

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

drivers/staging/ramster/xvmalloc.h+0−30

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

drivers/staging/ramster/xvmalloc_int.h+0−95

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

drivers/staging/ramster/zbud.c+1060−0

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

drivers/staging/ramster/zbud.h+33−0

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

drivers/staging/ramster/zcache-main.c+1033−2533

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

drivers/staging/ramster/zcache.h+43−12

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

drivers/staging/rtl8187se/ieee80211/ieee80211.h+1−1

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

drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c+3−10

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

drivers/staging/rtl8187se/ieee80211/ieee80211_softmac_wx.c+3−2

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

drivers/staging/rtl8187se/r8180_core.c+2−2

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

drivers/staging/rtl8187se/r8180_hw.h+7−2

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

drivers/staging/rtl8187se/r8185b_init.c+1−1

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

drivers/staging/rtl8192e/rtl8192e/r8192E_firmware.c+5−4

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

drivers/staging/rtl8192e/rtl8192e/r8192E_firmware.h+4−0

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

drivers/staging/rtl8192e/rtl8192e/rtl_core.c+4−2

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

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

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

drivers/staging/rtl8192e/rtllib.h+4−4

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

drivers/staging/rtl8192e/rtllib_softmac.c+8−16

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

drivers/staging/rtl8192e/rtllib_softmac_wx.c+4−3

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

drivers/staging/rtl8192u/ieee80211/ieee80211.h+2−2

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

drivers/staging/rtl8192u/ieee80211/ieee80211_softmac.c+7−13

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

drivers/staging/rtl8192u/ieee80211/ieee80211_softmac_wx.c+3−2

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

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

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

drivers/staging/rtl8192u/ieee80211/rtl819x_HT.h+2−2

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

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

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

drivers/staging/rtl8192u/r8192U_core.c+8−19

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

drivers/staging/rtl8192u/r819xU_HTType.h+1−1

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

drivers/staging/rtl8192u/r819xU_phyreg.h+1−1

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

drivers/staging/rtl8712/drv_types.h+0−9

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

drivers/staging/rtl8712/ethernet.h+0−8

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

drivers/staging/rtl8712/os_intfs.c+1−1

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

drivers/staging/rtl8712/rtl8712_recv.c+8−1

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

drivers/staging/rtl8712/rtl8712_recv.h+1−1

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

drivers/staging/rtl8712/rtl8712_xmit.c+1−1

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

drivers/staging/rtl8712/rtl871x_ioctl_linux.c+1−3

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

drivers/staging/rtl8712/rtl871x_ioctl_set.c+1−4

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

drivers/staging/rtl8712/rtl871x_mlme.c+3−2

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

drivers/staging/rtl8712/rtl871x_pwrctrl.h+0−20

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

drivers/staging/rtl8712/rtl871x_recv.c+5−4

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

drivers/staging/rtl8712/rtl871x_security.c+4−4

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

drivers/staging/rtl8712/usb_intf.c+0−1

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

drivers/staging/rtl8712/usb_osintf.h+0−3

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

drivers/staging/rtl8712/usb_vendor_req.h+0−58

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

drivers/staging/rts5139/rts51x_fop.c+1−1

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

drivers/staging/rts5139/trace.h+3−29

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

drivers/staging/rts_pstor/ms.c+340−532

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

drivers/staging/rts_pstor/rtsx.c+54−58

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

drivers/staging/rts_pstor/rtsx_card.c+81−105

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

drivers/staging/rts_pstor/rtsx_chip.c+246−317

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

drivers/staging/rts_pstor/rtsx_scsi.c+169−236

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

drivers/staging/rts_pstor/rtsx_transport.c+45−55

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

drivers/staging/rts_pstor/sd.c+415−640

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

drivers/staging/rts_pstor/trace.h+3−27

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

drivers/staging/sbe-2t3e3/2t3e3.h+0−1

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

drivers/staging/sbe-2t3e3/dc.c+6−4

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

drivers/staging/sbe-2t3e3/module.c+11−4

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

drivers/staging/sbe-2t3e3/netdev.c+4−4

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

drivers/staging/sep/sep_main.c+1−1

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

drivers/staging/serqt_usb2/serqt_usb2.c+3−8

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

drivers/staging/silicom/Kconfig+46−0

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

drivers/staging/silicom/Makefile+9−0

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

drivers/staging/silicom/README+14−0

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

drivers/staging/silicom/TODO+8−0

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

drivers/staging/silicom/bits.h+56−0

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

drivers/staging/silicom/bp_ioctl.h+140−0

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

drivers/staging/silicom/bp_mod.c+8931−0

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

drivers/staging/silicom/bp_mod.h+704−0

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

drivers/staging/silicom/bp_proc.c+1350−0

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

drivers/staging/silicom/bypass.h+202−0

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

drivers/staging/silicom/bypasslib/Makefile+6−0

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

drivers/staging/silicom/bypasslib/bp_ioctl.h+198−0

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

drivers/staging/silicom/bypasslib/bplibk.h+47−0

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

drivers/staging/silicom/bypasslib/bypass.c+529−0

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

drivers/staging/silicom/bypasslib/libbp_sd.h+509−0

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

drivers/staging/silicom/libbp_sd.h+550−0

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

drivers/staging/slicoss/slicoss.c+14−26

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

drivers/staging/sm7xxfb/sm7xx.h+1−1

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

drivers/staging/sm7xxfb/sm7xxfb.c+49−70

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

drivers/staging/speakup/i18n.c+1−0

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

drivers/staging/speakup/speakup_soft.c+5−10

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

drivers/staging/telephony/ixj.c+2−2

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

drivers/staging/tidspbridge/Documentation/error-codes+1−1

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

drivers/staging/tidspbridge/core/_tiomap.h+1−1

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

drivers/staging/tidspbridge/core/chnl_sm.c+5−4

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

drivers/staging/tidspbridge/core/dsp-clock.c+2−0

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

drivers/staging/tidspbridge/core/io_sm.c+5−5

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

drivers/staging/tidspbridge/core/sync.c+1−1

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

drivers/staging/tidspbridge/core/tiomap3430.c+4−4

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

drivers/staging/tidspbridge/core/tiomap3430_pwr.c+1−1

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

drivers/staging/tidspbridge/core/wdt.c+4−3

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

drivers/staging/tidspbridge/dynload/tramp.c+4−4

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

drivers/staging/tidspbridge/gen/uuidutil.c+0−21

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

drivers/staging/tidspbridge/hw/hw_mmu.c+3−3

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

drivers/staging/tidspbridge/include/dspbridge/dspioctl.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/mbx_sh.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/node.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/ntfy.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/proc.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/strm.h+1−1

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

drivers/staging/tidspbridge/include/dspbridge/sync.h+2−2

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

drivers/staging/tidspbridge/include/dspbridge/uuidutil.h+0−20

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

drivers/staging/tidspbridge/rmgr/dbdcd.c+23−6

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

drivers/staging/tidspbridge/rmgr/drv_interface.c+1−13

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

drivers/staging/tidspbridge/rmgr/dspdrv.c+2−2

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

drivers/staging/tidspbridge/rmgr/mgr.c+2−2

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

drivers/staging/tidspbridge/rmgr/nldr.c+1−1

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

drivers/staging/tidspbridge/rmgr/node.c+2−3

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

drivers/staging/tidspbridge/rmgr/proc.c+1−1

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

drivers/staging/usbip/Kconfig+2−2

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

drivers/staging/usbip/stub_dev.c+6−2

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

drivers/staging/usbip/stub_rx.c+1−1

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

drivers/staging/usbip/usbip_common.c+4−0

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

drivers/staging/usbip/userspace/configure.ac+6−6

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

drivers/staging/usbip/userspace/doc/usbip.8+42−24

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

drivers/staging/usbip/userspace/doc/usbip_bind_driver.8+0−42

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

drivers/staging/usbip/userspace/doc/usbipd.8+10−6

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

drivers/staging/usbip/vhci_hcd.c+22−9

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

drivers/staging/vme/devices/vme_pio2_core.c+5−5

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

drivers/staging/vme/devices/vme_user.c+5−5

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

drivers/staging/vt6655/80211mgr.h+1−1

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

drivers/staging/vt6655/baseband.c+86−86

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

drivers/staging/vt6655/baseband.h+5−5

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

drivers/staging/vt6655/bssdb.c+2−2

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

drivers/staging/vt6655/card.c+51−50

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

drivers/staging/vt6655/datarate.c+1−1

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

drivers/staging/vt6655/device.h+2−2

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

drivers/staging/vt6655/device_main.c+48−56

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

drivers/staging/vt6655/dpc.c+1−1

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

drivers/staging/vt6655/hostap.c+2−6

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

drivers/staging/vt6655/ioctl.c+3−6

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

drivers/staging/vt6655/iwctl.c+3−3

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

drivers/staging/vt6655/key.c+1−1

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

drivers/staging/vt6655/mac.c+6−6

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

drivers/staging/vt6655/mac.h+1−1

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

drivers/staging/vt6655/mib.c+1−1

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

drivers/staging/vt6655/power.c+1−1

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

drivers/staging/vt6655/rf.c+41−41

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

drivers/staging/vt6655/rf.h+1−1

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

drivers/staging/vt6655/rxtx.c+21−21

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

drivers/staging/vt6655/tcrc.c+1−1

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

drivers/staging/vt6655/tcrc.h+1−1

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

drivers/staging/vt6655/tether.c+2−2

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

drivers/staging/vt6655/tkip.c+1−1

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

drivers/staging/vt6655/vntwifi.c+1−1

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

drivers/staging/vt6655/wcmd.c+3−3

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

drivers/staging/vt6655/wmgr.c+28−28

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

drivers/staging/vt6655/wmgr.h+2−2

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

drivers/staging/vt6655/wpa.c+1−1

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

drivers/staging/vt6655/wpa2.c+4−4

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

drivers/staging/vt6655/wpactl.c+3−3

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

drivers/staging/vt6655/wroute.c+1−1

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

drivers/staging/vt6656/80211mgr.h+2−2

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

drivers/staging/vt6656/baseband.c+3−3

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

drivers/staging/vt6656/baseband.h+1−1

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

drivers/staging/vt6656/bssdb.c+9−9

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

drivers/staging/vt6656/card.c+19−19

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

drivers/staging/vt6656/device.h+1−1

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

drivers/staging/vt6656/dpc.c+1−1

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

drivers/staging/vt6656/hostap.c+13−17

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

drivers/staging/vt6656/int.c+1−1

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

drivers/staging/vt6656/ioctl.c+4−7

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

drivers/staging/vt6656/iwctl.c+1−1

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

drivers/staging/vt6656/key.c+2−2

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

drivers/staging/vt6656/main_usb.c+10−10

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

drivers/staging/vt6656/power.c+1−1

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

drivers/staging/vt6656/rf.c+29−29

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

drivers/staging/vt6656/rf.h+1−1

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

drivers/staging/vt6656/rxtx.c+26−26

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

drivers/staging/vt6656/tcrc.c+1−1

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

drivers/staging/vt6656/tcrc.h+1−1

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

drivers/staging/vt6656/tether.c+2−2

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

drivers/staging/vt6656/tkip.c+1−1

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

drivers/staging/vt6656/wcmd.c+4−4

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

drivers/staging/vt6656/wctl.c+1−1

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

drivers/staging/vt6656/wmgr.c+13−13

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

drivers/staging/vt6656/wpa.c+1−1

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

drivers/staging/vt6656/wpa2.c+3−3

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

drivers/staging/vt6656/wpactl.c+3−3

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

drivers/staging/winbond/Kconfig+1−1

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

drivers/staging/winbond/localpara.h+2−2

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

drivers/staging/winbond/mds.c+1−1

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

drivers/staging/winbond/mto.c+1−1

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

drivers/staging/winbond/phy_calibration.c+7−7

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

drivers/staging/winbond/reg.c+1−1

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

drivers/staging/winbond/sme_api.h+5−6

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

drivers/staging/winbond/wb35reg.c+2−2

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

drivers/staging/winbond/wb35tx.c+74−80

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

drivers/staging/winbond/wb35tx_s.h+19−27

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

drivers/staging/wlags49_h2/README.ubuntu+6−6

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

drivers/staging/wlags49_h2/TODO+5−5

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

drivers/staging/wlags49_h2/hcf.c+10−10

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

drivers/staging/wlags49_h2/hcfcfg.h+1−1

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

drivers/staging/wlags49_h2/hcfdef.h+3−3

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

drivers/staging/wlags49_h2/mdd.h+4−4

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

drivers/staging/wlags49_h2/sta_h2.c+1−1

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

drivers/staging/wlags49_h2/sta_h25.c+1−1

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

drivers/staging/wlags49_h2/wl_enc.h+1−1

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

drivers/staging/wlags49_h2/wl_if.h+1−1

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

drivers/staging/wlags49_h2/wl_internal.h+2−2

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

drivers/staging/wlags49_h2/wl_main.c+9−9

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

drivers/staging/wlags49_h2/wl_netdev.c+19−40

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

drivers/staging/wlags49_h2/wl_pci.c+4−4

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

drivers/staging/wlags49_h2/wl_priv.c+1−1

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

drivers/staging/wlags49_h2/wl_profile.c+1−1

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

drivers/staging/wlags49_h2/wl_version.h+1−1

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

drivers/staging/wlags49_h2/wl_wext.c+14−13

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

drivers/staging/wlags49_h25/Kconfig+1−1

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

drivers/staging/wlags49_h25/TODO+4−4

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

drivers/staging/wlan-ng/cfg80211.c+7−4

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

drivers/staging/wlan-ng/hfa384x_usb.c+11−26

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

drivers/staging/wlan-ng/p80211conv.c+3−6

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

drivers/staging/wlan-ng/p80211netdev.c+4−17

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

drivers/staging/wlan-ng/p80211netdev.h+1−1

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

drivers/staging/wlan-ng/p80211req.c+69−83

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

drivers/staging/wlan-ng/p80211types.h+1−1

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

drivers/staging/wlan-ng/p80211wep.c+6−12

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

drivers/staging/wlan-ng/prism2fw.c+28−28

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

drivers/staging/wlan-ng/prism2sta.c+13−40

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

drivers/staging/xgifb/XGI_main_26.c+25−20

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

drivers/staging/xgifb/vb_def.h+0−21

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

drivers/staging/xgifb/vb_init.c+1−4

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

drivers/staging/xgifb/vb_setmode.c+170−431

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

drivers/staging/xgifb/vb_struct.h+6−43

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

drivers/staging/xgifb/vb_table.h+46−148

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

drivers/staging/zcache/tmem.c+1−1

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

drivers/staging/zsmalloc/zsmalloc-main.c+273−49

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

drivers/staging/zsmalloc/zsmalloc_int.h+0−155

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

include/linux/hid-sensor-hub.h+160−0

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

include/linux/hid-sensor-ids.h+112−0

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

include/linux/iio/adc/ad_sigma_delta.h+173−0

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

include/linux/iio/buffer.h+2−4

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

include/linux/iio/consumer.h+41−3

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

include/linux/iio/iio.h+58−7

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

include/linux/iio/kfifo_buf.h+3−0

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

include/linux/iio/machine.h+5−0

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

include/linux/iio/trigger.h+7−6

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

include/linux/iio/trigger_consumer.h+11−0

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

include/linux/iio/types.h+1−0

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

include/linux/mod_devicetable.h+8−0

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

include/linux/platform_data/ad5755.h+103−0

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

include/linux/platform_data/ad7791.h+17−0

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

include/linux/power/generic-adc-battery.h+29−0

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

scripts/mod/file2alias.c+15−0

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