st_magn_core.c 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551
  1. /*
  2. * STMicroelectronics magnetometers driver
  3. *
  4. * Copyright 2012-2013 STMicroelectronics Inc.
  5. *
  6. * Denis Ciocca <denis.ciocca@st.com>
  7. *
  8. * Licensed under the GPL-2.
  9. */
  10. #include <linux/kernel.h>
  11. #include <linux/module.h>
  12. #include <linux/slab.h>
  13. #include <linux/errno.h>
  14. #include <linux/types.h>
  15. #include <linux/mutex.h>
  16. #include <linux/interrupt.h>
  17. #include <linux/i2c.h>
  18. #include <linux/gpio.h>
  19. #include <linux/irq.h>
  20. #include <linux/delay.h>
  21. #include <linux/iio/iio.h>
  22. #include <linux/iio/sysfs.h>
  23. #include <linux/iio/buffer.h>
  24. #include <linux/iio/common/st_sensors.h>
  25. #include "st_magn.h"
  26. #define ST_MAGN_NUMBER_DATA_CHANNELS 3
  27. /* DEFAULT VALUE FOR SENSORS */
  28. #define ST_MAGN_DEFAULT_OUT_X_H_ADDR 0X03
  29. #define ST_MAGN_DEFAULT_OUT_Y_H_ADDR 0X07
  30. #define ST_MAGN_DEFAULT_OUT_Z_H_ADDR 0X05
  31. /* FULLSCALE */
  32. #define ST_MAGN_FS_AVL_1300MG 1300
  33. #define ST_MAGN_FS_AVL_1900MG 1900
  34. #define ST_MAGN_FS_AVL_2500MG 2500
  35. #define ST_MAGN_FS_AVL_4000MG 4000
  36. #define ST_MAGN_FS_AVL_4700MG 4700
  37. #define ST_MAGN_FS_AVL_5600MG 5600
  38. #define ST_MAGN_FS_AVL_8000MG 8000
  39. #define ST_MAGN_FS_AVL_8100MG 8100
  40. #define ST_MAGN_FS_AVL_12000MG 12000
  41. #define ST_MAGN_FS_AVL_15000MG 15000
  42. #define ST_MAGN_FS_AVL_16000MG 16000
  43. /* Special L addresses for Sensor 2 */
  44. #define ST_MAGN_2_OUT_X_L_ADDR 0x28
  45. #define ST_MAGN_2_OUT_Y_L_ADDR 0x2a
  46. #define ST_MAGN_2_OUT_Z_L_ADDR 0x2c
  47. /* Special L addresses for sensor 3 */
  48. #define ST_MAGN_3_OUT_X_L_ADDR 0x68
  49. #define ST_MAGN_3_OUT_Y_L_ADDR 0x6a
  50. #define ST_MAGN_3_OUT_Z_L_ADDR 0x6c
  51. static const struct iio_chan_spec st_magn_16bit_channels[] = {
  52. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  53. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  54. ST_SENSORS_SCAN_X, 1, IIO_MOD_X, 's', IIO_BE, 16, 16,
  55. ST_MAGN_DEFAULT_OUT_X_H_ADDR),
  56. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  57. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  58. ST_SENSORS_SCAN_Y, 1, IIO_MOD_Y, 's', IIO_BE, 16, 16,
  59. ST_MAGN_DEFAULT_OUT_Y_H_ADDR),
  60. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  61. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  62. ST_SENSORS_SCAN_Z, 1, IIO_MOD_Z, 's', IIO_BE, 16, 16,
  63. ST_MAGN_DEFAULT_OUT_Z_H_ADDR),
  64. IIO_CHAN_SOFT_TIMESTAMP(3)
  65. };
  66. static const struct iio_chan_spec st_magn_2_16bit_channels[] = {
  67. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  68. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  69. ST_SENSORS_SCAN_X, 1, IIO_MOD_X, 's', IIO_LE, 16, 16,
  70. ST_MAGN_2_OUT_X_L_ADDR),
  71. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  72. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  73. ST_SENSORS_SCAN_Y, 1, IIO_MOD_Y, 's', IIO_LE, 16, 16,
  74. ST_MAGN_2_OUT_Y_L_ADDR),
  75. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  76. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  77. ST_SENSORS_SCAN_Z, 1, IIO_MOD_Z, 's', IIO_LE, 16, 16,
  78. ST_MAGN_2_OUT_Z_L_ADDR),
  79. IIO_CHAN_SOFT_TIMESTAMP(3)
  80. };
  81. static const struct iio_chan_spec st_magn_3_16bit_channels[] = {
  82. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  83. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  84. ST_SENSORS_SCAN_X, 1, IIO_MOD_X, 's', IIO_LE, 16, 16,
  85. ST_MAGN_3_OUT_X_L_ADDR),
  86. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  87. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  88. ST_SENSORS_SCAN_Y, 1, IIO_MOD_Y, 's', IIO_LE, 16, 16,
  89. ST_MAGN_3_OUT_Y_L_ADDR),
  90. ST_SENSORS_LSM_CHANNELS(IIO_MAGN,
  91. BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE),
  92. ST_SENSORS_SCAN_Z, 1, IIO_MOD_Z, 's', IIO_LE, 16, 16,
  93. ST_MAGN_3_OUT_Z_L_ADDR),
  94. IIO_CHAN_SOFT_TIMESTAMP(3)
  95. };
  96. static const struct st_sensor_settings st_magn_sensors_settings[] = {
  97. {
  98. .wai = 0, /* This sensor has no valid WhoAmI report 0 */
  99. .wai_addr = ST_SENSORS_DEFAULT_WAI_ADDRESS,
  100. .sensors_supported = {
  101. [0] = LSM303DLH_MAGN_DEV_NAME,
  102. },
  103. .ch = (struct iio_chan_spec *)st_magn_16bit_channels,
  104. .odr = {
  105. .addr = 0x00,
  106. .mask = 0x1c,
  107. .odr_avl = {
  108. { .hz = 1, .value = 0x00 },
  109. { .hz = 2, .value = 0x01 },
  110. { .hz = 3, .value = 0x02 },
  111. { .hz = 8, .value = 0x03 },
  112. { .hz = 15, .value = 0x04 },
  113. { .hz = 30, .value = 0x05 },
  114. { .hz = 75, .value = 0x06 },
  115. /* 220 Hz, 0x07 reportedly exist */
  116. },
  117. },
  118. .pw = {
  119. .addr = 0x02,
  120. .mask = 0x03,
  121. .value_on = 0x00,
  122. .value_off = 0x03,
  123. },
  124. .fs = {
  125. .addr = 0x01,
  126. .mask = 0xe0,
  127. .fs_avl = {
  128. [0] = {
  129. .num = ST_MAGN_FS_AVL_1300MG,
  130. .value = 0x01,
  131. .gain = 1100,
  132. .gain2 = 980,
  133. },
  134. [1] = {
  135. .num = ST_MAGN_FS_AVL_1900MG,
  136. .value = 0x02,
  137. .gain = 855,
  138. .gain2 = 760,
  139. },
  140. [2] = {
  141. .num = ST_MAGN_FS_AVL_2500MG,
  142. .value = 0x03,
  143. .gain = 670,
  144. .gain2 = 600,
  145. },
  146. [3] = {
  147. .num = ST_MAGN_FS_AVL_4000MG,
  148. .value = 0x04,
  149. .gain = 450,
  150. .gain2 = 400,
  151. },
  152. [4] = {
  153. .num = ST_MAGN_FS_AVL_4700MG,
  154. .value = 0x05,
  155. .gain = 400,
  156. .gain2 = 355,
  157. },
  158. [5] = {
  159. .num = ST_MAGN_FS_AVL_5600MG,
  160. .value = 0x06,
  161. .gain = 330,
  162. .gain2 = 295,
  163. },
  164. [6] = {
  165. .num = ST_MAGN_FS_AVL_8100MG,
  166. .value = 0x07,
  167. .gain = 230,
  168. .gain2 = 205,
  169. },
  170. },
  171. },
  172. .multi_read_bit = false,
  173. .bootime = 2,
  174. },
  175. {
  176. .wai = 0x3c,
  177. .wai_addr = ST_SENSORS_DEFAULT_WAI_ADDRESS,
  178. .sensors_supported = {
  179. [0] = LSM303DLHC_MAGN_DEV_NAME,
  180. [1] = LSM303DLM_MAGN_DEV_NAME,
  181. },
  182. .ch = (struct iio_chan_spec *)st_magn_16bit_channels,
  183. .odr = {
  184. .addr = 0x00,
  185. .mask = 0x1c,
  186. .odr_avl = {
  187. { .hz = 1, .value = 0x00 },
  188. { .hz = 2, .value = 0x01 },
  189. { .hz = 3, .value = 0x02 },
  190. { .hz = 8, .value = 0x03 },
  191. { .hz = 15, .value = 0x04 },
  192. { .hz = 30, .value = 0x05 },
  193. { .hz = 75, .value = 0x06 },
  194. { .hz = 220, .value = 0x07 },
  195. },
  196. },
  197. .pw = {
  198. .addr = 0x02,
  199. .mask = 0x03,
  200. .value_on = 0x00,
  201. .value_off = 0x03,
  202. },
  203. .fs = {
  204. .addr = 0x01,
  205. .mask = 0xe0,
  206. .fs_avl = {
  207. [0] = {
  208. .num = ST_MAGN_FS_AVL_1300MG,
  209. .value = 0x01,
  210. .gain = 909,
  211. .gain2 = 1020,
  212. },
  213. [1] = {
  214. .num = ST_MAGN_FS_AVL_1900MG,
  215. .value = 0x02,
  216. .gain = 1169,
  217. .gain2 = 1315,
  218. },
  219. [2] = {
  220. .num = ST_MAGN_FS_AVL_2500MG,
  221. .value = 0x03,
  222. .gain = 1492,
  223. .gain2 = 1666,
  224. },
  225. [3] = {
  226. .num = ST_MAGN_FS_AVL_4000MG,
  227. .value = 0x04,
  228. .gain = 2222,
  229. .gain2 = 2500,
  230. },
  231. [4] = {
  232. .num = ST_MAGN_FS_AVL_4700MG,
  233. .value = 0x05,
  234. .gain = 2500,
  235. .gain2 = 2816,
  236. },
  237. [5] = {
  238. .num = ST_MAGN_FS_AVL_5600MG,
  239. .value = 0x06,
  240. .gain = 3030,
  241. .gain2 = 3389,
  242. },
  243. [6] = {
  244. .num = ST_MAGN_FS_AVL_8100MG,
  245. .value = 0x07,
  246. .gain = 4347,
  247. .gain2 = 4878,
  248. },
  249. },
  250. },
  251. .multi_read_bit = false,
  252. .bootime = 2,
  253. },
  254. {
  255. .wai = 0x3d,
  256. .wai_addr = ST_SENSORS_DEFAULT_WAI_ADDRESS,
  257. .sensors_supported = {
  258. [0] = LIS3MDL_MAGN_DEV_NAME,
  259. },
  260. .ch = (struct iio_chan_spec *)st_magn_2_16bit_channels,
  261. .odr = {
  262. .addr = 0x20,
  263. .mask = 0x1c,
  264. .odr_avl = {
  265. { .hz = 1, .value = 0x00 },
  266. { .hz = 2, .value = 0x01 },
  267. { .hz = 3, .value = 0x02 },
  268. { .hz = 5, .value = 0x03 },
  269. { .hz = 10, .value = 0x04 },
  270. { .hz = 20, .value = 0x05 },
  271. { .hz = 40, .value = 0x06 },
  272. { .hz = 80, .value = 0x07 },
  273. },
  274. },
  275. .pw = {
  276. .addr = 0x22,
  277. .mask = 0x03,
  278. .value_on = 0x00,
  279. .value_off = 0x03,
  280. },
  281. .fs = {
  282. .addr = 0x21,
  283. .mask = 0x60,
  284. .fs_avl = {
  285. [0] = {
  286. .num = ST_MAGN_FS_AVL_4000MG,
  287. .value = 0x00,
  288. .gain = 146,
  289. },
  290. [1] = {
  291. .num = ST_MAGN_FS_AVL_8000MG,
  292. .value = 0x01,
  293. .gain = 292,
  294. },
  295. [2] = {
  296. .num = ST_MAGN_FS_AVL_12000MG,
  297. .value = 0x02,
  298. .gain = 438,
  299. },
  300. [3] = {
  301. .num = ST_MAGN_FS_AVL_16000MG,
  302. .value = 0x03,
  303. .gain = 584,
  304. },
  305. },
  306. },
  307. .drdy_irq = {
  308. /* drdy line is routed drdy pin */
  309. .stat_drdy = {
  310. .addr = ST_SENSORS_DEFAULT_STAT_ADDR,
  311. .mask = 0x07,
  312. },
  313. },
  314. .sim = {
  315. .addr = 0x22,
  316. .value = BIT(2),
  317. },
  318. .multi_read_bit = true,
  319. .bootime = 2,
  320. },
  321. {
  322. .wai = 0x40,
  323. .wai_addr = 0x4f,
  324. .sensors_supported = {
  325. [0] = LSM303AGR_MAGN_DEV_NAME,
  326. [1] = LIS2MDL_MAGN_DEV_NAME,
  327. },
  328. .ch = (struct iio_chan_spec *)st_magn_3_16bit_channels,
  329. .odr = {
  330. .addr = 0x60,
  331. .mask = 0x0c,
  332. .odr_avl = {
  333. { .hz = 10, .value = 0x00 },
  334. { .hz = 20, .value = 0x01 },
  335. { .hz = 50, .value = 0x02 },
  336. { .hz = 100, .value = 0x03 },
  337. },
  338. },
  339. .pw = {
  340. .addr = 0x60,
  341. .mask = 0x03,
  342. .value_on = 0x00,
  343. .value_off = 0x03,
  344. },
  345. .fs = {
  346. .fs_avl = {
  347. [0] = {
  348. .num = ST_MAGN_FS_AVL_15000MG,
  349. .gain = 1500,
  350. },
  351. },
  352. },
  353. .bdu = {
  354. .addr = 0x62,
  355. .mask = 0x10,
  356. },
  357. .drdy_irq = {
  358. .int1 = {
  359. .addr = 0x62,
  360. .mask = 0x01,
  361. },
  362. .stat_drdy = {
  363. .addr = 0x67,
  364. .mask = 0x07,
  365. },
  366. },
  367. .multi_read_bit = false,
  368. .bootime = 2,
  369. },
  370. };
  371. static int st_magn_read_raw(struct iio_dev *indio_dev,
  372. struct iio_chan_spec const *ch, int *val,
  373. int *val2, long mask)
  374. {
  375. int err;
  376. struct st_sensor_data *mdata = iio_priv(indio_dev);
  377. switch (mask) {
  378. case IIO_CHAN_INFO_RAW:
  379. err = st_sensors_read_info_raw(indio_dev, ch, val);
  380. if (err < 0)
  381. goto read_error;
  382. return IIO_VAL_INT;
  383. case IIO_CHAN_INFO_SCALE:
  384. *val = 0;
  385. if ((ch->scan_index == ST_SENSORS_SCAN_Z) &&
  386. (mdata->current_fullscale->gain2 != 0))
  387. *val2 = mdata->current_fullscale->gain2;
  388. else
  389. *val2 = mdata->current_fullscale->gain;
  390. return IIO_VAL_INT_PLUS_MICRO;
  391. case IIO_CHAN_INFO_SAMP_FREQ:
  392. *val = mdata->odr;
  393. return IIO_VAL_INT;
  394. default:
  395. return -EINVAL;
  396. }
  397. read_error:
  398. return err;
  399. }
  400. static int st_magn_write_raw(struct iio_dev *indio_dev,
  401. struct iio_chan_spec const *chan, int val, int val2, long mask)
  402. {
  403. int err;
  404. switch (mask) {
  405. case IIO_CHAN_INFO_SCALE:
  406. err = st_sensors_set_fullscale_by_gain(indio_dev, val2);
  407. break;
  408. case IIO_CHAN_INFO_SAMP_FREQ:
  409. if (val2)
  410. return -EINVAL;
  411. mutex_lock(&indio_dev->mlock);
  412. err = st_sensors_set_odr(indio_dev, val);
  413. mutex_unlock(&indio_dev->mlock);
  414. return err;
  415. default:
  416. err = -EINVAL;
  417. }
  418. return err;
  419. }
  420. static ST_SENSORS_DEV_ATTR_SAMP_FREQ_AVAIL();
  421. static ST_SENSORS_DEV_ATTR_SCALE_AVAIL(in_magn_scale_available);
  422. static struct attribute *st_magn_attributes[] = {
  423. &iio_dev_attr_sampling_frequency_available.dev_attr.attr,
  424. &iio_dev_attr_in_magn_scale_available.dev_attr.attr,
  425. NULL,
  426. };
  427. static const struct attribute_group st_magn_attribute_group = {
  428. .attrs = st_magn_attributes,
  429. };
  430. static const struct iio_info magn_info = {
  431. .attrs = &st_magn_attribute_group,
  432. .read_raw = &st_magn_read_raw,
  433. .write_raw = &st_magn_write_raw,
  434. .debugfs_reg_access = &st_sensors_debugfs_reg_access,
  435. };
  436. #ifdef CONFIG_IIO_TRIGGER
  437. static const struct iio_trigger_ops st_magn_trigger_ops = {
  438. .set_trigger_state = ST_MAGN_TRIGGER_SET_STATE,
  439. .validate_device = st_sensors_validate_device,
  440. };
  441. #define ST_MAGN_TRIGGER_OPS (&st_magn_trigger_ops)
  442. #else
  443. #define ST_MAGN_TRIGGER_OPS NULL
  444. #endif
  445. int st_magn_common_probe(struct iio_dev *indio_dev)
  446. {
  447. struct st_sensor_data *mdata = iio_priv(indio_dev);
  448. int irq = mdata->get_irq_data_ready(indio_dev);
  449. int err;
  450. indio_dev->modes = INDIO_DIRECT_MODE;
  451. indio_dev->info = &magn_info;
  452. mutex_init(&mdata->tb.buf_lock);
  453. err = st_sensors_power_enable(indio_dev);
  454. if (err)
  455. return err;
  456. err = st_sensors_check_device_support(indio_dev,
  457. ARRAY_SIZE(st_magn_sensors_settings),
  458. st_magn_sensors_settings);
  459. if (err < 0)
  460. goto st_magn_power_off;
  461. mdata->num_data_channels = ST_MAGN_NUMBER_DATA_CHANNELS;
  462. mdata->multiread_bit = mdata->sensor_settings->multi_read_bit;
  463. indio_dev->channels = mdata->sensor_settings->ch;
  464. indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS;
  465. mdata->current_fullscale = (struct st_sensor_fullscale_avl *)
  466. &mdata->sensor_settings->fs.fs_avl[0];
  467. mdata->odr = mdata->sensor_settings->odr.odr_avl[0].hz;
  468. err = st_sensors_init_sensor(indio_dev, NULL);
  469. if (err < 0)
  470. goto st_magn_power_off;
  471. err = st_magn_allocate_ring(indio_dev);
  472. if (err < 0)
  473. goto st_magn_power_off;
  474. if (irq > 0) {
  475. err = st_sensors_allocate_trigger(indio_dev,
  476. ST_MAGN_TRIGGER_OPS);
  477. if (err < 0)
  478. goto st_magn_probe_trigger_error;
  479. }
  480. err = iio_device_register(indio_dev);
  481. if (err)
  482. goto st_magn_device_register_error;
  483. dev_info(&indio_dev->dev, "registered magnetometer %s\n",
  484. indio_dev->name);
  485. return 0;
  486. st_magn_device_register_error:
  487. if (irq > 0)
  488. st_sensors_deallocate_trigger(indio_dev);
  489. st_magn_probe_trigger_error:
  490. st_magn_deallocate_ring(indio_dev);
  491. st_magn_power_off:
  492. st_sensors_power_disable(indio_dev);
  493. return err;
  494. }
  495. EXPORT_SYMBOL(st_magn_common_probe);
  496. void st_magn_common_remove(struct iio_dev *indio_dev)
  497. {
  498. struct st_sensor_data *mdata = iio_priv(indio_dev);
  499. st_sensors_power_disable(indio_dev);
  500. iio_device_unregister(indio_dev);
  501. if (mdata->get_irq_data_ready(indio_dev) > 0)
  502. st_sensors_deallocate_trigger(indio_dev);
  503. st_magn_deallocate_ring(indio_dev);
  504. }
  505. EXPORT_SYMBOL(st_magn_common_remove);
  506. MODULE_AUTHOR("Denis Ciocca <denis.ciocca@st.com>");
  507. MODULE_DESCRIPTION("STMicroelectronics magnetometers driver");
  508. MODULE_LICENSE("GPL v2");