xref: /OK3568_Linux_fs/kernel/drivers/power/supply/rk816_battery.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /*
2*4882a593Smuzhiyun  * rk816_battery.h: fuel gauge driver structures
3*4882a593Smuzhiyun  *
4*4882a593Smuzhiyun  * Copyright (C) 2016 Rockchip Electronics Co., Ltd
5*4882a593Smuzhiyun  * Author: chenjh <chenjh@rock-chips.com>
6*4882a593Smuzhiyun  *
7*4882a593Smuzhiyun  * This program is free software; you can redistribute it and/or modify it
8*4882a593Smuzhiyun  * under the terms and conditions of the GNU General Public License,
9*4882a593Smuzhiyun  * version 2, as published by the Free Software Foundation.
10*4882a593Smuzhiyun  *
11*4882a593Smuzhiyun  * This program is distributed in the hope it will be useful, but WITHOUT
12*4882a593Smuzhiyun  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13*4882a593Smuzhiyun  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14*4882a593Smuzhiyun  * more details.
15*4882a593Smuzhiyun  */
16*4882a593Smuzhiyun 
17*4882a593Smuzhiyun #ifndef RK816_BATTERY
18*4882a593Smuzhiyun #define RK816_BATTERY
19*4882a593Smuzhiyun 
20*4882a593Smuzhiyun /*TS_CTRL_REG*/
21*4882a593Smuzhiyun #define GG_EN			BIT(7)
22*4882a593Smuzhiyun #define ADC_CUR_EN		BIT(6)
23*4882a593Smuzhiyun #define ADC_TS1_EN		BIT(5)
24*4882a593Smuzhiyun #define ADC_TS2_EN		BIT(4)
25*4882a593Smuzhiyun 
26*4882a593Smuzhiyun /*GGCON*/
27*4882a593Smuzhiyun #define ADC_CUR_MODE		(0x01 << 1)
28*4882a593Smuzhiyun #define AVG_CUR_MODE		(0x00 << 0)
29*4882a593Smuzhiyun #define ADC_CAL_MIN_MSK		0x30
30*4882a593Smuzhiyun #define ADC_CAL_8MIN		(0x00 << 4)
31*4882a593Smuzhiyun #define OCV_SAMP_MIN_MSK	0x0c
32*4882a593Smuzhiyun #define OCV_SAMP_8MIN		(0x00 << 2)
33*4882a593Smuzhiyun 
34*4882a593Smuzhiyun /*GGSTS*/
35*4882a593Smuzhiyun #define FCC_LOCK		(1 << 5)
36*4882a593Smuzhiyun #define BAT_CON			(1 << 4)
37*4882a593Smuzhiyun #define RELAX_STS		(1 << 1)
38*4882a593Smuzhiyun #define RELAX_VOL1_UPD		BIT(3)
39*4882a593Smuzhiyun #define RELAX_VOL2_UPD		BIT(2)
40*4882a593Smuzhiyun #define RELAX_VOL12_UPD_MSK	(RELAX_VOL1_UPD | RELAX_VOL2_UPD)
41*4882a593Smuzhiyun 
42*4882a593Smuzhiyun /*SUP_STS_REG*/
43*4882a593Smuzhiyun #define BAT_EXS			(1 << 7)
44*4882a593Smuzhiyun #define CHARGE_OFF		(0x00 << 4)
45*4882a593Smuzhiyun #define DEAD_CHARGE		(0x01 << 4)
46*4882a593Smuzhiyun #define TRICKLE_CHARGE		(0x02 << 4)
47*4882a593Smuzhiyun #define CC_OR_CV		(0x03 << 4)
48*4882a593Smuzhiyun #define CHARGE_FINISH		(0x04 << 4)
49*4882a593Smuzhiyun #define USB_OVER_VOL		(0x05 << 4)
50*4882a593Smuzhiyun #define BAT_TMP_ERR		(0x06 << 4)
51*4882a593Smuzhiyun #define TIMER_ERR		(0x07 << 4)
52*4882a593Smuzhiyun #define USB_EXIST		(1 << 1)
53*4882a593Smuzhiyun #define USB_EFF			(1 << 0)
54*4882a593Smuzhiyun #define USB_VLIMIT_EN		BIT(3)
55*4882a593Smuzhiyun #define USB_CLIMIT_EN		BIT(2)
56*4882a593Smuzhiyun #define CHRG_STATUS_MSK		0x70
57*4882a593Smuzhiyun 
58*4882a593Smuzhiyun /*USB_CTRL_REG*/
59*4882a593Smuzhiyun #define CHRG_CT_EN		(1 << 7)
60*4882a593Smuzhiyun #define INPUT_CUR_MSK		(0x0f)
61*4882a593Smuzhiyun #define FINISH_CUR_MSK		0xc0
62*4882a593Smuzhiyun #define CHRG_CUR_MSK		(0x0f)
63*4882a593Smuzhiyun 
64*4882a593Smuzhiyun /* BAT_CTRL_REG */
65*4882a593Smuzhiyun #define USB_SYS_EN		BIT(6)
66*4882a593Smuzhiyun 
67*4882a593Smuzhiyun /* THERMAL_REG */
68*4882a593Smuzhiyun #define FB_TEMP_MSK		0x0c
69*4882a593Smuzhiyun #define HOTDIE_STS		BIT(1)
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun /*CHGR_CUR_INPUT*/
72*4882a593Smuzhiyun #define INPUT_CUR450MA		(0x00)
73*4882a593Smuzhiyun #define INPUT_CUR80MA		(0x01)
74*4882a593Smuzhiyun #define INPUT_CUR850MA		(0x02)
75*4882a593Smuzhiyun #define INPUT_CUR1000MA		(0x03)
76*4882a593Smuzhiyun #define INPUT_CUR1250MA		(0x04)
77*4882a593Smuzhiyun #define INPUT_CUR1500MA		(0x05)
78*4882a593Smuzhiyun #define INPUT_CUR1750MA		(0x06)
79*4882a593Smuzhiyun #define INPUT_CUR2000MA		(0x07)
80*4882a593Smuzhiyun #define INPUT_CUR2250MA		(0x08)
81*4882a593Smuzhiyun #define INPUT_CUR2500MA		(0x09)
82*4882a593Smuzhiyun #define INPUT_CUR2750MA		(0x0A)
83*4882a593Smuzhiyun #define INPUT_CUR3000MA		(0x0B)
84*4882a593Smuzhiyun 
85*4882a593Smuzhiyun /*CHRG_VOL_SEL*/
86*4882a593Smuzhiyun #define CHRG_VOL4050MV		(0x00 << 4)
87*4882a593Smuzhiyun #define CHRG_VOL4100MV		(0x01 << 4)
88*4882a593Smuzhiyun #define CHRG_VOL4150MV		(0x02 << 4)
89*4882a593Smuzhiyun #define CHRG_VOL4200MV		(0x03 << 4)
90*4882a593Smuzhiyun #define CHRG_VOL4300MV		(0x04 << 4)
91*4882a593Smuzhiyun #define CHRG_VOL4350MV		(0x05 << 4)
92*4882a593Smuzhiyun 
93*4882a593Smuzhiyun /*CHRG_CUR_SEL*/
94*4882a593Smuzhiyun #define CHRG_CUR1000MA		(0x00)
95*4882a593Smuzhiyun #define CHRG_CUR1200MA		(0x01)
96*4882a593Smuzhiyun #define CHRG_CUR1400MA		(0x02)
97*4882a593Smuzhiyun #define CHRG_CUR1600MA		(0x03)
98*4882a593Smuzhiyun #define CHRG_CUR1800MA		(0x04)
99*4882a593Smuzhiyun #define CHRG_CUR2000MA		(0x05)
100*4882a593Smuzhiyun #define CHRG_CUR2200MA		(0x06)
101*4882a593Smuzhiyun #define CHRG_CUR2400MA		(0x07)
102*4882a593Smuzhiyun #define CHRG_CUR2600MA		(0x08)
103*4882a593Smuzhiyun #define CHRG_CUR2800MA		(0x09)
104*4882a593Smuzhiyun #define CHRG_CUR3000MA		(0x0A)
105*4882a593Smuzhiyun 
106*4882a593Smuzhiyun /*THREAML_REG*/
107*4882a593Smuzhiyun #define TEMP_85C		(0x00 << 2)
108*4882a593Smuzhiyun #define TEMP_95C		(0x01 << 2)
109*4882a593Smuzhiyun #define TEMP_105C		(0x02 << 2)
110*4882a593Smuzhiyun #define TEMP_115C		(0x03 << 2)
111*4882a593Smuzhiyun 
112*4882a593Smuzhiyun /*CHRG_CTRL_REG2*/
113*4882a593Smuzhiyun #define CHG_CCCV_4HOUR		(0x00)
114*4882a593Smuzhiyun #define CHG_CCCV_5HOUR		(0x01)
115*4882a593Smuzhiyun #define CHG_CCCV_6HOUR		(0x02)
116*4882a593Smuzhiyun #define CHG_CCCV_8HOUR		(0x03)
117*4882a593Smuzhiyun #define CHG_CCCV_10HOUR		(0x04)
118*4882a593Smuzhiyun #define CHG_CCCV_12HOUR		(0x05)
119*4882a593Smuzhiyun #define CHG_CCCV_14HOUR		(0x06)
120*4882a593Smuzhiyun #define CHG_CCCV_16HOUR		(0x07)
121*4882a593Smuzhiyun #define FINISH_100MA		(0x00 << 6)
122*4882a593Smuzhiyun #define FINISH_150MA		(0x01 << 6)
123*4882a593Smuzhiyun #define FINISH_200MA		(0x02 << 6)
124*4882a593Smuzhiyun #define FINISH_250MA		(0x03 << 6)
125*4882a593Smuzhiyun 
126*4882a593Smuzhiyun /*CHRG_CTRL_REG3*/
127*4882a593Smuzhiyun #define CHRG_TERM_ANA_SIGNAL	(0 << 5)
128*4882a593Smuzhiyun #define CHRG_TERM_DIG_SIGNAL	(1 << 5)
129*4882a593Smuzhiyun #define CHRG_TIMER_CCCV_EN	(1 << 2)
130*4882a593Smuzhiyun #define CHRG_EN			(1 << 7)
131*4882a593Smuzhiyun 
132*4882a593Smuzhiyun #define BOOST_OTG_MASK		((0x3 << 5) | (0x3 << 1))
133*4882a593Smuzhiyun #define BOOST_OTG_ON		((0x3 << 5) | (0x3 << 1))
134*4882a593Smuzhiyun #define BOOST_OTG_OFF		((0x3 << 5) | (0x0 << 1))
135*4882a593Smuzhiyun #define BOOST_OFF_OTG_ON	((0x3 << 5) | (0x2 << 1))
136*4882a593Smuzhiyun 
137*4882a593Smuzhiyun #define OTG_BOOST_SLP_ON	(0x3 << 5)
138*4882a593Smuzhiyun 
139*4882a593Smuzhiyun /* MISC_MARK_REG */
140*4882a593Smuzhiyun #define FG_INIT			BIT(3)
141*4882a593Smuzhiyun #define FG_RESET_LATE		BIT(1)
142*4882a593Smuzhiyun #define FG_RESET_NOW		BIT(0)
143*4882a593Smuzhiyun #define ALGO_REST_MODE_MSK	(0xc0)
144*4882a593Smuzhiyun #define ALGO_REST_MODE_SHIFT	6
145*4882a593Smuzhiyun 
146*4882a593Smuzhiyun #define FB_TEMP_SHIFT		2
147*4882a593Smuzhiyun #define CHRG_VOL_SEL_SHIFT	4
148*4882a593Smuzhiyun #define CHRG_CRU_INPUT_SHIFT	0
149*4882a593Smuzhiyun #define CHRG_CRU_SEL_SHIFT	0
150*4882a593Smuzhiyun #define CHRG_CCCV_HOUR_SHIFT	0
151*4882a593Smuzhiyun #define	OCV_CALIB_SHIFT		(1 << 1)
152*4882a593Smuzhiyun #define PLUG_IN_STS		(1 << 6)
153*4882a593Smuzhiyun 
154*4882a593Smuzhiyun #define DRIVER_VERSION		"1.2"
155*4882a593Smuzhiyun #define TIMER_MS_COUNTS		1000
156*4882a593Smuzhiyun #define MAX_PERCENTAGE		100
157*4882a593Smuzhiyun #define MAX_INT			0x7FFF
158*4882a593Smuzhiyun #define MAX_INTERPOLATE		1000
159*4882a593Smuzhiyun 
160*4882a593Smuzhiyun struct temp_chrg_table {
161*4882a593Smuzhiyun 	int temp_down;
162*4882a593Smuzhiyun 	int temp_up;
163*4882a593Smuzhiyun 	u32 chrg_current;
164*4882a593Smuzhiyun 	u8 set_chrg_current;
165*4882a593Smuzhiyun };
166*4882a593Smuzhiyun 
167*4882a593Smuzhiyun struct battery_platform_data {
168*4882a593Smuzhiyun 	u32 *ocv_table;
169*4882a593Smuzhiyun 	u32 *zero_table;
170*4882a593Smuzhiyun 	struct temp_chrg_table *tc_table;
171*4882a593Smuzhiyun 	u32 tc_count;
172*4882a593Smuzhiyun 
173*4882a593Smuzhiyun 	u32 table_t[4][21];
174*4882a593Smuzhiyun 	int temp_t[4];
175*4882a593Smuzhiyun 	u32 temp_t_num;
176*4882a593Smuzhiyun 
177*4882a593Smuzhiyun 	u32 *ntc_table;
178*4882a593Smuzhiyun 	u32 ocv_size;
179*4882a593Smuzhiyun 	u32 ntc_size;
180*4882a593Smuzhiyun 	int ntc_degree_from;
181*4882a593Smuzhiyun 	u32 ntc_factor;
182*4882a593Smuzhiyun 	u32 max_input_current;
183*4882a593Smuzhiyun 	u32 max_chrg_current;
184*4882a593Smuzhiyun 	u32 max_chrg_voltage;
185*4882a593Smuzhiyun 	u32 pwroff_vol;
186*4882a593Smuzhiyun 	u32 monitor_sec;
187*4882a593Smuzhiyun 	u32 zero_algorithm_vol;
188*4882a593Smuzhiyun 	u32 zero_reserve_dsoc;
189*4882a593Smuzhiyun 	u32 bat_res;
190*4882a593Smuzhiyun 	u32 design_capacity;
191*4882a593Smuzhiyun 	u32 design_qmax;
192*4882a593Smuzhiyun 	u32 sleep_enter_current;
193*4882a593Smuzhiyun 	u32 sleep_exit_current;
194*4882a593Smuzhiyun 	u32 sleep_filter_current;
195*4882a593Smuzhiyun 	u32 power_dc2otg;
196*4882a593Smuzhiyun 	u32 max_soc_offset;
197*4882a593Smuzhiyun 	u32 bat_mode;
198*4882a593Smuzhiyun 	u32 fb_temp;
199*4882a593Smuzhiyun 	u32 energy_mode;
200*4882a593Smuzhiyun 	u32 cccv_hour;
201*4882a593Smuzhiyun 	u32 dc_det_adc;
202*4882a593Smuzhiyun 	int dc_det_pin;
203*4882a593Smuzhiyun 	u8  dc_det_level;
204*4882a593Smuzhiyun 	int otg5v_suspend_enable;
205*4882a593Smuzhiyun 	u32 sample_res;
206*4882a593Smuzhiyun 	bool extcon;
207*4882a593Smuzhiyun };
208*4882a593Smuzhiyun 
209*4882a593Smuzhiyun enum work_mode {
210*4882a593Smuzhiyun 	MODE_ZERO = 0,
211*4882a593Smuzhiyun 	MODE_FINISH,
212*4882a593Smuzhiyun 	MODE_SMOOTH_CHRG,
213*4882a593Smuzhiyun 	MODE_SMOOTH_DISCHRG,
214*4882a593Smuzhiyun 	MODE_SMOOTH,
215*4882a593Smuzhiyun };
216*4882a593Smuzhiyun 
217*4882a593Smuzhiyun enum bat_mode {
218*4882a593Smuzhiyun 	MODE_BATTARY = 0,
219*4882a593Smuzhiyun 	MODE_VIRTUAL,
220*4882a593Smuzhiyun };
221*4882a593Smuzhiyun 
222*4882a593Smuzhiyun enum charger_t {
223*4882a593Smuzhiyun 	USB_TYPE_UNKNOWN_CHARGER,
224*4882a593Smuzhiyun 	USB_TYPE_NONE_CHARGER,
225*4882a593Smuzhiyun 	USB_TYPE_USB_CHARGER,
226*4882a593Smuzhiyun 	USB_TYPE_AC_CHARGER,
227*4882a593Smuzhiyun 	USB_TYPE_CDP_CHARGER,
228*4882a593Smuzhiyun 	DC_TYPE_DC_CHARGER,
229*4882a593Smuzhiyun 	DC_TYPE_NONE_CHARGER,
230*4882a593Smuzhiyun };
231*4882a593Smuzhiyun 
232*4882a593Smuzhiyun enum charger_state {
233*4882a593Smuzhiyun 	OFFLINE = 0,
234*4882a593Smuzhiyun 	ONLINE
235*4882a593Smuzhiyun };
236*4882a593Smuzhiyun 
237*4882a593Smuzhiyun static const u16 FEED_BACK_TEMP[] = {
238*4882a593Smuzhiyun 	85, 95, 105, 115
239*4882a593Smuzhiyun };
240*4882a593Smuzhiyun 
241*4882a593Smuzhiyun static const u16 CHRG_VOL_SEL[] = {
242*4882a593Smuzhiyun 	4050, 4100, 4150, 4200, 4250, 4300, 4350
243*4882a593Smuzhiyun };
244*4882a593Smuzhiyun 
245*4882a593Smuzhiyun /*
246*4882a593Smuzhiyun  * If sample resistor changes, we need caculate a new CHRG_CUR_SEL[] table.
247*4882a593Smuzhiyun  *
248*4882a593Smuzhiyun  * Calculation method:
249*4882a593Smuzhiyun  * 1. find 20mR(default) current charge table, that is:
250*4882a593Smuzhiyun  *	20mR: [1000, 1200, 1400, 1600, 1800, 2000, 2250, 2400]
251*4882a593Smuzhiyun  *
252*4882a593Smuzhiyun  * 2. caculate Rfac(not care much, just using it) by sample resistor(ie. Rsam);
253*4882a593Smuzhiyun  *	Rsam = 20mR: Rfac = 10;
254*4882a593Smuzhiyun  *	Rsam > 20mR: Rfac = Rsam * 10 / 20;
255*4882a593Smuzhiyun  *	Rsam < 20mR: Rfac = 20 * 10 / Rsam;
256*4882a593Smuzhiyun  *
257*4882a593Smuzhiyun  * 3. from step2, we get Rfac, then we can get new charge current table by 20mR
258*4882a593Smuzhiyun  *    charge table:
259*4882a593Smuzhiyun  *	Iorg: member from 20mR charge table; Inew: new member for charge table.
260*4882a593Smuzhiyun  *
261*4882a593Smuzhiyun  *	Rsam > 20mR: Inew = Iorg * 10 / Rfac;
262*4882a593Smuzhiyun  *	Rsam < 20mR: Inew = Iorg * Rfac / 10;
263*4882a593Smuzhiyun  *
264*4882a593Smuzhiyun  * Notice: Inew should round up if it is not a integer!!!
265*4882a593Smuzhiyun  *
266*4882a593Smuzhiyun  * Example:
267*4882a593Smuzhiyun  *	10mR: [2000, 2400, 2800, 3200, 3600, 4000, 4500, 4800]
268*4882a593Smuzhiyun  *	20mR: [1000, 1200, 1400, 1600, 1800, 2000, 2250, 2400]
269*4882a593Smuzhiyun  *	40mR: [500,  600,  700,  800,  900,  1000, 1125, 1200]
270*4882a593Smuzhiyun  *	50mR: [400,  480,  560,  640,  720,  800,  900,  960]
271*4882a593Smuzhiyun  *	60mR: [334,  400,  467,  534,  600,  667,  750,  800]
272*4882a593Smuzhiyun  *
273*4882a593Smuzhiyun  * You should add property 'sample_res = <Rsam>' at battery node.
274*4882a593Smuzhiyun  */
275*4882a593Smuzhiyun 
276*4882a593Smuzhiyun static const u16 CHRG_CUR_SEL[] = {
277*4882a593Smuzhiyun 	1000, 1200, 1400, 1600, 1800, 2000, 2250, 2400
278*4882a593Smuzhiyun };
279*4882a593Smuzhiyun 
280*4882a593Smuzhiyun static const u16 CHRG_CUR_INPUT[] = {
281*4882a593Smuzhiyun 	450, 80, 850, 1000, 1250, 1500, 1750, 2000
282*4882a593Smuzhiyun };
283*4882a593Smuzhiyun 
284*4882a593Smuzhiyun void kernel_power_off(void);
285*4882a593Smuzhiyun 
286*4882a593Smuzhiyun #endif
287