PageRenderTime 55ms CodeModel.GetById 17ms RepoModel.GetById 1ms app.codeStats 0ms

/drivers/staging/iio/dds/ad9834.c

https://github.com/mstsirkin/linux
C | 464 lines | 381 code | 72 blank | 11 comment | 65 complexity | 0cf290a6e03ad9ecf62c51499748b587 MD5 | raw file
  1. /*
  2. * AD9833/AD9834/AD9837/AD9838 SPI DDS driver
  3. *
  4. * Copyright 2010-2011 Analog Devices Inc.
  5. *
  6. * Licensed under the GPL-2.
  7. */
  8. #include <linux/interrupt.h>
  9. #include <linux/workqueue.h>
  10. #include <linux/device.h>
  11. #include <linux/kernel.h>
  12. #include <linux/slab.h>
  13. #include <linux/sysfs.h>
  14. #include <linux/list.h>
  15. #include <linux/spi/spi.h>
  16. #include <linux/regulator/consumer.h>
  17. #include <linux/err.h>
  18. #include <asm/div64.h>
  19. #include "../iio.h"
  20. #include "../sysfs.h"
  21. #include "dds.h"
  22. #include "ad9834.h"
  23. static unsigned int ad9834_calc_freqreg(unsigned long mclk, unsigned long fout)
  24. {
  25. unsigned long long freqreg = (u64) fout * (u64) (1 << AD9834_FREQ_BITS);
  26. do_div(freqreg, mclk);
  27. return freqreg;
  28. }
  29. static int ad9834_write_frequency(struct ad9834_state *st,
  30. unsigned long addr, unsigned long fout)
  31. {
  32. unsigned long regval;
  33. if (fout > (st->mclk / 2))
  34. return -EINVAL;
  35. regval = ad9834_calc_freqreg(st->mclk, fout);
  36. st->freq_data[0] = cpu_to_be16(addr | (regval &
  37. RES_MASK(AD9834_FREQ_BITS / 2)));
  38. st->freq_data[1] = cpu_to_be16(addr | ((regval >>
  39. (AD9834_FREQ_BITS / 2)) &
  40. RES_MASK(AD9834_FREQ_BITS / 2)));
  41. return spi_sync(st->spi, &st->freq_msg);
  42. }
  43. static int ad9834_write_phase(struct ad9834_state *st,
  44. unsigned long addr, unsigned long phase)
  45. {
  46. if (phase > (1 << AD9834_PHASE_BITS))
  47. return -EINVAL;
  48. st->data = cpu_to_be16(addr | phase);
  49. return spi_sync(st->spi, &st->msg);
  50. }
  51. static ssize_t ad9834_write(struct device *dev,
  52. struct device_attribute *attr,
  53. const char *buf,
  54. size_t len)
  55. {
  56. struct iio_dev *dev_info = dev_get_drvdata(dev);
  57. struct ad9834_state *st = iio_priv(dev_info);
  58. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  59. int ret;
  60. long val;
  61. ret = strict_strtoul(buf, 10, &val);
  62. if (ret)
  63. goto error_ret;
  64. mutex_lock(&dev_info->mlock);
  65. switch (this_attr->address) {
  66. case AD9834_REG_FREQ0:
  67. case AD9834_REG_FREQ1:
  68. ret = ad9834_write_frequency(st, this_attr->address, val);
  69. break;
  70. case AD9834_REG_PHASE0:
  71. case AD9834_REG_PHASE1:
  72. ret = ad9834_write_phase(st, this_attr->address, val);
  73. break;
  74. case AD9834_OPBITEN:
  75. if (st->control & AD9834_MODE) {
  76. ret = -EINVAL; /* AD9843 reserved mode */
  77. break;
  78. }
  79. if (val)
  80. st->control |= AD9834_OPBITEN;
  81. else
  82. st->control &= ~AD9834_OPBITEN;
  83. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  84. ret = spi_sync(st->spi, &st->msg);
  85. break;
  86. case AD9834_PIN_SW:
  87. if (val)
  88. st->control |= AD9834_PIN_SW;
  89. else
  90. st->control &= ~AD9834_PIN_SW;
  91. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  92. ret = spi_sync(st->spi, &st->msg);
  93. break;
  94. case AD9834_FSEL:
  95. case AD9834_PSEL:
  96. if (val == 0)
  97. st->control &= ~(this_attr->address | AD9834_PIN_SW);
  98. else if (val == 1) {
  99. st->control |= this_attr->address;
  100. st->control &= ~AD9834_PIN_SW;
  101. } else {
  102. ret = -EINVAL;
  103. break;
  104. }
  105. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  106. ret = spi_sync(st->spi, &st->msg);
  107. break;
  108. case AD9834_RESET:
  109. if (val)
  110. st->control &= ~AD9834_RESET;
  111. else
  112. st->control |= AD9834_RESET;
  113. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  114. ret = spi_sync(st->spi, &st->msg);
  115. break;
  116. default:
  117. ret = -ENODEV;
  118. }
  119. mutex_unlock(&dev_info->mlock);
  120. error_ret:
  121. return ret ? ret : len;
  122. }
  123. static ssize_t ad9834_store_wavetype(struct device *dev,
  124. struct device_attribute *attr,
  125. const char *buf,
  126. size_t len)
  127. {
  128. struct iio_dev *dev_info = dev_get_drvdata(dev);
  129. struct ad9834_state *st = iio_priv(dev_info);
  130. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  131. int ret = 0;
  132. bool is_ad9833_7 = (st->devid == ID_AD9833) || (st->devid == ID_AD9837);
  133. mutex_lock(&dev_info->mlock);
  134. switch (this_attr->address) {
  135. case 0:
  136. if (sysfs_streq(buf, "sine")) {
  137. st->control &= ~AD9834_MODE;
  138. if (is_ad9833_7)
  139. st->control &= ~AD9834_OPBITEN;
  140. } else if (sysfs_streq(buf, "triangle")) {
  141. if (is_ad9833_7) {
  142. st->control &= ~AD9834_OPBITEN;
  143. st->control |= AD9834_MODE;
  144. } else if (st->control & AD9834_OPBITEN) {
  145. ret = -EINVAL; /* AD9843 reserved mode */
  146. } else {
  147. st->control |= AD9834_MODE;
  148. }
  149. } else if (is_ad9833_7 && sysfs_streq(buf, "square")) {
  150. st->control &= ~AD9834_MODE;
  151. st->control |= AD9834_OPBITEN;
  152. } else {
  153. ret = -EINVAL;
  154. }
  155. break;
  156. case 1:
  157. if (sysfs_streq(buf, "square") &&
  158. !(st->control & AD9834_MODE)) {
  159. st->control &= ~AD9834_MODE;
  160. st->control |= AD9834_OPBITEN;
  161. } else {
  162. ret = -EINVAL;
  163. }
  164. break;
  165. default:
  166. ret = -EINVAL;
  167. break;
  168. }
  169. if (!ret) {
  170. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  171. ret = spi_sync(st->spi, &st->msg);
  172. }
  173. mutex_unlock(&dev_info->mlock);
  174. return ret ? ret : len;
  175. }
  176. static ssize_t ad9834_show_out0_wavetype_available(struct device *dev,
  177. struct device_attribute *attr,
  178. char *buf)
  179. {
  180. struct iio_dev *dev_info = dev_get_drvdata(dev);
  181. struct ad9834_state *st = iio_priv(dev_info);
  182. char *str;
  183. if ((st->devid == ID_AD9833) || (st->devid == ID_AD9837))
  184. str = "sine triangle square";
  185. else if (st->control & AD9834_OPBITEN)
  186. str = "sine";
  187. else
  188. str = "sine triangle";
  189. return sprintf(buf, "%s\n", str);
  190. }
  191. static IIO_DEVICE_ATTR(dds0_out0_wavetype_available, S_IRUGO,
  192. ad9834_show_out0_wavetype_available, NULL, 0);
  193. static ssize_t ad9834_show_out1_wavetype_available(struct device *dev,
  194. struct device_attribute *attr,
  195. char *buf)
  196. {
  197. struct iio_dev *dev_info = dev_get_drvdata(dev);
  198. struct ad9834_state *st = iio_priv(dev_info);
  199. char *str;
  200. if (st->control & AD9834_MODE)
  201. str = "";
  202. else
  203. str = "square";
  204. return sprintf(buf, "%s\n", str);
  205. }
  206. static IIO_DEVICE_ATTR(dds0_out1_wavetype_available, S_IRUGO,
  207. ad9834_show_out1_wavetype_available, NULL, 0);
  208. /**
  209. * see dds.h for further information
  210. */
  211. static IIO_DEV_ATTR_FREQ(0, 0, S_IWUSR, NULL, ad9834_write, AD9834_REG_FREQ0);
  212. static IIO_DEV_ATTR_FREQ(0, 1, S_IWUSR, NULL, ad9834_write, AD9834_REG_FREQ1);
  213. static IIO_DEV_ATTR_FREQSYMBOL(0, S_IWUSR, NULL, ad9834_write, AD9834_FSEL);
  214. static IIO_CONST_ATTR_FREQ_SCALE(0, "1"); /* 1Hz */
  215. static IIO_DEV_ATTR_PHASE(0, 0, S_IWUSR, NULL, ad9834_write, AD9834_REG_PHASE0);
  216. static IIO_DEV_ATTR_PHASE(0, 1, S_IWUSR, NULL, ad9834_write, AD9834_REG_PHASE1);
  217. static IIO_DEV_ATTR_PHASESYMBOL(0, S_IWUSR, NULL, ad9834_write, AD9834_PSEL);
  218. static IIO_CONST_ATTR_PHASE_SCALE(0, "0.0015339808"); /* 2PI/2^12 rad*/
  219. static IIO_DEV_ATTR_PINCONTROL_EN(0, S_IWUSR, NULL,
  220. ad9834_write, AD9834_PIN_SW);
  221. static IIO_DEV_ATTR_OUT_ENABLE(0, S_IWUSR, NULL, ad9834_write, AD9834_RESET);
  222. static IIO_DEV_ATTR_OUTY_ENABLE(0, 1, S_IWUSR, NULL,
  223. ad9834_write, AD9834_OPBITEN);
  224. static IIO_DEV_ATTR_OUT_WAVETYPE(0, 0, ad9834_store_wavetype, 0);
  225. static IIO_DEV_ATTR_OUT_WAVETYPE(0, 1, ad9834_store_wavetype, 1);
  226. static struct attribute *ad9834_attributes[] = {
  227. &iio_dev_attr_dds0_freq0.dev_attr.attr,
  228. &iio_dev_attr_dds0_freq1.dev_attr.attr,
  229. &iio_const_attr_dds0_freq_scale.dev_attr.attr,
  230. &iio_dev_attr_dds0_phase0.dev_attr.attr,
  231. &iio_dev_attr_dds0_phase1.dev_attr.attr,
  232. &iio_const_attr_dds0_phase_scale.dev_attr.attr,
  233. &iio_dev_attr_dds0_pincontrol_en.dev_attr.attr,
  234. &iio_dev_attr_dds0_freqsymbol.dev_attr.attr,
  235. &iio_dev_attr_dds0_phasesymbol.dev_attr.attr,
  236. &iio_dev_attr_dds0_out_enable.dev_attr.attr,
  237. &iio_dev_attr_dds0_out1_enable.dev_attr.attr,
  238. &iio_dev_attr_dds0_out0_wavetype.dev_attr.attr,
  239. &iio_dev_attr_dds0_out1_wavetype.dev_attr.attr,
  240. &iio_dev_attr_dds0_out0_wavetype_available.dev_attr.attr,
  241. &iio_dev_attr_dds0_out1_wavetype_available.dev_attr.attr,
  242. NULL,
  243. };
  244. static mode_t ad9834_attr_is_visible(struct kobject *kobj,
  245. struct attribute *attr, int n)
  246. {
  247. struct device *dev = container_of(kobj, struct device, kobj);
  248. struct iio_dev *dev_info = dev_get_drvdata(dev);
  249. struct ad9834_state *st = iio_priv(dev_info);
  250. mode_t mode = attr->mode;
  251. if (((st->devid == ID_AD9833) || (st->devid == ID_AD9837)) &&
  252. ((attr == &iio_dev_attr_dds0_out1_enable.dev_attr.attr) ||
  253. (attr == &iio_dev_attr_dds0_out1_wavetype.dev_attr.attr) ||
  254. (attr ==
  255. &iio_dev_attr_dds0_out1_wavetype_available.dev_attr.attr) ||
  256. (attr == &iio_dev_attr_dds0_pincontrol_en.dev_attr.attr)))
  257. mode = 0;
  258. return mode;
  259. }
  260. static const struct attribute_group ad9834_attribute_group = {
  261. .attrs = ad9834_attributes,
  262. .is_visible = ad9834_attr_is_visible,
  263. };
  264. static const struct iio_info ad9834_info = {
  265. .attrs = &ad9834_attribute_group,
  266. .driver_module = THIS_MODULE,
  267. };
  268. static int __devinit ad9834_probe(struct spi_device *spi)
  269. {
  270. struct ad9834_platform_data *pdata = spi->dev.platform_data;
  271. struct ad9834_state *st;
  272. struct iio_dev *indio_dev;
  273. struct regulator *reg;
  274. int ret;
  275. if (!pdata) {
  276. dev_dbg(&spi->dev, "no platform data?\n");
  277. return -ENODEV;
  278. }
  279. reg = regulator_get(&spi->dev, "vcc");
  280. if (!IS_ERR(reg)) {
  281. ret = regulator_enable(reg);
  282. if (ret)
  283. goto error_put_reg;
  284. }
  285. indio_dev = iio_allocate_device(sizeof(*st));
  286. if (indio_dev == NULL) {
  287. ret = -ENOMEM;
  288. goto error_disable_reg;
  289. }
  290. spi_set_drvdata(spi, indio_dev);
  291. st = iio_priv(indio_dev);
  292. st->mclk = pdata->mclk;
  293. st->spi = spi;
  294. st->devid = spi_get_device_id(spi)->driver_data;
  295. st->reg = reg;
  296. indio_dev->dev.parent = &spi->dev;
  297. indio_dev->name = spi_get_device_id(spi)->name;
  298. indio_dev->info = &ad9834_info;
  299. indio_dev->modes = INDIO_DIRECT_MODE;
  300. /* Setup default messages */
  301. st->xfer.tx_buf = &st->data;
  302. st->xfer.len = 2;
  303. spi_message_init(&st->msg);
  304. spi_message_add_tail(&st->xfer, &st->msg);
  305. st->freq_xfer[0].tx_buf = &st->freq_data[0];
  306. st->freq_xfer[0].len = 2;
  307. st->freq_xfer[0].cs_change = 1;
  308. st->freq_xfer[1].tx_buf = &st->freq_data[1];
  309. st->freq_xfer[1].len = 2;
  310. spi_message_init(&st->freq_msg);
  311. spi_message_add_tail(&st->freq_xfer[0], &st->freq_msg);
  312. spi_message_add_tail(&st->freq_xfer[1], &st->freq_msg);
  313. st->control = AD9834_B28 | AD9834_RESET;
  314. if (!pdata->en_div2)
  315. st->control |= AD9834_DIV2;
  316. if (!pdata->en_signbit_msb_out && (st->devid == ID_AD9834))
  317. st->control |= AD9834_SIGN_PIB;
  318. st->data = cpu_to_be16(AD9834_REG_CMD | st->control);
  319. ret = spi_sync(st->spi, &st->msg);
  320. if (ret) {
  321. dev_err(&spi->dev, "device init failed\n");
  322. goto error_free_device;
  323. }
  324. ret = ad9834_write_frequency(st, AD9834_REG_FREQ0, pdata->freq0);
  325. if (ret)
  326. goto error_free_device;
  327. ret = ad9834_write_frequency(st, AD9834_REG_FREQ1, pdata->freq1);
  328. if (ret)
  329. goto error_free_device;
  330. ret = ad9834_write_phase(st, AD9834_REG_PHASE0, pdata->phase0);
  331. if (ret)
  332. goto error_free_device;
  333. ret = ad9834_write_phase(st, AD9834_REG_PHASE1, pdata->phase1);
  334. if (ret)
  335. goto error_free_device;
  336. ret = iio_device_register(indio_dev);
  337. if (ret)
  338. goto error_free_device;
  339. return 0;
  340. error_free_device:
  341. iio_free_device(indio_dev);
  342. error_disable_reg:
  343. if (!IS_ERR(reg))
  344. regulator_disable(reg);
  345. error_put_reg:
  346. if (!IS_ERR(reg))
  347. regulator_put(reg);
  348. return ret;
  349. }
  350. static int __devexit ad9834_remove(struct spi_device *spi)
  351. {
  352. struct iio_dev *indio_dev = spi_get_drvdata(spi);
  353. struct ad9834_state *st = iio_priv(indio_dev);
  354. struct regulator *reg = st->reg;
  355. iio_device_unregister(indio_dev);
  356. if (!IS_ERR(reg)) {
  357. regulator_disable(reg);
  358. regulator_put(reg);
  359. }
  360. return 0;
  361. }
  362. static const struct spi_device_id ad9834_id[] = {
  363. {"ad9833", ID_AD9833},
  364. {"ad9834", ID_AD9834},
  365. {"ad9837", ID_AD9837},
  366. {"ad9838", ID_AD9838},
  367. {}
  368. };
  369. static struct spi_driver ad9834_driver = {
  370. .driver = {
  371. .name = "ad9834",
  372. .bus = &spi_bus_type,
  373. .owner = THIS_MODULE,
  374. },
  375. .probe = ad9834_probe,
  376. .remove = __devexit_p(ad9834_remove),
  377. .id_table = ad9834_id,
  378. };
  379. static int __init ad9834_init(void)
  380. {
  381. return spi_register_driver(&ad9834_driver);
  382. }
  383. module_init(ad9834_init);
  384. static void __exit ad9834_exit(void)
  385. {
  386. spi_unregister_driver(&ad9834_driver);
  387. }
  388. module_exit(ad9834_exit);
  389. MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
  390. MODULE_DESCRIPTION("Analog Devices AD9833/AD9834/AD9837/AD9838 DDS");
  391. MODULE_LICENSE("GPL v2");
  392. MODULE_ALIAS("spi:ad9834");