apds9306.c 36 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /*
  3. * APDS-9306/APDS-9306-065 Ambient Light Sensor
  4. * I2C Address: 0x52
  5. * Datasheet: https://docs.broadcom.com/doc/AV02-4755EN
  6. *
  7. * Copyright (C) 2024 Subhajit Ghosh <subhajit.ghosh@tweaklogic.com>
  8. */
  9. #include <linux/bits.h>
  10. #include <linux/cleanup.h>
  11. #include <linux/delay.h>
  12. #include <linux/err.h>
  13. #include <linux/i2c.h>
  14. #include <linux/interrupt.h>
  15. #include <linux/minmax.h>
  16. #include <linux/module.h>
  17. #include <linux/mutex.h>
  18. #include <linux/pm.h>
  19. #include <linux/pm_runtime.h>
  20. #include <linux/regmap.h>
  21. #include <linux/regulator/consumer.h>
  22. #include <linux/types.h>
  23. #include <linux/units.h>
  24. #include <linux/iio/iio.h>
  25. #include <linux/iio/iio-gts-helper.h>
  26. #include <linux/iio/events.h>
  27. #include <linux/iio/sysfs.h>
  28. #include <linux/unaligned.h>
  29. #define APDS9306_MAIN_CTRL_REG 0x00
  30. #define APDS9306_ALS_MEAS_RATE_REG 0x04
  31. #define APDS9306_ALS_GAIN_REG 0x05
  32. #define APDS9306_PART_ID_REG 0x06
  33. #define APDS9306_MAIN_STATUS_REG 0x07
  34. #define APDS9306_CLEAR_DATA_0_REG 0x0A
  35. #define APDS9306_CLEAR_DATA_1_REG 0x0B
  36. #define APDS9306_CLEAR_DATA_2_REG 0x0C
  37. #define APDS9306_ALS_DATA_0_REG 0x0D
  38. #define APDS9306_ALS_DATA_1_REG 0x0E
  39. #define APDS9306_ALS_DATA_2_REG 0x0F
  40. #define APDS9306_INT_CFG_REG 0x19
  41. #define APDS9306_INT_PERSISTENCE_REG 0x1A
  42. #define APDS9306_ALS_THRES_UP_0_REG 0x21
  43. #define APDS9306_ALS_THRES_UP_1_REG 0x22
  44. #define APDS9306_ALS_THRES_UP_2_REG 0x23
  45. #define APDS9306_ALS_THRES_LOW_0_REG 0x24
  46. #define APDS9306_ALS_THRES_LOW_1_REG 0x25
  47. #define APDS9306_ALS_THRES_LOW_2_REG 0x26
  48. #define APDS9306_ALS_THRES_VAR_REG 0x27
  49. #define APDS9306_ALS_INT_STAT_MASK BIT(4)
  50. #define APDS9306_ALS_DATA_STAT_MASK BIT(3)
  51. #define APDS9306_ALS_THRES_VAL_MAX (BIT(20) - 1)
  52. #define APDS9306_ALS_THRES_VAR_NUM_VALS 8
  53. #define APDS9306_ALS_PERSIST_NUM_VALS 16
  54. #define APDS9306_ALS_READ_DATA_DELAY_US (20 * USEC_PER_MSEC)
  55. #define APDS9306_NUM_REPEAT_RATES 7
  56. #define APDS9306_INT_SRC_CLEAR 0
  57. #define APDS9306_INT_SRC_ALS 1
  58. #define APDS9306_SAMP_FREQ_10HZ 0
  59. /**
  60. * struct part_id_gts_multiplier - Part no. and corresponding gts multiplier
  61. *
  62. * GTS (Gain Time Scale) are helper functions for Light sensors which along
  63. * with hardware gains also has gains associated with Integration times.
  64. *
  65. * There are two variants of the device with slightly different characteristics,
  66. * they have same ADC count for different Lux levels as mentioned in the
  67. * datasheet. This multiplier array is used to store the derived Lux per count
  68. * value for the two variants to be used by the GTS helper functions.
  69. *
  70. * @part_id: Part ID of the device
  71. * @max_scale_int: Multiplier for iio_init_iio_gts()
  72. * @max_scale_nano: Multiplier for iio_init_iio_gts()
  73. */
  74. struct part_id_gts_multiplier {
  75. int part_id;
  76. int max_scale_int;
  77. int max_scale_nano;
  78. };
  79. /*
  80. * As per the datasheet, at HW Gain = 3x, Integration time 100mS (32x),
  81. * typical 2000 ADC counts are observed for 49.8 uW per sq cm (340.134 lux)
  82. * for apds9306 and 43 uW per sq cm (293.69 lux) for apds9306-065.
  83. * Assuming lux per count is linear across all integration time ranges.
  84. *
  85. * Lux = (raw + offset) * scale; offset can be any value by userspace.
  86. * HG = Hardware Gain; ITG = Gain by changing integration time.
  87. * Scale table by IIO GTS Helpers = (1 / HG) * (1 / ITG) * Multiplier.
  88. *
  89. * The Lux values provided in the datasheet are at ITG=32x and HG=3x,
  90. * at typical 2000 count for both variants of the device.
  91. *
  92. * Lux per ADC count at 3x and 32x for apds9306 = 340.134 / 2000
  93. * Lux per ADC count at 3x and 32x for apds9306-065 = 293.69 / 2000
  94. *
  95. * The Multiplier for the scale table provided to userspace:
  96. * IIO GTS scale Multiplier for apds9306 = (340.134 / 2000) * 32 * 3 = 16.326432
  97. * and for apds9306-065 = (293.69 / 2000) * 32 * 3 = 14.09712
  98. */
  99. static const struct part_id_gts_multiplier apds9306_gts_mul[] = {
  100. {
  101. .part_id = 0xB1,
  102. .max_scale_int = 16,
  103. .max_scale_nano = 3264320,
  104. }, {
  105. .part_id = 0xB3,
  106. .max_scale_int = 14,
  107. .max_scale_nano = 9712000,
  108. },
  109. };
  110. static const int apds9306_repeat_rate_freq[APDS9306_NUM_REPEAT_RATES][2] = {
  111. { 40, 0 },
  112. { 20, 0 },
  113. { 10, 0 },
  114. { 5, 0 },
  115. { 2, 0 },
  116. { 1, 0 },
  117. { 0, 500000 },
  118. };
  119. static const int apds9306_repeat_rate_period[APDS9306_NUM_REPEAT_RATES] = {
  120. 25000, 50000, 100000, 200000, 500000, 1000000, 2000000,
  121. };
  122. /**
  123. * struct apds9306_regfields - apds9306 regmap fields definitions
  124. *
  125. * @sw_reset: Software reset regfield
  126. * @en: Enable regfield
  127. * @intg_time: Resolution regfield
  128. * @repeat_rate: Measurement Rate regfield
  129. * @gain: Hardware gain regfield
  130. * @int_src: Interrupt channel regfield
  131. * @int_thresh_var_en: Interrupt variance threshold regfield
  132. * @int_en: Interrupt enable regfield
  133. * @int_persist_val: Interrupt persistence regfield
  134. * @int_thresh_var_val: Interrupt threshold variance value regfield
  135. */
  136. struct apds9306_regfields {
  137. struct regmap_field *sw_reset;
  138. struct regmap_field *en;
  139. struct regmap_field *intg_time;
  140. struct regmap_field *repeat_rate;
  141. struct regmap_field *gain;
  142. struct regmap_field *int_src;
  143. struct regmap_field *int_thresh_var_en;
  144. struct regmap_field *int_en;
  145. struct regmap_field *int_persist_val;
  146. struct regmap_field *int_thresh_var_val;
  147. };
  148. /**
  149. * struct apds9306_data - apds9306 private data and registers definitions
  150. *
  151. * @dev: Pointer to the device structure
  152. * @gts: IIO Gain Time Scale structure
  153. * @mutex: Lock for protecting adc reads, device settings changes where
  154. * some calculations are required before or after setting or
  155. * getting the raw settings values from regmap writes or reads
  156. * respectively.
  157. * @regmap: Regmap structure pointer
  158. * @rf: Regmap register fields structure
  159. * @nlux_per_count: Nano lux per ADC count for a particular model
  160. * @read_data_available: Flag set by IRQ handler for ADC data available
  161. */
  162. struct apds9306_data {
  163. struct device *dev;
  164. struct iio_gts gts;
  165. struct mutex mutex;
  166. struct regmap *regmap;
  167. struct apds9306_regfields rf;
  168. int nlux_per_count;
  169. int read_data_available;
  170. };
  171. /*
  172. * Available scales with gain 1x - 18x, timings 3.125, 25, 50, 100, 200, 400 ms
  173. * Time impacts to gain: 1x, 8x, 16x, 32x, 64x, 128x
  174. */
  175. #define APDS9306_GSEL_1X 0x00
  176. #define APDS9306_GSEL_3X 0x01
  177. #define APDS9306_GSEL_6X 0x02
  178. #define APDS9306_GSEL_9X 0x03
  179. #define APDS9306_GSEL_18X 0x04
  180. static const struct iio_gain_sel_pair apds9306_gains[] = {
  181. GAIN_SCALE_GAIN(1, APDS9306_GSEL_1X),
  182. GAIN_SCALE_GAIN(3, APDS9306_GSEL_3X),
  183. GAIN_SCALE_GAIN(6, APDS9306_GSEL_6X),
  184. GAIN_SCALE_GAIN(9, APDS9306_GSEL_9X),
  185. GAIN_SCALE_GAIN(18, APDS9306_GSEL_18X),
  186. };
  187. #define APDS9306_MEAS_MODE_400MS 0x00
  188. #define APDS9306_MEAS_MODE_200MS 0x01
  189. #define APDS9306_MEAS_MODE_100MS 0x02
  190. #define APDS9306_MEAS_MODE_50MS 0x03
  191. #define APDS9306_MEAS_MODE_25MS 0x04
  192. #define APDS9306_MEAS_MODE_3125US 0x05
  193. static const struct iio_itime_sel_mul apds9306_itimes[] = {
  194. GAIN_SCALE_ITIME_US(400000, APDS9306_MEAS_MODE_400MS, BIT(7)),
  195. GAIN_SCALE_ITIME_US(200000, APDS9306_MEAS_MODE_200MS, BIT(6)),
  196. GAIN_SCALE_ITIME_US(100000, APDS9306_MEAS_MODE_100MS, BIT(5)),
  197. GAIN_SCALE_ITIME_US(50000, APDS9306_MEAS_MODE_50MS, BIT(4)),
  198. GAIN_SCALE_ITIME_US(25000, APDS9306_MEAS_MODE_25MS, BIT(3)),
  199. GAIN_SCALE_ITIME_US(3125, APDS9306_MEAS_MODE_3125US, BIT(0)),
  200. };
  201. static const struct iio_event_spec apds9306_event_spec[] = {
  202. {
  203. .type = IIO_EV_TYPE_THRESH,
  204. .dir = IIO_EV_DIR_RISING,
  205. .mask_shared_by_all = BIT(IIO_EV_INFO_VALUE),
  206. }, {
  207. .type = IIO_EV_TYPE_THRESH,
  208. .dir = IIO_EV_DIR_FALLING,
  209. .mask_shared_by_all = BIT(IIO_EV_INFO_VALUE),
  210. }, {
  211. .type = IIO_EV_TYPE_THRESH,
  212. .dir = IIO_EV_DIR_EITHER,
  213. .mask_shared_by_all = BIT(IIO_EV_INFO_PERIOD),
  214. .mask_separate = BIT(IIO_EV_INFO_ENABLE),
  215. }, {
  216. .type = IIO_EV_TYPE_THRESH_ADAPTIVE,
  217. .mask_shared_by_all = BIT(IIO_EV_INFO_VALUE) |
  218. BIT(IIO_EV_INFO_ENABLE),
  219. },
  220. };
  221. static const struct iio_chan_spec apds9306_channels_with_events[] = {
  222. {
  223. .type = IIO_LIGHT,
  224. .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_INT_TIME) |
  225. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  226. .info_mask_shared_by_all_available = BIT(IIO_CHAN_INFO_INT_TIME) |
  227. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  228. .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
  229. BIT(IIO_CHAN_INFO_SCALE),
  230. .info_mask_separate_available = BIT(IIO_CHAN_INFO_SCALE),
  231. .event_spec = apds9306_event_spec,
  232. .num_event_specs = ARRAY_SIZE(apds9306_event_spec),
  233. }, {
  234. .type = IIO_INTENSITY,
  235. .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_INT_TIME) |
  236. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  237. .info_mask_shared_by_all_available = BIT(IIO_CHAN_INFO_INT_TIME) |
  238. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  239. .channel2 = IIO_MOD_LIGHT_CLEAR,
  240. .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
  241. .modified = 1,
  242. .event_spec = apds9306_event_spec,
  243. .num_event_specs = ARRAY_SIZE(apds9306_event_spec),
  244. },
  245. };
  246. static const struct iio_chan_spec apds9306_channels_without_events[] = {
  247. {
  248. .type = IIO_LIGHT,
  249. .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_INT_TIME) |
  250. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  251. .info_mask_shared_by_all_available = BIT(IIO_CHAN_INFO_INT_TIME) |
  252. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  253. .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
  254. BIT(IIO_CHAN_INFO_SCALE),
  255. .info_mask_separate_available = BIT(IIO_CHAN_INFO_SCALE),
  256. }, {
  257. .type = IIO_INTENSITY,
  258. .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_INT_TIME) |
  259. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  260. .info_mask_shared_by_all_available = BIT(IIO_CHAN_INFO_INT_TIME) |
  261. BIT(IIO_CHAN_INFO_SAMP_FREQ),
  262. .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
  263. .modified = 1,
  264. .channel2 = IIO_MOD_LIGHT_CLEAR,
  265. },
  266. };
  267. /* INT_PERSISTENCE available */
  268. static IIO_CONST_ATTR(thresh_either_period_available, "[0 1 15]");
  269. /* ALS_THRESH_VAR available */
  270. static IIO_CONST_ATTR(thresh_adaptive_either_values_available, "[0 1 7]");
  271. static struct attribute *apds9306_event_attributes[] = {
  272. &iio_const_attr_thresh_either_period_available.dev_attr.attr,
  273. &iio_const_attr_thresh_adaptive_either_values_available.dev_attr.attr,
  274. NULL
  275. };
  276. static const struct attribute_group apds9306_event_attr_group = {
  277. .attrs = apds9306_event_attributes,
  278. };
  279. static const struct regmap_range apds9306_readable_ranges[] = {
  280. regmap_reg_range(APDS9306_MAIN_CTRL_REG, APDS9306_ALS_THRES_VAR_REG)
  281. };
  282. static const struct regmap_range apds9306_writable_ranges[] = {
  283. regmap_reg_range(APDS9306_MAIN_CTRL_REG, APDS9306_ALS_GAIN_REG),
  284. regmap_reg_range(APDS9306_INT_CFG_REG, APDS9306_ALS_THRES_VAR_REG)
  285. };
  286. static const struct regmap_range apds9306_volatile_ranges[] = {
  287. regmap_reg_range(APDS9306_MAIN_STATUS_REG, APDS9306_MAIN_STATUS_REG),
  288. regmap_reg_range(APDS9306_CLEAR_DATA_0_REG, APDS9306_ALS_DATA_2_REG)
  289. };
  290. static const struct regmap_range apds9306_precious_ranges[] = {
  291. regmap_reg_range(APDS9306_MAIN_STATUS_REG, APDS9306_MAIN_STATUS_REG)
  292. };
  293. static const struct regmap_access_table apds9306_readable_table = {
  294. .yes_ranges = apds9306_readable_ranges,
  295. .n_yes_ranges = ARRAY_SIZE(apds9306_readable_ranges)
  296. };
  297. static const struct regmap_access_table apds9306_writable_table = {
  298. .yes_ranges = apds9306_writable_ranges,
  299. .n_yes_ranges = ARRAY_SIZE(apds9306_writable_ranges)
  300. };
  301. static const struct regmap_access_table apds9306_volatile_table = {
  302. .yes_ranges = apds9306_volatile_ranges,
  303. .n_yes_ranges = ARRAY_SIZE(apds9306_volatile_ranges)
  304. };
  305. static const struct regmap_access_table apds9306_precious_table = {
  306. .yes_ranges = apds9306_precious_ranges,
  307. .n_yes_ranges = ARRAY_SIZE(apds9306_precious_ranges)
  308. };
  309. static const struct regmap_config apds9306_regmap = {
  310. .name = "apds9306_regmap",
  311. .reg_bits = 8,
  312. .val_bits = 8,
  313. .rd_table = &apds9306_readable_table,
  314. .wr_table = &apds9306_writable_table,
  315. .volatile_table = &apds9306_volatile_table,
  316. .precious_table = &apds9306_precious_table,
  317. .max_register = APDS9306_ALS_THRES_VAR_REG,
  318. .cache_type = REGCACHE_RBTREE,
  319. };
  320. static const struct reg_field apds9306_rf_sw_reset =
  321. REG_FIELD(APDS9306_MAIN_CTRL_REG, 4, 4);
  322. static const struct reg_field apds9306_rf_en =
  323. REG_FIELD(APDS9306_MAIN_CTRL_REG, 1, 1);
  324. static const struct reg_field apds9306_rf_intg_time =
  325. REG_FIELD(APDS9306_ALS_MEAS_RATE_REG, 4, 6);
  326. static const struct reg_field apds9306_rf_repeat_rate =
  327. REG_FIELD(APDS9306_ALS_MEAS_RATE_REG, 0, 2);
  328. static const struct reg_field apds9306_rf_gain =
  329. REG_FIELD(APDS9306_ALS_GAIN_REG, 0, 2);
  330. static const struct reg_field apds9306_rf_int_src =
  331. REG_FIELD(APDS9306_INT_CFG_REG, 4, 5);
  332. static const struct reg_field apds9306_rf_int_thresh_var_en =
  333. REG_FIELD(APDS9306_INT_CFG_REG, 3, 3);
  334. static const struct reg_field apds9306_rf_int_en =
  335. REG_FIELD(APDS9306_INT_CFG_REG, 2, 2);
  336. static const struct reg_field apds9306_rf_int_persist_val =
  337. REG_FIELD(APDS9306_INT_PERSISTENCE_REG, 4, 7);
  338. static const struct reg_field apds9306_rf_int_thresh_var_val =
  339. REG_FIELD(APDS9306_ALS_THRES_VAR_REG, 0, 2);
  340. static int apds9306_regfield_init(struct apds9306_data *data)
  341. {
  342. struct device *dev = data->dev;
  343. struct regmap *regmap = data->regmap;
  344. struct regmap_field *tmp;
  345. struct apds9306_regfields *rf = &data->rf;
  346. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_sw_reset);
  347. if (IS_ERR(tmp))
  348. return PTR_ERR(tmp);
  349. rf->sw_reset = tmp;
  350. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_en);
  351. if (IS_ERR(tmp))
  352. return PTR_ERR(tmp);
  353. rf->en = tmp;
  354. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_intg_time);
  355. if (IS_ERR(tmp))
  356. return PTR_ERR(tmp);
  357. rf->intg_time = tmp;
  358. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_repeat_rate);
  359. if (IS_ERR(tmp))
  360. return PTR_ERR(tmp);
  361. rf->repeat_rate = tmp;
  362. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_gain);
  363. if (IS_ERR(tmp))
  364. return PTR_ERR(tmp);
  365. rf->gain = tmp;
  366. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_int_src);
  367. if (IS_ERR(tmp))
  368. return PTR_ERR(tmp);
  369. rf->int_src = tmp;
  370. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_int_thresh_var_en);
  371. if (IS_ERR(tmp))
  372. return PTR_ERR(tmp);
  373. rf->int_thresh_var_en = tmp;
  374. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_int_en);
  375. if (IS_ERR(tmp))
  376. return PTR_ERR(tmp);
  377. rf->int_en = tmp;
  378. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_int_persist_val);
  379. if (IS_ERR(tmp))
  380. return PTR_ERR(tmp);
  381. rf->int_persist_val = tmp;
  382. tmp = devm_regmap_field_alloc(dev, regmap, apds9306_rf_int_thresh_var_val);
  383. if (IS_ERR(tmp))
  384. return PTR_ERR(tmp);
  385. rf->int_thresh_var_val = tmp;
  386. return 0;
  387. }
  388. static int apds9306_power_state(struct apds9306_data *data, bool state)
  389. {
  390. struct apds9306_regfields *rf = &data->rf;
  391. int ret;
  392. /* Reset not included as it causes ugly I2C bus error */
  393. if (state) {
  394. ret = regmap_field_write(rf->en, 1);
  395. if (ret)
  396. return ret;
  397. /* 5ms wake up time */
  398. fsleep(5000);
  399. return 0;
  400. }
  401. return regmap_field_write(rf->en, 0);
  402. }
  403. static int apds9306_read_data(struct apds9306_data *data, int *val, int reg)
  404. {
  405. struct device *dev = data->dev;
  406. struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  407. struct apds9306_regfields *rf = &data->rf;
  408. u64 ev_code;
  409. int ret, delay, intg_time, intg_time_idx, repeat_rate_idx, int_src;
  410. int status = 0;
  411. u8 buff[3];
  412. ret = pm_runtime_resume_and_get(data->dev);
  413. if (ret)
  414. return ret;
  415. ret = regmap_field_read(rf->intg_time, &intg_time_idx);
  416. if (ret)
  417. return ret;
  418. ret = regmap_field_read(rf->repeat_rate, &repeat_rate_idx);
  419. if (ret)
  420. return ret;
  421. ret = regmap_field_read(rf->int_src, &int_src);
  422. if (ret)
  423. return ret;
  424. intg_time = iio_gts_find_int_time_by_sel(&data->gts, intg_time_idx);
  425. if (intg_time < 0)
  426. return intg_time;
  427. /* Whichever is greater - integration time period or sampling period. */
  428. delay = max(intg_time, apds9306_repeat_rate_period[repeat_rate_idx]);
  429. /*
  430. * Clear stale data flag that might have been set by the interrupt
  431. * handler if it got data available flag set in the status reg.
  432. */
  433. data->read_data_available = 0;
  434. /*
  435. * If this function runs parallel with the interrupt handler, either
  436. * this reads and clears the status registers or the interrupt handler
  437. * does. The interrupt handler sets a flag for read data available
  438. * in our private structure which we read here.
  439. */
  440. ret = regmap_read_poll_timeout(data->regmap, APDS9306_MAIN_STATUS_REG,
  441. status, data->read_data_available ||
  442. (status & (APDS9306_ALS_DATA_STAT_MASK |
  443. APDS9306_ALS_INT_STAT_MASK)),
  444. APDS9306_ALS_READ_DATA_DELAY_US, delay * 2);
  445. if (ret)
  446. return ret;
  447. /* If we reach here before the interrupt handler we push an event */
  448. if ((status & APDS9306_ALS_INT_STAT_MASK)) {
  449. if (int_src == APDS9306_INT_SRC_ALS)
  450. ev_code = IIO_UNMOD_EVENT_CODE(IIO_LIGHT, 0,
  451. IIO_EV_TYPE_THRESH,
  452. IIO_EV_DIR_EITHER);
  453. else
  454. ev_code = IIO_MOD_EVENT_CODE(IIO_INTENSITY, 0,
  455. IIO_MOD_LIGHT_CLEAR,
  456. IIO_EV_TYPE_THRESH,
  457. IIO_EV_DIR_EITHER);
  458. iio_push_event(indio_dev, ev_code, iio_get_time_ns(indio_dev));
  459. }
  460. ret = regmap_bulk_read(data->regmap, reg, buff, sizeof(buff));
  461. if (ret) {
  462. dev_err_ratelimited(dev, "read data failed\n");
  463. return ret;
  464. }
  465. *val = get_unaligned_le24(&buff);
  466. pm_runtime_mark_last_busy(data->dev);
  467. pm_runtime_put_autosuspend(data->dev);
  468. return 0;
  469. }
  470. static int apds9306_intg_time_get(struct apds9306_data *data, int *val2)
  471. {
  472. struct apds9306_regfields *rf = &data->rf;
  473. int ret, intg_time_idx;
  474. ret = regmap_field_read(rf->intg_time, &intg_time_idx);
  475. if (ret)
  476. return ret;
  477. ret = iio_gts_find_int_time_by_sel(&data->gts, intg_time_idx);
  478. if (ret < 0)
  479. return ret;
  480. *val2 = ret;
  481. return 0;
  482. }
  483. static int apds9306_intg_time_set(struct apds9306_data *data, int val2)
  484. {
  485. struct device *dev = data->dev;
  486. struct apds9306_regfields *rf = &data->rf;
  487. int ret, intg_old, gain_old, gain_new, gain_new_closest, intg_time_idx;
  488. int gain_idx;
  489. bool ok;
  490. if (!iio_gts_valid_time(&data->gts, val2)) {
  491. dev_err_ratelimited(dev, "Unsupported integration time %u\n", val2);
  492. return -EINVAL;
  493. }
  494. ret = regmap_field_read(rf->intg_time, &intg_time_idx);
  495. if (ret)
  496. return ret;
  497. ret = regmap_field_read(rf->gain, &gain_idx);
  498. if (ret)
  499. return ret;
  500. intg_old = iio_gts_find_int_time_by_sel(&data->gts, intg_time_idx);
  501. if (intg_old < 0)
  502. return intg_old;
  503. if (intg_old == val2)
  504. return 0;
  505. gain_old = iio_gts_find_gain_by_sel(&data->gts, gain_idx);
  506. if (gain_old < 0)
  507. return gain_old;
  508. iio_gts_find_new_gain_by_old_gain_time(&data->gts, gain_old, intg_old,
  509. val2, &gain_new);
  510. if (gain_new < 0) {
  511. dev_err_ratelimited(dev, "Unsupported gain with time\n");
  512. return gain_new;
  513. }
  514. gain_new_closest = iio_find_closest_gain_low(&data->gts, gain_new, &ok);
  515. if (gain_new_closest < 0) {
  516. gain_new_closest = iio_gts_get_min_gain(&data->gts);
  517. if (gain_new_closest < 0)
  518. return gain_new_closest;
  519. }
  520. if (!ok)
  521. dev_dbg(dev, "Unable to find optimum gain, setting minimum");
  522. ret = iio_gts_find_sel_by_int_time(&data->gts, val2);
  523. if (ret < 0)
  524. return ret;
  525. ret = regmap_field_write(rf->intg_time, ret);
  526. if (ret)
  527. return ret;
  528. ret = iio_gts_find_sel_by_gain(&data->gts, gain_new_closest);
  529. if (ret < 0)
  530. return ret;
  531. return regmap_field_write(rf->gain, ret);
  532. }
  533. static int apds9306_sampling_freq_get(struct apds9306_data *data, int *val,
  534. int *val2)
  535. {
  536. struct apds9306_regfields *rf = &data->rf;
  537. int ret, repeat_rate_idx;
  538. ret = regmap_field_read(rf->repeat_rate, &repeat_rate_idx);
  539. if (ret)
  540. return ret;
  541. if (repeat_rate_idx >= ARRAY_SIZE(apds9306_repeat_rate_freq))
  542. return -EINVAL;
  543. *val = apds9306_repeat_rate_freq[repeat_rate_idx][0];
  544. *val2 = apds9306_repeat_rate_freq[repeat_rate_idx][1];
  545. return 0;
  546. }
  547. static int apds9306_sampling_freq_set(struct apds9306_data *data, int val,
  548. int val2)
  549. {
  550. struct apds9306_regfields *rf = &data->rf;
  551. int i;
  552. for (i = 0; i < ARRAY_SIZE(apds9306_repeat_rate_freq); i++) {
  553. if (apds9306_repeat_rate_freq[i][0] == val &&
  554. apds9306_repeat_rate_freq[i][1] == val2)
  555. return regmap_field_write(rf->repeat_rate, i);
  556. }
  557. return -EINVAL;
  558. }
  559. static int apds9306_scale_get(struct apds9306_data *data, int *val, int *val2)
  560. {
  561. struct apds9306_regfields *rf = &data->rf;
  562. int gain, intg, ret, intg_time_idx, gain_idx;
  563. ret = regmap_field_read(rf->gain, &gain_idx);
  564. if (ret)
  565. return ret;
  566. ret = regmap_field_read(rf->intg_time, &intg_time_idx);
  567. if (ret)
  568. return ret;
  569. gain = iio_gts_find_gain_by_sel(&data->gts, gain_idx);
  570. if (gain < 0)
  571. return gain;
  572. intg = iio_gts_find_int_time_by_sel(&data->gts, intg_time_idx);
  573. if (intg < 0)
  574. return intg;
  575. return iio_gts_get_scale(&data->gts, gain, intg, val, val2);
  576. }
  577. static int apds9306_scale_set(struct apds9306_data *data, int val, int val2)
  578. {
  579. struct apds9306_regfields *rf = &data->rf;
  580. int i, ret, time_sel, gain_sel, intg_time_idx;
  581. ret = regmap_field_read(rf->intg_time, &intg_time_idx);
  582. if (ret)
  583. return ret;
  584. ret = iio_gts_find_gain_sel_for_scale_using_time(&data->gts,
  585. intg_time_idx, val, val2, &gain_sel);
  586. if (ret) {
  587. for (i = 0; i < data->gts.num_itime; i++) {
  588. time_sel = data->gts.itime_table[i].sel;
  589. if (time_sel == intg_time_idx)
  590. continue;
  591. ret = iio_gts_find_gain_sel_for_scale_using_time(&data->gts,
  592. time_sel, val, val2, &gain_sel);
  593. if (!ret)
  594. break;
  595. }
  596. if (ret)
  597. return -EINVAL;
  598. ret = regmap_field_write(rf->intg_time, time_sel);
  599. if (ret)
  600. return ret;
  601. }
  602. return regmap_field_write(rf->gain, gain_sel);
  603. }
  604. static int apds9306_event_period_get(struct apds9306_data *data, int *val)
  605. {
  606. struct apds9306_regfields *rf = &data->rf;
  607. int period, ret;
  608. ret = regmap_field_read(rf->int_persist_val, &period);
  609. if (ret)
  610. return ret;
  611. if (!in_range(period, 0, APDS9306_ALS_PERSIST_NUM_VALS))
  612. return -EINVAL;
  613. *val = period;
  614. return ret;
  615. }
  616. static int apds9306_event_period_set(struct apds9306_data *data, int val)
  617. {
  618. struct apds9306_regfields *rf = &data->rf;
  619. if (!in_range(val, 0, APDS9306_ALS_PERSIST_NUM_VALS))
  620. return -EINVAL;
  621. return regmap_field_write(rf->int_persist_val, val);
  622. }
  623. static int apds9306_event_thresh_get(struct apds9306_data *data, int dir,
  624. int *val)
  625. {
  626. int var, ret;
  627. u8 buff[3];
  628. if (dir == IIO_EV_DIR_RISING)
  629. var = APDS9306_ALS_THRES_UP_0_REG;
  630. else if (dir == IIO_EV_DIR_FALLING)
  631. var = APDS9306_ALS_THRES_LOW_0_REG;
  632. else
  633. return -EINVAL;
  634. ret = regmap_bulk_read(data->regmap, var, buff, sizeof(buff));
  635. if (ret)
  636. return ret;
  637. *val = get_unaligned_le24(&buff);
  638. return 0;
  639. }
  640. static int apds9306_event_thresh_set(struct apds9306_data *data, int dir,
  641. int val)
  642. {
  643. int var;
  644. u8 buff[3];
  645. if (dir == IIO_EV_DIR_RISING)
  646. var = APDS9306_ALS_THRES_UP_0_REG;
  647. else if (dir == IIO_EV_DIR_FALLING)
  648. var = APDS9306_ALS_THRES_LOW_0_REG;
  649. else
  650. return -EINVAL;
  651. if (!in_range(val, 0, APDS9306_ALS_THRES_VAL_MAX))
  652. return -EINVAL;
  653. put_unaligned_le24(val, buff);
  654. return regmap_bulk_write(data->regmap, var, buff, sizeof(buff));
  655. }
  656. static int apds9306_event_thresh_adaptive_get(struct apds9306_data *data, int *val)
  657. {
  658. struct apds9306_regfields *rf = &data->rf;
  659. int thr_adpt, ret;
  660. ret = regmap_field_read(rf->int_thresh_var_val, &thr_adpt);
  661. if (ret)
  662. return ret;
  663. if (!in_range(thr_adpt, 0, APDS9306_ALS_THRES_VAR_NUM_VALS))
  664. return -EINVAL;
  665. *val = thr_adpt;
  666. return ret;
  667. }
  668. static int apds9306_event_thresh_adaptive_set(struct apds9306_data *data, int val)
  669. {
  670. struct apds9306_regfields *rf = &data->rf;
  671. if (!in_range(val, 0, APDS9306_ALS_THRES_VAR_NUM_VALS))
  672. return -EINVAL;
  673. return regmap_field_write(rf->int_thresh_var_val, val);
  674. }
  675. static int apds9306_read_raw(struct iio_dev *indio_dev,
  676. struct iio_chan_spec const *chan, int *val,
  677. int *val2, long mask)
  678. {
  679. struct apds9306_data *data = iio_priv(indio_dev);
  680. int ret, reg;
  681. switch (mask) {
  682. case IIO_CHAN_INFO_RAW:
  683. if (chan->channel2 == IIO_MOD_LIGHT_CLEAR)
  684. reg = APDS9306_CLEAR_DATA_0_REG;
  685. else
  686. reg = APDS9306_ALS_DATA_0_REG;
  687. /*
  688. * Changing device parameters during adc operation, resets
  689. * the ADC which has to avoided.
  690. */
  691. ret = iio_device_claim_direct_mode(indio_dev);
  692. if (ret)
  693. return ret;
  694. ret = apds9306_read_data(data, val, reg);
  695. iio_device_release_direct_mode(indio_dev);
  696. if (ret)
  697. return ret;
  698. return IIO_VAL_INT;
  699. case IIO_CHAN_INFO_INT_TIME:
  700. ret = apds9306_intg_time_get(data, val2);
  701. if (ret)
  702. return ret;
  703. *val = 0;
  704. return IIO_VAL_INT_PLUS_MICRO;
  705. case IIO_CHAN_INFO_SAMP_FREQ:
  706. ret = apds9306_sampling_freq_get(data, val, val2);
  707. if (ret)
  708. return ret;
  709. return IIO_VAL_INT_PLUS_MICRO;
  710. case IIO_CHAN_INFO_SCALE:
  711. ret = apds9306_scale_get(data, val, val2);
  712. if (ret)
  713. return ret;
  714. return IIO_VAL_INT_PLUS_NANO;
  715. default:
  716. return -EINVAL;
  717. }
  718. };
  719. static int apds9306_read_avail(struct iio_dev *indio_dev,
  720. struct iio_chan_spec const *chan,
  721. const int **vals, int *type, int *length,
  722. long mask)
  723. {
  724. struct apds9306_data *data = iio_priv(indio_dev);
  725. switch (mask) {
  726. case IIO_CHAN_INFO_INT_TIME:
  727. return iio_gts_avail_times(&data->gts, vals, type, length);
  728. case IIO_CHAN_INFO_SCALE:
  729. return iio_gts_all_avail_scales(&data->gts, vals, type, length);
  730. case IIO_CHAN_INFO_SAMP_FREQ:
  731. *length = ARRAY_SIZE(apds9306_repeat_rate_freq) * 2;
  732. *vals = (const int *)apds9306_repeat_rate_freq;
  733. *type = IIO_VAL_INT_PLUS_MICRO;
  734. return IIO_AVAIL_LIST;
  735. default:
  736. return -EINVAL;
  737. }
  738. }
  739. static int apds9306_write_raw_get_fmt(struct iio_dev *indio_dev,
  740. struct iio_chan_spec const *chan,
  741. long mask)
  742. {
  743. switch (mask) {
  744. case IIO_CHAN_INFO_SCALE:
  745. return IIO_VAL_INT_PLUS_NANO;
  746. case IIO_CHAN_INFO_INT_TIME:
  747. return IIO_VAL_INT_PLUS_MICRO;
  748. case IIO_CHAN_INFO_SAMP_FREQ:
  749. return IIO_VAL_INT_PLUS_MICRO;
  750. default:
  751. return -EINVAL;
  752. }
  753. }
  754. static int apds9306_write_raw(struct iio_dev *indio_dev,
  755. struct iio_chan_spec const *chan, int val,
  756. int val2, long mask)
  757. {
  758. struct apds9306_data *data = iio_priv(indio_dev);
  759. guard(mutex)(&data->mutex);
  760. switch (mask) {
  761. case IIO_CHAN_INFO_INT_TIME:
  762. if (val)
  763. return -EINVAL;
  764. return apds9306_intg_time_set(data, val2);
  765. case IIO_CHAN_INFO_SCALE:
  766. return apds9306_scale_set(data, val, val2);
  767. case IIO_CHAN_INFO_SAMP_FREQ:
  768. return apds9306_sampling_freq_set(data, val, val2);
  769. default:
  770. return -EINVAL;
  771. }
  772. }
  773. static irqreturn_t apds9306_irq_handler(int irq, void *priv)
  774. {
  775. struct iio_dev *indio_dev = priv;
  776. struct apds9306_data *data = iio_priv(indio_dev);
  777. struct apds9306_regfields *rf = &data->rf;
  778. u64 ev_code;
  779. int ret, status, int_src;
  780. /*
  781. * The interrupt line is released and the interrupt flag is
  782. * cleared as a result of reading the status register. All the
  783. * status flags are cleared as a result of this read.
  784. */
  785. ret = regmap_read(data->regmap, APDS9306_MAIN_STATUS_REG, &status);
  786. if (ret < 0) {
  787. dev_err_ratelimited(data->dev, "status reg read failed\n");
  788. return IRQ_HANDLED;
  789. }
  790. ret = regmap_field_read(rf->int_src, &int_src);
  791. if (ret)
  792. return ret;
  793. if ((status & APDS9306_ALS_INT_STAT_MASK)) {
  794. if (int_src == APDS9306_INT_SRC_ALS)
  795. ev_code = IIO_UNMOD_EVENT_CODE(IIO_LIGHT, 0,
  796. IIO_EV_TYPE_THRESH,
  797. IIO_EV_DIR_EITHER);
  798. else
  799. ev_code = IIO_MOD_EVENT_CODE(IIO_INTENSITY, 0,
  800. IIO_MOD_LIGHT_CLEAR,
  801. IIO_EV_TYPE_THRESH,
  802. IIO_EV_DIR_EITHER);
  803. iio_push_event(indio_dev, ev_code, iio_get_time_ns(indio_dev));
  804. }
  805. /*
  806. * If a one-shot read through sysfs is underway at the same time
  807. * as this interrupt handler is executing and a read data available
  808. * flag was set, this flag is set to inform read_poll_timeout()
  809. * to exit.
  810. */
  811. if ((status & APDS9306_ALS_DATA_STAT_MASK))
  812. data->read_data_available = 1;
  813. return IRQ_HANDLED;
  814. }
  815. static int apds9306_read_event(struct iio_dev *indio_dev,
  816. const struct iio_chan_spec *chan,
  817. enum iio_event_type type,
  818. enum iio_event_direction dir,
  819. enum iio_event_info info,
  820. int *val, int *val2)
  821. {
  822. struct apds9306_data *data = iio_priv(indio_dev);
  823. int ret;
  824. switch (type) {
  825. case IIO_EV_TYPE_THRESH:
  826. if (dir == IIO_EV_DIR_EITHER && info == IIO_EV_INFO_PERIOD)
  827. ret = apds9306_event_period_get(data, val);
  828. else
  829. ret = apds9306_event_thresh_get(data, dir, val);
  830. if (ret)
  831. return ret;
  832. return IIO_VAL_INT;
  833. case IIO_EV_TYPE_THRESH_ADAPTIVE:
  834. ret = apds9306_event_thresh_adaptive_get(data, val);
  835. if (ret)
  836. return ret;
  837. return IIO_VAL_INT;
  838. default:
  839. return -EINVAL;
  840. }
  841. }
  842. static int apds9306_write_event(struct iio_dev *indio_dev,
  843. const struct iio_chan_spec *chan,
  844. enum iio_event_type type,
  845. enum iio_event_direction dir,
  846. enum iio_event_info info,
  847. int val, int val2)
  848. {
  849. struct apds9306_data *data = iio_priv(indio_dev);
  850. switch (type) {
  851. case IIO_EV_TYPE_THRESH:
  852. if (dir == IIO_EV_DIR_EITHER && info == IIO_EV_INFO_PERIOD)
  853. return apds9306_event_period_set(data, val);
  854. return apds9306_event_thresh_set(data, dir, val);
  855. case IIO_EV_TYPE_THRESH_ADAPTIVE:
  856. return apds9306_event_thresh_adaptive_set(data, val);
  857. default:
  858. return -EINVAL;
  859. }
  860. }
  861. static int apds9306_read_event_config(struct iio_dev *indio_dev,
  862. const struct iio_chan_spec *chan,
  863. enum iio_event_type type,
  864. enum iio_event_direction dir)
  865. {
  866. struct apds9306_data *data = iio_priv(indio_dev);
  867. struct apds9306_regfields *rf = &data->rf;
  868. int int_en, int_src, ret;
  869. switch (type) {
  870. case IIO_EV_TYPE_THRESH: {
  871. guard(mutex)(&data->mutex);
  872. ret = regmap_field_read(rf->int_src, &int_src);
  873. if (ret)
  874. return ret;
  875. ret = regmap_field_read(rf->int_en, &int_en);
  876. if (ret)
  877. return ret;
  878. if (chan->type == IIO_LIGHT)
  879. return int_en && (int_src == APDS9306_INT_SRC_ALS);
  880. if (chan->type == IIO_INTENSITY)
  881. return int_en && (int_src == APDS9306_INT_SRC_CLEAR);
  882. return -EINVAL;
  883. }
  884. case IIO_EV_TYPE_THRESH_ADAPTIVE:
  885. ret = regmap_field_read(rf->int_thresh_var_en, &int_en);
  886. if (ret)
  887. return ret;
  888. return int_en;
  889. default:
  890. return -EINVAL;
  891. }
  892. }
  893. static int apds9306_write_event_config(struct iio_dev *indio_dev,
  894. const struct iio_chan_spec *chan,
  895. enum iio_event_type type,
  896. enum iio_event_direction dir,
  897. int state)
  898. {
  899. struct apds9306_data *data = iio_priv(indio_dev);
  900. struct apds9306_regfields *rf = &data->rf;
  901. int ret, enabled;
  902. switch (type) {
  903. case IIO_EV_TYPE_THRESH: {
  904. guard(mutex)(&data->mutex);
  905. ret = regmap_field_read(rf->int_en, &enabled);
  906. if (ret)
  907. return ret;
  908. /*
  909. * If interrupt is enabled, the channel is set before enabling
  910. * the interrupt. In case of disable, no need to switch
  911. * channels. In case of different channel is selected while
  912. * interrupt in on, just change the channel.
  913. */
  914. if (state) {
  915. if (chan->type == IIO_LIGHT)
  916. ret = regmap_field_write(rf->int_src, 1);
  917. else if (chan->type == IIO_INTENSITY)
  918. ret = regmap_field_write(rf->int_src, 0);
  919. else
  920. return -EINVAL;
  921. if (ret)
  922. return ret;
  923. if (enabled)
  924. return 0;
  925. ret = regmap_field_write(rf->int_en, 1);
  926. if (ret)
  927. return ret;
  928. return pm_runtime_resume_and_get(data->dev);
  929. } else {
  930. if (!enabled)
  931. return 0;
  932. ret = regmap_field_write(rf->int_en, 0);
  933. if (ret)
  934. return ret;
  935. pm_runtime_mark_last_busy(data->dev);
  936. pm_runtime_put_autosuspend(data->dev);
  937. return 0;
  938. }
  939. }
  940. case IIO_EV_TYPE_THRESH_ADAPTIVE:
  941. if (state)
  942. return regmap_field_write(rf->int_thresh_var_en, 1);
  943. else
  944. return regmap_field_write(rf->int_thresh_var_en, 0);
  945. default:
  946. return -EINVAL;
  947. }
  948. }
  949. static const struct iio_info apds9306_info_no_events = {
  950. .read_avail = apds9306_read_avail,
  951. .read_raw = apds9306_read_raw,
  952. .write_raw = apds9306_write_raw,
  953. .write_raw_get_fmt = apds9306_write_raw_get_fmt,
  954. };
  955. static const struct iio_info apds9306_info = {
  956. .read_avail = apds9306_read_avail,
  957. .read_raw = apds9306_read_raw,
  958. .write_raw = apds9306_write_raw,
  959. .write_raw_get_fmt = apds9306_write_raw_get_fmt,
  960. .read_event_value = apds9306_read_event,
  961. .write_event_value = apds9306_write_event,
  962. .read_event_config = apds9306_read_event_config,
  963. .write_event_config = apds9306_write_event_config,
  964. .event_attrs = &apds9306_event_attr_group,
  965. };
  966. static int apds9306_init_iio_gts(struct apds9306_data *data)
  967. {
  968. int i, ret, part_id;
  969. ret = regmap_read(data->regmap, APDS9306_PART_ID_REG, &part_id);
  970. if (ret)
  971. return ret;
  972. for (i = 0; i < ARRAY_SIZE(apds9306_gts_mul); i++)
  973. if (part_id == apds9306_gts_mul[i].part_id)
  974. break;
  975. if (i == ARRAY_SIZE(apds9306_gts_mul))
  976. return -ENOENT;
  977. return devm_iio_init_iio_gts(data->dev,
  978. apds9306_gts_mul[i].max_scale_int,
  979. apds9306_gts_mul[i].max_scale_nano,
  980. apds9306_gains, ARRAY_SIZE(apds9306_gains),
  981. apds9306_itimes, ARRAY_SIZE(apds9306_itimes),
  982. &data->gts);
  983. }
  984. static void apds9306_powerdown(void *ptr)
  985. {
  986. struct apds9306_data *data = (struct apds9306_data *)ptr;
  987. struct apds9306_regfields *rf = &data->rf;
  988. int ret;
  989. ret = regmap_field_write(rf->int_thresh_var_en, 0);
  990. if (ret)
  991. return;
  992. ret = regmap_field_write(rf->int_en, 0);
  993. if (ret)
  994. return;
  995. apds9306_power_state(data, false);
  996. }
  997. static int apds9306_device_init(struct apds9306_data *data)
  998. {
  999. struct apds9306_regfields *rf = &data->rf;
  1000. int ret;
  1001. ret = apds9306_init_iio_gts(data);
  1002. if (ret)
  1003. return ret;
  1004. ret = regmap_field_write(rf->intg_time, APDS9306_MEAS_MODE_100MS);
  1005. if (ret)
  1006. return ret;
  1007. ret = regmap_field_write(rf->repeat_rate, APDS9306_SAMP_FREQ_10HZ);
  1008. if (ret)
  1009. return ret;
  1010. ret = regmap_field_write(rf->gain, APDS9306_GSEL_3X);
  1011. if (ret)
  1012. return ret;
  1013. ret = regmap_field_write(rf->int_src, APDS9306_INT_SRC_ALS);
  1014. if (ret)
  1015. return ret;
  1016. ret = regmap_field_write(rf->int_en, 0);
  1017. if (ret)
  1018. return ret;
  1019. return regmap_field_write(rf->int_thresh_var_en, 0);
  1020. }
  1021. static int apds9306_pm_init(struct apds9306_data *data)
  1022. {
  1023. struct device *dev = data->dev;
  1024. int ret;
  1025. ret = apds9306_power_state(data, true);
  1026. if (ret)
  1027. return ret;
  1028. ret = pm_runtime_set_active(dev);
  1029. if (ret)
  1030. return ret;
  1031. ret = devm_pm_runtime_enable(dev);
  1032. if (ret)
  1033. return ret;
  1034. pm_runtime_set_autosuspend_delay(dev, 5000);
  1035. pm_runtime_use_autosuspend(dev);
  1036. pm_runtime_get(dev);
  1037. return 0;
  1038. }
  1039. static int apds9306_probe(struct i2c_client *client)
  1040. {
  1041. struct device *dev = &client->dev;
  1042. struct apds9306_data *data;
  1043. struct iio_dev *indio_dev;
  1044. int ret;
  1045. indio_dev = devm_iio_device_alloc(dev, sizeof(*data));
  1046. if (!indio_dev)
  1047. return -ENOMEM;
  1048. data = iio_priv(indio_dev);
  1049. mutex_init(&data->mutex);
  1050. data->regmap = devm_regmap_init_i2c(client, &apds9306_regmap);
  1051. if (IS_ERR(data->regmap))
  1052. return dev_err_probe(dev, PTR_ERR(data->regmap),
  1053. "regmap initialization failed\n");
  1054. data->dev = dev;
  1055. i2c_set_clientdata(client, indio_dev);
  1056. ret = apds9306_regfield_init(data);
  1057. if (ret)
  1058. return dev_err_probe(dev, ret, "regfield initialization failed\n");
  1059. ret = devm_regulator_get_enable(dev, "vdd");
  1060. if (ret)
  1061. return dev_err_probe(dev, ret, "Failed to enable regulator\n");
  1062. indio_dev->name = "apds9306";
  1063. indio_dev->modes = INDIO_DIRECT_MODE;
  1064. if (client->irq) {
  1065. indio_dev->info = &apds9306_info;
  1066. indio_dev->channels = apds9306_channels_with_events;
  1067. indio_dev->num_channels = ARRAY_SIZE(apds9306_channels_with_events);
  1068. ret = devm_request_threaded_irq(dev, client->irq, NULL,
  1069. apds9306_irq_handler, IRQF_ONESHOT,
  1070. "apds9306_event", indio_dev);
  1071. if (ret)
  1072. return dev_err_probe(dev, ret,
  1073. "failed to assign interrupt.\n");
  1074. } else {
  1075. indio_dev->info = &apds9306_info_no_events;
  1076. indio_dev->channels = apds9306_channels_without_events;
  1077. indio_dev->num_channels =
  1078. ARRAY_SIZE(apds9306_channels_without_events);
  1079. }
  1080. ret = apds9306_pm_init(data);
  1081. if (ret)
  1082. return dev_err_probe(dev, ret, "failed pm init\n");
  1083. ret = apds9306_device_init(data);
  1084. if (ret)
  1085. return dev_err_probe(dev, ret, "failed to init device\n");
  1086. ret = devm_add_action_or_reset(dev, apds9306_powerdown, data);
  1087. if (ret)
  1088. return dev_err_probe(dev, ret, "failed to add action or reset\n");
  1089. ret = devm_iio_device_register(dev, indio_dev);
  1090. if (ret)
  1091. return dev_err_probe(dev, ret, "failed iio device registration\n");
  1092. pm_runtime_put_autosuspend(dev);
  1093. return 0;
  1094. }
  1095. static int apds9306_runtime_suspend(struct device *dev)
  1096. {
  1097. struct apds9306_data *data = iio_priv(dev_get_drvdata(dev));
  1098. return apds9306_power_state(data, false);
  1099. }
  1100. static int apds9306_runtime_resume(struct device *dev)
  1101. {
  1102. struct apds9306_data *data = iio_priv(dev_get_drvdata(dev));
  1103. return apds9306_power_state(data, true);
  1104. }
  1105. static DEFINE_RUNTIME_DEV_PM_OPS(apds9306_pm_ops,
  1106. apds9306_runtime_suspend,
  1107. apds9306_runtime_resume,
  1108. NULL);
  1109. static const struct of_device_id apds9306_of_match[] = {
  1110. { .compatible = "avago,apds9306" },
  1111. { }
  1112. };
  1113. MODULE_DEVICE_TABLE(of, apds9306_of_match);
  1114. static struct i2c_driver apds9306_driver = {
  1115. .driver = {
  1116. .name = "apds9306",
  1117. .pm = pm_ptr(&apds9306_pm_ops),
  1118. .of_match_table = apds9306_of_match,
  1119. },
  1120. .probe = apds9306_probe,
  1121. };
  1122. module_i2c_driver(apds9306_driver);
  1123. MODULE_AUTHOR("Subhajit Ghosh <subhajit.ghosh@tweaklogic.com>");
  1124. MODULE_DESCRIPTION("APDS9306 Ambient Light Sensor driver");
  1125. MODULE_LICENSE("GPL");
  1126. MODULE_IMPORT_NS(IIO_GTS_HELPER);