ncp1854.c 25 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942
  1. /* Copyright Statement:
  2. *
  3. * This software/firmware and related documentation ("MediaTek Software") are
  4. * protected under relevant copyright laws. The information contained herein
  5. * is confidential and proprietary to MediaTek Inc. and/or its licensors.
  6. * Without the prior written permission of MediaTek inc. and/or its licensors,
  7. * any reproduction, modification, use or disclosure of MediaTek Software,
  8. * and information contained herein, in whole or in part, shall be strictly prohibited.
  9. */
  10. /* MediaTek Inc. (C) 2015. All rights reserved.
  11. *
  12. * BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
  13. * THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
  14. * RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER ON
  15. * AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
  16. * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
  17. * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
  18. * NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
  19. * SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
  20. * SUPPLIED WITH THE MEDIATEK SOFTWARE, AND RECEIVER AGREES TO LOOK ONLY TO SUCH
  21. * THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. RECEIVER EXPRESSLY ACKNOWLEDGES
  22. * THAT IT IS RECEIVER'S SOLE RESPONSIBILITY TO OBTAIN FROM ANY THIRD PARTY ALL PROPER LICENSES
  23. * CONTAINED IN MEDIATEK SOFTWARE. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK
  24. * SOFTWARE RELEASES MADE TO RECEIVER'S SPECIFICATION OR TO CONFORM TO A PARTICULAR
  25. * STANDARD OR OPEN FORUM. RECEIVER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND
  26. * CUMULATIVE LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
  27. * AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
  28. * OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY RECEIVER TO
  29. * MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
  30. */
  31. #include <platform/mt_typedefs.h>
  32. #include <platform/mt_reg_base.h>
  33. #include <platform/mt_i2c.h>
  34. #include <platform/mt_gpio.h>
  35. #include <platform/mt_pmic.h>
  36. #include <platform/ncp1854.h>
  37. #include <printf.h>
  38. #if !defined(CONFIG_POWER_EXT)
  39. #include <platform/upmu_common.h>
  40. #endif
  41. int g_ncp1854_log_en = 0;
  42. #define I2C_SWITCHING_CHARGER_CHANNEL 3
  43. #define DISABLE_NCP1854_FACTORY_MODE
  44. /**********************************************************
  45. *
  46. * [I2C Slave Setting]
  47. *
  48. *********************************************************/
  49. #define NCP1854_SLAVE_ADDR_WRITE 0x6C
  50. #define NCP1854_SLAVE_ADDR_READ 0x6D
  51. /**********************************************************
  52. *
  53. * [Global Variable]
  54. *
  55. *********************************************************/
  56. #define NCP1854_REG_NUM 18
  57. #ifdef I2C_SWITCHING_CHARGER_CHANNEL
  58. #define NCP1854_BUSNUM I2C_SWITCHING_CHARGER_CHANNEL
  59. #else
  60. #define NCP1854_BUSNUM 3
  61. #endif
  62. #define PRECC_BATVOL 2800 /* preCC 2.8V */
  63. /* #ifndef GPIO_SWCHARGER_EN_PIN
  64. #define GPIO_SWCHARGER_EN_PIN 65
  65. #endif */
  66. kal_uint8 ncp1854_reg[NCP1854_REG_NUM] = { 0 };
  67. /**********************************************************
  68. *
  69. * [I2C Function For Read/Write ncp1854]
  70. *
  71. *********************************************************/
  72. static struct mt_i2c_t ncp1854_i2c;
  73. kal_uint32 ncp1854_write_byte(kal_uint8 addr, kal_uint8 value)
  74. {
  75. kal_uint32 ret_code = I2C_OK;
  76. kal_uint8 write_data[2];
  77. kal_uint16 len;
  78. write_data[0] = addr;
  79. write_data[1] = value;
  80. ncp1854_i2c.id = NCP1854_BUSNUM;
  81. /* Since i2c will left shift 1 bit, we need to set NCP1854 I2C address to >>1 */
  82. ncp1854_i2c.addr = (NCP1854_SLAVE_ADDR_WRITE >> 1);
  83. ncp1854_i2c.mode = ST_MODE;
  84. ncp1854_i2c.speed = 100;
  85. len = 2;
  86. ret_code = i2c_write(&ncp1854_i2c, write_data, len);
  87. if (I2C_OK != ret_code)
  88. dprintf(INFO, "%s: i2c_write: ret_code: %d\n", __func__, ret_code);
  89. return ret_code;
  90. }
  91. kal_uint32 ncp1854_read_byte(kal_uint8 addr, kal_uint8 *dataBuffer)
  92. {
  93. kal_uint32 ret_code = I2C_OK;
  94. kal_uint16 len;
  95. *dataBuffer = addr;
  96. ncp1854_i2c.id = NCP1854_BUSNUM;
  97. /* Since i2c will left shift 1 bit, we need to set NCP1854 I2C address to >>1 */
  98. ncp1854_i2c.addr = (NCP1854_SLAVE_ADDR_READ >> 1);
  99. ncp1854_i2c.mode = ST_MODE;
  100. ncp1854_i2c.speed = 100;
  101. len = 1;
  102. ret_code = i2c_write_read(&ncp1854_i2c, dataBuffer, len, len);
  103. if (I2C_OK != ret_code)
  104. dprintf(INFO, "%s: i2c_read: ret_code: %d\n", __func__, ret_code);
  105. return ret_code;
  106. }
  107. /**********************************************************
  108. *
  109. * [Read / Write Function]
  110. *
  111. *********************************************************/
  112. kal_uint32 ncp1854_read_interface(kal_uint8 RegNum, kal_uint8 *val, kal_uint8 MASK,
  113. kal_uint8 SHIFT)
  114. {
  115. kal_uint8 ncp1854_reg = 0;
  116. int ret = 0;
  117. dprintf(INFO, "--------------------------------------------------\n");
  118. ret = ncp1854_read_byte(RegNum, &ncp1854_reg);
  119. dprintf(INFO, "[ncp1854_read_interface] Reg[%x]=0x%x\n", RegNum, ncp1854_reg);
  120. ncp1854_reg &= (MASK << SHIFT);
  121. *val = (ncp1854_reg >> SHIFT);
  122. dprintf(INFO, "[ncp1854_read_interface] Val=0x%x\n", *val);
  123. return ret;
  124. }
  125. kal_uint32 ncp1854_config_interface(kal_uint8 RegNum, kal_uint8 val, kal_uint8 MASK,
  126. kal_uint8 SHIFT)
  127. {
  128. kal_uint8 ncp1854_reg = 0;
  129. int ret = 0;
  130. dprintf(INFO, "--------------------------------------------------\n");
  131. ret = ncp1854_read_byte(RegNum, &ncp1854_reg);
  132. /* dprintf(INFO, "[ncp1854_config_interface] Reg[%x]=0x%x\n", RegNum, ncp1854_reg); */
  133. ncp1854_reg &= ~(MASK << SHIFT);
  134. ncp1854_reg |= (val << SHIFT);
  135. if (RegNum == NCP1854_CON1 && val == 1 && MASK == CON1_REG_RST_MASK
  136. && SHIFT == CON1_REG_RST_SHIFT) {
  137. /* RESET bit */
  138. } else if (RegNum == NCP1854_CON1) {
  139. ncp1854_reg &= ~0x80; /* RESET bit read returs 1, so clear it */
  140. }
  141. ret = ncp1854_write_byte(RegNum, ncp1854_reg);
  142. /* dprintf(INFO, "[ncp18546_config_interface] Write Reg[%x]=0x%x\n", RegNum, ncp1854_reg); */
  143. /* Check */
  144. /* ncp1854_read_byte(RegNum, &ncp1854_reg); */
  145. /* dprintf(INFO, "[ncp1854_config_interface] Check Reg[%x]=0x%x\n", RegNum, ncp1854_reg); */
  146. return ret;
  147. }
  148. /**********************************************************
  149. *
  150. * [ncp1854 Function]
  151. *
  152. *********************************************************/
  153. /* CON0 */
  154. kal_uint32 ncp1854_get_chip_status(void)
  155. {
  156. kal_uint32 ret = 0;
  157. kal_uint8 val = 0;
  158. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON0),
  159. (&val),
  160. (kal_uint8) (CON0_STATE_MASK), (kal_uint8) (CON0_STATE_SHIFT)
  161. );
  162. return val;
  163. }
  164. kal_uint32 ncp1854_get_batfet(void)
  165. {
  166. kal_uint32 ret = 0;
  167. kal_uint8 val = 0;
  168. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON0),
  169. (&val),
  170. (kal_uint8) (CON0_BATFET_MASK), (kal_uint8) (CON0_BATFET_SHIFT)
  171. );
  172. return val;
  173. }
  174. kal_uint32 ncp1854_get_statint(void)
  175. {
  176. kal_uint32 ret = 0;
  177. kal_uint8 val = 0;
  178. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON0),
  179. (&val),
  180. (kal_uint8) (CON0_STATINT_MASK),
  181. (kal_uint8) (CON0_STATINT_SHIFT)
  182. );
  183. return val;
  184. }
  185. kal_uint32 ncp1854_get_faultint(void)
  186. {
  187. kal_uint32 ret = 0;
  188. kal_uint8 val = 0;
  189. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON0),
  190. (&val),
  191. (kal_uint8) (CON0_FAULTINT_MASK),
  192. (kal_uint8) (CON0_FAULTINT_SHIFT)
  193. );
  194. return val;
  195. }
  196. /* CON1 */
  197. void ncp1854_set_reset(kal_uint32 val)
  198. {
  199. kal_uint32 ret = 0;
  200. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  201. (kal_uint8) (val),
  202. (kal_uint8) (CON1_REG_RST_MASK),
  203. (kal_uint8) (CON1_REG_RST_SHIFT)
  204. );
  205. }
  206. void ncp1854_set_chg_en(kal_uint32 val)
  207. {
  208. kal_uint32 ret = 0;
  209. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  210. (kal_uint8) (val),
  211. (kal_uint8) (CON1_CHG_EN_MASK),
  212. (kal_uint8) (CON1_CHG_EN_SHIFT)
  213. );
  214. }
  215. void ncp1854_set_otg_en(kal_uint32 val)
  216. {
  217. kal_uint32 ret = 0;
  218. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  219. (kal_uint8) (val),
  220. (kal_uint8) (CON1_OTG_EN_MASK),
  221. (kal_uint8) (CON1_OTG_EN_SHIFT)
  222. );
  223. return val;
  224. }
  225. kal_uint32 ncp1854_get_otg_en(void)
  226. {
  227. kal_uint32 ret = 0;
  228. kal_uint8 val = 0;
  229. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON1),
  230. (&val),
  231. (kal_uint8) (CON1_OTG_EN_MASK), (kal_uint8) (CON1_OTG_EN_SHIFT)
  232. );
  233. return val;
  234. }
  235. void ncp1854_set_fctry_mode(kal_uint32 val)
  236. {
  237. kal_uint32 ret = 0;
  238. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  239. (kal_uint8) (val),
  240. (kal_uint8) (CON1_FCTRY_MOD_MASK),
  241. (kal_uint8) (CON1_FCTRY_MOD_SHIFT)
  242. );
  243. }
  244. void ncp1854_set_tj_warn_opt(kal_uint32 val)
  245. {
  246. kal_uint32 ret = 0;
  247. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  248. (kal_uint8) (val),
  249. (kal_uint8) (CON1_TJ_WARN_OPT_MASK),
  250. (kal_uint8) (CON1_TJ_WARN_OPT_SHIFT)
  251. );
  252. }
  253. kal_uint32 ncp1854_get_usb_cfg(void)
  254. {
  255. kal_uint32 ret = 0;
  256. kal_uint8 val = 0;
  257. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON1),
  258. (&val),
  259. (kal_uint8) (CON1_USB_CFG_MASK),
  260. (kal_uint8) (CON1_USB_CFG_SHIFT)
  261. );
  262. return val;
  263. }
  264. void ncp1854_set_tchg_rst(kal_uint32 val)
  265. {
  266. kal_uint32 ret = 0;
  267. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  268. (kal_uint8) (val),
  269. (kal_uint8) (CON1_TCHG_RST_MASK),
  270. (kal_uint8) (CON1_TCHG_RST_SHIFT)
  271. );
  272. }
  273. void ncp1854_set_int_mask(kal_uint32 val)
  274. {
  275. kal_uint32 ret = 0;
  276. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON1),
  277. (kal_uint8) (val),
  278. (kal_uint8) (CON1_INT_MASK_MASK),
  279. (kal_uint8) (CON1_INT_MASK_SHIFT)
  280. );
  281. }
  282. /* CON2 */
  283. void ncp1854_set_wdto_dis(kal_uint32 val)
  284. {
  285. kal_uint32 ret = 0;
  286. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  287. (kal_uint8) (val),
  288. (kal_uint8) (CON2_WDTO_DIS_MASK),
  289. (kal_uint8) (CON2_WDTO_DIS_SHIFT)
  290. );
  291. }
  292. void ncp1854_set_chgto_dis(kal_uint32 val)
  293. {
  294. kal_uint32 ret = 0;
  295. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  296. (kal_uint8) (val),
  297. (kal_uint8) (CON2_CHGTO_DIS_MASK),
  298. (kal_uint8) (CON2_CHGTO_DIS_SHIFT)
  299. );
  300. }
  301. void ncp1854_set_pwr_path(kal_uint32 val)
  302. {
  303. kal_uint32 ret = 0;
  304. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  305. (kal_uint8) (val),
  306. (kal_uint8) (CON2_PWR_PATH_MASK),
  307. (kal_uint8) (CON2_PWR_PATH_SHIFT)
  308. );
  309. }
  310. void ncp1854_set_trans_en(kal_uint32 val)
  311. {
  312. kal_uint32 ret = 0;
  313. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  314. (kal_uint8) (val),
  315. (kal_uint8) (CON2_TRANS_EN_MASK),
  316. (kal_uint8) (CON2_TRANS_EN_SHIFT)
  317. );
  318. }
  319. void ncp1854_set_iinset_pin_en(kal_uint32 val)
  320. {
  321. kal_uint32 ret = 0;
  322. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  323. (kal_uint8) (val),
  324. (kal_uint8) (CON2_IINSET_PIN_EN_MASK),
  325. (kal_uint8) (CON2_IINSET_PIN_EN_SHIFT)
  326. );
  327. }
  328. void ncp1854_set_iinlim_en(kal_uint32 val)
  329. {
  330. kal_uint32 ret = 0;
  331. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  332. (kal_uint8) (val),
  333. (kal_uint8) (CON2_IINLIM_EN_MASK),
  334. (kal_uint8) (CON2_IINLIM_EN_SHIFT)
  335. );
  336. }
  337. void ncp1854_set_aicl_en(kal_uint32 val)
  338. {
  339. kal_uint32 ret = 0;
  340. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON2),
  341. (kal_uint8) (val),
  342. (kal_uint8) (CON2_AICL_EN_MASK),
  343. (kal_uint8) (CON2_AICL_EN_SHIFT)
  344. );
  345. }
  346. /* CON8 */
  347. kal_uint32 ncp1854_get_vfet_ok(void)
  348. {
  349. kal_uint32 ret = 0;
  350. kal_uint8 val = 0;
  351. ret = ncp1854_read_interface((kal_uint8) (NCP1854_CON8),
  352. (&val),
  353. (kal_uint8) (CON8_VFET_OK_MASK),
  354. (kal_uint8) (CON8_VFET_OK_SHIFT)
  355. );
  356. return val;
  357. }
  358. /* CON14 */
  359. void ncp1854_set_ctrl_vbat(kal_uint32 val)
  360. {
  361. kal_uint32 ret = 0;
  362. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON14),
  363. (kal_uint8) (val),
  364. (kal_uint8) (CON14_CTRL_VBAT_MASK),
  365. (kal_uint8) (CON14_CTRL_VBAT_SHIFT)
  366. );
  367. }
  368. /* CON15 */
  369. void ncp1854_set_ichg_high(kal_uint32 val)
  370. {
  371. kal_uint32 ret = 0;
  372. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON15),
  373. (kal_uint8) (val),
  374. (kal_uint8) (CON15_ICHG_HIGH_MASK),
  375. (kal_uint8) (CON15_ICHG_HIGH_SHIFT)
  376. );
  377. }
  378. void ncp1854_set_ieoc(kal_uint32 val)
  379. {
  380. kal_uint32 ret = 0;
  381. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON15),
  382. (kal_uint8) (val),
  383. (kal_uint8) (CON15_IEOC_MASK), (kal_uint8) (CON15_IEOC_SHIFT)
  384. );
  385. }
  386. void ncp1854_set_ichg(kal_uint32 val)
  387. {
  388. kal_uint32 ret = 0;
  389. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON15),
  390. (kal_uint8) (val),
  391. (kal_uint8) (CON15_ICHG_MASK), (kal_uint8) (CON15_ICHG_SHIFT)
  392. );
  393. }
  394. kal_uint32 ncp1854_get_ichg(void)
  395. {
  396. kal_uint32 ret = 0;
  397. kal_uint8 val = 0;
  398. ret = ncp1854_read_interface((kal_uint8) NCP1854_CON15,
  399. (&val),
  400. (kal_uint8) CON15_ICHG_MASK, (kal_uint8) CON15_ICHG_SHIFT);
  401. return val;
  402. }
  403. /* CON16 */
  404. void ncp1854_set_iweak(kal_uint32 val)
  405. {
  406. kal_uint32 ret = 0;
  407. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON16),
  408. (kal_uint8) (val),
  409. (kal_uint8) (CON16_IWEAK_MASK),
  410. (kal_uint8) (CON16_IWEAK_SHIFT)
  411. );
  412. }
  413. void ncp1854_set_ctrl_vfet(kal_uint32 val)
  414. {
  415. kal_uint32 ret = 0;
  416. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON16),
  417. (kal_uint8) (val),
  418. (kal_uint8) (CON16_CTRL_VFET_MASK),
  419. (kal_uint8) (CON16_CTRL_VFET_SHIFT)
  420. );
  421. }
  422. void ncp1854_set_iinlim(kal_uint32 val)
  423. {
  424. kal_uint32 ret = 0;
  425. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON16),
  426. (kal_uint8) (val),
  427. (kal_uint8) (CON16_IINLIM_MASK),
  428. (kal_uint8) (CON16_IINLIM_SHIFT)
  429. );
  430. }
  431. /* CON17 */
  432. void ncp1854_set_iinlim_ta(kal_uint32 val)
  433. {
  434. kal_uint32 ret = 0;
  435. ret = ncp1854_config_interface((kal_uint8) (NCP1854_CON17),
  436. (kal_uint8) (val),
  437. (kal_uint8) (CON17_IINLIM_TA_MASK),
  438. (kal_uint8) (CON17_IINLIM_TA_SHIFT)
  439. );
  440. }
  441. /**********************************************************
  442. *
  443. * [Internal Function]
  444. *
  445. *********************************************************/
  446. void ncp1854_dump_register(void)
  447. {
  448. int i = 0;
  449. for (i = 0; i < NCP1854_REG_NUM; i++) {
  450. if ((i == 3) || (i == 4) || (i == 5) || (i == 6)) /* do not dump read clear status register */
  451. continue;
  452. if ((i == 10) || (i == 11) || (i == 12) || (i == 13)) /* do not dump interrupt mask bit register */
  453. continue;
  454. ncp1854_read_byte(i, &ncp1854_reg[i]);
  455. printf("[ncp1854_dump_register] Reg[0x%X]=0x%X\n", i, ncp1854_reg[i]);
  456. }
  457. }
  458. void ncp1854_hw_init(void)
  459. {
  460. printf("[ncp1854] ChargerHwInit_ncp1854\n");
  461. kal_uint32 ncp1854_status;
  462. ncp1854_status = ncp1854_get_chip_status();
  463. /* if you want disable factory mode,the FTRY pin and FCTRY_MOD_REG need different */
  464. #ifdef DISABLE_NCP1854_FACTORY_MODE
  465. ncp1854_set_fctry_mode(0x0);
  466. #else
  467. ncp1854_set_fctry_mode(0x1);
  468. #endif
  469. ncp1854_set_otg_en(0x0);
  470. ncp1854_set_trans_en(0);
  471. ncp1854_set_tj_warn_opt(0x0);
  472. /* ncp1854_set_int_mask(0x0); //disable all interrupt */
  473. ncp1854_set_int_mask(0x1); /* enable all interrupt for boost mode status monitor */
  474. /* ncp1854_set_tchg_rst(0x1); //reset charge timer */
  475. #ifdef NCP1854_PWR_PATH
  476. ncp1854_set_pwr_path(0x1);
  477. #else
  478. ncp1854_set_pwr_path(0x0);
  479. #endif
  480. if ((ncp1854_status == 0x8) || (ncp1854_status == 0x9) || (ncp1854_status == 0xA)) /* WEAK WAIT, WEAK SAFE, WEAK CHARGE */
  481. ncp1854_set_ctrl_vbat(0x1C); /* VCHG = 4.0V */
  482. else {
  483. ncp1854_set_ctrl_vbat(0x24); /* VCHG = 4.2V */
  484. ncp1854_set_aicl_en(0x1); /* enable AICL as PT team suggest */
  485. ncp1854_set_iinset_pin_en(0x0); /* Input current limit and AICL control by I2C */
  486. ncp1854_set_chgto_dis(0x1); /* disable charge timer */
  487. }
  488. ncp1854_set_ieoc(0x4); /* terminate current = 200mA for ICS optimized suspend power */
  489. ncp1854_set_iweak(0x3); /* weak charge current = 300mA */
  490. ncp1854_set_ctrl_vfet(0x0); /* VFET = 3.1V */
  491. }
  492. static CHARGER_TYPE g_chr_type_num = CHARGER_UNKNOWN;
  493. int hw_charging_get_charger_type(void);
  494. extern int g_std_ac_large_current_en;
  495. void ncp1854_charging_enable(kal_uint32 bEnable)
  496. {
  497. int temp_CC_value = 0;
  498. kal_int32 bat_val = 0;
  499. if (CHARGER_UNKNOWN == g_chr_type_num && KAL_TRUE == upmu_is_chr_det()) {
  500. hw_charging_get_charger_type();
  501. dprintf(CRITICAL, "[BATTERY:ncp1854] charger type: %d\n", g_chr_type_num);
  502. }
  503. bat_val = get_i_sense_volt(1);
  504. if (g_chr_type_num == STANDARD_CHARGER) {
  505. if (g_std_ac_large_current_en == 1) {
  506. temp_CC_value = 2000;
  507. ncp1854_set_iinlim_ta(0xF); /* IN current limit at 2A */
  508. ncp1854_set_iinlim_en(0x1); /* IN current limit enable */
  509. if (bat_val < PRECC_BATVOL) {
  510. ncp1854_set_ichg_high(0x0); /* ICHG */
  511. ncp1854_set_ichg(0x1); /* Pre-Charging Current Limit at 500mA */
  512. } else {
  513. ncp1854_set_ichg_high(0); /* ICHG */
  514. ncp1854_set_ichg(0xF); /* Fast Charging Current Limit at 1.9A */
  515. }
  516. } else {
  517. temp_CC_value = 1500;
  518. ncp1854_set_iinlim_ta(0xA); /* IN current limit at 1.5A */
  519. ncp1854_set_iinlim_en(0x1); /* IN current limit enable */
  520. if (bat_val < PRECC_BATVOL) {
  521. ncp1854_set_ichg_high(0x0); /* ICHG */
  522. ncp1854_set_ichg(0x1); /* Pre-Charging Current Limit at 500mA */
  523. } else {
  524. ncp1854_set_ichg_high(0); /* ICHG */
  525. ncp1854_set_ichg(0xB); /* Fast Charging Current Limit at 1.5A */
  526. }
  527. }
  528. } else if (g_chr_type_num == STANDARD_HOST
  529. || g_chr_type_num == CHARGING_HOST || g_chr_type_num == NONSTANDARD_CHARGER) {
  530. temp_CC_value = 500;
  531. ncp1854_set_iinlim_ta(0); /* IINLIM */
  532. ncp1854_set_iinlim(0x1); /* IN current limit at 500mA */
  533. ncp1854_set_iinlim_en(0x1); /* IN current limit enable */
  534. ncp1854_set_ichg_high(0x0); /* ICHG */
  535. ncp1854_set_ichg(0x1); /* Pre-Charging Current Limit at 500mA */
  536. } else {
  537. temp_CC_value = 500;
  538. ncp1854_set_iinlim_ta(0); /* IINLIM */
  539. ncp1854_set_iinlim(0x1); /* IN current limit at 500mA */
  540. ncp1854_set_iinlim_en(0x1); /* IN current limit enable */
  541. ncp1854_set_ichg_high(0x0); /* ICHG */
  542. ncp1854_set_ichg(0x1); /* Pre-Charging Current Limit at 500mA */
  543. }
  544. if (KAL_TRUE == bEnable)
  545. ncp1854_set_chg_en(0x1); /* charger enable */
  546. else
  547. ncp1854_set_chg_en(0x0); /* charger disable */
  548. ncp1854_set_wdto_dis(0x0);
  549. dprintf(INFO, "[BATTERY:ncp1854] ncp1854_set_ac_current(), CC value(%dmA) \r\n",
  550. temp_CC_value);
  551. dprintf(INFO, "[BATTERY:ncp1854] charger enable/disable %d !\r\n", bEnable);
  552. }
  553. #if defined(CONFIG_POWER_EXT)
  554. int hw_charging_get_charger_type(void)
  555. {
  556. g_chr_type_num = STANDARD_HOST;
  557. return STANDARD_HOST;
  558. }
  559. #else
  560. extern void Charger_Detect_Init(void);
  561. extern void Charger_Detect_Release(void);
  562. extern void mdelay(unsigned long msec);
  563. extern kal_uint16 bc11_set_register_value(PMU_FLAGS_LIST_ENUM flagname, kal_uint32 val);
  564. static void hw_bc11_dump_register(void)
  565. {
  566. /*
  567. kal_uint32 reg_val = 0;
  568. kal_uint32 reg_num = CHR_CON18;
  569. kal_uint32 i = 0;
  570. for(i=reg_num ; i<=CHR_CON19 ; i+=2)
  571. {
  572. reg_val = upmu_get_reg_value(i);
  573. dprintf(INFO, "Chr Reg[0x%x]=0x%x \r\n", i, reg_val);
  574. }
  575. */
  576. }
  577. static void hw_bc11_init(void)
  578. {
  579. mdelay(200);
  580. Charger_Detect_Init();
  581. /* RG_bc11_BIAS_EN=1 */
  582. bc11_set_register_value(PMIC_RG_BC11_BIAS_EN, 1);
  583. /* RG_bc11_VSRC_EN[1:0]=00 */
  584. bc11_set_register_value(PMIC_RG_BC11_VSRC_EN, 0);
  585. /* RG_bc11_VREF_VTH = [1:0]=00 */
  586. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0);
  587. /* RG_bc11_CMP_EN[1.0] = 00 */
  588. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0);
  589. /* RG_bc11_IPU_EN[1.0] = 00 */
  590. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0);
  591. /* RG_bc11_IPD_EN[1.0] = 00 */
  592. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0);
  593. /* bc11_RST=1 */
  594. bc11_set_register_value(PMIC_RG_BC11_RST, 1);
  595. /* bc11_BB_CTRL=1 */
  596. bc11_set_register_value(PMIC_RG_BC11_BB_CTRL, 1);
  597. mdelay(50);
  598. if (g_ncp1854_log_en > 1) {
  599. dprintf(INFO, "hw_bc11_init() \r\n");
  600. hw_bc11_dump_register();
  601. }
  602. }
  603. static U32 hw_bc11_DCD(void)
  604. {
  605. U32 wChargerAvail = 0;
  606. /* RG_bc11_IPU_EN[1.0] = 10 */
  607. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0x2);
  608. /* RG_bc11_IPD_EN[1.0] = 01 */
  609. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x1);
  610. /* RG_bc11_VREF_VTH = [1:0]=01 */
  611. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x1);
  612. /* RG_bc11_CMP_EN[1.0] = 10 */
  613. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x2);
  614. mdelay(80);
  615. wChargerAvail = bc11_get_register_value(PMIC_RGS_BC11_CMP_OUT);
  616. if (g_ncp1854_log_en > 1) {
  617. dprintf(INFO, "hw_bc11_DCD() \r\n");
  618. hw_bc11_dump_register();
  619. }
  620. /* RG_bc11_IPU_EN[1.0] = 00 */
  621. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0x0);
  622. /* RG_bc11_IPD_EN[1.0] = 00 */
  623. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x0);
  624. /* RG_bc11_CMP_EN[1.0] = 00 */
  625. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x0);
  626. /* RG_bc11_VREF_VTH = [1:0]=00 */
  627. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x0);
  628. return wChargerAvail;
  629. }
  630. static U32 hw_bc11_stepA1(void)
  631. {
  632. U32 wChargerAvail = 0;
  633. /* RG_bc11_IPD_EN[1.0] = 01 */
  634. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x1);
  635. /* RG_bc11_VREF_VTH = [1:0]=00 */
  636. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x0);
  637. /* RG_bc11_CMP_EN[1.0] = 01 */
  638. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x1);
  639. mdelay(80);
  640. wChargerAvail = bc11_get_register_value(PMIC_RGS_BC11_CMP_OUT);
  641. if (g_ncp1854_log_en > 1) {
  642. dprintf(INFO, "hw_bc11_stepA1() \r\n");
  643. hw_bc11_dump_register();
  644. }
  645. /* RG_bc11_IPD_EN[1.0] = 00 */
  646. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x0);
  647. /* RG_bc11_CMP_EN[1.0] = 00 */
  648. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x0);
  649. return wChargerAvail;
  650. }
  651. static U32 hw_bc11_stepA2(void)
  652. {
  653. U32 wChargerAvail = 0;
  654. /* RG_bc11_VSRC_EN[1.0] = 10 */
  655. bc11_set_register_value(PMIC_RG_BC11_VSRC_EN, 0x2);
  656. /* RG_bc11_IPD_EN[1:0] = 01 */
  657. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x1);
  658. /* RG_bc11_VREF_VTH = [1:0]=00 */
  659. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x0);
  660. /* RG_bc11_CMP_EN[1.0] = 01 */
  661. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x1);
  662. mdelay(80);
  663. wChargerAvail = bc11_get_register_value(PMIC_RGS_BC11_CMP_OUT);
  664. if (g_ncp1854_log_en) {
  665. dprintf(INFO, "hw_bc11_stepB1() \r\n");
  666. hw_bc11_dump_register();
  667. }
  668. /* RG_bc11_VSRC_EN[1:0]=00 */
  669. bc11_set_register_value(PMIC_RG_BC11_VSRC_EN, 0x0);
  670. /* RG_bc11_IPD_EN[1.0] = 00 */
  671. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x0);
  672. /* RG_bc11_CMP_EN[1.0] = 00 */
  673. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x0);
  674. return wChargerAvail;
  675. }
  676. static U32 hw_bc11_stepB2(void)
  677. {
  678. U32 wChargerAvail = 0;
  679. /* RG_bc11_IPU_EN[1:0]=10 */
  680. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0x2);
  681. /* RG_bc11_VREF_VTH = [1:0]=01 */
  682. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x1);
  683. /* RG_bc11_CMP_EN[1.0] = 01 */
  684. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x1);
  685. mdelay(80);
  686. wChargerAvail = bc11_get_register_value(PMIC_RGS_BC11_CMP_OUT);
  687. if (g_ncp1854_log_en) {
  688. dprintf(INFO, "hw_bc11_stepB2() \r\n");
  689. hw_bc11_dump_register();
  690. }
  691. if (!wChargerAvail) {
  692. /* RG_bc11_VSRC_EN[1.0] = 10 */
  693. /* mt6325_upmu_set_rg_bc11_vsrc_en(0x2); */
  694. bc11_set_register_value(PMIC_RG_BC11_VSRC_EN, 0x2);
  695. }
  696. /* RG_bc11_IPU_EN[1.0] = 00 */
  697. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0x0);
  698. /* RG_bc11_CMP_EN[1.0] = 00 */
  699. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x0);
  700. /* RG_bc11_VREF_VTH = [1:0]=00 */
  701. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x0);
  702. return wChargerAvail;
  703. }
  704. static void hw_bc11_done(void)
  705. {
  706. /* RG_bc11_VSRC_EN[1:0]=00 */
  707. bc11_set_register_value(PMIC_RG_BC11_VSRC_EN, 0x0);
  708. /* RG_bc11_VREF_VTH = [1:0]=0 */
  709. bc11_set_register_value(PMIC_RG_BC11_VREF_VTH, 0x0);
  710. /* RG_bc11_CMP_EN[1.0] = 00 */
  711. bc11_set_register_value(PMIC_RG_BC11_CMP_EN, 0x0);
  712. /* RG_bc11_IPU_EN[1.0] = 00 */
  713. bc11_set_register_value(PMIC_RG_BC11_IPU_EN, 0x0);
  714. /* RG_bc11_IPD_EN[1.0] = 00 */
  715. bc11_set_register_value(PMIC_RG_BC11_IPD_EN, 0x0);
  716. /* RG_bc11_BIAS_EN=0 */
  717. bc11_set_register_value(PMIC_RG_BC11_BIAS_EN, 0x0);
  718. Charger_Detect_Release();
  719. if (g_ncp1854_log_en > 1) {
  720. dprintf(INFO, "hw_bc11_done() \r\n");
  721. hw_bc11_dump_register();
  722. }
  723. }
  724. int hw_charging_get_charger_type(void)
  725. {
  726. if (CHARGER_UNKNOWN != g_chr_type_num)
  727. return g_chr_type_num;
  728. #if 0
  729. return STANDARD_HOST;
  730. #else
  731. CHARGER_TYPE CHR_Type_num = CHARGER_UNKNOWN;
  732. /********* Step initial ***************/
  733. hw_bc11_init();
  734. /********* Step DCD ***************/
  735. if (1 == hw_bc11_DCD()) {
  736. /********* Step A1 ***************/
  737. if (1 == hw_bc11_stepA1()) {
  738. CHR_Type_num = APPLE_2_1A_CHARGER;
  739. dprintf(INFO, "step A1 : Apple 2.1A CHARGER!\r\n");
  740. } else {
  741. CHR_Type_num = NONSTANDARD_CHARGER;
  742. dprintf(INFO, "step A1 : Non STANDARD CHARGER!\r\n");
  743. }
  744. } else {
  745. /********* Step A2 ***************/
  746. if (1 == hw_bc11_stepA2()) {
  747. /********* Step B2 ***************/
  748. if (1 == hw_bc11_stepB2()) {
  749. CHR_Type_num = STANDARD_CHARGER;
  750. dprintf(INFO, "step B2 : STANDARD CHARGER!\r\n");
  751. } else {
  752. CHR_Type_num = CHARGING_HOST;
  753. dprintf(INFO, "step B2 : Charging Host!\r\n");
  754. }
  755. } else {
  756. CHR_Type_num = STANDARD_HOST;
  757. dprintf(INFO, "step A2 : Standard USB Host!\r\n");
  758. }
  759. }
  760. /********* Finally setting *******************************/
  761. hw_bc11_done();
  762. g_chr_type_num = CHR_Type_num;
  763. return g_chr_type_num;
  764. #endif
  765. }
  766. #endif