88pm860x_battery.c 25 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016
  1. // SPDX-License-Identifier: GPL-2.0-only
  2. /*
  3. * Battery driver for Marvell 88PM860x PMIC
  4. *
  5. * Copyright (c) 2012 Marvell International Ltd.
  6. * Author: Jett Zhou <jtzhou@marvell.com>
  7. * Haojian Zhuang <haojian.zhuang@marvell.com>
  8. */
  9. #include <linux/kernel.h>
  10. #include <linux/module.h>
  11. #include <linux/platform_device.h>
  12. #include <linux/slab.h>
  13. #include <linux/mutex.h>
  14. #include <linux/string.h>
  15. #include <linux/power_supply.h>
  16. #include <linux/mfd/88pm860x.h>
  17. #include <linux/delay.h>
  18. /* bit definitions of Status Query Interface 2 */
  19. #define STATUS2_CHG (1 << 2)
  20. #define STATUS2_BAT (1 << 3)
  21. #define STATUS2_VBUS (1 << 4)
  22. /* bit definitions of Measurement Enable 1 Register */
  23. #define MEAS1_TINT (1 << 3)
  24. #define MEAS1_GP1 (1 << 5)
  25. /* bit definitions of Measurement Enable 3 Register */
  26. #define MEAS3_IBAT (1 << 0)
  27. #define MEAS3_BAT_DET (1 << 1)
  28. #define MEAS3_CC (1 << 2)
  29. /* bit definitions of Measurement Off Time Register */
  30. #define MEAS_OFF_SLEEP_EN (1 << 1)
  31. /* bit definitions of GPADC Bias Current 2 Register */
  32. #define GPBIAS2_GPADC1_SET (2 << 4)
  33. /* GPADC1 Bias Current value in uA unit */
  34. #define GPBIAS2_GPADC1_UA ((GPBIAS2_GPADC1_SET >> 4) * 5 + 1)
  35. /* bit definitions of GPADC Misc 1 Register */
  36. #define GPMISC1_GPADC_EN (1 << 0)
  37. /* bit definitions of Charger Control 6 Register */
  38. #define CC6_BAT_DET_GPADC1 1
  39. /* bit definitions of Coulomb Counter Reading Register */
  40. #define CCNT_AVG_SEL (4 << 3)
  41. /* bit definitions of RTC miscellaneous Register1 */
  42. #define RTC_SOC_5LSB (0x1F << 3)
  43. /* bit definitions of RTC Register1 */
  44. #define RTC_SOC_3MSB (0x7)
  45. /* bit definitions of Power up Log register */
  46. #define BAT_WU_LOG (1<<6)
  47. /* coulomb counter index */
  48. #define CCNT_POS1 0
  49. #define CCNT_POS2 1
  50. #define CCNT_NEG1 2
  51. #define CCNT_NEG2 3
  52. #define CCNT_SPOS 4
  53. #define CCNT_SNEG 5
  54. /* OCV -- Open Circuit Voltage */
  55. #define OCV_MODE_ACTIVE 0
  56. #define OCV_MODE_SLEEP 1
  57. /* Vbat range of CC for measuring Rbat */
  58. #define LOW_BAT_THRESHOLD 3600
  59. #define VBATT_RESISTOR_MIN 3800
  60. #define VBATT_RESISTOR_MAX 4100
  61. /* TBAT for batt, TINT for chip itself */
  62. #define PM860X_TEMP_TINT (0)
  63. #define PM860X_TEMP_TBAT (1)
  64. /*
  65. * Battery temperature based on NTC resistor, defined
  66. * corresponding resistor value -- Ohm / C degeree.
  67. */
  68. #define TBAT_NEG_25D 127773 /* -25 */
  69. #define TBAT_NEG_10D 54564 /* -10 */
  70. #define TBAT_0D 32330 /* 0 */
  71. #define TBAT_10D 19785 /* 10 */
  72. #define TBAT_20D 12468 /* 20 */
  73. #define TBAT_30D 8072 /* 30 */
  74. #define TBAT_40D 5356 /* 40 */
  75. struct pm860x_battery_info {
  76. struct pm860x_chip *chip;
  77. struct i2c_client *i2c;
  78. struct device *dev;
  79. struct power_supply *battery;
  80. struct mutex lock;
  81. int status;
  82. int irq_cc;
  83. int irq_batt;
  84. int max_capacity;
  85. int resistor; /* Battery Internal Resistor */
  86. int last_capacity;
  87. int start_soc;
  88. unsigned present:1;
  89. unsigned temp_type:1; /* TINT or TBAT */
  90. };
  91. struct ccnt {
  92. unsigned long long int pos;
  93. unsigned long long int neg;
  94. unsigned int spos;
  95. unsigned int sneg;
  96. int total_chg; /* mAh(3.6C) */
  97. int total_dischg; /* mAh(3.6C) */
  98. };
  99. /*
  100. * State of Charge.
  101. * The first number is mAh(=3.6C), and the second number is percent point.
  102. */
  103. static int array_soc[][2] = {
  104. {4170, 100}, {4154, 99}, {4136, 98}, {4122, 97}, {4107, 96},
  105. {4102, 95}, {4088, 94}, {4081, 93}, {4070, 92}, {4060, 91},
  106. {4053, 90}, {4044, 89}, {4035, 88}, {4028, 87}, {4019, 86},
  107. {4013, 85}, {4006, 84}, {3995, 83}, {3987, 82}, {3982, 81},
  108. {3976, 80}, {3968, 79}, {3962, 78}, {3954, 77}, {3946, 76},
  109. {3941, 75}, {3934, 74}, {3929, 73}, {3922, 72}, {3916, 71},
  110. {3910, 70}, {3904, 69}, {3898, 68}, {3892, 67}, {3887, 66},
  111. {3880, 65}, {3874, 64}, {3868, 63}, {3862, 62}, {3854, 61},
  112. {3849, 60}, {3843, 59}, {3840, 58}, {3833, 57}, {3829, 56},
  113. {3824, 55}, {3818, 54}, {3815, 53}, {3810, 52}, {3808, 51},
  114. {3804, 50}, {3801, 49}, {3798, 48}, {3796, 47}, {3792, 46},
  115. {3789, 45}, {3785, 44}, {3784, 43}, {3782, 42}, {3780, 41},
  116. {3777, 40}, {3776, 39}, {3774, 38}, {3772, 37}, {3771, 36},
  117. {3769, 35}, {3768, 34}, {3764, 33}, {3763, 32}, {3760, 31},
  118. {3760, 30}, {3754, 29}, {3750, 28}, {3749, 27}, {3744, 26},
  119. {3740, 25}, {3734, 24}, {3732, 23}, {3728, 22}, {3726, 21},
  120. {3720, 20}, {3716, 19}, {3709, 18}, {3703, 17}, {3698, 16},
  121. {3692, 15}, {3683, 14}, {3675, 13}, {3670, 12}, {3665, 11},
  122. {3661, 10}, {3649, 9}, {3637, 8}, {3622, 7}, {3609, 6},
  123. {3580, 5}, {3558, 4}, {3540, 3}, {3510, 2}, {3429, 1},
  124. };
  125. static struct ccnt ccnt_data;
  126. /*
  127. * register 1 bit[7:0] -- bit[11:4] of measured value of voltage
  128. * register 0 bit[3:0] -- bit[3:0] of measured value of voltage
  129. */
  130. static int measure_12bit_voltage(struct pm860x_battery_info *info,
  131. int offset, int *data)
  132. {
  133. unsigned char buf[2];
  134. int ret;
  135. ret = pm860x_bulk_read(info->i2c, offset, 2, buf);
  136. if (ret < 0)
  137. return ret;
  138. *data = ((buf[0] & 0xff) << 4) | (buf[1] & 0x0f);
  139. /* V_MEAS(mV) = data * 1.8 * 1000 / (2^12) */
  140. *data = ((*data & 0xfff) * 9 * 25) >> 9;
  141. return 0;
  142. }
  143. static int measure_vbatt(struct pm860x_battery_info *info, int state,
  144. int *data)
  145. {
  146. unsigned char buf[5];
  147. int ret;
  148. switch (state) {
  149. case OCV_MODE_ACTIVE:
  150. ret = measure_12bit_voltage(info, PM8607_VBAT_MEAS1, data);
  151. if (ret)
  152. return ret;
  153. /* V_BATT_MEAS(mV) = value * 3 * 1.8 * 1000 / (2^12) */
  154. *data *= 3;
  155. break;
  156. case OCV_MODE_SLEEP:
  157. /*
  158. * voltage value of VBATT in sleep mode is saved in different
  159. * registers.
  160. * bit[11:10] -- bit[7:6] of LDO9(0x18)
  161. * bit[9:8] -- bit[7:6] of LDO8(0x17)
  162. * bit[7:6] -- bit[7:6] of LDO7(0x16)
  163. * bit[5:4] -- bit[7:6] of LDO6(0x15)
  164. * bit[3:0] -- bit[7:4] of LDO5(0x14)
  165. */
  166. ret = pm860x_bulk_read(info->i2c, PM8607_LDO5, 5, buf);
  167. if (ret < 0)
  168. return ret;
  169. ret = ((buf[4] >> 6) << 10) | ((buf[3] >> 6) << 8)
  170. | ((buf[2] >> 6) << 6) | ((buf[1] >> 6) << 4)
  171. | (buf[0] >> 4);
  172. /* V_BATT_MEAS(mV) = data * 3 * 1.8 * 1000 / (2^12) */
  173. *data = ((*data & 0xff) * 27 * 25) >> 9;
  174. break;
  175. default:
  176. return -EINVAL;
  177. }
  178. return 0;
  179. }
  180. /*
  181. * Return value is signed data.
  182. * Negative value means discharging, and positive value means charging.
  183. */
  184. static int measure_current(struct pm860x_battery_info *info, int *data)
  185. {
  186. unsigned char buf[2];
  187. short s;
  188. int ret;
  189. ret = pm860x_bulk_read(info->i2c, PM8607_IBAT_MEAS1, 2, buf);
  190. if (ret < 0)
  191. return ret;
  192. s = ((buf[0] & 0xff) << 8) | (buf[1] & 0xff);
  193. /* current(mA) = value * 0.125 */
  194. *data = s >> 3;
  195. return 0;
  196. }
  197. static int set_charger_current(struct pm860x_battery_info *info, int data,
  198. int *old)
  199. {
  200. int ret;
  201. if (data < 50 || data > 1600 || !old)
  202. return -EINVAL;
  203. data = ((data - 50) / 50) & 0x1f;
  204. *old = pm860x_reg_read(info->i2c, PM8607_CHG_CTRL2);
  205. *old = (*old & 0x1f) * 50 + 50;
  206. ret = pm860x_set_bits(info->i2c, PM8607_CHG_CTRL2, 0x1f, data);
  207. if (ret < 0)
  208. return ret;
  209. return 0;
  210. }
  211. static int read_ccnt(struct pm860x_battery_info *info, int offset,
  212. int *ccnt)
  213. {
  214. unsigned char buf[2];
  215. int ret;
  216. ret = pm860x_set_bits(info->i2c, PM8607_CCNT, 7, offset & 7);
  217. if (ret < 0)
  218. goto out;
  219. ret = pm860x_bulk_read(info->i2c, PM8607_CCNT_MEAS1, 2, buf);
  220. if (ret < 0)
  221. goto out;
  222. *ccnt = ((buf[0] & 0xff) << 8) | (buf[1] & 0xff);
  223. return 0;
  224. out:
  225. return ret;
  226. }
  227. static int calc_ccnt(struct pm860x_battery_info *info, struct ccnt *ccnt)
  228. {
  229. unsigned int sum;
  230. int ret;
  231. int data;
  232. ret = read_ccnt(info, CCNT_POS1, &data);
  233. if (ret)
  234. goto out;
  235. sum = data & 0xffff;
  236. ret = read_ccnt(info, CCNT_POS2, &data);
  237. if (ret)
  238. goto out;
  239. sum |= (data & 0xffff) << 16;
  240. ccnt->pos += sum;
  241. ret = read_ccnt(info, CCNT_NEG1, &data);
  242. if (ret)
  243. goto out;
  244. sum = data & 0xffff;
  245. ret = read_ccnt(info, CCNT_NEG2, &data);
  246. if (ret)
  247. goto out;
  248. sum |= (data & 0xffff) << 16;
  249. sum = ~sum + 1; /* since it's negative */
  250. ccnt->neg += sum;
  251. ret = read_ccnt(info, CCNT_SPOS, &data);
  252. if (ret)
  253. goto out;
  254. ccnt->spos += data;
  255. ret = read_ccnt(info, CCNT_SNEG, &data);
  256. if (ret)
  257. goto out;
  258. /*
  259. * charge(mAh) = count * 1.6984 * 1e(-8)
  260. * = count * 16984 * 1.024 * 1.024 * 1.024 / (2 ^ 40)
  261. * = count * 18236 / (2 ^ 40)
  262. */
  263. ccnt->total_chg = (int) ((ccnt->pos * 18236) >> 40);
  264. ccnt->total_dischg = (int) ((ccnt->neg * 18236) >> 40);
  265. return 0;
  266. out:
  267. return ret;
  268. }
  269. static int clear_ccnt(struct pm860x_battery_info *info, struct ccnt *ccnt)
  270. {
  271. int data;
  272. memset(ccnt, 0, sizeof(*ccnt));
  273. /* read to clear ccnt */
  274. read_ccnt(info, CCNT_POS1, &data);
  275. read_ccnt(info, CCNT_POS2, &data);
  276. read_ccnt(info, CCNT_NEG1, &data);
  277. read_ccnt(info, CCNT_NEG2, &data);
  278. read_ccnt(info, CCNT_SPOS, &data);
  279. read_ccnt(info, CCNT_SNEG, &data);
  280. return 0;
  281. }
  282. /* Calculate Open Circuit Voltage */
  283. static int calc_ocv(struct pm860x_battery_info *info, int *ocv)
  284. {
  285. int ret;
  286. int i;
  287. int data;
  288. int vbatt_avg;
  289. int vbatt_sum;
  290. int ibatt_avg;
  291. int ibatt_sum;
  292. if (!ocv)
  293. return -EINVAL;
  294. for (i = 0, ibatt_sum = 0, vbatt_sum = 0; i < 10; i++) {
  295. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  296. if (ret)
  297. goto out;
  298. vbatt_sum += data;
  299. ret = measure_current(info, &data);
  300. if (ret)
  301. goto out;
  302. ibatt_sum += data;
  303. }
  304. vbatt_avg = vbatt_sum / 10;
  305. ibatt_avg = ibatt_sum / 10;
  306. mutex_lock(&info->lock);
  307. if (info->present)
  308. *ocv = vbatt_avg - ibatt_avg * info->resistor / 1000;
  309. else
  310. *ocv = vbatt_avg;
  311. mutex_unlock(&info->lock);
  312. dev_dbg(info->dev, "VBAT average:%d, OCV:%d\n", vbatt_avg, *ocv);
  313. return 0;
  314. out:
  315. return ret;
  316. }
  317. /* Calculate State of Charge (percent points) */
  318. static int calc_soc(struct pm860x_battery_info *info, int state, int *soc)
  319. {
  320. int i;
  321. int ocv;
  322. int count;
  323. int ret = -EINVAL;
  324. if (!soc)
  325. return -EINVAL;
  326. switch (state) {
  327. case OCV_MODE_ACTIVE:
  328. ret = calc_ocv(info, &ocv);
  329. break;
  330. case OCV_MODE_SLEEP:
  331. ret = measure_vbatt(info, OCV_MODE_SLEEP, &ocv);
  332. break;
  333. }
  334. if (ret)
  335. return ret;
  336. count = ARRAY_SIZE(array_soc);
  337. if (ocv < array_soc[count - 1][0]) {
  338. *soc = 0;
  339. return 0;
  340. }
  341. for (i = 0; i < count; i++) {
  342. if (ocv >= array_soc[i][0]) {
  343. *soc = array_soc[i][1];
  344. break;
  345. }
  346. }
  347. return 0;
  348. }
  349. static irqreturn_t pm860x_coulomb_handler(int irq, void *data)
  350. {
  351. struct pm860x_battery_info *info = data;
  352. calc_ccnt(info, &ccnt_data);
  353. return IRQ_HANDLED;
  354. }
  355. static irqreturn_t pm860x_batt_handler(int irq, void *data)
  356. {
  357. struct pm860x_battery_info *info = data;
  358. int ret;
  359. mutex_lock(&info->lock);
  360. ret = pm860x_reg_read(info->i2c, PM8607_STATUS_2);
  361. if (ret & STATUS2_BAT) {
  362. info->present = 1;
  363. info->temp_type = PM860X_TEMP_TBAT;
  364. } else {
  365. info->present = 0;
  366. info->temp_type = PM860X_TEMP_TINT;
  367. }
  368. mutex_unlock(&info->lock);
  369. /* clear ccnt since battery is attached or dettached */
  370. clear_ccnt(info, &ccnt_data);
  371. return IRQ_HANDLED;
  372. }
  373. static void pm860x_init_battery(struct pm860x_battery_info *info)
  374. {
  375. unsigned char buf[2];
  376. int ret;
  377. int data;
  378. int bat_remove;
  379. int soc = 0;
  380. /* measure enable on GPADC1 */
  381. data = MEAS1_GP1;
  382. if (info->temp_type == PM860X_TEMP_TINT)
  383. data |= MEAS1_TINT;
  384. ret = pm860x_set_bits(info->i2c, PM8607_MEAS_EN1, data, data);
  385. if (ret)
  386. goto out;
  387. /* measure enable on IBAT, BAT_DET, CC. IBAT is depend on CC. */
  388. data = MEAS3_IBAT | MEAS3_BAT_DET | MEAS3_CC;
  389. ret = pm860x_set_bits(info->i2c, PM8607_MEAS_EN3, data, data);
  390. if (ret)
  391. goto out;
  392. /* measure disable CC in sleep time */
  393. ret = pm860x_reg_write(info->i2c, PM8607_MEAS_OFF_TIME1, 0x82);
  394. if (ret)
  395. goto out;
  396. ret = pm860x_reg_write(info->i2c, PM8607_MEAS_OFF_TIME2, 0x6c);
  397. if (ret)
  398. goto out;
  399. /* enable GPADC */
  400. ret = pm860x_set_bits(info->i2c, PM8607_GPADC_MISC1,
  401. GPMISC1_GPADC_EN, GPMISC1_GPADC_EN);
  402. if (ret < 0)
  403. goto out;
  404. /* detect battery via GPADC1 */
  405. ret = pm860x_set_bits(info->i2c, PM8607_CHG_CTRL6,
  406. CC6_BAT_DET_GPADC1, CC6_BAT_DET_GPADC1);
  407. if (ret < 0)
  408. goto out;
  409. ret = pm860x_set_bits(info->i2c, PM8607_CCNT, 7 << 3,
  410. CCNT_AVG_SEL);
  411. if (ret < 0)
  412. goto out;
  413. /* set GPADC1 bias */
  414. ret = pm860x_set_bits(info->i2c, PM8607_GP_BIAS2, 0xF << 4,
  415. GPBIAS2_GPADC1_SET);
  416. if (ret < 0)
  417. goto out;
  418. /* check whether battery present) */
  419. mutex_lock(&info->lock);
  420. ret = pm860x_reg_read(info->i2c, PM8607_STATUS_2);
  421. if (ret < 0) {
  422. mutex_unlock(&info->lock);
  423. goto out;
  424. }
  425. if (ret & STATUS2_BAT) {
  426. info->present = 1;
  427. info->temp_type = PM860X_TEMP_TBAT;
  428. } else {
  429. info->present = 0;
  430. info->temp_type = PM860X_TEMP_TINT;
  431. }
  432. mutex_unlock(&info->lock);
  433. ret = calc_soc(info, OCV_MODE_ACTIVE, &soc);
  434. if (ret < 0)
  435. goto out;
  436. data = pm860x_reg_read(info->i2c, PM8607_POWER_UP_LOG);
  437. bat_remove = data & BAT_WU_LOG;
  438. dev_dbg(info->dev, "battery wake up? %s\n",
  439. bat_remove != 0 ? "yes" : "no");
  440. /* restore SOC from RTC domain register */
  441. if (bat_remove == 0) {
  442. buf[0] = pm860x_reg_read(info->i2c, PM8607_RTC_MISC2);
  443. buf[1] = pm860x_reg_read(info->i2c, PM8607_RTC1);
  444. data = ((buf[1] & 0x3) << 5) | ((buf[0] >> 3) & 0x1F);
  445. if (data > soc + 15)
  446. info->start_soc = soc;
  447. else if (data < soc - 15)
  448. info->start_soc = soc;
  449. else
  450. info->start_soc = data;
  451. dev_dbg(info->dev, "soc_rtc %d, soc_ocv :%d\n", data, soc);
  452. } else {
  453. pm860x_set_bits(info->i2c, PM8607_POWER_UP_LOG,
  454. BAT_WU_LOG, BAT_WU_LOG);
  455. info->start_soc = soc;
  456. }
  457. info->last_capacity = info->start_soc;
  458. dev_dbg(info->dev, "init soc : %d\n", info->last_capacity);
  459. out:
  460. return;
  461. }
  462. static void set_temp_threshold(struct pm860x_battery_info *info,
  463. int min, int max)
  464. {
  465. int data;
  466. /* (tmp << 8) / 1800 */
  467. if (min <= 0)
  468. data = 0;
  469. else
  470. data = (min << 8) / 1800;
  471. pm860x_reg_write(info->i2c, PM8607_GPADC1_HIGHTH, data);
  472. dev_dbg(info->dev, "TEMP_HIGHTH : min: %d, 0x%x\n", min, data);
  473. if (max <= 0)
  474. data = 0xff;
  475. else
  476. data = (max << 8) / 1800;
  477. pm860x_reg_write(info->i2c, PM8607_GPADC1_LOWTH, data);
  478. dev_dbg(info->dev, "TEMP_LOWTH:max : %d, 0x%x\n", max, data);
  479. }
  480. static int measure_temp(struct pm860x_battery_info *info, int *data)
  481. {
  482. int ret;
  483. int temp;
  484. int min;
  485. int max;
  486. if (info->temp_type == PM860X_TEMP_TINT) {
  487. ret = measure_12bit_voltage(info, PM8607_TINT_MEAS1, data);
  488. if (ret)
  489. return ret;
  490. *data = (*data - 884) * 1000 / 3611;
  491. } else {
  492. ret = measure_12bit_voltage(info, PM8607_GPADC1_MEAS1, data);
  493. if (ret)
  494. return ret;
  495. /* meausered Vtbat(mV) / Ibias_current(11uA)*/
  496. *data = (*data * 1000) / GPBIAS2_GPADC1_UA;
  497. if (*data > TBAT_NEG_25D) {
  498. temp = -30; /* over cold , suppose -30 roughly */
  499. max = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  500. set_temp_threshold(info, 0, max);
  501. } else if (*data > TBAT_NEG_10D) {
  502. temp = -15; /* -15 degree, code */
  503. max = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  504. set_temp_threshold(info, 0, max);
  505. } else if (*data > TBAT_0D) {
  506. temp = -5; /* -5 degree */
  507. min = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  508. max = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  509. set_temp_threshold(info, min, max);
  510. } else if (*data > TBAT_10D) {
  511. temp = 5; /* in range of (0, 10) */
  512. min = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  513. max = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  514. set_temp_threshold(info, min, max);
  515. } else if (*data > TBAT_20D) {
  516. temp = 15; /* in range of (10, 20) */
  517. min = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  518. max = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  519. set_temp_threshold(info, min, max);
  520. } else if (*data > TBAT_30D) {
  521. temp = 25; /* in range of (20, 30) */
  522. min = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  523. max = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  524. set_temp_threshold(info, min, max);
  525. } else if (*data > TBAT_40D) {
  526. temp = 35; /* in range of (30, 40) */
  527. min = TBAT_NEG_10D * GPBIAS2_GPADC1_UA / 1000;
  528. max = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  529. set_temp_threshold(info, min, max);
  530. } else {
  531. min = TBAT_40D * GPBIAS2_GPADC1_UA / 1000;
  532. set_temp_threshold(info, min, 0);
  533. temp = 45; /* over heat ,suppose 45 roughly */
  534. }
  535. dev_dbg(info->dev, "temp_C:%d C,temp_mv:%d mv\n", temp, *data);
  536. *data = temp;
  537. }
  538. return 0;
  539. }
  540. static int calc_resistor(struct pm860x_battery_info *info)
  541. {
  542. int vbatt_sum1;
  543. int vbatt_sum2;
  544. int chg_current;
  545. int ibatt_sum1;
  546. int ibatt_sum2;
  547. int data;
  548. int ret;
  549. int i;
  550. ret = measure_current(info, &data);
  551. /* make sure that charging is launched by data > 0 */
  552. if (ret || data < 0)
  553. goto out;
  554. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  555. if (ret)
  556. goto out;
  557. /* calculate resistor only in CC charge mode */
  558. if (data < VBATT_RESISTOR_MIN || data > VBATT_RESISTOR_MAX)
  559. goto out;
  560. /* current is saved */
  561. if (set_charger_current(info, 500, &chg_current))
  562. goto out;
  563. /*
  564. * set charge current as 500mA, wait about 500ms till charging
  565. * process is launched and stable with the newer charging current.
  566. */
  567. msleep(500);
  568. for (i = 0, vbatt_sum1 = 0, ibatt_sum1 = 0; i < 10; i++) {
  569. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  570. if (ret)
  571. goto out_meas;
  572. vbatt_sum1 += data;
  573. ret = measure_current(info, &data);
  574. if (ret)
  575. goto out_meas;
  576. if (data < 0)
  577. ibatt_sum1 = ibatt_sum1 - data; /* discharging */
  578. else
  579. ibatt_sum1 = ibatt_sum1 + data; /* charging */
  580. }
  581. if (set_charger_current(info, 100, &ret))
  582. goto out_meas;
  583. /*
  584. * set charge current as 100mA, wait about 500ms till charging
  585. * process is launched and stable with the newer charging current.
  586. */
  587. msleep(500);
  588. for (i = 0, vbatt_sum2 = 0, ibatt_sum2 = 0; i < 10; i++) {
  589. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  590. if (ret)
  591. goto out_meas;
  592. vbatt_sum2 += data;
  593. ret = measure_current(info, &data);
  594. if (ret)
  595. goto out_meas;
  596. if (data < 0)
  597. ibatt_sum2 = ibatt_sum2 - data; /* discharging */
  598. else
  599. ibatt_sum2 = ibatt_sum2 + data; /* charging */
  600. }
  601. /* restore current setting */
  602. if (set_charger_current(info, chg_current, &ret))
  603. goto out_meas;
  604. if ((vbatt_sum1 > vbatt_sum2) && (ibatt_sum1 > ibatt_sum2) &&
  605. (ibatt_sum2 > 0)) {
  606. /* calculate resistor in discharging case */
  607. data = 1000 * (vbatt_sum1 - vbatt_sum2)
  608. / (ibatt_sum1 - ibatt_sum2);
  609. if ((data - info->resistor > 0) &&
  610. (data - info->resistor < info->resistor))
  611. info->resistor = data;
  612. if ((info->resistor - data > 0) &&
  613. (info->resistor - data < data))
  614. info->resistor = data;
  615. }
  616. return 0;
  617. out_meas:
  618. set_charger_current(info, chg_current, &ret);
  619. out:
  620. return -EINVAL;
  621. }
  622. static int calc_capacity(struct pm860x_battery_info *info, int *cap)
  623. {
  624. int ret;
  625. int data;
  626. int ibat;
  627. int cap_ocv = 0;
  628. int cap_cc = 0;
  629. ret = calc_ccnt(info, &ccnt_data);
  630. if (ret)
  631. goto out;
  632. soc:
  633. data = info->max_capacity * info->start_soc / 100;
  634. if (ccnt_data.total_dischg - ccnt_data.total_chg <= data) {
  635. cap_cc =
  636. data + ccnt_data.total_chg - ccnt_data.total_dischg;
  637. } else {
  638. clear_ccnt(info, &ccnt_data);
  639. calc_soc(info, OCV_MODE_ACTIVE, &info->start_soc);
  640. dev_dbg(info->dev, "restart soc = %d !\n",
  641. info->start_soc);
  642. goto soc;
  643. }
  644. cap_cc = cap_cc * 100 / info->max_capacity;
  645. if (cap_cc < 0)
  646. cap_cc = 0;
  647. else if (cap_cc > 100)
  648. cap_cc = 100;
  649. dev_dbg(info->dev, "%s, last cap : %d", __func__,
  650. info->last_capacity);
  651. ret = measure_current(info, &ibat);
  652. if (ret)
  653. goto out;
  654. /* Calculate the capacity when discharging(ibat < 0) */
  655. if (ibat < 0) {
  656. ret = calc_soc(info, OCV_MODE_ACTIVE, &cap_ocv);
  657. if (ret)
  658. cap_ocv = info->last_capacity;
  659. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  660. if (ret)
  661. goto out;
  662. if (data <= LOW_BAT_THRESHOLD) {
  663. /* choose the lower capacity value to report
  664. * between vbat and CC when vbat < 3.6v;
  665. * than 3.6v;
  666. */
  667. *cap = min(cap_ocv, cap_cc);
  668. } else {
  669. /* when detect vbat > 3.6v, but cap_cc < 15,and
  670. * cap_ocv is 10% larger than cap_cc, we can think
  671. * CC have some accumulation error, switch to OCV
  672. * to estimate capacity;
  673. * */
  674. if (cap_cc < 15 && cap_ocv - cap_cc > 10)
  675. *cap = cap_ocv;
  676. else
  677. *cap = cap_cc;
  678. }
  679. /* when discharging, make sure current capacity
  680. * is lower than last*/
  681. if (*cap > info->last_capacity)
  682. *cap = info->last_capacity;
  683. } else {
  684. *cap = cap_cc;
  685. }
  686. info->last_capacity = *cap;
  687. dev_dbg(info->dev, "%s, cap_ocv:%d cap_cc:%d, cap:%d\n",
  688. (ibat < 0) ? "discharging" : "charging",
  689. cap_ocv, cap_cc, *cap);
  690. /*
  691. * store the current capacity to RTC domain register,
  692. * after next power up , it will be restored.
  693. */
  694. pm860x_set_bits(info->i2c, PM8607_RTC_MISC2, RTC_SOC_5LSB,
  695. (*cap & 0x1F) << 3);
  696. pm860x_set_bits(info->i2c, PM8607_RTC1, RTC_SOC_3MSB,
  697. ((*cap >> 5) & 0x3));
  698. return 0;
  699. out:
  700. return ret;
  701. }
  702. static void pm860x_external_power_changed(struct power_supply *psy)
  703. {
  704. struct pm860x_battery_info *info = dev_get_drvdata(psy->dev.parent);
  705. calc_resistor(info);
  706. }
  707. static int pm860x_batt_get_prop(struct power_supply *psy,
  708. enum power_supply_property psp,
  709. union power_supply_propval *val)
  710. {
  711. struct pm860x_battery_info *info = dev_get_drvdata(psy->dev.parent);
  712. int data;
  713. int ret;
  714. switch (psp) {
  715. case POWER_SUPPLY_PROP_PRESENT:
  716. val->intval = info->present;
  717. break;
  718. case POWER_SUPPLY_PROP_CAPACITY:
  719. ret = calc_capacity(info, &data);
  720. if (ret)
  721. return ret;
  722. if (data < 0)
  723. data = 0;
  724. else if (data > 100)
  725. data = 100;
  726. /* return 100 if battery is not attached */
  727. if (!info->present)
  728. data = 100;
  729. val->intval = data;
  730. break;
  731. case POWER_SUPPLY_PROP_TECHNOLOGY:
  732. val->intval = POWER_SUPPLY_TECHNOLOGY_LION;
  733. break;
  734. case POWER_SUPPLY_PROP_VOLTAGE_NOW:
  735. /* return real vbatt Voltage */
  736. ret = measure_vbatt(info, OCV_MODE_ACTIVE, &data);
  737. if (ret)
  738. return ret;
  739. val->intval = data * 1000;
  740. break;
  741. case POWER_SUPPLY_PROP_VOLTAGE_AVG:
  742. /* return Open Circuit Voltage (not measured voltage) */
  743. ret = calc_ocv(info, &data);
  744. if (ret)
  745. return ret;
  746. val->intval = data * 1000;
  747. break;
  748. case POWER_SUPPLY_PROP_CURRENT_NOW:
  749. ret = measure_current(info, &data);
  750. if (ret)
  751. return ret;
  752. val->intval = data;
  753. break;
  754. case POWER_SUPPLY_PROP_TEMP:
  755. if (info->present) {
  756. ret = measure_temp(info, &data);
  757. if (ret)
  758. return ret;
  759. data *= 10;
  760. } else {
  761. /* Fake Temp 25C Without Battery */
  762. data = 250;
  763. }
  764. val->intval = data;
  765. break;
  766. default:
  767. return -ENODEV;
  768. }
  769. return 0;
  770. }
  771. static int pm860x_batt_set_prop(struct power_supply *psy,
  772. enum power_supply_property psp,
  773. const union power_supply_propval *val)
  774. {
  775. struct pm860x_battery_info *info = dev_get_drvdata(psy->dev.parent);
  776. switch (psp) {
  777. case POWER_SUPPLY_PROP_CHARGE_FULL:
  778. clear_ccnt(info, &ccnt_data);
  779. info->start_soc = 100;
  780. dev_dbg(info->dev, "chg done, update soc = %d\n",
  781. info->start_soc);
  782. break;
  783. default:
  784. return -EPERM;
  785. }
  786. return 0;
  787. }
  788. static enum power_supply_property pm860x_batt_props[] = {
  789. POWER_SUPPLY_PROP_PRESENT,
  790. POWER_SUPPLY_PROP_CAPACITY,
  791. POWER_SUPPLY_PROP_TECHNOLOGY,
  792. POWER_SUPPLY_PROP_VOLTAGE_NOW,
  793. POWER_SUPPLY_PROP_VOLTAGE_AVG,
  794. POWER_SUPPLY_PROP_CURRENT_NOW,
  795. POWER_SUPPLY_PROP_TEMP,
  796. };
  797. static const struct power_supply_desc pm860x_battery_desc = {
  798. .name = "battery-monitor",
  799. .type = POWER_SUPPLY_TYPE_BATTERY,
  800. .properties = pm860x_batt_props,
  801. .num_properties = ARRAY_SIZE(pm860x_batt_props),
  802. .get_property = pm860x_batt_get_prop,
  803. .set_property = pm860x_batt_set_prop,
  804. .external_power_changed = pm860x_external_power_changed,
  805. };
  806. static int pm860x_battery_probe(struct platform_device *pdev)
  807. {
  808. struct pm860x_chip *chip = dev_get_drvdata(pdev->dev.parent);
  809. struct pm860x_battery_info *info;
  810. struct pm860x_power_pdata *pdata;
  811. int ret;
  812. info = devm_kzalloc(&pdev->dev, sizeof(*info), GFP_KERNEL);
  813. if (!info)
  814. return -ENOMEM;
  815. info->irq_cc = platform_get_irq(pdev, 0);
  816. if (info->irq_cc <= 0)
  817. return -EINVAL;
  818. info->irq_batt = platform_get_irq(pdev, 1);
  819. if (info->irq_batt <= 0)
  820. return -EINVAL;
  821. info->chip = chip;
  822. info->i2c =
  823. (chip->id == CHIP_PM8607) ? chip->client : chip->companion;
  824. info->dev = &pdev->dev;
  825. info->status = POWER_SUPPLY_STATUS_UNKNOWN;
  826. pdata = pdev->dev.platform_data;
  827. mutex_init(&info->lock);
  828. platform_set_drvdata(pdev, info);
  829. pm860x_init_battery(info);
  830. if (pdata && pdata->max_capacity)
  831. info->max_capacity = pdata->max_capacity;
  832. else
  833. info->max_capacity = 1500; /* set default capacity */
  834. if (pdata && pdata->resistor)
  835. info->resistor = pdata->resistor;
  836. else
  837. info->resistor = 300; /* set default internal resistor */
  838. info->battery = devm_power_supply_register(&pdev->dev,
  839. &pm860x_battery_desc,
  840. NULL);
  841. if (IS_ERR(info->battery))
  842. return PTR_ERR(info->battery);
  843. info->battery->dev.parent = &pdev->dev;
  844. ret = devm_request_threaded_irq(chip->dev, info->irq_cc, NULL,
  845. pm860x_coulomb_handler, IRQF_ONESHOT,
  846. "coulomb", info);
  847. if (ret < 0) {
  848. dev_err(chip->dev, "Failed to request IRQ: #%d: %d\n",
  849. info->irq_cc, ret);
  850. return ret;
  851. }
  852. ret = devm_request_threaded_irq(chip->dev, info->irq_batt, NULL,
  853. pm860x_batt_handler,
  854. IRQF_ONESHOT, "battery", info);
  855. if (ret < 0) {
  856. dev_err(chip->dev, "Failed to request IRQ: #%d: %d\n",
  857. info->irq_batt, ret);
  858. return ret;
  859. }
  860. return 0;
  861. }
  862. #ifdef CONFIG_PM_SLEEP
  863. static int pm860x_battery_suspend(struct device *dev)
  864. {
  865. struct platform_device *pdev = to_platform_device(dev);
  866. struct pm860x_chip *chip = dev_get_drvdata(pdev->dev.parent);
  867. if (device_may_wakeup(dev))
  868. chip->wakeup_flag |= 1 << PM8607_IRQ_CC;
  869. return 0;
  870. }
  871. static int pm860x_battery_resume(struct device *dev)
  872. {
  873. struct platform_device *pdev = to_platform_device(dev);
  874. struct pm860x_chip *chip = dev_get_drvdata(pdev->dev.parent);
  875. if (device_may_wakeup(dev))
  876. chip->wakeup_flag &= ~(1 << PM8607_IRQ_CC);
  877. return 0;
  878. }
  879. #endif
  880. static SIMPLE_DEV_PM_OPS(pm860x_battery_pm_ops,
  881. pm860x_battery_suspend, pm860x_battery_resume);
  882. static struct platform_driver pm860x_battery_driver = {
  883. .driver = {
  884. .name = "88pm860x-battery",
  885. .pm = &pm860x_battery_pm_ops,
  886. },
  887. .probe = pm860x_battery_probe,
  888. };
  889. module_platform_driver(pm860x_battery_driver);
  890. MODULE_DESCRIPTION("Marvell 88PM860x Battery driver");
  891. MODULE_LICENSE("GPL");