ade7754.c 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587
  1. /*
  2. * ADE7754 Polyphase Multifunction Energy Metering IC Driver
  3. *
  4. * Copyright 2010 Analog Devices Inc.
  5. *
  6. * Licensed under the GPL-2 or later.
  7. */
  8. #include <linux/interrupt.h>
  9. #include <linux/irq.h>
  10. #include <linux/delay.h>
  11. #include <linux/mutex.h>
  12. #include <linux/device.h>
  13. #include <linux/kernel.h>
  14. #include <linux/spi/spi.h>
  15. #include <linux/slab.h>
  16. #include <linux/sysfs.h>
  17. #include <linux/list.h>
  18. #include <linux/module.h>
  19. #include <linux/iio/iio.h>
  20. #include <linux/iio/sysfs.h>
  21. #include "meter.h"
  22. #include "ade7754.h"
  23. static int ade7754_spi_write_reg_8(struct device *dev,
  24. u8 reg_address,
  25. u8 val)
  26. {
  27. int ret;
  28. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  29. struct ade7754_state *st = iio_priv(indio_dev);
  30. mutex_lock(&st->buf_lock);
  31. st->tx[0] = ADE7754_WRITE_REG(reg_address);
  32. st->tx[1] = val;
  33. ret = spi_write(st->us, st->tx, 2);
  34. mutex_unlock(&st->buf_lock);
  35. return ret;
  36. }
  37. static int ade7754_spi_write_reg_16(struct device *dev,
  38. u8 reg_address,
  39. u16 value)
  40. {
  41. int ret;
  42. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  43. struct ade7754_state *st = iio_priv(indio_dev);
  44. mutex_lock(&st->buf_lock);
  45. st->tx[0] = ADE7754_WRITE_REG(reg_address);
  46. st->tx[1] = (value >> 8) & 0xFF;
  47. st->tx[2] = value & 0xFF;
  48. ret = spi_write(st->us, st->tx, 3);
  49. mutex_unlock(&st->buf_lock);
  50. return ret;
  51. }
  52. static int ade7754_spi_read_reg_8(struct device *dev,
  53. u8 reg_address,
  54. u8 *val)
  55. {
  56. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  57. struct ade7754_state *st = iio_priv(indio_dev);
  58. int ret;
  59. ret = spi_w8r8(st->us, ADE7754_READ_REG(reg_address));
  60. if (ret < 0) {
  61. dev_err(&st->us->dev, "problem when reading 8 bit register 0x%02X",
  62. reg_address);
  63. return ret;
  64. }
  65. *val = ret;
  66. return 0;
  67. }
  68. static int ade7754_spi_read_reg_16(struct device *dev,
  69. u8 reg_address,
  70. u16 *val)
  71. {
  72. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  73. struct ade7754_state *st = iio_priv(indio_dev);
  74. int ret;
  75. ret = spi_w8r16be(st->us, ADE7754_READ_REG(reg_address));
  76. if (ret < 0) {
  77. dev_err(&st->us->dev, "problem when reading 16 bit register 0x%02X",
  78. reg_address);
  79. return ret;
  80. }
  81. *val = ret;
  82. return 0;
  83. }
  84. static int ade7754_spi_read_reg_24(struct device *dev,
  85. u8 reg_address,
  86. u32 *val)
  87. {
  88. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  89. struct ade7754_state *st = iio_priv(indio_dev);
  90. int ret;
  91. struct spi_transfer xfers[] = {
  92. {
  93. .tx_buf = st->tx,
  94. .rx_buf = st->rx,
  95. .bits_per_word = 8,
  96. .len = 4,
  97. },
  98. };
  99. mutex_lock(&st->buf_lock);
  100. st->tx[0] = ADE7754_READ_REG(reg_address);
  101. st->tx[1] = 0;
  102. st->tx[2] = 0;
  103. st->tx[3] = 0;
  104. ret = spi_sync_transfer(st->us, xfers, ARRAY_SIZE(xfers));
  105. if (ret) {
  106. dev_err(&st->us->dev, "problem when reading 24 bit register 0x%02X",
  107. reg_address);
  108. goto error_ret;
  109. }
  110. *val = (st->rx[1] << 16) | (st->rx[2] << 8) | st->rx[3];
  111. error_ret:
  112. mutex_unlock(&st->buf_lock);
  113. return ret;
  114. }
  115. static ssize_t ade7754_read_8bit(struct device *dev,
  116. struct device_attribute *attr,
  117. char *buf)
  118. {
  119. int ret;
  120. u8 val = 0;
  121. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  122. ret = ade7754_spi_read_reg_8(dev, this_attr->address, &val);
  123. if (ret)
  124. return ret;
  125. return sprintf(buf, "%u\n", val);
  126. }
  127. static ssize_t ade7754_read_16bit(struct device *dev,
  128. struct device_attribute *attr,
  129. char *buf)
  130. {
  131. int ret;
  132. u16 val = 0;
  133. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  134. ret = ade7754_spi_read_reg_16(dev, this_attr->address, &val);
  135. if (ret)
  136. return ret;
  137. return sprintf(buf, "%u\n", val);
  138. }
  139. static ssize_t ade7754_read_24bit(struct device *dev,
  140. struct device_attribute *attr,
  141. char *buf)
  142. {
  143. int ret;
  144. u32 val = 0;
  145. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  146. ret = ade7754_spi_read_reg_24(dev, this_attr->address, &val);
  147. if (ret)
  148. return ret;
  149. return sprintf(buf, "%u\n", val & 0xFFFFFF);
  150. }
  151. static ssize_t ade7754_write_8bit(struct device *dev,
  152. struct device_attribute *attr,
  153. const char *buf,
  154. size_t len)
  155. {
  156. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  157. int ret;
  158. u8 val;
  159. ret = kstrtou8(buf, 10, &val);
  160. if (ret)
  161. goto error_ret;
  162. ret = ade7754_spi_write_reg_8(dev, this_attr->address, val);
  163. error_ret:
  164. return ret ? ret : len;
  165. }
  166. static ssize_t ade7754_write_16bit(struct device *dev,
  167. struct device_attribute *attr,
  168. const char *buf,
  169. size_t len)
  170. {
  171. struct iio_dev_attr *this_attr = to_iio_dev_attr(attr);
  172. int ret;
  173. u16 val;
  174. ret = kstrtou16(buf, 10, &val);
  175. if (ret)
  176. goto error_ret;
  177. ret = ade7754_spi_write_reg_16(dev, this_attr->address, val);
  178. error_ret:
  179. return ret ? ret : len;
  180. }
  181. static int ade7754_reset(struct device *dev)
  182. {
  183. int ret;
  184. u8 val;
  185. ret = ade7754_spi_read_reg_8(dev, ADE7754_OPMODE, &val);
  186. if (ret < 0)
  187. return ret;
  188. val |= BIT(6); /* Software Chip Reset */
  189. return ade7754_spi_write_reg_8(dev, ADE7754_OPMODE, val);
  190. }
  191. static IIO_DEV_ATTR_AENERGY(ade7754_read_24bit, ADE7754_AENERGY);
  192. static IIO_DEV_ATTR_LAENERGY(ade7754_read_24bit, ADE7754_LAENERGY);
  193. static IIO_DEV_ATTR_VAENERGY(ade7754_read_24bit, ADE7754_VAENERGY);
  194. static IIO_DEV_ATTR_LVAENERGY(ade7754_read_24bit, ADE7754_LVAENERGY);
  195. static IIO_DEV_ATTR_VPEAK(S_IWUSR | S_IRUGO,
  196. ade7754_read_8bit,
  197. ade7754_write_8bit,
  198. ADE7754_VPEAK);
  199. static IIO_DEV_ATTR_IPEAK(S_IWUSR | S_IRUGO,
  200. ade7754_read_8bit,
  201. ade7754_write_8bit,
  202. ADE7754_VPEAK);
  203. static IIO_DEV_ATTR_APHCAL(S_IWUSR | S_IRUGO,
  204. ade7754_read_8bit,
  205. ade7754_write_8bit,
  206. ADE7754_APHCAL);
  207. static IIO_DEV_ATTR_BPHCAL(S_IWUSR | S_IRUGO,
  208. ade7754_read_8bit,
  209. ade7754_write_8bit,
  210. ADE7754_BPHCAL);
  211. static IIO_DEV_ATTR_CPHCAL(S_IWUSR | S_IRUGO,
  212. ade7754_read_8bit,
  213. ade7754_write_8bit,
  214. ADE7754_CPHCAL);
  215. static IIO_DEV_ATTR_AAPOS(S_IWUSR | S_IRUGO,
  216. ade7754_read_16bit,
  217. ade7754_write_16bit,
  218. ADE7754_AAPOS);
  219. static IIO_DEV_ATTR_BAPOS(S_IWUSR | S_IRUGO,
  220. ade7754_read_16bit,
  221. ade7754_write_16bit,
  222. ADE7754_BAPOS);
  223. static IIO_DEV_ATTR_CAPOS(S_IWUSR | S_IRUGO,
  224. ade7754_read_16bit,
  225. ade7754_write_16bit,
  226. ADE7754_CAPOS);
  227. static IIO_DEV_ATTR_WDIV(S_IWUSR | S_IRUGO,
  228. ade7754_read_8bit,
  229. ade7754_write_8bit,
  230. ADE7754_WDIV);
  231. static IIO_DEV_ATTR_VADIV(S_IWUSR | S_IRUGO,
  232. ade7754_read_8bit,
  233. ade7754_write_8bit,
  234. ADE7754_VADIV);
  235. static IIO_DEV_ATTR_CFNUM(S_IWUSR | S_IRUGO,
  236. ade7754_read_16bit,
  237. ade7754_write_16bit,
  238. ADE7754_CFNUM);
  239. static IIO_DEV_ATTR_CFDEN(S_IWUSR | S_IRUGO,
  240. ade7754_read_16bit,
  241. ade7754_write_16bit,
  242. ADE7754_CFDEN);
  243. static IIO_DEV_ATTR_ACTIVE_POWER_A_GAIN(S_IWUSR | S_IRUGO,
  244. ade7754_read_16bit,
  245. ade7754_write_16bit,
  246. ADE7754_AAPGAIN);
  247. static IIO_DEV_ATTR_ACTIVE_POWER_B_GAIN(S_IWUSR | S_IRUGO,
  248. ade7754_read_16bit,
  249. ade7754_write_16bit,
  250. ADE7754_BAPGAIN);
  251. static IIO_DEV_ATTR_ACTIVE_POWER_C_GAIN(S_IWUSR | S_IRUGO,
  252. ade7754_read_16bit,
  253. ade7754_write_16bit,
  254. ADE7754_CAPGAIN);
  255. static IIO_DEV_ATTR_AIRMS(S_IRUGO,
  256. ade7754_read_24bit,
  257. NULL,
  258. ADE7754_AIRMS);
  259. static IIO_DEV_ATTR_BIRMS(S_IRUGO,
  260. ade7754_read_24bit,
  261. NULL,
  262. ADE7754_BIRMS);
  263. static IIO_DEV_ATTR_CIRMS(S_IRUGO,
  264. ade7754_read_24bit,
  265. NULL,
  266. ADE7754_CIRMS);
  267. static IIO_DEV_ATTR_AVRMS(S_IRUGO,
  268. ade7754_read_24bit,
  269. NULL,
  270. ADE7754_AVRMS);
  271. static IIO_DEV_ATTR_BVRMS(S_IRUGO,
  272. ade7754_read_24bit,
  273. NULL,
  274. ADE7754_BVRMS);
  275. static IIO_DEV_ATTR_CVRMS(S_IRUGO,
  276. ade7754_read_24bit,
  277. NULL,
  278. ADE7754_CVRMS);
  279. static IIO_DEV_ATTR_AIRMSOS(S_IRUGO,
  280. ade7754_read_16bit,
  281. ade7754_write_16bit,
  282. ADE7754_AIRMSOS);
  283. static IIO_DEV_ATTR_BIRMSOS(S_IRUGO,
  284. ade7754_read_16bit,
  285. ade7754_write_16bit,
  286. ADE7754_BIRMSOS);
  287. static IIO_DEV_ATTR_CIRMSOS(S_IRUGO,
  288. ade7754_read_16bit,
  289. ade7754_write_16bit,
  290. ADE7754_CIRMSOS);
  291. static IIO_DEV_ATTR_AVRMSOS(S_IRUGO,
  292. ade7754_read_16bit,
  293. ade7754_write_16bit,
  294. ADE7754_AVRMSOS);
  295. static IIO_DEV_ATTR_BVRMSOS(S_IRUGO,
  296. ade7754_read_16bit,
  297. ade7754_write_16bit,
  298. ADE7754_BVRMSOS);
  299. static IIO_DEV_ATTR_CVRMSOS(S_IRUGO,
  300. ade7754_read_16bit,
  301. ade7754_write_16bit,
  302. ADE7754_CVRMSOS);
  303. static int ade7754_set_irq(struct device *dev, bool enable)
  304. {
  305. int ret;
  306. u16 irqen;
  307. ret = ade7754_spi_read_reg_16(dev, ADE7754_IRQEN, &irqen);
  308. if (ret)
  309. goto error_ret;
  310. if (enable)
  311. irqen |= BIT(14); /* Enables an interrupt when a data is
  312. present in the waveform register */
  313. else
  314. irqen &= ~BIT(14);
  315. ret = ade7754_spi_write_reg_16(dev, ADE7754_IRQEN, irqen);
  316. if (ret)
  317. goto error_ret;
  318. error_ret:
  319. return ret;
  320. }
  321. /* Power down the device */
  322. static int ade7754_stop_device(struct device *dev)
  323. {
  324. int ret;
  325. u8 val;
  326. ret = ade7754_spi_read_reg_8(dev, ADE7754_OPMODE, &val);
  327. if (ret < 0) {
  328. dev_err(dev, "unable to power down the device, error: %d",
  329. ret);
  330. return ret;
  331. }
  332. val |= 7 << 3; /* ADE7754 powered down */
  333. return ade7754_spi_write_reg_8(dev, ADE7754_OPMODE, val);
  334. }
  335. static int ade7754_initial_setup(struct iio_dev *indio_dev)
  336. {
  337. int ret;
  338. struct ade7754_state *st = iio_priv(indio_dev);
  339. struct device *dev = &indio_dev->dev;
  340. /* use low spi speed for init */
  341. st->us->mode = SPI_MODE_3;
  342. spi_setup(st->us);
  343. /* Disable IRQ */
  344. ret = ade7754_set_irq(dev, false);
  345. if (ret) {
  346. dev_err(dev, "disable irq failed");
  347. goto err_ret;
  348. }
  349. ade7754_reset(dev);
  350. msleep(ADE7754_STARTUP_DELAY);
  351. err_ret:
  352. return ret;
  353. }
  354. static ssize_t ade7754_read_frequency(struct device *dev,
  355. struct device_attribute *attr,
  356. char *buf)
  357. {
  358. int ret;
  359. u8 t;
  360. int sps;
  361. ret = ade7754_spi_read_reg_8(dev,
  362. ADE7754_WAVMODE,
  363. &t);
  364. if (ret)
  365. return ret;
  366. t = (t >> 3) & 0x3;
  367. sps = 26000 / (1 + t);
  368. return sprintf(buf, "%d\n", sps);
  369. }
  370. static ssize_t ade7754_write_frequency(struct device *dev,
  371. struct device_attribute *attr,
  372. const char *buf,
  373. size_t len)
  374. {
  375. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  376. struct ade7754_state *st = iio_priv(indio_dev);
  377. u16 val;
  378. int ret;
  379. u8 reg, t;
  380. ret = kstrtou16(buf, 10, &val);
  381. if (ret)
  382. return ret;
  383. if (!val)
  384. return -EINVAL;
  385. mutex_lock(&indio_dev->mlock);
  386. t = 26000 / val;
  387. if (t > 0)
  388. t--;
  389. if (t > 1)
  390. st->us->max_speed_hz = ADE7754_SPI_SLOW;
  391. else
  392. st->us->max_speed_hz = ADE7754_SPI_FAST;
  393. ret = ade7754_spi_read_reg_8(dev, ADE7754_WAVMODE, &reg);
  394. if (ret)
  395. goto out;
  396. reg &= ~(3 << 3);
  397. reg |= t << 3;
  398. ret = ade7754_spi_write_reg_8(dev, ADE7754_WAVMODE, reg);
  399. out:
  400. mutex_unlock(&indio_dev->mlock);
  401. return ret ? ret : len;
  402. }
  403. static IIO_DEV_ATTR_TEMP_RAW(ade7754_read_8bit);
  404. static IIO_CONST_ATTR(in_temp_offset, "129 C");
  405. static IIO_CONST_ATTR(in_temp_scale, "4 C");
  406. static IIO_DEV_ATTR_SAMP_FREQ(S_IWUSR | S_IRUGO,
  407. ade7754_read_frequency,
  408. ade7754_write_frequency);
  409. static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("26000 13000 65000 33000");
  410. static struct attribute *ade7754_attributes[] = {
  411. &iio_dev_attr_in_temp_raw.dev_attr.attr,
  412. &iio_const_attr_in_temp_offset.dev_attr.attr,
  413. &iio_const_attr_in_temp_scale.dev_attr.attr,
  414. &iio_dev_attr_sampling_frequency.dev_attr.attr,
  415. &iio_const_attr_sampling_frequency_available.dev_attr.attr,
  416. &iio_dev_attr_aenergy.dev_attr.attr,
  417. &iio_dev_attr_laenergy.dev_attr.attr,
  418. &iio_dev_attr_vaenergy.dev_attr.attr,
  419. &iio_dev_attr_lvaenergy.dev_attr.attr,
  420. &iio_dev_attr_vpeak.dev_attr.attr,
  421. &iio_dev_attr_ipeak.dev_attr.attr,
  422. &iio_dev_attr_aphcal.dev_attr.attr,
  423. &iio_dev_attr_bphcal.dev_attr.attr,
  424. &iio_dev_attr_cphcal.dev_attr.attr,
  425. &iio_dev_attr_aapos.dev_attr.attr,
  426. &iio_dev_attr_bapos.dev_attr.attr,
  427. &iio_dev_attr_capos.dev_attr.attr,
  428. &iio_dev_attr_wdiv.dev_attr.attr,
  429. &iio_dev_attr_vadiv.dev_attr.attr,
  430. &iio_dev_attr_cfnum.dev_attr.attr,
  431. &iio_dev_attr_cfden.dev_attr.attr,
  432. &iio_dev_attr_active_power_a_gain.dev_attr.attr,
  433. &iio_dev_attr_active_power_b_gain.dev_attr.attr,
  434. &iio_dev_attr_active_power_c_gain.dev_attr.attr,
  435. &iio_dev_attr_airms.dev_attr.attr,
  436. &iio_dev_attr_birms.dev_attr.attr,
  437. &iio_dev_attr_cirms.dev_attr.attr,
  438. &iio_dev_attr_avrms.dev_attr.attr,
  439. &iio_dev_attr_bvrms.dev_attr.attr,
  440. &iio_dev_attr_cvrms.dev_attr.attr,
  441. &iio_dev_attr_airmsos.dev_attr.attr,
  442. &iio_dev_attr_birmsos.dev_attr.attr,
  443. &iio_dev_attr_cirmsos.dev_attr.attr,
  444. &iio_dev_attr_avrmsos.dev_attr.attr,
  445. &iio_dev_attr_bvrmsos.dev_attr.attr,
  446. &iio_dev_attr_cvrmsos.dev_attr.attr,
  447. NULL,
  448. };
  449. static const struct attribute_group ade7754_attribute_group = {
  450. .attrs = ade7754_attributes,
  451. };
  452. static const struct iio_info ade7754_info = {
  453. .attrs = &ade7754_attribute_group,
  454. .driver_module = THIS_MODULE,
  455. };
  456. static int ade7754_probe(struct spi_device *spi)
  457. {
  458. int ret;
  459. struct ade7754_state *st;
  460. struct iio_dev *indio_dev;
  461. /* setup the industrialio driver allocated elements */
  462. indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
  463. if (!indio_dev)
  464. return -ENOMEM;
  465. /* this is only used for removal purposes */
  466. spi_set_drvdata(spi, indio_dev);
  467. st = iio_priv(indio_dev);
  468. st->us = spi;
  469. mutex_init(&st->buf_lock);
  470. indio_dev->name = spi->dev.driver->name;
  471. indio_dev->dev.parent = &spi->dev;
  472. indio_dev->info = &ade7754_info;
  473. indio_dev->modes = INDIO_DIRECT_MODE;
  474. /* Get the device into a sane initial state */
  475. ret = ade7754_initial_setup(indio_dev);
  476. if (ret)
  477. goto powerdown_on_error;
  478. ret = iio_device_register(indio_dev);
  479. if (ret)
  480. goto powerdown_on_error;
  481. return ret;
  482. powerdown_on_error:
  483. ade7754_stop_device(&indio_dev->dev);
  484. return ret;
  485. }
  486. /* fixme, confirm ordering in this function */
  487. static int ade7754_remove(struct spi_device *spi)
  488. {
  489. struct iio_dev *indio_dev = spi_get_drvdata(spi);
  490. iio_device_unregister(indio_dev);
  491. ade7754_stop_device(&indio_dev->dev);
  492. return 0;
  493. }
  494. static struct spi_driver ade7754_driver = {
  495. .driver = {
  496. .name = "ade7754",
  497. },
  498. .probe = ade7754_probe,
  499. .remove = ade7754_remove,
  500. };
  501. module_spi_driver(ade7754_driver);
  502. MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
  503. MODULE_DESCRIPTION("Analog Devices ADE7754 Polyphase Multifunction Energy Metering IC Driver");
  504. MODULE_LICENSE("GPL v2");
  505. MODULE_ALIAS("spi:ad7754");